//--- // fxos.semantics: Analyzed data types and locations (OS semantics) //--- #ifndef LIBFXOS_SEMANTICS_H #define LIBFXOS_SEMANTICS_H #include #include #include namespace FxOS { //--- // Data type representation // // The abstract interpreter supports the following data types when analyzing // data movement and access: // Integers i8 u8 i16 u16 i32 u32 (regs, mem) // Bit fields over ints T { } (mem) //--- struct DataType { enum DataKind { /* Base types */ Integral, /* Bit fields over integers */ BitField, /* Structures (can only reside in memory) */ Struct, /* Arrays (can only reside in memory) */ Array, }; /* Type kind */ DataKind kind; /* Type size in bytes, as would be returned by sizeof(). Must be 1, 2 or 4 for integral types and bit fields. Might be 0 for arrays if the size of the array is unknown */ uint16_t size; /* Type alignment, can only be 1, 2 or 4 */ uint16_t align; /* Type of fields in bit fields */ using Field = std::pair; union { /* For integer types of size 1, whether to display as char (might be extended to more attributes later) */ bool ischar; /* For array types, number of elements (0 if unknown or variable-size NUL-terminated strings) */ int elements; }; /* The following members are not in the union because they have non- trivial destructors/copy and I don't want to care. */ /* For array */ std::shared_ptr arraytype; /* For bit field types */ std::vector fields; /* For struct types */ std::vector attributes; }; //--- // Data values // // These objects are instances of the types described by DataType. //--- struct DataValue { /* Default constructor, gives undetermined values */ DataValue(); /* Data type affected to the value */ DataType const *type; /* Whether the value can be determined. If this boolean is false, the rest of the data must be ignored. */ bool determined; union { /* Unsigned integer (all sizes) and bit fields */ uint32_t uinteger; /* Signed integer (all sizes) */ int32_t integer; }; /* For arrays (homogeneous) and structures (heterogeneous) */ std::vector entries; /* Perform a read operation at the specified offset from the start of the object. */ uint32_t read(int offset, int size); /* Perform a write operation at the specified offset from the start of the object. */ void write(int offset, int size, uint32_t contents); }; //--- // Location representation // // The abstract interpreter keeps track of data stored at registers, memory // addresses and mapped modules as long as the exact location fits within the // expressive power of a RelConst. //--- using Location = RelConst; } /* namespace FxOS */ #endif /* LIBFXOS_SEMANTICS_H */