Enterprise-Grade License Verification for Rust
Secure, fast, and reliable license validation with hardware binding and automatic expiry enforcement
licverify is a Rust client for the go-license license verification system. It provides enterprise-grade license validation with cryptographic signatures, hardware binding, and automatic expiry enforcement, fully compatible with licenses generated by the go-license ecosystem.
- ๐ข Enterprise Software: Mission-critical applications requiring secure licensing
- ๐ฌ Scientific Tools: Research software with institutional licensing
- ๐ฎ Gaming: Game engines and tools with hardware-locked licenses
- ๐ผ SaaS Applications: Cloud services with node-locked licensing
| Feature | Benefit | Implementation |
|---|---|---|
| ๐ RSA-SHA256 | Cryptographic integrity | 2048-bit RSA with SHA-256 |
| ๐ป Hardware Binding | Device-locked licensing | MAC, Disk ID, Hostname |
| โฐ Auto-Expiry | Time-based enforcement | Background monitoring |
| ๐ Format Support | Legacy compatibility | Binary v2.0+ & JSON v1.x |
Add this to your Cargo.toml:
[dependencies]
licverify = "0.1.0"use licverify::Verifier;
#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
// Load your RSA public key
let public_key_pem = std::fs::read_to_string("public.pem")?;
let verifier = Verifier::new(&public_key_pem)?;
// Load and verify license
let license = verifier.load_license("license.lic")?;
match verifier.verify(&license) {
Ok(()) => {
println!("โ
License is valid!");
println!("๐ Customer: {}", license.customer_id);
println!("๐ฆ Product: {}", license.product_id);
println!("โฐ Expires: {}", license.expiry_date.format("%Y-%m-%d"));
}
Err(e) => {
eprintln!("โ License verification failed: {}", e);
std::process::exit(1);
}
}
Ok(())
}# Install from source
git clone https://github.com/luhtfiimanal/rust-licverify
cd rust-licverify
cargo build --release
# Verify a license
./target/release/licverify --public-key public.pem --license license.licOutput:
License ID: 1
Customer: BMKG
Product: Digitizer
Serial: SN12345
Issue Date: 2025-04-29 07:57:17 UTC
Expiry Date: 2026-04-29 07:57:17 UTC
Features: basic, miniseed, seedlink
Days remaining: 225
โ
License is valid!
Prevent license sharing by binding to specific hardware:
use licverify::{Verifier, HardwareInfo};
let verifier = Verifier::new(&public_key_pem)?;
let license = verifier.load_license("license.lic")?;
// Check hardware binding
match verifier.verify_hardware_binding(&license) {
Ok(()) => println!("โ
Hardware binding valid"),
Err(e) => println!("โ Hardware mismatch: {}", e),
}
// Get current hardware info
let hw_info = HardwareInfo::get()?;
println!("๐ฅ๏ธ MAC Addresses: {:?}", hw_info.mac_addresses);
println!("๐พ Disk IDs: {:?}", hw_info.disk_ids);
println!("๐ท๏ธ Hostname: {}", hw_info.hostname);use licverify::{Verifier, LicenseError};
use std::time::Duration;
use std::thread;
fn start_license_monitor(verifier: Verifier, license_path: String) {
thread::spawn(move || {
loop {
thread::sleep(Duration::from_secs(3600)); // Check every hour
match verifier.load_license(&license_path) {
Ok(license) => {
if let Err(_) = verifier.verify(&license) {
eprintln!"โ ๏ธ License expired or invalid - terminating application");
std::process::exit(1);
}
}
Err(_) => {
eprintln!("โ Could not load license - terminating application");
std::process::exit(1);
}
}
}
});
}use licverify::Verifier;
use std::sync::{Arc, atomic::{AtomicBool, Ordering}};
use std::time::Duration;
use std::thread;
pub struct LicenseGuard {
should_shutdown: Arc<AtomicBool>,
}
impl LicenseGuard {
pub fn new(verifier: Verifier, license_path: String, check_interval_secs: u64) -> Self {
let should_shutdown = Arc::new(AtomicBool::new(false));
let should_shutdown_clone = should_shutdown.clone();
thread::spawn(move || {
loop {
thread::sleep(Duration::from_secs(check_interval_secs));
match verifier.load_license(&license_path) {
Ok(license) => {
match verifier.verify(&license) {
Ok(()) => {
// Check if license expires within 7 days
let days_remaining = license.days_until_expiry();
if days_remaining <= 7 {
eprintln!("โ ๏ธ License expires in {} days!", days_remaining);
}
}
Err(_) => {
eprintln!("๐จ License expired - initiating graceful shutdown");
should_shutdown_clone.store(true, Ordering::Relaxed);
return;
}
}
}
Err(_) => {
eprintln!("โ License file error - initiating shutdown");
should_shutdown_clone.store(true, Ordering::Relaxed);
return;
}
}
}
});
Self { should_shutdown }
}
pub fn should_shutdown(&self) -> bool {
self.should_shutdown.load(Ordering::Relaxed)
}
}
// Usage in your application
fn main() {
let verifier = Verifier::new(&public_key_pem).unwrap();
let license_guard = LicenseGuard::new(verifier, "license.lic".to_string(), 300); // Check every 5 minutes
// Your application main loop
loop {
if license_guard.should_shutdown() {
println!("๐ License expired - shutting down gracefully");
break;
}
// Your application logic here
thread::sleep(Duration::from_secs(1));
}
}- ๐ Cross-Platform: Supports Linux, Windows, and macOS
- ๐ RSA-SHA256: 2048-bit RSA with PKCS#1 v1.5 padding
- ๐ป Hardware Binding: MAC addresses, disk IDs, and hostname verification
- ๐ Dual Format: Binary (v2.0+) and JSON (v1.x) license support
- ๐ฅ๏ธ CLI Interface: Simple command-line verification tool
- ๐ Library: Embeddable Rust library for applications
- โฐ Auto-Expiry: Background monitoring and enforcement
This Rust implementation is fully compatible with the go-license ecosystem:
| Component | Repository | Purpose |
|---|---|---|
| ๐ง License Generator | go-license | Create and sign licenses |
| ๐ Python Client | python-licverify | Python verification |
| ๐ฆ Rust Client | rust-licverify (this project) | Rust verification |
| Format | Version | Features | Status |
|---|---|---|---|
| Binary | v2.0+ | Full feature set | โ Supported |
| JSON | v1.x | Legacy compatibility | โ Supported |
| Signature | All | RSA-2048 + SHA-256 | โ Verified |
This project is part of the broader go-license ecosystem for cross-platform license management:
- ๐ง go-license - Main license generator and Go client
- ๐ python-licverify - Python verification client
- ๐ฆ rust-licverify - Rust verification client (this project)
All clients can verify licenses generated by the go-license system interchangeably, providing flexibility for multi-language environments.
Contributions are welcome! Please feel free to submit a Pull Request. For major changes, please open an issue first to discuss what you would like to change.
# Fork and clone the repository
git clone https://github.com/luhtfiimanal/rust-licverify
cd rust-licverify
# Run tests
cargo test
# Format code
cargo fmt
# Run linter
cargo clippy
# Check for security vulnerabilities
cargo audit# Run all tests
cargo test
# Run with coverage
cargo test --all-features
# Run benchmarks
cargo bench# Basic usage example
cargo run --example basic_usage
# CLI verification
./target/release/licverify --help