Dirección de stack no válida y señal fatal 11

De vez en cuando, mi aplicación se bloqueará y mi registro leerá:

@@@ ABORTING: INVALID HEAP ADDRESS IN dlfree Fatal signal 11 (SIGSEGV) at 0xdeadbaad (code=1) 

A veces code=2 , pero siempre la Fatal signal 11 y la invalid heap address .

Intenté investigar qué significa esto y cómo solucionarlo. Este hilo ha sido de lo más útil ; Sin embargo, todavía no tengo una solución.

El error ocurre cuando ejecuto un par de AsyncTasks para descargar varias imágenes.

Esta es mi principal AsyncTask

 public class FetchArtistImages extends AsyncTask implements Constants { private final WeakReference contextReference; public FetchArtistImages(Context context) { contextReference = new WeakReference(context); } @Override protected String[] doInBackground(Void... params) { String[] projection = new String[] { Audio.Artists._ID, Audio.Artists.ARTIST }; String sortOrder = Audio.Artists.DEFAULT_SORT_ORDER; Uri uri = Audio.Artists.EXTERNAL_CONTENT_URI; Cursor c = contextReference.get().getContentResolver() .query(uri, projection, null, null, sortOrder); ArrayList artistIds = new ArrayList(); if (c != null) { int count = c.getCount(); if (count > 0) { final int ARTIST_IDX = c.getColumnIndex(Audio.Artists.ARTIST); for (int i = 0; i < count; i++) { c.moveToPosition(i); artistIds.add(c.getString(ARTIST_IDX)); } } c.close(); c = null; } return artistIds.toArray(new String[artistIds.size()]); } @Override protected void onPostExecute(String[] result) { for (int i = 0; i < result.length; i++) { new LastfmGetArtistImages(contextReference.get()).executeOnExecutor( AsyncTask.THREAD_POOL_EXECUTOR, result[i]); } super.onPostExecute(result); } 

Aunque intenté investigar qué pasa con esto, aún me encuentro perdido a la hora de solucionarlo. Si alguien tiene alguna idea, definitivamente apreciaría verla. El error no se produce cada vez que execute mis AsyncTasks , pero no puedo encontrar mucho de un patrón para ayudar a aislar por qué ocurre esto. Hay un par de otros hilos en SO sobre la fatal signal 11 , pero no proporcionan mucha ayuda en mi caso.

Me encontré con el mismo problema y lo tuve en un estado reproducible. Este es el error que estaba recibiendo:

08-04 17: 37: 05.491: A / libc (4233): @@@ ABORTO: DIRECCIÓN DE HEAP NO VÁLIDA EN dlfree 08-04 17: 37: 05.491: A / libc (4233): señal fatal 11 (SIGSEGV) en 0xdeadbaad (código = 1)

Lo que se reduce a una llamada de función se realiza a partir de dos hilos diferentes al mismo tiempo.

Más específicamente, esta función era el método close () de BluetoothSocket.

Revisé el código fuente en este sitio web , y la llamada no está sincronizada (no estoy seguro de si esto cambió, ya que es de Android 2.1).

En cualquier caso, ¿quizás tengas una situación similar en la que una llamada a función se realice a partir de varios hilos? No puedo decir con certeza del código fuente que está mostrando.

¿También has intentado no usar THREAD_POOL_EXECUTOR? De acuerdo con la guía de desarrollo de Android :

Cuando se introdujo por primera vez, las AsyncTasks se ejecutaron en serie en una única cadena de fondo. Comenzando con DONUT, esto se cambió a un conjunto de subprocesos que permite que varias tareas funcionen en paralelo. Comenzando con HONEYCOMB, las tareas se ejecutan en un único hilo para evitar errores de aplicación comunes causados ​​por la ejecución paralela.

Ayer tuve el mismo error. Siempre sucedió, pero no siempre de manera consistente. Lo que me causó esto hasta ahora no ha sido mencionado.

Pensé que podría tener un problema similar porque también estaba tratando con hilos, sin embargo, eliminé todo el enhebrado y el problema todavía estaba ocurriendo. Finalmente, después de un montón de declaraciones impresas, pude rastrearlo hasta una clase que había instanciado, que tenía un puntero como miembro privado, pero olvidé inicializar el puntero.

Más tarde, cuando esa clase destruyó, intentaba eliminar el puntero, sin embargo, debido a que el puntero no se inicializó a NULL, puede tener o no algún valor de basura, por lo que a veces no causaría un locking y otras veces lo haría. Probablemente sea porque cuando el valor de basura era una ubicación de memoria que no me pertenece o cuando lo hace y borro algo importante, causa el locking / error.

Aquí hay un ejemplo simplificado del problema que encontré:

 class BadFoo { public: BadFoo() {} // BAD! We didn't initialize the pointer ~BadFoo() { if (myPtr) { delete myPtr; } } // OTHER MEMBER FUNCTIONS HERE private: int* myPtr; } class GoodFoo { public: GoodFoo() : myPtr(NULL) {} // GOOD! Can't be garbage value now ~GoodFoo() { if (myPtr) { delete myPtr; } } // OTHER MEMBER FUNCTIONS HERE private: int* myPtr; } 

Es interesante notar que este locking no ocurrió en mi Transformer Prime, pero sí en mi Nexus4. ¡Solo sirve para mostrar que debemos probar en múltiples dispositivos! Hasta ahora, el Nexus gana al ayudarme a rastrear errores, ya que parece ser mucho más exigente.