[solved] Crash when loading manually created mesh


21-04-2010 17:16:20


i created a custom mesh via the mesh manager and subsequently vertex and index buffers,
but when i call mesh.load() my program crashes (on the ogre side, completely and without
any log entries or console output)

i initialize the mesh and buffer declaration here
def init(self, sceneManager, name):
self.name = name
self.mesh = ogre.MeshManager.getSingleton().createManual(name,"default")
self.mesh.sharedVertexData = ogre.VertexData()
declaration = self.mesh.sharedVertexData.vertexDeclaration
offset = 0
declaration.addElement(0, offset, ogre.VET_FLOAT3, ogre.VES_POSITION)
offset += ogre.VertexElement.getTypeSize(ogre.VET_FLOAT3)

declaration.addElement(0, offset, ogre.VET_FLOAT3, ogre.VES_NORMAL)
offset += ogre.VertexElement.getTypeSize(ogre.VET_FLOAT3)

declaration.addElement(0, offset, ogre.VET_FLOAT2, ogre.VES_TEXTURE_COORDINATES)
offset += ogre.VertexElement.getTypeSize(ogre.VET_FLOAT2)

and then procede to populate the buffers here
def build(self):
vertices = []
indices = []
faceIndex = 0
for face in self.faces:
v0 = self.vertices[face[0]]
v1 = self.vertices[face[1]]
v2 = self.vertices[face[2]]
normal = (v1 - v0).crossProduct(v2 - v0).normalisedCopy()
vertices.extend([ v0.x, v0.y, v0.z,
normal.x, normal.y, normal.z,
v1.x, v1.y, v1.z,
normal.x, normal.y, normal.z,
v2.x, v2.y, v2.z,
normal.x, normal.y, normal.z,
self.textureCoordinates[faceIndex+2][0],self.textureCoordinates[faceIndex+2][1] ])
faceIndex += 3
componentsPerVertex = 3 + 3 + 2 * 1 # pos + normal + textcoords * coordsets

submesh = self.mesh.createSubMesh()
vertexData = self.mesh.sharedVertexData
vertexData.vertexCount = len(vertices) / componentsPerVertex
submesh.indexData.indexCount = len(indices)

hwBM = ogre.HardwareBufferManager.getSingleton()

vertexBuffer = hwBM.createVertexBuffer(vertexData.vertexDeclaration.getVertexSize(0), vertexData.vertexCount, ogre.HardwareBuffer.HBU_STATIC_WRITE_ONLY)
indexBuffer = hwBM.createIndexBuffer(ogre.HardwareIndexBuffer.IT_32BIT, submesh.indexData.indexCount, ogre.HardwareBuffer.HBU_STATIC_WRITE_ONLY)

import ctypes

pointer = vertexBuffer.lock(ogre.HardwareBuffer.HBL_DISCARD)
storage = (ctypes.c_float * len(vertices))
vBuffer = storage.from_address(ogre.CastInt(pointer))
for i in range(len(vertices)):
vBuffer[i] = ctypes.c_float(vertices[i])

pointer = indexBuffer.lock(ogre.HardwareBuffer.HBL_DISCARD)
storage = (ctypes.c_float * len(indices))
iBuffer = storage.from_address(ogre.CastInt(pointer))
for i in range(len(indices)):
iBuffer[i] = indices[i]


vertexData.vertexBufferBinding.setBinding(0, vertexBuffer)
submesh.indexData.indexBuffer = indexBuffer

r = self.vertices[0].length()
self.mesh._setBounds(ogre.AxisAlignedBox(ogre.Vector3(-r, -r, -r), ogre.Vector3(r, r, r)))

submesh.useSharedVertices = True
submesh.indexData.indexStart = 0


after sorting out the issue with void pointers and such the methods work fine, until the mesh.load() call,
which results in a "visual studio just in time debugger has encountered an error" etc. message box popping up
and me not knowing what exactly went wrong

I've found that there was an instance of someone having a similar crash, this person then realized his vertex
declaration semantics were wrong, but i can't find an error there in my case. If someone can shed light onto
this issue, or has at least some clue what is going on, i'd much appreciate it

PS: can anyone tell me if its possible to use HardwareBuffer.writeData() with python ? i couldn't figure out how
to specify the pointer to the source of the vertex data, the closest i got was a pointer that was type LP_c_long
instead of the seemingly needed c_uint. I'd prefer that method to .lock() and writing manually if someone can
tell me how to get it to work (though as the mesh doesn't load at the moment, that's not top priority)


24-04-2010 10:04:06

Can you submit a complete test program ? Unfortunately its difficult to help when only seeing fragments..

As a suggestion check if there are buffers/arrays etc that the C++ functions expect to stay in scope and ensure you have "self." them (or made them global).. One of the most common errors is creating index buffers and having them go out of scope, the C++ function then calls them and you get a crash..




01-05-2010 06:33:11

For starters you are trying to write floats to the indexBuffer:

storage = (ctypes.c_float * len(indices))

The above should be ctypes.c_uint32/ctypes.c_uint16 for ogre.HardwareIndexBuffer.IT_32BIT/16BIT index buffers.


01-05-2010 13:45:32

Thats what you get for using copypasta :lol:
How stupid of me not to think of checking the type for the index buffer

Well, it works now, thanks a lot :)