vinegere_cipher.sf 2.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394
  1. #!/usr/bin/ruby
  2. # Author: Trizen
  3. # Date: 05 May 2024
  4. # https://github.com/trizen
  5. # Simple implementation of the Vinegere cipher.
  6. # Inspired by:
  7. # The Unbreakable Kryptos Code
  8. # https://youtube.com/watch?v=jVpsLMCIB0Y
  9. func vinegere_cipher_encode(text, key, alphabet_key = '', alphabet = @('A' .. 'Z')) {
  10. key.chars!
  11. alphabet_key.flip.each {|c|
  12. alphabet.delete(c)
  13. alphabet.unshift(c)
  14. }
  15. var table = [alphabet]
  16. for (2 .. alphabet.len) {
  17. table.push(table[-1].rotate(1))
  18. }
  19. var lookup_table = Hash()
  20. table.each_kv {|k,v|
  21. lookup_table{v[0]} = k
  22. }
  23. var ciphertext = []
  24. var key_len = key.len
  25. text.chars.each_kv {|k,v|
  26. if (lookup_table.has(v)) {
  27. ciphertext << table[lookup_table{key[k % key_len]}][lookup_table{v}]
  28. }
  29. else {
  30. die "error: character #{'0x%02x' % v.ord} is not included in the alphabet"
  31. }
  32. }
  33. return ciphertext.join
  34. }
  35. func vinegere_cipher_decode(ciphertext, key, alphabet_key = '', alphabet = @('A' .. 'Z')) {
  36. key.chars!
  37. alphabet_key.flip.each {|c|
  38. alphabet.delete(c)
  39. alphabet.unshift(c)
  40. }
  41. var table = [alphabet]
  42. for (2 .. alphabet.len) {
  43. table.push(table[-1].rotate(1))
  44. }
  45. var lookup_table = Hash()
  46. table.each {|row|
  47. lookup_table{row[0]} = Hash(row.kv.map { .flip... }...)
  48. }
  49. var text = []
  50. var key_len = key.len
  51. ciphertext.chars.each_kv {|k,v|
  52. if (lookup_table.has(v)) {
  53. text << table[lookup_table{key[k % key_len]}{v}][0]
  54. }
  55. else {
  56. die "error: character #{'0x%02x' % v.ord} is not included in the alphabet"
  57. }
  58. }
  59. return text.join
  60. }
  61. say vinegere_cipher_encode("SECRETMESSAGE", "HIDDEN", "KRYPTOS") #=> QKNEVWSKJJMSZ
  62. say vinegere_cipher_decode("QKNEVWSKJJMSZ", "HIDDEN", "KRYPTOS") #=> SECRETMESSAGE
  63. var data = File(__FILE__).read(:raw)
  64. var enc = vinegere_cipher_encode(data, "HIDDEN", "KRYPTOS", @(0..255).map{.chr})
  65. var dec = vinegere_cipher_decode(enc, "HIDDEN", "KRYPTOS", @(0..255).map{.chr})
  66. assert_eq(dec, data)