2010-12-08 3 views
1

Une application iPad fonctionnant correctement sous IOS3 échoue sous IOS4.2 Elle a une classe qui exécute une session http à partir d'une file d'attente d'opérations et l'échec est lié à cette activité. Voici la sortie de la console:L'application IOS4.2 se ferme avec EXC_BAD_ACCESS

Program received signal: “EXC_BAD_ACCESS”. 
[Switching to thread 11523] 

Exécution NSZombies permis n'a pas révélé quoi que ce soit donc je suis mettais des déclarations NSLog dans le code et a constaté que l'incident se produit lorsqu'une variable locale est modifiée. Voici la section de code:

self.currentOperation = [[[DeduceAccessOperation alloc] init] autorelease]; 
[self.currentOperation addObserver:self forKeyPath:@"isFinished" 
options:(NSKeyValueObservingOptionNew | NSKeyValueObservingOptionOld) 
context:NULL]; 
NSLog (@"Start observer added");  
[operationQueue addOperation:self.currentOperation]; 
NSLog (@"Start operation added"); 
NSLog(@"State is %d", self.status); 
self.status = IEnablerServiceUpdating; 
NSLog (@"State updated"); 

Et voici la sortie du journal de la console:

2010-12-08 21:26:44.548 UCiEnabler[5180:307] Start observer added 
2010-12-08 21:26:44.550 UCiEnabler[5180:307] Start operation added 
2010-12-08 21:26:44.552 UCiEnabler[5180:307] State is 1 
Program received signal: “EXC_BAD_ACCESS”. 
[Switching to thread 11523] 

Il est comme le statut est devenu en lecture seule (sa propriété est déclarée comme atomique et readwrite).

L'autre information pertinente est qu'une vue secondaire vient d'être modifiée et qu'elle déclenche l'appel sur la routine ci-dessus. Son code est:

//Start the update  
UCiEnablerAppDelegate *controller = (UCiEnablerAppDelegate *)[[UIApplication sharedApplication] delegate]; 
[controller deduceIEnablerServiceAccess]; 
controller.serviceBusy = TRUE; //1.04 

Est-ce que quelqu'un a déjà vu quelque chose comme ça?

Est-ce que quelqu'un a des idées où chercher?

Cordialement Robin

Voici la trace de la pile:

#0 0x34a80464 in objc_msgSend 
#1 0x3119543e in NSKVOPendingNotificationCreate 
#2 0x3119535a in NSKeyValuePushPendingNotificationPerThread 
#3 0x3117009a in NSKeyValueWillChange 
#4 0x311682c6 in -[NSObject(NSKeyValueObserverNotification) willChangeValueForKey:] 
#5 0x311cc718 in _NSSetIntValueAndNotify 
#6 0x000097ce in -[IEnablerService startDeducingAccessState] at IEnablerService.m:55 
#7 0x00002bc0 in -[UCiEnablerAppDelegate deduceIEnablerServiceAccess] at UCiEnablerAppDelegate.m:100 
#8 0x0000a33e in -[RootViewControlleriPad animationDidStop:finished:context:] at RootViewController-iPad.m:43 
#9 0x341bb336 in -[UIViewAnimationState sendDelegateAnimationDidStop:finished:] 
+0

Dans le futur ** s'il vous plaît ** examinez votre question pour vous assurer que le formatage du code est correct. – JeremyP

+0

Aussi, exécutez ceci dans le débogueur, obtenez la trace de la pile et affichez-la ici. – JeremyP

+0

aucune chance que vous ayez un setter personnalisé pour le statut qui cause le crash? Que se passe-t-il si vous définissez un point d'arrêt sur cette ligne et entrez dans le self.status = IEnablerServiceUpdating? – Rog

Répondre

0

NSOperationQueue dans iOS 4.2 utilise maintenant lors du démarrage NSOperations Grand Central Dispatch. There's a Technical Q&A here

Quasiment la file d'attente appelle maintenant start de la sous-classe NSOperation méthode dans un nouveau thread quelle que soit la propriété isConcurrent. Dans mon expérience cela signifie que si vous utilisez NSURLConnection à l'intérieur d'une méthode start votre code ne sera plus exécuté car le thread start est en cours d'exécution n'a pas de NSRunLoop. Apple dit que cette modification ne rompt pas la compatibilité parce que vous étiez censé générer un nouveau thread dans la méthode start de toute façon.

Pour des raisons de compatibilité ascendante, vous devez modifier votre sous-classe en utilisant start pour utiliser run.

+0

Mes recherches sur GCD suggèrent qu'il est approprié pour les files d'attente de répartition (Guide de concurrence simultanée p13) et non pour les files d'attente d'opération. Mais NSURLConnections doit s'exécuter à partir des files d'attente d'opération. Mais depuis iOS3, la meilleure façon de les appeler est via les appels d'API asynchrones. Mais je ne suis pas disposé/incapable de réviser le code car je n'ai pas accès à l'environnement pour le tester complètement. Arrgghhhh! –

Questions connexes