Changeset 90a8125 for libcfa/src
- Timestamp:
- Jun 3, 2022, 3:10:01 PM (3 years ago)
- Branches:
- ADT, ast-experimental, master, pthread-emulation, qualifiedEnum
- Children:
- 7affcda
- Parents:
- bf0263c (diff), fc134a48 (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the(diff)
links above to see all the changes relative to each parent. - Location:
- libcfa/src
- Files:
-
- 54 edited
Legend:
- Unmodified
- Added
- Removed
-
libcfa/src/Makefile.am
rbf0263c r90a8125 33 33 # The built sources must not depend on the installed inst_headers_src 34 34 AM_CFAFLAGS = -quiet -cfalib -I$(srcdir)/stdhdr -I$(srcdir)/concurrency $(if $(findstring ${gdbwaittarget}, ${@}), -XCFA --gdb) @CONFIG_CFAFLAGS@ 35 AM_CFLAGS = -g -Wall -Werror=return-type -Wno-unused-function -fPIC -fexceptions - pthread @ARCH_FLAGS@ @CONFIG_CFLAGS@35 AM_CFLAGS = -g -Wall -Werror=return-type -Wno-unused-function -fPIC -fexceptions -fvisibility=hidden -pthread @ARCH_FLAGS@ @CONFIG_CFLAGS@ 36 36 AM_CCASFLAGS = -g -Wall -Werror=return-type -Wno-unused-function @ARCH_FLAGS@ @CONFIG_CFLAGS@ 37 37 CFACC = @CFACC@ … … 194 194 195 195 prelude.o : prelude.cfa extras.cf gcc-builtins.cf builtins.cf @LOCAL_CFACC@ @CFACPP@ 196 ${AM_V_GEN}$(CFACOMPILE) -quiet -XCFA,-l ${<} -c - o ${@}196 ${AM_V_GEN}$(CFACOMPILE) -quiet -XCFA,-l ${<} -c -fvisibility=default -o ${@} 197 197 198 198 prelude.lo: prelude.cfa extras.cf gcc-builtins.cf builtins.cf @LOCAL_CFACC@ @CFACPP@ 199 199 ${AM_V_GEN}$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile \ 200 $(CFACOMPILE) -quiet -XCFA,-l ${<} -c - o ${@}200 $(CFACOMPILE) -quiet -XCFA,-l ${<} -c -fvisibility=default -o ${@} 201 201 202 202 concurrency/io/call.cfa: $(srcdir)/concurrency/io/call.cfa.in -
libcfa/src/algorithms/range_iterator.cfa
rbf0263c r90a8125 20 20 #include <fstream.hfa> 21 21 22 void main(RangeIter & this) { 22 #include "bits/defs.hfa" 23 24 void main(RangeIter & this) libcfa_public { 23 25 for() { 24 26 this._start = -1; -
libcfa/src/assert.cfa
rbf0263c r90a8125 19 19 #include <unistd.h> // STDERR_FILENO 20 20 #include "bits/debug.hfa" 21 #include "bits/defs.hfa" 21 22 22 23 extern "C" { … … 26 27 27 28 // called by macro assert in assert.h 28 void __assert_fail( const char assertion[], const char file[], unsigned int line, const char function[] ) { 29 // would be cool to remove libcfa_public but it's needed for libcfathread 30 void __assert_fail( const char assertion[], const char file[], unsigned int line, const char function[] ) libcfa_public { 29 31 __cfaabi_bits_print_safe( STDERR_FILENO, CFA_ASSERT_FMT ".\n", assertion, __progname, function, line, file ); 30 32 abort(); … … 32 34 33 35 // called by macro assertf 34 void __assert_fail_f( const char assertion[], const char file[], unsigned int line, const char function[], const char fmt[], ... ) { 36 // would be cool to remove libcfa_public but it's needed for libcfathread 37 void __assert_fail_f( const char assertion[], const char file[], unsigned int line, const char function[], const char fmt[], ... ) libcfa_public { 35 38 __cfaabi_bits_acquire(); 36 39 __cfaabi_bits_print_nolock( STDERR_FILENO, CFA_ASSERT_FMT ": ", assertion, __progname, function, line, file ); -
libcfa/src/bits/debug.cfa
rbf0263c r90a8125 21 21 #include <unistd.h> 22 22 23 #include "bits/defs.hfa" 24 23 25 enum { buffer_size = 4096 }; 24 26 static char buffer[ buffer_size ]; 25 27 26 28 extern "C" { 27 void __cfaabi_bits_write( int fd, const char in_buffer[], int len ) { 29 // would be cool to remove libcfa_public but it's needed for libcfathread 30 void __cfaabi_bits_write( int fd, const char in_buffer[], int len ) libcfa_public { 28 31 // ensure all data is written 29 32 for ( int count = 0, retcode; count < len; count += retcode ) { … … 44 47 void __cfaabi_bits_release() __attribute__((__weak__)) {} 45 48 46 int __cfaabi_bits_print_safe ( int fd, const char fmt[], ... ) __attribute__(( format(printf, 2, 3) )) { 49 // would be cool to remove libcfa_public but it's needed for libcfathread 50 int __cfaabi_bits_print_safe ( int fd, const char fmt[], ... ) __attribute__(( format(printf, 2, 3) )) libcfa_public { 47 51 va_list args; 48 52 -
libcfa/src/bits/defs.hfa
rbf0263c r90a8125 36 36 #define __cfa_dlink(x) struct { struct x * next; struct x * back; } __dlink_substitute 37 37 #endif 38 39 #define libcfa_public __attribute__((visibility("default"))) 38 40 39 41 #ifdef __cforall -
libcfa/src/bits/weakso_locks.cfa
rbf0263c r90a8125 18 18 #include "bits/weakso_locks.hfa" 19 19 20 #pragma GCC visibility push(default) 21 20 22 void ?{}( blocking_lock &, bool, bool ) {} 21 23 void ^?{}( blocking_lock & ) {} -
libcfa/src/common.cfa
rbf0263c r90a8125 18 18 #include <stdlib.h> // div_t, *div 19 19 20 #pragma GCC visibility push(default) 21 20 22 //--------------------------------------- 21 23 -
libcfa/src/concurrency/alarm.cfa
rbf0263c r90a8125 141 141 //============================================================================================= 142 142 143 void sleep( Duration duration ) {143 void sleep( Duration duration ) libcfa_public { 144 144 alarm_node_t node = { active_thread(), duration, 0`s }; 145 145 -
libcfa/src/concurrency/clib/cfathread.cfa
rbf0263c r90a8125 237 237 238 238 typedef ThreadCancelled(cfathread_object) cfathread_exception; 239 typedef ThreadCancelled_vtable(cfathread_object) cfathread_vtable;239 typedef vtable(ThreadCancelled(cfathread_object)) cfathread_vtable; 240 240 241 241 void defaultResumptionHandler(ThreadCancelled(cfathread_object) & except) { … … 283 283 284 284 typedef ThreadCancelled(__cfainit) __cfainit_exception; 285 typedef ThreadCancelled_vtable(__cfainit) __cfainit_vtable;285 typedef vtable(ThreadCancelled(__cfainit)) __cfainit_vtable; 286 286 287 287 void defaultResumptionHandler(ThreadCancelled(__cfainit) & except) { … … 326 326 } 327 327 328 #pragma GCC visibility push(default) 329 328 330 //================================================================================ 329 331 // Main Api 330 332 extern "C" { 331 int cfathread_cluster_create(cfathread_cluster_t * cl) __attribute__((nonnull(1))) {333 int cfathread_cluster_create(cfathread_cluster_t * cl) __attribute__((nonnull(1))) libcfa_public { 332 334 *cl = new(); 333 335 return 0; 334 336 } 335 337 336 cfathread_cluster_t cfathread_cluster_self(void) {338 cfathread_cluster_t cfathread_cluster_self(void) libcfa_public { 337 339 return active_cluster(); 338 340 } 339 341 340 int cfathread_cluster_print_stats( cfathread_cluster_t cl ) {342 int cfathread_cluster_print_stats( cfathread_cluster_t cl ) libcfa_public { 341 343 #if !defined(__CFA_NO_STATISTICS__) 342 344 print_stats_at_exit( *cl, CFA_STATS_READY_Q | CFA_STATS_IO ); -
libcfa/src/concurrency/coroutine.cfa
rbf0263c r90a8125 48 48 //----------------------------------------------------------------------------- 49 49 forall(T &) 50 void copy(CoroutineCancelled(T) * dst, CoroutineCancelled(T) * src) {50 void copy(CoroutineCancelled(T) * dst, CoroutineCancelled(T) * src) libcfa_public { 51 51 dst->virtual_table = src->virtual_table; 52 52 dst->the_coroutine = src->the_coroutine; … … 55 55 56 56 forall(T &) 57 const char * msg(CoroutineCancelled(T) *) {57 const char * msg(CoroutineCancelled(T) *) libcfa_public { 58 58 return "CoroutineCancelled(...)"; 59 59 } … … 62 62 forall(T & | is_coroutine(T)) 63 63 void __cfaehm_cancelled_coroutine( 64 T & cor, coroutine$ * desc, EHM_DEFAULT_VTABLE(CoroutineCancelled , (T)) ){64 T & cor, coroutine$ * desc, EHM_DEFAULT_VTABLE(CoroutineCancelled(T)) ) libcfa_public { 65 65 verify( desc->cancellation ); 66 66 desc->state = Cancelled; … … 89 89 90 90 void __stack_prepare( __stack_info_t * this, size_t create_size ); 91 void __stack_clean ( __stack_info_t * this );91 static void __stack_clean ( __stack_info_t * this ); 92 92 93 93 //----------------------------------------------------------------------------- … … 114 114 } 115 115 116 void ?{}( coroutine$ & this, const char name[], void * storage, size_t storageSize ) with( this ) {116 void ?{}( coroutine$ & this, const char name[], void * storage, size_t storageSize ) libcfa_public with( this ) { 117 117 (this.context){0p, 0p}; 118 118 (this.stack){storage, storageSize}; … … 124 124 } 125 125 126 void ^?{}(coroutine$& this) {126 void ^?{}(coroutine$& this) libcfa_public { 127 127 if(this.state != Halted && this.state != Start && this.state != Primed) { 128 128 coroutine$ * src = active_coroutine(); … … 146 146 // Part of the Public API 147 147 // Not inline since only ever called once per coroutine 148 forall(T & | is_coroutine(T) | { EHM_DEFAULT_VTABLE(CoroutineCancelled ,(T)); })149 void prime(T& cor) {148 forall(T & | is_coroutine(T) | { EHM_DEFAULT_VTABLE(CoroutineCancelled(T)); }) 149 void prime(T& cor) libcfa_public { 150 150 coroutine$* this = get_coroutine(cor); 151 151 assert(this->state == Start); … … 155 155 } 156 156 157 [void *, size_t] __stack_alloc( size_t storageSize ) {157 static [void *, size_t] __stack_alloc( size_t storageSize ) { 158 158 const size_t stack_data_size = libCeiling( sizeof(__stack_t), 16 ); // minimum alignment 159 159 assert(__page_size != 0l); … … 193 193 } 194 194 195 void __stack_clean ( __stack_info_t * this ) {195 static void __stack_clean ( __stack_info_t * this ) { 196 196 void * storage = this->storage->limit; 197 197 … … 215 215 } 216 216 217 void __stack_prepare( __stack_info_t * this, size_t create_size ) {217 void __stack_prepare( __stack_info_t * this, size_t create_size ) libcfa_public { 218 218 const size_t stack_data_size = libCeiling( sizeof(__stack_t), 16 ); // minimum alignment 219 219 bool userStack; -
libcfa/src/concurrency/coroutine.hfa
rbf0263c r90a8125 22 22 //----------------------------------------------------------------------------- 23 23 // Exception thrown from resume when a coroutine stack is cancelled. 24 EHM_FORALL_EXCEPTION(CoroutineCancelled, (coroutine_t &), (coroutine_t)) ( 24 forall(coroutine_t &) 25 exception CoroutineCancelled { 25 26 coroutine_t * the_coroutine; 26 27 exception_t * the_exception; 27 );28 }; 28 29 29 30 forall(T &) … … 37 38 // Anything that implements this trait can be resumed. 38 39 // Anything that is resumed is a coroutine. 39 trait is_coroutine(T & | IS_RESUMPTION_EXCEPTION(CoroutineCancelled ,(T))) {40 trait is_coroutine(T & | IS_RESUMPTION_EXCEPTION(CoroutineCancelled(T))) { 40 41 void main(T & this); 41 42 coroutine$ * get_coroutine(T & this); … … 60 61 //----------------------------------------------------------------------------- 61 62 // Public coroutine API 62 forall(T & | is_coroutine(T) | { EHM_DEFAULT_VTABLE(CoroutineCancelled ,(T)); })63 forall(T & | is_coroutine(T) | { EHM_DEFAULT_VTABLE(CoroutineCancelled(T)); }) 63 64 void prime(T & cor); 64 65 … … 113 114 114 115 extern void __stack_prepare( __stack_info_t * this, size_t size /* ignored if storage already allocated */); 115 extern void __stack_clean ( __stack_info_t * this );116 117 116 118 117 // Suspend implementation inlined for performance … … 141 140 forall(T & | is_coroutine(T)) 142 141 void __cfaehm_cancelled_coroutine( 143 T & cor, coroutine$ * desc, EHM_DEFAULT_VTABLE(CoroutineCancelled ,(T)) );142 T & cor, coroutine$ * desc, EHM_DEFAULT_VTABLE(CoroutineCancelled(T)) ); 144 143 145 144 // Resume implementation inlined for performance 146 forall(T & | is_coroutine(T) | { EHM_DEFAULT_VTABLE(CoroutineCancelled ,(T)); })145 forall(T & | is_coroutine(T) | { EHM_DEFAULT_VTABLE(CoroutineCancelled(T)); }) 147 146 static inline T & resume(T & cor) { 148 147 // optimization : read TLS once and reuse it -
libcfa/src/concurrency/exception.cfa
rbf0263c r90a8125 64 64 extern "C" { 65 65 66 struct exception_context_t * this_exception_context(void) {66 struct exception_context_t * this_exception_context(void) libcfa_public { 67 67 return &__get_stack( active_coroutine() )->exception_context; 68 68 } 69 69 70 _Unwind_Reason_Code __cfaehm_cancellation_unwind( struct _Unwind_Exception * unwind_exception ) {70 _Unwind_Reason_Code __cfaehm_cancellation_unwind( struct _Unwind_Exception * unwind_exception ) libcfa_public { 71 71 _Unwind_Stop_Fn stop_func; 72 72 void * stop_param; -
libcfa/src/concurrency/invoke.c
rbf0263c r90a8125 36 36 extern void enable_interrupts( _Bool poll ); 37 37 38 void __cfactx_invoke_coroutine(38 libcfa_public void __cfactx_invoke_coroutine( 39 39 void (*main)(void *), 40 40 void *this … … 70 70 } 71 71 72 void __cfactx_coroutine_unwind(struct _Unwind_Exception * storage, struct coroutine$ * cor) __attribute__ ((__noreturn__));72 libcfa_public void __cfactx_coroutine_unwind(struct _Unwind_Exception * storage, struct coroutine$ * cor) __attribute__ ((__noreturn__)); 73 73 void __cfactx_coroutine_unwind(struct _Unwind_Exception * storage, struct coroutine$ * cor) { 74 74 _Unwind_Reason_Code ret = _Unwind_ForcedUnwind( storage, __cfactx_coroutine_unwindstop, cor ); … … 77 77 } 78 78 79 void __cfactx_invoke_thread(79 libcfa_public void __cfactx_invoke_thread( 80 80 void (*main)(void *), 81 81 void *this … … 98 98 } 99 99 100 void __cfactx_start(100 libcfa_public void __cfactx_start( 101 101 void (*main)(void *), 102 102 struct coroutine$ * cor, -
libcfa/src/concurrency/io.cfa
rbf0263c r90a8125 221 221 const unsigned long long ctsc = rdtscl(); 222 222 223 if(proc->io.target == MAX) {223 if(proc->io.target == UINT_MAX) { 224 224 uint64_t chaos = __tls_rand(); 225 225 unsigned ext = chaos & 0xff; … … 232 232 else { 233 233 const unsigned target = proc->io.target; 234 /* paranoid */ verify( io.tscs[target].tv != MAX );234 /* paranoid */ verify( io.tscs[target].tv != ULLONG_MAX ); 235 235 HELP: if(target < ctxs_count) { 236 236 const unsigned long long cutoff = calc_cutoff(ctsc, ctx->cq.id, ctxs_count, io.data, io.tscs, __shard_factor.io); … … 246 246 __STATS__( true, io.calls.helped++; ) 247 247 } 248 proc->io.target = MAX;248 proc->io.target = UINT_MAX; 249 249 } 250 250 } … … 340 340 // for convenience, return both the index and the pointer to the sqe 341 341 // sqe == &sqes[idx] 342 struct $io_context * cfa_io_allocate(struct io_uring_sqe * sqes[], __u32 idxs[], __u32 want) {342 struct $io_context * cfa_io_allocate(struct io_uring_sqe * sqes[], __u32 idxs[], __u32 want) libcfa_public { 343 343 // __cfadbg_print_safe(io, "Kernel I/O : attempting to allocate %u\n", want); 344 344 … … 419 419 } 420 420 421 void cfa_io_submit( struct $io_context * inctx, __u32 idxs[], __u32 have, bool lazy ) __attribute__((nonnull (1))) {421 void cfa_io_submit( struct $io_context * inctx, __u32 idxs[], __u32 have, bool lazy ) __attribute__((nonnull (1))) libcfa_public { 422 422 // __cfadbg_print_safe(io, "Kernel I/O : attempting to submit %u (%s)\n", have, lazy ? "lazy" : "eager"); 423 423 -
libcfa/src/concurrency/io/call.cfa.in
rbf0263c r90a8125 139 139 // I/O Interface 140 140 //============================================================================================= 141 #pragma GCC visibility push(default) 141 142 """ 142 143 -
libcfa/src/concurrency/io/setup.cfa
rbf0263c r90a8125 26 26 27 27 #if !defined(CFA_HAVE_LINUX_IO_URING_H) 28 void ?{}(io_context_params & this) {}28 void ?{}(io_context_params & this) libcfa_public {} 29 29 30 30 void ?{}($io_context & this, struct cluster & cl) {} … … 66 66 #pragma GCC diagnostic pop 67 67 68 void ?{}(io_context_params & this) {68 void ?{}(io_context_params & this) libcfa_public { 69 69 this.num_entries = 256; 70 70 } -
libcfa/src/concurrency/io/types.hfa
rbf0263c r90a8125 17 17 #pragma once 18 18 19 #include <limits.h> 20 19 21 extern "C" { 20 22 #include <linux/types.h> … … 25 27 #include "iofwd.hfa" 26 28 #include "kernel/fwd.hfa" 27 #include "limits.hfa"28 29 29 30 #if defined(CFA_HAVE_LINUX_IO_URING_H) … … 140 141 const __u32 tail = *this->cq.tail; 141 142 142 if(head == tail) return MAX;143 if(head == tail) return ULLONG_MAX; 143 144 144 145 return this->cq.ts; -
libcfa/src/concurrency/kernel.cfa
rbf0263c r90a8125 389 389 390 390 // KERNEL_ONLY 391 void returnToKernel() {391 static void returnToKernel() { 392 392 /* paranoid */ verify( ! __preemption_enabled() ); 393 393 coroutine$ * proc_cor = get_coroutine(kernelTLS().this_processor->runner); … … 547 547 } 548 548 549 void unpark( thread$ * thrd, unpark_hint hint ) {549 void unpark( thread$ * thrd, unpark_hint hint ) libcfa_public { 550 550 if( !thrd ) return; 551 551 … … 558 558 } 559 559 560 void park( void ) {560 void park( void ) libcfa_public { 561 561 __disable_interrupts_checked(); 562 562 /* paranoid */ verify( kernelTLS().this_thread->preempted == __NO_PREEMPTION ); … … 601 601 602 602 // KERNEL ONLY 603 bool force_yield( __Preemption_Reason reason ) {603 bool force_yield( __Preemption_Reason reason ) libcfa_public { 604 604 __disable_interrupts_checked(); 605 605 thread$ * thrd = kernelTLS().this_thread; … … 849 849 //----------------------------------------------------------------------------- 850 850 // Debug 851 bool threading_enabled(void) __attribute__((const)) {851 bool threading_enabled(void) __attribute__((const)) libcfa_public { 852 852 return true; 853 853 } … … 856 856 // Statistics 857 857 #if !defined(__CFA_NO_STATISTICS__) 858 void print_halts( processor & this ) {858 void print_halts( processor & this ) libcfa_public { 859 859 this.print_halts = true; 860 860 } … … 873 873 } 874 874 875 void crawl_cluster_stats( cluster & this ) {875 static void crawl_cluster_stats( cluster & this ) { 876 876 // Stop the world, otherwise stats could get really messed-up 877 877 // this doesn't solve all problems but does solve many … … 889 889 890 890 891 void print_stats_now( cluster & this, int flags ) {891 void print_stats_now( cluster & this, int flags ) libcfa_public { 892 892 crawl_cluster_stats( this ); 893 893 __print_stats( this.stats, flags, "Cluster", this.name, (void*)&this ); -
libcfa/src/concurrency/kernel.hfa
rbf0263c r90a8125 49 49 50 50 // Coroutine used py processors for the 2-step context switch 51 coroutine processorCtx_t { 51 52 struct processorCtx_t { 53 struct coroutine$ self; 52 54 struct processor * proc; 53 55 }; -
libcfa/src/concurrency/kernel/cluster.cfa
rbf0263c r90a8125 49 49 50 50 // returns the maximum number of processors the RWLock support 51 __attribute__((weak)) unsigned __max_processors() {51 __attribute__((weak)) unsigned __max_processors() libcfa_public { 52 52 const char * max_cores_s = getenv("CFA_MAX_PROCESSORS"); 53 53 if(!max_cores_s) { … … 233 233 if(is_empty(sl)) { 234 234 assert( sl.anchor.next == 0p ); 235 assert( sl.anchor.ts == -1llu);235 assert( sl.anchor.ts == MAX ); 236 236 assert( mock_head(sl) == sl.prev ); 237 237 } else { 238 238 assert( sl.anchor.next != 0p ); 239 assert( sl.anchor.ts != -1llu);239 assert( sl.anchor.ts != MAX ); 240 240 assert( mock_head(sl) != sl.prev ); 241 241 } … … 259 259 /* paranoid */ verifyf( it, "Unexpected null iterator, at index %u of %u\n", i, count); 260 260 it->rdq.id = valrq; 261 it->rdq.target = MAX;261 it->rdq.target = UINT_MAX; 262 262 valrq += __shard_factor.readyq; 263 263 #if defined(CFA_HAVE_LINUX_IO_URING_H) 264 264 it->io.ctx->cq.id = valio; 265 it->io.target = MAX;265 it->io.target = UINT_MAX; 266 266 valio += __shard_factor.io; 267 267 #endif … … 472 472 this.prev = mock_head(this); 473 473 this.anchor.next = 0p; 474 this.anchor.ts = -1llu;474 this.anchor.ts = MAX; 475 475 #if !defined(__CFA_NO_STATISTICS__) 476 476 this.cnt = 0; … … 484 484 /* paranoid */ verify( &mock_head(this)->link.ts == &this.anchor.ts ); 485 485 /* paranoid */ verify( mock_head(this)->link.next == 0p ); 486 /* paranoid */ verify( mock_head(this)->link.ts == -1llu);486 /* paranoid */ verify( mock_head(this)->link.ts == MAX ); 487 487 /* paranoid */ verify( mock_head(this) == this.prev ); 488 488 /* paranoid */ verify( __alignof__(__intrusive_lane_t) == 128 ); … … 495 495 // Make sure the list is empty 496 496 /* paranoid */ verify( this.anchor.next == 0p ); 497 /* paranoid */ verify( this.anchor.ts == -1llu);497 /* paranoid */ verify( this.anchor.ts == MAX ); 498 498 /* paranoid */ verify( mock_head(this) == this.prev ); 499 499 } -
libcfa/src/concurrency/kernel/cluster.hfa
rbf0263c r90a8125 19 19 #include "kernel/private.hfa" 20 20 21 #include "limits.hfa"21 #include <limits.h> 22 22 23 23 //----------------------------------------------------------------------- … … 37 37 38 38 static inline void touch_tsc(__timestamp_t * tscs, size_t idx, unsigned long long ts_prev, unsigned long long ts_next) { 39 if (ts_next == MAX) return;39 if (ts_next == ULLONG_MAX) return; 40 40 unsigned long long now = rdtscl(); 41 41 unsigned long long pma = __atomic_load_n(&tscs[ idx ].ma, __ATOMIC_RELAXED); … … 59 59 for(i; shard_factor) { 60 60 unsigned long long ptsc = ts(data[start + i]); 61 if(ptsc != -1ull) {61 if(ptsc != ULLONG_MAX) { 62 62 /* paranoid */ verify( start + i < count ); 63 63 unsigned long long tsc = moving_average(ctsc, ptsc, tscs[start + i].ma); -
libcfa/src/concurrency/kernel/private.hfa
rbf0263c r90a8125 109 109 //----------------------------------------------------------------------------- 110 110 // Processor 111 void main(processorCtx_t *); 111 void main(processorCtx_t &); 112 static inline coroutine$* get_coroutine(processorCtx_t & this) { return &this.self; } 112 113 113 114 void * __create_pthread( pthread_t *, void * (*)(void *), void * ); -
libcfa/src/concurrency/kernel/startup.cfa
rbf0263c r90a8125 120 120 #endif 121 121 122 cluster * mainCluster ;122 cluster * mainCluster libcfa_public; 123 123 processor * mainProcessor; 124 124 thread$ * mainThread; … … 169 169 }; 170 170 171 void ?{}( current_stack_info_t & this ) {171 static void ?{}( current_stack_info_t & this ) { 172 172 __stack_context_t ctx; 173 173 CtxGet( ctx ); … … 209 209 // Construct the processor context of the main processor 210 210 void ?{}(processorCtx_t & this, processor * proc) { 211 (this. __cor){ "Processor" };212 this. __cor.starter = 0p;211 (this.self){ "Processor" }; 212 this.self.starter = 0p; 213 213 this.proc = proc; 214 214 } … … 507 507 self_mon_p = &self_mon; 508 508 link.next = 0p; 509 link.ts = -1llu;509 link.ts = MAX; 510 510 preferred = ready_queue_new_preferred(); 511 511 last_proc = 0p; … … 526 526 // Construct the processor context of non-main processors 527 527 static void ?{}(processorCtx_t & this, processor * proc, current_stack_info_t * info) { 528 (this. __cor){ info };528 (this.self){ info }; 529 529 this.proc = proc; 530 530 } … … 578 578 } 579 579 580 void ?{}(processor & this, const char name[], cluster & _cltr, thread$ * initT) {580 void ?{}(processor & this, const char name[], cluster & _cltr, thread$ * initT) libcfa_public { 581 581 ( this.terminated ){}; 582 582 ( this.runner ){}; … … 591 591 } 592 592 593 void ?{}(processor & this, const char name[], cluster & _cltr) {593 void ?{}(processor & this, const char name[], cluster & _cltr) libcfa_public { 594 594 (this){name, _cltr, 0p}; 595 595 } 596 596 597 597 extern size_t __page_size; 598 void ^?{}(processor & this) with( this ){598 void ^?{}(processor & this) libcfa_public with( this ) { 599 599 /* paranoid */ verify( !__atomic_load_n(&do_terminate, __ATOMIC_ACQUIRE) ); 600 600 __cfadbg_print_safe(runtime_core, "Kernel : core %p signaling termination\n", &this); … … 623 623 } 624 624 625 void ?{}(cluster & this, const char name[], Duration preemption_rate, unsigned num_io, const io_context_params & io_params) with( this ) {625 void ?{}(cluster & this, const char name[], Duration preemption_rate, unsigned num_io, const io_context_params & io_params) libcfa_public with( this ) { 626 626 this.name = name; 627 627 this.preemption_rate = preemption_rate; … … 658 658 } 659 659 660 void ^?{}(cluster & this) {660 void ^?{}(cluster & this) libcfa_public { 661 661 destroy(this.io.arbiter); 662 662 -
libcfa/src/concurrency/locks.cfa
rbf0263c r90a8125 24 24 #include <stdlib.hfa> 25 25 26 #pragma GCC visibility push(default) 27 26 28 //----------------------------------------------------------------------------- 27 29 // info_thread … … 116 118 } 117 119 118 void pop_and_set_new_owner( blocking_lock & this ) with( this ) {120 static void pop_and_set_new_owner( blocking_lock & this ) with( this ) { 119 121 thread$ * t = &try_pop_front( blocked_threads ); 120 122 owner = t; … … 192 194 void ^?{}( alarm_node_wrap(L) & this ) { } 193 195 194 void timeout_handler ( alarm_node_wrap(L) & this ) with( this ) {196 static void timeout_handler ( alarm_node_wrap(L) & this ) with( this ) { 195 197 // This condition_variable member is called from the kernel, and therefore, cannot block, but it can spin. 196 198 lock( cond->lock __cfaabi_dbg_ctx2 ); … … 216 218 217 219 // this casts the alarm node to our wrapped type since we used type erasure 218 void alarm_node_wrap_cast( alarm_node_t & a ) { timeout_handler( (alarm_node_wrap(L) &)a ); }220 static void alarm_node_wrap_cast( alarm_node_t & a ) { timeout_handler( (alarm_node_wrap(L) &)a ); } 219 221 } 220 222 … … 233 235 void ^?{}( condition_variable(L) & this ){ } 234 236 235 void process_popped( condition_variable(L) & this, info_thread(L) & popped ) with( this ) {237 static void process_popped( condition_variable(L) & this, info_thread(L) & popped ) with( this ) { 236 238 if(&popped != 0p) { 237 239 popped.signalled = true; … … 278 280 int counter( condition_variable(L) & this ) with(this) { return count; } 279 281 280 s ize_t queue_and_get_recursion( condition_variable(L) & this, info_thread(L) * i ) with(this) {282 static size_t queue_and_get_recursion( condition_variable(L) & this, info_thread(L) * i ) with(this) { 281 283 // add info_thread to waiting queue 282 284 insert_last( blocked_threads, *i ); … … 291 293 292 294 // helper for wait()'s' with no timeout 293 void queue_info_thread( condition_variable(L) & this, info_thread(L) & i ) with(this) {295 static void queue_info_thread( condition_variable(L) & this, info_thread(L) & i ) with(this) { 294 296 lock( lock __cfaabi_dbg_ctx2 ); 295 297 size_t recursion_count = queue_and_get_recursion(this, &i); … … 308 310 309 311 // helper for wait()'s' with a timeout 310 void queue_info_thread_timeout( condition_variable(L) & this, info_thread(L) & info, Duration t, Alarm_Callback callback ) with(this) {312 static void queue_info_thread_timeout( condition_variable(L) & this, info_thread(L) & info, Duration t, Alarm_Callback callback ) with(this) { 311 313 lock( lock __cfaabi_dbg_ctx2 ); 312 314 size_t recursion_count = queue_and_get_recursion(this, &info); … … 343 345 // fast_cond_var 344 346 void ?{}( fast_cond_var(L) & this ){ 345 this.blocked_threads{}; 347 this.blocked_threads{}; 346 348 #ifdef __CFA_DEBUG__ 347 349 this.lock_used = 0p; -
libcfa/src/concurrency/monitor.cfa
rbf0263c r90a8125 44 44 static inline void restore( monitor$ * ctx [], __lock_size_t count, __spinlock_t * locks [], unsigned int /*in */ recursions [], __waitfor_mask_t /*in */ masks [] ); 45 45 46 static inline void ?{}(__condition_node_t & this, thread$ * waiting_thread, __lock_size_t count, uintptr_t user_info ); 47 static inline void ?{}(__condition_criterion_t & this ); 48 static inline void ?{}(__condition_criterion_t & this, monitor$ * target, __condition_node_t * owner ); 49 46 50 static inline void init ( __lock_size_t count, monitor$ * monitors [], __condition_node_t & waiter, __condition_criterion_t criteria [] ); 47 51 static inline void init_push( __lock_size_t count, monitor$ * monitors [], __condition_node_t & waiter, __condition_criterion_t criteria [] ); … … 243 247 244 248 // Leave single monitor 245 void __leave( monitor$ * this ) {249 static void __leave( monitor$ * this ) { 246 250 // Lock the monitor spinlock 247 251 lock( this->lock __cfaabi_dbg_ctx2 ); … … 278 282 279 283 // Leave single monitor for the last time 280 void __dtor_leave( monitor$ * this, bool join ) {284 static void __dtor_leave( monitor$ * this, bool join ) { 281 285 __cfaabi_dbg_debug_do( 282 286 if( active_thread() != this->owner ) { … … 344 348 // Ctor for monitor guard 345 349 // Sorts monitors before entering 346 void ?{}( monitor_guard_t & this, monitor$ * m [], __lock_size_t count, fptr_t func ) {350 void ?{}( monitor_guard_t & this, monitor$ * m [], __lock_size_t count, fptr_t func ) libcfa_public { 347 351 thread$ * thrd = active_thread(); 348 352 … … 369 373 } 370 374 371 void ?{}( monitor_guard_t & this, monitor$ * m [], __lock_size_t count ) {375 void ?{}( monitor_guard_t & this, monitor$ * m [], __lock_size_t count ) libcfa_public { 372 376 this{ m, count, 0p }; 373 377 } … … 375 379 376 380 // Dtor for monitor guard 377 void ^?{}( monitor_guard_t & this ) {381 void ^?{}( monitor_guard_t & this ) libcfa_public { 378 382 // __cfaabi_dbg_print_safe( "MGUARD : leaving %d\n", this.count); 379 383 … … 389 393 // Ctor for monitor guard 390 394 // Sorts monitors before entering 391 void ?{}( monitor_dtor_guard_t & this, monitor$ * m [], fptr_t func, bool join ) {395 void ?{}( monitor_dtor_guard_t & this, monitor$ * m [], fptr_t func, bool join ) libcfa_public { 392 396 // optimization 393 397 thread$ * thrd = active_thread(); … … 409 413 410 414 // Dtor for monitor guard 411 void ^?{}( monitor_dtor_guard_t & this ) {415 void ^?{}( monitor_dtor_guard_t & this ) libcfa_public { 412 416 // Leave the monitors in order 413 417 __dtor_leave( this.m, this.join ); … … 419 423 //----------------------------------------------------------------------------- 420 424 // Internal scheduling types 421 void ?{}(__condition_node_t & this, thread$ * waiting_thread, __lock_size_t count, uintptr_t user_info ) {425 static void ?{}(__condition_node_t & this, thread$ * waiting_thread, __lock_size_t count, uintptr_t user_info ) { 422 426 this.waiting_thread = waiting_thread; 423 427 this.count = count; … … 426 430 } 427 431 428 void ?{}(__condition_criterion_t & this ) with( this ) {432 static void ?{}(__condition_criterion_t & this ) with( this ) { 429 433 ready = false; 430 434 target = 0p; … … 433 437 } 434 438 435 void ?{}(__condition_criterion_t & this, monitor$ * target, __condition_node_t & owner ) {439 static void ?{}(__condition_criterion_t & this, monitor$ * target, __condition_node_t & owner ) { 436 440 this.ready = false; 437 441 this.target = target; … … 442 446 //----------------------------------------------------------------------------- 443 447 // Internal scheduling 444 void wait( condition & this, uintptr_t user_info = 0 ) {448 void wait( condition & this, uintptr_t user_info = 0 ) libcfa_public { 445 449 brand_condition( this ); 446 450 … … 496 500 } 497 501 498 bool signal( condition & this ) {502 bool signal( condition & this ) libcfa_public { 499 503 if( is_empty( this ) ) { return false; } 500 504 … … 538 542 } 539 543 540 bool signal_block( condition & this ) {544 bool signal_block( condition & this ) libcfa_public { 541 545 if( !this.blocked.head ) { return false; } 542 546 … … 586 590 587 591 // Access the user_info of the thread waiting at the front of the queue 588 uintptr_t front( condition & this ) {592 uintptr_t front( condition & this ) libcfa_public { 589 593 verifyf( !is_empty(this), 590 594 "Attempt to access user data on an empty condition.\n" … … 608 612 // setup mask 609 613 // block 610 void __waitfor_internal( const __waitfor_mask_t & mask, int duration ) {614 void __waitfor_internal( const __waitfor_mask_t & mask, int duration ) libcfa_public { 611 615 // This statment doesn't have a contiguous list of monitors... 612 616 // Create one! … … 994 998 // Can't be accepted since a mutex stmt is effectively an anonymous routine 995 999 // Thus we do not need a monitor group 996 void lock( monitor$ * this ) {1000 void lock( monitor$ * this ) libcfa_public { 997 1001 thread$ * thrd = active_thread(); 998 1002 … … 1046 1050 // Leave routine for mutex stmt 1047 1051 // Is just a wrapper around __leave for the is_lock trait to see 1048 void unlock( monitor$ * this ) { __leave( this ); }1052 void unlock( monitor$ * this ) libcfa_public { __leave( this ); } 1049 1053 1050 1054 // Local Variables: // -
libcfa/src/concurrency/monitor.hfa
rbf0263c r90a8125 119 119 } 120 120 121 void ?{}(__condition_node_t & this, thread$ * waiting_thread, __lock_size_t count, uintptr_t user_info );122 void ?{}(__condition_criterion_t & this );123 void ?{}(__condition_criterion_t & this, monitor$ * target, __condition_node_t * owner );121 // void ?{}(__condition_node_t & this, thread$ * waiting_thread, __lock_size_t count, uintptr_t user_info ); 122 // void ?{}(__condition_criterion_t & this ); 123 // void ?{}(__condition_criterion_t & this, monitor$ * target, __condition_node_t * owner ); 124 124 125 125 struct condition { -
libcfa/src/concurrency/preemption.cfa
rbf0263c r90a8125 38 38 #endif 39 39 40 __attribute__((weak)) Duration default_preemption() {40 __attribute__((weak)) Duration default_preemption() libcfa_public { 41 41 const char * preempt_rate_s = getenv("CFA_DEFAULT_PREEMPTION"); 42 42 if(!preempt_rate_s) { … … 238 238 //---------- 239 239 // special case for preemption since used often 240 __attribute__((optimize("no-reorder-blocks"))) bool __preemption_enabled() {240 __attribute__((optimize("no-reorder-blocks"))) bool __preemption_enabled() libcfa_public { 241 241 // create a assembler label before 242 242 // marked as clobber all to avoid movement … … 276 276 // Get data from the TLS block 277 277 // struct asm_region __cfaasm_get; 278 uintptr_t __cfatls_get( unsigned long int offset ) __attribute__((__noinline__ )); //no inline to avoid problems278 uintptr_t __cfatls_get( unsigned long int offset ) __attribute__((__noinline__, visibility("default"))); //no inline to avoid problems 279 279 uintptr_t __cfatls_get( unsigned long int offset ) { 280 280 // create a assembler label before … … 295 295 extern "C" { 296 296 // Disable interrupts by incrementing the counter 297 void disable_interrupts(){297 __attribute__((__noinline__, visibility("default"))) void disable_interrupts() libcfa_public { 298 298 // create a assembler label before 299 299 // marked as clobber all to avoid movement … … 326 326 // Enable interrupts by decrementing the counter 327 327 // If counter reaches 0, execute any pending __cfactx_switch 328 void enable_interrupts( bool poll ) {328 void enable_interrupts( bool poll ) libcfa_public { 329 329 // Cache the processor now since interrupts can start happening after the atomic store 330 330 processor * proc = __cfaabi_tls.this_processor; … … 362 362 //----------------------------------------------------------------------------- 363 363 // Kernel Signal Debug 364 void __cfaabi_check_preemption() {364 void __cfaabi_check_preemption() libcfa_public { 365 365 bool ready = __preemption_enabled(); 366 366 if(!ready) { abort("Preemption should be ready"); } -
libcfa/src/concurrency/ready_queue.cfa
rbf0263c r90a8125 125 125 const unsigned long long ctsc = rdtscl(); 126 126 127 if(proc->rdq.target == MAX) {127 if(proc->rdq.target == UINT_MAX) { 128 128 uint64_t chaos = __tls_rand(); 129 129 unsigned ext = chaos & 0xff; … … 137 137 const unsigned target = proc->rdq.target; 138 138 __cfadbg_print_safe(ready_queue, "Kernel : %u considering helping %u, tcsc %llu\n", this, target, readyQ.tscs[target].tv); 139 /* paranoid */ verify( readyQ.tscs[target].tv != MAX );139 /* paranoid */ verify( readyQ.tscs[target].tv != ULLONG_MAX ); 140 140 if(target < lanes_count) { 141 141 const unsigned long long cutoff = calc_cutoff(ctsc, proc->rdq.id, lanes_count, cltr->sched.readyQ.data, cltr->sched.readyQ.tscs, __shard_factor.readyq); … … 147 147 } 148 148 } 149 proc->rdq.target = MAX;149 proc->rdq.target = UINT_MAX; 150 150 } 151 151 … … 245 245 // get preferred ready for new thread 246 246 unsigned ready_queue_new_preferred() { 247 unsigned pref = MAX;247 unsigned pref = UINT_MAX; 248 248 if(struct thread$ * thrd = publicTLS_get( this_thread )) { 249 249 pref = thrd->preferred; -
libcfa/src/concurrency/ready_subqueue.hfa
rbf0263c r90a8125 32 32 /* paranoid */ verify( this.lock ); 33 33 /* paranoid */ verify( node->link.next == 0p ); 34 /* paranoid */ verify( node->link.ts== MAX );34 /* paranoid */ verify( __atomic_load_n(&node->link.ts, __ATOMIC_RELAXED) == MAX ); 35 35 /* paranoid */ verify( this.prev->link.next == 0p ); 36 /* paranoid */ verify( this.prev->link.ts== MAX );36 /* paranoid */ verify( __atomic_load_n(&this.prev->link.ts, __ATOMIC_RELAXED) == MAX ); 37 37 if( this.anchor.next == 0p ) { 38 38 /* paranoid */ verify( this.anchor.next == 0p ); 39 /* paranoid */ verify( this.anchor.ts== MAX );40 /* paranoid */ verify( this.anchor.ts!= 0 );39 /* paranoid */ verify( __atomic_load_n(&this.anchor.ts, __ATOMIC_RELAXED) == MAX ); 40 /* paranoid */ verify( __atomic_load_n(&this.anchor.ts, __ATOMIC_RELAXED) != 0 ); 41 41 /* paranoid */ verify( this.prev == mock_head( this ) ); 42 42 } else { 43 43 /* paranoid */ verify( this.anchor.next != 0p ); 44 /* paranoid */ verify( this.anchor.ts!= MAX );45 /* paranoid */ verify( this.anchor.ts!= 0 );44 /* paranoid */ verify( __atomic_load_n(&this.anchor.ts, __ATOMIC_RELAXED) != MAX ); 45 /* paranoid */ verify( __atomic_load_n(&this.anchor.ts, __ATOMIC_RELAXED) != 0 ); 46 46 /* paranoid */ verify( this.prev != mock_head( this ) ); 47 47 } … … 62 62 /* paranoid */ verify( this.lock ); 63 63 /* paranoid */ verify( this.anchor.next != 0p ); 64 /* paranoid */ verify( this.anchor.ts!= MAX );65 /* paranoid */ verify( this.anchor.ts != 0);64 /* paranoid */ verify( __atomic_load_n(&this.anchor.ts, __ATOMIC_RELAXED) != MAX ); 65 /* paranoid */ verify( __atomic_load_n(&this.anchor.ts, __ATOMIC_RELAXED) != 0 ); 66 66 67 67 // Get the relevant nodes locally 68 68 thread$ * node = this.anchor.next; 69 69 this.anchor.next = node->link.next; 70 this.anchor.ts = node->link.ts;70 __atomic_store_n(&this.anchor.ts, __atomic_load_n(&node->link.ts, __ATOMIC_RELAXED), __ATOMIC_RELAXED); 71 71 bool is_empty = this.anchor.next == 0p; 72 72 node->link.next = 0p; 73 node->link.ts = MAX;73 __atomic_store_n(&node->link.ts, ULLONG_MAX, __ATOMIC_RELAXED); 74 74 #if !defined(__CFA_NO_STATISTICS__) 75 75 this.cnt--; … … 79 79 if(is_empty) this.prev = mock_head( this ); 80 80 81 unsigned long long ats = __atomic_load_n(&this.anchor.ts, __ATOMIC_RELAXED); 81 82 /* paranoid */ verify( node->link.next == 0p ); 82 /* paranoid */ verify( node->link.ts == MAX);83 /* paranoid */ verify( node->link.ts != 0);84 /* paranoid */ verify( this.anchor.ts != 0);85 /* paranoid */ verify( ( this.anchor.ts== MAX) == is_empty );86 return [node, this.anchor.ts];83 /* paranoid */ verify( __atomic_load_n(&node->link.ts , __ATOMIC_RELAXED) == MAX ); 84 /* paranoid */ verify( __atomic_load_n(&node->link.ts , __ATOMIC_RELAXED) != 0 ); 85 /* paranoid */ verify( ats != 0 ); 86 /* paranoid */ verify( (ats == MAX) == is_empty ); 87 return [node, ats]; 87 88 } 88 89 … … 96 97 // Cannot verify 'emptiness' here since it may not be locked 97 98 /* paranoid */ verify(this.anchor.ts != 0); 98 return this.anchor.ts; 99 /* paranoid */ static_assert(__atomic_always_lock_free(sizeof(this.anchor.ts), &this.anchor.ts)); 100 return __atomic_load_n(&this.anchor.ts, __ATOMIC_RELAXED); 99 101 } -
libcfa/src/concurrency/thread.cfa
rbf0263c r90a8125 19 19 #include "thread.hfa" 20 20 21 #include "exception.hfa" 21 22 #include "kernel/private.hfa" 22 #include " exception.hfa"23 #include "limits.hfa" 23 24 24 25 #define __CFA_INVOKE_PRIVATE__ … … 26 27 27 28 extern uint32_t __global_random_seed, __global_random_prime, __global_random_mask; 29 30 #pragma GCC visibility push(default) 28 31 29 32 //----------------------------------------------------------------------------- … … 42 45 curr_cluster = &cl; 43 46 link.next = 0p; 44 link.ts = -1llu;47 link.ts = MAX; 45 48 preferred = ready_queue_new_preferred(); 46 49 last_proc = 0p; … … 86 89 } 87 90 88 forall(T & | is_thread(T) | IS_EXCEPTION(ThreadCancelled ,(T))89 | { EHM_DEFAULT_VTABLE(ThreadCancelled ,(T)); })91 forall(T & | is_thread(T) | IS_EXCEPTION(ThreadCancelled(T)) 92 | { EHM_DEFAULT_VTABLE(ThreadCancelled(T)); }) 90 93 void ?{}( thread_dtor_guard_t & this, 91 94 T & thrd, void(*cancelHandler)(ThreadCancelled(T) &)) { … … 165 168 166 169 //----------------------------------------------------------------------------- 167 forall(T & | is_thread(T) | IS_RESUMPTION_EXCEPTION(ThreadCancelled ,(T))168 | { EHM_DEFAULT_VTABLE(ThreadCancelled,(T)); })170 forall(T & | is_thread(T) | IS_RESUMPTION_EXCEPTION(ThreadCancelled(T)) 171 | { EHM_DEFAULT_VTABLE(ThreadCancelled(T)); }) 169 172 T & join( T & this ) { 170 173 thread_dtor_guard_t guard = { this, defaultResumptionHandler }; -
libcfa/src/concurrency/thread.hfa
rbf0263c r90a8125 32 32 }; 33 33 34 EHM_FORALL_EXCEPTION(ThreadCancelled, (thread_t &), (thread_t)) ( 34 forall(thread_t &) 35 exception ThreadCancelled { 35 36 thread_t * the_thread; 36 37 exception_t * the_exception; 37 );38 }; 38 39 39 40 forall(T &) … … 79 80 }; 80 81 81 forall( T & | is_thread(T) | IS_EXCEPTION(ThreadCancelled ,(T))82 | { EHM_DEFAULT_VTABLE(ThreadCancelled,(T)); })82 forall( T & | is_thread(T) | IS_EXCEPTION(ThreadCancelled(T)) 83 | { EHM_DEFAULT_VTABLE(ThreadCancelled(T)); }) 83 84 void ?{}( thread_dtor_guard_t & this, T & thrd, void(*)(ThreadCancelled(T) &) ); 84 85 void ^?{}( thread_dtor_guard_t & this ); … … 126 127 //---------- 127 128 // join 128 forall( T & | is_thread(T) | IS_RESUMPTION_EXCEPTION(ThreadCancelled ,(T))129 | { EHM_DEFAULT_VTABLE(ThreadCancelled,(T)); })129 forall( T & | is_thread(T) | IS_RESUMPTION_EXCEPTION(ThreadCancelled(T)) 130 | { EHM_DEFAULT_VTABLE(ThreadCancelled(T)); }) 130 131 T & join( T & this ); 131 132 -
libcfa/src/containers/maybe.cfa
rbf0263c r90a8125 17 17 #include <assert.h> 18 18 19 #pragma GCC visibility push(default) 19 20 20 21 forall(T) -
libcfa/src/containers/result.cfa
rbf0263c r90a8125 17 17 #include <assert.h> 18 18 19 #pragma GCC visibility push(default) 19 20 20 21 forall(T, E) -
libcfa/src/containers/string.cfa
rbf0263c r90a8125 18 18 #include <stdlib.hfa> 19 19 20 #pragma GCC visibility push(default) 20 21 21 22 /* -
libcfa/src/containers/string_sharectx.hfa
rbf0263c r90a8125 16 16 #pragma once 17 17 18 #pragma GCC visibility push(default) 19 18 20 //######################### String Sharing Context ######################### 19 21 20 22 struct VbyteHeap; 21 23 22 // A string_sharectx 24 // A string_sharectx 23 25 // 24 26 // Usage: -
libcfa/src/containers/vector.cfa
rbf0263c r90a8125 18 18 #include <stdlib.hfa> 19 19 20 #pragma GCC visibility push(default) 21 20 22 forall(T, allocator_t | allocator_c(T, allocator_t)) 21 void copy_internal(vector(T, allocator_t)* this, vector(T, allocator_t)* other);23 static void copy_internal(vector(T, allocator_t)* this, vector(T, allocator_t)* other); 22 24 23 25 //------------------------------------------------------------------------------ … … 83 85 84 86 forall(T, allocator_t | allocator_c(T, allocator_t)) 85 void copy_internal(vector(T, allocator_t)* this, vector(T, allocator_t)* other)87 static void copy_internal(vector(T, allocator_t)* this, vector(T, allocator_t)* other) 86 88 { 87 89 this->size = other->size; -
libcfa/src/device/cpu.cfa
rbf0263c r90a8125 31 31 } 32 32 33 #include "bits/defs.hfa" 33 34 #include "algorithms/range_iterator.hfa" 34 35 … … 456 457 } 457 458 458 cpu_info_t cpu_info;459 libcfa_public cpu_info_t cpu_info; -
libcfa/src/exception.c
rbf0263c r90a8125 27 27 #include "stdhdr/assert.h" 28 28 #include "virtual.h" 29 30 #pragma GCC visibility push(default) 31 29 32 #include "lsda.h" 30 33 … … 261 264 #else // defined( __ARM_ARCH ) 262 265 // The return code from _Unwind_RaiseException seems to be corrupt on ARM at end of stack. 263 // This workaround tries to keep default exception handling working. 266 // This workaround tries to keep default exception handling working. 264 267 if ( ret == _URC_FATAL_PHASE1_ERROR || ret == _URC_FATAL_PHASE2_ERROR ) { 265 268 #endif -
libcfa/src/exception.hfa
rbf0263c r90a8125 10 10 // Created On : Thu Apr 7 10:25:00 2020 11 11 // Last Modified By : Andrew Beach 12 // Last Modified On : Thr Apr 8 15:16:00 202113 // Update Count : 412 // Last Modified On : Wed May 25 17:20:00 2022 13 // Update Count : 5 14 14 // 15 15 … … 18 18 // ----------------------------------------------------------------------------------------------- 19 19 20 // EHM_EXCEPTION(exception_name)(fields...); 21 // Create an exception (a virtual structure that inherits from exception_t) 22 // with the given name and fields. 23 #define EHM_EXCEPTION(exception_name) \ 24 _EHM_TYPE_ID_STRUCT(exception_name, ); \ 25 _EHM_TYPE_ID_VALUE(exception_name, ); \ 26 _EHM_VIRTUAL_TABLE_STRUCT(exception_name, , ); \ 27 _EHM_EXCEPTION_STRUCT(exception_name, , ) 20 // EHM_DEFAULT_VTABLE(exception_type) 21 // Create a declaration for a (possibly polymorphic) default vtable. 22 // Mostly used by and for the currency module. 23 #define EHM_DEFAULT_VTABLE(type) vtable(type) & const _default_vtable 28 24 29 // EHM_EXTERN_VTABLE(exception_name, table_name); 30 // Forward declare a virtual table called table_name for exception_name type. 31 #define EHM_EXTERN_VTABLE(exception_name, table_name) \ 32 _EHM_EXTERN_VTABLE(exception_name, , table_name) 33 34 // EHM_VIRTUAL_TABLE(exception_name, table_name); 35 // Define a virtual table called table_name for exception_name type. 36 #define EHM_VIRTUAL_TABLE(exception_name, table_name) \ 37 _EHM_DEFINE_COPY(exception_name, ) \ 38 _EHM_DEFINE_MSG(exception_name, ) \ 39 _EHM_VIRTUAL_TABLE(exception_name, , table_name) 40 41 // EHM_FORALL_EXCEPTION(exception_name, (assertions), (parameters))(fields...); 42 // As EHM_EXCEPTION but for polymorphic types instead of monomorphic ones. 43 // The assertions list should include all polymorphic parameters and 44 // assertions inside a parentisized list. Parameters should include all the 45 // polymorphic parameter names inside a parentisized list (same order). 46 #define EHM_FORALL_EXCEPTION(exception_name, assertions, parameters) \ 47 _EHM_TYPE_ID_STRUCT(exception_name, forall assertions); \ 48 _EHM_VIRTUAL_TABLE_STRUCT(exception_name, forall assertions, parameters); \ 49 _EHM_EXCEPTION_STRUCT(exception_name, forall assertions, parameters) 50 51 // EHM_FORALL_EXTERN_VTABLE(exception_name, (arguments), table_name); 52 // As EHM_EXTERN_VTABLE but for polymorphic types instead of monomorphic ones. 53 // Arguments should be the parentisized list of polymorphic arguments. 54 #define EHM_FORALL_EXTERN_VTABLE(exception_name, arguments, table_name) \ 55 _EHM_EXTERN_VTABLE(exception_name, arguments, table_name) 56 57 // EHM_FORALL_VIRTUAL_TABLE(exception_name, (arguments), table_name); 58 // As EHM_VIRTUAL_TABLE but for polymorphic types instead of monomorphic ones. 59 // Arguments should be the parentisized list of polymorphic arguments. 60 #define EHM_FORALL_VIRTUAL_TABLE(exception_name, arguments, table_name) \ 61 _EHM_TYPE_ID_VALUE(exception_name, arguments); \ 62 _EHM_DEFINE_COPY(exception_name, arguments) \ 63 _EHM_DEFINE_MSG(exception_name, arguments) \ 64 _EHM_VIRTUAL_TABLE(exception_name, arguments, table_name) 65 66 // EHM_DEFAULT_VTABLE(exception_name, (arguments)) 67 // Create a declaration for a (possibly polymorphic) default vtable. 68 #define EHM_DEFAULT_VTABLE(exception_name, arguments) \ 69 _EHM_VTABLE_TYPE(exception_name) arguments & const _default_vtable 70 71 // IS_EXCEPTION(exception_name [, (...parameters)]) 72 // IS_RESUMPTION_EXCEPTION(exception_name [, (parameters...)]) 73 // IS_TERMINATION_EXCEPTION(exception_name [, (parameters...)]) 74 // Create an assertion that exception_name, possibly with the qualifing parameters, is the given 75 // kind of exception with the standard vtable with the same parameters if applicable. 76 #define IS_EXCEPTION(...) _IS_EXCEPTION(is_exception, __VA_ARGS__, , ~) 77 #define IS_RESUMPTION_EXCEPTION(...) _IS_EXCEPTION(is_resumption_exception, __VA_ARGS__, , ~) 78 #define IS_TERMINATION_EXCEPTION(...) _IS_EXCEPTION(is_termination_exception, __VA_ARGS__, , ~) 79 80 // Macros starting with a leading underscore are internal. 81 82 // Create an exception type definition. must be tailing, can be polymorphic. 83 #define _EHM_EXCEPTION_STRUCT(exception_name, forall_clause, parameters) \ 84 forall_clause struct exception_name { \ 85 _EHM_VTABLE_TYPE(exception_name) parameters const * virtual_table; \ 86 _CLOSE 87 88 // Create a (possibly polymorphic) virtual table forward declaration. 89 #define _EHM_EXTERN_VTABLE(exception_name, arguments, table_name) \ 90 extern const _EHM_VTABLE_TYPE(exception_name) arguments table_name 91 92 // Create a (possibly polymorphic) virtual table definition. 93 #define _EHM_VIRTUAL_TABLE(exception_type, arguments, table_name) \ 94 const _EHM_VTABLE_TYPE(exception_type) arguments table_name @= { \ 95 .__cfavir_typeid : &_EHM_TYPE_ID_NAME(exception_type), \ 96 .size : sizeof(struct exception_type arguments), \ 97 .copy : copy, \ 98 .^?{} : ^?{}, \ 99 .msg : msg, \ 100 } 101 102 // Create a (possibly polymorphic) copy function from an assignment operator. 103 #define _EHM_DEFINE_FORALL_COPY(exception_name, forall_clause, parameters) \ 104 forall_clause void copy(exception_name parameters * this, \ 105 exception_name parameters * that) { \ 106 *this = *that; \ 107 } 108 109 #define _EHM_DEFINE_COPY(exception_name, arguments) \ 110 void copy(exception_name arguments * this, exception_name arguments * that) { \ 111 *this = *that; \ 112 } 113 114 // Create a (possibly polymorphic) msg function 115 #define _EHM_DEFINE_FORALL_MSG(exception_name, forall_clause, parameters) \ 116 forall_clause const char * msg(exception_name parameters * this) { \ 117 return #exception_name #parameters; \ 118 } 119 120 #define _EHM_DEFINE_MSG(exception_name, arguments) \ 121 const char * msg(exception_name arguments * this) { \ 122 return #exception_name #arguments; \ 123 } 124 125 // Produces the C compatable name of the virtual table type for a virtual type. 126 #define _EHM_VTABLE_TYPE(type_name) struct _GLUE2(type_name,_vtable) 127 128 // Create the vtable type for exception name. 129 #define _EHM_VIRTUAL_TABLE_STRUCT(exception_name, forall_clause, parameters) \ 130 forall_clause struct exception_name; \ 131 forall_clause _EHM_VTABLE_TYPE(exception_name) { \ 132 _EHM_TYPE_ID_TYPE(exception_name) parameters const * __cfavir_typeid; \ 133 size_t size; \ 134 void (*copy)(exception_name parameters * this, exception_name parameters * other); \ 135 void (*^?{})(exception_name parameters & this); \ 136 const char * (*msg)(exception_name parameters * this); \ 137 } 138 139 // Define the function required to satify the trait for exceptions. 140 #define _EHM_TRAIT_FUNCTION(exception_name, forall_clause, parameters) \ 141 forall_clause inline void mark_exception( \ 142 exception_name parameters const &, \ 143 _EHM_VTABLE_TYPE(exception_name) parameters const &) {} \ 144 145 #define __EHM_TRAIT_FUNCTION(exception_name, forall_clause, parameters) \ 146 forall_clause inline _EHM_VTABLE_TYPE(exception_name) parameters const & \ 147 get_exception_vtable(exception_name parameters const & this) { \ 148 /* This comes before the structure definition, but we know the offset. */ \ 149 /* return (_EHM_VTABLE_TYPE(exception_name) parameters const &)this; */ \ 150 assert(false); \ 151 } 152 153 // Generates a new type-id structure. This is used to mangle the name of the 154 // type-id instance so it also includes polymorphic information. Must be the 155 // direct decendent of exception_t. 156 // The second field is used to recover type information about the exception. 157 #define _EHM_TYPE_ID_STRUCT(exception_name, forall_clause) \ 158 forall_clause _EHM_TYPE_ID_TYPE(exception_name) { \ 159 __cfavir_type_info const * parent; \ 160 } 161 162 // Generate a new type-id value. 163 #define _EHM_TYPE_ID_VALUE(exception_name, arguments) \ 164 __attribute__((cfa_linkonce)) \ 165 _EHM_TYPE_ID_TYPE(exception_name) arguments const \ 166 _EHM_TYPE_ID_NAME(exception_name) = { \ 167 &__cfatid_exception_t, \ 168 } 169 170 // _EHM_TYPE_ID_STRUCT and _EHM_TYPE_ID_VALUE are the two that would need to 171 // be updated to extend the hierarchy if we are still using macros when that 172 // is added. 173 174 // Produce the C compatable name of the type-id type for an exception type. 175 #define _EHM_TYPE_ID_TYPE(exception_name) \ 176 struct _GLUE2(__cfatid_struct_, exception_name) 177 178 // Produce the name of the instance of the type-id for an exception type. 179 #define _EHM_TYPE_ID_NAME(exception_name) _GLUE2(__cfatid_,exception_name) 180 181 #define _IS_EXCEPTION(kind, exception_name, parameters, ...) \ 182 kind(exception_name parameters, _EHM_VTABLE_TYPE(exception_name) parameters) 183 184 // Internal helper macros: 185 #define _CLOSE(...) __VA_ARGS__ } 186 #define _GLUE2(left, right) left##right 25 // IS_EXCEPTION(exception_type) 26 // IS_RESUMPTION_EXCEPTION(exception_type) 27 // IS_TERMINATION_EXCEPTION(exception_type) 28 // Create an assertion that exception_type is the given kind of exception. 29 // This is used to mimic associated types so the vtable type is unmentioned. 30 #define IS_EXCEPTION(type) is_exception(type, vtable(type)) 31 #define IS_RESUMPTION_EXCEPTION(type) is_resumption_exception(type, vtable(type)) 32 #define IS_TERMINATION_EXCEPTION(type) is_termination_exception(type, vtable(type)) -
libcfa/src/fstream.cfa
rbf0263c r90a8125 22 22 #include <assert.h> 23 23 #include <errno.h> // errno 24 25 #pragma GCC visibility push(default) 24 26 25 27 // *********************************** ofstream *********************************** … … 118 120 // abort | IO_MSG "open output file \"" | name | "\"" | nl | strerror( errno ); 119 121 } // if 120 (os){ file }; // initialize 122 (os){ file }; // initialize 121 123 } // open 122 124 … … 157 159 va_list args; 158 160 va_start( args, format ); 159 161 160 162 int len; 161 163 for ( cnt; 10 ) { … … 241 243 // abort | IO_MSG "open input file \"" | name | "\"" | nl | strerror( errno ); 242 244 } // if 243 (is){ file }; // initialize 245 (is){ file }; // initialize 244 246 } // open 245 247 -
libcfa/src/fstream.hfa
rbf0263c r90a8125 18 18 #include "bits/weakso_locks.hfa" // mutex_lock 19 19 #include "iostream.hfa" 20 #include <exception.hfa>21 20 22 21 -
libcfa/src/heap.cfa
rbf0263c r90a8125 36 36 static bool traceHeap = false; 37 37 38 inline bool traceHeap() { return traceHeap; }39 40 bool traceHeapOn() {38 inline bool traceHeap() libcfa_public { return traceHeap; } 39 40 bool traceHeapOn() libcfa_public { 41 41 bool temp = traceHeap; 42 42 traceHeap = true; … … 44 44 } // traceHeapOn 45 45 46 bool traceHeapOff() {46 bool traceHeapOff() libcfa_public { 47 47 bool temp = traceHeap; 48 48 traceHeap = false; … … 50 50 } // traceHeapOff 51 51 52 bool traceHeapTerm() { return false; }52 bool traceHeapTerm() libcfa_public { return false; } 53 53 54 54 55 55 static bool prtFree = false; 56 56 57 bool prtFree() {57 static bool prtFree() { 58 58 return prtFree; 59 59 } // prtFree 60 60 61 bool prtFreeOn() {61 static bool prtFreeOn() { 62 62 bool temp = prtFree; 63 63 prtFree = true; … … 65 65 } // prtFreeOn 66 66 67 bool prtFreeOff() {67 static bool prtFreeOff() { 68 68 bool temp = prtFree; 69 69 prtFree = false; … … 388 388 static unsigned int maxBucketsUsed; // maximum number of buckets in use 389 389 // extern visibility, used by runtime kernel 390 size_t __page_size; // architecture pagesize 391 int __map_prot; // common mmap/mprotect protection 390 // would be cool to remove libcfa_public but it's needed for libcfathread 391 libcfa_public size_t __page_size; // architecture pagesize 392 libcfa_public int __map_prot; // common mmap/mprotect protection 392 393 393 394 … … 727 728 728 729 729 s ize_t prtFree( Heap & manager ) with( manager ) {730 static size_t prtFree( Heap & manager ) with( manager ) { 730 731 size_t total = 0; 731 732 #ifdef __STATISTICS__ … … 879 880 // Allocates size bytes and returns a pointer to the allocated memory. The contents are undefined. If size is 0, 880 881 // then malloc() returns a unique pointer value that can later be successfully passed to free(). 881 void * malloc( size_t size ) {882 void * malloc( size_t size ) libcfa_public { 882 883 #ifdef __STATISTICS__ 883 884 if ( likely( size > 0 ) ) { … … 894 895 895 896 // Same as malloc() except size bytes is an array of dim elements each of elemSize bytes. 896 void * aalloc( size_t dim, size_t elemSize ) {897 void * aalloc( size_t dim, size_t elemSize ) libcfa_public { 897 898 size_t size = dim * elemSize; 898 899 #ifdef __STATISTICS__ … … 910 911 911 912 // Same as aalloc() with memory set to zero. 912 void * calloc( size_t dim, size_t elemSize ) {913 void * calloc( size_t dim, size_t elemSize ) libcfa_public { 913 914 size_t size = dim * elemSize; 914 915 if ( unlikely( size ) == 0 ) { // 0 BYTE ALLOCATION RETURNS NULL POINTER … … 951 952 // not 0p, then the call is equivalent to free(oaddr). Unless oaddr is 0p, it must have been returned by an earlier 952 953 // call to malloc(), alloc(), calloc() or realloc(). If the area pointed to was moved, a free(oaddr) is done. 953 void * resize( void * oaddr, size_t size ) {954 void * resize( void * oaddr, size_t size ) libcfa_public { 954 955 // If size is equal to 0, either NULL or a pointer suitable to be passed to free() is returned. 955 956 if ( unlikely( size == 0 ) ) { // special cases … … 996 997 // Same as resize() but the contents are unchanged in the range from the start of the region up to the minimum of 997 998 // the old and new sizes. 998 void * realloc( void * oaddr, size_t size ) {999 void * realloc( void * oaddr, size_t size ) libcfa_public { 999 1000 // If size is equal to 0, either NULL or a pointer suitable to be passed to free() is returned. 1000 1001 if ( unlikely( size == 0 ) ) { // special cases … … 1060 1061 1061 1062 // Same as realloc() except the new allocation size is large enough for an array of nelem elements of size elsize. 1062 void * reallocarray( void * oaddr, size_t dim, size_t elemSize ) {1063 void * reallocarray( void * oaddr, size_t dim, size_t elemSize ) libcfa_public { 1063 1064 return realloc( oaddr, dim * elemSize ); 1064 1065 } // reallocarray … … 1066 1067 1067 1068 // Same as malloc() except the memory address is a multiple of alignment, which must be a power of two. (obsolete) 1068 void * memalign( size_t alignment, size_t size ) {1069 void * memalign( size_t alignment, size_t size ) libcfa_public { 1069 1070 #ifdef __STATISTICS__ 1070 1071 if ( likely( size > 0 ) ) { … … 1081 1082 1082 1083 // Same as aalloc() with memory alignment. 1083 void * amemalign( size_t alignment, size_t dim, size_t elemSize ) {1084 void * amemalign( size_t alignment, size_t dim, size_t elemSize ) libcfa_public { 1084 1085 size_t size = dim * elemSize; 1085 1086 #ifdef __STATISTICS__ … … 1097 1098 1098 1099 // Same as calloc() with memory alignment. 1099 void * cmemalign( size_t alignment, size_t dim, size_t elemSize ) {1100 void * cmemalign( size_t alignment, size_t dim, size_t elemSize ) libcfa_public { 1100 1101 size_t size = dim * elemSize; 1101 1102 if ( unlikely( size ) == 0 ) { // 0 BYTE ALLOCATION RETURNS NULL POINTER … … 1136 1137 // Same as memalign(), but ISO/IEC 2011 C11 Section 7.22.2 states: the value of size shall be an integral multiple 1137 1138 // of alignment. This requirement is universally ignored. 1138 void * aligned_alloc( size_t alignment, size_t size ) {1139 void * aligned_alloc( size_t alignment, size_t size ) libcfa_public { 1139 1140 return memalign( alignment, size ); 1140 1141 } // aligned_alloc … … 1145 1146 // is 0, then posix_memalign() returns either 0p, or a unique pointer value that can later be successfully passed to 1146 1147 // free(3). 1147 int posix_memalign( void ** memptr, size_t alignment, size_t size ) {1148 int posix_memalign( void ** memptr, size_t alignment, size_t size ) libcfa_public { 1148 1149 if ( unlikely( alignment < libAlign() || ! is_pow2( alignment ) ) ) return EINVAL; // check alignment 1149 1150 *memptr = memalign( alignment, size ); … … 1154 1155 // Allocates size bytes and returns a pointer to the allocated memory. The memory address shall be a multiple of the 1155 1156 // page size. It is equivalent to memalign(sysconf(_SC_PAGESIZE),size). 1156 void * valloc( size_t size ) {1157 void * valloc( size_t size ) libcfa_public { 1157 1158 return memalign( __page_size, size ); 1158 1159 } // valloc … … 1160 1161 1161 1162 // Same as valloc but rounds size to multiple of page size. 1162 void * pvalloc( size_t size ) {1163 void * pvalloc( size_t size ) libcfa_public { 1163 1164 return memalign( __page_size, ceiling2( size, __page_size ) ); // round size to multiple of page size 1164 1165 } // pvalloc … … 1168 1169 // or realloc(). Otherwise, or if free(ptr) has already been called before, undefined behaviour occurs. If ptr is 1169 1170 // 0p, no operation is performed. 1170 void free( void * addr ) {1171 void free( void * addr ) libcfa_public { 1171 1172 if ( unlikely( addr == 0p ) ) { // special case 1172 1173 #ifdef __STATISTICS__ … … 1189 1190 1190 1191 // Returns the alignment of an allocation. 1191 size_t malloc_alignment( void * addr ) {1192 size_t malloc_alignment( void * addr ) libcfa_public { 1192 1193 if ( unlikely( addr == 0p ) ) return libAlign(); // minimum alignment 1193 1194 Heap.Storage.Header * header = HeaderAddr( addr ); … … 1201 1202 1202 1203 // Returns true if the allocation is zero filled, e.g., allocated by calloc(). 1203 bool malloc_zero_fill( void * addr ) {1204 bool malloc_zero_fill( void * addr ) libcfa_public { 1204 1205 if ( unlikely( addr == 0p ) ) return false; // null allocation is not zero fill 1205 1206 Heap.Storage.Header * header = HeaderAddr( addr ); … … 1212 1213 1213 1214 // Returns original total allocation size (not bucket size) => array size is dimension * sizeof(T). 1214 size_t malloc_size( void * addr ) {1215 size_t malloc_size( void * addr ) libcfa_public { 1215 1216 if ( unlikely( addr == 0p ) ) return 0; // null allocation has zero size 1216 1217 Heap.Storage.Header * header = HeaderAddr( addr ); … … 1224 1225 // Returns the number of usable bytes in the block pointed to by ptr, a pointer to a block of memory allocated by 1225 1226 // malloc or a related function. 1226 size_t malloc_usable_size( void * addr ) {1227 size_t malloc_usable_size( void * addr ) libcfa_public { 1227 1228 if ( unlikely( addr == 0p ) ) return 0; // null allocation has 0 size 1228 1229 Heap.Storage.Header * header; … … 1236 1237 1237 1238 // Prints (on default standard error) statistics about memory allocated by malloc and related functions. 1238 void malloc_stats( void ) {1239 void malloc_stats( void ) libcfa_public { 1239 1240 #ifdef __STATISTICS__ 1240 1241 printStats(); … … 1245 1246 1246 1247 // Changes the file descriptor where malloc_stats() writes statistics. 1247 int malloc_stats_fd( int fd __attribute__(( unused )) ) {1248 int malloc_stats_fd( int fd __attribute__(( unused )) ) libcfa_public { 1248 1249 #ifdef __STATISTICS__ 1249 1250 int temp = stats_fd; … … 1259 1260 // The string is printed on the file stream stream. The exported string includes information about all arenas (see 1260 1261 // malloc). 1261 int malloc_info( int options, FILE * stream __attribute__(( unused )) ) {1262 int malloc_info( int options, FILE * stream __attribute__(( unused )) ) libcfa_public { 1262 1263 if ( options != 0 ) { errno = EINVAL; return -1; } 1263 1264 #ifdef __STATISTICS__ … … 1271 1272 // Adjusts parameters that control the behaviour of the memory-allocation functions (see malloc). The param argument 1272 1273 // specifies the parameter to be modified, and value specifies the new value for that parameter. 1273 int mallopt( int option, int value ) {1274 int mallopt( int option, int value ) libcfa_public { 1274 1275 if ( value < 0 ) return 0; 1275 1276 choose( option ) { … … 1285 1286 1286 1287 // Attempt to release free memory at the top of the heap (by calling sbrk with a suitable argument). 1287 int malloc_trim( size_t ) {1288 int malloc_trim( size_t ) libcfa_public { 1288 1289 return 0; // => impossible to release memory 1289 1290 } // malloc_trim … … 1294 1295 // structure dynamically allocated via malloc, and a pointer to that data structure is returned as the function 1295 1296 // result. (The caller must free this memory.) 1296 void * malloc_get_state( void ) {1297 void * malloc_get_state( void ) libcfa_public { 1297 1298 return 0p; // unsupported 1298 1299 } // malloc_get_state … … 1301 1302 // Restores the state of all malloc internal bookkeeping variables to the values recorded in the opaque data 1302 1303 // structure pointed to by state. 1303 int malloc_set_state( void * ) {1304 int malloc_set_state( void * ) libcfa_public { 1304 1305 return 0; // unsupported 1305 1306 } // malloc_set_state … … 1307 1308 1308 1309 // Sets the amount (bytes) to extend the heap when there is insufficent free storage to service an allocation. 1309 __attribute__((weak)) size_t malloc_expansion() { return __CFA_DEFAULT_HEAP_EXPANSION__; }1310 __attribute__((weak)) size_t malloc_expansion() libcfa_public { return __CFA_DEFAULT_HEAP_EXPANSION__; } 1310 1311 1311 1312 // Sets the crossover point between allocations occuring in the sbrk area or separately mmapped. 1312 __attribute__((weak)) size_t malloc_mmap_start() { return __CFA_DEFAULT_MMAP_START__; }1313 __attribute__((weak)) size_t malloc_mmap_start() libcfa_public { return __CFA_DEFAULT_MMAP_START__; } 1313 1314 1314 1315 // Amount subtracted to adjust for unfreed program storage (debug only). 1315 __attribute__((weak)) size_t malloc_unfreed() { return __CFA_DEFAULT_HEAP_UNFREED__; }1316 __attribute__((weak)) size_t malloc_unfreed() libcfa_public { return __CFA_DEFAULT_HEAP_UNFREED__; } 1316 1317 } // extern "C" 1317 1318 1318 1319 1319 1320 // Must have CFA linkage to overload with C linkage realloc. 1320 void * resize( void * oaddr, size_t nalign, size_t size ) {1321 void * resize( void * oaddr, size_t nalign, size_t size ) libcfa_public { 1321 1322 // If size is equal to 0, either NULL or a pointer suitable to be passed to free() is returned. 1322 1323 if ( unlikely( size == 0 ) ) { // special cases … … 1380 1381 1381 1382 1382 void * realloc( void * oaddr, size_t nalign, size_t size ) {1383 void * realloc( void * oaddr, size_t nalign, size_t size ) libcfa_public { 1383 1384 // If size is equal to 0, either NULL or a pointer suitable to be passed to free() is returned. 1384 1385 if ( unlikely( size == 0 ) ) { // special cases -
libcfa/src/interpose.cfa
rbf0263c r90a8125 36 36 //============================================================================================= 37 37 38 void preload_libgcc(void) {38 static void preload_libgcc(void) { 39 39 dlopen( "libgcc_s.so.1", RTLD_NOW ); 40 40 if ( const char * error = dlerror() ) abort( "interpose_symbol : internal error pre-loading libgcc, %s\n", error ); … … 42 42 43 43 typedef void (* generic_fptr_t)(void); 44 generic_fptr_t interpose_symbol( const char symbol[], const char version[] ) {44 static generic_fptr_t interpose_symbol( const char symbol[], const char version[] ) { 45 45 const char * error; 46 46 … … 83 83 //============================================================================================= 84 84 85 void sigHandler_segv( __CFA_SIGPARMS__ );86 void sigHandler_ill ( __CFA_SIGPARMS__ );87 void sigHandler_fpe ( __CFA_SIGPARMS__ );88 void sigHandler_abrt( __CFA_SIGPARMS__ );89 void sigHandler_term( __CFA_SIGPARMS__ );90 91 st ruct {85 static void sigHandler_segv( __CFA_SIGPARMS__ ); 86 static void sigHandler_ill ( __CFA_SIGPARMS__ ); 87 static void sigHandler_fpe ( __CFA_SIGPARMS__ ); 88 static void sigHandler_abrt( __CFA_SIGPARMS__ ); 89 static void sigHandler_term( __CFA_SIGPARMS__ ); 90 91 static struct { 92 92 void (* exit)( int ) __attribute__(( __noreturn__ )); 93 93 void (* abort)( void ) __attribute__(( __noreturn__ )); 94 94 } __cabi_libc; 95 95 96 int cfa_main_returned;96 libcfa_public int cfa_main_returned; 97 97 98 98 extern "C" { … … 148 148 149 149 // Forward declare abort after the __typeof__ call to avoid ambiguities 150 void exit( int status, const char fmt[], ... ) __attribute__(( format(printf, 2, 3), __nothrow__, __leaf__, __noreturn__ ));151 void abort( const char fmt[], ... ) __attribute__(( format(printf, 1, 2), __nothrow__, __leaf__, __noreturn__ ));152 void abort( bool signalAbort, const char fmt[], ... ) __attribute__(( format(printf, 2, 3), __nothrow__, __leaf__, __noreturn__ ));153 void __abort( bool signalAbort, const char fmt[], va_list args ) __attribute__(( __nothrow__, __leaf__, __noreturn__ ));150 libcfa_public void exit( int status, const char fmt[], ... ) __attribute__(( format(printf, 2, 3), __nothrow__, __leaf__, __noreturn__ )); 151 libcfa_public void abort( const char fmt[], ... ) __attribute__(( format(printf, 1, 2), __nothrow__, __leaf__, __noreturn__ )); 152 libcfa_public void abort( bool signalAbort, const char fmt[], ... ) __attribute__(( format(printf, 2, 3), __nothrow__, __leaf__, __noreturn__ )); 153 libcfa_public void __abort( bool signalAbort, const char fmt[], va_list args ) __attribute__(( __nothrow__, __leaf__, __noreturn__ )); 154 154 155 155 extern "C" { 156 void abort( void ) __attribute__(( __nothrow__, __leaf__, __noreturn__ )) {156 libcfa_public void abort( void ) __attribute__(( __nothrow__, __leaf__, __noreturn__ )) { 157 157 abort( false, "%s", "" ); 158 158 } 159 159 160 void __cabi_abort( const char fmt[], ... ) __attribute__(( format(printf, 1, 2), __nothrow__, __leaf__, __noreturn__ )) {160 libcfa_public void __cabi_abort( const char fmt[], ... ) __attribute__(( format(printf, 1, 2), __nothrow__, __leaf__, __noreturn__ )) { 161 161 va_list argp; 162 162 va_start( argp, fmt ); … … 165 165 } 166 166 167 void exit( int status ) __attribute__(( __nothrow__, __leaf__, __noreturn__ )) {167 libcfa_public void exit( int status ) __attribute__(( __nothrow__, __leaf__, __noreturn__ )) { 168 168 __cabi_libc.exit( status ); 169 169 } -
libcfa/src/iostream.cfa
rbf0263c r90a8125 32 32 #include "bitmanip.hfa" // high1 33 33 34 #pragma GCC visibility push(default) 34 35 35 36 // *********************************** ostream *********************************** -
libcfa/src/limits.cfa
rbf0263c r90a8125 20 20 #include <complex.h> 21 21 #include "limits.hfa" 22 23 #pragma GCC visibility push(default) 22 24 23 25 // Integral Constants -
libcfa/src/memory.cfa
rbf0263c r90a8125 16 16 #include "memory.hfa" 17 17 #include "stdlib.hfa" 18 19 #pragma GCC visibility push(default) 18 20 19 21 // Internal data object. -
libcfa/src/parseargs.cfa
rbf0263c r90a8125 24 24 #include "common.hfa" 25 25 #include "limits.hfa" 26 27 #pragma GCC visibility push(default) 26 28 27 29 extern int cfa_args_argc __attribute__((weak)); -
libcfa/src/parseconfig.cfa
rbf0263c r90a8125 14 14 15 15 16 #pragma GCC visibility push(default) 17 16 18 // *********************************** exceptions *********************************** 17 19 18 20 19 21 // TODO: Add names of missing config entries to exception (see further below) 20 staticvtable(Missing_Config_Entries) Missing_Config_Entries_vt;22 vtable(Missing_Config_Entries) Missing_Config_Entries_vt; 21 23 22 24 [ void ] ?{}( & Missing_Config_Entries this, unsigned int num_missing ) { … … 31 33 32 34 33 staticvtable(Parse_Failure) Parse_Failure_vt;35 vtable(Parse_Failure) Parse_Failure_vt; 34 36 35 37 [ void ] ?{}( & Parse_Failure this, [] char failed_key, [] char failed_value ) { … … 53 55 54 56 55 staticvtable(Validation_Failure) Validation_Failure_vt;57 vtable(Validation_Failure) Validation_Failure_vt; 56 58 57 59 [ void ] ?{}( & Validation_Failure this, [] char failed_key, [] char failed_value ) { … … 110 112 111 113 112 [ bool ] comments( & ifstream in, [] char name ) {114 static [ bool ] comments( & ifstream in, [] char name ) { 113 115 while () { 114 116 in | name; -
libcfa/src/rational.cfa
rbf0263c r90a8125 17 17 #include "fstream.hfa" 18 18 #include "stdlib.hfa" 19 20 #pragma GCC visibility push(default) 19 21 20 22 forall( T | Arithmetic( T ) ) { -
libcfa/src/startup.cfa
rbf0263c r90a8125 41 41 } // __cfaabi_appready_shutdown 42 42 43 void disable_interrupts() __attribute__(( weak )) {}44 void enable_interrupts() __attribute__(( weak )) {}43 void disable_interrupts() __attribute__(( weak )) libcfa_public {} 44 void enable_interrupts() __attribute__(( weak )) libcfa_public {} 45 45 46 46 … … 64 64 struct __spinlock_t; 65 65 extern "C" { 66 void __cfaabi_dbg_record_lock(struct __spinlock_t & this, const char prev_name[]) __attribute__(( weak )) {}66 void __cfaabi_dbg_record_lock(struct __spinlock_t & this, const char prev_name[]) __attribute__(( weak )) libcfa_public {} 67 67 } 68 68 -
libcfa/src/stdlib.cfa
rbf0263c r90a8125 25 25 #include <complex.h> // _Complex_I 26 26 #include <assert.h> 27 28 #pragma GCC visibility push(default) 27 29 28 30 //--------------------------------------- … … 225 227 #define GENERATOR LCG 226 228 227 uint32_t __global_random_seed; // sequential/concurrent 228 uint32_t __global_random_state; // sequential only 229 // would be cool to make hidden but it's needed for libcfathread 230 __attribute__((visibility("default"))) uint32_t __global_random_seed; // sequential/concurrent 231 __attribute__((visibility("hidden"))) uint32_t __global_random_state; // sequential only 229 232 230 233 void set_seed( PRNG & prng, uint32_t seed_ ) with( prng ) { state = seed = seed_; GENERATOR( state ); } // set seed -
libcfa/src/strstream.cfa
rbf0263c r90a8125 1 // 1 // 2 2 // Cforall Version 1.0.0 Copyright (C) 2021 University of Waterloo 3 // 3 // 4 4 // The contents of this file are covered under the licence agreement in the 5 5 // file "LICENCE" distributed with Cforall. 6 6 // 7 // strstream.cfa -- 8 // 7 // strstream.cfa -- 8 // 9 9 // Author : Peter A. Buhr 10 10 // Created On : Thu Apr 22 22:24:35 2021 … … 12 12 // Last Modified On : Sun Oct 10 16:13:20 2021 13 13 // Update Count : 101 14 // 14 // 15 15 16 16 #include "strstream.hfa" … … 24 24 #include <unistd.h> // sbrk, sysconf 25 25 26 #pragma GCC visibility push(default) 26 27 27 28 // *********************************** strstream *********************************** -
libcfa/src/time.cfa
rbf0263c r90a8125 18 18 #include <stdio.h> // snprintf 19 19 #include <assert.h> 20 21 #pragma GCC visibility push(default) 20 22 21 23 static char * nanomsd( long int ns, char * buf ) { // most significant digits -
libcfa/src/virtual.c
rbf0263c r90a8125 16 16 #include "virtual.h" 17 17 #include "assert.h" 18 19 #pragma GCC visibility push(default) 18 20 19 21 int __cfavir_is_parent(
Note:
See TracChangeset
for help on using the changeset viewer.