Comando nm de Linux
Guía completa de comandos de Linux
nmEs una importante herramienta de línea de comandos en el sistema Linux, cuyo nombre completo es "Name List". Se utiliza para mostrar la información de símbolos en archivos objeto binarios (como archivos de biblioteca y ejecutables), y es una herramienta de uso común para programadores y para analizar archivos binarios.
Funciones principales
- Listar los símbolos en archivos objeto (funciones, variables, etc.)
- Mostrar el tipo y los atributos de los símbolos
- Ayudar a analizar problemas de enlace de programas
- Asistir en la depuración e ingeniería inversa
Sintaxis básica
nm [选项] 文件名
Descripción de opciones y parámetros comunes
| Opción | Descripción |
|---|---|
-a |
Mostrar todos los símbolos, incluidos los símbolos de depuración |
-g |
Mostrar solo símbolos externos (globales) |
-u |
Mostrar solo símbolos no definidos |
-D |
Mostrar símbolos dinámicos (para bibliotecas compartidas) |
-C |
Decodificar (demangle) los nombres de símbolos de C++ |
-l |
Mostrar el número de línea donde se encuentra el símbolo (requiere información de depuración) |
-S |
Mostrar el tamaño de los símbolos |
-t |
Especificar el formato de salida (d-decimal, o-octal, x-hexadecimal) |
--size-sort |
Ordenar por tamaño de símbolo |
--defined-only |
Mostrar solo símbolos definidos |
Explicación de tipos de símbolos
nmEl tipo de símbolo de salida se representa con una letra; los más comunes son:
| Tipo | Descripción |
|---|---|
| A | Símbolo absoluto, no se modifica durante el enlace |
| B/b | Símbolo en la sección de datos no inicializados (sección BSS) |
| D/d | Símbolo en la sección de datos inicializados |
| T/t | Símbolo en la sección de código (T indica global, t indica local) |
| U | Símbolo no definido (necesita enlazarse desde otros archivos) |
| W/w | Símbolo débil (weak symbol) |
| R/r | Símbolo en la sección de datos de solo lectura |
| C | Símbolo común (common symbol) |
| I | Referencia indirecta a otros símbolos |
Ejemplos de aplicación práctica
Ejemplo 1: Ver la tabla de símbolos de un archivo ejecutable
nm /bin/ls
Ejemplo de salida:
0000000000000000 A _IO_stdin_used 0000000000000000 R _fp_hw 0000000000000000 T _init 0000000000000000 W _ITM_deregisterTMCloneTable 0000000000000000 W _ITM_registerTMCloneTable 0000000000000000 W __cxa_finalize 0000000000000000 W __gmon_start__ 0000000000000000 T __libc_csu_fini 0000000000000000 T __libc_csu_init ...
Ejemplo 2: Ver solo los símbolos no definidos
nm -u /bin/ls
Ejemplo de salida:
U __ctype_toupper_loc
U __errno_location
U __overflow
U __stack_chk_fail
U __strtoul_internal
U _obstack_begin
U _obstack_newchunk
U abort
U access
...
Ejemplo 3: Ver los símbolos de un programa C++ (nombres decodificados)
nm -C my_program
Ejemplo de salida:
0000000000000000 T main 0000000000000000 T std::cout 0000000000000000 T std::basic_ostream<char, std::char_traits >& std::operator<< <std::char_traits >(std::basic_ostream<char, std::char_traits >&, char const*) ...
Ejemplo 4: Ver el tamaño de los símbolos y ordenarlos por tamaño
nm -S --size-sort my_library.so
Ejemplo de salida:
0000000000000001 0000000000000001 T func1 0000000000000002 0000000000000002 T func2 0000000000000004 0000000000000004 D global_var 0000000000000008 0000000000000008 B large_buffer ...
Escenarios de uso comunes
1. Resolver errores de enlace
Cuando encuentre el error "undefined reference", puede usarnmpara verificar qué símbolos no están definidos:
nm -u my_program.o
2. Analizar el contenido de archivos de biblioteca
Ver los símbolos exportados de una biblioteca compartida:
nm -D libexample.so
3. Comparar dos versiones de archivos binarios
Ejemplo
nm new_version > new.txt
diff old.txt new.txt
4. Buscar símbolos específicos
nm my_program | grep "main"
Precauciones
- Para archivos binarios que han sido despojados (stripped),
nmpuede que no se pueda mostrar información útil - Los archivos binarios de diferentes arquitecturas pueden requerir el uso de la cadena de herramientas de compilación cruzada
nm - Los símbolos dinámicos (en bibliotecas compartidas) requieren usar la opción
-Dpara verlos - Para programas C++, se recomienda usar siempre la opción
-Cpara decodificar los nombres de los símbolos
Técnicas avanzadas
Uso combinado con otras herramientas
Ejemplo
objdump -t my_program
# Usar readelf para ver la información del encabezado de archivos ELF
readelf -s my_program
Escribir scripts para analizar símbolos
Ejemplo
# Contar la distribución de tipos de símbolos
nm $1 | awk '{print $2}' | sort | uniq -c | sort -nr
Crear archivos de mapeo de símbolos
nm -n my_program > symbol_map.txt
Resumen
nmEl comando es una de las herramientas importantes para los desarrolladores de Linux; dominarlo permite:
- Comprender mejor la estructura de los programas
- Localizar rápidamente problemas de enlace
- Analizar el contenido de bibliotecas de terceros
- Asistir en la depuración e ingeniería inversa
A través de los usos básicos y ejemplos prácticos presentados en este artículo, ya deberías haber dominadonmlas funciones principales del comando. En el trabajo real, puedes utilizar flexiblemente varias opciones y parámetros según las necesidades específicas.
Otras extensiones