diff --git a/source/app.d b/source/app.d index aa1ce8e..f3ea994 100644 --- a/source/app.d +++ b/source/app.d @@ -11,19 +11,28 @@ int main(string[] args) "encrypt" : false, "decrypt" : false ]; - Cipher cipher = Cipher.chacha20; + Cipher cipher = Cipher.salsa20; string keyFileName = "symkey.asc"; bool armor; - auto helpInformation = getopt( - args, - std.getopt.config.bundling, - "gen-key|g", "Generate a new 256 bit key.", &actions["genKey"], - "encrypt|e", "Encrypt a message.", &actions["encrypt"], - "decrypt|d", "Decrypt a message.", &actions["decrypt"], - "cipher|c", "The cipher to use (default: %s).".format(cipher), &cipher, - "key|k", "The file which contains the key (default: %s).".format(keyFileName), &keyFileName, - "armor|a", "use ascii-armored I/O.", &armor); + GetoptResult result; + try + { + result = getopt( + args, + std.getopt.config.bundling, + "gen-key|g", "Generate a new 256 bit key.", &actions["genKey"], + "encrypt|e", "Encrypt a message.", &actions["encrypt"], + "decrypt|d", "Decrypt a message.", &actions["decrypt"], + "cipher|c", "The cipher to use (default: %s).".format(cipher), &cipher, + "key|k", "The file which contains the key (default: %s).".format(keyFileName), &keyFileName, + "armor|a", "use ascii-armored I/O.", &armor); + } + catch(Exception e) + { + stderr.writeln(e.msg); + return 1; + } size_t numberOfActions; foreach(value; actions.values) @@ -54,19 +63,22 @@ int main(string[] args) } else { - helpInformation.helpWanted = true; + result.helpWanted = true; } - if(helpInformation.helpWanted) - { - defaultGetoptPrinter("Usage: mycrypt [options]\n\nCommon options:", - helpInformation.options[$-1..$]); - defaultGetoptPrinter("\nGlobal options:", - helpInformation.options[$-2..$-1]); - defaultGetoptPrinter("\nActions:", - helpInformation.options[0..3]); - defaultGetoptPrinter("\nAction options:", - helpInformation.options[3..5]); - } + printHelp(result.options); + return 0; } + +void printHelp(Option[] options) +{ + defaultGetoptPrinter("Usage: learncrypt [options]\n\nCommon options:", + options[$-1..$]); + defaultGetoptPrinter("\nGlobal options:", + options[$-2..$-1]); + defaultGetoptPrinter("\nActions:", + options[0..3]); + defaultGetoptPrinter("\nAction options:", + options[3..5]); +} diff --git a/source/bitmanip.d b/source/bitmanip.d index 3dd19c7..1d4f5cb 100644 --- a/source/bitmanip.d +++ b/source/bitmanip.d @@ -1,8 +1,9 @@ module bitmanip; private import std.traits : isUnsigned; +private import std.bitmanip : nativeToLittleEndian, littleEndianToNative; -UIntType rotateLeft(UIntType)(in UIntType val, in size_t len) nothrow @nogc pure +UIntType rotateLeft(UIntType)(in UIntType val, in size_t len) nothrow @nogc pure @safe if(isUnsigned!UIntType) { auto reducedLen = len % (8 * UIntType.sizeof); @@ -19,7 +20,7 @@ unittest assert(test[1].rotateLeft(7) == 128); } -UIntType rotateRight(UIntType)(in UIntType val, in size_t len) nothrow @nogc pure +UIntType rotateRight(UIntType)(in UIntType val, in size_t len) nothrow @nogc pure @safe if(isUnsigned!UIntType) { auto reducedLen = len % (8 * UIntType.sizeof); @@ -35,3 +36,26 @@ unittest assert(test[2].rotateRight(1) == 64); assert(test[2].rotateRight(7) == 1); } + +alias littleEndianInv = nativeToLittleEndian; + +uint littleEndian(in ubyte[] input) @safe pure nothrow @nogc +in +{ + assert(input.length == uint.sizeof); +} +body +{ + ubyte[uint.sizeof] buf = input; + return littleEndianToNative!uint(buf); +} + +unittest +{ + ubyte[] test0 = [0, 0, 0, 0]; + ubyte[] test1 = [86, 75, 30, 9]; + ubyte[] test2 = [255, 255, 255, 250]; + assert(littleEndian(test0) == 0x00000000); + assert(littleEndian(test1) == 0x091e4b56); + assert(littleEndian(test2) == 0xfaffffff); +} diff --git a/source/chacha20.d b/source/chacha20.d index c128232..f738a9f 100644 --- a/source/chacha20.d +++ b/source/chacha20.d @@ -212,30 +212,7 @@ enum string colRound(alias _x00, alias _x01, alias _x02, alias _x03, 0x481c2027, 0x53a8e4b5, 0x4c1f89c5, 0x3f78c9c8]); }*/ -alias littleEndianInv = nativeToLittleEndian; - -uint littleEndian(in ubyte[] input) -in -{ - assert(input.length == uint.sizeof); -} -body -{ - ubyte[uint.sizeof] buf = input; - return littleEndianToNative!uint(buf); -} - -unittest -{ - ubyte[] test0 = [0, 0, 0, 0]; - ubyte[] test1 = [86, 75, 30, 9]; - ubyte[] test2 = [255, 255, 255, 250]; - assert(littleEndian(test0) == 0x00000000); - assert(littleEndian(test1) == 0x091e4b56); - assert(littleEndian(test2) == 0xfaffffff); -} - -ubyte[] chacha20(in ubyte[] input) +ubyte[] chacha20(in ubyte[] input) @safe nothrow pure in { assert(input.length == 64); @@ -332,7 +309,7 @@ enum ubyte[4] σ1 = [110, 100, 32, 51]; enum ubyte[4] σ2 = [ 50, 45, 98, 121]; enum ubyte[4] σ3 = [116, 101, 32, 107]; -ubyte[] chacha20Exp(in ubyte[] key, in ubyte[] n) +ubyte[] chacha20Exp(in ubyte[] key, in ubyte[] n) @safe nothrow pure in { assert(key.length == 32); diff --git a/source/cipher.d b/source/cipher.d index 620a731..cddfc9c 100644 --- a/source/cipher.d +++ b/source/cipher.d @@ -19,9 +19,9 @@ auto cipherFunction(R)(R range, ubyte[32] key, ubyte[8] nonce, Cipher cipher) final switch(cipher) { case Cipher.salsa20: - return salsa20Cipher(range, key, nonce); + return range.salsa20Cipher(key, nonce); case Cipher.chacha20: - return salsa20Cipher(range, key, nonce); + return range.salsa20Cipher(key, nonce); } } diff --git a/source/salsa20.d b/source/salsa20.d index b184465..b81f5a7 100644 --- a/source/salsa20.d +++ b/source/salsa20.d @@ -3,7 +3,6 @@ module salsa20; private import std.traits : isUnsigned; private import std.string : format; private import std.range : isInputRange, isForwardRange, ElementType; -private import std.bitmanip : nativeToLittleEndian, littleEndianToNative; private import std.array; private import bitmanip; @@ -212,30 +211,7 @@ unittest 0x481c2027, 0x53a8e4b5, 0x4c1f89c5, 0x3f78c9c8]); } -alias littleEndianInv = nativeToLittleEndian; - -uint littleEndian(in ubyte[] input) -in -{ - assert(input.length == uint.sizeof); -} -body -{ - ubyte[uint.sizeof] buf = input; - return littleEndianToNative!uint(buf); -} - -unittest -{ - ubyte[] test0 = [0, 0, 0, 0]; - ubyte[] test1 = [86, 75, 30, 9]; - ubyte[] test2 = [255, 255, 255, 250]; - assert(littleEndian(test0) == 0x00000000); - assert(littleEndian(test1) == 0x091e4b56); - assert(littleEndian(test2) == 0xfaffffff); -} - -ubyte[] salsa20(in ubyte[] input) +ubyte[] salsa20(in ubyte[] input) @save pure nothrow @safe in { assert(input.length == 64); @@ -332,7 +308,7 @@ enum ubyte[4] σ1 = [110, 100, 32, 51]; enum ubyte[4] σ2 = [ 50, 45, 98, 121]; enum ubyte[4] σ3 = [116, 101, 32, 107]; -ubyte[] salsa20Exp(in ubyte[] key, in ubyte[] n) +ubyte[] salsa20Exp(in ubyte[] key, in ubyte[] n) @safe pure nothrow in { assert(key.length == 32);