
ARM64 ELF Virtual-Machine-Schutzsystem
ARM64 ELF Virtuelles-Maschinen-Schutzsystem
Übersetzt native ARM64-Anweisungen in benutzerdefinierten VM-Bytecode für funktionsweisen Code-Schutz
🇨🇳 中文文档 • Funktionen • Architektur • Schnellstart • Verwendung • Lizenz
VMPacker ist ein Virtual Machine Protection (VMP)-System für ARM64 (AArch64) Linux ELF-Binärdateien. Es dekodiert die nativen ARM64-Anweisungen der Zielfunktion in eine Zwischendarstellung, übersetzt sie in benutzerdefinierten VM-Bytecode und injiziert einen eingebetteten VM-Interpreter in die ELF-Datei. Zur Laufzeit werden geschützte Funktionen vom VM-Interpreter anstatt nativ ausgeführt.
ARM64 nativer Code → Dekodieren → Übersetzen → Benutzerdefinierter VM-Bytecode
↓
Original-ELF ← Injizieren ← VM-Interpreter-Stub
vmp/
├── cmd/vmpacker/ # CLI-Einstiegspunkt
│ ├── main.go # CLI-Argument-Parsing + Orchestrierung
│ └── vm_interp.bin # Kompilierter VM-Interpreter (GCC, go:embed)
│
├── pkg/ # Go-Kernbibliothek
│ ├── arch/arm64/ # ARM64-Architekturunterstützung
│ │ ├── decoder.go # Tabellengesteuerter Befehlsdekoder (implementiert vm.Decoder)
│ │ ├── decode_*.go # Dekodierungsmustertabellen (DP-IMM/DP-REG/Branch/LdSt)
│ │ ├── translator.go # ARM64 → VM-Bytecode-Übersetzer
│ │ ├── tr_alu.go # ALU-Befehlsübersetzung
│ │ ├── tr_branch.go # Verzweigungsbefehlsübersetzung
│ │ ├── tr_loadstore.go # Speicherbefehlsübersetzung
│ │ ├── tr_bitfield.go # Bitfeld-Befehlsübersetzung
│ │ └── tr_special.go # Spezielle Befehle (ADRP/ADR)
│ ├── vm/ # VM-ISA-Definitionen
│ │ ├── types.go # Gemeinsame Typen + Schnittstellen (Decoder/Translator/Packer)
│ │ ├── opcodes.go # 58+ VM-Opcode-Definitionen (zufällig zugeordnete Werte)
│ │ └── disasm.go # VM-Bytecode-Disassembler
│ └── binary/elf/ # ELF-Binärdatei-Manipulation
│ ├── packer.go # ELF-VMP-Injektion (PT_NOTE-Hijack, Trampolin-Generierung)
│ └── trampoline.go # Trampolin-Code-Generierung
│
├── stub/ # C-VM-Interpreter (kompiliert als PIC Flat Binary)
│ ├── vm_interp_clean.c # Interpreter-Hauptschleife + Einstiegspunkte
│ ├── vm_types.h # VM-CPU-Kontext (vm_ctx_t)
│ ├── vm_opcodes.h # C-seitige Opcode-Definitionen (synchron mit opcodes.go)
│ ├── vm_decode.h # Bytecode-Lese-Dienstprogramme
│ ├── vm_token.h # Token-Codieren/Decodieren + Deskriptortabelle
│ ├── vm_dispatch.h # Indirekte Dispatch-Sprungtabelle
│ ├── vm_crc.h # CRC32-Integritätsprüfung
│ ├── vm_sections.h # Handler-Abschnitts-Streuungs-Makros
│ ├── vm_interp.lds # Linker-Skript
│ └── vm_handlers/ # Modulare Anweisungs-Handler
│ ├── h_alu.h # Arithmetik/Logik-Operationen
│ ├── h_mem.h # Speicherzugriff
│ ├── h_branch.h # Verzweigung/Sprung
│ ├── h_cmp.h # Vergleich/Bedingung
│ ├── h_mov.h # Datenbewegung
│ ├── h_stack.h # Stack (PUSH/POP)
│ └── h_system.h # System (SVC/MRS/BLR/BR/RET)
│
├── vmp-gui/ # Wails-GUI-Frontend
│ ├── frontend/ # Vue 3 + Element Plus
│ └── backend/ # Go-Backend-Bindungen
│
└── build/ # Vorkompilierte Tools + Test-Artefakte
Das Projekt verwendet eine schnittstellengesteuerte modulare Architektur, was eine einfache Erweiterung auf neue ISAs und Binärformate ermöglicht:
// Architecture decoder interface — extensible to x86, RISC-V
type Decoder interface {
Decode(raw uint32, offset int) Instruction
InstName(op int) string
}
// Bytecode translator interface
type Translator interface {
Translate(instructions []Instruction) (*TranslateResult, error)
}
// Binary format injector interface — extensible to PE, Mach-O
type Packer interface {
Process() error
}
graph LR
A[Eingabe ELF] --> B[Zielfunktion lokalisieren]
B --> C[ARM64-Anweisungen extrahieren]
C --> D[ARM64 dekodieren]
D --> E[In VM-Bytecode übersetzen]
E --> F[XOR-Verschlüsselung des Bytecodes]
F --> G[VM-Interpreter injizieren]
G --> H[Trampolin generieren]
H --> I[Funktionseintritt ersetzen]
I --> J[Geschützte ELF ausgeben]
git clone https://github.com/LeoChen-CoreMind/VMPacker.git
cd VMPacker
make all
# Einzelne Funktion schützen
./vmpacker -func check_license -v -o protected.elf original.elf
# Mehrere Funktionen schützen
./vmpacker -func "check_license,verify_token" -v -o protected.elf original.elf
# Adressbereich angeben
./vmpacker -addr "0x4006AC-0x400790:main" -v -o protected.elf original.elf
# Gemischter Modus
./vmpacker -addr "0x4006AC-0x400790:main" -func verify -o protected.elf original.elf
./vmpacker -info input.elf
# Standard Build (GCC)
aarch64-linux-gnu-gcc -Os -nostdlib -fPIC -ffreestanding \
-o stub.elf stub/vm_interp_clean.c \
-T stub/vm_interp.lds
aarch64-linux-gnu-objcopy -O binary stub.elf vm_interp.bin
go build -o vmpacker ./cmd/vmpacker/
cd vmpacker
make gui
VMPacker definiert eine benutzerdefinierte Befehlssatzarchitektur (ISA) mit zufällig zugeordneten Opcode-Werten, um die Reverse-Engineering-Schwierigkeit zu erhöhen.
📖 Für die vollständige Opcode-Tabelle mit Kodierungsdetails siehe die chinesische Dokumentation.
Beiträge sind willkommen! Bitte befolgen Sie diese Richtlinien:
git checkout -b feature/neue-architekturgit commit -m 'feat: x86_64-Dekoder hinzugefügt'git push origin feature/neue-architekturWir folgen Conventional Commits:
feat: Neue Funktionfix: Fehlerbehebungrefactor: Code-Umstrukturierungdocs: Dokumentationtest: TestsDieses Projekt ist unter der AGPL-3.0-Lizenz lizenziert.
Warum AGPL-3.0:
DIESE SOFTWARE WIRD "AS IS" BEREITGESTELLT, OHNE JEGLICHE AUSDRÜCKLICHE ODER STILLSCHWEIGENDE GEWÄHRLEISTUNG, EINSCHLIESSLICH, ABER NICHT BESCHRÄNKT AUF DIE GEWÄHRLEISTUNG DER MARKTGÄNGIGKEIT, DER EIGNUNG FÜR EINEN BESTIMMTEN ZWECK UND DER NICHTVERLETZUNG VON RECHTEN. IN KEINEM FALL HAFTEN DIE AUTOREN ODER COPYRIGHT-INHABER FÜR JEGLICHE ANSPRÜCHE, SCHÄDEN ODER ANDERE HAFTUNG, OB AUS VERTRAG, UNERLAUBTER HANDLUNG ODER ANDERWEITIG, DIE SICH AUS DER SOFTWARE ODER DER NUTZUNG ODER ANDEREN GESCHÄFTEN MIT DER SOFTWARE ERGEBEN.
Dieses Projekt dient dem legitimen Schutz geistigen Eigentums für Softwareentwickler und hilft, Kernalgorithmen und kritischen Code in kommerzieller Software vor unbefugtem Reverse Engineering oder Diebstahl zu schützen.
Hinweis für Benutzer:
- Sie müssen alle geltenden Gesetze und Vorschriften Ihres Rechtsgebiets bei der Nutzung dieser Software einhalten
- Es ist strengstens verboten, diese Software für illegale Zwecke zu verwenden, einschließlich, aber nicht beschränkt auf: Entwicklung von Schadsoftware, Umgehung von Sicherheitsprüfungen, Verletzung der Rechte geistigen Eigentums anderer oder Beeinträchtigung der Sicherheit von Computersystemen
- Der/die Autor(en) haftet / haften nicht für direkte oder indirekte Folgen, die sich aus der Nutzung dieser Software durch irgendeine Person ergeben
- Durch Herunterladen, Nutzen oder Verteilen dieser Software erklären Sie, dass Sie die oben genannten Bedingungen gelesen haben und ihnen zustimmen
LeoChen — @LeoChen-CoreMind
Copyright © 2025 LeoChen. Alle Rechte vorbehalten.
| Schicht | Technik | Beschreibung |
|---|
| VM-Schutz | Benutzerdefinierte ISA | Zufällig zugeordnete Opcodes – Reverse Engineers können die Anweisungssemantik nicht direkt identifizieren |
| OpcodeCryptor | Per-Anweisung Opcode-Verschlüsselung | enc[pc] = op[pc] ^ (key ^ (pc * 0x9E3779B9)) |
| Bytecode-Umkehrung | Umkehrung der Ausführungsreihenfolge | Anweisungen in umgekehrter Reihenfolge gespeichert; Interpreter durchläuft rückwärts |
| Token-Eintritt | 3-Anweisungs-Trampolin | Ursprüngliche Funktion durch tokenisierten Eintritt ersetzt, versteckt die tatsächliche Bytecode-Position |
| Indirekter Dispatch | Funktionszeiger-Sprungtabelle | Wird zur Laufzeit auf dem Stack gefüllt, unterbricht IDA-Kreuzverweise |
![]() | ![]() | ![]() |
| Funktionsliste | Analyse & Auswahl | Schutzoptionen |
![]() | ![]() | |
| Echtzeitprotokolle | Schutz abgeschlossen |
| Option | Standard | Beschreibung |
|---|
-func | — | Zu schützende Funktionsname(n) (kommagetrennt) |
-addr | — | Schutz nach Adresse (0xSTART-0xEND[:name]) |
-o | input.vmp | Ausgabedateipfad |
-v | false | Ausführliche Ausgabe (Disassembly anzeigen) |
-strip | true | Symboltabelle entfernen |
-debug | false | ARM64 → VM-Bytecode-Debug-Zuordnungsdatei generieren |
-token | true | Token-basierter Eintrittsmodus |
-info | false | Nur ELF-Info ausgeben |
| Kategorie | Anzahl | Beschreibung |
|---|
| Datenbewegung | 3 | MOV_IMM64, MOV_IMM32, MOV_REG |
| Arithmetik/Logik | 21 | ADD, SUB, MUL, XOR, AND, OR, SHL, SHR, ASR, NOT, ROR, UMULH + _IMM-Varianten |
| Speicherzugriff | 8 | LOAD/STORE 8/16/32/64 |
| Verzweigung/Sprung | 13 | JMP, JE, JNE, JL, JGE, JGT, JLE, JB, JAE, JBE, JA, TBZ, TBNZ |
| Vergleich | 6 | CMP, CMP_IMM, CCMP_REG, CCMP_IMM, CCMN_REG, CCMN_IMM |
| Stack | 2 | PUSH, POP |
| System/Spezial | 8 | NOP, HALT, RET, CALL_NATIVE, CALL_REG, BR_REG, SVC, MRS |
| SIMD | 2 | VLD16, VST16 |
| Gesamt | 63 |