// // Author: Danny Loffredo // dgl4b@virginia.edu // // Version 1.0 - 29 August 3:54PM // // usage: // // a.out // // and are the names of files containing ciphertexts at 0 and 1's (as // in the c1.txt and c2.txt // // is a plain text file for the message guess. // // The output is the plaintext corresponding to , if is the message // that encodes. // // Non-printable characters appear as '$'. // // C1 = M1 xor K // C2 = M2 xor K // C' = C1 xor C2 = M1 xor M2 // M2 = C' xor M1 #include #include #include #include #include using namespace std; typedef char SevenBits; typedef vector Bits; Bits StringToBits ( string ascii_string ); Bits BitStringToBits ( string bit_string ); string BitsToString ( Bits the_bits ); Bits XorBits ( Bits a, Bits b ); Bits XorBits ( Bits a, Bits b ) { Bits answer; int smallest; if ( a.size() < b.size() ) smallest = a.size(); else smallest = b.size(); for(int index = 0; index < smallest; index++) { int a_int = int( a[index] ); int b_int = int( b[index] ); int next = (a_int ^ b_int) & 127; answer.push_back( char(next) ); } return answer; } string BitsToString ( Bits the_bits ) { string answer; answer.resize( the_bits.size() ); for(int index = 0; index < the_bits.size(); index++) { if (the_bits[index] == 0) answer[index] = '$'; else answer[index] = the_bits[index]; if (!isprint (answer[index])) { answer[index] = '$'; } } return answer; } Bits StringToBits ( string ascii_string ) { Bits answer; answer.resize( ascii_string.size() ); for(int index = 0; index < ascii_string.size(); index++) { answer[index] = ascii_string[index]; } return answer; } Bits BitStringToBits ( string bit_string ) { Bits answer; if ( bit_string.size() % 7 != 0 ) return answer; answer.resize( bit_string.size() / 7 ); for(int index = 0; index < answer.size(); index++) { int number = 0; for(int count = 0; count < 7; count++) { char this_bit = bit_string[index * 7 + count]; switch(this_bit) { case '0': number = 2 * number; break; case '1': number = 2 * number + 1; break; } } answer[index] = char(number); } return answer; } int main(int argc, char* argv[]) { if(argc < 4) { cout << "Usage: " << string(argv[0]) << " " << endl; return 1; } else { ifstream Cipher1Stream; ifstream Cipher2Stream; ifstream Message1Stream; Cipher1Stream.open(argv[1], ios::in); Cipher2Stream.open(argv[2], ios::in); Message1Stream.open(argv[3], ios::in); string C1Input; string C2Input; string M1Input; Cipher1Stream >> C1Input; Cipher2Stream >> C2Input; Message1Stream >> M1Input; string input; int ic; while ((ic = Message1Stream.get ()) != EOF) M1Input = M1Input + char (ic); Bits Cipher1 = BitStringToBits(C1Input); Bits Cipher2 = BitStringToBits(C2Input); Bits Message1 = StringToBits(M1Input); Bits CipherPrime = XorBits(Cipher1, Cipher2); Bits Message2 = XorBits(CipherPrime, Message1); cout << BitsToString(Message2) << endl; return 0; } }