Windows specific UV error

i extended Cairo in one place and now tests only on winows are failing with

  Got an exception of type Base.UVError outside of a @test
  unlink: resource busy or locked (EBUSY)
   in uv_error at .\libuv.jl:68 [inlined]
   in unlink(::String) at .\file.jl:382
   in #rm#7(::Bool, ::Bool, ::Function, ::String) at .\file.jl:107
   in macro expansion; at C:\Users\appveyor\.julia\v0.5\Cairo\test\runtests.jl:197 [inlined]
   in macro expansion; at .\test.jl:674 [inlined]
   in anonymous at .\<missing>:?
   in include_from_node1(::String) at .\loading.jl:488
   in process_options(::Base.JLOptions) at .\client.jl:265
   in _start() at .\client.jl:321

while linux and OSX testing has no complaints.

Are there know windows specific UV issues?

Not a libuv issue. Explicitly close files before doing anything else with them.

Could you please clarify. You mean: open file, close file, rm file in sequence without writing to file? Is this special on UV windows?
For the longer story see https://github.com/JuliaGraphics/Cairo.jl/pull/183/files where i use the same tests on scripting surfaces like previously on other surfaces that create a file.

I mean close the file before doing anything else (i.e. not through the opened file handle) on the file. This includes removing the file. This is unrelated to libuv but is windows specific.

is this documented somewhere and does it apply also to IOstreams?

It’s an windows issue so you should expect to find the document in windows documentation.

It applies to all files including but no limited to, ccall(:open), any libraries that open files, mmap, open, etc and in this case it’s likely that cairo is doing it.

I have now tried to track down the exact issue and to make a simpler example and now the error vanished (?)

The sequence of actions is:

  • open IOBuffer
  • hand over to a low-level call to libcairo that writes to that IObuffer
  • use str = String(take!(io)) to get the written data
  • forget about io and hope it will be GCed

This happens a few times in the runtests.jl and only for one call it’s raising the error
https://ci.appveyor.com/project/JuliaGraphics/cairo-jl/build/1.0.110/job/u0x12fyqelxs4b2v#L124

Now i reduced the example to a smaller set of tests (and externalise to a dummy Package) and it passes:
https://ci.appveyor.com/project/lobingera/l1dummy/build/1.0.8/job/ibefj454fhopirvw#L116

Any good idea?

That’s expected since IOBuffer isn’t a file.

As I said before already, this is a windows issue since you didn’t

So you just need to do just that. Also,

So you might need to make sure libcairo closes it’s handle on that file too.

I somehow understand the situation. Still, the same sequence of actions is/was already tested successfully and now the ‘new’ test is failing. Could it be libuv can manage only a limited set of ‘unclosed’ files/stream and start complaining at N+1? My goal was to isolate the error and it seems like i’m seeing side-effects of previous access?

OK. I was confused (error reporting on exact line number and file…).

The situation i’m testing is:

  • create file
  • open
  • read
  • close
  • rm file

and it’s working, but fails if done inside @testset

I still don’t understand what are you confused by. A few guesses.

  1. You are seeing a windows specific issue so it won’t appear anywhere else.
  2. The issue is related to files so it won’t appear for any other file-like objects including IOBuffer()
  3. The error happens only if someone kept a file handle open, it is likely in libcairo and the issue might appear or not depending on what you are doing with it.
  4. The error happens if GC didn’t do the cleanup on some object. Moving the code can very easily affect this.