adelphes / android-dev-ext

Android debugging support for VS Code
https://marketplace.visualstudio.com/items?itemName=adelphes.android-dev-ext
MIT License
212 stars 29 forks source link

Breakpoints in already-loaded classes don't work #139

Open fancypantalons opened 10 months ago

fancypantalons commented 10 months ago

I'm not sure if this is new behaviour in ADB, but it appears that the classprepare event doesn't get triggered if the JVM has already loaded a class.

The trouble is that the plugin relies on those events to learn about classes when setting breakpoints. So if you set a breakpoint before you start the debugger, then the event is registered before the class is loaded and everything works fine.

But if you set a breakpoint after the application has started in an already-loaded class, the plugin is never notified that the class exists and so the breakpoint can never be enabled.

I've thrown together a PR that changes this behaviour so that the plugin calls getAllClasses (which doesn't actually appear to be that slow?) if a class isn't known, and only after that fails does it then register for a classprepare event so that the JVM will notify the plugin when the class finally loads.

It all seems to work, both for BPs set before the debugger is started and after its already loaded. Feel free to take a look. To be honest it feels a little hacky, and I'm sure there's a more elegant approach possible, but I'm low on sleep and pretty far outta my depth!

adelphes commented 10 months ago

It's true that classprepare is used to setup breakpoints when the classes are loaded, but it should be the case that breakpoints added after a class is loaded should still work.

However, it's been a while since I've reviewed this code and it's definitely possible that something has broken. If I remember correctly, there is some uncertainty when it comes to mapping compiled classes to their source locations.

There is also the possibility that a class is loaded before the app is run and is somehow injected into the app without passing through the loading states - I don't remember encountering that, but it would cause issues and yes, I guess the solution would be to try and find the appropriate class from the list of all loaded classes.