Compare commits
5 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| c051b402dd | |||
| 30e73fcba1 | |||
| a9aca0f00b | |||
| 4f12bcc476 | |||
| 3c29879755 |
2
.dir-locals.el
Normal file
2
.dir-locals.el
Normal file
@@ -0,0 +1,2 @@
|
|||||||
|
((c-mode . ((tab-width . 4)
|
||||||
|
(indent-tabs-mode . t))))
|
||||||
1
.gitignore
vendored
1
.gitignore
vendored
@@ -7,3 +7,4 @@ config.h
|
|||||||
.direnv
|
.direnv
|
||||||
result
|
result
|
||||||
.cache
|
.cache
|
||||||
|
.fuse_hidden*
|
||||||
|
|||||||
4
all.h
4
all.h
@@ -159,12 +159,12 @@ enum J {
|
|||||||
#define JMPS(X) \
|
#define JMPS(X) \
|
||||||
X(retw) X(retl) X(rets) X(retd) \
|
X(retw) X(retl) X(rets) X(retd) \
|
||||||
X(retsb) X(retub) X(retsh) X(retuh) \
|
X(retsb) X(retub) X(retsh) X(retuh) \
|
||||||
X(retc) X(ret0) X(jmp) X(jnz) \
|
X(retc) X(ret0) X(jmp) X(jnz) \
|
||||||
X(jfieq) X(jfine) X(jfisge) X(jfisgt) \
|
X(jfieq) X(jfine) X(jfisge) X(jfisgt) \
|
||||||
X(jfisle) X(jfislt) X(jfiuge) X(jfiugt) \
|
X(jfisle) X(jfislt) X(jfiuge) X(jfiugt) \
|
||||||
X(jfiule) X(jfiult) X(jffeq) X(jffge) \
|
X(jfiule) X(jfiult) X(jffeq) X(jffge) \
|
||||||
X(jffgt) X(jffle) X(jfflt) X(jffne) \
|
X(jffgt) X(jffle) X(jfflt) X(jffne) \
|
||||||
X(jffo) X(jffuo) X(hlt)
|
X(jffo) X(jffuo) X(hlt) X(tail)
|
||||||
#define X(j) J##j,
|
#define X(j) J##j,
|
||||||
JMPS(X)
|
JMPS(X)
|
||||||
#undef X
|
#undef X
|
||||||
|
|||||||
@@ -602,7 +602,8 @@ seljmp(Blk *b, Fn *fn)
|
|||||||
|
|
||||||
if (b->jmp.type == Jret0
|
if (b->jmp.type == Jret0
|
||||||
|| b->jmp.type == Jjmp
|
|| b->jmp.type == Jjmp
|
||||||
|| b->jmp.type == Jhlt)
|
|| b->jmp.type == Jhlt
|
||||||
|
|| b->jmp.type == Jtail)
|
||||||
return;
|
return;
|
||||||
assert(b->jmp.type == Jjnz);
|
assert(b->jmp.type == Jjnz);
|
||||||
r = b->jmp.arg;
|
r = b->jmp.arg;
|
||||||
|
|||||||
14
amd64/sysv.c
14
amd64/sysv.c
@@ -167,7 +167,7 @@ argsclass(Ins *i0, Ins *i1, AClass *ac, int op, AClass *aret, Ref *env)
|
|||||||
nsse = 8;
|
nsse = 8;
|
||||||
varc = 0;
|
varc = 0;
|
||||||
envc = 0;
|
envc = 0;
|
||||||
for (i=i0, a=ac; i<i1; i++, a++)
|
for (i=i0, a=ac; i<i1; i++, a++) {
|
||||||
switch (i->op - op + Oarg) {
|
switch (i->op - op + Oarg) {
|
||||||
case Oarg:
|
case Oarg:
|
||||||
if (KBASE(i->cls) == 0)
|
if (KBASE(i->cls) == 0)
|
||||||
@@ -211,8 +211,9 @@ argsclass(Ins *i0, Ins *i1, AClass *ac, int op, AClass *aret, Ref *env)
|
|||||||
varc = 1;
|
varc = 1;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
die("unreachable");
|
die("218 unreachable");
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (varc && envc)
|
if (varc && envc)
|
||||||
err("sysv abi does not support variadic env calls");
|
err("sysv abi does not support variadic env calls");
|
||||||
@@ -686,7 +687,7 @@ amd64_sysv_abi(Fn *fn)
|
|||||||
continue;
|
continue;
|
||||||
curi = &insb[NIns];
|
curi = &insb[NIns];
|
||||||
selret(b, fn);
|
selret(b, fn);
|
||||||
for (i=&b->ins[b->nins]; i!=b->ins;)
|
for (i=&b->ins[b->nins]; i!=b->ins;) {
|
||||||
switch ((--i)->op) {
|
switch ((--i)->op) {
|
||||||
default:
|
default:
|
||||||
emiti(*i);
|
emiti(*i);
|
||||||
@@ -706,8 +707,13 @@ amd64_sysv_abi(Fn *fn)
|
|||||||
break;
|
break;
|
||||||
case Oarg:
|
case Oarg:
|
||||||
case Oargc:
|
case Oargc:
|
||||||
die("unreachable");
|
if (b->jmp.type != Jtail) {
|
||||||
|
die("710 unreachable");
|
||||||
|
} else {
|
||||||
|
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
if (b == fn->start)
|
if (b == fn->start)
|
||||||
for (; ral; ral=ral->link)
|
for (; ral; ral=ral->link)
|
||||||
emiti(ral->i);
|
emiti(ral->i);
|
||||||
|
|||||||
0
dump-enums.c
Normal file
0
dump-enums.c
Normal file
@@ -34,12 +34,8 @@
|
|||||||
gcc
|
gcc
|
||||||
clang-analyzer
|
clang-analyzer
|
||||||
clang-tools
|
clang-tools
|
||||||
|
gdbgui
|
||||||
];
|
];
|
||||||
# shellHook = ''
|
|
||||||
# [[ ! -z "$LD_LIBRARY_PATH" ]] \
|
|
||||||
# && export LD_LIBRARY_PATH=:$LD_LIBRARY_PATH
|
|
||||||
# export LD_LIBRARY_PATH="${self.packages.${system}.default.libllvm.lib}/lib$LD_LIBRARY_PATH"
|
|
||||||
# '';
|
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|||||||
1
main.c
1
main.c
@@ -17,6 +17,7 @@ char debug['Z'+1] = {
|
|||||||
['L'] = 0, /* liveness */
|
['L'] = 0, /* liveness */
|
||||||
['S'] = 0, /* spilling */
|
['S'] = 0, /* spilling */
|
||||||
['R'] = 0, /* reg. allocation */
|
['R'] = 0, /* reg. allocation */
|
||||||
|
['E'] = 0, /* enums */
|
||||||
};
|
};
|
||||||
|
|
||||||
extern Target T_amd64_sysv;
|
extern Target T_amd64_sysv;
|
||||||
|
|||||||
14
parse.c
14
parse.c
@@ -53,6 +53,7 @@ enum Token {
|
|||||||
Tphi,
|
Tphi,
|
||||||
Tjmp,
|
Tjmp,
|
||||||
Tjnz,
|
Tjnz,
|
||||||
|
Ttail,
|
||||||
Tret,
|
Tret,
|
||||||
Thlt,
|
Thlt,
|
||||||
Texport,
|
Texport,
|
||||||
@@ -113,6 +114,7 @@ static char *kwmap[Ntok] = {
|
|||||||
[Tphi] = "phi",
|
[Tphi] = "phi",
|
||||||
[Tjmp] = "jmp",
|
[Tjmp] = "jmp",
|
||||||
[Tjnz] = "jnz",
|
[Tjnz] = "jnz",
|
||||||
|
[Ttail] = "tail",
|
||||||
[Tret] = "ret",
|
[Tret] = "ret",
|
||||||
[Thlt] = "hlt",
|
[Thlt] = "hlt",
|
||||||
[Texport] = "export",
|
[Texport] = "export",
|
||||||
@@ -664,6 +666,13 @@ parseline(PState ps)
|
|||||||
curb->jmp.arg = r;
|
curb->jmp.arg = r;
|
||||||
}
|
}
|
||||||
goto Close;
|
goto Close;
|
||||||
|
case Ttail:
|
||||||
|
curb->jmp.type = Jtail;
|
||||||
|
curb->jmp.arg = parseref ();
|
||||||
|
/* Ins *restore = curi; */
|
||||||
|
parserefl(1);
|
||||||
|
/* curi = restore; */
|
||||||
|
goto Close;
|
||||||
case Tjmp:
|
case Tjmp:
|
||||||
curb->jmp.type = Jjmp;
|
curb->jmp.type = Jjmp;
|
||||||
goto Jump;
|
goto Jump;
|
||||||
@@ -1434,6 +1443,11 @@ printfn(Fn *fn, FILE *f)
|
|||||||
if (b->s1 != b->link)
|
if (b->s1 != b->link)
|
||||||
fprintf(f, "\tjmp @%s\n", b->s1->name);
|
fprintf(f, "\tjmp @%s\n", b->s1->name);
|
||||||
break;
|
break;
|
||||||
|
case Jtail:
|
||||||
|
fprintf (f, "\ttail ");
|
||||||
|
printref (b->jmp.arg, fn, f);
|
||||||
|
fprintf (f, "\n");
|
||||||
|
break;
|
||||||
default:
|
default:
|
||||||
fprintf(f, "\t%s ", jtoa[b->jmp.type]);
|
fprintf(f, "\t%s ", jtoa[b->jmp.type]);
|
||||||
if (b->jmp.type == Jjnz) {
|
if (b->jmp.type == Jjnz) {
|
||||||
|
|||||||
11
test/call-factorial.ssa
Normal file
11
test/call-factorial.ssa
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
function w $factorial (w %n, w %acc) {
|
||||||
|
@start
|
||||||
|
jnz %n, @nz, @z
|
||||||
|
@z
|
||||||
|
ret %acc
|
||||||
|
@nz
|
||||||
|
%n_next =w sub %n, 1
|
||||||
|
%acc_next =w mul %n, %acc
|
||||||
|
%r =w call $factorial (w %n_next, w %acc)
|
||||||
|
ret %r
|
||||||
|
}
|
||||||
10
test/tail.ssa
Normal file
10
test/tail.ssa
Normal file
@@ -0,0 +1,10 @@
|
|||||||
|
function w $factorial (w %n, w %acc) {
|
||||||
|
@start
|
||||||
|
jnz %n, @nz, @z
|
||||||
|
@z
|
||||||
|
ret %acc
|
||||||
|
@nz
|
||||||
|
%n_next =w sub %n, 1
|
||||||
|
%acc_next =w mul %n, %acc
|
||||||
|
tail $factorial (w %n_next, w %acc)
|
||||||
|
}
|
||||||
9
util.c
9
util.c
@@ -261,6 +261,7 @@ igroup(Blk *b, Ins *i, Ins **i0, Ins **i1)
|
|||||||
|
|
||||||
ib = b->ins;
|
ib = b->ins;
|
||||||
ie = ib + b->nins;
|
ie = ib + b->nins;
|
||||||
|
|
||||||
switch (i->op) {
|
switch (i->op) {
|
||||||
case Oblit0:
|
case Oblit0:
|
||||||
*i0 = i;
|
*i0 = i;
|
||||||
@@ -285,8 +286,12 @@ igroup(Blk *b, Ins *i, Ins **i0, Ins **i1)
|
|||||||
*i0 = i;
|
*i0 = i;
|
||||||
for (; i<ie && i->op != Ocall; i++)
|
for (; i<ie && i->op != Ocall; i++)
|
||||||
;
|
;
|
||||||
assert(i < ie);
|
if (b->jmp.type == Jtail) {
|
||||||
*i1 = i + 1;
|
*i1 = ie;
|
||||||
|
} else {
|
||||||
|
assert(i < ie);
|
||||||
|
*i1 = i + 1;
|
||||||
|
}
|
||||||
return;
|
return;
|
||||||
case Osel1:
|
case Osel1:
|
||||||
for (; i>ib && (i-1)->op == Osel1; i--)
|
for (; i>ib && (i-1)->op == Osel1; i--)
|
||||||
|
|||||||
Reference in New Issue
Block a user