Changes in / [a505021:8c50aed]
- Files:
-
- 20 added
- 47 deleted
- 87 edited
-
Jenkinsfile (modified) (1 diff)
-
benchmark/Makefile.am (modified) (9 diffs)
-
benchmark/Makefile.in (modified) (10 diffs)
-
benchmark/baselines/x64/schedint.csv (deleted)
-
benchmark/baselines/x64/signal.csv (added)
-
benchmark/baselines/x86/schedint.csv (deleted)
-
benchmark/baselines/x86/signal.csv (added)
-
doc/papers/ibm_CASCON19/ThreadingModels.fig (deleted)
-
doc/papers/ibm_CASCON19/ThreadingModels.png (deleted)
-
doc/papers/ibm_CASCON19/ThreadingModels.svg (deleted)
-
doc/papers/ibm_CASCON19/abstract.txt (deleted)
-
doc/papers/ibm_CASCON19/client.cfa (deleted)
-
doc/papers/ibm_CASCON19/server.cfa (deleted)
-
doc/papers/ibm_CASCON19/slides.pdf (deleted)
-
doc/theses/thierry_delisle_PhD/.gitignore (deleted)
-
doc/theses/thierry_delisle_PhD/code/Makefile (deleted)
-
doc/theses/thierry_delisle_PhD/code/bts_test.cpp (deleted)
-
doc/theses/thierry_delisle_PhD/code/randbit.cpp (deleted)
-
doc/theses/thierry_delisle_PhD/code/relaxed_list.cpp (modified) (7 diffs)
-
doc/theses/thierry_delisle_PhD/code/relaxed_list.hpp (modified) (16 diffs)
-
doc/theses/thierry_delisle_PhD/code/relaxed_list_layout.cpp (deleted)
-
doc/theses/thierry_delisle_PhD/code/scale.sh (deleted)
-
doc/theses/thierry_delisle_PhD/code/utils.hpp (modified) (4 diffs)
-
doc/theses/thierry_delisle_PhD/comp_II/Makefile (deleted)
-
doc/theses/thierry_delisle_PhD/comp_II/comp_II.tex (deleted)
-
doc/theses/thierry_delisle_PhD/comp_II/comp_II_too_big.tex (deleted)
-
doc/theses/thierry_delisle_PhD/comp_II/glossary.tex (deleted)
-
doc/theses/thierry_delisle_PhD/comp_II/local.bib (deleted)
-
driver/cfa.cc (modified) (1 diff)
-
libcfa/prelude/Makefile.am (modified) (2 diffs)
-
libcfa/prelude/Makefile.in (modified) (4 diffs)
-
libcfa/prelude/extras.regx (modified) (1 diff)
-
libcfa/prelude/extras.regx2 (deleted)
-
libcfa/prelude/prototypes.awk (modified) (4 diffs)
-
libcfa/src/assert.cfa (modified) (3 diffs)
-
libcfa/src/bits/debug.cfa (modified) (2 diffs)
-
libcfa/src/bits/debug.hfa (modified) (3 diffs)
-
libcfa/src/bits/locks.hfa (modified) (2 diffs)
-
libcfa/src/concurrency/coroutine.cfa (modified) (2 diffs)
-
libcfa/src/concurrency/coroutine.hfa (modified) (3 diffs)
-
libcfa/src/concurrency/kernel.cfa (modified) (5 diffs)
-
libcfa/src/concurrency/kernel.hfa (modified) (3 diffs)
-
libcfa/src/exception.c (modified) (4 diffs)
-
libcfa/src/fstream.cfa (modified) (12 diffs)
-
libcfa/src/fstream.hfa (modified) (5 diffs)
-
libcfa/src/gmp.hfa (modified) (5 diffs)
-
libcfa/src/heap.cfa (modified) (3 diffs)
-
libcfa/src/interpose.cfa (modified) (8 diffs)
-
libcfa/src/iostream.cfa (modified) (43 diffs)
-
libcfa/src/iostream.hfa (modified) (10 diffs)
-
libcfa/src/math.hfa (modified) (2 diffs)
-
libcfa/src/rational.cfa (modified) (2 diffs)
-
libcfa/src/startup.cfa (modified) (2 diffs)
-
libcfa/src/stdhdr/assert.h (modified) (2 diffs)
-
libcfa/src/stdhdr/bfdlink.h (modified) (1 diff)
-
libcfa/src/stdhdr/hwloc.h (modified) (1 diff)
-
libcfa/src/stdhdr/krb5.h (modified) (1 diff)
-
libcfa/src/stdhdr/math.h (modified) (1 diff)
-
libcfa/src/stdhdr/sys/ucontext.h (modified) (1 diff)
-
libcfa/src/stdlib.cfa (modified) (4 diffs)
-
libcfa/src/stdlib.hfa (modified) (2 diffs)
-
libcfa/src/time.cfa (modified) (2 diffs)
-
libcfa/src/time.hfa (modified) (2 diffs)
-
longrun_tests/Makefile.in (modified) (1 diff)
-
src/CodeGen/CodeGenerator.cc (modified) (24 diffs)
-
src/CodeGen/CodeGenerator.h (modified) (5 diffs)
-
src/CodeGen/FixMain.h (modified) (2 diffs)
-
src/CodeGen/GenType.h (modified) (2 diffs)
-
src/CodeGen/Generate.cc (modified) (2 diffs)
-
src/CodeGen/OperatorTable.cc (modified) (3 diffs)
-
src/CodeGen/OperatorTable.h (modified) (3 diffs)
-
src/CodeGen/Options.h (modified) (1 diff)
-
src/CodeTools/ResolvProtoDump.cc (modified) (2 diffs)
-
src/Common/PassVisitor.impl.h (modified) (3 diffs)
-
src/Common/SemanticError.h (modified) (2 diffs)
-
src/Common/utility.h (modified) (3 diffs)
-
src/ControlStruct/Mutate.cc (modified) (2 diffs)
-
src/InitTweak/FixInit.cc (modified) (2 diffs)
-
src/InitTweak/FixInit.h (modified) (2 diffs)
-
src/MakeLibCfa.cc (modified) (3 diffs)
-
src/Parser/ParseNode.h (modified) (2 diffs)
-
src/Parser/ParserTypes.h (modified) (2 diffs)
-
src/Parser/TypedefTable.cc (modified) (2 diffs)
-
src/Parser/TypedefTable.h (modified) (2 diffs)
-
src/Parser/lex.ll (modified) (4 diffs)
-
src/Parser/parser.yy (modified) (4 diffs)
-
src/ResolvExpr/Resolver.cc (modified) (3 diffs)
-
src/SymTab/Demangle.cc (modified) (4 diffs)
-
src/SymTab/Mangler.cc (modified) (3 diffs)
-
src/SymTab/Validate.cc (modified) (3 diffs)
-
src/SynTree/Attribute.h (modified) (2 diffs)
-
src/cfa.make (modified) (1 diff)
-
src/main.cc (modified) (5 diffs)
-
tests/.expect/alloc-ERROR.txt (modified) (4 diffs)
-
tests/.expect/alloc.txt (modified) (1 diff)
-
tests/.expect/completeTypeError.txt (added)
-
tests/.expect/declarationErrors.txt (added)
-
tests/.expect/nested-types-ERR1.txt (modified) (1 diff)
-
tests/.expect/nested-types-ERR2.txt (modified) (1 diff)
-
tests/.expect/rational.txt (modified) (1 diff)
-
tests/.expect/scopeErrors.txt (added)
-
tests/.expect/userLiterals.txt (deleted)
-
tests/Makefile.in (modified) (1 diff)
-
tests/abort.cfa (added)
-
tests/alloc.cfa (modified) (2 diffs)
-
tests/completeTypeError.cfa (added)
-
tests/concurrent/examples/quickSort.cfa (modified) (3 diffs)
-
tests/context.cfa (added)
-
tests/declarationErrors.cfa (added)
-
tests/errors/.expect/completeType.txt (deleted)
-
tests/errors/.expect/declaration.txt (deleted)
-
tests/errors/.expect/scope.txt (deleted)
-
tests/errors/.expect/signature.txt (deleted)
-
tests/errors/completeType.cfa (deleted)
-
tests/errors/declaration.cfa (deleted)
-
tests/errors/scope.cfa (deleted)
-
tests/errors/signature.cfa (deleted)
-
tests/exceptions/.expect/except-0.txt (deleted)
-
tests/exceptions/.expect/except-1.txt (deleted)
-
tests/exceptions/.expect/except-2.txt (deleted)
-
tests/exceptions/.expect/except-3.txt (deleted)
-
tests/exceptions/except-0.cfa (modified) (2 diffs)
-
tests/exceptions/except-2.cfa (modified) (3 diffs)
-
tests/labelledExit.cfa (modified) (2 diffs)
-
tests/linking/.expect/nostdlib.txt (deleted)
-
tests/linking/nostdlib.cfa (deleted)
-
tests/namedParmArg.cfa (added)
-
tests/nested-types.cfa (modified) (2 diffs)
-
tests/occursError.cfa (added)
-
tests/pybin/tools.py (modified) (2 diffs)
-
tests/quotedKeyword.cfa (modified) (2 diffs)
-
tests/rational.cfa (modified) (5 diffs)
-
tests/scope.cfa (added)
-
tests/scopeErrors.cfa (added)
-
tests/structMember.cfa (added)
-
tests/subrange.cfa (added)
-
tests/test.py (modified) (1 diff)
-
tests/typeGenerator.cfa (added)
-
tests/typedef.cfa (added)
-
tests/typedefDeclarator.cfa (added)
-
tests/userLiterals.cfa (modified) (6 diffs)
-
tests/virtualCast.cfa (added)
-
tests/withStatement.cfa (added)
-
tests/zombies/context.cfa (deleted)
-
tests/zombies/namedParmArg.cfa (deleted)
-
tests/zombies/occursError.cfa (deleted)
-
tests/zombies/scope.cfa (deleted)
-
tests/zombies/structMember.cfa (deleted)
-
tests/zombies/subrange.cfa (deleted)
-
tests/zombies/typeGenerator.cfa (deleted)
-
tests/zombies/typedef.cfa (deleted)
-
tests/zombies/typedefDeclarator.cfa (deleted)
-
tests/zombies/virtualCast.cfa (deleted)
-
tests/zombies/withStatement.cfa (deleted)
Legend:
- Unmodified
- Added
- Removed
-
Jenkinsfile
ra505021 r8c50aed 215 215 216 216 //Then publish the results 217 do_plot(Settings.RunBenchmark && Settings.Publish, 'compile' , groupCompile , false, 'Compilation')218 do_plot(Settings.RunBenchmark && Settings.Publish, 'compile.diff' , groupCompile , true , 'Compilation (relative)')219 do_plot(Settings.RunBenchmark && Settings.Publish, 'ctxswitch' , groupConcurrency, false, 'Context Switching')220 do_plot(Settings.RunBenchmark && Settings.Publish, 'ctxswitch.diff' , groupConcurrency, true , 'Context Switching (relative)')221 do_plot(Settings.RunBenchmark && Settings.Publish, 'mutex' , groupConcurrency, false, 'Mutual Exclusion')222 do_plot(Settings.RunBenchmark && Settings.Publish, 'mutex.diff' , groupConcurrency, true , 'Mutual Exclusion (relative)')223 do_plot(Settings.RunBenchmark && Settings.Publish, 's cheduling', groupConcurrency, false, 'Internal and External Scheduling')224 do_plot(Settings.RunBenchmark && Settings.Publish, 's cheduling.diff', groupConcurrency, true , 'Internal and External Scheduling (relative)')217 do_plot(Settings.RunBenchmark && Settings.Publish, 'compile' , groupCompile , false, 'Compilation') 218 do_plot(Settings.RunBenchmark && Settings.Publish, 'compile.diff' , groupCompile , true , 'Compilation (relative)') 219 do_plot(Settings.RunBenchmark && Settings.Publish, 'ctxswitch' , groupConcurrency, false, 'Context Switching') 220 do_plot(Settings.RunBenchmark && Settings.Publish, 'ctxswitch.diff', groupConcurrency, true , 'Context Switching (relative)') 221 do_plot(Settings.RunBenchmark && Settings.Publish, 'mutex' , groupConcurrency, false, 'Mutual Exclusion') 222 do_plot(Settings.RunBenchmark && Settings.Publish, 'mutex.diff' , groupConcurrency, true , 'Mutual Exclusion (relative)') 223 do_plot(Settings.RunBenchmark && Settings.Publish, 'signal' , groupConcurrency, false, 'Internal and External Scheduling') 224 do_plot(Settings.RunBenchmark && Settings.Publish, 'signal.diff' , groupConcurrency, true , 'Internal and External Scheduling (relative)') 225 225 } 226 226 } -
benchmark/Makefile.am
ra505021 r8c50aed 30 30 BENCH_V_UPP = $(__bench_v_UPP_$(__quiet)) 31 31 BENCH_V_GOC = $(__bench_v_GOC_$(__quiet)) 32 BENCH_V_PY = $(__bench_v_PY_$(__quiet))33 32 BENCH_V_RUSTC = $(__bench_v_RUSTC_$(__quiet)) 34 33 BENCH_V_NODEJS = $(__bench_v_NODEJS_$(__quiet)) … … 48 47 __bench_v_UPP_verbose = $(AM_V_UPP) 49 48 __bench_v_GOC_verbose = $(AM_V_GOC) 50 __bench_v_PY_verbose = $(AM_V_PY) 51 __bench_v_RUSTC_verbose = $(AM_V_RUST) 49 __bench_v_RUSTC_verbose = $(AM_V_RUSTC) 52 50 __bench_v_NODEJS_verbose = $(AM_V_NODEJS) 53 51 __bench_v_JAVAC_verbose = $(AM_V_JAVAC) … … 74 72 echo "int main() { return 0; }" > ${@} 75 73 76 .SILENT: # do not print recipe 74 #.SILENT: # do not print recipe 75 .ONESHELL: # use one shell to execute recipe 77 76 .NOTPARALLEL: 78 .PHONY: jenkins cleancsv77 .PHONY: compile.csv basic.csv ctxswitch.csv mutex.csv schedint.csv 79 78 80 79 ## ========================================================================================================= … … 143 142 FIX_NEW_LINES = cat $@ | tr "\n" "\t" | sed -r 's/\t,/,/' | tr "\t" "\n" > $@ 144 143 145 cleancsv: 146 rm -f compile.csv basic.csv ctxswitch.csv mutex.csv scheduling.csv 147 148 jenkins$(EXEEXT): cleancsv 144 jenkins$(EXEEXT): 149 145 @DOifskipcompile@ 150 146 +make compile.csv 151 147 -+make compile.diff.csv 152 148 @DOendif@ 149 +make basic.csv 150 -+make basic.diff.csv 153 151 +make ctxswitch.csv 154 152 -+make ctxswitch.diff.csv 155 153 +make mutex.csv 156 154 -+make mutex.diff.csv 157 +make sched uling.csv158 -+make sched uling.diff.csv155 +make schedint.csv 156 -+make schedint.diff.csv 159 157 @DOifskipcompile@ 160 158 cat compile.csv 161 159 -cat compile.diff.csv 162 160 @DOendif@ 161 cat basic.csv 162 -cat basic.diff.csv 163 163 cat ctxswitch.csv 164 164 -cat ctxswitch.diff.csv 165 165 cat mutex.csv 166 166 -cat mutex.diff.csv 167 cat sched uling.csv168 -cat sched uling.diff.csv167 cat schedint.csv 168 -cat schedint.diff.csv 169 169 170 170 compile.csv: 171 echo "building $@"172 171 echo "array,attributes,empty,expression,io,monitor,operators,typeof" > $@ 173 172 +make TIME_FORMAT='%e,' PRINT_FORMAT='' compile-array.make >> $@ … … 181 180 $(srcdir)/fixcsv.sh $@ 182 181 182 basic.csv: 183 echo "generator,coroutine,thread" > $@ 184 +make basic-cfa_generator.runquiet >> $@ && echo -n ',' >> $@ 185 +make basic-cfa_coroutine.runquiet >> $@ && echo -n ',' >> $@ 186 +make basic-cfa_thread.runquiet >> $@ 187 $(srcdir)/fixcsv.sh $@ 188 183 189 ctxswitch.csv: 184 echo "building $@"185 190 echo "generator,coroutine,thread" > $@ 186 191 +make ctxswitch-cfa_generator.runquiet >> $@ && echo -n ',' >> $@ … … 190 195 191 196 mutex.csv: 192 echo "building $@"193 197 echo "1-monitor,2-monitor" > $@ 194 198 +make mutex-cfa1.runquiet >> $@ && echo -n ',' >> $@ … … 196 200 $(srcdir)/fixcsv.sh $@ 197 201 198 scheduling.csv: 199 echo "building $@" 202 schedint.csv: 200 203 echo "schedint-1,schedint-2,schedext-1,schedext-2" > $@ 201 204 +make schedint-cfa1.runquiet >> $@ && echo -n ',' >> $@ … … 286 289 287 290 ctxswitch-python_coroutine$(EXEEXT): 288 $(BENCH_V_PY)echo "#!/bin/sh" > a.out291 echo "#!/bin/sh" > a.out 289 292 echo "python3.7 $(srcdir)/ctxswitch/python_cor.py" >> a.out 290 293 chmod a+x a.out 291 294 292 295 ctxswitch-nodejs_coroutine$(EXEEXT): 293 $(BENCH_V_NODEJS)echo "#!/bin/sh" > a.out296 echo "#!/bin/sh" > a.out 294 297 echo "nodejs $(srcdir)/ctxswitch/node_cor.js" >> a.out 295 298 chmod a+x a.out 296 299 297 300 ctxswitch-nodejs_await$(EXEEXT): 298 $(BENCH_V_NODEJS)echo "#!/bin/sh" > a.out301 echo "#!/bin/sh" > a.out 299 302 echo "nodejs $(srcdir)/ctxswitch/node_await.js" >> a.out 300 303 chmod a+x a.out … … 449 452 450 453 creation-python_coroutine$(EXEEXT): 451 $(BENCH_V_PY)echo "#!/bin/sh" > a.out454 echo "#!/bin/sh" > a.out 452 455 echo "python3.7 $(srcdir)/creation/python_cor.py" >> a.out 453 456 chmod a+x a.out 454 457 455 458 creation-nodejs_coroutine$(EXEEXT): 456 $(BENCH_V_NODEJS)echo "#!/bin/sh" > a.out459 echo "#!/bin/sh" > a.out 457 460 echo "nodejs $(srcdir)/creation/node_cor.js" >> a.out 458 461 chmod a+x a.out -
benchmark/Makefile.in
ra505021 r8c50aed 368 368 am__v_GOC_0 = @echo " GOC " $@; 369 369 am__v_GOC_1 = 370 AM_V_PY = $(am__v_PY_@AM_V@)371 am__v_PY_ = $(am__v_PY_@AM_DEFAULT_V@)372 am__v_PY_0 = @echo " PYTHON " $@;373 am__v_PY_1 =374 370 AM_V_RUST = $(am__v_RUST_@AM_V@) 375 371 am__v_RUST_ = $(am__v_RUST_@AM_DEFAULT_V@) 376 am__v_RUST_0 = @echo " RUST " $@;372 am__v_RUST_0 = @echo " RUST " $@; 377 373 am__v_RUST_1 = 378 374 AM_V_NODEJS = $(am__v_NODEJS_@AM_V@) 379 375 am__v_NODEJS_ = $(am__v_NODEJS_@AM_DEFAULT_V@) 380 am__v_NODEJS_0 = @echo " NODEJS " $@;376 am__v_NODEJS_0 = @echo " NODEJS " $@; 381 377 am__v_NODEJS_1 = 382 378 AM_V_JAVAC = $(am__v_JAVAC_@AM_V@) … … 394 390 BENCH_V_UPP = $(__bench_v_UPP_$(__quiet)) 395 391 BENCH_V_GOC = $(__bench_v_GOC_$(__quiet)) 396 BENCH_V_PY = $(__bench_v_PY_$(__quiet))397 392 BENCH_V_RUSTC = $(__bench_v_RUSTC_$(__quiet)) 398 393 BENCH_V_NODEJS = $(__bench_v_NODEJS_$(__quiet)) … … 411 406 __bench_v_UPP_verbose = $(AM_V_UPP) 412 407 __bench_v_GOC_verbose = $(AM_V_GOC) 413 __bench_v_PY_verbose = $(AM_V_PY) 414 __bench_v_RUSTC_verbose = $(AM_V_RUST) 408 __bench_v_RUSTC_verbose = $(AM_V_RUSTC) 415 409 __bench_v_NODEJS_verbose = $(AM_V_NODEJS) 416 410 __bench_v_JAVAC_verbose = $(AM_V_JAVAC) … … 790 784 echo "int main() { return 0; }" > ${@} 791 785 792 .SILENT: # do not print recipe 786 #.SILENT: # do not print recipe 787 .ONESHELL: # use one shell to execute recipe 793 788 .NOTPARALLEL: 794 .PHONY: jenkins cleancsv789 .PHONY: compile.csv basic.csv ctxswitch.csv mutex.csv schedint.csv 795 790 796 791 all : basic$(EXEEXT) ctxswitch$(EXEEXT) mutex$(EXEEXT) schedint$(EXEEXT) schedext$(EXEEXT) creation$(EXEEXT) … … 822 817 +make -C ${abs_top_builddir}/tools repeat 823 818 824 cleancsv: 825 rm -f compile.csv basic.csv ctxswitch.csv mutex.csv scheduling.csv 826 827 jenkins$(EXEEXT): cleancsv 819 jenkins$(EXEEXT): 828 820 @DOifskipcompile@ 829 821 +make compile.csv 830 822 -+make compile.diff.csv 831 823 @DOendif@ 824 +make basic.csv 825 -+make basic.diff.csv 832 826 +make ctxswitch.csv 833 827 -+make ctxswitch.diff.csv 834 828 +make mutex.csv 835 829 -+make mutex.diff.csv 836 +make sched uling.csv837 -+make sched uling.diff.csv830 +make schedint.csv 831 -+make schedint.diff.csv 838 832 @DOifskipcompile@ 839 833 cat compile.csv 840 834 -cat compile.diff.csv 841 835 @DOendif@ 836 cat basic.csv 837 -cat basic.diff.csv 842 838 cat ctxswitch.csv 843 839 -cat ctxswitch.diff.csv 844 840 cat mutex.csv 845 841 -cat mutex.diff.csv 846 cat sched uling.csv847 -cat sched uling.diff.csv842 cat schedint.csv 843 -cat schedint.diff.csv 848 844 849 845 compile.csv: 850 echo "building $@"851 846 echo "array,attributes,empty,expression,io,monitor,operators,typeof" > $@ 852 847 +make TIME_FORMAT='%e,' PRINT_FORMAT='' compile-array.make >> $@ … … 860 855 $(srcdir)/fixcsv.sh $@ 861 856 857 basic.csv: 858 echo "generator,coroutine,thread" > $@ 859 +make basic-cfa_generator.runquiet >> $@ && echo -n ',' >> $@ 860 +make basic-cfa_coroutine.runquiet >> $@ && echo -n ',' >> $@ 861 +make basic-cfa_thread.runquiet >> $@ 862 $(srcdir)/fixcsv.sh $@ 863 862 864 ctxswitch.csv: 863 echo "building $@"864 865 echo "generator,coroutine,thread" > $@ 865 866 +make ctxswitch-cfa_generator.runquiet >> $@ && echo -n ',' >> $@ … … 869 870 870 871 mutex.csv: 871 echo "building $@"872 872 echo "1-monitor,2-monitor" > $@ 873 873 +make mutex-cfa1.runquiet >> $@ && echo -n ',' >> $@ … … 875 875 $(srcdir)/fixcsv.sh $@ 876 876 877 scheduling.csv: 878 echo "building $@" 877 schedint.csv: 879 878 echo "schedint-1,schedint-2,schedext-1,schedext-2" > $@ 880 879 +make schedint-cfa1.runquiet >> $@ && echo -n ',' >> $@ … … 932 931 933 932 ctxswitch-python_coroutine$(EXEEXT): 934 $(BENCH_V_PY)echo "#!/bin/sh" > a.out933 echo "#!/bin/sh" > a.out 935 934 echo "python3.7 $(srcdir)/ctxswitch/python_cor.py" >> a.out 936 935 chmod a+x a.out 937 936 938 937 ctxswitch-nodejs_coroutine$(EXEEXT): 939 $(BENCH_V_NODEJS)echo "#!/bin/sh" > a.out938 echo "#!/bin/sh" > a.out 940 939 echo "nodejs $(srcdir)/ctxswitch/node_cor.js" >> a.out 941 940 chmod a+x a.out 942 941 943 942 ctxswitch-nodejs_await$(EXEEXT): 944 $(BENCH_V_NODEJS)echo "#!/bin/sh" > a.out943 echo "#!/bin/sh" > a.out 945 944 echo "nodejs $(srcdir)/ctxswitch/node_await.js" >> a.out 946 945 chmod a+x a.out … … 1086 1085 1087 1086 creation-python_coroutine$(EXEEXT): 1088 $(BENCH_V_PY)echo "#!/bin/sh" > a.out1087 echo "#!/bin/sh" > a.out 1089 1088 echo "python3.7 $(srcdir)/creation/python_cor.py" >> a.out 1090 1089 chmod a+x a.out 1091 1090 1092 1091 creation-nodejs_coroutine$(EXEEXT): 1093 $(BENCH_V_NODEJS)echo "#!/bin/sh" > a.out1092 echo "#!/bin/sh" > a.out 1094 1093 echo "nodejs $(srcdir)/creation/node_cor.js" >> a.out 1095 1094 chmod a+x a.out -
doc/theses/thierry_delisle_PhD/code/relaxed_list.cpp
ra505021 r8c50aed 9 9 #include <vector> 10 10 11 #include <getopt.h>12 11 #include <unistd.h> 13 12 #include <sys/sysinfo.h> … … 22 21 23 22 int value; 24 int id; 25 26 Node() { creates++; } 27 Node(int value): value(value) { creates++; } 28 ~Node() { destroys++; } 23 Node(int value): value(value) { 24 creates++; 25 } 26 27 ~Node() { 28 destroys++; 29 } 29 30 }; 30 31 … … 32 33 std::atomic_size_t Node::destroys = { 0 }; 33 34 35 static const constexpr int nodes_per_threads = 128; 36 struct NodeArray { 37 __attribute__((aligned(64))) Node * array[nodes_per_threads]; 38 __attribute__((aligned(64))) char pad; 39 }; 40 34 41 bool enable_stats = false; 35 36 template<>37 thread_local relaxed_list<Node>::TLS relaxed_list<Node>::tls = {};38 39 template<>40 relaxed_list<Node> * relaxed_list<Node>::head = nullptr;41 42 #ifndef NO_STATS43 template<>44 relaxed_list<Node>::GlobalStats relaxed_list<Node>::global_stats = {};45 #endif46 47 // ================================================================================================48 // UTILS49 // ================================================================================================50 42 51 43 struct local_stat_t { … … 55 47 size_t crc_in = 0; 56 48 size_t crc_out = 0; 57 size_t valmax = 0;58 size_t valmin = 100000000ul;59 49 }; 60 50 61 struct global_stat_t { 62 std::atomic_size_t in = { 0 }; 63 std::atomic_size_t out = { 0 }; 64 std::atomic_size_t empty = { 0 }; 65 std::atomic_size_t crc_in = { 0 }; 66 std::atomic_size_t crc_out = { 0 }; 67 std::atomic_size_t valmax = { 0 }; 68 std::atomic_size_t valmin = { 100000000ul }; 69 }; 70 71 void atomic_max(std::atomic_size_t & target, size_t value) { 72 for(;;) { 73 size_t expect = target.load(std::memory_order_relaxed); 74 if(value <= expect) return; 75 bool success = target.compare_exchange_strong(expect, value); 76 if(success) return; 77 } 78 } 79 80 void atomic_min(std::atomic_size_t & target, size_t value) { 81 for(;;) { 82 size_t expect = target.load(std::memory_order_relaxed); 83 if(value >= expect) return; 84 bool success = target.compare_exchange_strong(expect, value); 85 if(success) return; 86 } 87 } 88 89 void tally_stats(global_stat_t & global, local_stat_t & local) { 90 91 global.in += local.in; 92 global.out += local.out; 93 global.empty += local.empty; 94 95 global.crc_in += local.crc_in; 96 global.crc_out += local.crc_out; 97 98 atomic_max(global.valmax, local.valmax); 99 atomic_min(global.valmin, local.valmin); 100 101 relaxed_list<Node>::stats_tls_tally(); 102 } 103 104 void waitfor(double & duration, barrier_t & barrier, std::atomic_bool & done) { 51 __attribute__((noinline)) void run_body( 52 std::atomic<bool>& done, 53 Random & rand, 54 Node * (&my_nodes)[128], 55 local_stat_t & local, 56 relaxed_list<Node> & list 57 ) { 58 while(__builtin_expect(!done.load(std::memory_order_relaxed), true)) { 59 int idx = rand.next() % nodes_per_threads; 60 if (auto node = my_nodes[idx]) { 61 local.crc_in += node->value; 62 list.push(node); 63 my_nodes[idx] = nullptr; 64 local.in++; 65 } 66 else if(auto node = list.pop()) { 67 local.crc_out += node->value; 68 my_nodes[idx] = node; 69 local.out++; 70 } 71 else { 72 local.empty++; 73 } 74 } 75 } 76 77 void run(unsigned nthread, unsigned nqueues, unsigned fill, double duration) { 78 // List being tested 79 relaxed_list<Node> list = { nthread * nqueues }; 80 81 // Barrier for synchronization 82 barrier_t barrier(nthread + 1); 83 84 // Data to check everything is OK 85 struct { 86 std::atomic_size_t in = { 0 }; 87 std::atomic_size_t out = { 0 }; 88 std::atomic_size_t empty = { 0 }; 89 std::atomic_size_t crc_in = { 0 }; 90 std::atomic_size_t crc_out = { 0 }; 91 struct { 92 struct { 93 std::atomic_size_t attempt = { 0 }; 94 std::atomic_size_t success = { 0 }; 95 } push; 96 struct { 97 std::atomic_size_t attempt = { 0 }; 98 std::atomic_size_t success = { 0 }; 99 } pop; 100 } pick; 101 } global; 102 103 // Flag to signal termination 104 std::atomic_bool done = { false }; 105 106 // Prep nodes 107 std::cout << "Initializing "; 108 size_t nnodes = 0; 109 size_t npushed = 0; 110 NodeArray all_nodes[nthread]; 111 for(auto & nodes : all_nodes) { 112 Random rand(rdtscl()); 113 for(auto & node : nodes.array) { 114 auto r = rand.next() % 100; 115 if(r < fill) { 116 node = new Node(rand.next() % 100); 117 nnodes++; 118 } else { 119 node = nullptr; 120 } 121 } 122 123 for(int i = 0; i < 10; i++) { 124 int idx = rand.next() % nodes_per_threads; 125 if (auto node = nodes.array[idx]) { 126 global.crc_in += node->value; 127 list.push(node); 128 npushed++; 129 nodes.array[idx] = nullptr; 130 } 131 } 132 } 133 134 std::cout << nnodes << " nodes " << fill << "% (" << npushed << " pushed)" << std::endl; 135 136 enable_stats = true; 137 138 std::thread * threads[nthread]; 139 unsigned i = 1; 140 for(auto & t : threads) { 141 auto & my_nodes = all_nodes[i - 1].array; 142 t = new std::thread([&done, &list, &barrier, &global, &my_nodes](unsigned tid) { 143 Random rand(tid + rdtscl()); 144 145 local_stat_t local; 146 147 // affinity(tid); 148 149 barrier.wait(tid); 150 151 // EXPERIMENT START 152 153 run_body(done, rand, my_nodes, local, list); 154 155 // EXPERIMENT END 156 157 barrier.wait(tid); 158 159 global.in += local.in; 160 global.out += local.out; 161 global.empty += local.empty; 162 163 for(auto node : my_nodes) { 164 delete node; 165 } 166 167 global.crc_in += local.crc_in; 168 global.crc_out += local.crc_out; 169 170 global.pick.push.attempt += relaxed_list<Node>::tls.pick.push.attempt; 171 global.pick.push.success += relaxed_list<Node>::tls.pick.push.success; 172 global.pick.pop .attempt += relaxed_list<Node>::tls.pick.pop.attempt; 173 global.pick.pop .success += relaxed_list<Node>::tls.pick.pop.success; 174 }, i++); 175 } 176 105 177 std::cout << "Starting" << std::endl; 106 178 auto before = Clock::now(); … … 124 196 duration = durr.count(); 125 197 std::cout << "\rClosing down" << std::endl; 126 } 127 128 void waitfor(double & duration, barrier_t & barrier, const std::atomic_size_t & count) { 129 std::cout << "Starting" << std::endl; 130 auto before = Clock::now(); 131 barrier.wait(0); 132 133 while(true) { 134 usleep(100000); 135 size_t c = count.load(); 136 if( c == 0 ) { 137 break; 138 } 139 std::cout << "\r" << c; 140 std::cout.flush(); 141 } 142 143 barrier.wait(0); 144 auto after = Clock::now(); 145 duration_t durr = after - before; 146 duration = durr.count(); 147 std::cout << "\rClosing down" << std::endl; 148 } 149 150 void print_stats(double duration, unsigned nthread, global_stat_t & global) { 198 199 for(auto t : threads) { 200 t->join(); 201 delete t; 202 } 203 204 enable_stats = false; 205 206 while(auto node = list.pop()) { 207 global.crc_out += node->value; 208 delete node; 209 } 210 151 211 assert(Node::creates == Node::destroys); 152 212 assert(global.crc_in == global.crc_out); … … 164 224 std::cout << "Ops/sec : " << ops_sec << "\n"; 165 225 std::cout << "Total ops : " << ops << "(" << global.in << "i, " << global.out << "o, " << global.empty << "e)\n"; 166 if(global.valmax != 0) {167 std::cout << "Max runs : " << global.valmax << "\n";168 std::cout << "Min runs : " << global.valmin << "\n";169 }170 226 #ifndef NO_STATS 171 relaxed_list<Node>::stats_print(std::cout); 227 double push_sur = (100.0 * double(global.pick.push.success) / global.pick.push.attempt); 228 double pop_sur = (100.0 * double(global.pick.pop .success) / global.pick.pop .attempt); 229 std::cout << "Push Pick % : " << push_sur << "(" << global.pick.push.success << " / " << global.pick.push.attempt << ")\n"; 230 std::cout << "Pop Pick % : " << pop_sur << "(" << global.pick.pop .success << " / " << global.pick.pop .attempt << ")\n"; 172 231 #endif 173 232 } 174 233 175 void save_fairness(const int data[], int factor, unsigned nthreads, size_t columns, size_t rows, const std::string & output); 176 177 // ================================================================================================ 178 // EXPERIMENTS 179 // ================================================================================================ 180 181 // ================================================================================================ 182 __attribute__((noinline)) void runChurn_body( 183 std::atomic<bool>& done, 184 Random & rand, 185 Node * my_nodes[], 186 unsigned nslots, 187 local_stat_t & local, 188 relaxed_list<Node> & list 189 ) { 190 while(__builtin_expect(!done.load(std::memory_order_relaxed), true)) { 191 int idx = rand.next() % nslots; 192 if (auto node = my_nodes[idx]) { 193 local.crc_in += node->value; 194 list.push(node); 195 my_nodes[idx] = nullptr; 196 local.in++; 197 } 198 else if(auto node = list.pop()) { 199 local.crc_out += node->value; 200 my_nodes[idx] = node; 201 local.out++; 202 } 203 else { 204 local.empty++; 205 } 206 } 207 } 208 209 void runChurn(unsigned nthread, unsigned nqueues, double duration, unsigned nnodes, const unsigned nslots) { 210 std::cout << "Churn Benchmark" << std::endl; 211 assert(nnodes <= nslots); 212 // List being tested 213 214 // Barrier for synchronization 215 barrier_t barrier(nthread + 1); 216 217 // Data to check everything is OK 218 global_stat_t global; 219 220 // Flag to signal termination 221 std::atomic_bool done = { false }; 222 223 // Prep nodes 224 std::cout << "Initializing "; 225 size_t npushed = 0; 226 relaxed_list<Node> list = { nthread * nqueues }; 227 { 228 Node** all_nodes[nthread]; 229 for(auto & nodes : all_nodes) { 230 nodes = new __attribute__((aligned(64))) Node*[nslots + 8]; 231 Random rand(rdtscl()); 232 for(unsigned i = 0; i < nnodes; i++) { 233 nodes[i] = new Node(rand.next() % 100); 234 } 235 236 for(unsigned i = nnodes; i < nslots; i++) { 237 nodes[i] = nullptr; 238 } 239 240 for(int i = 0; i < 10 && i < (int)nslots; i++) { 241 int idx = rand.next() % nslots; 242 if (auto node = nodes[idx]) { 243 global.crc_in += node->value; 244 list.push(node); 245 npushed++; 246 nodes[idx] = nullptr; 247 } 248 } 249 } 250 251 std::cout << nnodes << " nodes (" << nslots << " slots)" << std::endl; 252 253 enable_stats = true; 254 255 std::thread * threads[nthread]; 256 unsigned i = 1; 257 for(auto & t : threads) { 258 auto & my_nodes = all_nodes[i - 1]; 259 t = new std::thread([&done, &list, &barrier, &global, &my_nodes, nslots](unsigned tid) { 260 Random rand(tid + rdtscl()); 261 262 local_stat_t local; 263 264 // affinity(tid); 265 266 barrier.wait(tid); 267 268 // EXPERIMENT START 269 270 runChurn_body(done, rand, my_nodes, nslots, local, list); 271 272 // EXPERIMENT END 273 274 barrier.wait(tid); 275 276 tally_stats(global, local); 277 278 for(unsigned i = 0; i < nslots; i++) { 279 delete my_nodes[i]; 280 } 281 }, i++); 282 } 283 284 waitfor(duration, barrier, done); 285 286 for(auto t : threads) { 287 t->join(); 288 delete t; 289 } 290 291 enable_stats = false; 292 293 while(auto node = list.pop()) { 294 global.crc_out += node->value; 295 delete node; 296 } 297 298 for(auto nodes : all_nodes) { 299 delete[] nodes; 300 } 301 } 302 303 print_stats(duration, nthread, global); 304 } 305 306 // ================================================================================================ 307 __attribute__((noinline)) void runPingPong_body( 308 std::atomic<bool>& done, 309 Node initial_nodes[], 310 unsigned nnodes, 311 local_stat_t & local, 312 relaxed_list<Node> & list 313 ) { 314 Node * nodes[nnodes]; 315 { 316 unsigned i = 0; 317 for(auto & n : nodes) { 318 n = &initial_nodes[i++]; 319 } 320 } 321 322 while(__builtin_expect(!done.load(std::memory_order_relaxed), true)) { 323 324 for(Node * & node : nodes) { 325 local.crc_in += node->value; 326 list.push(node); 327 local.in++; 328 } 329 330 // ----- 331 332 for(Node * & node : nodes) { 333 node = list.pop(); 334 assert(node); 335 local.crc_out += node->value; 336 local.out++; 337 } 338 } 339 } 340 341 void runPingPong(unsigned nthread, unsigned nqueues, double duration, unsigned nnodes) { 342 std::cout << "PingPong Benchmark" << std::endl; 343 344 345 // Barrier for synchronization 346 barrier_t barrier(nthread + 1); 347 348 // Data to check everything is OK 349 global_stat_t global; 350 351 // Flag to signal termination 352 std::atomic_bool done = { false }; 353 354 std::cout << "Initializing "; 355 // List being tested 356 relaxed_list<Node> list = { nthread * nqueues }; 357 { 358 enable_stats = true; 359 360 std::thread * threads[nthread]; 361 unsigned i = 1; 362 for(auto & t : threads) { 363 t = new std::thread([&done, &list, &barrier, &global, nnodes](unsigned tid) { 364 Random rand(tid + rdtscl()); 365 366 Node nodes[nnodes]; 367 for(auto & n : nodes) { 368 n.value = (int)rand.next() % 100; 369 } 370 371 local_stat_t local; 372 373 // affinity(tid); 374 375 barrier.wait(tid); 376 377 // EXPERIMENT START 378 379 runPingPong_body(done, nodes, nnodes, local, list); 380 381 // EXPERIMENT END 382 383 barrier.wait(tid); 384 385 tally_stats(global, local); 386 }, i++); 387 } 388 389 waitfor(duration, barrier, done); 390 391 for(auto t : threads) { 392 t->join(); 393 delete t; 394 } 395 396 enable_stats = false; 397 } 398 399 print_stats(duration, nthread, global); 400 } 401 402 // ================================================================================================ 403 __attribute__((noinline)) void runFairness_body( 404 unsigned tid, 405 size_t width, 406 size_t length, 407 int output[], 408 std::atomic_size_t & count, 409 Node initial_nodes[], 410 unsigned nnodes, 411 local_stat_t & local, 412 relaxed_list<Node> & list 413 ) { 414 Node * nodes[nnodes]; 415 { 416 unsigned i = 0; 417 for(auto & n : nodes) { 418 n = &initial_nodes[i++]; 419 } 420 } 421 422 while(__builtin_expect(0 != count.load(std::memory_order_relaxed), true)) { 423 424 for(Node * & node : nodes) { 425 local.crc_in += node->id; 426 list.push(node); 427 local.in++; 428 } 429 430 // ----- 431 432 for(Node * & node : nodes) { 433 node = list.pop(); 434 assert(node); 435 436 if (unsigned(node->value) < length) { 437 size_t idx = (node->value * width) + node->id; 438 assert(idx < (width * length)); 439 output[idx] = tid; 440 } 441 442 node->value++; 443 if(unsigned(node->value) == length) count--; 444 445 local.crc_out += node->id; 446 local.out++; 447 } 448 } 449 } 450 451 void runFairness(unsigned nthread, unsigned nqueues, double duration, unsigned nnodes, const std::string & output) { 452 std::cout << "Fairness Benchmark, outputing to : " << output << std::endl; 453 454 // Barrier for synchronization 455 barrier_t barrier(nthread + 1); 456 457 // Data to check everything is OK 458 global_stat_t global; 459 460 std::cout << "Initializing "; 461 462 // Check fairness by creating a png of where the threads ran 463 size_t width = nthread * nnodes; 464 size_t length = 100000; 465 466 std::unique_ptr<int[]> data_out { new int[width * length] }; 467 468 // Flag to signal termination 469 std::atomic_size_t count = width; 470 471 // List being tested 472 relaxed_list<Node> list = { nthread * nqueues }; 473 { 474 enable_stats = true; 475 476 std::thread * threads[nthread]; 477 unsigned i = 1; 478 for(auto & t : threads) { 479 t = new std::thread([&count, &list, &barrier, &global, nnodes, width, length, data_out = data_out.get()](unsigned tid) { 480 unsigned int start = (tid - 1) * nnodes; 481 Node nodes[nnodes]; 482 for(auto & n : nodes) { 483 n.id = start; 484 n.value = 0; 485 start++; 486 } 487 488 local_stat_t local; 489 490 // affinity(tid); 491 492 barrier.wait(tid); 493 494 // EXPERIMENT START 495 496 runFairness_body(tid, width, length, data_out, count, nodes, nnodes, local, list); 497 498 // EXPERIMENT END 499 500 barrier.wait(tid); 501 502 for(const auto & n : nodes) { 503 local.valmax = max(local.valmax, size_t(n.value)); 504 local.valmin = min(local.valmin, size_t(n.value)); 505 } 506 507 tally_stats(global, local); 508 }, i++); 509 } 510 511 waitfor(duration, barrier, count); 512 513 for(auto t : threads) { 514 t->join(); 515 delete t; 516 } 517 518 enable_stats = false; 519 } 520 521 print_stats(duration, nthread, global); 522 523 save_fairness(data_out.get(), 100, nthread, width, length, output); 524 } 525 526 // ================================================================================================ 527 528 bool iequals(const std::string& a, const std::string& b) 529 { 530 return std::equal(a.begin(), a.end(), 531 b.begin(), b.end(), 532 [](char a, char b) { 533 return std::tolower(a) == std::tolower(b); 534 }); 234 void usage(char * argv[]) { 235 std::cerr << argv[0] << ": [DURATION (FLOAT:SEC)] [NTHREADS] [NQUEUES] [FILL]" << std::endl;; 236 std::exit(1); 535 237 } 536 238 … … 539 241 double duration = 5.0; 540 242 unsigned nthreads = 2; 541 unsigned nqueues = 4; 542 unsigned nnodes = 100; 543 unsigned nslots = 100; 544 std::string out = "fairness.png"; 545 546 enum { 547 Churn, 548 PingPong, 549 Fairness, 550 NONE 551 } benchmark = NONE; 243 unsigned nqueues = 2; 244 unsigned fill = 100; 552 245 553 246 std::cout.imbue(std::locale("")); 554 247 555 for(;;) { 556 static struct option options[] = { 557 {"duration", required_argument, 0, 'd'}, 558 {"nthreads", required_argument, 0, 't'}, 559 {"nqueues", required_argument, 0, 'q'}, 560 {"benchmark", required_argument, 0, 'b'}, 561 {0, 0, 0, 0} 562 }; 563 564 int idx = 0; 565 int opt = getopt_long(argc, argv, "d:t:q:b:", options, &idx); 566 567 std::string arg = optarg ? optarg : ""; 568 size_t len = 0; 569 switch(opt) { 570 // Exit Case 571 case -1: 572 /* paranoid */ assert(optind <= argc); 573 switch(benchmark) { 574 case NONE: 575 std::cerr << "Must specify a benchmark" << std::endl; 576 goto usage; 577 case PingPong: 578 nnodes = 1; 579 nslots = 1; 580 switch(argc - optind) { 581 case 0: break; 582 case 1: 583 try { 584 arg = optarg = argv[optind]; 585 nnodes = stoul(optarg, &len); 586 if(len != arg.size()) { throw std::invalid_argument(""); } 587 } catch(std::invalid_argument &) { 588 std::cerr << "Number of nodes must be a positive integer, was " << arg << std::endl; 589 goto usage; 590 } 591 break; 592 default: 593 std::cerr << "'PingPong' benchmark doesn't accept more than 2 extra arguments" << std::endl; 594 goto usage; 595 } 596 break; 597 case Churn: 598 nnodes = 100; 599 nslots = 100; 600 switch(argc - optind) { 601 case 0: break; 602 case 1: 603 try { 604 arg = optarg = argv[optind]; 605 nnodes = stoul(optarg, &len); 606 if(len != arg.size()) { throw std::invalid_argument(""); } 607 nslots = nnodes; 608 } catch(std::invalid_argument &) { 609 std::cerr << "Number of nodes must be a positive integer, was " << arg << std::endl; 610 goto usage; 611 } 612 break; 613 case 2: 614 try { 615 arg = optarg = argv[optind]; 616 nnodes = stoul(optarg, &len); 617 if(len != arg.size()) { throw std::invalid_argument(""); } 618 } catch(std::invalid_argument &) { 619 std::cerr << "Number of nodes must be a positive integer, was " << arg << std::endl; 620 goto usage; 621 } 622 try { 623 arg = optarg = argv[optind + 1]; 624 nslots = stoul(optarg, &len); 625 if(len != arg.size()) { throw std::invalid_argument(""); } 626 } catch(std::invalid_argument &) { 627 std::cerr << "Number of slots must be a positive integer, was " << arg << std::endl; 628 goto usage; 629 } 630 break; 631 default: 632 std::cerr << "'Churn' benchmark doesn't accept more than 2 extra arguments" << std::endl; 633 goto usage; 634 } 635 break; 636 case Fairness: 637 nnodes = 1; 638 switch(argc - optind) { 639 case 0: break; 640 case 1: 641 arg = optarg = argv[optind]; 642 out = arg; 643 break; 644 default: 645 std::cerr << "'Churn' benchmark doesn't accept more than 2 extra arguments" << std::endl; 646 goto usage; 647 } 648 } 649 goto run; 650 // Benchmarks 651 case 'b': 652 if(benchmark != NONE) { 653 std::cerr << "Only when benchmark can be run" << std::endl; 654 goto usage; 655 } 656 if(iequals(arg, "churn")) { 657 benchmark = Churn; 658 break; 659 } 660 if(iequals(arg, "pingpong")) { 661 benchmark = PingPong; 662 break; 663 } 664 if(iequals(arg, "fairness")) { 665 benchmark = Fairness; 666 break; 667 } 668 std::cerr << "Unkown benchmark " << arg << std::endl; 669 goto usage; 670 // Numeric Arguments 671 case 'd': 672 try { 673 duration = stod(optarg, &len); 674 if(len != arg.size()) { throw std::invalid_argument(""); } 675 } catch(std::invalid_argument &) { 676 std::cerr << "Duration must be a valid double, was " << arg << std::endl; 677 goto usage; 678 } 679 break; 680 case 't': 681 try { 682 nthreads = stoul(optarg, &len); 683 if(len != arg.size()) { throw std::invalid_argument(""); } 684 } catch(std::invalid_argument &) { 685 std::cerr << "Number of threads must be a positive integer, was " << arg << std::endl; 686 goto usage; 687 } 688 break; 689 case 'q': 690 try { 691 nqueues = stoul(optarg, &len); 692 if(len != arg.size()) { throw std::invalid_argument(""); } 693 } catch(std::invalid_argument &) { 694 std::cerr << "Number of queues must be a positive integer, was " << arg << std::endl; 695 goto usage; 696 } 697 break; 698 // Other cases 699 default: /* ? */ 700 std::cerr << opt << std::endl; 701 usage: 702 std::cerr << "Usage: " << argv[0] << ": [options] -b churn [NNODES] [NSLOTS = NNODES]" << std::endl; 703 std::cerr << " or: " << argv[0] << ": [options] -b pingpong [NNODES]" << std::endl; 704 std::cerr << std::endl; 705 std::cerr << " -d, --duration=DURATION Duration of the experiment, in seconds" << std::endl; 706 std::cerr << " -t, --nthreads=NTHREADS Number of kernel threads" << std::endl; 707 std::cerr << " -q, --nqueues=NQUEUES Number of queues per threads" << std::endl; 708 std::exit(1); 709 } 710 } 711 run: 248 switch (argc) 249 { 250 case 5: 251 fill = std::stoul(argv[4]); 252 [[fallthrough]]; 253 case 4: 254 nqueues = std::stoul(argv[3]); 255 [[fallthrough]]; 256 case 3: 257 nthreads = std::stoul(argv[2]); 258 [[fallthrough]]; 259 case 2: 260 duration = std::stod(argv[1]); 261 if( duration <= 0.0 ) { 262 std::cerr << "Duration must be positive, was " << argv[1] << "(" << duration << ")" << std::endl; 263 usage(argv); 264 } 265 [[fallthrough]]; 266 case 1: 267 break; 268 default: 269 usage(argv); 270 break; 271 } 712 272 713 273 check_cache_line_size(); 714 274 715 275 std::cout << "Running " << nthreads << " threads (" << (nthreads * nqueues) << " queues) for " << duration << " seconds" << std::endl; 716 switch(benchmark) { 717 case Churn: 718 runChurn(nthreads, nqueues, duration, nnodes, nslots); 719 break; 720 case PingPong: 721 runPingPong(nthreads, nqueues, duration, nnodes); 722 break; 723 case Fairness: 724 runFairness(nthreads, nqueues, duration, nnodes, out); 725 break; 726 default: 727 abort(); 728 } 276 run(nthreads, nqueues, fill, duration); 277 729 278 return 0; 730 279 } 731 280 281 template<> 282 thread_local relaxed_list<Node>::TLS relaxed_list<Node>::tls = {}; 283 284 template<> 285 relaxed_list<Node>::intrusive_queue_t::stat::Dif relaxed_list<Node>::intrusive_queue_t::stat::dif = {}; 286 732 287 const char * __my_progname = "Relaxed List"; 733 734 struct rgb_t {735 double r; // a fraction between 0 and 1736 double g; // a fraction between 0 and 1737 double b; // a fraction between 0 and 1738 };739 740 struct hsv_t {741 double h; // angle in degrees742 double s; // a fraction between 0 and 1743 double v; // a fraction between 0 and 1744 };745 746 rgb_t hsv2rgb(hsv_t in) {747 double hh, p, q, t, ff;748 long i;749 rgb_t out;750 751 if(in.s <= 0.0) { // < is bogus, just shuts up warnings752 out.r = in.v;753 out.g = in.v;754 out.b = in.v;755 return out;756 }757 hh = in.h;758 if(hh >= 360.0) hh = 0.0;759 hh /= 60.0;760 i = (long)hh;761 ff = hh - i;762 p = in.v * (1.0 - in.s);763 q = in.v * (1.0 - (in.s * ff));764 t = in.v * (1.0 - (in.s * (1.0 - ff)));765 766 switch(i) {767 case 0:768 out.r = in.v;769 out.g = t;770 out.b = p;771 break;772 case 1:773 out.r = q;774 out.g = in.v;775 out.b = p;776 break;777 case 2:778 out.r = p;779 out.g = in.v;780 out.b = t;781 break;782 783 case 3:784 out.r = p;785 out.g = q;786 out.b = in.v;787 break;788 case 4:789 out.r = t;790 out.g = p;791 out.b = in.v;792 break;793 case 5:794 default:795 out.r = in.v;796 out.g = p;797 out.b = q;798 break;799 }800 return out;801 }802 803 void save_fairness(const int data[], int factor, unsigned nthreads, size_t columns, size_t rows, const std::string & output) {804 std::ofstream os(output);805 os << "<html>\n";806 os << "<head>\n";807 os << "<style>\n";808 os << "</style>\n";809 os << "</head>\n";810 os << "<body>\n";811 os << "<table style=\"width=100%\">\n";812 813 size_t idx = 0;814 for(size_t r = 0ul; r < rows; r++) {815 os << "<tr>\n";816 for(size_t c = 0ul; c < columns; c++) {817 os << "<td class=\"custom custom" << data[idx] << "\"></td>\n";818 idx++;819 }820 os << "</tr>\n";821 }822 823 os << "</table>\n";824 os << "</body>\n";825 os << "</html>\n";826 os << std::endl;827 }828 829 #include <png.h>830 #include <setjmp.h>831 832 /*833 void save_fairness(const int data[], int factor, unsigned nthreads, size_t columns, size_t rows, const std::string & output) {834 int width = columns * factor;835 int height = rows / factor;836 837 int code = 0;838 int idx = 0;839 FILE *fp = NULL;840 png_structp png_ptr = NULL;841 png_infop info_ptr = NULL;842 png_bytep row = NULL;843 844 // Open file for writing (binary mode)845 fp = fopen(output.c_str(), "wb");846 if (fp == NULL) {847 fprintf(stderr, "Could not open file %s for writing\n", output.c_str());848 code = 1;849 goto finalise;850 }851 852 // Initialize write structure853 png_ptr = png_create_write_struct(PNG_LIBPNG_VER_STRING, NULL, NULL, NULL);854 if (png_ptr == NULL) {855 fprintf(stderr, "Could not allocate write struct\n");856 code = 1;857 goto finalise;858 }859 860 // Initialize info structure861 info_ptr = png_create_info_struct(png_ptr);862 if (info_ptr == NULL) {863 fprintf(stderr, "Could not allocate info struct\n");864 code = 1;865 goto finalise;866 }867 868 // Setup Exception handling869 if (setjmp(png_jmpbuf(png_ptr))) {870 fprintf(stderr, "Error during png creation\n");871 code = 1;872 goto finalise;873 }874 875 png_init_io(png_ptr, fp);876 877 // Write header (8 bit colour depth)878 png_set_IHDR(png_ptr, info_ptr, width, height,879 8, PNG_COLOR_TYPE_RGB, PNG_INTERLACE_NONE,880 PNG_COMPRESSION_TYPE_BASE, PNG_FILTER_TYPE_BASE);881 882 png_write_info(png_ptr, info_ptr);883 884 // Allocate memory for one row (3 bytes per pixel - RGB)885 row = (png_bytep) malloc(3 * width * sizeof(png_byte));886 887 // Write image data888 int x, y;889 for (y=0 ; y<height ; y++) {890 for (x=0 ; x<width ; x++) {891 auto & r = row[(x * 3) + 0];892 auto & g = row[(x * 3) + 1];893 auto & b = row[(x * 3) + 2];894 assert(idx < (rows * columns));895 int color = data[idx] - 1;896 assert(color < nthreads);897 assert(color >= 0);898 idx++;899 900 double angle = double(color) / double(nthreads);901 902 auto c = hsv2rgb({ 360.0 * angle, 0.8, 0.8 });903 904 r = char(c.r * 255.0);905 g = char(c.g * 255.0);906 b = char(c.b * 255.0);907 908 }909 png_write_row(png_ptr, row);910 }911 912 assert(idx == (rows * columns));913 914 // End write915 png_write_end(png_ptr, NULL);916 917 finalise:918 if (fp != NULL) fclose(fp);919 if (info_ptr != NULL) png_free_data(png_ptr, info_ptr, PNG_FREE_ALL, -1);920 if (png_ptr != NULL) png_destroy_write_struct(&png_ptr, (png_infopp)NULL);921 if (row != NULL) free(row);922 }923 */ -
doc/theses/thierry_delisle_PhD/code/relaxed_list.hpp
ra505021 r8c50aed 37 37 }; 38 38 39 static inline bool bts(std::atomic_size_t & target, size_t bit ) {40 //*41 int result = 0;42 asm volatile(43 "LOCK btsq %[bit], %[target]\n\t"44 :"=@ccc" (result)45 : [target] "m" (target), [bit] "r" (bit)46 );47 return result != 0;48 /*/49 size_t mask = 1ul << bit;50 size_t ret = target.fetch_or(mask, std::memory_order_relaxed);51 return (ret & mask) != 0;52 //*/53 }54 55 static inline bool btr(std::atomic_size_t & target, size_t bit ) {56 //*57 int result = 0;58 asm volatile(59 "LOCK btrq %[bit], %[target]\n\t"60 :"=@ccc" (result)61 : [target] "m" (target), [bit] "r" (bit)62 );63 return result != 0;64 /*/65 size_t mask = 1ul << bit;66 size_t ret = target.fetch_and(~mask, std::memory_order_relaxed);67 return (ret & mask) != 0;68 //*/69 }70 39 71 40 extern bool enable_stats; … … 79 48 size_t attempt = 0; 80 49 size_t success = 0; 81 size_t mask_attempt = 0;82 } pop;83 };84 85 struct empty_stat {86 struct {87 size_t value = 0;88 size_t count = 0;89 } push;90 struct {91 size_t value = 0;92 size_t count = 0;93 50 } pop; 94 51 }; … … 105 62 static_assert(std::is_same<decltype(node_t::_links), _LinksFields_t<node_t>>::value, "Node must have a links field"); 106 63 64 107 65 public: 108 66 relaxed_list(unsigned numLists) 109 : lists(new intrusive_queue_t[numLists]) 67 : numNonEmpty{0} 68 , lists(new intrusive_queue_t[numLists]) 110 69 , numLists(numLists) 111 { 112 assertf(7 * 8 * 8 >= numLists, "List currently only supports 448 sublists"); 113 // assert(sizeof(*this) == 128); 114 std::cout << "Constructing Relaxed List with " << numLists << std::endl; 115 70 {} 71 72 ~relaxed_list() { 73 lists.reset(); 116 74 #ifndef NO_STATS 117 if(head) this->next = head; 118 head = this; 75 std::cout << "Difference : " 76 << ssize_t(double(intrusive_queue_t::stat::dif.value) / intrusive_queue_t::stat::dif.num ) << " avg\t" 77 << intrusive_queue_t::stat::dif.max << "max" << std::endl; 119 78 #endif 120 }121 122 ~relaxed_list() {123 std::cout << "Destroying Relaxed List" << std::endl;124 lists.reset();125 79 } 126 80 … … 130 84 while(true) { 131 85 // Pick a random list 132 unsignedi = tls.rng.next() % numLists;86 int i = tls.rng.next() % numLists; 133 87 134 88 #ifndef NO_STATS … … 139 93 if( !lists[i].lock.try_lock() ) continue; 140 94 141 __attribute__((unused)) int num = numNonEmpty;142 143 95 // Actually push it 144 if(lists[i].push(node)) { 145 numNonEmpty++; 146 size_t qword = i >> 6ull; 147 size_t bit = i & 63ull; 148 assertf((list_mask[qword] & (1ul << bit)) == 0, "Before set %zu:%zu (%u), %zx & %zx", qword, bit, i, list_mask[qword].load(), (1ul << bit)); 149 __attribute__((unused)) bool ret = bts(list_mask[qword], bit); 150 assert(!ret); 151 assertf((list_mask[qword] & (1ul << bit)) != 0, "After set %zu:%zu (%u), %zx & %zx", qword, bit, i, list_mask[qword].load(), (1ul << bit)); 152 } 96 lists[i].push(node, numNonEmpty); 153 97 assert(numNonEmpty <= (int)numLists); 154 98 … … 158 102 #ifndef NO_STATS 159 103 tls.pick.push.success++; 160 tls.empty.push.value += num;161 tls.empty.push.count += 1;162 104 #endif 163 105 return; … … 166 108 167 109 __attribute__((noinline, hot)) node_t * pop() { 168 #if !defined(NO_BITMASK) 169 // for(int r = 0; r < 10 && numNonEmpty != 0; r++) { 170 // // Pick two lists at random 171 // unsigned i = tls.rng.next() % numLists; 172 // unsigned j = tls.rng.next() % numLists; 173 174 // if(auto node = try_pop(i, j)) return node; 175 // } 176 int nnempty; 177 while(0 != (nnempty = numNonEmpty)) { 178 tls.pick.pop.mask_attempt++; 179 unsigned i, j; 180 // if( numLists < 4 || (numLists / nnempty) < 4 ) { 181 // // Pick two lists at random 182 // i = tls.rng.next() % numLists; 183 // j = tls.rng.next() % numLists; 184 // } else 185 { 186 #ifndef NO_STATS 187 // tls.pick.push.mask_attempt++; 188 #endif 189 190 // Pick two lists at random 191 unsigned num = ((numLists - 1) >> 6) + 1; 192 193 unsigned ri = tls.rng.next(); 194 unsigned rj = tls.rng.next(); 195 196 unsigned wdxi = (ri >> 6u) % num; 197 unsigned wdxj = (rj >> 6u) % num; 198 199 size_t maski = list_mask[wdxi].load(std::memory_order_relaxed); 200 size_t maskj = list_mask[wdxj].load(std::memory_order_relaxed); 201 202 if(maski == 0 && maskj == 0) continue; 203 204 unsigned bi = rand_bit(ri, maski); 205 unsigned bj = rand_bit(rj, maskj); 206 207 assertf(bi < 64, "%zu %u", maski, bi); 208 assertf(bj < 64, "%zu %u", maskj, bj); 209 210 i = bi | (wdxi << 6); 211 j = bj | (wdxj << 6); 212 213 assertf(i < numLists, "%u", wdxi << 6); 214 assertf(j < numLists, "%u", wdxj << 6); 215 } 216 217 if(auto node = try_pop(i, j)) return node; 218 } 219 #else 220 while(numNonEmpty != 0) { 221 // Pick two lists at random 222 int i = tls.rng.next() % numLists; 223 int j = tls.rng.next() % numLists; 224 225 if(auto node = try_pop(i, j)) return node; 226 } 227 #endif 110 while(numNonEmpty != 0) { 111 // Pick two lists at random 112 int i = tls.rng.next() % numLists; 113 int j = tls.rng.next() % numLists; 114 115 #ifndef NO_STATS 116 tls.pick.pop.attempt++; 117 #endif 118 119 // Pick the bet list 120 int w = i; 121 if( __builtin_expect(lists[j].ts() != 0, true) ) { 122 w = (lists[i].ts() < lists[j].ts()) ? i : j; 123 } 124 125 auto & list = lists[w]; 126 // If list looks empty retry 127 if( list.ts() == 0 ) continue; 128 129 // If we can't get the lock retry 130 if( !list.lock.try_lock() ) continue; 131 132 // If list is empty, unlock and retry 133 if( list.ts() == 0 ) { 134 list.lock.unlock(); 135 continue; 136 } 137 138 // Actually pop the list 139 auto node = list.pop(numNonEmpty); 140 assert(node); 141 142 // Unlock and return 143 list.lock.unlock(); 144 assert(numNonEmpty >= 0); 145 #ifndef NO_STATS 146 tls.pick.pop.success++; 147 #endif 148 return node; 149 } 228 150 229 151 return nullptr; 230 152 } 231 232 private:233 node_t * try_pop(unsigned i, unsigned j) {234 #ifndef NO_STATS235 tls.pick.pop.attempt++;236 #endif237 238 // Pick the bet list239 int w = i;240 if( __builtin_expect(lists[j].ts() != 0, true) ) {241 w = (lists[i].ts() < lists[j].ts()) ? i : j;242 }243 244 auto & list = lists[w];245 // If list looks empty retry246 if( list.ts() == 0 ) return nullptr;247 248 // If we can't get the lock retry249 if( !list.lock.try_lock() ) return nullptr;250 251 __attribute__((unused)) int num = numNonEmpty;252 253 // If list is empty, unlock and retry254 if( list.ts() == 0 ) {255 list.lock.unlock();256 return nullptr;257 }258 259 // Actually pop the list260 node_t * node;261 bool emptied;262 std::tie(node, emptied) = list.pop();263 assert(node);264 265 if(emptied) {266 numNonEmpty--;267 size_t qword = w >> 6ull;268 size_t bit = w & 63ull;269 assert((list_mask[qword] & (1ul << bit)) != 0);270 __attribute__((unused)) bool ret = btr(list_mask[qword], bit);271 assert(ret);272 assert((list_mask[qword] & (1ul << bit)) == 0);273 }274 275 // Unlock and return276 list.lock.unlock();277 assert(numNonEmpty >= 0);278 #ifndef NO_STATS279 tls.pick.pop.success++;280 tls.empty.pop.value += num;281 tls.empty.pop.count += 1;282 #endif283 return node;284 }285 153 286 154 private: … … 294 162 struct stat { 295 163 ssize_t diff = 0; 296 size_t push = 0; 297 size_t pop = 0; 298 // size_t value = 0; 299 // size_t count = 0; 164 165 static struct Dif { 166 ssize_t value = 0; 167 size_t num = 0; 168 ssize_t max = 0; 169 } dif; 300 170 }; 301 171 … … 308 178 sentinel_t before; 309 179 sentinel_t after; 310 #ifndef NO_STATS 311 stat s; 312 #endif 313 314 #pragma GCC diagnostic push 315 #pragma GCC diagnostic ignored "-Winvalid-offsetof" 180 stat s; 181 316 182 static constexpr auto fields_offset = offsetof( node_t, _links ); 317 #pragma GCC diagnostic pop318 183 public: 319 184 intrusive_queue_t() … … 321 186 , after {{ head(), nullptr }} 322 187 { 323 /* paranoid */ assert((reinterpret_cast<uintptr_t>( head() ) + fields_offset) == reinterpret_cast<uintptr_t>(&before)); 324 /* paranoid */ assert((reinterpret_cast<uintptr_t>( tail() ) + fields_offset) == reinterpret_cast<uintptr_t>(&after )); 325 /* paranoid */ assert(head()->_links.prev == nullptr); 326 /* paranoid */ assert(head()->_links.next == tail() ); 327 /* paranoid */ assert(tail()->_links.next == nullptr); 328 /* paranoid */ assert(tail()->_links.prev == head() ); 329 /* paranoid */ assert(sizeof(*this) == 128); 330 /* paranoid */ assert((intptr_t(this) % 128) == 0); 331 } 332 333 ~intrusive_queue_t() = default; 188 assert((reinterpret_cast<uintptr_t>( head() ) + fields_offset) == reinterpret_cast<uintptr_t>(&before)); 189 assert((reinterpret_cast<uintptr_t>( tail() ) + fields_offset) == reinterpret_cast<uintptr_t>(&after )); 190 assert(head()->_links.prev == nullptr); 191 assert(head()->_links.next == tail() ); 192 assert(tail()->_links.next == nullptr); 193 assert(tail()->_links.prev == head() ); 194 assert(sizeof(*this) == 128); 195 assert((intptr_t(this) % 128) == 0); 196 } 197 198 ~intrusive_queue_t() { 199 #ifndef NO_STATS 200 stat::dif.value+= s.diff; 201 stat::dif.num ++; 202 stat::dif.max = std::abs(stat::dif.max) > std::abs(s.diff) ? stat::dif.max : s.diff; 203 #endif 204 } 334 205 335 206 inline node_t * head() const { … … 349 220 } 350 221 351 inline bool push(node_t * node) {222 inline void push(node_t * node, std::atomic_int & nonEmpty) { 352 223 assert(lock); 353 224 assert(node->_links.ts != 0); … … 361 232 prev->_links.next = node; 362 233 tail->_links.prev = node; 363 #ifndef NO_STATS364 if(enable_stats) {365 s.diff++;366 s.push++;367 }368 #endif369 234 if(before._links.ts == 0l) { 235 nonEmpty += 1; 370 236 before._links.ts = node->_links.ts; 371 assert(node->_links.prev == this->head());372 return true;373 }374 return false;375 } 376 377 inline std::pair<node_t *, bool> pop() {237 } 238 #ifndef NO_STATS 239 if(enable_stats) s.diff++; 240 #endif 241 } 242 243 inline node_t * pop(std::atomic_int & nonEmpty) { 378 244 assert(lock); 379 245 node_t * head = this->head(); … … 382 248 node_t * node = head->_links.next; 383 249 node_t * next = node->_links.next; 384 if(node == tail) return {nullptr, false};250 if(node == tail) return nullptr; 385 251 386 252 head->_links.next = next; 387 253 next->_links.prev = head; 388 254 389 #ifndef NO_STATS390 if(enable_stats) {391 s.diff--;392 s.pop ++;393 }394 #endif395 255 if(next == tail) { 396 256 before._links.ts = 0l; 397 return {node, true};257 nonEmpty -= 1; 398 258 } 399 259 else { … … 401 261 before._links.ts = next->_links.ts; 402 262 assert(before._links.ts != 0); 403 return {node, false}; 404 } 263 } 264 #ifndef NO_STATS 265 if(enable_stats) s.diff--; 266 #endif 267 return node; 405 268 } 406 269 … … 414 277 415 278 static __attribute__((aligned(128))) thread_local struct TLS { 416 Random rng = { int(rdtscl()) }; 417 pick_stat pick; 418 empty_stat empty; 279 Random rng = { int(rdtscl()) }; 280 pick_stat pick; 419 281 } tls; 420 282 421 public:422 std::atomic_int numNonEmpty = { 0 }; // number of non-empty lists423 std::atomic_size_t list_mask[7] = { {0}, {0}, {0}, {0}, {0}, {0}, {0} }; // which queues are empty424 283 private: 284 std::atomic_int numNonEmpty; // number of non-empty lists 425 285 __attribute__((aligned(64))) std::unique_ptr<intrusive_queue_t []> lists; 426 286 const unsigned numLists; … … 428 288 public: 429 289 static const constexpr size_t sizeof_queue = sizeof(intrusive_queue_t); 430 431 #ifndef NO_STATS 432 static void stats_print(std::ostream & os) { 433 auto it = head; 434 while(it) { 435 it->stats_print_local(os); 436 it = it->next; 437 } 438 } 439 440 static void stats_tls_tally() { 441 global_stats.pick.push.attempt += tls.pick.push.attempt; 442 global_stats.pick.push.success += tls.pick.push.success; 443 global_stats.pick.pop .attempt += tls.pick.pop.attempt; 444 global_stats.pick.pop .success += tls.pick.pop.success; 445 global_stats.pick.pop .mask_attempt += tls.pick.pop.mask_attempt; 446 447 global_stats.qstat.push.value += tls.empty.push.value; 448 global_stats.qstat.push.count += tls.empty.push.count; 449 global_stats.qstat.pop .value += tls.empty.pop .value; 450 global_stats.qstat.pop .count += tls.empty.pop .count; 451 } 452 453 private: 454 static struct GlobalStats { 455 struct { 456 struct { 457 std::atomic_size_t attempt = { 0 }; 458 std::atomic_size_t success = { 0 }; 459 } push; 460 struct { 461 std::atomic_size_t attempt = { 0 }; 462 std::atomic_size_t success = { 0 }; 463 std::atomic_size_t mask_attempt = { 0 }; 464 } pop; 465 } pick; 466 struct { 467 struct { 468 std::atomic_size_t value = { 0 }; 469 std::atomic_size_t count = { 0 }; 470 } push; 471 struct { 472 std::atomic_size_t value = { 0 }; 473 std::atomic_size_t count = { 0 }; 474 } pop; 475 } qstat; 476 } global_stats; 477 478 // Link list of all lists for stats 479 __attribute__((aligned(64))) relaxed_list<node_t> * next = nullptr; 480 481 static relaxed_list<node_t> * head; 482 483 void stats_print_local(std::ostream & os ) { 484 std::cout << "----- Relaxed List Stats -----" << std::endl; 485 { 486 ssize_t diff = 0; 487 size_t num = 0; 488 ssize_t max = 0; 489 490 for(size_t i = 0; i < numLists; i++) { 491 const auto & list = lists[i]; 492 diff+= list.s.diff; 493 num ++; 494 max = std::abs(max) > std::abs(list.s.diff) ? max : list.s.diff; 495 os << "Local Q ops : " << (list.s.push + list.s.pop) << "(" << list.s.push << "i, " << list.s.pop << "o)\n"; 496 } 497 498 os << "Difference : " << ssize_t(double(diff) / num ) << " avg\t" << max << "max" << std::endl; 499 } 500 501 const auto & global = global_stats; 502 503 double push_sur = (100.0 * double(global.pick.push.success) / global.pick.push.attempt); 504 double pop_sur = (100.0 * double(global.pick.pop .success) / global.pick.pop .attempt); 505 double mpop_sur = (100.0 * double(global.pick.pop .success) / global.pick.pop .mask_attempt); 506 507 os << "Push Pick % : " << push_sur << "(" << global.pick.push.success << " / " << global.pick.push.attempt << ")\n"; 508 os << "Pop Pick % : " << pop_sur << "(" << global.pick.pop .success << " / " << global.pick.pop .attempt << ")\n"; 509 os << "TryPop Pick % : " << mpop_sur << "(" << global.pick.pop .success << " / " << global.pick.pop .mask_attempt << ")\n"; 510 511 double avgQ_push = double(global.qstat.push.value) / global.qstat.push.count; 512 double avgQ_pop = double(global.qstat.pop .value) / global.qstat.pop .count; 513 double avgQ = double(global.qstat.push.value + global.qstat.pop .value) / (global.qstat.push.count + global.qstat.pop .count); 514 os << "Push Avg Qs : " << avgQ_push << " (" << global.qstat.push.count << "ops)\n"; 515 os << "Pop Avg Qs : " << avgQ_pop << " (" << global.qstat.pop .count << "ops)\n"; 516 os << "Global Avg Qs : " << avgQ << " (" << (global.qstat.push.count + global.qstat.pop .count) << "ops)\n"; 517 } 518 #endif 519 }; 290 }; -
doc/theses/thierry_delisle_PhD/code/utils.hpp
ra505021 r8c50aed 10 10 #include <unistd.h> 11 11 #include <sys/sysinfo.h> 12 13 #include <x86intrin.h>14 12 15 13 // Barrier from … … 58 56 } 59 57 60 static inlinevoid affinity(int tid) {58 void affinity(int tid) { 61 59 static int cpus = get_nprocs(); 62 60 … … 72 70 73 71 static const constexpr std::size_t cache_line_size = 64; 74 static inlinevoid check_cache_line_size() {72 void check_cache_line_size() { 75 73 std::cout << "Checking cache line size" << std::endl; 76 74 const std::string cache_file = "/sys/devices/system/cpu/cpu0/cache/index0/coherency_line_size"; … … 105 103 return std::chrono::duration_cast<std::chrono::duration<T, Ratio>>(std::chrono::duration<T>(seconds)).count(); 106 104 } 107 108 static inline unsigned rand_bit(unsigned rnum, size_t mask) {109 unsigned bit = mask ? rnum % __builtin_popcountl(mask) : 0;110 #if !defined(__BMI2__)111 uint64_t v = mask; // Input value to find position with rank r.112 unsigned int r = bit + 1;// Input: bit's desired rank [1-64].113 unsigned int s; // Output: Resulting position of bit with rank r [1-64]114 uint64_t a, b, c, d; // Intermediate temporaries for bit count.115 unsigned int t; // Bit count temporary.116 117 // Do a normal parallel bit count for a 64-bit integer,118 // but store all intermediate steps.119 a = v - ((v >> 1) & ~0UL/3);120 b = (a & ~0UL/5) + ((a >> 2) & ~0UL/5);121 c = (b + (b >> 4)) & ~0UL/0x11;122 d = (c + (c >> 8)) & ~0UL/0x101;123 124 125 t = (d >> 32) + (d >> 48);126 // Now do branchless select!127 s = 64;128 s -= ((t - r) & 256) >> 3; r -= (t & ((t - r) >> 8));129 t = (d >> (s - 16)) & 0xff;130 s -= ((t - r) & 256) >> 4; r -= (t & ((t - r) >> 8));131 t = (c >> (s - 8)) & 0xf;132 s -= ((t - r) & 256) >> 5; r -= (t & ((t - r) >> 8));133 t = (b >> (s - 4)) & 0x7;134 s -= ((t - r) & 256) >> 6; r -= (t & ((t - r) >> 8));135 t = (a >> (s - 2)) & 0x3;136 s -= ((t - r) & 256) >> 7; r -= (t & ((t - r) >> 8));137 t = (v >> (s - 1)) & 0x1;138 s -= ((t - r) & 256) >> 8;139 return s - 1;140 #else141 uint64_t picked = _pdep_u64(1ul << bit, mask);142 return picked ? __builtin_ctzl(picked) : 0;143 #endif144 } -
driver/cfa.cc
ra505021 r8c50aed 411 411 args[nargs++] = "-lcfathread"; 412 412 args[nargs++] = "-Wl,--pop-state"; 413 args[nargs++] = "-Wl,--push-state,--no-as-needed";414 413 args[nargs++] = "-lcfa"; 415 args[nargs++] = "-Wl,--pop-state";416 414 args[nargs++] = "-pthread"; 417 415 args[nargs++] = "-ldl"; -
libcfa/prelude/Makefile.am
ra505021 r8c50aed 11 11 ## Created On : Sun May 31 08:54:01 2015 12 12 ## Last Modified By : Peter A. Buhr 13 ## Last Modified On : Mon Feb 3 21:27:18 202014 ## Update Count : 20 813 ## Last Modified On : Wed Dec 14 15:00:35 2016 14 ## Update Count : 205 15 15 ############################################################################### 16 16 … … 36 36 extras.cf : ${srcdir}/extras.regx ${srcdir}/extras.c 37 37 ${AM_V_GEN}gcc ${AM_CFLAGS} -E ${srcdir}/extras.c | grep -f ${srcdir}/extras.regx > extras.cf 38 ${AM_V_GEN}gcc ${AM_CFLAGS} -E ${srcdir}/extras.c | grep -zo -f ${srcdir}/extras.regx2 | tr '\0' '\n' >> extras.cf39 38 40 39 # create forward declarations for gcc builtins -
libcfa/prelude/Makefile.in
ra505021 r8c50aed 1 # Makefile.in generated by automake 1.1 6.1from Makefile.am.1 # Makefile.in generated by automake 1.15 from Makefile.am. 2 2 # @configure_input@ 3 3 4 # Copyright (C) 1994-201 8Free Software Foundation, Inc.4 # Copyright (C) 1994-2014 Free Software Foundation, Inc. 5 5 6 6 # This Makefile.in is free software; the Free Software Foundation … … 331 331 cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \ 332 332 *) \ 333 echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__ maybe_remake_depfiles)'; \334 cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__ maybe_remake_depfiles);; \333 echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \ 334 cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \ 335 335 esac; 336 336 … … 377 377 378 378 379 distdir: $(BUILT_SOURCES) 380 $(MAKE) $(AM_MAKEFLAGS) distdir-am 381 382 distdir-am: $(DISTFILES) 379 distdir: $(DISTFILES) 383 380 @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ 384 381 topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ … … 543 540 extras.cf : ${srcdir}/extras.regx ${srcdir}/extras.c 544 541 ${AM_V_GEN}gcc ${AM_CFLAGS} -E ${srcdir}/extras.c | grep -f ${srcdir}/extras.regx > extras.cf 545 ${AM_V_GEN}gcc ${AM_CFLAGS} -E ${srcdir}/extras.c | grep -zo -f ${srcdir}/extras.regx2 | tr '\0' '\n' >> extras.cf546 542 547 543 # create forward declarations for gcc builtins -
libcfa/prelude/extras.regx
ra505021 r8c50aed 24 24 typedef.* char32_t; 25 25 typedef.* wchar_t; 26 extern.*\*malloc\(.*\).* 27 extern.* free\(.*\).* 28 extern.* exit\(.*\).* 29 extern.* atexit\(.*\).* 30 extern.* abort\(.*\).* 31 extern.* printf\(.*\).* -
libcfa/prelude/prototypes.awk
ra505021 r8c50aed 10 10 # Created On : Sat May 16 07:57:37 2015 11 11 # Last Modified By : Peter A. Buhr 12 # Last Modified On : Sat Feb 8 09:46:58 202013 # Update Count : 3 612 # Last Modified On : Thu Jun 6 20:46:28 2019 13 # Update Count : 34 14 14 # 15 15 … … 17 17 18 18 BEGIN { 19 FS = "[( )]"19 FS = "[( )]" 20 20 # order so string search is longest string 21 21 i=-1 … … 84 84 85 85 /BT_FN/ { 86 for (i = 1; i <= NF; i += 1) {87 if( match($i, "BT_FN") != 0 ) {88 prototypes[$i] = $i89 }86 for (i = 1; i <= NF; i++) { 87 if( match($i, "BT_FN") != 0 ) { 88 prototypes[$i] = $i 89 } 90 90 } 91 }91 } 92 92 93 93 END { … … 103 103 104 104 for ( prototype in prototypes ) { 105 # printf( "//\"%s\"\n", prototype ) 106 if ( index( "BT_LAST", prototype ) == 1 ) { 107 continue 105 # printf( "//\"%s\"\n", prototype ) 106 if ( index( "BT_LAST", prototype ) == 1 ) { 107 continue 108 } # if 109 110 printf( "#define %s(NAME) FUNC_SIMPLE(", prototype ) 111 112 if ( sub( "BT_FN_", "", prototype ) == 0 ) { 113 printf( "\n********** BAD MACRO NAME \"%s\" **********\n", prototype ) 114 exit 0 115 } # if 116 117 # generate function return type as macro 118 for ( t = 0; t < N; t += 1 ) { # find longest match 119 type = types[t]; 120 if ( index( prototype, type ) == 1 ) { # found match 121 printf( "BT_%s, NAME", type ) 122 sub( type, "", prototype ) 123 break; 108 124 } # if 125 } # for 109 126 110 printf( "#define %s(NAME) FUNC_SIMPLE(", prototype ) 111 112 if ( sub( "BT_FN_", "", prototype ) == 0 ) { 113 printf( "\n********** BAD MACRO NAME \"%s\" **********\n", prototype ) 127 # generate function parameter types as macro 128 if ( index( prototype, "VAR" ) != 2 ) { # C-style empty parameters ? 129 for ( p = 0; length( prototype ) > 0; p += 1 ) { # until all parameters types are removed 130 sub( "_", "", prototype) # remove "_" 131 printf( ", ", type ) 132 temp = prototype 133 for ( t = 0; t < N; t += 1 ) { # find longest match 134 type = types[t]; 135 if ( index( prototype, type ) == 1 ) { # found match 136 printf( "BT_%s", type ) 137 sub( type, "", prototype ) 138 break; 139 } # if 140 } # for 141 if ( temp == prototype ) { # no match found for parameter in macro table 142 printf( "\n********** MISSING TYPE \"%s\" **********\n", prototype ) 114 143 exit 0 115 } # if 116 117 # generate function return type as macro 118 for ( t = 0; t < N; t += 1 ) { # find longest match 119 type = types[t]; 120 if ( index( prototype, type ) == 1 ) { # found match 121 printf( "BT_%s, NAME", type ) 122 sub( type, "", prototype ) 123 break; 124 } # if 144 } # if 125 145 } # for 126 127 # generate function parameter types as macro 128 if ( index( prototype, "VAR" ) != 2 ) { # C-style empty parameters ? 129 for ( p = 0; length( prototype ) > 0; p += 1 ) { # until all parameters types are removed 130 sub( "_", "", prototype) # remove "_" 131 printf( ", ", type ) 132 temp = prototype 133 for ( t = 0; t < N; t += 1 ) { # find longest match 134 type = types[t]; 135 if ( index( prototype, type ) == 1 ) { # found match 136 printf( "BT_%s", type ) 137 sub( type, "", prototype ) 138 break; 139 } # if 140 } # for 141 if ( temp == prototype ) { # no match found for parameter in macro table 142 printf( "\n********** MISSING TYPE \"%s\" **********\n", prototype ) 143 exit 0 144 } # if 145 } # for 146 } # if 147 printf( ")\n" ) 146 } # if 147 printf( ")\n" ) 148 148 } # for 149 149 -
libcfa/src/assert.cfa
ra505021 r8c50aed 10 10 // Created On : Mon Nov 28 12:27:26 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : T ue Feb 4 13:00:18 202013 // Update Count : 612 // Last Modified On : Thu Nov 21 17:09:26 2019 13 // Update Count : 5 14 14 // 15 15 … … 26 26 27 27 // called by macro assert in assert.h 28 void __assert_fail( const char assertion[], const char file[], unsigned int line, const char function[]) {28 void __assert_fail( const char *assertion, const char *file, unsigned int line, const char *function ) { 29 29 __cfaabi_bits_print_safe( STDERR_FILENO, CFA_ASSERT_FMT ".\n", assertion, __progname, function, line, file ); 30 30 abort(); … … 32 32 33 33 // called by macro assertf 34 void __assert_fail_f( const char assertion[], const char file[], unsigned int line, const char function[], const char fmt[], ... ) {34 void __assert_fail_f( const char *assertion, const char *file, unsigned int line, const char *function, const char *fmt, ... ) { 35 35 __cfaabi_bits_acquire(); 36 36 __cfaabi_bits_print_nolock( STDERR_FILENO, CFA_ASSERT_FMT ": ", assertion, __progname, function, line, file ); -
libcfa/src/bits/debug.cfa
ra505021 r8c50aed 10 10 // Created On : Thu Mar 30 12:30:01 2017 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : T ue Feb 4 13:03:16 202013 // Update Count : 1 112 // Last Modified On : Thu Nov 21 17:16:30 2019 13 // Update Count : 10 14 14 // 15 15 … … 27 27 28 28 extern "C" { 29 void __cfaabi_bits_write( int fd, const char in_buffer[], int len ) { 29 30 void __cfaabi_bits_write( int fd, const char *in_buffer, int len ) { 30 31 // ensure all data is written 31 32 for ( int count = 0, retcode; count < len; count += retcode ) { -
libcfa/src/bits/debug.hfa
ra505021 r8c50aed 10 10 // Created On : Mon Nov 28 12:27:26 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : T ue Feb 4 12:29:21 202013 // Update Count : 912 // Last Modified On : Thu Nov 21 17:06:58 2019 13 // Update Count : 8 14 14 // 15 15 … … 21 21 #define __cfaabi_dbg_ctx __PRETTY_FUNCTION__ 22 22 #define __cfaabi_dbg_ctx2 , __PRETTY_FUNCTION__ 23 #define __cfaabi_dbg_ctx_param const char caller[]24 #define __cfaabi_dbg_ctx_param2 , const char caller[]23 #define __cfaabi_dbg_ctx_param const char * caller 24 #define __cfaabi_dbg_ctx_param2 , const char * caller 25 25 #else 26 26 #define __cfaabi_dbg_debug_do(...) … … 38 38 #include <stdio.h> 39 39 40 extern void __cfaabi_bits_write( int fd, const char buffer[], int len );40 extern void __cfaabi_bits_write( int fd, const char *buffer, int len ); 41 41 extern void __cfaabi_bits_acquire(); 42 42 extern void __cfaabi_bits_release(); -
libcfa/src/bits/locks.hfa
ra505021 r8c50aed 10 10 // Created On : Tue Oct 31 15:14:38 2017 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Feb 4 13:03:19 202013 // Update Count : 1 112 // Last Modified On : Sat Aug 11 15:42:24 2018 13 // Update Count : 10 14 14 // 15 15 … … 54 54 55 55 #ifdef __CFA_DEBUG__ 56 void __cfaabi_dbg_record(__spinlock_t & this, const char prev_name[]);56 void __cfaabi_dbg_record(__spinlock_t & this, const char * prev_name); 57 57 #else 58 58 #define __cfaabi_dbg_record(x, y) -
libcfa/src/concurrency/coroutine.cfa
ra505021 r8c50aed 10 10 // Created On : Mon Nov 28 12:27:26 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : T ue Feb 4 12:29:25 202013 // Update Count : 1 612 // Last Modified On : Thu Dec 5 14:37:29 2019 13 // Update Count : 15 14 14 // 15 15 … … 89 89 } 90 90 91 void ?{}( coroutine_desc & this, const char name[], void * storage, size_t storageSize ) with( this ) {91 void ?{}( coroutine_desc & this, const char * name, void * storage, size_t storageSize ) with( this ) { 92 92 (this.context){0p, 0p}; 93 93 (this.stack){storage, storageSize}; -
libcfa/src/concurrency/coroutine.hfa
ra505021 r8c50aed 10 10 // Created On : Mon Nov 28 12:27:26 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Feb 4 12:29:26 202013 // Update Count : 1 112 // Last Modified On : Tue Dec 3 22:47:58 2019 13 // Update Count : 10 14 14 // 15 15 … … 35 35 // void ^?{}( coStack_t & this ); 36 36 37 void ?{}( coroutine_desc & this, const char name[], void * storage, size_t storageSize );37 void ?{}( coroutine_desc & this, const char * name, void * storage, size_t storageSize ); 38 38 void ^?{}( coroutine_desc & this ); 39 39 … … 41 41 static inline void ?{}( coroutine_desc & this, size_t stackSize) { this{ "Anonymous Coroutine", 0p, stackSize }; } 42 42 static inline void ?{}( coroutine_desc & this, void * storage, size_t storageSize ) { this{ "Anonymous Coroutine", storage, storageSize }; } 43 static inline void ?{}( coroutine_desc & this, const char name[]) { this{ name, 0p, 0 }; }44 static inline void ?{}( coroutine_desc & this, const char name[], size_t stackSize ) { this{ name, 0p, stackSize }; }43 static inline void ?{}( coroutine_desc & this, const char * name) { this{ name, 0p, 0 }; } 44 static inline void ?{}( coroutine_desc & this, const char * name, size_t stackSize ) { this{ name, 0p, stackSize }; } 45 45 46 46 //----------------------------------------------------------------------------- -
libcfa/src/concurrency/kernel.cfa
ra505021 r8c50aed 10 10 // Created On : Tue Jan 17 12:27:26 2017 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : T ue Feb 4 13:03:15202013 // Update Count : 5 812 // Last Modified On : Thu Jan 30 22:55:50 2020 13 // Update Count : 56 14 14 // 15 15 … … 210 210 static void * CtxInvokeProcessor(void * arg); 211 211 212 void ?{}(processor & this, const char name[], cluster & cltr) with( this ) {212 void ?{}(processor & this, const char * name, cluster & cltr) with( this ) { 213 213 this.name = name; 214 214 this.cltr = &cltr; … … 244 244 } 245 245 246 void ?{}(cluster & this, const char name[], Duration preemption_rate) with( this ) {246 void ?{}(cluster & this, const char * name, Duration preemption_rate) with( this ) { 247 247 this.name = name; 248 248 this.preemption_rate = preemption_rate; … … 459 459 } 460 460 461 static void Abort( int ret, const char func[]) {461 static void Abort( int ret, const char * func ) { 462 462 if ( ret ) { // pthread routines return errno values 463 463 abort( "%s : internal error, error(%d) %s.", func, ret, strerror( ret ) ); … … 960 960 __cfaabi_dbg_debug_do( 961 961 extern "C" { 962 void __cfaabi_dbg_record(__spinlock_t & this, const char prev_name[]) {962 void __cfaabi_dbg_record(__spinlock_t & this, const char * prev_name) { 963 963 this.prev_name = prev_name; 964 964 this.prev_thrd = kernelTLS.this_thread; -
libcfa/src/concurrency/kernel.hfa
ra505021 r8c50aed 10 10 // Created On : Tue Jan 17 12:27:26 2017 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Feb 4 12:29:26 202013 // Update Count : 2212 // Last Modified On : Wed Dec 4 07:54:51 2019 13 // Update Count : 18 14 14 // 15 15 … … 101 101 }; 102 102 103 void ?{}(processor & this, const char name[], struct cluster & cltr);103 void ?{}(processor & this, const char * name, struct cluster & cltr); 104 104 void ^?{}(processor & this); 105 105 106 106 static inline void ?{}(processor & this) { this{ "Anonymous Processor", *mainCluster}; } 107 107 static inline void ?{}(processor & this, struct cluster & cltr) { this{ "Anonymous Processor", cltr}; } 108 static inline void ?{}(processor & this, const char name[]) { this{name, *mainCluster }; }108 static inline void ?{}(processor & this, const char * name) { this{name, *mainCluster }; } 109 109 110 110 static inline [processor *&, processor *& ] __get( processor & this ) /*__attribute__((const))*/ { return this.node.[next, prev]; } … … 144 144 extern Duration default_preemption(); 145 145 146 void ?{} (cluster & this, const char name[], Duration preemption_rate);146 void ?{} (cluster & this, const char * name, Duration preemption_rate); 147 147 void ^?{}(cluster & this); 148 148 149 149 static inline void ?{} (cluster & this) { this{"Anonymous Cluster", default_preemption()}; } 150 150 static inline void ?{} (cluster & this, Duration preemption_rate) { this{"Anonymous Cluster", preemption_rate}; } 151 static inline void ?{} (cluster & this, const char name[]) { this{name, default_preemption()}; }151 static inline void ?{} (cluster & this, const char * name) { this{name, default_preemption()}; } 152 152 153 153 static inline [cluster *&, cluster *& ] __get( cluster & this ) /*__attribute__((const))*/ { return this.node.[next, prev]; } -
libcfa/src/exception.c
ra505021 r8c50aed 248 248 } 249 249 250 #pragma GCC push_options 251 #pragma GCC optimize("O0") 252 250 #if defined(PIC) 251 #warning Exceptions not yet supported when using Position-Independent Code 252 __attribute__((noinline)) 253 void __cfaabi_ehm__try_terminate(void (*try_block)(), 254 void (*catch_block)(int index, exception_t * except), 255 __attribute__((unused)) int (*match_block)(exception_t * except)) { 256 abort(); 257 } 258 #else // PIC 253 259 // This is our personality routine. For every stack frame annotated with 254 260 // ".cfi_personality 0x3,__gcfa_personality_v0" this function will be called twice when unwinding. … … 425 431 426 432 // Setup the personality routine and exception table. 427 #ifdef __PIC__428 asm volatile (".cfi_personality 0x9b,CFA.ref.__gcfa_personality_v0");429 asm volatile (".cfi_lsda 0x1b, .LLSDACFA2");430 #else431 433 asm volatile (".cfi_personality 0x3,__gcfa_personality_v0"); 432 434 asm volatile (".cfi_lsda 0x3, .LLSDACFA2"); 433 #endif434 435 435 436 // Label which defines the start of the area for which the handler is setup. … … 463 464 // have a single call to the try routine. 464 465 465 #ifdef __PIC__466 #if defined( __i386 ) || defined( __x86_64 )467 asm (468 // HEADER469 ".LFECFA1:\n"470 " .globl __gcfa_personality_v0\n"471 " .section .gcc_except_table,\"a\",@progbits\n"472 // TABLE HEADER (important field is the BODY length at the end)473 ".LLSDACFA2:\n"474 " .byte 0xff\n"475 " .byte 0xff\n"476 " .byte 0x1\n"477 " .uleb128 .LLSDACSECFA2-.LLSDACSBCFA2\n"478 // BODY (language specific data)479 // This uses language specific data and can be modified arbitrarily480 // We use handled area offset, handled area length,481 // handler landing pad offset and 1 (action code, gcc seems to use 0).482 ".LLSDACSBCFA2:\n"483 " .uleb128 .TRYSTART-__cfaabi_ehm__try_terminate\n"484 " .uleb128 .TRYEND-.TRYSTART\n"485 " .uleb128 .CATCH-__cfaabi_ehm__try_terminate\n"486 " .uleb128 1\n"487 ".LLSDACSECFA2:\n"488 // TABLE FOOTER489 " .text\n"490 " .size __cfaabi_ehm__try_terminate, .-__cfaabi_ehm__try_terminate\n"491 );492 493 // Somehow this piece of helps with the resolution of debug symbols.494 __attribute__((unused)) static const int dummy = 0;495 496 asm (497 // Add a hidden symbol which points at the function.498 " .hidden CFA.ref.__gcfa_personality_v0\n"499 " .weak CFA.ref.__gcfa_personality_v0\n"500 // No clue what this does specifically501 " .section .data.rel.local.CFA.ref.__gcfa_personality_v0,\"awG\",@progbits,CFA.ref.__gcfa_personality_v0,comdat\n"502 " .align 8\n"503 " .type CFA.ref.__gcfa_personality_v0, @object\n"504 " .size CFA.ref.__gcfa_personality_v0, 8\n"505 "CFA.ref.__gcfa_personality_v0:\n"506 #if defined( __x86_64 )507 " .quad __gcfa_personality_v0\n"508 #else // then __i386509 " .long __gcfa_personality_v0\n"510 #endif511 );512 #else513 #error Exception Handling: unknown architecture for position independent code.514 #endif // __i386 || __x86_64515 #else // __PIC__516 466 #if defined( __i386 ) || defined( __x86_64 ) 517 467 asm ( … … 541 491 " .size __cfaabi_ehm__try_terminate, .-__cfaabi_ehm__try_terminate\n" 542 492 " .ident \"GCC: (Ubuntu 6.2.0-3ubuntu11~16.04) 6.2.0 20160901\"\n" 543 " .section .note.GNU-stack,\"x\",@progbits\n"493 // " .section .note.GNU-stack,\"x\",@progbits\n" 544 494 ); 545 #else546 #error Exception Handling: unknown architecture for position dependent code.547 495 #endif // __i386 || __x86_64 548 #endif // __PIC__ 549 550 #pragma GCC pop_options 496 #endif // PIC -
libcfa/src/fstream.cfa
ra505021 r8c50aed 10 10 // Created On : Wed May 27 17:56:53 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Fri Feb 7 19:01:01 202013 // Update Count : 3 6312 // Last Modified On : Fri Nov 29 06:56:46 2019 13 // Update Count : 355 14 14 // 15 15 … … 32 32 33 33 void ?{}( ofstream & os, void * file ) { 34 os.$file = file; 35 os.$sepDefault = true; 36 os.$sepOnOff = false; 37 os.$nlOnOff = true; 38 os.$prt = false; 39 os.$sawNL = false; 40 $sepSetCur( os, sepGet( os ) ); 34 os.file = file; 35 os.sepDefault = true; 36 os.sepOnOff = false; 37 os.nlOnOff = true; 38 os.prt = false; 39 os.sawNL = false; 41 40 sepSet( os, " " ); 41 sepSetCur( os, sepGet( os ) ); 42 42 sepSetTuple( os, ", " ); 43 43 } // ?{} 44 44 45 45 // private 46 bool $sepPrt( ofstream & os ) { $setNL( os, false ); return os.$sepOnOff; }47 void $sepReset( ofstream & os ) { os.$sepOnOff = os.$sepDefault; }48 void $sepReset( ofstream & os, bool reset ) { os.$sepDefault = reset; os.$sepOnOff = os.$sepDefault; }49 const char * $sepGetCur( ofstream & os ) { return os.$sepCur; }50 void $sepSetCur( ofstream & os, const char sepCur[] ) { os.$sepCur = sepCur; }51 bool $getNL( ofstream & os ) { return os.$sawNL; }52 void $setNL( ofstream & os, bool state ) { os.$sawNL = state; }53 bool $getANL( ofstream & os ) { return os.$nlOnOff; }54 bool $getPrt( ofstream & os ) { return os.$prt; }55 void $setPrt( ofstream & os, bool state ) { os.$prt = state; }46 bool sepPrt( ofstream & os ) { setNL( os, false ); return os.sepOnOff; } 47 void sepReset( ofstream & os ) { os.sepOnOff = os.sepDefault; } 48 void sepReset( ofstream & os, bool reset ) { os.sepDefault = reset; os.sepOnOff = os.sepDefault; } 49 const char * sepGetCur( ofstream & os ) { return os.sepCur; } 50 void sepSetCur( ofstream & os, const char * sepCur ) { os.sepCur = sepCur; } 51 bool getNL( ofstream & os ) { return os.sawNL; } 52 void setNL( ofstream & os, bool state ) { os.sawNL = state; } 53 bool getANL( ofstream & os ) { return os.nlOnOff; } 54 bool getPrt( ofstream & os ) { return os.prt; } 55 void setPrt( ofstream & os, bool state ) { os.prt = state; } 56 56 57 57 // public 58 void ?{}( ofstream & os ) { os. $file = 0p; }59 60 void ?{}( ofstream & os, const char name[], const char mode[]) {58 void ?{}( ofstream & os ) { os.file = 0; } 59 60 void ?{}( ofstream & os, const char * name, const char * mode ) { 61 61 open( os, name, mode ); 62 62 } // ?{} 63 63 64 void ?{}( ofstream & os, const char name[]) {64 void ?{}( ofstream & os, const char * name ) { 65 65 open( os, name, "w" ); 66 66 } // ?{} … … 70 70 } // ^?{} 71 71 72 void sepOn( ofstream & os ) { os. $sepOnOff = ! $getNL( os ); }73 void sepOff( ofstream & os ) { os. $sepOnOff = false; }72 void sepOn( ofstream & os ) { os.sepOnOff = ! getNL( os ); } 73 void sepOff( ofstream & os ) { os.sepOnOff = false; } 74 74 75 75 bool sepDisable( ofstream & os ) { 76 bool temp = os. $sepDefault;77 os. $sepDefault = false;78 $sepReset( os );76 bool temp = os.sepDefault; 77 os.sepDefault = false; 78 sepReset( os ); 79 79 return temp; 80 80 } // sepDisable 81 81 82 82 bool sepEnable( ofstream & os ) { 83 bool temp = os. $sepDefault;84 os. $sepDefault = true;85 if ( os. $sepOnOff ) $sepReset( os );// start of line ?83 bool temp = os.sepDefault; 84 os.sepDefault = true; 85 if ( os.sepOnOff ) sepReset( os ); // start of line ? 86 86 return temp; 87 87 } // sepEnable 88 88 89 void nlOn( ofstream & os ) { os. $nlOnOff = true; }90 void nlOff( ofstream & os ) { os. $nlOnOff = false; }91 92 const char * sepGet( ofstream & os ) { return os. $separator; }93 void sepSet( ofstream & os, const char s[]) {89 void nlOn( ofstream & os ) { os.nlOnOff = true; } 90 void nlOff( ofstream & os ) { os.nlOnOff = false; } 91 92 const char * sepGet( ofstream & os ) { return os.separator; } 93 void sepSet( ofstream & os, const char * s ) { 94 94 assert( s ); 95 strncpy( os. $separator, s, sepSize - 1 );96 os. $separator[sepSize - 1] = '\0';95 strncpy( os.separator, s, sepSize - 1 ); 96 os.separator[sepSize - 1] = '\0'; 97 97 } // sepSet 98 98 99 const char * sepGetTuple( ofstream & os ) { return os. $tupleSeparator; }100 void sepSetTuple( ofstream & os, const char s[]) {99 const char * sepGetTuple( ofstream & os ) { return os.tupleSeparator; } 100 void sepSetTuple( ofstream & os, const char * s ) { 101 101 assert( s ); 102 strncpy( os. $tupleSeparator, s, sepSize - 1 );103 os. $tupleSeparator[sepSize - 1] = '\0';102 strncpy( os.tupleSeparator, s, sepSize - 1 ); 103 os.tupleSeparator[sepSize - 1] = '\0'; 104 104 } // sepSet 105 105 106 106 void ends( ofstream & os ) { 107 if ( $getANL( os ) ) nl( os );108 else $setPrt( os, false ); // turn off107 if ( getANL( os ) ) nl( os ); 108 else setPrt( os, false ); // turn off 109 109 if ( &os == &exit ) exit( EXIT_FAILURE ); 110 110 if ( &os == &abort ) abort(); … … 112 112 113 113 int fail( ofstream & os ) { 114 return os. $file == 0 || ferror( (FILE *)(os.$file) );114 return os.file == 0 || ferror( (FILE *)(os.file) ); 115 115 } // fail 116 116 117 117 int flush( ofstream & os ) { 118 return fflush( (FILE *)(os. $file) );118 return fflush( (FILE *)(os.file) ); 119 119 } // flush 120 120 121 void open( ofstream & os, const char name[], const char mode[]) {121 void open( ofstream & os, const char * name, const char * mode ) { 122 122 FILE * file = fopen( name, mode ); 123 123 #ifdef __CFA_DEBUG__ 124 if ( file == 0 p) {124 if ( file == 0 ) { 125 125 abort | IO_MSG "open output file \"" | name | "\"" | nl | strerror( errno ); 126 126 } // if … … 129 129 } // open 130 130 131 void open( ofstream & os, const char name[]) {131 void open( ofstream & os, const char * name ) { 132 132 open( os, name, "w" ); 133 133 } // open 134 134 135 135 void close( ofstream & os ) { 136 if ( (FILE *)(os. $file) == stdout || (FILE *)(os.$file) == stderr ) return;137 138 if ( fclose( (FILE *)(os. $file) ) == EOF ) {136 if ( (FILE *)(os.file) == stdout || (FILE *)(os.file) == stderr ) return; 137 138 if ( fclose( (FILE *)(os.file) ) == EOF ) { 139 139 abort | IO_MSG "close output" | nl | strerror( errno ); 140 140 } // if 141 141 } // close 142 142 143 ofstream & write( ofstream & os, const char data[], size_t size ) {143 ofstream & write( ofstream & os, const char * data, size_t size ) { 144 144 if ( fail( os ) ) { 145 145 abort | IO_MSG "attempt write I/O on failed stream"; 146 146 } // if 147 147 148 if ( fwrite( data, 1, size, (FILE *)(os. $file) ) != size ) {148 if ( fwrite( data, 1, size, (FILE *)(os.file) ) != size ) { 149 149 abort | IO_MSG "write" | nl | strerror( errno ); 150 150 } // if … … 155 155 va_list args; 156 156 va_start( args, format ); 157 int len = vfprintf( (FILE *)(os. $file), format, args );157 int len = vfprintf( (FILE *)(os.file), format, args ); 158 158 if ( len == EOF ) { 159 if ( ferror( (FILE *)(os. $file) ) ) {159 if ( ferror( (FILE *)(os.file) ) ) { 160 160 abort | IO_MSG "invalid write"; 161 161 } // if … … 163 163 va_end( args ); 164 164 165 $setPrt( os, true );// called in output cascade166 $sepReset( os );// reset separator165 setPrt( os, true ); // called in output cascade 166 sepReset( os ); // reset separator 167 167 return len; 168 168 } // fmt … … 184 184 // private 185 185 void ?{}( ifstream & is, void * file ) { 186 is. $file = file;187 is. $nlOnOff = false;186 is.file = file; 187 is.nlOnOff = false; 188 188 } // ?{} 189 189 190 190 // public 191 void ?{}( ifstream & is ) { is.$file = 0p; }192 193 void ?{}( ifstream & is, const char name[], const char mode[]) {191 void ?{}( ifstream & is ) { is.file = 0; } 192 193 void ?{}( ifstream & is, const char * name, const char * mode ) { 194 194 open( is, name, mode ); 195 195 } // ?{} 196 196 197 void ?{}( ifstream & is, const char name[]) {197 void ?{}( ifstream & is, const char * name ) { 198 198 open( is, name, "r" ); 199 199 } // ?{} … … 203 203 } // ^?{} 204 204 205 void nlOn( ifstream & os ) { os. $nlOnOff = true; }206 void nlOff( ifstream & os ) { os. $nlOnOff = false; }207 bool getANL( ifstream & os ) { return os. $nlOnOff; }205 void nlOn( ifstream & os ) { os.nlOnOff = true; } 206 void nlOff( ifstream & os ) { os.nlOnOff = false; } 207 bool getANL( ifstream & os ) { return os.nlOnOff; } 208 208 209 209 int fail( ifstream & is ) { 210 return is. $file == 0p || ferror( (FILE *)(is.$file) );210 return is.file == 0 || ferror( (FILE *)(is.file) ); 211 211 } // fail 212 212 213 213 int eof( ifstream & is ) { 214 return feof( (FILE *)(is. $file) );214 return feof( (FILE *)(is.file) ); 215 215 } // eof 216 216 217 void open( ifstream & is, const char name[], const char mode[]) {217 void open( ifstream & is, const char * name, const char * mode ) { 218 218 FILE * file = fopen( name, mode ); 219 219 #ifdef __CFA_DEBUG__ 220 if ( file == 0 p) {220 if ( file == 0 ) { 221 221 abort | IO_MSG "open input file \"" | name | "\"" | nl | strerror( errno ); 222 222 } // if 223 223 #endif // __CFA_DEBUG__ 224 is. $file = file;225 } // open 226 227 void open( ifstream & is, const char name[]) {224 is.file = file; 225 } // open 226 227 void open( ifstream & is, const char * name ) { 228 228 open( is, name, "r" ); 229 229 } // open 230 230 231 231 void close( ifstream & is ) { 232 if ( (FILE *)(is. $file) == stdin ) return;233 234 if ( fclose( (FILE *)(is. $file) ) == EOF ) {232 if ( (FILE *)(is.file) == stdin ) return; 233 234 if ( fclose( (FILE *)(is.file) ) == EOF ) { 235 235 abort | IO_MSG "close input" | nl | strerror( errno ); 236 236 } // if … … 242 242 } // if 243 243 244 if ( fread( data, size, 1, (FILE *)(is. $file) ) == 0 ) {244 if ( fread( data, size, 1, (FILE *)(is.file) ) == 0 ) { 245 245 abort | IO_MSG "read" | nl | strerror( errno ); 246 246 } // if … … 253 253 } // if 254 254 255 if ( ungetc( c, (FILE *)(is. $file) ) == EOF ) {255 if ( ungetc( c, (FILE *)(is.file) ) == EOF ) { 256 256 abort | IO_MSG "ungetc" | nl | strerror( errno ); 257 257 } // if … … 263 263 264 264 va_start( args, format ); 265 int len = vfscanf( (FILE *)(is. $file), format, args );265 int len = vfscanf( (FILE *)(is.file), format, args ); 266 266 if ( len == EOF ) { 267 if ( ferror( (FILE *)(is. $file) ) ) {267 if ( ferror( (FILE *)(is.file) ) ) { 268 268 abort | IO_MSG "invalid read"; 269 269 } // if -
libcfa/src/fstream.hfa
ra505021 r8c50aed 10 10 // Created On : Wed May 27 17:56:53 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Mon Feb 17 08:29:23 202013 // Update Count : 1 7512 // Last Modified On : Fri Nov 29 06:56:02 2019 13 // Update Count : 168 14 14 // 15 15 … … 24 24 enum { sepSize = 16 }; 25 25 struct ofstream { 26 void * $file;27 bool $sepDefault;28 bool $sepOnOff;29 bool $nlOnOff;30 bool $prt; // print text31 bool $sawNL;32 const char * $sepCur;33 char $separator[sepSize];34 char $tupleSeparator[sepSize];26 void * file; 27 bool sepDefault; 28 bool sepOnOff; 29 bool nlOnOff; 30 bool prt; // print text 31 bool sawNL; 32 const char * sepCur; 33 char separator[sepSize]; 34 char tupleSeparator[sepSize]; 35 35 }; // ofstream 36 36 37 37 // private 38 bool $sepPrt( ofstream & );39 void $sepReset( ofstream & );40 void $sepReset( ofstream &, bool );41 const char * $sepGetCur( ofstream & );42 void $sepSetCur( ofstream &, const char []);43 bool $getNL( ofstream & );44 void $setNL( ofstream &, bool );45 bool $getANL( ofstream & );46 bool $getPrt( ofstream & );47 void $setPrt( ofstream &, bool );38 bool sepPrt( ofstream & ); 39 void sepReset( ofstream & ); 40 void sepReset( ofstream &, bool ); 41 const char * sepGetCur( ofstream & ); 42 void sepSetCur( ofstream &, const char * ); 43 bool getNL( ofstream & ); 44 void setNL( ofstream &, bool ); 45 bool getANL( ofstream & ); 46 bool getPrt( ofstream & ); 47 void setPrt( ofstream &, bool ); 48 48 49 49 // public … … 56 56 57 57 const char * sepGet( ofstream & ); 58 void sepSet( ofstream &, const char []);58 void sepSet( ofstream &, const char * ); 59 59 const char * sepGetTuple( ofstream & ); 60 void sepSetTuple( ofstream &, const char []);60 void sepSetTuple( ofstream &, const char * ); 61 61 62 62 void ends( ofstream & os ); 63 63 int fail( ofstream & ); 64 64 int flush( ofstream & ); 65 void open( ofstream &, const char name[], const char mode[]);66 void open( ofstream &, const char name[]);65 void open( ofstream &, const char * name, const char * mode ); 66 void open( ofstream &, const char * name ); 67 67 void close( ofstream & ); 68 ofstream & write( ofstream &, const char data[], size_t size );69 int fmt( ofstream &, const char format[], ... ) __attribute__(( format(printf, 2, 3) ));68 ofstream & write( ofstream &, const char * data, size_t size ); 69 int fmt( ofstream &, const char format[], ... ); 70 70 71 71 void ?{}( ofstream & os ); 72 void ?{}( ofstream & os, const char name[], const char mode[]);73 void ?{}( ofstream & os, const char name[]);72 void ?{}( ofstream & os, const char * name, const char * mode ); 73 void ?{}( ofstream & os, const char * name ); 74 74 void ^?{}( ofstream & os ); 75 75 … … 82 82 83 83 struct ifstream { 84 void * $file;85 bool $nlOnOff;84 void * file; 85 bool nlOnOff; 86 86 }; // ifstream 87 87 … … 92 92 int fail( ifstream & is ); 93 93 int eof( ifstream & is ); 94 void open( ifstream & is, const char name[], const char mode[]);95 void open( ifstream & is, const char name[]);94 void open( ifstream & is, const char * name, const char * mode ); 95 void open( ifstream & is, const char * name ); 96 96 void close( ifstream & is ); 97 97 ifstream & read( ifstream & is, char * data, size_t size ); 98 98 ifstream & ungetc( ifstream & is, char c ); 99 int fmt( ifstream &, const char format[], ... ) __attribute__(( format(scanf, 2, 3) ));99 int fmt( ifstream &, const char format[], ... ); 100 100 101 101 void ?{}( ifstream & is ); 102 void ?{}( ifstream & is, const char name[], const char mode[]);103 void ?{}( ifstream & is, const char name[]);102 void ?{}( ifstream & is, const char * name, const char * mode ); 103 void ?{}( ifstream & is, const char * name ); 104 104 void ^?{}( ifstream & is ); 105 105 -
libcfa/src/gmp.hfa
ra505021 r8c50aed 10 10 // Created On : Tue Apr 19 08:43:43 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : S un Feb 9 09:56:54 202013 // Update Count : 3112 // Last Modified On : Sat Jul 13 15:25:05 2019 13 // Update Count : 27 14 14 // 15 15 … … 24 24 25 25 static inline { 26 // constructor , zero_t/one_t are unnecessary because of relationship with signed/unsigned int26 // constructor 27 27 void ?{}( Int & this ) { mpz_init( this.mpz ); } 28 28 void ?{}( Int & this, Int init ) { mpz_init_set( this.mpz, init.mpz ); } 29 void ?{}( Int & this, zero_t ) { mpz_init_set_si( this.mpz, 0 ); } 30 void ?{}( Int & this, one_t ) { mpz_init_set_si( this.mpz, 1 ); } 29 31 void ?{}( Int & this, signed long int init ) { mpz_init_set_si( this.mpz, init ); } 30 32 void ?{}( Int & this, unsigned long int init ) { mpz_init_set_ui( this.mpz, init ); } 31 void ?{}( Int & this, const char val[]) { if ( mpz_init_set_str( this.mpz, val, 0 ) ) abort(); }33 void ?{}( Int & this, const char * val ) { if ( mpz_init_set_str( this.mpz, val, 0 ) ) abort(); } 32 34 void ^?{}( Int & this ) { mpz_clear( this.mpz ); } 33 35 … … 35 37 Int ?`mp( signed long int init ) { return (Int){ init }; } 36 38 Int ?`mp( unsigned long int init ) { return (Int){ init }; } 37 Int ?`mp( const char init[]) { return (Int){ init }; }39 Int ?`mp( const char * init ) { return (Int){ init }; } 38 40 39 41 // assignment … … 41 43 Int ?=?( Int & lhs, long int rhs ) { mpz_set_si( lhs.mpz, rhs ); return lhs; } 42 44 Int ?=?( Int & lhs, unsigned long int rhs ) { mpz_set_ui( lhs.mpz, rhs ); return lhs; } 43 Int ?=?( Int & lhs, const char rhs[]) { if ( mpz_set_str( lhs.mpz, rhs, 0 ) ) { abort | "invalid string conversion"; } return lhs; }45 Int ?=?( Int & lhs, const char * rhs ) { if ( mpz_set_str( lhs.mpz, rhs, 0 ) ) { abort | "invalid string conversion"; } return lhs; } 44 46 45 47 char ?=?( char & lhs, Int rhs ) { char val = mpz_get_si( rhs.mpz ); lhs = val; return lhs; } … … 263 265 forall( dtype ostype | ostream( ostype ) ) { 264 266 ostype & ?|?( ostype & os, Int mp ) { 265 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );267 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 266 268 gmp_printf( "%Zd", mp.mpz ); 267 269 sepOn( os ); -
libcfa/src/heap.cfa
ra505021 r8c50aed 10 10 // Created On : Tue Dec 19 21:58:35 2017 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Feb 4 10:04:51 202013 // Update Count : 64 812 // Last Modified On : Sun Dec 8 21:01:31 2019 13 // Update Count : 647 14 14 // 15 15 … … 380 380 381 381 382 static inline void checkHeader( bool check, const char name[], void * addr ) {382 static inline void checkHeader( bool check, const char * name, void * addr ) { 383 383 if ( unlikely( check ) ) { // bad address ? 384 384 abort( "Attempt to %s storage %p with address outside the heap.\n" … … 418 418 419 419 420 static inline bool headers( const char name[]__attribute__(( unused )), void * addr, HeapManager.Storage.Header *& header, HeapManager.FreeHeader *& freeElem, size_t & size, size_t & alignment ) with ( heapManager ) {420 static inline bool headers( const char * name __attribute__(( unused )), void * addr, HeapManager.Storage.Header *& header, HeapManager.FreeHeader *& freeElem, size_t & size, size_t & alignment ) with ( heapManager ) { 421 421 header = headerAddr( addr ); 422 422 -
libcfa/src/interpose.cfa
ra505021 r8c50aed 10 10 // Created On : Wed Mar 29 16:10:31 2017 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Mon Feb 17 10:18:53202013 // Update Count : 1 6612 // Last Modified On : Thu Jan 30 17:47:32 2020 13 // Update Count : 156 14 14 // 15 15 … … 29 29 #include "bits/signal.hfa" // sigHandler_? 30 30 #include "startup.hfa" // STARTUP_PRIORITY_CORE 31 #include <assert.h>32 31 33 32 //============================================================================================= … … 41 40 42 41 typedef void (* generic_fptr_t)(void); 43 generic_fptr_t interpose_symbol( const char symbol[], const char version[]) {42 generic_fptr_t interpose_symbol( const char * symbol, const char * version ) { 44 43 const char * error; 45 44 … … 146 145 extern "C" { 147 146 void abort( void ) __attribute__(( __nothrow__, __leaf__, __noreturn__ )) { 148 abort( false, "%s", "" );147 abort( false, NULL ); // FIX ME: 0p does not work 149 148 } 150 149 … … 162 161 163 162 void * kernel_abort( void ) __attribute__(( __nothrow__, __leaf__, __weak__ )) { return 0p; } 164 void kernel_abort_msg( void * data, char buffer[], int size ) __attribute__(( __nothrow__, __leaf__, __weak__ )) {}163 void kernel_abort_msg( void * data, char * buffer, int size ) __attribute__(( __nothrow__, __leaf__, __weak__ )) {} 165 164 // See concurrency/kernel.cfa for strong definition used in multi-processor mode. 166 165 int kernel_abort_lastframe( void ) __attribute__(( __nothrow__, __leaf__, __weak__ )) { return 4; } … … 170 169 171 170 static void __cfaabi_backtrace( int start ) { 172 enum { Frames = 50, }; // maximum number of stack frames 171 enum { 172 Frames = 50, // maximum number of stack frames 173 }; 173 174 int last = kernel_abort_lastframe(); // skip last N stack frames 174 175 175 176 void * array[Frames]; 176 177 size_t size = backtrace( array, Frames ); 177 char ** messages = backtrace_symbols( array, size ); // does not demangle names178 char ** messages = backtrace_symbols( array, size ); 178 179 179 180 *index( messages[0], '(' ) = '\0'; // find executable name … … 183 184 char * name = 0p, * offset_begin = 0p, * offset_end = 0p; 184 185 185 for ( char * p = messages[i]; *p; p += 1 ) {// find parantheses and +offset186 for ( char * p = messages[i]; *p; ++p ) { // find parantheses and +offset 186 187 //__cfaabi_bits_print_nolock( "X %s\n", p); 187 188 if ( *p == '(' ) { … … 227 228 __cfaabi_bits_write( STDERR_FILENO, abort_text, len ); 228 229 229 assert( fmt ); 230 va_list args; 231 va_start( args, fmt ); 232 233 len = vsnprintf( abort_text, abort_text_size, fmt, args ); 234 va_end( args ); 235 __cfaabi_bits_write( STDERR_FILENO, abort_text, len ); 236 237 if ( fmt[strlen( fmt ) - 1] != '\n' ) { // add optional newline if missing at the end of the format text 238 __cfaabi_dbg_write( "\n", 1 ); 239 } // if 230 if ( fmt ) { 231 va_list args; 232 va_start( args, fmt ); 233 234 len = vsnprintf( abort_text, abort_text_size, fmt, args ); 235 va_end( args ); 236 __cfaabi_bits_write( STDERR_FILENO, abort_text, len ); 237 238 if ( fmt[strlen( fmt ) - 1] != '\n' ) { // add optional newline if missing at the end of the format text 239 __cfaabi_dbg_write( "\n", 1 ); 240 } 241 } 242 240 243 kernel_abort_msg( kernel_data, abort_text, abort_text_size ); 241 242 __cfaabi_backtrace( signalAbort ? 4 : 2 ); 244 __cfaabi_backtrace( signalAbort ? 4 : 3 ); 243 245 244 246 __cabi_libc.abort(); // print stack trace in handler -
libcfa/src/iostream.cfa
ra505021 r8c50aed 10 10 // Created On : Wed May 27 17:56:53 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Thu Feb 20 15:53:23 202013 // Update Count : 82 912 // Last Modified On : Sat Jul 13 08:07:59 2019 13 // Update Count : 821 14 14 // 15 15 … … 19 19 #include <stdio.h> 20 20 #include <stdbool.h> // true/false 21 #include <stdint.h> // UINT64_MAX22 21 //#include <string.h> // strlen, strcmp 23 22 extern size_t strlen (const char *__s) __attribute__ ((__nothrow__ , __leaf__)) __attribute__ ((__pure__)) __attribute__ ((__nonnull__ (1))); … … 36 35 forall( dtype ostype | ostream( ostype ) ) { 37 36 ostype & ?|?( ostype & os, zero_t ) { 38 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );37 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 39 38 fmt( os, "%d", 0n ); 40 39 return os; … … 45 44 46 45 ostype & ?|?( ostype & os, one_t ) { 47 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );46 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 48 47 fmt( os, "%d", 1n ); 49 48 return os; … … 54 53 55 54 ostype & ?|?( ostype & os, bool b ) { 56 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );55 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 57 56 fmt( os, "%s", b ? "true" : "false" ); 58 57 return os; … … 64 63 ostype & ?|?( ostype & os, char c ) { 65 64 fmt( os, "%c", c ); 66 if ( c == '\n' ) $setNL( os, true );65 if ( c == '\n' ) setNL( os, true ); 67 66 return sepOff( os ); 68 67 } // ?|? … … 72 71 73 72 ostype & ?|?( ostype & os, signed char sc ) { 74 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );73 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 75 74 fmt( os, "%hhd", sc ); 76 75 return os; … … 81 80 82 81 ostype & ?|?( ostype & os, unsigned char usc ) { 83 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );82 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 84 83 fmt( os, "%hhu", usc ); 85 84 return os; … … 90 89 91 90 ostype & ?|?( ostype & os, short int si ) { 92 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );91 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 93 92 fmt( os, "%hd", si ); 94 93 return os; … … 99 98 100 99 ostype & ?|?( ostype & os, unsigned short int usi ) { 101 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );100 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 102 101 fmt( os, "%hu", usi ); 103 102 return os; … … 108 107 109 108 ostype & ?|?( ostype & os, int i ) { 110 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );109 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 111 110 fmt( os, "%d", i ); 112 111 return os; … … 117 116 118 117 ostype & ?|?( ostype & os, unsigned int ui ) { 119 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );118 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 120 119 fmt( os, "%u", ui ); 121 120 return os; … … 126 125 127 126 ostype & ?|?( ostype & os, long int li ) { 128 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );127 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 129 128 fmt( os, "%ld", li ); 130 129 return os; … … 135 134 136 135 ostype & ?|?( ostype & os, unsigned long int uli ) { 137 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );136 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 138 137 fmt( os, "%lu", uli ); 139 138 return os; … … 144 143 145 144 ostype & ?|?( ostype & os, long long int lli ) { 146 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );145 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 147 146 fmt( os, "%lld", lli ); 148 147 return os; … … 153 152 154 153 ostype & ?|?( ostype & os, unsigned long long int ulli ) { 155 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );154 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 156 155 fmt( os, "%llu", ulli ); 157 156 return os; … … 160 159 (ostype &)(os | ulli); ends( os ); 161 160 } // ?|? 162 163 #if defined( __SIZEOF_INT128__ )164 // UINT64_MAX 18_446_744_073_709_551_615_ULL165 #define P10_UINT64 10_000_000_000_000_000_000_ULL // 19 zeroes166 167 static void base10_128( ostype & os, unsigned int128 val ) {168 if ( val > UINT64_MAX ) {169 base10_128( os, val / P10_UINT64 ); // recursive170 fmt( os, "%.19lu", (uint64_t)(val % P10_UINT64) );171 } else {172 fmt( os, "%lu", (uint64_t)val );173 } // if174 } // base10_128175 176 static void base10_128( ostype & os, int128 val ) {177 if ( val < 0 ) {178 fmt( os, "-" ); // leading negative sign179 val = -val;180 } // if181 base10_128( os, (unsigned int128)val ); // print zero/positive value182 } // base10_128183 184 ostype & ?|?( ostype & os, int128 llli ) {185 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );186 base10_128( os, llli );187 return os;188 } // ?|?189 void & ?|?( ostype & os, int128 llli ) {190 (ostype &)(os | llli); ends( os );191 } // ?|?192 193 ostype & ?|?( ostype & os, unsigned int128 ullli ) {194 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );195 base10_128( os, ullli );196 return os;197 } // ?|?198 void & ?|?( ostype & os, unsigned int128 ullli ) {199 (ostype &)(os | ullli); ends( os );200 } // ?|?201 #endif // __SIZEOF_INT128__202 161 203 162 #define PrintWithDP( os, format, val, ... ) \ … … 216 175 217 176 ostype & ?|?( ostype & os, float f ) { 218 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );177 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 219 178 PrintWithDP( os, "%g", f ); 220 179 return os; … … 225 184 226 185 ostype & ?|?( ostype & os, double d ) { 227 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );186 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 228 187 PrintWithDP( os, "%.*lg", d, DBL_DIG ); 229 188 return os; … … 234 193 235 194 ostype & ?|?( ostype & os, long double ld ) { 236 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );195 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 237 196 PrintWithDP( os, "%.*Lg", ld, LDBL_DIG ); 238 197 return os; … … 243 202 244 203 ostype & ?|?( ostype & os, float _Complex fc ) { 245 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );204 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 246 205 // os | crealf( fc ) | nonl; 247 206 PrintWithDP( os, "%g", crealf( fc ) ); … … 255 214 256 215 ostype & ?|?( ostype & os, double _Complex dc ) { 257 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );216 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 258 217 // os | creal( dc ) | nonl; 259 218 PrintWithDP( os, "%.*lg", creal( dc ), DBL_DIG ); … … 267 226 268 227 ostype & ?|?( ostype & os, long double _Complex ldc ) { 269 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );228 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 270 229 // os | creall( ldc ) || nonl; 271 230 PrintWithDP( os, "%.*Lg", creall( ldc ), LDBL_DIG ); … … 278 237 } // ?|? 279 238 280 ostype & ?|?( ostype & os, const char str[]) {239 ostype & ?|?( ostype & os, const char * str ) { 281 240 enum { Open = 1, Close, OpenClose }; 282 241 static const unsigned char mask[256] @= { … … 298 257 // first character IS NOT spacing or closing punctuation => add left separator 299 258 unsigned char ch = str[0]; // must make unsigned 300 if ( $sepPrt( os ) && mask[ ch ] != Close && mask[ ch ] != OpenClose ) {301 fmt( os, "%s", $sepGetCur( os ) );259 if ( sepPrt( os ) && mask[ ch ] != Close && mask[ ch ] != OpenClose ) { 260 fmt( os, "%s", sepGetCur( os ) ); 302 261 } // if 303 262 304 263 // if string starts line, must reset to determine open state because separator is off 305 $sepReset( os );// reset separator264 sepReset( os ); // reset separator 306 265 307 266 // last character IS spacing or opening punctuation => turn off separator for next item 308 267 size_t len = strlen( str ); 309 268 ch = str[len - 1]; // must make unsigned 310 if ( $sepPrt( os ) && mask[ ch ] != Open && mask[ ch ] != OpenClose ) {269 if ( sepPrt( os ) && mask[ ch ] != Open && mask[ ch ] != OpenClose ) { 311 270 sepOn( os ); 312 271 } else { 313 272 sepOff( os ); 314 273 } // if 315 if ( ch == '\n' ) $setNL( os, true ); // check *AFTER* $sepPrt call above as it resets NL flag274 if ( ch == '\n' ) setNL( os, true ); // check *AFTER* sepPrt call above as it resets NL flag 316 275 return write( os, str, len ); 317 276 } // ?|? 318 319 void ?|?( ostype & os, const char str[] ) { 277 void ?|?( ostype & os, const char * str ) { 320 278 (ostype &)(os | str); ends( os ); 321 279 } // ?|? 322 280 323 281 // ostype & ?|?( ostype & os, const char16_t * str ) { 324 // if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );282 // if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 325 283 // fmt( os, "%ls", str ); 326 284 // return os; … … 329 287 // #if ! ( __ARM_ARCH_ISA_ARM == 1 && __ARM_32BIT_STATE == 1 ) // char32_t == wchar_t => ambiguous 330 288 // ostype & ?|?( ostype & os, const char32_t * str ) { 331 // if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );289 // if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 332 290 // fmt( os, "%ls", str ); 333 291 // return os; … … 336 294 337 295 // ostype & ?|?( ostype & os, const wchar_t * str ) { 338 // if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );296 // if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 339 297 // fmt( os, "%ls", str ); 340 298 // return os; … … 342 300 343 301 ostype & ?|?( ostype & os, const void * p ) { 344 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );302 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 345 303 fmt( os, "%p", p ); 346 304 return os; … … 357 315 void ?|?( ostype & os, ostype & (* manip)( ostype & ) ) { 358 316 (ostype &)(manip( os )); 359 if ( $getPrt( os ) ) ends( os );// something printed ?360 $setPrt( os, false ); // turn off317 if ( getPrt( os ) ) ends( os ); // something printed ? 318 setPrt( os, false ); // turn off 361 319 } // ?|? 362 320 … … 371 329 ostype & nl( ostype & os ) { 372 330 (ostype &)(os | '\n'); 373 $setPrt( os, false ); // turn off374 $setNL( os, true );331 setPrt( os, false ); // turn off 332 setNL( os, true ); 375 333 flush( os ); 376 334 return sepOff( os ); // prepare for next line … … 378 336 379 337 ostype & nonl( ostype & os ) { 380 $setPrt( os, false ); // turn off338 setPrt( os, false ); // turn off 381 339 return os; 382 340 } // nonl … … 417 375 ostype & ?|?( ostype & os, T arg, Params rest ) { 418 376 (ostype &)(os | arg); // print first argument 419 $sepSetCur( os, sepGetTuple( os ) );// switch to tuple separator377 sepSetCur( os, sepGetTuple( os ) ); // switch to tuple separator 420 378 (ostype &)(os | rest); // print remaining arguments 421 $sepSetCur( os, sepGet( os ) ); // switch to regular separator379 sepSetCur( os, sepGet( os ) ); // switch to regular separator 422 380 return os; 423 381 } // ?|? … … 425 383 // (ostype &)(?|?( os, arg, rest )); ends( os ); 426 384 (ostype &)(os | arg); // print first argument 427 $sepSetCur( os, sepGetTuple( os ) );// switch to tuple separator385 sepSetCur( os, sepGetTuple( os ) ); // switch to tuple separator 428 386 (ostype &)(os | rest); // print remaining arguments 429 $sepSetCur( os, sepGet( os ) ); // switch to regular separator387 sepSetCur( os, sepGet( os ) ); // switch to regular separator 430 388 ends( os ); 431 389 } // ?|? … … 456 414 forall( dtype ostype | ostream( ostype ) ) { \ 457 415 ostype & ?|?( ostype & os, _Ostream_Manip(T) f ) { \ 458 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) ); \416 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); \ 459 417 \ 460 418 if ( f.base == 'b' || f.base == 'B' ) { /* bespoke binary format */ \ … … 505 463 \ 506 464 if ( ! f.flags.pc ) { /* no precision */ \ 465 /* printf( "%s\n", &fmtstr[star] ); */ \ 507 466 fmtstr[sizeof(IFMTNP)-2] = f.base; /* sizeof includes '\0' */ \ 508 /* printf( "%s %c %c\n", &fmtstr[star], f.base, CODE ); */ \509 467 fmt( os, &fmtstr[star], f.wd, f.val ); \ 510 468 } else { /* precision */ \ 511 469 fmtstr[sizeof(IFMTP)-2] = f.base; /* sizeof includes '\0' */ \ 512 /* printf( "%s %c %c\n", &fmtstr[star], f.base, CODE); */ \470 /* printf( "%s\n", &fmtstr[star] ); */ \ 513 471 fmt( os, &fmtstr[star], f.wd, f.pc, f.val ); \ 514 472 } /* if */ \ … … 528 486 IntegralFMTImpl( signed long long int, 'd', "% *ll ", "% *.*ll " ) 529 487 IntegralFMTImpl( unsigned long long int, 'u', "% *ll ", "% *.*ll " ) 530 531 532 #if defined( __SIZEOF_INT128__ )533 // Default prefix for non-decimal prints is 0b, 0, 0x.534 #define IntegralFMTImpl128( T, SIGNED, CODE, IFMTNP, IFMTP ) \535 forall( dtype ostype | ostream( ostype ) ) \536 static void base10_128( ostype & os, _Ostream_Manip(T) fmt ) { \537 if ( fmt.val > UINT64_MAX ) { \538 fmt.val /= P10_UINT64; \539 base10_128( os, fmt ); /* recursive */ \540 _Ostream_Manip(unsigned long long int) fmt2 @= { (uint64_t)(fmt.val % P10_UINT64), 0, 19, 'u', { .all : 0 } }; \541 fmt2.flags.nobsdp = true; \542 printf( "fmt2 %c %lld %d\n", fmt2.base, fmt2.val, fmt2.all ); \543 sepOff( os ); \544 (ostype &)(os | fmt2); \545 } else { \546 printf( "fmt %c %lld %d\n", fmt.base, fmt.val, fmt.all ); \547 (ostype &)(os | fmt); \548 } /* if */ \549 } /* base10_128 */ \550 forall( dtype ostype | ostream( ostype ) ) { \551 ostype & ?|?( ostype & os, _Ostream_Manip(T) f ) { \552 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) ); \553 \554 if ( f.base == 'b' | f.base == 'o' | f.base == 'x' | f.base == 'X' ) { \555 unsigned long long int msig = (unsigned long long int)(f.val >> 64); \556 unsigned long long int lsig = (unsigned long long int)(f.val); \557 _Ostream_Manip(SIGNED long long int) fmt @= { msig, f.wd, f.pc, f.base, { .all : f.all } }; \558 _Ostream_Manip(unsigned long long int) fmt2 @= { lsig, 0, 0, f.base, { .all : 0 } }; \559 if ( msig == 0 ) { \560 fmt.val = lsig; \561 (ostype &)(os | fmt); \562 } else { \563 fmt2.flags.pad0 = fmt2.flags.nobsdp = true; \564 if ( f.base == 'b' ) { \565 if ( f.wd > 64 ) fmt.wd = f.wd - 64; \566 fmt2.wd = 64; \567 (ostype &)(os | fmt | "" | fmt2); \568 } else if ( f.base == 'o' ) { \569 fmt.val = (unsigned long long int)fmt.val >> 2; \570 if ( f.wd > 21 ) fmt.wd = f.wd - 21; \571 fmt2.wd = 1; \572 fmt2.val = ((msig & 0x3) << 1) + 1; \573 (ostype &)(os | fmt | "" | fmt2); \574 sepOff( os ); \575 fmt2.wd = 21; \576 fmt2.val = lsig & 0x7fffffffffffffff; \577 (ostype &)(os | fmt2); \578 } else { \579 if ( f.flags.left ) { \580 if ( f.wd > 16 ) fmt2.wd = f.wd - 16; \581 fmt.wd = 16; \582 } else { \583 if ( f.wd > 16 ) fmt.wd = f.wd - 16; \584 fmt2.wd = 16; \585 } /* if */ \586 (ostype &)(os | fmt | "" | fmt2); \587 } /* if */ \588 } /* if */ \589 } else { \590 base10_128( os, f ); \591 } /* if */ \592 return os; \593 } /* ?|? */ \594 void ?|?( ostype & os, _Ostream_Manip(T) f ) { (ostype &)(os | f); ends( os ); } \595 } // distribution596 597 IntegralFMTImpl128( int128, signed, 'd', "% *ll ", "% *.*ll " )598 IntegralFMTImpl128( unsigned int128, unsigned, 'u', "% *ll ", "% *.*ll " )599 #endif // __SIZEOF_INT128__600 488 601 489 //*********************************** floating point *********************************** … … 625 513 forall( dtype ostype | ostream( ostype ) ) { \ 626 514 ostype & ?|?( ostype & os, _Ostream_Manip(T) f ) { \ 627 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) ); \515 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); \ 628 516 char fmtstr[sizeof(DFMTP)]; /* sizeof includes '\0' */ \ 629 517 if ( ! f.flags.pc ) memcpy( &fmtstr, DFMTNP, sizeof(DFMTNP) ); \ … … 648 536 return os; \ 649 537 } /* ?|? */ \ 650 \651 538 void ?|?( ostype & os, _Ostream_Manip(T) f ) { (ostype &)(os | f); ends( os ); } \ 652 539 } // distribution … … 668 555 } // if 669 556 670 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );557 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 671 558 672 559 #define CFMTNP "% * " … … 684 571 return os; 685 572 } // ?|? 686 687 573 void ?|?( ostype & os, _Ostream_Manip(char) f ) { (ostype &)(os | f); ends( os ); } 688 574 } // distribution … … 706 592 } // if 707 593 708 if ( $sepPrt( os ) ) fmt( os, "%s", $sepGetCur( os ) );594 if ( sepPrt( os ) ) fmt( os, "%s", sepGetCur( os ) ); 709 595 710 596 #define SFMTNP "% * " … … 730 616 return os; 731 617 } // ?|? 732 733 618 void ?|?( ostype & os, _Ostream_Manip(const char *) f ) { (ostype &)(os | f); ends( os ); } 734 619 } // distribution … … 850 735 } // ?|? 851 736 852 // istype & ?|?( istype & is, const char fmt[]) {737 // istype & ?|?( istype & is, const char * fmt ) { 853 738 // fmt( is, fmt, "" ); 854 739 // return is; -
libcfa/src/iostream.hfa
ra505021 r8c50aed 10 10 // Created On : Wed May 27 17:56:53 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Thu Feb 20 15:30:56 202013 // Update Count : 33 712 // Last Modified On : Fri Jul 12 12:08:38 2019 13 // Update Count : 334 14 14 // 15 15 … … 24 24 trait ostream( dtype ostype ) { 25 25 // private 26 bool $sepPrt( ostype & ); // get separator state (on/off)27 void $sepReset( ostype & ); // set separator state to default state28 void $sepReset( ostype &, bool ); // set separator and default state29 const char * $sepGetCur( ostype & );// get current separator string30 void $sepSetCur( ostype &, const char []); // set current separator string31 bool $getNL( ostype & );// check newline32 void $setNL( ostype &, bool ); // saw newline33 bool $getANL( ostype & ); // get auto newline (on/off)34 bool $getPrt( ostype & ); // get fmt called in output cascade35 void $setPrt( ostype &, bool ); // set fmt called in output cascade26 bool sepPrt( ostype & ); // get separator state (on/off) 27 void sepReset( ostype & ); // set separator state to default state 28 void sepReset( ostype &, bool ); // set separator and default state 29 const char * sepGetCur( ostype & ); // get current separator string 30 void sepSetCur( ostype &, const char * ); // set current separator string 31 bool getNL( ostype & ); // check newline 32 void setNL( ostype &, bool ); // saw newline 33 bool getANL( ostype & ); // get auto newline (on/off) 34 bool getPrt( ostype & ); // get fmt called in output cascade 35 void setPrt( ostype &, bool ); // set fmt called in output cascade 36 36 // public 37 37 void sepOn( ostype & ); // turn separator state on … … 43 43 44 44 const char * sepGet( ostype & ); // get separator string 45 void sepSet( ostype &, const char []); // set separator to string (15 character maximum)45 void sepSet( ostype &, const char * ); // set separator to string (15 character maximum) 46 46 const char * sepGetTuple( ostype & ); // get tuple separator string 47 void sepSetTuple( ostype &, const char [] );// set tuple separator to string (15 character maximum)47 void sepSetTuple( ostype &, const char * ); // set tuple separator to string (15 character maximum) 48 48 49 49 void ends( ostype & os ); // end of output statement 50 50 int fail( ostype & ); 51 51 int flush( ostype & ); 52 void open( ostype & os, const char name[], const char mode[]);52 void open( ostype & os, const char * name, const char * mode ); 53 53 void close( ostype & os ); 54 ostype & write( ostype &, const char [], size_t );54 ostype & write( ostype &, const char *, size_t ); 55 55 int fmt( ostype &, const char format[], ... ) __attribute__(( format(printf, 2, 3) )); 56 56 }; // ostream … … 98 98 ostype & ?|?( ostype &, unsigned long long int ); 99 99 void ?|?( ostype &, unsigned long long int ); 100 #if defined( __SIZEOF_INT128__ )101 ostype & ?|?( ostype &, int128 );102 void ?|?( ostype &, int128 );103 ostype & ?|?( ostype &, unsigned int128 );104 void ?|?( ostype &, unsigned int128 );105 #endif // __SIZEOF_INT128__106 100 107 101 ostype & ?|?( ostype &, float ); … … 119 113 void ?|?( ostype &, long double _Complex ); 120 114 121 ostype & ?|?( ostype &, const char []);122 void ?|?( ostype &, const char []);115 ostype & ?|?( ostype &, const char * ); 116 void ?|?( ostype &, const char * ); 123 117 // ostype & ?|?( ostype &, const char16_t * ); 124 118 #if ! ( __ARM_ARCH_ISA_ARM == 1 && __ARM_32BIT_STATE == 1 ) // char32_t == wchar_t => ambiguous … … 212 206 IntegralFMTDecl( signed long long int, 'd' ) 213 207 IntegralFMTDecl( unsigned long long int, 'u' ) 214 #if defined( __SIZEOF_INT128__ )215 IntegralFMTDecl( int128, 'd' )216 IntegralFMTDecl( unsigned int128, 'u' )217 #endif218 208 219 209 //*********************************** floating point *********************************** … … 266 256 267 257 static inline { 268 _Ostream_Manip(const char *) bin( const char s[]) { return (_Ostream_Manip(const char *))@{ s, 1, 0, 'b', { .all : 0 } }; }269 _Ostream_Manip(const char *) oct( const char s[]) { return (_Ostream_Manip(const char *))@{ s, 1, 0, 'o', { .all : 0 } }; }270 _Ostream_Manip(const char *) hex( const char s[]) { return (_Ostream_Manip(const char *))@{ s, 1, 0, 'x', { .all : 0 } }; }271 _Ostream_Manip(const char *) wd( unsigned int w, const char s[]) { return (_Ostream_Manip(const char *))@{ s, w, 0, 's', { .all : 0 } }; }272 _Ostream_Manip(const char *) wd( unsigned int w, unsigned char pc, const char s[]) { return (_Ostream_Manip(const char *))@{ s, w, pc, 's', { .flags.pc : true } }; }258 _Ostream_Manip(const char *) bin( const char * s ) { return (_Ostream_Manip(const char *))@{ s, 1, 0, 'b', { .all : 0 } }; } 259 _Ostream_Manip(const char *) oct( const char * s ) { return (_Ostream_Manip(const char *))@{ s, 1, 0, 'o', { .all : 0 } }; } 260 _Ostream_Manip(const char *) hex( const char * s ) { return (_Ostream_Manip(const char *))@{ s, 1, 0, 'x', { .all : 0 } }; } 261 _Ostream_Manip(const char *) wd( unsigned int w, const char * s ) { return (_Ostream_Manip(const char *))@{ s, w, 0, 's', { .all : 0 } }; } 262 _Ostream_Manip(const char *) wd( unsigned int w, unsigned char pc, const char * s ) { return (_Ostream_Manip(const char *))@{ s, w, pc, 's', { .flags.pc : true } }; } 273 263 _Ostream_Manip(const char *) & wd( unsigned int w, _Ostream_Manip(const char *) & fmt ) { fmt.wd = w; return fmt; } 274 264 _Ostream_Manip(const char *) & wd( unsigned int w, unsigned char pc, _Ostream_Manip(const char *) & fmt ) { fmt.wd = w; fmt.pc = pc; fmt.flags.pc = true; return fmt; } … … 291 281 int fail( istype & ); 292 282 int eof( istype & ); 293 void open( istype & is, const char name[]);283 void open( istype & is, const char * name ); 294 284 void close( istype & is ); 295 285 istype & read( istype &, char *, size_t ); … … 326 316 istype & ?|?( istype &, long double _Complex & ); 327 317 328 // istype & ?|?( istype &, const char []);318 // istype & ?|?( istype &, const char * ); 329 319 istype & ?|?( istype &, char * ); 330 320 … … 353 343 static inline { 354 344 _Istream_Cstr skip( unsigned int n ) { return (_Istream_Cstr){ 0p, 0p, n, { .all : 0 } }; } 355 _Istream_Cstr skip( const char scanset[]) { return (_Istream_Cstr){ 0p, scanset, -1, { .all : 0 } }; }356 _Istream_Cstr incl( const char scanset[], char * s ) { return (_Istream_Cstr){ s, scanset, -1, { .flags.inex : false } }; }357 _Istream_Cstr & incl( const char scanset[], _Istream_Cstr & fmt ) { fmt.scanset = scanset; fmt.flags.inex = false; return fmt; }358 _Istream_Cstr excl( const char scanset[], char * s ) { return (_Istream_Cstr){ s, scanset, -1, { .flags.inex : true } }; }359 _Istream_Cstr & excl( const char scanset[], _Istream_Cstr & fmt ) { fmt.scanset = scanset; fmt.flags.inex = true; return fmt; }360 _Istream_Cstr ignore( const char s[]) { return (_Istream_Cstr)@{ s, 0p, -1, { .flags.ignore : true } }; }345 _Istream_Cstr skip( const char * scanset ) { return (_Istream_Cstr){ 0p, scanset, -1, { .all : 0 } }; } 346 _Istream_Cstr incl( const char * scanset, char * s ) { return (_Istream_Cstr){ s, scanset, -1, { .flags.inex : false } }; } 347 _Istream_Cstr & incl( const char * scanset, _Istream_Cstr & fmt ) { fmt.scanset = scanset; fmt.flags.inex = false; return fmt; } 348 _Istream_Cstr excl( const char * scanset, char * s ) { return (_Istream_Cstr){ s, scanset, -1, { .flags.inex : true } }; } 349 _Istream_Cstr & excl( const char * scanset, _Istream_Cstr & fmt ) { fmt.scanset = scanset; fmt.flags.inex = true; return fmt; } 350 _Istream_Cstr ignore( const char * s ) { return (_Istream_Cstr)@{ s, 0p, -1, { .flags.ignore : true } }; } 361 351 _Istream_Cstr & ignore( _Istream_Cstr & fmt ) { fmt.flags.ignore = true; return fmt; } 362 _Istream_Cstr wdi( unsigned int w, char s[]) { return (_Istream_Cstr)@{ s, 0p, w, { .all : 0 } }; }352 _Istream_Cstr wdi( unsigned int w, char * s ) { return (_Istream_Cstr)@{ s, 0p, w, { .all : 0 } }; } 363 353 _Istream_Cstr & wdi( unsigned int w, _Istream_Cstr & fmt ) { fmt.wd = w; return fmt; } 364 354 } // distribution -
libcfa/src/math.hfa
ra505021 r8c50aed 10 10 // Created On : Mon Apr 18 23:37:04 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Feb 4 10:27:11 202013 // Update Count : 11 712 // Last Modified On : Fri Jul 13 11:02:15 2018 13 // Update Count : 116 14 14 // 15 15 … … 51 51 static inline long double fdim( long double x, long double y ) { return fdiml( x, y ); } 52 52 53 static inline float nan( const char tag[]) { return nanf( tag ); }54 // extern "C" { double nan( const char []); }55 static inline long double nan( const char tag[]) { return nanl( tag ); }53 static inline float nan( const char * tag ) { return nanf( tag ); } 54 // extern "C" { double nan( const char * ); } 55 static inline long double nan( const char * tag ) { return nanl( tag ); } 56 56 57 57 //---------------------- Exponential ---------------------- -
libcfa/src/rational.cfa
ra505021 r8c50aed 10 10 // Created On : Wed Apr 6 17:54:28 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sat Feb 8 17:56:36 202013 // Update Count : 18 712 // Last Modified On : Fri Jul 12 18:12:08 2019 13 // Update Count : 184 14 14 // 15 15 … … 56 56 } // rational 57 57 58 void ?{}( Rational(RationalImpl) & r, zero_t ) {59 r{ (RationalImpl){0}, (RationalImpl){1} };60 } // rational61 62 void ?{}( Rational(RationalImpl) & r, one_t ) {63 r{ (RationalImpl){1}, (RationalImpl){1} };64 } // rational65 58 66 59 // getter for numerator/denominator -
libcfa/src/startup.cfa
ra505021 r8c50aed 10 10 // Created On : Tue Jul 24 16:21:57 2018 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Feb 4 13:03:18 202013 // Update Count : 3012 // Last Modified On : Fri Dec 13 13:16:45 2019 13 // Update Count : 29 14 14 // 15 15 … … 41 41 struct __spinlock_t; 42 42 extern "C" { 43 void __cfaabi_dbg_record(struct __spinlock_t & this, const char prev_name[]) __attribute__(( weak )) {}43 void __cfaabi_dbg_record(struct __spinlock_t & this, const char * prev_name) __attribute__(( weak )) {} 44 44 } 45 45 -
libcfa/src/stdhdr/assert.h
ra505021 r8c50aed 10 10 // Created On : Mon Jul 4 23:25:26 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Feb 4 12:58:49 202013 // Update Count : 1 512 // Last Modified On : Mon Jul 31 23:09:32 2017 13 // Update Count : 13 14 14 // 15 15 … … 27 27 #define assertf( expr, fmt, ... ) ((expr) ? ((void)0) : __assert_fail_f(__VSTRINGIFY__(expr), __FILE__, __LINE__, __PRETTY_FUNCTION__, fmt, ## __VA_ARGS__ )) 28 28 29 void __assert_fail_f( const char assertion[], const char file[], unsigned int line, const char function[], const char fmt[], ... ) __attribute__((noreturn, format( printf, 5, 6) ));29 void __assert_fail_f( const char *assertion, const char *file, unsigned int line, const char *function, const char *fmt, ... ) __attribute__((noreturn, format( printf, 5, 6) )); 30 30 #endif 31 31 -
libcfa/src/stdhdr/bfdlink.h
ra505021 r8c50aed 10 10 // Created On : Tue Jul 18 07:26:04 2017 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Fri Feb 7 19:05:08202013 // Update Count : 612 // Last Modified On : Sat Feb 1 07:15:29 2020 13 // Update Count : 5 14 14 // 15 15 16 16 // include file uses the CFA keyword "with". 17 17 #if ! defined( with ) // nesting ? 18 #define with ``with // make keyword an identifier18 #define with ``with`` // make keyword an identifier 19 19 #define __CFA_BFDLINK_H__ 20 20 #endif -
libcfa/src/stdhdr/hwloc.h
ra505021 r8c50aed 10 10 // Created On : Tue Jul 18 07:45:00 2017 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Fri Feb 7 19:05:18202013 // Update Count : 612 // Last Modified On : Sat Feb 1 07:15:39 2020 13 // Update Count : 5 14 14 // 15 15 16 16 // include file uses the CFA keyword "thread". 17 17 #if ! defined( thread ) // nesting ? 18 #define thread ``thread // make keyword an identifier18 #define thread ``thread`` // make keyword an identifier 19 19 #define __CFA_HWLOC_H__ 20 20 #endif -
libcfa/src/stdhdr/krb5.h
ra505021 r8c50aed 10 10 // Created On : Tue Jul 18 07:55:44 2017 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Fri Feb 7 19:05:35202013 // Update Count : 612 // Last Modified On : Sat Feb 1 07:15:47 2020 13 // Update Count : 5 14 14 // 15 15 16 16 // include file uses the CFA keyword "enable". 17 17 #if ! defined( enable ) // nesting ? 18 #define enable ``enable // make keyword an identifier18 #define enable ``enable`` // make keyword an identifier 19 19 #define __CFA_KRB5_H__ 20 20 #endif -
libcfa/src/stdhdr/math.h
ra505021 r8c50aed 10 10 // Created On : Mon Jul 4 23:25:26 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Fri Feb 7 19:05:27202013 // Update Count : 1 512 // Last Modified On : Sat Feb 1 07:15:58 2020 13 // Update Count : 14 14 14 // 15 15 16 16 extern "C" { 17 17 #if ! defined( exception ) // nesting ? 18 #define exception ``exception // make keyword an identifier18 #define exception ``exception`` // make keyword an identifier 19 19 #define __CFA_MATH_H__ 20 20 #endif -
libcfa/src/stdhdr/sys/ucontext.h
ra505021 r8c50aed 10 10 // Created On : Thu Feb 8 23:48:16 2018 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Fri Feb 7 19:05:41202013 // Update Count : 612 // Last Modified On : Sat Feb 1 07:16:05 2020 13 // Update Count : 5 14 14 // 15 15 16 16 #if ! defined( ftype ) // nesting ? 17 #define ftype ``ftype // make keyword an identifier17 #define ftype ``ftype`` // make keyword an identifier 18 18 #define __CFA_UCONTEXT_H__ 19 19 #endif -
libcfa/src/stdlib.cfa
ra505021 r8c50aed 10 10 // Created On : Thu Jan 28 17:10:29 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Feb 4 08:27:08 202013 // Update Count : 48 612 // Last Modified On : Wed Nov 20 17:22:47 2019 13 // Update Count : 485 14 14 // 15 15 … … 107 107 //--------------------------------------- 108 108 109 float _Complex strto( const char sptr[], char ** eptr ) {109 float _Complex strto( const char * sptr, char ** eptr ) { 110 110 float re, im; 111 111 char * eeptr; … … 118 118 } // strto 119 119 120 double _Complex strto( const char sptr[], char ** eptr ) {120 double _Complex strto( const char * sptr, char ** eptr ) { 121 121 double re, im; 122 122 char * eeptr; … … 129 129 } // strto 130 130 131 long double _Complex strto( const char sptr[], char ** eptr ) {131 long double _Complex strto( const char * sptr, char ** eptr ) { 132 132 long double re, im; 133 133 char * eeptr; -
libcfa/src/stdlib.hfa
ra505021 r8c50aed 10 10 // Created On : Thu Jan 28 17:12:35 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Feb 4 08:27:01 202013 // Update Count : 40 112 // Last Modified On : Fri Nov 29 23:08:02 2019 13 // Update Count : 400 14 14 // 15 15 … … 193 193 194 194 static inline { 195 int strto( const char sptr[], char ** eptr, int base ) { return (int)strtol( sptr, eptr, base ); }196 unsigned int strto( const char sptr[], char ** eptr, int base ) { return (unsigned int)strtoul( sptr, eptr, base ); }197 long int strto( const char sptr[], char ** eptr, int base ) { return strtol( sptr, eptr, base ); }198 unsigned long int strto( const char sptr[], char ** eptr, int base ) { return strtoul( sptr, eptr, base ); }199 long long int strto( const char sptr[], char ** eptr, int base ) { return strtoll( sptr, eptr, base ); }200 unsigned long long int strto( const char sptr[], char ** eptr, int base ) { return strtoull( sptr, eptr, base ); }201 202 float strto( const char sptr[], char ** eptr ) { return strtof( sptr, eptr ); }203 double strto( const char sptr[], char ** eptr ) { return strtod( sptr, eptr ); }204 long double strto( const char sptr[], char ** eptr ) { return strtold( sptr, eptr ); }205 } // distribution 206 207 float _Complex strto( const char sptr[], char ** eptr );208 double _Complex strto( const char sptr[], char ** eptr );209 long double _Complex strto( const char sptr[], char ** eptr );195 int strto( const char * sptr, char ** eptr, int base ) { return (int)strtol( sptr, eptr, base ); } 196 unsigned int strto( const char * sptr, char ** eptr, int base ) { return (unsigned int)strtoul( sptr, eptr, base ); } 197 long int strto( const char * sptr, char ** eptr, int base ) { return strtol( sptr, eptr, base ); } 198 unsigned long int strto( const char * sptr, char ** eptr, int base ) { return strtoul( sptr, eptr, base ); } 199 long long int strto( const char * sptr, char ** eptr, int base ) { return strtoll( sptr, eptr, base ); } 200 unsigned long long int strto( const char * sptr, char ** eptr, int base ) { return strtoull( sptr, eptr, base ); } 201 202 float strto( const char * sptr, char ** eptr ) { return strtof( sptr, eptr ); } 203 double strto( const char * sptr, char ** eptr ) { return strtod( sptr, eptr ); } 204 long double strto( const char * sptr, char ** eptr ) { return strtold( sptr, eptr ); } 205 } // distribution 206 207 float _Complex strto( const char * sptr, char ** eptr ); 208 double _Complex strto( const char * sptr, char ** eptr ); 209 long double _Complex strto( const char * sptr, char ** eptr ); 210 210 211 211 static inline { 212 int ato( const char sptr[]) { return (int)strtol( sptr, 0p, 10 ); }213 unsigned int ato( const char sptr[]) { return (unsigned int)strtoul( sptr, 0p, 10 ); }214 long int ato( const char sptr[]) { return strtol( sptr, 0p, 10 ); }215 unsigned long int ato( const char sptr[]) { return strtoul( sptr, 0p, 10 ); }216 long long int ato( const char sptr[]) { return strtoll( sptr, 0p, 10 ); }217 unsigned long long int ato( const char sptr[]) { return strtoull( sptr, 0p, 10 ); }218 219 float ato( const char sptr[]) { return strtof( sptr, 0p ); }220 double ato( const char sptr[]) { return strtod( sptr, 0p ); }221 long double ato( const char sptr[]) { return strtold( sptr, 0p ); }222 223 float _Complex ato( const char sptr[]) { return strto( sptr, 0p ); }224 double _Complex ato( const char sptr[]) { return strto( sptr, 0p ); }225 long double _Complex ato( const char sptr[]) { return strto( sptr, 0p ); }212 int ato( const char * sptr ) { return (int)strtol( sptr, 0p, 10 ); } 213 unsigned int ato( const char * sptr ) { return (unsigned int)strtoul( sptr, 0p, 10 ); } 214 long int ato( const char * sptr ) { return strtol( sptr, 0p, 10 ); } 215 unsigned long int ato( const char * sptr ) { return strtoul( sptr, 0p, 10 ); } 216 long long int ato( const char * sptr ) { return strtoll( sptr, 0p, 10 ); } 217 unsigned long long int ato( const char * sptr ) { return strtoull( sptr, 0p, 10 ); } 218 219 float ato( const char * sptr ) { return strtof( sptr, 0p ); } 220 double ato( const char * sptr ) { return strtod( sptr, 0p ); } 221 long double ato( const char * sptr ) { return strtold( sptr, 0p ); } 222 223 float _Complex ato( const char * sptr ) { return strto( sptr, 0p ); } 224 double _Complex ato( const char * sptr ) { return strto( sptr, 0p ); } 225 long double _Complex ato( const char * sptr ) { return strto( sptr, 0p ); } 226 226 } // distribution 227 227 -
libcfa/src/time.cfa
ra505021 r8c50aed 10 10 // Created On : Tue Mar 27 13:33:14 2018 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Feb 4 08:24:18202013 // Update Count : 7012 // Last Modified On : Sun Jan 5 17:27:40 2020 13 // Update Count : 69 14 14 // 15 15 … … 129 129 } // dd_mm_yy 130 130 131 size_t strftime( char buf[], size_t size, const char fmt[], Time time ) with( time ) {131 size_t strftime( char * buf, size_t size, const char * fmt, Time time ) with( time ) { 132 132 time_t s = tn / TIMEGRAN; 133 133 tm tm; -
libcfa/src/time.hfa
ra505021 r8c50aed 10 10 // Created On : Wed Mar 14 23:18:57 2018 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Feb 4 08:24:32202013 // Update Count : 65 412 // Last Modified On : Mon Jan 6 12:50:16 2020 13 // Update Count : 653 14 14 // 15 15 … … 191 191 } // dmy 192 192 193 size_t strftime( char buf[], size_t size, const char fmt[], Time time );193 size_t strftime( char * buf, size_t size, const char * fmt, Time time ); 194 194 195 195 //------------------------- timeval (cont) ------------------------- -
longrun_tests/Makefile.in
ra505021 r8c50aed 502 502 am__v_GOC_0 = @echo " GOC " $@; 503 503 am__v_GOC_1 = 504 AM_V_PY = $(am__v_PY_@AM_V@)505 am__v_PY_ = $(am__v_PY_@AM_DEFAULT_V@)506 am__v_PY_0 = @echo " PYTHON " $@;507 am__v_PY_1 =508 504 AM_V_RUST = $(am__v_RUST_@AM_V@) 509 505 am__v_RUST_ = $(am__v_RUST_@AM_DEFAULT_V@) 510 am__v_RUST_0 = @echo " RUST " $@;506 am__v_RUST_0 = @echo " RUST " $@; 511 507 am__v_RUST_1 = 512 508 AM_V_NODEJS = $(am__v_NODEJS_@AM_V@) 513 509 am__v_NODEJS_ = $(am__v_NODEJS_@AM_DEFAULT_V@) 514 am__v_NODEJS_0 = @echo " NODEJS " $@;510 am__v_NODEJS_0 = @echo " NODEJS " $@; 515 511 am__v_NODEJS_1 = 516 512 AM_V_JAVAC = $(am__v_JAVAC_@AM_V@) -
src/CodeGen/CodeGenerator.cc
ra505021 r8c50aed 10 10 // Created On : Mon May 18 07:44:20 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sun Feb 16 08:32:48 202013 // Update Count : 5 3212 // Last Modified On : Fri Dec 13 23:13:28 2019 13 // Update Count : 508 14 14 // 15 15 #include "CodeGenerator.h" … … 39 39 int CodeGenerator::tabsize = 4; 40 40 41 // The kinds of statements that would ideally be followed by whitespace.41 // the kinds of statements that would ideally be followed by whitespace 42 42 bool wantSpacing( Statement * stmt) { 43 43 return dynamic_cast< IfStmt * >( stmt ) || dynamic_cast< CompoundStmt * >( stmt ) || … … 78 78 } 79 79 80 // Using updateLocation at the beginning of a node and endl within a node should become the method of formating. 80 /* Using updateLocation at the beginning of a node and endl 81 * within a node should become the method of formating. 82 */ 81 83 void CodeGenerator::updateLocation( CodeLocation const & to ) { 82 84 // skip if linemarks shouldn't appear or if codelocation is unset … … 93 95 } else { 94 96 output << "\n# " << to.first_line << " \"" << to.filename 95 << "\"\n" << indent;97 << "\"\n" << indent; 96 98 currentLocation = to; 97 99 } … … 129 131 130 132 void CodeGenerator::genAttributes( list< Attribute * > & attributes ) { 131 if ( attributes.empty() ) return;133 if ( attributes.empty() ) return; 132 134 output << "__attribute__ (("; 133 135 for ( list< Attribute * >::iterator attr( attributes.begin() );; ) { … … 138 140 output << ")"; 139 141 } // if 140 if ( ++attr == attributes.end() ) break;142 if ( ++attr == attributes.end() ) break; 141 143 output << ","; // separator 142 144 } // for … … 163 165 previsit( (BaseSyntaxNode *)node ); 164 166 GuardAction( [this, node](){ 165 if ( options.printExprTypes && node->result ) {166 output << " /* " << genType( node->result, "", options ) << " */ ";167 }168 } );167 if ( options.printExprTypes && node->result ) { 168 output << " /* " << genType( node->result, "", options ) << " */ "; 169 } 170 } ); 169 171 } 170 172 … … 397 399 extension( applicationExpr ); 398 400 if ( VariableExpr * varExpr = dynamic_cast< VariableExpr* >( applicationExpr->get_function() ) ) { 399 const OperatorInfo *opInfo;400 if ( varExpr->get_var()->get_linkage() == LinkageSpec::Intrinsic && ( opInfo = operatorLookup( varExpr->get_var()->get_name() )) ) {401 OperatorInfo opInfo; 402 if ( varExpr->get_var()->get_linkage() == LinkageSpec::Intrinsic && operatorLookup( varExpr->get_var()->get_name(), opInfo ) ) { 401 403 std::list< Expression* >::iterator arg = applicationExpr->get_args().begin(); 402 switch ( opInfo ->type ) {404 switch ( opInfo.type ) { 403 405 case OT_INDEX: 404 406 assert( applicationExpr->get_args().size() == 2 ); … … 421 423 output << "("; 422 424 (*arg++)->accept( *visitor ); 423 output << ") /* " << opInfo ->inputName << " */";425 output << ") /* " << opInfo.inputName << " */"; 424 426 } else if ( applicationExpr->get_args().size() == 2 ) { 425 427 // intrinsic two parameter constructors are essentially bitwise assignment 426 428 output << "("; 427 429 (*arg++)->accept( *visitor ); 428 output << opInfo ->symbol;430 output << opInfo.symbol; 429 431 (*arg)->accept( *visitor ); 430 output << ") /* " << opInfo ->inputName << " */";432 output << ") /* " << opInfo.inputName << " */"; 431 433 } else { 432 434 // no constructors with 0 or more than 2 parameters … … 439 441 assert( applicationExpr->get_args().size() == 1 ); 440 442 output << "("; 441 output << opInfo ->symbol;443 output << opInfo.symbol; 442 444 (*arg)->accept( *visitor ); 443 445 output << ")"; … … 448 450 assert( applicationExpr->get_args().size() == 1 ); 449 451 (*arg)->accept( *visitor ); 450 output << opInfo ->symbol;452 output << opInfo.symbol; 451 453 break; 452 454 … … 457 459 output << "("; 458 460 (*arg++)->accept( *visitor ); 459 output << opInfo ->symbol;461 output << opInfo.symbol; 460 462 (*arg)->accept( *visitor ); 461 463 output << ")"; … … 484 486 extension( untypedExpr ); 485 487 if ( NameExpr * nameExpr = dynamic_cast< NameExpr* >( untypedExpr->function ) ) { 486 const OperatorInfo * opInfo = operatorLookup( nameExpr->name );487 if ( op Info) {488 OperatorInfo opInfo; 489 if ( operatorLookup( nameExpr->name, opInfo ) ) { 488 490 std::list< Expression* >::iterator arg = untypedExpr->args.begin(); 489 switch ( opInfo ->type ) {491 switch ( opInfo.type ) { 490 492 case OT_INDEX: 491 493 assert( untypedExpr->args.size() == 2 ); … … 506 508 output << "("; 507 509 (*arg++)->accept( *visitor ); 508 output << ") /* " << opInfo ->inputName << " */";510 output << ") /* " << opInfo.inputName << " */"; 509 511 } else if ( untypedExpr->get_args().size() == 2 ) { 510 512 // intrinsic two parameter constructors are essentially bitwise assignment 511 513 output << "("; 512 514 (*arg++)->accept( *visitor ); 513 output << opInfo ->symbol;515 output << opInfo.symbol; 514 516 (*arg)->accept( *visitor ); 515 output << ") /* " << opInfo ->inputName << " */";517 output << ") /* " << opInfo.inputName << " */"; 516 518 } else { 517 519 // no constructors with 0 or more than 2 parameters … … 519 521 output << "("; 520 522 (*arg++)->accept( *visitor ); 521 output << opInfo ->symbol << "{ ";523 output << opInfo.symbol << "{ "; 522 524 genCommaList( arg, untypedExpr->args.end() ); 523 output << "}) /* " << opInfo ->inputName << " */";525 output << "}) /* " << opInfo.inputName << " */"; 524 526 } // if 525 527 break; … … 530 532 assert( untypedExpr->args.size() == 1 ); 531 533 output << "("; 532 output << opInfo ->symbol;534 output << opInfo.symbol; 533 535 (*arg)->accept( *visitor ); 534 536 output << ")"; … … 539 541 assert( untypedExpr->args.size() == 1 ); 540 542 (*arg)->accept( *visitor ); 541 output << opInfo ->symbol;543 output << opInfo.symbol; 542 544 break; 543 545 … … 547 549 output << "("; 548 550 (*arg++)->accept( *visitor ); 549 output << opInfo ->symbol;551 output << opInfo.symbol; 550 552 (*arg)->accept( *visitor ); 551 553 output << ")"; … … 579 581 void CodeGenerator::postvisit( NameExpr * nameExpr ) { 580 582 extension( nameExpr ); 581 const OperatorInfo * opInfo = operatorLookup( nameExpr->name );582 if ( op Info) {583 if ( opInfo ->type == OT_CONSTANT ) {584 output << opInfo ->symbol;583 OperatorInfo opInfo; 584 if ( operatorLookup( nameExpr->name, opInfo ) ) { 585 if ( opInfo.type == OT_CONSTANT ) { 586 output << opInfo.symbol; 585 587 } else { 586 output << opInfo ->outputName;588 output << opInfo.outputName; 587 589 } 588 590 } else { … … 652 654 void CodeGenerator::postvisit( VariableExpr * variableExpr ) { 653 655 extension( variableExpr ); 654 const OperatorInfo *opInfo;655 if ( variableExpr->get_var()->get_linkage() == LinkageSpec::Intrinsic && (opInfo = operatorLookup( variableExpr->get_var()->get_name() )) && opInfo->type == OT_CONSTANT ) {656 output << opInfo ->symbol;656 OperatorInfo opInfo; 657 if ( variableExpr->get_var()->get_linkage() == LinkageSpec::Intrinsic && operatorLookup( variableExpr->get_var()->get_name(), opInfo ) && opInfo.type == OT_CONSTANT ) { 658 output << opInfo.symbol; 657 659 } else { 658 660 output << mangleName( variableExpr->get_var() ); … … 1009 1011 case BranchStmt::FallThroughDefault: 1010 1012 assertf( ! options.genC, "fallthru should not reach code generation." ); 1011 output << "fallthru";1013 output << "fallthru"; 1012 1014 break; 1013 1015 } // switch … … 1033 1035 1034 1036 output << ((throwStmt->get_kind() == ThrowStmt::Terminate) ? 1035 "throw" : "throwResume");1037 "throw" : "throwResume"); 1036 1038 if (throwStmt->get_expr()) { 1037 1039 output << " "; … … 1048 1050 1049 1051 output << ((stmt->get_kind() == CatchStmt::Terminate) ? 1050 "catch" : "catchResume");1052 "catch" : "catchResume"); 1051 1053 output << "( "; 1052 1054 stmt->decl->accept( *visitor ); … … 1185 1187 1186 1188 std::string genName( DeclarationWithType * decl ) { 1187 const OperatorInfo * opInfo = operatorLookup( decl->get_name() );1188 if ( op Info) {1189 return opInfo ->outputName;1189 CodeGen::OperatorInfo opInfo; 1190 if ( operatorLookup( decl->get_name(), opInfo ) ) { 1191 return opInfo.outputName; 1190 1192 } else { 1191 1193 return decl->get_name(); -
src/CodeGen/CodeGenerator.h
ra505021 r8c50aed 9 9 // Author : Richard C. Bilson 10 10 // Created On : Mon May 18 07:44:20 2015 11 // Last Modified By : Peter A. Buhr12 // Last Modified On : Sun Feb 16 03:58:31 202013 // Update Count : 6211 // Last Modified By : Andrew Beach 12 // Last Modified On : Tue Apr 30 12:01:00 2019 13 // Update Count : 57 14 14 // 15 15 … … 29 29 namespace CodeGen { 30 30 struct CodeGenerator : public WithShortCircuiting, public WithGuards, public WithVisitorRef<CodeGenerator> { 31 static int tabsize;31 static int tabsize; 32 32 33 33 CodeGenerator( std::ostream &os, bool pretty = false, bool genC = false, bool lineMarks = false, bool printExprTypes = false ); … … 104 104 void postvisit( AsmStmt * ); 105 105 void postvisit( DirectiveStmt * ); 106 void postvisit( AsmDecl * ); // special: statement in declaration context106 void postvisit( AsmDecl * ); // special: statement in declaration context 107 107 void postvisit( IfStmt * ); 108 108 void postvisit( SwitchStmt * ); … … 147 147 LabelPrinter printLabels; 148 148 Options options; 149 public:149 public: 150 150 LineEnder endl; 151 private:151 private: 152 152 153 153 CodeLocation currentLocation; … … 162 162 template< class Iterator > 163 163 void CodeGenerator::genCommaList( Iterator begin, Iterator end ) { 164 if ( begin == end ) return;164 if ( begin == end ) return; 165 165 for ( ;; ) { 166 166 (*begin++)->accept( *visitor ); 167 if ( begin == end ) break;167 if ( begin == end ) break; 168 168 output << ", "; // separator 169 169 } // for -
src/CodeGen/FixMain.h
ra505021 r8c50aed 10 10 // Created On : Thr Jan 12 14:11:09 2017 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sun Feb 16 03:24:32 202013 // Update Count : 512 // Last Modified On : Fri Dec 13 23:12:21 2019 13 // Update Count : 3 14 14 // 15 15 … … 42 42 static std::unique_ptr<FunctionDecl> main_signature; 43 43 }; 44 } // namespace CodeGen44 }; -
src/CodeGen/GenType.h
ra505021 r8c50aed 9 9 // Author : Richard C. Bilson 10 10 // Created On : Mon May 18 07:44:20 2015 11 // Last Modified By : Peter A. Buhr12 // Last Modified On : Sun Feb 16 04:11:40 202013 // Update Count : 511 // Last Modified By : Andrew Beach 12 // Last Modified On : Tue Apr 30 11:47:00 2019 13 // Update Count : 3 14 14 // 15 15 … … 25 25 std::string genType( Type *type, const std::string &baseString, const Options &options ); 26 26 std::string genType( Type *type, const std::string &baseString, bool pretty = false, bool genC = false, bool lineMarks = false ); 27 std::string genPrettyType( Type * type, const std::string & baseString );27 std::string genPrettyType( Type * type, const std::string & baseString ); 28 28 } // namespace CodeGen 29 29 -
src/CodeGen/Generate.cc
ra505021 r8c50aed 10 10 // Created On : Mon May 18 07:44:20 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sun Feb 16 03:01:51 202013 // Update Count : 912 // Last Modified On : Fri Dec 13 23:38:56 2019 13 // Update Count : 8 14 14 // 15 15 #include "Generate.h" … … 64 64 void generate( BaseSyntaxNode * node, std::ostream & os ) { 65 65 if ( Type * type = dynamic_cast< Type * >( node ) ) { 66 os << genPrettyType( type, "" );66 os << CodeGen::genPrettyType( type, "" ); 67 67 } else { 68 68 PassVisitor<CodeGenerator> cgv( os, true, false, false, false ); -
src/CodeGen/OperatorTable.cc
ra505021 r8c50aed 10 10 // Created On : Mon May 18 07:44:20 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Feb 18 15:55:01 202013 // Update Count : 5512 // Last Modified On : Sat Jul 15 17:12:22 2017 13 // Update Count : 15 14 14 // 15 15 … … 17 17 #include <map> // for map, _Rb_tree_const_iterator, map<>::const_iterator 18 18 #include <utility> // for pair 19 using namespace std;20 19 21 20 #include "OperatorTable.h" … … 23 22 24 23 namespace CodeGen { 25 const OperatorInfo CodeGen::tableValues[] ={26 // inputName symbol outputName friendlyName type27 { "?[?]", "", "_operator_index", "Index", OT_INDEX},28 { "?{}", "=", "_constructor", "Constructor", OT_CTOR},29 { "^?{}", "", "_destructor", "Destructor", OT_DTOR},30 { "?()", "", "_operator_call", "Call Operator", OT_CALL},31 { "?++", "++", "_operator_postincr", "Postfix Increment", OT_POSTFIXASSIGN},32 { "?--", "--", "_operator_postdecr", "Postfix Decrement", OT_POSTFIXASSIGN},33 { "*?", "*", "_operator_deref", "Dereference", OT_PREFIX},34 { "+?", "+", "_operator_unaryplus", "Plus", OT_PREFIX},35 { "-?", "-", "_operator_unaryminus", "Minus", OT_PREFIX},36 { "~?", "~", "_operator_bitnot", "Bitwise Not", OT_PREFIX},37 { "!?", "!", "_operator_lognot", "Logical Not", OT_PREFIX},38 { "++?", "++", "_operator_preincr", "Prefix Increment", OT_PREFIXASSIGN},39 { "--?", "--", "_operator_predecr", "Prefix Decrement", OT_PREFIXASSIGN},40 { "?\\?", "\\", "_operator_exponential", "Exponentiation", OT_INFIX},41 { "?*?", "*", "_operator_multiply", "Multiplication", OT_INFIX},42 { "?/?", "/", "_operator_divide", "Division", OT_INFIX},43 { "?%?", "%", "_operator_modulus", "Modulo", OT_INFIX},44 { "?+?", "+", "_operator_add", "Addition", OT_INFIX},45 { "?-?", "-", "_operator_subtract", "Substraction", OT_INFIX},46 { "?<<?", "<<", "_operator_shiftleft", "Shift Left", OT_INFIX},47 { "?>>?", ">>", "_operator_shiftright", "Shift Right", OT_INFIX},48 { "?<?", "<", "_operator_less", "Less-than", OT_INFIX},49 { "?>?", ">", "_operator_greater", "Greater-than", OT_INFIX},50 { "?<=?", "<=", "_operator_lessequal", "Less-than-or-Equal", OT_INFIX},51 { "?>=?", ">=", "_operator_greaterequal", "Greater-than-or-Equal", OT_INFIX},52 { "?==?", "==", "_operator_equal", "Equality", OT_INFIX},53 { "?!=?", "!=", "_operator_notequal", "Not-Equal", OT_INFIX},54 { "?&?", "&", "_operator_bitand", "Bitwise And", OT_INFIX},55 { "?^?", "^", "_operator_bitxor", "Bitwise Xor", OT_INFIX},56 { "?|?", "|", "_operator_bitor", "Bitwise Or", OT_INFIX},57 { "?=?", "=", "_operator_assign", "Assignment", OT_INFIXASSIGN},58 { "?\\=?", "\\=", "_operator_expassign", "Exponentiation Assignment", OT_INFIXASSIGN},59 { "?*=?", "*=", "_operator_multassign", "Multiplication Assignment", OT_INFIXASSIGN},60 { "?/=?", "/=", "_operator_divassign", "Division Assignment", OT_INFIXASSIGN},61 { "?%=?", "%=", "_operator_modassign", "Modulo Assignment", OT_INFIXASSIGN},62 { "?+=?", "+=", "_operator_addassign", "Addition Assignment", OT_INFIXASSIGN},63 { "?-=?", "-=", "_operator_subassign", "Substrction Assignment", OT_INFIXASSIGN},64 { "?<<=?", "<<=", "_operator_shiftleftassign", "Shift Left Assignment", OT_INFIXASSIGN},65 { "?>>=?", ">>=", "_operator_shiftrightassign", "Shift Right Assignment", OT_INFIXASSIGN},66 { "?&=?", "&=", "_operator_bitandassign", "Bitwise And Assignment", OT_INFIXASSIGN},67 { "?^=?", "^=", "_operator_bitxorassign", "Bitwise Xor Assignment", OT_INFIXASSIGN},68 { "?|=?", "|=", "_operator_bitorassign", "Bitwise Or Assignment", OT_INFIXASSIGN},69 }; // tableValues24 namespace { 25 const OperatorInfo tableValues[] = { 26 { "?[?]", "", "_operator_index", OT_INDEX }, 27 { "?{}", "=", "_constructor", OT_CTOR }, 28 { "^?{}", "", "_destructor", OT_DTOR }, 29 { "?()", "", "_operator_call", OT_CALL }, 30 { "?++", "++", "_operator_postincr", OT_POSTFIXASSIGN }, 31 { "?--", "--", "_operator_postdecr", OT_POSTFIXASSIGN }, 32 { "*?", "*", "_operator_deref", OT_PREFIX }, 33 { "+?", "+", "_operator_unaryplus", OT_PREFIX }, 34 { "-?", "-", "_operator_unaryminus", OT_PREFIX }, 35 { "~?", "~", "_operator_bitnot", OT_PREFIX }, 36 { "!?", "!", "_operator_lognot", OT_PREFIX }, 37 { "++?", "++", "_operator_preincr", OT_PREFIXASSIGN }, 38 { "--?", "--", "_operator_predecr", OT_PREFIXASSIGN }, 39 { "?\\?", "\\", "_operator_exponential", OT_INFIX }, 40 { "?*?", "*", "_operator_multiply", OT_INFIX }, 41 { "?/?", "/", "_operator_divide", OT_INFIX }, 42 { "?%?", "%", "_operator_modulus", OT_INFIX }, 43 { "?+?", "+", "_operator_add", OT_INFIX }, 44 { "?-?", "-", "_operator_subtract", OT_INFIX }, 45 { "?<<?", "<<", "_operator_shiftleft", OT_INFIX }, 46 { "?>>?", ">>", "_operator_shiftright", OT_INFIX }, 47 { "?<?", "<", "_operator_less", OT_INFIX }, 48 { "?>?", ">", "_operator_greater", OT_INFIX }, 49 { "?<=?", "<=", "_operator_lessequal", OT_INFIX }, 50 { "?>=?", ">=", "_operator_greaterequal", OT_INFIX }, 51 { "?==?", "==", "_operator_equal", OT_INFIX }, 52 { "?!=?", "!=", "_operator_notequal", OT_INFIX }, 53 { "?&?", "&", "_operator_bitand", OT_INFIX }, 54 { "?^?", "^", "_operator_bitxor", OT_INFIX }, 55 { "?|?", "|", "_operator_bitor", OT_INFIX }, 56 { "?=?", "=", "_operator_assign", OT_INFIXASSIGN }, 57 { "?\\=?", "\\=", "_operator_expassign", OT_INFIXASSIGN }, 58 { "?*=?", "*=", "_operator_multassign", OT_INFIXASSIGN }, 59 { "?/=?", "/=", "_operator_divassign", OT_INFIXASSIGN }, 60 { "?%=?", "%=", "_operator_modassign", OT_INFIXASSIGN }, 61 { "?+=?", "+=", "_operator_addassign", OT_INFIXASSIGN }, 62 { "?-=?", "-=", "_operator_subassign", OT_INFIXASSIGN }, 63 { "?<<=?", "<<=", "_operator_shiftleftassign", OT_INFIXASSIGN }, 64 { "?>>=?", ">>=", "_operator_shiftrightassign", OT_INFIXASSIGN }, 65 { "?&=?", "&=", "_operator_bitandassign", OT_INFIXASSIGN }, 66 { "?^=?", "^=", "_operator_bitxorassign", OT_INFIXASSIGN }, 67 { "?|=?", "|=", "_operator_bitorassign", OT_INFIXASSIGN }, 68 }; 70 69 71 std::map< std::string, OperatorInfo > CodeGen::table;70 const int numOps = sizeof( tableValues ) / sizeof( OperatorInfo ); 72 71 73 CodeGen::CodeGen() { 74 enum { numOps = sizeof( tableValues ) / sizeof( OperatorInfo ) }; 75 for ( int i = 0; i < numOps; i += 1 ) { 76 table[ tableValues[i].inputName ] = tableValues[i]; 77 } // for 72 std::map< std::string, OperatorInfo > table; 73 74 void initialize() { 75 for ( int i = 0; i < numOps; ++i ) { 76 table[ tableValues[i].inputName ] = tableValues[i]; 77 } // for 78 } 79 } // namespace 80 81 bool operatorLookup( const std::string & funcName, OperatorInfo & info ) { 82 static bool init = false; 83 if ( ! init ) { 84 initialize(); 85 } // if 86 87 std::map< std::string, OperatorInfo >::const_iterator i = table.find( funcName ); 88 if ( i == table.end() ) { 89 if ( isPrefix( funcName, "?`" ) ) { 90 // handle literal suffixes, which are user-defined postfix operators 91 info.inputName = funcName; 92 info.symbol = funcName.substr(2); 93 info.outputName = toString( "__operator_literal_", info.symbol ); 94 info.type = OT_POSTFIX; 95 return true; 96 } 97 return false; 98 } else { 99 info = i->second; 100 return true; 101 } // if 78 102 } 79 103 80 const OperatorInfo * operatorLookup( const string & funcName ) { 81 if ( funcName.find_first_of( "?^*+-!", 0, 1 ) == string::npos ) return nullptr; // prefilter 82 const OperatorInfo * ret = &CodeGen::table.find( funcName )->second; // must be in the table 83 assert( ret ); 84 return ret; 104 bool isOperator( const std::string & funcName ) { 105 OperatorInfo info; 106 return operatorLookup( funcName, info ); 85 107 } 86 108 87 bool isOperator( const string & funcName ) { 88 return operatorLookup( funcName ) != nullptr; 89 } 90 91 string operatorFriendlyName( const string & funcName ) { 92 const OperatorInfo * info = operatorLookup( funcName ); 93 if ( info ) return info->friendlyName; 94 return ""; 95 } 96 97 bool isConstructor( const string & funcName ) { 98 const OperatorInfo * info = operatorLookup( funcName ); 99 if ( info ) return info->type == OT_CTOR; 109 /// determines if a given function name is one of the operator types between [begin, end) 110 template<typename Iterator> 111 bool isOperatorType( const std::string & funcName, Iterator begin, Iterator end ) { 112 OperatorInfo info; 113 if ( operatorLookup( funcName, info ) ) { 114 return std::find( begin, end, info.type ) != end; 115 } 100 116 return false; 101 117 } 102 118 103 bool isDestructor( const string & funcName ) { 104 const OperatorInfo * info = operatorLookup( funcName ); 105 if ( info ) return info->type == OT_DTOR; 106 return false; 119 bool isConstructor( const std::string & funcName ) { 120 static OperatorType types[] = { OT_CTOR }; 121 return isOperatorType( funcName, std::begin(types), std::end(types) ); 107 122 } 108 123 109 bool isCtorDtor( const string & funcName ) { 110 const OperatorInfo * info = operatorLookup( funcName ); 111 if ( info ) return info->type <= OT_CONSTRUCTOR; 112 return false; 124 bool isDestructor( const std::string & funcName ) { 125 static OperatorType types[] = { OT_DTOR }; 126 return isOperatorType( funcName, std::begin(types), std::end(types) ); 113 127 } 114 128 115 bool isAssignment( const string & funcName ) { 116 const OperatorInfo * info = operatorLookup( funcName ); 117 if ( info ) return info->type > OT_CONSTRUCTOR && info->type <= OT_ASSIGNMENT; 118 return false; 129 bool isAssignment( const std::string & funcName ) { 130 static OperatorType types[] = { OT_PREFIXASSIGN, OT_POSTFIXASSIGN, OT_INFIXASSIGN }; 131 return isOperatorType( funcName, std::begin(types), std::end(types) ); 119 132 } 120 133 121 bool isCtorDtorAssign( const string & funcName ) { 122 const OperatorInfo * info = operatorLookup( funcName ); 123 if ( info ) return info->type <= OT_ASSIGNMENT; 124 return false; 134 bool isCtorDtor( const std::string & funcName ) { 135 static OperatorType types[] = { OT_CTOR, OT_DTOR }; 136 return isOperatorType( funcName, std::begin(types), std::end(types) ); 125 137 } 126 138 127 CodeGen codegen; // initialize singleton package 139 bool isCtorDtorAssign( const std::string & funcName ) { 140 static OperatorType types[] = { OT_CTOR, OT_DTOR, OT_PREFIXASSIGN, OT_POSTFIXASSIGN, OT_INFIXASSIGN }; 141 return isOperatorType( funcName, std::begin(types), std::end(types) ); 142 } 128 143 } // namespace CodeGen 129 144 130 145 // Local Variables: // 131 146 // tab-width: 4 // 147 // mode: c++ // 148 // compile-command: "make install" // 132 149 // End: // -
src/CodeGen/OperatorTable.h
ra505021 r8c50aed 10 10 // Created On : Mon May 18 07:44:20 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sun Feb 16 08:13:34 202013 // Update Count : 2612 // Last Modified On : Fri Jul 21 22:17:11 2017 13 // Update Count : 6 14 14 // 15 15 … … 17 17 18 18 #include <string> 19 #include <map>20 19 21 20 namespace CodeGen { 22 21 enum OperatorType { 22 OT_INDEX, 23 23 OT_CTOR, 24 24 OT_DTOR, 25 OT_CONSTRUCTOR = OT_DTOR, 25 OT_CALL, 26 OT_PREFIX, 27 OT_POSTFIX, 28 OT_INFIX, 26 29 OT_PREFIXASSIGN, 27 30 OT_POSTFIXASSIGN, 28 31 OT_INFIXASSIGN, 29 OT_ASSIGNMENT = OT_INFIXASSIGN,30 OT_CALL,31 OT_PREFIX,32 OT_INFIX,33 OT_POSTFIX,34 OT_INDEX,35 32 OT_LABELADDRESS, 36 33 OT_CONSTANT … … 41 38 std::string symbol; 42 39 std::string outputName; 43 std::string friendlyName;44 40 OperatorType type; 45 41 }; 46 42 47 class CodeGen {48 friend const OperatorInfo * operatorLookup( const std::string & funcName );49 50 static const OperatorInfo tableValues[];51 static std::map< std::string, OperatorInfo > table;52 public:53 CodeGen();54 }; // CodeGen55 56 43 bool isOperator( const std::string & funcName ); 57 const OperatorInfo * operatorLookup( const std::string & funcName ); 58 std::string operatorFriendlyName( const std::string & funcName ); 44 bool operatorLookup( const std::string & funcName, OperatorInfo & info ); 59 45 60 46 bool isConstructor( const std::string & ); -
src/CodeGen/Options.h
ra505021 r8c50aed 9 9 // Author : Andrew Beach 10 10 // Created On : Tue Apr 30 11:36:00 2019 11 // Last Modified By : Peter A. Buhr12 // Last Modified On : Sat Feb 15 18:37:06 202013 // Update Count : 311 // Last Modified By : Andrew Beach 12 // Last Modified On : Thr May 2 10:45:00 2019 13 // Update Count : 2 14 14 // 15 15 16 16 #pragma once 17 17 18 struct Options { 19 // External Options: Same thoughout a pass. 20 bool pretty; 21 bool genC; 22 bool lineMarks; 23 bool printExprTypes; 18 namespace CodeGen { 19 struct Options { 20 // External Options: Same thoughout a pass. 21 bool pretty; 22 bool genC; 23 bool lineMarks; 24 bool printExprTypes; 24 25 25 // Internal Options: Changed on some recurisive calls.26 bool anonymousUnused = false;26 // Internal Options: Changed on some recurisive calls. 27 bool anonymousUnused = false; 27 28 28 Options(bool pretty, bool genC, bool lineMarks, bool printExprTypes) :29 pretty(pretty), genC(genC), lineMarks(lineMarks), printExprTypes(printExprTypes)29 Options(bool pretty, bool genC, bool lineMarks, bool printExprTypes) : 30 pretty(pretty), genC(genC), lineMarks(lineMarks), printExprTypes(printExprTypes) 30 31 {} 31 }; 32 }; 33 } // namespace CodeGen 32 34 33 35 // Local Variables: // -
src/CodeTools/ResolvProtoDump.cc
ra505021 r8c50aed 9 9 // Author : Aaron Moss 10 10 // Created On : Tue Sep 11 09:04:00 2018 11 // Last Modified By : Peter A. Buhr12 // Last Modified On : Sat Feb 15 13:50:11 202013 // Update Count : 311 // Last Modified By : Aaron Moss 12 // Last Modified On : Tue Sep 11 09:04:00 2018 13 // Update Count : 1 14 14 // 15 15 … … 182 182 183 183 // replace operator names 184 const CodeGen::OperatorInfo * opInfo = CodeGen::operatorLookup( name );185 if ( opInfo) {184 CodeGen::OperatorInfo info; 185 if ( CodeGen::operatorLookup( name, info ) ) { 186 186 ss << new_prefix(pre, ""); 187 op_name( opInfo->outputName, ss );187 op_name( info.outputName, ss ); 188 188 return; 189 189 } -
src/Common/PassVisitor.impl.h
ra505021 r8c50aed 3302 3302 VISIT_START( node ); 3303 3303 3304 indexerAdd Union( node->name );3304 indexerAddStruct( node->name ); 3305 3305 3306 3306 { … … 3317 3317 VISIT_START( node ); 3318 3318 3319 indexerAdd Union( node->name );3319 indexerAddStruct( node->name ); 3320 3320 3321 3321 { … … 3332 3332 MUTATE_START( node ); 3333 3333 3334 indexerAdd Union( node->name );3334 indexerAddStruct( node->name ); 3335 3335 3336 3336 { -
src/Common/SemanticError.h
ra505021 r8c50aed 49 49 struct WarningData { 50 50 const char * const name; 51 const char * const message; 51 52 const Severity default_severity; 52 const char * const message;53 53 }; 54 54 55 55 constexpr WarningData WarningFormats[] = { 56 {"self-assign" , Severity::Warn , "self assignment of expression: %s" }, 57 {"reference-conversion" , Severity::Warn , "rvalue to reference conversion of rvalue: %s" }, 58 {"qualifiers-zero_t-one_t", Severity::Warn , "questionable use of type qualifier %s with %s" }, 59 {"aggregate-forward-decl" , Severity::Warn , "forward declaration of nested aggregate: %s" }, 60 {"superfluous-decl" , Severity::Warn , "declaration does not allocate storage: %s" }, 61 {"gcc-attributes" , Severity::Warn , "invalid attribute: %s" }, 62 {"c++-like-copy" , Severity::Warn , "Constructor from reference is not a valid copy constructor" }, 56 {"self-assign" , "self assignment of expression: %s" , Severity::Warn}, 57 {"reference-conversion" , "rvalue to reference conversion of rvalue: %s" , Severity::Warn}, 58 {"qualifiers-zero_t-one_t", "questionable use of type qualifier %s with %s", Severity::Warn}, 59 {"aggregate-forward-decl" , "forward declaration of nested aggregate: %s" , Severity::Warn}, 60 {"superfluous-decl" , "declaration does not allocate storage: %s" , Severity::Warn}, 61 {"gcc-attributes" , "invalid attribute: %s" , Severity::Warn}, 63 62 }; 64 63 … … 70 69 SuperfluousDecl, 71 70 GccAttributes, 72 CppCopy,73 71 NUMBER_OF_WARNINGS, // This MUST be the last warning 74 72 }; -
src/Common/utility.h
ra505021 r8c50aed 10 10 // Created On : Mon May 18 07:44:20 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Feb 11 13:00:36 202013 // Update Count : 5012 // Last Modified On : Wed Jul 24 14:28:19 2019 13 // Update Count : 41 14 14 // 15 15 … … 29 29 #include <utility> 30 30 #include <vector> 31 #include <cstring> // memcmp32 31 33 32 #include "Common/Indenter.h" … … 265 264 } 266 265 267 // determines if pref is a prefix of str268 static inline bool isPrefix( const std::string & str, const std::string & pref , unsigned int start = 0) {266 /// determines if `pref` is a prefix of `str` 267 static inline bool isPrefix( const std::string & str, const std::string & pref ) { 269 268 if ( pref.size() > str.size() ) return false; 270 return 0 == memcmp( str.c_str() + start, pref.c_str(), pref.size() );271 // return prefix == full.substr(0, prefix.size()); // for future, requires c++17269 auto its = std::mismatch( pref.begin(), pref.end(), str.begin() ); 270 return its.first == pref.end(); 272 271 } 273 272 -
src/ControlStruct/Mutate.cc
ra505021 r8c50aed 10 10 // Created On : Mon May 18 07:44:20 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sun Feb 16 03:22:07 202013 // Update Count : 1012 // Last Modified On : Thu Aug 4 11:39:08 2016 13 // Update Count : 9 14 14 // 15 15 … … 37 37 mutateAll( translationUnit, formut ); 38 38 } 39 } // namespace Co ntrolStruct39 } // namespace CodeGen 40 40 41 41 // Local Variables: // -
src/InitTweak/FixInit.cc
ra505021 r8c50aed 10 10 // Created On : Wed Jan 13 16:29:30 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sun Feb 16 04:17:07 202013 // Update Count : 8212 // Last Modified On : Fri Dec 13 23:41:27 2019 13 // Update Count : 77 14 14 // 15 15 #include "FixInit.h" … … 745 745 } 746 746 747 // to prevent warnings ( '_unq0'may be used uninitialized in this function),747 // to prevent warnings (‘_unq0’ may be used uninitialized in this function), 748 748 // insert an appropriate zero initializer for UniqueExpr temporaries. 749 749 Initializer * makeInit( Type * t ) { -
src/InitTweak/FixInit.h
ra505021 r8c50aed 10 10 // Created On : Wed Jan 13 16:29:30 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : S un Feb 16 07:54:50 202013 // Update Count : 812 // Last Modified On : Sat Jul 22 09:31:06 2017 13 // Update Count : 6 14 14 // 15 15 … … 22 22 23 23 namespace InitTweak { 24 /// replace constructor initializers with expression statements and unwrap basic C-style initializers 24 /// replace constructor initializers with expression statements 25 /// and unwrap basic C-style initializers 25 26 void fix( std::list< Declaration * > & translationUnit, bool inLibrary ); 26 27 } // namespace -
src/MakeLibCfa.cc
ra505021 r8c50aed 10 10 // Created On : Sat May 16 10:33:33 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sun Feb 16 03:49:49 202013 // Update Count : 4 512 // Last Modified On : Fri Dec 13 23:41:40 2019 13 // Update Count : 42 14 14 // 15 15 … … 96 96 97 97 FunctionDecl *funcDecl = origFuncDecl->clone(); 98 const CodeGen::OperatorInfo *opInfo;99 opInfo = CodeGen::operatorLookup( funcDecl->get_name());100 assert( opInfo);98 CodeGen::OperatorInfo opInfo; 99 bool lookResult = CodeGen::operatorLookup( funcDecl->get_name(), opInfo ); 100 assert( lookResult ); 101 101 assert( ! funcDecl->get_statements() ); 102 102 // build a recursive call - this is okay, as the call will actually be codegen'd using operator syntax … … 120 120 121 121 Statement * stmt = nullptr; 122 switch ( opInfo ->type ) {122 switch ( opInfo.type ) { 123 123 case CodeGen::OT_INDEX: 124 124 case CodeGen::OT_CALL: -
src/Parser/ParseNode.h
ra505021 r8c50aed 10 10 // Created On : Sat May 16 13:28:16 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Fri Feb 7 17:56:02 202013 // Update Count : 8 9112 // Last Modified On : Mon Dec 16 07:46:01 2019 13 // Update Count : 888 14 14 // 15 15 … … 449 449 * out++ = result; 450 450 } else { 451 SemanticError( cur->location, "type specifier declaration in forall clause is currently unimplemented.");451 assertf(false, "buildList unknown type"); 452 452 } // if 453 453 } catch( SemanticErrorException & e ) { -
src/Parser/ParserTypes.h
ra505021 r8c50aed 10 10 // Created On : Sat Sep 22 08:58:10 2001 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sat Feb 15 11:04:40 202013 // Update Count : 35 112 // Last Modified On : Sat Jul 22 09:33:28 2017 13 // Update Count : 350 14 14 // 15 15 … … 27 27 // current location in the input 28 28 extern int yylineno; 29 extern char * yyfilename;29 extern char *yyfilename; 30 30 31 31 struct Location { 32 char * file;32 char *file; 33 33 int line; 34 34 }; // Location 35 35 36 36 struct Token { 37 std::string * str; // must be pointer as used in union37 std::string *str; // must be pointer as used in union 38 38 Location loc; 39 39 -
src/Parser/TypedefTable.cc
ra505021 r8c50aed 10 10 // Created On : Sat May 16 15:20:13 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sat Feb 15 08:06:36 202013 // Update Count : 25 912 // Last Modified On : Wed Jul 25 15:32:35 2018 13 // Update Count : 258 14 14 // 15 15 … … 47 47 } // TypedefTable::~TypedefTable 48 48 49 bool TypedefTable::exists( const string & identifier ) const{49 bool TypedefTable::exists( const string & identifier ) { 50 50 return kindTable.find( identifier ) != kindTable.end(); 51 51 } // TypedefTable::exists 52 52 53 bool TypedefTable::existsCurr( const string & identifier ) const{53 bool TypedefTable::existsCurr( const string & identifier ) { 54 54 return kindTable.findAt( kindTable.currentScope() - 1, identifier ) != kindTable.end(); 55 55 } // TypedefTable::exists -
src/Parser/TypedefTable.h
ra505021 r8c50aed 10 10 // Created On : Sat May 16 15:24:36 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sat Feb 15 08:06:37 202013 // Update Count : 11 712 // Last Modified On : Wed Jul 25 15:33:55 2018 13 // Update Count : 114 14 14 // 15 15 … … 30 30 ~TypedefTable(); 31 31 32 bool exists( const std::string & identifier ) const;33 bool existsCurr( const std::string & identifier ) const;32 bool exists( const std::string & identifier ); 33 bool existsCurr( const std::string & identifier ); 34 34 int isKind( const std::string & identifier ) const; 35 35 void makeTypedef( const std::string & name, int kind = TYPEDEFname ); -
src/Parser/lex.ll
ra505021 r8c50aed 10 10 * Created On : Sat Sep 22 08:58:10 2001 11 11 * Last Modified By : Peter A. Buhr 12 * Last Modified On : Sat Feb 15 11:05:50202013 * Update Count : 7 3712 * Last Modified On : Sat Feb 1 07:16:44 2020 13 * Update Count : 724 14 14 */ 15 15 … … 42 42 #include "ParseNode.h" 43 43 #include "TypedefTable.h" 44 45 string * build_postfix_name( string * name );46 44 47 45 char *yyfilename; … … 332 330 /* identifier */ 333 331 {identifier} { IDENTIFIER_RETURN(); } 334 "``"{identifier} {// CFA335 yytext[yyleng ] = '\0'; yytext += 2;// SKULLDUGGERY: remove backquotes (ok to shorten?)332 "``"{identifier}"``" { // CFA 333 yytext[yyleng - 2] = '\0'; yytext += 2; // SKULLDUGGERY: remove backquotes (ok to shorten?) 336 334 IDENTIFIER_RETURN(); 337 335 } … … 434 432 "?"({op_unary_pre_post}|"()"|"[?]"|"{}") { IDENTIFIER_RETURN(); } 435 433 "^?{}" { IDENTIFIER_RETURN(); } 436 "?`"{identifier} { // postfix operator 437 yylval.tok.str = new string( &yytext[2] ); // remove ?` 438 yylval.tok.str = build_postfix_name( yylval.tok.str ); // add prefix 439 RETURN_LOCN( typedefTable.isKind( *yylval.tok.str ) ); 440 } 434 "?`"{identifier} { IDENTIFIER_RETURN(); } // postfix operator 441 435 "?"{op_binary_over}"?" { IDENTIFIER_RETURN(); } // binary 442 436 /* -
src/Parser/parser.yy
ra505021 r8c50aed 10 10 // Created On : Sat Sep 1 20:22:55 2001 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Fri Feb 21 14:47:29202013 // Update Count : 44 6812 // Last Modified On : Sat Feb 1 10:04:40 2020 13 // Update Count : 4440 14 14 // 15 15 … … 166 166 } // rebindForall 167 167 168 string * build_postfix_name( string * name ) { 169 *name = string("__postfix_func_") + *name; 170 return name; 168 NameExpr * build_postfix_name( const string * name ) { 169 NameExpr * new_name = build_varref( new string( "?`" + *name ) ); 170 delete name; 171 return new_name; 171 172 } // build_postfix_name 172 173 … … 632 633 { $$ = new ExpressionNode( build_func( $1, $3 ) ); } 633 634 | postfix_expression '`' identifier // CFA, postfix call 634 { $$ = new ExpressionNode( build_func( new ExpressionNode( build_ varref( build_postfix_name( $3 )) ), $1 ) ); }635 { $$ = new ExpressionNode( build_func( new ExpressionNode( build_postfix_name( $3 ) ), $1 ) ); } 635 636 | constant '`' identifier // CFA, postfix call 636 { $$ = new ExpressionNode( build_func( new ExpressionNode( build_ varref( build_postfix_name( $3 )) ), $1 ) ); }637 { $$ = new ExpressionNode( build_func( new ExpressionNode( build_postfix_name( $3 ) ), $1 ) ); } 637 638 | string_literal '`' identifier // CFA, postfix call 638 { $$ = new ExpressionNode( build_func( new ExpressionNode( build_ varref( build_postfix_name( $3 )) ), new ExpressionNode( $1 ) ) ); }639 { $$ = new ExpressionNode( build_func( new ExpressionNode( build_postfix_name( $3 ) ), new ExpressionNode( $1 ) ) ); } 639 640 | postfix_expression '.' identifier 640 641 { $$ = new ExpressionNode( build_fieldSel( $1, build_varref( $3 ) ) ); } … … 1589 1590 // type_specifier can resolve to just TYPEDEFname (e.g., typedef int T; int f( T );). Therefore this must be 1590 1591 // flattened to allow lookahead to the '(' without having to reduce identifier_or_type_name. 1591 cfa_abstract_tuple identifier_or_type_name '(' push cfa_parameter_ellipsis_list_opt pop ')' attribute_list_opt1592 cfa_abstract_tuple identifier_or_type_name '(' push cfa_parameter_ellipsis_list_opt pop ')' 1592 1593 // To obtain LR(1 ), this rule must be factored out from function return type (see cfa_abstract_declarator). 1593 { $$ = DeclarationNode::newFunction( $2, $1, $5, 0 ) ->addQualifiers( $8 ); }1594 | cfa_function_return identifier_or_type_name '(' push cfa_parameter_ellipsis_list_opt pop ')' attribute_list_opt1595 { $$ = DeclarationNode::newFunction( $2, $1, $5, 0 ) ->addQualifiers( $8 ); }1594 { $$ = DeclarationNode::newFunction( $2, $1, $5, 0 ); } 1595 | cfa_function_return identifier_or_type_name '(' push cfa_parameter_ellipsis_list_opt pop ')' 1596 { $$ = DeclarationNode::newFunction( $2, $1, $5, 0 ); } 1596 1597 ; 1597 1598 -
src/ResolvExpr/Resolver.cc
ra505021 r8c50aed 84 84 void previsit( ThrowStmt * throwStmt ); 85 85 void previsit( CatchStmt * catchStmt ); 86 void postvisit( CatchStmt * catchStmt );87 86 void previsit( WaitForStmt * stmt ); 88 87 … … 568 567 569 568 void Resolver_old::previsit( CatchStmt * catchStmt ) { 570 // Until we are very sure this invarent (ifs that move between passes have thenPart)571 // holds, check it. This allows a check for when to decode the mangling.572 if ( IfStmt * ifStmt = dynamic_cast<IfStmt *>( catchStmt->body ) ) {573 assert( ifStmt->thenPart );574 }575 // Encode the catchStmt so the condition can see the declaration.576 569 if ( catchStmt->cond ) { 577 IfStmt * ifStmt = new IfStmt( catchStmt->cond, nullptr, catchStmt->body ); 578 catchStmt->cond = nullptr; 579 catchStmt->body = ifStmt; 580 } 581 } 582 583 void Resolver_old::postvisit( CatchStmt * catchStmt ) { 584 // Decode the catchStmt so everything is stored properly. 585 IfStmt * ifStmt = dynamic_cast<IfStmt *>( catchStmt->body ); 586 if ( nullptr != ifStmt && nullptr == ifStmt->thenPart ) { 587 assert( ifStmt->condition ); 588 assert( ifStmt->elsePart ); 589 catchStmt->cond = ifStmt->condition; 590 catchStmt->body = ifStmt->elsePart; 591 ifStmt->condition = nullptr; 592 ifStmt->elsePart = nullptr; 593 delete ifStmt; 570 findSingleExpression( catchStmt->cond, new BasicType( noQualifiers, BasicType::Bool ), indexer ); 594 571 } 595 572 } … … 1489 1466 1490 1467 const ast::CatchStmt * Resolver_new::previsit( const ast::CatchStmt * catchStmt ) { 1491 // TODO: This will need a fix for the decl/cond scoping problem.1492 1468 if ( catchStmt->cond ) { 1493 1469 ast::ptr< ast::Type > boolType = new ast::BasicType{ ast::BasicType::Bool }; -
src/SymTab/Demangle.cc
ra505021 r8c50aed 10 10 // Created On : Thu Jul 19 12:52:41 2018 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Feb 11 15:09:18 202013 // Update Count : 1012 // Last Modified On : Fri Dec 13 14:54:15 2019 13 // Update Count : 4 14 14 // 15 15 … … 19 19 #include "CodeGen/GenType.h" 20 20 #include "Common/PassVisitor.h" 21 #include "Common/utility.h" // isPrefix22 21 #include "Mangler.h" 23 22 #include "SynTree/Type.h" … … 417 416 418 417 bool StringView::isPrefix(const std::string & pref) { 419 // if ( pref.size() > str.size()-idx ) return false; 420 // auto its = std::mismatch( pref.begin(), pref.end(), std::next(str.begin(), idx) ); 421 // if (its.first == pref.end()) { 422 // idx += pref.size(); 423 // return true; 424 // } 425 426 // This update is untested because there are no tests for this code. 427 if ( ::isPrefix( str, pref, idx ) ) { 418 if ( pref.size() > str.size()-idx ) return false; 419 auto its = std::mismatch( pref.begin(), pref.end(), std::next(str.begin(), idx) ); 420 if (its.first == pref.end()) { 428 421 idx += pref.size(); 429 422 return true; … … 436 429 PRINT( std::cerr << "====== " << str.size() << " " << str << std::endl; ) 437 430 if (str.size() < 2+Encoding::manglePrefix.size()) return false; // +2 for at least _1 suffix 438 if ( ! isPrefix(Encoding::manglePrefix) || ! isdigit(str.back() )) return false;431 if (! isPrefix(Encoding::manglePrefix) || ! isdigit(str.back())) return false; 439 432 440 433 // get name -
src/SymTab/Mangler.cc
ra505021 r8c50aed 10 10 // Created On : Sun May 17 21:40:29 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sat Feb 15 13:55:12 202013 // Update Count : 3312 // Last Modified On : Fri Dec 13 23:43:49 2019 13 // Update Count : 28 14 14 // 15 15 #include "Mangler.h" … … 128 128 } // if 129 129 mangleName << Encoding::manglePrefix; 130 const CodeGen::OperatorInfo * opInfo = CodeGen::operatorLookup( declaration->get_name() );131 if ( op Info) {132 mangleName << opInfo ->outputName.size() << opInfo->outputName;130 CodeGen::OperatorInfo opInfo; 131 if ( operatorLookup( declaration->get_name(), opInfo ) ) { 132 mangleName << opInfo.outputName.size() << opInfo.outputName; 133 133 } else { 134 134 mangleName << declaration->name.size() << declaration->name; … … 471 471 } // if 472 472 mangleName << Encoding::manglePrefix; 473 const CodeGen::OperatorInfo * opInfo = CodeGen::operatorLookup( decl->name );474 if ( op Info) {475 mangleName << opInfo ->outputName.size() << opInfo->outputName;473 CodeGen::OperatorInfo opInfo; 474 if ( operatorLookup( decl->name, opInfo ) ) { 475 mangleName << opInfo.outputName.size() << opInfo.outputName; 476 476 } else { 477 477 mangleName << decl->name.size() << decl->name; -
src/SymTab/Validate.cc
ra505021 r8c50aed 311 311 Stats::Heap::newPass("validate-A"); 312 312 Stats::Time::BlockGuard guard("validate-A"); 313 VerifyCtorDtorAssign::verify( translationUnit ); // must happen before autogen, because autogen examines existing ctor/dtors314 313 acceptAll( translationUnit, hoistDecls ); 315 314 ReplaceTypedef::replaceTypedef( translationUnit ); … … 337 336 Stats::Time::BlockGuard guard("validate-C"); 338 337 acceptAll( translationUnit, genericParams ); // check as early as possible - can't happen before LinkReferenceToTypes_old 338 VerifyCtorDtorAssign::verify( translationUnit ); // must happen before autogen, because autogen examines existing ctor/dtors 339 339 ReturnChecker::checkFunctionReturns( translationUnit ); 340 340 InitTweak::fixReturnStatements( translationUnit ); // must happen before autogen … … 1182 1182 if ( CodeGen::isCtorDtorAssign( funcDecl->get_name() ) ) { // TODO: also check /=, etc. 1183 1183 if ( params.size() == 0 ) { 1184 SemanticError( funcDecl ->location, "Constructors, destructors, and assignment functions require at least one parameter." );1184 SemanticError( funcDecl, "Constructors, destructors, and assignment functions require at least one parameter " ); 1185 1185 } 1186 1186 ReferenceType * refType = dynamic_cast< ReferenceType * >( params.front()->get_type() ); 1187 1187 if ( ! refType ) { 1188 SemanticError( funcDecl ->location, "First parameter of a constructor, destructor, or assignment function must be a reference." );1188 SemanticError( funcDecl, "First parameter of a constructor, destructor, or assignment function must be a reference " ); 1189 1189 } 1190 1190 if ( CodeGen::isCtorDtor( funcDecl->get_name() ) && returnVals.size() != 0 ) { 1191 if(!returnVals.front()->get_type()->isVoid()) { 1192 SemanticError( funcDecl->location, "Constructors and destructors cannot have explicit return values." ); 1193 } 1191 SemanticError( funcDecl, "Constructors and destructors cannot have explicit return values " ); 1194 1192 } 1195 1193 } -
src/SynTree/Attribute.h
ra505021 r8c50aed 10 10 // Created On : Mon May 18 07:44:20 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Thu Feb 13 21:34:08 202013 // Update Count : 4012 // Last Modified On : Sat Jul 22 09:54:14 2017 13 // Update Count : 39 14 14 // 15 15 … … 38 38 virtual ~Attribute(); 39 39 40 const std::string &get_name() const { return name; }40 std::string get_name() const { return name; } 41 41 void set_name( const std::string & newValue ) { name = newValue; } 42 42 std::list< Expression * > & get_parameters() { return parameters; } -
src/cfa.make
ra505021 r8c50aed 32 32 am__v_GOC_1 = 33 33 34 AM_V_PY = $(am__v_PY_@AM_V@)35 am__v_PY_ = $(am__v_PY_@AM_DEFAULT_V@)36 am__v_PY_0 = @echo " PYTHON " $@;37 am__v_PY_1 =38 39 34 AM_V_RUST = $(am__v_RUST_@AM_V@) 40 35 am__v_RUST_ = $(am__v_RUST_@AM_DEFAULT_V@) 41 am__v_RUST_0 = @echo " RUST " $@;36 am__v_RUST_0 = @echo " RUST " $@; 42 37 am__v_RUST_1 = 43 38 44 39 AM_V_NODEJS = $(am__v_NODEJS_@AM_V@) 45 40 am__v_NODEJS_ = $(am__v_NODEJS_@AM_DEFAULT_V@) 46 am__v_NODEJS_0 = @echo " NODEJS " $@;41 am__v_NODEJS_0 = @echo " NODEJS " $@; 47 42 am__v_NODEJS_1 = 48 43 -
src/main.cc
ra505021 r8c50aed 10 10 // Created On : Fri May 15 23:12:02 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sat Feb 8 08:33:50 202013 // Update Count : 6 3312 // Last Modified On : Mon Dec 16 17:55:53 2019 13 // Update Count : 627 14 14 // 15 15 … … 105 105 106 106 static void backtrace( int start ) { // skip first N stack frames 107 enum { Frames = 50 , }; // maximum number of stack frames107 enum { Frames = 50 }; 108 108 void * array[Frames]; 109 size_t size = ::backtrace( array, Frames );109 int size = ::backtrace( array, Frames ); 110 110 char ** messages = ::backtrace_symbols( array, size ); // does not demangle names 111 111 … … 114 114 115 115 // skip last 2 stack frames after main 116 for ( unsignedint i = start; i < size - 2 && messages != nullptr; i += 1 ) {116 for ( int i = start; i < size - 2 && messages != nullptr; i += 1 ) { 117 117 char * mangled_name = nullptr, * offset_begin = nullptr, * offset_end = nullptr; 118 118 … … 180 180 } // sigSegvBusHandler 181 181 182 static void sigFpeHandler( SIGPARMS ) {183 const char * msg;184 185 switch ( sfp->si_code ) {186 case FPE_INTDIV: case FPE_FLTDIV: msg = "divide by zero"; break;187 case FPE_FLTOVF: msg = "overflow"; break;188 case FPE_FLTUND: msg = "underflow"; break;189 case FPE_FLTRES: msg = "inexact result"; break;190 case FPE_FLTINV: msg = "invalid operation"; break;191 default: msg = "unknown";192 } // choose193 cerr << "Computation error " << msg << " at location " << sfp->si_addr << endl194 << "Possible cause is constant-expression evaluation invalid." << endl;195 backtrace( 2 ); // skip first 2 stack frames196 abort(); // cause core dump for debugging197 } // sigFpeHandler198 199 182 static void sigAbortHandler( SIGPARMS ) { 200 183 backtrace( 6 ); // skip first 6 stack frames … … 210 193 Signal( SIGSEGV, sigSegvBusHandler, SA_SIGINFO ); 211 194 Signal( SIGBUS, sigSegvBusHandler, SA_SIGINFO ); 212 Signal( SIGFPE, sigFpeHandler, SA_SIGINFO );213 195 Signal( SIGABRT, sigAbortHandler, SA_SIGINFO ); 214 196 -
tests/.expect/alloc-ERROR.txt
ra505021 r8c50aed 1 alloc.cfa:31 0:1 error: No reasonable alternatives for expression Applying untyped:1 alloc.cfa:311:1 error: No reasonable alternatives for expression Applying untyped: 2 2 Name: ?=? 3 3 ...to: … … 19 19 20 20 21 alloc.cfa:31 1:1 error: No reasonable alternatives for expression Applying untyped:21 alloc.cfa:312:1 error: No reasonable alternatives for expression Applying untyped: 22 22 Name: ?=? 23 23 ...to: … … 39 39 40 40 41 alloc.cfa:31 2:1 error: No reasonable alternatives for expression Applying untyped:41 alloc.cfa:313:1 error: No reasonable alternatives for expression Applying untyped: 42 42 Name: ?=? 43 43 ...to: … … 50 50 51 51 52 alloc.cfa:31 3:1 error: No reasonable alternatives for expression Applying untyped:52 alloc.cfa:314:1 error: No reasonable alternatives for expression Applying untyped: 53 53 Name: ?=? 54 54 ...to: -
tests/.expect/alloc.txt
ra505021 r8c50aed 2 2 CFA malloc 0xdeadbeef 3 3 CFA alloc 0xdeadbeef 4 CFA array alloc, fill 0xde 4 5 CFA alloc, fill dededede 5 6 CFA alloc, fill 3 -
tests/.expect/nested-types-ERR1.txt
ra505021 r8c50aed 1 nested-types.cfa: 83:1 error: Use of undefined type T1 nested-types.cfa:70:1 error: Use of undefined type T -
tests/.expect/nested-types-ERR2.txt
ra505021 r8c50aed 1 nested-types.cfa: 86:1 error: Use of undefined global type Z2 nested-types.cfa: 87:1 error: Qualified type requires an aggregate on the left, but has: signed int3 nested-types.cfa: 88:1 error: Undefined type in qualified type: Qualified Type:1 nested-types.cfa:73:1 error: Use of undefined global type Z 2 nested-types.cfa:74:1 error: Qualified type requires an aggregate on the left, but has: signed int 3 nested-types.cfa:75:1 error: Undefined type in qualified type: Qualified Type: 4 4 instance of struct S with body 1 5 5 instance of type Z (not function type) -
tests/.expect/rational.txt
ra505021 r8c50aed 1 1 constructor 2 3/1 4/1 0/1 0/1 1/12 3/1 4/1 0/1 3 3 1/2 5/7 4 4 2/3 -3/2 -
tests/Makefile.in
ra505021 r8c50aed 374 374 am__v_GOC_0 = @echo " GOC " $@; 375 375 am__v_GOC_1 = 376 AM_V_PY = $(am__v_PY_@AM_V@)377 am__v_PY_ = $(am__v_PY_@AM_DEFAULT_V@)378 am__v_PY_0 = @echo " PYTHON " $@;379 am__v_PY_1 =380 376 AM_V_RUST = $(am__v_RUST_@AM_V@) 381 377 am__v_RUST_ = $(am__v_RUST_@AM_DEFAULT_V@) 382 am__v_RUST_0 = @echo " RUST " $@;378 am__v_RUST_0 = @echo " RUST " $@; 383 379 am__v_RUST_1 = 384 380 AM_V_NODEJS = $(am__v_NODEJS_@AM_V@) 385 381 am__v_NODEJS_ = $(am__v_NODEJS_@AM_DEFAULT_V@) 386 am__v_NODEJS_0 = @echo " NODEJS " $@;382 am__v_NODEJS_0 = @echo " NODEJS " $@; 387 383 am__v_NODEJS_1 = 388 384 AM_V_JAVAC = $(am__v_JAVAC_@AM_V@) -
tests/alloc.cfa
ra505021 r8c50aed 10 10 // Created On : Wed Feb 3 07:56:22 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sun Feb 16 09:21:13 202013 // Update Count : 40 512 // Last Modified On : Fri Nov 22 15:34:19 2019 13 // Update Count : 404 14 14 // 15 15 … … 48 48 49 49 p = alloc_set( fill ); // CFA alloc, fill 50 printf( "CFA array alloc, fill %#hhx\n", fill ); 50 51 printf( "CFA alloc, fill %08x\n", *p ); 51 52 free( p ); -
tests/concurrent/examples/quickSort.cfa
ra505021 r8c50aed 11 11 // Created On : Wed Dec 6 12:15:52 2017 12 12 // Last Modified By : Peter A. Buhr 13 // Last Modified On : Wed Feb 12 18:24:47 202014 // Update Count : 17 713 // Last Modified On : Thu Oct 10 13:58:18 2019 14 // Update Count : 176 15 15 // 16 16 … … 27 27 28 28 void ?{}( Quicksort & qs, int values[], int size, int depth ) { 29 qs. [values, low, high, depth] = [values, 0, size, depth];29 qs.values = values; qs.low = 0; qs.high = size; qs.depth = depth; 30 30 } // Quicksort 31 31 … … 167 167 values[counter] = size - counter; // descending values 168 168 } // for 169 for ( i ; 200 ) {// random shuffle a few values169 for ( int i = 0; i < 200; i +=1 ) { // random shuffle a few values 170 170 swap( values[rand() % size], values[rand() % size] ); 171 171 } // for -
tests/exceptions/except-0.cfa
ra505021 r8c50aed 19 19 }; 20 20 21 void ?{}(signal_exit &this, const char * area) {22 this .area = area;23 } 24 25 void ^?{}(signal_exit &this) {26 printf("Exiting: %s\n", this .area);21 void ?{}(signal_exit * this, const char * area) { 22 this->area = area; 23 } 24 25 void ^?{}(signal_exit * this) { 26 printf("Exiting: %s\n", this->area); 27 27 // sout | "Exiting:" | this->area; 28 28 } … … 242 242 243 243 // Uncaught termination test. 244 /* Removed due to non-deterministic output.245 244 printf("Throw uncaught.\n"); 246 245 yang z; 247 246 terminate(&z); 248 */ 249 } 247 } -
tests/exceptions/except-2.cfa
ra505021 r8c50aed 12 12 struct TABLE(BASE_EXCEPT) const * parent; 13 13 size_t size; 14 void (*copy)(num_error &this, num_error &other);15 void (*free)(num_error &this);14 void (*copy)(num_error *this, num_error * other); 15 void (*free)(num_error *this); 16 16 const char * (*msg)(num_error *this); 17 17 int (*code)(num_error *this); … … 28 28 if ( ! this->msg ) { 29 29 static const char * base = "Num Error with code: X"; 30 this->msg = (char *)malloc(22);30 this->msg = malloc(22); 31 31 for (int i = 0 ; (this->msg[i] = base[i]) ; ++i); 32 32 } … … 34 34 return this->msg; 35 35 } 36 void ?{}(num_error &this, int num) {37 this .virtual_table = &INSTANCE(num_error);38 this .msg = 0;39 this .num = num;36 void ?{}(num_error * this, int num) { 37 this->virtual_table = &INSTANCE(num_error); 38 this->msg = 0; 39 this->num = num; 40 40 } 41 void ?{}(num_error & this, num_error &other) {42 this .virtual_table = other.virtual_table;43 this .msg = 0;44 this .num = other.num;41 void ?{}(num_error * this, num_error * other) { 42 this->virtual_table = other->virtual_table; 43 this->msg = 0; 44 this->num = other->num; 45 45 } 46 void ^?{}(num_error &this) {47 if( this .msg ) free( this.msg );46 void ^?{}(num_error * this) { 47 if( this->msg ) free( this->msg ); 48 48 } 49 49 int num_error_code( num_error * this ) { -
tests/labelledExit.cfa
ra505021 r8c50aed 10 10 // Created On : Wed Aug 10 07:29:39 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Wed Feb 5 16:49:48 202013 // Update Count : 912 // Last Modified On : Fri Oct 25 17:41:51 2019 13 // Update Count : 7 14 14 // 15 15 … … 162 162 163 163 // computed goto 164 {165 void *array[] = { &&foo, &&bar, &&hack };166 foo: bar: hack:167 &&foo;168 &&bar;169 goto *array[i];170 }164 // { 165 // void *array[] = { &&foo, &&bar, &&hack }; 166 // foo: bar: hack: 167 // &&foo; 168 // &&bar; 169 // goto *array[i]; 170 // } 171 171 172 172 Q: if ( i > 5 ) { -
tests/nested-types.cfa
ra505021 r8c50aed 10 10 // Created On : Mon Jul 9 10:20:03 2018 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Wed Feb 12 18:21:15 202013 // Update Count : 312 // Last Modified On : Tue Nov 6 17:59:40 2018 13 // Update Count : 2 14 14 // 15 15 … … 50 50 // double d; 51 51 // }; 52 53 // struct S {54 // enum C { R, G, B };55 // int i;56 // struct T {57 // int i;58 // };59 // T t;60 // };61 62 // S s;63 // S.C c;64 // S.T t;65 52 66 53 int main() { -
tests/pybin/tools.py
ra505021 r8c50aed 175 175 176 176 def which(program): 177 fpath, fname = os.path.split(program) 178 if fpath: 179 if is_exe(program): 180 return program 181 else: 182 for path in os.environ["PATH"].split(os.pathsep): 183 exe_file = os.path.join(path, program) 184 if is_exe(exe_file): 185 return exe_file 186 return None 177 fpath, fname = os.path.split(program) 178 if fpath: 179 if is_exe(program): 180 return program 181 else: 182 for path in os.environ["PATH"].split(os.pathsep): 183 exe_file = os.path.join(path, program) 184 if is_exe(exe_file): 185 return exe_file 186 187 return None 187 188 188 189 @contextlib.contextmanager … … 364 365 365 366 class Timed: 366 def __enter__(self):367 self.start = time.time()368 return self369 370 def __exit__(self, *args):371 self.end = time.time()372 self.duration = self.end - self.start367 def __enter__(self): 368 self.start = time.time() 369 return self 370 371 def __exit__(self, *args): 372 self.end = time.time() 373 self.duration = self.end - self.start 373 374 374 375 def timed(src, timeout): 375 376 expire = time.time() + timeout 376 377 i = iter(src) 377 with contextlib.suppress(StopIteration): 378 while True: 379 yield i.next(max(expire - time.time(), 0)) 378 while True: 379 yield i.next(max(expire - time.time(), 0)) -
tests/quotedKeyword.cfa
ra505021 r8c50aed 10 10 // Created On : Wed May 27 17:56:53 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Fri Feb 7 19:07:07202013 // Update Count : 2 512 // Last Modified On : Sat Feb 1 00:02:22 2020 13 // Update Count : 24 14 14 // 15 15 … … 17 17 18 18 struct { 19 int ``otype ;20 int ``struct ;19 int ``otype``; 20 int ``struct``; 21 21 } st = { 10, 10 }; 22 22 23 typedef int ``forall ;24 ``forall xxx = 10;23 typedef int ``forall``; 24 ``forall`` xxx = 10; 25 25 26 int ``_Alignas , ``_Alignof, ``__alignof, ``__alignof__, ``asm, ``__asm, ``__asm__, ``_At, ``_Atomic, ``__attribute,27 ``__attribute__ , ``auto, ``_Bool, ``break, ``case, ``catch, ``catchResume, ``char, ``choose, ``_Complex, ``__complex,28 ``__complex__ , ``const, ``__const, ``__const__, ``continue, ``default, ``disable, ``do, ``double, ``dtype, ``else,29 ``enable , ``enum, ``__extension__, ``extern, ``fallthru, ``finally, ``float, ``__float128, ``for, ``forall, ``fortran,30 ``ftype , ``_Generic, ``goto, ``if, ``_Imaginary, ``__imag, ``__imag__, ``inline, ``__inline, ``__inline__, ``int,31 ``__int128 , ``__label__, ``long, ``lvalue, ``_Noreturn, ``__builtin_offsetof, ``otype, ``register, ``restrict,32 ``__restrict , ``__restrict__, ``return, ``short, ``signed, ``__signed, ``__signed__, ``sizeof, ``static,33 ``_Static_assert , ``struct, ``switch, ``_Thread_local, ``throw, ``throwResume, ``trait, ``try, ``typedef,34 ``typeof , ``__typeof, ``__typeof__, ``union, ``unsigned, ``__builtin_va_list, ``void, ``volatile, ``__volatile,35 ``__volatile__ , ``while;26 int ``_Alignas``, ``_Alignof``, ``__alignof``, ``__alignof__``, ``asm``, ``__asm``, ``__asm__``, ``_At``, ``_Atomic``, ``__attribute``, 27 ``__attribute__``, ``auto``, ``_Bool``, ``break``, ``case``, ``catch``, ``catchResume``, ``char``, ``choose``, ``_Complex``, ``__complex``, 28 ``__complex__``, ``const``, ``__const``, ``__const__``, ``continue``, ``default``, ``disable``, ``do``, ``double``, ``dtype``, ``else``, 29 ``enable``, ``enum``, ``__extension__``, ``extern``, ``fallthru``, ``finally``, ``float``, ``__float128``, ``for``, ``forall``, ``fortran``, 30 ``ftype``, ``_Generic``, ``goto``, ``if``, ``_Imaginary``, ``__imag``, ``__imag__``, ``inline``, ``__inline``, ``__inline__``, ``int``, 31 ``__int128``, ``__label__``, ``long``, ``lvalue``, ``_Noreturn``, ``__builtin_offsetof``, ``otype``, ``register``, ``restrict``, 32 ``__restrict``, ``__restrict__``, ``return``, ``short``, ``signed``, ``__signed``, ``__signed__``, ``sizeof``, ``static``, 33 ``_Static_assert``, ``struct``, ``switch``, ``_Thread_local``, ``throw``, ``throwResume``, ``trait``, ``try``, ``typedef``, 34 ``typeof``, ``__typeof``, ``__typeof__``, ``union``, ``unsigned``, ``__builtin_va_list``, ``void``, ``volatile``, ``__volatile``, 35 ``__volatile__``, ``while``; 36 36 37 37 int main() { 38 int ``if = 0;39 ``catch = 1;40 st.``otype = 2;41 st.``struct = 3;42 ``throw = 4;43 sout | ``catch + st.``otype + st.``struct + ``throw;38 int ``if`` = 0; 39 ``catch`` = 1; 40 st.``otype`` = 2; 41 st.``struct`` = 3; 42 ``throw`` = 4; 43 sout | ``catch`` + st.``otype`` + st.``struct`` + ``throw``; 44 44 } 45 45 -
tests/rational.cfa
ra505021 r8c50aed 10 10 // Created On : Mon Mar 28 08:43:12 2016 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sat Feb 8 18:46:23 202013 // Update Count : 8 612 // Last Modified On : Wed Mar 27 07:37:17 2019 13 // Update Count : 80 14 14 // 15 15 … … 19 19 #include <fstream.hfa> 20 20 21 typedef Rational(int) RatInt; 22 double convert( int i ) { return (double)i; } // used by narrow/widen 21 double convert( int i ) { return (double)i; } 23 22 int convert( double d ) { return (int)d; } 24 23 25 24 int main() { 26 25 sout | "constructor"; 27 Rat Int a = { 3 }, b = { 4 }, c, d = 0, e = 1;28 sout | a | b | c | d | e;26 Rational(int) a = { 3 }, b = { 4 }, c; 27 sout | a | b | c; 29 28 30 a = (Rat Int){ 4, 8 };31 b = (Rat Int){ 5, 7 };29 a = (Rational(int)){ 4, 8 }; 30 b = (Rational(int)){ 5, 7 }; 32 31 sout | a | b; 33 a = (Rat Int){ -2, -3 };34 b = (Rat Int){ 3, -2 };32 a = (Rational(int)){ -2, -3 }; 33 b = (Rational(int)){ 3, -2 }; 35 34 sout | a | b; 36 a = (Rat Int){ -2, 3 };37 b = (Rat Int){ 3, 2 };35 a = (Rational(int)){ -2, 3 }; 36 b = (Rational(int)){ 3, 2 }; 38 37 sout | a | b; 39 38 40 39 sout | "logical"; 41 a = (Rat Int){ -2 };42 b = (Rat Int){ -3, 2 };40 a = (Rational(int)){ -2 }; 41 b = (Rational(int)){ -3, 2 }; 43 42 sout | a | b; 44 43 // sout | a == 1; // FIX ME … … 59 58 60 59 sout | "conversion"; 61 a = (Rat Int){ 3, 4 };60 a = (Rational(int)){ 3, 4 }; 62 61 sout | widen( a ); 63 a = (Rat Int){ 1, 7 };62 a = (Rational(int)){ 1, 7 }; 64 63 sout | widen( a ); 65 a = (Rat Int){ 355, 113 };64 a = (Rational(int)){ 355, 113 }; 66 65 sout | widen( a ); 67 66 sout | narrow( 0.75, 4 ); … … 75 74 76 75 sout | "more tests"; 77 Rat Intx = { 1, 2 }, y = { 2 };76 Rational(int) x = { 1, 2 }, y = { 2 }; 78 77 sout | x - y; 79 78 sout | x > y; … … 81 80 sout | y | denominator( y, -2 ) | y; 82 81 83 Rat Intz = { 0, 5 };82 Rational(int) z = { 0, 5 }; 84 83 sout | z; 85 84 86 85 sout | x | numerator( x, 0 ) | x; 87 86 88 x = (Rat Int){ 1, MAX } + (RatInt){ 1, MAX };87 x = (Rational(int)){ 1, MAX } + (Rational(int)){ 1, MAX }; 89 88 sout | x; 90 x = (Rat Int){ 3, MAX } + (RatInt){ 2, MAX };89 x = (Rational(int)){ 3, MAX } + (Rational(int)){ 2, MAX }; 91 90 sout | x; 92 91 -
tests/test.py
ra505021 r8c50aed 152 152 # run everything in a temp directory to make sure core file are handled properly 153 153 with tempdir(): 154 # if the make command succe eds continue otherwise skip to diff154 # if the make command succeds continue otherwise skip to diff 155 155 if success(make_ret): 156 156 with Timed() as run_dur: -
tests/userLiterals.cfa
ra505021 r8c50aed 5 5 // file "LICENCE" distributed with Cforall. 6 6 // 7 // user Literals.cfa --7 // user_literals.cfa -- 8 8 // 9 9 // Author : Peter A. Buhr 10 10 // Created On : Wed Sep 6 21:40:50 2017 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Wed Feb 19 07:48:45 202013 // Update Count : 7412 // Last Modified On : Tue Dec 4 22:03:10 2018 13 // Update Count : 56 14 14 // 15 15 … … 24 24 int ?`__thingy_( int x ) { sout | "_thingy_" | x; return x; } 25 25 26 int ?`s( const char * s ) { sout | "s " | s; return 0; }27 int ?`m( const char16_t * m ) { sout | "m " | m; return 0;}28 int ?`h( const char32_t * h ) { sout | "h " | h; return 0; }26 int ?`s( const char * s ) { sout | "secs" | s; return 0; } 27 int ?`m( const char16_t * m ) { sout | "mins" | m; return 0;} 28 int ?`h( const char32_t * h ) { sout | "hours" | h; return 0; } 29 29 int ?`_A_( const wchar_t * str ) { sout | "_A_" | str; return 0; } 30 30 int ?`__thingy_( const char * str ) { sout | "_thingy_" | str; return 0; } … … 37 37 return (Weight){ l.stones + r.stones }; 38 38 } 39 ofstream & ?|?( ofstream & os, Weight w ) { return os | wd(1,1, w.stones); } 40 void ?|?( ofstream & os, Weight w ) { (ofstream)(os | w); ends( os ); } 39 ofstream & ?|?( ofstream & os, Weight w ) { return os | w.stones; } 41 40 42 41 Weight ?`st( double w ) { return (Weight){ w }; } // backquote for user literals … … 61 60 sout | w; 62 61 63 0`s;62 // 0`secs; 64 63 1`s; 65 64 23`s; … … 83 82 84 83 "abc"`s; 85 // FIX ME: requires char16_t, char32_t, and wchar_t be unique types 86 // u"abc"`m; 87 // U_"abc"`h; 88 // L"abc"`_A_; 84 // u"abc"`m; 85 // U_"abc"`h; 86 // L"abc"`_A_; 89 87 u8_"abc"`__thingy_; 90 88 } // main … … 92 90 // Local Variables: // 93 91 // tab-width: 4 // 94 // compile-command: "cfa user Literals.cfa" //92 // compile-command: "cfa user_literals.cfa" // 95 93 // End: //
Note:
See TracChangeset
for help on using the changeset viewer.