Intentando leer un archivo .trace de Xcode Instruments. ¿Cuál es el formato de archivo de un archivo .trace?

Estoy escribiendo un sistema de perfiles automatizado para perfilar diferentes pantallas intensivas de GPU en mi aplicación. He intentado utilizar ‘XCode Instruments’ para esto, con el instrumento ‘OpenGL ES Driver’ que captura los datos de uso de la GPU.

Mi sistema automatizado ejecuta Xcode Instruments desde la línea de comandos que ejecuta la aplicación, los perfiles y captura los datos, y escribe los datos en un archivo “.trace”.

Ahora quiero poder abrir el archivo de rastreo y leer los datos de rastreo usando mi sistema de perfil automatizado, para poder informar a los desarrolladores de la aplicación de cómo funcionan las distintas partes de la aplicación.

Sin embargo, no puedo encontrar ninguna forma de leer el archivo de rastreo. Parece ser un paquete que contiene varios directorios, y allí está enterrado un archivo .zip que parece contener algunos datos binarios. ¿Cómo se analizan los datos en este archivo?

El sistema Instruments parece bastante sofisticado, y me ha sorprendido lo difícil que ha sido acceder a los datos de seguimiento que produce.

¿Alguien sabe cómo analizar el archivo de rastreo?

Actualmente estoy usando XCode 4.6.1

Muy bien, para responder a la pregunta principal: los datos en el archivo .zip son un conjunto de datos que se serializaron con la clase NSArchiver (tienen un encabezado bastante distintivo al abrirse con una herramienta hexadecimal (utilicé hex demon), por lo que esa fue la primera pista). Es bastante fácil de leer, todo lo que tienes que hacer es hacer una llamada a NSUnarchiver , al menos esa es la teoría. Antes de entrar en los detalles, aquí hay una aplicación de ejemplo muy simple que arroja algunas informaciones: https://github.com/JustSid/Traced

Entonces, el problema con NSArchiver y NSUnarchiver es que antes que nada necesitas tener todas las clases que fueron archivadas, y segundo, debes leer los datos en el orden en que fueron archivados (ese fue el complicado Poco, utilicé class-dump para volcar la interfaz para algunas de las clases requeridas y luego intenté desarchivar el objeto de datos por objeto y ver lo que obtuve. Afortunadamente, NSArchiver muere con mensajes de error descriptivos, si hay una clase falta, le dirá cuál es su nombre). El mayor problema que tuve fue que el binario de Instruments y los frameworks usados ​​no contienen todas las clases que necesitaba, en particular el archivo contiene datos serializados de una clase llamada XRVideoCardRun . Supongo que el archivo .template dentro del paquete .trace contiene una biblioteca dinámica con la clase requerida (es decir, tiene más de 300 kb de tamaño y contiene muchos blobs (por cierto, es una lista binaria)). Era demasiado flojo para extraer los datos binarios y ejecutar class-dump contra, y tuve la suerte de que la mayoría de los datos que salieron del archivo eran consistentes con lo que esperaba ver para la superclase, XRRun (que encontré en uno de los marcos de instrumentos), con la excepción de una matriz que contiene diccionarios, cuyo contenido se parecía a los datos de muestra.

Entonces, el rest fue simplemente combinar todo junto. Si observa la aplicación de muestra, la parte más interesante debería ser el archivo XRRun.m y .h . Contienen un poco de documentación y algunas piezas sobre cómo extraer los datos de las muestras, aunque es probable que desee reemplazar esto con su propia lógica para su automatización. Espero eso ayude.

La aplicación arrojada contra el archivo de muestra muestra esto:

 Run 1, starting at 24.05.13 17:42:16, running until 24.05.13 17:42:28 Sample 0: FPS: 27 Device: 0% Renderer: 0% Tiler: 0% Timestamp: 1.012740 Sample 1: FPS: 35 Device: 11% Renderer: 10% Tiler: 2% Timestamp: 2.018574 Sample 2: FPS: 34 Device: 33% Renderer: 32% Tiler: 7% Timestamp: 3.026101 Sample 3: FPS: 59 Device: 59% Renderer: 59% Tiler: 16% Timestamp: 4.032030 Sample 4: FPS: 60 Device: 59% Renderer: 58% Tiler: 16% Timestamp: 5.038990 Sample 5: FPS: 59 Device: 59% Renderer: 58% Tiler: 16% Timestamp: 6.046022 Sample 6: FPS: 59 Device: 57% Renderer: 53% Tiler: 17% Timestamp: 7.051187 Sample 7: FPS: 60 Device: 67% Renderer: 66% Tiler: 14% Timestamp: 8.057343 Sample 8: FPS: 59 Device: 64% Renderer: 64% Tiler: 11% Timestamp: 9.064914 Sample 9: FPS: 60 Device: 67% Renderer: 67% Tiler: 11% Timestamp: 10.072592 Sample 10: FPS: 59 Device: 65% Renderer: 65% Tiler: 15% Timestamp: 11.080248 

(PD: si el formato cambia, la aplicación se romperá también …)

Estoy intentando analizar el documento .trace utilizando los marcos no documentados enviados con Instruments. Ahora está trabajando con Time Profiler y no debería ser difícil hacerlo funcionar con otras plantillas de instrumentos, con un poco más de trabajo de ingeniería inversa.

Hay bastantes marcos incluidos con Instruments como se puede ver en /Applications/Xcode.app/Contents/Applications/Instruments.app/Contents/Frameworks .

Sin embargo, solo tenemos que vincularnos con estos dos:

  • DVTInstrumentsFoundation.framework
  • InstrumentsPlugIn.framework

Otra cosa que debe saber antes de comenzar es que las plantillas de instrumento son en realidad complementos en /Applications/Xcode.app/Contents/Applications/Instruments.app/Contents/PlugIns .

Por ejemplo, SamplerPlugin.xrplugin es para Time Profiler.

El código es breve y está comentado: https://github.com/Qusic/TraceUtility

.trace es en realidad una carpeta y tiene un zip 1.run.zip en .trace / instruments_data / y después de algunas carpetas encontrarás el zip. Descomprímelo y obtendrá 1.run. No estoy seguro de cómo decodificar eso. La mejor manera es llamar – instrumentos .trace – esto se abrirá en los instrumentos con los detalles.

Es posible que no pueda analizar el archivo Trace directamente con un script, pero puede exportarlo a un archivo CSV que puede analizarse mediante un script o colocarse en Excel, Numbers, etc. Incluso puede agregar la exportación como una CSV para sus pruebas automatizadas, dependiendo de cómo se hace.