## https://sploitus.com/exploit?id=9158EF99-80E6-5568-8BF3-FC4DAB14A820
# exp_baddial
XTC Children’s Watch Dial Plugin Remote Code Execution Vulnerability – PoC
## Vulnerability Overview
When the XTC i3launcher loads DEX plugins in the `.pl` format from the external storage `/sdcard/xtc/dial/compose/element/`, it performs the following operations:
- **Zero-signature verification**
- **Zero-integrity checks**
- Executes directly in the **UID 1000 (system)** process
- inherits all 70+ system permissions from i3launcher
Any attacker with write access to the storage can exploit this vulnerability by replacing the `.pl` file with malicious code. ## Reproducing Steps
### Prerequisites
- XTC children’s watch (with ADB enabled)
- ADB connection
- [XtcDialFactory](https://github.com/Starry2233/XtcDialFactory) installed (for compiling `.pl` plugins)
### 1. Create a combined dial containing step count shortcuts
Create a combined dial on the watch using the built-in **desktop customization** feature. This will generate the original legitimate plugin file:
```
/sdcard/xtc/dial/compose/element/shortcut_step/13/shortcut_step.pl
```
### 2. Disconnect the watch from the network
**Important:** Prevent local dial files from being overwritten by cloud synchronization.
```bash
adb shell settings put global wifi_on 0
adb shell svc wifi disable
```
Or manually turn off the network in the watch’s settings. ### 3. Compile the PoC plugin
Use [XtcDialFactory](https://github.com/Starry2233/XtcDialFactory) to compile the PoC code in this repository:
```bash
# Clone XtcDialFactory
git clone https://github.com/Starry2233/XtcDialFactory
cd XtcDialFactory
# Compile the PoC plugin
# XtcDialFactory will automatically perform javac → d8 → aapt processes
# Output: output/shortcut_step.pl
```
### 4. Deploy the PoC plugin
```bash
# Replace the original plugin with the malicious one
adb push ./output/shortcut_step.pl \
/sdcard/xtc/dial/compose/element/shortcut_step/13/shortcut_step.pl
```
### 5. Trigger the vulnerability
1. **Switch dials twice** (switch between any two dials)
- First switch: Launcher reloads the dial configuration
- Second switch: Forces the combined dial elements to be reinstantiated
2. **Click the newly appeared icon**
- The PoC plugin will display the text `[BadDial PoC]` in red
- Clicking it will execute the `id` command
3. **Observe the Toast output**
```
[BadDial]
uid=1000(system) gid=1000(system) groups=1000(system),3003(inet),...
```
### Verification
The message `uid=1000(system)` indicates that:
- ✅ Malicious code was successfully loaded from external storage
- ✅ No signature verification was required
- ✅ The code was executed with the highest system permissions (UID 1000)
## Impact of the Vulnerability
### Attacker’s Capabilities
Permissions available from UID 1000 include:
| Permission | Capabilities |
|------------|-----------------|
| SEND_SMS | Silently send SMS to expensive numbers |
| READ_SMS / RECEIVE_SMS | Read/intercept all SMS messages (including verification codes) |
| READ_CONTACTS | Steal contact information |
| ACCESS_FINE_LOCATION | Real-time GPS tracking |
| RECORD_AUDIO | Secretly record audio |
| CAMERA | Secretly take photos |
| INSTALL_PACKAGES | Silently install malicious apps |
| WRITE_SECURE_SETTINGS | Modify system security settings |
| READ_CALL_LOG | Read call logs |
### Attack Scenario
```
Malicious app (only requires WRITE_EXTERNAL_STORAGE)
↓
Place the malicious .pl file in /sdcard/xtc/dial/compose/element/
↓
User switches dials or restarts the device
↓
The malicious DEX is loaded in the UID 1000 process
↓
Execute arbitrary system commands, gaining full control over the device
```
## Fix Suggestions
1. **Enable signature verification**
- Verify the APK signature before loading `.pl`/`.cl` files
- Reject plugins with unauthorized signatures
2. **Isolate the execution environment**
- Use `android:isolatedProcess="true"` to load plugins
- Limit permissions through Binder IPC communication
3. **Remove external storage loading**
- Move the dial file to the `/data/data/com.xtc.i3launcher/` private directory
- Disable loading executable code from `/sdcard/`
4. **Principle of least privilege**
- i3launcher should not use `android:sharedUserId="android.uid.system"`
- Downgrade to a normal app UID
5. **Enable SELinux Enforcing**
- If SELinux is in the permissive mode, loaded plugins are not restricted by MAC
- Enforcing can increase the difficulty of attacks
## Timeline
- **2026-05-24**: Vulnerability discovered & PoC verified
- **Pending updates**: Manufacturers’ responses
## References
- [Android Security Best Practices - Dynamic Code Loading](https://developer.android.com/privacy-and-security/security-tips#DynamicCode)
- [CVE-2019-2215: Binder Use-After-Free](https://bugs.chromium.org/p/project-zero/issues/detail?id=1942)
## Disclaimer
This PoC is used solely for security research and educational purposes. Do not use on unauthorized devices. Users must bear their own legal responsibilities. ## License
MIT License – See the [LICENSE](LICENSE) file