Changeset fe97de26
- Timestamp:
- Dec 22, 2020, 9:16:13 AM (4 years ago)
- Branches:
- ADT, arm-eh, ast-experimental, enum, forall-pointer-decay, jacob/cs343-translation, master, new-ast-unique-expr, pthread-emulation, qualifiedEnum
- Children:
- 797a193
- Parents:
- 0285efe (diff), 3f8baf4 (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. - Files:
-
- 4 added
- 7 edited
Legend:
- Unmodified
- Added
- Removed
-
benchmark/Makefile.am
r0285efe rfe97de26 522 522 size-cfa$(EXEEXT): 523 523 $(BENCH_V_CFA)$(CFACOMPILE) $(srcdir)/size/size.cfa 524 525 ## ========================================================================================================= 526 527 %-tokio$(EXEEXT): $(srcdir)/readyQ/%.rs $(srcdir)/bench.rs 528 cd $(builddir) && cargo build --release 529 cp $(builddir)/target/release/$(basename $@) $@ -
benchmark/readyQ/bench.go
r0285efe rfe97de26 5 5 "flag" 6 6 "fmt" 7 "log" 7 8 "os" 8 9 "runtime" 10 "runtime/pprof" 9 11 "sync/atomic" 10 12 "time" … … 43 45 } 44 46 45 func bench_init() {47 func bench_init() func() { 46 48 nprocsOpt := flag.Int("p", 1, "The number of processors") 47 49 nthreadsOpt := flag.Int("t", 1, "The number of threads") 48 50 durationOpt := flag.Float64("d", 0, "Duration of the experiment in seconds") 49 51 stopOpt := flag.Uint64("i", 0, "Duration of the experiment in iterations") 52 cpuprofile := flag.String("cpuprofile", "", "write cpu profile to file") 50 53 51 54 flag.Parse() … … 72 75 73 76 runtime.GOMAXPROCS(nprocs) 77 78 if (*cpuprofile) != "" { 79 f, err := os.Create(*cpuprofile) 80 if err != nil { 81 log.Fatal(err) 82 } 83 pprof.StartCPUProfile(f) 84 } 85 86 return func() { 87 if (*cpuprofile) != "" { 88 pprof.StopCPUProfile() 89 } 90 } 74 91 } -
benchmark/readyQ/cycle.rs
r0285efe rfe97de26 1 #[cfg(any(2 feature = "sync time rt-threaded",3 ))]4 5 extern crate tokio;6 7 use std::io::{self, Write};8 1 use std::sync::Arc; 9 use std::sync::atomic:: {AtomicU64, AtomicBool,Ordering};10 use std::time:: {Instant,Duration};2 use std::sync::atomic::Ordering; 3 use std::time::Instant; 11 4 12 5 use tokio::runtime::Builder; 13 6 use tokio::sync; 14 use tokio::time;15 7 16 extern crate isatty; 17 use isatty::stdout_isatty; 18 19 extern crate num_format; 8 use clap::{Arg, App}; 20 9 use num_format::{Locale, ToFormattedString}; 21 10 22 extern crate clap; 23 use clap::{Arg, App};11 #[path = "../bench.rs"] 12 mod bench; 24 13 25 use std::cell::UnsafeCell; 26 use std::mem::MaybeUninit; 27 use std::ops; 28 29 pub struct InitializeCell<T> { 30 inner: UnsafeCell<MaybeUninit<T>>, 31 } 32 33 unsafe impl<T> Sync for InitializeCell<T> {} 34 35 impl<T> InitializeCell<T> { 36 pub const unsafe fn new_uninitialized() -> InitializeCell<T> { 37 InitializeCell { 38 inner: UnsafeCell::new(MaybeUninit::uninit()), 39 } 40 } 41 pub const fn new(init: T) -> InitializeCell<T> { 42 InitializeCell { 43 inner: UnsafeCell::new(MaybeUninit::new(init)), 44 } 45 } 46 pub unsafe fn init(&self, init: T) { 47 (*self.inner.get()) = MaybeUninit::new(init); 48 } 49 } 50 51 impl<T> ops::Deref for InitializeCell<T> { 52 type Target = T; 53 fn deref(&self) -> &T { 54 unsafe { 55 &*(*self.inner.get()).as_ptr() 56 } 57 } 58 } 59 60 static CLOCK_MODE: InitializeCell<bool> = unsafe { InitializeCell::new_uninitialized() }; 61 static STOP_COUNT: InitializeCell<u64> = unsafe { InitializeCell::new_uninitialized() }; 62 static DURATION: InitializeCell<f64> = unsafe { InitializeCell::new_uninitialized() }; 63 static STOP : AtomicBool = AtomicBool::new(false); 64 static THREADS_LEFT : AtomicU64 = AtomicU64 ::new(10); 65 14 // ================================================== 66 15 struct Partner { 67 16 sem: sync::Semaphore, … … 69 18 } 70 19 71 async fn partner_main( result: sync::oneshot::Sender<u64>, idx: usize, others: Arc<Vec<Arc<Partner>>> ){20 async fn partner_main(idx: usize, others: Arc<Vec<Arc<Partner>>>, exp: Arc<bench::BenchData> ) -> u64 { 72 21 let this = &others[idx]; 73 22 let mut count:u64 = 0; … … 77 26 count += 1; 78 27 79 if *CLOCK_MODE && STOP.load(Ordering::Relaxed) { break; }80 if ! *CLOCK_MODE && count >= *STOP_COUNT{ break; }28 if exp.clock_mode && exp.stop.load(Ordering::Relaxed) { break; } 29 if !exp.clock_mode && count >= exp.stop_count { break; } 81 30 } 82 31 83 THREADS_LEFT.fetch_sub(1, Ordering::SeqCst);84 result.send( count ).unwrap();32 exp.threads_left.fetch_sub(1, Ordering::SeqCst); 33 count 85 34 } 86 35 87 fn prep(nthreads: usize, tthreads: usize) -> Vec<Arc<Partner>> { 88 let mut thddata = Vec::with_capacity(tthreads); 89 for i in 0..tthreads { 90 let pi = (i + nthreads) % tthreads; 91 thddata.push(Arc::new(Partner{ 92 sem: sync::Semaphore::new(0), 93 next: pi, 94 })); 95 } 96 return thddata; 97 } 98 99 async fn wait(start: &Instant, is_tty: bool) { 100 loop { 101 time::sleep(Duration::from_micros(100000)).await; 102 let delta = start.elapsed(); 103 if is_tty { 104 print!(" {:.1}\r", delta.as_secs_f32()); 105 io::stdout().flush().unwrap(); 106 } 107 if *CLOCK_MODE && delta >= Duration::from_secs_f64(*DURATION) { 108 break; 109 } 110 else if !*CLOCK_MODE && THREADS_LEFT.load(Ordering::Relaxed) == 0 { 111 break; 112 } 113 } 114 } 115 36 // ================================================== 116 37 fn main() { 117 38 let options = App::new("Cycle Tokio") 118 .arg(Arg::with_name("duration") .short("d").long("duration") .takes_value(true).default_value("5").help("Duration of the experiments in seconds")) 119 .arg(Arg::with_name("iterations").short("i").long("iterations").takes_value(true).conflicts_with("duration").help("Number of iterations of the experiments")) 120 .arg(Arg::with_name("nthreads") .short("t").long("nthreads") .takes_value(true).default_value("1").help("Number of threads to use")) 121 .arg(Arg::with_name("nprocs") .short("p").long("nprocs") .takes_value(true).default_value("1").help("Number of processors to use")) 39 .args(&bench::args()) 122 40 .arg(Arg::with_name("ringsize") .short("r").long("ringsize") .takes_value(true).default_value("1").help("Number of threads in a cycle")) 123 41 .get_matches(); … … 127 45 let nprocs = options.value_of("nprocs").unwrap().parse::<usize>().unwrap(); 128 46 129 if options.is_present("iterations") { 130 unsafe{ 131 CLOCK_MODE.init( false ); 132 STOP_COUNT.init( options.value_of("iterations").unwrap().parse::<u64>().unwrap() ); 133 } 134 } 135 else { 136 unsafe{ 137 CLOCK_MODE.init(true); 138 DURATION .init(options.value_of("duration").unwrap().parse::<f64>().unwrap()); 139 } 140 } 47 let tthreads = nthreads * ring_size; 48 let exp = Arc::new(bench::BenchData::new(options, tthreads)); 141 49 142 50 let s = (1000000 as u64).to_formatted_string(&Locale::en); 143 51 assert_eq!(&s, "1,000,000"); 144 52 145 146 let tthreads = nthreads * ring_size; 147 THREADS_LEFT.store(tthreads as u64, Ordering::SeqCst); 148 let thddata = Arc::new(prep(nthreads, tthreads)); 53 let thddata : Arc<Vec<Arc<Partner>>> = Arc::new( 54 (0..tthreads).map(|i| { 55 let pi = (i + nthreads) % tthreads; 56 Arc::new(Partner{ 57 sem: sync::Semaphore::new(0), 58 next: pi, 59 }) 60 }).collect() 61 ); 149 62 150 63 let mut global_counter :u64 = 0; … … 157 70 158 71 runtime.block_on(async { 159 let mut result : Vec<sync::oneshot::Receiver::<u64>> = Vec::with_capacity(tthreads); 160 { 161 let mut threads = Vec::with_capacity(tthreads); 162 for i in 0..tthreads { 163 let (s, r) = sync::oneshot::channel::<u64>(); 164 result.push(r); 165 threads.push(tokio::spawn(partner_main(s, i, thddata.clone()))); 166 } 167 println!("Starting"); 72 let threads: Vec<_> = (0..tthreads).map(|i| { 73 tokio::spawn(partner_main(i, thddata.clone(), exp.clone())) 74 }).collect(); 75 println!("Starting"); 168 76 169 let is_tty = stdout_isatty(); 170 let start = Instant::now(); 77 let start = Instant::now(); 171 78 172 173 174 79 for i in 0..nthreads { 80 thddata[i].sem.add_permits(1); 81 } 175 82 176 wait(&start, is_tty).await;83 duration = exp.wait(&start).await; 177 84 178 STOP.store(true, Ordering::SeqCst); 179 duration = start.elapsed(); 85 println!("\nDone"); 180 86 181 println!("\nDone"); 87 for i in 0..tthreads { 88 thddata[i].sem.add_permits(1); 89 } 182 90 183 for i in 0..tthreads { 184 thddata[i].sem.add_permits(1); 185 } 186 187 for _ in 0..tthreads { 188 global_counter += result.pop().unwrap().await.unwrap(); 189 } 91 for t in threads { 92 global_counter += t.await.unwrap(); 190 93 } 191 94 }); -
benchmark/readyQ/locality.go
r0285efe rfe97de26 18 18 // ================================================== 19 19 type MyData struct { 20 _p1 [16]uint64 // padding 20 21 ttid int 21 22 id int 22 23 data [] uint64 24 _p2 [16]uint64 // padding 23 25 } 24 26 … … 29 31 data[i] = 0 30 32 } 31 return &MyData{ syscall.Gettid(), id, data}33 return &MyData{[16]uint64{0}, syscall.Gettid(), id, data,[16]uint64{0}} 32 34 } 33 35 … … 46 48 // ================================================== 47 49 type MyCtx struct { 50 _p1 [16]uint64 // padding 48 51 s * semaphore.Weighted 49 52 d unsafe.Pointer … … 51 54 ttid int 52 55 id int 56 _p2 [16]uint64 // padding 53 57 } 54 58 55 59 func NewCtx( data * MyData, id int ) (MyCtx) { 56 r := MyCtx{ semaphore.NewWeighted(1), unsafe.Pointer(data), context.Background(), syscall.Gettid(), id}60 r := MyCtx{[16]uint64{0},semaphore.NewWeighted(1), unsafe.Pointer(data), context.Background(), syscall.Gettid(), id,[16]uint64{0}} 57 61 r.s.Acquire(context.Background(), 1) 58 62 return r … … 71 75 // May exchanges data 72 76 type Spot struct { 77 _p1 [16]uint64 // padding 73 78 ptr uintptr // atomic variable use fo MES 74 79 id int // id for debugging 80 _p2 [16]uint64 // padding 75 81 } 76 82 … … 215 221 func main() { 216 222 // Benchmark specific command line arguments 217 work_sizeOpt := flag.Uint64("w", 2 , " Number of words (uint64) per threads")218 countOpt := flag.Uint64("c", 2 , "Number of words (uint64) to touch")223 work_sizeOpt := flag.Uint64("w", 2 , "Size of the array for each threads, in words (64bit)") 224 countOpt := flag.Uint64("c", 2 , "Number of words to touch when working (random pick, cells can be picked more than once)") 219 225 shareOpt := flag.Bool ("s", false, "Pass the work data to the next thread when blocking") 220 226 … … 239 245 channels := make([]Spot, nthreads - nprocs) // Number of spots 240 246 for i := range channels { 241 channels[i] = Spot{ uintptr(0), i} // init spots247 channels[i] = Spot{[16]uint64{0},uintptr(0), i,[16]uint64{0}} // init spots 242 248 } 243 249 … … 266 272 267 273 // Join and accumulate results 268 global_result:= NewResult()274 results := NewResult() 269 275 for i := 0; i < nthreads; i++ { 270 276 r := <- result 271 global_result.count += r.count272 global_result.gmigs += r.gmigs273 global_result.dmigs += r.dmigs277 results.count += r.count 278 results.gmigs += r.gmigs 279 results.dmigs += r.dmigs 274 280 } 275 281 … … 280 286 p.Printf("Number of threads : %d\n", nthreads); 281 287 p.Printf("Work size (64bit words): %d\n", size); 282 p.Printf("Total Operations(ops) : %15d\n", global_result.count)283 p.Printf("Total G Migrations : %15d\n", global_result.gmigs)284 p.Printf("Total D Migrations : %15d\n", global_result.dmigs)285 p.Printf("Ops per second : %18.2f\n", float64( global_result.count) / delta.Seconds())286 p.Printf("ns per ops : %18.2f\n", float64(delta.Nanoseconds()) / float64( global_result.count))287 p.Printf("Ops per threads : %15d\n", global_result.count / uint64(nthreads))288 p.Printf("Ops per procs : %15d\n", global_result.count / uint64(nprocs))289 p.Printf("Ops/sec/procs : %18.2f\n", (float64( global_result.count) / float64(nprocs)) / delta.Seconds())290 p.Printf("ns per ops/procs : %18.2f\n", float64(delta.Nanoseconds()) / (float64( global_result.count) / float64(nprocs)))291 } 288 p.Printf("Total Operations(ops) : %15d\n", results.count) 289 p.Printf("Total G Migrations : %15d\n", results.gmigs) 290 p.Printf("Total D Migrations : %15d\n", results.dmigs) 291 p.Printf("Ops per second : %18.2f\n", float64(results.count) / delta.Seconds()) 292 p.Printf("ns per ops : %18.2f\n", float64(delta.Nanoseconds()) / float64(results.count)) 293 p.Printf("Ops per threads : %15d\n", results.count / uint64(nthreads)) 294 p.Printf("Ops per procs : %15d\n", results.count / uint64(nprocs)) 295 p.Printf("Ops/sec/procs : %18.2f\n", (float64(results.count) / float64(nprocs)) / delta.Seconds()) 296 p.Printf("ns per ops/procs : %18.2f\n", float64(delta.Nanoseconds()) / (float64(results.count) / float64(nprocs))) 297 } -
configure.ac
r0285efe rfe97de26 295 295 # Some of our makefile don't need to be distributed 296 296 AM_CONDITIONAL([CFORALL_DISTRIBUTE], [test -e $TOP_SRCDIR/autogen.sh]) 297 AM_COND_IF([CFORALL_DISTRIBUTE], 298 [AC_CONFIG_FILES([297 AM_COND_IF([CFORALL_DISTRIBUTE], [ 298 AC_CONFIG_FILES([ 299 299 longrun_tests/Makefile 300 300 benchmark/Makefile … … 302 302 tools/Makefile 303 303 tools/prettyprinter/Makefile 304 ])]) 304 ]) 305 306 AC_OUTPUT(benchmark/Cargo.toml) 307 ]) 305 308 306 309 AC_CONFIG_LINKS([tests/test.py:tests/test.py]) -
libcfa/src/parseargs.cfa
r0285efe rfe97de26 185 185 } 186 186 187 bool parse_truefalse(const char * arg, bool & value) { 188 if(strcmp(arg, "true") == 0) { 189 value = true; 190 return true; 191 } 192 193 if(strcmp(arg, "false") == 0) { 194 value = false; 195 return true; 196 } 197 198 return false; 199 } 200 187 201 bool parse_settrue (const char *, bool & value ) { 188 202 value = true; -
libcfa/src/parseargs.hfa
r0285efe rfe97de26 37 37 void print_args_usage(int argc, char * argv[], cfa_option options[], size_t opt_count, const char * usage, bool error) __attribute__ ((noreturn)); 38 38 39 bool parse_yesno (const char *, bool & ); 40 bool parse_settrue (const char *, bool & ); 41 bool parse_setfalse(const char *, bool & ); 39 bool parse_yesno (const char *, bool & ); 40 bool parse_truefalse(const char *, bool & ); 41 bool parse_settrue (const char *, bool & ); 42 bool parse_setfalse (const char *, bool & ); 42 43 43 44 bool parse(const char *, const char * & );
Note: See TracChangeset
for help on using the changeset viewer.