Skip to content

Commit

Permalink
Complete implementations of constant instructions
Browse files Browse the repository at this point in the history
  • Loading branch information
fernandezseb committed Dec 14, 2023
1 parent dd5a615 commit 8892ada
Show file tree
Hide file tree
Showing 6 changed files with 141 additions and 31 deletions.
2 changes: 2 additions & 0 deletions src/Core.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,10 +27,12 @@
#define u1 uint8_t
#define u2 uint16_t
#define u4 uint32_t
#define u8 uint64_t

#define i1 int8_t
#define i2 int16_t
#define i4 int32_t
#define i8 int64_t

// Memory sizes
#define KIB(x) ((size_t) (x) << 10)
Expand Down
3 changes: 2 additions & 1 deletion src/Data/Variable.h
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,8 @@ enum VariableType
VariableType_BYTE,
VariableType_INT,
VariableType_FLOAT,
VariableType_LONG
VariableType_LONG,
VariableType_DOUBLE
};

enum ArrayType : char {
Expand Down
105 changes: 105 additions & 0 deletions src/VM/ConstantInstructions.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,10 @@
#include "Data/Variable.h"
#include "VM.h"

void nop(uint8_t* args, uint16_t argsCount, int8_t arg, JavaHeap* heap, VMThread* thread)
{
}

void aconst_null(uint8_t* args, uint16_t argsCount, i1 arg, JavaHeap* heap, VMThread* thread)
{
Variable reference = {};
Expand Down Expand Up @@ -40,3 +44,104 @@ void fconst_i(uint8_t* args, uint16_t argsCount, int8_t arg, JavaHeap* heap, VMT
variable.data = (casted);
thread->currentFrame->operands.push_back(variable);
}

void dconst_i(uint8_t* args, uint16_t argsCount, int8_t arg, JavaHeap* heap, VMThread* thread)
{
double d = arg;
u4 lowBytes = *((u8*)(&d));
u4 highBytes = (*((u8*)(&(d))) >> 32);

uint64_t bytes = ((uint64_t)highBytes << 32) + (uint64_t)lowBytes;
// The value is double back = *reinterpret_cast<double*> (&bytes);
Variable variableHigh = {};
variableHigh.type = VariableType_LONG;
variableHigh.data = highBytes;
Variable variableLow = {};
variableLow.type = VariableType_LONG;
variableLow.data = lowBytes;
thread->currentFrame->operands.push_back(variableHigh);
thread->currentFrame->operands.push_back(variableLow);
}

void bipush(uint8_t* args, uint16_t argsCount, int8_t arg, JavaHeap* heap, VMThread* thread)
{
uint8_t byte = args[0];
Variable variable = {};
variable.type = VariableType_INT;
variable.data = byte;
thread->currentFrame->operands.push_back(variable);
}

void sipush(uint8_t* args, uint16_t argsCount, int8_t arg, JavaHeap* heap, VMThread* thread)
{
i2 shortValue = (args[0] << 8) | args[1];
i4 intValue = shortValue;
Variable variable = {};
variable.type = VariableType_INT;
variable.data = intValue;
thread->currentFrame->operands.push_back(variable);
}

void loadConstant(VMThread* thread, u4 index)
{
ConstantPoolItem* cpItem = thread->currentFrame->constantPool->constants[index-1];
if (cpItem->getType() == CT_INTEGER)
{
CPIntegerInfo* integerInfo = (CPIntegerInfo*) cpItem;
Variable var = {};
var.type = VariableType_INT;
var.data = integerInfo->bytes;
thread->currentFrame->operands.push_back(var);
} else
{
fprintf(stderr, "Error: LDC not implemented yet for type: %d\n", cpItem->getType());
Platform::exitProgram(-32);
}
}

void loadConstant2(VMThread* thread, u4 index)
{
ConstantPoolItem* cpItem = thread->currentFrame->constantPool->constants[index-1];
if (cpItem->getType() == CT_LONG)
{
CPLongInfo* integerInfo = (CPLongInfo*) cpItem;
Variable highVar = {};
highVar.type = VariableType_LONG;
highVar.data = integerInfo->highBytes;
thread->currentFrame->operands.push_back(highVar);
Variable lowVar = {};
lowVar.type = VariableType_LONG;
lowVar.data = integerInfo->lowBytes;
thread->currentFrame->operands.push_back(lowVar);
}
else if (cpItem->getType() == CT_DOUBLE)
{
CPDoubleInfo* integerInfo = (CPDoubleInfo*) cpItem;
Variable highVar = {};
highVar.type = VariableType_DOUBLE;
highVar.data = integerInfo->highBytes;
thread->currentFrame->operands.push_back(highVar);
Variable lowVar = {};
lowVar.type = VariableType_DOUBLE;
lowVar.data = integerInfo->lowBytes;
thread->currentFrame->operands.push_back(lowVar);
}
}

void ldc(uint8_t* args, uint16_t argsCount, int8_t arg, JavaHeap* heap, VMThread* thread)
{
u1 index = args[0];
loadConstant(thread, index);
}

void ldc_w(uint8_t* args, uint16_t argsCount, int8_t arg, JavaHeap* heap, VMThread* thread)
{
u2 index = (args[0] << 8) | args[1];
loadConstant(thread, index);
}

void ldc2_w(uint8_t* args, uint16_t argsCount, int8_t arg, JavaHeap* heap, VMThread* thread)
{
u2 index = (args[0] << 8) | args[1];
loadConstant2(thread, index);
}
8 changes: 7 additions & 1 deletion src/VM/ConstantInstructions.h
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,14 @@
class VMThread;
class JavaHeap;

void nop(u1* args, u2 argsCount, i1 arg, JavaHeap* heap, VMThread* thread);
void aconst_null(u1* args, u2 argsCount, i1 arg, JavaHeap* heap, VMThread* thread);
void iconst_i(u1* args, u2 argsCount, i1 arg, JavaHeap* heap, VMThread* thread);
void lconst_i(u1* args, u2 argsCount, i1 arg, JavaHeap* heap, VMThread* thread);
void fconst_i(u1* args, u2 argsCount, i1 arg, JavaHeap* heap, VMThread* thread);
// void dconst_i(u1* args, u2 argsCount, i1 arg, JavaHeap* heap, VMThread* thread);
void dconst_i(u1* args, u2 argsCount, i1 arg, JavaHeap* heap, VMThread* thread);
void bipush(u1* args, u2 argsCount, i1 arg, JavaHeap* heap, VMThread* thread);
void sipush(u1* args, u2 argsCount, i1 arg, JavaHeap* heap, VMThread* thread);
void ldc(u1* args, u2 argsCount, i1 arg, JavaHeap* heap, VMThread* thread);
void ldc_w(u1* args, u2 argsCount, i1 arg, JavaHeap* heap, VMThread* thread);
void ldc2_w(u1* args, u2 argsCount, i1 arg, JavaHeap* heap, VMThread* thread);
11 changes: 1 addition & 10 deletions src/VM/VM.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -186,20 +186,11 @@ void VM::executeLoop(VMThread* thread)
}
if (found)
{
break;
continue;
}

switch (opcode)
{
case 0x10: // bipush: push byte
{
uint8_t byte = code[thread->pc++];
Variable variable;
variable.type = VariableType_INT;
variable.data = byte;
topFrame->operands.push_back(variable);
break;
}
case 0x2a: // aload_0
{
// TODO: Check if it is OK type and such
Expand Down
43 changes: 24 additions & 19 deletions src/VM/VM.h
Original file line number Diff line number Diff line change
Expand Up @@ -77,26 +77,31 @@ struct Instruction

class VM {
private:
Instruction instructions[13] =
{
Instruction instructions[21] =
{
// Constants
{i_aconst_null, 0, "aconst_null", 0, aconst_null},
{i_iconst_m1, 0, "iconst_m1", -1, iconst_i},
{i_iconst_0, 0, "iconst_0", 0, iconst_i},
{i_iconst_1, 0, "iconst_1", 1, iconst_i},
{i_iconst_2, 0, "iconst_2", 2, iconst_i},
{i_iconst_3, 0, "iconst_3", 3, iconst_i},
{i_iconst_4, 0, "iconst_4", 4, iconst_i},
{i_iconst_5, 0, "iconst_5", 5, iconst_i},
{i_lconst_0, 0, "lconst_0", 0, lconst_i},
{i_lconst_1, 0, "lconst_1", 1, lconst_i},
{i_fconst_0, 0, "fconst_0", 0, fconst_i},
{i_fconst_1, 0, "fconst_1", 1, fconst_i},
{i_fconst_2, 0, "fconst_2", 2, fconst_i},
//dconst_0
//dconst_1

};
{i_nop, 0, "nop", 0, nop},
{i_aconst_null, 0, "aconst_null", 0, aconst_null},
{i_iconst_m1, 0, "iconst_m1", -1, iconst_i},
{i_iconst_0, 0, "iconst_0", 0, iconst_i},
{i_iconst_1, 0, "iconst_1", 1, iconst_i},
{i_iconst_2, 0, "iconst_2", 2, iconst_i},
{i_iconst_3, 0, "iconst_3", 3, iconst_i},
{i_iconst_4, 0, "iconst_4", 4, iconst_i},
{i_iconst_5, 0, "iconst_5", 5, iconst_i},
{i_lconst_0, 0, "lconst_0", 0, lconst_i},
{i_lconst_1, 0, "lconst_1", 1, lconst_i},
{i_fconst_0, 0, "fconst_0", 0, fconst_i},
{i_fconst_1, 0, "fconst_1", 1, fconst_i},
{i_fconst_2, 0, "fconst_2", 2, fconst_i},
{i_dconst_0, 0, "dconst_0", 0, dconst_i},
{i_dconst_1, 0, "dconst_1", 1, dconst_i},
{i_bipush, 1, "bipush", 0, bipush},
{i_sipush, 2, "sipush", 0, sipush},
{i_ldc, 1, "ldc", 0, ldc},
{i_ldc_w, 2, "ldc_w", 0, ldc_w},
{i_ldc2_w, 2, "ldc2_w", 0, ldc2_w},
};
ClassLoader bootstrapClassLoader;
JavaHeap heap;
VMThread thread;
Expand Down

0 comments on commit 8892ada

Please sign in to comment.