From 28de409f774394242d835610bda1df98c44dea22 Mon Sep 17 00:00:00 2001 From: Technion Date: Fri, 9 Apr 2021 18:44:53 +1000 Subject: [PATCH 01/34] Allow p_cost to be set - implements #42 --- README.md | 3 +-- lib/argon2.rb | 5 ++++- lib/argon2/ffi_engine.rb | 8 ++++---- test/api_test.rb | 6 ++++-- test/error_test.rb | 8 ++++---- test/low_level_test.rb | 18 ++++++++++++------ 6 files changed, 29 insertions(+), 19 deletions(-) diff --git a/README.md b/README.md index 263c3ea..03d36b3 100644 --- a/README.md +++ b/README.md @@ -17,7 +17,6 @@ This project has several key tenets to its design: * Errors from the C interface are raised as Exceptions. There are a lot of exception classes, but they tend to relate to things like very broken input, and code bugs. Calls to this library should generally not require a rescue. * Test suites should aim for 100% code coverage. * Default work values should not be considered constants. I will increase them from time to time. -* Not exposing the threads parameter is a design choice. I believe there is significant risk, and minimal gain in using a value other than '1'. Four threads on a four core box completely ties up the entire server to process one user logon. If you want more security, increase m_cost. * Many Rubocop errors have been disabled, but any commit should avoid new alerts or demonstrate their necessity. ## Usage @@ -31,7 +30,7 @@ require 'argon2' To generate a hash using specific time and memory cost: ```ruby -hasher = Argon2::Password.new(t_cost: 2, m_cost: 16) +hasher = Argon2::Password.new(t_cost: 2, m_cost: 16, p_cost: 1) hasher.create("password") => "$argon2i$v=19$m=65536,t=2,p=1$jL7lLEAjDN+pY2cG1N8D2g$iwj1ueduCvm6B9YVjBSnAHu+6mKzqGmDW745ALR38Uo" ``` diff --git a/lib/argon2.rb b/lib/argon2.rb index 2d3ba7c..ed69f78 100644 --- a/lib/argon2.rb +++ b/lib/argon2.rb @@ -16,6 +16,9 @@ def initialize(options = {}) @m_cost = options[:m_cost] || 16 raise ArgonHashFail, "Invalid m_cost" if @m_cost < 1 || @m_cost > 31 + @p_cost = options[:p_cost] || 1 + raise ArgonHashFail, "Invalid p_cost" if @p_cost < 1 || @p_cost > 8 + @salt = options[:salt_do_not_supply] || Engine.saltgen @secret = options[:secret] end @@ -25,7 +28,7 @@ def create(pass) pass.is_a?(String) Argon2::Engine.hash_argon2id_encode( - pass, @salt, @t_cost, @m_cost, @secret) + pass, @salt, @t_cost, @m_cost, @p_cost, @secret) end # Helper class, just creates defaults and calls hash() diff --git a/lib/argon2/ffi_engine.rb b/lib/argon2/ffi_engine.rb index 7258042..b41d055 100644 --- a/lib/argon2/ffi_engine.rb +++ b/lib/argon2/ffi_engine.rb @@ -62,13 +62,13 @@ def self.hash_argon2i(password, salt, t_cost, m_cost, out_len = nil) result.unpack('H*').join end - def self.hash_argon2id(password, salt, t_cost, m_cost, out_len = nil) + def self.hash_argon2id(password, salt, t_cost, m_cost, p_cost, out_len = nil) out_len = (out_len || Constants::OUT_LEN).to_i raise ArgonHashFail, "Invalid output length" if out_len < 1 result = '' FFI::MemoryPointer.new(:char, out_len) do |buffer| - ret = Ext.argon2id_hash_raw(t_cost, 1 << m_cost, 1, password, + ret = Ext.argon2id_hash_raw(t_cost, 1 << m_cost, p_cost, password, password.length, salt, salt.length, buffer, out_len) raise ArgonHashFail, ERRORS[ret.abs] unless ret.zero? @@ -78,7 +78,7 @@ def self.hash_argon2id(password, salt, t_cost, m_cost, out_len = nil) result.unpack('H*').join end - def self.hash_argon2id_encode(password, salt, t_cost, m_cost, secret) + def self.hash_argon2id_encode(password, salt, t_cost, m_cost, p_cost, secret) result = '' secretlen = secret.nil? ? 0 : secret.bytesize passwordlen = password.nil? ? 0 : password.bytesize @@ -87,7 +87,7 @@ def self.hash_argon2id_encode(password, salt, t_cost, m_cost, secret) FFI::MemoryPointer.new(:char, Constants::ENCODE_LEN) do |buffer| ret = Ext.argon2_wrap(buffer, password, passwordlen, salt, salt.length, t_cost, (1 << m_cost), - 1, secret, secretlen) + p_cost, secret, secretlen) raise ArgonHashFail, ERRORS[ret.abs] unless ret.zero? result = buffer.read_string(Constants::ENCODE_LEN) diff --git a/test/api_test.rb b/test/api_test.rb index cd299a2..575b5bd 100644 --- a/test/api_test.rb +++ b/test/api_test.rb @@ -5,7 +5,7 @@ module Argon2 # Simple stub to facilitate testing these variables class Password - attr_accessor :t_cost, :m_cost, :secret + attr_accessor :t_cost, :m_cost, :p_cost, :secret end end @@ -15,14 +15,16 @@ def test_create_default assert_instance_of Argon2::Password, pass assert_equal 16, pass.m_cost assert_equal 2, pass.t_cost + assert_equal 1, pass.p_cost assert_nil pass.secret end def test_create_args - assert pass = Argon2::Password.new(t_cost: 4, m_cost: 12) + assert pass = Argon2::Password.new(t_cost: 4, m_cost: 12, p_cost: 4) assert_instance_of Argon2::Password, pass assert_equal 12, pass.m_cost assert_equal 4, pass.t_cost + assert_equal 4, pass.p_cost assert_nil pass.secret end diff --git a/test/error_test.rb b/test/error_test.rb index be87dbb..479466b 100644 --- a/test/error_test.rb +++ b/test/error_test.rb @@ -5,27 +5,27 @@ class Argon2ErrorTest < Minitest::Test def test_ffi_fail assert_raises Argon2::ArgonHashFail do - Argon2::Engine.hash_argon2i("password", "somesalt\0\0\0\0\0\0\0\0", 2, 1) + Argon2::Engine.hash_argon2i("password", "somesalt\0\0\0\0\0\0\0\0", 2, 1, 1) end end def test_memory_too_small assert_raises Argon2::ArgonHashFail do Argon2::Engine.hash_argon2id_encode("password", - "somesalt\0\0\0\0\0\0\0\0", 2, 1, nil) + "somesalt\0\0\0\0\0\0\0\0", 2, 1, 1, nil) end end def test_salt_size assert_raises Argon2::ArgonHashFail do - Argon2::Engine.hash_argon2id_encode("password", "somesalt", 2, 16, nil) + Argon2::Engine.hash_argon2id_encode("password", "somesalt", 2, 16, 1, nil) end end def test_passwd_null assert_raises Argon2::ArgonHashFail do Argon2::Engine.hash_argon2id_encode(nil, "somesalt\0\0\0\0\0\0\0\0", 2, - 16, nil) + 16, 1, nil) end end end diff --git a/test/low_level_test.rb b/test/low_level_test.rb index d62eead..f5c8741 100644 --- a/test/low_level_test.rb +++ b/test/low_level_test.rb @@ -43,30 +43,34 @@ def test_ffi_vector '85d58a069b81f7606dc772810d00496d' assert_equal Argon2::Engine.hash_argon2id( - "password", "somesaltsomesalt", 2, 16), + "password", "somesaltsomesalt", 2, 16, 1), 'fc33b78139231d34b71626bd6245c1d72efa190ad605c3d8166a72adcedfa2c2' end def test_encoded_hash assert_equal Argon2::Engine.hash_argon2id_encode( - "password", "somesalt\0\0\0\0\0\0\0\0", 2, 16, nil), + "password", "somesalt\0\0\0\0\0\0\0\0", 2, 16, 1, nil), '$argon2id$v=19$m=65536,t=2,p=1$c29tZXNhbHQAAAAAAAAAAA$syf8TzB9pvMIGtFhvRATHW1nX43iP+FLaaTXnqpyMrY' assert_equal Argon2::Engine.hash_argon2id_encode( - "password", "somesalt\0\0\0\0\0\0\0\0", 2, 8, nil), + "password", "somesalt\0\0\0\0\0\0\0\0", 2, 8, 1, nil), '$argon2id$v=19$m=256,t=2,p=1$c29tZXNhbHQAAAAAAAAAAA$TCsNUutWgv3lowstIasFJbdiamKiq8qPUdz2wSvQ4rw' assert_equal Argon2::Engine.hash_argon2id_encode( - "password", "somesalt\0\0\0\0\0\0\0\0", 1, 16, nil), + "password", "somesalt\0\0\0\0\0\0\0\0", 1, 16, 1, nil), '$argon2id$v=19$m=65536,t=1,p=1$c29tZXNhbHQAAAAAAAAAAA$b7sLmBJ4YGj/yOjMnUDWC1dvrtZr7EPdMT6zB9Fq0pk' assert_equal Argon2::Engine.hash_argon2id_encode( - "differentpassword", "somesalt\0\0\0\0\0\0\0\0", 2, 16, nil), + "differentpassword", "somesalt\0\0\0\0\0\0\0\0", 2, 16, 1, nil), '$argon2id$v=19$m=65536,t=2,p=1$c29tZXNhbHQAAAAAAAAAAA$0bDR2fpiZutijzxlxrjLnqnCSmtG1/reR4QNcavfKLk' assert_equal Argon2::Engine.hash_argon2id_encode( - "password", "diffsalt\0\0\0\0\0\0\0\0", 2, 16, nil), + "password", "diffsalt\0\0\0\0\0\0\0\0", 2, 16, 1, nil), '$argon2id$v=19$m=65536,t=2,p=1$ZGlmZnNhbHQAAAAAAAAAAA$vm1qQXZQ+/MgT2Y+Go7XnxtA9dJz3wotjfg0itOgKlY' + + assert_equal Argon2::Engine.hash_argon2id_encode( + "password", "somesalt\0\0\0\0\0\0\0\0", 2, 8, 2, nil), + '$argon2id$v=19$m=256,t=2,p=2$c29tZXNhbHQAAAAAAAAAAA$Q221Riroi3JIY9jaA0mEj0Pwmm2N02LSpV8jbkU35vQ' end def test_verify @@ -78,5 +82,7 @@ def test_verify refute Argon2::Engine.argon2_verify("notword", "$argon2id$v=19$m=65536,t=2,p=1$c29tZXNhbHQ$CTFhFdXPJO1aFaMaO6Mm5c8y7cJHAph8ArZWb2GRPPc", nil) assert Argon2::Engine.argon2_verify("password", "$argon2d$v=19$m=65536,t=2,p=1$YzI5dFpYTmhiSFFBQUFBQUFBQUFBQQ$Jxy74cswY2mq9y+u+iJcJy8EqOp4t/C7DWDzGwGB3IM", nil) refute Argon2::Engine.argon2_verify("notword", "$argon2d$v=19$m=65536,t=2,p=1$YzI5dFpYTmhiSFFBQUFBQUFBQUFBQQ$Jxy74cswY2mq9y+u+iJcJy8EqOp4t/C7DWDzGwGB3IM", nil) + assert Argon2::Engine.argon2_verify("password", "$argon2id$v=19$m=65536,t=2,p=2$xTwU4uxw28aTQPi9f8Cx6Q$9VoZS0TrgUmnBtkcHk0klTywH1NUPn2vbrLfiDpyY4M", nil) + refute Argon2::Engine.argon2_verify("notword", "$argon2id$v=19$m=65536,t=2,p=2$xTwU4uxw28aTQPi9f8Cx6Q$9VoZS0TrgUmnBtkcHk0klTywH1NUPn2vbrLfiDpyY4M", nil) end end From f053f2b18ef18fc1911e89a29289147bf5cc9709 Mon Sep 17 00:00:00 2001 From: Technion Date: Fri, 9 Apr 2021 18:51:15 +1000 Subject: [PATCH 02/34] Updated for Rubocop rules. Keep excluding low level functions where appropriate - ties to C aren't normal Ruby --- .rubocop.yml | 30 +++++++++++++++++++++++++++++- Steepfile | 2 ++ 2 files changed, 31 insertions(+), 1 deletion(-) diff --git a/.rubocop.yml b/.rubocop.yml index 6f8032e..1ca9e24 100644 --- a/.rubocop.yml +++ b/.rubocop.yml @@ -7,6 +7,11 @@ Metrics/CyclomaticComplexity: Metrics/PerceivedComplexity: Enabled: false +Metrics/ParameterLists: + Max: 5 + Exclude: + - 'lib/argon2/ffi_engine.rb' + Layout/LineLength: Max: 160 Exclude: @@ -205,4 +210,27 @@ Style/RedundantArgument: # (new in 1.4) Enabled: true Style/SwapValues: # (new in 1.1) Enabled: true - +Gemspec/DateAssignment: # (new in 1.10) + Enabled: true +Lint/DeprecatedConstants: # (new in 1.8) + Enabled: true +Lint/LambdaWithoutLiteralBlock: # (new in 1.8) + Enabled: true +Lint/NumberedParameterAssignment: # (new in 1.9) + Enabled: true +Lint/OrAssignmentToConstant: # (new in 1.9) + Enabled: true +Lint/RedundantDirGlobSort: # (new in 1.8) + Enabled: true +Lint/SymbolConversion: # (new in 1.9) + Enabled: true +Lint/TripleQuotes: # (new in 1.9) + Enabled: true +Style/EndlessMethod: # (new in 1.8) + Enabled: true +Style/HashConversion: # (new in 1.10) + Enabled: true +Style/IfWithBooleanLiteralBranches: # (new in 1.9) + Enabled: true +Style/StringChars: # (new in 1.12) + Enabled: true diff --git a/Steepfile b/Steepfile index 01dfa43..981ab7f 100644 --- a/Steepfile +++ b/Steepfile @@ -1,3 +1,5 @@ +# frozen_string_literal: true + target :lib do signature "sig" From 28b096b31af37cd76981a63b2543da31824727b1 Mon Sep 17 00:00:00 2001 From: Technion Date: Fri, 9 Apr 2021 18:51:55 +1000 Subject: [PATCH 03/34] Added type for p_cost --- argon2.gemspec | 1 + sig/argon2.rbs | 1 + 2 files changed, 2 insertions(+) diff --git a/argon2.gemspec b/argon2.gemspec index a965d65..4a30eee 100644 --- a/argon2.gemspec +++ b/argon2.gemspec @@ -31,5 +31,6 @@ Gem::Specification.new do |spec| spec.add_development_dependency "rubocop", '~> 1.7' spec.add_development_dependency "simplecov", '~> 0.20' spec.add_development_dependency "simplecov-lcov", '~> 0.8' + spec.add_development_dependency "steep" spec.extensions << 'ext/argon2_wrap/extconf.rb' end diff --git a/sig/argon2.rbs b/sig/argon2.rbs index 8da18d9..322eb31 100644 --- a/sig/argon2.rbs +++ b/sig/argon2.rbs @@ -3,6 +3,7 @@ module Argon2 class Password @t_cost: Integer @m_cost: Integer + @p_cost: Integer @salt: nil | String @secret: nil | String From 59a3b8389a86220622407a5a4d2a558a68c8ab86 Mon Sep 17 00:00:00 2001 From: Technion Date: Fri, 9 Apr 2021 19:03:05 +1000 Subject: [PATCH 04/34] Updated master upstream --- ext/phc-winner-argon2 | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ext/phc-winner-argon2 b/ext/phc-winner-argon2 index 440ceb9..16d3df6 160000 --- a/ext/phc-winner-argon2 +++ b/ext/phc-winner-argon2 @@ -1 +1 @@ -Subproject commit 440ceb9612d5a20997e3e12728542df2de713ca4 +Subproject commit 16d3df698db2486dde480b09a732bf9bf48599f9 From b9e5c79830d97b0577eb7851b7bc359a06cd0d22 Mon Sep 17 00:00:00 2001 From: Technion Date: Fri, 9 Apr 2021 09:15:37 +0000 Subject: [PATCH 05/34] Fix #33 as best as possible with a cert. --- argon2.gemspec | 3 +++ certs/technion.pem | 25 +++++++++++++++++++++++++ ext/phc-winner-argon2 | 2 +- 3 files changed, 29 insertions(+), 1 deletion(-) create mode 100644 certs/technion.pem diff --git a/argon2.gemspec b/argon2.gemspec index 4a30eee..acfa8f5 100644 --- a/argon2.gemspec +++ b/argon2.gemspec @@ -33,4 +33,7 @@ Gem::Specification.new do |spec| spec.add_development_dependency "simplecov-lcov", '~> 0.8' spec.add_development_dependency "steep" spec.extensions << 'ext/argon2_wrap/extconf.rb' + + spec.cert_chain = ['certs/technion.pem'] + spec.signing_key = File.expand_path("~/.ssh/gem-private_key.pem") if $0 =~ /gem\z/ end diff --git a/certs/technion.pem b/certs/technion.pem new file mode 100644 index 0000000..b88f6d0 --- /dev/null +++ b/certs/technion.pem @@ -0,0 +1,25 @@ +-----BEGIN CERTIFICATE----- +MIIEQDCCAqigAwIBAgIBATANBgkqhkiG9w0BAQsFADAlMSMwIQYDVQQDDBp0ZWNo +bmlvbi9EQz1sb2x3YXJlL0RDPW5ldDAeFw0yMTA0MDkwOTA0MTBaFw0yMjA0MDkw +OTA0MTBaMCUxIzAhBgNVBAMMGnRlY2huaW9uL0RDPWxvbHdhcmUvREM9bmV0MIIB +ojANBgkqhkiG9w0BAQEFAAOCAY8AMIIBigKCAYEAriyPpPsQ6f9cporrUnEdlI4y +/+RwAKND/ZhWCC7w7y2Md5kpQSsF6paF3DerF5WC/nmLlaNW8rniUI0beOaY1NdH +Oo5/YZWMDULp/WNAu3obfd4S0yJzxJyuvgFLGyw/qYQFKAqekA4ZybU+8JAkJTmX +ev7jEMOszjdn2jKilInQIBE0C5Na9jJamV6D21b+tiEEatW0JF2N1OhaibkPbFV0 +8LkpuiBfPNug6bzgA4BL2Skk9++8PBzD4Bs3UhSCbwztlYhZd8asD23nNQJXlczs +7GIm2exMzoLdcLG/KIEpcPmJo/pdHQeJY8o5FetpeZyWgOEpTCmVe3IAWIWNYwGy +KYVwrqE1/B3H7uMyzOKivrNuSbFNLsm7FT06tp5Ka2nU5lIfWpU+J/dkOLqlm6Rv +aS4uAqQd/lShRvvbOfHynV6JogLtBlETy5l1lE3+Mcab659MC/mntuT0Xam1f9Bb +UerOJi3f9W+qD6kg3yMr3ugnDYO/UfnUQvN0Zc7hAgMBAAGjezB5MAkGA1UdEwQC +MAAwCwYDVR0PBAQDAgSwMB0GA1UdDgQWBBSMFwaH0t75TudFUk6Cc3NN7AFnhzAf +BgNVHREEGDAWgRR0ZWNobmlvbkBsb2x3YXJlLm5ldDAfBgNVHRIEGDAWgRR0ZWNo +bmlvbkBsb2x3YXJlLm5ldDANBgkqhkiG9w0BAQsFAAOCAYEABpZ9DRj7Nl+2hdaA +Ize78tBWRzCygHmSweACzUHYosHYKF6nbTLuF3fzlpXEjjt2oc+FSpAspysihypX +2qPb65jUvo4t8zuR64Fb+r4MD86U/qfdWKoDTmhYKqGYrGT1Azls/6SZ/eZvhmaU +CVhcXv08OpxbK477OwmFO0d7L/w8A0rRCDwEXXaeIkPKeYjBunpf80ijxrC9HuuM +8HV1Qvv07uG91OEZX42lE3Mztj8ecAKl1PMKF3AZ8S/NBFbGWv3E+ELLx+2D4OVL +qcr0EVJX1tyjC8faFBb804P5WF1KwDjwE/4PS4nIM2nVdtXT48fISHoc+Hxe2UuN +FWTM2kdrRq8nA9EL/KqsIqBVj9+rxaRX14hslnc1x0870xZsWItzJRXRoleYwi5s +SJjN24jinuP8qd9TwHF/wbIZOetHLCXD9Bey3kDmk2nAIB2NyR/SIiuA9hVE3LUy +5w7IGyvd7+3qqApuWBCSKPgGfrv2GA+eDntVYC33szP+58M0 +-----END CERTIFICATE----- diff --git a/ext/phc-winner-argon2 b/ext/phc-winner-argon2 index 16d3df6..440ceb9 160000 --- a/ext/phc-winner-argon2 +++ b/ext/phc-winner-argon2 @@ -1 +1 @@ -Subproject commit 16d3df698db2486dde480b09a732bf9bf48599f9 +Subproject commit 440ceb9612d5a20997e3e12728542df2de713ca4 From dd3c5155c85f621365a5a6ec9bb92d33650c18a0 Mon Sep 17 00:00:00 2001 From: Technion Date: Fri, 9 Apr 2021 10:21:00 +0000 Subject: [PATCH 06/34] Described signing. Documented version bump. --- Changelog.md | 5 +++++ README.md | 9 +++++++++ argon2.gemspec | 2 +- certs/technion.pem | 0 lib/argon2/version.rb | 2 +- 5 files changed, 16 insertions(+), 2 deletions(-) mode change 100644 => 100755 certs/technion.pem diff --git a/Changelog.md b/Changelog.md index 5810c28..8681de9 100644 --- a/Changelog.md +++ b/Changelog.md @@ -1,3 +1,8 @@ +## v2.1.0: 2021-04-09 +- Expose "lanes" (p_cost) parameter +- Sign gem +- Ship RBS type signatures + ## v2.0.3: 2021-01-02 - Address potential memory leak. Unlikely to be exploitable. diff --git a/README.md b/README.md index 03d36b3..2c149cc 100644 --- a/README.md +++ b/README.md @@ -85,6 +85,15 @@ These tools will need to be installed manually at this time and will be added to ## Version 2.0 - Argon 2id Version 2.x upwards will now default to the Argon2id hash format. This is consistent with current recommendations regarding Argon2 usage. It remains capable of verifying existing hashes. +## Gem signing +Given the unsigned dependencies and key distribution difficulties, signing on this gem adds little security value. If you'd like to use the signed version however, import the key like this: + +```sh +gem cert --add <(curl -Ls https://raw.githubusercontent.com/technion/ruby-argon2/master/certs/technion.pem) +gem install argon2 -P MediumSecurity +``` +You will not be able to use HighSecurity. + ## Important notes regarding version 1.0 upgrade Version 1.0.0 included a major version bump over 0.1.4 due to several breaking changes. The first of these was an API change, which you can read the background on [here](https://github.com/technion/ruby-argon2/issues/9). diff --git a/argon2.gemspec b/argon2.gemspec index acfa8f5..8e1ed01 100644 --- a/argon2.gemspec +++ b/argon2.gemspec @@ -31,7 +31,7 @@ Gem::Specification.new do |spec| spec.add_development_dependency "rubocop", '~> 1.7' spec.add_development_dependency "simplecov", '~> 0.20' spec.add_development_dependency "simplecov-lcov", '~> 0.8' - spec.add_development_dependency "steep" + spec.add_development_dependency "steep", "~> 0.43.1" spec.extensions << 'ext/argon2_wrap/extconf.rb' spec.cert_chain = ['certs/technion.pem'] diff --git a/certs/technion.pem b/certs/technion.pem old mode 100644 new mode 100755 diff --git a/lib/argon2/version.rb b/lib/argon2/version.rb index 3ff3d13..7729e22 100644 --- a/lib/argon2/version.rb +++ b/lib/argon2/version.rb @@ -3,5 +3,5 @@ # Standard Gem version constant. module Argon2 - VERSION = "2.0.3" + VERSION = "2.1.0" end From 411016852bde0976ff2bb8484b3fc2c82edd2a0b Mon Sep 17 00:00:00 2001 From: Technion Date: Fri, 9 Apr 2021 10:25:20 +0000 Subject: [PATCH 07/34] Last commit dropped Ruby 2.5 support. This is EOL. --- .github/workflows/ruby.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/ruby.yml b/.github/workflows/ruby.yml index 9a531a9..ccc11b1 100644 --- a/.github/workflows/ruby.yml +++ b/.github/workflows/ruby.yml @@ -8,7 +8,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - ruby-version: ['3.0', 2.7, 2.5] + ruby-version: ['3.0', 2.7] steps: - uses: actions/checkout@v2 From 71eb10d28253c7c8f6f57774adaf328c1eda6287 Mon Sep 17 00:00:00 2001 From: Technion Date: Fri, 9 Apr 2021 10:43:04 +0000 Subject: [PATCH 08/34] Revert "Described signing. Documented version bump." See #33 This reverts commit dd3c5155c85f621365a5a6ec9bb92d33650c18a0. --- Changelog.md | 5 ----- README.md | 9 --------- argon2.gemspec | 2 +- certs/technion.pem | 0 lib/argon2/version.rb | 2 +- 5 files changed, 2 insertions(+), 16 deletions(-) mode change 100755 => 100644 certs/technion.pem diff --git a/Changelog.md b/Changelog.md index 8681de9..5810c28 100644 --- a/Changelog.md +++ b/Changelog.md @@ -1,8 +1,3 @@ -## v2.1.0: 2021-04-09 -- Expose "lanes" (p_cost) parameter -- Sign gem -- Ship RBS type signatures - ## v2.0.3: 2021-01-02 - Address potential memory leak. Unlikely to be exploitable. diff --git a/README.md b/README.md index 2c149cc..03d36b3 100644 --- a/README.md +++ b/README.md @@ -85,15 +85,6 @@ These tools will need to be installed manually at this time and will be added to ## Version 2.0 - Argon 2id Version 2.x upwards will now default to the Argon2id hash format. This is consistent with current recommendations regarding Argon2 usage. It remains capable of verifying existing hashes. -## Gem signing -Given the unsigned dependencies and key distribution difficulties, signing on this gem adds little security value. If you'd like to use the signed version however, import the key like this: - -```sh -gem cert --add <(curl -Ls https://raw.githubusercontent.com/technion/ruby-argon2/master/certs/technion.pem) -gem install argon2 -P MediumSecurity -``` -You will not be able to use HighSecurity. - ## Important notes regarding version 1.0 upgrade Version 1.0.0 included a major version bump over 0.1.4 due to several breaking changes. The first of these was an API change, which you can read the background on [here](https://github.com/technion/ruby-argon2/issues/9). diff --git a/argon2.gemspec b/argon2.gemspec index 8e1ed01..acfa8f5 100644 --- a/argon2.gemspec +++ b/argon2.gemspec @@ -31,7 +31,7 @@ Gem::Specification.new do |spec| spec.add_development_dependency "rubocop", '~> 1.7' spec.add_development_dependency "simplecov", '~> 0.20' spec.add_development_dependency "simplecov-lcov", '~> 0.8' - spec.add_development_dependency "steep", "~> 0.43.1" + spec.add_development_dependency "steep" spec.extensions << 'ext/argon2_wrap/extconf.rb' spec.cert_chain = ['certs/technion.pem'] diff --git a/certs/technion.pem b/certs/technion.pem old mode 100755 new mode 100644 diff --git a/lib/argon2/version.rb b/lib/argon2/version.rb index 7729e22..3ff3d13 100644 --- a/lib/argon2/version.rb +++ b/lib/argon2/version.rb @@ -3,5 +3,5 @@ # Standard Gem version constant. module Argon2 - VERSION = "2.1.0" + VERSION = "2.0.3" end From 25f2dccfe4e8aea7d1cd03bbeef16e7f40a6fee3 Mon Sep 17 00:00:00 2001 From: Technion Date: Fri, 9 Apr 2021 10:44:08 +0000 Subject: [PATCH 09/34] "Fix #33 as best as possible with a cert." This reverts commit b9e5c79830d97b0577eb7851b7bc359a06cd0d22. --- argon2.gemspec | 3 --- certs/technion.pem | 25 ------------------------- ext/phc-winner-argon2 | 2 +- 3 files changed, 1 insertion(+), 29 deletions(-) delete mode 100644 certs/technion.pem diff --git a/argon2.gemspec b/argon2.gemspec index acfa8f5..4a30eee 100644 --- a/argon2.gemspec +++ b/argon2.gemspec @@ -33,7 +33,4 @@ Gem::Specification.new do |spec| spec.add_development_dependency "simplecov-lcov", '~> 0.8' spec.add_development_dependency "steep" spec.extensions << 'ext/argon2_wrap/extconf.rb' - - spec.cert_chain = ['certs/technion.pem'] - spec.signing_key = File.expand_path("~/.ssh/gem-private_key.pem") if $0 =~ /gem\z/ end diff --git a/certs/technion.pem b/certs/technion.pem deleted file mode 100644 index b88f6d0..0000000 --- a/certs/technion.pem +++ /dev/null @@ -1,25 +0,0 @@ ------BEGIN CERTIFICATE----- -MIIEQDCCAqigAwIBAgIBATANBgkqhkiG9w0BAQsFADAlMSMwIQYDVQQDDBp0ZWNo -bmlvbi9EQz1sb2x3YXJlL0RDPW5ldDAeFw0yMTA0MDkwOTA0MTBaFw0yMjA0MDkw -OTA0MTBaMCUxIzAhBgNVBAMMGnRlY2huaW9uL0RDPWxvbHdhcmUvREM9bmV0MIIB -ojANBgkqhkiG9w0BAQEFAAOCAY8AMIIBigKCAYEAriyPpPsQ6f9cporrUnEdlI4y -/+RwAKND/ZhWCC7w7y2Md5kpQSsF6paF3DerF5WC/nmLlaNW8rniUI0beOaY1NdH -Oo5/YZWMDULp/WNAu3obfd4S0yJzxJyuvgFLGyw/qYQFKAqekA4ZybU+8JAkJTmX -ev7jEMOszjdn2jKilInQIBE0C5Na9jJamV6D21b+tiEEatW0JF2N1OhaibkPbFV0 -8LkpuiBfPNug6bzgA4BL2Skk9++8PBzD4Bs3UhSCbwztlYhZd8asD23nNQJXlczs -7GIm2exMzoLdcLG/KIEpcPmJo/pdHQeJY8o5FetpeZyWgOEpTCmVe3IAWIWNYwGy -KYVwrqE1/B3H7uMyzOKivrNuSbFNLsm7FT06tp5Ka2nU5lIfWpU+J/dkOLqlm6Rv -aS4uAqQd/lShRvvbOfHynV6JogLtBlETy5l1lE3+Mcab659MC/mntuT0Xam1f9Bb -UerOJi3f9W+qD6kg3yMr3ugnDYO/UfnUQvN0Zc7hAgMBAAGjezB5MAkGA1UdEwQC -MAAwCwYDVR0PBAQDAgSwMB0GA1UdDgQWBBSMFwaH0t75TudFUk6Cc3NN7AFnhzAf -BgNVHREEGDAWgRR0ZWNobmlvbkBsb2x3YXJlLm5ldDAfBgNVHRIEGDAWgRR0ZWNo -bmlvbkBsb2x3YXJlLm5ldDANBgkqhkiG9w0BAQsFAAOCAYEABpZ9DRj7Nl+2hdaA -Ize78tBWRzCygHmSweACzUHYosHYKF6nbTLuF3fzlpXEjjt2oc+FSpAspysihypX -2qPb65jUvo4t8zuR64Fb+r4MD86U/qfdWKoDTmhYKqGYrGT1Azls/6SZ/eZvhmaU -CVhcXv08OpxbK477OwmFO0d7L/w8A0rRCDwEXXaeIkPKeYjBunpf80ijxrC9HuuM -8HV1Qvv07uG91OEZX42lE3Mztj8ecAKl1PMKF3AZ8S/NBFbGWv3E+ELLx+2D4OVL -qcr0EVJX1tyjC8faFBb804P5WF1KwDjwE/4PS4nIM2nVdtXT48fISHoc+Hxe2UuN -FWTM2kdrRq8nA9EL/KqsIqBVj9+rxaRX14hslnc1x0870xZsWItzJRXRoleYwi5s -SJjN24jinuP8qd9TwHF/wbIZOetHLCXD9Bey3kDmk2nAIB2NyR/SIiuA9hVE3LUy -5w7IGyvd7+3qqApuWBCSKPgGfrv2GA+eDntVYC33szP+58M0 ------END CERTIFICATE----- diff --git a/ext/phc-winner-argon2 b/ext/phc-winner-argon2 index 440ceb9..16d3df6 160000 --- a/ext/phc-winner-argon2 +++ b/ext/phc-winner-argon2 @@ -1 +1 @@ -Subproject commit 440ceb9612d5a20997e3e12728542df2de713ca4 +Subproject commit 16d3df698db2486dde480b09a732bf9bf48599f9 From b89f08dfffaf160dffcda1f9163e2e3e31076c9a Mon Sep 17 00:00:00 2001 From: Technion Date: Fri, 9 Apr 2021 10:47:41 +0000 Subject: [PATCH 10/34] Setup for version 2.1.0 release --- Changelog.md | 4 ++++ argon2.gemspec | 2 +- ext/phc-winner-argon2 | 2 +- lib/argon2/version.rb | 2 +- 4 files changed, 7 insertions(+), 3 deletions(-) diff --git a/Changelog.md b/Changelog.md index 5810c28..5c6a850 100644 --- a/Changelog.md +++ b/Changelog.md @@ -1,3 +1,7 @@ +## v2.1.0: 2021-04-09 +- Introduce RBS types +- Expose p parameter + ## v2.0.3: 2021-01-02 - Address potential memory leak. Unlikely to be exploitable. diff --git a/argon2.gemspec b/argon2.gemspec index 4a30eee..923c12a 100644 --- a/argon2.gemspec +++ b/argon2.gemspec @@ -31,6 +31,6 @@ Gem::Specification.new do |spec| spec.add_development_dependency "rubocop", '~> 1.7' spec.add_development_dependency "simplecov", '~> 0.20' spec.add_development_dependency "simplecov-lcov", '~> 0.8' - spec.add_development_dependency "steep" + spec.add_development_dependency "steep", "~> 0.43.1" spec.extensions << 'ext/argon2_wrap/extconf.rb' end diff --git a/ext/phc-winner-argon2 b/ext/phc-winner-argon2 index 16d3df6..440ceb9 160000 --- a/ext/phc-winner-argon2 +++ b/ext/phc-winner-argon2 @@ -1 +1 @@ -Subproject commit 16d3df698db2486dde480b09a732bf9bf48599f9 +Subproject commit 440ceb9612d5a20997e3e12728542df2de713ca4 diff --git a/lib/argon2/version.rb b/lib/argon2/version.rb index 3ff3d13..7729e22 100644 --- a/lib/argon2/version.rb +++ b/lib/argon2/version.rb @@ -3,5 +3,5 @@ # Standard Gem version constant. module Argon2 - VERSION = "2.0.3" + VERSION = "2.1.0" end From 75cf7c81f8ff092178ef3e295cc5fa632367e7ab Mon Sep 17 00:00:00 2001 From: Josh Buker Date: Wed, 28 Apr 2021 00:04:34 -0700 Subject: [PATCH 11/34] Add hash format helpers (#47) * Add hash format helpers * Check hash validity before splitting * Simplify HashFormat test setup --- lib/argon2.rb | 4 ++-- lib/argon2/hash_format.rb | 49 +++++++++++++++++++++++++++++++++++++++ test/hash_format_test.rb | 45 +++++++++++++++++++++++++++++++++++ 3 files changed, 96 insertions(+), 2 deletions(-) create mode 100644 lib/argon2/hash_format.rb create mode 100644 test/hash_format_test.rb diff --git a/lib/argon2.rb b/lib/argon2.rb index ed69f78..7cece60 100644 --- a/lib/argon2.rb +++ b/lib/argon2.rb @@ -5,6 +5,7 @@ require 'argon2/version' require 'argon2/errors' require 'argon2/engine' +require 'argon2/hash_format' module Argon2 # Front-end API for the Argon2 module. @@ -37,9 +38,8 @@ def self.create(pass) argon2.create(pass) end - # Supports 1 and argon2id formats. def self.valid_hash?(hash) - /^\$argon2(id?|d).{,113}/ =~ hash + Argon2::HashFormat.valid_hash?(hash) end def self.verify_password(pass, hash, secret = nil) diff --git a/lib/argon2/hash_format.rb b/lib/argon2/hash_format.rb new file mode 100644 index 0000000..59023df --- /dev/null +++ b/lib/argon2/hash_format.rb @@ -0,0 +1,49 @@ +# frozen_string_literal: true + +module Argon2 + ## + # Get the values from an Argon2 compatible string. + # + class HashFormat + attr_reader :variant, :version, :t_cost, :m_cost, :p_cost, :salt, :checksum + + # FIXME: Reduce complexity/AbcSize + # rubocop:disable Metrics/AbcSize + def initialize(digest) + digest = digest.to_s unless digest.is_a?(String) + + raise Argon2::ArgonHashFail, 'Invalid Argon2 hash' unless self.class.valid_hash?(digest) + + _, variant, version, config, salt, checksum = digest.split('$') + # Regex magic to extract the values for each setting + version = /v=(\d+)/.match(version) + t_cost = /t=(\d+),/.match(config) + m_cost = /m=(\d+),/.match(config) + p_cost = /p=(\d+)/.match(config) + + # Make sure none of the values are missing + raise Argon2::ArgonHashFail, 'Invalid Argon2 version' if version.nil? + raise Argon2::ArgonHashFail, 'Invalid Argon2 time cost' if t_cost.nil? + raise Argon2::ArgonHashFail, 'Invalid Argon2 memory cost' if m_cost.nil? + raise Argon2::ArgonHashFail, 'Invalid Argon2 parallelism cost' if p_cost.nil? + + @variant = variant.to_str + @version = version[1].to_i + @t_cost = t_cost[1].to_i + @m_cost = m_cost[1].to_i + @p_cost = p_cost[1].to_i + @salt = salt.to_str + @checksum = checksum.to_str + end + # rubocop:enable Metrics/AbcSize + + ## + # Checks whether a given digest is a valid Argon2 hash. + # + # Supports 1 and argon2id formats. + # + def self.valid_hash?(digest) + /^\$argon2(id?|d).{,113}/ =~ digest + end + end +end diff --git a/test/hash_format_test.rb b/test/hash_format_test.rb new file mode 100644 index 0000000..ecea79b --- /dev/null +++ b/test/hash_format_test.rb @@ -0,0 +1,45 @@ +# frozen_string_literal: true + +require 'test_helper' + +class Argon2HashFormatTest < Minitest::Test + PASSWORD = 'My secret password' + OPTIONS = { + t_cost: 4, + m_cost: 12, + p_cost: 3 + }.freeze + + TEMP = Argon2::Password.new(OPTIONS) + DIGEST = TEMP.create(PASSWORD) + + def test_hash_format_variant + assert argon2 = Argon2::HashFormat.new(DIGEST) + + assert_equal 'argon2id', argon2.variant + end + + def test_hash_format_version + assert argon2 = Argon2::HashFormat.new(DIGEST) + + assert_equal 19, argon2.version + end + + def test_hash_format_t_cost + assert argon2 = Argon2::HashFormat.new(DIGEST) + + assert_equal OPTIONS[:t_cost], argon2.t_cost + end + + def test_hash_format_m_cost + assert argon2 = Argon2::HashFormat.new(DIGEST) + + assert_equal (2**OPTIONS[:m_cost]), argon2.m_cost + end + + def test_hash_format_p_cost + assert argon2 = Argon2::HashFormat.new(DIGEST) + + assert_equal OPTIONS[:p_cost], argon2.p_cost + end +end From d65c6e652c241b2970b4c56cc3ee22603db8f4f4 Mon Sep 17 00:00:00 2001 From: Josh Buker Date: Tue, 4 May 2021 02:24:45 -0700 Subject: [PATCH 12/34] Update Argon2::Password.create to support passing options (#49) --- lib/argon2.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/argon2.rb b/lib/argon2.rb index 7cece60..15426ec 100644 --- a/lib/argon2.rb +++ b/lib/argon2.rb @@ -33,8 +33,8 @@ def create(pass) end # Helper class, just creates defaults and calls hash() - def self.create(pass) - argon2 = Argon2::Password.new + def self.create(pass, options = {}) + argon2 = Argon2::Password.new(options) argon2.create(pass) end From ad6b30542ef313a1160de7a783ca968715de9e10 Mon Sep 17 00:00:00 2001 From: Josh Buker Date: Tue, 4 May 2021 02:27:06 -0700 Subject: [PATCH 13/34] Update Github Actions to test pull requests (#48) * Update bin files to allow easier setup/testing Updated the setup command to include the require commands for initializing the git submodules, as well as building the Argon2 C Library. Also added bin/test to run the C test suite as well. These were originally added to allow easy setup/testing in the Github Actions, but also make local dev on the wrapper easier as well. * Update Github Actions Added support for running actions against pull requests, as well as parallelism for the coveralls tests. * Update required ruby version to match supported versions --- .github/workflows/rubocop.yml | 16 ------- .github/workflows/ruby.yml | 78 ++++++++++++++++++++++++++--------- README.md | 16 +++---- argon2.gemspec | 2 + bin/console | 8 ++-- bin/setup | 8 +++- bin/test | 10 +++++ 7 files changed, 89 insertions(+), 49 deletions(-) delete mode 100644 .github/workflows/rubocop.yml create mode 100755 bin/test diff --git a/.github/workflows/rubocop.yml b/.github/workflows/rubocop.yml deleted file mode 100644 index 3deeaa7..0000000 --- a/.github/workflows/rubocop.yml +++ /dev/null @@ -1,16 +0,0 @@ -name: Rubocop - -# Run this workflow every time a new commit pushed to your repository -on: push - -jobs: - - rubocop: - name: Rubocopchecks - runs-on: ubuntu-latest - steps: - - name: Run Rubocop - uses: gimenete/rubocop-action@1.0 - env: - GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} - diff --git a/.github/workflows/ruby.yml b/.github/workflows/ruby.yml index ccc11b1..a622b3a 100644 --- a/.github/workflows/ruby.yml +++ b/.github/workflows/ruby.yml @@ -1,32 +1,70 @@ name: Test Suite -on: push +# Run against all commits and pull requests. +on: [ push, pull_request ] jobs: - test: + test_matrix: - runs-on: ubuntu-latest strategy: + fail-fast: false matrix: - ruby-version: ['3.0', 2.7] + os: + - ubuntu + - macos + ruby: + - 2.6 + - 2.7 + - 3.0 + - head + + runs-on: ${{ matrix.os }}-latest + + env: + TEST_CHECKS: 100 + + steps: + - uses: actions/checkout@v2 + - name: Set up Ruby + uses: ruby/setup-ruby@v1 + with: + ruby-version: ${{ matrix.ruby }} + bundler-cache: true + - name: Build Argon2 C library + run: bin/setup + - name: Test Argon2 C library + run: bin/test + - name: Run tests + run: bundle exec rake test + - name: Coveralls Parallel + uses: coverallsapp/github-action@master + with: + github-token: ${{ secrets.GITHUB_TOKEN }} + flag-name: run-${{ matrix.ruby-version }} + parallel: true + + rubocop: + + runs-on: ubuntu-latest steps: - uses: actions/checkout@v2 - - name: Set up Ruby ${{ matrix.ruby-version }} + - name: Set up Ruby uses: ruby/setup-ruby@v1 with: - ruby-version: ${{ matrix.ruby-version }} - - name: Install dependencies - run: bundle install - - name: Init submodules - run: git submodule update --init --recursive - - name: Build C library - run: bin/setup - - name: Test C library - run: cd ext/argon2_wrap/ && make test && cd ../.. - - name: Run tests - run: bundle exec rake - - name: Coveralls - uses: coverallsapp/github-action@master - with: - github-token: ${{ secrets.GITHUB_TOKEN }} + ruby-version: 3.0 + bundler-cache: true + - name: Run rubocop + run: bundle exec rake rubocop + + finish: + runs-on: ubuntu-latest + needs: [ test_matrix, rubocop ] + steps: + - name: Coveralls Finished + uses: coverallsapp/github-action@master + with: + github-token: ${{ secrets.GITHUB_TOKEN }} + parallel-finished: true + - name: Wait for status checks + run: echo "All Green!" diff --git a/README.md b/README.md index 03d36b3..ff72ec8 100644 --- a/README.md +++ b/README.md @@ -133,17 +133,19 @@ Any form of contribution is appreciated, however, please review [CONTRIBUTING.md ## Building locally/Tests -To build the gem locally, you will need to checkout the submodule and build it manually: +To build the gem locally, you will need to run the setup script: ```shell -git submodule update --init --recursive -bundle install -cd ext/argon2_wrap/ -make -cd ../.. +./bin/setup ``` -The test harness includes a property based test. To more strenuously perform this test, you can tune the iterations parameter: +You can test that the Argon2 C library was properly imported by running the C test suite: + +```shell +./bin/test +``` + +The ruby wrapper test suite includes a property based test. To more strenuously perform this test, you can tune the iterations parameter: ```shell TEST_CHECKS=10000 bundle exec rake test diff --git a/argon2.gemspec b/argon2.gemspec index 923c12a..b5d41b2 100644 --- a/argon2.gemspec +++ b/argon2.gemspec @@ -11,6 +11,8 @@ Gem::Specification.new do |spec| spec.authors = ["Technion"] spec.email = ["technion@lolware.net"] + spec.required_ruby_version = '>= 2.6.0' + spec.summary = 'Argon2 Password hashing binding' spec.description = 'Argon2 FFI binding' spec.homepage = 'https://github.com/technion/ruby-argon2' diff --git a/bin/console b/bin/console index f9a9ac5..8aff6b9 100755 --- a/bin/console +++ b/bin/console @@ -1,15 +1,15 @@ #!/usr/bin/env ruby # frozen_string_literal: true -require "bundler/setup" -require "argon2" +require 'bundler/setup' +require 'argon2' # You can add fixtures and/or initialization code here to make experimenting # with your gem easier. You can also use a different console, if you like. # (If you use this, don't forget to add pry to your Gemfile!) -# require "pry" +# require 'pry' # Pry.start -require "irb" +require 'irb' IRB.start diff --git a/bin/setup b/bin/setup index 5e24cd4..abc4e72 100755 --- a/bin/setup +++ b/bin/setup @@ -1,10 +1,14 @@ #!/bin/bash +# Exit the script immediately if a command fails set -euo pipefail +# Internal Field Separator IFS=$'\n\t' +# Initialize Git Submodules +git submodule update --init --recursive + +# Build the Argon2 C Library. Git submodules must be initialized first! bundle install cd ext/argon2_wrap/ make cd ../.. - -# Do any other automated setup that you need to do here diff --git a/bin/test b/bin/test new file mode 100755 index 0000000..9ed1ff7 --- /dev/null +++ b/bin/test @@ -0,0 +1,10 @@ +#!/bin/bash +# Exit the script immediately if a command fails +set -euo pipefail +# Internal Field Separator +IFS=$'\n\t' + +# Run the Argon2 C Library tests +cd ext/argon2_wrap/ +make test +cd ../.. From 8e3f0248eb5ca054a01b61e0ec49a57669e4ab65 Mon Sep 17 00:00:00 2001 From: Technion Date: Wed, 5 May 2021 13:35:21 +1000 Subject: [PATCH 14/34] Address potential API misuse. See #51. --- README.md | 1 - lib/argon2.rb | 7 +++++-- test/salt_reuse_test.rb | 19 +++++++++++++++++++ 3 files changed, 24 insertions(+), 3 deletions(-) create mode 100644 test/salt_reuse_test.rb diff --git a/README.md b/README.md index ff72ec8..51e3e56 100644 --- a/README.md +++ b/README.md @@ -42,7 +42,6 @@ hasher = Argon2::Password.new hasher.create("password") ``` -If you follow this pattern, it is important to create a new `Argon2::Password` every time you generate a hash, in order to ensure a unique salt. See [issue 23](https://github.com/technion/ruby-argon2/issues/23) for more information. Alternatively, use this shortcut: ```ruby diff --git a/lib/argon2.rb b/lib/argon2.rb index 15426ec..3429f68 100644 --- a/lib/argon2.rb +++ b/lib/argon2.rb @@ -20,7 +20,7 @@ def initialize(options = {}) @p_cost = options[:p_cost] || 1 raise ArgonHashFail, "Invalid p_cost" if @p_cost < 1 || @p_cost > 8 - @salt = options[:salt_do_not_supply] || Engine.saltgen + @salt_do_not_supply = options[:salt_do_not_supply] @secret = options[:secret] end @@ -28,8 +28,11 @@ def create(pass) raise ArgonHashFail, "Invalid password (expected string)" unless pass.is_a?(String) + # Ensure salt is freshly generated unless it was intentionally supplied. + salt = @salt_do_not_supply || Engine.saltgen + Argon2::Engine.hash_argon2id_encode( - pass, @salt, @t_cost, @m_cost, @p_cost, @secret) + pass, salt, @t_cost, @m_cost, @p_cost, @secret) end # Helper class, just creates defaults and calls hash() diff --git a/test/salt_reuse_test.rb b/test/salt_reuse_test.rb new file mode 100644 index 0000000..ca69f4f --- /dev/null +++ b/test/salt_reuse_test.rb @@ -0,0 +1,19 @@ +# frozen_string_literal: true + +require 'test_helper' + +class Argon2SaltReuseTest < Minitest::Test + def test_salt_reuse + assert temp = Argon2::Password.new + assert pass1 = temp.create('any password here 1') + assert pass2 = temp.create('any password here 2') + + refute_equal pass1, pass2 + + assert salt1 = Argon2::HashFormat.new(pass1).salt + assert salt2 = Argon2::HashFormat.new(pass2).salt + + refute_equal salt1, salt2 + end +end + From c79362aaf45f032ab9debe9165262ad1eebb885f Mon Sep 17 00:00:00 2001 From: Technion Date: Wed, 5 May 2021 14:01:18 +1000 Subject: [PATCH 15/34] Fix rubocop error - newline --- test/salt_reuse_test.rb | 1 - 1 file changed, 1 deletion(-) diff --git a/test/salt_reuse_test.rb b/test/salt_reuse_test.rb index ca69f4f..a467a39 100644 --- a/test/salt_reuse_test.rb +++ b/test/salt_reuse_test.rb @@ -16,4 +16,3 @@ def test_salt_reuse refute_equal salt1, salt2 end end - From 0ef1e33b7d9ec5d8a1fc59b0a092e236d59109ca Mon Sep 17 00:00:00 2001 From: Josh Buker Date: Thu, 20 May 2021 19:29:11 -0700 Subject: [PATCH 16/34] Rename salt option to hammer home that you should not use it normally (#52) I do feel we can never win this one. React has a variable __SECRET_DOM_DO_NOT_USE_OR_YOU_WILL_BE_FIRED and I've inherited code that uses it in production. Your name works though. --- lib/argon2.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/argon2.rb b/lib/argon2.rb index 3429f68..a5c7df8 100644 --- a/lib/argon2.rb +++ b/lib/argon2.rb @@ -20,7 +20,7 @@ def initialize(options = {}) @p_cost = options[:p_cost] || 1 raise ArgonHashFail, "Invalid p_cost" if @p_cost < 1 || @p_cost > 8 - @salt_do_not_supply = options[:salt_do_not_supply] + @insecure_salt = options[:salt_for_testing_purposes_only] @secret = options[:secret] end @@ -29,7 +29,7 @@ def create(pass) pass.is_a?(String) # Ensure salt is freshly generated unless it was intentionally supplied. - salt = @salt_do_not_supply || Engine.saltgen + salt = @insecure_salt || Engine.saltgen Argon2::Engine.hash_argon2id_encode( pass, salt, @t_cost, @m_cost, @p_cost, @secret) From 1b0d400d217b69bc6e15807a8f5ad52f523e36c4 Mon Sep 17 00:00:00 2001 From: Technion Date: Tue, 5 Oct 2021 21:04:50 +0000 Subject: [PATCH 17/34] Revert "Rename salt option to hammer home that you should not use it normally (#52)" This reverts commit 0ef1e33b7d9ec5d8a1fc59b0a092e236d59109ca. --- lib/argon2.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/argon2.rb b/lib/argon2.rb index a5c7df8..3429f68 100644 --- a/lib/argon2.rb +++ b/lib/argon2.rb @@ -20,7 +20,7 @@ def initialize(options = {}) @p_cost = options[:p_cost] || 1 raise ArgonHashFail, "Invalid p_cost" if @p_cost < 1 || @p_cost > 8 - @insecure_salt = options[:salt_for_testing_purposes_only] + @salt_do_not_supply = options[:salt_do_not_supply] @secret = options[:secret] end @@ -29,7 +29,7 @@ def create(pass) pass.is_a?(String) # Ensure salt is freshly generated unless it was intentionally supplied. - salt = @insecure_salt || Engine.saltgen + salt = @salt_do_not_supply || Engine.saltgen Argon2::Engine.hash_argon2id_encode( pass, salt, @t_cost, @m_cost, @p_cost, @secret) From db0747b09ca5204114caf05864eb57d3e090e61e Mon Sep 17 00:00:00 2001 From: Technion Date: Tue, 5 Oct 2021 21:05:20 +0000 Subject: [PATCH 18/34] Increment version. Fixes #54. --- lib/argon2/version.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/argon2/version.rb b/lib/argon2/version.rb index 7729e22..cb421cb 100644 --- a/lib/argon2/version.rb +++ b/lib/argon2/version.rb @@ -3,5 +3,5 @@ # Standard Gem version constant. module Argon2 - VERSION = "2.1.0" + VERSION = "2.1.1" end From 0822cddc9feab76d15df0ec3a4203359c0b16be9 Mon Sep 17 00:00:00 2001 From: Technion Date: Wed, 5 Jan 2022 11:11:07 +0000 Subject: [PATCH 19/34] Added Ruby 3.1 to tests. --- .github/workflows/ruby.yml | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/.github/workflows/ruby.yml b/.github/workflows/ruby.yml index a622b3a..917316c 100644 --- a/.github/workflows/ruby.yml +++ b/.github/workflows/ruby.yml @@ -15,8 +15,7 @@ jobs: ruby: - 2.6 - 2.7 - - 3.0 - - head + - 3.1 runs-on: ${{ matrix.os }}-latest From 15f2842121695385a16ff8feff0f2009f585f1f6 Mon Sep 17 00:00:00 2001 From: Technion Date: Mon, 24 Oct 2022 22:22:15 +1100 Subject: [PATCH 20/34] Bundle upstream. Bump steep. Update signatures for newer steep. --- argon2.gemspec | 2 +- ext/phc-winner-argon2 | 2 +- sig/argon2.rbs | 7 ++++++- sig/ffi.rbs | 18 ++++++++++++++++++ 4 files changed, 26 insertions(+), 3 deletions(-) create mode 100644 sig/ffi.rbs diff --git a/argon2.gemspec b/argon2.gemspec index 8e1ed01..5c2afcd 100644 --- a/argon2.gemspec +++ b/argon2.gemspec @@ -31,7 +31,7 @@ Gem::Specification.new do |spec| spec.add_development_dependency "rubocop", '~> 1.7' spec.add_development_dependency "simplecov", '~> 0.20' spec.add_development_dependency "simplecov-lcov", '~> 0.8' - spec.add_development_dependency "steep", "~> 0.43.1" + spec.add_development_dependency "steep", "~> 1.2.1" spec.extensions << 'ext/argon2_wrap/extconf.rb' spec.cert_chain = ['certs/technion.pem'] diff --git a/ext/phc-winner-argon2 b/ext/phc-winner-argon2 index 440ceb9..16d3df6 160000 --- a/ext/phc-winner-argon2 +++ b/ext/phc-winner-argon2 @@ -1 +1 @@ -Subproject commit 440ceb9612d5a20997e3e12728542df2de713ca4 +Subproject commit 16d3df698db2486dde480b09a732bf9bf48599f9 diff --git a/sig/argon2.rbs b/sig/argon2.rbs index 322eb31..fe34641 100644 --- a/sig/argon2.rbs +++ b/sig/argon2.rbs @@ -7,10 +7,15 @@ module Argon2 @salt: nil | String @secret: nil | String - def initialize: (?Hash[Symbol, Integer] options) -> (nil | String) + def initialize: (?::Hash[untyped, untyped] options) -> void def create: (String pass) -> untyped def self.create: (String pass) -> untyped def self.valid_hash?: (string hash) -> Integer? def self.verify_password: (untyped pass, untyped hash, ?nil secret) -> untyped end + class Engine + def self.saltgen: () -> String + end + class ArgonHashFail < StandardError + end end diff --git a/sig/ffi.rbs b/sig/ffi.rbs new file mode 100644 index 0000000..8badbf7 --- /dev/null +++ b/sig/ffi.rbs @@ -0,0 +1,18 @@ +module Argon2 + # Direct external bindings. Call these methods via the Engine class to ensure points are dealt with + module Ext + extend FFI::Library + end + + # The engine class shields users from the FFI interface. + # It is generally not advised to directly use this class. + class Engine + def self.hash_argon2i: (untyped password, untyped salt, untyped t_cost, untyped m_cost, ?untyped? out_len) -> untyped + + def self.hash_argon2id: (untyped password, untyped salt, untyped t_cost, untyped m_cost, untyped p_cost, ?untyped? out_len) -> untyped + + def self.hash_argon2id_encode: (untyped password, untyped salt, untyped t_cost, untyped m_cost, untyped p_cost, untyped secret) -> untyped + + def self.argon2_verify: (untyped pwd, untyped hash, untyped secret) -> (false | true) + end +end From 0a7758cb9891472cc3634aa153946305ce859424 Mon Sep 17 00:00:00 2001 From: Technion Date: Mon, 24 Oct 2022 22:29:53 +1100 Subject: [PATCH 21/34] Rubocop update --- .rubocop.yml | 82 ++++++++++++++++++++++++++++++++++++++++++++++++-- argon2.gemspec | 5 ++- 2 files changed, 84 insertions(+), 3 deletions(-) diff --git a/.rubocop.yml b/.rubocop.yml index 1ca9e24..6f4f921 100644 --- a/.rubocop.yml +++ b/.rubocop.yml @@ -210,8 +210,6 @@ Style/RedundantArgument: # (new in 1.4) Enabled: true Style/SwapValues: # (new in 1.1) Enabled: true -Gemspec/DateAssignment: # (new in 1.10) - Enabled: true Lint/DeprecatedConstants: # (new in 1.8) Enabled: true Lint/LambdaWithoutLiteralBlock: # (new in 1.8) @@ -234,3 +232,83 @@ Style/IfWithBooleanLiteralBranches: # (new in 1.9) Enabled: true Style/StringChars: # (new in 1.12) Enabled: true +Gemspec/DeprecatedAttributeAssignment: # new in 1.30 + Enabled: true +Gemspec/RequireMFA: # new in 1.23 + Enabled: true +Layout/LineContinuationLeadingSpace: # new in 1.31 + Enabled: true +Layout/LineContinuationSpacing: # new in 1.31 + Enabled: true +Layout/LineEndStringConcatenationIndentation: # new in 1.18 + Enabled: true +Lint/AmbiguousOperatorPrecedence: # new in 1.21 + Enabled: true +Lint/AmbiguousRange: # new in 1.19 + Enabled: true +Lint/ConstantOverwrittenInRescue: # new in 1.31 + Enabled: true +Lint/DuplicateMagicComment: # new in 1.37 + Enabled: true +Lint/EmptyInPattern: # new in 1.16 + Enabled: true +Lint/IncompatibleIoSelectWithFiberScheduler: # new in 1.21 + Enabled: true +Lint/NonAtomicFileOperation: # new in 1.31 + Enabled: true +Lint/RefinementImportMethods: # new in 1.27 + Enabled: true +Lint/RequireRangeParentheses: # new in 1.32 + Enabled: true +Lint/RequireRelativeSelfPath: # new in 1.22 + Enabled: true +Lint/UselessRuby2Keywords: # new in 1.23 + Enabled: true +Naming/BlockForwarding: # new in 1.24 + Enabled: true +Security/CompoundHash: # new in 1.28 + Enabled: true +Security/IoMethods: # new in 1.22 + Enabled: true +Style/EmptyHeredoc: # new in 1.32 + Enabled: true +Style/EnvHome: # new in 1.29 + Enabled: true +Style/FetchEnvVar: # new in 1.28 + Enabled: true +Style/FileRead: # new in 1.24 + Enabled: true +Style/FileWrite: # new in 1.24 + Enabled: true +Style/InPatternThen: # new in 1.16 + Enabled: true +Style/MagicCommentFormat: # new in 1.35 + Enabled: true +Style/MapCompactWithConditionalBlock: # new in 1.30 + Enabled: true +Style/MapToHash: # new in 1.24 + Enabled: true +Style/MultilineInPatternThen: # new in 1.16 + Enabled: true +Style/NestedFileDirname: # new in 1.26 + Enabled: true +Style/NumberedParameters: # new in 1.22 + Enabled: true +Style/NumberedParametersLimit: # new in 1.22 + Enabled: true +Style/ObjectThen: # new in 1.28 + Enabled: true +Style/OpenStructUse: # new in 1.23 + Enabled: true +Style/OperatorMethodCall: # new in 1.37 + Enabled: true +Style/QuotedSymbols: # new in 1.16 + Enabled: true +Style/RedundantInitialize: # new in 1.27 + Enabled: true +Style/RedundantSelfAssignmentBranch: # new in 1.19 + Enabled: true +Style/RedundantStringEscape: # new in 1.37 + Enabled: true +Style/SelectByRegexp: # new in 1.22 + Enabled: true diff --git a/argon2.gemspec b/argon2.gemspec index e9a2e4d..5a70d27 100644 --- a/argon2.gemspec +++ b/argon2.gemspec @@ -17,8 +17,11 @@ Gem::Specification.new do |spec| spec.description = 'Argon2 FFI binding' spec.homepage = 'https://github.com/technion/ruby-argon2' spec.license = 'MIT' + spec.metadata = { + 'rubygems_mfa_required' => 'true' + } - spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) } + spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) } spec.files << `find ext`.split spec.bindir = "exe" From 97b0a1902c4373ce947a73da8764ffcb96dedad1 Mon Sep 17 00:00:00 2001 From: Technion Date: Mon, 24 Oct 2022 22:33:23 +1100 Subject: [PATCH 22/34] Version bump --- lib/argon2/version.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/argon2/version.rb b/lib/argon2/version.rb index cb421cb..a57b934 100644 --- a/lib/argon2/version.rb +++ b/lib/argon2/version.rb @@ -3,5 +3,5 @@ # Standard Gem version constant. module Argon2 - VERSION = "2.1.1" + VERSION = "2.1.2" end From 8ddbbdd2584ca96bcf823653e81508996964bcc8 Mon Sep 17 00:00:00 2001 From: Joshua Small Date: Sun, 13 Nov 2022 11:37:35 +1100 Subject: [PATCH 23/34] Create codeql.yml (#55) * Create codeql.yml * Update codeql.yml --- .github/workflows/codeql.yml | 74 ++++++++++++++++++++++++++++++++++++ 1 file changed, 74 insertions(+) create mode 100644 .github/workflows/codeql.yml diff --git a/.github/workflows/codeql.yml b/.github/workflows/codeql.yml new file mode 100644 index 0000000..7c3e450 --- /dev/null +++ b/.github/workflows/codeql.yml @@ -0,0 +1,74 @@ +# For most projects, this workflow file will not need changing; you simply need +# to commit it to your repository. +# +# You may wish to alter this file to override the set of languages analyzed, +# or to provide custom queries or build logic. +# +# ******** NOTE ******** +# We have attempted to detect the languages in your repository. Please check +# the `language` matrix defined below to confirm you have the correct set of +# supported CodeQL languages. +# +name: "CodeQL" + +on: + push: + branches: [ "master" ] + pull_request: + # The branches below must be a subset of the branches above + branches: [ "master" ] + schedule: + - cron: '34 3 * * 3' + +jobs: + analyze: + name: Analyze + runs-on: ubuntu-latest + permissions: + actions: read + contents: read + security-events: write + + strategy: + fail-fast: false + matrix: + language: [ 'ruby' ] + # CodeQL supports [ 'cpp', 'csharp', 'go', 'java', 'javascript', 'python', 'ruby' ] + # Learn more about CodeQL language support at https://aka.ms/codeql-docs/language-support + + steps: + - name: Checkout repository + uses: actions/checkout@v3 + + # Initializes the CodeQL tools for scanning. + - name: Initialize CodeQL + uses: github/codeql-action/init@v2 + with: + languages: ${{ matrix.language }} + # If you wish to specify custom queries, you can do so here or in a config file. + # By default, queries listed here will override any specified in a config file. + # Prefix the list here with "+" to use these queries and those in the config file. + + # Details on CodeQL's query packs refer to : https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-code-scanning#using-queries-in-ql-packs + # queries: security-extended,security-and-quality + + + # Autobuild attempts to build any compiled languages (C/C++, C#, Go, or Java). + # If this step fails, then you should remove it and run the build manually (see below) + - name: Autobuild + uses: github/codeql-action/autobuild@v2 + + # ℹī¸ Command-line programs to run using the OS shell. + # 📚 See https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions#jobsjob_idstepsrun + + # If the Autobuild fails above, remove it and uncomment the following three lines. + # modify them (or add more) to build your code if your project, please refer to the EXAMPLE below for guidance. + + # - run: | + # echo "Run, Build Application using script" + # ./location_of_script_within_repo/buildscript.sh + + - name: Perform CodeQL Analysis + uses: github/codeql-action/analyze@v2 + with: + category: "/language:${{matrix.language}}" From 1f3ab8eb2ca90d3eda1197e19d9ba12379140c7c Mon Sep 17 00:00:00 2001 From: Technion Date: Mon, 26 Dec 2022 20:09:50 +1100 Subject: [PATCH 24/34] Update dependencies, particularly ffi --- README.md | 2 +- argon2.gemspec | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 51e3e56..3fa1da2 100644 --- a/README.md +++ b/README.md @@ -13,7 +13,7 @@ This project has several key tenets to its design: * The reference Argon2 implementation is to be used "unaltered". To ensure compliance with this goal, and encourage regular updates from upstream, the upstream library is implemented as a git submodule, and is intended to stay that way. * The FFI interface is kept as slim as possible, with wrapper classes preferred to implementing context structs in FFI * Security and maintainability take top priority. This can have an impact on platform support. A PR that contains platform specific code paths is unlikely to be accepted. -* Tested platforms are MRI Ruby 2.2, 2.3 and JRuby 9000. No assertions are made on other platforms. +* Tested platforms are MRI Ruby 2.7 and 3.0. No assertions are made on other platforms. * Errors from the C interface are raised as Exceptions. There are a lot of exception classes, but they tend to relate to things like very broken input, and code bugs. Calls to this library should generally not require a rescue. * Test suites should aim for 100% code coverage. * Default work values should not be considered constants. I will increase them from time to time. diff --git a/argon2.gemspec b/argon2.gemspec index 5a70d27..a421c3f 100644 --- a/argon2.gemspec +++ b/argon2.gemspec @@ -27,7 +27,7 @@ Gem::Specification.new do |spec| spec.bindir = "exe" spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) } spec.require_paths = ["lib"] - spec.add_dependency 'ffi', '~> 1.14' + spec.add_dependency 'ffi', '~> 1.15' spec.add_dependency 'ffi-compiler', '~> 1.0' spec.add_development_dependency "bundler", '~> 2.0' From 79f69b3ead3ed2f2dd12279094a3407d0fe0496b Mon Sep 17 00:00:00 2001 From: Technion Date: Mon, 26 Dec 2022 20:11:24 +1100 Subject: [PATCH 25/34] Introduce testing of Ruby 3.2 --- .github/workflows/ruby.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/ruby.yml b/.github/workflows/ruby.yml index 917316c..9f95bd9 100644 --- a/.github/workflows/ruby.yml +++ b/.github/workflows/ruby.yml @@ -13,9 +13,9 @@ jobs: - ubuntu - macos ruby: - - 2.6 - 2.7 - 3.1 + - 3.2 runs-on: ${{ matrix.os }}-latest From aeb986caec88a1a78b0b8637871dec0f845d0744 Mon Sep 17 00:00:00 2001 From: Technion Date: Mon, 26 Dec 2022 20:25:06 +1100 Subject: [PATCH 26/34] Bump version --- lib/argon2/version.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/argon2/version.rb b/lib/argon2/version.rb index a57b934..755d24b 100644 --- a/lib/argon2/version.rb +++ b/lib/argon2/version.rb @@ -3,5 +3,5 @@ # Standard Gem version constant. module Argon2 - VERSION = "2.1.2" + VERSION = "2.1.3" end From 282543d667b0086aa2dd400a7475b2a73744b899 Mon Sep 17 00:00:00 2001 From: Technion Date: Tue, 27 Dec 2022 09:41:57 +1100 Subject: [PATCH 27/34] WIP - change build system --- ext/argon2_wrap/Makefile | 74 -------------------------------------- ext/argon2_wrap/extconf.rb | 24 ++++++++++++- 2 files changed, 23 insertions(+), 75 deletions(-) delete mode 100644 ext/argon2_wrap/Makefile diff --git a/ext/argon2_wrap/Makefile b/ext/argon2_wrap/Makefile deleted file mode 100644 index 842fbd7..0000000 --- a/ext/argon2_wrap/Makefile +++ /dev/null @@ -1,74 +0,0 @@ -# Argon Wrapper Makefile -# This file is based on the original Argon2 reference -# Argon2 source code package -# -# This work is licensed under a Creative Commons CC0 1.0 License/Waiver. -# -# You should have received a copy of the CC0 Public Domain Dedication along with -# this software. If not, see . -# - -DIST_SRC = ../phc-winner-argon2/src -SRC = $(DIST_SRC)/argon2.c $(DIST_SRC)/core.c $(DIST_SRC)/blake2/blake2b.c $(DIST_SRC)/thread.c $(DIST_SRC)/encoding.c argon_wrap.c -OBJ = $(SRC:.c=.o) - -CFLAGS = -pthread -O3 -Wall -g -I../phc-winner-argon2/include -I../phc-winner-argon2/src - -OPTTEST := $(shell $(CC) -Iinclude -Isrc -march=native src/opt.c -c 2>/dev/null; echo $$?) -# Detect compatible platform -ifneq ($(OPTTEST), 0) - SRC += $(DIST_SRC)/ref.c -else - CFLAGS += -march=native - SRC += $(DIST_SRC)/opt.c -endif - - -BUILD_PATH := $(shell pwd) -KERNEL_NAME := $(shell uname -s) - -LIB_NAME=argon2_wrap -ifeq ($(KERNEL_NAME), Linux) - LIB_EXT := so - LIB_CFLAGS := -shared -fPIC -endif -ifeq ($(KERNEL_NAME), NetBSD) - LIB_EXT := so - LIB_CFLAGS := -shared -fPIC -endif -ifeq ($(KERNEL_NAME), Darwin) - LIB_EXT := bundle - LIB_CFLAGS := -bundle -endif -ifeq ($(findstring MINGW, $(KERNEL_NAME)), MINGW) - LIB_EXT := dll - LIB_CFLAGS := -shared -Wl,--out-implib,lib$(LIB_NAME).$(LIB_EXT).a -endif -ifeq ($(KERNEL_NAME), $(filter $(KERNEL_NAME),OpenBSD FreeBSD)) - LIB_EXT := so - LIB_CFLAGS := -shared -fPIC -endif -ifeq ($(KERNEL_NAME), SunOS) - CC := gcc - CFLAGS += -D_REENTRANT - LIB_EXT := so - LIB_CFLAGS := -shared -fPIC -endif - -LIB_SH := lib$(LIB_NAME).$(LIB_EXT) - -all: libs -libs: $(SRC) - $(CC) $(CFLAGS) $(LIB_CFLAGS) $^ -o libargon2_wrap.$(LIB_EXT) - -#Deliberately avoiding the CFLAGS for our test cases - disable optimise and -#C89 -test: $(SRC) test.c - clang -pthread -O3 -fsanitize=address -fsanitize=undefined -Wall -g $^ -o tests $(CFLAGS) - ./tests - -clean: - rm -f tests libargon2_wrap.$(LIB_EXT) - -install: - echo none diff --git a/ext/argon2_wrap/extconf.rb b/ext/argon2_wrap/extconf.rb index b04d0eb..a314462 100644 --- a/ext/argon2_wrap/extconf.rb +++ b/ext/argon2_wrap/extconf.rb @@ -1,2 +1,24 @@ # frozen_string_literal: true -#I must admit I have no understanding of why this empty file works. +require 'mkmf' +$CFLAGS += " -march=native -lpthread" + +find_header("argon2.h", "../../../../ext/phc-winner-argon2/include", "../phc-winner-argon2/include") +find_header("argon2.c", "../../../../ext/phc-winner-argon2/src", "../phc-winner-argon2/src") +$srcs = %w( ../phc-winner-argon2/src/argon2.c + ../phc-winner-argon2/src/core.c + ../phc-winner-argon2/src/blake2/blake2b.c + ../phc-winner-argon2/src/thread.c + ../phc-winner-argon2/src/encoding.c + ../phc-winner-argon2/src/opt.c + argon_wrap.c) +$objs = $srcs.map { |x| x.gsub /\.c/, '.o' } + +File.open("Makefile", "at") do |mk| + mk.print(<<~EOF) +test: $(SRC) test.c + clang -pthread -O3 -fsanitize=address -fsanitize=undefined -Wall -g $^ -o tests $(CFLAGS) + ./tests + EOF +end + +create_makefile('libargon2_wrap') From 279d82662746020d7544b3062c06ec98afb47f7f Mon Sep 17 00:00:00 2001 From: Technion Date: Tue, 27 Dec 2022 13:15:32 +1100 Subject: [PATCH 28/34] Attempts at updating test to run with new build system. --- bin/setup | 1 + ext/argon2_wrap/extconf.rb | 9 +++++++-- 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/bin/setup b/bin/setup index abc4e72..6b3da02 100755 --- a/bin/setup +++ b/bin/setup @@ -10,5 +10,6 @@ git submodule update --init --recursive # Build the Argon2 C Library. Git submodules must be initialized first! bundle install cd ext/argon2_wrap/ +ruby extconf.rb make cd ../.. diff --git a/ext/argon2_wrap/extconf.rb b/ext/argon2_wrap/extconf.rb index a314462..31dc17e 100644 --- a/ext/argon2_wrap/extconf.rb +++ b/ext/argon2_wrap/extconf.rb @@ -13,12 +13,17 @@ argon_wrap.c) $objs = $srcs.map { |x| x.gsub /\.c/, '.o' } +create_makefile('libargon2_wrap') + File.open("Makefile", "at") do |mk| mk.print(<<~EOF) +DIST_SRC = ../phc-winner-argon2/src +SRC = $(DIST_SRC)/argon2.c $(DIST_SRC)/core.c $(DIST_SRC)/blake2/blake2b.c $(DIST_SRC)/thread.c $(DIST_SRC)/encoding.c argon_wrap.c $(DIST_SRC)/opt.c + +OBJ = $(SRC:.c=.o) +CFLAGS = -pthread -O3 -Wall -g -I../phc-winner-argon2/include -I../phc-winner-argon2/src test: $(SRC) test.c clang -pthread -O3 -fsanitize=address -fsanitize=undefined -Wall -g $^ -o tests $(CFLAGS) ./tests EOF end - -create_makefile('libargon2_wrap') From d60c37332770cc600587467082cdcf79a5ada742 Mon Sep 17 00:00:00 2001 From: Technion Date: Tue, 27 Dec 2022 13:27:54 +1100 Subject: [PATCH 29/34] Implement new platform detection --- ext/argon2_wrap/extconf.rb | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/ext/argon2_wrap/extconf.rb b/ext/argon2_wrap/extconf.rb index 31dc17e..357dc8d 100644 --- a/ext/argon2_wrap/extconf.rb +++ b/ext/argon2_wrap/extconf.rb @@ -2,6 +2,13 @@ require 'mkmf' $CFLAGS += " -march=native -lpthread" +case RUBY_PLATFORM +when /darwin/ + $CFLAGS += " -bundle" +else + $CFLAGS += " -shared -fPIC" +end + find_header("argon2.h", "../../../../ext/phc-winner-argon2/include", "../phc-winner-argon2/include") find_header("argon2.c", "../../../../ext/phc-winner-argon2/src", "../phc-winner-argon2/src") $srcs = %w( ../phc-winner-argon2/src/argon2.c From 6166c77438c4f56e27bd6264584aa6fa923edc71 Mon Sep 17 00:00:00 2001 From: Technion Date: Tue, 27 Dec 2022 13:41:28 +1100 Subject: [PATCH 30/34] Debugging on build process --- ext/argon2_wrap/extconf.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ext/argon2_wrap/extconf.rb b/ext/argon2_wrap/extconf.rb index 357dc8d..4bdd5e6 100644 --- a/ext/argon2_wrap/extconf.rb +++ b/ext/argon2_wrap/extconf.rb @@ -19,7 +19,7 @@ ../phc-winner-argon2/src/opt.c argon_wrap.c) $objs = $srcs.map { |x| x.gsub /\.c/, '.o' } - +puts $CFLAGS create_makefile('libargon2_wrap') File.open("Makefile", "at") do |mk| From 927bf0ecb18ed1746fa535cfb7acedf992ccdb27 Mon Sep 17 00:00:00 2001 From: Technion Date: Tue, 27 Dec 2022 14:11:35 +1100 Subject: [PATCH 31/34] Hail Mary hack --- ext/argon2_wrap/Makefile.real | 74 +++++++++++++++++++++++++++++++++++ ext/argon2_wrap/extconf.rb | 35 +---------------- 2 files changed, 76 insertions(+), 33 deletions(-) create mode 100644 ext/argon2_wrap/Makefile.real diff --git a/ext/argon2_wrap/Makefile.real b/ext/argon2_wrap/Makefile.real new file mode 100644 index 0000000..842fbd7 --- /dev/null +++ b/ext/argon2_wrap/Makefile.real @@ -0,0 +1,74 @@ +# Argon Wrapper Makefile +# This file is based on the original Argon2 reference +# Argon2 source code package +# +# This work is licensed under a Creative Commons CC0 1.0 License/Waiver. +# +# You should have received a copy of the CC0 Public Domain Dedication along with +# this software. If not, see . +# + +DIST_SRC = ../phc-winner-argon2/src +SRC = $(DIST_SRC)/argon2.c $(DIST_SRC)/core.c $(DIST_SRC)/blake2/blake2b.c $(DIST_SRC)/thread.c $(DIST_SRC)/encoding.c argon_wrap.c +OBJ = $(SRC:.c=.o) + +CFLAGS = -pthread -O3 -Wall -g -I../phc-winner-argon2/include -I../phc-winner-argon2/src + +OPTTEST := $(shell $(CC) -Iinclude -Isrc -march=native src/opt.c -c 2>/dev/null; echo $$?) +# Detect compatible platform +ifneq ($(OPTTEST), 0) + SRC += $(DIST_SRC)/ref.c +else + CFLAGS += -march=native + SRC += $(DIST_SRC)/opt.c +endif + + +BUILD_PATH := $(shell pwd) +KERNEL_NAME := $(shell uname -s) + +LIB_NAME=argon2_wrap +ifeq ($(KERNEL_NAME), Linux) + LIB_EXT := so + LIB_CFLAGS := -shared -fPIC +endif +ifeq ($(KERNEL_NAME), NetBSD) + LIB_EXT := so + LIB_CFLAGS := -shared -fPIC +endif +ifeq ($(KERNEL_NAME), Darwin) + LIB_EXT := bundle + LIB_CFLAGS := -bundle +endif +ifeq ($(findstring MINGW, $(KERNEL_NAME)), MINGW) + LIB_EXT := dll + LIB_CFLAGS := -shared -Wl,--out-implib,lib$(LIB_NAME).$(LIB_EXT).a +endif +ifeq ($(KERNEL_NAME), $(filter $(KERNEL_NAME),OpenBSD FreeBSD)) + LIB_EXT := so + LIB_CFLAGS := -shared -fPIC +endif +ifeq ($(KERNEL_NAME), SunOS) + CC := gcc + CFLAGS += -D_REENTRANT + LIB_EXT := so + LIB_CFLAGS := -shared -fPIC +endif + +LIB_SH := lib$(LIB_NAME).$(LIB_EXT) + +all: libs +libs: $(SRC) + $(CC) $(CFLAGS) $(LIB_CFLAGS) $^ -o libargon2_wrap.$(LIB_EXT) + +#Deliberately avoiding the CFLAGS for our test cases - disable optimise and +#C89 +test: $(SRC) test.c + clang -pthread -O3 -fsanitize=address -fsanitize=undefined -Wall -g $^ -o tests $(CFLAGS) + ./tests + +clean: + rm -f tests libargon2_wrap.$(LIB_EXT) + +install: + echo none diff --git a/ext/argon2_wrap/extconf.rb b/ext/argon2_wrap/extconf.rb index 4bdd5e6..c8908d6 100644 --- a/ext/argon2_wrap/extconf.rb +++ b/ext/argon2_wrap/extconf.rb @@ -1,36 +1,5 @@ # frozen_string_literal: true require 'mkmf' -$CFLAGS += " -march=native -lpthread" - -case RUBY_PLATFORM -when /darwin/ - $CFLAGS += " -bundle" -else - $CFLAGS += " -shared -fPIC" -end - -find_header("argon2.h", "../../../../ext/phc-winner-argon2/include", "../phc-winner-argon2/include") -find_header("argon2.c", "../../../../ext/phc-winner-argon2/src", "../phc-winner-argon2/src") -$srcs = %w( ../phc-winner-argon2/src/argon2.c - ../phc-winner-argon2/src/core.c - ../phc-winner-argon2/src/blake2/blake2b.c - ../phc-winner-argon2/src/thread.c - ../phc-winner-argon2/src/encoding.c - ../phc-winner-argon2/src/opt.c - argon_wrap.c) -$objs = $srcs.map { |x| x.gsub /\.c/, '.o' } -puts $CFLAGS create_makefile('libargon2_wrap') - -File.open("Makefile", "at") do |mk| - mk.print(<<~EOF) -DIST_SRC = ../phc-winner-argon2/src -SRC = $(DIST_SRC)/argon2.c $(DIST_SRC)/core.c $(DIST_SRC)/blake2/blake2b.c $(DIST_SRC)/thread.c $(DIST_SRC)/encoding.c argon_wrap.c $(DIST_SRC)/opt.c - -OBJ = $(SRC:.c=.o) -CFLAGS = -pthread -O3 -Wall -g -I../phc-winner-argon2/include -I../phc-winner-argon2/src -test: $(SRC) test.c - clang -pthread -O3 -fsanitize=address -fsanitize=undefined -Wall -g $^ -o tests $(CFLAGS) - ./tests - EOF -end +File.unlink('Makefile') +File.rename('Makefile.real', 'Makefile') From 27793abfbf8b4d0b35556ccce2d895ea6ee55637 Mon Sep 17 00:00:00 2001 From: Technion Date: Tue, 27 Dec 2022 14:31:47 +1100 Subject: [PATCH 32/34] Bump version. New horrible solution to #56 --- ext/argon2_wrap/extconf.rb | 3 +-- lib/argon2/version.rb | 2 +- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/ext/argon2_wrap/extconf.rb b/ext/argon2_wrap/extconf.rb index c8908d6..f0c8b2c 100644 --- a/ext/argon2_wrap/extconf.rb +++ b/ext/argon2_wrap/extconf.rb @@ -1,5 +1,4 @@ # frozen_string_literal: true require 'mkmf' -create_makefile('libargon2_wrap') -File.unlink('Makefile') File.rename('Makefile.real', 'Makefile') +system "make" diff --git a/lib/argon2/version.rb b/lib/argon2/version.rb index 755d24b..d30bd88 100644 --- a/lib/argon2/version.rb +++ b/lib/argon2/version.rb @@ -3,5 +3,5 @@ # Standard Gem version constant. module Argon2 - VERSION = "2.1.3" + VERSION = "2.2.0" end From 938404b241c094831cdffbf2312cb3064c6c456c Mon Sep 17 00:00:00 2001 From: Technion Date: Tue, 27 Dec 2022 14:39:06 +1100 Subject: [PATCH 33/34] Rubocop fix. --- ext/argon2_wrap/extconf.rb | 2 ++ 1 file changed, 2 insertions(+) diff --git a/ext/argon2_wrap/extconf.rb b/ext/argon2_wrap/extconf.rb index f0c8b2c..b6e91a2 100644 --- a/ext/argon2_wrap/extconf.rb +++ b/ext/argon2_wrap/extconf.rb @@ -1,4 +1,6 @@ # frozen_string_literal: true + require 'mkmf' + File.rename('Makefile.real', 'Makefile') system "make" From 8d2c1328bd3b9e6a0b97e178eed3b67d3638d0ca Mon Sep 17 00:00:00 2001 From: Technion Date: Tue, 27 Dec 2022 16:28:53 +1100 Subject: [PATCH 34/34] Better fix for rubygems issue --- ext/argon2_wrap/Makefile.real | 1 + ext/argon2_wrap/extconf.rb | 1 - 2 files changed, 1 insertion(+), 1 deletion(-) diff --git a/ext/argon2_wrap/Makefile.real b/ext/argon2_wrap/Makefile.real index 842fbd7..a2eb90a 100644 --- a/ext/argon2_wrap/Makefile.real +++ b/ext/argon2_wrap/Makefile.real @@ -60,6 +60,7 @@ LIB_SH := lib$(LIB_NAME).$(LIB_EXT) all: libs libs: $(SRC) $(CC) $(CFLAGS) $(LIB_CFLAGS) $^ -o libargon2_wrap.$(LIB_EXT) + cp libargon2_wrap.$(LIB_EXT) ../../lib #Deliberately avoiding the CFLAGS for our test cases - disable optimise and #C89 diff --git a/ext/argon2_wrap/extconf.rb b/ext/argon2_wrap/extconf.rb index b6e91a2..d6af9e0 100644 --- a/ext/argon2_wrap/extconf.rb +++ b/ext/argon2_wrap/extconf.rb @@ -3,4 +3,3 @@ require 'mkmf' File.rename('Makefile.real', 'Makefile') -system "make"