code.c 3.3 KB
Newer Older
1
2
3
4
#include <stdio.h>
#include <stdlib.h>

#include "code.h"
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
5
#include "desc.h"
6
#include "thunk.h"
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
7
#include "mem.h"
8

9
struct Thunk* exec(Code* expr, int frame_ptr, Thunk* target)
10
11
12
{   
	switch(expr->type)
	{
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
13
		case CT_LIT:		
14
15
16
			switch(expr->local_type)
			{
				case LIT_INT:
17
18
19
					return updateI(target, ((LitEntry*) expr)->_int);
				case LIT_BOOL:
					return updateB(target, ((LitEntry*) expr)->_bool);						
20
21
22
23
24
				default:
					printf("Exec: Unhandled LIT type");
					exit(-1);
			}
			break;
25
26
27
		case CT_VAR:
			switch(expr->local_type)
			{
28
				case VAR_FN:		
29
					return updateF(target, get_slice(((VarEntry*) expr)->f, 0));
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
30
31
32
33
					
				case VAR_ARG:
				{
					Thunk* var = stack[frame_ptr - ((VarEntry*) expr)->index];
34
					return forward_to(target, var);
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
35
36
37
38
				}
				case VAR_LOCAL:
				{
					Thunk* var = stack[frame_ptr + ((VarEntry*) expr)->index + 1];
39
					return forward_to(target, var);
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
40
				}
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
41
42
43
			}
			break;
		case CT_APP:		
44
45
46
47
		
			// TODO: check over application
			// TODO: enforce strictness in ADT/Record
		
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
48
49
			VarEntry* var;
			var = ((AppEntry*)expr)->var;
50
51
			Thunk* thunk;
			
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
52
53
			switch(var->base.local_type)
			{
54
				case VAR_FN:		
55
					thunk = updateF(target, get_slice(var->f, expr->nr_args));
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
56
57
					for(int i=0; i<thunk->desc->arity; i++)
					{
58
						thunk->_args[i] = exec(((AppEntry*)expr)->args[i], frame_ptr, NULL);
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
59
60
					}
					return thunk;
61
62
				case VAR_ARG:
					Thunk* basethunk;
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
63
64
					basethunk = stack[frame_ptr - var->index];
					eval(basethunk);
65
					
66
67
68
					thunk = updateF(target, 
						get_slice(basethunk->desc->type == FT_SLICE ?
							((SliceEntry*) basethunk->desc)->forward_ptr : basethunk->desc, basethunk->desc->arity + expr->nr_args));
69
70
71
72
73
74
75
76

					for(int i=0; i<basethunk->desc->arity; i++)
					{
						thunk->_args[i] = basethunk->_args[i];
					}
					
					for(int i=0; i<expr->nr_args; i++)
					{
77
						thunk->_args[basethunk->desc->arity + i] = exec(((AppEntry*)expr)->args[i], frame_ptr, NULL);
78
79
					}
					return thunk;					
80
				default:
81
					printf("Exec: Unhandled VAR type in CT_APP");
82
83
					exit(-1);				
			}
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
84
85
86
87
			break;
		case CT_SELECT:
		{
			Thunk* pattern = exec(((SelectEntry*)expr)->expr, frame_ptr, NULL);
88
89
			pattern = eval(pattern);
								
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
			for(int i=0; i<expr->nr_cases; i++)
			{
				SelectCaseEntry* caseEntry = &((SelectEntry*)expr)->cases[i];
				
				switch(caseEntry->type)
				{
					case SC_CONS:
						// Pattern match
						if((Desc*) caseEntry->cons != pattern->desc) continue;

						// Put the constructor arguments to the stack if matches
						for(int i=0; i<pattern->desc->arity; i++)
						{
							pushs(pattern->_args[i]);
						}
						
						// Fall through on purpose
					case SC_DEFAULT:
						return exec(caseEntry->body, frame_ptr, target);
					default:
						printf("Exec: Unhandled entry type in CT_SELECT");
						exit(-1);		
				}
			}
			
			printf("Exec: no select cases matches");
116
			print(pattern, false);
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
117
118
			exit(-1);			
		}
119
120
		case CT_IF:
		{
121
122
123
			//Thunk* tmp = (Thunk*) malloc(sizeof(Thunk) + 8);
			//tmp->desc = (Desc*) find_desc("add");
			
124
			Thunk* cond = exec(((IfEntry*)expr)->cond, frame_ptr, NULL);
125
			cond = eval(cond);
126
127
128
129
130
131
132
133
134
135
			
			if(readB(cond))
			{
				return exec(((IfEntry*)expr)->texpr, frame_ptr, target);
			}
			else
			{
				return exec(((IfEntry*)expr)->fexpr, frame_ptr, target);
			}
		}			
Laszlo Domoszlai's avatar
Laszlo Domoszlai committed
136
137
138
		default:
			printf("Exec: Unhandled CODE type");
			exit(-1);				
139
140
	}
}
141