Browse Source

new compiler warnings and dirty fixes (wip)

Kajetan Johannes Hammerle 1 year ago
parent
commit
5b7815f533
25 changed files with 307 additions and 259 deletions
  1. 59 58
      Compiler.c
  2. 26 13
      DataType.c
  3. 10 8
      DataType.h
  4. 1 1
      Main.c
  5. 9 8
      Test.c
  6. 1 1
      Test.h
  7. 1 1
      libraries/Math.c
  8. 1 1
      libraries/Math.h
  9. 7 7
      libraries/Time.c
  10. 1 1
      libraries/Time.h
  11. 14 1
      meson.build
  12. 18 14
      tokenizer/FileTokens.c
  13. 1 1
      tokenizer/Token.c
  14. 32 29
      tokenizer/Tokenizer.c
  15. 3 3
      tokenizer/Tokenizer.h
  16. 16 15
      utils/ByteCodePrinter.c
  17. 7 6
      utils/Functions.c
  18. 6 5
      utils/Functions.h
  19. 3 2
      utils/Variables.c
  20. 1 0
      utils/Variables.h
  21. 7 7
      vm/Arrays.c
  22. 2 1
      vm/Arrays.h
  23. 7 7
      vm/ByteCode.c
  24. 1 1
      vm/ByteCode.h
  25. 73 68
      vm/Script.c

+ 59 - 58
Compiler.c

@@ -46,15 +46,16 @@ static int forWhileStack = 0;
 static int continueAt = 0;
 
 typedef struct {
+    const char* name;
     Operation intOp;
     Operation floatOp;
     Operation pointerOp;
-    const char* name;
+    char padding[sizeof(Operation)];
 } TypedOp;
 
 #define TYPE_OP(NAME, FLOAT, POINTER, text)                                    \
-    static const TypedOp TYPED_##NAME = {OP_##NAME##_INT, OP_##FLOAT,          \
-                                         OP_##POINTER, text};
+    static const TypedOp TYPED_##NAME = {                                      \
+        text, OP_##NAME##_INT, OP_##FLOAT, OP_##POINTER, {0}};
 TYPE_OP(MUL, MUL_FLOAT, NOTHING, "*")
 TYPE_OP(DIV, DIV_FLOAT, NOTHING, "/")
 TYPE_OP(MOD, NOTHING, NOTHING, "%")
@@ -96,7 +97,7 @@ static void cDeclared(const char* name) {
     cError("%s has already been declared", name);
 }
 
-static void cTooMuchArguments() {
+static void cTooMuchArguments(void) {
     cError("too much function arguments");
 }
 
@@ -111,8 +112,8 @@ static void cUnknownFunction(Function* f) {
     char buffer[BUFFER_SIZE] = {'\0'};
     for(int i = 0; i < f->arguments; i++) {
         const char* name = dtGetName(&structs, f->argumentTypes[i]);
-        max += snprintf(buffer + max, BUFFER_SIZE - max, i > 0 ? ", %s" : "%s",
-                        name);
+        max += snprintf(buffer + max, (size_t)(BUFFER_SIZE - max),
+                        i > 0 ? ", %s" : "%s", name);
     }
     cError("unknown function: %s(%s)", f->name, buffer);
 }
@@ -122,7 +123,7 @@ static void cAddOperation(Operation token) {
     bcAddBytes(code, &c, 1);
 }
 
-static int32 cReserveInt32() {
+static int32 cReserveInt32(void) {
     return bcReserveBytes(code, sizeof(int32));
 }
 
@@ -144,12 +145,12 @@ static void cAddByteOperation(Operation token, int8 i) {
     bcAddBytes(code, &i, sizeof(int8));
 }
 
-static void cAddLine(int16 line) {
+static void cAddLine(int16 l) {
     cAddOperation(OP_LINE);
-    bcAddBytes(code, &line, sizeof(int16));
+    bcAddBytes(code, &l, sizeof(int16));
 }
 
-static Token cReadTokenAndLine() {
+static Token cReadTokenAndLine(void) {
     hasReturn--;
     Token t;
     if(tReadTokenAndLine(&t, &line)) {
@@ -169,7 +170,7 @@ static bool cConsumeTokenIf(Token t) {
     return tPeekToken() == t && cReadTokenAndLine() == t;
 }
 
-static void cConstantInt32() {
+static void cConstantInt32(void) {
     int32 value;
     if(tReadInt32(&value)) {
         cError("int token without an int");
@@ -177,7 +178,7 @@ static void cConstantInt32() {
     cAddInt32Operation(OP_PUSH_INT, value);
 }
 
-static void cConstantFloat() {
+static void cConstantFloat(void) {
     float value;
     if(tReadFloat(&value)) {
         cError("float token without a float");
@@ -186,7 +187,7 @@ static void cConstantFloat() {
     bcAddBytes(code, &value, sizeof(float));
 }
 
-static const char* cReadString() {
+static const char* cReadString(void) {
     const char* literal = tReadString();
     if(literal == NULL) {
         cError("literal without string on line %d", line);
@@ -237,7 +238,7 @@ static DataType cReadExtendedType(Token t, bool force) {
     return dt;
 }
 
-static DataType cExpression();
+static DataType cExpression(void);
 
 static void cLoadRef(DataType type) {
     if(dtIsArray(type)) {
@@ -257,7 +258,7 @@ static DataType cUnpack(DataType dt) {
     return dt;
 }
 
-static DataType cUnpackedExpression() {
+static DataType cUnpackedExpression(void) {
     return cUnpack(cExpression());
 }
 
@@ -322,7 +323,7 @@ static void cStore(DataType left, DataType right, const char* name) {
     }
 }
 
-static DataType cLiteral() {
+static DataType cLiteral(void) {
     const char* literal = cReadString();
     if(cConsumeTokenIf(T_OPEN_BRACKET)) {
         return cCallFunction(literal);
@@ -347,7 +348,7 @@ static DataType cLiteral() {
     return dtVoid();
 }
 
-static DataType cText() {
+static DataType cText(void) {
     cAddOperation(OP_PUSH_TEXT);
     int32 lengthAddress = cReserveInt32();
     int32 length = 0;
@@ -360,19 +361,19 @@ static DataType cText() {
     return dtText();
 }
 
-static DataType cBracketPrimary() {
+static DataType cBracketPrimary(void) {
     DataType result = cExpression();
     cConsumeToken(T_CLOSE_BRACKET);
     return result;
 }
 
-static void cArrayIndex() {
+static void cArrayIndex(void) {
     if(!dtIsInt(cUnpackedExpression())) {
         cError("array index must be an int");
     }
 }
 
-static DataType cAllocArray() {
+static DataType cAllocArray(void) {
     DataType dt = cReadType(cReadTokenAndLine(), true);
     if(dt.array != 0) {
         cError("array type must not be an array");
@@ -384,7 +385,7 @@ static DataType cAllocArray() {
     return dtToArray(dt);
 }
 
-static DataType cLength() {
+static DataType cLength(void) {
     DataType array = cUnpackedExpression();
     if(!dtIsArray(array)) {
         cError("length expects an array");
@@ -393,7 +394,7 @@ static DataType cLength() {
     return dtInt();
 }
 
-static DataType cPrimary() {
+static DataType cPrimary(void) {
     Token t = cReadTokenAndLine();
     switch(t) {
         case T_INT_VALUE: cConstantInt32(); return dtInt();
@@ -420,7 +421,7 @@ static void cExpectType(DataType actual, DataType wanted, const char* name) {
 }
 
 static void cChangeType(DataType* dt, Operation op, Operation pushOp,
-                        int change) {
+                        int8 change) {
     if(onLine) {
         cAddByteOperation(op, change);
         *dt = dtVoid();
@@ -429,7 +430,7 @@ static void cChangeType(DataType* dt, Operation op, Operation pushOp,
     }
 }
 
-static void cPostChange(DataType* dt, int change, const char* name) {
+static void cPostChange(DataType* dt, int8 change, const char* name) {
     cRemoveReference(dt, name);
     if(dtIsInt(*dt)) {
         cChangeType(dt, OP_CHANGE_INT, OP_PUSH_POST_CHANGE_INT, change);
@@ -455,7 +456,7 @@ static DataType cStructAccess(DataType dt) {
     return dtToPointer(inner.type);
 }
 
-static DataType cAccess() {
+static DataType cAccess(void) {
     DataType dt = cPrimary();
     while(true) {
         if(cConsumeTokenIf(T_INCREMENT)) {
@@ -471,7 +472,7 @@ static DataType cAccess() {
             }
             cAddOperation(OP_LOAD_ARRAY);
             dtRemovePointer(&dt);
-            cArrayIndex("index");
+            cArrayIndex();
             cConsumeToken(T_CLOSE_SQUARE_BRACKET);
             cAddInt32Operation(OP_ADD_REFERENCE, cGetSize(dt));
             dt = dtToPointer(dtRemoveArray(dt));
@@ -481,7 +482,7 @@ static DataType cAccess() {
     }
 }
 
-static DataType cPreChange(DataType dt, int change, const char* name) {
+static DataType cPreChange(DataType dt, int8 change, const char* name) {
     cRemoveReference(&dt, name);
     if(dtIsInt(dt)) {
         cChangeType(&dt, OP_CHANGE_INT, OP_PUSH_PRE_CHANGE_INT, change);
@@ -526,7 +527,7 @@ static DataType cUnaryBitNot(DataType dt) {
     return dt;
 }
 
-static DataType cPreUnary() {
+static DataType cPreUnary(void) {
     int marker = tGetMarker();
     if(cConsumeTokenIf(T_OPEN_BRACKET)) {
         if(cConsumeTokenIf(T_FLOAT) && cConsumeTokenIf(T_CLOSE_BRACKET)) {
@@ -568,7 +569,7 @@ static void cAddTypeOperation(DataType* a, Parser bf, const TypedOp* op) {
     }
 }
 
-static DataType cMul() {
+static DataType cMul(void) {
     DataType a = cPreUnary();
     while(true) {
         if(cConsumeTokenIf(T_MUL)) {
@@ -583,7 +584,7 @@ static DataType cMul() {
     }
 }
 
-static DataType cAdd() {
+static DataType cAdd(void) {
     DataType a = cMul();
     while(true) {
         if(cConsumeTokenIf(T_ADD)) {
@@ -596,7 +597,7 @@ static DataType cAdd() {
     }
 }
 
-static DataType cShift() {
+static DataType cShift(void) {
     DataType a = cAdd();
     while(true) {
         if(cConsumeTokenIf(T_LEFT_SHIFT)) {
@@ -609,7 +610,7 @@ static DataType cShift() {
     }
 }
 
-static DataType cComparison() {
+static DataType cComparison(void) {
     DataType a = cShift();
     while(true) {
         if(cConsumeTokenIf(T_LESS)) {
@@ -630,7 +631,7 @@ static DataType cComparison() {
     }
 }
 
-static DataType cEqual() {
+static DataType cEqual(void) {
     DataType a = cComparison();
     while(true) {
         if(cConsumeTokenIf(T_EQUAL)) {
@@ -653,15 +654,15 @@ static DataType cRepeat(Token t, Parser f, const TypedOp* op) {
     return a;
 }
 
-static DataType cBitAnd() {
+static DataType cBitAnd(void) {
     return cRepeat(T_BIT_AND, cEqual, &TYPED_BIT_AND);
 }
 
-static DataType cBitXor() {
+static DataType cBitXor(void) {
     return cRepeat(T_BIT_XOR, cBitAnd, &TYPED_BIT_XOR);
 }
 
-static DataType cBitOr() {
+static DataType cBitOr(void) {
     return cRepeat(T_BIT_OR, cBitXor, &TYPED_BIT_OR);
 }
 
@@ -680,18 +681,18 @@ static DataType cLogical(Parser f, Token t, Operation jump, Operation op) {
     return a;
 }
 
-static DataType cAnd() {
+static DataType cAnd(void) {
     return cLogical(cBitOr, T_AND, OP_PEEK_FALSE_GOTO, OP_AND);
 }
 
-static DataType cExpression() {
+static DataType cExpression(void) {
     return cLogical(cAnd, T_OR, OP_PEEK_TRUE_GOTO, OP_OR);
 }
 
-static void cLine();
+static void cLine(void);
 
-static void cConsumeBody() {
-    int oldLine = line;
+static void cConsumeBody(void) {
+    int16 oldLine = line;
     while(!cConsumeTokenIf(T_CLOSE_CURVED_BRACKET)) {
         if(tPeekToken() == T_END) {
             line = oldLine;
@@ -701,7 +702,7 @@ static void cConsumeBody() {
     }
 }
 
-static void cConsumeScope() {
+static void cConsumeScope(void) {
     Scope scope;
     vsEnterScope(&vars, &scope);
     cConsumeBody();
@@ -716,7 +717,7 @@ static void cAddReturn(Operation op) {
     returns[returnIndex++] = cReserveInt32();
 }
 
-static void cReturn() {
+static void cReturn(void) {
     if(dtIsVoid(returnType)) {
         cConsumeToken(T_SEMICOLON);
         cAddReturn(OP_RETURN);
@@ -739,7 +740,7 @@ static void cReturn() {
     hasReturn = 2;
 }
 
-static void cIf() {
+static void cIf(void) {
     cConsumeToken(T_OPEN_BRACKET);
     cExpectType(cExpression(), dtInt(), "if");
     cConsumeToken(T_CLOSE_BRACKET);
@@ -769,7 +770,7 @@ static void cConsumeBreaks(int start, int address) {
     breakIndex = start;
 }
 
-static void cWhile() {
+static void cWhile(void) {
     int start = code->length;
     cConsumeToken(T_OPEN_BRACKET);
     cExpectType(cExpression(), dtInt(), "while");
@@ -796,7 +797,7 @@ static void cOperationSet(DataType left, const TypedOp* op) {
     cStore(left, left, "=");
 }
 
-static void cSetVariable() {
+static void cSetVariable(void) {
     onLine = true;
     DataType dt = cPreUnary();
     onLine = false;
@@ -846,7 +847,7 @@ static bool cDeclaration(Token t) {
     return true;
 }
 
-static void cLineExpression() {
+static void cLineExpression(void) {
     int marker = tGetMarker();
     Token t = cReadTokenAndLine();
     if(cDeclaration(t)) {
@@ -856,7 +857,7 @@ static void cLineExpression() {
     cSetVariable();
 }
 
-static void cFor() {
+static void cFor(void) {
     Scope scope;
     vsEnterScope(&vars, &scope);
 
@@ -890,7 +891,7 @@ static void cFor() {
     vsLeaveScope(&vars, &scope);
 }
 
-static void cBreak() {
+static void cBreak(void) {
     if(forWhileStack == 0) {
         cError("break without for or while");
     } else if(breakIndex >= BREAK_BUFFER) {
@@ -901,7 +902,7 @@ static void cBreak() {
     cConsumeToken(T_SEMICOLON);
 }
 
-static void cContinue() {
+static void cContinue(void) {
     if(forWhileStack == 0) {
         cError("continue without for or while");
     }
@@ -909,7 +910,7 @@ static void cContinue() {
     cConsumeToken(T_SEMICOLON);
 }
 
-static void cLine() {
+static void cLine(void) {
     int marker = tGetMarker();
     Token t = cReadTokenAndLine();
     cAddLine(line);
@@ -928,11 +929,11 @@ static void cLine() {
     }
 }
 
-static void cBuildFunction(Function* f, DataType rType, const char* name) {
+static void cBuildFunction(Function* f, DataType rType, const char* fName) {
     if(rType.type == DT_STRUCT && rType.array == 0) {
         cError("structs cannot be returned");
     }
-    fInit(f, name, line);
+    fInit(f, fName, line);
     f->returnType = rType;
     vsReset(&vars);
     cConsumeToken(T_OPEN_BRACKET);
@@ -1009,7 +1010,7 @@ static void cFunction(DataType rType, const char* name) {
     cSetInt32(end, code->length);
 }
 
-static void cStruct() {
+static void cStruct(void) {
     cConsumeToken(T_LITERAL);
     const char* name = cReadString();
     if(stsSearch(&structs, name) != NULL) {
@@ -1057,7 +1058,7 @@ static void cGlobalScope(Token t) {
     cConsumeToken(T_SEMICOLON);
 }
 
-static void cCallMain() {
+static void cCallMain(void) {
     Function f;
     fInit(&f, "main", line);
     Function* found = fsSearch(&functions, &f);
@@ -1068,7 +1069,7 @@ static void cCallMain() {
     }
 }
 
-static void cForEachLine() {
+static void cForEachLine(void) {
     cAddOperation(OP_GRESERVE);
     int p = cReserveInt32();
     while(true) {
@@ -1083,7 +1084,7 @@ static void cForEachLine() {
     cAddInt32Operation(OP_GRESERVE, -globalVars.maxAddress);
 }
 
-static void cLinkQueuedFunctions() {
+static void cLinkQueuedFunctions(void) {
     for(int i = 0; i < functionQueue.entries; i++) {
         Function* f = functionQueue.data + i;
         Function* found = fsSearch(&functions, f);
@@ -1095,7 +1096,7 @@ static void cLinkQueuedFunctions() {
     }
 }
 
-static void cAllocAndCompile() {
+static void cAllocAndCompile(void) {
     forWhileStack = 0;
     breakIndex = 0;
     returnType = dtVoid();

+ 26 - 13
DataType.c

@@ -29,7 +29,15 @@ const char* dtGetName(const Structs* sts, DataType dt) {
     switch(dt.type) {
         case DT_INT: dtAppend("int"); break;
         case DT_FLOAT: dtAppend("float"); break;
-        case DT_STRUCT: dtAppend(dtGetStruct(sts, dt)->name); break;
+        case DT_STRUCT: {
+            Struct* s = dtGetStruct(sts, dt);
+            if(s != NULL) {
+                dtAppend(s->name);
+            } else {
+                dtAppend("?-struct");
+            }
+            break;
+        }
         case DT_VOID: dtAppend("void"); break;
         default: dtAppend("unknown");
     }
@@ -52,6 +60,9 @@ int dtGetSize(DataType dt, const Structs* sts) {
         case DT_STRUCT: {
             int size = 0;
             Struct* st = dtGetStruct(sts, dt);
+            if(st == NULL) {
+                return 0;
+            }
             for(int i = 0; i < st->amount; i++) {
                 size += dtGetSize(st->vars[i].type, sts);
             }
@@ -61,17 +72,17 @@ int dtGetSize(DataType dt, const Structs* sts) {
     }
 }
 
-DataType dtInt() {
+DataType dtInt(void) {
     DataType dt = {DT_INT, 0, 0, 0};
     return dt;
 }
 
-DataType dtFloat() {
+DataType dtFloat(void) {
     DataType dt = {DT_FLOAT, 0, 0, 0};
     return dt;
 }
 
-DataType dtVoid() {
+DataType dtVoid(void) {
     DataType dt = {DT_VOID, 0, 0, 0};
     return dt;
 }
@@ -81,7 +92,7 @@ DataType dtStruct(const Struct* st) {
     return dt;
 }
 
-DataType dtText() {
+DataType dtText(void) {
     DataType dt = {DT_INT, 0, 1, 0};
     return dt;
 }
@@ -146,7 +157,8 @@ Struct* dtGetStruct(const Structs* sts, DataType dt) {
 void stAddVariable(Struct* st, const char* name, DataType type) {
     int index = st->amount;
     st->amount++;
-    st->vars = realloc(st->vars, sizeof(StructVariable) * st->amount);
+    st->vars = (StructVariable*)realloc(st->vars, sizeof(StructVariable) *
+                                                      (size_t)st->amount);
     st->vars[index].name = name;
     st->vars[index].type = type;
 }
@@ -154,7 +166,7 @@ void stAddVariable(Struct* st, const char* name, DataType type) {
 void stsInit(Structs* sts) {
     sts->capacity = 4;
     sts->entries = 0;
-    sts->data = malloc(sizeof(Struct) * sts->capacity);
+    sts->data = (Struct*)malloc(sizeof(Struct) * (size_t)sts->capacity);
 }
 
 void stsDelete(Structs* sts) {
@@ -186,27 +198,28 @@ Struct* stsSearch(Structs* sts, const char* name) {
 Struct* stsAdd(Structs* sts, const char* name) {
     if(sts->entries >= sts->capacity) {
         sts->capacity *= 2;
-        sts->data = realloc(sts->data, sizeof(Struct) * sts->capacity);
+        sts->data =
+            (Struct*)realloc(sts->data, sizeof(Struct) * (size_t)sts->capacity);
     }
-    int index = sts->entries++;
-    sts->data[index].id = index << 1;
+    uint16 index = (uint16)sts->entries++;
+    sts->data[index].id = (uint16)(index << 1);
     sts->data[index].amount = 0;
     sts->data[index].name = name;
     sts->data[index].vars = NULL;
     return sts->data + index;
 }
 
-void gstsInit() {
+void gstsInit(void) {
     stsInit(&globalStructs);
     useGlobals = true;
 }
 
-void gstsDelete() {
+void gstsDelete(void) {
     stsDelete(&globalStructs);
     useGlobals = false;
 }
 
-Structs* gstsGet() {
+Structs* gstsGet(void) {
     return &globalStructs;
 }
 

+ 10 - 8
DataType.h

@@ -39,11 +39,13 @@ typedef struct {
 typedef struct {
     const char* name;
     DataType type;
+    char padding[sizeof(const char*) - sizeof(DataType)];
 } StructVariable;
 
 typedef struct {
     const char* name;
-    int id;
+    uint16 id;
+    char padding[2];
     int amount;
     StructVariable* vars;
 } Struct;
@@ -56,11 +58,11 @@ typedef struct {
 
 int dtGetSize(DataType dt, const Structs* sts);
 
-DataType dtInt();
-DataType dtFloat();
-DataType dtVoid();
+DataType dtInt(void);
+DataType dtFloat(void);
+DataType dtVoid(void);
 DataType dtStruct(const Struct* st);
-DataType dtText();
+DataType dtText(void);
 
 DataType dtToArray(DataType dt);
 DataType dtRemoveArray(DataType dt);
@@ -84,9 +86,9 @@ void stsDelete(Structs* sts);
 Struct* stsSearch(Structs* sts, const char* name);
 Struct* stsAdd(Structs* sts, const char* name);
 
-void gstsInit();
-void gstsDelete();
-Structs* gstsGet();
+void gstsInit(void);
+void gstsDelete(void);
+Structs* gstsGet(void);
 Struct* gstsAdd(const char* name);
 
 #ifdef __cplusplus

+ 1 - 1
Main.c

@@ -10,7 +10,7 @@
 #include "utils/Functions.h"
 #include "vm/Script.h"
 
-long getNanos() {
+static long getNanos(void) {
     struct timespec time;
     clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &time);
     return time.tv_nsec + time.tv_sec * 1000000000l;

+ 9 - 8
Test.c

@@ -7,6 +7,7 @@
 #include <string.h>
 
 #include "Compiler.h"
+#include "Test.h"
 #include "tokenizer/Tokenizer.h"
 #include "utils/ByteCodePrinter.h"
 #include "utils/Functions.h"
@@ -25,8 +26,8 @@ static void tsPrintToBuffer(const char* format, ...) {
     va_list args;
     va_start(args, format);
     int leftBytes = TEST_BUFFER_LENGTH - testBufferIndex;
-    testBufferIndex +=
-        vsnprintf(testBuffer + testBufferIndex, leftBytes, format, args);
+    testBufferIndex += vsnprintf(testBuffer + testBufferIndex,
+                                 (size_t)leftBytes, format, args);
     if(testBufferIndex > TEST_BUFFER_LENGTH) {
         testBufferIndex = TEST_BUFFER_LENGTH;
     }
@@ -46,7 +47,7 @@ static void tsFloatPrinter(Script* sc) {
     if(sPopFloat(sc, &f)) {
         return;
     }
-    tsPrintToBuffer("%.2f\n", f);
+    tsPrintToBuffer("%.2lf\n", (double)f);
 }
 
 static void tsTextPrinter(Script* sc) {
@@ -81,7 +82,7 @@ static void tsReset(int marker) {
 
 static bool tsCompareResults(FILE* file) {
     for(int i = 0; i < testBufferIndex; i++) {
-        char a = fgetc(file);
+        char a = (char)fgetc(file);
         char b = testBuffer[i];
         if(a != b) {
             printf("error in '%s': expected '%c', got:\n%s", path, a,
@@ -122,7 +123,7 @@ static void tsCheckScript(Script* sc) {
     fclose(file);
 }
 
-static void tsCheckFile() {
+static void tsCheckFile(void) {
     allTests++;
     Error e;
     tTokenize(path, &e);
@@ -144,7 +145,7 @@ static void tsCheckFile() {
     sDelete(sc);
 }
 
-static void tsScanDirectory() {
+static void tsScanDirectory(void) {
     DIR* dir = opendir(path);
     if(dir == NULL) {
         printf("cannot open '%s': %s\n", path, strerror(errno));
@@ -178,14 +179,14 @@ static void tsAddPrinter(DataType in, ScriptFunction sf) {
     gfsAdd(&f);
 }
 
-void tsStart(const char* path) {
+void tsStart(const char* fPath) {
     tsAddPrinter(dtInt(), tsInt32Printer);
     tsAddPrinter(dtFloat(), tsFloatPrinter);
     tsAddPrinter(dtText(), tsTextPrinter);
 
     doneTests = 0;
     allTests = 0;
-    tsAppend(path);
+    tsAppend(fPath);
     tsScanDirectory();
     printf("%d / %d tests succeeded\n", doneTests, allTests);
 }

+ 1 - 1
Test.h

@@ -5,7 +5,7 @@
 extern "C" {
 #endif
 
-void tsStart(const char* path);
+void tsStart(const char* fPath);
 
 #ifdef __cplusplus
 }

+ 1 - 1
libraries/Math.c

@@ -36,7 +36,7 @@ static void lAddFloatFunction(const char* name, ScriptFunction sf) {
     gfsAdd(&f);
 }
 
-void lMathRegister() {
+void lMathRegister(void) {
     lAddFloatFunction("sin", lSin);
     lAddFloatFunction("cos", lCos);
     lAddFloatFunction("tan", lTan);

+ 1 - 1
libraries/Math.h

@@ -5,7 +5,7 @@
 extern "C" {
 #endif
 
-void lMathRegister();
+void lMathRegister(void);
 
 #ifdef __cplusplus
 }

+ 7 - 7
libraries/Time.c

@@ -16,8 +16,8 @@ static void lGetMillis(Script* sc) {
     if(v == NULL) {
         return;
     }
-    v[0].data.intValue = time.tv_sec;
-    v[1].data.intValue = (time.tv_nsec / 1000000) * 1000000;
+    v[0].data.intValue = (int)time.tv_sec;
+    v[1].data.intValue = (int)((time.tv_nsec / 1000000) * 1000000);
 }
 
 static void lGetNanos(Script* sc) {
@@ -30,8 +30,8 @@ static void lGetNanos(Script* sc) {
     if(v == NULL) {
         return;
     }
-    v[0].data.intValue = time.tv_sec;
-    v[1].data.intValue = time.tv_nsec;
+    v[0].data.intValue = (int)time.tv_sec;
+    v[1].data.intValue = (int)time.tv_nsec;
 }
 
 static void lToTime(Script* sc) {
@@ -54,7 +54,7 @@ static void lToTime(Script* sc) {
     time[3].data.intValue = local->tm_hour;
     time[4].data.intValue = local->tm_min;
     time[5].data.intValue = local->tm_sec;
-    time[6].data.intValue = millis % 1000;
+    time[6].data.intValue = (int)(millis % 1000);
     time[7].data.intValue = local->tm_isdst;
 }
 
@@ -78,11 +78,11 @@ static void lToMillis(Script* sc) {
         return;
     }
 
-    timer[0].data.intValue = seconds;
+    timer[0].data.intValue = (int)seconds;
     timer[1].data.intValue = time[6].data.intValue * 1000000;
 }
 
-void lTimeRegister() {
+void lTimeRegister(void) {
     Struct* timer = gstsAdd("Timer");
     stAddVariable(timer, "seconds", dtInt());
     stAddVariable(timer, "nanos", dtInt());

+ 1 - 1
libraries/Time.h

@@ -5,7 +5,7 @@
 extern "C" {
 #endif
 
-void lTimeRegister();
+void lTimeRegister(void);
 
 #ifdef __cplusplus
 }

+ 14 - 1
meson.build

@@ -22,7 +22,20 @@ src = [
 cc = meson.get_compiler('c')
 math_dep = cc.find_library('m', required : true)
 
-args = ['-Wall', '-Wextra', '-pedantic', '-Werror']
+#args = ['-Wall', '-Wextra', '-pedantic', '-Werror']
+
+args = cc.get_supported_arguments([
+    '-Werror', '-pedantic', '-pedantic-errors', '-Wall', '-Wextra', '-Wdouble-promotion', 
+    '-Wformat=2', '-Wformat-signedness', '-Wnull-dereference', '-Winfinite-recursion', 
+    '-Winit-self', '-Wmissing-include-dirs', '-Wshift-overflow=2', '-Wtrivial-auto-var-init', 
+    '-Wduplicated-branches', '-Wduplicated-cond', '-Wfloat-equal', '-Wshadow', '-Wundef', 
+    '-Wcast-qual', '-Wcast-align=strict', '-Wconversion', '-Warith-conversion', 
+    '-Wsign-conversion', '-Wlogical-op', '-Wmissing-declarations', '-Wpadded', 
+    '-Woverlength-strings', '-Wwrite-strings', '-Walloca', '-Walloc-zero', '-Wdate-time', 
+    '-Wc++-compat', '-Wdisabled-optimization', '-Winvalid-pch', '-Wmultichar', 
+    '-Wbidi-chars=any', '-Wbad-function-cast', '-Wjump-misses-init', '-Wstrict-prototypes', 
+    '-Wmissing-prototypes', '-Wnested-externs', '-Wunsuffixed-float-constants', '-Wredundant-decls'
+])
 
 inc = include_directories('.')
 liblonelytiger = static_library('lonelytiger', 

+ 18 - 14
tokenizer/FileTokens.c

@@ -95,7 +95,8 @@ static void ftToSpace(FileToken* t) {
 static FileToken* ftAddToken(FileTokens* ft, FileTokenType type) {
     if(ft->length >= ft->capacity) {
         ft->capacity = (ft->capacity * 5) / 4 + 8;
-        ft->tokens = realloc(ft->tokens, ft->capacity * sizeof(FileToken));
+        ft->tokens = (FileToken*)realloc(ft->tokens, (size_t)ft->capacity *
+                                                         sizeof(FileToken));
     }
     FileToken* t = ft->tokens + ft->length++;
     t->type = type;
@@ -124,7 +125,7 @@ static void ftAddNewline(FileTokens* ft) {
 }
 
 static void ftAddLiteral(FileTokens* ft, const char* path, int length) {
-    ftAddToken(ft, FT_LITERAL)->literal = strndup(path, length);
+    ftAddToken(ft, FT_LITERAL)->literal = strndup(path, (size_t)length);
 }
 
 static void ftAddSingle(FileTokens* ft, int single) {
@@ -150,12 +151,13 @@ void ftPrint(FileTokens* ft) {
                 printf("\033[0;31m%c", (char)ft->tokens[i].single);
                 break;
             case FT_SPACE: putchar(' '); break;
+            default: putchar('?'); break;
         }
     }
     printf("\033[0m");
 }
 
-static bool ftHasError() {
+static bool ftHasError(void) {
     return eHasError(error);
 }
 
@@ -230,15 +232,16 @@ static void ftReadFull(FILE* file, FileTokens* parent, FileTokens* ft,
         ftSystemError("cannot seek end of file", parent, ft, index);
         return;
     }
-    long length = ftell(file);
-    if(length < 0) {
+    long signedLength = ftell(file);
+    if(signedLength < 0) {
         ftSystemError("cannot tell end of file", parent, ft, index);
         return;
     }
+    size_t length = (size_t)signedLength;
     rewind(file);
 
-    unsigned char* data = malloc(length + 1);
-    int readValues = fread(data, 1, length, file);
+    unsigned char* data = (unsigned char*)malloc(length + 1);
+    size_t readValues = fread(data, 1, length, file);
     if(readValues != length) {
         ftSystemError("cannot read file", parent, ft, index);
         free(data);
@@ -265,7 +268,8 @@ static void ftReadFullFile(FileTokens* parent, FileTokens* ft, int index) {
 static void ftReplace(int from, int toEx, FileTokens* ft,
                       const FileTokens* replacement) {
     int newCapacity = ft->capacity + replacement->capacity;
-    FileToken* newTokens = malloc(newCapacity * sizeof(FileToken));
+    FileToken* newTokens =
+        (FileToken*)malloc((size_t)newCapacity * sizeof(FileToken));
 
     // these will be overwritten
     for(int i = from; i < toEx; i++) {
@@ -273,7 +277,7 @@ static void ftReplace(int from, int toEx, FileTokens* ft,
         ft->tokens[i].literal = NULL;
     }
 
-    memcpy(newTokens, ft->tokens, from * sizeof(FileToken));
+    memcpy(newTokens, ft->tokens, (size_t)from * sizeof(FileToken));
     for(int i = 0; i < replacement->length; i++) {
         FileToken* src = replacement->tokens + i;
         FileToken* dst = newTokens + from + i;
@@ -282,7 +286,7 @@ static void ftReplace(int from, int toEx, FileTokens* ft,
         dst->type = src->type;
     }
     memcpy(newTokens + from + replacement->length, ft->tokens + toEx,
-           (ft->length - toEx) * sizeof(FileToken));
+           (size_t)(ft->length - toEx) * sizeof(FileToken));
 
     free(ft->tokens);
     ft->tokens = newTokens;
@@ -327,13 +331,13 @@ static void ftHandleInclude(int* index, int start, FileTokens* ft) {
     }
     const char* parentPath = ftGetPath(ft, *index - 1);
 
-    int afterLastSlash = 0;
-    for(int i = 0; parentPath[i] != '\0'; i++) {
+    size_t afterLastSlash = 0;
+    for(size_t i = 0; parentPath[i] != '\0'; i++) {
         afterLastSlash = parentPath[i] == '/' ? i + 1 : afterLastSlash;
     }
 
-    int pathLength = strlen(path) + 1;
-    char* fullPath = malloc(afterLastSlash + pathLength);
+    size_t pathLength = strlen(path) + 1;
+    char* fullPath = (char*)malloc(afterLastSlash + pathLength);
     memcpy(fullPath, parentPath, afterLastSlash);
     memcpy(fullPath + afterLastSlash, path, pathLength);
 

+ 1 - 1
tokenizer/Token.c

@@ -64,6 +64,6 @@ const char* tGetName(Token token) {
         case T_OPEN_PATH: return "open path";
         case T_CLOSE_PATH: return "close path";
         case T_END: return "end";
+        default: return "unknown";
     }
-    return "unknown";
 }

+ 32 - 29
tokenizer/Tokenizer.c

@@ -20,7 +20,8 @@ static Error* error = NULL;
 
 typedef struct {
     const char* path;
-    int line;
+    int16 line;
+    char padding[sizeof(const char*) - sizeof(int16)];
 } IncludeEntry;
 static IncludeEntry includeStack[INCLUDE_STACK_LENGTH];
 static int includeStackIndex = 0;
@@ -48,7 +49,7 @@ static void tAdd(const void* data, int length) {
     if(writeIndex + length > TOKEN_BUFFER_LENGTH) {
         tError("the token buffer is too small");
     }
-    memcpy(tokenBuffer + writeIndex, data, length);
+    memcpy(tokenBuffer + writeIndex, data, (size_t)length);
     writeIndex += length;
 }
 
@@ -62,19 +63,19 @@ static bool tReadTokens(void* dest, int length) {
     if(readIndex + length > writeIndex) {
         return true;
     }
-    memcpy(dest, tokenBuffer + readIndex, length);
+    memcpy(dest, tokenBuffer + readIndex, (size_t)length);
     readIndex += length;
     return false;
 }
 
-static FileToken* tNextToken() {
+static FileToken* tNextToken(void) {
     if(fileTokenIndex >= fileTokens.length) {
         tError("unexpected end of file");
     }
     return fileTokens.tokens + fileTokenIndex++;
 }
 
-static bool tReadSingleIf(char c) {
+static bool tReadSingleIf(int c) {
     if(fileTokenIndex >= fileTokens.length ||
        fileTokens.tokens[fileTokenIndex].type != FT_SINGLE ||
        fileTokens.tokens[fileTokenIndex].single != c) {
@@ -121,7 +122,7 @@ static void tParseLiteral(const char* buffer) {
         tAdd(&i, sizeof(int32));
     } else {
         tAddToken(T_LITERAL);
-        tAdd(buffer, strlen(buffer) + 1);
+        tAdd(buffer, (int)strlen(buffer) + 1);
     }
 }
 
@@ -153,29 +154,29 @@ static void tParseNumber(const char* buffer) {
         }
         long long comma = tParseInt(t->literal);
 
-        float f = comma;
+        float f = (float)comma;
         while(f > 1.0f) {
             f /= 10.0f;
         }
-        f += l;
+        f += (float)l;
         tAddToken(T_FLOAT_VALUE);
         tAdd(&f, sizeof(float));
     } else {
         if(l > INT32_MAX) {
             tError("invalid int on line %d", line);
         }
-        int32 i = l;
+        int32 i = (int)l;
         tAddToken(T_INT_VALUE);
         tAdd(&i, sizeof(int32));
     }
 }
 
-static int32 tNextUnicodePart() {
+static int32 tNextUnicodePart(void) {
     FileToken* t = tNextToken();
     if(t->type == FT_SINGLE) {
         return t->single;
     } else if(t->type == FT_LITERAL) {
-        int length = strlen(t->literal);
+        int length = (int)strlen(t->literal);
         if(length != 1) {
             tError("unicode literal has wrong length %d", length);
         }
@@ -201,7 +202,7 @@ static int32 tUnicode(int32 c) {
         c = ((c & 0x1F) << 6) | (tNextUnicodePart() & 0x3F);
     } else if((c & 0xF0) == 0xE0) {
         c = ((c & 0xF) << 12) | ((tNextUnicodePart() & 0x3F) << 6);
-        c |= tNextUnicodePart(&fileTokens) & 0x3F;
+        c |= tNextUnicodePart() & 0x3F;
     } else if((c & 0xF8) == 0xF0) {
         c = ((c & 0x7) << 18) | ((tNextUnicodePart() & 0x3F) << 12);
         c |= (tNextUnicodePart() & 0x3F) << 6;
@@ -243,7 +244,7 @@ static int32 tStringUnicode(const char* s, int* index, int length) {
     return c;
 }
 
-static void tAddString() {
+static void tAddString(void) {
     tAddToken(T_TEXT);
 
     FileToken* t = tNextToken();
@@ -252,7 +253,7 @@ static void tAddString() {
             tError("unexpected single '%d'", t->single);
         }
     } else if(t->type == FT_LITERAL) {
-        int length = strlen(t->literal);
+        int length = (int)strlen(t->literal);
         const char* s = t->literal;
         int index = 0;
         while(index < length) {
@@ -270,10 +271,10 @@ static void tAddString() {
     tAdd(&c, sizeof(int32));
 }
 
-static void tAddUnicode() {
+static void tAddUnicode(void) {
     FileToken* t = tNextToken();
     if(t->type == FT_LITERAL) {
-        int length = strlen(t->literal);
+        int length = (int)strlen(t->literal);
         if(length != 1) {
             tError("invalid character on line %d", line);
         }
@@ -318,7 +319,7 @@ static void tAddToken4(int c, Token tce, Token tc, Token te, Token t) {
 
 static void tParseToken(FileToken* t) {
     switch(t->type) {
-        case FT_PATH:
+        case FT_PATH: {
             if(includeStackIndex >= INCLUDE_STACK_LENGTH) {
                 tError("include stack overflow");
             }
@@ -327,9 +328,10 @@ static void tParseToken(FileToken* t) {
             includeStackIndex++;
             line = 1;
             tAddToken(T_OPEN_PATH);
-            tAdd(t->literal, strlen(t->literal) + 1);
+            tAdd(t->literal, (int)strlen(t->literal) + 1);
             return;
-        case FT_END_PATH:
+        }
+        case FT_END_PATH: {
             if(includeStackIndex <= 0) {
                 tError("include stack underflow");
             }
@@ -339,8 +341,9 @@ static void tParseToken(FileToken* t) {
             const char* path = includeStackIndex > 0
                                    ? includeStack[includeStackIndex - 1].path
                                    : "path not set";
-            tAdd(path, strlen(path) + 1);
+            tAdd(path, (int)strlen(path) + 1);
             return;
+        }
         case FT_NEWLINE: line++; return;
         case FT_LITERAL: {
             const char* buffer = t->literal;
@@ -355,7 +358,7 @@ static void tParseToken(FileToken* t) {
         }
         case FT_SPACE: return;
         case FT_SINGLE: {
-            char c = t->single;
+            int c = t->single;
             switch(c) {
                 case ' ': return;
                 case '+':
@@ -404,7 +407,7 @@ static void tParseToken(FileToken* t) {
     }
 }
 
-static void tParseFile() {
+static void tParseFile(void) {
     readIndex = 0;
     writeIndex = 0;
     line = 1;
@@ -427,19 +430,19 @@ void tTokenize(const char* path, Error* e) {
     ftDelete(&fileTokens);
 }
 
-Token tPeekToken() {
+Token tPeekToken(void) {
     if(readIndex >= writeIndex) {
         return T_END;
     }
-    return tokenBuffer[readIndex];
+    return (Token)tokenBuffer[readIndex];
 }
 
-bool tReadTokenAndLine(Token* t, int16* line) {
+bool tReadTokenAndLine(Token* t, int16* l) {
     if(readIndex >= writeIndex) {
         return true;
     }
-    *t = tokenBuffer[readIndex++];
-    return tReadTokens(line, sizeof(int16));
+    *t = (Token)tokenBuffer[readIndex++];
+    return tReadTokens(l, sizeof(int16));
 }
 
 bool tReadInt32(int32* i) {
@@ -450,7 +453,7 @@ bool tReadFloat(float* f) {
     return tReadTokens(f, sizeof(float));
 }
 
-const char* tReadString() {
+const char* tReadString(void) {
     const char* s = tokenBuffer + readIndex;
     while(readIndex <= writeIndex) {
         if(tokenBuffer[readIndex++] == '\0') {
@@ -460,7 +463,7 @@ const char* tReadString() {
     return NULL;
 }
 
-int tGetMarker() {
+int tGetMarker(void) {
     return readIndex;
 }
 

+ 3 - 3
tokenizer/Tokenizer.h

@@ -11,12 +11,12 @@ extern "C" {
 
 void tTokenize(const char* path, Error* e);
 
-Token tPeekToken();
+Token tPeekToken(void);
 bool tReadTokenAndLine(Token* t, int16* line);
 bool tReadInt32(int32* i);
 bool tReadFloat(float* f);
-const char* tReadString();
-int tGetMarker();
+const char* tReadString(void);
+int tGetMarker(void);
 void tReset(int marker);
 
 #ifdef __cplusplus

+ 16 - 15
utils/ByteCodePrinter.c

@@ -13,11 +13,11 @@ static int line;
 static char buffer[LINE_LENGTH];
 static int bIndex;
 
-static void btPrintEnd() {
+static void btPrintEnd(void) {
     puts("+--------+-------+----------------------+------------+------------+");
 }
 
-static void btPrintHeading() {
+static void btPrintHeading(void) {
     btPrintEnd();
     puts("|  Index |  Line |            Operation | Argument 1 | Argument 2 |");
     btPrintEnd();
@@ -26,21 +26,22 @@ static void btPrintHeading() {
 static void btAdd(const char* format, ...) {
     va_list args;
     va_start(args, format);
-    bIndex += vsnprintf(buffer + bIndex, LINE_LENGTH - bIndex, format, args);
+    bIndex += vsnprintf(buffer + bIndex, (size_t)(LINE_LENGTH - bIndex), format,
+                        args);
     va_end(args);
 }
 
-static void btFillBase() {
+static void btFillBase(void) {
     buffer[0] = '\0';
     bIndex = 0;
     btAdd("| %6d | %5d |", readIndex - 1, line);
 }
 
-static void btRead(void* buffer, int length) {
+static void btRead(void* b, int length) {
     if(readIndex + length > code->length) {
         return;
     }
-    memcpy(buffer, code->code + readIndex, length);
+    memcpy(b, code->code + readIndex, (size_t)length);
     readIndex += length;
 }
 
@@ -51,25 +52,25 @@ static void btAddOperation(const char* s) {
     btAdd(" %20s |", s);
 }
 
-static void btAddInt32() {
+static void btAddInt32(void) {
     int32 value = 0;
     btRead(&value, sizeof(int32));
     btAdd(" %10d |", value);
 }
 
-static void btAddInt8() {
+static void btAddInt8(void) {
     int8 value = 0;
     btRead(&value, sizeof(int8));
     btAdd(" %10d |", (int32)value);
 }
 
-static void btAddFloat() {
+static void btAddFloat(void) {
     float value = 0;
     btRead(&value, sizeof(float));
-    btAdd(" %10.2f |", value);
+    btAdd(" %10.2lf |", (double)value);
 }
 
-static void btAddText() {
+static void btAddText(void) {
     int32 length = 0;
     btRead(&length, sizeof(int32));
     for(int i = 0; i < length; i++) {
@@ -79,11 +80,11 @@ static void btAddText() {
     btAdd(" %10s |", "Text");
 }
 
-static void btAddFiller() {
+static void btAddFiller(void) {
     btAdd("            |");
 }
 
-static void sPrintLine() {
+static void sPrintLine(void) {
     btRead(&line, 2);
     printf("| %6d |-------|----------------------|------------|------------|\n",
            readIndex - 3);
@@ -155,8 +156,8 @@ static void btPrintText(const char* op) {
     PRINT_OP(OP_EQUAL_##TYPE);                                                 \
     PRINT_OP(OP_NOT_EQUAL_##TYPE);
 
-static void btConsumeOperation() {
-    Operation op = code->code[readIndex++];
+static void btConsumeOperation(void) {
+    Operation op = (Operation)code->code[readIndex++];
     switch(op) {
         PRINT_TYPES(INT);
         PRINT_TYPES(FLOAT);

+ 7 - 6
utils/Functions.c

@@ -6,7 +6,7 @@
 static bool useGlobals = false;
 static Functions globalFunctions;
 
-void fInit(Function* f, const char* name, int line) {
+void fInit(Function* f, const char* name, int16 line) {
     f->name = name;
     f->arguments = 0;
     f->returnType = dtVoid();
@@ -41,7 +41,7 @@ static bool fCompare(Function* a, Function* b) {
 void fsInit(Functions* fs) {
     fs->capacity = 16;
     fs->entries = 0;
-    fs->data = malloc(sizeof(Function) * fs->capacity);
+    fs->data = (Function*)malloc(sizeof(Function) * (size_t)fs->capacity);
 }
 
 void fsDelete(Functions* fs) {
@@ -70,7 +70,8 @@ Function* fsSearch(Functions* fs, Function* f) {
 void fsAdd(Functions* fs, Function* f) {
     if(fs->entries >= fs->capacity) {
         fs->capacity *= 2;
-        fs->data = realloc(fs->data, sizeof(Function) * fs->capacity);
+        fs->data = (Function*)realloc(fs->data,
+                                      sizeof(Function) * (size_t)fs->capacity);
     }
     fs->data[fs->entries++] = *f;
 }
@@ -85,7 +86,7 @@ bool gfAddArgument(Function* f, DataType type) {
     return fAddArgument(f, type, gstsGet());
 }
 
-void gfsInit() {
+void gfsInit(void) {
     fsInit(&globalFunctions);
     useGlobals = true;
 }
@@ -96,7 +97,7 @@ bool gfsAdd(Function* f) {
     }
     int index = globalFunctions.entries;
     fsAdd(&globalFunctions, f);
-    globalFunctions.data[index].line = index;
+    globalFunctions.data[index].line = (int16)index;
     globalFunctions.data[index].global = true;
     return false;
 }
@@ -109,7 +110,7 @@ bool gfsCall(Script* sc, int id) {
     return false;
 }
 
-void gfsDelete() {
+void gfsDelete(void) {
     fsDelete(&globalFunctions);
     useGlobals = false;
 }

+ 6 - 5
utils/Functions.h

@@ -16,14 +16,15 @@ typedef void (*ScriptFunction)(Script*);
 
 typedef struct {
     const char* name;
+    ScriptFunction scriptFunction;
     int arguments;
     DataType argumentTypes[FUNCTION_ARGUMENTS];
     DataType returnType;
     int address;
     int size;
-    int line;
+    int16 line;
     bool global;
-    ScriptFunction scriptFunction;
+    char padding[1];
 } Function;
 
 typedef struct {
@@ -32,7 +33,7 @@ typedef struct {
     Function* data;
 } Functions;
 
-void fInit(Function* f, const char* name, int line);
+void fInit(Function* f, const char* name, int16 line);
 bool fAddArgument(Function* f, DataType type, Structs* sts);
 
 void fsInit(Functions* fs);
@@ -42,10 +43,10 @@ void fsAdd(Functions* fs, Function* f);
 
 void gfInit(Function* f, const char* name, DataType r, ScriptFunction sf);
 bool gfAddArgument(Function* f, DataType type);
-void gfsInit();
+void gfsInit(void);
 bool gfsAdd(Function* f);
 bool gfsCall(Script* sc, int id);
-void gfsDelete();
+void gfsDelete(void);
 
 #ifdef __cplusplus
 }

+ 3 - 2
utils/Variables.c

@@ -6,7 +6,7 @@
 void vsInit(Variables* v) {
     v->capacity = 16;
     vsReset(v);
-    v->data = malloc(sizeof(Variable) * v->capacity);
+    v->data = (Variable*)malloc(sizeof(Variable) * (size_t)v->capacity);
 }
 
 void vsDelete(Variables* v) {
@@ -48,7 +48,8 @@ bool vSearchStruct(Variable* v, Structs* sts, Struct* st, const char* s) {
 Variable* vsAdd(Variables* v, const char* s, DataType type, Structs* sts) {
     if(v->entries >= v->capacity) {
         v->capacity *= 2;
-        v->data = realloc(v->data, sizeof(Variable) * v->capacity);
+        v->data =
+            (Variable*)realloc(v->data, sizeof(Variable) * (size_t)v->capacity);
     }
     int index = v->entries++;
     v->data[index] = (Variable){s, type, v->address};

+ 1 - 0
utils/Variables.h

@@ -28,6 +28,7 @@ typedef struct {
     int scope;
     Variable* data;
     int maxAddress;
+    char padding[sizeof(Variable*) - sizeof(int)];
 } Variables;
 
 void vsInit(Variables* v);

+ 7 - 7
vm/Arrays.c

@@ -8,7 +8,7 @@
 static long long allocatedBytes = 0;
 
 static int aGetSize(SnuviArray* a) {
-    return sizeof(Value) * a->realLength;
+    return (int)sizeof(Value) * a->realLength;
 }
 
 void asInit(SnuviArrays* as) {
@@ -23,7 +23,7 @@ void asDelete(SnuviArrays* as) {
         allocatedBytes -= aGetSize(as->data + i);
         free(as->data[i].data);
     }
-    allocatedBytes -= as->capacity * sizeof(SnuviArray);
+    allocatedBytes -= as->capacity * (int)sizeof(SnuviArray);
     free(as->data);
 }
 
@@ -51,13 +51,13 @@ static bool asEnsureCapacity(SnuviArrays* as) {
     }
     int oldCapacity = as->capacity;
     int capacity = (as->data == NULL) ? 4 : as->capacity * 2;
-    int oldBytes = sizeof(SnuviArray) * oldCapacity;
-    int bytes = sizeof(SnuviArray) * capacity;
+    int oldBytes = (int)sizeof(SnuviArray) * oldCapacity;
+    int bytes = (int)sizeof(SnuviArray) * capacity;
     if(bytes < 0 || allocatedBytes - oldBytes + bytes > MAX_ALLOCATED_BYTES) {
         return true;
     }
     allocatedBytes += bytes - oldBytes;
-    as->data = realloc(as->data, bytes);
+    as->data = (SnuviArray*)realloc(as->data, (size_t)bytes);
     as->capacity = capacity;
     asInitArrays(as, oldCapacity);
     return false;
@@ -78,7 +78,7 @@ int asAllocate(SnuviArrays* as, int typeSize, int length) {
     if(asEnsureCapacity(as)) {
         return -1;
     }
-    int bytes = sizeof(Value) * typeSize * length;
+    int bytes = (int)sizeof(Value) * typeSize * length;
     if(bytes < 0) {
         return -2;
     } else if(allocatedBytes + bytes > MAX_ALLOCATED_BYTES) {
@@ -102,7 +102,7 @@ int asAllocate(SnuviArrays* as, int typeSize, int length) {
 
     array->realLength = typeSize * length;
     array->length = length;
-    array->data = malloc(bytes);
+    array->data = (Value*)malloc((size_t)bytes);
     return index;
 }
 

+ 2 - 1
vm/Arrays.h

@@ -18,10 +18,11 @@ typedef struct {
 } SnuviArray;
 
 typedef struct {
+    SnuviArray* data;
     int capacity;
     int usedStart;
     int freeStart;
-    SnuviArray* data;
+    char padding[sizeof(SnuviArray*) - sizeof(int)];
 } SnuviArrays;
 
 void asInit(SnuviArrays* as);

+ 7 - 7
vm/ByteCode.c

@@ -4,11 +4,11 @@
 
 #include "vm/ByteCode.h"
 
-ByteCode* bcInit() {
-    ByteCode* bc = malloc(sizeof(ByteCode));
+ByteCode* bcInit(void) {
+    ByteCode* bc = (ByteCode*)malloc(sizeof(ByteCode));
     bc->capacity = 16;
     bc->length = 0;
-    bc->code = malloc(bc->capacity);
+    bc->code = (unsigned char*)malloc((size_t)bc->capacity);
     return bc;
 }
 
@@ -20,7 +20,7 @@ void bcDelete(ByteCode* bc) {
 static void bcReAlloc(ByteCode* bc, int length) {
     while(bc->length + length > bc->capacity) {
         bc->capacity *= 2;
-        bc->code = realloc(bc->code, bc->capacity);
+        bc->code = (unsigned char*)realloc(bc->code, (size_t)bc->capacity);
     }
 }
 
@@ -32,7 +32,7 @@ int bcReserveBytes(ByteCode* bc, int length) {
 }
 
 void bcSetBytes(ByteCode* bc, int p, const void* data, int length) {
-    memcpy(bc->code + p, data, length);
+    memcpy(bc->code + p, data, (size_t)length);
 }
 
 void bcAddBytes(ByteCode* bc, const void* data, int length) {
@@ -46,7 +46,7 @@ int bcGetAddress(ByteCode* bc) {
 void bcInsertBytes(ByteCode* bc, const void* data, int length, int address) {
     bcReAlloc(bc, length);
     memmove(bc->code + address + length, bc->code + address,
-            bc->length - address);
-    memcpy(bc->code + address, data, length);
+            (size_t)(bc->length - address));
+    memcpy(bc->code + address, data, (size_t)length);
     bc->length += length;
 }

+ 1 - 1
vm/ByteCode.h

@@ -13,7 +13,7 @@ typedef struct {
     unsigned char* code;
 } ByteCode;
 
-ByteCode* bcInit();
+ByteCode* bcInit(void);
 void bcDelete(ByteCode* bc);
 
 int bcReserveBytes(ByteCode* bc, int length);

+ 73 - 68
vm/Script.c

@@ -23,7 +23,7 @@ static bool sRead(Script* sc, void* buffer, int length) {
         sError(sc, "cannot read expected %d bytes of data from bytecode");
         return true;
     }
-    memcpy(buffer, sc->code->code + sc->readIndex, length);
+    memcpy(buffer, sc->code->code + sc->readIndex, (size_t)length);
     sc->readIndex += length;
     return false;
 }
@@ -33,7 +33,7 @@ static Operation sReadOperation(Script* sc) {
     if(sRead(sc, &c, 1)) {
         return OP_NOTHING;
     }
-    return c;
+    return (Operation)c;
 }
 
 static Value* sPeekStack(Script* sc, int type) {
@@ -341,7 +341,7 @@ static void sDereference(Script* sc) {
     Value* v = sPushStack(sc, 1);
     if(v != NULL) {
         v->type = VT_POINTER;
-        v->offset = address + sc->stackVarIndex;
+        v->offset = ((unsigned int)(address + sc->stackVarIndex)) & 0x0FFFFFFF;
         v->data.intValue = -1;
     }
 }
@@ -354,7 +354,7 @@ static void sGlobalDereference(Script* sc) {
     Value* v = sPushStack(sc, 1);
     if(v != NULL) {
         v->type = VT_POINTER;
-        v->offset = address;
+        v->offset = ((unsigned int)address) & 0x0FFFFFFF;
         v->data.intValue = -1;
     }
 }
@@ -377,13 +377,13 @@ static void sAddReference(Script* sc) {
     }
     Value* v = sPeekStack(sc, VT_POINTER);
     if(v != NULL) {
-        v->offset += add * size;
+        v->offset = ((unsigned int)(v->offset + add * size)) & 0x3FFFFFF;
     } else {
         sc->error[0] = '\0';
-        Value* v = sPeekStack(sc, VT_ARRAY);
+        v = sPeekStack(sc, VT_ARRAY);
         if(v != NULL) {
             v->type = VT_POINTER;
-            v->offset += add * size;
+            v->offset = ((unsigned int)(v->offset + add * size)) & 0x3FFFFFF;
         }
     }
 }
@@ -639,7 +639,7 @@ static void sPushAfterChange(Script* sc) {
 static void sFloatToInt32(Script* sc) {
     Value* v = sPeekStack(sc, VT_FLOAT);
     if(v != NULL) {
-        v->data.intValue = v->data.floatValue;
+        v->data.intValue = (int)v->data.floatValue;
         v->type = VT_INT;
     }
 }
@@ -647,28 +647,29 @@ static void sFloatToInt32(Script* sc) {
 static void sInt32ToFloat(Script* sc) {
     Value* v = sPeekStack(sc, VT_INT);
     if(v != NULL) {
-        v->data.floatValue = v->data.intValue;
+        v->data.floatValue = (float)v->data.intValue;
         v->type = VT_FLOAT;
     }
 }
 
 #define CASE_NUMBER_OP(name, op)                                               \
-    case OP_##name##_INT: NUMBER_OP(int32, Int32, op); break;                  \
+    case OP_##name##_INT: NUMBER_OP(int32, Int32, op); return;                 \
     case OP_##name##_FLOAT:                                                    \
         NUMBER_OP(float, Float, op);                                           \
-        break;
+        return;
 #define CASE_BOOL_OP(name, op)                                                 \
-    case OP_##name##_INT: BOOL_OP(int32, Int32, op); break;                    \
+    case OP_##name##_INT: BOOL_OP(int32, Int32, op); return;                   \
     case OP_##name##_FLOAT:                                                    \
         BOOL_OP(float, Float, op);                                             \
-        break;
+        return;
 #define CASE_TYPE(TYPE, Type, type)                                            \
-    case OP_RETURN_##TYPE: RETURN(type, Type); break;                          \
-    case OP_EQUAL_##TYPE: BOOL_OP(type, Type, ==); break;                      \
-    case OP_NOT_EQUAL_##TYPE: BOOL_OP(type, Type, !=); break;
+    case OP_RETURN_##TYPE: RETURN(type, Type); return;                         \
+    case OP_EQUAL_##TYPE: BOOL_OP(type, Type, ==); return;                     \
+    case OP_NOT_EQUAL_##TYPE: BOOL_OP(type, Type, !=); return;
 
 static void sConsumeInstruction(Script* sc) {
-    switch(sReadOperation(sc)) {
+    Operation op = sReadOperation(sc);
+    switch(op) {
         CASE_NUMBER_OP(ADD, +);
         CASE_NUMBER_OP(SUB, -);
         CASE_NUMBER_OP(MUL, *);
@@ -677,57 +678,61 @@ static void sConsumeInstruction(Script* sc) {
         CASE_BOOL_OP(GREATER, >);
         CASE_BOOL_OP(GREATER_EQUAL, >=);
         CASE_TYPE(INT, Int32, int32);
+#pragma GCC diagnostic push
+#pragma GCC diagnostic ignored "-Wfloat-equal"
         CASE_TYPE(FLOAT, Float, float);
-        case OP_STORE_INT: sStoreInt32(sc); break;
-        case OP_STORE_FLOAT: sStoreFloat(sc); break;
-        case OP_LOAD_INT: sLoadInt32(sc); break;
-        case OP_LOAD_FLOAT: sLoadFloat(sc); break;
-        case OP_PUSH_PRE_CHANGE_INT: sPushAfterChange(sc); break;
-        case OP_PUSH_POST_CHANGE_INT: sPushBeforeChange(sc); break;
-        case OP_CHANGE_INT: sChange(sc); break;
-        case OP_FLOAT_TO_INT: sFloatToInt32(sc); break;
-        case OP_INT_TO_FLOAT: sInt32ToFloat(sc); break;
-        case OP_BIT_AND_INT: NUMBER_OP(int32, Int32, &); break;
-        case OP_BIT_OR_INT: NUMBER_OP(int32, Int32, |); break;
-        case OP_BIT_XOR_INT: NUMBER_OP(int32, Int32, ^); break;
-        case OP_LEFT_SHIFT_INT: NUMBER_OP(int32, Int32, <<); break;
-        case OP_RIGHT_SHIFT_INT: NUMBER_OP(int32, Int32, >>); break;
-        case OP_NOTHING: break;
-        case OP_PUSH_INT: sPushInt32Value(sc); break;
-        case OP_PUSH_FLOAT: sPushFloatValue(sc); break;
-        case OP_PUSH_TEXT: sPushText(sc); break;
-        case OP_DIV_INT: DIVISION(int32, Int32); break;
-        case OP_DIV_FLOAT: DIVISION(float, Float); break;
-        case OP_MOD_INT: MODULE(int32, Int32); break;
-        case OP_INVERT_SIGN_INT: INVERT_SIGN(int32, Int32); break;
-        case OP_INVERT_SIGN_FLOAT: INVERT_SIGN(float, Float); break;
-        case OP_NOT: sNot(sc); break;
-        case OP_AND: BOOL_OP(int32, Int32, &&); break;
-        case OP_OR: BOOL_OP(int32, Int32, ||); break;
-        case OP_BIT_NOT_INT: sBitNotInt32(sc); break;
-        case OP_LINE: sLine(sc); break;
-        case OP_GOTO: sGoTo(sc); break;
-        case OP_IF_GOTO: sIfGoTo(sc); break;
-        case OP_PEEK_FALSE_GOTO: sPeekFalseGoTo(sc); break;
-        case OP_PEEK_TRUE_GOTO: sPeekTrueGoTo(sc); break;
-        case OP_GOSUB: sGoSub(sc); break;
-        case OP_RETURN: sReturn(sc); break;
-        case OP_RETURN_POINTER: sReturnPointer(sc); break;
-        case OP_RESERVE: sReserveBytes(sc); break;
-        case OP_GRESERVE: sGlobalReserveBytes(sc); break;
-        case OP_DEREFERENCE_VAR: sDereference(sc); break;
-        case OP_DEREFERENCE_GVAR: sGlobalDereference(sc); break;
-        case OP_LOAD_ARRAY: sLoadArray(sc); break;
-        case OP_DUPLICATE_REFERENCE: sDuplicateReference(sc); break;
-        case OP_ADD_REFERENCE: sAddReference(sc); break;
-        case OP_PUSH_STRUCT_REFERENCE: sPushStructReference(sc); break;
-        case OP_NEW: sNewArray(sc); break;
-        case OP_LENGTH: sLength(sc); break;
-        case OP_STORE_ARRAY: sStoreArray(sc); break;
-        case OP_EQUAL_POINTER: sEqualArrays(sc, true); break;
-        case OP_NOT_EQUAL_POINTER: sEqualArrays(sc, false); break;
-        case OP_CALL: sCall(sc); break;
-    }
+        case OP_DIV_FLOAT: DIVISION(float, Float); return;
+#pragma GCC diagnostic pop
+        case OP_DIV_INT: DIVISION(int32, Int32); return;
+        case OP_STORE_INT: sStoreInt32(sc); return;
+        case OP_STORE_FLOAT: sStoreFloat(sc); return;
+        case OP_LOAD_INT: sLoadInt32(sc); return;
+        case OP_LOAD_FLOAT: sLoadFloat(sc); return;
+        case OP_PUSH_PRE_CHANGE_INT: sPushAfterChange(sc); return;
+        case OP_PUSH_POST_CHANGE_INT: sPushBeforeChange(sc); return;
+        case OP_CHANGE_INT: sChange(sc); return;
+        case OP_FLOAT_TO_INT: sFloatToInt32(sc); return;
+        case OP_INT_TO_FLOAT: sInt32ToFloat(sc); return;
+        case OP_BIT_AND_INT: NUMBER_OP(int32, Int32, &); return;
+        case OP_BIT_OR_INT: NUMBER_OP(int32, Int32, |); return;
+        case OP_BIT_XOR_INT: NUMBER_OP(int32, Int32, ^); return;
+        case OP_LEFT_SHIFT_INT: NUMBER_OP(int32, Int32, <<); return;
+        case OP_RIGHT_SHIFT_INT: NUMBER_OP(int32, Int32, >>); return;
+        case OP_NOTHING: return;
+        case OP_PUSH_INT: sPushInt32Value(sc); return;
+        case OP_PUSH_FLOAT: sPushFloatValue(sc); return;
+        case OP_PUSH_TEXT: sPushText(sc); return;
+        case OP_MOD_INT: MODULE(int32, Int32); return;
+        case OP_INVERT_SIGN_INT: INVERT_SIGN(int32, Int32); return;
+        case OP_INVERT_SIGN_FLOAT: INVERT_SIGN(float, Float); return;
+        case OP_NOT: sNot(sc); return;
+        case OP_AND: BOOL_OP(int32, Int32, &&); return;
+        case OP_OR: BOOL_OP(int32, Int32, ||); return;
+        case OP_BIT_NOT_INT: sBitNotInt32(sc); return;
+        case OP_LINE: sLine(sc); return;
+        case OP_GOTO: sGoTo(sc); return;
+        case OP_IF_GOTO: sIfGoTo(sc); return;
+        case OP_PEEK_FALSE_GOTO: sPeekFalseGoTo(sc); return;
+        case OP_PEEK_TRUE_GOTO: sPeekTrueGoTo(sc); return;
+        case OP_GOSUB: sGoSub(sc); return;
+        case OP_RETURN: sReturn(sc); return;
+        case OP_RETURN_POINTER: sReturnPointer(sc); return;
+        case OP_RESERVE: sReserveBytes(sc); return;
+        case OP_GRESERVE: sGlobalReserveBytes(sc); return;
+        case OP_DEREFERENCE_VAR: sDereference(sc); return;
+        case OP_DEREFERENCE_GVAR: sGlobalDereference(sc); return;
+        case OP_LOAD_ARRAY: sLoadArray(sc); return;
+        case OP_DUPLICATE_REFERENCE: sDuplicateReference(sc); return;
+        case OP_ADD_REFERENCE: sAddReference(sc); return;
+        case OP_PUSH_STRUCT_REFERENCE: sPushStructReference(sc); return;
+        case OP_NEW: sNewArray(sc); return;
+        case OP_LENGTH: sLength(sc); return;
+        case OP_STORE_ARRAY: sStoreArray(sc); return;
+        case OP_EQUAL_POINTER: sEqualArrays(sc, true); return;
+        case OP_NOT_EQUAL_POINTER: sEqualArrays(sc, false); return;
+        case OP_CALL: sCall(sc); return;
+    }
+    sError(sc, "unknown operation %d", (int)op);
 }
 
 static bool sHasData(Script* sc) {
@@ -735,7 +740,7 @@ static bool sHasData(Script* sc) {
 }
 
 Script* sInit(ByteCode* code) {
-    Script* sc = malloc(sizeof(Script));
+    Script* sc = (Script*)malloc(sizeof(Script));
     sc->error[0] = '\0';
     sc->code = code;
     sc->readIndex = 0;