2 SuperCollider real time audio synthesis system
3 Copyright (c) 2002 James McCartney. All rights reserved.
4 http://www.audiosynth.com
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
22 #include "PyrParseNode.h"
24 #include "PyrKernel.h"
26 #include "PyrPrimitive.h"
33 # define snprintf _snprintf
34 # define PATH_MAX _MAX_PATH
40 void dumpNodeList(PyrParseNode
*node
)
42 for (; node
; node
= node
->mNext
) {
47 void PyrCurryArgNode::dump(int level
)
49 postfl("%2d CurryArg %d\n", level
, mArgNum
);
52 void PyrSlotNode::dump(int level
)
54 if (mClassno
== pn_PushLitNode
)
56 else if (mClassno
== pn_PushNameNode
)
57 postfl("%2d PushName '%s'\n", level
, slotRawSymbol(&mSlot
)->name
);
58 else if (mClassno
== pn_LiteralNode
)
61 postfl("%2d SlotNode\n", level
);
64 DUMPNODE(mNext
, level
);
67 void PyrPushKeyArgNode::dump(int level
)
69 postfl("%2d PushKeyArgNode\n", level
);
70 DUMPNODE(mSelector
, level
+1);
71 DUMPNODE(mExpr
, level
+1);
72 DUMPNODE(mNext
, level
);
75 void PyrClassExtNode::dump(int level
)
77 postfl("%2d ClassExt '%s'\n", level
, slotRawSymbol(&mClassName
->mSlot
)->name
);
78 DUMPNODE(mMethods
, level
+1);
79 DUMPNODE(mNext
, level
);
82 void PyrClassNode::dump(int level
)
84 postfl("%2d Class '%s'\n", level
, slotRawSymbol(&mClassName
->mSlot
)->name
);
85 DUMPNODE(mSuperClassName
, level
+1);
86 DUMPNODE(mVarlists
, level
+1);
87 DUMPNODE(mMethods
, level
+1);
88 DUMPNODE(mNext
, level
);
91 void PyrMethodNode::dump(int level
)
93 postfl("%2d MethodNode '%s' %s\n", level
, slotRawSymbol(&mMethodName
->mSlot
)->name
,
94 mPrimitiveName
? slotRawSymbol(&mPrimitiveName
->mSlot
)->name
:"");
95 DUMPNODE(mArglist
, level
+1);
96 DUMPNODE(mBody
, level
+1);
97 DUMPNODE(mNext
, level
);
100 void PyrArgListNode::dump(int level
)
102 postfl("%2d ArgList\n", level
);
103 DUMPNODE(mVarDefs
, level
+1);
104 DUMPNODE(mRest
, level
+1);
105 DUMPNODE(mNext
, level
);
108 void PyrVarListNode::dump(int level
)
110 postfl("%2d VarList\n", level
);
111 DUMPNODE(mVarDefs
, level
+1);
112 DUMPNODE(mNext
, level
);
115 void PyrVarDefNode::dump(int level
)
117 postfl("%2d VarDef '%s'\n", level
, slotRawSymbol(&mVarName
->mSlot
)->name
);
118 DUMPNODE(mDefVal
, level
);
119 DUMPNODE(mNext
, level
);
122 void PyrCallNode::dump(int level
)
124 postfl("%2d Call '%s'\n", level
, slotRawSymbol(&mSelector
->mSlot
)->name
);
125 DUMPNODE(mArglist
, level
+1);
126 DUMPNODE(mKeyarglist
, level
+1);
127 DUMPNODE(mNext
, level
);
130 void PyrBinopCallNode::dump(int level
)
132 postfl("%2d BinopCall '%s'\n", level
, slotRawSymbol(&mSelector
->mSlot
)->name
);
133 DUMPNODE(mArglist
, level
+1);
134 DUMPNODE(mNext
, level
);
137 void PyrDropNode::dump(int level
)
139 postfl("%2d Drop (\n", level
);
140 DUMPNODE(mExpr1
, level
+1);
141 postfl(" -> %2d Drop\n", level
);
142 DUMPNODE(mExpr2
, level
+1);
143 postfl(") %2d Drop\n", level
);
144 DUMPNODE(mNext
, level
);
147 void PyrSlotNode::dumpPushLit(int level
)
149 postfl("%2d PushLit\n", level
);
150 if (!IsPtr(&mSlot
)) dumpPyrSlot(&mSlot
);
152 DUMPNODE((PyrParseNode
*)slotRawObject(&mSlot
), level
);
156 void PyrSlotNode::dumpLiteral(int level
)
158 postfl("%2d Literal\n", level
);
159 if (!IsPtr(&mSlot
)) dumpPyrSlot(&mSlot
);
161 DUMPNODE((PyrParseNode
*)slotRawObject(&mSlot
), level
);
165 void PyrReturnNode::dump(int level
)
167 postfl("%2d Return (\n", level
);
168 DUMPNODE(mExpr
, level
+1);
169 postfl(") %2d Return \n", level
);
170 DUMPNODE(mNext
, level
);
173 void PyrBlockReturnNode::dump(int level
)
175 postfl("%2d FuncReturn\n", level
);
176 DUMPNODE(mNext
, level
);
179 void PyrAssignNode::dump(int level
)
181 postfl("%2d Assign '%s'\n", level
, slotRawSymbol(&mVarName
->mSlot
)->name
);
182 DUMPNODE(mVarName
, level
+1);
183 DUMPNODE(mExpr
, level
+1);
184 DUMPNODE(mNext
, level
);
187 void PyrSetterNode::dump(int level
)
189 //postfl("%2d Assign '%s'\n", level, slotRawSymbol(&mVarName->mSlot)->name);
190 DUMPNODE(mSelector
, level
+1);
191 DUMPNODE(mExpr1
, level
+1);
192 DUMPNODE(mExpr2
, level
+1);
195 void PyrMultiAssignNode::dump(int level
)
197 postfl("%2d MultiAssign\n", level
);
198 DUMPNODE(mVarList
, level
+1);
199 DUMPNODE(mExpr
, level
+1);
200 DUMPNODE(mNext
, level
);
203 void PyrMultiAssignVarListNode::dump(int level
)
205 postfl("%2d MultiAssignVarList\n", level
);
206 DUMPNODE(mVarNames
, level
+1);
207 DUMPNODE(mRest
, level
+1);
208 DUMPNODE(mNext
, level
);
211 void PyrDynDictNode::dump(int level
)
213 postfl("%2d DynDict\n", level
);
214 DUMPNODE(mElems
, level
+1);
215 DUMPNODE(mNext
, level
);
218 void PyrDynListNode::dump(int level
)
220 postfl("%2d DynList\n", level
);
221 DUMPNODE(mElems
, level
+1);
222 DUMPNODE(mNext
, level
);
225 void PyrLitListNode::dump(int level
)
227 postfl("%2d LitList\n", level
);
228 postfl(" %2d mElems\n", level
);
229 DUMPNODE(mElems
, level
+1);
230 postfl(" %2d mNext\n", level
);
231 DUMPNODE(mNext
, level
);
234 void PyrBlockNode::dump(int level
)
236 postfl("%2d Func\n", level
);
237 DUMPNODE(mArglist
, level
+1);
238 DUMPNODE(mBody
, level
+1);
239 DUMPNODE(mNext
, level
);
242 void dumpPyrSlot(PyrSlot
* slot
)
245 slotString(slot
, str
);
249 void slotString(PyrSlot
*slot
, char *str
)
251 switch (GetTag(slot
)) {
253 sprintf(str
, "Integer %d", slotRawInt(slot
));
256 sprintf(str
, "Character %d '%c'", static_cast<int>(slotRawChar(slot
)), static_cast<int>(slotRawChar(slot
)));
259 if (strlen(slotRawSymbol(slot
)->name
) > 240) {
261 memcpy(str2
, slotRawSymbol(slot
)->name
, 240);
263 snprintf(str
, 256, "Symbol '%s...'", str2
);
265 snprintf(str
, 256, "Symbol '%s'", slotRawSymbol(slot
)->name
);
269 if (slotRawObject(slot
)) {
270 PyrClass
* classptr
= slotRawObject(slot
)->classptr
;
271 if (classptr
== class_class
) {
272 sprintf(str
, "class %s (%p)",
273 slotRawSymbol(&((PyrClass
*)slotRawObject(slot
))->name
)->name
, slotRawObject(slot
));
274 } else if (classptr
== class_string
) {
277 if (slotRawObject(slot
)->size
> 47) {
278 memcpy(str2
, (char*)slotRawObject(slot
)->slots
, 44);
284 len
= sc_min(47, slotRawObject(slot
)->size
);
285 memcpy(str2
, (char*)slotRawObject(slot
)->slots
, len
);
288 sprintf(str
, "\"%s\"", str2
);
289 } else if (classptr
== class_method
) {
290 sprintf(str
, "instance of Method %s:%s (%p)",
291 slotRawSymbol(&slotRawClass(&slotRawMethod(slot
)->ownerclass
)->name
)->name
,
292 slotRawSymbol(&slotRawMethod(slot
)->name
)->name
, slotRawMethod(slot
));
293 } else if (classptr
== class_fundef
) {
294 PyrSlot
*context
, *nextcontext
;
295 // find function's method
296 nextcontext
= &slotRawBlock(slot
)->contextDef
;
297 if (NotNil(nextcontext
)) {
299 context
= nextcontext
;
300 nextcontext
= &slotRawBlock(context
)->contextDef
;
301 } while (NotNil(nextcontext
));
302 if (isKindOf(slotRawObject(context
), class_method
)) {
303 sprintf(str
, "instance of FunctionDef in Method %s:%s",
304 slotRawSymbol(&slotRawClass(&slotRawMethod(context
)->ownerclass
)->name
)->name
,
305 slotRawSymbol(&slotRawMethod(context
)->name
)->name
);
307 sprintf(str
, "instance of FunctionDef in closed FunctionDef");
310 sprintf(str
, "instance of FunctionDef - closed");
312 } else if (classptr
== class_frame
) {
313 if (!slotRawFrame(slot
)) {
314 sprintf(str
, "Frame (%0X)", slotRawInt(slot
));
315 } else if (slotRawBlock(&slotRawFrame(slot
)->method
)->classptr
== class_method
) {
316 sprintf(str
, "Frame (%p) of %s:%s", slotRawObject(slot
),
317 slotRawSymbol(&slotRawClass(&slotRawMethod(&slotRawFrame(slot
)->method
)->ownerclass
)->name
)->name
,
318 slotRawSymbol(&slotRawMethod(&slotRawFrame(slot
)->method
)->name
)->name
);
320 sprintf(str
, "Frame (%p) of Function", slotRawFrame(slot
));
323 sprintf(str
, "instance of %s (%p, size=%d, set=%d)",
324 slotRawSymbol(&classptr
->name
)->name
,
325 slotRawObject(slot
), slotRawObject(slot
)->size
,
326 slotRawObject(slot
)->obj_sizeclass
);
329 sprintf(str
, "NULL Object Pointer");
336 sprintf(str
, "false");
339 sprintf(str
, "true");
342 sprintf(str
, "RawPointer %p", slotRawPtr(slot
));
350 u
.f
= slotRawFloat(slot
);
351 sprintf(str
, "Float %f %08X %08X", u
.f
, u
.i
[0], u
.i
[1]);
357 static void printObject(PyrSlot
* slot
, PyrObject
* obj
, char *str
)
360 PyrClass
* classptr
= obj
->classptr
;
361 if (classptr
== class_class
) {
362 sprintf(str
, "class %s", slotRawSymbol(&((PyrClass
*)obj
)->name
)->name
);
363 } else if (classptr
== class_string
) {
366 if (obj
->size
> 31) {
367 memcpy(str2
, (char*)obj
->slots
, 28);
373 len
= sc_min(31, obj
->size
);
374 memcpy(str2
, (char*)obj
->slots
, len
);
377 sprintf(str
, "\"%s\"", str2
);
378 } else if (classptr
== class_method
) {
379 sprintf(str
, "%s:%s",
380 slotRawSymbol(&slotRawClass(&slotRawMethod(slot
)->ownerclass
)->name
)->name
,
381 slotRawSymbol(&slotRawMethod(slot
)->name
)->name
);
382 } else if (classptr
== class_fundef
) {
383 PyrSlot
*context
, *nextcontext
;
384 // find function's method
385 nextcontext
= &slotRawBlock(slot
)->contextDef
;
386 if (NotNil(nextcontext
)) {
388 context
= nextcontext
;
389 nextcontext
= &slotRawBlock(context
)->contextDef
;
390 } while (NotNil(nextcontext
));
391 if (isKindOf(slotRawObject(context
), class_method
)) {
392 sprintf(str
, "< FunctionDef in Method %s:%s >",
393 slotRawSymbol(&slotRawClass(&slotRawMethod(context
)->ownerclass
)->name
)->name
,
394 slotRawSymbol(&slotRawMethod(context
)->name
)->name
);
396 sprintf(str
, "< FunctionDef in closed FunctionDef >");
399 sprintf(str
, "< closed FunctionDef >");
401 } else if (classptr
== class_frame
) {
402 if (!slotRawFrame(slot
)) {
403 sprintf(str
, "Frame (null)");
404 } else if (!slotRawBlock(&slotRawFrame(slot
)->method
)) {
405 sprintf(str
, "Frame (null method)");
406 } else if (slotRawBlock(&slotRawFrame(slot
)->method
)->classptr
== class_method
) {
407 sprintf(str
, "Frame (%p) of %s:%s", obj
,
408 slotRawSymbol(&slotRawClass(&slotRawMethod(&slotRawFrame(slot
)->method
)->ownerclass
)->name
)->name
,
409 slotRawSymbol(&slotRawMethod(&slotRawFrame(slot
)->method
)->name
)->name
);
411 sprintf(str
, "Frame (%p) of Function", obj
);
413 } else if (classptr
== class_array
) {
414 sprintf(str
, "[*%d]", obj
->size
);
416 sprintf(str
, "<instance of %s>", slotRawSymbol(&classptr
->name
)->name
);
420 void slotOneWord(PyrSlot
*slot
, char *str
)
423 switch (GetTag(slot
)) {
425 sprintf(str
, "%d", slotRawInt(slot
));
428 sprintf(str
, "$%c", static_cast<int>(slotRawChar(slot
)));
431 if (strlen(slotRawSymbol(slot
)->name
) > 240) {
433 memcpy(str2
, slotRawSymbol(slot
)->name
, 240);
435 snprintf(str
, 256, "'%s...'", str2
);
437 snprintf(str
, 256, "'%s'", slotRawSymbol(slot
)->name
);
442 PyrObject
* slotObj
= slotRawObject(slot
);
444 printObject(slot
, slotObj
, str
);
446 sprintf(str
, "NULL Object Pointer");
453 sprintf(str
, "false");
456 sprintf(str
, "true");
459 sprintf(str
, "ptr%p", slotRawPtr(slot
));
462 sprintf(str
, "%.14g", slotRawFloat(slot
));
467 bool postString(PyrSlot
*slot
, char *str
)
470 switch (GetTag(slot
)) {
472 sprintf(str
, "%d", slotRawInt(slot
));
475 sprintf(str
, "%c", slotRawChar(slot
));
483 PyrObject
* slotObj
= slotRawObject(slot
);
485 PyrClass
* classptr
= slotRawObject(slot
)->classptr
;
486 if (classptr
== class_class
|| classptr
== class_method
|| classptr
== class_fundef
|| classptr
== class_frame
)
487 printObject(slot
, slotObj
, str
);
494 sprintf(str
, "NULL Object Pointer");
501 sprintf(str
, "false");
504 sprintf(str
, "true");
507 sprintf(str
, "%p", slotRawPtr(slot
));
510 sprintf(str
, "%.14g", slotRawFloat(slot
));
517 int asCompileString(PyrSlot
*slot
, char *str
)
519 switch (GetTag(slot
)) {
521 sprintf(str
, "%d", slotRawInt(slot
));
525 int c
= slotRawChar(slot
);
527 sprintf(str
, "$%c", c
);
530 case '\n' : strcpy(str
, "$\\n"); break;
531 case '\r' : strcpy(str
, "$\\r"); break;
532 case '\t' : strcpy(str
, "$\\t"); break;
533 case '\f' : strcpy(str
, "$\\f"); break;
534 case '\v' : strcpy(str
, "$\\v"); break;
535 default: sprintf(str
, "%d.asAscii", c
);
548 sprintf(str
, "false");
551 sprintf(str
, "true");
554 strcpy(str
, "/*Ptr*/ nil");
557 sprintf(str
, "%f", slotRawFloat(slot
));
564 void stringFromPyrString(PyrString
*obj
, char *str
, int maxlength
);
565 void stringFromPyrString(PyrString
*obj
, char *str
, int maxlength
)
567 if (obj
->classptr
== class_string
) {
569 if (obj
->size
> maxlength
-4) {
570 memcpy(str
, obj
->s
, maxlength
-4);
571 str
[maxlength
-4] = '.';
572 str
[maxlength
-3] = '.';
573 str
[maxlength
-2] = '.';
574 str
[maxlength
-1] = 0;
576 len
= sc_min(maxlength
-1, obj
->size
);
577 memcpy(str
, obj
->s
, len
);
581 sprintf(str
, "not a string");
585 void pstrncpy(unsigned char *s1
, unsigned char *s2
, int n
);
587 void pstringFromPyrString(PyrString
*obj
, unsigned char *str
, int maxlength
)
589 static const char not_a_string
[] = "not a string";
592 if (obj
&& obj
->classptr
== class_string
) {
593 len
= sc_min(maxlength
-1, obj
->size
);
596 len
= sizeof(not_a_string
);
599 memcpy(str
+1, src
, len
);