c++ - studio - Cómo utilizar la biblioteca de impulso(incluido shared_ptr) con Android NDK y STLport
android ndk location (4)
Cabe destacar que NDK r5 viene con STLport y GNU STL, por lo que los hacks aquí ya no serán necesarios ahora que hay a) soporte de STL b) soporte de excepción en el compilador NDK C ++.
Esto es más una respuesta que una pregunta, porque lo he descubierto, al menos en cuanto a la compilación limpia de la biblioteca. El principal problema para mí fue trabajar con shared_ptr.
Ingredientes:
Boost v. 1.45.0
La versión de STLport en http://www.anddev.org/viewtopic.php?p=29939 .
Versión r4b del NDK.
Direcciones:
En su archivo Android.mk, agregue:
LOCAL_CFLAGS += -DBOOST_EXCEPTION_DISABLE -D_STLP_NO_EXCEPTIONS -DOS_ANDROID -D_STLP_USE_SIMPLE_NODE_ALLOC
Elimine la llamada a __stl_throw_length_error en la línea 613 de stlport / stl / _string.h. Puede usar _STLP_NO_EXCEPTIONS si lo desea.
Edite boost / boost / smart_ptr / shared_ptr.hpp después de la línea 261 para deshacerse de la llamada a boost :: throw_exception en el constructor shared_ptr. Usé #ifndef BOOST_EXCEPTION_DISABLE en todo el cuerpo del método. (Pero vea la respuesta a continuación).
A continuación, debe proporcionar algunas piezas faltantes. Crea un archivo de encabezado con lo siguiente:
#ifdef OS_ANDROID
#include <exception>
namespace std
{
struct bad_alloc : public exception { bad_alloc operator()(){}};
}
#endif
y un archivo fuente con una clase de excepción reducida para admitir bad_alloc:
#ifdef OS_ANDROID
#include <exception>
namespace std
{
exception::exception() {}
exception::~exception() {}
const char* exception::what() const {}
}
#endif
Incluya el encabezado donde sea que esté incluyendo boost / shared_ptr.hpp. Compila la fuente y agrégala a tu biblioteca.
La versión actual de Android NDK (r9) ahora admite excepciones.
Las capacidades de los diversos tiempos de ejecución varían. Ver esta tabla:
C++ C++ Standard
Exceptions RTTI Library
system no no no
gabi++ yes yes no
stlport yes yes yes
gnustl yes yes yes
stlport puede ser utilizado en binarios no GPL. Todavía está marcado como experimental, pero puedes usarlo con clang y gcc.
Otra solución para shared_ptr en particular es usar boost :: intrusive_ptr en su lugar. Esto no siempre es posible, pero funcionó para mi situación.
Resultó que este enfoque no funciona del todo al compilar una biblioteca depurable. La biblioteca de versiones está compilada con -O2 que optimiza algunas infelicidades, pero la biblioteca de depuración está hecha con -O0, lo que revela algunos problemas adicionales. Además, no estaba muy contento de tener que editar los archivos de impulso. Entonces, con un estudio adicional, he encontrado la siguiente solución.
Primero, no edite ninguno de los archivos de impulso. En su lugar, agregue lo siguiente al encabezado dentro del espacio de nombres estándar:
struct bad_cast : public exception {bad_cast operator()(){}};
A continuación, agregue lo siguiente al archivo fuente:
namespace boost
{
void throw_exception(std::exception const&) {}
}
Esto ahora compila y enlaza con la aplicación incluso con android: debuggable = "true" en AndroidManifest.xml. No se ejecuta en el emulador, pero tampoco estaba haciendo eso antes de incluir esta biblioteca.