andrewchambers / c Goto Github PK
View Code? Open in Web Editor NEWsmall self hosting C compiler
Home Page: http://acha.ninja
License: BSD 2-Clause "Simplified" License
small self hosting C compiler
Home Page: http://acha.ninja
License: BSD 2-Clause "Simplified" License
int foo(void); not handled correctly.
struct s0 {
long m0;
long m1;
};
struct s1 {
struct s0 m0;
long m1;
};
struct s2 {
int m0;
};
void abort(void);
struct s1
f(int p0, struct s2 p1)
{
struct s1 r;
r.m0.m0 = 1293431308;
r.m0.m1 = 61651767;
r.m1 = 1736112203;
if(p0 != 413324820) abort();
if(p1.m0 != 1141848071) abort();
return r;
}
int
main()
{
struct s1 r;
int p0;
struct s2 p1;
p0 = 413324820;
p1.m0 = 1141848071;
r = f(p0, p1);
if(r.m0.m0 != 1293431308) abort();
if(r.m0.m1 != 61651767) abort();
if(r.m1 != 1736112203) abort();
return 0;
}
We should fuzz our abi implementation by generating random structs and random function definitions and calling back and forth from gcc/clang compiled code.
int
main()
{
int i;
for(i = 0; i < 3; i++)
continue;
return 0;
}
In the following piece of code I think you meant to write if(c >= 'A' && c <= 'F')
.
hexnumberc(int c) { if(numberc(c)) return 1; if(c >= 'a' && c <= 'f') return 1; if(c >= 'F' && c <= 'F') return 1; return 0; }
(0xffffffff + 1) == 0;
We currently fail this test because we are extending all values. Comparisions and Bool checking need to take size into account.
on arml6
$make test
make clean
make[1]: Wejście do katalogu '/home/user/inne/c'
rm -rf src/panic.o src/cc/cpp.o src/cc/lex.o src/cc/parse.o src/cc/types.o src/cc/foldexpr.o src/cc/error.o src/mem/mem.o src/ds/list.o src/ds/map.o src/ds/vec.o src/ds/strset.o src/cmd/cpp/main.o src/cmd/6c/emit.o src/cmd/6c/frontend.o src/cmd/6c/main.o src/cmd/abifuzz/main.o lib bin
make[1]: Opuszczenie katalogu '/home/user/inne/c'
make all
make[1]: Wejście do katalogu '/home/user/inne/c'
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/cmd/6c/emit.o -c src/cmd/6c/emit.c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/cmd/6c/frontend.o -c src/cmd/6c/frontend.c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/cmd/6c/main.o -c src/cmd/6c/main.c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/panic.o -c src/panic.c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/cc/cpp.o -c src/cc/cpp.c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/cc/lex.o -c src/cc/lex.c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/cc/parse.o -c src/cc/parse.c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/cc/types.o -c src/cc/types.c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/cc/foldexpr.o -c src/cc/foldexpr.c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/cc/error.o -c src/cc/error.c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/mem/mem.o -c src/mem/mem.c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/ds/list.o -c src/ds/list.c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/ds/map.o -c src/ds/map.c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/ds/vec.o -c src/ds/vec.c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/ds/strset.o -c src/ds/strset.c
ar rcs lib/libcompiler.a src/panic.o src/cc/cpp.o src/cc/lex.o src/cc/parse.o src/cc/types.o src/cc/foldexpr.o src/cc/error.o src/mem/mem.o src/ds/list.o src/ds/map.o src/ds/vec.o src/ds/strset.o
cc src/cmd/6c/emit.o src/cmd/6c/frontend.o src/cmd/6c/main.o lib/libcompiler.a -o bin/6c
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/cmd/cpp/main.o -c src/cmd/cpp/main.c
cc src/cmd/cpp/main.o lib/libcompiler.a -o bin/cpp
cc -std=c89 -g -Wfatal-errors -Wno-unused-parameter -Wall -Wextra -D_DEFAULT_SOURCE -Isrc/ -o src/cmd/abifuzz/main.o -c src/cmd/abifuzz/main.c
cc src/cmd/abifuzz/main.o lib/libcompiler.a -o bin/abifuzz
make[1]: Opuszczenie katalogu '/home/user/inne/c'
./test.sh
test/execute/0001-sanity.c.s: Assembler messages:
test/execute/0001-sanity.c.s:7: Error: bad instruction pushq %rbp' test/execute/0001-sanity.c.s:8: Error: bad instruction
movq %rsp,%rbp'
test/execute/0001-sanity.c.s:9: Error: bad instruction movq $0,%rax' test/execute/0001-sanity.c.s:10: Error: bad instruction
leave'
test/execute/0001-sanity.c.s:11: Error: bad instruction ret' test/execute/0001-sanity.c.s:12: Error: bad instruction
leave'
test/execute/0001-sanity.c.s:13: Error: bad instruction `ret'
test/execute/0001-sanity.c FAIL
Makefile:31: polecenia dla obiektu 'test' nie powiodły się
make: *** [test] Błąd 1
$uname -a
Linux 4.14.98+ #1200 Tue Feb 12 20:11:02 GMT 2019 armv6l GNU/Linux
$make no errors
Should be:
case '+': if(l->p && r->p) return 0; if(l->p) + return mkconst(l->p, l->v + r->v); if(r->p) + return mkconst(r->p, l->v + r->v); return mkconst(0, l->v + r->v);
struct s {
char a;
char b;
};
void abort(void);
struct s
f()
{
struct s r;
r.a = 1;
r.b = 2;
return r;
}
int
main()
{
struct s r;
r = f();
if(r.a != 1) abort();
if(r.b != 2) abort();
return 0;
}
char * x = " sdasd
dsda";
A reminder.
int
main()
{
int i, n, p, next, isprime;
n = 5;
p = 11;
next = 12;
while(n != 100) {
isprime = 1;
if(next % 2 == 0) {
isprime = 0;
} else {
for(i = 3; i < next; i = i + 2) {
if(next % i == 0) {
isprime = 0;
break;
}
}
}
if(isprime) {
p = next;
n++;
}
next = next + 1;
}
if(p != 541)
return 1;
return 0;
}
Hello Andrew, I'm Nergal and I'm interesting in forking over this C compiler suite to create a game scripting language. May I have permission? Also, how stable is this compiler suite?
a;
abort();
main() {
int b = 1080377166;
long c = a;
if (b != 1080377166)
abort();
}
found with abifuzz and creduce
Hey, it seems that the stack pointer is not correctly set to 0 mod 16 at call boundaries. The following example triggers a segfault on my machine.
int printf(char *, ...);
int *calloc(int, int);
int N;
int *t;
print() {
int x;
int y;
for (y=0; y<8; y++) {
for (x=0; x<8; x++)
if (t[x + 8*y])
printf(" Q");
else
printf(" .");
printf("\n");
}
printf("\n");
}
chk(int x, int y) {
int i;
int r;
for (r=i=0; i<8; i++) {
r = r + t[x + 8*i];
r = r + t[i + 8*y];
if (x+i < 8 & y+i < 8)
r = r + t[x+i + 8*(y+i)];
if (x+i < 8 & y-i >= 0)
r = r + t[x+i + 8*(y-i)];
if (x-i >= 0 & y+i < 8)
r = r + t[x-i + 8*(y+i)];
if (x-i >= 0 & y-i >= 0)
r = r + t[x-i + 8*(y-i)];
}
return r;
}
go(int n, int x, int y) {
if (n == 8) {
print();
N++;
return 0;
}
for (; y<8; y++) {
for (; x<8; x++)
if (chk(x, y) == 0) {
t[x + 8*y]++;
go(n+1, x, y);
t[x + 8*y]--;
}
x = 0;
}
}
main() {
t = calloc(64, sizeof(int));
go(0, 0, 0);
printf("found %d solutions\n", N);
}
The lexer has become one of the ugliest parts of the code. At the very least number, ident, comment and whitespace processing can be put in dedicated functions.
$ make test
...
...
test/bugs/0004.c PASS
test/bugs/0005.c PASS
test/bugs/0006.c PASS
test/bugs/0008.c PASS
/usr/bin/ld: test/bugs/0012.c.o: relocation R_X86_64_PC32 against symbol `abort@@GLIBC_2.2.5' can not be used when making a shared object; recompile with -fPIC
/usr/bin/ld: final link failed: Bad value
collect2: error: ld returned 1 exit status
test/bugs/0012.c FAIL
Makefile:31: recipe for target 'test' failed
make: *** [test] Error 1
how fix?!
We can get most of the benefits of not doing manual memory management, but allow compilation of multiple files by using a pool allocator and freeing the pools at the end of each .c file.
Hello, is Windows support planned?
WG14 is considering adding constexpr to C23, they're worried it may kill single pass, no AST compilers from working, and it looks like yours fits that description.
what are your thoughts?
enum {
TOKAUTO,
};
static struct {char *kw; int t;} arr[2] = {
{0, TOKAUTO},
{0, 0}
};
int
main()
{
return 0;
}
fields in init overlaps with another field at ./bug.c:8:9
char *x = "abc";
int
main()
{
char *p;
p = x;
p = p + 1;
if(p[0] != 'b')
return 1;
return 0;
}
types.c
case CARR: if(r->t != CARR) return 0; if(r->Arr.dim != l->Arr.dim) return 0; + if(!sametype(l->Arr.subty, r->Arr.subty)) + return 0; return 1;
The old version did not check the subtype of the array.
Is possible create haiku port?
int (((p))); is valid.
Is possible to create my own frontend?
for example bison or ragel grammar
Running the compiler on amd64 ubuntu I get the following valgrind report. Is this a false positive?
andrew@blackheart:~/src/c$ valgrind bin/6c test/execute/0001-sanity.c
==3118== Memcheck, a memory error detector
==3118== Copyright (C) 2002-2013, and GNU GPL'd, by Julian Seward et al.
==3118== Using Valgrind-3.10.1 and LibVEX; rerun with -h for copyright info
==3118== Command: bin/6c test/execute/0001-sanity.c
==3118==
==3118== Conditional jump or move depends on uninitialised value(s)
==3118== at 0x4540D6: __linkin_atfork (in /home/andrew/src/c/bin/6c)
==3118== by 0x42CDA3: ptmalloc_init.part.7 (in /home/andrew/src/c/bin/6c)
==3118== by 0x42D1F4: malloc_hook_ini (in /home/andrew/src/c/bin/6c)
==3118== by 0x47AA3A: _dl_get_origin (in /home/andrew/src/c/bin/6c)
==3118== by 0x45499E: _dl_non_dynamic_init (in /home/andrew/src/c/bin/6c)
==3118== by 0x455797: __libc_init_first (in /home/andrew/src/c/bin/6c)
==3118== by 0x409B3B: (below main) (in /home/andrew/src/c/bin/6c)
...
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.