Better fix for 295590
(problem reported in bug 307082, comment 8).
Solution applied is similar to what is in 307082 patch
(i.e. do not destroy the internal helgrind var if nWaiters > 0).
But also do not remove it from the FM.

+ add a test case (re-using the drd test case)



git-svn-id: svn://svn.valgrind.org/valgrind/trunk@13329 a5019735-40e9-0310-863c-91ae7b9d1cf9
diff --git a/helgrind/hg_main.c b/helgrind/hg_main.c
index 5c109af..2da58b0 100644
--- a/helgrind/hg_main.c
+++ b/helgrind/hg_main.c
@@ -2156,7 +2156,7 @@
    tl_assert(thr); /* cannot fail - Thread* must already exist */
 
    map_cond_to_CVInfo_INIT();
-   if (VG_(delFromFM)( map_cond_to_CVInfo, &keyW, &valW, (UWord)cond )) {
+   if (VG_(lookupFM)( map_cond_to_CVInfo, &keyW, &valW, (UWord)cond )) {
       CVInfo* cvi = (CVInfo*)valW;
       tl_assert(keyW == (UWord)cond);
       tl_assert(cvi);
@@ -2165,7 +2165,12 @@
          HG_(record_error_Misc)(thr,
                                 "pthread_cond_destroy:"
                                 " destruction of condition variable being waited upon");
+         /* Destroying a cond var being waited upon outcome is EBUSY and
+            variable is not destroyed. */
+         return;
       }
+      if (!VG_(delFromFM)( map_cond_to_CVInfo, &keyW, &valW, (UWord)cond ))
+         tl_assert(0); // cond var found above, and not here ???
       libhb_so_dealloc(cvi->so);
       cvi->mx_ga = 0;
       HG_(free)(cvi);
diff --git a/helgrind/tests/Makefile.am b/helgrind/tests/Makefile.am
index 8e090f3..68da5df 100644
--- a/helgrind/tests/Makefile.am
+++ b/helgrind/tests/Makefile.am
@@ -42,6 +42,7 @@
 	pth_barrier3.vgtest pth_barrier3.stdout.exp pth_barrier3.stderr.exp \
 	pth_destroy_cond.vgtest \
 		pth_destroy_cond.stdout.exp pth_destroy_cond.stderr.exp \
+	pth_cond_destroy_busy.vgtest pth_cond_destroy_busy.stderr.exp \
 	pth_spinlock.vgtest pth_spinlock.stdout.exp pth_spinlock.stderr.exp \
 	rwlock_race.vgtest rwlock_race.stdout.exp rwlock_race.stderr.exp \
 	rwlock_test.vgtest rwlock_test.stdout.exp rwlock_test.stderr.exp \
diff --git a/helgrind/tests/pth_cond_destroy_busy.stderr.exp b/helgrind/tests/pth_cond_destroy_busy.stderr.exp
new file mode 100644
index 0000000..6ffa3c2
--- /dev/null
+++ b/helgrind/tests/pth_cond_destroy_busy.stderr.exp
@@ -0,0 +1,24 @@
+
+---Thread-Announcement------------------------------------------
+
+Thread #x is the program's root thread
+
+----------------------------------------------------------------
+
+Thread #x: pthread_cond_destroy: destruction of condition variable being waited upon
+   at 0x........: pthread_cond_destroy_WRK (hg_intercepts.c:...)
+   by 0x........: pthread_cond_destroy@* (hg_intercepts.c:...)
+   by 0x........: main (pth_cond_destroy_busy.c:52)
+
+----------------------------------------------------------------
+
+Thread #x's call to pthread_cond_destroy failed
+   with error code 16 (EBUSY: Device or resource busy)
+   at 0x........: pthread_cond_destroy_WRK (hg_intercepts.c:...)
+   by 0x........: pthread_cond_destroy@* (hg_intercepts.c:...)
+   by 0x........: main (pth_cond_destroy_busy.c:52)
+
+First pthread_cond_destroy() call returned EBUSY.
+Second pthread_cond_destroy() call returned success.
+
+ERROR SUMMARY: 2 errors from 2 contexts (suppressed: 0 from 0)
diff --git a/helgrind/tests/pth_cond_destroy_busy.vgtest b/helgrind/tests/pth_cond_destroy_busy.vgtest
new file mode 100644
index 0000000..c2e380e
--- /dev/null
+++ b/helgrind/tests/pth_cond_destroy_busy.vgtest
@@ -0,0 +1 @@
+prog: ../../drd/tests/pth_cond_destroy_busy
diff --git a/helgrind/tests/pth_destroy_cond.stderr.exp b/helgrind/tests/pth_destroy_cond.stderr.exp
index 4f9eeb7..783582c 100644
--- a/helgrind/tests/pth_destroy_cond.stderr.exp
+++ b/helgrind/tests/pth_destroy_cond.stderr.exp
@@ -15,14 +15,3 @@
    by 0x........: mythread_wrapper (hg_intercepts.c:...)
    ...
 
----Thread-Announcement------------------------------------------
-
-Thread #x is the program's root thread
-
-----------------------------------------------------------------
-
-Thread #x: condition variable has been destroyed while being waited upon
-   at 0x........: pthread_cond_wait_WRK (hg_intercepts.c:...)
-   by 0x........: pthread_cond_wait@* (hg_intercepts.c:...)
-   by 0x........: main (pth_destroy_cond.c:31)
-
diff --git a/memcheck/tests/x86/sse2_memory.stdout.exp b/memcheck/tests/x86/sse2_memory.stdout.exp
index 186f6e9..f0110e3 100644
--- a/memcheck/tests/x86/sse2_memory.stdout.exp
+++ b/memcheck/tests/x86/sse2_memory.stdout.exp
@@ -814,7 +814,7 @@
 r      psrld 794527a66e3323fcc2b189733486eab1 31f41b235bcc2cc0705ac0a48b31bf8e 00000000000000000000000000000000
 r      psrld f610be5d9fa2148e5bdb7c092091b268 9f7c01b140ccb49e9293f3b60914f44b 00000000000000000000000000000000
 m      psrld 51b82d7c05d86f1e1a36bdd4bc90f39e 501b27500e0687b4492e463c9156af4f 00000000000000000000000000000000
-m      psrld 86f91770e7c2d5fbed2f5592fd0fa12a 85e8f106018a94df9afd0ae0d9d18826 00000000000000000000000000000000
+m      psrl` 86f91770e7c2d5fbed2f5592fd0fa12a 85e8f106018a94df9afd0ae0d9d18826 00000000000000000000000000000000
 m      psrld 65557fdd943c286862adf1a8cd656f62 efd90de61c38b45cbb7947aeaedc478c 00000000000000000000000000000000
 m      psrld ea4ff449507381d68603b1ed808c0706 4d31cd3663fabf5a77b6dd3c243154fd 00000000000000000000000000000000
 m      psrld 714a681bc16f5992c5621717cd5f70b4 ba12e01c3a9ceee7fca60d00b06a78da 00000000000000000000000000000000