diff options
author | Aldy Hernandez <aldyh@redhat.com> | 2011-10-10 18:32:07 +0000 |
---|---|---|
committer | Aldy Hernandez <aldyh@gcc.gnu.org> | 2011-10-10 18:32:07 +0000 |
commit | 13d563f0742f043e94666965709462d1de456048 (patch) | |
tree | fa03215149018aa1220886091f1712884567ee0d | |
parent | fa6963330dc6edccda21ca2af39bc40f9fda3094 (diff) | |
download | gcc-13d563f0742f043e94666965709462d1de456048.zip gcc-13d563f0742f043e94666965709462d1de456048.tar.gz gcc-13d563f0742f043e94666965709462d1de456048.tar.bz2 |
simulate-thread.gdb: Call wrappers for *other_threads() and *final_verify().
* gcc.dg/simulate-thread/simulate-thread.gdb: Call
wrappers for *other_threads() and *final_verify().
* gcc.dg/simulate-thread/simulate-thread.h
(simulate_thread_wrapper_other_threads): New.
(simulate_thread_wrapper_final_verify): New.
Co-Authored-By: Andrew MacLeod <amacleod@redhat.com>
From-SVN: r179768
-rw-r--r-- | gcc/testsuite/ChangeLog | 9 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/simulate-thread/simulate-thread.gdb | 4 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/simulate-thread/simulate-thread.h | 104 |
3 files changed, 115 insertions, 2 deletions
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 7d5a1f4..faa52ac 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,12 @@ +2011-10-10 Aldy Hernandez <aldyh@redhat.com> + Andrew Macleod <amacleod@redhat.com> + + * gcc.dg/simulate-thread/simulate-thread.gdb: Call + wrappers for *other_threads() and *final_verify(). + * gcc.dg/simulate-thread/simulate-thread.h + (simulate_thread_wrapper_other_threads): New. + (simulate_thread_wrapper_final_verify): New. + 2011-10-10 Uros Bizjak <ubizjak@gmail.com> * lib/gcc-gdb-test.exp (gdb-test): Delete $cmd_file before return. diff --git a/gcc/testsuite/gcc.dg/simulate-thread/simulate-thread.gdb b/gcc/testsuite/gcc.dg/simulate-thread/simulate-thread.gdb index 004909f..c7bac73 100644 --- a/gcc/testsuite/gcc.dg/simulate-thread/simulate-thread.gdb +++ b/gcc/testsuite/gcc.dg/simulate-thread/simulate-thread.gdb @@ -5,13 +5,13 @@ run set $ret = 0 while (simulate_thread_fini != 1) && (! $ret) - call simulate_thread_other_threads() + call simulate_thread_wrapper_other_threads() stepi set $ret |= simulate_thread_step_verify() end if (! $ret) - set $ret |= simulate_thread_final_verify() + set $ret |= simulate_thread_wrapper_final_verify() end continue quit $ret diff --git a/gcc/testsuite/gcc.dg/simulate-thread/simulate-thread.h b/gcc/testsuite/gcc.dg/simulate-thread/simulate-thread.h index 8dabfa2..9e2361f 100644 --- a/gcc/testsuite/gcc.dg/simulate-thread/simulate-thread.h +++ b/gcc/testsuite/gcc.dg/simulate-thread/simulate-thread.h @@ -5,3 +5,107 @@ simulate_thread_done () { simulate_thread_fini = 1; } + +/* A hostile thread is one which changes a memory location so quickly + that another thread may never see the same value again. This is + simulated when simulate_thread_other_thread() is defined to modify + a memory location every cycle. + + A process implementing a dependency on this value can run into + difficulties with such a hostile thread. For instance, + implementing an add with a compare_and_swap loop goes something + like: + + expected = *mem; + loop: + new = expected += value; + if (!succeed (expected = compare_and_swap (mem, expected, new))) + goto loop; + + If the content of 'mem' are changed every cycle by + simulate_thread_other_thread () this will become an infinite loop + since the value *mem will never be 'expected' by the time the + compare_and_swap is executed. + + HOSTILE_THREAD_THRESHOLD defines the number of intructions which a + program will execute before triggering the hostile thread + pause. The pause will last for HOSTILE_THREAD_PAUSE instructions, + and then the counter will reset and begin again. During the pause + period, simulate_thread_other_thread will not be called. + + This provides a chance for forward progress to be made and the + infinite loop to be avoided. + + If the testcase defines HOSTILE_PAUSE_ERROR, then it will be + considered an RUNTIME FAILURE if the hostile pause is triggered. + This will allow to test for guaranteed forward progress routines. + + If the default values for HOSTILE_THREAD_THRESHOLD or + HOSTILE_THREAD_PAUSE are insufficient, then the testcase may + override these by defining the values before including this file. + + Most testcase are intended to run for very short periods of time, + so these defaults are considered to be high enough to not trigger + on a typical case, but not drag the test time out too much if a + hostile condition is interferring. */ + + +/* Define the threshold to start pausing the hostile thread. */ +#if !defined (HOSTILE_THREAD_THRESHOLD) +#define HOSTILE_THREAD_THRESHOLD 500 +#endif + +/* Define the length of pause in cycles for the hostile thread to pause to + allow forward progress to be made. */ +#if !defined (HOSTILE_THREAD_PAUSE) +#define HOSTILE_THREAD_PAUSE 20 +#endif + +void simulate_thread_other_threads (void); +int simulate_thread_final_verify (void); + +static int simulate_thread_hostile_pause = 0; + +/* This function wraps simulate_thread_other_threads an monitors for + an infinite loop. If the threshold value HOSTILE_THREAD_THRESHOLD + is reached, the other_thread process is paused for + HOSTILE_THREAD_PAUSE cycles before resuming, and the counters start + again. */ +void +simulate_thread_wrapper_other_threads() +{ + static int count = 0; + static int pause = 0; + + if (++count >= HOSTILE_THREAD_THRESHOLD) + { + if (!simulate_thread_hostile_pause) + simulate_thread_hostile_pause = 1; + + /* Count cycles before calling the hostile thread again. */ + if (pause++ < HOSTILE_THREAD_PAUSE) + return; + + /* Reset the pause counter, as well as the thread counter. */ + pause = 0; + count = 0; + } + simulate_thread_other_threads (); +} + + +/* If the test case defines HOSTILE_PAUSE_ERROR, then the test case + will fail execution if it had a hostile pause. */ +int +simulate_thread_wrapper_final_verify () +{ + int ret = simulate_thread_final_verify (); +#if defined (HOSTILE_PAUSE_ERROR) + if (simulate_thread_hostile_pause) + { + printf ("FAIL: Forward progress made only by pausing hostile thread\n"); + ret = ret | 1; /* 0 indicates proper comnpletion. */ + } +#endif + return ret; +} |