Pure-Ruby implementation of Stateful Decryption Counter(SDCTR) Mode for Block Ciphers. See RFC4344 for detail.
# File lib/net/ssh/transport/ctr.rb, line 8 8: def self.extended(orig) 9: orig.instance_eval { 10: @remaining = "" 11: @counter = nil 12: @counter_len = orig.block_size 13: orig.encrypt 14: orig.padding = 0 15: } 16: 17: class <<orig 18: alias :_update :update 19: private :_update 20: undef :update 21: 22: def iv 23: @counter 24: end 25: 26: def iv_len 27: block_size 28: end 29: 30: def iv=(iv_s) 31: @counter = iv_s if @counter.nil? 32: end 33: 34: def encrypt 35: # DO NOTHING (always set to "encrypt") 36: end 37: 38: def decrypt 39: # DO NOTHING (always set to "encrypt") 40: end 41: 42: def padding=(pad) 43: # DO NOTHING (always 0) 44: end 45: 46: def reset 47: @remaining = "" 48: end 49: 50: def update(data) 51: @remaining += data 52: 53: encrypted = "" 54: 55: while @remaining.bytesize >= block_size 56: encrypted += xor!(@remaining.slice!(0, block_size), 57: _update(@counter)) 58: increment_counter! 59: end 60: 61: encrypted 62: end 63: 64: def final 65: unless @remaining.empty? 66: s = xor!(@remaining, _update(@counter)) 67: else 68: s = "" 69: end 70: 71: @remaining = "" 72: 73: s 74: end 75: 76: private 77: 78: def xor!(s1, s2) 79: s = [] 80: s1.unpack('Q*').zip(s2.unpack('Q*')) {|a,b| s.push(a^b) } 81: s.pack('Q*') 82: end 83: 84: def increment_counter! 85: c = @counter_len 86: while ((c -= 1) > 0) 87: if @counter.setbyte(c, (@counter.getbyte(c) + 1) & 0xff) != 0 88: break 89: end 90: end 91: end 92: end
# File lib/net/ssh/transport/ctr.rb, line 38 38: def decrypt 39: # DO NOTHING (always set to "encrypt") 40: end
# File lib/net/ssh/transport/ctr.rb, line 34 34: def encrypt 35: # DO NOTHING (always set to "encrypt") 36: end
# File lib/net/ssh/transport/ctr.rb, line 64 64: def final 65: unless @remaining.empty? 66: s = xor!(@remaining, _update(@counter)) 67: else 68: s = "" 69: end 70: 71: @remaining = "" 72: 73: s 74: end
# File lib/net/ssh/transport/ctr.rb, line 84 84: def increment_counter! 85: c = @counter_len 86: while ((c -= 1) > 0) 87: if @counter.setbyte(c, (@counter.getbyte(c) + 1) & 0xff) != 0 88: break 89: end 90: end 91: end
# File lib/net/ssh/transport/ctr.rb, line 22 22: def iv 23: @counter 24: end
# File lib/net/ssh/transport/ctr.rb, line 30 30: def iv=(iv_s) 31: @counter = iv_s if @counter.nil? 32: end
# File lib/net/ssh/transport/ctr.rb, line 26 26: def iv_len 27: block_size 28: end
# File lib/net/ssh/transport/ctr.rb, line 42 42: def padding=(pad) 43: # DO NOTHING (always 0) 44: end
# File lib/net/ssh/transport/ctr.rb, line 46 46: def reset 47: @remaining = "" 48: end
# File lib/net/ssh/transport/ctr.rb, line 50 50: def update(data) 51: @remaining += data 52: 53: encrypted = "" 54: 55: while @remaining.bytesize >= block_size 56: encrypted += xor!(@remaining.slice!(0, block_size), 57: _update(@counter)) 58: increment_counter! 59: end 60: 61: encrypted 62: end
Disabled; run with --debug to generate this.
Generated with the Darkfish Rdoc Generator 1.1.6.