diff --git a/src/context.jl b/src/context.jl index 7c77cec2..aea70d4d 100644 --- a/src/context.jl +++ b/src/context.jl @@ -8,7 +8,10 @@ type Context @check api.clRetainContext(ctx_id) end ctx = new(ctx_id) - finalizer(ctx, c -> release!(c)) + finalizer(ctx, c -> begin + retain || _deletecached!(c); + release!(c) + end ) return ctx end end diff --git a/src/macros.jl b/src/macros.jl index 9b83a336..dc8b0af6 100644 --- a/src/macros.jl +++ b/src/macros.jl @@ -97,3 +97,29 @@ macro str_info(what, arg1, arg2) bytestring(convert(Ptr{CL_char}, result)) end end + +function _version_test(qm, elem :: Symbol, ex :: Expr, version :: VersionNumber) + @assert qm == :? + @assert ex.head == :(:) + @assert length(ex.args) == 2 + + esc(quote + if OpenCL.check_version($elem, $version) + $(ex.args[1]) + else + $(ex.args[2]) + end + end) +end + +macro min_v11(qm, elem, ex) + _version_test(qm, elem, ex, v"1.1") +end + +macro min_v12(qm, elem, ex) + _version_test(qm, elem, ex, v"1.2") +end + +macro min_v20(qm, elem, ex) + _version_test(qm, elem, ex, v"2.0") +end diff --git a/src/queue.jl b/src/queue.jl index b86dc7ff..6bf25f05 100644 --- a/src/queue.jl +++ b/src/queue.jl @@ -8,7 +8,10 @@ type CmdQueue @check api.clRetainCommandQueue(q_id) end q = new(q_id) - finalizer(q, x -> release!(x)) + finalizer(q, x -> begin + retain || _deletecached!(q) + release!(x) + end ) return q end end diff --git a/src/util.jl b/src/util.jl index c5d1d862..666abc12 100644 --- a/src/util.jl +++ b/src/util.jl @@ -5,7 +5,17 @@ function create_compute_context() return (device, ctx, queue) end -opencl_version(p::Platform) = api.parse_version(p[:version]) -opencl_version(d::Device) = opencl_version(d[:platform]) -opencl_version(c::Context) = opencl_version(first(devices(c))) -opencl_version(q::CmdQueue) = opencl_version(q[:context]) +opencl_version(p :: Platform) = api.parse_version(p[:version]) +opencl_version(d :: Device) = api.parse_version(d[:version]) +opencl_version(c :: Context) = opencl_version(first(devices(c))) +opencl_version(q :: CmdQueue) = opencl_version(q[:device]) + +const _versionDict = Dict{Ptr{Void}, VersionNumber}() + +_deletecached!(obj) = delete!(_versionDict, pointer(obj)) + +function check_version(obj, version :: VersionNumber) + version <= get!(_versionDict, pointer(obj)) do + opencl_version(obj) + end +end diff --git a/test/runtests.jl b/test/runtests.jl index c057e3ea..9323f498 100644 --- a/test/runtests.jl +++ b/test/runtests.jl @@ -3,6 +3,7 @@ const tests = [ "context" "device" "cmdqueue" + "macros" "event" "program" "kernel" diff --git a/test/test_macros.jl b/test/test_macros.jl new file mode 100644 index 00000000..90e87853 --- /dev/null +++ b/test/test_macros.jl @@ -0,0 +1,76 @@ +using FactCheck +using Base.Test + +import OpenCL +const cl = OpenCL + +facts("OpenCL.Macros") do + + context("OpenCL.Macros version platform") do + for platform in cl.platforms() + + version = cl.opencl_version(platform) + + v11 = cl.@min_v11? platform true : false + v12 = cl.@min_v12? platform true : false + v20 = cl.@min_v20? platform true : false + + if version == v"1.0" + @fact v11 => false + @fact v12 => false + @fact v20 => false + + elseif version == v"1.1" + @fact v11 => true + @fact v12 => false + @fact v20 => false + + elseif version == v"1.2" + @fact v11 => true + @fact v12 => true + @fact v20 => false + + elseif version == v"2.0" + @fact v11 => true + @fact v12 => true + @fact v20 => true + + end + end + end + + context("OpenCL.Macros version device") do + for platform in cl.platforms() + for device in cl.devices(platform) + version = cl.opencl_version(device) + + v11 = cl.@min_v11? device true : false + v12 = cl.@min_v12? device true : false + v20 = cl.@min_v20? device true : false + + if version == v"1.0" + @fact v11 => false + @fact v12 => false + @fact v20 => false + + elseif version == v"1.1" + @fact v11 => true + @fact v12 => false + @fact v20 => false + + elseif version == v"1.2" + @fact v11 => true + @fact v12 => true + @fact v20 => false + + elseif version == v"2.0" + @fact v11 => true + @fact v12 => true + @fact v20 => true + + end + end + end + end +end +