Tencent/tinker · error · IOException

Tinker Exception:FileLockHelper lock file failed: {}

Error message

Tinker Exception:FileLockHelper lock file failed: {}

What it means

ShareFileLockHelper's constructor tries to acquire an exclusive FileLock on the lock file, retrying with Thread.sleep(LOCK_WAIT_EACH_TIME) up to a bounded number of attempts; the saveException from each try is kept. When all attempts fail it throws IOException('Tinker Exception:FileLockHelper lock file failed: <path>', saveException), exposing the last underlying failure (often OverlappingFileLockException, ClosedChannelException, or EMFILE too many open files).

Source

Thrown at tinker-android/tinker-android-loader-no-op/src/main/java/com/tencent/tinker/loader/shareutil/ShareFileLockHelper.java:66

                if (isGetLockSuccess) {
                    break;
                }

            } catch (Exception e) {
                saveException = e;
                ShareTinkerLog.e(TAG, "getInfoLock Thread failed time:" + LOCK_WAIT_EACH_TIME);
            }

            //it can just sleep 0, afraid of cpu scheduling
            try {
                Thread.sleep(LOCK_WAIT_EACH_TIME);
            } catch (Exception ignore) {
                ShareTinkerLog.e(TAG, "getInfoLock Thread sleep exception", ignore);
            }
        }

        if (localFileLock == null) {
            throw new IOException("Tinker Exception:FileLockHelper lock file failed: " + lockFile.getAbsolutePath(), saveException);
        }
        fileLock = localFileLock;
    }

    public static ShareFileLockHelper getFileLock(File lockFile) throws IOException {
        return new ShareFileLockHelper(lockFile);
    }

    @Override
    public void close() throws IOException {
        try {
            if (fileLock != null) {
                fileLock.release();
            }
        } finally {
            if (outputStream != null) {
                outputStream.close();
            }

View on GitHub (pinned to 1b7ea02c23)

Solutions

  1. Centralize patch apply/load operations in one process (e.g. only the main process or a dedicated :patch process) to remove lock contention.
  2. Close every ShareFileLockHelper via try-with-resources/finally; leaked helpers hold locks and exhaust FDs.
  3. Inspect the suppressed saveException cause: OverlappingFileLockException means same-JVM contention; Too many open files means an FD leak elsewhere in the app.
  4. If a stale lock survives a crashed process, cleanPatch() or app restart releases it (FileLock releases on process death).

Example fix

// before (leaks lock, later callers fail)
ShareFileLockHelper fileLock = ShareFileLockHelper.getFileLock(lockFile);
writeInfo(info);
// lock never closed

// after
try (ShareFileLockHelper fileLock = ShareFileLockHelper.getFileLock(lockFile)) {
    writeInfo(info);
}
Defensive patterns

Strategy: fallback

Validate before calling

public static void withLock(File lockFile, Callable<Void> body) throws IOException {
    try (ShareFileLockHelper lock = ShareFileLockHelper.getFileLock(lockFile)) {
        body.call();
    } // always released
}

Try / catch

try (ShareFileLockHelper lock = ShareFileLockHelper.getFileLock(f)) {
    doWork();
} catch (IOException e) {
    if (e.getMessage() != null && e.getMessage().contains("lock file failed")) {
        // contention or FD exhaustion: back off and retry later
    }
}

Prevention

When it happens

Trigger: getFileLock(lockFile) called while another thread/process already holds the lock for longer than the total retry window; the lock file was deleted while held; the process ran out of file descriptors so the channel could not be opened; channel closed concurrently.

Common situations: Multiple processes (main + :patch + push) applying or loading patches simultaneously; a previous crash leaving the lock held; heavy FD usage leaking channels; tinker info file locking contended during patch apply on slow devices.

Related errors


AI-assisted analysis of Tencent/tinker@1b7ea02c23 (2026-08-14). Data as JSON: /api/errors/acad970982df8026. Report an issue: GitHub.