diff --git a/include/ConsoleProgress.hpp b/include/ConsoleProgress.hpp index 3289da0..ca42304 100644 --- a/include/ConsoleProgress.hpp +++ b/include/ConsoleProgress.hpp @@ -13,7 +13,7 @@ class ConsoleProgress : public Progress public: /// Start a thread to print progress explicit ConsoleProgress(std::ostream& os, - const std::chrono::milliseconds& interval = std::chrono::milliseconds(200)); + const std::chrono::milliseconds& interval = std::chrono::milliseconds{200}); /// Notify and stop the printing thread ~ConsoleProgress(); diff --git a/include/Progress.hpp b/include/Progress.hpp index 7e6f64b..6cd6d42 100644 --- a/include/Progress.hpp +++ b/include/Progress.hpp @@ -25,7 +25,7 @@ class Progress template void log(F f) { - const std::scoped_lock lock{m_os_mutex}; + const auto lock = std::scoped_lock{m_os_mutex}; f(m_os); } diff --git a/include/types.hpp b/include/types.hpp index 2d3eb21..439f114 100644 --- a/include/types.hpp +++ b/include/types.hpp @@ -36,7 +36,7 @@ constexpr auto msb(std::uint32_t x) -> std::uint8_t /// Constant value for bit masking template -constexpr std::uint32_t mask = ~0u << begin & ~0u >> (32 - end); +constexpr auto mask = std::uint32_t{~0u << begin & ~0u >> (32 - end)}; /// \brief Maximum difference between 32-bits integers A and B[x,32) /// knowing that A = B + b and b is a byte. @@ -48,6 +48,6 @@ constexpr std::uint32_t mask = ~0u << begin & ~0u >> (32 - end); /// A - B[x,32) = B[0,x) + b /// A - B[x,32) <= 0xffffffff[0,x) + 0xff template -constexpr std::uint32_t maxdiff = mask<0, x> + 0xff; +constexpr auto maxdiff = std::uint32_t{mask<0, x> + 0xff}; #endif // BKCRACK_TYPES_HPP diff --git a/src/Arguments.cpp b/src/Arguments.cpp index b81af73..164cbb2 100644 --- a/src/Arguments.cpp +++ b/src/Arguments.cpp @@ -14,7 +14,7 @@ namespace auto charRange(char first, char last) -> std::bitset<256> { - std::bitset<256> bitset; + auto bitset = std::bitset<256>{}; do { @@ -33,11 +33,11 @@ auto translateIntParseError(F&& f, const std::string& value) } catch (const std::invalid_argument&) { - throw Arguments::Error("expected an integer, got \"" + value + "\""); + throw Arguments::Error{"expected an integer, got \"" + value + "\""}; } catch (const std::out_of_range&) { - throw Arguments::Error("integer value " + value + " is out of range"); + throw Arguments::Error{"integer value " + value + " is out of range"}; } } @@ -53,11 +53,11 @@ auto parseSize(const std::string& value) -> std::size_t auto parseInterval(const std::string& value) -> std::variant { - const std::string separator = ".."; + const auto separator = std::string{".."}; if (const auto minEnd = value.find(separator); minEnd != std::string::npos) { - Arguments::LengthInterval interval; + auto interval = Arguments::LengthInterval{}; if (0 < minEnd) interval.minLength = parseSize(value.substr(0, minEnd)); @@ -74,7 +74,7 @@ auto parseInterval(const std::string& value) -> std::variant(Data::encryptionHeaderSize); + constexpr auto minimumOffset = -static_cast(Data::encryptionHeaderSize); if (offset < minimumOffset) - throw Error("plaintext offset " + std::to_string(offset) + " is too small (minimum is " + - std::to_string(minimumOffset) + ")"); + throw Error{"plaintext offset " + std::to_string(offset) + " is too small (minimum is " + + std::to_string(minimumOffset) + ")"}; } if (decipheredFile && !cipherFile && !cipherIndex) - throw Error("-c or --cipher-index parameter is missing (required by -d)"); + throw Error{"-c or --cipher-index parameter is missing (required by -d)"}; if (decipheredFile && !cipherArchive && decipheredFile == cipherFile) - throw Error("-c and -d parameters must point to different files"); + throw Error{"-c and -d parameters must point to different files"}; if (changePassword && !cipherArchive) - throw Error("-C parameter is missing (required by -U)"); + throw Error{"-C parameter is missing (required by -U)"}; if (changePassword && changePassword->unlockedArchive == cipherArchive) - throw Error("-C and -U parameters must point to different files"); + throw Error{"-C and -U parameters must point to different files"}; if (changeKeys && !cipherArchive) - throw Error("-C parameter is missing (required by --change-keys)"); + throw Error{"-C parameter is missing (required by --change-keys)"}; if (changeKeys && changeKeys->unlockedArchive == cipherArchive) - throw Error("-C and --change-keys parameters must point to different files"); + throw Error{"-C and --change-keys parameters must point to different files"}; if (length && !bruteforce) - throw Error("--bruteforce parameter is missing (required by --length)"); + throw Error{"--bruteforce parameter is missing (required by --length)"}; } auto Arguments::loadData() const -> Data { // load known plaintext - std::vector plaintext; + auto plaintext = std::vector{}; if (plainArchive) { const auto archive = Zip{*plainArchive}; @@ -160,14 +160,14 @@ auto Arguments::loadData() const -> Data plaintext = loadFile(*plainFile, plainFilePrefix); // load ciphertext needed by the attack - std::size_t needed = Data::encryptionHeaderSize; + auto needed = Data::encryptionHeaderSize; if (!plaintext.empty()) needed = std::max(needed, Data::encryptionHeaderSize + offset + plaintext.size()); if (!extraPlaintext.empty()) needed = std::max(needed, Data::encryptionHeaderSize + extraPlaintext.rbegin()->first + 1); - std::vector ciphertext; - std::optional> extraPlaintextWithCheckByte; + auto ciphertext = std::vector{}; + auto extraPlaintextWithCheckByte = std::optional>{}; if (cipherArchive) { const auto archive = Zip{*cipherArchive}; @@ -184,8 +184,7 @@ auto Arguments::loadData() const -> Data else ciphertext = loadFile(*cipherFile, needed); - return Data(std::move(ciphertext), std::move(plaintext), offset, - extraPlaintextWithCheckByte.value_or(extraPlaintext)); + return {std::move(ciphertext), std::move(plaintext), offset, extraPlaintextWithCheckByte.value_or(extraPlaintext)}; } auto Arguments::LengthInterval::operator&(const Arguments::LengthInterval& other) const -> Arguments::LengthInterval @@ -228,8 +227,8 @@ void Arguments::parseArgument() break; case Option::extraPlaintext: { - int i = readInt("offset"); - for (const std::uint8_t b : readHex("data")) + auto i = readInt("offset"); + for (const auto b : readHex("data")) extraPlaintext[i++] = b; break; } @@ -255,7 +254,7 @@ void Arguments::parseArgument() changePassword = {readString("unlockedzip"), readString("password")}; break; case Option::changeKeys: - changeKeys = {readString("unlockedzip"), Keys{readKey("X"), readKey("Y"), readKey("Z")}}; + changeKeys = {readString("unlockedzip"), {readKey("X"), readKey("Y"), readKey("Z")}}; break; case Option::bruteforce: bruteforce = readCharset(); @@ -312,7 +311,7 @@ void Arguments::parseArgument() auto Arguments::readString(const std::string& description) -> std::string { if (finished()) - throw Error("expected " + description + ", got nothing"); + throw Error{"expected " + description + ", got nothing"}; return *m_current++; } @@ -323,7 +322,7 @@ auto Arguments::readOption(const std::string& description) -> Arguments::Option #define PAIR(string, option) {#string, Option::option} #define PAIRS(short, long, option) PAIR(short, option), PAIR(long, option) - static const std::map stringToOption = { + static const auto stringToOption = std::map{ PAIRS(-c, --cipher-file, cipherFile), PAIR ( --cipher-index, cipherIndex), PAIRS(-C, --cipher-zip, cipherArchive), @@ -356,9 +355,9 @@ auto Arguments::readOption(const std::string& description) -> Arguments::Option #undef PAIR #undef PAIRS - const std::string str = readString(description); + const auto str = readString(description); if (const auto it = stringToOption.find(str); it == stringToOption.end()) - throw Error("unknown option " + str); + throw Error{"unknown option " + str}; else return it->second; } @@ -375,15 +374,15 @@ auto Arguments::readSize(const std::string& description) -> std::size_t auto Arguments::readHex(const std::string& description) -> std::vector { - std::string str = readString(description); + const auto str = readString(description); if (str.size() % 2) - throw Error("expected an even-length string, got " + str); - if (!std::all_of(str.begin(), str.end(), [](unsigned char c) { return std::isxdigit(c); })) - throw Error("expected " + description + " in hexadecimal, got " + str); + throw Error{"expected an even-length string, got " + str}; + if (!std::all_of(str.begin(), str.end(), [](char c) { return std::isxdigit(static_cast(c)); })) + throw Error{"expected " + description + " in hexadecimal, got " + str}; - std::vector data; - for (std::size_t i = 0; i < str.length(); i += 2) + auto data = std::vector{}; + for (auto i = std::size_t{}; i < str.length(); i += 2) data.push_back(static_cast(std::stoul(str.substr(i, 2), nullptr, 16))); return data; @@ -391,30 +390,30 @@ auto Arguments::readHex(const std::string& description) -> std::vector std::uint32_t { - std::string str = readString(description); + const auto str = readString(description); if (str.size() > 8) - throw Error("expected a string of length 8 or less, got " + str); - if (!std::all_of(str.begin(), str.end(), [](unsigned char c) { return std::isxdigit(c); })) - throw Error("expected " + description + " in hexadecimal, got " + str); + throw Error{"expected a string of length 8 or less, got " + str}; + if (!std::all_of(str.begin(), str.end(), [](char c) { return std::isxdigit(static_cast(c)); })) + throw Error{"expected " + description + " in hexadecimal, got " + str}; return static_cast(std::stoul(str, nullptr, 16)); } auto Arguments::readCharset() -> std::vector { - const std::bitset<256> lowercase = charRange('a', 'z'); - const std::bitset<256> uppercase = charRange('A', 'Z'); - const std::bitset<256> digits = charRange('0', '9'); - const std::bitset<256> alphanum = lowercase | uppercase | digits; - const std::bitset<256> printable = charRange(' ', '~'); - const std::bitset<256> punctuation = printable & ~alphanum; - - const std::string charsetArg = readString("charset"); + const auto lowercase = charRange('a', 'z'); + const auto uppercase = charRange('A', 'Z'); + const auto digits = charRange('0', '9'); + const auto alphanum = lowercase | uppercase | digits; + const auto printable = charRange(' ', '~'); + const auto punctuation = printable & ~alphanum; + + const auto charsetArg = readString("charset"); if (charsetArg.empty()) - throw Error("the charset for password recovery is empty"); + throw Error{"the charset for password recovery is empty"}; - std::bitset<256> charset; + auto charset = std::bitset<256>{}; for (auto it = charsetArg.begin(); it != charsetArg.end(); ++it) { @@ -439,15 +438,15 @@ auto Arguments::readCharset() -> std::vector case '?': charset.set('?'); break; // clang-format on default: - throw Error(std::string("unknown charset ?") + *it); + throw Error{std::string{"unknown charset ?"} + *it}; } } else charset.set(*it); } - std::vector result; - for (int c = 0; c < 256; c++) + auto result = std::vector{}; + for (auto c = 0; c < 256; c++) if (charset[c]) result.push_back(c); diff --git a/src/Attack.cpp b/src/Attack.cpp index d626115..b37926a 100644 --- a/src/Attack.cpp +++ b/src/Attack.cpp @@ -11,12 +11,12 @@ Attack::Attack(const Data& data, std::size_t index, std::vector& solutions, std::mutex& solutionsMutex, bool exhaustive, Progress& progress) -: data(data) -, index(index + 1 - Attack::contiguousSize) -, solutions(solutions) -, solutionsMutex(solutionsMutex) -, exhaustive(exhaustive) -, progress(progress) +: data{data} +, index{index + 1 - Attack::contiguousSize} +, solutions{solutions} +, solutionsMutex{solutionsMutex} +, exhaustive{exhaustive} +, progress{progress} { } @@ -31,10 +31,10 @@ void Attack::exploreZlists(int i) if (i != 0) // the Z-list is not complete so generate Z{i-1}[2,32) values { // get Z{i-1}[10,32) from CRC32^-1 - const std::uint32_t zim1_10_32 = Crc32Tab::getZim1_10_32(zlist[i]); + const auto zim1_10_32 = Crc32Tab::getZim1_10_32(zlist[i]); // get Z{i-1}[2,16) values from keystream byte k{i-1} and Z{i-1}[10,16) - for (const std::uint32_t zim1_2_16 : KeystreamTab::getZi_2_16_vector(data.keystream[index + i - 1], zim1_10_32)) + for (const auto zim1_2_16 : KeystreamTab::getZi_2_16_vector(data.keystream[index + i - 1], zim1_10_32)) { // add Z{i-1}[2,32) to the Z-list zlist[i - 1] = zim1_10_32 | zim1_2_16; @@ -53,10 +53,10 @@ void Attack::exploreZlists(int i) else // the Z-list is complete so iterate over possible Y values { // guess Y7[8,24) and keep prod == (Y7[8,32) - 1) * mult^-1 - for (std::uint32_t y7_8_24 = 0, prod = (MultTab::getMultinv(msb(ylist[7])) << 24) - MultTab::multInv; + for (auto y7_8_24 = std::uint32_t{}, prod = (MultTab::getMultinv(msb(ylist[7])) << 24) - MultTab::multInv; y7_8_24 < 1 << 24; y7_8_24 += 1 << 8, prod += MultTab::multInv << 8) // get possible Y7[0,8) values - for (const std::uint8_t y7_0_8 : MultTab::getMsbProdFiber3(msb(ylist[6]) - msb(prod))) + for (const auto y7_0_8 : MultTab::getMsbProdFiber3(msb(ylist[6]) - msb(prod))) // filter Y7[0,8) using Y6[24,32) if (prod + MultTab::getMultinv(y7_0_8) - (ylist[6] & mask<24, 32>) <= maxdiff<24>) { @@ -70,14 +70,14 @@ void Attack::exploreYlists(int i) { if (i != 3) // the Y-list is not complete so generate Y{i-1} values { - const std::uint32_t fy = (ylist[i] - 1) * MultTab::multInv; - const std::uint32_t ffy = (fy - 1) * MultTab::multInv; + const auto fy = (ylist[i] - 1) * MultTab::multInv; + const auto ffy = (fy - 1) * MultTab::multInv; // get possible LSB(Xi) - for (const std::uint8_t xi_0_8 : MultTab::getMsbProdFiber2(msb(ffy - (ylist[i - 2] & mask<24, 32>)))) + for (const auto xi_0_8 : MultTab::getMsbProdFiber2(msb(ffy - (ylist[i - 2] & mask<24, 32>)))) { // compute corresponding Y{i-1} - const std::uint32_t yim1 = fy - xi_0_8; + const auto yim1 = fy - xi_0_8; // filter values with Y{i-2}[24,32) if (ffy - MultTab::getMultinv(xi_0_8) - (ylist[i - 2] & mask<24, 32>) <= maxdiff<24> && @@ -100,22 +100,22 @@ void Attack::exploreYlists(int i) void Attack::testXlist() { // compute X7 - for (int i = 5; i <= 7; i++) + for (auto i = 5; i <= 7; i++) xlist[i] = (Crc32Tab::crc32(xlist[i - 1], data.plaintext[index + i - 1]) & mask<8, 32>) // discard the LSB | lsb(xlist[i]); // set the LSB // compute X3 - std::uint32_t x = xlist[7]; - for (int i = 6; i >= 3; i--) + auto x = xlist[7]; + for (auto i = 6; i >= 3; i--) x = Crc32Tab::crc32inv(x, data.plaintext[index + i]); // check that X3 fits with Y1[26,32) - const std::uint32_t y1_26_32 = Crc32Tab::getYi_24_32(zlist[1], zlist[0]) & mask<26, 32>; + const auto y1_26_32 = Crc32Tab::getYi_24_32(zlist[1], zlist[0]) & mask<26, 32>; if (((ylist[3] - 1) * MultTab::multInv - lsb(x) - 1) * MultTab::multInv - y1_26_32 > maxdiff<26>) return; // decipher and filter by comparing with remaining contiguous plaintext forward - Keys keysForward(xlist[7], ylist[7], zlist[7]); + auto keysForward = Keys{xlist[7], ylist[7], zlist[7]}; keysForward.update(data.plaintext[index + 7]); for (auto p = data.plaintext.begin() + index + 8, c = data.ciphertext.begin() + data.offset + index + 8; p != data.plaintext.end(); ++p, ++c) @@ -125,10 +125,10 @@ void Attack::testXlist() keysForward.update(*p); } - std::size_t indexForward = data.offset + data.plaintext.size(); + auto indexForward = data.offset + data.plaintext.size(); // and also backward - Keys keysBackward(x, ylist[3], zlist[3]); + auto keysBackward = Keys{x, ylist[3], zlist[3]}; for (auto p = std::reverse_iterator{data.plaintext.begin() + index + 3}, c = std::reverse_iterator{data.ciphertext.begin() + data.offset + index + 3}; p != data.plaintext.rend(); ++p, ++c) @@ -138,12 +138,12 @@ void Attack::testXlist() return; } - std::size_t indexBackward = data.offset; + auto indexBackward = data.offset; // continue filtering with extra known plaintext for (const auto& [extraIndex, extraByte] : data.extraPlaintext) { - std::uint8_t p; + auto p = std::uint8_t{}; if (extraIndex < indexBackward) { keysBackward.updateBackward(data.ciphertext, indexBackward, extraIndex); @@ -180,12 +180,12 @@ void Attack::testXlist() auto attack(const Data& data, const std::vector& zi_2_32_vector, int& start, std::size_t index, int jobs, const bool exhaustive, Progress& progress) -> std::vector { - const std::uint32_t* candidates = zi_2_32_vector.data(); - const auto size = static_cast(zi_2_32_vector.size()); + const auto* candidates = zi_2_32_vector.data(); + const auto size = static_cast(zi_2_32_vector.size()); - std::vector solutions; - std::mutex solutionsMutex; - Attack worker(data, index, solutions, solutionsMutex, exhaustive, progress); + auto solutions = std::vector{}; + auto solutionsMutex = std::mutex{}; + auto worker = Attack{data, index, solutions, solutionsMutex, exhaustive, progress}; progress.done = start; progress.total = size; diff --git a/src/ConsoleProgress.cpp b/src/ConsoleProgress.cpp index ce15b26..6d774f0 100644 --- a/src/ConsoleProgress.cpp +++ b/src/ConsoleProgress.cpp @@ -13,7 +13,7 @@ ConsoleProgress::ConsoleProgress(std::ostream& os, const std::chrono::millisecon ConsoleProgress::~ConsoleProgress() { { - const std::scoped_lock lock{m_in_destructor_mutex}; + const auto lock = std::scoped_lock{m_in_destructor_mutex}; m_in_destructor = true; } @@ -23,18 +23,18 @@ ConsoleProgress::~ConsoleProgress() void ConsoleProgress::printerFunction() { - bool repeat = true; + auto repeat = true; // Give a small delay before the first time progress is printed so that // the running operation is likely to have initialized the total number of steps. { - std::unique_lock lock(m_in_destructor_mutex); - repeat = !m_in_destructor_cv.wait_for(lock, std::chrono::milliseconds(1), [this] { return m_in_destructor; }); + auto lock = std::unique_lock{m_in_destructor_mutex}; + repeat = !m_in_destructor_cv.wait_for(lock, std::chrono::milliseconds{1}, [this] { return m_in_destructor; }); } while (repeat) { - if (const int total = this->total.load()) + if (const auto total = this->total.load()) log( [done = done.load(), total](std::ostream& os) { @@ -48,11 +48,11 @@ void ConsoleProgress::printerFunction() os.flags(flagsBefore); }); - std::unique_lock lock(m_in_destructor_mutex); - repeat = !m_in_destructor_cv.wait_for(lock, m_interval, [this] { return m_in_destructor; }); + auto lock = std::unique_lock{m_in_destructor_mutex}; + repeat = !m_in_destructor_cv.wait_for(lock, m_interval, [this] { return m_in_destructor; }); } - if (const int total = this->total.load()) + if (const auto total = this->total.load()) log( [done = done.load(), total](std::ostream& os) { diff --git a/src/Crc32Tab.cpp b/src/Crc32Tab.cpp index 7bec4f1..010188a 100644 --- a/src/Crc32Tab.cpp +++ b/src/Crc32Tab.cpp @@ -5,13 +5,13 @@ const Crc32Tab Crc32Tab::instance; Crc32Tab::Crc32Tab() { // CRC32 polynomial representation - constexpr std::uint32_t crcPolynom = 0xedb88320; + constexpr auto crcPolynom = 0xedb88320; - for (int b = 0; b < 256; b++) + for (auto b = 0; b < 256; b++) { - std::uint32_t crc = b; + auto crc = static_cast(b); // compute CRC32 from the original definition - for (int i = 0; i < 8; i++) + for (auto i = 0; i < 8; i++) if (crc & 1) crc = crc >> 1 ^ crcPolynom; else diff --git a/src/Data.cpp b/src/Data.cpp index acfd4ca..2d8ff62 100644 --- a/src/Data.cpp +++ b/src/Data.cpp @@ -28,35 +28,35 @@ struct Range } // namespace Data::Error::Error(const std::string& description) -: BaseError("Data error", description) +: BaseError{"Data error", description} { } Data::Data(std::vector ciphertextArg, std::vector plaintextArg, int offsetArg, const std::map& extraPlaintextArg) -: ciphertext(std::move(ciphertextArg)) -, plaintext(std::move(plaintextArg)) +: ciphertext{std::move(ciphertextArg)} +, plaintext{std::move(plaintextArg)} { // validate lengths if (ciphertext.size() < Attack::attackSize) - throw Error("ciphertext is too small for an attack (minimum length is " + std::to_string(Attack::attackSize) + - ")"); + throw Error{"ciphertext is too small for an attack (minimum length is " + std::to_string(Attack::attackSize) + + ")"}; if (ciphertext.size() < plaintext.size()) - throw Error("ciphertext is smaller than plaintext"); + throw Error{"ciphertext is smaller than plaintext"}; // validate offsets - constexpr int minimumOffset = -static_cast(encryptionHeaderSize); + constexpr auto minimumOffset = -static_cast(encryptionHeaderSize); if (offsetArg < minimumOffset) - throw Error("plaintext offset " + std::to_string(offsetArg) + " is too small (minimum is " + - std::to_string(minimumOffset) + ")"); + throw Error{"plaintext offset " + std::to_string(offsetArg) + " is too small (minimum is " + + std::to_string(minimumOffset) + ")"}; if (ciphertext.size() < encryptionHeaderSize + offsetArg + plaintext.size()) - throw Error("plaintext offset " + std::to_string(offsetArg) + " is too large"); + throw Error{"plaintext offset " + std::to_string(offsetArg) + " is too large"}; if (!extraPlaintextArg.empty() && extraPlaintextArg.begin()->first < minimumOffset) - throw Error("extra plaintext offset " + std::to_string(extraPlaintextArg.begin()->first) + - " is too small (minimum is " + std::to_string(minimumOffset) + ")"); + throw Error{"extra plaintext offset " + std::to_string(extraPlaintextArg.begin()->first) + + " is too small (minimum is " + std::to_string(minimumOffset) + ")"}; if (!extraPlaintextArg.empty() && ciphertext.size() <= encryptionHeaderSize + extraPlaintextArg.rbegin()->first) - throw Error("extra plaintext offset " + std::to_string(extraPlaintextArg.rbegin()->first) + " is too large"); + throw Error{"extra plaintext offset " + std::to_string(extraPlaintextArg.rbegin()->first) + " is too large"}; // shift offsets to absolute values offset = encryptionHeaderSize + offsetArg; @@ -99,11 +99,11 @@ Data::Data(std::vector ciphertextArg, std::vector pl // find the longest contiguous sequence in extra plaintext and use is as contiguous plaintext if sensible { - Range range = {extraPlaintext.begin(), extraPlaintext.begin()}; // empty + auto range = Range{extraPlaintext.begin(), extraPlaintext.begin()}; // empty for (auto it = extraPlaintext.begin(); it != extraPlaintext.end();) { - Range current = {it, ++it}; + auto current = Range{it, ++it}; while (it != extraPlaintext.end() && it->first == (current.end - 1)->first + 1) current.end = ++it; @@ -112,11 +112,11 @@ Data::Data(std::vector ciphertextArg, std::vector pl if (plaintext.size() < range.size()) { - const std::size_t plaintextSize = plaintext.size(); - const std::size_t rangeOffset = range.begin->first; + const auto plaintextSize = plaintext.size(); + const auto rangeOffset = range.begin->first; // append last bytes from the range to contiguous plaintext - for (std::size_t i = plaintextSize; i < range.size(); i++) + for (auto i = plaintextSize; i < range.size(); i++) plaintext.push_back(range.begin[i].second); // remove those bytes from the range @@ -135,7 +135,7 @@ Data::Data(std::vector ciphertextArg, std::vector pl } // swap bytes between the former contiguous plaintext and the beginning of the range - for (std::size_t i = 0; i < plaintextSize; i++) + for (auto i = std::size_t{}; i < plaintextSize; i++) { range.begin[i].first = offset + i; std::swap(plaintext[i], range.begin[i].second); @@ -147,11 +147,11 @@ Data::Data(std::vector ciphertextArg, std::vector pl // check that there is enough known plaintext if (plaintext.size() < Attack::contiguousSize) - throw Error("not enough contiguous plaintext (" + std::to_string(plaintext.size()) + - " bytes available, minimum is " + std::to_string(Attack::contiguousSize) + ")"); + throw Error{"not enough contiguous plaintext (" + std::to_string(plaintext.size()) + + " bytes available, minimum is " + std::to_string(Attack::contiguousSize) + ")"}; if (plaintext.size() + extraPlaintext.size() < Attack::attackSize) - throw Error("not enough plaintext (" + std::to_string(plaintext.size() + extraPlaintext.size()) + - " bytes available, minimum is " + std::to_string(Attack::attackSize) + ")"); + throw Error{"not enough plaintext (" + std::to_string(plaintext.size() + extraPlaintext.size()) + + " bytes available, minimum is " + std::to_string(Attack::attackSize) + ")"}; // reorder remaining extra plaintext for filtering { diff --git a/src/Keys.cpp b/src/Keys.cpp index 64a8602..f2ad1b4 100644 --- a/src/Keys.cpp +++ b/src/Keys.cpp @@ -1,15 +1,15 @@ #include "Keys.hpp" Keys::Keys(std::uint32_t x, std::uint32_t y, std::uint32_t z) -: x(x) -, y(y) -, z(z) +: x{x} +, y{y} +, z{z} { } Keys::Keys(const std::string& password) { - for (const char p : password) + for (const auto p : password) update(p); } diff --git a/src/KeystreamTab.cpp b/src/KeystreamTab.cpp index c3a7dc1..25c84a3 100644 --- a/src/KeystreamTab.cpp +++ b/src/KeystreamTab.cpp @@ -4,9 +4,10 @@ const KeystreamTab KeystreamTab::instance; KeystreamTab::KeystreamTab() { - for (std::uint32_t z_2_16 = 0; z_2_16 < 1 << 16; z_2_16 += 4) + for (auto z_2_16 = std::uint32_t{}; z_2_16 < 1 << 16; z_2_16 += 4) { - const std::uint8_t k = lsb((z_2_16 | 2) * (z_2_16 | 3) >> 8); + const auto k = lsb((z_2_16 | 2) * (z_2_16 | 3) >> 8); + keystreamtab[z_2_16 >> 2] = k; keystreaminvfiltertab[k][z_2_16 >> 10].push_back(z_2_16); keystreaminvexists[k].set(z_2_16 >> 10); diff --git a/src/MultTab.cpp b/src/MultTab.cpp index f18a6d2..1f5ee34 100644 --- a/src/MultTab.cpp +++ b/src/MultTab.cpp @@ -4,9 +4,9 @@ const MultTab MultTab::instance; MultTab::MultTab() { - std::uint32_t prod = 0; // x * mult - std::uint32_t prodinv = 0; // x * mult^-1 - for (int x = 0; x < 256; x++, prod += mult, prodinv += multInv) + auto prod = std::uint32_t{}; // x * mult + auto prodinv = std::uint32_t{}; // x * mult^-1 + for (auto x = 0; x < 256; x++, prod += mult, prodinv += multInv) { multtab[x] = prod; multinvtab[x] = prodinv; diff --git a/src/VirtualTerminalSupport.cpp b/src/VirtualTerminalSupport.cpp index 49400ac..74c709a 100644 --- a/src/VirtualTerminalSupport.cpp +++ b/src/VirtualTerminalSupport.cpp @@ -12,7 +12,7 @@ class VirtualTerminalSupport::Impl : hStdOut{GetStdHandle(STD_OUTPUT_HANDLE)} , originalMode{[this] { - DWORD mode; + auto mode = DWORD{}; return GetConsoleMode(hStdOut, &mode) ? std::optional{mode} : std::nullopt; }()} { diff --git a/src/Zip.cpp b/src/Zip.cpp index 7772589..37f2d9f 100644 --- a/src/Zip.cpp +++ b/src/Zip.cpp @@ -16,8 +16,8 @@ auto read(std::istream& is, T& x) -> std::istream& static_assert(N <= sizeof(T), "read requires output type to have at least N bytes"); // We make no assumption about platform endianness. - x = T(); - for (std::size_t index = 0; index < N; index++) + x = T{}; + for (auto index = std::size_t{}; index < N; index++) x |= static_cast(is.get()) << (8 * index); return is; @@ -35,7 +35,7 @@ auto write(std::ostream& os, const T& x) -> std::ostream& static_assert(N <= sizeof(T), "write requires input type to have at least N bytes"); // We make no assumption about platform endianness. - for (std::size_t index = 0; index < N; index++) + for (auto index = std::size_t{}; index < N; index++) os.put(lsb(x >> (8 * index))); return os; @@ -52,18 +52,18 @@ enum class Signature : std::uint32_t auto checkSignature(std::istream& is, const Signature& signature) -> bool { - std::uint32_t sig; + auto sig = std::uint32_t{}; return read(is, sig) && sig == static_cast(signature); } auto findCentralDirectoryOffset(std::istream& is) -> std::uint64_t { - std::uint64_t centralDirectoryOffset; + auto centralDirectoryOffset = std::uint64_t{}; // find end of central directory signature { - std::uint32_t signature; - std::uint16_t commentLength = 0; + auto signature = std::uint32_t{}; + auto commentLength = std::uint16_t{}; do { is.seekg(-22 - commentLength, std::ios::end); @@ -71,40 +71,40 @@ auto findCentralDirectoryOffset(std::istream& is) -> std::uint64_t commentLength++ < mask<0, 16>); if (!is || signature != static_cast(Signature::Eocd)) - throw Zip::Error("could not find end of central directory signature"); + throw Zip::Error{"could not find end of central directory signature"}; } // read end of central directory record { - std::uint16_t disk; + auto disk = std::uint16_t{}; read(is, disk); is.seekg(10, std::ios::cur); read(is, centralDirectoryOffset); if (!is) - throw Zip::Error("could not read end of central directory record"); + throw Zip::Error{"could not read end of central directory record"}; if (disk != 0) - throw Zip::Error("split zip archives are not supported"); + throw Zip::Error{"split zip archives are not supported"}; } // look for Zip64 end of central directory locator is.seekg(-40, std::ios::cur); if (checkSignature(is, Signature::Zip64EocdLocator)) { - std::uint64_t zip64EndOfCentralDirectoryOffset; + auto zip64EndOfCentralDirectoryOffset = std::uint64_t{}; is.seekg(4, std::ios::cur); read(is, zip64EndOfCentralDirectoryOffset); if (!is) - throw Zip::Error("could not read Zip64 end of central directory locator record"); + throw Zip::Error{"could not read Zip64 end of central directory locator record"}; // read Zip64 end of central directory record is.seekg(zip64EndOfCentralDirectoryOffset, std::ios::beg); if (checkSignature(is, Signature::Zip64Eocd)) { - std::uint16_t versionNeededToExtract; + auto versionNeededToExtract = std::uint16_t{}; is.seekg(10, std::ios::cur); read(is, versionNeededToExtract); @@ -112,12 +112,12 @@ auto findCentralDirectoryOffset(std::istream& is) -> std::uint64_t read(is, centralDirectoryOffset); if (!is) - throw Zip::Error("could not read Zip64 end of central directory record"); + throw Zip::Error{"could not read Zip64 end of central directory record"}; if (versionNeededToExtract >= 62) // Version 6.2 introduces central directory encryption. - throw Zip::Error("central directory encryption is not supported"); + throw Zip::Error{"central directory encryption is not supported"}; } else - throw Zip::Error("could not find Zip64 end of central directory record"); + throw Zip::Error{"could not find Zip64 end of central directory record"}; } return centralDirectoryOffset; @@ -126,7 +126,7 @@ auto findCentralDirectoryOffset(std::istream& is) -> std::uint64_t } // namespace Zip::Error::Error(const std::string& description) -: BaseError("Zip error", description) +: BaseError{"Zip error", description} { } @@ -142,14 +142,14 @@ auto Zip::Iterator::operator++() -> Zip::Iterator& if (!checkSignature(*m_is, Signature::CentralDirectoryHeader)) return *this = Iterator{}; - std::uint16_t flags; - std::uint16_t method; - std::uint16_t lastModTime; - std::uint16_t lastModDate; + auto flags = std::uint16_t{}; + auto method = std::uint16_t{}; + auto lastModTime = std::uint16_t{}; + auto lastModDate = std::uint16_t{}; - std::uint16_t filenameLength; - std::uint16_t extraFieldLength; - std::uint16_t fileCommentLength; + auto filenameLength = std::uint16_t{}; + auto extraFieldLength = std::uint16_t{}; + auto fileCommentLength = std::uint16_t{}; m_is->seekg(4, std::ios::cur); read(*m_is, flags); @@ -174,11 +174,11 @@ auto Zip::Iterator::operator++() -> Zip::Iterator& m_entry->checkByte = (flags >> 3) & 1 ? static_cast(lastModTime >> 8) : msb(m_entry->crc32); - for (int remaining = extraFieldLength; remaining > 0;) + for (auto remaining = extraFieldLength; remaining > 0;) { // read extra field header - std::uint16_t id; - std::uint16_t size; + auto id = std::uint16_t{}; + auto size = std::uint16_t{}; read(*m_is, id); read(*m_is, size); remaining -= 4 + size; @@ -210,7 +210,7 @@ auto Zip::Iterator::operator++() -> Zip::Iterator& std::accumulate(m_entry->name.begin(), m_entry->name.end(), mask<0, 32>, Crc32Tab::crc32) ^ mask<0, 32>; - std::uint32_t expectedNameCrc32; + auto expectedNameCrc32 = std::uint32_t{}; m_is->seekg(1, std::ios::cur); read(*m_is, expectedNameCrc32); size -= 5; @@ -226,7 +226,7 @@ auto Zip::Iterator::operator++() -> Zip::Iterator& case 0x9901: // AE-x encryption structure if (7 <= size) { - std::uint16_t actualMethod; + auto actualMethod = std::uint16_t{}; m_is->seekg(5, std::ios::cur); read(*m_is, actualMethod); size -= 7; @@ -246,7 +246,7 @@ auto Zip::Iterator::operator++() -> Zip::Iterator& m_is->seekg(fileCommentLength, std::ios::cur); if (!*m_is) - throw Error("could not read central directory header"); + throw Error{"could not read central directory header"}; return *this; } @@ -277,19 +277,19 @@ auto Zip::operator[](const std::string& name) const -> Zip::Entry const auto it = std::find_if(begin(), end(), [&name](const Entry& entry) { return entry.name == name; }); if (it == end()) - throw Error("found no entry named \"" + name + "\""); + throw Error{"found no entry named \"" + name + "\""}; else return *it; } auto Zip::operator[](std::size_t index) const -> Zip::Entry { - std::size_t nextIndex = 0; - const auto it = std::find_if(begin(), end(), [&nextIndex, index](const Entry&) { return nextIndex++ == index; }); + auto nextIndex = std::size_t{}; + const auto it = std::find_if(begin(), end(), [&nextIndex, index](const Entry&) { return nextIndex++ == index; }); if (it == end()) - throw Error("found no entry at index " + std::to_string(index) + " (maximum index for this archive is " + - std::to_string(nextIndex - 1) + ")"); + throw Error{"found no entry at index " + std::to_string(index) + " (maximum index for this archive is " + + std::to_string(nextIndex - 1) + ")"}; else return *it; } @@ -299,11 +299,11 @@ void Zip::checkEncryption(const Entry& entry, Encryption expected) if (entry.encryption != expected) { if (entry.encryption == Encryption::None) - throw Error("entry \"" + entry.name + "\" is not encrypted"); + throw Error{"entry \"" + entry.name + "\" is not encrypted"}; else if (expected == Encryption::None) - throw Error("entry \"" + entry.name + "\" is encrypted"); + throw Error{"entry \"" + entry.name + "\" is encrypted"}; else - throw Error("entry \"" + entry.name + "\" is encrypted with an unsupported algorithm"); + throw Error{"entry \"" + entry.name + "\" is encrypted with an unsupported algorithm"}; } } @@ -311,11 +311,11 @@ auto Zip::seek(const Entry& entry) const -> std::istream& { m_is.seekg(entry.offset, std::ios::beg); if (!checkSignature(m_is, Signature::LocalFileHeader)) - throw Error("could not find local file header"); + throw Error{"could not find local file header"}; // skip local file header - std::uint16_t nameSize; - std::uint16_t extraSize; + auto nameSize = std::uint16_t{}; + auto extraSize = std::uint16_t{}; m_is.seekg(22, std::ios::cur); read(m_is, nameSize); read(m_is, extraSize); @@ -333,14 +333,14 @@ void Zip::changeKeys(std::ostream& os, const Keys& oldKeys, const Keys& newKeys, { // Store encrypted entries local file header offset and packed size. // Use std::map to sort them by local file header offset. - std::map packedSizeByLocalOffset; + auto packedSizeByLocalOffset = std::map{}; for (const auto& entry : *this) if (entry.encryption == Encryption::Traditional) packedSizeByLocalOffset.insert({entry.offset, entry.packedSize}); // Rewind input stream and iterate on encrypted entries to change the keys, copy the rest. m_is.seekg(0, std::ios::beg); - std::uint64_t currentOffset = 0; + auto currentOffset = std::uint64_t{}; progress.done = 0; progress.total = packedSizeByLocalOffset.size(); @@ -349,21 +349,21 @@ void Zip::changeKeys(std::ostream& os, const Keys& oldKeys, const Keys& newKeys, { if (currentOffset < localHeaderOffset) { - std::copy_n(std::istreambuf_iterator(m_is), localHeaderOffset - currentOffset, - std::ostreambuf_iterator(os)); + std::copy_n(std::istreambuf_iterator{m_is}, localHeaderOffset - currentOffset, + std::ostreambuf_iterator{os}); m_is.get(); } if (!checkSignature(m_is, Signature::LocalFileHeader)) - throw Error("could not find local file header"); + throw Error{"could not find local file header"}; write(os, static_cast(Signature::LocalFileHeader)); - std::copy_n(std::istreambuf_iterator(m_is), 22, std::ostreambuf_iterator(os)); + std::copy_n(std::istreambuf_iterator{m_is}, 22, std::ostreambuf_iterator{os}); m_is.get(); - std::uint16_t filenameLength; - std::uint16_t extraSize; + auto filenameLength = std::uint16_t{}; + auto extraSize = std::uint16_t{}; read(m_is, filenameLength); read(m_is, extraSize); write(os, filenameLength); @@ -371,19 +371,18 @@ void Zip::changeKeys(std::ostream& os, const Keys& oldKeys, const Keys& newKeys, if (0 < filenameLength + extraSize) { - std::copy_n(std::istreambuf_iterator(m_is), filenameLength + extraSize, - std::ostreambuf_iterator(os)); + std::copy_n(std::istreambuf_iterator{m_is}, filenameLength + extraSize, std::ostreambuf_iterator{os}); m_is.get(); } - Keys decrypt = oldKeys; - Keys encrypt = newKeys; - std::istreambuf_iterator in(m_is); - std::generate_n(std::ostreambuf_iterator(os), packedSize, + auto decrypt = oldKeys; + auto encrypt = newKeys; + auto in = std::istreambuf_iterator{m_is}; + std::generate_n(std::ostreambuf_iterator{os}, packedSize, [&in, &decrypt, &encrypt]() -> char { - const std::uint8_t p = *in++ ^ decrypt.getK(); - const std::uint8_t c = p ^ encrypt.getK(); + const auto p = *in++ ^ decrypt.getK(); + const auto c = p ^ encrypt.getK(); decrypt.update(p); encrypt.update(p); return c; @@ -394,6 +393,5 @@ void Zip::changeKeys(std::ostream& os, const Keys& oldKeys, const Keys& newKeys, progress.done++; } - std::copy(std::istreambuf_iterator(m_is), std::istreambuf_iterator(), - std::ostreambuf_iterator(os)); + std::copy(std::istreambuf_iterator{m_is}, {}, std::ostreambuf_iterator{os}); } diff --git a/src/Zreduction.cpp b/src/Zreduction.cpp index b4ed926..d45058b 100644 --- a/src/Zreduction.cpp +++ b/src/Zreduction.cpp @@ -8,12 +8,12 @@ #include Zreduction::Zreduction(const std::vector& keystream) -: keystream(keystream) +: keystream{keystream} { index = keystream.size() - 1; zi_vector.reserve(1 << 22); - for (std::uint32_t zi_10_32_shifted = 0; zi_10_32_shifted < 1 << 22; zi_10_32_shifted++) + for (auto zi_10_32_shifted = std::uint32_t{}; zi_10_32_shifted < 1 << 22; zi_10_32_shifted++) if (KeystreamTab::hasZi_2_16(keystream[index], zi_10_32_shifted << 10)) zi_vector.push_back(zi_10_32_shifted << 10); } @@ -21,36 +21,38 @@ Zreduction::Zreduction(const std::vector& keystream) void Zreduction::reduce(Progress& progress) { // variables to keep track of the smallest Zi[2,32) vector - constexpr std::size_t trackSizeThreshold = 1 << 16; - bool tracking = false; - std::vector bestCopy; - std::size_t bestIndex = index; - std::size_t bestSize = trackSizeThreshold; + constexpr auto trackSizeThreshold = std::size_t{1 << 16}; + + auto tracking = false; + auto bestCopy = std::vector{}; + auto bestIndex = index; + auto bestSize = trackSizeThreshold; // variables to wait for a limited number of steps when a small enough vector is found - constexpr std::size_t waitSizeThreshold = 1 << 8; - bool waiting = false; - std::size_t wait = 0; + constexpr auto waitSizeThreshold = std::size_t{1 << 8}; + + auto waiting = false; + auto wait = std::size_t{}; - std::vector zim1_10_32_vector; + auto zim1_10_32_vector = std::vector{}; zim1_10_32_vector.reserve(1 << 22); - std::bitset<1 << 22> zim1_10_32_set; + auto zim1_10_32_set = std::bitset<1 << 22>{}; progress.done = 0; progress.total = keystream.size() - Attack::contiguousSize; - for (std::size_t i = index; i >= Attack::contiguousSize; i--) + for (auto i = index; i >= Attack::contiguousSize; i--) { zim1_10_32_vector.clear(); zim1_10_32_set.reset(); - std::size_t number_of_zim1_2_32 = 0; + auto number_of_zim1_2_32 = std::size_t{}; // generate the Z{i-1}[10,32) values - for (const std::uint32_t zi_10_32 : zi_vector) - for (const std::uint32_t zi_2_16 : KeystreamTab::getZi_2_16_vector(keystream[i], zi_10_32)) + for (const auto zi_10_32 : zi_vector) + for (const auto zi_2_16 : KeystreamTab::getZi_2_16_vector(keystream[i], zi_10_32)) { // get Z{i-1}[10,32) from CRC32^-1 - const std::uint32_t zim1_10_32 = Crc32Tab::getZim1_10_32(zi_10_32 | zi_2_16); + const auto zim1_10_32 = Crc32Tab::getZim1_10_32(zi_10_32 | zi_2_16); // collect without duplicates only those that are compatible with keystream{i-1} if (!zim1_10_32_set[zim1_10_32 >> 10] && KeystreamTab::hasZi_2_16(keystream[i - 1], zim1_10_32)) { @@ -106,12 +108,11 @@ void Zreduction::reduce(Progress& progress) void Zreduction::generate() { - const std::size_t number_of_zi_10_32 = zi_vector.size(); - for (std::size_t i = 0; i < number_of_zi_10_32; i++) + const auto number_of_zi_10_32 = zi_vector.size(); + for (auto i = std::size_t{}; i < number_of_zi_10_32; i++) { - const std::vector& zi_2_16_vector = - KeystreamTab::getZi_2_16_vector(keystream[index], zi_vector[i]); - for (std::size_t j = 1; j < zi_2_16_vector.size(); j++) + const auto& zi_2_16_vector = KeystreamTab::getZi_2_16_vector(keystream[index], zi_vector[i]); + for (auto j = std::size_t{1}; j < zi_2_16_vector.size(); j++) zi_vector.push_back(zi_vector[i] | zi_2_16_vector[j]); zi_vector[i] |= zi_2_16_vector[0]; } diff --git a/src/file.cpp b/src/file.cpp index 840dbf9..4b29f8c 100644 --- a/src/file.cpp +++ b/src/file.cpp @@ -1,23 +1,23 @@ #include "file.hpp" FileError::FileError(const std::string& description) -: BaseError("File error", description) +: BaseError{"File error", description} { } auto openInput(const std::string& filename) -> std::ifstream { - if (std::ifstream is = std::ifstream(filename, std::ios::binary)) + if (auto is = std::ifstream{filename, std::ios::binary}) return is; else - throw FileError("could not open input file " + filename); + throw FileError{"could not open input file " + filename}; } auto loadStream(std::istream& is, std::size_t size) -> std::vector { - std::vector content; - std::istreambuf_iterator it(is); - for (std::size_t i = 0; i < size && it != std::istreambuf_iterator(); i++, ++it) + auto content = std::vector{}; + auto it = std::istreambuf_iterator{is}; + for (auto i = std::size_t{}; i < size && it != std::istreambuf_iterator{}; i++, ++it) content.push_back(*it); return content; @@ -25,14 +25,14 @@ auto loadStream(std::istream& is, std::size_t size) -> std::vector auto loadFile(const std::string& filename, std::size_t size) -> std::vector { - std::ifstream is = openInput(filename); + auto is = openInput(filename); return loadStream(is, size); } auto openOutput(const std::string& filename) -> std::ofstream { - if (std::ofstream os = std::ofstream(filename, std::ios::binary)) + if (auto os = std::ofstream{filename, std::ios::binary}) return os; else - throw FileError("could not open output file " + filename); + throw FileError{"could not open output file " + filename}; } diff --git a/src/log.cpp b/src/log.cpp index 54037ff..bd5596e 100644 --- a/src/log.cpp +++ b/src/log.cpp @@ -7,7 +7,7 @@ auto put_time(std::ostream& os) -> std::ostream& { - const std::time_t t = std::time(nullptr); + const auto t = std::time(nullptr); return os << std::put_time(std::localtime(&t), "%T"); } diff --git a/src/main.cpp b/src/main.cpp index 474d564..cb9415c 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -106,12 +106,12 @@ auto main(int argc, const char* argv[]) -> int try { // enable virtual terminal support on Windows, no-op on other platforms - VirtualTerminalSupport vtSupport; + const auto vtSupport = VirtualTerminalSupport{}; // version information std::cout << "bkcrack " << bkcrackVersion << " - " << bkcrackVersionDate << std::endl; - const Arguments args(argc, argv); + const auto args = Arguments{argc, argv}; if (args.help) { std::cout << usage << std::endl; @@ -130,7 +130,7 @@ try return 0; } - std::vector keysvec; + auto keysvec = std::vector{}; if (args.keys) keysvec.push_back(*args.keys); else if (args.password) @@ -142,16 +142,16 @@ try else // find keys from known plaintext { - const Data data = args.loadData(); + const auto data = args.loadData(); // generate and reduce Zi[10,32) values - Zreduction zr(data.keystream); + auto zr = Zreduction{data.keystream}; if (data.keystream.size() > Attack::contiguousSize) { std::cout << "[" << put_time << "] Z reduction using " << (data.keystream.size() - Attack::contiguousSize) << " bytes of known plaintext" << std::endl; - ConsoleProgress progress(std::cout); + auto progress = ConsoleProgress{std::cout}; zr.reduce(progress); } @@ -165,9 +165,9 @@ try const auto [state, restart] = [&]() -> std::pair { - int start = args.attackStart; - ConsoleProgress progress(std::cout); - const SigintHandler sigintHandler{progress.state}; + auto start = args.attackStart; + auto progress = ConsoleProgress{std::cout}; + const auto sigintHandler = SigintHandler{progress.state}; keysvec = attack(data, zr.getCandidates(), start, zr.getIndex(), args.jobs, args.exhaustive, progress); return {progress.state, start}; }(); @@ -192,14 +192,14 @@ try else { std::cout << "Keys" << std::endl; - for (const Keys& keys : keysvec) + for (const auto& keys : keysvec) std::cout << keys << std::endl; } } // From there, keysvec is not empty. - const Keys keys = keysvec.front(); + const auto keys = keysvec.front(); if ((args.decipheredFile || args.changePassword || args.changeKeys || args.bruteforce) && keysvec.size() > 1) std::cout << "Continuing with keys " << keys << "\n" << "Use the command line option -k to provide other keys." << std::endl; @@ -213,8 +213,8 @@ try std::cout << std::endl; { - std::ifstream cipherstream = openInput(args.cipherArchive ? *args.cipherArchive : *args.cipherFile); - std::size_t ciphersize = std::numeric_limits::max(); + auto cipherstream = openInput(args.cipherArchive ? *args.cipherArchive : *args.cipherFile); + auto ciphersize = std::numeric_limits::max(); if (args.cipherArchive) { @@ -226,7 +226,7 @@ try ciphersize = entry.packedSize; } - std::ofstream decipheredstream = openOutput(*args.decipheredFile); + auto decipheredstream = openOutput(*args.decipheredFile); decipher(cipherstream, ciphersize, args.keepHeader ? 0 : static_cast(Data::encryptionHeaderSize), decipheredstream, @@ -245,10 +245,10 @@ try << newPassword << "\"" << std::endl; { - const auto archive = Zip{*args.cipherArchive}; - std::ofstream unlocked = openOutput(unlockedArchive); + const auto archive = Zip{*args.cipherArchive}; + auto unlocked = openOutput(unlockedArchive); - ConsoleProgress progress(std::cout); + auto progress = ConsoleProgress{std::cout}; archive.changeKeys(unlocked, keys, Keys{newPassword}, progress); } @@ -263,10 +263,10 @@ try << std::endl; { - const auto archive = Zip{*args.cipherArchive}; - std::ofstream unlocked = openOutput(unlockedArchive); + const auto archive = Zip{*args.cipherArchive}; + auto unlocked = openOutput(unlockedArchive); - ConsoleProgress progress(std::cout); + auto progress = ConsoleProgress{std::cout}; archive.changeKeys(unlocked, keys, newKeys, progress); } @@ -278,16 +278,15 @@ try { std::cout << "[" << put_time << "] Recovering password" << std::endl; - std::vector passwords; + auto passwords = std::vector{}; const auto [state, restart] = [&]() -> std::pair { const auto& charset = *args.bruteforce; const auto& [minLength, maxLength] = args.length.value_or(Arguments::LengthInterval{}); - std::string start = args.recoveryStart; - - ConsoleProgress progress(std::cout); - const SigintHandler sigintHandler(progress.state); + auto start = args.recoveryStart; + auto progress = ConsoleProgress{std::cout}; + const auto sigintHandler = SigintHandler{progress.state}; passwords = recoverPassword(keysvec.front(), charset, minLength, maxLength, start, args.jobs, args.exhaustive, progress); return {progress.state, start}; @@ -306,7 +305,7 @@ try const auto fillBefore = std::cout.fill('0'); std::cout << "You may resume the password recovery with the option: --continue-recovery "; - for (std::uint8_t c : restart) + for (const auto c : restart) std::cout << std::setw(2) << static_cast(c); std::cout << std::endl; @@ -331,7 +330,7 @@ try for (const auto& password : passwords) { std::cout << "as bytes: "; - for (std::uint8_t c : password) + for (const auto c : password) std::cout << std::setw(2) << static_cast(c) << ' '; std::cout << std::endl; std::cout << "as text: " << password << std::endl; @@ -403,7 +402,7 @@ auto getCompressionDescription(Zip::Compression compression) -> std::string void listEntries(const std::string& archiveFilename) { - auto archive = Zip{archiveFilename}; + const auto archive = Zip{archiveFilename}; std::cout << "Archive: " << archiveFilename << "\n" << "Index Encryption Compression CRC32 Uncompressed Packed size Name\n" @@ -413,7 +412,7 @@ void listEntries(const std::string& archiveFilename) std::cout.setf(std::ios::right | std::ios::dec, std::ios::adjustfield | std::ios::basefield); const auto fillBefore = std::cout.fill(' '); - std::size_t index = 0; + auto index = std::size_t{}; for (const auto& entry : archive) { // clang-format off @@ -440,16 +439,16 @@ void listEntries(const std::string& archiveFilename) void decipher(std::istream& is, std::size_t size, std::size_t discard, std::ostream& os, Keys keys) { - std::istreambuf_iterator cipher(is); - std::size_t i; + auto cipher = std::istreambuf_iterator{is}; + auto i = std::size_t{}; - for (i = 0; i < discard && i < size && cipher != std::istreambuf_iterator(); i++, ++cipher) + for (; i < discard && i < size && cipher != std::istreambuf_iterator{}; i++, ++cipher) keys.update(*cipher ^ keys.getK()); - for (std::ostreambuf_iterator plain(os); i < size && cipher != std::istreambuf_iterator(); + for (auto plain = std::ostreambuf_iterator{os}; i < size && cipher != std::istreambuf_iterator{}; i++, ++cipher, ++plain) { - const std::uint8_t p = *cipher ^ keys.getK(); + const auto p = *cipher ^ keys.getK(); keys.update(p); *plain = p; } diff --git a/src/password.cpp b/src/password.cpp index 96380d1..a9dd643 100644 --- a/src/password.cpp +++ b/src/password.cpp @@ -10,11 +10,11 @@ Recovery::Recovery(const Keys& keys, const std::vector& charset, std::vector& solutions, std::mutex& solutionsMutex, bool exhaustive, Progress& progress) -: charset(charset) -, solutions(solutions) -, solutionsMutex(solutionsMutex) -, exhaustive(exhaustive) -, progress(progress) +: charset{charset} +, solutions{solutions} +, solutionsMutex{solutionsMutex} +, exhaustive{exhaustive} +, progress{progress} { // initialize target X, Y and Z values x[6] = keys.getX(); @@ -25,17 +25,17 @@ Recovery::Recovery(const Keys& keys, const std::vector& charset, s y[5] = (y[6] - 1) * MultTab::multInv - lsb(x[6]); // derive more Z bytes - for (int i = 6; 1 < i; i--) + for (auto i = 6; 1 < i; i--) z[i - 1] = Crc32Tab::crc32inv(z[i], msb(y[i])); // precompute possible Z0[16,32) and Z{-1}[24,32) - for (const std::uint8_t p5 : charset) + for (const auto p5 : charset) { x[5] = Crc32Tab::crc32inv(x[6], p5); y[4] = (y[5] - 1) * MultTab::multInv - lsb(x[5]); z[3] = Crc32Tab::crc32inv(z[4], msb(y[4])); - for (const std::uint8_t p4 : charset) + for (const auto p4 : charset) { x[4] = Crc32Tab::crc32inv(x[5], p4); y[3] = (y[4] - 1) * MultTab::multInv - lsb(x[4]); @@ -61,7 +61,7 @@ void Recovery::recoverShortPassword(const Keys& initial) z[0] = initial.getZ(); // complete Z values and derive Y[24,32) values - for (int i = 1; i <= 4; i++) + for (auto i = 1; i <= 4; i++) { y[i] = Crc32Tab::getYi_24_32(z[i], z[i - 1]); z[i] = Crc32Tab::crc32(z[i - 1], msb(y[i])); @@ -82,16 +82,16 @@ void Recovery::recoverLongPassword(const Keys& initial) prefix.push_back(charset[0]); // precompute as much as we can about the next cipher state without knowing the password byte - const std::uint32_t x0_partial = Crc32Tab::crc32(initial.getX(), 0); - const std::uint32_t y0_partial = initial.getY() * MultTab::mult + 1; - const std::uint32_t z0_partial = Crc32Tab::crc32(initial.getZ(), 0); + const auto x0_partial = Crc32Tab::crc32(initial.getX(), 0); + const auto y0_partial = initial.getY() * MultTab::mult + 1; + const auto z0_partial = Crc32Tab::crc32(initial.getZ(), 0); - for (const std::uint8_t pi : charset) + for (const auto pi : charset) { // finish to update the cipher state - const std::uint32_t x0 = x0_partial ^ Crc32Tab::crc32(0, pi); - const std::uint32_t y0 = y0_partial + MultTab::getMult(lsb(x0)); - const std::uint32_t z0 = z0_partial ^ Crc32Tab::crc32(0, msb(y0)); + const auto x0 = x0_partial ^ Crc32Tab::crc32(0, pi); + const auto y0 = y0_partial + MultTab::getMult(lsb(x0)); + const auto z0 = z0_partial ^ Crc32Tab::crc32(0, msb(y0)); // recoverShortPassword is inlined below for performance @@ -126,7 +126,7 @@ void Recovery::recoverLongPassword(const Keys& initial) { prefix.push_back(charset[0]); - for (const std::uint8_t pi : charset) + for (const auto pi : charset) { Keys init = initial; init.update(pi); @@ -144,14 +144,14 @@ void Recovery::recursion(int i) { if (i != 1) // the Y-list is not complete so generate Y{i-1} values { - const std::uint32_t fy = (y[i] - 1) * MultTab::multInv; - const std::uint32_t ffy = (fy - 1) * MultTab::multInv; + const auto fy = (y[i] - 1) * MultTab::multInv; + const auto ffy = (fy - 1) * MultTab::multInv; // get possible LSB(Xi) - for (const std::uint8_t xi_0_8 : MultTab::getMsbProdFiber2(msb(ffy - (y[i - 2] & mask<24, 32>)))) + for (const auto xi_0_8 : MultTab::getMsbProdFiber2(msb(ffy - (y[i - 2] & mask<24, 32>)))) { // compute corresponding Y{i-1} - const std::uint32_t yim1 = fy - xi_0_8; + const auto yim1 = fy - xi_0_8; // filter values with Y{i-2}[24,32) if (ffy - MultTab::getMultinv(xi_0_8) - (y[i - 2] & mask<24, 32>) <= maxdiff<24> && @@ -175,22 +175,24 @@ void Recovery::recursion(int i) return; // complete X values and derive password - for (int j = 5; 0 <= j; j--) + for (auto j = 5; 0 <= j; j--) { - const std::uint32_t xi_xor_pi = Crc32Tab::crc32inv(x[j + 1], 0); - p[j] = lsb(xi_xor_pi ^ x[j]); - x[j] = xi_xor_pi ^ p[j]; + const auto xi_xor_pi = Crc32Tab::crc32inv(x[j + 1], 0); + p[j] = lsb(xi_xor_pi ^ x[j]); + x[j] = xi_xor_pi ^ p[j]; } if (x[0] == candidateX0) // the password is successfully recovered { - std::string password = std::string(prefix.begin(), prefix.end()); + auto password = prefix; password.append(p.begin(), p.end()); password.erase(password.begin(), password.end() - length); - const bool isInCharset = + const auto isInCharset = std::all_of(password.begin(), password.end(), - [this](unsigned char c) { return std::binary_search(charset.begin(), charset.end(), c); }); + [this](char c) { + return std::binary_search(charset.begin(), charset.end(), static_cast(c)); + }); if (!isInCharset) { @@ -201,7 +203,7 @@ void Recovery::recursion(int i) const auto fillBefore = os.fill('0'); os << "Password: " << password << " (as bytes:"; - for (const std::uint8_t c : password) + for (const auto c : password) os << ' ' << std::setw(2) << static_cast(c); os << ')' << std::endl; @@ -233,9 +235,9 @@ namespace void recoverPasswordRecursive(Recovery& worker, int jobs, const Keys& initial, const std::string& start, std::string& restart, Progress& progress) { - const int charsetSize = worker.charset.size(); + const auto charsetSize = static_cast(worker.charset.size()); - int index_start = 0; + auto index_start = 0; if (worker.prefix.size() < start.size()) while (index_start < charsetSize && worker.charset[index_start] < static_cast(start[worker.prefix.size()])) @@ -256,9 +258,9 @@ void recoverPasswordRecursive(Recovery& worker, int jobs, const Keys& initial, c { for (auto i = nextCandidateIndex++; i < charsetSize; i = nextCandidateIndex++) { - const std::uint8_t pm4 = worker.charset[i]; + const auto pm4 = worker.charset[i]; - Keys init = initial; + auto init = initial; init.update(pm4); worker.prefix.back() = pm4; @@ -297,8 +299,8 @@ void recoverPasswordRecursive(Recovery& worker, int jobs, const Keys& initial, c worker.prefix.push_back(worker.charset[0]); worker.prefix.push_back(worker.charset[0]); - const bool reportProgress = worker.prefix.size() == 2; - const bool reportProgressCoarse = worker.prefix.size() == 3; + const auto reportProgress = worker.prefix.size() == 2; + const auto reportProgressCoarse = worker.prefix.size() == 3; if (reportProgress) progress.done += index_start; @@ -315,10 +317,10 @@ void recoverPasswordRecursive(Recovery& worker, int jobs, const Keys& initial, c { for (auto i = nextCandidateIndex++; i < charsetSize * charsetSize; i = nextCandidateIndex++) { - const std::uint8_t pm4 = worker.charset[i / charsetSize]; - const std::uint8_t pm3 = worker.charset[i % charsetSize]; + const auto pm4 = worker.charset[i / charsetSize]; + const auto pm3 = worker.charset[i % charsetSize]; - Keys init = initial; + auto init = initial; init.update(pm4); init.update(pm3); @@ -352,18 +354,18 @@ void recoverPasswordRecursive(Recovery& worker, int jobs, const Keys& initial, c { worker.prefix.push_back(worker.charset[0]); - const bool reportProgress = worker.prefix.size() == 2; + const auto reportProgress = worker.prefix.size() == 2; if (worker.prefix.size() == 1) progress.done += index_start * charsetSize; else if (reportProgress) progress.done += index_start; - for (int i = index_start; i < charsetSize; i++) + for (auto i = index_start; i < charsetSize; i++) { - const std::uint8_t pi = worker.charset[i]; + const auto pi = worker.charset[i]; - Keys init = initial; + auto init = initial; init.update(pi); worker.prefix.back() = pi; @@ -390,13 +392,13 @@ auto recoverPassword(const Keys& keys, const std::vector& charset, std::size_t maxLength, std::string& start, int jobs, bool exhaustive, Progress& progress) -> std::vector { - std::vector solutions; - std::mutex solutionsMutex; - Recovery worker(keys, charset, solutions, solutionsMutex, exhaustive, progress); + auto solutions = std::vector{}; + auto solutionsMutex = std::mutex{}; + auto worker = Recovery{keys, charset, solutions, solutionsMutex, exhaustive, progress}; - std::string restart; - const std::size_t startLength = std::max(minLength, start.empty() ? 0 : start.size() + 6); - for (std::size_t length = startLength; length <= maxLength; length++) + auto restart = std::string{}; + const auto startLength = std::max(minLength, start.empty() ? 0 : start.size() + 6); + for (auto length = startLength; length <= maxLength; length++) { if (progress.state != Progress::State::Normal) break; @@ -405,10 +407,10 @@ auto recoverPassword(const Keys& keys, const std::vector& charset, { progress.log([](std::ostream& os) { os << "length 0-6..." << std::endl; }); - Keys initial; + auto initial = Keys{}; // look for a password of length between 0 and 6 - for (int l = 6; l >= 0; l--) + for (auto l = 6; l >= 0; l--) { worker.length = l; worker.recoverShortPassword(initial); diff --git a/src/types.cpp b/src/types.cpp index d0476f5..6c30b4e 100644 --- a/src/types.cpp +++ b/src/types.cpp @@ -1,6 +1,6 @@ #include "types.hpp" BaseError::BaseError(const std::string& type, const std::string& description) -: std::runtime_error(type + ": " + description + ".") +: std::runtime_error{type + ": " + description + "."} { }