#include "../../include/ground.h" #include static void writeValue(FILE* f, GroundValue* v) { switch (v->type.type) { case GroundType_Int: { uint8_t tag = 0; fwrite(&tag, 1, 1, f); fwrite(&v->as.Int, 8, 1, f); break; } case GroundType_Double: { uint8_t tag = 1; fwrite(&tag, 1, 1, f); fwrite(&v->as.Double, 8, 1, f); break; } case GroundType_Char: { uint8_t tag = 2; fwrite(&tag, 1, 1, f); fwrite(&v->as.Char, 1, 1, f); break; } case GroundType_Bool: { uint8_t tag = 3; fwrite(&tag, 1, 1, f); fwrite(&v->as.Bool, 1, 1, f); break; } case GroundType_String: { uint8_t tag = 4; fwrite(&tag, 1, 1, f); uint64_t len = v->as.String.len; fwrite(&len, 8, 1, f); fwrite(v->as.String.cstr, 1, len, f); break; } default: { uint8_t tag = 0xFF; fwrite(&tag, 1, 1, f); break; } } } void _GroundBytecodeSave(GroundBytecode* bytecode, const char* path) { FILE* f = fopen(path, "wb"); if (f == NULL) { Ground.Log.Error("failed to open file for writing in Ground.Bytecode.save"); Ground.Flags.error = true; return; } fwrite("GRNDbc\0", 7, 1, f); uint32_t version = 1; fwrite(&version, 4, 1, f); uint64_t count = bytecode->heap.len; fwrite(&count, 8, 1, f); for (GroundSize i = 0; i < count; i++) { writeValue(f, &bytecode->heap.heap[i]); } count = bytecode->program.len; fwrite(&count, 8, 1, f); for (GroundSize i = 0; i < count; i++) { uint8_t type = (uint8_t)bytecode->program.at[i].type; fwrite(&type, 1, 1, f); uint64_t argCount = bytecode->program.at[i].args.len; fwrite(&argCount, 8, 1, f); fwrite(bytecode->program.at[i].args.at, 8, argCount, f); } fclose(f); }