mirror of
https://github.com/krgamestudios/Toy.git
synced 2026-04-15 14:54:07 +10:00
pre-computed identifer hashes
This commit is contained in:
@@ -32,9 +32,9 @@ void initInterpreter(Interpreter* interpreter, unsigned char* bytecode, int leng
|
||||
}
|
||||
|
||||
void freeInterpreter(Interpreter* interpreter) {
|
||||
FREE_ARRAY(char, interpreter->bytecode, interpreter->length);
|
||||
freeLiteralArray(&interpreter->literalCache);
|
||||
interpreter->scope = popScope(interpreter->scope);
|
||||
FREE_ARRAY(char, interpreter->bytecode, interpreter->length);
|
||||
freeLiteralArray(&interpreter->stack);
|
||||
}
|
||||
|
||||
|
||||
@@ -10,12 +10,18 @@ typedef void (*PrintFn)(const char*);
|
||||
|
||||
//the interpreter acts depending on the bytecode instructions
|
||||
typedef struct Interpreter {
|
||||
LiteralArray literalCache; //generally doesn't change after initialization
|
||||
Scope* scope;
|
||||
//input
|
||||
unsigned char* bytecode;
|
||||
int length;
|
||||
int count;
|
||||
LiteralArray literalCache; //read-only - built from the bytecode
|
||||
|
||||
//operation
|
||||
Scope* scope;
|
||||
LiteralArray stack;
|
||||
|
||||
//output
|
||||
// LiteralDictionary exports; //read-write - interface with Toy from C
|
||||
PrintFn printOutput;
|
||||
PrintFn assertOutput;
|
||||
} Interpreter;
|
||||
|
||||
@@ -32,6 +32,25 @@ static void printToBuffer(const char* str) {
|
||||
globalPrintCount += strlen(str);
|
||||
}
|
||||
|
||||
//hash util functions
|
||||
static unsigned int hashString(const char* string, int length) {
|
||||
unsigned int hash = 2166136261u;
|
||||
|
||||
for (int i = 0; i < length; i++) {
|
||||
hash *= string[i];
|
||||
hash *= 16777619;
|
||||
}
|
||||
|
||||
return hash;
|
||||
}
|
||||
|
||||
static unsigned int hash(unsigned int x) {
|
||||
x = ((x >> 16) ^ x) * 0x45d9f3b;
|
||||
x = ((x >> 16) ^ x) * 0x45d9f3b;
|
||||
x = (x >> 16) ^ x;
|
||||
return x;
|
||||
}
|
||||
|
||||
//exposed functions
|
||||
void printLiteral(Literal literal) {
|
||||
printLiteralCustom(literal, stdoutWrapper);
|
||||
@@ -194,7 +213,7 @@ Literal _toStringLiteral(char* str) {
|
||||
}
|
||||
|
||||
Literal _toIdentifierLiteral(char* str) {
|
||||
return ((Literal){LITERAL_IDENTIFIER,{.identifier.ptr = (char*)str,.identifier.length = strlen((char*)str)}});
|
||||
return ((Literal){LITERAL_IDENTIFIER,{.identifier.ptr = (char*)str,.identifier.length = strlen((char*)str), .identifier.hash=hashString(str, strlen((char*)str))}});
|
||||
}
|
||||
|
||||
char* copyString(char* original, int length) {
|
||||
@@ -238,7 +257,7 @@ bool literalsAreEqual(Literal lhs, Literal rhs) {
|
||||
//TODO: literal array and literal dictionary equality checks
|
||||
|
||||
case LITERAL_IDENTIFIER:
|
||||
if (STRLEN_I(lhs) != STRLEN_I(rhs)) {
|
||||
if (HASH_I(lhs) != HASH_I(rhs) && STRLEN_I(lhs) != STRLEN_I(rhs)) {
|
||||
return false;
|
||||
}
|
||||
return !strncmp(AS_IDENTIFIER(lhs), AS_IDENTIFIER(rhs), STRLEN_I(lhs));
|
||||
@@ -250,25 +269,6 @@ bool literalsAreEqual(Literal lhs, Literal rhs) {
|
||||
}
|
||||
}
|
||||
|
||||
//hash functions
|
||||
static unsigned int hashString(const char* string, int length) {
|
||||
unsigned int hash = 2166136261u;
|
||||
|
||||
for (int i = 0; i < length; i++) {
|
||||
hash *= string[i];
|
||||
hash *= 16777619;
|
||||
}
|
||||
|
||||
return hash;
|
||||
}
|
||||
|
||||
static unsigned int hash(unsigned int x) {
|
||||
x = ((x >> 16) ^ x) * 0x45d9f3b;
|
||||
x = ((x >> 16) ^ x) * 0x45d9f3b;
|
||||
x = (x >> 16) ^ x;
|
||||
return x;
|
||||
}
|
||||
|
||||
int hashLiteral(Literal lit) {
|
||||
switch(lit.type) {
|
||||
case LITERAL_NULL:
|
||||
@@ -306,7 +306,7 @@ int hashLiteral(Literal lit) {
|
||||
}
|
||||
|
||||
case LITERAL_IDENTIFIER:
|
||||
return hashString(AS_IDENTIFIER(lit), STRLEN_I(lit));
|
||||
return HASH_I(lit); //pre-computed
|
||||
|
||||
default:
|
||||
//should never bee seen
|
||||
|
||||
@@ -36,6 +36,7 @@ typedef struct {
|
||||
struct { //for variable names
|
||||
char* ptr;
|
||||
int length;
|
||||
int hash;
|
||||
} identifier;
|
||||
|
||||
//TODO: type
|
||||
@@ -99,7 +100,7 @@ void freeLiteral(Literal literal);
|
||||
|
||||
#define STRLEN(lit) ((lit).as.string.length)
|
||||
#define STRLEN_I(lit) ((lit).as.identifier.length)
|
||||
#define TYPES(lit) ((lit).as.identifier.types)
|
||||
#define HASH_I(lit) ((lit).as.identifier.hash)
|
||||
|
||||
//BUGFIX: macros are not functions
|
||||
bool _isTruthy(Literal x);
|
||||
|
||||
@@ -476,7 +476,7 @@ ParseRule* getRule(TokenType type) {
|
||||
return &parseRules[type];
|
||||
}
|
||||
|
||||
//static analasys
|
||||
//constant folding
|
||||
static bool calcStaticBinaryArithmetic(Node** nodeHandle) {
|
||||
switch((*nodeHandle)->binary.opcode) {
|
||||
case OP_ADDITION:
|
||||
|
||||
Reference in New Issue
Block a user