Got rid of flexblocks
This commit is contained in:
@@ -6,20 +6,20 @@
|
||||
|
||||
namespace Leonetienne::GCrypt {
|
||||
|
||||
Feistel::Feistel() {
|
||||
}
|
||||
|
||||
Feistel::Feistel(const Key& key) {
|
||||
SetKey(key);
|
||||
return;
|
||||
}
|
||||
|
||||
Feistel::~Feistel() {
|
||||
ZeroKeyMemory();
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
void Feistel::SetKey(const Key& key) {
|
||||
GenerateRoundKeys(key);
|
||||
return;
|
||||
isInitialized = true;
|
||||
}
|
||||
|
||||
Block Feistel::Encipher(const Block& data) {
|
||||
@@ -31,6 +31,10 @@ namespace Leonetienne::GCrypt {
|
||||
}
|
||||
|
||||
Block Feistel::Run(const Block& data, bool modeEncrypt) {
|
||||
if (!isInitialized) {
|
||||
throw std::runtime_error("Attempted to digest data on uninitialized GCipher!");
|
||||
}
|
||||
|
||||
const auto splitData = FeistelSplit(data);
|
||||
Halfblock l = splitData.first;
|
||||
Halfblock r = splitData.second;
|
||||
@@ -245,6 +249,7 @@ namespace Leonetienne::GCrypt {
|
||||
|
||||
void Feistel::operator=(const Feistel& other) {
|
||||
roundKeys = other.roundKeys;
|
||||
isInitialized = other.isInitialized;
|
||||
|
||||
return;
|
||||
}
|
||||
|
@@ -7,17 +7,33 @@
|
||||
|
||||
namespace Leonetienne::GCrypt {
|
||||
|
||||
GCipher::GCipher() {
|
||||
}
|
||||
|
||||
GCipher::GCipher(const Key& key, const DIRECTION direction) :
|
||||
direction { direction },
|
||||
lastBlock(InitializationVector(key)), // Initialize our lastBlock with some deterministic initial value, based on the key
|
||||
feistel(key)
|
||||
{
|
||||
isInitialized = true;
|
||||
return;
|
||||
}
|
||||
|
||||
void GCipher::Initialize(const Key& key, const DIRECTION direction) {
|
||||
feistel = Feistel(key);
|
||||
lastBlock = InitializationVector(key);
|
||||
this->direction = direction;
|
||||
isInitialized = true;
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
Block GCipher::Digest(const Block& input) {
|
||||
|
||||
if (!isInitialized) {
|
||||
throw std::runtime_error("Attempted to digest data on uninitialized GCipher!");
|
||||
}
|
||||
|
||||
switch (direction) {
|
||||
case DIRECTION::ENCIPHER: {
|
||||
// Rename our input to cleartext
|
||||
@@ -52,6 +68,11 @@ namespace Leonetienne::GCrypt {
|
||||
}
|
||||
|
||||
void GCipher::SetKey(const Key& key) {
|
||||
|
||||
if (!isInitialized) {
|
||||
throw std::runtime_error("Attempted to set key on uninitialized GCipher!");
|
||||
}
|
||||
|
||||
feistel.SetKey(key);
|
||||
|
||||
return;
|
||||
@@ -61,6 +82,7 @@ namespace Leonetienne::GCrypt {
|
||||
direction = other.direction;
|
||||
feistel = other.feistel;
|
||||
lastBlock = other.lastBlock;
|
||||
isInitialized = other.isInitialized;
|
||||
|
||||
return;
|
||||
}
|
||||
|
@@ -5,17 +5,23 @@
|
||||
|
||||
namespace Leonetienne::GCrypt {
|
||||
|
||||
GHash::GHash() :
|
||||
GHash::GHash() {
|
||||
// Initialize our cipher with a static, but randomly distributed key.
|
||||
cipher(
|
||||
Block ivSeed;
|
||||
ivSeed.FromByteString("3J7IipfQTDJbO8jtasz9PgWui6faPaEMOuVuAqyhB1S2CRcLw5caawewgDUEG1WN");
|
||||
block = InitializationVector(ivSeed);
|
||||
|
||||
Key key;
|
||||
key.FromByteString("nsoCZfvdqpRkeVTt9wzvPR3TT26peOW9E2kTHh3pdPCq2M7BpskvUljJHSrobUTI");
|
||||
|
||||
cipher = GCipher(
|
||||
// The key really does not matter, as it gets changed
|
||||
// each time before digesting anything.
|
||||
Key(StringToBitblock("nsoCZfvdqpRkeVTt9wzvPR3TT26peOW9E2kTHh3pdPCq2M7BpskvUljJHSrobUTI")),
|
||||
key,
|
||||
GCipher::DIRECTION::ENCIPHER
|
||||
) {
|
||||
block = InitializationVector(StringToBitblock("3J7IipfQTDJbO8jtasz9PgWui6faPaEMOuVuAqyhB1S2CRcLw5caawewgDUEG1WN"));
|
||||
);
|
||||
|
||||
return;
|
||||
return;
|
||||
}
|
||||
|
||||
void GHash::DigestBlock(const Block& data) {
|
||||
@@ -64,7 +70,8 @@ namespace Leonetienne::GCrypt {
|
||||
|
||||
std::stringstream ss;
|
||||
ss << n_bytes;
|
||||
const Block lengthBlock = StringToBitblock(ss.str());
|
||||
Block lengthBlock;
|
||||
lengthBlock.FromTextString(ss.str());
|
||||
|
||||
// Digest the length block
|
||||
hasher.DigestBlock(lengthBlock);
|
||||
|
@@ -134,35 +134,25 @@ namespace Leonetienne::GCrypt {
|
||||
}
|
||||
}
|
||||
|
||||
Flexblock GWrapper::CipherFlexblock(
|
||||
const Flexblock& data,
|
||||
std::vector<Block> GWrapper::CipherBlocks(
|
||||
const std::vector<Block>& data,
|
||||
const Key& key,
|
||||
const GCipher::DIRECTION direction)
|
||||
{
|
||||
// Split input into blocks
|
||||
std::vector<Block> blocks;
|
||||
|
||||
for (std::size_t i = 0; i < data.size(); i += Block::BLOCK_SIZE_BITS) {
|
||||
blocks.push_back(Block(
|
||||
PadStringToLength(data.substr(i, Block::BLOCK_SIZE_BITS), Block::BLOCK_SIZE_BITS, '0', false))
|
||||
);
|
||||
}
|
||||
|
||||
// Create cipher instance
|
||||
GCipher cipher(key, direction);
|
||||
|
||||
for (Block& block : blocks) {
|
||||
block = cipher.Digest(block);
|
||||
}
|
||||
std::vector<Block> digested;
|
||||
digested.reserve(data.size());
|
||||
|
||||
// Concatenate ciphertext blocks back into a flexblock
|
||||
std::stringstream ss;
|
||||
for (Block& b : blocks) {
|
||||
ss << b;
|
||||
// Digest all our blocks
|
||||
for (const Block& block : data) {
|
||||
Block digestedBlock = cipher.Digest(block);
|
||||
digested.emplace_back(digestedBlock);
|
||||
}
|
||||
|
||||
// Return it
|
||||
return ss.str();
|
||||
return digested;
|
||||
}
|
||||
}
|
||||
|
||||
|
@@ -30,58 +30,16 @@ namespace Leonetienne::GCrypt {
|
||||
return ss.str();
|
||||
}
|
||||
|
||||
Block StringToBitblock(const std::string& s, bool padLeft) {
|
||||
std::stringstream ss;
|
||||
|
||||
for (std::size_t i = 0; i < s.size(); i++) {
|
||||
ss << std::bitset<8>(s[i]);
|
||||
}
|
||||
|
||||
// Pad rest with zeores
|
||||
return Block(PadStringToLength(ss.str(), Block::BLOCK_SIZE_BITS, '0', padLeft));
|
||||
}
|
||||
|
||||
Flexblock StringToBits(const std::string& s) {
|
||||
std::stringstream ss;
|
||||
|
||||
for (std::size_t i = 0; i < s.size(); i++) {
|
||||
ss << std::bitset<8>(s[i]);
|
||||
}
|
||||
|
||||
return Flexblock(ss.str());
|
||||
}
|
||||
|
||||
std::string BitblockToBytes(const Block& block) {
|
||||
std::stringstream ss;
|
||||
|
||||
std::uint8_t* curByte = (std::uint8_t*)(void*)block.Data();
|
||||
for (std::size_t j = 0; j < Block::BLOCK_SIZE; j++) {
|
||||
ss << *curByte++;
|
||||
}
|
||||
|
||||
return ss.str();
|
||||
}
|
||||
|
||||
std::string BitblocksToBytes(const std::vector<Block>& blocks) {
|
||||
std::stringstream ss;
|
||||
|
||||
for (const Block& block : blocks) {
|
||||
ss << BitblockToBytes(block);
|
||||
ss << block.ToByteString();
|
||||
}
|
||||
|
||||
return ss.str();
|
||||
}
|
||||
|
||||
std::string BitblockToString(const Block& bits) {
|
||||
// Decode to bytes
|
||||
std::string text = BitblockToBytes(bits);
|
||||
|
||||
// Dümp excess nullbytes
|
||||
text.resize(strlen(text.data()));
|
||||
|
||||
return text;
|
||||
}
|
||||
|
||||
std::string BitblocksToString(const std::vector<Block>& blocks) {
|
||||
// Decode to bytes
|
||||
std::string text = BitblocksToBytes(blocks);
|
||||
@@ -92,146 +50,6 @@ namespace Leonetienne::GCrypt {
|
||||
return text;
|
||||
}
|
||||
|
||||
std::string BitsToBytes(const Flexblock& bits) {
|
||||
std::stringstream ss;
|
||||
|
||||
const std::string bitstring = bits;
|
||||
|
||||
for (std::size_t i = 0; i < bits.size(); i += 8) {
|
||||
ss << (char)std::bitset<8>(bitstring.substr(i, 8)).to_ulong();
|
||||
}
|
||||
|
||||
return ss.str();
|
||||
}
|
||||
|
||||
std::string BitsToString(const Flexblock& bits) {
|
||||
// Decode to bytes
|
||||
std::string text = BitsToBytes(bits);
|
||||
|
||||
// Dümp excess nullbytes
|
||||
text.resize(strlen(text.data()));
|
||||
|
||||
return text;
|
||||
}
|
||||
|
||||
std::string BitblockToHexstring(const Block& b) {
|
||||
std::stringstream ss;
|
||||
const std::string charset = "0123456789abcdef";
|
||||
const std::string bstr = b.ToBinaryString();
|
||||
|
||||
for (std::size_t i = 0; i < bstr.size(); i += 4) {
|
||||
ss << charset[std::bitset<4>(bstr.substr(i, 4)).to_ulong()];
|
||||
}
|
||||
|
||||
return ss.str();
|
||||
}
|
||||
|
||||
std::string BitsToHexstring(const Flexblock& b) {
|
||||
std::stringstream ss;
|
||||
const std::string charset = "0123456789abcdef";
|
||||
const std::string bstr = b;
|
||||
|
||||
for (std::size_t i = 0; i < bstr.size(); i += 4) {
|
||||
ss << charset[std::bitset<4>(bstr.substr(i, 4)).to_ulong()];
|
||||
}
|
||||
|
||||
return ss.str();
|
||||
}
|
||||
|
||||
Block HexstringToBitblock(const std::string& hexstring) {
|
||||
std::stringstream ss;
|
||||
|
||||
for (std::size_t i = 0; i < hexstring.size(); i++) {
|
||||
const char c = hexstring[i];
|
||||
|
||||
// Get value
|
||||
std::size_t value;
|
||||
if ((c >= '0') && (c <= '9')) {
|
||||
// Is it a number?
|
||||
value = ((std::size_t)c - '0') + 0;
|
||||
}
|
||||
else if ((c >= 'a') && (c <= 'f')) {
|
||||
// Else, it is a lowercase letter
|
||||
value = ((std::size_t)c - 'a') + 10;
|
||||
}
|
||||
else {
|
||||
throw std::logic_error("non-hex string detected in HexstringToBits()");
|
||||
}
|
||||
|
||||
// Append to our bits
|
||||
ss << std::bitset<4>(value).to_string();
|
||||
}
|
||||
|
||||
return Block(ss.str());
|
||||
}
|
||||
|
||||
Flexblock HexstringToBits(const std::string& hexstring) {
|
||||
std::stringstream ss;
|
||||
|
||||
for (std::size_t i = 0; i < hexstring.size(); i++) {
|
||||
const char c = hexstring[i];
|
||||
|
||||
// Get value
|
||||
std::size_t value;
|
||||
if ((c >= '0') && (c <= '9')) {
|
||||
// Is it a number?
|
||||
value = ((std::size_t)c - '0') + 0;
|
||||
}
|
||||
else if ((c >= 'a') && (c <= 'f')) {
|
||||
// Else, it is a lowercase letter
|
||||
value = ((std::size_t)c - 'a') + 10;
|
||||
}
|
||||
else {
|
||||
throw std::logic_error("non-hex string detected in HexstringToBits()");
|
||||
}
|
||||
|
||||
// Append to our bits
|
||||
ss << std::bitset<4>(value).to_string();
|
||||
}
|
||||
|
||||
return ss.str();
|
||||
}
|
||||
|
||||
Flexblock ReadFileToBits(const std::string& filepath) {
|
||||
// Read file
|
||||
std::ifstream ifs(filepath, std::ios::binary);
|
||||
|
||||
if (!ifs.good()) {
|
||||
throw std::runtime_error("Unable to open ifilestream!");
|
||||
}
|
||||
|
||||
std::stringstream ss;
|
||||
std::copy(
|
||||
std::istreambuf_iterator<char>(ifs),
|
||||
std::istreambuf_iterator<char>(),
|
||||
std::ostreambuf_iterator<char>(ss)
|
||||
);
|
||||
|
||||
ifs.close();
|
||||
|
||||
const std::string bytes = ss.str();
|
||||
|
||||
// Convert bytes to bits
|
||||
return StringToBits(bytes);
|
||||
}
|
||||
|
||||
void WriteBitsToFile(const std::string& filepath, const Flexblock& bits) {
|
||||
// Convert bits to bytes
|
||||
const std::string bytes = BitsToBytes(bits);
|
||||
|
||||
// Write bits to file
|
||||
std::ofstream ofs(filepath, std::ios::binary);
|
||||
|
||||
if (!ofs.good()) {
|
||||
throw std::runtime_error("Unable to open ofilestream!");
|
||||
}
|
||||
|
||||
ofs.write(bytes.data(), bytes.length());
|
||||
ofs.close();
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
std::vector<Block> ReadFileToBlocks(const std::string& filepath, std::size_t& bytes_read) {
|
||||
// Read file
|
||||
bytes_read = 0;
|
||||
|
Reference in New Issue
Block a user