shithub: hammer

Download patch

ref: c2086cda32afb3960938a81df6f5a6a209bfaf33
parent: 893a6828d04ad197b2eb773d19bff69ba63af14e
author: Jacob Moody <moody@posixcafe.org>
date: Fri Apr 26 01:22:57 EDT 2024

function calls, refactor tabing in output, start of c output

--- a/dat.h
+++ b/dat.h
@@ -53,6 +53,7 @@
 	Nsym,
 	Ndcl,
 	Nfunc,
+	Ncall,
 };
 
 enum {
@@ -135,10 +136,16 @@
 			Typ	*type;
 			Nod	*body;
 		} func;
+		struct {
+			char	*name;
+			Nlst	args;
+		} call;
 	};
 };
 #pragma	   varargck    type  "N"   Nod*
+#pragma	   varargck    type  "O"   Nod*
 #pragma	   varargck    type  "L"   Nlst
+#pragma	   varargck    type  "M"   Nlst
 
 extern int	lexline;
 extern char*	lexfile;
--- a/fmt.c
+++ b/fmt.c
@@ -34,12 +34,14 @@
 nodfmt(Fmt *f)
 {
 	Nod *n;
-	int nt;
+	int nt, e;
 
 	nt = f->prec;
 	n = va_arg(f->args, Nod*);
 	if(n == nil)
 		return 0;
+	if(nt && n->t != Nblk)
+		fmtprint(f, "%.*s", nt, tabs);
 	switch(n->t){
 	default:
 		return fmtprint(f, "unknown nod type %d", n->t);
@@ -61,11 +63,16 @@
 		else
 			return fmtprint(f, "EXPR(%N %s %N)", n->expr.lhs, expoptab[n->expr.op], n->expr.rhs);
 	case Nblk:
-		return fmtprint(f, "{\n%.*L\n%.*s}", nt+1, n->blk.body, nt, tabs);
+		e = nt - 1;
+		if(e < 0)
+			e = 0;
+		return fmtprint(f, "{\n%.*L\n%.*s}", nt, n->blk.body, e, tabs);
 	case Ndcl:
 		return fmtprint(f, "DCL %s : %s", n->dcl.name, n->dcl.type->name);
 	case Nfunc:
-		return fmtprint(f, "FN %s (\n%.*L\n) → %N", n->func.name, nt+1, n->func.args, n->func.body);
+		return fmtprint(f, "FN %s (\n%.*L\n) → %.*N", n->func.name, nt+1, n->func.args, nt+1, n->func.body);
+	case Ncall:
+		return fmtprint(f, "CALL %s (\n%.*L\n%.*s)", n->call.name, nt+1, n->call.args, nt, tabs);
 	}
 }
 
@@ -78,7 +85,7 @@
 	nt = f->prec;
 	n = va_arg(f->args, Nlst);
 	for(i = 0; i < n.nv; i++){
-		fmtprint(f, "%.*s%N", nt, tabs, n.v[i]);
+		fmtprint(f, "%.*N", nt, n.v[i]);
 		if(i != n.nv-1)
 			fmtprint(f, "\n");
 	}
@@ -85,6 +92,66 @@
 	return 0;
 }
 
+int
+cnodfmt(Fmt *f)
+{
+	Nod *n;
+	int nt, e;
+
+	nt = f->prec;
+	n = va_arg(f->args, Nod*);
+	if(n == nil)
+		return 0;
+	if(nt && n->t != Nblk)
+		fmtprint(f, "%.*s", nt, tabs);
+	switch(n->t){
+	default:
+		return fmtprint(f, "unknown nod type %d", n->t);
+	case Nfor:
+		return fmtprint(f, "for(%O; %O; %O) %.*O", n->nfor.init, n->nfor.cond, n->nfor.step, nt+1, n->nfor.body);
+	case Nif:
+		if(n->nif.f)
+			return fmtprint(f, "if(%O)%.*Oelse%.*O", n->nif.cond, nt+1, n->nif.t, nt+1, n->nif.f);
+		return fmtprint(f, "if(%O)%.*O",  n->nif.cond, nt+1, n->nif.t);
+	case Nsym:
+		return fmtprint(f, "%s", n->sym.sym);
+	case Nlit:
+		return fmtprint(f, "%lld", n->lit.val);
+	case Nexpr:
+		if(n->expr.op == Olit || n->expr.op == Ovar)
+			return fmtprint(f, "%O", n->expr.lhs);
+		else
+			return fmtprint(f, "%O %s %O", n->expr.lhs, expoptab[n->expr.op], n->expr.rhs);
+	case Nblk:
+		e = nt - 1;
+		if(e < 0)
+			e = 0;
+		return fmtprint(f, "{\n%.*M\n%.*s}", nt, n->blk.body, e, tabs);
+	case Ndcl:
+		return fmtprint(f, "%s %s", n->dcl.type->name, n->dcl.name);
+	case Nfunc:
+		return fmtprint(f, "void\n%s(%M)\n%.*O", n->func.name, n->func.args, nt+1, n->func.body);
+	case Ncall:
+		return fmtprint(f, "%s(%M)", n->call.name, n->call.args);
+	}
+}
+
+int
+cnlstfmt(Fmt *f)
+{
+	int i, nt;
+	Nlst n;
+
+	nt = f->prec;
+	n = va_arg(f->args, Nlst);
+	for(i = 0; i < n.nv; i++){
+		fmtprint(f, "%.*O", nt, n.v[i]);
+		if(i != n.nv-1)
+			fmtprint(f, ", ");
+	}
+	return 0;
+}
+
 void
 astfmtinstall(void)
 {
@@ -92,4 +159,6 @@
 	tabs[nelem(tabs)-1] = '\0';
 	fmtinstall('N', nodfmt);
 	fmtinstall('L', nlstfmt);
+	fmtinstall('O', cnodfmt);
+	fmtinstall('M', cnlstfmt);
 }
--- a/fns.h
+++ b/fns.h
@@ -5,6 +5,7 @@
 Nod*	mkfor(Nod*, Nod*, Nod*, Nod*);
 Nod*	mkif(Nod*, Nod*, Nod*);
 Nod*	mkfunc(char*, Nlst, Typ*, Nlst);
+Nod*	mkcall(char*, Nlst);
 Nod*	mklit(vlong);
 Nod*	mksym(char*);
 Nod*	mkdecl(char*, Typ*, Nod*);
--- a/n.y
+++ b/n.y
@@ -40,10 +40,10 @@
 %token	<sval>	NAME;
 %token	<ival>	NUM
 
-%type<nod>	arg expr logexpr shifexpr addexpr mulexpr
+%type<nod>	defarg expr logexpr shifexpr addexpr mulexpr
 %type<nod>	unary prefexpr sufexpr compexpr top stmt
 %type<nod>	decl
-%type<lst>	args prog stmts
+%type<lst>	defargs prog stmts args
 %type<typ>	type return
 
 %%
@@ -56,7 +56,7 @@
 |	top			{ $$ = append(ZL, $1); }
 
 top
-:	FUNC NAME '(' args ')' return '{' stmts '}'
+:	FUNC NAME '(' defargs ')' return '{' stmts '}'
 				{ $$ = mkfunc($2, $4, $6, $8); }
 |	MOD NAME ';'		{ $$ = nil; modname = $2; }
 |	USE NAME ';'		{ $$ = nil; loaduse($2); }
@@ -85,6 +85,7 @@
 :	NUM			{ $$ = mkexpr(Olit, mklit($1), nil); }
 |	NAME			{ $$ = mkexpr(Ovar, mksym($1), nil); }
 |	'(' expr ')'		{ $$ = $2; }
+|	NAME '(' args ')'	{ $$ = mkcall($1, $3); }
 
 sufexpr
 :	sufexpr DEC		{ $$ = mkexpr(Odec, $1, nil); }
@@ -152,13 +153,18 @@
 				{ $$ = mkif($3, $5, $7); }
 |	IF '(' expr ')' stmt	{ $$ = mkif($3, $5, nil); }
 
-arg
+defarg
 :	NAME ':' type	{ $$ = mkdecl($1, $3, nil); }
 
+defargs
+:				{ $$ = ZL; }
+|	defarg			{ $$ = append(ZL, $1); }
+|	defargs ',' defarg	{ $$ = append($1, $3); }
+
 args
 :			{ $$ = ZL; }
-|	arg		{ $$ = append(ZL, $1); }
-|	args ',' arg	{ $$ = append($1, $3); }
+|	expr		{ $$ = append(ZL, $1); }
+|	args ',' expr	{ $$ = append($1, $3); }
 
 %%
 
@@ -336,7 +342,13 @@
 void
 main(int argc, char **argv)
 {
+	int ast;
+
+	ast = 0;
 	ARGBEGIN{
+	case 'a':
+		ast++;
+		break;
 	case 'd':
 		debug++;
 		break;
@@ -352,6 +364,9 @@
 	while(!goteof)
 		yyparse();
 	Bterm(bin);
-	print("%L\n", toplevel);
+	if(ast)
+		print("%L\n", toplevel);
+	else
+		print("%M\n", toplevel);
 	exits(nil);
 }
--- a/nod.c
+++ b/nod.c
@@ -104,6 +104,17 @@
 }
 
 Nod*
+mkcall(char *s, Nlst args)
+{
+	Nod *n;
+
+	n = new(Ncall);
+	n->call.name = s;
+	n->call.args = args;
+	return n;
+}
+
+Nod*
 mklit(vlong v)
 {
 	Nod *n;