ZeroTier Android app work report
Brenton Bostick
Mon Feb 27 2023
Overview
I started looking at the ZeroTier Android app when I joined in November 2022.
First items of work were fixing the many warnings when building Android app and ZeroTierOne itself.
There were crashes triggered by simply putting the device into landscape:
The landscape crash is about 20% of all reported events.
There were also crashes triggered by simply “playing around” with the app.
I believe the underlying cause of the toggle spamming is about another 20% of all reported events.
Looking at the code, there are TONS of warnings and lints in Android Studio.
Very low-hanging fruit to fix.
I have spent the last several weeks and months working on an update to the ZeroTier Android app and I believe it is in a good state.
What did I change?
The code is on branches in 2 repos:
https://github.com/zerotier/ZeroTierOne/tree/brenton/main
https://github.com/zerotier/ZeroTierAndroid/tree/brenton/main
I tried to maintain original style of code as much as possible and take a very conservative approach.
This is not a rewrite.
That being said, there are a lot of commits.
Redesigned the screens
old Network List screen and new Network List screen:
old Network Details screen and new Network Details screen:
old Add Network screen and new Add Network screen:
old Settings screen and new Settings screen:
Redesigned the icons
old icon and new icon:
Added splashscreen
Fixed all of the bugs I found
Fixed all of the lints I found
Added massive amount of error handling
Report unhandled pending exceptions in JNI callbacks.
Because java bytes, shorts, ints, and longs are signed, added protections for exceeding JSIZE_MAX in JNI code when going between signed and unsigned and in various constructors.
Lookup all jclass and jmethod once and cache
old way did a lot of unnecessary work constantly
Fixed bugs
ANDROID-0: multiple problems with building Android
ANDROID-1: last network cannot be removed
ANDROID-6: never updates to ONLINE
ANDROID-10: Notification not showing
ANDROID-11: eventBus was not registering on resume
ANDROID-17: bitwise operators in conditional statements
ANDROID-18: AddressType is always IPV6
ANDROID-30: bad byte comparisons in isIPv6Multicast
ANDROID-31: straighten out usage of NetworkConfig useCustomDNS
ANDROID-33: double-checked locking in greenDAO stuff
ANDROID-34: Thread safety
ANDROID-35: memory leak
ANDROID-36: ResultCode.java issues
ANDROID-37: VirtualNetworkStatus out-of-sync with ZT_VirtualNetworkStatus enum
ANDROID-38: stack corruption in onSendPacketRequested
ANDROID-39: NetworkType out-of-sync with VirtualNetworkType
ANDROID-40: VirtualNetworkConfigOperation out-of-sync with ZT_VirtualNetworkConfigOperation enum
ANDROID-41: still shows as connected after canceling VPN dialog
ANDROID-42: copy/paste error in VirtualNetworkConfig.java
ANDROID-44: Multiple NetworkList activities getting stacked
ANDROID-46: re-opening app does not show connected network
ANDROID-49: fix VirtualNetworkConfig.equals
ANDROID-50: RESULT_ERROR_BAD_PARAMETER typo
ANDROID-51: fieldName is uninitialized
ANDROID-52: synchronization bug with nodeMap
Other finished items
ANDROID-2: add splash screen
ANDROID-3: update icons
ANDROID-8: DNS work
ANDROID-13: OnBackInvokedCallback is not enabled for the application
ANDROID-21: redesign Join Network screen
ANDROID-22: redesign Network Details screen
ANDROID-23: redesign Network List screen
ANDROID-24: add view for when there are no networks yet
ANDROID-25: all string resources should be organized
ANDROID-29: Touch target size too small
ANDROID-32: remove Context.BIND_DEBUG_UNBIND
ANDROID-43: Big Database changes
ANDROID-45: Settings screen work
ANDROID-47: remove SQLCipher
ANDROID-48: cache field and method lookups
Known issues / loose ends / livewires
Try to quantify all known problems.
The toggle switches now feel “heavy” when toggling
There is now work being done when the switch toggles.
ONLINE being displayed, even when there is a problem
Should only set ONLINE when actually online.
ZeroTierOneService
All of the service binding / unbinding logic is not completely understood.
In logs:
stopSelfResult() failed!
stopService() returned false
~2 minute delay
The ~2 minute delay in disconnecting from VPN and then onDestroy() actually getting called.
onUnbind is called immediately, but then ~2 minutes later onDestroy is called and then service is actually destroyed.
Airplane mode
Currently, there is nothing to show that there is no network connectivity, just keeps going with no feedback
sending does fail, but this gets ignored in viaPath->send in Switch.cpp.
and is ignored in:
IncomingPacket.cpp
_doECHO
_path->send