RIPEMD-160

From Rosetta Code
Jump to: navigation, search
Task
RIPEMD-160
You are encouraged to solve this task according to the task description, using any language you may know.

RIPEMD-160 is another hash function; it computes a 160-bit message digest.

There is a RIPEMD-160 home page, with test vectors and pseudocode for RIPEMD-160. For padding the message, RIPEMD-160 acts like MD4 (RFC 1320).

Find the RIPEMD-160 message digest of a string of octets. Use the ASCII encoded string “Rosetta Code”. You may either call an RIPEMD-160 library, or implement RIPEMD-160 in your language.

Contents

[edit] D

import std.stdio, std.digest.ripemd;
 
void main() {
auto txt = "Rosetta Code";
writeln("%-(%02x%)", txt.ripemd160Of());
}
b3be159860842cebaa7174c8fff0aa9e50a5199f

[edit] Go

package main
 
import (
"code.google.com/p/go.crypto/ripemd160"
"fmt"
)
 
func main() {
h := ripemd160.New()
h.Write([]byte("Rosetta Code"))
fmt.Printf("%x\n", h.Sum(nil))
}
Output:
b3be159860842cebaa7174c8fff0aa9e50a5199f

[edit] Java

Library: BouncyCastle
import org.bouncycastle.crypto.digests.RIPEMD160Digest;
import org.bouncycastle.util.encoders.Hex;
 
public class RosettaRIPEMD160
{
public static void main (String[] argv) throws Exception
{
byte[] r = "Rosetta Code".getBytes("US-ASCII");
RIPEMD160Digest d = new RIPEMD160Digest();
d.update (r, 0, r.length);
byte[] o = new byte[d.getDigestSize()];
d.doFinal (o, 0);
Hex.encode (o, System.out);
System.out.println();
}
}
Output:
b3be159860842cebaa7174c8fff0aa9e50a5199f

[edit] Objeck

 
class Hash {
function : Main(args : String[]) ~ Nil {
in := "Rosetta Code"->ToByteArray();
hash := Encryption.Hash->RIPEMD160(in);
hash->ToHexString()->PrintLine();
}
}
 

Output:

B3BE159860842CEBAA7174C8FFF0AA9E50A5199F

[edit] Perl 6

=begin CREDITS
Crypto-JS v2.0.0
http:#code.google.com/p/crypto-js/
Copyright (c) 2009, Jeff Mott. All rights reserved.
=end
CREDITS
 
sub rotl($n, $b) { $n +< $b +| $n +> (32 - $b) }
sub prefix:<m^> { +^$^x % 2**32 }
sub infix:<m+> { ($^x + $^y) % 2**32 }
 
constant r1 = <
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
7 4 13 1 10 6 15 3 12 0 9 5 2 14 11 8
3 10 14 4 9 15 8 1 2 7 0 6 13 11 5 12
1 9 11 10 0 8 12 4 13 3 7 15 14 5 6 2
4 0 5 9 7 12 2 10 14 1 3 8 11 6 15 13
>;
constant r2 = <
5 14 7 0 9 2 11 4 13 6 15 8 1 10 3 12
6 11 3 7 0 13 5 10 14 15 8 12 4 9 1 2
15 5 1 3 7 14 6 9 11 8 12 2 10 0 4 13
8 6 4 1 3 11 15 0 5 12 2 13 9 7 10 14
12 15 10 4 1 5 8 7 6 2 13 14 0 3 9 11
>;
constant s1 = <
11 14 15 12 5 8 7 9 11 13 14 15 6 7 9 8
7 6 8 13 11 9 7 15 7 12 15 9 11 7 13 12
11 13 6 7 14 9 13 15 14 8 13 6 5 12 7 5
11 12 14 15 14 15 9 8 9 14 5 6 8 6 5 12
9 15 5 11 6 8 13 12 5 12 13 14 11 8 5 6
>;
constant s2 = <
8 9 9 11 13 15 15 5 7 7 8 11 14 14 12 6
9 13 15 7 12 8 9 11 7 7 12 7 6 15 13 11
9 7 15 11 8 6 6 14 12 13 5 14 13 13 7 5
15 5 8 11 14 14 6 14 6 9 12 9 12 5 15 8
8 5 12 9 12 5 14 6 8 13 6 5 15 13 11 11
>;
constant F =
* +^ * +^ *,
{ ($^x +& $^y) +| (m^$^x +& $^z) },
(* +| m^*) +^ *,
{ ($^x +& $^z) +| ($^y +& m^$^z) },
* +^ (* +| m^*),
;
constant K1 = <0x00000000 0x5a827999 0x6ed9eba1 0x8f1bbcdc 0xa953fd4e> »xx» 16;
constant K2 = <0x50a28be6 0x5c4dd124 0x6d703ef3 0x7a6d76e9 0x00000000> »xx» 16;
 
our proto rmd160($) returns Buf {*}
multi rmd160(Str $s) { rmd160 $s.encode: 'ascii' }
multi rmd160(Buf $data) {
my @b = $data.list, 0x80;
push @b, 0 until (8*@b-448) %% 512;
my $len = 8 * $data.elems;
push @b, gather for ^8 { take $len % 256; $len div= 256 }
 
my @word = gather for @b -> $a, $b, $c, $d {
take reduce * *256 + *, $d, $c, $b, $a;
}
 
my @h = 0x67452301, 0xefcdab89, 0x98badcfe, 0x10325476, 0xc3d2e1f0;
loop (my $i = 0; $i < @word; $i += 16) {
my @X = my @Y = @h;
for ^80 -> $j {
my $T = rotl(
@X[0] m+ F[$j div 16](|@X[1..3]) m+ (@word[$i+r1[$j]] // 0) m+ K1[$j],
s1[$j]
) m+ @X[4];
@X = @X[4], $T, @X[1], rotl(@X[2], 10) % 2**32, @X[3];
$T = rotl(
@Y[0] m+ F[(79-$j) div 16](|@Y[1..3]) m+ (@word[$i+r2[$j]] // 0) m+ K2[$j],
s2[$j]
) m+ @Y[4];
@Y = @Y[4], $T, @Y[1], rotl(@Y[2], 10) % 2**32, @Y[3];
}
@h = @h[1..4,^1] Z[m+] @X[2..4,^2] Z[m+] @Y[3..4,^3];
}
return Buf.new: gather for @h -> $word is rw {
for ^4 { take $word % 256; $word div= 256 }
}
}
 
say rmd160 "Rosetta Code";

Output:

Buf:0x<b3 be 15 98 60 84 2c eb aa 71 74 c8 ff f0 aa 9e 50 a5 19 9f>

[edit] Python

Python 3.3.0 (v3.3.0:bd8afb90ebf2, Sep 29 2012, 10:57:17) [MSC v.1600 64 bit (AMD64)] on win32
Type "copyright", "credits" or "license()" for more information.
>>> import hashlib
>>> h = hashlib.new('ripemd160')
>>> h.update(b"Rosetta Code")
>>> h.hexdigest()
'b3be159860842cebaa7174c8fff0aa9e50a5199f'
>>>


[edit] Racket

 
#lang racket
(require (planet soegaard/digest:1:2/digest))
(ripemd160 #"Rosetta Code")
 

Output:

 
"b3be159860842cebaa7174c8fff0aa9e50a5199f"
 

[edit] Ruby

Use 'digest' from Ruby's standard library.

require 'digest'
puts Digest::RMD160.hexdigest('Rosetta Code')

Use 'openssl' from Ruby's standard library.

require 'openssl'
puts OpenSSL::Digest::RIPEMD160.hexdigest('Rosetta Code')

Implement RIPEMD-160 in Ruby.

require 'stringio'
 
module RMD160
# functions and constants
MASK = (1 << 32) - 1
F = [
proc {|x, y, z| x ^ y ^ z},
proc {|x, y, z| (x & y) | (x.^(MASK) & z)},
proc {|x, y, z| (x | y.^(MASK)) ^ z},
proc {|x, y, z| (x & z) | (y & z.^(MASK))},
proc {|x, y, z| x ^ (y | z.^(MASK))},
].freeze
K = [0x00000000, 0x5a827999, 0x6ed9eba1, 0x8f1bbcdc, 0xa953fd4e]
KK = [0x50a28be6, 0x5c4dd124, 0x6d703ef3, 0x7a6d76e9, 0x00000000]
R = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15,
7, 4, 13, 1, 10, 6, 15, 3, 12, 0, 9, 5, 2, 14, 11, 8,
3, 10, 14, 4, 9, 15, 8, 1, 2, 7, 0, 6, 13, 11, 5, 12,
1, 9, 11, 10, 0, 8, 12, 4, 13, 3, 7, 15, 14, 5, 6, 2,
4, 0, 5, 9, 7, 12, 2, 10, 14, 1, 3, 8, 11, 6, 15, 13]
RR = [5, 14, 7, 0, 9, 2, 11, 4, 13, 6, 15, 8, 1, 10, 3, 12,
6, 11, 3, 7, 0, 13, 5, 10, 14, 15, 8, 12, 4, 9, 1, 2,
15, 5, 1, 3, 7, 14, 6, 9, 11, 8, 12, 2, 10, 0, 4, 13,
8, 6, 4, 1, 3, 11, 15, 0, 5, 12, 2, 13, 9, 7, 10, 14,
12, 15, 10, 4, 1, 5, 8, 7, 6, 2, 13, 14, 0, 3, 9, 11]
S = [11, 14, 15, 12, 5, 8, 7, 9, 11, 13, 14, 15, 6, 7, 9, 8,
7, 6, 8, 13, 11, 9, 7, 15, 7, 12, 15, 9, 11, 7, 13, 12,
11, 13, 6, 7, 14, 9, 13, 15, 14, 8, 13, 6, 5, 12, 7, 5,
11, 12, 14, 15, 14, 15, 9, 8, 9, 14, 5, 6, 8, 6, 5, 12,
9, 15, 5, 11, 6, 8, 13, 12, 5, 12, 13, 14, 11, 8, 5, 6]
SS = [8, 9, 9, 11, 13, 15, 15, 5, 7, 7, 8, 11, 14, 14, 12, 6,
9, 13, 15, 7, 12, 8, 9, 11, 7, 7, 12, 7, 6, 15, 13, 11,
9, 7, 15, 11, 8, 6, 6, 14, 12, 13, 5, 14, 13, 13, 7, 5,
15, 5, 8, 11, 14, 14, 6, 14, 6, 9, 12, 9, 12, 5, 15, 8,
8, 5, 12, 9, 12, 5, 14, 6, 8, 13, 6, 5, 15, 13, 11, 11]
 
module_function
 
def rol(value, shift)
(value << shift).&(MASK) | (value.&(MASK) >> (32 - shift))
end
 
# Calculates RIPEMD-160 message digest of _string_. Returns binary
# digest. For hexadecimal digest, use
# +*RMD160.rmd160(string).unpack('H*')+.
def rmd160(string)
# initial hash
h0 = 0x67452301
h1 = 0xefcdab89
h2 = 0x98badcfe
h3 = 0x10325476
h4 = 0xc3d2e1f0
 
io = StringIO.new(string)
block = ""
term = false # appended "\x80" in second-last block?
last = false # last block?
until last
# Read next block of 16 words (64 bytes, 512 bits).
io.read(64, block) or (
# Work around a bug in Rubinius 1.2.4. At eof,
# MRI and JRuby already replace block with "".
block.replace("")
)
 
# Unpack block into 32-bit words "V".
case len = block.length
when 64
# Unpack 16 words.
x = block.unpack("V16")
when 56..63
# Second-last block: append padding, unpack 16 words.
block.concat("\x80"); term = true
block.concat("\0" * (63 - len))
x = block.unpack("V16")
when 0..55
# Last block: append padding, unpack 14 words.
block.concat(term ? "\0" : "\x80")
block.concat("\0" * (55 - len))
x = block.unpack("V14")
 
# Append bit length, 2 words.
bit_len = string.length << 3
x.push(bit_len & MASK, bit_len >> 32)
last = true
else
fail "impossible"
end
 
# Process this block.
a, b, c, d, e = h0, h1, h2, h3, h4
aa, bb, cc, dd, ee = h0, h1, h2, h3, h4
j = 0
5.times {|ro|
f, ff = F[ro], F[4 - ro]
k, kk = K[ro], KK[ro]
16.times {
a, e, d, c, b = e, d, rol(c, 10), b,
rol(a + f[b, c, d] + x[R[j]] + k, S[j]) + e
aa, ee, dd, cc, bb = ee, dd, rol(cc, 10), bb,
rol(aa + ff[bb, cc, dd] + x[RR[j]] + kk, SS[j]) + ee
j += 1
}
}
h0, h1, h2, h3, h4 =
(h1 + c + dd) & MASK, (h2 + d + ee) & MASK,
(h3 + e + aa) & MASK, (h4 + a + bb) & MASK,
(h0 + b + cc) & MASK
end # until last
 
[h0, h1, h2, h3, h4].pack("V5")
end
end
 
if __FILE__ == $0
# Print an example RIPEMD-160 digest.
str = 'Rosetta Code'
printf "%s:\n  %s\n", str, *RMD160.rmd160(str).unpack('H*')
end

[edit] Tcl

Library: Tcllib (Package: ripemd160)
package require ripemd160
 
puts [ripemd::ripemd160 -hex "Rosetta Code"]
Output:
b3be159860842cebaa7174c8fff0aa9e50a5199f
Personal tools
Namespaces

Variants
Actions
Community
Explore
Misc
Toolbox