invenia / invenia/ReadWriteLocks.jl

deadlock behavior: reader could not `unlock` when writer is waiting for the lock

Open
#16 0 comments 0 reactions 0 assignees View on GitHub
Dominant language
Julia
Stars
6
Forks
8
PR merge metrics
No merged PRs in 30d

Description

the scenario is,
1. reader take the read lock
2. writer comes in and would like to take the write lock, while it cant, since there is already reader here. thus writer has to wait for the condition, **without releasing the main lock**
3. reader now finish work, and want to return the read lock, but it cant, since the main lock is already taken by writer
4. hence the dead lock

starts at line 80

```julia
function lock!(write_lock::WriteLock)
rwlock = write_lock.rwlock
lock(rwlock.lock)

try
while rwlock.readers > 0 || rwlock.writer
wait(rwlock.condition)
end

rwlock.writer = true
finally
unlock(rwlock.lock)
end

return nothing
end
```

and here is the mre(or i'm using it wrong?)

```julia

include("ReadWriteLocks.jl")

using .ReadWriteLocks

function readerTask(rwLock)
rLock = read_lock(rwLock)
lock!(rLock)
try
println("$(current_task()): using read lock")
finally
unlock!(rLock)
end
end

function writerTask(rwLock)
wLock = write_lock(rwLock)
lock!(wLock)
try
println("$(current_task()): using write lock")
finally
unlock!(wLock)
end
end

function main()
l = ReadWriteLock()
tasks = Array{Task, 1}(undef, 3)

# freeze everyone
lock!(write_lock(l))

try
tasks[1] = Threads.@task readerTask(l)
tasks[2] = Threads.@task readerTask(l)
tasks[3] = Threads.@task writerTask(l)
schedule.(tasks)
finally
# now release
unlock!(write_lock(l))
end

(l, tasks)
end

(l, t) = main()

istaskstarted.(t)
istaskdone.(t)
```

run with `julia -t 2 main.jl`
juliaversion: 1.8.0-rc1
expected output: all tasks should be finished, program exits immediately
actual output: program hangs

Contributor guide

No contributing guide indexed for this repository

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.