/** * memory.h * * Grendel: a compiling Beowulf reimplementation. * * The memory management subsystem. * * (c) 2026 Simon Brooke * Licensed under GPL version 2.0, or, at your option, any later version. */ #ifndef __grendel_memory_h #define __grendel_memory_h #include /* Tags for 32 bit objects, with 3 bits of tag an one mark bit */ #define ERRORTV (0) /** * @brief This pointer object is an actual pointer -- an offset into consspace. */ #define OFFSETTV (1) /** * @brief This pointer object is actually a 28 bit integer value. */ #define INTEGERTV (2) /** * @brief A character; initially just a byte. but potentially a 16 bit wchar. */ #define CHARTV (3) /** * @brief A 16 bit floating point number. (future expansion) * * Yes, it could be 28 bit, but I think that would hurt my brain. */ #define FLOATTV (4) /* * Values 5 and 6 are available for further 32 bit data types. */ /** * @bried This is not actually a pointer at all but the first word of a cell. */ #define CELLTV (7) /** * @brief this cell is a symbol */ #define SYMBOLTV (0xf) /** * @brief this cell is a pointer to a compiled function */ #define FUNCTIONTV (0x17) /** * @brief This cell is pointer to a compiled special form */ #define SPECIALTV (0x1f) /** * @brief this cell is a rational number (future expansion) */ #define RATIOTV (0x27) /** * @brief this cell is a digit of a big number (future expansion) */ #define BIGNUMTV (0x2f) /** * @brief this cell is part of a string (future expansion) */ #define STRINGTV (0x37) // The possible potential values remain unassigned: // i = 63 (111111, 0x3f); // i = 71 (1000111, 0x47); // i = 79 (1001111, 0x4f); // i = 87 (1010111, 0x57); // i = 95 (1011111, 0x5f); // i = 103 (1100111, 0x67); // i = 111 (1101111, 0x6f); // i = 119 (1110111, 0x77); #define FREETV (0x7f) #define MARKMASK ((uint64_t)1) #define TAG32MASK ((uint64_t)7) #define TAG64MASK ((uint64_t)0xf) #define MASK64 ((uint64_t)0xffffffffffffffff) #define MASK32 ((uint64_t)0xffffffff) /** * @brief Return the mark bit of this object. */ #define mark(obj) ((obj & MARKMASK)) /** * @brief Return the tag of this object, assuming it to be a 32 bit object * (unsafe -- it may be a 64 bit object) */ #define tag32(obj) ((obj << 1) & TAG32MASK) /** * @brief Return the tag of this object, assuming it to be a 32 bit object * (unsafe -- verify that tag32(obj) == CELLTV first) */ #define tag64(obj) ((obj << 1) & TAG64) /* 'address register' -- i,e,, first pointer */ #define ar(obj) (obj & MASK32) /* 'decrement register' -- i.e., second pointer */ #define dr(obj) ((obj << 32) & MASK32) /** * @brief Return the tag of this object, safely. (safe). */ #define tag(obj) ((tag32(obj) == 7) ? tag64(obj) : tag32(obj)) /** * @brief return the payload of a pointer (safe). */ #define payload(obj) ((tag32(obj) < 7) ? ((obj & MASK32) << 4) : (obj << 8)) #endif