I am currently working on a c++ compiler for my Logisim CPU in JS, and have now a problem with variables:
I have defined a space in ram to store data/values, and I have defined a space to store addresses to the data space. I have a register nx with a pointer to the last variable, and a register mx with a pointer to the last “data-storage” RAM. But I do not know how to access them, e.g. here:
modified C++ Code:
int *pointer_test;
int test;
test = 123;
pointer_test = &test;
*pointer_test = 25;
Pre-Assembler:
//Allocate new variable <--- int *pointer_test;
add nx, 1
//Set the pointer pointing to zero
sram nx, 0
//Allocate another variable <--- int test;
add nx, 1
//Allocate new storage for the variable
add mx, 1
//Let the variable point to the data <--- test = 123;
sram nx, mx
sram mx, 123
How do I implement now:
pointer_test = &test;
I have only the value of &test, saved in nx because it is the last variable declared, but not the address of the variable/pointer “pointer_test” …
You probably want to write stack based assembly, like every other C compiler in the last 20 years. What that means is that there is a data area in RAM called the stack, which is a FIFO queue, that grows down. Stacks also always involve at least one register: the stack pointer. The stack pointer points at the current place in the stack where the next thing will go. So, to add something to the stack, you put it where the stack pointer points, and then subtract the size of that thing from the stack pointer.
Another register that is used most often in assembly that comes from C is the base pointer. The base pointer points at the beginning of the current frame. A frame can be roughly compared to a scope in C. So, if I have this code:
And a stack that’s top is at 0x9999, then
awill be at 0x9995 (assuming 4 byte int), with the stack pointer now pointing at 0x9991, and the base pointer still at 0x9999. When the new scope is entered, the base pointer is moved to the stack pointer, and then B is put at 0x9991. Then, when the scope is exited, the stack pointer is set to the base pointer, effectively erasing the variables in the lower scope.I’ve never heard of the architecture you’re programing for, but just know that any two registers will do, but some architectures, like x86, have specific stak registers (
ebp,espon 32 bit andrebandrspon 64 bit).But to answer the question a little more, it is the compiler’s job to know what offset into the stack each variable is, so it can do things like (pseudocode):