ref: da6308e5df8ed9cdf8d8f6cad73eef10f31ac4b0
dir: /util.c/
#include <u.h>
#include <libc.h>
#include <thread.h>
#include "dat.h"
#include "fns.h"
Enumeration *
allocenum(uvlong count)
{
Enumeration *e = alloc(DataEnumeration);
setroot(e, 1);
e->count = count;
e->items = allocextra(e, sizeof(void *) * count);
return e;
}
void
trim(char *str)
{
for(int i = strlen(str)-1; i > 0; i--){
if(str[i] != '\n')
break;
else
str[i] = 0;
}
}
static void
indent(int depth)
{
for(int i = 0; i < depth; i++)
print(" ");
}
static void
printchild(char *desc, Ast *ast, int depth)
{
indent(depth);
print("%s:\n", desc);
indent(depth+1);
debugast(ast, depth+1);
}
void
debugast(Ast *ast, int depth)
{
if(ast == nil){
print("<nil>\n");
return;
}
int printchildren = 0;
switch(ast->tag){
case AstProg:
print("prog\n");
printchildren = 1;
break;
case AstFunc:
print("func\n");
depth++;
printchild("name", ast->funcname, depth);
printchild("result", ast->funcresult, depth);
printchild("left arg", ast->funcleftarg, depth);
printchild("right arg", ast->funcrightarg, depth);
printchild("local vars", ast->funclocals, depth);
indent(depth); print("body\n");
printchildren = 1;
break;
case AstName:
print("\"%s\"\n", ast->name);
break;
case AstLocals:
print("locals\n");
printchildren = 1;
break;
case AstAssign:
print("assign\n");
printchild("name", ast->left, depth+1);
printchild("value", ast->right, depth+1);
break;
case AstMonadic:
print("monadic call\n");
printchild("func", ast->func, depth+1);
printchild("right", ast->right, depth+1);
break;
case AstDyadic:
print("dyadic call\n");
printchild("func", ast->func, depth+1);
printchild("left", ast->left, depth+1);
printchild("right", ast->right, depth+1);
break;
case AstConst:
print("const:\n");
indent(depth+1);
print("%s\n", printarray(ast->val));
break;
case AstPrim:
print("prim: %d\n", ast->prim);
break;
case AstStrand:
print("strand\n");
printchildren = 1;
break;
default:
print("<ast node %d>\n", ast->tag);
break;
}
if(printchildren){
for(uvlong i = 0; i < ast->childcount; i++){
indent(depth+1);
debugast(ast->children[i], depth+1);
}
}
}
int
getuvlong(u8int *p, uvlong *vp)
{
int size = sizeof(uvlong);
uvlong v = 0;
for(int i = 0; i < size; i++){
uvlong x = *p;
p++;
v |= x << (8*i);
}
*vp = v;
return size;
}
void
debugbc(ByteCode *c)
{
uvlong o, v;
o = 0;
while(o < c->count){
int instr = c->instrs[o];
o++;
switch(instr){
case IPushConst:
o += getuvlong(c->instrs+o, &v);
print("CONST %p\n", (void*)v);
break;
case IPushPrim:
o += getuvlong(c->instrs+o, &v);
print("PRIM %p\n", v);
break;
case ILookup:
o += getuvlong(c->instrs+o, &v);
print("LOOKUP %ulld\n", v);
break;
case IStrand:
o += getuvlong(c->instrs+o, &v);
print("STRAND %ulld\n", v);
break;
case IMonadic:
print("MONADIC PRIM\n");
break;
case IDyadic:
print("DYADIC PRIM\n");
break;
case ICall:
print("CALL\n");
break;
case IClear:
print("CLEAR\n");
break;
case IParse:
o += getuvlong(c->instrs+o, &v);
print("PARSE %ulld\n", v);
break;
case IDone:
print("DONE\n");
break;
case IReturn:
print("RETURN\n");
break;
case IAssign:
o += getuvlong(c->instrs+o, &v);
print("ASSIGN %ulld\n", v);
break;
case ILocal:
o += getuvlong(c->instrs+o, &v);
print("LOCAL %ulld\n", v);
break;
default:
print("???");
return;
}
}
print("\n");
}