Obfuscate all sensitive string literals in agent binary

ober

1403d8f7948e8fb92d3902d12ef92c33f21cd2e9

diff --git a/build-all.ss b/build-all.ss
index ebd88ca..66de070 100644
--- a/build-all.ss
+++ b/build-all.ss
@@ -37,6 +37,7 @@
   (secmon monitor podman)
   (secmon monitor selinux)
   ;; Stealth
+  (secmon stealth obfuscate)
   (secmon stealth anti-debug)
   (secmon stealth masquerade)
   (secmon stealth env-sanitize)
diff --git a/build-secmon-musl.ss b/build-secmon-musl.ss
index e26d715..aa44c4e 100644
--- a/build-secmon-musl.ss
+++ b/build-secmon-musl.ss
@@ -122,6 +122,10 @@
                [generate-inspector-information #f]
                [compile-imported-libraries #t]
                [library-directories build-lib-dirs])
+  ;; Obfuscate macro (needed by many modules — compile first)
+  (printf "  Compiling lib/secmon/stealth/obfuscate.sls~n")
+  (compile-library "lib/secmon/stealth/obfuscate.sls")
+
   ;; Crypto modules (dependency order)
   (for-each
     (lambda (m)
@@ -231,7 +235,8 @@
         "std/gambit-compat"
         "std/crypto/native-rust"
         "std/db/sqlite-native"))
-    ;; Secmon modules
+    ;; Secmon modules (obfuscate first — many modules depend on it)
+    (list "lib/secmon/stealth/obfuscate.so")
     (map (lambda (m) (format "lib/secmon/crypto/~a.so" m))
       '("keys" "ecies" "psk"))
     (list "lib/secmon/monitor/events.so"
diff --git a/lib/secmon/config.sls b/lib/secmon/config.sls
index b061a84..f8fa3ae 100644
--- a/lib/secmon/config.sls
+++ b/lib/secmon/config.sls
@@ -9,6 +9,7 @@
   (import
     (chezscheme)
     (jerboa prelude clean)
+    (secmon stealth obfuscate)
     (std text hex))
 
   (define-record-type agent-config
@@ -41,21 +42,21 @@
 
   (define (load-agent-config)
     (make-agent-config
-      (or (getenv "SECMON_LISTEN") "0.0.0.0:31337")
-      (or (and (getenv "SECMON_POLL_MS")
-               (string->number (getenv "SECMON_POLL_MS")))
+      (or (getenv (obfstr "SECMON_LISTEN")) (obfstr "0.0.0.0:31337"))
+      (or (and (getenv (obfstr "SECMON_POLL_MS"))
+               (string->number (getenv (obfstr "SECMON_POLL_MS"))))
           100)
-      (or (and (getenv "SECMON_BUFFER_SIZE")
-               (string->number (getenv "SECMON_BUFFER_SIZE")))
+      (or (and (getenv (obfstr "SECMON_BUFFER_SIZE"))
+               (string->number (getenv (obfstr "SECMON_BUFFER_SIZE"))))
           10000)
-      (load-key-from-env "SECMON_PUBLIC_KEY" "keys/public.key")
-      (load-key-from-env "SECMON_PSK" "keys/psk.key")
-      (and (getenv "SECMON_DEBUG") #t)))
+      (load-key-from-env (obfstr "SECMON_PUBLIC_KEY") (obfstr "keys/public.key"))
+      (load-key-from-env (obfstr "SECMON_PSK") (obfstr "keys/psk.key"))
+      (and (getenv (obfstr "SECMON_DEBUG")) #t)))
 
   (define (load-collector-config)
     ;; Returns (values private-key psk)
     (values
-      (load-key-from-env "SECMON_PRIVATE_KEY" "keys/private.key")
-      (load-key-from-env "SECMON_PSK" "keys/psk.key")))
+      (load-key-from-env (obfstr "SECMON_PRIVATE_KEY") (obfstr "keys/private.key"))
+      (load-key-from-env (obfstr "SECMON_PSK") (obfstr "keys/psk.key"))))
 
 ) ;; end library
diff --git a/lib/secmon/monitor/container.sls b/lib/secmon/monitor/container.sls
index 4d32b44..a22d98f 100644
--- a/lib/secmon/monitor/container.sls
+++ b/lib/secmon/monitor/container.sls
@@ -4,7 +4,8 @@
     (chezscheme)
     (jerboa prelude clean)
     (secmon monitor events)
-    (secmon monitor suspicious))
+    (secmon monitor suspicious)
+    (secmon stealth obfuscate))
 
   ;; Container escape monitor: detects escape attempts from containers/jails
   (define (spawn-container-escape-monitor emit! poll-ms hostname)
@@ -36,8 +37,9 @@
                     (when (file-exists? path)
                       (emit! (make-escape-event hostname "container_socket_access"
                                path 'critical))))
-                  '("/var/run/docker.sock" "/run/docker.sock"
-                    "/var/run/containerd/containerd.sock"))
+                  (list (obfstr "/var/run/docker.sock")
+                        (obfstr "/run/docker.sock")
+                        (obfstr "/var/run/containerd/containerd.sock")))
                 ;; Check capabilities
                 (let ([caps (read-effective-caps)])
                   (when caps
@@ -64,18 +66,18 @@
 
   (define (is-containerized?)
     ;; Check for container indicators
-    (or (file-exists? "/.dockerenv")
-        (file-exists? "/run/.containerenv")
+    (or (file-exists? (obfstr "/.dockerenv"))
+        (file-exists? (obfstr "/run/.containerenv"))
         (guard (e [#t #f])
-          (let ([cgroup (read-file-safe "/proc/1/cgroup")])
+          (let ([cgroup (read-file-safe (obfstr "/proc/1/cgroup"))])
             (and cgroup
-                 (or (string-contains cgroup "docker")
-                     (string-contains cgroup "lxc")
-                     (string-contains cgroup "kubepods")))))))
+                 (or (string-contains cgroup (obfstr "docker"))
+                     (string-contains cgroup (obfstr "lxc"))
+                     (string-contains cgroup (obfstr "kubepods"))))))))
 
   (define (read-mounts)
     (guard (e [#t '()])
-      (let ([lines (local-read-file-lines "/proc/mounts")])
+      (let ([lines (local-read-file-lines (obfstr "/proc/mounts"))])
         (filter-map
           (lambda (line)
             (let ([parts (string-split line #\space)])
@@ -83,17 +85,17 @@
           lines))))
 
   (define (suspicious-mount? mount)
-    (or (string-prefix? "/host" mount)
-        (string-prefix? "/mnt/host" mount)
-        (string-contains mount "docker.sock")
-        (string-contains mount "containerd.sock")))
+    (or (string-prefix? (obfstr "/host") mount)
+        (string-prefix? (obfstr "/mnt/host") mount)
+        (string-contains mount (obfstr "docker.sock"))
+        (string-contains mount (obfstr "containerd.sock"))))
 
   (define (read-effective-caps)
     (guard (e [#t #f])
-      (let ([lines (local-read-file-lines "/proc/self/status")])
+      (let ([lines (local-read-file-lines (obfstr "/proc/self/status"))])
         (let loop ([ls lines])
           (if (null? ls) #f
-            (if (string-prefix? "CapEff:" (car ls))
+            (if (string-prefix? (obfstr "CapEff:") (car ls))
               (let* ([parts (string-split (car ls) #\tab)]
                      [hex (and (>= (length parts) 2)
                                (string-trim (cadr parts)))])
diff --git a/lib/secmon/monitor/lateral.sls b/lib/secmon/monitor/lateral.sls
index 8b517b0..83964e1 100644
--- a/lib/secmon/monitor/lateral.sls
+++ b/lib/secmon/monitor/lateral.sls
@@ -5,6 +5,7 @@
     (jerboa prelude clean)
     (secmon monitor events)
     (secmon monitor suspicious)
+    (secmon stealth obfuscate)
     (secmon platform provider))
 
   ;; Lateral movement monitor: detects SSH/RDP/WinRM/SMB to internal hosts, port scanning
@@ -32,7 +33,7 @@
                           [pname (connection-info-process-name c)])
                       (when (and (> pid 0)
                                  (internal-ip? raddr)
-                                 (not (equal? raddr "127.0.0.1"))
+                                 (not (equal? raddr (obfstr "127.0.0.1")))
                                  (equal? (connection-info-state c) "ESTABLISHED"))
                         ;; Track ports per (pid, target)
                         (let ([tracker-key (format "~a:~a" pid raddr)])
diff --git a/lib/secmon/monitor/logtamper.sls b/lib/secmon/monitor/logtamper.sls
index 1b464c1..918e794 100644
--- a/lib/secmon/monitor/logtamper.sls
+++ b/lib/secmon/monitor/logtamper.sls
@@ -5,6 +5,7 @@
     (jerboa prelude clean)
     (secmon monitor events)
     (secmon monitor suspicious)
+    (secmon stealth obfuscate)
     (std os file-info))
 
   ;; Log tamper monitor: detects log truncation, deletion, history clearing
@@ -29,10 +30,10 @@
   (define (find-history-files)
     (let ([files '()])
       (guard (e [#t files])
-        (let ([homes (append '("/root")
-                       (if (file-exists? "/home")
-                         (map (lambda (d) (string-append "/home/" d))
-                           (directory-list "/home"))
+        (let ([homes (append (list (obfstr "/root"))
+                       (if (file-exists? (obfstr "/home"))
+                         (map (lambda (d) (string-append (obfstr "/home/") d))
+                           (directory-list (obfstr "/home")))
                          '()))])
           (for-each
             (lambda (home)
@@ -41,9 +42,11 @@
                   (let ([path (string-append home "/" hist)])
                     (when (file-exists? path)
                       (set! files (cons path files)))))
-                '(".bash_history" ".zsh_history" ".sh_history"
-                  ".python_history" ".mysql_history" ".psql_history"
-                  ".node_repl_history" ".lesshst" ".viminfo")))
+                (list (obfstr ".bash_history") (obfstr ".zsh_history")
+                      (obfstr ".sh_history") (obfstr ".python_history")
+                      (obfstr ".mysql_history") (obfstr ".psql_history")
+                      (obfstr ".node_repl_history") (obfstr ".lesshst")
+                      (obfstr ".viminfo"))))
             homes))
         files)))
 
@@ -87,9 +90,9 @@
       (hashtable-keys log-sizes)))
 
   (define (history-file? path)
-    (or (string-contains path "history")
-        (string-contains path ".lesshst")
-        (string-contains path ".viminfo")))
+    (or (string-contains path (obfstr "history"))
+        (string-contains path (obfstr ".lesshst"))
+        (string-contains path (obfstr ".viminfo"))))
 
   (define (make-tamper-event hostname path tamper-type old-size new-size severity)
     (let ([data (make-hashtable string-hash string=?)])
diff --git a/lib/secmon/monitor/persistence.sls b/lib/secmon/monitor/persistence.sls
index dfeb091..02c6070 100644
--- a/lib/secmon/monitor/persistence.sls
+++ b/lib/secmon/monitor/persistence.sls
@@ -5,6 +5,7 @@
     (jerboa prelude clean)
     (secmon monitor events)
     (secmon monitor suspicious)
+    (secmon stealth obfuscate)
     (std crypto native-rust))
 
   ;; Persistence monitor: detects modifications to persistence mechanism locations
@@ -24,7 +25,7 @@
   (define (all-persistence-paths)
     (append
       ;; Individual files
-      '("/etc/ld.so.preload" "/etc/rc.local")
+      (list (obfstr "/etc/ld.so.preload") (obfstr "/etc/rc.local"))
       ;; Scan directories for files
       (scan-all-persistence-dirs)
       ;; Per-user shell profiles and authorized_keys
@@ -46,21 +47,21 @@
 
   (define (scan-user-homes)
     (guard (e [#t '()])
-      (let ([homes (if (file-exists? "/home")
-                     (map (lambda (d) (string-append "/home/" d))
-                       (directory-list "/home"))
+      (let ([homes (if (file-exists? (obfstr "/home"))
+                     (map (lambda (d) (string-append (obfstr "/home/") d))
+                       (directory-list (obfstr "/home")))
                      '())])
         (apply append
           (map
             (lambda (home)
               (filter file-exists?
                 (list
-                  (string-append home "/.bashrc")
-                  (string-append home "/.bash_profile")
-                  (string-append home "/.profile")
-                  (string-append home "/.zshrc")
-                  (string-append home "/.ssh/authorized_keys"))))
-            (cons "/root" homes))))))
+                  (string-append home (obfstr "/.bashrc"))
+                  (string-append home (obfstr "/.bash_profile"))
+                  (string-append home (obfstr "/.profile"))
+                  (string-append home (obfstr "/.zshrc"))
+                  (string-append home (obfstr "/.ssh/authorized_keys")))))
+            (cons (obfstr "/root") homes))))))
 
   (define (baseline-persistence-paths! hashes)
     (for-each
@@ -104,7 +105,7 @@
                                  (extract-suspicious-content full))))))))
               (directory-list dir)))))
       (append persistence-systemd-paths persistence-init-paths
-              '("/etc/sudoers.d"))))
+              (list (obfstr "/etc/sudoers.d")))))
 
   (define (extract-suspicious-content path)
     (guard (e [#t #f])
@@ -112,9 +113,12 @@
                        (lambda (p) (get-string-all p)))])
         (let ([lines (string-split content #\newline)]
               [suspicious-patterns
-               '("curl" "wget" "nc " "/dev/tcp/" "bash -i" "python -c"
-                 "eval" "base64" "chmod" "NOPASSWD" "LD_PRELOAD"
-                 "exec" "nohup" "crontab" "reverse")])
+               (list (obfstr "curl") (obfstr "wget") (obfstr "nc ")
+                     (obfstr "/dev/tcp/") (obfstr "bash -i") (obfstr "python -c")
+                     (obfstr "eval") (obfstr "base64") (obfstr "chmod")
+                     (obfstr "NOPASSWD") (obfstr "LD_PRELOAD")
+                     (obfstr "exec") (obfstr "nohup") (obfstr "crontab")
+                     (obfstr "reverse"))])
           (let loop ([ls lines])
             (if (null? ls) #f
               (let ([line (car ls)])
diff --git a/lib/secmon/monitor/revshell.sls b/lib/secmon/monitor/revshell.sls
index abbee78..490286f 100644
--- a/lib/secmon/monitor/revshell.sls
+++ b/lib/secmon/monitor/revshell.sls
@@ -5,6 +5,7 @@
     (jerboa prelude clean)
     (secmon monitor events)
     (secmon monitor suspicious)
+    (secmon stealth obfuscate)
     (secmon platform provider))
 
   ;; Reverse shell monitor: detects active reverse shell connections
@@ -25,8 +26,8 @@
                           [raddr (connection-info-remote-addr c)]
                           [rport (connection-info-remote-port c)])
                       (when (and (> pid 0)
-                                 (not (equal? raddr "0.0.0.0"))
-                                 (not (equal? raddr "127.0.0.1"))
+                                 (not (equal? raddr (obfstr "0.0.0.0")))
+                                 (not (equal? raddr (obfstr "127.0.0.1")))
                                  (equal? (connection-info-state c) "ESTABLISHED"))
                         (let ([key (format "~a:~a:~a" pid raddr rport)])
                           (unless (hashtable-ref reported key #f)
@@ -42,12 +43,15 @@
                                (emit! (make-revshell-event hostname pid pname
                                         raddr rport "known_c2_port" 'critical))]
                               ;; Known revshell tools
-                              [(member pname '("nc" "ncat" "socat" "telnet"))
+                              [(member pname (list (obfstr "nc") (obfstr "ncat")
+                                                   (obfstr "socat") (obfstr "telnet")))
                                (hashtable-set! reported key #t)
                                (emit! (make-revshell-event hostname pid pname
                                         raddr rport "shell_tool_outbound" 'critical))]
                               ;; Scripting tools with outbound
-                              [(member pname '("python" "python3" "perl" "ruby" "php"))
+                              [(member pname (list (obfstr "python") (obfstr "python3")
+                                                   (obfstr "perl") (obfstr "ruby")
+                                                   (obfstr "php")))
                                (let ([info ((process-provider-get-process proc-provider) pid)])
                                  (when info
                                    (let ([cmdline (string-join (process-info-cmdline info) " ")])
@@ -85,8 +89,8 @@
 
   ;; Extract IP:port from /dev/tcp/IP/PORT pattern
   (define (extract-dev-tcp-target cmdline)
-    (let ([pos (or (string-contains cmdline "/dev/tcp/")
-                   (string-contains cmdline "/dev/udp/"))])
+    (let ([pos (or (string-contains cmdline (obfstr "/dev/tcp/"))
+                   (string-contains cmdline (obfstr "/dev/udp/")))])
       (if (not pos)
         (cons "unknown" 0)
         (let* ([after (substring cmdline (+ pos 9) (string-length cmdline))]
diff --git a/lib/secmon/monitor/rootkit.sls b/lib/secmon/monitor/rootkit.sls
index abf8f62..1fb7e94 100644
--- a/lib/secmon/monitor/rootkit.sls
+++ b/lib/secmon/monitor/rootkit.sls
@@ -4,6 +4,7 @@
     (chezscheme)
     (jerboa prelude clean)
     (secmon monitor events)
+    (secmon stealth obfuscate)
     (secmon platform provider))
 
   ;; Rootkit monitor: detects hidden processes via /proc vs kill() discrepancy
@@ -87,13 +88,13 @@
 
   (define (read-pid-max)
     (guard (e [#t 32768])
-      (let ([content (call-with-input-file "/proc/sys/kernel/pid_max"
+      (let ([content (call-with-input-file (obfstr "/proc/sys/kernel/pid_max")
                        (lambda (p) (get-string-all p)))])
         (or (string->number (string-trim content)) 32768))))
 
   (define (check-loadavg-discrepancy visible-pids emit! hostname)
     (guard (e [#t (void)])
-      (let ([content (call-with-input-file "/proc/loadavg"
+      (let ([content (call-with-input-file (obfstr "/proc/loadavg")
                        (lambda (p) (get-string-all p)))])
         (let* ([parts (string-split content #\space)]
                [procs-part (and (>= (length parts) 4) (list-ref parts 3))]
diff --git a/lib/secmon/monitor/selinux.sls b/lib/secmon/monitor/selinux.sls
index 0118f1d..30f14cc 100644
--- a/lib/secmon/monitor/selinux.sls
+++ b/lib/secmon/monitor/selinux.sls
@@ -4,6 +4,7 @@
     (chezscheme)
     (jerboa prelude clean)
     (secmon monitor events)
+    (secmon stealth obfuscate)
     (std os file-info))
 
   ;; SELinux monitor: detects AVC denials, policy loads, mode changes
@@ -11,12 +12,12 @@
     (fork-thread
       (lambda ()
         ;; Only run if SELinux is available
-        (when (file-exists? "/sys/fs/selinux")
+        (when (file-exists? (obfstr "/sys/fs/selinux"))
           (let ([audit-pos (box 0)]
                 [current-mode (box (read-selinux-mode))])
             ;; Initialize audit log position to end
             (guard (e [#t (void)])
-              (let ([size (file-size-safe "/var/log/audit/audit.log")])
+              (let ([size (file-size-safe (obfstr "/var/log/audit/audit.log"))])
                 (when size (set-box! audit-pos size))))
             ;; Poll loop
             (let loop ()
@@ -35,7 +36,7 @@
 
   (define (read-selinux-mode)
     (guard (e [#t #f])
-      (let ([content (call-with-input-file "/sys/fs/selinux/enforce"
+      (let ([content (call-with-input-file (obfstr "/sys/fs/selinux/enforce")
                        (lambda (p) (get-string-all p)))])
         (if (string-contains content "1") "enforcing" "permissive"))))
 
@@ -45,7 +46,7 @@
 
   (define (tail-audit-log! pos-box emit! hostname)
     (guard (e [#t (void)])
-      (let ([path "/var/log/audit/audit.log"])
+      (let ([path (obfstr "/var/log/audit/audit.log")])
         (when (file-exists? path)
           (let ([size (file-size-safe path)])
             (when size
@@ -67,8 +68,9 @@
   (define (parse-audit-line! line emit! hostname)
     (cond
       ;; AVC denial/grant
-      [(string-contains line "type=AVC")
-       (let ([action (if (string-contains line "denied") "denied" "granted")]
+      [(string-contains line (obfstr "type=AVC"))
+       (let ([action (if (string-contains line (obfstr "denied"))
+                       "denied" "granted")]
              [comm (extract-field line "comm=\"" "\"")]
              [scontext (extract-field line "scontext=" " ")]
              [tcontext (extract-field line "tcontext=" " ")]
@@ -86,15 +88,15 @@
                     (if (equal? action "denied") 'high 'info)
                     data))))]
       ;; Policy load
-      [(string-contains line "MAC_POLICY_LOAD")
+      [(string-contains line (obfstr "MAC_POLICY_LOAD"))
        (emit! (make-selinux-event hostname "policy_load" "" 'medium))]
       ;; Boolean change
-      [(string-contains line "MAC_CONFIG_CHANGE")
+      [(string-contains line (obfstr "MAC_CONFIG_CHANGE"))
        (let ([bool-name (extract-field line "bool=" " ")])
          (emit! (make-selinux-event hostname "boolean_change"
                   (or bool-name "") 'medium)))]
       ;; Role change
-      [(string-contains line "USER_ROLE_CHANGE")
+      [(string-contains line (obfstr "USER_ROLE_CHANGE"))
        (emit! (make-selinux-event hostname "role_change" "" 'high))]))
 
   (define (extract-field line start end)
diff --git a/lib/secmon/monitor/suspicious.sls b/lib/secmon/monitor/suspicious.sls
index c762e64..918c562 100644
--- a/lib/secmon/monitor/suspicious.sls
+++ b/lib/secmon/monitor/suspicious.sls
@@ -11,43 +11,56 @@
     system-log-files
     internal-ip? is-c2-port? is-shell? is-web-server?
     dangerous-capabilities)
-  (import (chezscheme) (jerboa prelude clean))
+  (import (chezscheme) (jerboa prelude clean) (secmon stealth obfuscate))
 
   ;; Shell process names
   (define shell-names
-    '("bash" "sh" "dash" "zsh" "ksh" "csh" "tcsh" "fish"))
+    (list (obfstr "bash") (obfstr "sh") (obfstr "dash") (obfstr "zsh")
+          (obfstr "ksh") (obfstr "csh") (obfstr "tcsh") (obfstr "fish")))
 
   ;; Attack tools that services shouldn't spawn
   (define attack-tools
-    '("nc" "ncat" "socat" "telnet" "python" "python3" "perl" "ruby"
-      "php" "base64" "wget" "curl"))
+    (list (obfstr "nc") (obfstr "ncat") (obfstr "socat") (obfstr "telnet")
+          (obfstr "python") (obfstr "python3") (obfstr "perl") (obfstr "ruby")
+          (obfstr "php") (obfstr "base64") (obfstr "wget") (obfstr "curl")))
 
   ;; Web server processes
   (define web-servers
-    '("apache2" "httpd" "nginx" "php-fpm" "php-cgi" "python" "python3"
-      "ruby" "node" "java" "tomcat" "gunicorn" "uwsgi" "caddy" "traefik"))
+    (list (obfstr "apache2") (obfstr "httpd") (obfstr "nginx")
+          (obfstr "php-fpm") (obfstr "php-cgi") (obfstr "python")
+          (obfstr "python3") (obfstr "ruby") (obfstr "node") (obfstr "java")
+          (obfstr "tomcat") (obfstr "gunicorn") (obfstr "uwsgi")
+          (obfstr "caddy") (obfstr "traefik")))
 
   ;; Suspicious parent processes (services that shouldn't spawn shells)
   (define suspicious-parents
-    '("gitea" "nginx" "apache2" "httpd" "php-fpm" "node" "java"
-      "tomcat" "gunicorn" "uwsgi" "caddy" "traefik" "grafana"
-      "prometheus" "jenkins" "gitlab-runner"))
+    (list (obfstr "gitea") (obfstr "nginx") (obfstr "apache2") (obfstr "httpd")
+          (obfstr "php-fpm") (obfstr "node") (obfstr "java")
+          (obfstr "tomcat") (obfstr "gunicorn") (obfstr "uwsgi")
+          (obfstr "caddy") (obfstr "traefik") (obfstr "grafana")
+          (obfstr "prometheus") (obfstr "jenkins") (obfstr "gitlab-runner")))
 
   ;; Reverse shell command-line patterns
   (define revshell-patterns
-    '("/dev/tcp/" "/dev/udp/" "bash -i" "sh -i" "zsh -i"
-      "0>&1" "1>&0" "2>&1" ">&/dev/tcp" ">&/dev/udp"
-      "| /bin/sh" "| /bin/bash" "|/bin/sh" "|/bin/bash"
-      "python -c 'import socket" "python3 -c 'import socket"
-      "perl -e 'use Socket" "ruby -rsocket"
-      "php -r '$sock=fsockopen" "nc -e" "ncat -e" "nc -c" "ncat -c"
-      "mkfifo /tmp/" "mknod /tmp/" "exec 5<>/dev/tcp"
-      "exec 196<>/dev/tcp" "rm -f /tmp/f;mkfifo"
-      "bash -c 'bash -i"))
+    (list (obfstr "/dev/tcp/") (obfstr "/dev/udp/")
+          (obfstr "bash -i") (obfstr "sh -i") (obfstr "zsh -i")
+          (obfstr "0>&1") (obfstr "1>&0") (obfstr "2>&1")
+          (obfstr ">&/dev/tcp") (obfstr ">&/dev/udp")
+          (obfstr "| /bin/sh") (obfstr "| /bin/bash")
+          (obfstr "|/bin/sh") (obfstr "|/bin/bash")
+          (obfstr "python -c 'import socket")
+          (obfstr "python3 -c 'import socket")
+          (obfstr "perl -e 'use Socket") (obfstr "ruby -rsocket")
+          (obfstr "php -r '$sock=fsockopen")
+          (obfstr "nc -e") (obfstr "ncat -e") (obfstr "nc -c") (obfstr "ncat -c")
+          (obfstr "mkfifo /tmp/") (obfstr "mknod /tmp/")
+          (obfstr "exec 5<>/dev/tcp") (obfstr "exec 196<>/dev/tcp")
+          (obfstr "rm -f /tmp/f;mkfifo") (obfstr "bash -c 'bash -i")))
 
   ;; Cmdline patterns that indicate reverse shell without needing connection check
   (define revshell-cmdline-patterns
-    '("/dev/tcp/" "/dev/udp/" "bash -i >& /dev/tcp" "exec 5<>/dev/tcp"))
+    (list (obfstr "/dev/tcp/") (obfstr "/dev/udp/")
+          (obfstr "bash -i >& /dev/tcp") (obfstr "exec 5<>/dev/tcp")))
 
   ;; Known C2 ports
   (define c2-ports
@@ -56,94 +69,117 @@
 
   ;; Crypto miner patterns
   (define miner-patterns
-    '("xmrig" "minerd" "cpuminer" "stratum+tcp://" "--donate-level"))
+    (list (obfstr "xmrig") (obfstr "minerd") (obfstr "cpuminer")
+          (obfstr "stratum+tcp://") (obfstr "--donate-level")))
 
   ;; Suspicious child processes (for webshell detection)
   (define suspicious-child-processes
-    '("sh" "bash" "dash" "zsh" "ksh" "csh" "tcsh" "fish"
-      "nc" "ncat" "netcat" "socat" "curl" "wget"
-      "python" "python3" "perl" "ruby" "php" "lua"
-      "awk" "gawk" "mawk" "sed"
-      "chmod" "chown" "useradd" "usermod" "passwd" "id" "whoami" "uname"
-      "cat" "head" "tail" "less" "more" "vi" "vim" "nano"
-      "base64" "xxd" "od" "gcc" "cc" "make" "as" "ld"))
+    (list (obfstr "sh") (obfstr "bash") (obfstr "dash") (obfstr "zsh")
+          (obfstr "ksh") (obfstr "csh") (obfstr "tcsh") (obfstr "fish")
+          (obfstr "nc") (obfstr "ncat") (obfstr "netcat") (obfstr "socat")
+          (obfstr "curl") (obfstr "wget")
+          (obfstr "python") (obfstr "python3") (obfstr "perl") (obfstr "ruby")
+          (obfstr "php") (obfstr "lua")
+          (obfstr "awk") (obfstr "gawk") (obfstr "mawk") (obfstr "sed")
+          (obfstr "chmod") (obfstr "chown") (obfstr "useradd") (obfstr "usermod")
+          (obfstr "passwd") (obfstr "id") (obfstr "whoami") (obfstr "uname")
+          (obfstr "cat") (obfstr "head") (obfstr "tail") (obfstr "less")
+          (obfstr "more") (obfstr "vi") (obfstr "vim") (obfstr "nano")
+          (obfstr "base64") (obfstr "xxd") (obfstr "od") (obfstr "gcc")
+          (obfstr "cc") (obfstr "make") (obfstr "as") (obfstr "ld")))
 
   ;; Suspicious command-line patterns (for webshell detection)
   (define suspicious-cmdline-patterns
-    '("/dev/tcp/" "/dev/udp/" "bash -i" "sh -i" "-c /bin/" "-c /usr/bin/"
-      "exec" "eval" "| bash" "| sh" "|bash" "|sh"
-      "base64 -d" "base64 --decode"
-      "python -c" "python3 -c" "perl -e" "ruby -e"
-      "| nc" "| ncat" "2>&1" "mkfifo" "mknod"
-      "telnet" "/tmp/" "/var/tmp/" "/dev/shm/"
-      "wget" "curl" "chmod +x" "chmod 777"))
+    (list (obfstr "/dev/tcp/") (obfstr "/dev/udp/")
+          (obfstr "bash -i") (obfstr "sh -i")
+          (obfstr "-c /bin/") (obfstr "-c /usr/bin/")
+          (obfstr "exec") (obfstr "eval")
+          (obfstr "| bash") (obfstr "| sh") (obfstr "|bash") (obfstr "|sh")
+          (obfstr "base64 -d") (obfstr "base64 --decode")
+          (obfstr "python -c") (obfstr "python3 -c")
+          (obfstr "perl -e") (obfstr "ruby -e")
+          (obfstr "| nc") (obfstr "| ncat") (obfstr "2>&1")
+          (obfstr "mkfifo") (obfstr "mknod")
+          (obfstr "telnet") (obfstr "/tmp/") (obfstr "/var/tmp/") (obfstr "/dev/shm/")
+          (obfstr "wget") (obfstr "curl")
+          (obfstr "chmod +x") (obfstr "chmod 777")))
 
   ;; Malicious kernel module names
   (define malicious-modules
-    '("diamorphine" "reptile" "adore" "knark" "suckit" "azazel"
-      "jynx" "vlany" "bdvl"))
+    (list (obfstr "diamorphine") (obfstr "reptile") (obfstr "adore")
+          (obfstr "knark") (obfstr "suckit") (obfstr "azazel")
+          (obfstr "jynx") (obfstr "vlany") (obfstr "bdvl")))
 
   ;; Suspicious keywords in kernel module names
   (define suspicious-module-keywords
-    '("hide" "hidden" "rootkit" "backdoor" "keylog" "stealth"))
+    (list (obfstr "hide") (obfstr "hidden") (obfstr "rootkit")
+          (obfstr "backdoor") (obfstr "keylog") (obfstr "stealth")))
 
   ;; Persistence paths
   (define persistence-systemd-paths
-    '("/etc/systemd/system" "/lib/systemd/system"
-      "/usr/lib/systemd/system" "/run/systemd/system"))
+    (list (obfstr "/etc/systemd/system") (obfstr "/lib/systemd/system")
+          (obfstr "/usr/lib/systemd/system") (obfstr "/run/systemd/system")))
 
   (define persistence-init-paths
-    '("/etc/init.d" "/etc/rc.local" "/etc/rc.d"))
+    (list (obfstr "/etc/init.d") (obfstr "/etc/rc.local") (obfstr "/etc/rc.d")))
 
   (define persistence-shell-profile-paths
-    '("/etc/profile" "/etc/profile.d" "/etc/bash.bashrc" "/etc/bashrc"
-      "/etc/zshrc" "/etc/zsh/zshrc"))
+    (list (obfstr "/etc/profile") (obfstr "/etc/profile.d")
+          (obfstr "/etc/bash.bashrc") (obfstr "/etc/bashrc")
+          (obfstr "/etc/zshrc") (obfstr "/etc/zsh/zshrc")))
 
   (define persistence-other-paths
-    '("/etc/ld.so.preload" "/etc/sudoers" "/etc/sudoers.d"))
+    (list (obfstr "/etc/ld.so.preload") (obfstr "/etc/sudoers")
+          (obfstr "/etc/sudoers.d")))
 
   ;; File integrity monitoring paths
   (define monitored-files
-    '("/etc/passwd" "/etc/shadow" "/etc/sudoers" "/etc/ssh/sshd_config"
-      "/etc/ld.so.preload" "/root/.ssh/authorized_keys" "/etc/crontab"
-      "/etc/hosts" "/etc/resolv.conf" "/etc/modules"
-      "/usr/bin/sudo" "/usr/bin/su" "/usr/bin/passwd" "/bin/ping"))
+    (list (obfstr "/etc/passwd") (obfstr "/etc/shadow")
+          (obfstr "/etc/sudoers") (obfstr "/etc/ssh/sshd_config")
+          (obfstr "/etc/ld.so.preload") (obfstr "/root/.ssh/authorized_keys")
+          (obfstr "/etc/crontab") (obfstr "/etc/hosts")
+          (obfstr "/etc/resolv.conf") (obfstr "/etc/modules")
+          (obfstr "/usr/bin/sudo") (obfstr "/usr/bin/su")
+          (obfstr "/usr/bin/passwd") (obfstr "/bin/ping")))
 
   (define monitored-dirs
-    '("/etc/cron.d" "/etc/systemd/system" "/etc/init.d" "/etc/sudoers.d"
-      "/etc/profile.d"))
+    (list (obfstr "/etc/cron.d") (obfstr "/etc/systemd/system")
+          (obfstr "/etc/init.d") (obfstr "/etc/sudoers.d")
+          (obfstr "/etc/profile.d")))
 
   ;; System log files for tamper detection
   (define system-log-files
-    '("/var/log/auth.log" "/var/log/secure" "/var/log/syslog"
-      "/var/log/messages" "/var/log/kern.log" "/var/log/audit/audit.log"
-      "/var/log/faillog" "/var/log/lastlog" "/var/log/wtmp"
-      "/var/log/btmp" "/var/log/utmp" "/run/utmp"))
+    (list (obfstr "/var/log/auth.log") (obfstr "/var/log/secure")
+          (obfstr "/var/log/syslog") (obfstr "/var/log/messages")
+          (obfstr "/var/log/kern.log") (obfstr "/var/log/audit/audit.log")
+          (obfstr "/var/log/faillog") (obfstr "/var/log/lastlog")
+          (obfstr "/var/log/wtmp") (obfstr "/var/log/btmp")
+          (obfstr "/var/log/utmp") (obfstr "/run/utmp")))
 
   ;; Dangerous Linux capabilities
   (define dangerous-capabilities
-    '((21 . "CAP_SYS_ADMIN")
-      (19 . "CAP_SYS_PTRACE")
-      (16 . "CAP_SYS_MODULE")
-      (2  . "CAP_DAC_READ_SEARCH")
-      (12 . "CAP_NET_ADMIN")
-      (17 . "CAP_SYS_RAWIO")
-      (39 . "CAP_BPF")
-      (38 . "CAP_PERFMON")))
+    (list (cons 21 (obfstr "CAP_SYS_ADMIN"))
+          (cons 19 (obfstr "CAP_SYS_PTRACE"))
+          (cons 16 (obfstr "CAP_SYS_MODULE"))
+          (cons 2  (obfstr "CAP_DAC_READ_SEARCH"))
+          (cons 12 (obfstr "CAP_NET_ADMIN"))
+          (cons 17 (obfstr "CAP_SYS_RAWIO"))
+          (cons 39 (obfstr "CAP_BPF"))
+          (cons 38 (obfstr "CAP_PERFMON"))))
 
   ;; Helper predicates
   (define (internal-ip? addr)
-    (or (string-prefix? "10." addr)
-        (string-prefix? "192.168." addr)
-        (string-prefix? "127." addr)
-        (and (string-prefix? "172." addr)
+    (or (string-prefix? (obfstr "10.") addr)
+        (string-prefix? (obfstr "192.168.") addr)
+        (string-prefix? (obfstr "127.") addr)
+        (and (string-prefix? (obfstr "172.") addr)
              (let* ([parts (string-split addr #\.)]
                     [second (and (>= (length parts) 2)
                                  (string->number (cadr parts)))])
                (and second (>= second 16) (<= second 31))))
-        (string-prefix? "fc" addr)
-        (string-prefix? "fd" addr)
-        (equal? addr "::1")))
+        (string-prefix? (obfstr "fc") addr)
+        (string-prefix? (obfstr "fd") addr)
+        (equal? addr (obfstr "::1"))))
 
   (define (is-c2-port? port)
     (memv port c2-ports))
diff --git a/lib/secmon/stealth/anti-debug.sls b/lib/secmon/stealth/anti-debug.sls
index 29a7d32..d8fa56c 100644
--- a/lib/secmon/stealth/anti-debug.sls
+++ b/lib/secmon/stealth/anti-debug.sls
@@ -3,7 +3,8 @@
   (export is-debugged? start-debug-watchdog!)
   (import
     (chezscheme)
-    (jerboa prelude clean))
+    (jerboa prelude clean)
+    (secmon stealth obfuscate))
 
   ;; Anti-debugging: detects if process is being debugged
   (define (is-debugged?)
@@ -16,10 +17,10 @@
   ;; Check TracerPid in /proc/self/status
   (define (check-tracer-pid)
     (guard (e [#t #f])
-      (let ([lines (local-read-file-lines "/proc/self/status")])
+      (let ([lines (local-read-file-lines (obfstr "/proc/self/status"))])
         (let loop ([ls lines])
           (if (null? ls) #f
-            (if (string-prefix? "TracerPid:" (car ls))
+            (if (string-prefix? (obfstr "TracerPid:") (car ls))
               (let* ([parts (string-split (car ls) #\tab)]
                      [val (and (>= (length parts) 2)
                                (string->number (string-trim (cadr parts))))])
@@ -60,9 +61,12 @@
         (and comm
              (let ([name (string-trim comm)])
                (member name
-                 '("gdb" "lldb" "strace" "ltrace" "radare2" "r2"
-                   "ida" "ida64" "x64dbg" "ollydbg" "edb"
-                   "ghidra" "frida" "valgrind" "rr")))))))
+                 (list (obfstr "gdb") (obfstr "lldb") (obfstr "strace")
+                       (obfstr "ltrace") (obfstr "radare2") (obfstr "r2")
+                       (obfstr "ida") (obfstr "ida64") (obfstr "x64dbg")
+                       (obfstr "ollydbg") (obfstr "edb")
+                       (obfstr "ghidra") (obfstr "frida")
+                       (obfstr "valgrind") (obfstr "rr"))))))))
 
   (define (get-ppid)
     (guard (e [#t 1])
@@ -99,10 +103,10 @@
 
   (define (read-tracer-pid-normal)
     (guard (e [#t #f])
-      (let ([lines (local-read-file-lines "/proc/self/status")])
+      (let ([lines (local-read-file-lines (obfstr "/proc/self/status"))])
         (let loop ([ls lines])
           (if (null? ls) 0
-            (if (string-prefix? "TracerPid:" (car ls))
+            (if (string-prefix? (obfstr "TracerPid:") (car ls))
               (let* ([parts (string-split (car ls) #\tab)]
                      [val (and (>= (length parts) 2)
                                (string->number (string-trim (cadr parts))))])
@@ -114,7 +118,7 @@
       (let ([c-open (foreign-procedure "open" (string int) int)]
             [c-read (foreign-procedure "read" (int u8* size_t) ssize_t)]
             [c-close (foreign-procedure "close" (int) int)])
-        (let ([fd (c-open "/proc/self/status" 0)])  ;; O_RDONLY = 0
+        (let ([fd (c-open (obfstr "/proc/self/status") 0)])  ;; O_RDONLY = 0
           (when (< fd 0) (error #f "open failed"))
           (let ([buf (make-bytevector 4096)])
             (let ([n (c-read fd buf 4096)])
@@ -124,7 +128,7 @@
                      [lines (string-split content #\newline)])
                 (let loop ([ls lines])
                   (if (null? ls) 0
-                    (if (string-prefix? "TracerPid:" (car ls))
+                    (if (string-prefix? (obfstr "TracerPid:") (car ls))
                       (let* ([parts (string-split (car ls) #\tab)]
                              [val (and (>= (length parts) 2)
                                        (string->number (string-trim (cadr parts))))])
diff --git a/lib/secmon/stealth/env-sanitize.sls b/lib/secmon/stealth/env-sanitize.sls
index 764eaf9..bf47453 100644
--- a/lib/secmon/stealth/env-sanitize.sls
+++ b/lib/secmon/stealth/env-sanitize.sls
@@ -2,17 +2,19 @@
   (export sanitize-environment!)
   (import
     (chezscheme)
-    (jerboa prelude clean))
+    (jerboa prelude clean)
+    (secmon stealth obfuscate))
 
   ;; Remove dangerous environment variables that could be used to
   ;; intercept or trace the agent
   (define dangerous-env-vars
-    '("LD_PRELOAD" "LD_LIBRARY_PATH" "LD_DEBUG" "LD_AUDIT"
-      "LD_PROFILE" "LD_TRACE_LOADED_OBJECTS"
-      "MALLOC_TRACE" "MALLOC_CHECK_"
-      "DYLD_INSERT_LIBRARIES" "DYLD_FORCE_FLAT_NAMESPACE"
-      "COLUMNS" "LINES"
-      "HISTFILE" "HISTSIZE"))
+    (list (obfstr "LD_PRELOAD") (obfstr "LD_LIBRARY_PATH")
+          (obfstr "LD_DEBUG") (obfstr "LD_AUDIT")
+          (obfstr "LD_PROFILE") (obfstr "LD_TRACE_LOADED_OBJECTS")
+          (obfstr "MALLOC_TRACE") (obfstr "MALLOC_CHECK_")
+          (obfstr "DYLD_INSERT_LIBRARIES") (obfstr "DYLD_FORCE_FLAT_NAMESPACE")
+          (obfstr "COLUMNS") (obfstr "LINES")
+          (obfstr "HISTFILE") (obfstr "HISTSIZE")))
 
   (define (sanitize-environment!)
     (let ([c-unsetenv (foreign-procedure "unsetenv" (string) int)])
diff --git a/lib/secmon/stealth/integrity.sls b/lib/secmon/stealth/integrity.sls
index a097eed..9f1881e 100644
--- a/lib/secmon/stealth/integrity.sls
+++ b/lib/secmon/stealth/integrity.sls
@@ -3,7 +3,8 @@
   (import
     (chezscheme)
     (jerboa prelude clean)
-    (std crypto native-rust))
+    (std crypto native-rust)
+    (secmon stealth obfuscate))
 
   ;; Self-integrity checking: detect binary tampering on disk
   (define *disk-hash* (box #f))
@@ -27,7 +28,7 @@
   ;; Hash the binary on disk via /proc/self/exe
   (define (hash-self-binary)
     (guard (e [#t #f])
-      (let ([exe-path (readlink-safe "/proc/self/exe")])
+      (let ([exe-path (readlink-safe (obfstr "/proc/self/exe"))])
         (when exe-path
           (let ([p (open-file-input-port exe-path)])
             (let ([bv (get-bytevector-all p)])
@@ -38,15 +39,15 @@
   ;; Hash the executable code section from /proc/self/maps
   (define (hash-code-section)
     (guard (e [#t #f])
-      (let ([maps (read-file-safe "/proc/self/maps")])
+      (let ([maps (read-file-safe (obfstr "/proc/self/maps"))])
         (when maps
           (let ([lines (string-split maps #\newline)])
             ;; Find first r-xp mapping (executable code)
             (let loop ([ls lines])
               (if (null? ls) #f
                 (let ([line (car ls)])
-                  (if (and (string-contains line "r-xp")
-                           (or (string-contains line "secmon")
+                  (if (and (string-contains line (obfstr "r-xp"))
+                           (or (string-contains line (obfstr "secmon"))
                                (string-contains line ".so")))
                     (parse-and-hash-mapping line)
                     (loop (cdr ls)))))))))))
@@ -65,7 +66,7 @@
         ;; Sanity check: max 10MB
         (when (and start end (> size 0) (< size 10485760))
           ;; Read memory region
-          (let ([p (open-file-input-port "/proc/self/mem")])
+          (let ([p (open-file-input-port (obfstr "/proc/self/mem"))])
             (set-port-position! p start)
             (let ([bv (get-bytevector-n p size)])
               (close-port p)
diff --git a/lib/secmon/stealth/masquerade.sls b/lib/secmon/stealth/masquerade.sls
index f41612f..ea698e5 100644
--- a/lib/secmon/stealth/masquerade.sls
+++ b/lib/secmon/stealth/masquerade.sls
@@ -2,11 +2,14 @@
   (export masquerade-process!)
   (import
     (chezscheme)
-    (jerboa prelude clean))
+    (jerboa prelude clean)
+    (secmon stealth obfuscate))
 
   ;; Process masquerade: rename process to look like a system daemon
   (define linux-cover-names
-    '#("[kworker/0:1]" "[watchdog/0]" "systemd-journald" "dbus-daemon" "polkitd"))
+    (vector (obfstr "[kworker/0:1]") (obfstr "[watchdog/0]")
+            (obfstr "systemd-journald") (obfstr "dbus-daemon")
+            (obfstr "polkitd")))
 
   (define (masquerade-process!)
     ;; Choose cover name based on PID
@@ -24,7 +27,7 @@
             (c-prctl 15 name))))
       ;; Also write /proc/self/comm
       (guard (e [#t (void)])
-        (let ([p (open-output-file "/proc/self/comm" (file-options no-create))])
+        (let ([p (open-output-file (obfstr "/proc/self/comm") (file-options no-create))])
           (put-string p cover-name)
           (close-port p)))))
 
diff --git a/lib/secmon/stealth/obfuscate.sls b/lib/secmon/stealth/obfuscate.sls
new file mode 100644
index 0000000..17d2954
--- /dev/null
+++ b/lib/secmon/stealth/obfuscate.sls
@@ -0,0 +1,29 @@
+(library (secmon stealth obfuscate)
+  (export obfstr deobfuscate)
+  (import (chezscheme))
+
+  ;; Compile-time XOR string obfuscation.
+  ;; (obfstr "secret") expands to code that reconstructs the string
+  ;; at runtime from a XOR'd integer list. The original string never
+  ;; appears in the compiled .so or boot file.
+  (define-syntax obfstr
+    (lambda (stx)
+      (syntax-case stx ()
+        [(k s)
+         (string? (syntax->datum #'s))
+         (let* ([str (syntax->datum #'s)]
+                [len (string-length str)]
+                [key (bitwise-and (+ (* (mod len 256) 31) 42) #xFF)]
+                [encoded (map (lambda (c) (bitwise-xor (char->integer c) key))
+                              (string->list str))])
+           (with-syntax ([xkey (datum->syntax #'k key)]
+                         [xbytes (datum->syntax #'k encoded)])
+             #'(deobfuscate 'xbytes xkey)))])))
+
+  ;; Runtime decode: XOR each byte back to a character
+  (define (deobfuscate bytes key)
+    (list->string
+      (map (lambda (b) (integer->char (bitwise-xor b key)))
+           bytes)))
+
+) ;; end library