-
Notifications
You must be signed in to change notification settings - Fork 133
Description
Problem Description
I have a system that stores sensitive AI prompts securely, but they're still extractable via memory dumps despite encryption and memguard protection.
Current Workflow
-
Source: Sensitive prompts stored in
prompt.gofile:package main func GetData() string { return `# Role and Context You are an expert OpenAPI 3.0.0 specification generator with deep # Guidelines ## General Formatting ## Endpoint Specifications ...` // Large sensitive prompt content }
-
Build Process:
prompt.gois compiled intoprompt.soshared libraryprompt.sois encrypted using AES-256-GCM →prompt.so.enc
-
Runtime Process:
// Decrypt prompt.so.enc → prompt.so (temporary file) decryptFile("prompt.so.enc", tempPath) // Load plugin plugin.Open(tempPath) // Extract data and protect with memguard rawData := getDataFunc() // Gets the prompt string protected := memguard.NewBufferFromBytes([]byte(rawData))
-
Usage: Need to process prompt data (count characters, analyze content) but NOT expose it via API
Security Issue
Memory dumps still extract the original prompts despite memguard protection:
# Memory extraction shows:
[ERROR] FOUND in memory: 'Role and Context'
[ERROR] FOUND in memory: 'OpenAPI'
[ERROR] FOUND in memory: 'Guidelines'
# Full prompt content recoverable from process memoryRoot Cause Analysis
The memory leak occurs because:
- Plugin Loading:
plugin.Open()loads the compiledprompt.sointo memory, including all string literals from the originalprompt.go - String Constants: The
GetData()function's return value exists as embedded string constants in the plugin's data section - Memory Segments: These constants are loaded into regular process memory where memory dumps can extract them
- Memguard Limitation: memguard protects the copy, but original plugin data remains in unprotected memory
Current Architecture
prompt.go (source)
↓ [compile]
prompt.so (shared library with embedded strings)
↓ [encrypt]
prompt.so.enc (encrypted file)
↓ [runtime decrypt]
prompt.so (temporary, loaded by plugin.Open)
↓ [extract + memguard]
Protected memory (but original still extractable)
Security Requirement
- ✅ Can process data: Count characters, analyze prompt content
- ❌ Cannot extract via memory dump: Original prompt should not be recoverable from process memory
- ✅ Encrypted at rest: Data stored securely in
prompt.so.enc - ✅ Dynamic loading: System loads/decrypts at runtime, not compile-time
Questions for the Community
-
Is this approach fundamentally flawed? Can we ever prevent memory extraction when loading compiled Go plugins with embedded strings?
-
Alternative plugin architectures:
- Should
prompt.goread from an encrypted file instead of having embedded strings? - Could we use code generation to obfuscate the strings?
- Is there a way to store strings in a format that's not directly extractable?
- Should
-
Non-plugin alternatives:
- Custom encrypted file format with streaming decryption?
- In-memory XOR encoding/decoding?
- External process for prompt handling?
-
Memory protection: Are there Go libraries that provide stronger memory protection than memguard against dump attacks?
Environment
- Go version: go1.24.4
- OS: Linux
- Libraries: memguard, standard library plugins
- Attack vector: Memory dump tools scanning process memory regions
Expected Outcome
A solution where we can:
- Store prompts securely (currently in
prompt.go→ compiled → encrypted) - Process prompt data at runtime (count chars, analyze, etc.)
- Prevent memory dump attacks from extracting the original prompt content
- Maintain reasonable development workflow
Any suggestions on secure plugin architectures or alternative approaches would be greatly appreciated!
Repo link: https://github.com/lovestaco/simple-plugin-memguard