Skip to content

Commit ca17788

Browse files
authored
pcre: remove nthreads constant dependency (#44542)
This appears to be the only remaining place we use the nthreads variable to pre-initialize a shared array. Let us fix that code pattern now, since we know globals are already acquire/release.
1 parent b75a067 commit ca17788

File tree

3 files changed

+33
-14
lines changed

3 files changed

+33
-14
lines changed

base/Base.jl

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -507,6 +507,10 @@ function __init__()
507507
nothing
508508
end
509509

510+
# enable threads support
511+
@eval PCRE PCRE_COMPILE_LOCK = Threads.SpinLock()
512+
510513
end
511514

515+
512516
end # baremodule Base

base/client.jl

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -514,10 +514,6 @@ MainInclude.include
514514
function _start()
515515
empty!(ARGS)
516516
append!(ARGS, Core.ARGS)
517-
if ccall(:jl_generating_output, Cint, ()) != 0 && JLOptions().incremental == 0
518-
# clear old invalid pointers
519-
PCRE.__init__()
520-
end
521517
try
522518
exec_options(JLOptions())
523519
catch

base/pcre.jl

Lines changed: 29 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -24,28 +24,47 @@ function create_match_context()
2424
return ctx
2525
end
2626

27-
const THREAD_MATCH_CONTEXTS = Ptr{Cvoid}[C_NULL]
27+
THREAD_MATCH_CONTEXTS::Vector{Ptr{Cvoid}} = [C_NULL]
2828

2929
PCRE_COMPILE_LOCK = nothing
3030

31-
_tid() = Int(ccall(:jl_threadid, Int16, ())+1)
31+
_tid() = Int(ccall(:jl_threadid, Int16, ())) + 1
3232
_nth() = Int(unsafe_load(cglobal(:jl_n_threads, Cint)))
3333

3434
function get_local_match_context()
35+
global THREAD_MATCH_CONTEXTS
3536
tid = _tid()
36-
ctx = @inbounds THREAD_MATCH_CONTEXTS[tid]
37+
ctxs = THREAD_MATCH_CONTEXTS
38+
if length(ctxs) < tid
39+
# slow path to allocate it
40+
l = PCRE_COMPILE_LOCK::Threads.SpinLock
41+
lock(l)
42+
try
43+
THREAD_MATCH_CONTEXTS = ctxs = copyto!(fill(C_NULL, _nth()), THREAD_MATCH_CONTEXTS)
44+
finally
45+
unlock(l)
46+
end
47+
end
48+
ctx = @inbounds ctxs[tid]
3749
if ctx == C_NULL
38-
@inbounds THREAD_MATCH_CONTEXTS[tid] = ctx = create_match_context()
50+
# slow path to allocate it
51+
ctx = create_match_context()
52+
l = PCRE_COMPILE_LOCK
53+
if l === nothing
54+
THREAD_MATCH_CONTEXTS[tid] = ctx
55+
else
56+
l = l::Threads.SpinLock
57+
lock(l)
58+
try
59+
THREAD_MATCH_CONTEXTS[tid] = ctx
60+
finally
61+
unlock(l)
62+
end
63+
end
3964
end
4065
return ctx
4166
end
4267

43-
function __init__()
44-
resize!(THREAD_MATCH_CONTEXTS, _nth())
45-
fill!(THREAD_MATCH_CONTEXTS, C_NULL)
46-
global PCRE_COMPILE_LOCK = Threads.SpinLock()
47-
end
48-
4968
# supported options for different use cases
5069

5170
# arguments to pcre2_compile

0 commit comments

Comments
 (0)