Пренасяне на малка побитова XOR perl функция към Ruby

Имам следния Perl скрипт, който прави побитово XOR на низ с HEX ключ:

#!/usr/bin/perl

$key = pack("H*","3cb37efae7f4f376ebbd76cd");

print "Enter string to decode: ";
$str=<STDIN>;chomp $str; $str =~ s/\\//g;
$dec = decode($str);
print "Decoded string value: $dec\n";

sub decode{ #Sub to decode
    @subvar=@_;
    my $sqlstr = $subvar[0];
    $cipher = unpack("u", $sqlstr);
    $plain = $cipher^$key;
    return substr($plain, 0, length($cipher));
}

Примерен резултат от стартирането му:

$ perl deXOR.pl
Enter string to decode: (?LM-D\=^5DB$ \n
Decoded string value: Bx3k8aaW

Опитах се да го пренеса към Ruby, но правя нещо нередно, резултатът не е същият:

#!/usr/bin/env ruby

key = ['3cb37efae7f4f376ebbd76cd'].pack('H*')

print "Enter string to decode: "
STDOUT.flush
a_string = gets
a_string.chomp!
a_string = a_string.gsub(/\//, "")
dec = String(key)
puts "Decoded string value: "+dec

class String
  def xor(key)
    text = dup
    text.length.times {|n| text[n] = (text[n].ord ^ key[n.modulo key.size].ord).chr }
    text
  end
end

Примерен резултат:

$ ruby deXOR.rb
Enter string to decode: (?LM-D\=^5DB$ \n
Decoded string value: <³~úçôóvë½vÍ

какво правя грешно някакви мисли? Благодаря!

Променен, все още бъркотия...

key = ['3cb37efae7f4f376ebbd76cd'].pack('H*')

def xor(text, key)
  text.length.times {|n| text[n] = (text[n].ord ^ key[n.modulo key.size].ord).chr}
  text
end

print "Enter string to decode: "
STDOUT.flush
a_string = gets
a_string.chomp!
a_string = a_string.gsub(/\//, "")
dec = xor(a_string, key)
puts "Decoded string value: "+dec

Изход:

$ ruby deXOR.rb
Enter string to decode: (?LM-D\=^5DB$ \n
Decoded string value: 2·Ê°¯Kµ2"

Работна версия с помощта на Digitaka:

key = ['3cb37efae7f4f376ebbd76cd'].pack('H*')

def decode(str, key)
  text = str.dup
  text.length.times { |n| text[n] = (text[n].ord ^ key[n.modulo key.size].ord).chr }
  text
end

print "Enter string to decode: "
STDOUT.flush
a_string = gets
a_string.chomp!
a_string = a_string.gsub(/\\n/, "")
a_string = a_string.gsub(/\\/, "")
a_string = a_string.unpack('u')[0]
dec = decode(a_string,key)
puts "Decoded string value: "+dec

Изход:

$ ruby deXOR.rb
Enter string to decode: (?LM-D=^5DB$ \n
Decoded string value: Bx3k8aaW

person bsteo    schedule 19.02.2013    source източник
comment
Във вашия фрагмент изобщо не изглежда да извиквате вашата xor функция   -  person Frederick Cheung    schedule 20.02.2013
comment
Изглежда никой не може да помогне, благодаря все пак...   -  person bsteo    schedule 20.02.2013


Отговори (1)


В perl вашият код uudecodes въведения низ и еквивалентът не се случва в ruby. Този фрагмент uudecodes и decodes като perl кода:

key = ['3cb37efae7f4f376ebbd76cd'].pack('H*')

# took some liberties to simplify the input text code
istr = "(?LM-D=^5DB$ ".unpack('u')[0]

def decode(str, key)
  text = str.dup
  text.length.times { |n| text[n] = (text[n].ord ^ key[n.modulo key.size].ord).chr }
  text
end

puts decode(istr,key) 
# => Bx3k8aaW
person Digikata    schedule 20.02.2013
comment
Работи като чар! Благодаря! - person bsteo; 20.02.2013
comment
Хм, този кодиран низ е неуспешен: *%XI'R-7\!QT/?_0 \n -› +992ôkä трябва да дава +99225454@ - person bsteo; 20.02.2013
comment
Мисля, че трябва да добавя a_string = a_string.gsub(/\\/, ) - person bsteo; 20.02.2013
comment
Да, съжалявам, това беше едно от нещата, които извадих, за да получа работния фрагмент. - person Digikata; 20.02.2013