Pregunta

Estoy buscando una buena respuesta al estilo de desbordamiento de pila a la primera pregunta en la antigua entrada del blog ++ Code C tamaño , que voy a repetir a continuación:

  

Realmente me gustaría un poco de herramienta (idealmente, g ++ basa) que me muestra qué partes del código compilado / ligado se generan a partir de qué partes del código fuente en C ++. Por ejemplo, para ver si una plantilla particular está siendo instanciado para cientos de diferentes tipos (que se puede fijar a través de una plantilla de especialización) o si el código está siendo inlined en exceso, o si funciones particulares son más grandes de lo esperado.

¿Fue útil?

Solución

Parece como algo como esto debe existir, pero no he usado nada parecido. Puedo decirle cómo me gustaría ir sobre secuencias de comandos esto juntos, sin embargo. Es probable que existan más rápidas y / o más atractivas formas de hacerlo.

Primera algunas cosas que usted ya sabe:

El comando addr2line lleva en una dirección y se puede decir que el código fuente que el código máquina allí implementos. Las necesidades ejecutables que se construirán con símbolos de depuración, y es probable que no van a querer optimizarlo tanto (-O0, -O1, o -Os es, probablemente, lo más alto que gustaría ir al principio de todos modos). addr2line tiene varias banderas, y usted quiere leer su página de manual, pero que sin duda necesita utilizar -C o --demangle si quieres ver C ++ nombres de las funciones que tienen sentido en la salida.

El comando objdump puede imprimir todo tipo de cosas interesantes acerca de las cosas en muchos tipos de archivos de objetos. Una de las cosas que puede hacer es imprimir una tabla que representa los símbolos en los que se refiere por un archivo objeto (incluyendo los ejecutables).

Ahora, lo que quiere hacer con lo siguiente:

Lo que usted quiere es para objdump para decirle la dirección y el tamaño de la sección .text. Aquí es donde vive código real de máquina ejecutable. Hay varias maneras de hacer esto, pero la más fácil (para esto, de todos modos) es, probablemente, para que hagas:

objdump -h my_exe | grep text

Esto debe resultar en algo como:

 12  .text       0000049  000000f000  0000000f000 00000400  2**4

Si no grep que sería darle un encabezado como:

Idx  Name        Size     VMA         LMA         File off  Algn

creo que para los ejecutables del VMA y LMA deben ser los mismos, por lo que no importa que se utilice, pero creo que es la mejor LMA. También querrá el tamaño.

Con el LMA y el tamaño que se puede llamar repetidamente addr2line pidiendo el origen código fuente del código de máquina. No estoy seguro de cómo funcionaría si aprobó una dirección que estaba dentro de una instrucción, pero creo que debería funcionar.

addr2line -e my_exe <address>

La salida de este será una ruta / nombre de archivo, un colon, y un número de línea. Si se va a contar con la ocurrencia de cada ruta / archivo único: num usted debe ser capaz de mirar a los que tienen los más altos cargos. Perl hash utilizando la ruta / archivo: num como la clave y un contador como el valor sería una manera fácil de implementar esto, aunque hay maneras más rápido si usted encuentra que corre demasiado lento. También podría filtrar las cosas que se pueden determinar no necesitan ser incluidos temprano. Para mostrar su salida es posible que desee filtrar las diferentes líneas de la misma función, pero es posible que observe que las diferentes líneas dentro de una función tiene diferentes cargos, que podrían ser interesantes. De todos modos, lo que podía hacerse ya sea haciendo addr2line le diga el nombre de la función o el uso de objdump -t en el primer paso y el trabajo de una función a la vez.

Si ves que algún código de la plantilla o de otras líneas de código se están presentando en sus ejecutables más a menudo de lo que cree que deberían entonces usted puede localizar fácilmente y tener una mirada más cercana. Macros y funciones en línea pueden mostrar terminan manifestándose distinta a la esperada.

Si no lo sabía, y objdump addr2line son de la href="https://en.wikipedia.org/wiki/GNU_Binutils" rel="nofollow noreferrer"> GNU binutils paquete

Otros consejos

Si usted está buscando para encontrar fuentes de exceso de código en su código C ++, lo he usado 'nm' para eso. El siguiente comando lista de todos los símbolos en su aplicación con el código y de datos más grandes trozos de la parte superior:

nm --demangle --print-size --size-sort --reverse-sort <executable_or_lib_name> | less

Me escribió recientemente una herramienta, hinchazón de culpa , que hace algo similar a lo que < a href = "https://stackoverflow.com/questions/2509734/break-down-c-code-size/2510872#2510872"> nategoose propuesto .

No sé si va a ayudar, pero hay una bandera gcc para escribir el código ensamblador genera un archivo de texto para su examen.

" S     Se usa en vez de -c para hacer que el archivo fuente en ensamblador que se genere, usando .s como la extensión, en lugar del archivo objeto. Esto puede ser útil si tiene que examinar el código ensamblador generado. "

En la mayoría de los compiladores de C no es una forma de generar un archivo .map. Este archivo lista todas las bibliotecas compiladas su dirección y su tamaño. Puede utilizar ese archivo de mapa para ayudarle a determinar qué archivos debe estar buscando para optimizar primero.

No sé cómo asignar código-> generada ensamblaje en general.

Para instancias plantilla que puede usar algo como "cadenas -a | grep | sort -u | gc ++ filt". Para tener una idea aproximada de lo que está siendo creado

Los otros dos artículos que usted ha mencionado bastante subjetivo parecen realmente. ¿Qué es "demasiado" procesos en línea? ¿Le preocupa su archivo binario se está inflado? La única cosa que hacer no es en realidad entran en el BGF y desmonte la persona que llama para ver lo que genera, nada para comprobar si hay "excesiva" inline en general.

Para el tamaño de la función, de nuevo tengo curiosidad por qué es importante? ¿Estás tratando de encontrar el código que se expande de forma inesperada cuando se compila? ¿Cómo se puede incluso definir cuál es el tamaño esperado es una herramienta para examinar? Una vez más, siempre se puede disimular cualquier función que crea que está compilando a mucho más de lo que desea el código, y ver exactamente lo que el compilador está haciendo.

En Visual C ++, esto es esencialmente lo archivos PDB son para.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top