the programming language docs ios swift lldb

ios - programming - swift reference



LLDB(Swift): conversión de dirección sin formato en tipo utilizable (11)

¿Hay un comando LLDB que puede convertir una dirección sin procesar en una clase Swift utilizable?

Por ejemplo:

(lldb) po 0x7df67c50 as MKPinAnnotationView

Sé que esta dirección apunta a un MKPinAnnotationView, pero no está en un marco que pueda seleccionar. Pero, quiero convertir la dirección sin procesar en un MKPinAnnotationView para poder examinar sus propiedades. es posible?


A partir de Xcode 8 / Swift 3, esto es lo que funcionó para mí. (Esto se basa en la respuesta de @ sfaxon ).

(lldb) expr -l Swift -- import UIKit (lldb) expr -l Swift -- let $nav = unsafeBitCast(0x1030ff000, to: UINavigationController.self)


Bajo Xcode 8.2.1 y Swift 3, el comando lldb po o p no funcionará con la variable escrita. Deberá usar el comando rápido print para examinar las propiedades de la instancia del objeto escrito. (¡Gracias a la respuesta de cbowns !) Por ejemplo:

(lldb) expr -l Swift -- import UIKit (lldb) expr -l Swift -- let $pin = unsafeBitCast(0x7df67c50, to: MKPinAnnotationView.self) (lldb) expr -l Swift -- print($pin.alpha)


El formato lldb para la expression parece haber cambiado en Xcode 7.3. Lo siguiente me ayudó a comenzar:

(lldb) expr -l Swift -- import UIKit (lldb) expr -l Swift -- let $view = unsafeBitCast(0x7fb75d8349c0, UIView.self)


Gracias a todas las respuestas anteriores, unsafeBitCast también funciona bien con la aplicación Xcode 8.3.2 / Swift 3 / macOS / Cocoa.

Memorizar una dirección de instancia actual

(lldb) p tabView.controlTint (NSControlTint) $R10 = defaultControlTint (lldb) p self (LearningStoryboard.NSTabViewController) $R11 = 0x00006080000e2280 { .....

Más tarde, examínelos

(lldb) p unsafeBitCast(0x00006080000e2280, to: NSTabViewController.self).tabView.controlTint (NSControlTint) $R20 = graphiteControlTint (lldb) p $R11.tabView.controlTint (NSControlTint) $R21 = graphiteControlTint

Si sucede algo como esto

(lldb) p unsafeBitCast(0x00006080000e2280, to: NSTabViewController.self).tabView.controlTint error: use of undeclared identifier ''to'' (lldb) p $R11.tabView.controlTint error: use of undeclared identifier ''$R11''

asegúrese de elegir uno de los marcos de pila del código fuente de Swift en lugar del ensamblador.

Es probable que suceda cuando la aplicación se detuvo haciendo clic en el botón Pausa o se detuvo con una excepción. Al elegir un marco de pila en consecuencia, deje que lldb infiera un lenguaje de programación adecuado.


La forma más fácil, rápida 4

expr unsafeBitCast(0x7df67c50, to: MKPinAnnotationView.self)


La respuesta de @Xi Chen funciona perfectamente cuando su sesión LLDB se inició en un contexto Swift. Sin embargo, en algunos casos puede haberse detenido en un punto de interrupción fuera de un contexto Swift; por ejemplo, cuando es un punto de interrupción simbólico para la API Objective-C.

error: unknown type name ''let'' error: use of undeclared identifier ''unsafeBitCast''

En ese caso, deberá hacerlo a la antigua usanza Objective-C:

e MKPinAnnotationView *$pin = (MKPinAnnotationView *)0x7df67c50

y ahora puedes usar $pin como lo harías.


Me tomó más tiempo darme cuenta de que me gustaría admitirlo. Es similar a la respuesta de @afinlayson, pero con una mejor explicación (¡espero!) Y sintaxis fija

Si desea verificar las propiedades de un objeto utilizando el depurador de jerarquía de vistas de Xcode, esto funcionará: está en contexto objc de forma predeterminada, por lo que deberá cambiarlo a contexto Swift

  1. Primero importe su proyecto (si desea utilizar algunas de las clases definidas allí)

expr -l Swift -- import <YOUR PROJECT NAME>

  1. Transmita el objeto usando su dirección de memoria a la clase que desee

expr -l Swift -- let $vc = unsafeBitCast(0x7fb7c51cb270, to: <YOUR PROJECT NAME>.<YOUR CUSTOM CLASS NAME>.self)

  1. Acceda a cualquier valor que desee del objeto

expr -l Swift -- print($vc.<PROPERTY NAME>)

Ejemplo:

expr -l Swift -- import Football

expr -l Swift -- let $vc = unsafeBitCast(0x7fb7c51cb270, to: Football.Ball.self)

expr -l Swift -- print($vc.velocity)


Para clases personalizadas necesita importar su proyecto

expr -l Swift -- import MyTestProject expr -l Swift -- let $vc = unsafeBitCast(0x7fad22c066d0, ViewController.self) expr -l Swift -- print($vc.view)


Puede usar la función unsafeBitCast de Swift para emitir una dirección a una instancia de objeto:

(lldb) e let $pin = unsafeBitCast(0x7df67c50, MKPinAnnotationView.self) (lldb) po $pin

Entonces puede trabajar con $pin como de costumbre: acceder a propiedades, métodos de llamada, etc.

Consulte este artículo para obtener más información: Volcado rápido de memoria .


Versión Objective-C

po ((MKPinAnnotationView *)0x7df67c50).alpha


po es un alias, lo que significa que se puede anular. Puede anular po manejando direcciones hexadecimales usando objc:

command regex po s/(0x[[:xdigit:]]+)/expression -l objc -O -- %1/ s/(.+)/expression -O -- %1/

Para ver qué efecto tiene esto, puede decirle a lldb que expanda estos alias:

(lldb) settings set interpreter.expand-regex-aliases true

También he creado https://github.com/kastiglione/swift_po , que es un sustituto po para Swift. Maneja direcciones de objetos y tiene algunas otras mejoras también.