buffer too small

Johan Vos johan.vos at gluonhq.com
Tue Mar 8 14:14:08 UTC 2016


We got a number of bug reports (on Android and iOS) reported by developers
using large images:

java.lang.IllegalArgumentException: Upload requires 2475266 elements, but
only 1549938 elements remain in the buffer

at com.sun.prism.impl.BaseTexture.checkUpdateParams(BaseTexture.java:354)

at com.sun.prism.es2.ES2Texture.update(ES2Texture.java:640)

at com.sun.prism.impl.BaseContext.flushVertexBuffer(BaseContext.java:106)

at com.sun.prism.impl.BaseContext.updateMaskTexture(BaseContext.java:248)

at
com.sun.prism.impl.ps.BaseShaderGraphics.renderShape(BaseShaderGraphics.java:482)


I traced this down to the following:

initially, a buffer of [1024 * 1024] is allocated by
BaseContext.validateMaskTexture. When the MaskData becomes bigger than 1024
(w or h), a new buffer is allocated with capacity [newTexW * newTexH] with
newTexW and newTexH the new width/height that are passed when creating a
new Texture. However, the physical size of the texture can be different --
e.g.

ES2Texture.create (ES2Context, PixelFormat, WrapMode, int, int, bool) will
in some cases set the real texWidth/height to the next power of 2.

Subsequently, in next rendering loops when the Texture needs to be updated,
it is checked whether the capacity of the buffer is large enough to hold
the texture. In this case, the physical width is passed and the buffer is
not large enough.

Adding the following two lines in BaseContext.validateMaskTexture() (line
220) fixes the problem:

            newTexW = Math.max(newTexW, maskTex.getPhysicalWidth());

            newTexH = Math.max(newTexH, maskTex.getPhysicalHeight());

Using this patch, the size of the buffer will take the physical size of the
texture into account. I'm not sure this is the best approach though.

- Johan


More information about the openjfx-dev mailing list