About Monkey 2 › Forums › Monkey 2 Programming Help › Structs and the GC
Tagged: Struct
This topic contains 17 replies, has 7 voices, and was last updated by
sicilica 2 years, 8 months ago.
-
AuthorPosts
-
August 2, 2016 at 10:57 pm #2688
Strings are allocated from the heap, but are reference counted instead of GC’d.
August 12, 2016 at 4:21 pm #2950In case anyone searches into this thread later with a similar situation, a solution like this should work:
Monkey12345678910111213141516171819202122232425262728293031323334353637383940414243Import "<libc>"Using libc..Struct Vec3Property X:Float()Return data[0]Setter(val:Float)data[0] = valEndProperty Y:Float()Return data[1]Setter(val:Float)data[1] = valEndProperty Z:Float()Return data[2]Setter(val:Float)data[2] = valEndField data:Float PtrConst SIZE = 12 ' 3 floats, 4 bytes eachEndFunction Vec3_Alloc(out:Vec3 Ptr, count:Int = 1)Local mem:Byte Ptr = malloc(count * Vec3.SIZE)' this assignment work depends on your specific struct' probably need to do array syntax into mem, since pointer arithmetic isn't allowed?For Local i = 0 Until countout[i].data = Varptr mem[i * Vec3.SIZE]NextEndFunction Vec3_Free(val:Vec3 Ptr)' this depends on your specific struct' free whatever you had at mem[0], if you have multiple fields in the structfree(val.data)EndVec3_Alloc() can allocate arrays of contiguous memory for storing a large number structs.
Your struct should only contain pointers if you do this (even, say, a single float needs to be a pointer; classes are fine, since they are always be pointers, but ofc they shouldn’t be allocated from your malloc memory).
If you allocate an array of structs, they have to all be free’d at once, pass a pointer to the first one to the Vec3_Free() function (duh).
You still need to store your ACTUAL structs somewhere on the heap, so they are technically separate from the memory, eg:
Monkey12Global triangle:= New Vec3[3] ' this is telling the GC where the actual structs themselves are, use pointers everywhere except hereVec3_Allocate(Varptr triangle, 3)And as the last caveat, you’ll fracture your memory a lot worse than even the GC would if you don’t know what you’re doing, so for example, don’t actually create a single triangle this way.
August 13, 2016 at 2:18 am #2956Here’s a much better example.
Monkey12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849Function Mesh_Alloc(mesh:Mesh Ptr, numVertices:Int, numTriangles:Int)mesh->numVertices = numVerticesmesh->numTriangles = numTrianglesLocal mem:Byte Ptr = Cast<Byte Ptr>(malloc(numVertices*Vertex.SIZE + numTriangles*Triangle.SIZE))mesh->vertices = Cast<Vertex Ptr>(mem)mesh->triangles = Cast<Triangle Ptr>(Varptr mem[numVertices*Vertex.SIZE])EndFunction Mesh_Free(mesh:Mesh Ptr)free(mesh->vertices)mesh->numVertices = 0mesh->numTriangles = 0mesh->vertices = Nullmesh->triangles = NullEndStruct MeshField numVertices:IntField vertices:Vertex PtrField numTriangles:IntField triangles:Triangle PtrEndStruct VertexField texCoords:Vec2fField position:Vec3fConst SIZE:= 2*SIZE_OF_FLOAT + 3*SIZE_OF_FLOATEndStruct TriangleField vertexIndex0:ShortField vertexIndex1:ShortField vertexIndex2:ShortConst SIZE:= 3*SIZE_OF_SHORTEndConst SIZE_OF_SHORT:= 2Const SIZE_OF_FLOAT:= 4 -
AuthorPosts
You must be logged in to reply to this topic.