Archived
1
0
Fork 0

Started on function type and added copy operation

This commit is contained in:
Brandon Rozek 2018-06-09 18:40:32 -04:00
parent a47f72f510
commit e5d5aee39e
9 changed files with 74 additions and 14 deletions

View file

@ -1,5 +1,5 @@
run: prompt.c loperations.o lnumbers.o lexpressions.o lio.o lerror.o mpc.o
cc -std=c99 -Wall prompt.c loperations.o lnumbers.o lexpressions.o lio.o lerror.o mpc.o -ledit -lm -o prompt
run: prompt.c loperations.o lnumbers.o lexpressions.o lio.o lerror.o lenvironment.o mpc.o
cc -std=c99 -Wall prompt.c loperations.o lnumbers.o lexpressions.o lio.o lerror.o lenvironment.o mpc.o -ledit -lm -o prompt
loperations.o: lval/operations.c lval/operations.h
cc -std=c99 -Wall -c lval/operations.c -o loperations.o
lnumbers.o: lval/numbers.c lval/numbers.h
@ -10,6 +10,8 @@ lio.o: lval/io.c lval/io.h
cc -std=c99 -Wall -c lval/io.c -o lio.o
lerror.o: lval/error.c lval/error.h
cc -std=c99 -Wall -c lval/error.c -o lerror.o
lenvironment.o: lval/environment.c lval/environment.h
cc -std=c99 -Wall -c lval/environment.c -o lenvironment.o
mpc.o: mpc.c mpc.h
cc -std=c99 -Wall -lm -c mpc.c
clean:

2
lval.h
View file

@ -14,5 +14,7 @@
#include "lval/operations.h"
// Add the ability to print out lval structures
#include "lval/io.h"
// Add environments, variables, and functions
#include "lval/environment.h"
#endif

View file

@ -1,24 +1,34 @@
#ifndef LVAL_BASE
#define LVAL_BASE
struct lval;
struct lenv;
typedef struct lval lval;
typedef struct lenv lenv;
typedef lval* (*lbuiltin) (lenv*, lval*);
typedef union typeval {
long num;
double dec;
} TypeVal;
// A lispy value can either be a number, error, symbol, or an expression
typedef struct lval {
struct lval {
int type;
TypeVal data;
// Error and symbols contain string data
char* err;
char* sym;
lbuiltin fun;
// Count and pointer to a list of lval*
int count;
struct lval** cell;
} lval;
lval** cell;
};
// Possible lispy value types
enum { LVAL_ERR, LVAL_LONG, LVAL_DOUBLE, LVAL_SYM, LVAL_SEXPR, LVAL_QEXPR };
enum { LVAL_ERR, LVAL_LONG, LVAL_DOUBLE, LVAL_SYM, LVAL_SEXPR, LVAL_QEXPR, LVAL_FUN };
#endif

8
lval/environment.c Normal file
View file

@ -0,0 +1,8 @@
#include "environment.h"
lval* lval_fun(lbuiltin func) {
lval* v = malloc(sizeof(lval));
v->type = LVAL_FUN;
v->fun = func;
return v;
}

7
lval/environment.h Normal file
View file

@ -0,0 +1,7 @@
#ifndef LVAL_ENVIRONMENT
#define LVAL_ENVIRONMENT
#include "base.h"
lval* lval_fun(lbuiltin func);
#endif

View file

@ -29,6 +29,8 @@ void flval_print(FILE* stream, lval* v) {
case LVAL_SEXPR: flval_expr_print(stream, v, '(', ')'); break;
case LVAL_QEXPR: flval_expr_print(stream, v, '{', '}'); break;
case LVAL_FUN: fprintf(stream, "<function>"); break;
}
}

View file

@ -54,6 +54,7 @@ void lval_del(lval* v) {
switch (v->type) {
case LVAL_LONG: break;
case LVAL_DOUBLE: break;
case LVAL_FUN: break;
// Free the string data
case LVAL_ERR: free(v->err); break;
@ -75,4 +76,36 @@ void lval_del(lval* v) {
free(v);
}
lval* lval_copy(lval* v) {
lval* x = (lval*) malloc(sizeof(lval));
x->type = v->type;
switch (v->type) {
// Copy numbers and functions directly
case LVAL_LONG: x->data.num = v->data.num; break;
case LVAL_DOUBLE: x->data.dec = v->data.dec; break;
case LVAL_FUN: x->fun = v->fun; break;
// Copy strings using malloc and strcpy
case LVAL_ERR:
x->err = (char*) malloc(strlen(v->err) + 1);
strcpy(x->err, v->err); break;
case LVAL_SYM:
x->sym = (char*) malloc(strlen(v->sym) + 1);
strcpy(x->sym, v->sym); break;
// Copy lists by copying each sub-expression
case LVAL_SEXPR:
case LVAL_QEXPR:
x->count = v->count;
x->cell = (lval**) malloc(sizeof(lval*) * x->count);
for (int i = 0; i < x->count; i++) {
x->cell[i] = lval_copy(v->cell[i]);
}
break;
}
return x;
}

View file

@ -8,11 +8,12 @@
lval* lval_sym(char* s);
/*
Methods to read (parse AST), evaluate,
and delete lval structures
Methods to read (parse AST), evaluate,
copy, and delete lval structures
*/
lval* lval_read(mpc_ast_t* t);
lval* lval_eval(lval* v);
void lval_del(lval* v);
lval* lval_copy(lval* v);
#endif

View file

@ -53,12 +53,7 @@ int main (int argc, char** argv) {
"number : /[0-9]+/; "
"long : /-?[0-9]+/; "
"double : <long> '.' <number>; "
"symbol : '+' | '-' | '*' | '/' | '%' \
| '^' | \"min\" | \"max\" \
| \"list\" | \"head\" | \"tail\" \
| \"join\" | \"eval\" | \"len\" \
| \"init\" | \"cons\"; "
"symbol : /[a-zA-Z0-9_+\\-*\\/\\\\=<>!&]+/; "
"sexpr : '(' <expr>* ')'; "
"qexpr : '{' <expr>* '}'; "
"expr : (<double> | <long>) | <symbol> | <sexpr> | <qexpr>; "