ruby-xxHash 0.1.1 → 0.3.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 4b572ac0c8cdae1cf7f5521976d4d6d914f90942
4
+ data.tar.gz: 80fe87bebc85f75dc8e6e196c5fd8555091f24f8
5
+ SHA512:
6
+ metadata.gz: 8c1d74e45ec38e2757685c04ab47e9e3ab4d98e746d9d804a62b6e6ebdc4aac6110497c09b7576b521ccb3be842e5ba966e8d31d728fd629e12d01babf2c451d
7
+ data.tar.gz: 71652397a6f621ac2fca7dbe6a24749a67c3fec3adc21a5d6fc7f81ac1459946feb7de622c54f8b6c23a304ec15c7f5b8cd6e9b7cf051d24ec416c438b5bf433
data/.gitignore CHANGED
@@ -1,5 +1,8 @@
1
1
  *.gem
2
2
  *.rbc
3
+ **/*.iml
4
+ .idea/
5
+ ruby-xxhash/
3
6
  .bundle
4
7
  .config
5
8
  .yardoc
data/lib/ruby-xxhash.rb CHANGED
@@ -1,23 +1,18 @@
1
+ # Copyright 2014 Justin W. Smith
2
+
1
3
  require "ruby-xxhash/version"
4
+ require "ruby-xxhash32"
5
+ require "ruby-xxhash64"
2
6
 
3
7
  class XXhash
4
- @@mem_total_size = 16
5
- @@prime32_1 = 2654435761
6
- @@prime32_2 = 2246822519
7
- @@prime32_3 = 3266489917
8
- @@prime32_4 = 668265263
9
- @@prime32_5 = 374761393
10
-
11
- @@thirtytwo1s = (2**32-1)
12
-
13
8
  def XXhash.xxh32(input, seed = 0)
14
- xxh = XXhash.new(seed)
9
+ xxh = XXhash32.new(seed)
15
10
  xxh.feed(input)
16
11
  xxh.sum32
17
12
  end
18
13
 
19
14
  def XXhash.xxh32_stream(io, seed = 0, chunk = 32)
20
- xxh = XXhash.new(seed)
15
+ xxh = XXhash32.new(seed)
21
16
 
22
17
  while(data = io.read(chunk))
23
18
  xxh.feed(data)
@@ -26,103 +21,20 @@ class XXhash
26
21
  xxh.sum32
27
22
  end
28
23
 
29
- def initialize seed
30
- @seed = seed
31
- @v1 = seed + @@prime32_1 + @@prime32_2
32
- @v2 = seed + @@prime32_2
33
- @v3 = seed + 0
34
- @v4 = seed - @@prime32_1
35
- @total_len = 0
36
- @memory = Array.new(@@mem_total_size)
37
- @memsize = 0
38
- end
39
-
40
-
41
- def feed bytes
42
- if String === bytes
43
- bytes = bytes.unpack("C*")
44
- end
45
-
46
- @total_len += bytes.length
47
-
48
- p = 0
49
-
50
- while (remaining = (bytes.length - p)) > 0
51
-
52
- mem_avail = @@mem_total_size - @memsize
53
-
54
- if(remaining < mem_avail)
55
- @memory[@memsize, remaining] = bytes[p, remaining]
56
- @memsize += remaining
57
- break
58
- end
59
-
60
- @memory[@memsize, mem_avail] = bytes[p, mem_avail]
61
-
62
- i = 0
63
- [:v1, :v2, :v3, :v4].each do |m|
64
- p32 = uint32(
65
- @memory[i] |
66
- (@memory[i+1] << 8) |
67
- (@memory[i+2] << 16) |
68
- (@memory[i+3] << 24))
69
-
70
- v = uint32(self.send(m) + p32 * @@prime32_2)
71
- v = uint32(uint32((v << 13) | (v >> (32 - 13))) * @@prime32_1)
72
- self.send((m.to_s + "=").to_sym, v)
73
- i += 4
74
- end
75
-
76
- p += mem_avail
77
- @memsize = 0
78
- end
79
-
80
- return true
24
+ def XXhash.xxh64(input, seed = 0)
25
+ xxh = XXhash64.new(seed)
26
+ xxh.feed(input)
27
+ xxh.sum64
81
28
  end
82
29
 
83
- def sum32
84
- if @total_len >= 16
85
- h32 = ((@v1 << 1) | (@v1 >> (32 - 1))) +
86
- ((@v2 << 7) | (@v2 >> (32 - 7))) +
87
- ((@v3 << 12) | (@v3 >> (32 - 12))) +
88
- ((@v4 << 18) | (@v4 >> (32 - 18)))
89
- else
90
- h32 = @seed + @@prime32_5
91
- end
92
-
93
- h32 = uint32(h32 + @total_len)
94
-
95
- p = 0
96
- while p <= (@memsize - 4)
97
- p32 = uint32(@memory[p] |
98
- (@memory[p+1] << 8) |
99
- (@memory[p+2] << 16) |
100
- (@memory[p+3] << 24))
101
- h32 = uint32(h32 + p32 * @@prime32_3)
102
- h32 = uint32(uint32((h32 << 17) | (h32 >> (32 - 17))) * @@prime32_4)
103
- p += 4
104
- end
30
+ def XXhash.xxh64_stream(io, seed = 0, chunk = 32)
31
+ xxh = XXhash64.new(seed)
105
32
 
106
- while p < @memsize
107
- h32 = uint32(h32 + @memory[p] * @@prime32_5)
108
- h32 = uint32(uint32((h32 << 11) | (h32 >> (32 - 11))) * @@prime32_1)
109
- p += 1
33
+ while(data = io.read(chunk))
34
+ xxh.feed(data)
110
35
  end
111
36
 
112
- h32 ^= h32 >> 15
113
- h32 = uint32(h32 * @@prime32_2)
114
- h32 ^= h32 >> 13
115
- h32 = uint32(h32 * @@prime32_3)
116
- h32 ^= h32 >> 16
117
-
118
- h32
37
+ xxh.sum64
119
38
  end
120
39
 
121
- private
122
-
123
- attr_accessor :v1, :v2, :v3, :v4
124
-
125
- def uint32(x)
126
- x & @@thirtytwo1s
127
- end
128
- end
40
+ end
@@ -1,3 +1,3 @@
1
1
  class XXhash
2
- VERSION = "0.1.1"
2
+ VERSION = "0.3.0"
3
3
  end
@@ -0,0 +1,112 @@
1
+
2
+
3
+ class XXhash32
4
+ @@mem_total_size = 16
5
+ @@prime32_1 = 2654435761
6
+ @@prime32_2 = 2246822519
7
+ @@prime32_3 = 3266489917
8
+ @@prime32_4 = 668265263
9
+ @@prime32_5 = 374761393
10
+
11
+ @@thirtytwo1s = (2**32-1)
12
+
13
+ def initialize seed
14
+ @seed = seed
15
+ @v1 = seed + @@prime32_1 + @@prime32_2
16
+ @v2 = seed + @@prime32_2
17
+ @v3 = seed + 0
18
+ @v4 = seed - @@prime32_1
19
+ @total_len = 0
20
+ @memory = Array.new(@@mem_total_size)
21
+ @memsize = 0
22
+ end
23
+
24
+
25
+ def feed bytes
26
+ if String === bytes
27
+ bytes = bytes.unpack("C*")
28
+ end
29
+
30
+ @total_len += bytes.length
31
+
32
+ p = 0
33
+
34
+ while (remaining = (bytes.length - p)) > 0
35
+
36
+ mem_avail = @@mem_total_size - @memsize
37
+
38
+ if(remaining < mem_avail)
39
+ @memory[@memsize, remaining] = bytes[p, remaining]
40
+ @memsize += remaining
41
+ break
42
+ end
43
+
44
+ @memory[@memsize, mem_avail] = bytes[p, mem_avail]
45
+
46
+ i = 0
47
+ [:v1, :v2, :v3, :v4].each do |m|
48
+ p32 = uint32(
49
+ @memory[i] |
50
+ (@memory[i+1] << 8) |
51
+ (@memory[i+2] << 16) |
52
+ (@memory[i+3] << 24))
53
+
54
+ v = uint32(self.send(m) + p32 * @@prime32_2)
55
+ v = uint32(uint32((v << 13) | (v >> (32 - 13))) * @@prime32_1)
56
+ self.send((m.to_s + "=").to_sym, v)
57
+ i += 4
58
+ end
59
+
60
+ p += mem_avail
61
+ @memsize = 0
62
+ end
63
+
64
+ return true
65
+ end
66
+
67
+ def sum32
68
+ if @total_len >= 16
69
+ h32 = ((@v1 << 1) | (@v1 >> (32 - 1))) +
70
+ ((@v2 << 7) | (@v2 >> (32 - 7))) +
71
+ ((@v3 << 12) | (@v3 >> (32 - 12))) +
72
+ ((@v4 << 18) | (@v4 >> (32 - 18)))
73
+ else
74
+ h32 = @seed + @@prime32_5
75
+ end
76
+
77
+ h32 = uint32(h32 + @total_len)
78
+
79
+ p = 0
80
+ while p <= (@memsize - 4)
81
+ p32 = uint32(@memory[p] |
82
+ (@memory[p+1] << 8) |
83
+ (@memory[p+2] << 16) |
84
+ (@memory[p+3] << 24))
85
+ h32 = uint32(h32 + p32 * @@prime32_3)
86
+ h32 = uint32(uint32((h32 << 17) | (h32 >> (32 - 17))) * @@prime32_4)
87
+ p += 4
88
+ end
89
+
90
+ while p < @memsize
91
+ h32 = uint32(h32 + @memory[p] * @@prime32_5)
92
+ h32 = uint32(uint32((h32 << 11) | (h32 >> (32 - 11))) * @@prime32_1)
93
+ p += 1
94
+ end
95
+
96
+ h32 ^= h32 >> 15
97
+ h32 = uint32(h32 * @@prime32_2)
98
+ h32 ^= h32 >> 13
99
+ h32 = uint32(h32 * @@prime32_3)
100
+ h32 ^= h32 >> 16
101
+
102
+ h32
103
+ end
104
+
105
+ private
106
+
107
+ attr_accessor :v1, :v2, :v3, :v4
108
+
109
+ def uint32(x)
110
+ x & @@thirtytwo1s
111
+ end
112
+ end
@@ -0,0 +1,135 @@
1
+ require "ruby-xxhash/version"
2
+
3
+ class XXhash64
4
+ @@mem_total_size = 32
5
+ @@prime64_1 = 11400714785074694791
6
+ @@prime64_2 = 14029467366897019727
7
+ @@prime64_3 = 1609587929392839161
8
+ @@prime64_4 = 9650029242287828579
9
+ @@prime64_5 = 2870177450012600261
10
+
11
+ @@sixtyfour1s = (2**64-1)
12
+
13
+ def initialize seed
14
+ @seed = seed
15
+ @v1 = seed + @@prime64_1 + @@prime64_2;
16
+ @v2 = seed + @@prime64_2;
17
+ @v3 = seed + 0;
18
+ @v4 = seed - @@prime64_1;
19
+ @total_len = 0
20
+ @memory = Array.new(@@mem_total_size)
21
+ @memsize = 0
22
+ end
23
+
24
+ def feed bytes
25
+ if String === bytes
26
+ bytes = bytes.unpack("C*")
27
+ end
28
+
29
+ @total_len += bytes.length
30
+
31
+ p = 0
32
+ while (remaining = (bytes.length - p)) > 0
33
+ mem_avail = @@mem_total_size - @memsize
34
+
35
+ if(remaining < mem_avail)
36
+ @memory[@memsize, remaining] = bytes[p, remaining]
37
+ @memsize += remaining
38
+ break
39
+ end
40
+
41
+ @memory[@memsize, mem_avail] = bytes[p, mem_avail]
42
+
43
+ i = 0
44
+ [:v1, :v2, :v3, :v4].each do |m|
45
+ p64 = uint64(
46
+ @memory[i] |
47
+ (@memory[i+1] << 8) |
48
+ (@memory[i+2] << 16) |
49
+ (@memory[i+3] << 24) |
50
+ (@memory[i+4] << 32) |
51
+ (@memory[i+5] << 40) |
52
+ (@memory[i+6] << 48) |
53
+ (@memory[i+7] << 56))
54
+
55
+ v = uint64(self.send(m) + p64 * @@prime64_2)
56
+ v = uint64(uint64((v << 31) | (v >> (64 - 31))) * @@prime64_1)
57
+ self.send((m.to_s + "=").to_sym, v)
58
+ i += 8
59
+ end
60
+
61
+ p += mem_avail
62
+ @memsize = 0
63
+ end
64
+ end
65
+
66
+ def sum64
67
+ if @total_len >= 32
68
+ h64 = ((@v1 << 1) | (@v1 >> (64 - 1))) +
69
+ ((@v2 << 7) | (@v2 >> (64 - 7))) +
70
+ ((@v3 << 12) | (@v3 >> (64 - 12))) +
71
+ ((@v4 << 18) | (@v4 >> (64 - 18)))
72
+
73
+ [:v1, :v2, :v3, :v4].each do |m|
74
+ v = uint64(self.send(m) * @@prime64_2)
75
+ v = uint64((v << 31) | (v >> (64 - 31)))
76
+ h64 ^= uint64(v * @@prime64_1)
77
+ h64 = h64 * @@prime64_1 + @@prime64_4
78
+ end
79
+ else
80
+ h64 = @seed + @@prime64_5
81
+ end
82
+
83
+ h64 = uint64(h64 + @total_len)
84
+
85
+ i = 0
86
+ while i <= (@memsize - 8)
87
+ v = uint64(
88
+ @memory[i] |
89
+ (@memory[i+1] << 8) |
90
+ (@memory[i+2] << 16) |
91
+ (@memory[i+3] << 24) |
92
+ (@memory[i+4] << 32) |
93
+ (@memory[i+5] << 40) |
94
+ (@memory[i+6] << 48) |
95
+ (@memory[i+7] << 56))
96
+
97
+ v = uint64(v * @@prime64_2)
98
+ h64 ^= uint64(uint64((v << 31) | (v >> (64 - 31))) * @@prime64_1)
99
+ h64 = uint64(uint64((h64 << 27) | (h64 >> (64 - 27))) * @@prime64_1 + @@prime64_4)
100
+ i += 8
101
+ end
102
+
103
+ if i <= (@memsize - 4)
104
+ v = @memory[i] |
105
+ (@memory[i+1] << 8) |
106
+ (@memory[i+2] << 16) |
107
+ (@memory[i+3] << 24)
108
+ h64 ^= uint64(v * @@prime64_1)
109
+ h64 = uint64(uint64((h64 << 23) | (h64 >> (64-23))) * @@prime64_2 + @@prime64_3)
110
+ i += 4
111
+ end
112
+
113
+ while i < @memsize
114
+ h64 ^= uint64(@memory[i] * @@prime64_5)
115
+ h64 = uint64(uint64((h64 << 11) | (h64 >> (64 - 11))) * @@prime64_1)
116
+ i += 1
117
+ end
118
+
119
+ h64 ^= h64 >> 33
120
+ h64 = uint64(h64 * @@prime64_2)
121
+ h64 ^= h64 >> 29
122
+ h64 = uint64(h64 * @@prime64_3)
123
+ h64 ^= h64 >> 32
124
+
125
+ h64
126
+ end
127
+
128
+ private
129
+
130
+ attr_accessor :v1, :v2, :v3, :v4
131
+
132
+ def uint64(x)
133
+ x & @@sixtyfour1s
134
+ end
135
+ end
File without changes
@@ -0,0 +1,16 @@
1
+ ---
2
+ ? - test
3
+ - 123
4
+ : 3134990500624303823
5
+ ? - ! 'Lorem ipsum dolor sit amet, consectetuer adipiscing elit, '
6
+ - 0
7
+ : 17031984226649854695
8
+ ? - ! 'Lorem ipsum dolor sit amet, consectetuer adipiscing elit, '
9
+ - 1471
10
+ : 13163341760735734472
11
+ ? - ! 'Lorem ipsum dolor sit amet, consectetuer adipiscing elit, sed diam nonummy nibh euismod tincidunt ut laoreet dolore magna aliquam erat volutpat.'
12
+ - 0
13
+ : 14967567540383795520
14
+ ? - ! 'Lorem ipsum dolor sit amet, consectetuer adipiscing elit, sed diam nonummy nibh euismod tincidunt ut laoreet dolore magna aliquam erat volutpat.'
15
+ - 1471
16
+ : 4189552183125498197
data/spec/xxhash_spec.rb CHANGED
@@ -1,34 +1,57 @@
1
1
  #Copyright (c) 2012 Vasiliy Ermolovich
2
+ #Copyright (c) 2014 Justin W Smith
2
3
 
3
4
  require 'spec_helper'
4
5
  require 'stringio'
5
6
  require 'yaml'
6
7
 
7
8
  describe XXhash do
8
- hash = YAML.load(IO.read "spec/results.yaml")
9
+ hash32 = YAML.load(IO.read "spec/results32.yaml")
10
+ hash64 = YAML.load(IO.read "spec/results64.yaml")
9
11
 
10
- hash.each do |key, value|
12
+ hash32.each do |key, value|
11
13
  it 'returns correct hash' do
12
- XXhash.xxh32(key[0], key[1]).should eq(value)
14
+ expect(XXhash.xxh32(key[0], key[1])).to eq(value)
13
15
  end
14
16
  end
15
17
 
18
+ hash64.each do |key, value|
19
+ it 'returns correct hash' do
20
+ expect(XXhash.xxh64(key[0], key[1])).to eq(value)
21
+ end
22
+ end
16
23
 
17
24
  describe 'StreamingHash' do
18
25
  it 'raises error if argument is not an IO object' do
19
26
  expect { XXhash.xxh32_stream('test', 123)}.to raise_error
20
27
  end
21
28
 
22
- hash.each do |key, value|
29
+ hash32.each do |key, value|
23
30
  it 'returns correct hash' do
24
- XXhash.xxh32_stream(StringIO.new(key[0]), key[1]).should eq(value)
31
+ expect(XXhash.xxh32_stream(StringIO.new(key[0]), key[1])).to eq(value)
25
32
  end
26
33
  end
27
34
 
28
35
  it 'returns same hash for streamed files' do
29
36
  h1 = XXhash.xxh32(File.read(__FILE__), 123)
30
37
  h2 = XXhash.xxh32_stream(File.open(__FILE__), 123)
31
- h1.should eq(h2)
38
+ expect(h1).to eq(h2)
39
+ end
40
+
41
+ it 'raises error if argument is not an IO object' do
42
+ expect { XXhash.xxh64_stream('test', 123)}.to raise_error
43
+ end
44
+
45
+ hash64.each do |key, value|
46
+ it 'returns correct hash' do
47
+ expect(XXhash.xxh64_stream(StringIO.new(key[0]), key[1])).to eq(value)
48
+ end
49
+ end
50
+
51
+ it 'returns same hash for streamed files' do
52
+ h1 = XXhash.xxh64(File.read(__FILE__), 123)
53
+ h2 = XXhash.xxh64_stream(File.open(__FILE__), 123)
54
+ expect(h1).to eq(h2)
32
55
  end
33
56
  end
34
57
  end
metadata CHANGED
@@ -1,62 +1,55 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: ruby-xxHash
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.1
5
- prerelease:
4
+ version: 0.3.0
6
5
  platform: ruby
7
6
  authors:
8
7
  - Justin W Smith
9
8
  autorequire:
10
9
  bindir: bin
11
10
  cert_chain: []
12
- date: 2014-03-11 00:00:00.000000000 Z
11
+ date: 2014-12-09 00:00:00.000000000 Z
13
12
  dependencies:
14
13
  - !ruby/object:Gem::Dependency
15
14
  name: bundler
16
15
  requirement: !ruby/object:Gem::Requirement
17
- none: false
18
16
  requirements:
19
- - - ~>
17
+ - - "~>"
20
18
  - !ruby/object:Gem::Version
21
19
  version: '1.3'
22
20
  type: :development
23
21
  prerelease: false
24
22
  version_requirements: !ruby/object:Gem::Requirement
25
- none: false
26
23
  requirements:
27
- - - ~>
24
+ - - "~>"
28
25
  - !ruby/object:Gem::Version
29
26
  version: '1.3'
30
27
  - !ruby/object:Gem::Dependency
31
28
  name: rake
32
29
  requirement: !ruby/object:Gem::Requirement
33
- none: false
34
30
  requirements:
35
- - - ! '>='
31
+ - - ">="
36
32
  - !ruby/object:Gem::Version
37
33
  version: '0'
38
34
  type: :development
39
35
  prerelease: false
40
36
  version_requirements: !ruby/object:Gem::Requirement
41
- none: false
42
37
  requirements:
43
- - - ! '>='
38
+ - - ">="
44
39
  - !ruby/object:Gem::Version
45
40
  version: '0'
46
41
  - !ruby/object:Gem::Dependency
47
42
  name: rspec
48
43
  requirement: !ruby/object:Gem::Requirement
49
- none: false
50
44
  requirements:
51
- - - ! '>='
45
+ - - ">="
52
46
  - !ruby/object:Gem::Version
53
47
  version: '0'
54
48
  type: :development
55
49
  prerelease: false
56
50
  version_requirements: !ruby/object:Gem::Requirement
57
- none: false
58
51
  requirements:
59
- - - ! '>='
52
+ - - ">="
60
53
  - !ruby/object:Gem::Version
61
54
  version: '0'
62
55
  description: A pure Ruby implementation of xxhash.
@@ -66,43 +59,46 @@ executables: []
66
59
  extensions: []
67
60
  extra_rdoc_files: []
68
61
  files:
69
- - .gitignore
62
+ - ".gitignore"
70
63
  - Gemfile
71
64
  - LICENSE.txt
72
65
  - README.md
73
66
  - Rakefile
74
67
  - lib/ruby-xxhash.rb
75
68
  - lib/ruby-xxhash/version.rb
69
+ - lib/ruby-xxhash32.rb
70
+ - lib/ruby-xxhash64.rb
76
71
  - ruby-xxHash.gemspec
77
- - spec/results.yaml
72
+ - spec/results32.yaml
73
+ - spec/results64.yaml
78
74
  - spec/spec_helper.rb
79
75
  - spec/xxhash_spec.rb
80
76
  homepage: https://github.com/justinwsmith/ruby-xxhash
81
77
  licenses:
82
78
  - MIT
79
+ metadata: {}
83
80
  post_install_message:
84
81
  rdoc_options: []
85
82
  require_paths:
86
83
  - lib
87
84
  required_ruby_version: !ruby/object:Gem::Requirement
88
- none: false
89
85
  requirements:
90
- - - ! '>='
86
+ - - ">="
91
87
  - !ruby/object:Gem::Version
92
88
  version: '0'
93
89
  required_rubygems_version: !ruby/object:Gem::Requirement
94
- none: false
95
90
  requirements:
96
- - - ! '>='
91
+ - - ">="
97
92
  - !ruby/object:Gem::Version
98
93
  version: '0'
99
94
  requirements: []
100
95
  rubyforge_project:
101
- rubygems_version: 1.8.23
96
+ rubygems_version: 2.2.2
102
97
  signing_key:
103
- specification_version: 3
98
+ specification_version: 4
104
99
  summary: A pure Ruby implementation of xxhash.
105
100
  test_files:
106
- - spec/results.yaml
101
+ - spec/results32.yaml
102
+ - spec/results64.yaml
107
103
  - spec/spec_helper.rb
108
104
  - spec/xxhash_spec.rb