referência indefinida a `__android_log_print '

100

O que há de errado com meu arquivo make?

Android.mk

LOCAL_PATH := $(call my-dir)

include $(CLEAR_VARS)
LOCAL_MODULE    := foo
LOCAL_SRC_FILES := foo.c
LOCAL_EXPORT_LDLIBS := -llog
include $(BUILD_SHARED_LIBRARY)

foo.c

#include <string.h>
#include <jni.h>
#include <android/log.h>

#define  LOG_TAG    "foo"
#define  LOGI(...)  __android_log_print(ANDROID_LOG_INFO, LOG_TAG, __VA_ARGS__)

void test() {
    LOGI("test");
}

ndk-build

foo.c:9: undefined reference to `__android_log_print'
alex2k8
fonte

Respostas:

89

Tente o seguinte em seu Android.mkarquivo:

LOCAL_LDLIBS := -L$(SYSROOT)/usr/lib -llog
Ryan Reeves
fonte
1
O que é necessário para adicionar isso? Você poderia explicar em detalhes?
Dhasneem
está adicionando uma biblioteca android ao arquivo make - e funcionou para mim também
gheese
9
o -L é desnecessário. Aceite a outra resposta.
Jeff Allen de
5
Se estiver usando a nova integração Gradle NDK no Android Studio 1.3, você precisará adicionar ldLibs = ["android", "log"]as opções do android.ndk
Stephen Kaiser,
1
E se não estivermos usando o Android.mk?
cagdas
99

Você precisa adicionar

LOCAL_LDLIBS := -llog

para Android.mk

Kyle
fonte
1
corrigir. se houver várias bibliotecas, é necessário adicionar esta instrução para cada uma delas (após CLEAR VARS)
usuário13107
86

Se você usa o Android Studio e gradle, ele ignora o Android.mk. Adicione isso ao seu arquivo build.gradle:

android {
    defaultConfig {
        ndk {
            moduleName "your_module_name"
            ldLibs "log"
        }
    }
}
BoredT
fonte
7
Eu me pergunto onde isso está documentado. Eu também estava procurando por isso.
Randy Sugianto 'Yuku'
1
Eu estava recebendo "referência indefinida a '__android_log_print'" antes de adicionar ldLibs. Obrigado.
Denis Kniazhev
2
Adicionar isso corrigiu para mim. Apenas certifique-se de adicionar a ndkparte no build.gradle dentro da apppasta ao invés da parte na pasta do projeto (nome do módulo).
mathiass de
A partir do Gradle 2.5, use 'ldLibs + = "log"' ligeira mudança de sintaxe
Lorne K,
15
Isto não funcionou para mim. isto é o que eu tive que fazer:ldLibs.addAll(["android", "log"])
ᴛʜᴇᴘᴀᴛᴇʟ
29

Para Android Studio 2.2 e tools.build:gradle:2.2.0 usando CMake, adicione ou edite linha em CMakeLists.txt:

target_link_libraries(<your_library_name> 
                      android 
                      log)

Isso é conectar a biblioteca de registros à sua.

lewkka
fonte
16

Se você atualizar para o Android Studio 2.1, as respostas acima não funcionam, é necessário usar ldLibs.add () para carregar a lib como abaixo:

android.ndk {
    moduleName = "[the_module_name]"
    ldLibs.addAll(['android', 'log'])
}
DroidlikeCode
fonte
melhor resposta moderna (final de 2017)
Edgar Aroutiounian
7

Podemos vincular uma biblioteca compartilhada no Android de 3 maneiras. Nos 3 casos abaixo, as linhas mencionadas devem ser adicionadas emAndroid.mk

Então, aqui estão as três maneiras.

1. LOCAL_LDLIBS way
LOCAL_LDLIBS := -llog

Por algum motivo, se 1 não funcionar (não funcionou para mim), você pode tentar as 2 maneiras abaixo

2. LOCAL_LDFLAGS way
LOCAL_LDFLAGS := -llog

3. LOCAL_SHARED_LIBRARIES way
LOCAL_SHARED_LIBRARIES += liblog

Claro, você também precisa incluir #include <android/log.h> em seu arquivo C / H.

mk ..
fonte
6

Caso o projeto em que você está trabalhando tenha as seguintes características que diferem de outras respostas 'padrão':

  • Não usando o Android Studio
  • Não usando o Gradle e o CMake integrado
  • Nenhum Android.mk ou Application.mk usado para construir
  • Usando o CMake e o conjunto de ferramentas diretamente (talvez seu projeto seja baseado em Qt e sem usar QtCreator)

O seguinte uso de target_link_libraries o torna:

    find_library(ANDROID_LOG_LIB log)
    target_link_libraries(${TARGET_NAME} ${ANDROID_LOG_LIB})

Sendo TARGET_NAMEo nome do destino a construir (tendo-o configurado anteriormente com add_libraryou add_executable).

find_libraryé igualmente importante, bem como configurar o conjunto de ferramentas corretamente (use o conjunto de ferramentas fornecido pelo Android SDK em ANDROID_SDK_HOME/cmake/<version>/android.toolchain.cmakepara que ele configure o CMAKE_SYSROOTque é usado por find_comandos).

DNax
fonte
Única solução que me ajudou! Muito obrigado, gostaria de estendê-lo por um teste se a biblioteca fosse encontrada para um melhor feedback para o desenvolvedor, como aqui stackoverflow.com/a/37868829/10030695
ManuelTS
4

Sim, você precisa adicionar: LOCAL_LDLIBS := -llogcomo as outras respostas / comentários especificaram, no entanto, a pergunta original não especifica se ele usa a biblioteca jni como: LOCAL_JNI_SHARED_LIBRARIESou como LOCAL_REQUIRED_MODULES.

Posso dizer com certeza que ele o usou como: LOCAL_REQUIRED_MODULESpor causa do LOCAL_EXPORT_LDLIBS := -llogna pergunta ... a menos que tenha sido adicionado após uma edição.

Se você usar LOCAL_REQUIRED_MODULESa biblioteca compartilhada é instalada em / system / lib em vez de no apk, porque é um módulo obrigatório. Portanto, você precisará adicionar em LOCAL_LDLIBS := -L$(SYSROOT)/usr/lib -llogvez de apenas LOCAL_LDLIBS := -llogpara que quando o sistema de construção estiver construindo e vinculando a biblioteca compartilhada jni, ele terá as -llogdefinições no local correto, disponíveis para serem construídas abaixo $OUT/root/system/lib. Caso contrário, você continuará obtendo a mesma resposta, mesmo que apenas adicione LOCAL_LDLIBS := -llog.

Então, quem comentou que -Lnão é necessário, e a outra resposta estava correta, na verdade errou nessa situação.

SudoSURoot
fonte
Obrigado por realmente explicar o que está acontecendo!
Richard
4

Em vez de

Se estiver usando a nova integração Gradle NDK no Android Studio 1.3, você precisará adicionar ldLibs = ["android", "log"] às opções do android.ndk - Stephen Kaiser 24 de setembro às 4:20

usar ldLibs.addAll(["android", "log"])para o plugin experimental

sethbabs
fonte
3

Adicionar

LOCAL_SHARED_LIBRARIES:= \
        libbinder                       \
        liblog                          \

para Android.mk

user3535040
fonte
2
Por quê? Explique por que essa resposta deve funcionar para o autor da pergunta.
L0j1k de
1

Isso me ajudou:

Android.mk

    LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)

LOCAL_MODULE    := nativeDemo
LOCAL_SRC_FILES := main.cpp
LOCAL_LDLIBS += -llog

include $(BUILD_SHARED_LIBRARY)
NickUnuchek
fonte
0

No android studio versão 2.2 e superior, há suporte embutido para CPP quando você cria um novo projeto. Além disso, o liblog.so é incluído por padrão. Nada a ser feito além de incluir o arquivo de cabeçalho (android / log.h).

Checkout app / CMakeLists.txt que é criado pelo estúdio quando criamos um novo projeto de estúdio Android. Podemos ver que os blocos find_library () e target_link_libraries () para loglib já estão presentes.

Além disso, preste atenção à sintaxe da função. Deveria ser:

__android_log_print (prioridade int, const char * tag, const char * fmt, ...);

No meu caso, deixei de fora o parâmetro de tag e acabei gastando bons 3 dias para descobri-lo.

Mais sobre CMake: Adicionar código C e C ++ ao seu projeto

Praveen Kumar KR
fonte
0

-DCMAKE_CXX_FLAGS = "- llog" me ajuda

James
fonte
0

adicionar LOCAL_SHARED_LIBRARIES:= liblog ao Android.mk pode resolver meu problema. Isso ocorre porque o __android_log_printé definido em libLog

nld2019
fonte
0

PARA construir com Android.bp, siga a solução abaixo:

Neste - android_log_print é definido no NDK, então, para isso, já existe uma biblioteca disponível. Use a biblioteca " liblog " usando a tag shared_libs , consulte o código abaixo:

target: {
        android: {
            cppflags: [
                "-g",
                "-DUSE_LIBLOG",
            ],
            shared_libs: ["liblog"], // can use other dependency if required.
        },
        darwin: {
            enabled: false,
        },
    },  
Budhdi Sharma
fonte