I am getting into exception handling, but I am surprised at how my code works. Note that I am on Julia 0.6 (will port to 1.0 as soon as it’s out!). So, here goes:
function bungle(c)
out = 0
try
@printf "Bungling away\n"
out = 1
if c == 1
@assert false @sprintf "We have a main %s undervolt" "B"
elseif c==2
M = spzeros(1e4)
v = randn(1e4)
x = M\v
elseif c==3
a = sqrt(-1.)
elseif c==4
throw(DomainError())
end
catch ex
out = 2
@printf "\nHouston we have a problem:\n%s\n" ex.msg
finally
@printf "Shutting down.\n"
return out
end
end # function bungle
@show bungle(0)
Calling bungle(0) and bungle(1) behaves as I intend. Bungle(2), bungle(3) and bungle(4) throw exceptions, which should be caught and reported. However, in these cases, the catch block is not executed, while the finaly block is. Why on earth!?!
This has to be a bug. I cannot see how the combination of return statement and some exception types can make it logical not to execute the catch block.
I will plagiate your code and report this as a bug.
I will find some workaround: the reason I catch exceptions is I want to return whatever the computations have achieved (the steps that converged)…
julia> function h()
try
sqrt(-1)
catch e
println("Houston!")
finally return 1
end
end;
julia> h()
Houston!
1
BTW your example prints error under 0.7.0-rc1.15
0.7.0-rc1.15> @show bungle(3)
Bungling away
Houston we have a problem:
sqrt will only return a complex result if called with a complex argument. Try sqrt(Complex(x)).
Shutting down.
bungle(3) = 2
2
In all examples catch block is executed. The problem is that when an exception in catch block is thrown then it is not passed through if there is a return statement in finally.
And the specific problem is in the original code that not all exceptions have msg field. Then the Julia throws error that is not passed through later. But the core problem is what I have explained in my MWE (without catch). If in this MWE you move out return past finally error is raised:
julia> function h()
try
sqrt(-1)
finally
println("Finally")
end
return 1
end
h (generic function with 1 method)
julia> h()
Finally
ERROR: DomainError:
Stacktrace:
[1] h() at .\REPL[4]:3
compare it to what I wrote before about 0.7.0. I didn’t analyze it deeply but it seemed to me that in 0.6.1 printf to Houston was not processed. (I could be wrong).
The reason is that DomainError has field msg in Julia 0.7 and it does not have it in Julia 0.6. So in Julia 0.7 no error is thrown in catch clause and all is processed cleanly.
Issues are best handled on Github.
It has the right tools for the job,
In terms of cross-referencing; devs getting notifications,
closing, etc etc.
Just open an issue.
It may be closed, it may not.
But trust me no one will get mad for creating an issue prematurely without discussing it with them on discourse first.