2015-03-09 13 views
7

Ho ricevuto uno strano arresto EXC_BAD_ACCESS all'interno del metodo -[NSData(NSData) getBytes:length:] della Foundation. Succede abbastanza spesso, ma non riesco a ottenere informazioni significative dalla traccia dello stack. Non ci sono chiamate a getBytes:length: all'interno del mio codice, tranne che per le librerie open-source (una su SDWebImage e una su SocketRocket), ma non sembra che stiano causando l'arresto.Impossibile rintracciare [NSData getBytes: length:] crash

L'unico suggerimento è che l'arresto si verifica all'interno del thread com.apple.CFNetwork.addPersistCacheToStorageDaemon, ma non ho idea di cosa si tratta. Qualcuno può aiutare?

Stacktrace da Crashlytics:

Thread : Crashed: com.apple.CFNetwork.addPersistCacheToStorageDaemon 
0 libsystem_platform.dylib  0x3044a208 _platform_memmove$VARIANT$CortexA9 + 160 
1 Foundation      0x22df9167 -[NSData(NSData) getBytes:length:] + 118 
2 Foundation      0x22df9167 -[NSData(NSData) getBytes:length:] + 118 
3 Foundation      0x22e21a1b -[NSData(NSData) replacementObjectForCoder:] + 134 
4 Foundation      0x22dc2aff -[NSXPCEncoder _replaceObject:] + 90 
5 Foundation      0x22e240dd -[NSXPCEncoder _encodeArrayOfObjects:forKey:] + 192 
6 Foundation      0x22e212ff -[NSDictionary(NSDictionary) encodeWithCoder:] + 922 
7 Foundation      0x22dc32c9 -[NSXPCEncoder _encodeObject:] + 604 
8 Foundation      0x22dc379d encodeInvocationArguments + 460 
9 Foundation      0x22dc3455 -[NSXPCEncoder encodeInvocation:] + 360 
10 Foundation      0x22dc32c9 -[NSXPCEncoder _encodeObject:] + 604 
11 Foundation      0x22dc2335 -[NSXPCConnection _sendInvocation:proxyNumber:remoteInterface:withErrorHandler:timeout:userInfo:] + 1860 
12 Foundation      0x22dd2823 -[NSXPCConnection _sendInvocation:proxyNumber:remoteInterface:withErrorHandler:] + 58 
13 Foundation      0x22dd27db -[_NSXPCDistantObjectWithError forwardInvocation:] + 114 
14 CoreFoundation     0x2217e831 ___forwarding___ + 352 
15 CoreFoundation     0x220afb88 _CF_forwarding_prep_0 + 24 
16 CFNetwork      0x21c52ac9 -[NSURLStorage_CacheClient addCachedResponseWithDictionary:key:] + 120 
17 CFNetwork      0x21c21e29 ___ZN12__CFURLCache23CreateAndStoreCacheNodeEP16__CFURLCacheNodePK20_CFCachedURLResponsePK10__CFStringPK13_CFURLRequestPKvbRb_block_invoke + 1576 
18 libdispatch.dylib    0x302cf423 _dispatch_call_block_and_release + 10 
19 libdispatch.dylib    0x302d95d9 _dispatch_queue_drain$VARIANT$mp + 948 
20 libdispatch.dylib    0x302d90a9 _dispatch_queue_invoke$VARIANT$mp + 84 
21 libdispatch.dylib    0x302db0d3 _dispatch_root_queue_drain + 330 
22 libdispatch.dylib    0x302dc1fb _dispatch_worker_thread3 + 106 
23 libsystem_pthread.dylib  0x3044ce25 _pthread_wqthread + 668 

E un altro (capita meno spesso):

Thread : Crashed: com.apple.CFNetwork.addPersistCacheToStorageDaemon 
0 libsystem_platform.dylib  0x000000019344d300 _platform_memmove + 176 
1 Foundation      0x0000000182dfce18 -[NSData(NSData) getBytes:length:] + 172 
2 Foundation      0x0000000182dfce18 -[NSData(NSData) getBytes:length:] + 172 
3 Foundation      0x0000000182e2ae3c -[NSData(NSData) replacementObjectForCoder:] + 160 
4 Foundation      0x0000000182dbd320 -[NSXPCEncoder _replaceObject:] + 120 
5 Foundation      0x0000000182e2dac8 -[NSXPCEncoder _encodeArrayOfObjects:forKey:] + 256 
6 Foundation      0x0000000182e2a544 -[NSDictionary(NSDictionary) encodeWithCoder:] + 1016 
7 Foundation      0x0000000182dbdd10 -[NSXPCEncoder _encodeObject:] + 716 
8 Foundation      0x0000000182dbe2e8 encodeInvocationArguments + 508 
9 Foundation      0x0000000182dbdee4 -[NSXPCEncoder encodeInvocation:] + 412 
10 Foundation      0x0000000182dbdd10 -[NSXPCEncoder _encodeObject:] + 716 
11 Foundation      0x0000000182dbcb0c -[NSXPCConnection _sendInvocation:proxyNumber:remoteInterface:withErrorHandler:timeout:userInfo:] + 2196 
12 CoreFoundation     0x0000000181fde230 ___forwarding___ + 440 
13 CoreFoundation     0x0000000181ee2b6c _CF_forwarding_prep_0 + 92 
14 CFNetwork      0x000000018199c908 ___ZN12__CFURLCache23CreateAndStoreCacheNodeEP16__CFURLCacheNodePK20_CFCachedURLResponsePK10__CFStringPK13_CFURLRequestPKvbRb_block_invoke + 1976 
15 libdispatch.dylib    0x00000001932793ac _dispatch_call_block_and_release + 24 
16 libdispatch.dylib    0x000000019327936c _dispatch_client_callout + 16 
17 libdispatch.dylib    0x00000001932834c0 _dispatch_queue_drain + 1216 
18 libdispatch.dylib    0x000000019327c474 _dispatch_queue_invoke + 132 
19 libdispatch.dylib    0x0000000193285224 _dispatch_root_queue_drain + 664 
20 libdispatch.dylib    0x000000019328675c _dispatch_worker_thread3 + 108 
21 libsystem_pthread.dylib  0x00000001934552e4 _pthread_wqthread + 816 
+0

Questo succede nell'ambiente di sviluppo? – zaph

+0

@Zaph: nah, non potrei riprodurlo da solo. Succede solo nella produzione. – Spail

+1

Probabilmente 'getData' è stato passato un indirizzo di buffer fasullo, ma chi sarebbe stato responsabile è difficile da indovinare. Nota che entrambi i casi riguardano operazioni con la cache dell'URL. –

risposta

2

La mia ipotesi è che si deve

  • alcuni __unsafe_unretained (cioè unavoidable per percorso setter [NSInvocation setArgument:atIndex:])
  • o un problema come uno this
  • o (più probabilmente ) un deadlock durante una performBlockAndWait (da quando ho visto una connessione/timeout nello stack)

Un paio di suggerimenti correlati :

1) NSManagedObject, NSManagedObjectContext e NSPersistentStoreCoordinator (data la caduta a addPersistCacheToStorageDaemon) non è thread-safe:

012.
  • considerano questo se si utilizza performBlockAndWait per inviare messaggi al vostro NSManagedObjectContext (più here e here) o nested MOC.

2) CFNetwork è una classe di livello inferiore che è avvolto dal NSURLConnection:

  • quindi non usare NSURL? evitando addObserver:self forKeyPath (KVO) in una proprietà di una sessione NSURL?
2

la questione potrebbe in realtà essere da SDWebImage citazione da questo sito:

http://webcache.googleusercontent.com/search?q=cache:BCShJT0ZrvoJ:quabr.com/15786084/uicollectionview-bad-acces-on-uicollectionviewdata-setlayoutattributesatglo+&cd=7&hl=fr&ct=clnk&gl=jp

Ora, se si utilizza AFNetworking per impostare l'immagine direttamente dal URL utilizzando la categoria AFNetworking si può vuoi utilizzare il metodo alternativo in modo da poter intervenire e ridimensionare l'immagine. Il codice qui sotto lo farà.

NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:imageURL]; 
[request addValue:@"image/*" forHTTPHeaderField:@"Accept"]; 

[imageView setImageWithURLRequest:request placeholderImage:nil success:^(NSURLRequest *request, NSHTTPURLResponse *response, UIImage *image) { 
    // resize image 
    // set image on imageView 
} failure:^(NSURLRequest *request, NSHTTPURLResponse *response, NSError *error) { 
    // handle error 
}]; 

vorrei anche controllare questa pagina per incidenti correlati:

https://github.com/rs/SDWebImage/issues?q=is%3Aopen+is%3Aissue+label%3Acrash

Verificare se si sta utilizzando l'ultima versione di SDWebImage, altrimenti si potrebbe avere di controllare i problemi più grandi.

3

Con l'introduzione di iOS 8 ci sono alcuni eventi inaspettati che stanno accadendo anche noi dobbiamo tenerlo a mente.

App come il MIT Mobile, anche il punto Mile soffre del problema come il tuo, anche se non è molto diffuso.

Ecco i collegamenti ai bug per MIT & MilePoint.

com.apple.CFNetwork.addPersistCacheToStorageDaemon

CFNetwork è basso livello C API ed è avvolto da una maggiore classe livello come NSURLConnection.

così l'incidente si verifica durante un'operazione di rete

EXC_BAD_ACCESS

Significa che il messaggio è stato inviato a un indirizzo di memoria dove non c'è un'istanza di una classe per eseguirlo. Così risulta "cattivo accesso"

Quando accadrà?

  1. Un oggetto non inizializzato
  2. Un oggetto è già rilasciato
  3. qualcos'altro che non è molto probabile che accada

Come possiamo risolvere questo problema?

  • Potete prendere alcuni dei bug (numero 2) attivando NSZombie in Xcode

Abilitazione NSZombie:

Quando questa funzione è abilitata, un oggetto fittizio (uno zombi) è tenuto sul posto di ogni oggetto rilasciato, permettendo così di eseguire il debug di oggetti che sono stati già rilasciati.Molto semplice da attivare:

  1. Fare doppio clic l'eseguibile nelle “eseguibili” in XCode
  2. Aperto “argomenti” scheda In “Variabili da impostare per l'ambiente” (che è la lista in fondo, fare attenzione che uno si modifica)
  3. fare clic sul pulsante “+” e il nome della variabile immettere “NSZombieEnabled” e per il valore “sI”

Ora, invece di chiedersi cosa sta succedendo e quale oggetto esatto prodotto il problema , vedrai esattamente quale classe è la fonte del problema, a e farai il debug abbastanza velocemente.

Nota: Non lasciare abilitati gli zombi quando si invia l'app all'App store. Inoltre, è buona norma disabilitarli se non ne hai veramente bisogno.

  • Se si utilizza librerie di terze parti gentilmente aggiornarlo all'ultima

Nota:

il mio suggerimento è mai usare framework di terze parti a meno che la sua inevitabile perché la libreria stessa avrà bug volte che è fuori dal controllo dello sviluppatore e talvolta la libreria verrà aggiornata in ritardo rispetto all'SDK corrente. Puoi trovare ulteriori informazioni su di esso here

Spero che questo aiuti

Problemi correlati