Files
shoes/include/shoes.h
Andrey YastrebovandClaude Sonnet 4.6 80f910874b Add mobile build artifacts for iOS and Android (#127)
* Add mobile build artifacts for iOS and Android

- Add GitHub Actions workflow to build XCFramework (iOS) and AAR (Android)
  and publish them to GitHub releases on tag pushes
- Add scripts/build-ios.sh and scripts/build-android.sh for local builds
- Add android/ project (Gradle library module with Kotlin JNI wrapper)
- Add include/shoes.h C header for FFI consumers
- Gitignore /output build directory

Co-Authored-By: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>

* Fix Android JNI build: pin jni to 0.21, use --locked

The committed Cargo.toml had `jni = "*"` which resolved to jni 0.22.4 in
CI. jni 0.22 renamed JNIEnv to EnvUnowned, breaking the Android FFI code
written for the 0.21 API.

- Pin jni to "=0.21" (resolves to 0.21.1 via Cargo.lock)
- Add --locked to cargo ndk to enforce the lock file in CI

Co-Authored-By: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>

* Migrate Android JNI bindings to jni 0.22

jni 0.22 split JNIEnv into two types:
- EnvUnowned<'local> — FFI-safe type for native method signatures
- Env<'local> — high-level wrapper with get_string, new_string, etc.

Changes:
- Replace JNIEnv with EnvUnowned in all function signatures
- Use EnvUnowned::with_env() to access the Env inside each function
- Use Outcome enum (Ok/Err/Panic) from into_outcome() for error handling
- Replace new_global_ref return type: GlobalRef -> Global<JObject<'static>>
- Replace attach_current_thread() guard pattern with callback closure
- Replace &str method names/sigs with jni_str!/jni_sig! compile-time macros

Co-Authored-By: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>

* Auto-generate iOS C header with cbindgen

Replace hand-written include/shoes.h with cbindgen-generated output.
The header is now derived from doc comments on extern "C" functions
in src/ffi/ios.rs, keeping it in sync with the Rust source.

- Add cbindgen.toml (exports only ProtectSocketCallback + FFI functions)
- build-ios.sh runs cbindgen before building the XCFramework
- CI installs cbindgen in the iOS job

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

* Fix clippy and rustfmt CI failures

- Reorder jni imports in ffi/android.rs to match rustfmt order
- Remove unnecessary `as usize` cast in shadow_tls_server_handler.rs
- Collapse match guard in config/validate.rs (clippy::collapsible_match)

Co-Authored-By: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>

---------

Co-authored-by: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 01:46:58 +08:00

94 lines
2.0 KiB
C

/**
* @file shoes.h
* @brief C interface for the shoes proxy library (auto-generated by cbindgen).
*
* Provides C-compatible functions for embedding the shoes VPN/proxy engine
* into iOS applications via Swift or Objective-C.
*/
#ifndef SHOES_H
#define SHOES_H
#include <stdbool.h>
#include <stdint.h>
/**
* Socket protector callback type.
* Called from Rust to protect sockets from VPN routing.
* The callback receives a file descriptor and should return true if protected successfully.
*/
typedef bool (*ProtectSocketCallback)(int fd);
/**
* Initialize the shoes library.
*
* # Arguments
* * `log_level` - Log level string: "error", "warn", "info", "debug", "trace"
*
* # Returns
* * 0 on success
* * -1 on error
*
* # Safety
* `log_level` must be a valid null-terminated C string.
*/
int shoes_init(const char *log_level);
/**
* Start the shoes VPN service.
*
* # Arguments
* * `config_yaml` - YAML configuration string (must include device_fd in TUN config)
* * `protect_callback` - Callback function to protect sockets from VPN routing
*
* # Returns
* * Handle (> 0) on success
* * -1 on error
*
* # Safety
* `config_yaml` must be a valid null-terminated C string.
*/
long shoes_start(const char *config_yaml, ProtectSocketCallback protect_callback);
/**
* Stop the shoes VPN service.
*
* # Arguments
* * `handle` - Handle returned by shoes_start (currently unused, we use global state)
*/
void shoes_stop(long _handle);
/**
* Check if the shoes service is running.
*
* # Returns
* * true if running
* * false if not running
*/
bool shoes_is_running(void);
/**
* Get the shoes library version.
*
* # Returns
* A static string containing the version. Do not free this pointer.
*/
const char *shoes_get_version(void);
/**
* Set the log file path for file-based logging.
*
* # Arguments
* * `path` - Absolute path to the log file
*
* # Returns
* * 0 on success
* * -1 on error
*
* # Safety
* `path` must be a valid null-terminated C string.
*/
int shoes_set_log_file(const char *path);
#endif /* SHOES_H */