mirror of
https://github.com/JannisHeydemann/BoredOS.git
synced 2026-05-30 10:26:59 +00:00
userland: replace legacy cc with native TCC and vendor submodule
This commit is contained in:
13
src/userland/cli/third_party/tcc/tests/42test.h
vendored
Normal file
13
src/userland/cli/third_party/tcc/tests/42test.h
vendored
Normal file
@@ -0,0 +1,13 @@
|
||||
/* This file is to test compute #include directives. It's named so
|
||||
that it starts with a pre-processing number which isn't a valid
|
||||
number (42test.h). Including this must work. */
|
||||
#ifndef INC42_FIRST
|
||||
int have_included_42test_h;
|
||||
#define INC42_FIRST
|
||||
#elif !defined INC42_SECOND
|
||||
#define INC42_SECOND
|
||||
int have_included_42test_h_second;
|
||||
#else
|
||||
#define INC42_THIRD
|
||||
int have_included_42test_h_third;
|
||||
#endif
|
||||
351
src/userland/cli/third_party/tcc/tests/Makefile
vendored
Normal file
351
src/userland/cli/third_party/tcc/tests/Makefile
vendored
Normal file
@@ -0,0 +1,351 @@
|
||||
#
|
||||
# Tiny C Compiler Makefile - tests
|
||||
#
|
||||
|
||||
TOP = ..
|
||||
include $(TOP)/Makefile
|
||||
VPATH = $(TOPSRC)/tests $(TOPSRC)
|
||||
CFLAGS := $(filter-out -g% -O%,$(CFLAGS)) -I$(TOPSRC) -I$(TOP) $(LDFLAGS)
|
||||
|
||||
# what tests to run
|
||||
TESTS = \
|
||||
hello-exe \
|
||||
hello-run \
|
||||
libtest \
|
||||
libtest_mt \
|
||||
test3 \
|
||||
abitest \
|
||||
asm-c-connect-test \
|
||||
vla_test-run \
|
||||
tests2-dir \
|
||||
pp-dir \
|
||||
memtest \
|
||||
dlltest \
|
||||
cross-test
|
||||
|
||||
# test4_static -- Not all relocation types are implemented yet.
|
||||
# asmtest / asmtest2 -- minor differences with gcc
|
||||
|
||||
ifeq ($(CONFIG_backtrace),no)
|
||||
TESTS := $(filter-out libtest_mt, $(TESTS))
|
||||
else ifneq ($(CONFIG_bcheck),no)
|
||||
TESTS += btest test1b tccb
|
||||
endif
|
||||
ifeq ($(CONFIG_dll),no)
|
||||
TESTS := $(filter-out dlltest, $(TESTS))
|
||||
endif
|
||||
ifeq (-$(CONFIG_arm_eabi)-$(CONFIG_arm_vfp)-,-yes--)
|
||||
TESTS := $(filter-out test3 test1b,$(TESTS))
|
||||
endif
|
||||
ifeq (,$(filter i386 x86_64,$(ARCH)))
|
||||
TESTS := $(filter-out asm-c-connect-test,$(TESTS))
|
||||
endif
|
||||
ifeq ($(OS),Windows_NT) # for libtcc_test to find libtcc.dll
|
||||
PATH := $(CURDIR)/$(TOP)$(if $(findstring ;,$(PATH)),;,:)$(PATH)
|
||||
endif
|
||||
ifdef CONFIG_OSX
|
||||
LIBS += $(LINK_LIBTCC)
|
||||
endif
|
||||
ifeq ($(ARCH),arm)
|
||||
# tcctest refers to the alignment of functions, and with thumb mode
|
||||
# the low bit of code addresses selects the mode, so the "alignment"
|
||||
# of functions via bit masking comes out as 1. Just disable thumb.
|
||||
test.ref: CFLAGS+=-marm
|
||||
endif
|
||||
ifeq ($(ARCH)$(CONFIG_WIN32),i386)
|
||||
# tcctest.c:get_asm_string uses a construct that is checked too strictly
|
||||
# by GCC in 32bit mode when PIC is enabled.
|
||||
test.ref: CFLAGS+=-fno-PIC -fno-PIE -Wl,-z,notext
|
||||
endif
|
||||
ifeq ($(CC_NAME),msvc)
|
||||
test.ref abitest : CC = gcc
|
||||
endif
|
||||
ifeq ($(TARGETOS),OpenBSD)
|
||||
dlltest: CFLAGS+=-fno-stack-protector
|
||||
endif
|
||||
ifneq (,$(filter FreeBSD NetBSD,$(TARGETOS)))
|
||||
# test3 has dlsym problems
|
||||
TESTS := $(filter-out test3,$(TESTS))
|
||||
TESTS += test1
|
||||
endif
|
||||
|
||||
RUN_TCC = -run $(TOPSRC)/tcc.c $(TCCFLAGS)
|
||||
DISAS = objdump -d
|
||||
ifdef CONFIG_OSX
|
||||
DUMPTCC = (set -x; $(TCC_LOCAL) -vv; otool -L $(TCC_LOCAL); exit 1)
|
||||
else
|
||||
DUMPTCC = (set -x; $(TCC_LOCAL) -vv; ldd $(TCC_LOCAL); exit 1)
|
||||
endif
|
||||
|
||||
all test :
|
||||
@echo ------------ version ------------
|
||||
@$(TCC_LOCAL) -v
|
||||
@$(MAKE) --no-print-directory -s clean
|
||||
@$(MAKE) --no-print-directory -s -r _all
|
||||
@echo ------- ALL TESTS PASSED --------
|
||||
|
||||
_all : $(TESTS)
|
||||
|
||||
hello-exe: ../examples/ex1.c
|
||||
@echo ------------ $@ ------------
|
||||
$(TCC) $< -o hello$(EXESUF) && ./hello$(EXESUF) || $(DUMPTCC)
|
||||
|
||||
hello-run: ../examples/ex1.c
|
||||
@echo ------------ $@ ------------
|
||||
$(TCC) -run $< || $(DUMPTCC)
|
||||
|
||||
libtes%: libtcc_tes%$(EXESUF)
|
||||
@echo ------------ $@ ------------
|
||||
./libtcc_tes$*$(EXESUF) $(TOPSRC)/tcc.c $(TCCFLAGS)
|
||||
|
||||
libtcc_test$(EXESUF): libtcc_test.c
|
||||
$(CC) -o $@ $< $(CFLAGS) $(-LTCC) $(LIBS)
|
||||
|
||||
libtcc_test_mt$(EXESUF): libtcc_test_mt.c
|
||||
$(CC) -o $@ $< $(CFLAGS) $(-LTCC) $(LIBS)
|
||||
|
||||
%-dir:
|
||||
@echo ------------ $@ ------------
|
||||
$(MAKE) -k -C $*
|
||||
|
||||
# test.ref - generate using cc
|
||||
test.ref: tcctest.c
|
||||
$(CC) -o tcctest.gcc$(EXESUF) $< $(CFLAGS) -w -O0 -std=gnu99 -fno-omit-frame-pointer
|
||||
./tcctest.gcc$(EXESUF) > $@
|
||||
|
||||
# auto test
|
||||
test1 test1b: tcctest.c test.ref
|
||||
@echo ------------ $@ ------------
|
||||
$(TCC) $(RUN_TCC) -w -run $< > test.out1
|
||||
@diff -u test.ref test.out1 && echo "$(AUTO_TEST) OK"
|
||||
|
||||
# iterated test2 (compile tcc then compile tcctest.c !)
|
||||
test2 test2b: tcctest.c test.ref
|
||||
@echo ------------ $@ ------------
|
||||
$(TCC) $(RUN_TCC) $(RUN_TCC) -w -run $< > test.out2
|
||||
@diff -u test.ref test.out2 && echo "$(AUTO_TEST)2 OK"
|
||||
|
||||
# iterated test3 (compile tcc then compile tcc then compile tcctest.c !)
|
||||
test3 test3b: tcctest.c test.ref
|
||||
@echo ------------ $@ ------------
|
||||
$(TCC) $(RUN_TCC) $(RUN_TCC) $(RUN_TCC) -w -run $< > test.out3
|
||||
@diff -u test.ref test.out3 && echo "$(AUTO_TEST)3 OK"
|
||||
|
||||
AUTO_TEST = Auto Test
|
||||
test%b : TCCFLAGS += -b -bt1
|
||||
test%b : AUTO_TEST = Auto Bound-Test
|
||||
|
||||
# binary output test
|
||||
test4: tcctest.c test.ref
|
||||
@echo ------------ $@ ------------
|
||||
# object + link output
|
||||
$(TCC) -c -o tcctest3.o $<
|
||||
$(TCC) -o tcctest3 tcctest3.o
|
||||
./tcctest3 > test3.out
|
||||
@if diff -u test.ref test3.out ; then echo "Object $(AUTO_TEST) OK"; fi
|
||||
# dynamic output
|
||||
$(TCC) -o tcctest1 $<
|
||||
./tcctest1 > test1.out
|
||||
@if diff -u test.ref test1.out ; then echo "Dynamic $(AUTO_TEST) OK"; fi
|
||||
# dynamic output + bound check
|
||||
$(TCC) -b -o tcctest4 $<
|
||||
./tcctest4 > test4.out
|
||||
@if diff -u test.ref test4.out ; then echo "BCheck $(AUTO_TEST) OK"; fi
|
||||
|
||||
test4_static: tcctest.c test.ref
|
||||
@echo ------------ $@ ------------
|
||||
# static output.
|
||||
$(TCC) -static -o tcctest2 $<
|
||||
./tcctest2 > test2.out
|
||||
@if diff -u test.ref test2.out ; then echo "Static $(AUTO_TEST) OK"; fi
|
||||
|
||||
# use tcc to create libtcc.so/.dll and the tcc(.exe) frontend and run them
|
||||
dlltest:
|
||||
@echo ------------ $@ ------------
|
||||
$(TCC) -DLIBTCC_AS_DLL $(TOPSRC)/libtcc.c $(LIBS) -shared -o libtcc2$(DLLSUF)
|
||||
$(TCC) -DONE_SOURCE=0 $(TOPSRC)/tcc.c libtcc2$(DLLSUF) $(LIBS) -Wl,-rpath=. -o tcc2$(EXESUF)
|
||||
./tcc2$(EXESUF) $(TCCFLAGS) $(RUN_TCC) -run $(TOPSRC)/examples/ex1.c
|
||||
ifeq (,$(filter Darwin WIN32,$(TARGETOS)))
|
||||
@echo ------------ $@ with PIC ------------
|
||||
$(CC) $(CFLAGS) -fPIC -DLIBTCC_AS_DLL -c $(TOPSRC)/libtcc.c
|
||||
$(TCC) libtcc.o $(LIBS) -shared -o libtcc2$(DLLSUF)
|
||||
$(TCC) -DONE_SOURCE=0 $(TOPSRC)/tcc.c libtcc2$(DLLSUF) $(LIBS) -Wl,-rpath=. -o tcc2$(EXESUF)
|
||||
./tcc2$(EXESUF) $(TCCFLAGS) $(RUN_TCC) -run $(TOPSRC)/examples/ex1.c
|
||||
endif
|
||||
@rm tcc2$(EXESUF) libtcc2$(DLLSUF)
|
||||
|
||||
memtest:
|
||||
@echo ------------ $@ ------------
|
||||
$(CC) $(CFLAGS) -DMEM_DEBUG=2 $(TOPSRC)/tcc.c $(LIBS) -o memtest-tcc$(EXESUF)
|
||||
./memtest-tcc$(EXESUF) $(TCCFLAGS) $(TOPSRC)/tcc.c $(LIBS)
|
||||
./memtest-tcc$(EXESUF) $(TCCFLAGS) -run $(TOPSRC)/tcc.c $(TCCFLAGS) -w $(TOPSRC)/tests/tcctest.c
|
||||
@echo OK
|
||||
|
||||
# memory and bound check auto test
|
||||
BOUNDS_OK = 1 4 8 10 14 16
|
||||
BOUNDS_FAIL= 2 5 6 7 9 11 12 13 15 17 18
|
||||
|
||||
btest: boundtest.c
|
||||
@echo ------------ $@ ------------
|
||||
@for i in $(BOUNDS_OK); do \
|
||||
if $(TCC) -b -run $< $$i >/dev/null 2>&1 ; then \
|
||||
echo "Test $$i succeeded as expected" ; \
|
||||
else\
|
||||
echo "Failed positive test $$i" ; exit 1 ; \
|
||||
fi ;\
|
||||
done ;\
|
||||
for i in $(BOUNDS_FAIL); do \
|
||||
if $(TCC) -b -bt1 -run $< $$i >/dev/null 2>&1 ; then \
|
||||
echo "Failed negative test $$i" ; exit 1 ;\
|
||||
else\
|
||||
echo "Test $$i failed as expected" ; \
|
||||
fi ;\
|
||||
done ;\
|
||||
echo Bound-Test OK
|
||||
|
||||
tccb:
|
||||
@echo ------------ $@ ------------
|
||||
$(TCC) -b $(TOPSRC)/tcc.c $(TCCFLAGS) $(LIBS) -o tccb1.exe
|
||||
mv tccb1.exe tccb2.exe
|
||||
./tccb2.exe -b $(TOPSRC)/tcc.c $(TCCFLAGS) $(LIBS) -o tccb1.exe
|
||||
cmp -s tccb1.exe tccb2.exe && echo "Exe Bound-Test OK"
|
||||
|
||||
|
||||
# speed test
|
||||
speedtest: ex2 ex3
|
||||
@echo ------------ $@ ------------
|
||||
time ./ex2 1238 2 3 4 10 13 4
|
||||
time $(TCC) -run $(TOPSRC)/examples/ex2.c 1238 2 3 4 10 13 4
|
||||
time ./ex3 35
|
||||
time $(TCC) -run $(TOPSRC)/examples/ex3.c 35
|
||||
|
||||
weaktest: tcctest.c test.ref
|
||||
@echo ------------ $@ ------------
|
||||
$(TCC) -c $< -o weaktest.tcc.o
|
||||
$(CC) -c $< -o weaktest.gcc.o $(CFLAGS) -w -O0 -std=gnu99 -fno-omit-frame-pointer
|
||||
objdump -t weaktest.tcc.o | grep ' w ' | sed -e 's/.* \([a-zA-Z0-9_]*\)$$/\1/' | LC_ALL=C sort > weaktest.tcc.o.txt
|
||||
objdump -t weaktest.gcc.o | grep ' w ' | sed -e 's/.* \([a-zA-Z0-9_]*\)$$/\1/' | LC_ALL=C sort > weaktest.gcc.o.txt
|
||||
diff weaktest.gcc.o.txt weaktest.tcc.o.txt && echo "Weak Auto Test OK"
|
||||
|
||||
ex%: $(TOPSRC)/examples/ex%.c
|
||||
$(CC) -o $@ $< $(CFLAGS)
|
||||
|
||||
# tiny assembler testing
|
||||
asmtest.ref: asmtest.S
|
||||
$(CC) -Wa,-W -Wa,-mx86-used-note=no -o asmtest.ref.o -c asmtest.S
|
||||
objdump -D asmtest.ref.o > asmtest.ref
|
||||
|
||||
ifeq ($(ARCH),arm)
|
||||
asmtest asmtest2:
|
||||
TCC="${TCC}" ./arm-asm-testsuite.sh
|
||||
else
|
||||
asmtest asmtest2: asmtest.ref
|
||||
@echo ------------ $@ ------------
|
||||
$(TCC) $(MAYBE_RUN_TCC) -c asmtest.S
|
||||
objdump -D asmtest.o > asmtest.out
|
||||
@if diff -u --ignore-matching-lines="file format" asmtest.ref asmtest.out ; then echo "ASM Auto Test OK"; fi
|
||||
endif
|
||||
|
||||
# test assembler with tcc compiled by itself
|
||||
asmtest2: MAYBE_RUN_TCC = $(RUN_TCC)
|
||||
|
||||
# Check that code generated by libtcc is binary compatible with
|
||||
# that generated by CC
|
||||
abitest-cc.exe: abitest.c
|
||||
$(CC) -o $@ $^ $(CFLAGS) $(-LTCC) $(LIBS) -w
|
||||
|
||||
abitest-tcc.exe: abitest.c libtcc.c
|
||||
$(TCC) -o $@ $^ $(LIBS)
|
||||
|
||||
abitest-% : abitest-%.exe
|
||||
@echo ------------ $@ ------------
|
||||
./$< $(TCCFLAGS)
|
||||
|
||||
abitest: abitest-cc
|
||||
ifneq (-$(CONFIG_arm_eabi)-$(CONFIG_arm_vfp)-,-yes--)
|
||||
abitest: abitest-tcc
|
||||
endif
|
||||
|
||||
vla_test$(EXESUF): vla_test.c
|
||||
$(TCC) -o $@ $^
|
||||
|
||||
vla_test-run: vla_test$(EXESUF)
|
||||
@echo ------------ $@ ------------
|
||||
./vla_test$(EXESUF)
|
||||
|
||||
.PHONY: abitest vla_test tccb
|
||||
|
||||
asm-c-connect$(EXESUF): asm-c-connect-1.c asm-c-connect-2.c
|
||||
$(TCC) -o $@ $^
|
||||
|
||||
asm-c-connect-%.o: asm-c-connect-%.c
|
||||
$(TCC) -c -o $@ $<
|
||||
|
||||
asm-c-connect-sep$(EXESUF): asm-c-connect-1.o asm-c-connect-2.o
|
||||
$(TCC) -o $@ $^
|
||||
|
||||
asm-c-connect-test: asm-c-connect$(EXESUF) asm-c-connect-sep$(EXESUF)
|
||||
@echo ------------ $@ ------------
|
||||
./asm-c-connect$(EXESUF) > asm-c-connect.out1 && cat asm-c-connect.out1
|
||||
./asm-c-connect-sep$(EXESUF) > asm-c-connect.out2 && cat asm-c-connect.out2
|
||||
@diff -u asm-c-connect.out1 asm-c-connect.out2 || (echo "error"; exit 1)
|
||||
|
||||
# quick sanity check for cross-compilers
|
||||
cross-test : tcctest.c examples/ex3.c
|
||||
@echo ------------ $@ ------------
|
||||
$(foreach T,$(CROSS-TGTS),$(call CROSS-COMPILE,$T))
|
||||
|
||||
CROSS-TGTS = \
|
||||
i386 \
|
||||
i386-win32 \
|
||||
i386-OpenBSD \
|
||||
x86_64 \
|
||||
x86_64-win32 \
|
||||
x86_64-osx \
|
||||
x86_64-FreeBSD \
|
||||
x86_64-NetBSD \
|
||||
x86_64-OpenBSD \
|
||||
arm-fpa \
|
||||
arm-eabihf \
|
||||
arm-NetBSD \
|
||||
arm-wince \
|
||||
arm64 \
|
||||
arm64-win32 \
|
||||
arm64-osx \
|
||||
arm64-FreeBSD \
|
||||
arm64-NetBSD \
|
||||
arm64-OpenBSD \
|
||||
riscv64 \
|
||||
c67
|
||||
|
||||
define CROSS-COMPILE
|
||||
@echo " . $(1)"
|
||||
$(TCC) $(DEF-$1) -DTCC_CROSS_TEST -run $(TOPSRC)/tcc.c \
|
||||
-c $(if $(findstring c67,$1),$(filter %/ex3.c,$^),$<) -w $(TCCFLAGS)
|
||||
|
||||
endef
|
||||
|
||||
# targets for development
|
||||
%.bin: %.c tcc
|
||||
$(TCC) -g -o $@ $<
|
||||
$(DISAS) $@
|
||||
|
||||
instr: instr.o
|
||||
objdump -d instr.o
|
||||
|
||||
instr.o: instr.S
|
||||
$(CC) -o $@ -c $< -O2 -Wall -g
|
||||
|
||||
cache: tcc_g
|
||||
cachegrind ./tcc_g -o /tmp/linpack -lm bench/linpack.c
|
||||
vg_annotate tcc.c > /tmp/linpack.cache.log
|
||||
|
||||
# clean
|
||||
clean:
|
||||
rm -f *~ *.o *.a *.bin *.i *.ref *.out *.out? *.out?b *.cc *.gcc
|
||||
rm -f *-cc *-gcc *-tcc *.exe hello libtcc_test vla_test tcctest[1234]
|
||||
rm -f asm-c-connect asm-c-connect-sep
|
||||
rm -f ex? tcc_g weaktest.*.txt *.def *.pdb *.obj libtcc_test_mt
|
||||
@$(MAKE) -C tests2 $@
|
||||
@$(MAKE) -C pp $@
|
||||
|
||||
691
src/userland/cli/third_party/tcc/tests/abitest.c
vendored
Normal file
691
src/userland/cli/third_party/tcc/tests/abitest.c
vendored
Normal file
@@ -0,0 +1,691 @@
|
||||
#include <libtcc.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <stdarg.h>
|
||||
|
||||
// MinGW has 80-bit rather than 64-bit long double which isn't compatible with TCC or MSVC
|
||||
#if defined(_WIN32) && defined(__GNUC__)
|
||||
#define LONG_DOUBLE double
|
||||
#define LONG_DOUBLE_LITERAL(x) x
|
||||
#else
|
||||
#define LONG_DOUBLE long double
|
||||
#define LONG_DOUBLE_LITERAL(x) x ## L
|
||||
#endif
|
||||
|
||||
static int g_argc;
|
||||
static char **g_argv;
|
||||
|
||||
static void set_options(TCCState *s, int argc, char **argv)
|
||||
{
|
||||
int i;
|
||||
for (i = 1; i < argc; ++i) {
|
||||
char *a = argv[i];
|
||||
if (a[0] == '-') {
|
||||
if (a[1] == 'B')
|
||||
tcc_set_lib_path(s, a+2);
|
||||
else if (a[1] == 'I')
|
||||
tcc_add_include_path(s, a+2);
|
||||
else if (a[1] == 'L')
|
||||
tcc_add_library_path(s, a+2);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
typedef int (*callback_type) (void*);
|
||||
|
||||
/*
|
||||
* Compile source code and call a callback with a pointer to the symbol "f".
|
||||
*/
|
||||
static int run_callback(const char *src, callback_type callback) {
|
||||
TCCState *s;
|
||||
int result;
|
||||
void *ptr;
|
||||
|
||||
s = tcc_new();
|
||||
if (!s)
|
||||
return -1;
|
||||
|
||||
set_options(s, g_argc, g_argv);
|
||||
|
||||
if (tcc_set_output_type(s, TCC_OUTPUT_MEMORY) == -1)
|
||||
return -1;
|
||||
if (tcc_compile_string(s, src) == -1)
|
||||
return -1;
|
||||
if (tcc_relocate(s) == -1)
|
||||
return -1;
|
||||
|
||||
ptr = tcc_get_symbol(s, "f");
|
||||
if (!ptr)
|
||||
return -1;
|
||||
result = callback(ptr);
|
||||
|
||||
tcc_delete(s);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
#define STR2(x) #x
|
||||
#define STR(x) STR2(x)
|
||||
|
||||
#define RET_PRIMITIVE_TEST(name, type, val) \
|
||||
static int ret_ ## name ## _test_callback(void *ptr) { \
|
||||
type (*callback) (type) = (type(*)(type))ptr; \
|
||||
type x = val; \
|
||||
type y = callback(x); \
|
||||
return (y == x+x) ? 0 : -1; \
|
||||
} \
|
||||
\
|
||||
static int ret_ ## name ## _test(void) { \
|
||||
const char *src = STR(type) " f(" STR(type) " x) {return x+x;}"; \
|
||||
return run_callback(src, ret_ ## name ## _test_callback); \
|
||||
}
|
||||
|
||||
RET_PRIMITIVE_TEST(int, int, 70000)
|
||||
RET_PRIMITIVE_TEST(longlong, long long, 4333369356528LL)
|
||||
RET_PRIMITIVE_TEST(float, float, 63.0)
|
||||
RET_PRIMITIVE_TEST(double, double, 14789798.0)
|
||||
RET_PRIMITIVE_TEST(longdouble, LONG_DOUBLE, LONG_DOUBLE_LITERAL(378943892.0))
|
||||
|
||||
/*
|
||||
* ret_2float_test:
|
||||
*
|
||||
* On x86-64, a struct with 2 floats should be packed into a single
|
||||
* SSE register (VT_DOUBLE is used for this purpose).
|
||||
*/
|
||||
typedef struct ret_2float_test_type_s {float x, y;} ret_2float_test_type;
|
||||
typedef ret_2float_test_type (*ret_2float_test_function_type) (ret_2float_test_type);
|
||||
|
||||
static int ret_2float_test_callback(void *ptr) {
|
||||
ret_2float_test_function_type f = (ret_2float_test_function_type)ptr;
|
||||
ret_2float_test_type a = {10, 35};
|
||||
ret_2float_test_type r;
|
||||
r = f(a);
|
||||
return ((r.x == a.x*5) && (r.y == a.y*3)) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int ret_2float_test(void) {
|
||||
const char *src =
|
||||
"typedef struct ret_2float_test_type_s {float x, y;} ret_2float_test_type;"
|
||||
"ret_2float_test_type f(ret_2float_test_type a) {\n"
|
||||
" ret_2float_test_type r = {a.x*5, a.y*3};\n"
|
||||
" return r;\n"
|
||||
"}\n";
|
||||
|
||||
return run_callback(src, ret_2float_test_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* ret_2double_test:
|
||||
*
|
||||
* On x86-64, a struct with 2 doubles should be passed in two SSE
|
||||
* registers.
|
||||
*/
|
||||
typedef struct ret_2double_test_type_s {double x, y;} ret_2double_test_type;
|
||||
typedef ret_2double_test_type (*ret_2double_test_function_type) (ret_2double_test_type);
|
||||
|
||||
static int ret_2double_test_callback(void *ptr) {
|
||||
ret_2double_test_function_type f = (ret_2double_test_function_type)ptr;
|
||||
ret_2double_test_type a = {10, 35};
|
||||
ret_2double_test_type r;
|
||||
r = f(a);
|
||||
return ((r.x == a.x*5) && (r.y == a.y*3)) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int ret_2double_test(void) {
|
||||
const char *src =
|
||||
"typedef struct ret_2double_test_type_s {double x, y;} ret_2double_test_type;"
|
||||
"ret_2double_test_type f(ret_2double_test_type a) {\n"
|
||||
" ret_2double_test_type r = {a.x*5, a.y*3};\n"
|
||||
" return r;\n"
|
||||
"}\n";
|
||||
|
||||
return run_callback(src, ret_2double_test_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* ret_8plus2double_test:
|
||||
*
|
||||
* This catches a corner case in the x86_64 ABI code: the first 7
|
||||
* arguments fit into registers, the 8th doesn't, but the 9th argument
|
||||
* fits into the 8th XMM register.
|
||||
*
|
||||
* Note that the purpose of the 10th argument is to avoid a situation
|
||||
* in which gcc would accidentally put the double at the right
|
||||
* address, thus causing a success message even though TCC actually
|
||||
* generated incorrect code.
|
||||
*/
|
||||
typedef ret_2double_test_type (*ret_8plus2double_test_function_type) (double, double, double, double, double, double, double, ret_2double_test_type, double, double);
|
||||
|
||||
static int ret_8plus2double_test_callback(void *ptr) {
|
||||
ret_8plus2double_test_function_type f = (ret_8plus2double_test_function_type)ptr;
|
||||
ret_2double_test_type a = {10, 35};
|
||||
ret_2double_test_type r;
|
||||
r = f(0, 0, 0, 0, 0, 0, 0, a, 37, 38);
|
||||
return ((r.x == 37) && (r.y == 37)) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int ret_8plus2double_test(void) {
|
||||
const char *src =
|
||||
"typedef struct ret_2double_test_type_s {double x, y;} ret_2double_test_type;"
|
||||
"ret_2double_test_type f(double x1, double x2, double x3, double x4, double x5, double x6, double x7, ret_2double_test_type a, double x8, double x9) {\n"
|
||||
" ret_2double_test_type r = { x8, x8 };\n"
|
||||
" return r;\n"
|
||||
"}\n";
|
||||
|
||||
return run_callback(src, ret_8plus2double_test_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* ret_mixed_test:
|
||||
*
|
||||
* On x86-64, a struct with a double and a 64-bit integer should be
|
||||
* passed in one SSE register and one integer register.
|
||||
*/
|
||||
typedef struct ret_mixed_test_type_s {double x; long long y;} ret_mixed_test_type;
|
||||
typedef ret_mixed_test_type (*ret_mixed_test_function_type) (ret_mixed_test_type);
|
||||
|
||||
static int ret_mixed_test_callback(void *ptr) {
|
||||
ret_mixed_test_function_type f = (ret_mixed_test_function_type)ptr;
|
||||
ret_mixed_test_type a = {10, 35};
|
||||
ret_mixed_test_type r;
|
||||
r = f(a);
|
||||
return ((r.x == a.x*5) && (r.y == a.y*3)) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int ret_mixed_test(void) {
|
||||
const char *src =
|
||||
"typedef struct ret_mixed_test_type_s {double x; long long y;} ret_mixed_test_type;"
|
||||
"ret_mixed_test_type f(ret_mixed_test_type a) {\n"
|
||||
" ret_mixed_test_type r = {a.x*5, a.y*3};\n"
|
||||
" return r;\n"
|
||||
"}\n";
|
||||
|
||||
return run_callback(src, ret_mixed_test_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* ret_mixed2_test:
|
||||
*
|
||||
* On x86-64, a struct with two floats and two 32-bit integers should
|
||||
* be passed in one SSE register and one integer register.
|
||||
*/
|
||||
typedef struct ret_mixed2_test_type_s {float x,x2; int y,y2;} ret_mixed2_test_type;
|
||||
typedef ret_mixed2_test_type (*ret_mixed2_test_function_type) (ret_mixed2_test_type);
|
||||
|
||||
static int ret_mixed2_test_callback(void *ptr) {
|
||||
ret_mixed2_test_function_type f = (ret_mixed2_test_function_type)ptr;
|
||||
ret_mixed2_test_type a = {10, 5, 35, 7 };
|
||||
ret_mixed2_test_type r;
|
||||
r = f(a);
|
||||
return ((r.x == a.x*5) && (r.y == a.y*3)) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int ret_mixed2_test(void) {
|
||||
const char *src =
|
||||
"typedef struct ret_mixed2_test_type_s {float x, x2; int y,y2;} ret_mixed2_test_type;"
|
||||
"ret_mixed2_test_type f(ret_mixed2_test_type a) {\n"
|
||||
" ret_mixed2_test_type r = {a.x*5, 0, a.y*3, 0};\n"
|
||||
" return r;\n"
|
||||
"}\n";
|
||||
|
||||
return run_callback(src, ret_mixed2_test_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* ret_mixed3_test:
|
||||
*
|
||||
* On x86-64, this struct should be passed in two integer registers.
|
||||
*/
|
||||
typedef struct ret_mixed3_test_type_s {float x; int y; float x2; int y2;} ret_mixed3_test_type;
|
||||
typedef ret_mixed3_test_type (*ret_mixed3_test_function_type) (ret_mixed3_test_type);
|
||||
|
||||
static int ret_mixed3_test_callback(void *ptr) {
|
||||
ret_mixed3_test_function_type f = (ret_mixed3_test_function_type)ptr;
|
||||
ret_mixed3_test_type a = {10, 5, 35, 7 };
|
||||
ret_mixed3_test_type r;
|
||||
r = f(a);
|
||||
return ((r.x == a.x*5) && (r.y2 == a.y*3)) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int ret_mixed3_test(void) {
|
||||
const char *src =
|
||||
"typedef struct ret_mixed3_test_type_s {float x; int y; float x2; int y2;} ret_mixed3_test_type;"
|
||||
"ret_mixed3_test_type f(ret_mixed3_test_type a) {\n"
|
||||
" ret_mixed3_test_type r = {a.x*5, 0, 0, a.y*3};\n"
|
||||
" return r;\n"
|
||||
"}\n";
|
||||
|
||||
return run_callback(src, ret_mixed3_test_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* reg_pack_test: return a small struct which should be packed into
|
||||
* registers (Win32) during return.
|
||||
*/
|
||||
typedef struct reg_pack_test_type_s {int x, y;} reg_pack_test_type;
|
||||
typedef reg_pack_test_type (*reg_pack_test_function_type) (reg_pack_test_type);
|
||||
|
||||
static int reg_pack_test_callback(void *ptr) {
|
||||
reg_pack_test_function_type f = (reg_pack_test_function_type)ptr;
|
||||
reg_pack_test_type a = {10, 35};
|
||||
reg_pack_test_type r;
|
||||
r = f(a);
|
||||
return ((r.x == a.x*5) && (r.y == a.y*3)) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int reg_pack_test(void) {
|
||||
const char *src =
|
||||
"typedef struct reg_pack_test_type_s {int x, y;} reg_pack_test_type;"
|
||||
"reg_pack_test_type f(reg_pack_test_type a) {\n"
|
||||
" reg_pack_test_type r = {a.x*5, a.y*3};\n"
|
||||
" return r;\n"
|
||||
"}\n";
|
||||
|
||||
return run_callback(src, reg_pack_test_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* reg_pack_longlong_test: return a small struct which should be packed into
|
||||
* registers (x86-64) during return.
|
||||
*/
|
||||
typedef struct reg_pack_longlong_test_type_s {long long x, y;} reg_pack_longlong_test_type;
|
||||
typedef reg_pack_longlong_test_type (*reg_pack_longlong_test_function_type) (reg_pack_longlong_test_type);
|
||||
|
||||
static int reg_pack_longlong_test_callback(void *ptr) {
|
||||
reg_pack_longlong_test_function_type f = (reg_pack_longlong_test_function_type)ptr;
|
||||
reg_pack_longlong_test_type a = {10, 35};
|
||||
reg_pack_longlong_test_type r;
|
||||
r = f(a);
|
||||
return ((r.x == a.x*5) && (r.y == a.y*3)) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int reg_pack_longlong_test(void) {
|
||||
const char *src =
|
||||
"typedef struct reg_pack_longlong_test_type_s {long long x, y;} reg_pack_longlong_test_type;"
|
||||
"reg_pack_longlong_test_type f(reg_pack_longlong_test_type a) {\n"
|
||||
" reg_pack_longlong_test_type r = {a.x*5, a.y*3};\n"
|
||||
" return r;\n"
|
||||
"}\n";
|
||||
|
||||
return run_callback(src, reg_pack_longlong_test_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* ret_6plus2longlong_test:
|
||||
*
|
||||
* This catches a corner case in the x86_64 ABI code: the first 5
|
||||
* arguments fit into registers, the 6th doesn't, but the 7th argument
|
||||
* fits into the 6th argument integer register, %r9.
|
||||
*
|
||||
* Note that the purpose of the 10th argument is to avoid a situation
|
||||
* in which gcc would accidentally put the longlong at the right
|
||||
* address, thus causing a success message even though TCC actually
|
||||
* generated incorrect code.
|
||||
*/
|
||||
typedef reg_pack_longlong_test_type (*ret_6plus2longlong_test_function_type) (long long, long long, long long, long long, long long, reg_pack_longlong_test_type, long long, long long);
|
||||
|
||||
static int ret_6plus2longlong_test_callback(void *ptr) {
|
||||
ret_6plus2longlong_test_function_type f = (ret_6plus2longlong_test_function_type)ptr;
|
||||
reg_pack_longlong_test_type a = {10, 35};
|
||||
reg_pack_longlong_test_type r;
|
||||
r = f(0, 0, 0, 0, 0, a, 37, 38);
|
||||
return ((r.x == 37) && (r.y == 37)) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int ret_6plus2longlong_test(void) {
|
||||
const char *src =
|
||||
"typedef struct reg_pack_longlong_test_type_s {long long x, y;} reg_pack_longlong_test_type;"
|
||||
"reg_pack_longlong_test_type f(long long x1, long long x2, long long x3, long long x4, long long x5, reg_pack_longlong_test_type a, long long x8, long long x9) {\n"
|
||||
" reg_pack_longlong_test_type r = { x8, x8 };\n"
|
||||
" return r;\n"
|
||||
"}\n";
|
||||
|
||||
return run_callback(src, ret_6plus2longlong_test_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* sret_test: Create a struct large enough to be returned via sret
|
||||
* (hidden pointer as first function argument)
|
||||
*/
|
||||
typedef struct sret_test_type_s {long long a, b, c;} sret_test_type;
|
||||
typedef sret_test_type (*sret_test_function_type) (sret_test_type);
|
||||
|
||||
static int sret_test_callback(void *ptr) {
|
||||
sret_test_function_type f = (sret_test_function_type)(ptr);
|
||||
sret_test_type x = {5436LL, 658277698LL, 43878957LL};
|
||||
sret_test_type r = f(x);
|
||||
return ((r.a==x.a*35)&&(r.b==x.b*19)&&(r.c==x.c*21)) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int sret_test(void) {
|
||||
const char *src =
|
||||
"typedef struct sret_test_type_s {long long a, b, c;} sret_test_type;\n"
|
||||
"sret_test_type f(sret_test_type x) {\n"
|
||||
" sret_test_type r = {x.a*35, x.b*19, x.c*21};\n"
|
||||
" return r;\n"
|
||||
"}\n";
|
||||
|
||||
return run_callback(src, sret_test_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* one_member_union_test:
|
||||
*
|
||||
* In the x86-64 ABI a union should always be passed on the stack. However
|
||||
* it appears that a single member union is treated by GCC as its member.
|
||||
*/
|
||||
typedef union one_member_union_test_type_u {int x;} one_member_union_test_type;
|
||||
typedef one_member_union_test_type (*one_member_union_test_function_type) (one_member_union_test_type);
|
||||
|
||||
static int one_member_union_test_callback(void *ptr) {
|
||||
one_member_union_test_function_type f = (one_member_union_test_function_type)ptr;
|
||||
one_member_union_test_type a, b;
|
||||
a.x = 34;
|
||||
b = f(a);
|
||||
return (b.x == a.x*2) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int one_member_union_test(void) {
|
||||
const char *src =
|
||||
"typedef union one_member_union_test_type_u {int x;} one_member_union_test_type;\n"
|
||||
"one_member_union_test_type f(one_member_union_test_type a) {\n"
|
||||
" one_member_union_test_type b;\n"
|
||||
" b.x = a.x * 2;\n"
|
||||
" return b;\n"
|
||||
"}\n";
|
||||
return run_callback(src, one_member_union_test_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* two_member_union_test:
|
||||
*
|
||||
* In the x86-64 ABI a union should always be passed on the stack.
|
||||
*/
|
||||
typedef union two_member_union_test_type_u {int x; long y;} two_member_union_test_type;
|
||||
typedef two_member_union_test_type (*two_member_union_test_function_type) (two_member_union_test_type);
|
||||
|
||||
static int two_member_union_test_callback(void *ptr) {
|
||||
two_member_union_test_function_type f = (two_member_union_test_function_type)ptr;
|
||||
two_member_union_test_type a, b;
|
||||
a.x = 34;
|
||||
b = f(a);
|
||||
return (b.x == a.x*2) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int two_member_union_test(void) {
|
||||
const char *src =
|
||||
"typedef union two_member_union_test_type_u {int x; long y;} two_member_union_test_type;\n"
|
||||
"two_member_union_test_type f(two_member_union_test_type a) {\n"
|
||||
" two_member_union_test_type b;\n"
|
||||
" b.x = a.x * 2;\n"
|
||||
" return b;\n"
|
||||
"}\n";
|
||||
return run_callback(src, two_member_union_test_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* Win64 calling convention test.
|
||||
*/
|
||||
|
||||
typedef struct many_struct_test_type_s {long long a, b, c;} many_struct_test_type;
|
||||
typedef many_struct_test_type (*many_struct_test_function_type) (many_struct_test_type,many_struct_test_type,many_struct_test_type,many_struct_test_type,many_struct_test_type,many_struct_test_type);
|
||||
|
||||
static int many_struct_test_callback(void *ptr) {
|
||||
many_struct_test_function_type f = (many_struct_test_function_type)ptr;
|
||||
many_struct_test_type v = {1, 2, 3};
|
||||
many_struct_test_type r = f(v,v,v,v,v,v);
|
||||
return ((r.a == 6) && (r.b == 12) && (r.c == 18))?0:-1;
|
||||
}
|
||||
|
||||
static int many_struct_test(void) {
|
||||
const char *src =
|
||||
"typedef struct many_struct_test_type_s {long long a, b, c;} many_struct_test_type;\n"
|
||||
"many_struct_test_type f(many_struct_test_type x1, many_struct_test_type x2, many_struct_test_type x3, many_struct_test_type x4, many_struct_test_type x5, many_struct_test_type x6) {\n"
|
||||
" many_struct_test_type y;\n"
|
||||
" y.a = x1.a + x2.a + x3.a + x4.a + x5.a + x6.a;\n"
|
||||
" y.b = x1.b + x2.b + x3.b + x4.b + x5.b + x6.b;\n"
|
||||
" y.c = x1.c + x2.c + x3.c + x4.c + x5.c + x6.c;\n"
|
||||
" return y;\n"
|
||||
"}\n";
|
||||
return run_callback(src, many_struct_test_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* Win64 calling convention test.
|
||||
*/
|
||||
|
||||
typedef struct many_struct_test_2_type_s {int a, b;} many_struct_test_2_type;
|
||||
typedef many_struct_test_2_type (*many_struct_test_2_function_type) (many_struct_test_2_type,many_struct_test_2_type,many_struct_test_2_type,many_struct_test_2_type,many_struct_test_2_type,many_struct_test_2_type);
|
||||
|
||||
static int many_struct_test_2_callback(void *ptr) {
|
||||
many_struct_test_2_function_type f = (many_struct_test_2_function_type)ptr;
|
||||
many_struct_test_2_type v = {1,2};
|
||||
many_struct_test_2_type r = f(v,v,v,v,v,v);
|
||||
return ((r.a == 6) && (r.b == 12))?0:-1;
|
||||
}
|
||||
|
||||
static int many_struct_test_2(void) {
|
||||
const char *src =
|
||||
"typedef struct many_struct_test_2_type_s {int a, b;} many_struct_test_2_type;\n"
|
||||
"many_struct_test_2_type f(many_struct_test_2_type x1, many_struct_test_2_type x2, many_struct_test_2_type x3, many_struct_test_2_type x4, many_struct_test_2_type x5, many_struct_test_2_type x6) {\n"
|
||||
" many_struct_test_2_type y;\n"
|
||||
" y.a = x1.a + x2.a + x3.a + x4.a + x5.a + x6.a;\n"
|
||||
" y.b = x1.b + x2.b + x3.b + x4.b + x5.b + x6.b;\n"
|
||||
" return y;\n"
|
||||
"}\n";
|
||||
return run_callback(src, many_struct_test_2_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* Win64 calling convention test.
|
||||
*/
|
||||
|
||||
typedef struct many_struct_test_3_type_s {int a, b;} many_struct_test_3_type;
|
||||
typedef many_struct_test_3_type (*many_struct_test_3_function_type) (many_struct_test_3_type,many_struct_test_3_type,many_struct_test_3_type,many_struct_test_3_type,many_struct_test_3_type,many_struct_test_3_type, ...);
|
||||
typedef struct many_struct_test_3_struct_type { many_struct_test_3_function_type f; many_struct_test_3_function_type *f2; } many_struct_test_3_struct_type;
|
||||
|
||||
static void many_struct_test_3_dummy(double d, ...)
|
||||
{
|
||||
volatile double x = d;
|
||||
}
|
||||
|
||||
static int many_struct_test_3_callback(void *ptr) {
|
||||
many_struct_test_3_struct_type s = { ptr, };
|
||||
many_struct_test_3_struct_type *s2 = &s;
|
||||
s2->f2 = &s2->f;
|
||||
many_struct_test_3_dummy(1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, &s2);
|
||||
many_struct_test_3_function_type f = *(s2->f2);
|
||||
many_struct_test_3_type v = {1,2};
|
||||
many_struct_test_3_type r = (*((s2->f2=&f)+0))(v,v,v,v,v,v,1.0);
|
||||
return ((r.a == 6) && (r.b == 12))?0:-1;
|
||||
}
|
||||
|
||||
static int many_struct_test_3(void) {
|
||||
const char *src =
|
||||
"typedef struct many_struct_test_3_type_s {int a, b;} many_struct_test_3_type;\n"
|
||||
"many_struct_test_3_type f(many_struct_test_3_type x1, many_struct_test_3_type x2, many_struct_test_3_type x3, many_struct_test_3_type x4, many_struct_test_3_type x5, many_struct_test_3_type x6, ...) {\n"
|
||||
" many_struct_test_3_type y;\n"
|
||||
" y.a = x1.a + x2.a + x3.a + x4.a + x5.a + x6.a;\n"
|
||||
" y.b = x1.b + x2.b + x3.b + x4.b + x5.b + x6.b;\n"
|
||||
" return y;\n"
|
||||
"}\n";
|
||||
return run_callback(src, many_struct_test_3_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* stdarg_test: Test variable argument list ABI
|
||||
*/
|
||||
|
||||
typedef struct {long long a, b, c;} stdarg_test_struct_type;
|
||||
typedef void (*stdarg_test_function_type) (int,int,int,...);
|
||||
|
||||
static int stdarg_test_callback(void *ptr) {
|
||||
stdarg_test_function_type f = (stdarg_test_function_type)ptr;
|
||||
int x;
|
||||
double y;
|
||||
stdarg_test_struct_type z = {1, 2, 3}, w;
|
||||
f(10, 10, 5,
|
||||
1, 2, 3, 4, 5, 6, 7, 8, 9, 10, &x,
|
||||
1.0, 2.0, 3.0, 4.0, 5.0, 6.0, 7.0, 8.0, 9.0, 10.0, &y,
|
||||
z, z, z, z, z, &w);
|
||||
return ((x == 55) && (y == 55) && (w.a == 5) && (w.b == 10) && (w.c == 15)) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int stdarg_test(void) {
|
||||
const char *src =
|
||||
"#include <stdarg.h>\n"
|
||||
"typedef struct {long long a, b, c;} stdarg_test_struct_type;\n"
|
||||
"void f(int n_int, int n_float, int n_struct, ...) {\n"
|
||||
" int i, ti = 0;\n"
|
||||
" double td = 0.0;\n"
|
||||
" stdarg_test_struct_type ts = {0,0,0}, tmp;\n"
|
||||
" va_list ap;\n"
|
||||
" va_start(ap, n_struct);\n"
|
||||
" for (i = 0, ti = 0; i < n_int; ++i)\n"
|
||||
" ti += va_arg(ap, int);\n"
|
||||
" *va_arg(ap, int*) = ti;\n"
|
||||
" for (i = 0, td = 0; i < n_float; ++i)\n"
|
||||
" td += va_arg(ap, double);\n"
|
||||
" *va_arg(ap, double*) = td;\n"
|
||||
" for (i = 0; i < n_struct; ++i) {\n"
|
||||
" tmp = va_arg(ap, stdarg_test_struct_type);\n"
|
||||
" ts.a += tmp.a; ts.b += tmp.b; ts.c += tmp.c;"
|
||||
" }\n"
|
||||
" *va_arg(ap, stdarg_test_struct_type*) = ts;\n"
|
||||
" va_end(ap);"
|
||||
"}\n";
|
||||
return run_callback(src, stdarg_test_callback);
|
||||
}
|
||||
|
||||
typedef struct {long long a, b;} stdarg_many_test_struct_type;
|
||||
typedef void (*stdarg_many_test_function_type) (int, int, int, int, int,
|
||||
stdarg_many_test_struct_type,
|
||||
int, int, ...);
|
||||
|
||||
static int stdarg_many_test_callback(void *ptr)
|
||||
{
|
||||
stdarg_many_test_function_type f = (stdarg_many_test_function_type)ptr;
|
||||
int x;
|
||||
stdarg_many_test_struct_type l = {10, 11};
|
||||
f(1, 2, 3, 4, 5, l, 6, 7, &x, 44);
|
||||
return x == 44 ? 0 : -1;
|
||||
}
|
||||
|
||||
static int stdarg_many_test(void)
|
||||
{
|
||||
const char *src =
|
||||
"#include <stdarg.h>\n"
|
||||
"typedef struct {long long a, b;} stdarg_many_test_struct_type;\n"
|
||||
"void f (int a, int b, int c, int d, int e, stdarg_many_test_struct_type l, int f, int g, ...){\n"
|
||||
" va_list ap;\n"
|
||||
" int *p;\n"
|
||||
" va_start (ap, g);\n"
|
||||
" p = va_arg(ap, int*);\n"
|
||||
" *p = va_arg(ap, int);\n"
|
||||
" va_end (ap);\n"
|
||||
"}\n";
|
||||
return run_callback(src, stdarg_many_test_callback);
|
||||
}
|
||||
|
||||
/*
|
||||
* Test Win32 stdarg handling, since the calling convention will pass a pointer
|
||||
* to the struct and the stdarg pointer must point to that pointer initially.
|
||||
*/
|
||||
|
||||
typedef struct {long long a, b, c;} stdarg_struct_test_struct_type;
|
||||
typedef int (*stdarg_struct_test_function_type) (stdarg_struct_test_struct_type a, ...);
|
||||
|
||||
static int stdarg_struct_test_callback(void *ptr) {
|
||||
stdarg_struct_test_function_type f = (stdarg_struct_test_function_type)ptr;
|
||||
stdarg_struct_test_struct_type v = {10, 35, 99};
|
||||
int x = f(v, 234);
|
||||
return (x == 378) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int stdarg_struct_test(void) {
|
||||
const char *src =
|
||||
"#include <stdarg.h>\n"
|
||||
"typedef struct {long long a, b, c;} stdarg_struct_test_struct_type;\n"
|
||||
"int f(stdarg_struct_test_struct_type a, ...) {\n"
|
||||
" va_list ap;\n"
|
||||
" va_start(ap, a);\n"
|
||||
" int z = va_arg(ap, int);\n"
|
||||
" va_end(ap);\n"
|
||||
" return z + a.a + a.b + a.c;\n"
|
||||
"}\n";
|
||||
return run_callback(src, stdarg_struct_test_callback);
|
||||
}
|
||||
|
||||
/* Test that x86-64 arranges the stack correctly for arguments with alignment >8 bytes */
|
||||
|
||||
typedef LONG_DOUBLE (*arg_align_test_callback_type) (LONG_DOUBLE,int,LONG_DOUBLE,int,LONG_DOUBLE);
|
||||
|
||||
static int arg_align_test_callback(void *ptr) {
|
||||
arg_align_test_callback_type f = (arg_align_test_callback_type)ptr;
|
||||
long double x = f(12, 0, 25, 0, 37);
|
||||
return (x == 74) ? 0 : -1;
|
||||
}
|
||||
|
||||
static int arg_align_test(void) {
|
||||
const char *src =
|
||||
"long double f(long double a, int b, long double c, int d, long double e) {\n"
|
||||
" return a + c + e;\n"
|
||||
"}\n";
|
||||
return run_callback(src, arg_align_test_callback);
|
||||
}
|
||||
|
||||
#define RUN_TEST(t) \
|
||||
if (!testname || (strcmp(#t, testname) == 0)) { \
|
||||
fputs(#t "... ", stdout); \
|
||||
fflush(stdout); \
|
||||
if (t() == 0) { \
|
||||
fputs("success\n", stdout); \
|
||||
} else { \
|
||||
fputs("failure\n", stdout); \
|
||||
retval = EXIT_FAILURE; \
|
||||
} \
|
||||
}
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
int i;
|
||||
const char *testname = NULL;
|
||||
int retval = EXIT_SUCCESS;
|
||||
|
||||
/* if tcclib.h and libtcc1.a are not installed, where can we find them */
|
||||
for (i = 1; i < argc; ++i) {
|
||||
if (!memcmp(argv[i], "run_test=", 9))
|
||||
testname = argv[i] + 9;
|
||||
}
|
||||
|
||||
g_argv = argv, g_argc = argc;
|
||||
|
||||
RUN_TEST(ret_int_test);
|
||||
RUN_TEST(ret_longlong_test);
|
||||
RUN_TEST(ret_float_test);
|
||||
RUN_TEST(ret_double_test);
|
||||
RUN_TEST(ret_longdouble_test);
|
||||
RUN_TEST(ret_2float_test);
|
||||
RUN_TEST(ret_2double_test);
|
||||
RUN_TEST(ret_8plus2double_test);
|
||||
RUN_TEST(ret_6plus2longlong_test);
|
||||
#if !defined __x86_64__ || defined _WIN32
|
||||
/* currently broken on x86_64 linux */
|
||||
RUN_TEST(ret_mixed_test);
|
||||
RUN_TEST(ret_mixed2_test);
|
||||
#endif
|
||||
RUN_TEST(ret_mixed3_test);
|
||||
RUN_TEST(reg_pack_test);
|
||||
RUN_TEST(reg_pack_longlong_test);
|
||||
RUN_TEST(sret_test);
|
||||
RUN_TEST(one_member_union_test);
|
||||
RUN_TEST(two_member_union_test);
|
||||
RUN_TEST(many_struct_test);
|
||||
RUN_TEST(many_struct_test_2);
|
||||
RUN_TEST(many_struct_test_3);
|
||||
RUN_TEST(stdarg_test);
|
||||
RUN_TEST(stdarg_many_test);
|
||||
RUN_TEST(stdarg_struct_test);
|
||||
RUN_TEST(arg_align_test);
|
||||
return retval;
|
||||
}
|
||||
243
src/userland/cli/third_party/tcc/tests/arm-asm-testsuite.sh
vendored
Executable file
243
src/userland/cli/third_party/tcc/tests/arm-asm-testsuite.sh
vendored
Executable file
@@ -0,0 +1,243 @@
|
||||
#!/bin/sh
|
||||
|
||||
set -e
|
||||
|
||||
# Note: "{r3}" is definitely different--but would complicate the assembler.
|
||||
|
||||
state="`mktemp -d`"
|
||||
cat ../arm-tok.h | \
|
||||
grep DEF_ASM | \
|
||||
grep -v 'not useful' | \
|
||||
grep -v '#define' | \
|
||||
grep -v '/[*]' | \
|
||||
grep -v 'DEF_ASM_CONDED_WITH_SUFFIX(x' | \
|
||||
sed -e 's;^[ ]*DEF_ASM_CONDED_VFP_F32_F64[^(]*(\(.*\)).*$; DEF_ASM_CONDED(\1.f32)\
|
||||
DEF_ASM_CONDED(\1.f64);g' | \
|
||||
sed -e 's;^[ ]*DEF_ASM[^(]*(\(.*\)).*$;\1;g' -e 's;, ;.;g' | \
|
||||
egrep -v '^((r|c|p|s|d)[0-9]+|fp|ip|sp|lr|pc|asl|apsr_nzcv|fpsid|fpscr|fpexc)$' | while read s
|
||||
do
|
||||
as_opts=""
|
||||
if [ "${s#v}" != "${s}" ]
|
||||
then
|
||||
if grep -q "CONFIG_arm_vfp=yes" ../config.mak
|
||||
then
|
||||
as_opts="${as_opts} -mfpu=vfp"
|
||||
else
|
||||
echo "note: skipping VFP instruction: $s (because VFP is disabled)">&2
|
||||
continue
|
||||
fi
|
||||
fi
|
||||
ok=0
|
||||
for args in "r3, r4, r5, r6" \
|
||||
"r3, r4, r5" \
|
||||
"r3, r4, r5, asl #7" \
|
||||
"r3, r4, r5, lsl #7" \
|
||||
"r3, r4, r5, asr #7" \
|
||||
"r3, r4, r5, lsr #7" \
|
||||
"r3, r4, r5, ror #7" \
|
||||
"r3, r4, r5, rrx" \
|
||||
"r3, r4, r5, asl r6" \
|
||||
"r3, r4, r5, lsl r6" \
|
||||
"r3, r4, r5, asr r6" \
|
||||
"r3, r4, r5, lsr r6" \
|
||||
"r3, r4, r5, ror r6" \
|
||||
"r3, r4, #5, asl #7" \
|
||||
"r3, r4, #5, lsl #7" \
|
||||
"r3, r4, #5, asr #7" \
|
||||
"r3, r4, #5, lsr #7" \
|
||||
"r3, r4, #5, ror #7" \
|
||||
"r3, r4, #5, rrx" \
|
||||
"r3, #5, r4" \
|
||||
"r3, #4, #8" \
|
||||
"r3, r4, asl #5" \
|
||||
"r3, r4, lsl #5" \
|
||||
"r3, r4, asr #5" \
|
||||
"r3, r4, lsr #5" \
|
||||
"r3, r4, ror #5" \
|
||||
"r3, r4, ror #8" \
|
||||
"r3, r4, asl r5" \
|
||||
"r3, r4, lsl r5" \
|
||||
"r3, r4, asr r5" \
|
||||
"r3, r4, lsr r5" \
|
||||
"r3, r4, ror r5" \
|
||||
"r3, r4, ror #8" \
|
||||
"r3, r4, ror #16" \
|
||||
"r3, r4, ror #24" \
|
||||
"r3, r4, rrx" \
|
||||
"r3, #4, asl #5" \
|
||||
"r3, #4, lsl #5" \
|
||||
"r3, #4, asr #5" \
|
||||
"r3, #4, lsr #5" \
|
||||
"r3, #4, ror #5" \
|
||||
"r3, r4, rrx" \
|
||||
"r3, r4" \
|
||||
"r3" \
|
||||
"{r3,r4,r5}" \
|
||||
"{r3,r5,r4}" \
|
||||
"r2!, {r3,r4,r5}" \
|
||||
"r2!, {r3,r5,r4}" \
|
||||
"r2, {r3,r4,r5}" \
|
||||
"r2, {r3,r5,r4}" \
|
||||
"r2, [r3, r4]" \
|
||||
"r2, [r3, r4]!" \
|
||||
"r2, [r3, -r4]" \
|
||||
"r2, [r3, -r4]!" \
|
||||
"r2, [r3], r4" \
|
||||
"r2, [r3], -r4" \
|
||||
"r2, [r3]" \
|
||||
"r2, r3, [r4, lsl# 2]" \
|
||||
"r2, [r3, r4, lsr# 1]" \
|
||||
"r2, [r3, r4, lsr# 2]!" \
|
||||
"r2, [r3, -r4, ror# 3]" \
|
||||
"r2, [r3, -r4, lsl# 1]!" \
|
||||
"r2, [r3], r4, lsl# 3" \
|
||||
"r2, [r3], -r4, asr# 31" \
|
||||
"r2, [r3], -r4, asl# 1" \
|
||||
"r2, [r3], -r4, rrx" \
|
||||
"r2, [r3]" \
|
||||
"r2, r3, [r4]" \
|
||||
"r2, [r3, #4]" \
|
||||
"r2, [r3, #-4]" \
|
||||
"r2, [r3, #0x45]" \
|
||||
"r2, [r3, #-0x45]" \
|
||||
"r2, r3, #4" \
|
||||
"r2, r3, #-4" \
|
||||
"p10, #7, c2, c0, c1, #4" \
|
||||
"p10, #7, r2, c0, c1, #4" \
|
||||
"p10, #0, c2, c0, c1, #4" \
|
||||
"p10, #0, r2, c0, c1, #4" \
|
||||
"r2, #4" \
|
||||
"r2, #-4" \
|
||||
"r2, #0xEFFF" \
|
||||
"r3, #0x0000" \
|
||||
"r4, #0x0201" \
|
||||
"r4, #0xFFFFFF00" \
|
||||
"r2, #-4" \
|
||||
"p10, #7, c2, c0, c1, #4" \
|
||||
"p10, #7, r2, c0, c1, #4" \
|
||||
"#4" \
|
||||
"#-4" \
|
||||
"p5, c2, [r3]" \
|
||||
"p5, c3, [r4]" \
|
||||
"p5, c2, [r3, #4]" \
|
||||
"p5, c2, [r3, #-4]" \
|
||||
"p5, c2, [r3, #0x45]" \
|
||||
"p5, c2, [r3, #-0x45]" \
|
||||
"s2, [r3]" \
|
||||
"s3, [r4]" \
|
||||
"s2, [r3, #4]" \
|
||||
"s2, [r3, #-4]" \
|
||||
"s2, [r3, #0x45]" \
|
||||
"s2, [r3, #-0x45]" \
|
||||
"r1, {d3-d4}" \
|
||||
"r1!, {d3-d4}" \
|
||||
"r2, {d4-d15}" \
|
||||
"r3!, {d4-d15}" \
|
||||
"r3!, {d4}" \
|
||||
"r2, {s4-s31}" \
|
||||
"r3!, {s4}" \
|
||||
"{d3-d4}" \
|
||||
"{d4-d15}" \
|
||||
"{d4}" \
|
||||
"{s4-s31}" \
|
||||
"{s4}" \
|
||||
"s2, s3, s4" \
|
||||
"s2, s3" \
|
||||
"d2, d3, d4" \
|
||||
"d2, d3" \
|
||||
"s2, #0" \
|
||||
"d2, #0" \
|
||||
"s3, #0.0" \
|
||||
"d3, #0.0" \
|
||||
"s4, #-0.1796875" \
|
||||
"d4, #0.1796875" \
|
||||
"r2, r3, d1" \
|
||||
"d1, r2, r3" \
|
||||
"s1, r2" \
|
||||
"r2, s1" \
|
||||
"r2, fpexc" \
|
||||
"r2, fpscr" \
|
||||
"r2, fpsid" \
|
||||
"apsr_nzcv, fpscr" \
|
||||
"fpexc, r2" \
|
||||
"fpscr, r2" \
|
||||
"fpsid, r2" \
|
||||
"s3, d4" \
|
||||
"d4, s3" \
|
||||
""
|
||||
do
|
||||
#echo ".syntax unified" > a.s
|
||||
err="`mktemp --suffix=-stderr.log`"
|
||||
as_object="${state}/as-$s $args.o"
|
||||
tcc_object="${state}/tcc-$s $args.o"
|
||||
expected="${state}/expected-$s $args"
|
||||
got="${state}/got-$s $args"
|
||||
if echo "$s $args" | "${CROSS_COMPILE}as" -mlittle-endian ${as_opts} -o "${as_object}" - 2>"${err}"
|
||||
then
|
||||
cat "${err}"
|
||||
rm -f "${err}"
|
||||
total_count=`expr $total_count + 1`
|
||||
"${CROSS_COMPILE}objdump" -S "${as_object}" |grep "^[ ]*0:" >"${expected}"
|
||||
|
||||
#echo '__asm__("'"$s ${args}"'");' > "${csource}"
|
||||
if echo '__asm__("'"$s ${args}"'");'| ${TCC} -o "${tcc_object}" -c -
|
||||
then
|
||||
"${CROSS_COMPILE}objdump" -S "${tcc_object}" |grep "^[ ]*0:" >"${got}"
|
||||
if diff -u "${got}" "${expected}"
|
||||
then
|
||||
touch "${state}/ok-$s $args"
|
||||
else
|
||||
echo "warning: '$s $args' did not work in tcc (see above)">&2
|
||||
fi
|
||||
else
|
||||
rm -f "${tcc_object}"
|
||||
echo "warning: '$s $args' did not work in tcc">&2
|
||||
fi
|
||||
ok=1
|
||||
else # GNU as can't do it either--so we don't care
|
||||
rm -f "${as_object}"
|
||||
fi
|
||||
rm -f "${err}"
|
||||
done
|
||||
if [ "${ok}" -eq "0" ]
|
||||
then
|
||||
echo "warning: $s could not be used.">&2
|
||||
continue
|
||||
fi
|
||||
done
|
||||
|
||||
successful_count="$(ls -1 "${state}/ok-"* |wc -l)"
|
||||
total_count="$(ls -1 "${state}/as-"*.o |wc -l)"
|
||||
echo "${successful_count} of ${total_count} tests succeeded.">&2
|
||||
if [ "${successful_count}" -eq "${total_count}" ]
|
||||
then
|
||||
rm -rf "${state}"
|
||||
exit 0
|
||||
else
|
||||
status=0
|
||||
for s in "${state}/as-"*.o
|
||||
do
|
||||
test="$(basename "$s")"
|
||||
test="${test%.o}"
|
||||
test="${test#as-}"
|
||||
t="${state}/ok-${test}"
|
||||
if [ ! -f "$t" ]
|
||||
then
|
||||
case "${test}" in
|
||||
"bl r3"|"b r3"|"mov r2, #0xEFFF"|"mov r4, #0x0201")
|
||||
known_failure=" (known failure)"
|
||||
;;
|
||||
"vmov.f32 r2, r3, d1"|"vmov.f32 d1, r2, r3") # GNU as bug
|
||||
known_failure=" (known failure)"
|
||||
;;
|
||||
*)
|
||||
known_failure=""
|
||||
status=1
|
||||
;;
|
||||
esac
|
||||
echo "Failed test: ${test}${known_failure}">&2
|
||||
fi
|
||||
done
|
||||
rm -rf "${state}"
|
||||
exit "${status}"
|
||||
fi
|
||||
69
src/userland/cli/third_party/tcc/tests/asm-c-connect-1.c
vendored
Normal file
69
src/userland/cli/third_party/tcc/tests/asm-c-connect-1.c
vendored
Normal file
@@ -0,0 +1,69 @@
|
||||
#include <stdio.h>
|
||||
|
||||
#if (defined _WIN32 || defined __APPLE__) && (!defined __TINYC__ || defined __leading_underscore)
|
||||
# define _ "_"
|
||||
#else
|
||||
# define _
|
||||
#endif
|
||||
|
||||
#ifdef __clang__
|
||||
/* clang needs some help tp not throw functions away even at -O0 */
|
||||
#define __USED __attribute__((__used__))
|
||||
#else
|
||||
#define __USED
|
||||
#endif
|
||||
|
||||
static int __USED x1_c (void)
|
||||
{
|
||||
printf(" x1");
|
||||
return 1;
|
||||
}
|
||||
|
||||
#if __i386__
|
||||
asm(".text;"_"x1: call "_"x1_c; ret");
|
||||
#else
|
||||
/* Keep stack aligned */
|
||||
asm(".text;"_"x1: sub $8,%rsp; call "_"x1_c; add $8,%rsp; ret");
|
||||
#endif
|
||||
|
||||
void callx4(void);
|
||||
void callx5_again(void);
|
||||
|
||||
void x6()
|
||||
{
|
||||
printf(" x6-1");
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
printf("*");
|
||||
asm("call "_"x1");
|
||||
asm("call "_"x2");
|
||||
asm("call "_"x3");
|
||||
callx4();
|
||||
asm("call "_"x5");
|
||||
callx5_again();
|
||||
x6();
|
||||
printf(" *\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
static
|
||||
int __USED x2(void)
|
||||
{
|
||||
printf(" x2");
|
||||
return 2;
|
||||
}
|
||||
|
||||
extern int x3(void);
|
||||
|
||||
void x4(void)
|
||||
{
|
||||
printf(" x4");
|
||||
}
|
||||
|
||||
void x5(void);
|
||||
void x5(void)
|
||||
{
|
||||
printf(" x5");
|
||||
}
|
||||
48
src/userland/cli/third_party/tcc/tests/asm-c-connect-2.c
vendored
Normal file
48
src/userland/cli/third_party/tcc/tests/asm-c-connect-2.c
vendored
Normal file
@@ -0,0 +1,48 @@
|
||||
#include <stdio.h>
|
||||
|
||||
#if (defined _WIN32 || defined __APPLE__) && (!defined __TINYC__ || defined __leading_underscore)
|
||||
# define _ "_"
|
||||
#else
|
||||
# define _
|
||||
#endif
|
||||
|
||||
#ifdef __clang__
|
||||
/* clang needs some help tp not throw functions away even at -O0 */
|
||||
#define __USED __attribute__((__used__))
|
||||
#else
|
||||
#define __USED
|
||||
#endif
|
||||
|
||||
int x3(void)
|
||||
{
|
||||
printf(" x3");
|
||||
return 3;
|
||||
}
|
||||
|
||||
/* That callx4 is defined globally (as if ".globl callx4")
|
||||
is a TCC extension. GCC doesn't behave like this. */
|
||||
void callx4(void);
|
||||
#if __i386__
|
||||
__asm__(_"callx4: call "_"x4; ret;"
|
||||
#else
|
||||
/* Keep stack aligned */
|
||||
__asm__(_"callx4: sub $8,%rsp; call "_"x4; add $8,%rsp; ret;"
|
||||
#endif
|
||||
#ifndef __TINYC__
|
||||
" .global "_"callx4"
|
||||
#endif
|
||||
);
|
||||
|
||||
extern void x5(void);
|
||||
|
||||
void callx5_again(void);
|
||||
void callx5_again(void)
|
||||
{
|
||||
x5();
|
||||
asm("call "_"x6");
|
||||
}
|
||||
|
||||
static void __USED x6()
|
||||
{
|
||||
printf(" x6-2");
|
||||
}
|
||||
1025
src/userland/cli/third_party/tcc/tests/asmtest.S
vendored
Normal file
1025
src/userland/cli/third_party/tcc/tests/asmtest.S
vendored
Normal file
File diff suppressed because it is too large
Load Diff
297
src/userland/cli/third_party/tcc/tests/boundtest.c
vendored
Normal file
297
src/userland/cli/third_party/tcc/tests/boundtest.c
vendored
Normal file
@@ -0,0 +1,297 @@
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#define NB_ITS 1000000
|
||||
//#define NB_ITS 1
|
||||
#define TAB_SIZE 100
|
||||
|
||||
int tab[TAB_SIZE];
|
||||
int ret_sum;
|
||||
char tab3[256];
|
||||
|
||||
int test1(void)
|
||||
{
|
||||
int i, sum = 0;
|
||||
for(i=0;i<TAB_SIZE;i++) {
|
||||
sum += tab[i];
|
||||
}
|
||||
return sum;
|
||||
}
|
||||
|
||||
/* error */
|
||||
int test2(void)
|
||||
{
|
||||
int i, sum = 0;
|
||||
for(i=0;i<TAB_SIZE + 1;i++) {
|
||||
sum += tab[i];
|
||||
}
|
||||
return sum;
|
||||
}
|
||||
|
||||
/* actually, profiling test */
|
||||
int test3(void)
|
||||
{
|
||||
int sum;
|
||||
int i, it;
|
||||
|
||||
sum = 0;
|
||||
for(it=0;it<NB_ITS;it++) {
|
||||
for(i=0;i<TAB_SIZE;i++) {
|
||||
sum += tab[i];
|
||||
}
|
||||
}
|
||||
return sum;
|
||||
}
|
||||
|
||||
/* ok */
|
||||
int test4(void)
|
||||
{
|
||||
int i, sum = 0;
|
||||
int *tab4;
|
||||
|
||||
tab4 = malloc(20 * sizeof(int));
|
||||
for(i=0;i<20;i++) {
|
||||
sum += tab4[i];
|
||||
}
|
||||
free(tab4);
|
||||
|
||||
return sum;
|
||||
}
|
||||
|
||||
/* error */
|
||||
int test5(void)
|
||||
{
|
||||
int i, sum = 0;
|
||||
int *tab4;
|
||||
|
||||
tab4 = malloc(20 * sizeof(int));
|
||||
for(i=0;i<21;i++) {
|
||||
sum += tab4[i];
|
||||
}
|
||||
free(tab4);
|
||||
|
||||
return sum;
|
||||
}
|
||||
|
||||
/* error */
|
||||
int test6(void)
|
||||
{
|
||||
int i, sum = 0;
|
||||
int *tab4;
|
||||
|
||||
tab4 = malloc(20 * sizeof(int));
|
||||
free(tab4);
|
||||
for(i=0;i<21;i++) {
|
||||
sum += tab4[i];
|
||||
}
|
||||
|
||||
return sum;
|
||||
}
|
||||
|
||||
/* error */
|
||||
int test7(void)
|
||||
{
|
||||
int i, sum = 0;
|
||||
int *p;
|
||||
|
||||
for(i=0;i<TAB_SIZE + 1;i++) {
|
||||
p = &tab[i];
|
||||
if (i == TAB_SIZE)
|
||||
printf("i=%d %x\n", i, p);
|
||||
sum += *p;
|
||||
}
|
||||
return sum;
|
||||
}
|
||||
|
||||
/* ok */
|
||||
int test8(void)
|
||||
{
|
||||
int i, sum = 0;
|
||||
int tab[10];
|
||||
|
||||
for(i=0;i<10;i++) {
|
||||
sum += tab[i];
|
||||
}
|
||||
return sum;
|
||||
}
|
||||
|
||||
/* error */
|
||||
int test9(void)
|
||||
{
|
||||
int i, sum = 0;
|
||||
char tab[10];
|
||||
|
||||
for(i=0;i<11;i++) {
|
||||
sum += tab[i];
|
||||
}
|
||||
return sum;
|
||||
}
|
||||
|
||||
/* ok */
|
||||
int test10(void)
|
||||
{
|
||||
char tab[10];
|
||||
char tab1[10];
|
||||
|
||||
memset(tab, 0, 10);
|
||||
memcpy(tab, tab1, 10);
|
||||
memmove(tab, tab1, 10);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* error */
|
||||
int test11(void)
|
||||
{
|
||||
char tab[10];
|
||||
|
||||
memset(tab, 0, 11);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* error */
|
||||
int test12(void)
|
||||
{
|
||||
void *ptr;
|
||||
ptr = malloc(10);
|
||||
free(ptr);
|
||||
free(ptr);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* error */
|
||||
int test13(void)
|
||||
{
|
||||
char pad1 = 0;
|
||||
char tab[10];
|
||||
char pad2 = 0;
|
||||
memset(tab, 'a', sizeof(tab));
|
||||
return strlen(tab);
|
||||
}
|
||||
|
||||
int test14(void)
|
||||
{
|
||||
char *p = alloca(TAB_SIZE);
|
||||
size_t ret;
|
||||
memset(p, 'a', TAB_SIZE);
|
||||
p[TAB_SIZE-1] = 0;
|
||||
ret = strlen(p);
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* error */
|
||||
int test15(void)
|
||||
{
|
||||
char *p = alloca(TAB_SIZE-1);
|
||||
size_t ret;
|
||||
memset(p, 'a', TAB_SIZE);
|
||||
p[TAB_SIZE-1] = 0;
|
||||
ret = strlen(p);
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* ok */
|
||||
int test16()
|
||||
{
|
||||
char *demo = "This is only a test.";
|
||||
char *p, *q;
|
||||
|
||||
p = alloca(16);
|
||||
strcpy(p,"12345678901234");
|
||||
|
||||
/* Test alloca embedded in a larger expression */
|
||||
printf("alloca : %s : %s\n", p, strcpy(q=alloca(strlen(demo)+1),demo) );
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* error */
|
||||
int test17()
|
||||
{
|
||||
char *demo = "This is only a test.";
|
||||
char *p, *q;
|
||||
|
||||
p = alloca(16);
|
||||
strcpy(p,"12345678901234");
|
||||
|
||||
/* Test alloca embedded in a larger expression */
|
||||
printf("alloca : %s : %s\n", p, strcpy(q=alloca(strlen(demo)),demo) );
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int test18(void)
|
||||
{
|
||||
int i, sum = 0, n = TAB_SIZE;
|
||||
int tab[n];
|
||||
for(i=0;i<TAB_SIZE+1;i++) {
|
||||
sum += tab[i];
|
||||
}
|
||||
return sum;
|
||||
}
|
||||
|
||||
int (*table_test[])(void) = {
|
||||
test1,
|
||||
test2,
|
||||
test3,
|
||||
test4,
|
||||
test5,
|
||||
test6,
|
||||
test7,
|
||||
test8,
|
||||
test9,
|
||||
test10,
|
||||
test11,
|
||||
test12,
|
||||
test13,
|
||||
test14,
|
||||
test15,
|
||||
test16,
|
||||
test17,
|
||||
test18
|
||||
};
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
int i;
|
||||
char *cp;
|
||||
int index;
|
||||
int (*ftest)(void);
|
||||
int index_max = sizeof(table_test)/sizeof(table_test[0]);
|
||||
|
||||
/* check bounds checking main arg */
|
||||
for (i = 0; i < argc; i++) {
|
||||
cp = argv[i];
|
||||
while (*cp) {
|
||||
cp++;
|
||||
}
|
||||
}
|
||||
|
||||
if (argc < 2) {
|
||||
printf(
|
||||
"test TCC bound checking system\n"
|
||||
"usage: boundtest N\n"
|
||||
" 1 <= N <= %d\n", index_max);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
index = 0;
|
||||
if (argc >= 2)
|
||||
index = atoi(argv[1]) - 1;
|
||||
|
||||
if ((index < 0) || (index >= index_max)) {
|
||||
printf("N is outside of the valid range (%d)\n", index);
|
||||
exit(2);
|
||||
}
|
||||
|
||||
/* well, we also use bounds on this ! */
|
||||
ftest = table_test[index];
|
||||
ftest();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* without bound 0.77 s
|
||||
* with bounds 4.73
|
||||
*/
|
||||
35
src/userland/cli/third_party/tcc/tests/bug.c
vendored
Normal file
35
src/userland/cli/third_party/tcc/tests/bug.c
vendored
Normal file
@@ -0,0 +1,35 @@
|
||||
#include <stdio.h>
|
||||
#include <stdarg.h>
|
||||
|
||||
int compile_errors(void)
|
||||
{
|
||||
#if TEST == 1
|
||||
{
|
||||
/* Not constant */
|
||||
static int i = (&"Foobar"[1] - &"Foobar"[0]);
|
||||
}
|
||||
#endif
|
||||
#if TEST == 2
|
||||
{
|
||||
/* Not constant */
|
||||
struct{int c;}v;
|
||||
static long i=((char*)&(v.c)-(char*)&v);
|
||||
}
|
||||
#endif
|
||||
#if TEST == 3
|
||||
{
|
||||
/* Not constant */
|
||||
static const short ar[] = { &&l1 - &&l1, &&l2 - &&l1 };
|
||||
void *p = &&l1 + ar[0];
|
||||
goto *p;
|
||||
l1: return 1;
|
||||
l2: return 2;
|
||||
}
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
main(void)
|
||||
{
|
||||
}
|
||||
164
src/userland/cli/third_party/tcc/tests/gcctestsuite.sh
vendored
Executable file
164
src/userland/cli/third_party/tcc/tests/gcctestsuite.sh
vendored
Executable file
@@ -0,0 +1,164 @@
|
||||
#!/bin/sh
|
||||
|
||||
if [ -z "$TESTSUITE_PATH" ]
|
||||
then
|
||||
if [ -d "$HOME/gcc/gcc-3.2/gcc/testsuite/gcc.c-torture" ]
|
||||
then
|
||||
TESTSUITE_PATH="$HOME/gcc/gcc-3.2/gcc/testsuite/gcc.c-torture"
|
||||
fi
|
||||
fi
|
||||
|
||||
if [ -z "$TESTSUITE_PATH" ]
|
||||
then
|
||||
echo "gcc testsuite not found."
|
||||
echo "define TESTSUITE_PATH to point to the gcc.c-torture directory"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
if [ -z "$TCC_SOURCE_PATH" ]
|
||||
then
|
||||
if [ -f "include/tccdefs.h" ]
|
||||
then
|
||||
TCC_SOURCE_PATH="."
|
||||
elif [ -f "../include/tccdefs.h" ]
|
||||
then
|
||||
TCC_SOURCE_PATH=".."
|
||||
elif [ -f "../tinycc/include/tccdefs.h" ]
|
||||
then
|
||||
TCC_SOURCE_PATH="../tinycc"
|
||||
fi
|
||||
fi
|
||||
|
||||
if [ -z "$RUNTIME_DIR" ]
|
||||
then
|
||||
RUNTIME_DIR=$XDG_RUNTIME_DIR
|
||||
fi
|
||||
if [ -z "$RUNTIME_DIR" ]
|
||||
then
|
||||
RUNTIME_DIR="/tmp"
|
||||
fi
|
||||
|
||||
if [ -z "$CC" ]
|
||||
then
|
||||
if [ -z "$TCC_SOURCE_PATH" ]
|
||||
then
|
||||
echo "tcc not found."
|
||||
echo "define TCC_SOURCE_PATH to point to the tcc source path"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
TCC="./tcc -B. -I$TCC_SOURCE_PATH/ -I$TCC_SOURCE_PATH/include -DNO_TRAMPOLINES"
|
||||
else
|
||||
TCC="$CC -O1 -Wno-implicit-int $CFLAGS"
|
||||
fi
|
||||
|
||||
rm -f tcc.sum tcc.fail
|
||||
nb_ok="0"
|
||||
nb_skipped="0"
|
||||
nb_failed="0"
|
||||
nb_exe_failed="0"
|
||||
|
||||
# skip some failed tests not implemented in tcc
|
||||
# builtin: gcc "__builtins_*"
|
||||
# ieee: gcc "__builtins_*" in the ieee directory
|
||||
# complex: C99 "_Complex" and gcc "__complex__"
|
||||
# misc: stdc features, other arch, gcc extensions (example: gnu_inline in c89)
|
||||
#
|
||||
|
||||
old_pwd="`pwd`"
|
||||
cd "$TESTSUITE_PATH"
|
||||
|
||||
skip_builtin="`grep '_builtin_' compile/*.c execute/*.c execute/ieee/*.c | cut -d ':' -f1 | cut -d '/' -f2 | sort -u `"
|
||||
skip_ieee="`grep '_builtin_' execute/ieee/*.c | cut -d ':' -f1 | cut -d '/' -f3 | sort -u `"
|
||||
skip_complex="`grep -i '_Complex' compile/*.c execute/*.c execute/ieee/*.c | cut -d ':' -f1 | cut -d '/' -f2 | sort -u `"
|
||||
skip_int128="`grep -Eiw '__int128_t|__uint128_t' compile/*.c execute/*.c execute/ieee/*.c | cut -d ':' -f1 | cut -d '/' -f2 | sort -u `"
|
||||
skip_vector="`grep -Eiw 'vector|vector_size|__vector_size__' compile/*.c execute/*.c execute/ieee/*.c | cut -d ':' -f1 | cut -d '/' -f2 | sort -u `"
|
||||
skip_misc="20000120-2.c mipscop-1.c mipscop-2.c mipscop-3.c mipscop-4.c
|
||||
fp-cmp-4f.c fp-cmp-4l.c fp-cmp-8f.c fp-cmp-8l.c pr38016.c "
|
||||
|
||||
cd "$old_pwd"
|
||||
|
||||
for src in $TESTSUITE_PATH/compile/*.c ; do
|
||||
echo $TCC -o $RUNTIME_DIR/tst.o -c $src
|
||||
if $TCC -o $RUNTIME_DIR/tst.o -c $src 2>&1 | grep 'cannot use local functions' >/dev/null 2>&1
|
||||
then
|
||||
result="SKIP"
|
||||
nb_skipped=$(( $nb_skipped + 1 ))
|
||||
else
|
||||
$TCC -o $RUNTIME_DIR/tst.o -c $src >> tcc.fail 2>&1
|
||||
if [ "$?" = "0" ] ; then
|
||||
result="PASS"
|
||||
nb_ok=$(( $nb_ok + 1 ))
|
||||
else
|
||||
base=`basename "$src"`
|
||||
skip_me="`echo $skip_builtin $skip_ieee $skip_complex $skip_int128 $skip_misc $skip_vector | grep -w $base`"
|
||||
|
||||
if [ -n "$skip_me" ]
|
||||
then
|
||||
result="SKIP"
|
||||
nb_skipped=$(( $nb_skipped + 1 ))
|
||||
else
|
||||
result="FAIL"
|
||||
nb_failed=$(( $nb_failed + 1 ))
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
echo "$result: $src" >> tcc.sum
|
||||
done
|
||||
|
||||
if [ -f "$RUNTIME_DIR/tst.o" ]
|
||||
then
|
||||
rm -f "$RUNTIME_DIR/tst.o"
|
||||
fi
|
||||
|
||||
for src in $TESTSUITE_PATH/execute/*.c $TESTSUITE_PATH/execute/ieee/*.c ; do
|
||||
echo $TCC $src -o $RUNTIME_DIR/tst -lm
|
||||
if $TCC $src -o $RUNTIME_DIR/tst -lm 2>&1 | grep 'cannot use local functions' >/dev/null 2>&1
|
||||
then
|
||||
result="SKIP"
|
||||
nb_skipped=$(( $nb_skipped + 1 ))
|
||||
else
|
||||
$TCC $src -o $RUNTIME_DIR/tst -lm >> tcc.fail 2>&1
|
||||
if [ "$?" = "0" ] ; then
|
||||
if $RUNTIME_DIR/tst >> tcc.fail 2>&1
|
||||
then
|
||||
result="PASS"
|
||||
nb_ok=$(( $nb_ok + 1 ))
|
||||
else
|
||||
result="FAILEXE"
|
||||
nb_exe_failed=$(( $nb_exe_failed + 1 ))
|
||||
fi
|
||||
else
|
||||
base=`basename "$src"`
|
||||
skip_me="`echo $skip_builtin $skip_ieee $skip_complex $skip_int128 $skip_misc $skip_vector | grep -w $base`"
|
||||
|
||||
if [ -n "$skip_me" ]
|
||||
then
|
||||
result="SKIP"
|
||||
nb_skipped=$(( $nb_skipped + 1 ))
|
||||
else
|
||||
result="FAIL"
|
||||
nb_failed=$(( $nb_failed + 1 ))
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
echo "$result: $src" >> tcc.sum
|
||||
done
|
||||
|
||||
if [ -f "$RUNTIME_DIR/tst.o" ]
|
||||
then
|
||||
rm -f "$RUNTIME_DIR/tst.o"
|
||||
fi
|
||||
if [ -f "$RUNTIME_DIR/tst" ]
|
||||
then
|
||||
rm -f "$RUNTIME_DIR/tst"
|
||||
fi
|
||||
|
||||
echo "$nb_ok test(s) ok." >> tcc.sum
|
||||
echo "$nb_ok test(s) ok."
|
||||
echo "$nb_skipped test(s) skipped." >> tcc.sum
|
||||
echo "$nb_skipped test(s) skipped."
|
||||
echo "$nb_failed test(s) failed." >> tcc.sum
|
||||
echo "$nb_failed test(s) failed."
|
||||
echo "$nb_exe_failed test(s) exe failed." >> tcc.sum
|
||||
echo "$nb_exe_failed test(s) exe failed."
|
||||
103
src/userland/cli/third_party/tcc/tests/libtcc_test.c
vendored
Normal file
103
src/userland/cli/third_party/tcc/tests/libtcc_test.c
vendored
Normal file
@@ -0,0 +1,103 @@
|
||||
/*
|
||||
* Simple Test program for libtcc
|
||||
*
|
||||
* libtcc can be useful to use tcc as a "backend" for a code generator.
|
||||
*/
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include "libtcc.h"
|
||||
|
||||
void handle_error(void *opaque, const char *msg)
|
||||
{
|
||||
fprintf(opaque, "%s\n", msg);
|
||||
}
|
||||
|
||||
/* this function is called by the generated code */
|
||||
int add(int a, int b)
|
||||
{
|
||||
return a + b;
|
||||
}
|
||||
|
||||
/* this strinc is referenced by the generated code */
|
||||
const char hello[] = "Hello World!";
|
||||
|
||||
char my_program[] =
|
||||
"#include <tcclib.h>\n" /* include the "Simple libc header for TCC" */
|
||||
"extern int add(int a, int b);\n"
|
||||
"#ifdef _WIN32\n" /* dynamically linked data needs 'dllimport' */
|
||||
" __attribute__((dllimport))\n"
|
||||
"#endif\n"
|
||||
"extern const char hello[];\n"
|
||||
"int fib(int n)\n"
|
||||
"{\n"
|
||||
" if (n <= 2)\n"
|
||||
" return 1;\n"
|
||||
" else\n"
|
||||
" return fib(n-1) + fib(n-2);\n"
|
||||
"}\n"
|
||||
"\n"
|
||||
"int foo(int n)\n"
|
||||
"{\n"
|
||||
" printf(\"%s\\n\", hello);\n"
|
||||
" printf(\"fib(%d) = %d\\n\", n, fib(n));\n"
|
||||
" printf(\"add(%d, %d) = %d\\n\", n, 2 * n, add(n, 2 * n));\n"
|
||||
" return 0;\n"
|
||||
"}\n";
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
TCCState *s;
|
||||
int i;
|
||||
int (*func)(int);
|
||||
|
||||
s = tcc_new();
|
||||
if (!s) {
|
||||
fprintf(stderr, "Could not create tcc state\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
/* set custom error/warning printer */
|
||||
tcc_set_error_func(s, stderr, handle_error);
|
||||
|
||||
/* if tcclib.h and libtcc1.a are not installed, where can we find them */
|
||||
for (i = 1; i < argc; ++i) {
|
||||
char *a = argv[i];
|
||||
if (a[0] == '-') {
|
||||
if (a[1] == 'B')
|
||||
tcc_set_lib_path(s, a+2);
|
||||
else if (a[1] == 'I')
|
||||
tcc_add_include_path(s, a+2);
|
||||
else if (a[1] == 'L')
|
||||
tcc_add_library_path(s, a+2);
|
||||
}
|
||||
}
|
||||
|
||||
/* MUST BE CALLED before any compilation */
|
||||
tcc_set_output_type(s, TCC_OUTPUT_MEMORY);
|
||||
|
||||
if (tcc_compile_string(s, my_program) == -1)
|
||||
return 1;
|
||||
|
||||
/* as a test, we add symbols that the compiled program can use.
|
||||
You may also open a dll with tcc_add_dll() and use symbols from that */
|
||||
tcc_add_symbol(s, "add", add);
|
||||
tcc_add_symbol(s, "hello", hello);
|
||||
|
||||
/* relocate the code */
|
||||
if (tcc_relocate(s) < 0)
|
||||
return 1;
|
||||
|
||||
/* get entry symbol */
|
||||
func = tcc_get_symbol(s, "foo");
|
||||
if (!func)
|
||||
return 1;
|
||||
|
||||
/* run the code */
|
||||
func(32);
|
||||
|
||||
/* delete the state */
|
||||
tcc_delete(s);
|
||||
|
||||
return 0;
|
||||
}
|
||||
363
src/userland/cli/third_party/tcc/tests/libtcc_test_mt.c
vendored
Normal file
363
src/userland/cli/third_party/tcc/tests/libtcc_test_mt.c
vendored
Normal file
@@ -0,0 +1,363 @@
|
||||
/*
|
||||
* Multi-thread Test for libtcc
|
||||
*/
|
||||
|
||||
#ifndef FIB
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <setjmp.h>
|
||||
#include "libtcc.h"
|
||||
|
||||
#define M 20 /* number of states */
|
||||
#define F(n) (n % 20 + 2) /* fib argument */
|
||||
|
||||
#ifdef _WIN32
|
||||
#include <windows.h>
|
||||
#define TF_TYPE(func, param) DWORD WINAPI func(void *param)
|
||||
typedef TF_TYPE(ThreadFunc, x);
|
||||
HANDLE hh[M];
|
||||
void create_thread(ThreadFunc f, int n)
|
||||
{
|
||||
DWORD tid;
|
||||
hh[n] = CreateThread(NULL, 0, f, (void*)(size_t)n, 0, &tid);
|
||||
}
|
||||
void wait_threads(int n)
|
||||
{
|
||||
WaitForMultipleObjects(n, hh, TRUE, INFINITE);
|
||||
while (n)
|
||||
CloseHandle(hh[--n]);
|
||||
}
|
||||
void sleep_ms(unsigned n)
|
||||
{
|
||||
Sleep(n);
|
||||
}
|
||||
#else
|
||||
#include <sys/time.h>
|
||||
#include <unistd.h>
|
||||
#include <pthread.h>
|
||||
#define TF_TYPE(func, param) void* func(void *param)
|
||||
typedef TF_TYPE(ThreadFunc, x);
|
||||
pthread_t hh[M];
|
||||
void create_thread(ThreadFunc f, int n)
|
||||
{
|
||||
pthread_create(&hh[n], NULL, f, (void*)(size_t)n);
|
||||
}
|
||||
void wait_threads(int n)
|
||||
{
|
||||
while (n)
|
||||
pthread_join(hh[--n], NULL);
|
||||
|
||||
}
|
||||
void sleep_ms(unsigned n)
|
||||
{
|
||||
usleep(n * 1000);
|
||||
}
|
||||
#endif
|
||||
|
||||
void handle_error(void *opaque, const char *msg)
|
||||
{
|
||||
fprintf(opaque, "%s\n", msg);
|
||||
}
|
||||
|
||||
/* this function is called by the generated code */
|
||||
int add(int a, int b)
|
||||
{
|
||||
return a + b;
|
||||
}
|
||||
|
||||
#define _str(s) #s
|
||||
#define str(s) _str(s)
|
||||
/* as a trick, prepend #line directive for better error/warning messages */
|
||||
#define PROG(lbl) \
|
||||
char lbl[] = "#line " str(__LINE__) " " str(__FILE__) "\n\n"
|
||||
|
||||
PROG(my_program)
|
||||
"#include <tcclib.h>\n" /* include the "Simple libc header for TCC" */
|
||||
"int add(int a, int b);\n"
|
||||
"int fib(int n)\n"
|
||||
"{\n"
|
||||
" if (n <= 2)\n"
|
||||
" return 1;\n"
|
||||
" else\n"
|
||||
" return add(fib(n-1),fib(n-2));\n"
|
||||
"}\n"
|
||||
"\n"
|
||||
"void bar(void) { *(void**)0 = 0; }\n"
|
||||
"\n"
|
||||
"int foo(int n)\n"
|
||||
"{\n"
|
||||
" printf(\" %d\", fib(n));\n"
|
||||
" if (n >= N_CRASH && n < N_CRASH + 8)\n"
|
||||
" bar();\n"
|
||||
" return 0;\n"
|
||||
"# warning is this the correct file:line...\n"
|
||||
"}\n";
|
||||
|
||||
int g_argc; char **g_argv;
|
||||
|
||||
void parse_args(TCCState *s)
|
||||
{
|
||||
int i;
|
||||
/* if tcclib.h and libtcc1.a are not installed, where can we find them */
|
||||
for (i = 1; i < g_argc; ++i) {
|
||||
char *a = g_argv[i];
|
||||
if (a[0] == '-') {
|
||||
if (a[1] == 'B')
|
||||
tcc_set_lib_path(s, a+2);
|
||||
else if (a[1] == 'I')
|
||||
tcc_add_include_path(s, a+2);
|
||||
else if (a[1] == 'L')
|
||||
tcc_add_library_path(s, a+2);
|
||||
else if (a[1] == 'D')
|
||||
tcc_define_symbol(s, a+2, NULL);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int backtrace_func(
|
||||
void *ud,
|
||||
void *pc,
|
||||
const char *file,
|
||||
int line,
|
||||
const char *func,
|
||||
const char *msg)
|
||||
{
|
||||
#if 0
|
||||
printf("\n *** %p %s %s:%d in '%s'",
|
||||
pc,
|
||||
msg ? "at" : "by",
|
||||
file ? file : "?",
|
||||
line,
|
||||
func ? func : "?");
|
||||
return 1; // want more backtrace levels
|
||||
#else
|
||||
//printf(" [%d]", *(int*)ud);
|
||||
printf("!");
|
||||
return 0; // cancel backtrace
|
||||
#endif
|
||||
}
|
||||
|
||||
TCCState *new_state(int w)
|
||||
{
|
||||
TCCState *s = tcc_new();
|
||||
if (!s) {
|
||||
fprintf(stderr, __FILE__ ": could not create tcc state\n");
|
||||
exit(1);
|
||||
}
|
||||
tcc_set_error_func(s, stdout, handle_error);
|
||||
parse_args(s);
|
||||
if (0 == (w & 1))
|
||||
tcc_set_options(s, "-w");
|
||||
if (w & 2) {
|
||||
tcc_set_options(s, "-bt");
|
||||
tcc_define_symbol(s, "N_CRASH", str(M/2));
|
||||
} else
|
||||
tcc_define_symbol(s, "N_CRASH", "-1000");
|
||||
tcc_set_output_type(s, TCC_OUTPUT_MEMORY);
|
||||
return s;
|
||||
}
|
||||
|
||||
void *reloc_state(TCCState *s, const char *entry)
|
||||
{
|
||||
void *func;
|
||||
tcc_add_symbol(s, "add", add);
|
||||
tcc_add_symbol(s, "printf", printf);
|
||||
if (tcc_relocate(s) < 0) {
|
||||
fprintf(stderr, __FILE__ ": could not relocate tcc state.\n");
|
||||
return NULL;
|
||||
}
|
||||
func = tcc_get_symbol(s, entry);
|
||||
if (!func)
|
||||
fprintf(stderr, __FILE__ ": could not get entry symbol.\n");
|
||||
return func;
|
||||
}
|
||||
|
||||
/* work with several states at the same time */
|
||||
int state_test(int w)
|
||||
{
|
||||
TCCState *s[M];
|
||||
int (*funcs[M])(int);
|
||||
int n;
|
||||
jmp_buf jb;
|
||||
|
||||
for (n = 0; n < M + 4; ++n) {
|
||||
unsigned a = n, b = n - 1, c = n - 2, d = n - 3, e = n - 4;
|
||||
if (a < M)
|
||||
s[a] = new_state(w);
|
||||
if (b < M)
|
||||
if (tcc_compile_string(s[b], my_program) == -1)
|
||||
break;
|
||||
if (c < M)
|
||||
funcs[c] = reloc_state(s[c], "foo");
|
||||
if (d < M && funcs[d]) {
|
||||
tcc_set_backtrace_func(s[d], &d, backtrace_func);
|
||||
if (0 == tcc_setjmp(s[d], jb, funcs[d]))
|
||||
funcs[d](F(d));
|
||||
}
|
||||
if (e < M)
|
||||
tcc_delete(s[e]);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* simple compilation in threads */
|
||||
TF_TYPE(thread_test_simple, vn)
|
||||
{
|
||||
TCCState *s;
|
||||
int (*func)(int);
|
||||
int ret;
|
||||
int n = (size_t)vn;
|
||||
jmp_buf jb;
|
||||
|
||||
s = new_state(0); /* '2' for exceptions */
|
||||
sleep_ms(1);
|
||||
ret = tcc_compile_string(s, my_program);
|
||||
sleep_ms(1);
|
||||
if (ret >= 0) {
|
||||
func = reloc_state(s, "foo");
|
||||
tcc_set_backtrace_func(s, &n, backtrace_func);
|
||||
if (func) {
|
||||
if (0 == tcc_setjmp(s, jb, func))
|
||||
func(F(n));
|
||||
}
|
||||
}
|
||||
tcc_delete(s);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* more complex compilation in threads */
|
||||
TF_TYPE(thread_test_complex, vn)
|
||||
{
|
||||
TCCState *s;
|
||||
int ret;
|
||||
int n = (size_t)vn;
|
||||
char *argv[30], b[10];
|
||||
int argc = 0, i;
|
||||
|
||||
sprintf(b, "%d", F(n));
|
||||
|
||||
for (i = 1; i < g_argc; ++i) argv[argc++] = g_argv[i];
|
||||
#if 0
|
||||
argv[argc++] = "-run";
|
||||
for (i = 1; i < g_argc; ++i) argv[argc++] = g_argv[i];
|
||||
#endif
|
||||
argv[argc++] = "-DFIB";
|
||||
argv[argc++] = "-run";
|
||||
argv[argc++] = __FILE__;
|
||||
argv[argc++] = b;
|
||||
argv[argc] = NULL;
|
||||
|
||||
s = new_state(1);
|
||||
sleep_ms(2);
|
||||
ret = tcc_add_file(s, argv[0]);
|
||||
sleep_ms(3);
|
||||
if (ret == 0)
|
||||
tcc_run(s, argc, argv);
|
||||
tcc_delete(s);
|
||||
fflush(stdout);
|
||||
return 0;
|
||||
}
|
||||
|
||||
void time_tcc(int n, const char *src)
|
||||
{
|
||||
TCCState *s;
|
||||
int ret, i = 0;
|
||||
while (i++ < n) {
|
||||
s = new_state(1);
|
||||
printf(" %d", i), fflush(stdout);
|
||||
ret = tcc_add_file(s, src);
|
||||
tcc_delete(s);
|
||||
if (ret < 0)
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
static unsigned getclock_ms(void)
|
||||
{
|
||||
#ifdef _WIN32
|
||||
return GetTickCount();
|
||||
#else
|
||||
struct timeval tv;
|
||||
gettimeofday(&tv, NULL);
|
||||
return tv.tv_sec*1000 + (tv.tv_usec+500)/1000;
|
||||
#endif
|
||||
}
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
int n;
|
||||
unsigned t;
|
||||
|
||||
g_argc = argc;
|
||||
g_argv = argv;
|
||||
|
||||
if (argc < 2) {
|
||||
fprintf(stderr, "usage: libtcc_test_mt tcc.c <options>\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
#if 1
|
||||
printf("running fib with mixed calls\n "), fflush(stdout);
|
||||
t = getclock_ms();
|
||||
state_test(0);
|
||||
printf("\n (%u ms)\n", getclock_ms() - t);
|
||||
#endif
|
||||
#if 1
|
||||
printf("producing some exceptions (!)\n "), fflush(stdout);
|
||||
t = getclock_ms();
|
||||
state_test(2);
|
||||
printf("\n (%u ms)\n", getclock_ms() - t);
|
||||
#endif
|
||||
#if 1
|
||||
//{ int i; for (i = 0; i < 100; ++i) { printf("(%d) ", i);
|
||||
printf("running fib in threads\n "), fflush(stdout);
|
||||
t = getclock_ms();
|
||||
for (n = 0; n < M; ++n)
|
||||
create_thread(thread_test_simple, n);
|
||||
wait_threads(n);
|
||||
printf("\n (%u ms)\n", getclock_ms() - t);
|
||||
//}}
|
||||
#endif
|
||||
#if 1
|
||||
printf("running tcc.c in threads to run fib\n "), fflush(stdout);
|
||||
t = getclock_ms();
|
||||
for (n = 0; n < M; ++n)
|
||||
create_thread(thread_test_complex, n);
|
||||
wait_threads(n);
|
||||
printf("\n (%u ms)\n", getclock_ms() - t);
|
||||
#endif
|
||||
#if 1
|
||||
printf("compiling tcc.c 10 times\n "), fflush(stdout);
|
||||
t = getclock_ms();
|
||||
time_tcc(10, argv[1]);
|
||||
printf("\n (%u ms)\n", getclock_ms() - t), fflush(stdout);
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
#else
|
||||
#include <tcclib.h>
|
||||
#ifdef _WIN32
|
||||
# ifndef _WIN64
|
||||
__declspec(stdcall)
|
||||
# endif
|
||||
void Sleep(unsigned);
|
||||
# define sleep_ms Sleep
|
||||
#else
|
||||
int usleep(unsigned long);
|
||||
# define sleep_ms(x) usleep((x)*1000);
|
||||
#endif
|
||||
|
||||
int fib(n)
|
||||
{
|
||||
return (n <= 2) ? 1 : fib(n-1) + fib(n-2);
|
||||
}
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
sleep_ms(333);
|
||||
printf(" %d", fib(atoi(argv[1])));
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
164
src/userland/cli/third_party/tcc/tests/msvcrt_start.c
vendored
Normal file
164
src/userland/cli/third_party/tcc/tests/msvcrt_start.c
vendored
Normal file
@@ -0,0 +1,164 @@
|
||||
/* ------------------------------------------------------------- */
|
||||
/* minimal startup with runtime linker to msvcrt */
|
||||
|
||||
#if 0
|
||||
|
||||
#define REDIR_ALL \
|
||||
REDIR(__set_app_type)\
|
||||
REDIR(__getmainargs)\
|
||||
REDIR(_controlfp)\
|
||||
REDIR(_vsnprintf)\
|
||||
REDIR(exit)\
|
||||
\
|
||||
REDIR(puts)\
|
||||
REDIR(printf)\
|
||||
REDIR(putchar)\
|
||||
REDIR(strtod)\
|
||||
REDIR(memset)\
|
||||
REDIR(strcpy)\
|
||||
REDIR(strlen)\
|
||||
REDIR(malloc)\
|
||||
REDIR(free)\
|
||||
|
||||
#if defined __i386__ && !defined __TINYC__
|
||||
# define __leading_underscore 1
|
||||
#endif
|
||||
|
||||
#ifdef __leading_underscore
|
||||
# define _(s) "_"#s
|
||||
#else
|
||||
# define _(s) #s
|
||||
#endif
|
||||
|
||||
#define REDIR(s) void *s;
|
||||
static struct { REDIR_ALL } all_ptrs;
|
||||
#undef REDIR
|
||||
|
||||
#define REDIR(s) #s"\0"
|
||||
static const char all_names[] = REDIR_ALL;
|
||||
#undef REDIR
|
||||
|
||||
#if __aarch64__
|
||||
#if defined __TINYC__
|
||||
# define ALIGN ".align 8"
|
||||
#else
|
||||
# define ALIGN ".align 3" /* .align is power of 2 on non-ELF platforms */
|
||||
#endif
|
||||
# define REDIR(s) \
|
||||
__asm__("\n"_(s)":"); \
|
||||
__asm__(".int 0x58000090"); /* ldr x16, [pc, #16] */ \
|
||||
__asm__(".int 0xf9400210"); /* ldr x16, [x16] */ \
|
||||
__asm__(".int 0xd61f0200"); /* br x16 */ \
|
||||
__asm__(".int 0xd503201f"); /* nop for alignment */ \
|
||||
__asm__(".quad all_ptrs + (. - all_jmps - 16) / 24 * 8"); \
|
||||
__asm__(".global "_(s));
|
||||
|
||||
__asm__("\t.text\n\t"ALIGN"\nall_jmps:");
|
||||
REDIR_ALL
|
||||
#else
|
||||
# define REDIR(s) \
|
||||
__asm__("\n"_(s)":");\
|
||||
__asm__("jmp *%0"::"m"(all_ptrs.s));\
|
||||
__asm__(".global "_(s));
|
||||
|
||||
static void all_jmps() { REDIR_ALL }
|
||||
#endif
|
||||
#undef REDIR
|
||||
|
||||
#if 0
|
||||
# include <windows.h>
|
||||
#else
|
||||
# if __i386__
|
||||
# define STDCALL __declspec(stdcall)
|
||||
# else
|
||||
# define STDCALL
|
||||
# endif
|
||||
# define DWORD long unsigned
|
||||
# define HMODULE void*
|
||||
# define HANDLE void*
|
||||
S TDCALL HMODULE LoadLibraryA(const char *);
|
||||
S TDCALL HMODULE GetProcAddress(HMODULE , char*);
|
||||
S TDCALL void ExitProcess(int);
|
||||
S TDCALL int WriteFile(HANDLE, const void*, DWORD, DWORD*, void*);
|
||||
S TDCALL HANDLE GetStdHandle(DWORD);
|
||||
S TDCALL int FlushFileBuffers(HANDLE);
|
||||
# define STD_ERROR_HANDLE -12
|
||||
#endif
|
||||
|
||||
static void eput(const char *s)
|
||||
{
|
||||
DWORD n_out;
|
||||
int n = 0;
|
||||
while (s[n])
|
||||
++n;
|
||||
WriteFile(GetStdHandle(STD_ERROR_HANDLE), s, n, &n_out, 0);
|
||||
}
|
||||
|
||||
static void rt_reloc()
|
||||
{
|
||||
const char *s = all_names;
|
||||
void **p = (void**)&all_ptrs;
|
||||
void *dll = LoadLibraryA("msvcrt.dll");
|
||||
do {
|
||||
char buf[100], *d = buf;
|
||||
*p = (void*)GetProcAddress(dll, (char*)s);
|
||||
*d++ = '_'; do *d++ = *s; while (*s++);
|
||||
if (0 == *p)
|
||||
*p = (void*)GetProcAddress(dll, buf);
|
||||
if (0 == *p) {
|
||||
eput("MSVCRT_START.C: RUNTIME RELOCATION ERROR: '");
|
||||
eput(buf+1);
|
||||
eput("'\n");
|
||||
ExitProcess(-1);
|
||||
}
|
||||
++p;
|
||||
} while (*s);
|
||||
}
|
||||
|
||||
#else
|
||||
# define rt_reloc()
|
||||
#endif
|
||||
|
||||
int main(int argc, char **argv, char **env);
|
||||
void exit(int);
|
||||
void __set_app_type(int apptype);
|
||||
|
||||
typedef struct { int newmode; } _startupinfo;
|
||||
int __getmainargs(int *pargc, char ***pargv, char ***penv, int globb, _startupinfo*);
|
||||
|
||||
void _controlfp(unsigned a, unsigned b);
|
||||
#define _MCW_PC 0x00030000 // Precision Control
|
||||
#define _PC_53 0x00010000 // 53 bits
|
||||
|
||||
int __argc;
|
||||
char **__argv;
|
||||
char **environ;
|
||||
_startupinfo start_info = {0};
|
||||
|
||||
void mainCRTStartup(void)
|
||||
{
|
||||
rt_reloc();
|
||||
#if defined __i386__ || defined __x86_64__
|
||||
_controlfp(_PC_53, _MCW_PC);
|
||||
#endif
|
||||
__set_app_type(1);
|
||||
__getmainargs(&__argc, &__argv, &environ, 0, &start_info);
|
||||
exit(main(__argc, __argv, environ));
|
||||
}
|
||||
|
||||
#include <stdarg.h>
|
||||
#define size_t __SIZE_TYPE__
|
||||
int printf(const char *, ...);
|
||||
int _vsnprintf(char *, size_t, const char *, va_list);
|
||||
|
||||
/* undefined on windows-11-arm64 */
|
||||
int vprintf(const char *format, va_list ap)
|
||||
{
|
||||
char buf[1000];
|
||||
_vsnprintf(buf, sizeof buf, format, ap);
|
||||
return printf("%s", buf);
|
||||
}
|
||||
|
||||
void __main() {} /* for gcc */
|
||||
void _pei386_runtime_relocator(void) {} /* for gcc */
|
||||
void __chkstk(unsigned n) {} /* for clang */
|
||||
6
src/userland/cli/third_party/tcc/tests/pp/01.c
vendored
Normal file
6
src/userland/cli/third_party/tcc/tests/pp/01.c
vendored
Normal file
@@ -0,0 +1,6 @@
|
||||
#define hash_hash # ## #
|
||||
#define mkstr(a) # a
|
||||
#define in_between(a) mkstr(a)
|
||||
#define join(c, d) in_between(c hash_hash d)
|
||||
char p[] = join(x, y);
|
||||
// char p[] = "x ## y";
|
||||
1
src/userland/cli/third_party/tcc/tests/pp/01.expect
vendored
Normal file
1
src/userland/cli/third_party/tcc/tests/pp/01.expect
vendored
Normal file
@@ -0,0 +1 @@
|
||||
char p[] = "x ## y";
|
||||
28
src/userland/cli/third_party/tcc/tests/pp/02.c
vendored
Normal file
28
src/userland/cli/third_party/tcc/tests/pp/02.c
vendored
Normal file
@@ -0,0 +1,28 @@
|
||||
#define x 3
|
||||
#define f(a) f(x * (a))
|
||||
#undef x
|
||||
#define x 2
|
||||
#define g f
|
||||
#define z z[0]
|
||||
#define h g(~
|
||||
#define m(a) a(w)
|
||||
#define w 0,1
|
||||
#define t(a) a
|
||||
#define p() int
|
||||
#define q(x) x
|
||||
#define r(x,y) x ## y
|
||||
#define str(x) # x
|
||||
f(y+1) + f(f(z)) % t(t(g)(0) + t)(1);
|
||||
g(x+(3,4)-w) | h 5) & m
|
||||
(f)^m(m);
|
||||
char c[2][6] = { str(hello), str() };
|
||||
/*
|
||||
* f(2 * (y+1)) + f(2 * (f(2 * (z[0])))) % f(2 * (0)) + t(1);
|
||||
* f(2 * (2+(3,4)-0,1)) | f(2 * (~ 5)) & f(2 * (0,1))^m(0,1);
|
||||
* char c[2][6] = { "hello", "" };
|
||||
*/
|
||||
#define L21 f(y+1) + f(f(z)) % t(t(g)(0) + t)(1);
|
||||
#define L22 g(x+(3,4)-w) | h 5) & m\
|
||||
(f)^m(m);
|
||||
L21
|
||||
L22
|
||||
5
src/userland/cli/third_party/tcc/tests/pp/02.expect
vendored
Normal file
5
src/userland/cli/third_party/tcc/tests/pp/02.expect
vendored
Normal file
@@ -0,0 +1,5 @@
|
||||
f(2 * (y+1)) + f(2 * (f(2 * (z[0])))) % f(2 * (0)) + t(1);
|
||||
f(2 * (2 +(3,4)-0,1)) | f(2 * (~ 5)) & f(2 * (0,1))^m(0,1);
|
||||
char c[2][6] = { "hello", "" };
|
||||
f(2 * (y+1)) + f(2 * (f(2 * (z[0])))) % f(2 * (0)) + t(1);
|
||||
f(2 * (2 +(3,4)-0,1)) | f(2 * (~ 5)) & f(2 * (0,1))^m(0,1);
|
||||
15
src/userland/cli/third_party/tcc/tests/pp/03.c
vendored
Normal file
15
src/userland/cli/third_party/tcc/tests/pp/03.c
vendored
Normal file
@@ -0,0 +1,15 @@
|
||||
#define str(s) # s
|
||||
#define xstr(s) str(s)
|
||||
#define debug(s, t) printf("x" # s "= %d, x" # t "= %s", \
|
||||
x ## s, x ## t)
|
||||
#define INCFILE(n) vers ## n
|
||||
#define glue(a, b) a ## b
|
||||
#define xglue(a, b) glue(a, b)
|
||||
#define HIGHLOW "hello"
|
||||
#define LOW LOW ", world"
|
||||
debug(1, 2);
|
||||
fputs(str(strncmp("abc\0d", "abc", '\4') // this goes away
|
||||
== 0) str(: @\n), s);
|
||||
\#include xstr(INCFILE(2).h)
|
||||
glue(HIGH, LOW);
|
||||
xglue(HIGH, LOW)
|
||||
5
src/userland/cli/third_party/tcc/tests/pp/03.expect
vendored
Normal file
5
src/userland/cli/third_party/tcc/tests/pp/03.expect
vendored
Normal file
@@ -0,0 +1,5 @@
|
||||
printf("x" "1" "= %d, x" "2" "= %s", x1, x2);
|
||||
fputs("strncmp(\"abc\\0d\", \"abc\", '\\4') == 0" ": @\n", s);
|
||||
\#include "vers2.h"
|
||||
"hello";
|
||||
"hello" ", world"
|
||||
4
src/userland/cli/third_party/tcc/tests/pp/04.c
vendored
Normal file
4
src/userland/cli/third_party/tcc/tests/pp/04.c
vendored
Normal file
@@ -0,0 +1,4 @@
|
||||
#define foobar 1
|
||||
#define C(x,y) x##y
|
||||
#define D(x) (C(x,bar))
|
||||
D(foo)
|
||||
1
src/userland/cli/third_party/tcc/tests/pp/04.expect
vendored
Normal file
1
src/userland/cli/third_party/tcc/tests/pp/04.expect
vendored
Normal file
@@ -0,0 +1 @@
|
||||
(1)
|
||||
7
src/userland/cli/third_party/tcc/tests/pp/05.c
vendored
Normal file
7
src/userland/cli/third_party/tcc/tests/pp/05.c
vendored
Normal file
@@ -0,0 +1,7 @@
|
||||
#define t(x,y,z) x ## y ## z
|
||||
#define xxx(s) int s[] = { t(1,2,3), t(,4,5), t(6,,7), t(8,9,), \
|
||||
t(10,,), t(,11,), t(,,12), t(,,) };
|
||||
|
||||
int j[] = { t(1,2,3), t(,4,5), t(6,,7), t(8,9,),
|
||||
t(10,,), t(,11,), t(,,12), t(,,) };
|
||||
xxx(j)
|
||||
3
src/userland/cli/third_party/tcc/tests/pp/05.expect
vendored
Normal file
3
src/userland/cli/third_party/tcc/tests/pp/05.expect
vendored
Normal file
@@ -0,0 +1,3 @@
|
||||
int j[] = { 123, 45, 67, 89,
|
||||
10, 11, 12, };
|
||||
int j[] = { 123, 45, 67, 89, 10, 11, 12, };
|
||||
5
src/userland/cli/third_party/tcc/tests/pp/06.c
vendored
Normal file
5
src/userland/cli/third_party/tcc/tests/pp/06.c
vendored
Normal file
@@ -0,0 +1,5 @@
|
||||
#define X(a,b, \
|
||||
c,d) \
|
||||
foo
|
||||
|
||||
X(1,2,3,4)
|
||||
1
src/userland/cli/third_party/tcc/tests/pp/06.expect
vendored
Normal file
1
src/userland/cli/third_party/tcc/tests/pp/06.expect
vendored
Normal file
@@ -0,0 +1 @@
|
||||
foo
|
||||
4
src/userland/cli/third_party/tcc/tests/pp/07.c
vendored
Normal file
4
src/userland/cli/third_party/tcc/tests/pp/07.c
vendored
Normal file
@@ -0,0 +1,4 @@
|
||||
#define a() YES
|
||||
#define b() a
|
||||
b()
|
||||
b()()
|
||||
2
src/userland/cli/third_party/tcc/tests/pp/07.expect
vendored
Normal file
2
src/userland/cli/third_party/tcc/tests/pp/07.expect
vendored
Normal file
@@ -0,0 +1,2 @@
|
||||
a
|
||||
YES
|
||||
4
src/userland/cli/third_party/tcc/tests/pp/08.c
vendored
Normal file
4
src/userland/cli/third_party/tcc/tests/pp/08.c
vendored
Normal file
@@ -0,0 +1,4 @@
|
||||
// test macro expansion in arguments
|
||||
#define s_pos s_s.s_pos
|
||||
#define foo(x) (x)
|
||||
foo(hej.s_pos)
|
||||
1
src/userland/cli/third_party/tcc/tests/pp/08.expect
vendored
Normal file
1
src/userland/cli/third_party/tcc/tests/pp/08.expect
vendored
Normal file
@@ -0,0 +1 @@
|
||||
(hej.s_s.s_pos)
|
||||
4
src/userland/cli/third_party/tcc/tests/pp/09.c
vendored
Normal file
4
src/userland/cli/third_party/tcc/tests/pp/09.c
vendored
Normal file
@@ -0,0 +1,4 @@
|
||||
#define C(a,b,c) a##b##c
|
||||
#define N(x,y) C(x,_,y)
|
||||
#define A_O aaaaoooo
|
||||
N(A,O)
|
||||
1
src/userland/cli/third_party/tcc/tests/pp/09.expect
vendored
Normal file
1
src/userland/cli/third_party/tcc/tests/pp/09.expect
vendored
Normal file
@@ -0,0 +1 @@
|
||||
aaaaoooo
|
||||
10
src/userland/cli/third_party/tcc/tests/pp/10.c
vendored
Normal file
10
src/userland/cli/third_party/tcc/tests/pp/10.c
vendored
Normal file
@@ -0,0 +1,10 @@
|
||||
#define f(x) x
|
||||
#define g(x) f(x) f(x
|
||||
#define i(x) g(x)) g(x
|
||||
#define h(x) i(x))) i(x
|
||||
#define k(x) i(x))) i(x))))
|
||||
f(x)
|
||||
g(x))
|
||||
i(x)))
|
||||
h(x))))
|
||||
k(x))))
|
||||
5
src/userland/cli/third_party/tcc/tests/pp/10.expect
vendored
Normal file
5
src/userland/cli/third_party/tcc/tests/pp/10.expect
vendored
Normal file
@@ -0,0 +1,5 @@
|
||||
x
|
||||
x x
|
||||
x x x x
|
||||
x x x x x x x x
|
||||
x x x x x x x x))))
|
||||
36
src/userland/cli/third_party/tcc/tests/pp/11.c
vendored
Normal file
36
src/userland/cli/third_party/tcc/tests/pp/11.c
vendored
Normal file
@@ -0,0 +1,36 @@
|
||||
#define D1(s, ...) s
|
||||
#define D2(s, ...) s D1(__VA_ARGS__)
|
||||
#define D3(s, ...) s D2(__VA_ARGS__)
|
||||
#define D4(s, ...) s D3(__VA_ARGS__)
|
||||
|
||||
D1(a)
|
||||
D2(a, b)
|
||||
D3(a, b, c)
|
||||
D4(a, b, c, d)
|
||||
|
||||
x D4(a, b, c, d) y
|
||||
x D4(a, b, c) y
|
||||
x D4(a, b) y
|
||||
x D4(a) y
|
||||
x D4() y
|
||||
|
||||
#define GNU_COMMA(X,Y...) X,##Y
|
||||
|
||||
x GNU_COMMA(A,B,C) y
|
||||
x GNU_COMMA(A,B) y
|
||||
x GNU_COMMA(A) y
|
||||
x GNU_COMMA() y
|
||||
|
||||
#define __sun_attr___noreturn__ __attribute__((__noreturn__))
|
||||
#define ___sun_attr_inner(__a) __sun_attr_##__a
|
||||
#define __sun_attr__(__a) ___sun_attr_inner __a
|
||||
#define __NORETURN __sun_attr__((__noreturn__))
|
||||
__NORETURN
|
||||
#define X(...)
|
||||
#define Y(...) 1 __VA_ARGS__ 2
|
||||
Y(X X() ())
|
||||
|
||||
#define DDD(A, B) D_ ## B ## _D_ ## A
|
||||
#define CCC(X, ...) DDD(X,## __VA_ARGS__)
|
||||
/* must be D_B_D_A (not D_B _D_A) */
|
||||
CCC(A,B)
|
||||
16
src/userland/cli/third_party/tcc/tests/pp/11.expect
vendored
Normal file
16
src/userland/cli/third_party/tcc/tests/pp/11.expect
vendored
Normal file
@@ -0,0 +1,16 @@
|
||||
a
|
||||
a b
|
||||
a b c
|
||||
a b c d
|
||||
x a b c d y
|
||||
x a b c y
|
||||
x a b y
|
||||
x a y
|
||||
x y
|
||||
x A,B,C y
|
||||
x A,B y
|
||||
x A y
|
||||
x y
|
||||
__attribute__((__noreturn__))
|
||||
1 2
|
||||
D_B_D_A
|
||||
8
src/userland/cli/third_party/tcc/tests/pp/12.S
vendored
Normal file
8
src/userland/cli/third_party/tcc/tests/pp/12.S
vendored
Normal file
@@ -0,0 +1,8 @@
|
||||
#define SRC(y...) \
|
||||
9999: y; \
|
||||
.section __ex_table, "a"; \
|
||||
.long 9999b, 6001f ; \
|
||||
// .previous
|
||||
|
||||
SRC(1: movw (%esi), %bx)
|
||||
6001:
|
||||
2
src/userland/cli/third_party/tcc/tests/pp/12.expect
vendored
Normal file
2
src/userland/cli/third_party/tcc/tests/pp/12.expect
vendored
Normal file
@@ -0,0 +1,2 @@
|
||||
9999: 1: movw (%esi), %bx; .section __ex_table, "a"; .long 9999b, 6001f ;
|
||||
6001:
|
||||
6
src/userland/cli/third_party/tcc/tests/pp/13.S
vendored
Normal file
6
src/userland/cli/third_party/tcc/tests/pp/13.S
vendored
Normal file
@@ -0,0 +1,6 @@
|
||||
# `modelist' label. Each video mode record looks like:
|
||||
#ifdef AAA
|
||||
# modelist' label. Each video mode record looks like:
|
||||
#endif
|
||||
.text
|
||||
endtext:
|
||||
2
src/userland/cli/third_party/tcc/tests/pp/13.expect
vendored
Normal file
2
src/userland/cli/third_party/tcc/tests/pp/13.expect
vendored
Normal file
@@ -0,0 +1,2 @@
|
||||
.text
|
||||
endtext:
|
||||
13
src/userland/cli/third_party/tcc/tests/pp/14.c
vendored
Normal file
13
src/userland/cli/third_party/tcc/tests/pp/14.c
vendored
Normal file
@@ -0,0 +1,13 @@
|
||||
#define W Z
|
||||
#define Z(X) W(X,2)
|
||||
#define Y(X) Z(X)
|
||||
#define X Y
|
||||
return X(X(1));
|
||||
|
||||
#define P Q
|
||||
#define Q(n) P(n,2)
|
||||
return P(1);
|
||||
|
||||
#define A (B * B)
|
||||
#define B (A + A)
|
||||
return A + B;
|
||||
3
src/userland/cli/third_party/tcc/tests/pp/14.expect
vendored
Normal file
3
src/userland/cli/third_party/tcc/tests/pp/14.expect
vendored
Normal file
@@ -0,0 +1,3 @@
|
||||
return Z(Z(1,2),2);
|
||||
return Q(1,2);
|
||||
return ((A + A) * (A + A)) + ((B * B) + (B * B));
|
||||
18
src/userland/cli/third_party/tcc/tests/pp/15.c
vendored
Normal file
18
src/userland/cli/third_party/tcc/tests/pp/15.c
vendored
Normal file
@@ -0,0 +1,18 @@
|
||||
// insert a space between two tokens if otherwise they
|
||||
// would form a single token when read back
|
||||
|
||||
#define n(x) x
|
||||
|
||||
return (n(long)n(double))d;
|
||||
return n(A)n(++)n(+)n(B);
|
||||
return n(A)n(+)n(++)n(B);
|
||||
return n(A)n(++)n(+)n(+)n(B);
|
||||
|
||||
// not a hex float
|
||||
return n(0x1E)n(-1);
|
||||
|
||||
// unlike gcc but correct
|
||||
// XXX: return n(x)+n(x)-n(1)+n(1)-2;
|
||||
|
||||
// unlike gcc, but cannot appear in valid C
|
||||
// XXX: return n(x)n(x)n(1)n(2)n(x);
|
||||
5
src/userland/cli/third_party/tcc/tests/pp/15.expect
vendored
Normal file
5
src/userland/cli/third_party/tcc/tests/pp/15.expect
vendored
Normal file
@@ -0,0 +1,5 @@
|
||||
return (long double)d;
|
||||
return A+++B;
|
||||
return A+ ++B;
|
||||
return A+++ +B;
|
||||
return 0x1E -1;
|
||||
3
src/userland/cli/third_party/tcc/tests/pp/16.c
vendored
Normal file
3
src/userland/cli/third_party/tcc/tests/pp/16.c
vendored
Normal file
@@ -0,0 +1,3 @@
|
||||
/* The following should warn */
|
||||
#define A ...
|
||||
#define A <<=
|
||||
2
src/userland/cli/third_party/tcc/tests/pp/16.expect
vendored
Normal file
2
src/userland/cli/third_party/tcc/tests/pp/16.expect
vendored
Normal file
@@ -0,0 +1,2 @@
|
||||
|
||||
16.c:3: warning: A redefined
|
||||
14
src/userland/cli/third_party/tcc/tests/pp/17.c
vendored
Normal file
14
src/userland/cli/third_party/tcc/tests/pp/17.c
vendored
Normal file
@@ -0,0 +1,14 @@
|
||||
#define STR1(u) # u
|
||||
#define pass(a) a
|
||||
#define __ASM_REG(reg) STR1(one##reg)
|
||||
#define _ASM_DX __ASM_REG(tok)
|
||||
X162 pass(__ASM_REG(tok))
|
||||
X161 pass(_ASM_DX)
|
||||
X163 pass(STR1(one##tok))
|
||||
|
||||
X170 pass(x ## y)
|
||||
X171 pass(x pass(##) y)
|
||||
|
||||
#define Y(x) Z(x)
|
||||
#define X Y
|
||||
X180 return X(X(1));
|
||||
6
src/userland/cli/third_party/tcc/tests/pp/17.expect
vendored
Normal file
6
src/userland/cli/third_party/tcc/tests/pp/17.expect
vendored
Normal file
@@ -0,0 +1,6 @@
|
||||
X162 "onetok"
|
||||
X161 "onetok"
|
||||
X163 "one##tok"
|
||||
X170 x ## y
|
||||
X171 x ## y
|
||||
X180 return Z(Z(1));
|
||||
30
src/userland/cli/third_party/tcc/tests/pp/18.c
vendored
Normal file
30
src/userland/cli/third_party/tcc/tests/pp/18.c
vendored
Normal file
@@ -0,0 +1,30 @@
|
||||
#define M_RETI_ARG27(x,y,z,aa, ...) aa
|
||||
#define M_RET_ARG27(...) M_RETI_ARG27(__VA_ARGS__)
|
||||
#define M_COMMA_P(...) M_RET_ARG27(__VA_ARGS__, 1, 1, 0, useless)
|
||||
#define M_EMPTYI_DETECT(...) 0, 1,
|
||||
#define M_EMPTYI_P_C1(...) M_COMMA_P(M_EMPTYI_DETECT __VA_ARGS__ () )
|
||||
#define EX
|
||||
#define empty(x)
|
||||
#define fnlike(x) yeah x
|
||||
/* If the following macro is called with empty arg (X183), the use
|
||||
of 'x' between fnlike and '(' doesn't hinder the recognition of this
|
||||
being a further fnlike macro invocation. */
|
||||
#define usefnlike(x) fnlike x (x)
|
||||
X181 M_EMPTYI_P_C1()
|
||||
X182 M_EMPTYI_P_C1(x)
|
||||
X183 usefnlike()
|
||||
|
||||
#define ABC(x) ABC : x
|
||||
#define A(a,b,c) a ## b ## c
|
||||
#define B(a,b,c) A(a,b,c)
|
||||
#define C(a,b,c) a b c
|
||||
B(
|
||||
C(A,C(,,),),
|
||||
C(B(,,),B,B(,,)),
|
||||
C(B(,,),B(,,),C)
|
||||
)/* */(a b c)
|
||||
|
||||
#define TEST(x) TEST : x
|
||||
#define K(a,b) a ## b
|
||||
#define L(a,b) K( TE a , b ST )
|
||||
L(,)(t e s t)
|
||||
5
src/userland/cli/third_party/tcc/tests/pp/18.expect
vendored
Normal file
5
src/userland/cli/third_party/tcc/tests/pp/18.expect
vendored
Normal file
@@ -0,0 +1,5 @@
|
||||
X181 1
|
||||
X182 0
|
||||
X183 yeah
|
||||
ABC : a b c
|
||||
TEST : t e s t
|
||||
101
src/userland/cli/third_party/tcc/tests/pp/19.c
vendored
Normal file
101
src/userland/cli/third_party/tcc/tests/pp/19.c
vendored
Normal file
@@ -0,0 +1,101 @@
|
||||
#define M_C2I(a, ...) a ## __VA_ARGS__
|
||||
#define M_C(a, ...) M_C2I(a, __VA_ARGS__)
|
||||
#define M_C3I(a, b, ...) a ## b ## __VA_ARGS__
|
||||
#define M_C3(a, b, ...) M_C3I(a ,b, __VA_ARGS__)
|
||||
|
||||
#define M_RETI_ARG2(a, b, ...) b
|
||||
#define M_RET_ARG2(...) M_RETI_ARG2(__VA_ARGS__)
|
||||
#define M_RETI_ARG27(a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z,aa, ...) aa
|
||||
#define M_RET_ARG27(...) M_RETI_ARG27(__VA_ARGS__)
|
||||
|
||||
#define M_TOBOOLI_0 1, 0,
|
||||
#define M_BOOL(x) M_RET_ARG2(M_C(M_TOBOOLI_, x), 1, useless)
|
||||
|
||||
#define M_IFI_0(true_macro, ...) __VA_ARGS__
|
||||
#define M_IFI_1(true_macro, ...) true_macro
|
||||
#define M_IF(c) M_C(M_IFI_, M_BOOL(c))
|
||||
|
||||
#define M_FLAT(...) __VA_ARGS__
|
||||
#define M_INVI_0 1
|
||||
#define M_INVI_1 0
|
||||
#define M_INV(x) M_C(M_INVI_, x)
|
||||
|
||||
#define M_ANDI_00 0
|
||||
#define M_ANDI_01 0
|
||||
#define M_ANDI_10 0
|
||||
#define M_ANDI_11 1
|
||||
#define M_AND(x,y) M_C3(M_ANDI_, x, y)
|
||||
|
||||
#define M_ORI_00 0
|
||||
#define M_ORI_01 1
|
||||
#define M_ORI_10 1
|
||||
#define M_ORI_11 1
|
||||
#define M_OR(x,y) M_C3(M_ORI_, x, y)
|
||||
|
||||
#define M_COMMA_P(...) M_RET_ARG27(__VA_ARGS__, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, useless)
|
||||
|
||||
#define M_EMPTYI_DETECT(...) 0, 1,
|
||||
#define M_EMPTYI_P_C1(...) M_COMMA_P(M_EMPTYI_DETECT __VA_ARGS__ ())
|
||||
#define M_EMPTYI_P_C2(...) M_COMMA_P(M_EMPTYI_DETECT __VA_ARGS__)
|
||||
#define M_EMPTYI_P_C3(...) M_COMMA_P(__VA_ARGS__ () )
|
||||
#define M_EMPTY_P(...) M_AND(M_EMPTYI_P_C1(__VA_ARGS__), M_INV(M_OR(M_OR(M_EMPTYI_P_C2(__VA_ARGS__), M_COMMA_P(__VA_ARGS__)),M_EMPTYI_P_C3(__VA_ARGS__))))
|
||||
#define M_APPLY_FUNC2B(func, arg1, arg2) \
|
||||
M_IF(M_EMPTY_P(arg2))(,func(arg1, arg2))
|
||||
#define M_MAP2B_0(func, data, a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x, y, z,...) \
|
||||
M_APPLY_FUNC2B(func, data, a) M_APPLY_FUNC2B(func, data, b) M_APPLY_FUNC2B(func, data, c) \
|
||||
M_APPLY_FUNC2B(func, data, d) M_APPLY_FUNC2B(func, data, e) M_APPLY_FUNC2B(func, data, f) \
|
||||
M_APPLY_FUNC2B(func, data, g) M_APPLY_FUNC2B(func, data, h) M_APPLY_FUNC2B(func, data, i) \
|
||||
M_APPLY_FUNC2B(func, data, j) M_APPLY_FUNC2B(func, data, k) M_APPLY_FUNC2B(func, data, l) \
|
||||
M_APPLY_FUNC2B(func, data, m) M_APPLY_FUNC2B(func, data, n) M_APPLY_FUNC2B(func, data, o) \
|
||||
M_APPLY_FUNC2B(func, data, p) M_APPLY_FUNC2B(func, data, q) M_APPLY_FUNC2B(func, data, r) \
|
||||
M_APPLY_FUNC2B(func, data, s) M_APPLY_FUNC2B(func, data, t) M_APPLY_FUNC2B(func, data, u) \
|
||||
M_APPLY_FUNC2B(func, data, v) M_APPLY_FUNC2B(func, data, w) M_APPLY_FUNC2B(func, data, x) \
|
||||
M_APPLY_FUNC2B(func, data, y) M_APPLY_FUNC2B(func, data, z)
|
||||
#define M_MAP2B(f, ...) M_MAP2B_0(f, __VA_ARGS__, , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , )
|
||||
#define M_INIT_INIT(a) ,a,
|
||||
|
||||
#define M_GET_METHOD(method, method_default, ...) \
|
||||
M_RET_ARG2 (M_MAP2B(M_C, M_C3(M_, method, _), __VA_ARGS__), method_default,)
|
||||
|
||||
#define M_TEST_METHOD_P(method, oplist) \
|
||||
M_BOOL(M_GET_METHOD (method, 0, M_FLAT oplist))
|
||||
|
||||
#define TRUE 1
|
||||
#define TEST1(n) \
|
||||
M_IF(n)(ok,nok)
|
||||
#define TEST2(op) \
|
||||
M_TEST_METHOD_P(INIT, op)
|
||||
#define TEST3(op) \
|
||||
M_IF(M_TEST_METHOD_P(INIT, op))(ok, nok)
|
||||
#define TEST4(op) \
|
||||
TEST1(TEST2(op))
|
||||
#define KO(a) ((void)1)
|
||||
|
||||
/* This checks that the various expansions that ultimately lead to
|
||||
something like 'KO(arg,arg)', where 'KO' comes from a macro
|
||||
expansion reducing from a large macro chain do not are regarded
|
||||
as funclike macro invocation of KO. E.g. X93 and X94 expand to 'KO',
|
||||
but X95 must not consume the (a,b) arguments outside the M_IF()
|
||||
invocation to reduce the 'KO' macro to an invocation. Instead
|
||||
X95 should reduce via M_IF(KO)(a,b) to 'a'.
|
||||
|
||||
The other lines here are variations on this scheme, with X1 to
|
||||
X6 coming from the bug report at
|
||||
http://lists.nongnu.org/archive/html/tinycc-devel/2017-07/msg00017.html */
|
||||
X92 M_IF(KO)
|
||||
X93 M_GET_METHOD(INIT, 0, INIT(KO))
|
||||
X94 M_GET_METHOD(INIT, 0, M_FLAT (INIT(KO)))
|
||||
X95 M_IF(M_GET_METHOD(INIT, 0, INIT(KO)))(a,b)
|
||||
X96 M_IF(M_GET_METHOD(INIT, 0, M_FLAT (INIT(KO))))
|
||||
X97 M_IF(M_GET_METHOD(INIT, 0, M_FLAT (INIT(KO))))(ok,nok)
|
||||
X98 (M_TEST_METHOD_P(INIT, (INIT(KO))))(ok, nok)
|
||||
X99 M_IF(M_TEST_METHOD_P(INIT, (INIT(KO))))(ok, nok)
|
||||
// test begins
|
||||
X1 TEST1(TRUE) // ==> expect ok, get ok
|
||||
// First test with a token which is not a macro
|
||||
X2 TEST2((INIT(ok))) // ==> expect 1, get 1
|
||||
X3 TEST3((INIT(ok))) // ==> expect ok, get ok
|
||||
// Then test with a token which is a macro, but should not be expanded.
|
||||
X4 TEST2((INIT(KO))) // ==> expect 1, get 1
|
||||
X5 TEST4(INIT(KO))
|
||||
X6 TEST3((INIT(KO))) // ==> expect ok, get "error: macro 'KO' used with too many args"
|
||||
14
src/userland/cli/third_party/tcc/tests/pp/19.expect
vendored
Normal file
14
src/userland/cli/third_party/tcc/tests/pp/19.expect
vendored
Normal file
@@ -0,0 +1,14 @@
|
||||
X92 M_IFI_1
|
||||
X93 KO
|
||||
X94 KO
|
||||
X95 a
|
||||
X96 M_IFI_1
|
||||
X97 ok
|
||||
X98 (1)(ok, nok)
|
||||
X99 ok
|
||||
X1 ok
|
||||
X2 1
|
||||
X3 ok
|
||||
X4 1
|
||||
X5 nok
|
||||
X6 ok
|
||||
13
src/userland/cli/third_party/tcc/tests/pp/20.c
vendored
Normal file
13
src/userland/cli/third_party/tcc/tests/pp/20.c
vendored
Normal file
@@ -0,0 +1,13 @@
|
||||
/* Various things I encountered while hacking the pre processor */
|
||||
#define wrap(x) x
|
||||
#define pr_warning(fmt, ...) printk(KERN_WARNING fmt, ##__VA_ARGS__)
|
||||
#define pr_warn(x,y) pr_warning(x,y)
|
||||
#define net_ratelimited_function(function, ...) function(__VA_ARGS__)
|
||||
X1 net_ratelimited_function(pr_warn, "pipapo", bla);
|
||||
X2 net_ratelimited_function(wrap(pr_warn), "bla", foo);
|
||||
#define two m n
|
||||
#define chain4(a,b,c,d) a ## b ## c ## d
|
||||
X2 chain4(two,o,p,q)
|
||||
X3 chain4(o,two,p,q)
|
||||
X4 chain4(o,p,two,q)
|
||||
X5 chain4(o,p,q,two)
|
||||
6
src/userland/cli/third_party/tcc/tests/pp/20.expect
vendored
Normal file
6
src/userland/cli/third_party/tcc/tests/pp/20.expect
vendored
Normal file
@@ -0,0 +1,6 @@
|
||||
X1 printk(KERN_WARNING "pipapo",bla);
|
||||
X2 printk(KERN_WARNING "bla",foo);
|
||||
X2 twoopq
|
||||
X3 otwopq
|
||||
X4 optwoq
|
||||
X5 opqtwo
|
||||
62
src/userland/cli/third_party/tcc/tests/pp/21.c
vendored
Normal file
62
src/userland/cli/third_party/tcc/tests/pp/21.c
vendored
Normal file
@@ -0,0 +1,62 @@
|
||||
/* accept 'defined' as result of substitution */
|
||||
|
||||
----- 1 ------
|
||||
#define AAA 2
|
||||
#define BBB
|
||||
#define CCC (defined ( AAA ) && AAA > 1 && !defined BBB)
|
||||
#if !CCC
|
||||
OK
|
||||
#else
|
||||
NOT OK
|
||||
#endif
|
||||
|
||||
----- 2 ------
|
||||
#undef BBB
|
||||
#if CCC
|
||||
OK
|
||||
#else
|
||||
NOT OK
|
||||
#endif
|
||||
|
||||
----- 3 ------
|
||||
#define DEFINED defined
|
||||
#define DDD (DEFINED ( AAA ) && AAA > 1 && !DEFINED BBB)
|
||||
#if (DDD)
|
||||
OK
|
||||
#else
|
||||
NOT OK
|
||||
#endif
|
||||
|
||||
----- 4 ------
|
||||
#undef AAA
|
||||
#if !(DDD)
|
||||
OK
|
||||
#else
|
||||
NOT OK
|
||||
#endif
|
||||
|
||||
----- 5 ------
|
||||
line __LINE__
|
||||
#define __LINE__ # ## #
|
||||
line __LINE__
|
||||
|
||||
----- 10 ------
|
||||
/* preprocessor numbers are (u)intmax_t */
|
||||
#if -2147483648 < 0
|
||||
1 true
|
||||
#endif
|
||||
#if -0x80000000 < 0
|
||||
2 true
|
||||
#endif
|
||||
#if -9223372036854775808U > 0
|
||||
3 true
|
||||
#endif
|
||||
#if -0x8000000000000000 > 0 // unsigned by overflow
|
||||
4 true
|
||||
#endif
|
||||
#if 1 << 31 > 2 && 1 << 32 > 2 && 1 << 63 < 2 && 1U << 63 > 2
|
||||
5 true
|
||||
#endif
|
||||
#if (1<<29) * 11 >= 1<<32 && defined DDD << 63 < 0
|
||||
6 true
|
||||
#endif
|
||||
18
src/userland/cli/third_party/tcc/tests/pp/21.expect
vendored
Normal file
18
src/userland/cli/third_party/tcc/tests/pp/21.expect
vendored
Normal file
@@ -0,0 +1,18 @@
|
||||
----- 1 ------
|
||||
OK
|
||||
----- 2 ------
|
||||
OK
|
||||
----- 3 ------
|
||||
OK
|
||||
----- 4 ------
|
||||
OK
|
||||
----- 5 ------
|
||||
line 39
|
||||
line ##
|
||||
----- 10 ------
|
||||
1 true
|
||||
2 true
|
||||
3 true
|
||||
4 true
|
||||
5 true
|
||||
6 true
|
||||
12
src/userland/cli/third_party/tcc/tests/pp/22.c
vendored
Normal file
12
src/userland/cli/third_party/tcc/tests/pp/22.c
vendored
Normal file
@@ -0,0 +1,12 @@
|
||||
#define TRACE(a,b,c) X a X b X c X
|
||||
#define rettrue(x) 1
|
||||
A rettrue(bla) B
|
||||
TRACE(
|
||||
ARG_1,
|
||||
#if rettrue(bla)
|
||||
ARG_2,
|
||||
#else
|
||||
ARG_2_wrong,
|
||||
#endif
|
||||
ARG_3
|
||||
);
|
||||
2
src/userland/cli/third_party/tcc/tests/pp/22.expect
vendored
Normal file
2
src/userland/cli/third_party/tcc/tests/pp/22.expect
vendored
Normal file
@@ -0,0 +1,2 @@
|
||||
A 1 B
|
||||
X ARG_1 X ARG_2 X ARG_3 X;
|
||||
19
src/userland/cli/third_party/tcc/tests/pp/23.S
vendored
Normal file
19
src/userland/cli/third_party/tcc/tests/pp/23.S
vendored
Normal file
@@ -0,0 +1,19 @@
|
||||
__LINE__
|
||||
# 10
|
||||
__LINE__
|
||||
# line 20
|
||||
__LINE__
|
||||
# 64mb
|
||||
__LINE__
|
||||
# line 30
|
||||
__LINE__
|
||||
#define LINE1 40
|
||||
# line LINE1
|
||||
__LINE__ __FILE__
|
||||
#define LINE2 50
|
||||
# line LINE2 "file1"
|
||||
__LINE__ __FILE__
|
||||
#define LINE3 60
|
||||
#define FILE "file2"
|
||||
# line LINE3 FILE
|
||||
__LINE__ __FILE__
|
||||
8
src/userland/cli/third_party/tcc/tests/pp/23.expect
vendored
Normal file
8
src/userland/cli/third_party/tcc/tests/pp/23.expect
vendored
Normal file
@@ -0,0 +1,8 @@
|
||||
1
|
||||
3
|
||||
20
|
||||
22
|
||||
30
|
||||
40 "23.S"
|
||||
50 "file1"
|
||||
60 "file2"
|
||||
56
src/userland/cli/third_party/tcc/tests/pp/Makefile
vendored
Normal file
56
src/userland/cli/third_party/tcc/tests/pp/Makefile
vendored
Normal file
@@ -0,0 +1,56 @@
|
||||
#
|
||||
# credits: 01..13.c from the pcc cpp-tests suite
|
||||
#
|
||||
|
||||
TOP = ../..
|
||||
include $(TOP)/Makefile
|
||||
SRC = $(TOPSRC)/tests/pp
|
||||
VPATH = $(SRC)
|
||||
|
||||
files = $(patsubst %.$1,%.test,$(notdir $(wildcard $(SRC)/*.$1)))
|
||||
TESTS = $(call files,c) $(call files,S)
|
||||
|
||||
all test testspp.all: $(sort $(TESTS))
|
||||
|
||||
DIFF_OPTS = -Nu -b
|
||||
|
||||
# Filter source directory in warnings/errors (out-of-tree builds)
|
||||
FILTER = 2>&1 | sed 's,$(SRC)/,,g'
|
||||
|
||||
%.test: %.c %.expect
|
||||
@echo PPTest $* ...
|
||||
-@$(TCC) -E -P $< $(FILTER) >$*.output 2>&1 ; \
|
||||
diff $(DIFF_OPTS) $(SRC)/$*.expect $*.output \
|
||||
&& rm -f $*.output
|
||||
|
||||
%.test: %.S %.expect
|
||||
@echo PPTest $* ...
|
||||
-@$(TCC) -E -P $< $(FILTER) >$*.output 2>&1 ; \
|
||||
diff $(DIFF_OPTS) $(SRC)/$*.expect $*.output \
|
||||
&& rm -f $*.output
|
||||
|
||||
testspp.%: %.test ;
|
||||
|
||||
# generate .expect file with tcc, e.g. "make testspp.17+"
|
||||
testspp.%+: %.c
|
||||
$(TCC) -E -P $*.[cS] -o $*.expect
|
||||
|
||||
# automatically generate .expect files with gcc:
|
||||
%.expect: # %.c
|
||||
gcc -E -P $*.[cS] >$*.expect 2>&1
|
||||
|
||||
# tell make not to delete
|
||||
.PRECIOUS: %.expect
|
||||
|
||||
clean:
|
||||
rm -f *.output
|
||||
|
||||
02.test : DIFF_OPTS += -w
|
||||
16.test : DIFF_OPTS += -B
|
||||
# 15.test : DIFF_OPTS += -I"^XXX:"
|
||||
|
||||
# diff options:
|
||||
# -b ighore space changes
|
||||
# -w ighore all whitespace
|
||||
# -B ignore blank lines
|
||||
# -I <RE> ignore lines matching RE
|
||||
27
src/userland/cli/third_party/tcc/tests/pp/pp-counter.c
vendored
Normal file
27
src/userland/cli/third_party/tcc/tests/pp/pp-counter.c
vendored
Normal file
@@ -0,0 +1,27 @@
|
||||
X1 __COUNTER__
|
||||
X2 __COUNTER__
|
||||
#if __COUNTER__
|
||||
X3 __COUNTER__
|
||||
#endif
|
||||
#define pass(x) x
|
||||
#define a x __COUNTER__ y
|
||||
#define a2 pass(__COUNTER__)
|
||||
#define f(c) c __COUNTER__
|
||||
#define apply(d) d d __COUNTER__ x2 f(d) y2 __COUNTER__
|
||||
#define _paste(a,b) a ## b
|
||||
#define paste(a,b) _paste(a,b)
|
||||
#define _paste3(a,b,c) a ## b ## c
|
||||
#define doublepaste(a,b) _paste3(a,b,b)
|
||||
#define str(x) #x
|
||||
X4 a
|
||||
X5 f(a)
|
||||
X6 f(b)
|
||||
X7 f(__COUNTER__)
|
||||
X8 apply(a)
|
||||
X9 apply(f(a))
|
||||
X10 apply(__COUNTER__)
|
||||
X11 apply(a2)
|
||||
X12 str(__COUNTER__)
|
||||
X13 paste(x,__COUNTER__)
|
||||
X14 _paste(x,__COUNTER__)
|
||||
X15 doublepaste(x,__COUNTER__)
|
||||
15
src/userland/cli/third_party/tcc/tests/pp/pp-counter.expect
vendored
Normal file
15
src/userland/cli/third_party/tcc/tests/pp/pp-counter.expect
vendored
Normal file
@@ -0,0 +1,15 @@
|
||||
X1 0
|
||||
X2 1
|
||||
X3 3
|
||||
X4 x 4 y
|
||||
X5 x 5 y 6
|
||||
X6 b 7
|
||||
X7 8 9
|
||||
X8 x 10 y x 10 y 11 x2 x 10 y 12 y2 13
|
||||
X9 x 14 y 15 x 14 y 15 16 x2 x 14 y 15 17 y2 18
|
||||
X10 19 19 20 x2 19 21 y2 22
|
||||
X11 23 23 24 x2 23 25 y2 26
|
||||
X12 "__COUNTER__"
|
||||
X13 x27
|
||||
X14 x__COUNTER__
|
||||
X15 x2828
|
||||
4520
src/userland/cli/third_party/tcc/tests/tcctest.c
vendored
Normal file
4520
src/userland/cli/third_party/tcc/tests/tcctest.c
vendored
Normal file
File diff suppressed because it is too large
Load Diff
9
src/userland/cli/third_party/tcc/tests/tcctest.h
vendored
Normal file
9
src/userland/cli/third_party/tcc/tests/tcctest.h
vendored
Normal file
@@ -0,0 +1,9 @@
|
||||
static inline const char *get_basefile_from_header(void)
|
||||
{
|
||||
return __BASE_FILE__;
|
||||
}
|
||||
|
||||
static inline const char *get_file_from_header(void)
|
||||
{
|
||||
return __FILE__;
|
||||
}
|
||||
74
src/userland/cli/third_party/tcc/tests/test-win32.bat
vendored
Normal file
74
src/userland/cli/third_party/tcc/tests/test-win32.bat
vendored
Normal file
@@ -0,0 +1,74 @@
|
||||
@echo off
|
||||
setlocal
|
||||
set CC=gcc
|
||||
set TESTS=
|
||||
if "%1"=="/?" goto :usage
|
||||
goto :p0
|
||||
|
||||
:usage
|
||||
echo usage: test-win32.bat [options...] [tests...]
|
||||
echo options:
|
||||
echo -c compiler reference compiler (gcc or clang)
|
||||
echo -p path prepend path to PATH
|
||||
echo tests tests to run (default all)
|
||||
echo requires: make, gcc/clang, and sh in the PATH
|
||||
exit /B 1
|
||||
|
||||
:p2
|
||||
shift
|
||||
:p1
|
||||
shift
|
||||
:p0
|
||||
if "%1"=="-c" set CC=%2&&goto p2
|
||||
if "%1"=="-p" set PATH=%2;%PATH%&&goto p2
|
||||
if not "%1"=="" set TESTS=%TESTS% %1&&goto p1
|
||||
if "%TESTS%"=="" set TESTS=all -k
|
||||
|
||||
set PATH=%CD%\..\win32;%PATH%
|
||||
|
||||
for /f "delims=-" %%a in ('tcc.exe -dumpmachine') do set ARCH=%%a
|
||||
set ARCH=%ARCH:aarch=arm%
|
||||
set MACH=%ARCH:i386=x86%
|
||||
set MACH=%MACH:x86_64=amd64%
|
||||
rem echo ARCH:%ARCH% MACHINE:%MACH%
|
||||
|
||||
set CRTLIB=c:/windows/system32/msvcrt.dll
|
||||
set LIBTCC=libtcc.dll
|
||||
set LGCC=-lgcc
|
||||
if %CC%==gcc goto :c2
|
||||
|
||||
set CRTLIB=msvcrt.lib
|
||||
set LIBTCC=libtcc.lib
|
||||
set LGCC=
|
||||
if exist %CRTLIB% goto :c3
|
||||
tcc -impdef msvcrt.dll
|
||||
lib >nul /def:msvcrt.def /out:%CRTLIB% /machine:%MACH%
|
||||
:c2
|
||||
if not exist %CRTLIB% echo test-win32.bat: error: %CRTLIB% not found&&exit /b 1
|
||||
:c3
|
||||
|
||||
set REF_LINK=-nostdlib msvcrt_start.c %LGCC% -lkernel32 %CRTLIB%
|
||||
set CFG_MAK=..\config.mak
|
||||
set CFG_H=..\config.h
|
||||
|
||||
echo>>%CFG_H% #define CC_NAME CC_%CC%
|
||||
echo>>%CFG_H% #define GCC_MAJOR 15
|
||||
|
||||
if exist %CFG_MAK% del %CFG_MAK%
|
||||
echo>>%CFG_MAK% CC = %CC%.exe
|
||||
echo>>%CFG_MAK% CC_NAME = %CC%
|
||||
echo>>%CFG_MAK% ARCH = %ARCH%
|
||||
echo>>%CFG_MAK% CFLAGS = -Wall -O0
|
||||
echo>>%CFG_MAK% LDFLAGS =
|
||||
echo>>%CFG_MAK% LIBSUF = .lib
|
||||
echo>>%CFG_MAK% prefix = $(TOP)/bin
|
||||
echo>>%CFG_MAK% EXESUF = .exe
|
||||
echo>>%CFG_MAK% DLLSUF = .dll
|
||||
echo>>%CFG_MAK% TARGETOS = WIN32
|
||||
echo>>%CFG_MAK% CONFIG_WIN32 = yes
|
||||
echo>>%CFG_MAK% TOPSRC = $(TOP)
|
||||
echo>>%CFG_MAK% SHELL = sh
|
||||
echo>>%CFG_MAK% test.ref: CFLAGS += %REF_LINK%
|
||||
|
||||
set GMAKE=make
|
||||
%GMAKE% TCC_LOCAL=tcc.exe LIBTCC=win32/%LIBTCC% %TESTS%
|
||||
510
src/userland/cli/third_party/tcc/tests/testfp.c
vendored
Normal file
510
src/userland/cli/third_party/tcc/tests/testfp.c
vendored
Normal file
@@ -0,0 +1,510 @@
|
||||
/*
|
||||
* Test 128-bit floating-point arithmetic on arm64:
|
||||
* build with two different compilers and compare the output.
|
||||
*
|
||||
* Copyright (c) 2015 Edmund Grimley Evans
|
||||
*
|
||||
* Copying and distribution of this file, with or without modification,
|
||||
* are permitted in any medium without royalty provided the copyright
|
||||
* notice and this notice are preserved. This file is offered as-is,
|
||||
* without any warranty.
|
||||
*/
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#define check(x) ((x) ? (void)0 : check_fail(#x, __FILE__, __LINE__))
|
||||
|
||||
void check_fail(const char *assertion, const char *file, unsigned int line)
|
||||
{
|
||||
printf("%s:%d: Check (%s) failed.", file, line, assertion);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
typedef struct {
|
||||
unsigned long long x0, x1;
|
||||
} u128_t;
|
||||
|
||||
float copy_fi(uint32_t x)
|
||||
{
|
||||
float f;
|
||||
memcpy(&f, &x, 4);
|
||||
return f;
|
||||
}
|
||||
|
||||
double copy_di(uint64_t x)
|
||||
{
|
||||
double f;
|
||||
memcpy(&f, &x, 8);
|
||||
return f;
|
||||
}
|
||||
|
||||
long double copy_ldi(u128_t x)
|
||||
{
|
||||
long double f;
|
||||
memcpy(&f, &x, 16);
|
||||
return f;
|
||||
}
|
||||
|
||||
uint32_t copy_if(float f)
|
||||
{
|
||||
uint32_t x;
|
||||
memcpy(&x, &f, 4);
|
||||
return x;
|
||||
}
|
||||
|
||||
uint64_t copy_id(double f)
|
||||
{
|
||||
uint64_t x;
|
||||
memcpy(&x, &f, 8);
|
||||
return x;
|
||||
}
|
||||
|
||||
u128_t copy_ild(long double f)
|
||||
{
|
||||
u128_t x;
|
||||
memcpy(&x, &f, 16);
|
||||
return x;
|
||||
}
|
||||
|
||||
long double make(int sgn, int exp, uint64_t high, uint64_t low)
|
||||
{
|
||||
u128_t x = { low,
|
||||
(0x0000ffffffffffff & high) |
|
||||
(0x7fff000000000000 & (uint64_t)exp << 48) |
|
||||
(0x8000000000000000 & (uint64_t)sgn << 63) };
|
||||
return copy_ldi(x);
|
||||
}
|
||||
|
||||
void cmp(long double a, long double b)
|
||||
{
|
||||
u128_t ax = copy_ild(a);
|
||||
u128_t bx = copy_ild(b);
|
||||
int eq = (a == b);
|
||||
int ne = (a != b);
|
||||
int lt = (a < b);
|
||||
int le = (a <= b);
|
||||
int gt = (a > b);
|
||||
int ge = (a >= b);
|
||||
|
||||
check(eq == 0 || eq == 1);
|
||||
check(lt == 0 || lt == 1);
|
||||
check(gt == 0 || gt == 1);
|
||||
check(ne == !eq && le == (lt | eq) && ge == (gt | eq));
|
||||
check(eq + lt + gt < 2);
|
||||
|
||||
printf("cmp %016llx%016llx %016llx%016llx %d %d %d\n",
|
||||
ax.x1, ax.x0, bx.x1, bx.x0, lt, eq, gt);
|
||||
}
|
||||
|
||||
void cmps(void)
|
||||
{
|
||||
int i, j;
|
||||
|
||||
for (i = 0; i < 2; i++)
|
||||
for (j = 0; j < 2; j++)
|
||||
cmp(make(i, 0, 0, 0), make(j, 0, 0, 0));
|
||||
|
||||
for (i = 0; i < 2; i++) {
|
||||
for (j = 0; j < 64; j++) {
|
||||
long double f1 = make(i, 32767, (uint64_t)1 << j, 0);
|
||||
long double f2 = make(i, 32767, 0, (uint64_t)1 << j);
|
||||
cmp(f1, 0);
|
||||
cmp(f2, 0);
|
||||
cmp(0, f1);
|
||||
cmp(0, f2);
|
||||
}
|
||||
}
|
||||
|
||||
for (i = 0; i < 6; i++)
|
||||
for (j = 0; j < 6; j++)
|
||||
cmp(make(i & 1, i >> 1, 0, 0),
|
||||
make(j & 1, j >> 1, 0, 0));
|
||||
|
||||
for (i = 0; i < 2; i++) {
|
||||
for (j = 0; j < 2; j++) {
|
||||
int a, b;
|
||||
for (a = 0; a < 2; a++) {
|
||||
for (b = 0; b < 2; b++) {
|
||||
cmp(make(i, j, a, b), make(i, j, 0, 0));
|
||||
cmp(make(i, j, 0, 0), make(i, j, a, b));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void xop(const char *name, long double a, long double b, long double c)
|
||||
{
|
||||
u128_t ax = copy_ild(a);
|
||||
u128_t bx = copy_ild(b);
|
||||
u128_t cx = copy_ild(c);
|
||||
printf("%s %016llx%016llx %016llx%016llx %016llx%016llx\n",
|
||||
name, ax.x1, ax.x0, bx.x1, bx.x0, cx.x1, cx.x0);
|
||||
}
|
||||
|
||||
void fadd(long double a, long double b)
|
||||
{
|
||||
xop("add", a, b, a + b);
|
||||
}
|
||||
|
||||
void fsub(long double a, long double b)
|
||||
{
|
||||
xop("sub", a, b, a - b);
|
||||
}
|
||||
|
||||
void fmul(long double a, long double b)
|
||||
{
|
||||
xop("mul", a, b, a * b);
|
||||
}
|
||||
|
||||
void fdiv(long double a, long double b)
|
||||
{
|
||||
xop("div", a, b, a / b);
|
||||
}
|
||||
|
||||
void nanz(void)
|
||||
{
|
||||
// Check NaNs:
|
||||
{
|
||||
long double x[7];
|
||||
int i, j, n = 0;
|
||||
x[n++] = make(0, 32000, 0x95132b76effc, 0xd79035214b4f8d53);
|
||||
x[n++] = make(1, 32001, 0xbe71d7a51587, 0x30601c6815d6c3ac);
|
||||
x[n++] = make(0, 32767, 0, 1);
|
||||
x[n++] = make(0, 32767, (uint64_t)1 << 46, 0);
|
||||
x[n++] = make(1, 32767, (uint64_t)1 << 47, 0);
|
||||
x[n++] = make(1, 32767, 0x7596c7099ad5, 0xe25fed2c58f73fc9);
|
||||
x[n++] = make(0, 32767, 0x835d143360f9, 0x5e315efb35630666);
|
||||
check(n == sizeof(x) / sizeof(*x));
|
||||
for (i = 0; i < n; i++) {
|
||||
for (j = 0; j < n; j++) {
|
||||
fadd(x[i], x[j]);
|
||||
fsub(x[i], x[j]);
|
||||
fmul(x[i], x[j]);
|
||||
fdiv(x[i], x[j]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Check infinities and zeroes:
|
||||
{
|
||||
long double x[6];
|
||||
int i, j, n = 0;
|
||||
x[n++] = make(1, 32000, 0x62acda85f700, 0x47b6c9f35edc4044);
|
||||
x[n++] = make(0, 32001, 0x94b7abf55af7, 0x9f425fe354428e19);
|
||||
x[n++] = make(0, 32767, 0, 0);
|
||||
x[n++] = make(1, 32767, 0, 0);
|
||||
x[n++] = make(0, 0, 0, 0);
|
||||
x[n++] = make(1, 0, 0, 0);
|
||||
check(n == sizeof(x) / sizeof(*x));
|
||||
for (i = 0; i < n; i++) {
|
||||
for (j = 0; j < n; j++) {
|
||||
fadd(x[i], x[j]);
|
||||
fsub(x[i], x[j]);
|
||||
fmul(x[i], x[j]);
|
||||
fdiv(x[i], x[j]);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void adds(void)
|
||||
{
|
||||
// Check shifting and add/sub:
|
||||
{
|
||||
int i;
|
||||
for (i = -130; i <= 130; i++) {
|
||||
int s1 = (uint32_t)i % 3 < 1;
|
||||
int s2 = (uint32_t)i % 5 < 2;
|
||||
fadd(make(s1, 16384 , 0x502c065e4f71a65d, 0xd2f9bdb031f4f031),
|
||||
make(s2, 16384 + i, 0xae267395a9bc1033, 0xb56b5800da1ba448));
|
||||
}
|
||||
}
|
||||
|
||||
// Check normalisation:
|
||||
{
|
||||
uint64_t a0 = 0xc6bab0a6afbef5ed;
|
||||
uint64_t a1 = 0x4f84136c4a2e9b52;
|
||||
int ee[] = { 0, 1, 10000 };
|
||||
int e, i;
|
||||
for (e = 0; e < sizeof(ee) / sizeof(*ee); e++) {
|
||||
int exp = ee[e];
|
||||
fsub(make(0, exp, a1, a0), make(0, 0, 0, 0));
|
||||
for (i = 63; i >= 0; i--)
|
||||
fsub(make(0, exp, a1 | (uint64_t)1 << i >> 1, a0),
|
||||
make(0, exp, a1 >> i << i, 0));
|
||||
for (i = 63; i >=0; i--)
|
||||
fsub(make(0, exp, a1, a0 | (uint64_t)1 << i >> 1),
|
||||
make(0, exp, a1, a0 >> i << i));
|
||||
}
|
||||
}
|
||||
|
||||
// Carry/overflow from rounding:
|
||||
{
|
||||
fadd(make(0, 114, -1, -1), make(0, 1, 0, 0));
|
||||
fadd(make(0, 32766, -1, -1), make(0, 32653, 0, 0));
|
||||
fsub(make(1, 32766, -1, -1), make(0, 32653, 0, 0));
|
||||
}
|
||||
}
|
||||
|
||||
void muls(void)
|
||||
{
|
||||
int i, j;
|
||||
|
||||
{
|
||||
long double max = make(0, 32766, -1, -1);
|
||||
long double min = make(0, 0, 0, 1);
|
||||
fmul(max, max);
|
||||
fmul(max, min);
|
||||
fmul(min, min);
|
||||
}
|
||||
|
||||
for (i = 117; i > 0; i--)
|
||||
fmul(make(0, 16268, 0x643dcea76edc, 0xe0877a598403627a),
|
||||
make(i & 1, i, 0, 0));
|
||||
|
||||
fmul(make(0, 16383, -1, -3), make(0, 16383, 0, 1));
|
||||
// Round to next exponent:
|
||||
fmul(make(0, 16383, -1, -2), make(0, 16383, 0, 1));
|
||||
// Round from subnormal to normal:
|
||||
fmul(make(0, 1, -1, -1), make(0, 16382, 0, 0));
|
||||
|
||||
for (i = 0; i < 2; i++)
|
||||
for (j = 0; j < 112; j++)
|
||||
fmul(make(0, 16383, (uint64_t)1 << i, 0),
|
||||
make(0, 16383,
|
||||
j < 64 ? 0 : (uint64_t)1 << (j - 64),
|
||||
j < 64 ? (uint64_t)1 << j : 0));
|
||||
}
|
||||
|
||||
void divs(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
{
|
||||
long double max = make(0, 32766, -1, -1);
|
||||
long double min = make(0, 0, 0, 1);
|
||||
fdiv(max, max);
|
||||
fdiv(max, min);
|
||||
fdiv(min, max);
|
||||
fdiv(min, min);
|
||||
}
|
||||
|
||||
for (i = 0; i < 64; i++)
|
||||
fdiv(make(0, 16383, -1, -1), make(0, 16383, -1, -(uint64_t)1 << i));
|
||||
for (i = 0; i < 48; i++)
|
||||
fdiv(make(0, 16383, -1, -1), make(0, 16383, -(uint64_t)1 << i, 0));
|
||||
}
|
||||
|
||||
void cvtlsw(int32_t a)
|
||||
{
|
||||
long double f = a;
|
||||
u128_t x = copy_ild(f);
|
||||
printf("cvtlsw %08lx %016llx%016llx\n", (long)(uint32_t)a, x.x1, x.x0);
|
||||
}
|
||||
|
||||
void cvtlsx(int64_t a)
|
||||
{
|
||||
long double f = a;
|
||||
u128_t x = copy_ild(f);
|
||||
printf("cvtlsx %016llx %016llx%016llx\n",
|
||||
(long long)(uint64_t)a, x.x1, x.x0);
|
||||
}
|
||||
|
||||
void cvtluw(uint32_t a)
|
||||
{
|
||||
long double f = a;
|
||||
u128_t x = copy_ild(f);
|
||||
printf("cvtluw %08lx %016llx%016llx\n", (long)a, x.x1, x.x0);
|
||||
}
|
||||
|
||||
void cvtlux(uint64_t a)
|
||||
{
|
||||
long double f = a;
|
||||
u128_t x = copy_ild(f);
|
||||
printf("cvtlux %016llx %016llx%016llx\n", (long long)a, x.x1, x.x0);
|
||||
}
|
||||
|
||||
void cvtil(long double a)
|
||||
{
|
||||
u128_t x = copy_ild(a);
|
||||
int32_t b1 = a;
|
||||
int64_t b2 = a;
|
||||
uint32_t b3 = a;
|
||||
uint64_t b4 = a;
|
||||
printf("cvtswl %016llx%016llx %08lx\n",
|
||||
x.x1, x.x0, (long)(uint32_t)b1);
|
||||
printf("cvtsxl %016llx%016llx %016llx\n",
|
||||
x.x1, x.x0, (long long)(uint64_t)b2);
|
||||
printf("cvtuwl %016llx%016llx %08lx\n",
|
||||
x.x1, x.x0, (long)b3);
|
||||
printf("cvtuxl %016llx%016llx %016llx\n",
|
||||
x.x1, x.x0, (long long)b4);
|
||||
}
|
||||
|
||||
void cvtlf(float a)
|
||||
{
|
||||
uint32_t ax = copy_if(a);
|
||||
long double b = a;
|
||||
u128_t bx = copy_ild(b);
|
||||
printf("cvtlf %08lx %016llx%016llx\n", (long)ax, bx.x1, bx.x0);
|
||||
}
|
||||
|
||||
void cvtld(double a)
|
||||
{
|
||||
uint64_t ax = copy_id(a);
|
||||
long double b = a;
|
||||
u128_t bx = copy_ild(b);
|
||||
printf("cvtld %016llx %016llx%016llx\n", (long long)ax, bx.x1, bx.x0);
|
||||
}
|
||||
|
||||
void cvtfl(long double a)
|
||||
{
|
||||
u128_t ax = copy_ild(a);
|
||||
float b = a;
|
||||
uint32_t bx = copy_if(b);
|
||||
printf("cvtfl %016llx%016llx %08lx\n", ax.x1, ax.x0, (long)bx);
|
||||
}
|
||||
|
||||
void cvtdl(long double a)
|
||||
{
|
||||
u128_t ax = copy_ild(a);
|
||||
double b = a;
|
||||
uint64_t bx = copy_id(b);
|
||||
printf("cvtdl %016llx%016llx %016llx\n", ax.x1, ax.x0, (long long)bx);
|
||||
}
|
||||
|
||||
void cvts(void)
|
||||
{
|
||||
int i, j;
|
||||
|
||||
{
|
||||
uint32_t x = 0xad040c5b;
|
||||
cvtlsw(0);
|
||||
for (i = 0; i < 31; i++)
|
||||
cvtlsw(x >> (31 - i));
|
||||
for (i = 0; i < 31; i++)
|
||||
cvtlsw(-(x >> (31 - i)));
|
||||
cvtlsw(0x80000000);
|
||||
}
|
||||
{
|
||||
uint64_t x = 0xb630a248cad9afd2;
|
||||
cvtlsx(0);
|
||||
for (i = 0; i < 63; i++)
|
||||
cvtlsx(x >> (63 - i));
|
||||
for (i = 0; i < 63; i++)
|
||||
cvtlsx(-(x >> (63 - i)));
|
||||
cvtlsx(0x8000000000000000);
|
||||
}
|
||||
{
|
||||
uint32_t x = 0xad040c5b;
|
||||
cvtluw(0);
|
||||
for (i = 0; i < 32; i++)
|
||||
cvtluw(x >> (31 - i));
|
||||
}
|
||||
{
|
||||
uint64_t x = 0xb630a248cad9afd2;
|
||||
cvtlux(0);
|
||||
for (i = 0; i < 64; i++)
|
||||
cvtlux(x >> (63 - i));
|
||||
}
|
||||
|
||||
for (i = 0; i < 2; i++) {
|
||||
cvtil(make(i, 32767, 0, 1));
|
||||
cvtil(make(i, 32767, (uint64_t)1 << 47, 0));
|
||||
cvtil(make(i, 32767, 123, 456));
|
||||
cvtil(make(i, 32767, 0, 0));
|
||||
cvtil(make(i, 16382, -1, -1));
|
||||
cvtil(make(i, 16383, -1, -1));
|
||||
cvtil(make(i, 16384, 0x7fffffffffff, -1));
|
||||
cvtil(make(i, 16384, 0x800000000000, 0));
|
||||
for (j = 0; j < 68; j++)
|
||||
cvtil(make(i, 16381 + j, 0xd4822c0a10ec, 0x1fe2f8b2669f5c9d));
|
||||
}
|
||||
|
||||
cvtlf(copy_fi(0x00000000));
|
||||
cvtlf(copy_fi(0x456789ab));
|
||||
cvtlf(copy_fi(0x7f800000));
|
||||
cvtlf(copy_fi(0x7f923456));
|
||||
cvtlf(copy_fi(0x7fdbcdef));
|
||||
cvtlf(copy_fi(0x80000000));
|
||||
cvtlf(copy_fi(0xabcdef12));
|
||||
cvtlf(copy_fi(0xff800000));
|
||||
cvtlf(copy_fi(0xff923456));
|
||||
cvtlf(copy_fi(0xffdbcdef));
|
||||
|
||||
cvtld(copy_di(0x0000000000000000));
|
||||
cvtld(copy_di(0x456789abcdef0123));
|
||||
cvtld(copy_di(0x7ff0000000000000));
|
||||
cvtld(copy_di(0x7ff123456789abcd));
|
||||
cvtld(copy_di(0x7ffabcdef1234567));
|
||||
cvtld(copy_di(0x8000000000000000));
|
||||
cvtld(copy_di(0xcdef123456789abc));
|
||||
cvtld(copy_di(0xfff0000000000000));
|
||||
cvtld(copy_di(0xfff123456789abcd));
|
||||
cvtld(copy_di(0xfffabcdef1234567));
|
||||
|
||||
for (i = 0; i < 2; i++) { \
|
||||
cvtfl(make(i, 0, 0, 0));
|
||||
cvtfl(make(i, 16232, -1, -1));
|
||||
cvtfl(make(i, 16233, 0, 0));
|
||||
cvtfl(make(i, 16233, 0, 1));
|
||||
cvtfl(make(i, 16383, 0xab0ffd000000, 0));
|
||||
cvtfl(make(i, 16383, 0xab0ffd000001, 0));
|
||||
cvtfl(make(i, 16383, 0xab0ffeffffff, 0));
|
||||
cvtfl(make(i, 16383, 0xab0fff000000, 0));
|
||||
cvtfl(make(i, 16383, 0xab0fff000001, 0));
|
||||
cvtfl(make(i, 16510, 0xfffffeffffff, -1));
|
||||
cvtfl(make(i, 16510, 0xffffff000000, 0));
|
||||
cvtfl(make(i, 16511, 0, 0));
|
||||
cvtfl(make(i, 32767, 0, 0));
|
||||
cvtfl(make(i, 32767, 0, 1));
|
||||
cvtfl(make(i, 32767, 0x4cbe01ac5f40, 0x75cee3c6afbb00b5));
|
||||
cvtfl(make(i, 32767, 0x800000000000, 1));
|
||||
cvtfl(make(i, 32767, 0xa11caaaf6a52, 0x696033e871eab099));
|
||||
}
|
||||
|
||||
for (i = 0; i < 2; i++) {
|
||||
cvtdl(make(i, 0, 0, 0));
|
||||
cvtdl(make(i, 15307, -1, -1));
|
||||
cvtdl(make(i, 15308, 0, 0));
|
||||
cvtdl(make(i, 15308, 0, 1));
|
||||
cvtdl(make(i, 16383, 0xabc123abc0ff, 0xe800000000000000));
|
||||
cvtdl(make(i, 16383, 0xabc123abc0ff, 0xe800000000000001));
|
||||
cvtdl(make(i, 16383, 0xabc123abc0ff, 0xf7ffffffffffffff));
|
||||
cvtdl(make(i, 16383, 0xabc123abc0ff, 0xf800000000000000));
|
||||
cvtdl(make(i, 16383, 0xabc123abc0ff, 0xf800000000000001));
|
||||
cvtdl(make(i, 17406, 0xffffffffffff, 0xf7ffffffffffffff));
|
||||
cvtdl(make(i, 17406, 0xffffffffffff, 0xf800000000000000));
|
||||
cvtdl(make(i, 17407, 0, 0));
|
||||
cvtdl(make(i, 32767, 0, 0));
|
||||
cvtdl(make(i, 32767, 0, 1));
|
||||
cvtdl(make(i, 32767, 0x4cbe01ac5f40, 0x75cee3c6afbb00b5));
|
||||
cvtdl(make(i, 32767, 0x800000000000, 1));
|
||||
cvtdl(make(i, 32767, 0xa11caaaf6a52, 0x696033e871eab099));
|
||||
}
|
||||
}
|
||||
|
||||
void tests(void)
|
||||
{
|
||||
cmps();
|
||||
nanz();
|
||||
adds();
|
||||
muls();
|
||||
divs();
|
||||
cvts();
|
||||
}
|
||||
|
||||
int main()
|
||||
{
|
||||
#ifdef __aarch64__
|
||||
tests();
|
||||
#else
|
||||
printf("This test program is intended for a little-endian architecture\n"
|
||||
"with an IEEE-standard 128-bit long double.\n");
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
18
src/userland/cli/third_party/tcc/tests/tests2/00_assignment.c
vendored
Normal file
18
src/userland/cli/third_party/tcc/tests/tests2/00_assignment.c
vendored
Normal file
@@ -0,0 +1,18 @@
|
||||
#include <stdio.h>
|
||||
|
||||
int main()
|
||||
{
|
||||
int a;
|
||||
a = 42;
|
||||
printf("%d\n", a);
|
||||
|
||||
int b = 64;
|
||||
printf("%d\n", b);
|
||||
|
||||
int c = 12, d = 34;
|
||||
printf("%d, %d\n", c, d);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
// vim: set expandtab ts=4 sw=3 sts=3 tw=80 :
|
||||
3
src/userland/cli/third_party/tcc/tests/tests2/00_assignment.expect
vendored
Normal file
3
src/userland/cli/third_party/tcc/tests/tests2/00_assignment.expect
vendored
Normal file
@@ -0,0 +1,3 @@
|
||||
42
|
||||
64
|
||||
12, 34
|
||||
14
src/userland/cli/third_party/tcc/tests/tests2/01_comment.c
vendored
Normal file
14
src/userland/cli/third_party/tcc/tests/tests2/01_comment.c
vendored
Normal file
@@ -0,0 +1,14 @@
|
||||
#include <stdio.h>
|
||||
|
||||
int main()
|
||||
{
|
||||
printf("Hello\n");
|
||||
printf("Hello\n"); /* this is a comment */ printf("Hello\n");
|
||||
printf("Hello\n");
|
||||
// this is also a comment sayhello();
|
||||
printf("Hello\n");
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
// vim: set expandtab ts=4 sw=3 sts=3 tw=80 :
|
||||
5
src/userland/cli/third_party/tcc/tests/tests2/01_comment.expect
vendored
Normal file
5
src/userland/cli/third_party/tcc/tests/tests2/01_comment.expect
vendored
Normal file
@@ -0,0 +1,5 @@
|
||||
Hello
|
||||
Hello
|
||||
Hello
|
||||
Hello
|
||||
Hello
|
||||
18
src/userland/cli/third_party/tcc/tests/tests2/02_printf.c
vendored
Normal file
18
src/userland/cli/third_party/tcc/tests/tests2/02_printf.c
vendored
Normal file
@@ -0,0 +1,18 @@
|
||||
#include <stdio.h>
|
||||
|
||||
int main()
|
||||
{
|
||||
printf("Hello world\n");
|
||||
|
||||
int Count;
|
||||
for (Count = -5; Count <= 5; Count++)
|
||||
printf("Count = %d\n", Count);
|
||||
|
||||
printf("String 'hello', 'there' is '%s', '%s'\n", "hello", "there");
|
||||
printf("Character 'A' is '%c'\n", 65);
|
||||
printf("Character 'a' is '%c'\n", 'a');
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
// vim: set expandtab ts=4 sw=3 sts=3 tw=80 :
|
||||
15
src/userland/cli/third_party/tcc/tests/tests2/02_printf.expect
vendored
Normal file
15
src/userland/cli/third_party/tcc/tests/tests2/02_printf.expect
vendored
Normal file
@@ -0,0 +1,15 @@
|
||||
Hello world
|
||||
Count = -5
|
||||
Count = -4
|
||||
Count = -3
|
||||
Count = -2
|
||||
Count = -1
|
||||
Count = 0
|
||||
Count = 1
|
||||
Count = 2
|
||||
Count = 3
|
||||
Count = 4
|
||||
Count = 5
|
||||
String 'hello', 'there' is 'hello', 'there'
|
||||
Character 'A' is 'A'
|
||||
Character 'a' is 'a'
|
||||
38
src/userland/cli/third_party/tcc/tests/tests2/03_struct.c
vendored
Normal file
38
src/userland/cli/third_party/tcc/tests/tests2/03_struct.c
vendored
Normal file
@@ -0,0 +1,38 @@
|
||||
extern int printf(const char*, ...);
|
||||
|
||||
struct fred;
|
||||
|
||||
void fred$(struct fred* this)
|
||||
{
|
||||
printf("~fred()\n");
|
||||
}
|
||||
|
||||
struct __attribute__((__cleanup__(fred$))) fred
|
||||
{
|
||||
int boris;
|
||||
int natasha;
|
||||
};
|
||||
|
||||
int main()
|
||||
{
|
||||
struct fred __attribute__((__cleanup__(fred$))) bloggs;
|
||||
|
||||
bloggs.boris = 12;
|
||||
bloggs.natasha = 34;
|
||||
|
||||
printf("%d\n", bloggs.boris);
|
||||
printf("%d\n", bloggs.natasha);
|
||||
|
||||
struct fred jones[2];
|
||||
jones[0].boris = 12;
|
||||
jones[0].natasha = 34;
|
||||
jones[1].boris = 56;
|
||||
jones[1].natasha = 78;
|
||||
|
||||
printf("%d\n", jones[0].boris);
|
||||
printf("%d\n", jones[0].natasha);
|
||||
printf("%d\n", jones[1].boris);
|
||||
printf("%d\n", jones[1].natasha);
|
||||
|
||||
return 0;
|
||||
}
|
||||
8
src/userland/cli/third_party/tcc/tests/tests2/03_struct.expect
vendored
Normal file
8
src/userland/cli/third_party/tcc/tests/tests2/03_struct.expect
vendored
Normal file
@@ -0,0 +1,8 @@
|
||||
03_struct.c:14: warning: attribute '__cleanup__' ignored on type
|
||||
12
|
||||
34
|
||||
12
|
||||
34
|
||||
56
|
||||
78
|
||||
~fred()
|
||||
15
src/userland/cli/third_party/tcc/tests/tests2/04_for.c
vendored
Normal file
15
src/userland/cli/third_party/tcc/tests/tests2/04_for.c
vendored
Normal file
@@ -0,0 +1,15 @@
|
||||
#include <stdio.h>
|
||||
|
||||
int main()
|
||||
{
|
||||
int Count;
|
||||
|
||||
for (Count = 1; Count <= 10; Count++)
|
||||
{
|
||||
printf("%d\n", Count);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
// vim: set expandtab ts=4 sw=3 sts=3 tw=80 :
|
||||
10
src/userland/cli/third_party/tcc/tests/tests2/04_for.expect
vendored
Normal file
10
src/userland/cli/third_party/tcc/tests/tests2/04_for.expect
vendored
Normal file
@@ -0,0 +1,10 @@
|
||||
1
|
||||
2
|
||||
3
|
||||
4
|
||||
5
|
||||
6
|
||||
7
|
||||
8
|
||||
9
|
||||
10
|
||||
21
src/userland/cli/third_party/tcc/tests/tests2/05_array.c
vendored
Normal file
21
src/userland/cli/third_party/tcc/tests/tests2/05_array.c
vendored
Normal file
@@ -0,0 +1,21 @@
|
||||
#include <stdio.h>
|
||||
|
||||
int main()
|
||||
{
|
||||
int Count;
|
||||
int Array[10];
|
||||
|
||||
for (Count = 1; Count <= 10; Count++)
|
||||
{
|
||||
Array[Count-1] = Count * Count;
|
||||
}
|
||||
|
||||
for (Count = 0; Count < 10; Count++)
|
||||
{
|
||||
printf("%d\n", Array[Count]);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
// vim: set expandtab ts=4 sw=3 sts=3 tw=80 :
|
||||
10
src/userland/cli/third_party/tcc/tests/tests2/05_array.expect
vendored
Normal file
10
src/userland/cli/third_party/tcc/tests/tests2/05_array.expect
vendored
Normal file
@@ -0,0 +1,10 @@
|
||||
1
|
||||
4
|
||||
9
|
||||
16
|
||||
25
|
||||
36
|
||||
49
|
||||
64
|
||||
81
|
||||
100
|
||||
29
src/userland/cli/third_party/tcc/tests/tests2/06_case.c
vendored
Normal file
29
src/userland/cli/third_party/tcc/tests/tests2/06_case.c
vendored
Normal file
@@ -0,0 +1,29 @@
|
||||
#include <stdio.h>
|
||||
|
||||
int main()
|
||||
{
|
||||
int Count;
|
||||
|
||||
for (Count = 0; Count < 4; Count++)
|
||||
{
|
||||
printf("%d\n", Count);
|
||||
switch (Count)
|
||||
{
|
||||
case 1:
|
||||
printf("%d\n", 1);
|
||||
break;
|
||||
|
||||
case 2:
|
||||
printf("%d\n", 2);
|
||||
break;
|
||||
|
||||
default:
|
||||
printf("%d\n", 0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
// vim: set expandtab ts=4 sw=3 sts=3 tw=80 :
|
||||
8
src/userland/cli/third_party/tcc/tests/tests2/06_case.expect
vendored
Normal file
8
src/userland/cli/third_party/tcc/tests/tests2/06_case.expect
vendored
Normal file
@@ -0,0 +1,8 @@
|
||||
0
|
||||
0
|
||||
1
|
||||
1
|
||||
2
|
||||
2
|
||||
3
|
||||
0
|
||||
35
src/userland/cli/third_party/tcc/tests/tests2/07_function.c
vendored
Normal file
35
src/userland/cli/third_party/tcc/tests/tests2/07_function.c
vendored
Normal file
@@ -0,0 +1,35 @@
|
||||
#include <stdio.h>
|
||||
|
||||
int myfunc(int x)
|
||||
{
|
||||
return x * x;
|
||||
}
|
||||
|
||||
void vfunc(int a)
|
||||
{
|
||||
printf("a=%d\n", a);
|
||||
}
|
||||
|
||||
void qfunc()
|
||||
{
|
||||
printf("qfunc()\n");
|
||||
}
|
||||
|
||||
void zfunc()
|
||||
{
|
||||
((void (*)(void))0) ();
|
||||
}
|
||||
|
||||
int main()
|
||||
{
|
||||
printf("%d\n", myfunc(3));
|
||||
printf("%d\n", myfunc(4));
|
||||
|
||||
vfunc(1234);
|
||||
|
||||
qfunc();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
// vim: set expandtab ts=4 sw=3 sts=3 tw=80 :
|
||||
4
src/userland/cli/third_party/tcc/tests/tests2/07_function.expect
vendored
Normal file
4
src/userland/cli/third_party/tcc/tests/tests2/07_function.expect
vendored
Normal file
@@ -0,0 +1,4 @@
|
||||
9
|
||||
16
|
||||
a=1234
|
||||
qfunc()
|
||||
24
src/userland/cli/third_party/tcc/tests/tests2/08_while.c
vendored
Normal file
24
src/userland/cli/third_party/tcc/tests/tests2/08_while.c
vendored
Normal file
@@ -0,0 +1,24 @@
|
||||
#include <stdio.h>
|
||||
|
||||
int main()
|
||||
{
|
||||
int a;
|
||||
int p;
|
||||
int t;
|
||||
|
||||
a = 1;
|
||||
p = 0;
|
||||
t = 0;
|
||||
|
||||
while (a < 100)
|
||||
{
|
||||
printf("%d\n", a);
|
||||
t = a;
|
||||
a = t + p;
|
||||
p = t;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
// vim: set expandtab ts=4 sw=3 sts=3 tw=80 :
|
||||
11
src/userland/cli/third_party/tcc/tests/tests2/08_while.expect
vendored
Normal file
11
src/userland/cli/third_party/tcc/tests/tests2/08_while.expect
vendored
Normal file
@@ -0,0 +1,11 @@
|
||||
1
|
||||
1
|
||||
2
|
||||
3
|
||||
5
|
||||
8
|
||||
13
|
||||
21
|
||||
34
|
||||
55
|
||||
89
|
||||
24
src/userland/cli/third_party/tcc/tests/tests2/09_do_while.c
vendored
Normal file
24
src/userland/cli/third_party/tcc/tests/tests2/09_do_while.c
vendored
Normal file
@@ -0,0 +1,24 @@
|
||||
#include <stdio.h>
|
||||
|
||||
int main()
|
||||
{
|
||||
int a;
|
||||
int p;
|
||||
int t;
|
||||
|
||||
a = 1;
|
||||
p = 0;
|
||||
t = 0;
|
||||
|
||||
do
|
||||
{
|
||||
printf("%d\n", a);
|
||||
t = a;
|
||||
a = t + p;
|
||||
p = t;
|
||||
} while (a < 100);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
// vim: set expandtab ts=4 sw=3 sts=3 tw=80 :
|
||||
11
src/userland/cli/third_party/tcc/tests/tests2/09_do_while.expect
vendored
Normal file
11
src/userland/cli/third_party/tcc/tests/tests2/09_do_while.expect
vendored
Normal file
@@ -0,0 +1,11 @@
|
||||
1
|
||||
1
|
||||
2
|
||||
3
|
||||
5
|
||||
8
|
||||
13
|
||||
21
|
||||
34
|
||||
55
|
||||
89
|
||||
34
src/userland/cli/third_party/tcc/tests/tests2/100_c99array-decls.c
vendored
Normal file
34
src/userland/cli/third_party/tcc/tests/tests2/100_c99array-decls.c
vendored
Normal file
@@ -0,0 +1,34 @@
|
||||
void foo(int [5]);
|
||||
void fooc(int x[const 5]);
|
||||
void foos(int x[static 5]);
|
||||
void foov(int x[volatile 5]);
|
||||
void foor(int x[restrict 5]);
|
||||
void fooc(int [const 5]);
|
||||
void foos(int [static 5]);
|
||||
void foov(int [volatile 5]);
|
||||
void foor(int [restrict 5]);
|
||||
void fooc(int (* const x));
|
||||
void foos(int *x);
|
||||
void foov(int * volatile x);
|
||||
void foor(int * restrict x);
|
||||
void fooc(int x[volatile 5])
|
||||
{
|
||||
x[3] = 42;
|
||||
#ifdef INVALID
|
||||
x = 0;
|
||||
#endif
|
||||
}
|
||||
void foovm(int x[const *]);
|
||||
void foovm(int * const x);
|
||||
#ifdef INVALID
|
||||
void wrongc(int x[3][const 4]);
|
||||
void wrongvm(int x[static *]);
|
||||
void foovm(int x[const *])
|
||||
{
|
||||
x[2] = 1;
|
||||
}
|
||||
#endif
|
||||
int main()
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
0
src/userland/cli/third_party/tcc/tests/tests2/100_c99array-decls.expect
vendored
Normal file
0
src/userland/cli/third_party/tcc/tests/tests2/100_c99array-decls.expect
vendored
Normal file
359
src/userland/cli/third_party/tcc/tests/tests2/101_cleanup.c
vendored
Normal file
359
src/userland/cli/third_party/tcc/tests/tests2/101_cleanup.c
vendored
Normal file
@@ -0,0 +1,359 @@
|
||||
extern int printf(const char*, ...);
|
||||
static int glob_i = 0;
|
||||
|
||||
typedef struct { int a; int b; int c; int d; int e; int f; int g; int h; } tstl;
|
||||
typedef struct { int a; int b; int c; int d; } tsti;
|
||||
typedef struct { double a; double b; } tstd;
|
||||
typedef struct { long double a; } tstld;
|
||||
typedef struct { int a; double b; } tstm;
|
||||
typedef struct { float a; float b; float c; float d; } tstf;
|
||||
|
||||
void incr_glob_i(int *i)
|
||||
{
|
||||
glob_i += *i;
|
||||
*i = -1;
|
||||
}
|
||||
|
||||
#define INCR_GI { \
|
||||
int i __attribute__ ((__cleanup__(incr_glob_i))) = 1; \
|
||||
}
|
||||
|
||||
#define INCR_GI0 INCR_GI INCR_GI INCR_GI INCR_GI
|
||||
#define INCR_GI1 INCR_GI0 INCR_GI0 INCR_GI0 INCR_GI0
|
||||
#define INCR_GI2 INCR_GI1 INCR_GI1 INCR_GI1 INCR_GI1
|
||||
#define INCR_GI3 INCR_GI2 INCR_GI2 INCR_GI2 INCR_GI2
|
||||
#define INCR_GI4 INCR_GI3 INCR_GI3 INCR_GI3 INCR_GI3
|
||||
#define INCR_GI5 INCR_GI4 INCR_GI4 INCR_GI4 INCR_GI4
|
||||
#define INCR_GI6 INCR_GI5 INCR_GI5 INCR_GI5 INCR_GI5
|
||||
#define INCR_GI7 INCR_GI6 INCR_GI6 INCR_GI6 INCR_GI6
|
||||
|
||||
|
||||
void check2(char **hum);
|
||||
|
||||
void check(int *j)
|
||||
{
|
||||
char * __attribute__ ((cleanup(check2))) stop_that = "wololo";
|
||||
int chk = 0;
|
||||
|
||||
{
|
||||
char * __attribute__ ((cleanup(check2))) stop_that = "plop";
|
||||
|
||||
{
|
||||
non_plopage:
|
||||
printf("---- %d\n", chk);
|
||||
}
|
||||
if (!chk) {
|
||||
chk = 1;
|
||||
goto non_plopage;
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
char * __attribute__ ((cleanup(check2))) stop_that = "tata !";
|
||||
|
||||
goto out;
|
||||
stop_that = "titi";
|
||||
}
|
||||
again:
|
||||
chk = 2;
|
||||
{
|
||||
char * __attribute__ ((cleanup(check2))) cascade1 = "1";
|
||||
{
|
||||
char * __attribute__ ((cleanup(check2))) cascade2 = "2";
|
||||
{
|
||||
char * __attribute__ ((cleanup(check2))) cascade3 = "3";
|
||||
|
||||
goto out;
|
||||
cascade3 = "nope";
|
||||
}
|
||||
}
|
||||
}
|
||||
out:
|
||||
if (chk != 2)
|
||||
goto again;
|
||||
{
|
||||
{
|
||||
char * __attribute__ ((cleanup(check2))) out = "last goto out";
|
||||
++chk;
|
||||
if (chk != 3)
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
*j = -1;
|
||||
return;
|
||||
}
|
||||
|
||||
void check_oh_i(char *oh_i)
|
||||
{
|
||||
printf("c: %c\n", *oh_i);
|
||||
*oh_i = '0';
|
||||
}
|
||||
|
||||
void goto_hell(double *f)
|
||||
{
|
||||
printf("oo: %f\n", *f);
|
||||
*f = -1.0;
|
||||
}
|
||||
|
||||
char *test()
|
||||
{
|
||||
char *__attribute__ ((cleanup(check2))) str = "I don't think this should be print(but gcc got it wrong too)";
|
||||
|
||||
return str;
|
||||
}
|
||||
|
||||
void test_ret_subcall(char *that)
|
||||
{
|
||||
printf("should be print before\n");
|
||||
}
|
||||
|
||||
void test_ret()
|
||||
{
|
||||
char *__attribute__ ((cleanup(check2))) that = "that";
|
||||
return test_ret_subcall(that);
|
||||
}
|
||||
|
||||
void test_ret2()
|
||||
{
|
||||
char *__attribute__ ((cleanup(check2))) that = "-that";
|
||||
{
|
||||
char *__attribute__ ((cleanup(check2))) that = "this should appear only once";
|
||||
}
|
||||
{
|
||||
char *__attribute__ ((cleanup(check2))) that = "-that2";
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
void test2(void) {
|
||||
int chk = 0;
|
||||
again:
|
||||
if (!chk) {
|
||||
char * __attribute__ ((cleanup(check2))) stop_that = "test2";
|
||||
chk++;
|
||||
goto again;
|
||||
}
|
||||
}
|
||||
|
||||
int test3(void) {
|
||||
char * __attribute__ ((cleanup(check2))) stop_that = "three";
|
||||
int chk = 0;
|
||||
|
||||
if (chk) {
|
||||
{
|
||||
outside:
|
||||
{
|
||||
char * __attribute__ ((cleanup(check2))) stop_that = "two";
|
||||
printf("---- %d\n", chk);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!chk)
|
||||
{
|
||||
char * __attribute__ ((cleanup(check2))) stop_that = "one";
|
||||
|
||||
if (!chk) {
|
||||
chk = 1;
|
||||
goto outside;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
void cl(int *ip)
|
||||
{
|
||||
printf("%d\n", *ip);
|
||||
*ip = -1;
|
||||
}
|
||||
|
||||
void loop_cleanups(void)
|
||||
{
|
||||
__attribute__((cleanup(cl))) int l = 1000;
|
||||
|
||||
printf("-- loop 0 --\n");
|
||||
for ( __attribute__((cleanup(cl))) int i = 0; i < 10; ++i) {
|
||||
__attribute__((cleanup(cl))) int j = 100;
|
||||
}
|
||||
|
||||
printf("-- loop 1 --\n");
|
||||
for (__attribute__((cleanup(cl))) int i = 0; i < 10; ++i) {
|
||||
__attribute__((cleanup(cl))) int j = 200;
|
||||
continue;
|
||||
}
|
||||
|
||||
printf("-- loop 2 --\n");
|
||||
for (__attribute__((cleanup(cl))) int i = 0; i < 10; ++i) {
|
||||
__attribute__((cleanup(cl))) int j = 300;
|
||||
break;
|
||||
}
|
||||
|
||||
printf("-- loop 3 --\n");
|
||||
for (int i = 0; i < 2; ++i) {
|
||||
__attribute__((cleanup(cl))) int j = 400;
|
||||
switch (i) {
|
||||
case 0:
|
||||
continue;
|
||||
default:
|
||||
{
|
||||
__attribute__((cleanup(cl))) int jj = 500;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
printf("after break\n");
|
||||
}
|
||||
|
||||
void my_cleanup1(int *p) {
|
||||
printf("%d\n", *p);
|
||||
*p = 0x90;
|
||||
}
|
||||
|
||||
int test_cleanup1(void) {
|
||||
int __attribute__((cleanup(my_cleanup1))) n = 42;
|
||||
return n;
|
||||
}
|
||||
|
||||
void my_cleanup2(tstl *p) {
|
||||
printf("%d %d %d %d %d %d %d %d\n", p->a, p->b, p->c, p->d,
|
||||
p->e, p->f, p->g, p->h);
|
||||
p->a = 0x90; p->b = 0x91; p->c = 0x92; p->d = 0x93;
|
||||
p->e = 0x94; p->f = 0x95; p->g = 0x96; p->h = 0x97;
|
||||
}
|
||||
|
||||
tstl test_cleanup2(void) {
|
||||
tstl __attribute__((cleanup(my_cleanup2))) n;
|
||||
n.a = 42; n.b = 43; n.c = 44; n.d = 45;
|
||||
n.e = 46; n.f = 47; n.g = 48; n.h = 49;
|
||||
return n;
|
||||
}
|
||||
|
||||
void my_cleanup3(tsti *p) {
|
||||
printf("%d %d %d %d\n", p->a, p->b, p->c, p->d);
|
||||
p->a = 0x90; p->b = 0x91; p->c = 0x92; p->d = 0x93;
|
||||
}
|
||||
|
||||
tsti test_cleanup3(void) {
|
||||
tsti __attribute__((cleanup(my_cleanup3))) n;
|
||||
n.a = 42; n.b = 43; n.c = 44; n.d = 45;
|
||||
return n;
|
||||
}
|
||||
|
||||
void my_cleanup4(tstd *p) {
|
||||
printf("%g %g\n", p->a, p->b);
|
||||
p->a = 90.0; p->b = 91.0;
|
||||
}
|
||||
|
||||
tstd test_cleanup4(void) {
|
||||
tstd __attribute__((cleanup(my_cleanup4))) n;
|
||||
n.a = 42.0; n.b = 43.0;
|
||||
return n;
|
||||
}
|
||||
|
||||
void my_cleanup5(tstld *p) {
|
||||
printf("%Lf\n", p->a);
|
||||
p->a = 90.0;
|
||||
}
|
||||
|
||||
tstld test_cleanup5(void) {
|
||||
tstld __attribute__((cleanup(my_cleanup5))) n;
|
||||
n.a = 42.0;
|
||||
return n;
|
||||
}
|
||||
|
||||
void my_cleanup6(tstm *p) {
|
||||
printf("%d %g\n", p->a, p->b);
|
||||
p->a = 90;
|
||||
p->b = 91.0;
|
||||
}
|
||||
|
||||
tstm test_cleanup6(void) {
|
||||
tstm __attribute__((cleanup(my_cleanup6))) n;
|
||||
n.a = 42;
|
||||
n.b = 43.0;
|
||||
return n;
|
||||
}
|
||||
|
||||
void my_cleanup7(tstf *p) {
|
||||
printf("%f %f %f %f\n", p->a, p->b, p->c, p->d);
|
||||
p->a = 0x90; p->b = 0x91; p->c = 0x92; p->d = 0x93;
|
||||
}
|
||||
|
||||
tstf test_cleanup7(void) {
|
||||
tstf __attribute__((cleanup(my_cleanup7))) n;
|
||||
n.a = 42; n.b = 43; n.c = 44; n.d = 45;
|
||||
return n;
|
||||
}
|
||||
|
||||
void my_cleanup8(int **p) {
|
||||
**p = 0x90;
|
||||
}
|
||||
|
||||
int test_cleanup8(void) {
|
||||
int n = 42;
|
||||
int __attribute__((cleanup(my_cleanup8))) *p = &n;
|
||||
return n;
|
||||
}
|
||||
|
||||
static void my_cleanupe(int *p) {
|
||||
*p = 0x90;
|
||||
}
|
||||
|
||||
int main()
|
||||
{
|
||||
int i __attribute__ ((__cleanup__(check))) = 0, not_i;
|
||||
int chk = 0;
|
||||
(void)not_i;
|
||||
tstl tl;
|
||||
tsti ti;
|
||||
tstd td;
|
||||
tstld tld;
|
||||
tstm tm;
|
||||
tstf tf;
|
||||
|
||||
{
|
||||
__attribute__ ((__cleanup__(check_oh_i))) char oh_i = 'o', o = 'a';
|
||||
}
|
||||
|
||||
INCR_GI7;
|
||||
printf("glob_i: %d\n", glob_i);
|
||||
naaaaaaaa:
|
||||
if (!chk) {
|
||||
__attribute__ ((__cleanup__(check_oh_i))) char oh_i = 'f';
|
||||
double __attribute__ ((__cleanup__(goto_hell))) f = 2.6;
|
||||
|
||||
chk = 1;
|
||||
goto naaaaaaaa;
|
||||
}
|
||||
i = 105;
|
||||
printf("because what if free was call inside cleanup function %s\n", test());
|
||||
test_ret();
|
||||
test_ret2();
|
||||
test2();
|
||||
test3();
|
||||
loop_cleanups();
|
||||
printf("%d\n", test_cleanup1());
|
||||
tl = test_cleanup2();
|
||||
printf("%d %d %d %d %d %d %d %d\n", tl.a, tl.b, tl.c, tl.d,
|
||||
tl.e, tl.f, tl.g, tl.h);
|
||||
ti = test_cleanup3();
|
||||
printf("%d %d %d %d\n", ti.a, ti.b, ti.c, ti.d);
|
||||
td = test_cleanup4();
|
||||
printf("%g %g\n", td.a, td.b);
|
||||
tld = test_cleanup5();
|
||||
printf("%Lf\n", tld.a);
|
||||
tm = test_cleanup6();
|
||||
printf("%d %g\n", tm.a, tm.b);
|
||||
tf = test_cleanup7();
|
||||
printf("%f %f %f %f\n", tf.a, tf.b, tf.c, tf.d);
|
||||
printf("%d\n", test_cleanup8());
|
||||
printf("%d\n", ({
|
||||
int __attribute__ ((cleanup(my_cleanupe))) n = 42;
|
||||
n; }));
|
||||
return i;
|
||||
}
|
||||
|
||||
void check2(char **hum)
|
||||
{
|
||||
printf("str: %s\n", *hum);
|
||||
*hum = "fail";
|
||||
}
|
||||
75
src/userland/cli/third_party/tcc/tests/tests2/101_cleanup.expect
vendored
Normal file
75
src/userland/cli/third_party/tcc/tests/tests2/101_cleanup.expect
vendored
Normal file
@@ -0,0 +1,75 @@
|
||||
c: a
|
||||
c: o
|
||||
glob_i: 65536
|
||||
oo: 2.600000
|
||||
c: f
|
||||
str: I don't think this should be print(but gcc got it wrong too)
|
||||
because what if free was call inside cleanup function I don't think this should be print(but gcc got it wrong too)
|
||||
should be print before
|
||||
str: that
|
||||
str: this should appear only once
|
||||
str: -that2
|
||||
str: -that
|
||||
str: test2
|
||||
str: one
|
||||
---- 1
|
||||
str: two
|
||||
str: three
|
||||
-- loop 0 --
|
||||
100
|
||||
100
|
||||
100
|
||||
100
|
||||
100
|
||||
100
|
||||
100
|
||||
100
|
||||
100
|
||||
100
|
||||
10
|
||||
-- loop 1 --
|
||||
200
|
||||
200
|
||||
200
|
||||
200
|
||||
200
|
||||
200
|
||||
200
|
||||
200
|
||||
200
|
||||
200
|
||||
10
|
||||
-- loop 2 --
|
||||
300
|
||||
0
|
||||
-- loop 3 --
|
||||
400
|
||||
500
|
||||
400
|
||||
after break
|
||||
1000
|
||||
42
|
||||
42
|
||||
42 43 44 45 46 47 48 49
|
||||
42 43 44 45 46 47 48 49
|
||||
42 43 44 45
|
||||
42 43 44 45
|
||||
42 43
|
||||
42 43
|
||||
42.000000
|
||||
42.000000
|
||||
42 43
|
||||
42 43
|
||||
42.000000 43.000000 44.000000 45.000000
|
||||
42.000000 43.000000 44.000000 45.000000
|
||||
42
|
||||
42
|
||||
---- 0
|
||||
---- 1
|
||||
str: plop
|
||||
str: tata !
|
||||
str: 3
|
||||
str: 2
|
||||
str: 1
|
||||
str: last goto out
|
||||
str: wololo
|
||||
29
src/userland/cli/third_party/tcc/tests/tests2/102_alignas.c
vendored
Normal file
29
src/userland/cli/third_party/tcc/tests/tests2/102_alignas.c
vendored
Normal file
@@ -0,0 +1,29 @@
|
||||
_Alignas(16) int i1;
|
||||
int _Alignas(16) i2;
|
||||
void _Alignas(16) *p2;
|
||||
_Alignas(16) i3;
|
||||
int _Alignas(double) i4;
|
||||
int _Alignas(int) i5;
|
||||
#if 0
|
||||
/* The following are currently wrongly accepted by TCC but really shouldn't. */
|
||||
int _Alignas(int _Alignas(16)) i6; //wrong, 'int _Alignas(16)' is no type-name
|
||||
typedef int _Alignas(16) int16aligned_t; //wrong, _Alignas invalid on typedef
|
||||
int16aligned_t i7;
|
||||
#endif
|
||||
/* i8 should get an alignment of 16, because unlike _Alignas the
|
||||
corresponding attribute _does_ apply to type-name, though not in
|
||||
some clang versions. */
|
||||
int _Alignas(int __attribute__((aligned(16)))) i8;
|
||||
extern int printf(const char*, ...);
|
||||
#ifdef _MSC_VER
|
||||
#define alignof(x) (int)__alignof(x)
|
||||
#else
|
||||
#define alignof(x) (int)__alignof__(x)
|
||||
#endif
|
||||
int main()
|
||||
{
|
||||
printf("%d %d %d %d\n",
|
||||
alignof(i1) == 16, alignof(i4) == alignof(double),
|
||||
alignof(i5) == alignof(int) , alignof(i8) == 16);
|
||||
return 0;
|
||||
}
|
||||
2
src/userland/cli/third_party/tcc/tests/tests2/102_alignas.expect
vendored
Normal file
2
src/userland/cli/third_party/tcc/tests/tests2/102_alignas.expect
vendored
Normal file
@@ -0,0 +1,2 @@
|
||||
102_alignas.c:4: warning: type defaults to int
|
||||
1 1 1 1
|
||||
20
src/userland/cli/third_party/tcc/tests/tests2/103_implicit_memmove.c
vendored
Normal file
20
src/userland/cli/third_party/tcc/tests/tests2/103_implicit_memmove.c
vendored
Normal file
@@ -0,0 +1,20 @@
|
||||
/* Test that the memmove TCC is emitting for the struct copy
|
||||
and hence implicitely declares can be declared properly also
|
||||
later. */
|
||||
struct S { int a,b,c,d, e[1024];};
|
||||
int foo (struct S *a, struct S *b)
|
||||
{
|
||||
*a = *b;
|
||||
return 0;
|
||||
}
|
||||
|
||||
void *memmove(void*,const void*,__SIZE_TYPE__);
|
||||
void foo2 (struct S *a, struct S *b)
|
||||
{
|
||||
memmove(a, b, sizeof *a);
|
||||
}
|
||||
|
||||
int main()
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
0
src/userland/cli/third_party/tcc/tests/tests2/103_implicit_memmove.expect
vendored
Normal file
0
src/userland/cli/third_party/tcc/tests/tests2/103_implicit_memmove.expect
vendored
Normal file
54
src/userland/cli/third_party/tcc/tests/tests2/104+_inline.c
vendored
Normal file
54
src/userland/cli/third_party/tcc/tests/tests2/104+_inline.c
vendored
Normal file
@@ -0,0 +1,54 @@
|
||||
|
||||
#define GOT(f) \
|
||||
__attribute__((weak)) void f(void); \
|
||||
printf("%d %s\n", !!((__SIZE_TYPE__)f & ~0u), #f);
|
||||
|
||||
int printf(const char*, ...);
|
||||
|
||||
void check_exports()
|
||||
{
|
||||
// 0
|
||||
GOT(inline_inline_2decl_only)
|
||||
GOT(inline_inline_undeclared)
|
||||
GOT(inline_inline_predeclared)
|
||||
GOT(inline_inline_postdeclared)
|
||||
GOT(inline_inline_prepostdeclared)
|
||||
GOT(inline_inline_undeclared2)
|
||||
GOT(inline_inline_predeclared2)
|
||||
GOT(inline_inline_postdeclared2)
|
||||
GOT(inline_inline_prepostdeclared2)
|
||||
|
||||
// 1
|
||||
GOT(extern_extern_postdeclared)
|
||||
GOT(extern_extern_postdeclared2)
|
||||
GOT(extern_extern_predeclared)
|
||||
GOT(extern_extern_predeclared2)
|
||||
GOT(extern_extern_prepostdeclared)
|
||||
GOT(extern_extern_prepostdeclared2)
|
||||
GOT(extern_extern_undeclared)
|
||||
GOT(extern_extern_undeclared2)
|
||||
GOT(extern_postdeclared)
|
||||
GOT(extern_postdeclared2)
|
||||
GOT(extern_predeclared)
|
||||
GOT(extern_predeclared2)
|
||||
GOT(extern_prepostdeclared)
|
||||
GOT(extern_undeclared)
|
||||
GOT(extern_undeclared2)
|
||||
GOT(inst2_extern_inline_postdeclared)
|
||||
GOT(inst2_extern_inline_predeclared)
|
||||
GOT(inst3_extern_inline_predeclared)
|
||||
GOT(inst_extern_inline_postdeclared)
|
||||
GOT(inst_extern_inline_predeclared)
|
||||
GOT(main)
|
||||
GOT(noinst_extern_inline_func)
|
||||
GOT(noinst_extern_inline_postdeclared)
|
||||
GOT(noinst_extern_inline_postdeclared2)
|
||||
GOT(noinst_extern_inline_undeclared)
|
||||
|
||||
// 0
|
||||
GOT(noinst_static_inline_postdeclared)
|
||||
GOT(noinst2_static_inline_postdeclared)
|
||||
GOT(noinst_static_inline_predeclared)
|
||||
GOT(noinst2_static_inline_predeclared)
|
||||
GOT(static_func)
|
||||
}
|
||||
132
src/userland/cli/third_party/tcc/tests/tests2/104_inline.c
vendored
Normal file
132
src/userland/cli/third_party/tcc/tests/tests2/104_inline.c
vendored
Normal file
@@ -0,0 +1,132 @@
|
||||
inline void inline_inline_2decl_only(void);
|
||||
inline void inline_inline_2decl_only(void);
|
||||
|
||||
inline void inline_inline_undeclared(void){}
|
||||
|
||||
inline void inline_inline_predeclared(void);
|
||||
inline void inline_inline_predeclared(void){}
|
||||
|
||||
inline void inline_inline_postdeclared(void){}
|
||||
inline void inline_inline_postdeclared(void);
|
||||
|
||||
inline void inline_inline_prepostdeclared(void);
|
||||
inline void inline_inline_prepostdeclared(void){}
|
||||
inline void inline_inline_prepostdeclared(void);
|
||||
|
||||
inline void inline_inline_undeclared2(void){}
|
||||
|
||||
inline void inline_inline_predeclared2(void);
|
||||
inline void inline_inline_predeclared2(void);
|
||||
inline void inline_inline_predeclared2(void){}
|
||||
|
||||
inline void inline_inline_postdeclared2(void){}
|
||||
inline void inline_inline_postdeclared2(void);
|
||||
inline void inline_inline_postdeclared2(void);
|
||||
|
||||
inline void inline_inline_prepostdeclared2(void);
|
||||
inline void inline_inline_prepostdeclared2(void);
|
||||
inline void inline_inline_prepostdeclared2(void){}
|
||||
inline void inline_inline_prepostdeclared2(void);
|
||||
inline void inline_inline_prepostdeclared2(void);
|
||||
|
||||
extern void extern_extern_undeclared(void){}
|
||||
|
||||
extern void extern_extern_predeclared(void);
|
||||
extern void extern_extern_predeclared(void){}
|
||||
|
||||
extern void extern_extern_postdeclared(void){}
|
||||
extern void extern_extern_postdeclared(void);
|
||||
|
||||
extern void extern_extern_prepostdeclared(void);
|
||||
extern void extern_extern_prepostdeclared(void){}
|
||||
extern void extern_extern_prepostdeclared(void);
|
||||
|
||||
extern void extern_extern_undeclared2(void){}
|
||||
|
||||
extern void extern_extern_predeclared2(void);
|
||||
extern void extern_extern_predeclared2(void);
|
||||
extern void extern_extern_predeclared2(void){}
|
||||
|
||||
extern void extern_extern_postdeclared2(void){}
|
||||
extern void extern_extern_postdeclared2(void);
|
||||
extern void extern_extern_postdeclared2(void);
|
||||
|
||||
extern void extern_extern_prepostdeclared2(void);
|
||||
extern void extern_extern_prepostdeclared2(void);
|
||||
extern void extern_extern_prepostdeclared2(void){}
|
||||
extern void extern_extern_prepostdeclared2(void);
|
||||
extern void extern_extern_prepostdeclared2(void);
|
||||
|
||||
void extern_undeclared(void){}
|
||||
|
||||
void extern_predeclared(void);
|
||||
void extern_predeclared(void){}
|
||||
|
||||
void extern_postdeclared(void){}
|
||||
void extern_postdeclared(void);
|
||||
|
||||
void extern_prepostdeclared(void);
|
||||
void extern_prepostdeclared(void){}
|
||||
void extern_prepostdeclared(void);
|
||||
|
||||
void extern_undeclared2(void){}
|
||||
|
||||
void extern_predeclared2(void);
|
||||
void extern_predeclared2(void);
|
||||
void extern_predeclared2(void){}
|
||||
|
||||
void extern_postdeclared2(void){}
|
||||
void extern_postdeclared2(void);
|
||||
void extern_postdeclared2(void);
|
||||
|
||||
|
||||
extern inline void noinst_extern_inline_undeclared(void){}
|
||||
|
||||
extern inline void noinst_extern_inline_postdeclared(void){}
|
||||
inline void noinst_extern_inline_postdeclared(void);
|
||||
|
||||
extern inline void noinst_extern_inline_postdeclared2(void){}
|
||||
inline void noinst_extern_inline_postdeclared2(void);
|
||||
inline void noinst_extern_inline_postdeclared2(void);
|
||||
|
||||
extern inline void inst_extern_inline_postdeclared(void){}
|
||||
extern inline void inst_extern_inline_postdeclared(void);
|
||||
inline void inst2_extern_inline_postdeclared(void){}
|
||||
void inst2_extern_inline_postdeclared(void);
|
||||
|
||||
void inst_extern_inline_predeclared(void);
|
||||
extern inline void inst_extern_inline_predeclared(void){}
|
||||
void inst2_extern_inline_predeclared(void);
|
||||
inline void inst2_extern_inline_predeclared(void){}
|
||||
extern inline void inst3_extern_inline_predeclared(void);
|
||||
inline void inst3_extern_inline_predeclared(void){}
|
||||
|
||||
static inline void noinst_static_inline_postdeclared(void){}
|
||||
static inline void noinst_static_inline_postdeclared(void);
|
||||
static inline void noinst2_static_inline_postdeclared(void){}
|
||||
static void noinst2_static_inline_postdeclared(void);
|
||||
|
||||
static void noinst_static_inline_predeclared(void);
|
||||
static inline void noinst_static_inline_predeclared(void){}
|
||||
static void noinst2_static_inline_predeclared(void);
|
||||
static inline void noinst2_static_inline_predeclared(void){}
|
||||
|
||||
static void static_func(void);
|
||||
void static_func(void) { }
|
||||
|
||||
inline void noinst_extern_inline_func(void);
|
||||
void noinst_extern_inline_func(void) { }
|
||||
|
||||
int main()
|
||||
{
|
||||
inline_inline_undeclared(); inline_inline_predeclared(); inline_inline_postdeclared();
|
||||
inline_inline_undeclared2(); inline_inline_predeclared2(); inline_inline_postdeclared2();
|
||||
noinst_static_inline_predeclared();
|
||||
noinst2_static_inline_predeclared();
|
||||
noinst_static_inline_predeclared();
|
||||
noinst2_static_inline_predeclared();
|
||||
|
||||
void check_exports();
|
||||
check_exports();
|
||||
return 0;
|
||||
}
|
||||
39
src/userland/cli/third_party/tcc/tests/tests2/104_inline.expect
vendored
Normal file
39
src/userland/cli/third_party/tcc/tests/tests2/104_inline.expect
vendored
Normal file
@@ -0,0 +1,39 @@
|
||||
0 inline_inline_2decl_only
|
||||
0 inline_inline_undeclared
|
||||
0 inline_inline_predeclared
|
||||
0 inline_inline_postdeclared
|
||||
0 inline_inline_prepostdeclared
|
||||
0 inline_inline_undeclared2
|
||||
0 inline_inline_predeclared2
|
||||
0 inline_inline_postdeclared2
|
||||
0 inline_inline_prepostdeclared2
|
||||
1 extern_extern_postdeclared
|
||||
1 extern_extern_postdeclared2
|
||||
1 extern_extern_predeclared
|
||||
1 extern_extern_predeclared2
|
||||
1 extern_extern_prepostdeclared
|
||||
1 extern_extern_prepostdeclared2
|
||||
1 extern_extern_undeclared
|
||||
1 extern_extern_undeclared2
|
||||
1 extern_postdeclared
|
||||
1 extern_postdeclared2
|
||||
1 extern_predeclared
|
||||
1 extern_predeclared2
|
||||
1 extern_prepostdeclared
|
||||
1 extern_undeclared
|
||||
1 extern_undeclared2
|
||||
1 inst2_extern_inline_postdeclared
|
||||
1 inst2_extern_inline_predeclared
|
||||
1 inst3_extern_inline_predeclared
|
||||
1 inst_extern_inline_postdeclared
|
||||
1 inst_extern_inline_predeclared
|
||||
1 main
|
||||
1 noinst_extern_inline_func
|
||||
1 noinst_extern_inline_postdeclared
|
||||
1 noinst_extern_inline_postdeclared2
|
||||
1 noinst_extern_inline_undeclared
|
||||
0 noinst_static_inline_postdeclared
|
||||
0 noinst2_static_inline_postdeclared
|
||||
0 noinst_static_inline_predeclared
|
||||
0 noinst2_static_inline_predeclared
|
||||
0 static_func
|
||||
12
src/userland/cli/third_party/tcc/tests/tests2/105_local_extern.c
vendored
Normal file
12
src/userland/cli/third_party/tcc/tests/tests2/105_local_extern.c
vendored
Normal file
@@ -0,0 +1,12 @@
|
||||
extern int printf(const char *, ...);
|
||||
void f(void);
|
||||
void bar(void) { void f(void); f(); }
|
||||
void foo(void) { extern void f(void); f(); }
|
||||
void f(void) { printf("f\n"); }
|
||||
|
||||
int main()
|
||||
{
|
||||
bar();
|
||||
foo();
|
||||
return 0;
|
||||
}
|
||||
2
src/userland/cli/third_party/tcc/tests/tests2/105_local_extern.expect
vendored
Normal file
2
src/userland/cli/third_party/tcc/tests/tests2/105_local_extern.expect
vendored
Normal file
@@ -0,0 +1,2 @@
|
||||
f
|
||||
f
|
||||
18
src/userland/cli/third_party/tcc/tests/tests2/106_versym.c
vendored
Normal file
18
src/userland/cli/third_party/tcc/tests/tests2/106_versym.c
vendored
Normal file
@@ -0,0 +1,18 @@
|
||||
#include <stdio.h>
|
||||
#include <pthread.h>
|
||||
#include <errno.h>
|
||||
|
||||
int
|
||||
main(void)
|
||||
{
|
||||
int ret;
|
||||
pthread_condattr_t attr;
|
||||
pthread_cond_t condition;
|
||||
|
||||
/* This test fails if symbol versioning does not work */
|
||||
pthread_condattr_init (&attr);
|
||||
pthread_condattr_setpshared (&attr, PTHREAD_PROCESS_SHARED);
|
||||
printf ("%s\n", pthread_cond_init (&condition, &attr) ? "fail":"ok");
|
||||
pthread_condattr_destroy (&attr);
|
||||
return 0;
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user