Re: [ANN] LuaJIT Roadmap 2012/2013

  • From: "Robert G. Jakabosky" <bobby@xxxxxxxxxxxxxxx>
  • To: luajit@xxxxxxxxxxxxx
  • Date: Wed, 13 Jun 2012 00:14:03 -0700

On Tuesday 12, Mike Pall wrote:
> Robert G. Jakabosky wrote:
> > On Monday 11, Mike Pall wrote:
> > > Adam Strzelecki wrote:
> > > > for i = 0, 1000 -- some tight loop
> > > > 
> > > >         local value = model[i] * view
> > > >         gl.UniformMatrix4fv(location, 1, gl.TRUE, value.gl)
> > > > 
> > > > end
> > > 
> > > Well, no, because 'value' *does* escape. There's no way for the
> > > compiler to know that gl.UniformMatrix4fv() doesn't store the
> > > 'value' pointer somewhere else.
> > 
> > If gl.UniformMatrix4fv() did store the value and the value wasn't also
> > stored somewhere on the Lua side, then there is already a bug since the
> > GC would free the value which might still be in use by the C code.
> 
> No, there's a guarantee that arguments to a C function call are
> not collected before the C call returns.

Sorry I was not very clear.  I have written new example code below.  Also by 
"bug" I was talking about the code in the loop being broken, if 
gl.UniformMatrix4fv() stored the value for later use.

I know that the value will not be collected until sometime after the end of 
the current loop iteration (the scope of the 'value' local).  It can be 
collected during the next loop iteration.  The point is that it is up to the 
programer to either keep the value alive (by storing it in a table) or use 
manual allocation if the C-side wants to hold onto the value.

Case where the C function stores a pointer to the value:
for i=1,1000 do
  -- In this example the programer must not use a collectable value
  local value = ffi.C.vecter3_new(i,i*2,i*3)
  -- C function that stores a pointer to the vector
  ffi.C.container_append(container, value)
end

The vector allocation in the above loop is not sinkable, because the 
allocation is on the C-side.

If the programer wrote the loop like this:
for i=1,1000 do
  -- GC collectable vector3 cdata value.
  local value = ffi.new("vector3", i,i*2,i*3)
  -- C function that stores a pointer to the vector
  ffi.C.container_append(container, value)
  -- end of scope for 'value' GC can collect it during the next iteration.
end

This code is broken even if LuaJIT doesn't sink the allocation, since the 
vector values will be collected at some point.  It shouldn't matter to LuaJIT 
if container_append() stores a pointer to the value or not.  It is up to the 
programer to correctly decide how the vector3 value is allocated.

What I am trying to get at is that only if the value is stored where the GC 
can find it should the store be counted as an escape.  If the value is only 
stored in another cdata or passed to an C function it shouldn't be counted as 
an escape, since the GC will not see it and will collect it.

From the point of view of the Lua code, allocation sinking should make it look 
like the GC is running really fast and freeing values as soon as execute 
leaves the scope of the value.

-- 
Robert G. Jakabosky

Other related posts: