mirror of
https://github.com/lukaszraczylo/go-obfuscation.git
synced 2026-10-12 05:32:33 +00:00
Bug fixes: - pclntab/rtcorrupt_linux.go: remove duplicate mprotectRW/mprotectRO that broke GOOS=linux builds (they're defined in rtcorrupt_unsafe.go for darwin+linux). - pclntab/pclntab.go: readUint now guards against negative offset (previously panicked via slice out-of-range). - integrity/integrity.go: SetExpectedHashHex now validates length 64 up-front and reports byte index on parse error; added ClearExpectedHash for runtime toggling and test isolation. - transform/mba.go: mbaApplyBinOp used strings.Index on first match instead of the current match; replaced with FindAllStringSubmatchIndex + two-pass replacement. - transform/transform.go: removed duplicate unconditional SplitLongStrings call. New transform passes (CLI flags + Config fields + pipeline wiring): - splice, constblind, mba, fakesigs, funcsplit, bbreorder — all default true. Cleanup: - strenc/keyderive.go: removed unused DeriveFromBinary + buildSeed. - transform/transform.go: removed unused trimFirstParen. - antidebug_hook_darwin.go: modernized readAddr to unsafe.Slice with noescape pattern (vet-safe). Tests (10 packages, 116 tests, all green): - internal/transform: 28 tests covering every pipeline stage. - pkg/strenc: 7 tests for key derivation + XOR stream. - pkg/stringcrypt: 7 tests for CFB round-trip + tamper detection. - pkg/pageman: 14 tests for alignment + mprotect guards. - pkg/integrity: 14 tests including ClearExpectedHash teardown. - pkg/pclntab: 12 tests including readUint negative-offset guard. - pkg/antisandbox: 6 tests for hostname/MAC lists + Check delegation. - pkg/antiemul: 6 tests (1 skipped on non-Linux) for no-panic + timing. Tooling: - Makefile: added test, verify, lint, fmt, vet targets. vet uses -unsafeptr=false (only legitimate uintptr→pointer is the darwin antidebug hook). fmt skips build/ (generated). - README.md: test coverage table + Makefile target reference.
106 lines
2.8 KiB
Go
106 lines
2.8 KiB
Go
package stringcrypt
|
|
|
|
import (
|
|
"bytes"
|
|
"encoding/base64"
|
|
"testing"
|
|
)
|
|
|
|
func TestEncryptDecryptRoundtrip(t *testing.T) {
|
|
cases := []string{
|
|
"",
|
|
"x",
|
|
"hello world",
|
|
"sk-proj-FAKE-KEY-1234567890abcdef",
|
|
"unicode: \u00e9\u4e2d\u6587",
|
|
"line1\nline2\ttabbed",
|
|
}
|
|
for _, pt := range cases {
|
|
enc := Encrypt(pt)
|
|
if pt != "" && bytes.Equal(enc.ciphertext, []byte(pt)) {
|
|
t.Errorf("ciphertext equals plaintext for %q", pt)
|
|
}
|
|
if got := enc.Decrypt(); got != pt {
|
|
t.Errorf("Decrypt() = %q, want %q", got, pt)
|
|
}
|
|
}
|
|
}
|
|
|
|
func TestEncryptUniqueKeys(t *testing.T) {
|
|
pt := "same plaintext"
|
|
a := Encrypt(pt)
|
|
b := Encrypt(pt)
|
|
if bytes.Equal(a.key, b.key) {
|
|
t.Error("two Encrypt calls produced identical keys (low probability event, but should not happen)")
|
|
}
|
|
if bytes.Equal(a.ciphertext, b.ciphertext) {
|
|
t.Error("two Encrypt calls produced identical ciphertext (keys should differ)")
|
|
}
|
|
}
|
|
|
|
func TestEncryptedStringB64Roundtrip(t *testing.T) {
|
|
enc := Encrypt("hello")
|
|
ct, err := base64.StdEncoding.DecodeString(enc.CiphertextB64())
|
|
if err != nil {
|
|
t.Fatalf("CiphertextB64() invalid base64: %v", err)
|
|
}
|
|
if !bytes.Equal(ct, enc.ciphertext) {
|
|
t.Error("CiphertextB64() does not roundtrip to raw ciphertext")
|
|
}
|
|
ky, err := base64.StdEncoding.DecodeString(enc.KeyB64())
|
|
if err != nil {
|
|
t.Fatalf("KeyB64() invalid base64: %v", err)
|
|
}
|
|
if !bytes.Equal(ky, enc.key) {
|
|
t.Error("KeyB64() does not roundtrip to raw key")
|
|
}
|
|
}
|
|
|
|
func TestRandomIdent(t *testing.T) {
|
|
const prefix = "x"
|
|
const length = 5
|
|
id := RandomIdent(prefix, length)
|
|
if len(id) != len(prefix)+length {
|
|
t.Errorf("RandomIdent len = %d, want %d (got %q)", len(id), len(prefix)+length, id)
|
|
}
|
|
if id[:len(prefix)] != prefix {
|
|
t.Errorf("RandomIdent prefix mismatch: %q", id)
|
|
}
|
|
const charset = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ"
|
|
for _, r := range id[len(prefix):] {
|
|
if !bytes.ContainsRune([]byte(charset), r) {
|
|
t.Errorf("RandomIdent contains unexpected char %q in %q", r, id)
|
|
}
|
|
}
|
|
}
|
|
|
|
func TestRandomIdentUniqueness(t *testing.T) {
|
|
seen := make(map[string]struct{})
|
|
for i := 0; i < 1000; i++ {
|
|
id := RandomIdent("_p", 6)
|
|
if _, dup := seen[id]; dup {
|
|
t.Fatalf("RandomIdent collision after %d iterations: %q", i, id)
|
|
}
|
|
seen[id] = struct{}{}
|
|
}
|
|
}
|
|
|
|
func TestRandomIdentZeroLength(t *testing.T) {
|
|
id := RandomIdent("p_", 0)
|
|
if id != "p_" {
|
|
t.Errorf("RandomIdent with 0 length = %q, want %q", id, "p_")
|
|
}
|
|
}
|
|
|
|
func TestGenerateRuntimeDecryptCallStructure(t *testing.T) {
|
|
src := GenerateRuntimeDecryptCall("aGVsbG8=", "a2V5")
|
|
if src == "" {
|
|
t.Error("GenerateRuntimeDecryptCall returned empty string")
|
|
}
|
|
for _, want := range []string{"base64.StdEncoding", "DecodeString", "return", "string(_pt)"} {
|
|
if !bytes.Contains([]byte(src), []byte(want)) {
|
|
t.Errorf("GenerateRuntimeDecryptCall missing %q in output:\n%s", want, src)
|
|
}
|
|
}
|
|
}
|