Left turn through porting in Ruby

I am trying to implement SHA1 in Ruby, and for this I need to prepare the left turn via hyphenation. The code I wrote seems to work 1 turn, but no more that it did not pass my tests, does anyone know why?

class Integer def rotate_left(count, size) temp = self count.times do first_bit = (self & 2 ** size)[size] temp = temp << 1 temp = temp ^ first_bit temp = temp ^ (2 ** (size + 1)) end return temp end end 
+4
source share
3 answers

First I checked Wikipedia to make sure I understood the operation. It looks like you are losing your carry. In addition, I added a testing class to make sure I get the right answers. I was not sure if you wanted to keep the bits portable or not, so I commented out the code to truncate the result. Hope this helps!

 class Integer def rotate_left(count, size) temp = self carry = 0 count.times do temp = temp << 1 temp = temp | carry carry = (temp >> size) & 1 end return temp # & (( 1 << size ) - 1) end end if __FILE__ == $0 then require 'test/unit' class TestRotateLeft < Test::Unit::TestCase def test_no_rotation result = 5.rotate_left(0,4) answer = result & 15 carry = ( result & 16 ) >> 4 assert_equal 5, result assert_equal 0, carry end def test_one_rotation result = 5.rotate_left(1,4) answer = result & 15 carry = ( result & 16 ) >> 4 assert_equal 10, answer assert_equal 0, carry end def test_first_carry result = 5.rotate_left(2,4) answer = result & 15 carry = ( result & 16 ) >> 4 assert_equal 4, answer assert_equal 1, carry end def test_shift_from_carry result = 5.rotate_left(3,4) answer = result & 15 carry = ( result & 16 ) >> 4 assert_equal 9, answer assert_equal 0, carry end def test_second_carry result = 5.rotate_left(4,4) answer = result & 15 carry = ( result & 16 ) >> 4 assert_equal 2, answer assert_equal 1, carry end def test_full_rotation result = 5.rotate_left(5,4) answer = result & 15 carry = ( result & 16 ) >> 4 assert_equal 5, answer assert_equal 0, carry end end end 
+2
source

what do you use for size ? If you try to do a 4-bit rotation, for example, and you set the size to 4, then evaluating first_bit gets the 5th bit:

  2**4 => 16 16.to_s(2) => "10000" 

So, indexing is OK. But in the inner loop, you get first_bit from self instead of temp. So this will only work for the first time.

0
source

I once implemented SHA-256 in Ruby (which uses the right turn) and finally used this code:

 class Integer def rotate(n=1) self >> n | self << (32 - n) end end 

You can change it to rotate on the left:

 class Integer def lotate(n=1) self << n | self >> (32 - n) end end 

Although it is very difficult to understand ... it works :)

0
source

All Articles