osqp/OSQP.jl

Segfault when calling dimensions on Model before setup

Opened this issue · 4 comments

julia> using OSQP

julia> m = OSQP.Model()
OSQP.Model(Ptr{OSQP.Workspace} @0x0000000000000000)

julia> OSQP.dimensions(m)

signal (11): Segmentation fault: 11
while loading no file, in expression starting on line 0
dimensions at /Users/twan/code/julia/RigidBodyDynamics/v0.6/OSQP/src/interface.jl:514
unknown function (ip: 0x11ce28e7f)
do_call at /Users/osx/buildbot/slave/package_osx64/build/src/interpreter.c:75
eval at /Users/osx/buildbot/slave/package_osx64/build/src/interpreter.c:242
jl_interpret_toplevel_expr at /Users/osx/buildbot/slave/package_osx64/build/src/interpreter.c:34
jl_toplevel_eval_flex at /Users/osx/buildbot/slave/package_osx64/build/src/toplevel.c:577
jl_toplevel_eval_in at /Users/osx/buildbot/slave/package_osx64/build/src/builtins.c:496
eval at /Applications/Julia-0.6.app/Contents/Resources/julia/lib/julia/sys.dylib (unknown line)
jlcall_eval_18039 at /Applications/Julia-0.6.app/Contents/Resources/julia/lib/julia/sys.dylib (unknown line)
eval_user_input at /Applications/Julia-0.6.app/Contents/Resources/julia/lib/julia/sys.dylib (unknown line)
jlcall_eval_user_input_20366 at /Applications/Julia-0.6.app/Contents/Resources/julia/lib/julia/sys.dylib (unknown line)
macro expansion at ./REPL.jl:97 [inlined]
#1 at ./event.jl:73
unknown function (ip: 0x11cdf344f)
jl_apply at /Users/osx/buildbot/slave/package_osx64/build/src/./julia.h:1424 [inlined]
start_task at /Users/osx/buildbot/slave/package_osx64/build/src/task.c:267
Allocations: 5426407 (Pool: 5424867; Big: 1540); GC: 10
Segmentation fault: 11
tk-sloth:OSQP twan$ 

Same with update_settings!. It would actually be quite nice to be able to set settings before calling setup!. In fact, if OSQP itself supported it, I would personally opt to remove the settings kwargs from setup! to completly separate problem-dependent data and solver settings, so as to simplify things.

This is the same issue as in here osqp/osqp#39. I think the easiest solution is to add a check if the workspace is null to all the OSQP update functions in C. If the workspace is null I would return an error using the exitflag in C without generating a segfault.

I would not change the C osqp_setup interface for now because it would make things more complicated in my opinion. We can extend the Julia interface with multiple functions, but I would keep the current functions as they are to mimic the Python and Matlab interfaces.

This actually does look like an interface-specific issue. That backtrace (and the similar backtrace in #86) appear to be trying to directly access the structure before setup has been called using the Julia memory accessors. This will of course try to access an unallocated piece of memory since the library hasn't been initialized. There isn't anything we can do in the C library to work around that, the field accessors for the Julia wrappers should do null pointer checks to ensure the data being accessed is valid. I do see that it is checking the workspace against C_NULL already here

function dimensions(model::OSQP.Model)
, so something else is needed as well.

Turns out this was the unsafe_load causing the segfault, not the subsequent access to the struct (which was already guarded in a null check). This was fixed in #126, but we need to audit the rest of the functions to make sure we don't try to load a null struct in any other places.