commit a94046e17ae7f874de5e3b64686fef376aac7aa4
parent 66a97175590473fce07b6ce5f952ea8faa37abbf
Author: luajitos <bbhbb2094@gmail.com>
Date: Sat, 6 Dec 2025 15:43:00 +0000
Changed crypto cli to base64
Diffstat:
2 files changed, 147 insertions(+), 55 deletions(-)
diff --git a/crypto/crypto.c b/crypto/crypto.c
@@ -252,37 +252,14 @@ static const uint8_t* get_encrypted_from_arg(lua_State *L, int arg, size_t *len)
}
/*
- * Get key from base64 or binary string
+ * Get key from binary string
* Returns pointer to key data (valid until Lua string is collected)
*/
static const uint8_t* get_key_from_arg(lua_State *L, int arg, size_t *key_len) {
size_t len;
const char *key_str = luaL_checklstring(L, arg, &len);
-
- /* Check if it's base64 (longer than 32 bytes means it's likely base64) */
- if (len > 32) {
- /* Assume base64 */
- size_t decoded_len;
- uint8_t *decoded = base64_decode(key_str, len, &decoded_len);
- if (!decoded || decoded_len != 32) {
- if (decoded) free(decoded);
- luaL_error(L, "Key must be 32 bytes (decoded from base64)");
- return NULL;
- }
- /* Store decoded key in Lua string on stack */
- lua_pushlstring(L, (const char*)decoded, 32);
- lua_replace(L, arg);
- free(decoded);
- *key_len = 32;
- return (const uint8_t*)lua_tolstring(L, arg, key_len);
- } else if (len == 32) {
- /* Binary key */
- *key_len = len;
- return (const uint8_t*)key_str;
- } else {
- luaL_error(L, "Key must be 32 bytes");
- return NULL;
- }
+ *key_len = len;
+ return (const uint8_t*)key_str;
}
/* generateKey() - Generate a random 32-byte key (returns binary string) */
@@ -365,8 +342,8 @@ static int l_decrypt(lua_State *L) {
return 1;
}
-/* encryptString(key, plaintext) - Encrypt and return base64 string */
-static int l_encryptString(lua_State *L) {
+/* encryptAsBase64(key, plaintext) - Encrypt and return base64 string */
+static int l_encryptAsBase64(lua_State *L) {
size_t key_len;
const uint8_t *key = get_key_from_arg(L, 1, &key_len);
@@ -393,8 +370,8 @@ static int l_encryptString(lua_State *L) {
return 1;
}
-/* decryptString(key, base64_encrypted) - Decrypt from base64 string */
-static int l_decryptString(lua_State *L) {
+/* decryptFromBase64(key, base64_encrypted) - Decrypt from base64 string */
+static int l_decryptFromBase64(lua_State *L) {
size_t key_len;
const uint8_t *key = get_key_from_arg(L, 1, &key_len);
@@ -1101,8 +1078,8 @@ static const luaL_Reg crypto_functions[] = {
/* AES-256-GCM (default) */
{"encrypt", l_encrypt},
{"decrypt", l_decrypt},
- {"encryptString", l_encryptString},
- {"decryptString", l_decryptString},
+ {"encryptAsBase64", l_encryptAsBase64},
+ {"decryptFromBase64", l_decryptFromBase64},
/* ChaCha20-Poly1305 */
{"encryptChaCha", l_encryptChaCha},
@@ -1147,28 +1124,28 @@ int luaopen_crypto(lua_State *L) {
/* Create module table */
luaL_newlib(L, crypto_functions);
- /* Create AES subtable - crypto.AES.encrypt/encryptString/decrypt/decryptString (AES-256-GCM) */
+ /* Create AES subtable - crypto.AES.encrypt/encryptAsBase64/decrypt/decryptFromBase64 (AES-256-GCM) */
lua_newtable(L);
lua_pushcfunction(L, l_encrypt);
lua_setfield(L, -2, "encrypt");
- lua_pushcfunction(L, l_encryptString);
- lua_setfield(L, -2, "encryptString");
+ lua_pushcfunction(L, l_encryptAsBase64);
+ lua_setfield(L, -2, "encryptAsBase64");
lua_pushcfunction(L, l_decrypt);
lua_setfield(L, -2, "decrypt");
- lua_pushcfunction(L, l_decryptString);
- lua_setfield(L, -2, "decryptString");
+ lua_pushcfunction(L, l_decryptFromBase64);
+ lua_setfield(L, -2, "decryptFromBase64");
lua_setfield(L, -2, "AES");
- /* Create AES128 subtable - crypto.AES128.encrypt/encryptString/decrypt/decryptString (AES-128-GCM) */
+ /* Create AES128 subtable - crypto.AES128.encrypt/encryptAsBase64/decrypt/decryptFromBase64 (AES-128-GCM) */
lua_newtable(L);
lua_pushcfunction(L, l_encryptAES128);
lua_setfield(L, -2, "encrypt");
lua_pushcfunction(L, l_encryptAES128String);
- lua_setfield(L, -2, "encryptString");
+ lua_setfield(L, -2, "encryptAsBase64");
lua_pushcfunction(L, l_decryptAES128);
lua_setfield(L, -2, "decrypt");
lua_pushcfunction(L, l_decryptAES128String);
- lua_setfield(L, -2, "decryptString");
+ lua_setfield(L, -2, "decryptFromBase64");
lua_setfield(L, -2, "AES128");
/* Create ChaCha20 subtable */
@@ -1176,11 +1153,11 @@ int luaopen_crypto(lua_State *L) {
lua_pushcfunction(L, l_encryptChaCha);
lua_setfield(L, -2, "encrypt");
lua_pushcfunction(L, l_encryptChaChaString);
- lua_setfield(L, -2, "encryptString");
+ lua_setfield(L, -2, "encryptAsBase64");
lua_pushcfunction(L, l_decryptChaCha);
lua_setfield(L, -2, "decrypt");
lua_pushcfunction(L, l_decryptChaChaString);
- lua_setfield(L, -2, "decryptString");
+ lua_setfield(L, -2, "decryptFromBase64");
lua_setfield(L, -2, "ChaCha20");
/* Create XChaCha20 subtable */
@@ -1188,11 +1165,11 @@ int luaopen_crypto(lua_State *L) {
lua_pushcfunction(L, l_encryptXChaCha);
lua_setfield(L, -2, "encrypt");
lua_pushcfunction(L, l_encryptXChaChaString);
- lua_setfield(L, -2, "encryptString");
+ lua_setfield(L, -2, "encryptAsBase64");
lua_pushcfunction(L, l_decryptXChaCha);
lua_setfield(L, -2, "decrypt");
lua_pushcfunction(L, l_decryptXChaChaString);
- lua_setfield(L, -2, "decryptString");
+ lua_setfield(L, -2, "decryptFromBase64");
lua_setfield(L, -2, "XChaCha20");
/* Create Serpent subtable */
@@ -1200,11 +1177,11 @@ int luaopen_crypto(lua_State *L) {
lua_pushcfunction(L, l_encryptSerpent);
lua_setfield(L, -2, "encrypt");
lua_pushcfunction(L, l_encryptSerpentString);
- lua_setfield(L, -2, "encryptString");
+ lua_setfield(L, -2, "encryptAsBase64");
lua_pushcfunction(L, l_decryptSerpent);
lua_setfield(L, -2, "decrypt");
lua_pushcfunction(L, l_decryptSerpentString);
- lua_setfield(L, -2, "decryptString");
+ lua_setfield(L, -2, "decryptFromBase64");
lua_setfield(L, -2, "Serpent");
/* Create Twofish subtable */
@@ -1212,11 +1189,11 @@ int luaopen_crypto(lua_State *L) {
lua_pushcfunction(L, l_encryptTwofish);
lua_setfield(L, -2, "encrypt");
lua_pushcfunction(L, l_encryptTwofishString);
- lua_setfield(L, -2, "encryptString");
+ lua_setfield(L, -2, "encryptAsBase64");
lua_pushcfunction(L, l_decryptTwofish);
lua_setfield(L, -2, "decrypt");
lua_pushcfunction(L, l_decryptTwofishString);
- lua_setfield(L, -2, "decryptString");
+ lua_setfield(L, -2, "decryptFromBase64");
lua_setfield(L, -2, "Twofish");
/* Create Salsa20 subtable */
@@ -1224,11 +1201,11 @@ int luaopen_crypto(lua_State *L) {
lua_pushcfunction(L, l_encryptSalsa);
lua_setfield(L, -2, "encrypt");
lua_pushcfunction(L, l_encryptSalsaString);
- lua_setfield(L, -2, "encryptString");
+ lua_setfield(L, -2, "encryptAsBase64");
lua_pushcfunction(L, l_decryptSalsa);
lua_setfield(L, -2, "decrypt");
lua_pushcfunction(L, l_decryptSalsaString);
- lua_setfield(L, -2, "decryptString");
+ lua_setfield(L, -2, "decryptFromBase64");
lua_setfield(L, -2, "Salsa20");
/* Register hash functions directly on crypto table */
@@ -1400,12 +1377,12 @@ int luaopen_crypto(lua_State *L) {
/* Keep default encrypt/decrypt at top level (AES) for convenience */
lua_pushcfunction(L, l_encrypt);
lua_setfield(L, -2, "encrypt");
- lua_pushcfunction(L, l_encryptString);
- lua_setfield(L, -2, "encryptString");
+ lua_pushcfunction(L, l_encryptAsBase64);
+ lua_setfield(L, -2, "encryptAsBase64");
lua_pushcfunction(L, l_decrypt);
lua_setfield(L, -2, "decrypt");
- lua_pushcfunction(L, l_decryptString);
- lua_setfield(L, -2, "decryptString");
+ lua_pushcfunction(L, l_decryptFromBase64);
+ lua_setfield(L, -2, "decryptFromBase64");
return 1;
}
diff --git a/iso_includes/apps/com.luajitos.crypto/src/init.lua b/iso_includes/apps/com.luajitos.crypto/src/init.lua
@@ -124,6 +124,31 @@ local function fromHex(hex)
return binary
end
+-- Helper function to detect and convert key from hex or base64 to binary
+local function parseKey(keyStr)
+ if not keyStr then return nil, "No key provided" end
+
+ -- Check if it looks like hex (only hex chars, even length)
+ local hexClean = keyStr:gsub("%s+", "")
+ if hexClean:match("^[0-9a-fA-F]+$") and #hexClean % 2 == 0 then
+ -- It's hex
+ return fromHex(hexClean)
+ end
+
+ -- Check if it looks like base64
+ local b64Clean = keyStr:gsub("%s+", "")
+ if b64Clean:match("^[A-Za-z0-9+/]+=*$") and #b64Clean % 4 == 0 then
+ -- It's base64
+ local decoded = base64.decode(b64Clean)
+ if decoded then
+ return decoded
+ end
+ end
+
+ -- Assume it's raw binary/text
+ return keyStr
+end
+
-- Helper function to format output based on options
local function formatOutput(data, options)
if not data then return "nil" end
@@ -230,12 +255,18 @@ if #args == 0 then
print(" X25519.publicKey <privkey_hex> - Derive public key")
print(" X25519.shared <privkey_hex> <pubkey_hex> - Compute shared secret")
print("")
+ print("Encryption (key auto-detected as hex, base64, or raw):")
+ print(" encrypt <cipher> <key> <data>")
+ print(" decrypt <cipher> <key> <ciphertext>")
+ print(" Ciphers: AES-256-GCM, ChaCha20-Poly1305, Serpent-256-GCM,")
+ print(" Twofish-256-GCM, Salsa20-Poly1305")
+ print("")
print("Random:")
print(" random <bytes> - Generate random bytes")
print(" newKey <bytes> - Generate cryptographic key")
print("")
print("Options:")
- print(" -key/-k <value> - Specify key (hex encoded)")
+ print(" -key/-k <value> - Specify key (hex, base64, or raw)")
print(" -salt/-s <value> - Specify salt")
print(" -iterations/-i <num> - Number of iterations (default: 100000)")
print(" -b64/-base64 - Output in base64 format (default: hex)")
@@ -246,6 +277,8 @@ if #args == 0 then
print(" crypto PBKDF2 \"mypassword\" -salt \"randomsalt\" -i 100000")
print(" crypto Ed25519.keypair -b64")
print(" crypto random 32 -b64")
+ print(" crypto encrypt AES-256-GCM <key-hex-or-b64> \"secret data\"")
+ print(" crypto decrypt AES-256-GCM <key-hex-or-b64> <ciphertext>")
return
end
@@ -541,6 +574,88 @@ elseif command == "newKey" then
print("Error: Failed to generate key")
end
+-- Encryption
+elseif command == "encrypt" then
+ if #positional < 4 then
+ print("Error: encrypt requires cipher, key, and data arguments")
+ print("Usage: crypto encrypt <cipher> <key> <data>")
+ return
+ end
+ local cipher = positional[2]
+ local keyStr = positional[3]
+ local plaintext = positional[4]
+
+ -- Auto-convert key from hex/base64 to binary
+ local key, err = parseKey(keyStr)
+ if not key then
+ print("Error: Invalid key: " .. (err or "unknown error"))
+ return
+ end
+
+ -- Map cipher name to crypto function
+ local cipherFuncs = {
+ ["AES-256-GCM"] = crypto["AES-256-GCM"],
+ ["ChaCha20-Poly1305"] = crypto["ChaCha20-Poly1305"],
+ ["Serpent-256-GCM"] = crypto["Serpent-256-GCM"],
+ ["Twofish-256-GCM"] = crypto["Twofish-256-GCM"],
+ ["Salsa20-Poly1305"] = crypto["Salsa20-Poly1305"]
+ }
+
+ local cipherMod = cipherFuncs[cipher]
+ if not cipherMod then
+ print("Error: Unknown cipher '" .. cipher .. "'")
+ print("Valid ciphers: AES-256-GCM, ChaCha20-Poly1305, Serpent-256-GCM, Twofish-256-GCM, Salsa20-Poly1305")
+ return
+ end
+
+ local ciphertext, encErr = cipherMod.encryptAsBase64(plaintext, key)
+ if ciphertext then
+ print(ciphertext)
+ else
+ print("Error: Encryption failed: " .. (encErr or "unknown error"))
+ end
+
+-- Decryption
+elseif command == "decrypt" then
+ if #positional < 4 then
+ print("Error: decrypt requires cipher, key, and ciphertext arguments")
+ print("Usage: crypto decrypt <cipher> <key> <ciphertext>")
+ return
+ end
+ local cipher = positional[2]
+ local keyStr = positional[3]
+ local ciphertext = positional[4]
+
+ -- Auto-convert key from hex/base64 to binary
+ local key, err = parseKey(keyStr)
+ if not key then
+ print("Error: Invalid key: " .. (err or "unknown error"))
+ return
+ end
+
+ -- Map cipher name to crypto function
+ local cipherFuncs = {
+ ["AES-256-GCM"] = crypto["AES-256-GCM"],
+ ["ChaCha20-Poly1305"] = crypto["ChaCha20-Poly1305"],
+ ["Serpent-256-GCM"] = crypto["Serpent-256-GCM"],
+ ["Twofish-256-GCM"] = crypto["Twofish-256-GCM"],
+ ["Salsa20-Poly1305"] = crypto["Salsa20-Poly1305"]
+ }
+
+ local cipherMod = cipherFuncs[cipher]
+ if not cipherMod then
+ print("Error: Unknown cipher '" .. cipher .. "'")
+ print("Valid ciphers: AES-256-GCM, ChaCha20-Poly1305, Serpent-256-GCM, Twofish-256-GCM, Salsa20-Poly1305")
+ return
+ end
+
+ local plaintext, decErr = cipherMod.decryptFromBase64(ciphertext, key)
+ if plaintext then
+ print(plaintext)
+ else
+ print("Error: Decryption failed: " .. (decErr or "unknown error"))
+ end
+
else
print("Error: Unknown command '" .. command .. "'")
print("Use 'crypto' without arguments for help")