|
@@ -8,9 +8,8 @@
|
|
|
#include "StringIntMap.h"
|
|
|
#include "Tokenizer.h"
|
|
|
|
|
|
-#define MAX_BYTES (1024 * 1024)
|
|
|
#define ERROR_LENGTH 256
|
|
|
-#define VARS 256
|
|
|
+#define RETURN_BUFFER 16
|
|
|
|
|
|
static jmp_buf errorJump;
|
|
|
static char error[ERROR_LENGTH] = {'\0'};
|
|
@@ -23,6 +22,9 @@ static int varIndex = 0;
|
|
|
static StringIntMap vars[2];
|
|
|
static FunctionMap functions;
|
|
|
|
|
|
+static int returns[RETURN_BUFFER];
|
|
|
+static int returnIndex = 0;
|
|
|
+
|
|
|
static void cError(const char* format, ...) {
|
|
|
va_list args;
|
|
|
va_start(args, format);
|
|
@@ -241,6 +243,10 @@ static void cFunctionInnerBody(int arguments) {
|
|
|
cLine(t);
|
|
|
}
|
|
|
cAddPop(p, vars[1].entries);
|
|
|
+ for(int i = 0; i < returnIndex; i++) {
|
|
|
+ cSetInt(returns[i], vars[1].entries);
|
|
|
+ }
|
|
|
+ returnIndex = 0;
|
|
|
}
|
|
|
|
|
|
static void cFunctionBody(const char* name, int arguments) {
|
|
@@ -270,6 +276,16 @@ static void cFunction() {
|
|
|
varIndex = 0;
|
|
|
}
|
|
|
|
|
|
+static void cReturn() {
|
|
|
+ if(returnIndex >= RETURN_BUFFER) {
|
|
|
+ cError("too much returns in function around line %d", line);
|
|
|
+ }
|
|
|
+ cAddOperation(OP_POP);
|
|
|
+ returns[returnIndex++] = cReserveInt(vars);
|
|
|
+ cAddOperation(OP_RETURN);
|
|
|
+ cConsumeToken(T_SEMICOLON);
|
|
|
+}
|
|
|
+
|
|
|
static void cPrint() {
|
|
|
cExpression();
|
|
|
cConsumeToken(T_SEMICOLON);
|
|
@@ -283,6 +299,7 @@ static void cLine(Token t) {
|
|
|
case T_PRINT: cPrint(); break;
|
|
|
case T_LITERAL: cLiteral(); break;
|
|
|
case T_FUNCTION: cFunction(); break;
|
|
|
+ case T_RETURN: cReturn(); break;
|
|
|
default: cUnexpectedToken(t);
|
|
|
}
|
|
|
}
|
|
@@ -297,6 +314,7 @@ static void cForEachLine() {
|
|
|
|
|
|
static void cAllocAndCompile() {
|
|
|
varIndex = 0;
|
|
|
+ returnIndex = 0;
|
|
|
simInit(vars);
|
|
|
simInit(vars + 1);
|
|
|
fmInit(&functions);
|