-
Notifications
You must be signed in to change notification settings - Fork 2
/
dplisp.cfg
174 lines (149 loc) · 12.3 KB
/
dplisp.cfg
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
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
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
// Basically, lisp is good because you could do:
// ( echo "this is fun" ( get me a return value ) )
exec blubvm/vmx86.cfg
// we use "fetch" from our utility library, but with different quoting
alias util::fetch "\"alias\" @_tmp \"set $2 \\\"$${${1 asis}}\\\"\"; @_tmp; unalias @_tmp"
alias "(" "@lisp_mainexpr ${* asis} )"
alias @null@ ""
set lisp_max_lambdas 20
set %lisp_token ""
set %lisp_retn ""
set %lisp_expr ""
set %lisp_tokenparser "@null@"
set %lisp_Estack "x"
set %lisp_Tstack "x"
// DP-ized stack functionality... it's lame, but it avoids the need for calculations...
// we need a count here too, let's support up to 16 parameters
// this is abused for lambda function names too
set %param::0.next "1"; set %param::1.next "2"; set %param::2.next "3"; set %param::3.next "4"
set %param::4.next "5"; set %param::5.next "6"; set %param::6.next "7"; set %param::7.next "8"
set %param::8.next "9"; set %param::9.next "10"; set %param::10.next "11"; set %param::11.next "12"
set %param::12.next "13"; set %param::13.next "14"; set %param::14.next "15"; set %param::15.next "16"
set %param::16.next "0"
// for the expression and token stack, we make abuse of cvars:
set %lisp_function 0
alias @lisp_bump_function "util::fetch %param::${%lisp_function}.next %lisp_function"
// manage a stack of expressions
alias @lisp_push "@lisp_push_expr; @lisp_push_token"
alias @lisp_pop "@lisp_pop_token; @lisp_pop_expr"
alias @lisp_push_expr "set \"%lisp::E[${%lisp_Estack}x].prev\" \"${%lisp_Estack}\"; @lisp_push_expr[2]"
alias @lisp_push_expr[2] "set \"%lisp::E[${%lisp_Estack}].value\" \"${%lisp_expr}\"; @lisp_push_expr[3]"
alias @lisp_push_expr[3] "set %lisp_Estack \"${%lisp_Estack}x\"; set %lisp_expr \"\""
alias @lisp_pop_expr "util::fetch \"%lisp::E[${%lisp_Estack}].prev\" %lisp_Estack; @lisp_pop_expr[2]"
alias @lisp_pop_expr[2] "util::fetch \"%lisp::E[${%lisp_Estack}].value\" %lisp_expr"
alias @lisp_push_token "set \"%lisp::T[${%lisp_Tstack}x].prev\" \"${%lisp_Tstack}\"; @lisp_push_token[2]"
alias @lisp_push_token[2] "set \"%lisp::T[${%lisp_Tstack}].value\" \"${%lisp_token}\"; @lisp_push_token[3]"
alias @lisp_push_token[3] "set %lisp_Tstack \"${%lisp_Tstack}x\"; set %lisp_token \"\""
alias @lisp_pop_token "util::fetch \"%lisp::T[${%lisp_Tstack}].prev\" %lisp_Tstack; @lisp_pop_token[2]"
alias @lisp_pop_token[2] "util::fetch \"%lisp::T[${%lisp_Tstack}].value\" %lisp_token"
alias @lisp_mainexpr "@lisp_expr ${* asis}; @_lisp_nextexpr"
alias @_lisp_nextexpr "@_lisp_nextexpr2 ${%lisp_token asis}"
alias @_lisp_nextexpr2 "set %lisp_action \"$1\"; toggle %lisp_action @null@ ( @_lisp_donext; @_lisp_action ${* asis}"
alias @_lisp_donext "${* asis}"
alias @lisp_expr "@lisp_push_expr; @_lisp_expr1 ${* asis}; @lisp_pop_expr"
alias @_lisp_parse_token "${%lisp_tokenparser asis}"
// alias @_lisp_parse_token2 "set %lisp_token ${%lisp_token}"
alias @_lisp_next "@_lisp_parse_token; ${%lisp_action} ${* asis}"
alias @_lisp_action "${%lisp_action} ${* asis}"
alias @_lisp_expr1 "set %lisp_token \"$1\"; set %lisp_action \"$1\"; toggle %lisp_action @_lisp_eat1 \"(\" @_lisp_subexpr1 \")\" @_lisp_end; @_lisp_next ${2- asis}"
alias @_lisp_expr2 "set %lisp_token \"$1\"; set %lisp_action \"$1\"; toggle %lisp_action @_lisp_eat \"(\" @_lisp_subexpr2 \")\" @_lisp_end; @_lisp_next ${2- asis}"
alias @_lisp_eat "\"alias\" @_tmp \"set %lisp_expr \\\"${%lisp_expr} $${${%lisp_token}}\\\"\"; @_tmp; unalias @_tmp; @_lisp_expr ${* asis}"
// eat1 should not eat, but instead parse the first function and then go to expr2
// so that a quote becomes an actual quote, it must then parse parentheses correctly
alias @_lisp_eat1 "@_lisp_translate; @_lisp_first ${* asis}"
alias @_lisp_eat "set %lisp_expr \"${%lisp_expr} ${%lisp_token}\"; @_lisp_expr2 ${* asis}"
alias @_lisp_eate1 "set %lisp_expr \"${%lisp_expr} ${%lisp_token}\"; @_lisp_expr1 ${* asis}"
alias @_lisp_subexpr1 "@lisp_expr ${* asis}; @_lisp_eat1ret; @_lisp_after_end"
alias @_lisp_subexpr2 "@lisp_expr ${* asis}; @_lisp_eatret; @_lisp_after_end"
alias @_lisp_eat1ret "set %lisp_oldtoken \"${%lisp_token}\"; set %lisp_token ${%lisp_retn}; @_lisp_translate; @_lisp_eat1ret2"
alias @_lisp_eat1ret2 "set %lisp_retn \"${%lisp_token}\"; set %lisp_token \"${%lisp_oldtoken}\"; @_lisp_eatret"
alias @_lisp_eatret "set %lisp_expr \"${%lisp_expr} \\\"${%lisp_retn}\\\"\""
alias @_lisp_eatret "set %lisp_expr \"${%lisp_expr} ${%lisp_retn}\""
alias @_lisp_eatret "set %lisp_expr \"${%lisp_expr} \\\"${%lisp_retn}\\\"\""
alias @_lisp_end "${%lisp_expr asis}; @_lisp_end2 ${* asis}"
alias @_lisp_end2 "set %lisp_retn \"$eax\"; set %lisp_token \"$*\""
alias @_lisp_endx "${%lisp_expr asis}; set %lisp_action \"$1\"; toggle %lisp_action @_lisp_endend ( @_lisp_endbeg; @_lisp_action ${* asis}"
alias @_lisp_endend "set %lisp_retn \"$eax\"; set %lisp_token \"$*\""
alias @_lisp_endx2 "@_lisp_endx3 ${%lisp_token asis}"
alias @_lisp_endx3 "set %lisp_action \"$1\"; toggle %lisp_action @null@ ( @_lisp_endbeg; @_lisp_action ${* asis}"
alias @_lisp_endbeg "@_lisp_expr1 ${2- asis}"
alias @_lisp_after_end "@_lisp_expr2 ${%lisp_token asis}"
alias @_lisp_first "@_lisp_eat ${* asis}"
alias @_lisp_first "set %lisp_action \"${%lisp_token}\"; toggle %lisp_action @_lisp_eate1 @lisp%quote @_lisp_lquote @lisp%if @_lisp_ifquote @lisp%lambda @_lisp_lbdquote; @_lisp_action ${* asis}"
alias @_lisp_lbdquote "@lisp%lambda ${* asis}; @_lisp_lbdend"
alias @_lisp_lbdend "echo \"after lambda T: ${%lisp_token}\"; echo \"after lambda E: ${%lisp_expr}\"; echo \"after lambda A: $eax\"; set %lisp_token \"@null@\"; @_lisp_eat ${%lisp_token asis}";
alias @_lisp_lbdend "set %lisp_expr \"\"; set %lisp_token \"@null@\"; @_lisp_expr2 ${%lisp_token asis}";
alias @_lisp_ifquote "@lisp%if ${* asis}; @_lisp_lbdend"
alias @_lisp_lquote "@lisp%quote ${* asis}; @_lisp_dolquote; @_lisp_lbdend"
alias @_lisp_dolquote "${%lisp_expr asis}"
//; @_lisp_lbdend"
// lisp functions only and stuff
set %lisp_funcs_math "x-+ @lisp%add x-- @lisp%sub x-* @lisp%mul x-/ @lisp%div"
set %lisp_funcs_common "x-get @lisp%get x-quote @lisp%quote x-lambda @lisp%lambda x-if @lisp%if"
alias @_lisp_translate "set %lisp_tmp \"${%lisp_token}\"; set %lisp_token \"x-${%lisp_token}\"; @_lisp_translat1"
alias @_lisp_translat1 "toggle %lisp_token \"${%lisp_tmp}\" ${%lisp_funcs_math asis} ${%lisp_funcs_common asis}"
// lambda function creation
// to add a parameter, we use:
// set %lisp_tmp ${%lisp_token}; toggle %lisp_token %lisp_tmp PARAMETER
alias @_lisp_new_param "set %lambda_paramcnt 1; set %lisp_tokenparser \"\""
alias @_lisp_add_param "set %lisp_tokenparser \"${%lisp_tokenparser} \\\\\\\"x-$1\\\\\\\" \\\\\\\"$$$$${%lambda_paramcnt}\\\\\\\"\"; @_lisp_add_param[1]"
alias @_lisp_add_param[1] "util::fetch %param::${%lambda_paramcnt}.next %lambda_paramcnt"
// quoting means, we quote ( and ), and just parse until we actually hit a )
alias @lisp%quote "set %lisp::quote_trans @null@; @_lquote ${* asis}"
alias @_lquote "set %lisp_token \"\"; set %lisp_expr \"\"; @_lquote[2] ${* asis}"
alias @_lquote[2] "set %lisp::quote_context quote; set %lisp::quote_use \"quote ...\"; set %lisp::quote_end @_lquote_endquot; @_quote_quote ${* asis}"
alias @_lquote_endquot "set %lisp_expr \"${%lisp_expr} )\"; set %lisp_token \") $*\""
// "if" expression, execute if the condition is true
// parse the condition and the code, then execute the code if the condition is true
// we use the lambda code to parse the result
alias @lisp%if "set %lisp::quote_trans @null@; set %lisp_token \"\"; set %lisp_expr \"(\"; @_if_cond ${* asis}"
alias @_if_cond "set %lisp::quote_context if; set %lisp::quote_use \"usage: ( if ^3( cond )^7 ( body ) )\"; @_if_cond[2] ${* asis}"
alias @_if_cond[2] "set %lisp::quote_end @_if_endquot; @_quote_body ${* asis}"
alias @_if_endquot "set %lisp_expr \"${%lisp_expr} )\"; set %lisp_action \"$1\"; toggle %lisp_action @_if_enderr ( @_if_ontrue; @_lisp_action ${* asis}"
alias @_if_enderr "echo \"^3usage: ^7( if ( cond ) ^3( body )^7 )\""
alias @_if_ontrue "${%lisp_expr asis}; set %lisp::quote_end @_if_endtrue; set %lisp::quote_use \"usage: ( if ( cond ) ^3( body )^7 )\"; @_if_ontrue[2] ${* asis}"
alias @_if_ontrue[2] "set %lisp_expr \"(\"; set %lisp_token \"\"; @_quote_body ${* asis}"
alias @_if_ontrue[3] "set %lisp_expr \"${%lisp_expr} (\"; @_quote_body ${* asis}"
alias @_if_endtrue "set %lisp_expr \"${%lisp_expr} )\"; set %lisp_action \"$1\"; toggle %lisp_action @_if_donetrue ( @_if_ontrue[3]; @_lisp_action ${* asis}"
alias @_if_donetrue "set %lisp_action $eax; toggle %lisp_action @_if_exec 0 @_if_skip; @_lisp_action ${* asis}"
alias @_if_exec "set eax \"%%EMPTY%%\"; ${%lisp_expr asis}; set %lisp_token \"$*\"; @_if_end"
alias @_if_skip "set eax \"%%EMPTY%%\"; set %lisp_token \"$*\"; @_if_end"
alias @_if_end "set %lisp_action \"x-$eax\"; toggle %lisp_action \"$eax\" x-%%EMPTY%% @null@; @_if_end[2]"
alias @_if_end[2] "set eax \"${%lisp_action}\""
// lambda is part of the common lisp, so it is @lisp%lambda
alias @lisp%lambda "set %lisp::quote_trans @_param_translate; @lisp_bump_function; @_lambda_start; @_lambda_expr ${* asis} ); @_lambda_end"
alias @_lambda_next "${%lisp_action} ${* asis}"
alias @_lambda_start "@lisp_push_expr; set %lisp_expr \"(\"; @lisp_push_token; @_lisp_new_param"
alias @_lambda_end "@_lambda_commit; @lisp_pop_token; @lisp_pop_expr"
alias @_lambda_commit "mov eax \"@lambda%${%lisp_function}\"; \"alias\" @lambda%${%lisp_function} \"${%lisp_expr}\""
alias @_lambda_expr "set %lisp_action \"$1\"; toggle %lisp_action @_lambda_error1 \"(\" @_lambda_params; @_lambda_next ${2- asis}"
alias @_lambda_error1 "echo ^3lambda: ^7usage: lambda ^2( [parameterlist] )^7 ( [commands] ); echo before \"$*\""
alias @_lambda_params "set %lisp_token \"$1\"; set %lisp_action \"$1\"; toggle %lisp_action @_lambda_pushpar \")\" @_lambda_body; @_lambda_next ${2- asis}"
alias @_lambda_pushpar "@_lisp_add_param \"${%lisp_token}\"; @_lambda_params ${* asis}"
alias @_lambda_body "set %lisp::quote_context lambda; set %lisp::quote_use \"lambda ( [parameterlist] ) ^3( [commands] )^7\"; @_lambda_body[2] ${* asis}"
alias @_lambda_body[2] "set %lisp::quote_end @_lambda_endquot; @_quote_body ${* asis}"
alias @_quote_body "set %lisp_action \"$1\"; toggle %lisp_action @_quote_error2 \"(\" @_quote_quote; @_lisp_action ${2- asis}"
alias @_quote_error2 "echo \"^3${%lisp::quote_context}: ^7usage: ${%lisp::quote_use}\"; echo before \"$*\""
alias @_quote_quote "set %lisp_token \"$1\"; set %lisp_action \"$1\"; toggle %lisp_action @_quote_eat ( @_quote_subexpr ) ${%lisp::quote_end}; @_lisp_action ${2- asis}"
alias @_quote_eat "${%lisp::quote_trans}; @_quote_eat2 ${* asis}"
alias @_quote_eat2 "set %lisp_expr \"${%lisp_expr} \\\"${%lisp_token}\\\"\"; @_quote_quote ${* asis}"
alias @_quote_eat2 "set %lisp_expr \"${%lisp_expr} ${%lisp_token}\"; @_quote_quote ${* asis}"
// instead of different quoting, implement a proper ( quote ) :P
alias @_quote_subexpr "${%lisp::quote_trans}; @_quote_subexp2 ${* asis}"
alias @_quote_subexp2 "set %lisp_expr \"${%lisp_expr} ${%lisp_token}\"; @_quote_quote ${* asis}; @_quote_subexp3"
alias @_quote_subexp3 "@_quote_quote ${%lisp_token asis}"
alias @_lambda_endquot "set %lisp_expr \"${%lisp_expr} )\"; set %lisp_action \"$1\"; toggle %lisp_action @_lambda_endend ( @_lambda_endbeg; @_lambda_next ${* asis}"
alias @_lambda_endend "set %lisp_token \"$*\""
alias @_lambda_endbeg "set %lisp_expr \"${%lisp_expr} (\"; @_quote_quote ${2- asis}"
alias @_param_translate "set %lisp_tmp \"${%lisp_token}\"; set %lisp_token \"x-${%lisp_token}\"; @_param_translat2"
alias @_param_translat2 "\"alias\" @_tmp \"toggle %lisp_token \\\"$${%lisp_tmp}\\\" ${%lisp_tokenparser asis}\"; @_tmp; unalias @_tmp"
// useful functions
alias get "\"alias\" @_tmp \"set eax $${$1}\"; @_tmp; unalias @_tmp"
alias quote "\"alias\" @_tmpx \"${* asis}\"; @_tmpx; unalias @_tmpx"
// some important functions - or: the lisp library
alias @lisp%get "\"alias\" @_tmp \"set eax $${$1}\"; @_tmp; unalias @_tmp"
alias @old::lisp%quote "\"alias\" @_tmpx \"${* asis}\"; @_tmpx; unalias @_tmpx"
alias @lisp%add "menu_cmd rpn /eax $1 $2 + def"
alias @lisp%sub "menu_cmd rpn /eax $1 $2 - def"
alias @lisp%mul "menu_cmd rpn /eax $1 $2 * def"
alias @lisp%div "menu_cmd rpn /eax $1 $2 / def"