]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
This one reliably runs 5 workers. Checking in before subsequent cleanups and debug...
authorstephan <stephan@noemail.net>
Fri, 6 Mar 2026 17:10:28 +0000 (17:10 +0000)
committerstephan <stephan@noemail.net>
Fri, 6 Mar 2026 17:10:28 +0000 (17:10 +0000)
FossilOrigin-Name: ba81d95febc5fd0f9bbb2685fef5b1b10f9991751f2bdfafba80c15877af1cef

ext/wasm/api/sqlite3-opfs-async-proxy.c-pp.js
manifest
manifest.uuid

index 89b1339a9ee3b235c29912438b02493688e5eee0..e2b48bff575c579384248a439f37557c366e2270 100644 (file)
@@ -629,17 +629,18 @@ const installAsyncProxy = function(){
                 && requestedMode === 'shared') ) {
           storeAndNotify(whichOp, 0);
           existing.mode = requestedMode/* ??? */;
-          fh.lockType = lockType;
+          fh.xLock = lockType;
           return 0 /* Already held at required or higher level */;
         }
         /*
           Upgrade path: we must release shared and acquire exclusive.
           This transition is NOT atomic in Web Locks API.
         */
-        if( 0 ){
+        if( 1 ){
           /* Except that it _effectively_ is atomic if we don't call
              closeSyncHandle(fh), as no other worker can lock that
-             until we let it go. */
+             until we let it go. But we can't do that without leading
+             to a deadly embrace, so... */
           await closeSyncHandle(fh);
         }
         existing.resolveRelease();
@@ -647,101 +648,77 @@ const installAsyncProxy = function(){
       }
 
       const oldLockType = fh.xLock;
-      let didNotify = false;
       return new Promise((resolveWaitLoop) => {
         //error("xLock() initial promise entered...");
         navigator.locks.request(lockName, { mode: requestedMode }, async (lock) => {
           //error("xLock() Web Lock entered.", fh);
-          fh.xLock = lockType;
+          fh.xLock = lockType/*must be set before getSyncHandle() is called*/;
           __implicitLocks.delete(fid);
-          if( 1 ){
+          let rc = 0;
+          try{
             /* Make ONE attempt to get the handle, but with a
-               higher-than-default retry-wait time. */
-            await getSyncHandle(fh, 'xLock', 1000, 5);
-          }else{
-            /* Try to get a lock until either we get one or trying to
-               results in a "not found" error (see getSyncHandle() docs). */
-            while( !fh.syncHandle ){
-              try{
-                await getSyncHandle(fh, 'xLock', 1000, 3);
-              }catch(e){
-                const rc = GetSyncHandleError.convertRc(e, 0);
-                if( rc === state.sq3Codes.SQLITE_CANTOPEN ){
-                  /* File was deleted - see getSyncHandle() */
-                  throw e;
-                }
-                error("xLock() still waiting to unlock SyncAccessHandle",fh);
-              }
-            }
+               higher-than-default retry-wait. */
+            await getSyncHandle(fh, 'xLock', 317, 5);
+          }catch(e){
+            fh.xLock = oldLockType;
+            state.s11n.storeException(1, e);
+            rc = GetSyncHandleError.convertRc(e, state.sq3Codes.SQLITE_BUSY);
           }
-          error("xLock() SAH acquired.", fh);
-          const releasePromise = new Promise((resolveRelease) => {
-            __activeWebLocks[fid] = { mode: requestedMode, resolveRelease };
-          });
-          didNotify = true;
-          storeAndNotify(whichOp, 0) /* Unblock the C side */;
+          const releasePromise = rc
+                ? undefined
+                : new Promise((resolveRelease) => {
+                  __activeWebLocks[fid] = { mode: requestedMode, resolveRelease };
+                });
+          storeAndNotify(whichOp, rc) /* Unblock the C side */;
           resolveWaitLoop(0) /* Unblock waitLoop() */;
           await releasePromise; // Hold the lock until xUnlock
-        }).catch(e=>{
-          /**
-             We have(?) a potential deadlock situation: if the above
-             throws, we can't just blindly storeAndNotify() here to
-             unlock the C side, as it might interfere with an
-             unrelated operation. The `didNotify` check here assumes
-             that any exception which can be thrown will happen before
-             the above `didNotify=true`.  e.g. getSyncHandle() can
-             throw. Apropos: we probably need to be able to configure
-             the async side with busy timeout values, and try until
-             that limit is reached, or tell it to wait indefinitely.
-
-             Because waitLoop() is `await`ing on this Promise, we can
-             be sure that the following storeAndNotify() is not
-             crossing wires with a different operation.
-          */
-          fh.xLock = oldLockType;
-          error("Exception acquiring Web Lock", e);
-          if( !didNotify ){
-            state.s11n.storeException(1, e);
-            const rc = GetSyncHandleError.convertRc(e, state.sq3Codes.SQLITE_IOERR_LOCK);
-            storeAndNotify(whichOp, rc);
-          }
-          throw e /* what else can we do? */;
-        })
+        });
       });
     };
 
+    const wlCloseHandle = async(fh)=>{
+      let rc = 0;
+      try{
+        await closeSyncHandle(fh);
+      }catch(e){
+        state.s11n.storeException(1,e);
+        rc = state.sq3Codes.SQLITE_IOERR_UNLOCK;
+      }
+      return rc;
+    };
+
     vfsAsyncImpls.xUnlock = async function(fid/*sqlite3_file pointer*/,
                                            lockType/*SQLITE_LOCK_...*/){
       const fh = __openFiles[fid];
       const existing = __activeWebLocks[fid];
       if( !existing ){
-        await closeSyncHandle(fh);
-        storeAndNotify('xUnlock', 0);
-        return 0;
+        const rc = await wlCloseHandle(fh);
+        storeAndNotify('xUnlock', rc);
+        return rc;
       }
       error("xUnlock()",fid, lockType, fh);
       let rc = 0;
       if( lockType === state.sq3Codes.SQLITE_LOCK_NONE ){
         /* SQLite usually unlocks all the way to NONE */
+        rc = await wlCloseHandle(fh);
         existing.resolveRelease();
         delete __activeWebLocks[fid];
-        try {await closeSyncHandle(fh)}
-        catch(e){
-          state.s11n.storeException(1,e);
-          rc = state.sq3Codes.SQLITE_IOERR_UNLOCK;
-        }
+        fh.xLock = lockType;
       }else if( lockType === state.sq3Codes.SQLITE_LOCK_SHARED
                 && existing.mode === 'exclusive' ){
         /* downgrade Exclusive -> Shared */
-        existing.resolveRelease();
-        delete __activeWebLocks[fid];
-        return vfsAsyncImpls.xLock(fid, lockType, true);
+        rc = await wlCloseHandle(fh);
+        if( 0===rc ){
+          fh.xLock = lockType;
+          existing.resolveRelease();
+          delete __activeWebLocks[fid];
+          return vfsAsyncImpls.xLock(fid, lockType, true);
+        }
       }else{
         /* ??? */
         error("xUnlock() unhandled condition", fh);
       }
       storeAndNotify('xUnlock', rc);
-      if( 0===rc ) fh.lockType = lockType;
       return 0;
     }
 
index b868981442ce49d370ce7d67e13162c1f911c85a..d85a70c59103416f69989a720a4f034d6182a1d0 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Correct\san\sinternal\sdoc\sfalsehood.
-D 2026-03-06T16:15:32.423
+C This\sone\sreliably\sruns\s5\sworkers.\sChecking\sin\sbefore\ssubsequent\scleanups\sand\sdebug\soutput\sremoval\sbreak\sit.
+D 2026-03-06T17:10:28.455
 F .fossil-settings/binary-glob 61195414528fb3ea9693577e1980230d78a1f8b0a54c78cf1b9b24d0a409ed6a x
 F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1
 F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea
@@ -594,7 +594,7 @@ F ext/wasm/api/sqlite3-api-oo1.c-pp.js 45454631265d9ce82685f1a64e1650ee19c8e121c
 F ext/wasm/api/sqlite3-api-prologue.js 98fedc159c9239b226d19567d7172300dee5ffce176e5fa2f62dd1f17d088385
 F ext/wasm/api/sqlite3-api-worker1.c-pp.js 1041dd645e8e821c082b628cd8d9acf70c667430f9d45167569633ffc7567938
 F ext/wasm/api/sqlite3-license-version-header.js 98d90255a12d02214db634e041c8e7f2f133d9361a8ebf000ba9c9af4c6761cc
-F ext/wasm/api/sqlite3-opfs-async-proxy.c-pp.js fd41c554fa0f25770841f4973eeaeda78db5fd9c24b2cbe7c62ce43bfae89840
+F ext/wasm/api/sqlite3-opfs-async-proxy.c-pp.js b3235922c15ee9b92a5424e34580bf16cb971adf23559c9e7119d563b8da2fe9
 F ext/wasm/api/sqlite3-vfs-helper.c-pp.js 3f828cc66758acb40e9c5b4dcfd87fd478a14c8fb7f0630264e6c7fa0e57515d
 F ext/wasm/api/sqlite3-vfs-kvvfs.c-pp.js a61dd2b4d919d2d5d83c5c7e49b89ecbff2525ff81419f6a6dbaecaf3819c490
 F ext/wasm/api/sqlite3-vfs-opfs-sahpool.c-pp.js 1575ea6bbcf2da1e6df6892c17521a0c1c1c199a672e9090176ea0b88de48bd9
@@ -2191,8 +2191,8 @@ F tool/warnings-clang.sh bbf6a1e685e534c92ec2bfba5b1745f34fb6f0bc2a362850723a9ee
 F tool/warnings.sh d924598cf2f55a4ecbc2aeb055c10bd5f48114793e7ba25f9585435da29e7e98
 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f
 F tool/winmain.c 00c8fb88e365c9017db14c73d3c78af62194d9644feaf60e220ab0f411f3604c
-P d4e8583e2e80665adfe4e814adb6c219936af1dcac4105795045cb1a7b1e4864
-R 88b88687281dda4abda2f12f0e145b46
+P 53aa080e357d7a2ffeab68a3584fda43d51ecef3dc8a1d46dd32392ae4f9740c
+R fcfb0bfb06d58bd7f0d57908763a15cf
 U stephan
-Z de5c6fc88fd27ce91eec8f28640e7eb1
+Z 62318d6c194878a798365e388df66b6b
 # Remove this line to create a well-formed Fossil manifest.
index 0a3bf6f088ac46e3da22eb72e07667e21e52a022..fc702daf4565456154fe452e8fb5a0e80c43e9dc 100644 (file)
@@ -1 +1 @@
-53aa080e357d7a2ffeab68a3584fda43d51ecef3dc8a1d46dd32392ae4f9740c
+ba81d95febc5fd0f9bbb2685fef5b1b10f9991751f2bdfafba80c15877af1cef