mirror of
https://github.com/TomHarte/CLK.git
synced 2026-04-19 19:16:34 +00:00
Implement recursive reverse.
This commit is contained in:
+24
-12
@@ -16,7 +16,23 @@
|
||||
|
||||
namespace CRC {
|
||||
|
||||
constexpr uint8_t reverse_byte(uint8_t byte) {
|
||||
template <typename IntT>
|
||||
constexpr IntT reverse(const IntT source) {
|
||||
static_assert(std::is_same_v<IntT, uint16_t> || std::is_same_v<IntT, uint32_t> || std::is_same_v<IntT, uint64_t>);
|
||||
using HalfIntT =
|
||||
std::conditional_t<std::is_same_v<IntT, uint16_t>, uint8_t,
|
||||
std::conditional_t<std::is_same_v<IntT, uint32_t>, uint16_t,
|
||||
uint32_t>>;
|
||||
constexpr auto HalfShift = sizeof(IntT) * 4;
|
||||
|
||||
return IntT(
|
||||
IntT(reverse(HalfIntT(source))) << HalfShift) |
|
||||
IntT(reverse(HalfIntT(source >> HalfShift))
|
||||
);
|
||||
}
|
||||
|
||||
template <>
|
||||
constexpr uint8_t reverse<uint8_t>(const uint8_t byte) {
|
||||
return
|
||||
((byte & 0x80) ? 0x01 : 0x00) |
|
||||
((byte & 0x40) ? 0x02 : 0x00) |
|
||||
@@ -64,26 +80,22 @@ public:
|
||||
return table;
|
||||
} ();
|
||||
|
||||
if constexpr (reflect_input) byte = reverse_byte(byte);
|
||||
if constexpr (reflect_input) byte = reverse(byte);
|
||||
value_ = IntType((value_ << 8) ^ xor_table[(value_ >> multibyte_shift) ^ byte]);
|
||||
}
|
||||
|
||||
/// @returns The current value of the CRC.
|
||||
inline IntType get_value() const {
|
||||
IntType result = value_ ^ output_xor;
|
||||
const IntType result = value_ ^ output_xor;
|
||||
if constexpr (reflect_output) {
|
||||
IntType reflected_output = 0;
|
||||
for(std::size_t c = 0; c < sizeof(IntType); ++c) {
|
||||
reflected_output = IntType(reflected_output << 8) | IntType(reverse_byte(result & 0xff));
|
||||
result >>= 8;
|
||||
}
|
||||
return reflected_output;
|
||||
return reverse(result);
|
||||
} else {
|
||||
return result;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
/// Sets the current value of the CRC.
|
||||
inline void set_value(IntType value) { value_ = value; }
|
||||
inline void set_value(const IntType value) { value_ = value; }
|
||||
|
||||
/*!
|
||||
A compound for:
|
||||
@@ -103,7 +115,7 @@ public:
|
||||
[add all data from @c begin to @c end]
|
||||
get_value()
|
||||
*/
|
||||
template <typename Iterator> IntType compute_crc(Iterator begin, Iterator end) {
|
||||
template <typename Iterator> IntType compute_crc(Iterator begin, const Iterator end) {
|
||||
reset();
|
||||
while(begin != end) {
|
||||
add(*begin);
|
||||
|
||||
@@ -212,7 +212,7 @@ std::optional<uint8_t> Parser::get_byte(Storage::Tape::TapeSerialiser &serialise
|
||||
}
|
||||
|
||||
if(should_flip_bytes()) {
|
||||
result = CRC::reverse_byte(result);
|
||||
result = CRC::reverse(result);
|
||||
}
|
||||
|
||||
checksum_ ^= result;
|
||||
|
||||
Reference in New Issue
Block a user