Browse Source

* WebAssembly threads: fix race condition, which causes sometimes an abandoned
basic event to be reported as signalled. This should fix the test tbrtlevt.pp
sometimes failing.

Nikolay Nikolov 1 year ago
parent
commit
00e5289967
1 changed files with 32 additions and 6 deletions
  1. 32 6
      rtl/wasi/systhrd.inc

+ 32 - 6
rtl/wasi/systhrd.inc

@@ -835,8 +835,17 @@ begin
                 end
               else if fpc_wasm32_i32_atomic_rmw_cmpxchg_u(@P^.Signal,1,0)=1 then
                 begin
-                  result:=wrSignaled;
-                  exit;
+                  if fpc_wasm32_i32_atomic_load8_u(@P^.Destroying)<>0 then
+                    begin
+                      fpc_wasm32_i32_atomic_store(@P^.Signal,1);
+                      result:=wrAbandoned;
+                      exit;
+                    end
+                  else
+                    begin
+                      result:=wrSignaled;
+                      exit;
+                    end;
                 end
               else
                 ; { try waiting again (loop continues) }
@@ -899,8 +908,16 @@ begin
           end
         else if fpc_wasm32_i32_atomic_load(@P^.Signal)<>0 then
           begin
-            result:=wrSignaled;
-            exit;
+            if fpc_wasm32_i32_atomic_load8_u(@P^.Destroying)<>0 then
+              begin
+                result:=wrAbandoned;
+                exit;
+              end
+            else
+              begin
+                result:=wrSignaled;
+                exit;
+              end;
           end;
       until false;
     end
@@ -924,8 +941,17 @@ begin
           end
         else if fpc_wasm32_i32_atomic_rmw_cmpxchg_u(@P^.Signal,1,0)=1 then
           begin
-            result:=wrSignaled;
-            exit;
+            if fpc_wasm32_i32_atomic_load8_u(@P^.Destroying)<>0 then
+              begin
+                fpc_wasm32_i32_atomic_store(@P^.Signal,1);
+                result:=wrAbandoned;
+                exit;
+              end
+            else
+              begin
+                result:=wrSignaled;
+                exit;
+              end;
           end;
       until false;
     end;