SharedKeyRiddle.vala 1.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657
  1. namespace Riddle {
  2. public class SharedKeyRiddle : Riddle {
  3. private uint8[] shared_key { get; set; }
  4. private uint8[] token { get; set; }
  5. private const int TOKEN_SIZE = 5120;
  6. public InetSocketAddress app_socket_address { get; set; }
  7. public SharedKeyRiddle(uint8[] shared_key) {
  8. this.shared_key = shared_key;
  9. token = new uint8[TOKEN_SIZE];
  10. Sodium.Random.random_bytes (token);
  11. }
  12. public static uint8[] generate_key() {
  13. return Sodium.Symmetric.generate_key();
  14. }
  15. protected override uint8[] generate (uint8[] secret) {
  16. var nonce = new uint8[Sodium.Symmetric.NONCE_BYTES];
  17. Sodium.Random.random_bytes (nonce);
  18. var message = join_data (token, secret);
  19. var cyphertext = Sodium.Symmetric.encrypt (message, shared_key, nonce);
  20. return join_data (nonce, cyphertext);
  21. }
  22. protected override GLib.InetSocketAddress? validate (uint8[] solution) {
  23. for(int i = 0; i < solution.length && i < TOKEN_SIZE; i++) {
  24. if(token[i] != solution[i]) {
  25. return null;
  26. }
  27. }
  28. return app_socket_address;
  29. }
  30. public override Solution? solve (uint8[] riddle) {
  31. var nonce = riddle[0:Sodium.Symmetric.NONCE_BYTES];
  32. var cyphertext = riddle[Sodium.Symmetric.NONCE_BYTES:];
  33. var message = Sodium.Symmetric.decrypt (cyphertext, shared_key, nonce);
  34. var token = message[0:TOKEN_SIZE];
  35. var secret = message[TOKEN_SIZE:];
  36. print(@"Token starts with $(token[0])\n");
  37. return new Solution (secret, token);
  38. }
  39. }
  40. }