step: savepoint.
This commit is contained in:
		
							parent
							
								
									c4f625caa4
								
							
						
					
					
						commit
						2b9cc75ed5
					
				
							
								
								
									
										79
									
								
								src/mumble.c
									
									
									
									
									
								
							
							
						
						
									
										79
									
								
								src/mumble.c
									
									
									
									
									
								
							| 
						 | 
				
			
			@ -207,7 +207,7 @@ void print_ast(mpc_ast_t* ast, int indent_level)
 | 
			
		|||
    free(indent);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Evaluate the lisval
 | 
			
		||||
// Evaluate the lispval
 | 
			
		||||
lispval* pop_lispval(lispval* v, int i)
 | 
			
		||||
{
 | 
			
		||||
	lispval* r = v->cell[i];
 | 
			
		||||
| 
						 | 
				
			
			@ -229,21 +229,77 @@ lispval* take_lispval(lispval* v, int i){
 | 
			
		|||
	return x;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
lispval* builtin_op(char* op, lispval* v){
 | 
			
		||||
	// For now, ensure all args are numbers
 | 
			
		||||
	for(int i=0; i<v->count; i++){
 | 
			
		||||
		if(v->cell[i]->type != LISPVAL_NUM){
 | 
			
		||||
			return lispval_err("Error: Operating on non-numbers");
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	// Check how many elements
 | 
			
		||||
	if(v->count == 0){
 | 
			
		||||
			return lispval_err("Error: No numbers on which to operate!");
 | 
			
		||||
	} else if(v->count == 1) {
 | 
			
		||||
		if(strcmp(op, "-")){
 | 
			
		||||
			return lispval_num(-v->cell[0]->num);
 | 
			
		||||
		}else {
 | 
			
		||||
			return lispval_err("Error: Non minus unary operation");
 | 
			
		||||
		}
 | 
			
		||||
	} else if (v->count >= 2){
 | 
			
		||||
		lispval* x = pop_lispval(v,0);
 | 
			
		||||
 | 
			
		||||
		while(v->count > 0){
 | 
			
		||||
			/* Pop the next element */
 | 
			
		||||
			lispval* y = pop_lispval(v, 0);
 | 
			
		||||
 | 
			
		||||
			if (strcmp(op, "+") == 0) { x->num += y->num; }
 | 
			
		||||
			if (strcmp(op, "-") == 0) { x->num -= y->num; }
 | 
			
		||||
			if (strcmp(op, "*") == 0) { x->num *= y->num; }
 | 
			
		||||
 | 
			
		||||
			if (strcmp(op, "/") == 0) {
 | 
			
		||||
				if (y->num == 0) {
 | 
			
		||||
					delete_lispval(x); delete_lispval(y);
 | 
			
		||||
					return lispval_err("Error: Division By Zero!");
 | 
			
		||||
				}
 | 
			
		||||
				x->num /= y->num;
 | 
			
		||||
			}
 | 
			
		||||
 | 
			
		||||
			delete_lispval(y);
 | 
			
		||||
		}
 | 
			
		||||
		return x;
 | 
			
		||||
	} else {
 | 
			
		||||
		return lispval_err("Error: Incorrect number of args. Perhaps a lispval->count was wrongly initialized?");
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
lispval* evaluate_lispval(lispval* l)
 | 
			
		||||
{
 | 
			
		||||
  // Evaluate the children
 | 
			
		||||
	for(int i=0; i<l->count; i++){
 | 
			
		||||
		l->cell[i] = evaluate_lispval(l->cell[i]);
 | 
			
		||||
		
 | 
			
		||||
	}
 | 
			
		||||
		// Check if any are errors.
 | 
			
		||||
	for(int i=0; i<l->count; i++){
 | 
			
		||||
		if(l->cell[i]->type == LISPVAL_ERR){ 
 | 
			
		||||
			char* msg = l->cell[i]->err; // lispval_take
 | 
			
		||||
			lispval* l2 = lispval_err(msg);
 | 
			
		||||
			delete_lispval(l);
 | 
			
		||||
			return l2;
 | 
			
		||||
			return pop_lispval(l, i);
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	
 | 
			
		||||
	// Check if the first item of a list is a symbol.
 | 
			
		||||
	if(l->count > 0 && l->cell[0]->type == LISPVAL_SYM){
 | 
			
		||||
		/* lispval* lisp_op = pop_lispval(l, 0);
 | 
			
		||||
		lispval* result = builtin_op(lisp_op->sym, l);
 | 
			
		||||
		delete_lispval(l);
 | 
			
		||||
		delete_lispval(lisp_op);
 | 
			
		||||
		return result;
 | 
			
		||||
		*/
 | 
			
		||||
		return l;
 | 
			
		||||
	}else{
 | 
			
		||||
		return l;
 | 
			
		||||
		// In particular, leave (5) (the list that contains 5) as is
 | 
			
		||||
		// rather than returning 5.
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	return l;
 | 
			
		||||
}
 | 
			
		||||
| 
						 | 
				
			
			@ -295,12 +351,15 @@ int main(int argc, char** argv)
 | 
			
		|||
                // if(VERBOSE) printf("\n\nEvaluating the AST");
 | 
			
		||||
                // lispval result = evaluate_ast(ast);
 | 
			
		||||
                lispval* l = read_lispval(ast);
 | 
			
		||||
                if (VERBOSE)
 | 
			
		||||
                if (VERBOSE){
 | 
			
		||||
                    printf("\n\nTree printing: ");
 | 
			
		||||
                print_lispval_tree(l, 0);
 | 
			
		||||
                if (VERBOSE)
 | 
			
		||||
										print_lispval_tree(l, 0);
 | 
			
		||||
								}
 | 
			
		||||
                if (VERBOSE){
 | 
			
		||||
                    printf("\nParenthesis printing: \n");
 | 
			
		||||
                print_lispval_parenthesis(l);
 | 
			
		||||
										print_lispval_parenthesis(l);
 | 
			
		||||
								}
 | 
			
		||||
								evaluate_lispval(l);
 | 
			
		||||
                delete_lispval(l);
 | 
			
		||||
            } else {
 | 
			
		||||
                /* Otherwise Print the Error */
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
		Reference in New Issue
	
	Block a user