diff options
author | Bjoern Brandenburg <bbb@mpi-sws.org> | 2017-07-28 15:44:24 -0400 |
---|---|---|
committer | Bjoern Brandenburg <bbb@mpi-sws.org> | 2017-07-28 15:44:24 -0400 |
commit | e9d67470da50e5428ab4d359f2beedf54a28f9aa (patch) | |
tree | aa69a8329bfc27c42c58b80488db1d334f1ac263 | |
parent | 053b34b5a4e661f9d10aca169c7e54cdc1b2328a (diff) |
rtspin: add -A option (read inter-arrival times from CSV)
Similar to the -C option, this option allows specifying pre-determined
inter-arrival times.
-rw-r--r-- | bin/rtspin.c | 77 |
1 files changed, 62 insertions, 15 deletions
diff --git a/bin/rtspin.c b/bin/rtspin.c index ccea300..68f721d 100644 --- a/bin/rtspin.c +++ b/bin/rtspin.c | |||
@@ -59,6 +59,9 @@ const char *usage_msg = | |||
59 | " -C FILE[:COLUMN] load per-job execution times from CSV file;\n" | 59 | " -C FILE[:COLUMN] load per-job execution times from CSV file;\n" |
60 | " if COLUMN is given, it specifies the column to read\n" | 60 | " if COLUMN is given, it specifies the column to read\n" |
61 | " per-job execution times from (default: 1)\n" | 61 | " per-job execution times from (default: 1)\n" |
62 | " -A FILE[:COLUMN] load sporadic inter-arrival times from CSV file (implies -T);\n" | ||
63 | " if COLUMN is given, it specifies the column to read\n" | ||
64 | " inter-arrival times from (default: 1)\n" | ||
62 | "\n" | 65 | "\n" |
63 | " -S[FILE] read from FILE to trigger sporadic job releases\n" | 66 | " -S[FILE] read from FILE to trigger sporadic job releases\n" |
64 | " default w/o -S: periodic job releases\n" | 67 | " default w/o -S: periodic job releases\n" |
@@ -260,7 +263,21 @@ static void job(double exec_time, double program_end, int lock_od, double cs_len | |||
260 | } | 263 | } |
261 | } | 264 | } |
262 | 265 | ||
263 | #define OPTSTR "p:c:wlveo:s:m:q:r:X:L:Q:iRu:U:Bhd:C:S::O::TD:E:" | 266 | static lt_t choose_inter_arrival_time_ns( |
267 | double* arrival_times, int num_arrivals, int cur_job, | ||
268 | double range_min, double range_max) | ||
269 | { | ||
270 | double iat_ms; | ||
271 | |||
272 | if (arrival_times) | ||
273 | iat_ms = arrival_times[cur_job % num_arrivals]; | ||
274 | else | ||
275 | iat_ms = range_min + drand48() * (range_max - range_min); | ||
276 | |||
277 | return ms2ns(iat_ms); | ||
278 | } | ||
279 | |||
280 | #define OPTSTR "p:c:wlveo:s:m:q:r:X:L:Q:iRu:U:Bhd:C:S::O::TD:E:A:" | ||
264 | 281 | ||
265 | int main(int argc, char** argv) | 282 | int main(int argc, char** argv) |
266 | { | 283 | { |
@@ -282,14 +299,22 @@ int main(int argc, char** argv) | |||
282 | int wait = 0; | 299 | int wait = 0; |
283 | int test_loop = 0; | 300 | int test_loop = 0; |
284 | int background_loop = 0; | 301 | int background_loop = 0; |
285 | int column = 1; | 302 | |
303 | int cost_column = 1; | ||
286 | const char *cost_csv_file = NULL; | 304 | const char *cost_csv_file = NULL; |
305 | int num_jobs = 0; | ||
306 | double *exec_times = NULL; | ||
307 | |||
308 | int arrival_column = 1; | ||
309 | const char *arrival_csv_file = NULL; | ||
310 | int num_arrival_times = 0; | ||
311 | double *arrival_times = NULL; | ||
312 | |||
287 | int want_enforcement = 0; | 313 | int want_enforcement = 0; |
288 | double duration = 0, start = 0; | 314 | double duration = 0, start = 0; |
289 | double *exec_times = NULL; | ||
290 | double scale = 0.95; | 315 | double scale = 0.95; |
291 | task_class_t class = RT_CLASS_HARD; | 316 | task_class_t class = RT_CLASS_HARD; |
292 | int cur_job = 0, num_jobs = 0; | 317 | int cur_job = 0; |
293 | struct rt_task param; | 318 | struct rt_task param; |
294 | 319 | ||
295 | char *after_colon; | 320 | char *after_colon; |
@@ -359,8 +384,18 @@ int main(int argc, char** argv) | |||
359 | after_colon = strsplit(':', optarg); | 384 | after_colon = strsplit(':', optarg); |
360 | cost_csv_file = optarg; | 385 | cost_csv_file = optarg; |
361 | if (after_colon) { | 386 | if (after_colon) { |
362 | column = want_non_negative_int(after_colon, "-C"); | 387 | cost_column = |
388 | want_non_negative_int(after_colon, "-C"); | ||
389 | } | ||
390 | break; | ||
391 | case 'A': | ||
392 | after_colon = strsplit(':', optarg); | ||
393 | arrival_csv_file = optarg; | ||
394 | if (after_colon) { | ||
395 | arrival_column = | ||
396 | want_non_negative_int(after_colon, "-A"); | ||
363 | } | 397 | } |
398 | linux_sleep = 1; | ||
364 | break; | 399 | break; |
365 | case 'S': | 400 | case 'S': |
366 | sporadic = 1; | 401 | sporadic = 1; |
@@ -517,7 +552,13 @@ int main(int argc, char** argv) | |||
517 | } | 552 | } |
518 | 553 | ||
519 | if (cost_csv_file) | 554 | if (cost_csv_file) |
520 | exec_times = csv_read_column(cost_csv_file, column, &num_jobs); | 555 | exec_times = csv_read_column(cost_csv_file, cost_column, |
556 | &num_jobs); | ||
557 | |||
558 | if (arrival_csv_file) | ||
559 | arrival_times = csv_read_column(arrival_csv_file, | ||
560 | arrival_column, &num_arrival_times); | ||
561 | |||
521 | 562 | ||
522 | if (argc - optind < 3 && cost_csv_file) | 563 | if (argc - optind < 3 && cost_csv_file) |
523 | /* If duration is not given explicitly, | 564 | /* If duration is not given explicitly, |
@@ -600,10 +641,8 @@ int main(int argc, char** argv) | |||
600 | start = wctime(); | 641 | start = wctime(); |
601 | } | 642 | } |
602 | 643 | ||
603 | if (cp) | 644 | |
604 | next_release = cp->release + period; | 645 | next_release = cp ? cp->release : litmus_clock(); |
605 | else | ||
606 | next_release = litmus_clock() + period; | ||
607 | 646 | ||
608 | /* default: periodic releases */ | 647 | /* default: periodic releases */ |
609 | if (!inter_arrival_min_ms) | 648 | if (!inter_arrival_min_ms) |
@@ -702,6 +741,17 @@ int main(int argc, char** argv) | |||
702 | /* Use vanilla Linux API. This looks to the | 741 | /* Use vanilla Linux API. This looks to the |
703 | * active LITMUS^RT plugin like a | 742 | * active LITMUS^RT plugin like a |
704 | * self-suspension. */ | 743 | * self-suspension. */ |
744 | |||
745 | inter_arrival_time = | ||
746 | choose_inter_arrival_time_ns( | ||
747 | arrival_times, | ||
748 | num_arrival_times, | ||
749 | cur_job, | ||
750 | inter_arrival_min_ms, | ||
751 | inter_arrival_max_ms); | ||
752 | |||
753 | next_release += inter_arrival_time; | ||
754 | |||
705 | if (verbose) | 755 | if (verbose) |
706 | fprintf(stderr, | 756 | fprintf(stderr, |
707 | "\tclock_nanosleep() until %" | 757 | "\tclock_nanosleep() until %" |
@@ -711,12 +761,9 @@ int main(int argc, char** argv) | |||
711 | ns2s((double) next_release), | 761 | ns2s((double) next_release), |
712 | (uint64_t) inter_arrival_time, | 762 | (uint64_t) inter_arrival_time, |
713 | ns2ms((double) inter_arrival_time)); | 763 | ns2ms((double) inter_arrival_time)); |
764 | |||
714 | lt_sleep_until(next_release); | 765 | lt_sleep_until(next_release); |
715 | inter_arrival_time = ms2ns( | 766 | |
716 | inter_arrival_min_ms + | ||
717 | drand48() * (inter_arrival_max_ms - | ||
718 | inter_arrival_min_ms)); | ||
719 | next_release += inter_arrival_time; | ||
720 | } else { | 767 | } else { |
721 | /* Use LITMUS^RT API: some plugins optimize | 768 | /* Use LITMUS^RT API: some plugins optimize |
722 | * this by not actually suspending the task. */ | 769 | * this by not actually suspending the task. */ |