Skip to content

Instantly share code, notes, and snippets.

@Twilight-Dream-Of-Magic
Created April 14, 2023 03:43
Show Gist options
  • Save Twilight-Dream-Of-Magic/897172584c4c0ebefb897971637811ea to your computer and use it in GitHub Desktop.
Save Twilight-Dream-Of-Magic/897172584c4c0ebefb897971637811ea to your computer and use it in GitHub Desktop.
Stream Cipher Weaker Test
#!/use/bin/bash
gcc -std=c++20 ./main.cpp
#include <iostream>
#include <cstdint>
#include <bitset>
#include <array>
#include <algorithm>
#include <ranges>
inline void Salsa20_WeakerTest()
{
std::array<std::uint32_t, 16> TestState
{
0x00000001, 0x00000000, 0x00000000, 0x00000000,
0x00000000, 0x00000000, 0x00000000, 0x00000000,
0x00000000, 0x00000000, 0x00000000, 0x00000000,
0x00000000, 0x00000000, 0x00000000, 0x00000000
};
std::array<std::uint32_t, 16> WorkingState
{
0x00000000, 0x00000000, 0x00000000, 0x00000000,
0x00000000, 0x00000000, 0x00000000, 0x00000000,
0x00000000, 0x00000000, 0x00000000, 0x00000000,
0x00000000, 0x00000000, 0x00000000, 0x00000000
};
auto QuarterRoundTest = [](std::uint32_t& a, std::uint32_t& b, std::uint32_t& c, std::uint32_t& d) -> void
{
b = (a + d);
c = (b + a);
d = (c + b);
a = (d + c);
};
auto PrintTestData = [&WorkingState]() ->void
{
// Print the state matrix in binary format after each 1/4 round function
std::cout << "{\n";
for ( size_t i = 0; i < 16; ++i )
{
std::cout << std::bitset<32>(WorkingState[ i ]).to_string();
if ( i % 4 == 3 )
{
std::cout << ",\n";
}
else
{
std::cout << ", ";
}
}
std::cout << "}\n";
};
//StateCopy = State
std::ranges::copy(TestState.begin(), TestState.end(), WorkingState.begin());
std::cout << "Weaker test with use Salsa20:" << std::endl;
//Round function
//State' = Function(StateCopy)
for ( std::uint32_t Round = 0; Round < 20; Round += 2 )
{
// Odd round
PrintTestData();
QuarterRoundTest( WorkingState[ 0 ], WorkingState[ 4 ], WorkingState[ 8 ], WorkingState[ 12 ] ); // column 1
PrintTestData();
QuarterRoundTest( WorkingState[ 5 ], WorkingState[ 9 ], WorkingState[ 13 ], WorkingState[ 1 ] ); // column 2
PrintTestData();
QuarterRoundTest( WorkingState[ 10 ], WorkingState[ 14 ], WorkingState[ 2 ], WorkingState[ 6 ] ); // column 3
PrintTestData();
QuarterRoundTest( WorkingState[ 15 ], WorkingState[ 3 ], WorkingState[ 7 ], WorkingState[ 11 ] ); // column 4
// Even round
PrintTestData();
QuarterRoundTest( WorkingState[ 0 ], WorkingState[ 1 ], WorkingState[ 2 ], WorkingState[ 3 ] ); // row 1
PrintTestData();
QuarterRoundTest( WorkingState[ 5 ], WorkingState[ 6 ], WorkingState[ 7 ], WorkingState[ 4 ] ); // row 2
PrintTestData();
QuarterRoundTest( WorkingState[ 10 ], WorkingState[ 11 ], WorkingState[ 8 ], WorkingState[ 9 ] ); // row 3
PrintTestData();
QuarterRoundTest( WorkingState[ 15 ], WorkingState[ 12 ], WorkingState[ 13 ], WorkingState[ 14 ] ); // row 4
PrintTestData();
}
//Mixing the data of the working state with the data of the state is equivalent to a secure hash function
//Hashed = Hash(State', State)
//Hashed = State' + State
//Hashed = Function(StateCopy) + State
for ( std::uint32_t Index = 0; Index < 16; ++Index )
WorkingState[ Index ] += TestState[ Index ];
}
inline void Chacha20_WeakerTest()
{
std::array<std::uint32_t, 16> TestState
{
0x00000001, 0x00000000, 0x00000000, 0x00000000,
0x00000000, 0x00000000, 0x00000000, 0x00000000,
0x00000000, 0x00000000, 0x00000000, 0x00000000,
0x00000000, 0x00000000, 0x00000000, 0x00000000
};
std::array<std::uint32_t, 16> WorkingState
{
0x00000000, 0x00000000, 0x00000000, 0x00000000,
0x00000000, 0x00000000, 0x00000000, 0x00000000,
0x00000000, 0x00000000, 0x00000000, 0x00000000,
0x00000000, 0x00000000, 0x00000000, 0x00000000
};
auto QuarterRoundTest = [](std::uint32_t& a, std::uint32_t& b, std::uint32_t& c, std::uint32_t& d) -> void
{
a += b; d = a;
c += d; b = c;
a += b; d = a;
c += d; b = c;
};
auto PrintTestData = [&WorkingState]() ->void
{
// Print the state matrix in binary format after each 1/4 round function
std::cout << "{\n";
for ( size_t i = 0; i < 16; ++i )
{
std::cout << std::bitset<32>(WorkingState[ i ]).to_string();
if ( i % 4 == 3 )
{
std::cout << ",\n";
}
else
{
std::cout << ", ";
}
}
std::cout << "}\n";
};
//StateCopy = State
std::ranges::copy(TestState.begin(), TestState.end(), WorkingState.begin());
std::cout << "Weaker test with use Chacha20:" << std::endl;
//Round function
//State' = Function(StateCopy)
for ( std::uint32_t Round = 0; Round < 20; Round += 2 )
{
// Odd round
PrintTestData();
QuarterRoundTest( WorkingState[ 0 ], WorkingState[ 4 ], WorkingState[ 8 ], WorkingState[ 12 ] ); // column 0
PrintTestData();
QuarterRoundTest( WorkingState[ 1 ], WorkingState[ 5 ], WorkingState[ 9 ], WorkingState[ 13 ] ); // column 1
PrintTestData();
QuarterRoundTest( WorkingState[ 2 ], WorkingState[ 6 ], WorkingState[ 10 ], WorkingState[ 14 ] ); // column 2
PrintTestData();
QuarterRoundTest( WorkingState[ 3 ], WorkingState[ 7 ], WorkingState[ 11 ], WorkingState[ 15 ] ); // column 3
PrintTestData();
// Even round
PrintTestData();
QuarterRoundTest( WorkingState[ 0 ], WorkingState[ 5 ], WorkingState[ 10 ], WorkingState[ 15 ] ); // diagonal 1 (main diagonal)
PrintTestData();
QuarterRoundTest( WorkingState[ 1 ], WorkingState[ 6 ], WorkingState[ 11 ], WorkingState[ 12 ] ); // diagonal 2
PrintTestData();
QuarterRoundTest( WorkingState[ 2 ], WorkingState[ 7 ], WorkingState[ 8 ], WorkingState[ 13 ] ); // diagonal 3
PrintTestData();
QuarterRoundTest( WorkingState[ 3 ], WorkingState[ 4 ], WorkingState[ 9 ], WorkingState[ 14 ] ); // diagonal 4
PrintTestData();
}
//Mixing the data of the working state with the data of the state is equivalent to a secure hash function
//Hashed = Hash(State', State)
//Hashed = State' + State
//Hashed = Function(StateCopy) + State
for ( std::uint32_t Index = 0; Index < 16; ++Index )
WorkingState[ Index ] += TestState[ Index ];
}
int main()
{
Salsa20_WeakerTest();
//Chacha20_WeakerTest();
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment