В моем приложении есть следующий метод:
- (void) loadModel {
// Runs in a seperate thread so we need to create an additional NSAutoreleasePool
pool = [[NSAutoreleasePool alloc] init];
NSData *getData = [activeModelInfo getFileData];
if (getData) {
if ([activeModel loadFromFileData:daeData]) {
[activeModel reset];
[mainViewController performSelectorOnMainThread:@selector(showModelView) withObject:nil waitUntilDone:NO];
}
else {
}
}
else {
}
[pool release];
}
Метод loadFromFileData вызывает следующий код, который загружает данные. :
- (void) loadVerticesFromSource:(NSString*)verticesSourceId meshNode:(TBXMLElement*)meshNode intoMesh: (Mesh3D*) mesh {
NSLog(@"Getting Vertices for Source %@",verticesSourceId);
FloatArray *floatArray = [self getFloatArrayFromSource: verticesSourceId meshNode: meshNode];
if (floatArray) {
[daeFloatArray addObject:floatArray];
}
if (floatArray) {
if ([floatArray.array count] % 3 != 0) {
NSLog(@"Float array length not divisible by 3!");
}
else {
mesh->verticesCount = [floatArray.array count] / 3;
mesh->vertices = malloc(sizeof(Vector3D) * mesh->verticesCount);
for (int i=0; i<mesh->verticesCount; i++) {
mesh->vertices[i].x = [[floatArray.array objectAtIndex:(i*3)] floatValue];
mesh->vertices[i].y = [[floatArray.array objectAtIndex:(i*3)+1] floatValue];
mesh->vertices[i].z = [[floatArray.array objectAtIndex:(i*3)+2] floatValue];
// update extents information
if (!extents.pointDefined || mesh->vertices[i].x < extents.minX) extents.minX = mesh->vertices[i].x;
else if (!extents.pointDefined || mesh->vertices[i].x > extents.maxX) extents.maxX = mesh->vertices[i].x;
if (!extents.pointDefined || mesh->vertices[i].y < extents.minY) extents.minY = mesh->vertices[i].y;
else if (!extents.pointDefined || mesh->vertices[i].y > extents.maxY) extents.maxY = mesh->vertices[i].y;
if (!extents.pointDefined || mesh->vertices[i].z < extents.minZ) extents.minZ = mesh->vertices[i].z;
else if (!extents.pointDefined || mesh->vertices[i].z > extents.maxZ) extents.maxZ = mesh->vertices[i].z;
if (!extents.pointDefined) extents.pointDefined = YES;
[pointerStorageArray addObject:[NSValue valueWithPointer:mesh->vertices]];
}
}
}
}
Поскольку этот метод вызывается несколько раз при загрузке данных, каждый раз, когда происходит неправильное использование памяти для структуры mesh-> vertices, я создал массив pointerStorage, в котором хранится указатель на неправильную память.
Затем приложение отображает 3D-объект с помощью OpenGL ES. Когда пользователь нажимает кнопку главного меню, я освобождаю pointerStorageArray следующим образом:
- (void) freeUpMallocedMemory
for (NSValue * value in pointerStorageArray) {
free(value);
}
Проблема заключается в том, что приложение завершает работу во время этого процесса. Все, что я получаю, это сообщение об ошибке EXC_BAD_ACCESSS и указатель на следующую строку кода в методе loadModel выше:
[pool release];
Ничего в трассировке стека. Я также пытался включить NSZombie, NSAutoreleaseTrackFreedObjectCheck и NSDebugEnabled, но до сих пор не получаю никакой дополнительной информации.
Странно то, что если я установлю задержку на кнопку в 2 секунды (т. Е. Вызов метода freeUpMallocedMemory только через 2 секунды), приложение больше не будет аварийно завершать работу и работает нормально.
Может кто-нибудь подсказать, что может быть причиной этого - действительно запутался и уже потратил несколько дней на устранение неисправностей.
Спасибо!