Skip to main content

ios_core/
lib.rs

1//! Unified high-level API for iOS device interaction.
2//!
3//! This crate ties together device discovery, pairing, tunneling, and service access
4//! into a single ergonomic API. It is the recommended entry point for library consumers.
5//!
6//! Key types:
7//! - [`ConnectedDevice`] - connected device handle with service access
8//! - [`discovery`] - USB and network device discovery
9//! - [`TunnelManager`] and [`TunMode`] - CoreDevice tunnel lifecycle helpers
10//! - [`XpcValue`] - RemoteXPC value model for iOS 17+ services
11//! - [`XpcClient`] - RemoteXPC client, available when the `tunnel` feature is enabled
12//!
13//! Service implementations are feature gated under [`services`]. The grouped feature flags
14//! are intended for common consumers:
15//!
16//! - `classic` enables lockdown-era services such as AFC, syslog, screenshots, and profiles.
17//! - `developer` enables DTX/Instruments, testmanager, debugserver, WebInspector, and related tools.
18//! - `ios17` enables CoreDevice/RSD services, mDNS discovery, and userspace tunnel support.
19//! - `management` enables restore, preboard, companion, arbitration, and device management helpers.
20//! - `full` enables the broad CLI surface.
21//!
22//! CoreDevice service availability is discovered from the device's RSD directory at runtime.
23//! Do not infer support from ProductVersion alone; newer devices can expose the tunnel and
24//! RSD while omitting a specific feature service such as fileservice.
25//!
26//! Internal transport modules are not part of the public API. Use top-level
27//! re-exports for supported types:
28//!
29//! ```
30//! use ios_core::{pair_new_device, PairedCredentials, PairingTransportError};
31//! use ios_core::{default_pair_record_path, LockdownClient, LockdownError, PairRecord};
32//! use ios_core::{archive_string, NsUrl, XcTestConfiguration, XctCapabilities};
33//! use ios_core::{TunMode, TunnelError, TunnelHandle, TunnelInfo, TunnelManager};
34//! ```
35//!
36//! ```compile_fail
37//! use ios_core::proto::nskeyedarchiver_encode::archive_string;
38//! ```
39//!
40//! ```compile_fail
41//! use ios_core::lockdown::PairRecord;
42//! ```
43//!
44//! ```compile_fail
45//! use ios_core::pairing_transport::UNTRUSTED_SERVICE_NAME;
46//! ```
47//!
48//! ```compile_fail
49//! use ios_core::tunnel::TunMode;
50//! ```
51//!
52//! ```compile_fail
53//! use ios_core::xpc::RsdHandshake;
54//! ```
55
56pub mod credentials;
57/// Device connection orchestration and service access helpers.
58pub mod device;
59/// USB and network discovery helpers.
60pub mod discovery;
61/// Shared high-level error type.
62pub mod error;
63pub(crate) mod lockdown;
64pub(crate) mod mux;
65#[cfg(all(feature = "tunnel", feature = "mdns"))]
66pub(crate) mod pairing_transport;
67pub(crate) mod proto;
68#[cfg(feature = "tunnel")]
69pub(crate) mod psk_tls;
70pub mod services;
71#[cfg(test)]
72pub(crate) mod test_util;
73pub(crate) mod tunnel;
74pub(crate) mod xpc;
75
76pub use credentials::{PersistedCredentials, RemotePairingRecord};
77#[cfg(feature = "mdns")]
78pub use device::discover_paired_mobdev2_devices;
79pub use device::{
80    connect_direct_usb_tunnel, connect_remote_pairing_tunnel, connect_tcp_lockdown_tunnel,
81    ConnectOptions, ConnectedDevice, InternationalConfiguration, PairedMobdev2Device,
82    ServiceStream,
83};
84#[cfg(feature = "mdns")]
85pub use discovery::{browse_mobdev2, browse_remotepairing, BonjourService, MdnsDevice};
86pub use discovery::{DeviceEvent, DeviceInfo};
87pub use error::CoreError;
88pub use lockdown::{
89    default_pair_record_path, handshake_only_service_tls, recv_lockdown, send_lockdown,
90    start_lockdown_session, start_service, strip_service_tls, wrap_service_tls, GetValueRequest,
91    GetValueResponse, LockdownClient, LockdownError, PairRecord, PairRecordError, QueryTypeRequest,
92    QueryTypeResponse, RemoveValueRequest, ServiceInfo, SetValueRequest, StartServiceRequest,
93    StartServiceResponse, StartSessionRequest, StartSessionResponse, StopSessionRequest,
94    ValueOperationResponse, CORE_DEVICE_PROXY, LOCKDOWN_PORT,
95};
96#[cfg(feature = "supervised-pair")]
97pub use lockdown::{pair_supervised, save_pair_record, FullPairRecord};
98pub use mux::MuxClient;
99#[cfg(all(feature = "tunnel", feature = "mdns"))]
100pub use pairing_transport::{pair_new_device, PairedCredentials, PairingTransportError};
101pub use proto::nskeyedarchiver_encode::{
102    archive_array, archive_bool, archive_data, archive_dict, archive_float, archive_int,
103    archive_nsurl, archive_null, archive_string, archive_uuid, archive_xct_capabilities,
104    archive_xctest_configuration, NsUrl, XcTestConfiguration, XctCapabilities,
105};
106#[cfg(feature = "accessibility_audit")]
107pub use services::accessibility_audit;
108#[cfg(feature = "afc")]
109pub use services::afc;
110#[cfg(feature = "amfi")]
111pub use services::amfi;
112#[cfg(feature = "apps")]
113pub use services::apps;
114#[cfg(feature = "arbitration")]
115pub use services::arbitration;
116#[cfg(feature = "companion")]
117pub use services::companion;
118#[cfg(feature = "crashreport")]
119pub use services::crashreport;
120#[cfg(feature = "debugserver")]
121pub use services::debugserver;
122#[cfg(feature = "deviceinfo")]
123pub use services::deviceinfo;
124#[cfg(feature = "diagnostics")]
125pub use services::diagnostics;
126#[cfg(feature = "diagnosticsservice")]
127pub use services::diagnosticsservice;
128#[cfg(feature = "dproxy")]
129pub use services::dproxy;
130#[cfg(feature = "dtx")]
131pub use services::dtx;
132#[cfg(feature = "fetchsymbols")]
133pub use services::fetchsymbols;
134#[cfg(feature = "file_relay")]
135pub use services::file_relay;
136#[cfg(feature = "fileservice")]
137pub use services::fileservice;
138#[cfg(feature = "heartbeat")]
139pub use services::heartbeat;
140#[cfg(feature = "idam")]
141pub use services::idam;
142#[cfg(feature = "imagemounter")]
143pub use services::imagemounter;
144#[cfg(feature = "instruments")]
145pub use services::instruments;
146#[cfg(feature = "mcinstall")]
147pub use services::mcinstall;
148#[cfg(feature = "misagent")]
149pub use services::misagent;
150#[cfg(feature = "mobileactivation")]
151pub use services::mobileactivation;
152#[cfg(feature = "notificationproxy")]
153pub use services::notificationproxy;
154#[cfg(feature = "ostrace")]
155pub use services::ostrace;
156#[cfg(feature = "pcap")]
157pub use services::pcap;
158#[cfg(feature = "power_assertion")]
159pub use services::power_assertion;
160#[cfg(feature = "preboard")]
161pub use services::preboard;
162#[cfg(feature = "prepare")]
163pub use services::prepare;
164#[cfg(feature = "restore")]
165pub use services::restore;
166#[cfg(feature = "screenshot")]
167pub use services::screenshot;
168#[cfg(feature = "springboard")]
169pub use services::springboard;
170#[cfg(feature = "syslog")]
171pub use services::syslog;
172#[cfg(feature = "testmanager")]
173pub use services::testmanager;
174#[cfg(feature = "webinspector")]
175pub use services::webinspector;
176pub use services::{backup2, device_link, simlocation};
177pub use tunnel::{TunMode, TunnelError, TunnelHandle, TunnelInfo, TunnelManager};
178#[cfg(feature = "tunnel")]
179pub use xpc::client::XpcClient;
180pub use xpc::message::flags as xpc_message_flags;
181pub use xpc::message::{
182    decode_message as decode_xpc_message, encode_message as encode_xpc_message, XpcMessage,
183    XpcValue,
184};
185pub use xpc::rsd::{RsdHandshake, ServiceDescriptor, RSD_PORT};
186pub use xpc::XpcError;
187
188/// List all currently connected iOS devices (via usbmuxd).
189pub async fn list_devices() -> Result<Vec<DeviceInfo>, CoreError> {
190    discovery::list_devices().await
191}
192
193/// Watch for usbmux attach/detach events through the reusable ios-core discovery layer.
194pub async fn watch_devices(
195) -> Result<impl futures_core::Stream<Item = Result<DeviceEvent, CoreError>>, CoreError> {
196    discovery::watch_devices().await
197}
198
199/// Connect to an iOS device by UDID and optionally establish a CDTunnel.
200pub async fn connect(udid: &str, opts: ConnectOptions) -> Result<ConnectedDevice, CoreError> {
201    device::connect(udid, opts).await
202}
203
204/// Discover iOS 17+ devices on the local network via mDNS.
205///
206/// Returns a stream of devices with their IPv6 address and RSD port.
207/// Use [`connect`] to establish a session and inspect the RSD service list.
208#[cfg(feature = "mdns")]
209pub async fn discover_mdns() -> Result<impl futures_core::Stream<Item = MdnsDevice>, CoreError> {
210    discovery::discover_mdns().await
211}