Skip to content

Instantly share code, notes, and snippets.

@mixinmax
Last active July 24, 2019 02:45
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save mixinmax/25bacb34711f4a0eade8 to your computer and use it in GitHub Desktop.
Save mixinmax/25bacb34711f4a0eade8 to your computer and use it in GitHub Desktop.
Uses 256-bit AES to encrypt a file which is signed using RSA. The ciphertext, RSA encrypted AES key and the signature are concatenated into a binary file to be used in rsa-decrypt.js
'use strict';
// set up required modules
var fs = require('fs');
var args = require('minimist')(process.argv.slice(2));
// the ursa module is imported to wrap OpenSSL and provide RSA encryption for
// the digital signing aswell as encrypting the symmetric key. URSA cannot do
// symmetric encryption natively, so we need another module for that
var ursa = require('ursa');
// the crypto module allows for the creation of pseudo-random bitstrings to be
// used for symmetric key creation and can also provide symmetric encryption
// and decryption
var crypto = require('crypto');
// make sure the proper amount of arguments exist
// this line could probably be a bit shorter...
if (!args.hasOwnProperty('in') || !args.hasOwnProperty('public') || !args.hasOwnProperty('private')) {
console.log("Usage: node encrypt.js --in=inputFile --public=publickey --private=privatekey");
process.exit(1);
}
console.log("\nNSA's Standard Encryption Utility");
console.log("with no backdoors (we swear)\n");
process.stdout.write("Working... ");
// read the file into memory
var msg = new Buffer(fs.readFileSync(args.in), 'hex');
// create the public and private keys
var key = ursa.createPrivateKey(fs.readFileSync(args.private));
var crt = ursa.createPublicKey(fs.readFileSync(args.public));
// generate the file's signature using RSA and SHA256 and the private key
var sig = key.hashAndSign('sha256', msg, 'hex', 'hex', true, ursa.RSA_PKCS1_SALT_LEN_HLEN);
sig = new Buffer(sig, 'hex');
// generate 256-bit symmetric key to be used for encryption
var token = crypto.randomBytes(32);
token = new Buffer(token, 'hex');
// encrypt file with the symmetric key using RSA
var cipher = crypto.createCipher('aes-256-cbc', token);
var enc_msg = cipher.update(msg, 'hex', 'hex');
enc_msg += cipher.final('hex');
enc_msg = new Buffer(enc_msg, 'hex');
// encrypt symmetric key with the public key
var enc_key = crt.encrypt(token, 'hex', 'hex');
enc_key = new Buffer(enc_key, 'hex')
// write results to a file
var wstream = fs.createWriteStream('output.bin', 'hex');
wstream.write(sig);
wstream.write(enc_key);
wstream.write(enc_msg);
wstream.end();
// tell the user the process is done
process.stdout.write("done\n");
console.log("Output binary saved to ./output.bin\n");
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment