diff --git a/src/env.c b/src/env.c index b6371a1..dbe78a6 100644 --- a/src/env.c +++ b/src/env.c @@ -20,7 +20,11 @@ void setGlobal(struct Environment* env) globalEnv = env; } -struct Dictionary dictionary; +struct Dictionary { + int structCount; + int structCapacity; + struct StructDef* structDefs; +} dictionary; Object fetchFromEnvironment(const char* name, struct Environment* env) { @@ -57,6 +61,13 @@ Object fetchFromEnvironment(const char* name, struct Environment* env) return errorWithContext(DID_NOT_FIND_SYMBOL, name); } +void addToEnvAt(int i, struct Environment* env, const char* name, const Object obj) +{ + env->strings[i] = malloc(sizeof(char) * strlen(name) + 1); + strcpy(env->strings[i], name); + env->objects[i] = cloneObject(obj); +} + struct Environment envForLambda(const Object* params, const Object* arg_forms, int paramCount, struct Environment* outer) { @@ -80,7 +91,7 @@ struct Environment envForLambda(const Object* params, const Object* arg_forms, i return env; } - env.strings = calloc(sizeof(char*), paramCount + 1); + env.strings = malloc(sizeof(char*) * (paramCount + 1)); env.objects = malloc(sizeof(Object) * (paramCount + 1)); const Object* march = arg_forms; @@ -88,28 +99,23 @@ struct Environment envForLambda(const Object* params, const Object* arg_forms, i const char* newObjName = itemAt(params, i)->string; // Eval the `march` list Object newEnvObj = march ? eval(march, outer) : errorWithContext(NOT_ENOUGH_ARGUMENTS, newObjName); - addToEnv(&env, newObjName, newEnvObj); // Could use eval_forms? + addToEnvAt(i, &env, newObjName, newEnvObj); // Could use eval_forms? cleanObject(&newEnvObj); march = march ? march->forward : NULL; } + env.strings[paramCount] = NULL; return env; } -void addToEnvAt(int i, struct Environment* env, const char* name, const Object obj) -{ - env->strings[i] = malloc(sizeof(char) * strlen(name) + 1); - strcpy(env->strings[i], name); - env->objects[i] = cloneObject(obj); -} - void addToEnv(struct Environment* env, const char* name, const Object obj) { struct Environment* temp_env = env; while (temp_env) { for (int i = 0; i < temp_env->capacity; i++) { if (temp_env->strings[i] == NULL) { - // Add *new* item to env only if we're in the original scope + // Add *new* item to env only if we're in the original scope, + // otherwise keep searching if (temp_env == env) { addToEnvAt(i, env, name, obj); return; @@ -418,7 +424,7 @@ struct Environment defaultEnv() struct Environment e = { .outer = NULL, - .strings = calloc(sizeof(char*), MAX_ENV_ELM), + .strings = malloc(sizeof(char*) * MAX_ENV_ELM), .objects = malloc(sizeof(Object) * MAX_ENV_ELM), .capacity = MAX_ENV_ELM, .refs = 1, @@ -478,9 +484,13 @@ struct Environment defaultEnv() #endif }; - for (int i = 0; i < sizeof(symFuncs) / sizeof(symFuncs[0]); i++) { + int i; + for (i = 0; i < sizeof(symFuncs) / sizeof(symFuncs[0]); i++) { addFunc(symFuncs[i].sym, symFuncs[i].func, &e, i); } + for (; i < e.capacity; i++) { + e.strings[i] = NULL; + } helpInitialized = 1; return e; diff --git a/src/env.h b/src/env.h index e92b4b4..8a94663 100644 --- a/src/env.h +++ b/src/env.h @@ -13,12 +13,6 @@ struct Environment { int refs; }; -struct Dictionary { - int structCount; - int structCapacity; - struct StructDef* structDefs; -}; - struct Environment* global(); void setGlobal(struct Environment* env); diff --git a/src/examples/pebblisp.pbl b/src/examples/pebblisp.pbl index d0ed3fb..026c36d 100644 --- a/src/examples/pebblisp.pbl +++ b/src/examples/pebblisp.pbl @@ -12,9 +12,12 @@ (def nl (ch 10)) -(def config (cat (env "HOME") "/.pebblisp.pbl")) +(def up "..") +(def ~ (env "HOME")) -(def reload (fn () (loadfile config))) +(def config (cat ~ "/.pebblisp.pbl")) + +(def r (fn () (loadfile config))) (def hour (fn (ti) ( (def h (% ti.hour 12)) diff --git a/src/object.c b/src/object.c index e9e0ce7..0dd03ae 100644 --- a/src/object.c +++ b/src/object.c @@ -805,7 +805,7 @@ inline enum errorCode getErrorCode(const Object obj) inline void errorAddContext(Object* o, const char* context, int lineNo, const char* fileName) { - o->error->context = calloc(sizeof(char), RESULT_LENGTH); + o->error->context = malloc(sizeof(char) * RESULT_LENGTH); char* cursor = o->error->context; cursor += sprintf(cursor, "%s", context); if (fileName) { diff --git a/src/pebblisp.c b/src/pebblisp.c index 8b72381..6dc4f8c 100644 --- a/src/pebblisp.c +++ b/src/pebblisp.c @@ -33,7 +33,7 @@ * @param env The environment to add the new definition to * @return The symbol(s) defined */ -Object def(Object* params, int length, struct Environment* env) +Object def(Object* params, unused int length, unused struct Environment* env) { const char* name = params[0].string; @@ -52,7 +52,7 @@ Object def(Object* params, int length, struct Environment* env) * * (struct point (x y)) */ -Object evalStructArgs(const Object* symbol, const Object* fields, struct Environment* env) +Object evalStructArgs(const Object* symbol, const Object* fields, unused struct Environment* env) { const char* name = symbol->string; @@ -311,7 +311,7 @@ Object eval(const Object* obj, struct Environment* env) return errorObject(BAD_TYPE); } -Object structAccess(Object* params, int length, struct Environment* env) +Object structAccess(Object* params, unused int length, unused struct Environment* env) { checkTypes(structAccess) diff --git a/src/pebblisp.h b/src/pebblisp.h index 4cf6c43..1128755 100644 --- a/src/pebblisp.h +++ b/src/pebblisp.h @@ -6,19 +6,20 @@ #include "env.h" #include "object.h" +#define unused __attribute__((unused)) + #define array_length(_array) (sizeof(_array) / sizeof((_array)[0])) #define UNPACK(...) __VA_ARGS__ #define fnn(_name, _docs, ...) \ static const char * const _name ## Doc = _docs; \ -__attribute__((unused)) static const char * const _name ## Tests[] = {__VA_ARGS__}; \ +unused static const char * const _name ## Tests[] = {__VA_ARGS__}; \ _Static_assert(array_length(_name ## Tests) % 2 == 0, "Array of test strings must have exactly one expected result for each test."); \ Object _name(Object* params, int length, struct Environment* env) -// GCC warns without the attribute, even when typeChecks are used #define tfn(_name, _symbol, _type, _docs, ...) \ -__attribute__((unused)) static int (*_name ## TypeChecks[])(Object) = UNPACK _type; \ +unused static int (*_name ## TypeChecks[])(Object) = UNPACK _type; \ static const char * const _name ## Symbol = _symbol; \ fnn(_name, _docs, __VA_ARGS__) diff --git a/src/plfunc.c b/src/plfunc.c index e01d262..a9e624b 100644 --- a/src/plfunc.c +++ b/src/plfunc.c @@ -3,7 +3,7 @@ #include "plfunc.h" -Object reduce(Object* params, int length, struct Environment* env) +Object reduce(Object* params, unused int length, struct Environment* env) { checkTypes(reduce) Object list = params[0]; @@ -21,7 +21,7 @@ Object reduce(Object* params, int length, struct Environment* env) return total; } -Object charAt(Object* params, int length, struct Environment* env) +Object charAt(Object* params, unused int length, unused struct Environment* env) { checkTypes(charAt) Object string = params[0]; @@ -41,7 +41,7 @@ Object charAt(Object* params, int length, struct Environment* env) return c; } -Object filter(Object* params, int length, struct Environment* env) +Object filter(Object* params, unused int length, struct Environment* env) { checkTypes(filter) Object condition = params[0]; @@ -62,7 +62,7 @@ Object filter(Object* params, int length, struct Environment* env) return filtered; } -Object append(Object* params, int length, struct Environment* env) +Object append(Object* params, unused int length, unused struct Environment* env) { checkTypes(append) Object list = params[0]; @@ -73,7 +73,7 @@ Object append(Object* params, int length, struct Environment* env) return newList; } -Object prepend(Object* params, int length, struct Environment* env) +Object prepend(Object* params, unused int length, unused struct Environment* env) { checkTypes(prepend) Object list = params[0]; @@ -85,7 +85,7 @@ Object prepend(Object* params, int length, struct Environment* env) return newList; } -Object at(Object* params, int length, struct Environment* env) +Object at(Object* params, unused int length, unused struct Environment* env) { checkTypes(at) Object index = params[0]; @@ -99,7 +99,7 @@ Object at(Object* params, int length, struct Environment* env) } } -Object rest(Object* params, int length, struct Environment* env) +Object rest(Object* params, unused int length, unused struct Environment* env) { checkTypes(rest) Object list = params[0]; @@ -118,7 +118,7 @@ Object rest(Object* params, int length, struct Environment* env) return ret; } -Object reverse(Object* params, int length, struct Environment* ignore2) +Object reverse(Object* params, unused int length, unused struct Environment* ignore2) { checkTypes(reverse) Object _list = params[0]; @@ -139,7 +139,7 @@ Object reverse(Object* params, int length, struct Environment* ignore2) return rev; } -Object isNum(Object* params, int length, struct Environment* env) +Object isNum(Object* params, unused int length, unused struct Environment* env) { checkTypes(isNum) Object test = params[0]; @@ -147,7 +147,7 @@ Object isNum(Object* params, int length, struct Environment* env) return boolObject(test.type == TYPE_NUMBER); } -Object isList(Object* params, int length, struct Environment* env) +Object isList(Object* params, unused int length, unused struct Environment* env) { checkTypes(isList) Object test = params[0]; @@ -155,7 +155,7 @@ Object isList(Object* params, int length, struct Environment* env) return boolObject(test.type == TYPE_LIST); } -Object isString(Object* params, int length, struct Environment* env) +Object isString(Object* params, unused int length, unused struct Environment* env) { checkTypes(isString) Object test = params[0]; @@ -163,7 +163,7 @@ Object isString(Object* params, int length, struct Environment* env) return boolObject(test.type == TYPE_STRING); } -Object isErr(Object* params, int length, struct Environment* env) +Object isErr(Object* params, unused int length, unused struct Environment* env) { checkTypes(isErr) Object test = params[0]; @@ -171,7 +171,7 @@ Object isErr(Object* params, int length, struct Environment* env) return boolObject(test.type == TYPE_ERROR); } -Object charVal(Object* params, int length, struct Environment* env) +Object charVal(Object* params, unused int length, unused struct Environment* env) { checkTypes(charVal) Object test = params[0]; @@ -179,7 +179,7 @@ Object charVal(Object* params, int length, struct Environment* env) return numberObject(test.string[0]); } -Object printEnvO(Object* params, int length, struct Environment* env) +Object printEnvO(Object* params, int length, unused struct Environment* env) { int printPointers = 0; if (length > 0 && params[0].type == TYPE_BOOL) { @@ -189,7 +189,7 @@ Object printEnvO(Object* params, int length, struct Environment* env) return numberObject(0); } -Object parseEvalO(Object* params, int length, struct Environment* env) +Object parseEvalO(Object* params, unused int length, struct Environment* env) { Object text = params[0]; @@ -209,7 +209,7 @@ Object parseEvalO(Object* params, int length, struct Environment* env) } } -Object catObjects(Object* params, int length, struct Environment* env) +Object catObjects(Object* params, int length, unused struct Environment* env) { checkTypes(catObjects) @@ -235,7 +235,7 @@ Object catObjects(Object* params, int length, struct Environment* env) } -Object len(Object* params, int length, struct Environment* env) +Object len(Object* params, unused int length, unused struct Environment* env) { checkTypes(len) @@ -294,7 +294,7 @@ int areEqual(const Object* obj1, const Object* obj2) return n1 == n2 && areSameType(obj1, obj2); } -Object equ(Object* params, int length, struct Environment* env) +Object equ(Object* params, int length, unused struct Environment* env) { if (length < 2) { return errorObject(NOT_ENOUGH_ARGUMENTS); @@ -309,7 +309,7 @@ Object equ(Object* params, int length, struct Environment* env) return trueObject(); } -Object or(Object* params, int length, struct Environment* env) +Object or(Object* params, int length, unused struct Environment* env) { if (length < 2) { return errorObject(NOT_ENOUGH_ARGUMENTS); @@ -348,7 +348,7 @@ BASIC_COMPARISON(and, &&) #include -Object print(Object* params, int length, struct Environment* env) +Object print(Object* params, int length, unused struct Environment* env) { for (int i = 0; i < length; i++) { _printObj(¶ms[i], 0); @@ -356,7 +356,7 @@ Object print(Object* params, int length, struct Environment* env) return numberObject(0); } -Object numToChar(Object* params, int length, struct Environment* env) +Object numToChar(Object* params, unused int length, unused struct Environment* env) { checkTypes(numToChar) Object c = params[0]; @@ -368,7 +368,7 @@ Object numToChar(Object* params, int length, struct Environment* env) return stringFromSlice(ch, 1); } -Object takeInput(Object* params, int length, struct Environment* env) +Object takeInput(Object* params, int length, unused struct Environment* env) { Object prompt = params[0]; if (length > 0 && prompt.type == TYPE_STRING) { @@ -381,7 +381,7 @@ Object takeInput(Object* params, int length, struct Environment* env) return errorWithContext(NULL_PARSE, "fgets() error"); } -Object loadFile(Object* params, int length, struct Environment* env) +Object loadFile(Object* params, unused int length, struct Environment* env) { checkTypes(loadFile) Object filename = params[0]; @@ -393,21 +393,20 @@ Object loadFile(Object* params, int length, struct Environment* env) return numberObject(1); } -Object cd(Object* params, int length, struct Environment* env) +Object cd(Object* params, unused int length, unused struct Environment* env) { checkTypes(cd) return numberObject(chdir(params[0].string)); } -Object cwd(Object* params, int length, struct Environment* env) +Object cwd(unused Object* params, unused int length, unused struct Environment* env) { char c[128]; - getcwd(c, sizeof(c)); - return nullTerminated(c); + return nullTerminated(getcwd(c, sizeof(c))); } -Object systemCall(Object* params, int length, struct Environment* env) +Object systemCall(Object* params, unused int length, unused struct Environment* env) { checkTypes(systemCall) Object process = params[0]; @@ -442,7 +441,7 @@ char* readFileToString(FILE* input) return string + 1; // Offset past refCount } -Object readFileToObject(Object* params, int length, struct Environment* env) +Object readFileToObject(Object* params, unused int length, unused struct Environment* env) { checkTypes(readFileToObject) Object filename = params[0]; @@ -461,7 +460,7 @@ Object readFileToObject(Object* params, int length, struct Environment* env) return string; } -Object getEnvVar(Object* params, int length, struct Environment* env) +Object getEnvVar(Object* params, unused int length, unused struct Environment* env) { checkTypes(getEnvVar) return nullTerminated(getenv(params[0].string)); @@ -471,7 +470,7 @@ Object getEnvVar(Object* params, int length, struct Environment* env) int timeStructDefinition = -1; -Object getTime(Object* params, int length, struct Environment* env) +Object getTime(unused Object* params, unused int length, struct Environment* env) { if (timeStructDefinition == -1) { parseEval("(struct Time (minute hour sec))", env);