Production-Ready x402 Protocol Implementation with Native Solana Wallet
Enable your ESP32-S3 devices to make autonomous x402 micropayments on Solana blockchain—with native Ed25519 signing on-device and full x402 protocol compliance.
A complete, production-ready x402 protocol SDK for ESP32-S3 microcontrollers that implements the standard x402 specification. Your IoT devices can generate keypairs, sign transactions, and make autonomous USDC payments on Solana—with full protocol compliance and native Ed25519 signing.
┌─────────────────────────────────────────────────────────┐
│ ESP32 Application (IoT Device) │
│ Single API Call: x402_fetch() │
└──────────────────┬──────────────────────────────────────┘
│
┌──────────────────▼──────────────────────────────────────┐
│ x402_protocol Component (Standard) │
│ • Detect 402 from API │
│ • Parse payment requirements (JSON body) │
│ • Query facilitator for fee payer │
│ • Build SPL token transfer (USDC) │
│ • Sign with native wallet (Ed25519) │
│ • Create PaymentPayload (JSON + Base64) │
│ • Retry with X-PAYMENT header │
│ • Parse X-PAYMENT-RESPONSE │
└──────────┬────────────────┬─────────────────────────────┘
│ │
┌──────▼──────┐ ┌────▼─────────┐
│ SPL Token │ │ Solana │
│ Builder │ │ Wallet │
│ • ATA │ │ • TweetNaCl │
│ • Token │ │ • Ed25519 │
│ • Token2022 │ │ • Signing │
└─────────────┘ └──────────────┘
ESP32 → x402 API → Facilitator → Kora → Solana
What makes this special:
- Standard x402 protocol compliance - works with any facilitator
- Native Ed25519 signing using TweetNaCl on ESP32-S3
- SPL Token support - USDC payments with Token & Token-2022
- Dynamic ATA derivation - proper PDA calculation with bump seeds
- Proper PaymentPayload structure - versioned, JSON + Base64
- Correct headers - X-PAYMENT, X-PAYMENT-RESPONSE
- Requirements in 402 body - not headers (per spec)
- Base58 encoding for Solana addresses
- WiFi + HTTPS support with certificate validation
- Pure ESP-IDF 6.x - no Arduino dependencies
- Production-ready - tested with Kora demo stack
Perfect for:
- Voice assistants paying for LLM/TTS APIs (gasless via facilitator!)
- Sensors selling data via micropayments
- Robots paying for navigation/vision APIs
- IoT devices accessing premium x402 APIs
- Any ESP32-S3 project needing autonomous payments
- Ed25519 keypair generation using ESP32-S3 hardware RNG
- On-device transaction signing with TweetNaCl
- Base58 address encoding for Solana
- User maintains custody of private keys
- SPL Token transactions - USDC transfers
- Full x402 spec compliance - works with any facilitator
- PaymentPayload structure - versioned, extensible
- JSON + Base64 encoding - standard format
- X-PAYMENT / X-PAYMENT-RESPONSE - correct headers
- Requirements in 402 body - per specification
- Automatic payment flow - single function call
- Settlement tracking - full transaction details
- Facilitator pays gas fees - no SOL balance needed on device
- User signs payment - maintains security and custody
- Works with Kora - tested with official demo stack
- USDC payments - micropayments in stablecoins
- Base units support - lamports for precise amounts
- Dynamic token program detection - auto-detects Token vs Token-2022
- Proper ATA derivation - PDA calculation with Ed25519 curve checking
- Multiple token support - works with any SPL token
- Fee payer support - facilitator-sponsored transactions
- RPC queries - automatic mint program lookup
- x402_protocol: Complete x402 implementation
x402_client.c- Main fetch logicx402_payment.c- Payment creationx402_requirements.c- 402 response parsingx402_encoding.c- PaymentPayload encodingx402_types.h- Type definitions
- spl_token: SPL token transfer builder
- Token & Token-2022 support
- ATA derivation with PDA
- Dynamic program detection
- solana_wallet: Native wallet with Ed25519
- Keypair management
- Transaction signing
- Balance queries
- SOL transfers
- solana_tx: Transaction builder & serializer
- Message construction
- Instruction encoding
- Signature handling
- solana_rpc: Solana JSON-RPC client
- HTTPS support
- Blockhash queries
- Balance lookups
- Transaction submission
- tweetnacl: Ed25519 cryptographic primitives
- Key generation
- Signing/verification
- Curve point validation
- base58: Solana address encoding
- Encode/decode
- Validation
- wifi_manager: WiFi connectivity
- Connection management
- Status monitoring
Complete x402 Protocol Flow:
#include "x402_client.h"
#include "solana_wallet.h"
// Create wallet (on-device signing)
solana_wallet_t *wallet = solana_wallet_from_keypair(secret_key, rpc_client);
// Automatic x402 payment flow - single function call!
x402_response_t response;
esp_err_t err = x402_fetch(
wallet, // User wallet (signs payments)
"http://192.168.1.100:4021/protected", // x402-enabled API
"GET", // HTTP method
NULL, // Optional headers
NULL, // Optional body
&response // Response output
);
if (err == ESP_OK) {
ESP_LOGI(TAG, "Status: %d", response.status_code);
ESP_LOGI(TAG, "Body: %s", response.body);
if (response.payment_made) {
ESP_LOGI(TAG, "💰 Payment made!");
ESP_LOGI(TAG, "Network: %s", response.settlement.network);
ESP_LOGI(TAG, "TX: %s", response.settlement.transaction);
ESP_LOGI(TAG, "Explorer: https://explorer.solana.com/tx/%s?cluster=devnet",
response.settlement.transaction);
}
x402_response_free(&response);
}
solana_wallet_destroy(wallet);The SDK automatically handles:
- Initial request → 402 detection
- Parse payment requirements from body
- Query facilitator for fee payer
- Decode token mint & determine program
- Build SPL token transfer with correct ATA
- Sign transaction with native wallet
- Encode PaymentPayload (JSON → Base64)
- Retry with X-PAYMENT header
- Parse X-PAYMENT-RESPONSE settlement
- Return final response + transaction details
Already have ESP-IDF v6.1+ installed? Get started in 5 minutes:
# Clone and build
git clone https://github.com/your-org/solana_esp32_x402
cd solana_esp32_x402
source ~/esp/esp-idf/export.sh
idf.py set-target esp32s3
idf.py build flash monitor
# Configure WiFi and wallet in main/main.c and main/test_keypair.h
# See detailed configuration belowHardware:
- ESP32-S3 development board (minimum 512KB RAM, 4MB Flash)
- USB cable for flashing and serial monitoring
Software:
- ESP-IDF v6.1+ (tested with v6.1-dev)
- Python 3.8+ (tested with Python 3.14.0)
- Git for cloning repositories
- CMake 3.16+ and Ninja build system
- USB-to-Serial drivers (usually auto-installed)
- CP210x drivers for Silicon Labs chips
- CH340/CH341 drivers for WCH chips
- FTDI drivers for FTDI chips
Optional (for x402 testing):
- Node.js 18+ and pnpm (for Kora demo stack)
- Solana CLI tools (for wallet management)
System Requirements:
- Disk Space: ~4 GB (ESP-IDF + tools + project)
- RAM: 4 GB minimum (8 GB recommended for building)
- OS: macOS 10.15+, Ubuntu 20.04+, Windows 10+
If you don't have ESP-IDF installed:
macOS / Linux:
# 1. Install prerequisites
# macOS:
brew install cmake ninja dfu-util python3
# Ubuntu/Debian:
sudo apt-get install git wget flex bison gperf python3 python3-pip python3-venv cmake ninja-build ccache libffi-dev libssl-dev dfu-util libusb-1.0-0
# 2. Create ESP directory
mkdir -p ~/esp
cd ~/esp
# 3. Clone ESP-IDF
git clone -b v6.1 --recursive https://github.com/espressif/esp-idf.git
# 4. Install ESP-IDF tools
cd ~/esp/esp-idf
./install.sh esp32s3
# 5. Set up environment (add to your ~/.bashrc or ~/.zshrc)
alias get_idf='. $HOME/esp/esp-idf/export.sh'
# 6. Activate ESP-IDF
source ~/esp/esp-idf/export.sh
# Or use: get_idfWindows: Download and run the ESP-IDF Windows Installer
Verify installation:
idf.py --version
# Expected output: ESP-IDF v6.1 or later# 1. Clone the repository
git clone https://github.com/your-org/solana_esp32_x402
cd solana_esp32_x402
# 2. Activate ESP-IDF environment
source ~/esp/esp-idf/export.sh
# 3. Set target to ESP32-S3
idf.py set-target esp32s3
# 4. (Optional) Configure project
idf.py menuconfig
# Navigate to: Component config → ESP System Settings
# Adjust stack sizes if needed- WiFi Setup - Edit
main/main.c:
#define WIFI_SSID "YOUR_WIFI_SSID"
#define WIFI_PASSWORD "YOUR_WIFI_PASSWORD"- Test Keypair - Edit
main/test_keypair.h:
#define USE_TEST_KEYPAIR 1 // Enable test mode
// Paste your Solana keypair secret key (64 bytes)
static const uint8_t TEST_SECRET_KEY[64] = {
// ... your keypair bytes
};- x402 API URL - Edit
main/main.c:
#define X402_API_URL "http://192.168.1.100:4021/protected"
#define X402_ENABLE_TEST 1 // Enable x402 test# 1. Build the project
idf.py build
# 2. Find your USB port
# macOS:
ls /dev/tty.*
# Look for: /dev/tty.usbserial-XXXX or /dev/tty.SLAB_USBtoUART
# Linux:
ls /dev/ttyUSB*
# Look for: /dev/ttyUSB0 or /dev/ttyACM0
# Windows:
# Use Device Manager or: mode
# Look for: COM3, COM4, etc.
# 3. Flash to ESP32-S3 (replace PORT with your actual port)
idf.py -p PORT flash
# 4. Monitor serial output
idf.py -p PORT monitor
# 5. Or flash and monitor in one command (recommended)
idf.py -p PORT flash monitor
# Example (macOS):
idf.py -p /dev/tty.usbserial-110 flash monitor
# Example (Linux):
idf.py -p /dev/ttyUSB0 flash monitor
# Example (Windows):
idf.py -p COM3 flash monitorTroubleshooting:
- "Permission denied" (Linux):
sudo usermod -a -G dialout $USERthen logout/login - "Port not found": Check USB cable (must support data), try different port
- "Failed to connect": Hold BOOT button while connecting, or try:
idf.py -p PORT erase-flash - Build errors: Ensure ESP-IDF is activated:
source ~/esp/esp-idf/export.sh
=======================================================
ESP32-S3 Solana Wallet
Solana x402 for Cute Physical AI Companions on ESP32
=======================================================
=== Testing TweetNaCl Ed25519 ===
✓ Signature verification SUCCESS!
✓ TweetNaCl Ed25519 is working perfectly on ESP32-S3!
=== Testing Base58 Encoding ===
Solana Address: [SOLANA_ADDRESS]
✓ Base58 encode/decode round-trip SUCCESS!
=== Testing WiFi Connection ===
✓ WiFi connected! IP: 192.168.1.100
=== Testing Solana RPC Client ===
✓ Got blockhash response
✓ Solana RPC client working!
=== Testing Wallet & Transactions ===
Wallet address: [SOLANA_ADDRESS]
Wallet balance: 997930220 lamports (0.997930220 SOL)
✓ Transaction successful!
✓ Signature: 2dQfct...E7JHA
✓ View on Solana Explorer:
https://explorer.solana.com/tx/2dQfct...E7JHA?cluster=devnet
==================================
Testing: x402 Protocol (Standard)
==================================
⚡ Running x402 Integration Test
Configuration:
API URL: http://192.168.1.100:4021/protected
Wallet: [SOLANA_ADDRESS]
USDC ATA: [USDC_ATA]
📡 Making x402 request...
✅ x402 Request Successful!
Status Code: 200
Response Body: {"message":"Access granted!"}
💰 Payment Details:
Network: solana-devnet
Success: true
Transaction: 3xK9Lm...pQ7Zv
🔗 View on Solana Explorer:
https://explorer.solana.com/tx/3xK9Lm...pQ7Zv?cluster=devnet
✓ Complete x402 flow executed successfully:
1. ✓ Initial request → 402 Payment Required
2. ✓ Parsed payment requirements
3. ✓ Queried facilitator /supported for fee payer
4. ✓ Built USDC transfer transaction
5. ✓ Signed transaction with Ed25519
6. ✓ Encoded PaymentPayload (JSON → Base64)
7. ✓ Retried with X-PAYMENT header
8. ✓ Payment validated and settled
9. ✓ Received 200 OK + content
10. ✓ Parsed X-PAYMENT-RESPONSE
==================================
All tests complete!
==================================
✓ TweetNaCl Ed25519 signing
✓ Base58 encoding/decoding
✓ WiFi connectivity
✓ Solana RPC client
✓ Transaction builder
✓ Wallet API
✓ SPL Token support (USDC)
✓ x402 Protocol (Standard Compliant)
🎉 Cute Physical AI Companions Are Ready for x402!
Files:
x402_client.h/c- Main x402 fetch logicx402_payment.h/c- Payment creation with signingx402_requirements.h/c- 402 response parsingx402_encoding.h/c- PaymentPayload JSON+Base64x402_types.h- Type definitions
Key API:
// Main function - handles entire x402 flow
esp_err_t x402_fetch(
solana_wallet_t *wallet,
const char *url,
const char *method,
const char *headers,
const char *body,
x402_response_t *response_out
);
// Free response memory
void x402_response_free(x402_response_t *response);Response Structure:
typedef struct {
int status_code; // HTTP status code
char *body; // Response body
bool payment_made; // Was payment required?
x402_settlement_t settlement; // Transaction details
} x402_response_t;
typedef struct {
char network[32]; // "solana-devnet"
bool success; // Payment successful?
char transaction[128]; // TX signature
} x402_settlement_t;Key Features:
- Token & Token-2022 support
- Dynamic program detection via RPC
- Proper ATA derivation with PDA
- Fee payer transactions
- Base units (lamports) support
Key API:
// Get token program for a mint (Token vs Token-2022)
esp_err_t spl_token_get_mint_program(
const char *rpc_url,
const uint8_t *mint_pubkey,
uint8_t *program_id_out
);
// Derive ATA with custom token program
esp_err_t spl_token_get_associated_token_address_with_program(
const uint8_t *wallet_pubkey,
const uint8_t *mint_pubkey,
const uint8_t *token_program_id,
uint8_t *ata_out
);
// Create token transfer transaction
esp_err_t spl_token_create_transfer_transaction(
const uint8_t *fee_payer,
const uint8_t *from_wallet,
const uint8_t *to_wallet,
const uint8_t *mint,
const uint8_t *token_program_id,
uint64_t amount, // Base units (lamports)
const uint8_t *recent_blockhash,
uint8_t *tx_out,
size_t *tx_len,
size_t max_tx_len
);Key Features:
- Ed25519 keypair management
- On-device transaction signing
- Balance queries
- SOL transfers
- Public key export
Key API:
// Create wallet from keypair
solana_wallet_t* solana_wallet_from_keypair(
const uint8_t *secret_key,
solana_rpc_handle_t rpc_client
);
// Get address (Base58)
esp_err_t solana_wallet_get_address(
solana_wallet_t *wallet,
char *address_out,
size_t max_len
);
// Get public key (raw bytes)
esp_err_t solana_wallet_get_pubkey(
solana_wallet_t *wallet,
uint8_t *pubkey_out
);
// Sign transaction
esp_err_t solana_wallet_sign(
solana_wallet_t *wallet,
const uint8_t *message,
size_t message_len,
uint8_t *signature_out
);
// Send SOL
esp_err_t solana_wallet_send_sol(
solana_wallet_t *wallet,
const char *to_address,
uint64_t lamports,
char *signature_out,
size_t max_sig_len
);
// Cleanup
void solana_wallet_destroy(solana_wallet_t *wallet);Key Features:
- Message construction
- Instruction encoding
- Signature handling
- Serialization
Key API:
// Create transaction
solana_tx_handle_t solana_tx_create(void);
// Add instruction
esp_err_t solana_tx_add_instruction(
solana_tx_handle_t tx,
uint8_t program_id[32],
const solana_tx_account_meta_t *accounts,
size_t num_accounts,
const uint8_t *data,
size_t data_len
);
// Set recent blockhash
esp_err_t solana_tx_set_recent_blockhash(
solana_tx_handle_t tx,
const char *blockhash_b58
);
// Serialize
esp_err_t solana_tx_serialize(
solana_tx_handle_t tx,
uint8_t *buffer,
size_t *len,
size_t max_len
);Key Features:
- HTTPS with certificate validation
- Blockhash queries
- Balance lookups
- Transaction submission
- Account queries
Key API:
// Initialize
solana_rpc_handle_t solana_rpc_init(const char *url);
// Get latest blockhash
esp_err_t solana_rpc_get_latest_blockhash(
solana_rpc_handle_t client,
solana_rpc_response_t *response
);
// Get balance
esp_err_t solana_rpc_get_balance(
solana_rpc_handle_t client,
const char *pubkey_b58,
solana_rpc_response_t *response
);
// Send transaction
esp_err_t solana_rpc_send_transaction(
solana_rpc_handle_t client,
const char *tx_b64,
solana_rpc_response_t *response
);
// Cleanup
void solana_rpc_destroy(solana_rpc_handle_t client);Key Features:
- Key generation
- Signing/verification
- Curve point validation
- Pure C implementation
Key API:
// Generate keypair
int crypto_sign_keypair(
uint8_t pk[32],
uint8_t sk[64]
);
// Sign message
int crypto_sign(
uint8_t *sm,
unsigned long long *smlen,
const uint8_t *m,
unsigned long long mlen,
const uint8_t *sk
);
// Verify signature
int crypto_sign_open(
uint8_t *m,
unsigned long long *mlen,
const uint8_t *sm,
unsigned long long smlen,
const uint8_t *pk
);
// Check if point is on curve (for PDA)
int unpackneg(gf r[4], const uint8_t p[32]);Key Features:
- Encode/decode
- Bitcoin-style Base58 alphabet
- Validation
Key API:
// Encode binary to Base58
bool base58_encode(
const uint8_t *data,
size_t len,
char *output,
size_t output_len
);
// Decode Base58 to binary
bool base58_decode(
const char *input,
uint8_t *output,
size_t *output_len,
size_t max_output_len
);Key Features:
- Connection management
- Status monitoring
- IP address queries
- Reconnection logic
Key API:
// Initialize
esp_err_t wifi_manager_init(void);
// Connect
esp_err_t wifi_manager_connect(
const char *ssid,
const char *password,
uint32_t timeout_ms
);
// Check status
bool wifi_manager_is_connected(void);
// Get IP
esp_err_t wifi_manager_get_ip(
char *ip_str,
size_t max_len
);The following dependencies are built into ESP-IDF and automatically available:
esp_http_client- HTTP/HTTPS client with TLS supportesp_wifi- WiFi connectivitynvs_flash- Non-volatile storagembedtls- TLS/SSL and cryptographycJSON(viaespressif__cjsoncomponent) - JSON parsingesp_crt_bundle- Certificate bundle for HTTPS
All custom components are included in the components/ directory:
x402_protocol/- x402 client implementationspl_token/- SPL token transaction buildersolana_wallet/- Native Solana walletsolana_tx/- Transaction serializersolana_rpc/- JSON-RPC clienttweetnacl/- Ed25519 cryptographybase58/- Address encodingwifi_manager/- WiFi management
No external library installation required!
For testing with the official Kora x402 demo:
# 1. Install Node.js and pnpm (if not already installed)
# macOS:
brew install node pnpm
# Ubuntu/Debian:
curl -fsSL https://deb.nodesource.com/setup_18.x | sudo -E bash -
sudo apt-get install -y nodejs
npm install -g pnpm
# 2. Clone Kora
cd ~/repos
git clone https://github.com/solana-foundation/kora
cd kora/docs/x402/demo
# 3. Install dependencies
pnpm install
# 4. Start services (3 terminals)
# Terminal 1: Kora
pnpm run start:kora
# Terminal 2: Facilitator
pnpm run start:facilitator
# Terminal 3: API Server
pnpm run start:api
# 5. Note the API server URL (e.g., http://192.168.1.100:4021)# 1. Install Solana CLI (if not already installed)
# macOS/Linux:
sh -c "$(curl -sSfL https://release.solana.com/stable/install)"
# 2. Generate a new keypair
solana-keygen new --outfile ~/test-wallet.json
# 3. Get the wallet address
solana-keygen pubkey ~/test-wallet.json
# Example output: HVnsW7xz1VkXEySxvXuMj6jUa3aewQbbCUkYis1DEh6Q
# 4. Get devnet SOL (for account rent + fees)
solana airdrop 1 YOUR_WALLET_ADDRESS --url devnet
# 5. Get devnet USDC from Circle faucet
# Visit: https://faucet.circle.com/
# Enter your wallet address and select "Solana Devnet"
# 6. Verify USDC balance
solana balance YOUR_WALLET_ADDRESS --url devnet # SOL balance
# Check USDC balance on Solana Explorer
# 7. Copy keypair bytes to main/test_keypair.h
# The keypair file contains a JSON array of 64 bytes
cat ~/test-wallet.json
# Copy the byte array to TEST_SECRET_KEY in test_keypair.hEdit main/main.c:
#define WIFI_SSID "YOUR_WIFI_SSID"
#define WIFI_PASSWORD "YOUR_WIFI_PASSWORD"
#define X402_API_URL "http://YOUR_IP:4021/protected" // Use your machine's IP
#define X402_ENABLE_TEST 1Edit main/test_keypair.h:
#define USE_TEST_KEYPAIR 1
static const uint8_t TEST_SECRET_KEY[64] = {
// Paste your 64 bytes from the keypair JSON here
0x01, 0x02, 0x03, ...
};# 1. Ensure ESP-IDF is activated
source ~/esp/esp-idf/export.sh
# 2. Build and flash
cd solana_esp32_x402
idf.py build flash monitor
# 3. Expected output: All tests pass including x402 integration
# Watch for:
# - ✓ TweetNaCl Ed25519 signing
# - ✓ Base58 encoding/decoding
# - ✓ WiFi connectivity
# - ✓ Solana RPC client
# - ✓ Transaction builder
# - ✓ Wallet API
# - ✓ SPL Token support (USDC)
# - ✓ x402 Protocol (Standard Compliant)- RAM: ~280 KB (56% of 512KB ESP32-S3)
- Flash: ~420 KB (10% of 4MB)
- Stack: ~8 KB per task
- Headroom: Plenty for your application
- HTTP Request: 100-500ms (network dependent)
- x402 Payment Flow: 2-4 seconds total
- Initial 402: ~100ms
- Payment creation: ~300ms
- RPC queries: ~1s
- Signing: ~20ms
- Retry with payment: ~100ms
- Acceptable for IoT: Non-blocking operations
- Bandwidth: ~2 KB per x402 request
- Connections: Reuses HTTP connections
- TLS: Hardware accelerated via mbedTLS
- WiFi: 2.4 GHz 802.11 b/g/n
- TLS/SSL: All HTTPS connections encrypted
- On-device signing: Private keys never leave ESP32
- Ed25519: Industry-standard signatures
- Certificate validation: HTTPS cert checking
- User custody: You control the private keys
- Private key storage: Keep secret keys secure
- Device physical security: Protect ESP32 access
- Wallet funding: Ensure sufficient USDC balance
- API endpoint validation: Trust your x402 APIs
- Store keypairs in encrypted NVS (not hardcoded)
- Use separate wallets per device/project
- Monitor payment activity
- Keep firmware updated
- Validate x402 API endpoints
Edit main/main.c:
#define WIFI_SSID "YOUR_WIFI_SSID"
#define WIFI_PASSWORD "YOUR_WIFI_PASSWORD"
#define SOLANA_RPC_URL "https://api.devnet.solana.com"Edit main/test_keypair.h:
#define USE_TEST_KEYPAIR 1
static const uint8_t TEST_SECRET_KEY[64] = {
// Your 64-byte Ed25519 secret key
0x01, 0x02, ...
};Generate a keypair:
solana-keygen new --outfile test-keypair.json
solana-keygen pubkey test-keypair.json # Get address
# Copy bytes from test-keypair.json to TEST_SECRET_KEYEdit main/main.c:
#define X402_API_URL "http://192.168.1.100:4021/protected"
#define X402_ENABLE_TEST 1solana_esp32_x402/
├── main/
│ ├── main.c # Main application & tests
│ ├── test_keypair.h # Test keypair configuration
│ └── CMakeLists.txt
│
├── components/
│ ├── x402_protocol/ # x402 implementation
│ │ ├── x402_client.h/c # Main fetch logic
│ │ ├── x402_payment.h/c # Payment creation
│ │ ├── x402_requirements.h/c # 402 parsing
│ │ ├── x402_encoding.h/c # PaymentPayload encoding
│ │ ├── x402_types.h # Type definitions
│ │ └── CMakeLists.txt
│ │
│ ├── spl_token/ # SPL token builder
│ │ ├── spl_token.h/c # Token transfers, ATA
│ │ └── CMakeLists.txt
│ │
│ ├── solana_wallet/ # Native wallet
│ │ ├── solana_wallet.h/c # Wallet API
│ │ └── CMakeLists.txt
│ │
│ ├── solana_tx/ # Transaction builder
│ │ ├── solana_tx.h/c # TX serialization
│ │ └── CMakeLists.txt
│ │
│ ├── solana_rpc/ # RPC client
│ │ ├── solana_rpc.h/c # JSON-RPC
│ │ └── CMakeLists.txt
│ │
│ ├── tweetnacl/ # Ed25519 crypto
│ │ ├── tweetnacl.h/c # TweetNaCl library
│ │ ├── tweetnacl_esp32.c # ESP32 adaptations
│ │ └── CMakeLists.txt
│ │
│ ├── base58/ # Base58 encoding
│ │ ├── base58.h/c # Encoder/decoder
│ │ └── CMakeLists.txt
│ │
│ └── wifi_manager/ # WiFi
│ ├── wifi_manager.h/c # WiFi management
│ └── CMakeLists.txt
│
├── CMakeLists.txt # Main build config
├── sdkconfig.defaults # ESP-IDF defaults
└── README.md # This file
1. ESP32 → API: GET /protected
← 402 Payment Required
Body: {"accepts": [...payment requirements...]}
2. ESP32 parses requirements:
- recipient: merchant wallet
- asset: token mint
- amount: "100" (base units)
- feePayer: facilitator wallet
- network: "solana-devnet"
3. ESP32 queries facilitator /supported:
- Get fee payer address
- Verify facilitator support
4. ESP32 builds SPL token transfer:
- Query mint program (Token vs Token-2022)
- Derive source ATA (user)
- Derive dest ATA (merchant)
- Build transfer instruction
- Get recent blockhash
5. ESP32 signs transaction:
- Native Ed25519 signing
- User signature added
6. ESP32 creates PaymentPayload:
- JSON structure
- Base64 encode
- Add version, scheme, network
7. ESP32 → API: GET /protected
Header: X-PAYMENT: <base64 payload>
8. API → Facilitator: Verify payment
- Facilitator signs (fee payer)
- Submits to Solana
- Returns settlement
9. API → ESP32: 200 OK
Header: X-PAYMENT-RESPONSE: <settlement>
Body: Protected content
10. ESP32 parses settlement:
- Transaction signature
- Network
- Success status
- ATA creation for new accounts
- SHA-256 for blockhash verification
- Payment caching/replay protection
- Offline payment queue
- Multiple wallet support
- NVS-based key storage
- Power management optimizations
- Mainnet testing & deployment
- ESP-IDF component registry
Error: "esp_http_client.h: No such file or directory"
- Cause: ESP-IDF environment not activated
- Solution:
source ~/esp/esp-idf/export.shbefore building
Error: "Toolchain not found"
- Cause: ESP32-S3 toolchain not installed
- Solution:
cd ~/esp/esp-idf && ./install.sh esp32s3
Error: "Python version too old"
- Cause: Python < 3.8
- Solution: Update Python or use pyenv:
pyenv install 3.14.0 && pyenv global 3.14.0
Error: "Cannot allocate memory" during build
- Cause: System RAM < 4GB or many background apps
- Solution: Close applications, add swap space, or reduce parallel builds:
idf.py -j1 build
Error: "Failed to connect to ESP32-S3"
- Solution 1: Hold BOOT button while connecting, release after "Connecting..."
- Solution 2: Try:
idf.py -p PORT erase-flashthen flash again - Solution 3: Check USB cable (must support data, not just power)
Error: "Permission denied: /dev/ttyUSB0" (Linux)
- Solution:
sudo usermod -a -G dialout $USERthen logout and login
Error: "Port not found"
- Solution: Check Device Manager (Windows) or
ls /dev/tty.*(macOS/Linux) - Try different USB port or cable
WiFi connection fails
- Check SSID and password in
main/main.c - Ensure 2.4GHz WiFi (ESP32-S3 doesn't support 5GHz)
- Check router allows new devices
x402 payment fails
- Verify Kora demo stack is running (
pnpm run start:*) - Check API URL matches your machine's IP (not
localhost) - Ensure wallet has USDC balance (Circle faucet)
- Verify wallet has SOL for rent (~0.001 SOL minimum)
Transaction fails with "insufficient funds"
- Get more SOL:
solana airdrop 1 YOUR_ADDRESS --url devnet - Get USDC: https://faucet.circle.com/
HTTPS certificate errors
- Usually auto-resolved by
esp_crt_bundle - If persistent, check system time is correct
Error: "Stack overflow" or "Guru Meditation Error"
- Cause: Stack too small for deep call chains
- Solution: Increase stack size in
idf.py menuconfig:- Component config → ESP System Settings → Main task stack size (increase to 8192+)
- Component config → FreeRTOS → Idle Task stack size
Out of memory errors
- Check available heap: The SDK logs heap usage
- Reduce buffer sizes in configurations if needed
- ESP32-S3 has 512KB RAM, ~400KB available after system overhead
This project is part of the Solana x402 Hackathon.
git clone https://github.com/your-org/solana_esp32_x402
cd solana_esp32_x402
source ~/esp/esp-idf/export.sh
idf.py set-target esp32s3
idf.py menuconfig # Optional: configure
idf.py build- Follow ESP-IDF coding style
- Document all public APIs
- Add tests for new features
- Update README for API changes
- Website: https://x402.org
- Spec: https://github.com/coinbase/x402
- Hackathon: https://solana.com/x402/hackathon
- Docs: https://docs.espressif.com/projects/esp-idf/en/latest/esp32s3/
- Getting Started: ESP-IDF setup guide
- API Reference: ESP-IDF API docs
- GitHub: https://github.com/espressif/esp-idf
Tested Configuration:
- ESP-IDF: v6.1-dev (commit 286b8cb76d)
- Python: 3.14.0 (works with 3.8+)
- CMake: 3.27+ (works with 3.16+)
- ESP32-S3: All variants (WROOM, WROVER, etc.)
Minimum Requirements:
- ESP-IDF: v6.1 or later (v5.x may work but untested)
- Python: 3.8 or later
- ESP32-S3: 512KB RAM, 4MB Flash minimum
Note: This project uses ESP-IDF 6.x features. If you're on ESP-IDF 5.x, you may need to:
- Update to ESP-IDF 6.1+:
cd ~/esp/esp-idf && git pull && git checkout v6.1 && ./install.sh - Or modify component includes for compatibility (not recommended)
Track: Best x402 Dev Tool
Why this wins:
- Complete SDK for x402 on embedded devices
- Production-ready - tested with official Kora demo
- Novel category - first x402 for microcontrollers
- Native implementation - on-device Ed25519 signing
- Full compliance - standard x402 protocol
- Comprehensive docs - easy to use & extend
- Open source - MIT licensed, reusable
What it enables:
- Voice assistants with autonomous payments
- IoT sensor marketplaces
- Robot payment systems
- Embedded x402 API clients
- Physical AI devices with web3 payments
- Issues: GitHub Issues
- Discussions: GitHub Discussions
- Discord: Solana x402 community
Built with ❤️ for the Solana x402 Hackathon
Bringing autonomous micropayments to ESP32-S3 devices—one transaction at a time.
🎉 Cute Physical AI Companions Are Ready for x402!