Class: Eco::Data::Crypto::OpenSSL

Inherits:
Object
  • Object
show all
Defined in:
lib/eco/data/crypto/encryption.rb

Constant Summary collapse

DEFAULT_KEY_LENGTH =
256
DEFAULT_RSA_LENGTH =
2048
SALT_LENGTH =
128
SALT_SEED =
"$%!@_halt9000"
BLOCK_OCTETS =
512

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(init = {}) ⇒ OpenSSL

Returns a new instance of OpenSSL.



79
80
81
82
83
84
85
86
# File 'lib/eco/data/crypto/encryption.rb', line 79

def initialize(init = {})
  @digest = ::OpenSSL::Digest
  @pkcs5 = ::OpenSSL::PKCS5
  #@kdf = ::OpenSSL::KDF

  @cipher = ::OpenSSL::Cipher
  self.salt_seed = SALT_SEED
  @rsa = ::OpenSSL::PKey::RSA
end

Instance Attribute Details

#cipherObject (readonly)

Returns the value of attribute cipher.



77
78
79
# File 'lib/eco/data/crypto/encryption.rb', line 77

def cipher
  @cipher
end

#digestObject (readonly)

Returns the value of attribute digest.



77
78
79
# File 'lib/eco/data/crypto/encryption.rb', line 77

def digest
  @digest
end

#kdfObject (readonly)

Returns the value of attribute kdf.



77
78
79
# File 'lib/eco/data/crypto/encryption.rb', line 77

def kdf
  @kdf
end

#pkcs5Object (readonly)

Returns the value of attribute pkcs5.



77
78
79
# File 'lib/eco/data/crypto/encryption.rb', line 77

def pkcs5
  @pkcs5
end

#rsaObject (readonly)

Returns the value of attribute rsa.



77
78
79
# File 'lib/eco/data/crypto/encryption.rb', line 77

def rsa
  @rsa
end

#saltObject (readonly)

Returns the value of attribute salt.



78
79
80
# File 'lib/eco/data/crypto/encryption.rb', line 78

def salt
  @salt
end

#salt_seedObject

Returns the value of attribute salt_seed.



76
77
78
# File 'lib/eco/data/crypto/encryption.rb', line 76

def salt_seed
  @salt_seed
end

Instance Method Details

#aes256_decrypt(data, key:, iv:, block_octets: BLOCK_OCTETS) ⇒ Object

EncryptedData.new(str_c, key: key, iv: iv)



149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
# File 'lib/eco/data/crypto/encryption.rb', line 149

def aes256_decrypt(data, key: , iv: , block_octets: BLOCK_OCTETS)
  block_bits = block_bits * 8
  #validation = encrypted_data && encrypted_data.key && encrypted_data.iv

  # return nil unless validation

  cipher = @cipher.new('aes-256-cbc')
  cipher.decrypt
  cipher.key = key
  cipher.iv  = iv
  #cipher.key = encrypted_data.key

  #cipher.iv = encrypted_data.iv

  #str_c = encrypted_data.content

  str_c = data
  str = ""
  while str_c.length > 0
    str += cipher.update(str_c.slice!(0, block_bits))
    #puts str[-50..-1] || str

  end
  str += cipher.final
  return str
end

#aes256_encrypt(data, key: nil, iv: nil, block_octets: BLOCK_OCTETS) ⇒ Object



129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
# File 'lib/eco/data/crypto/encryption.rb', line 129

def aes256_encrypt(data, key: nil, iv: nil, block_octets: BLOCK_OCTETS)
  block_bits = block_bits * 8
  cipher = @cipher.new('aes-256-cbc')
  cipher.encrypt

  if key ; cipher.key = key
  else   ; key = cipher.random_key
  end
  if iv  ; cipher.iv = iv
  else   ; iv = cipher.random_iv
  end

  str_c = ""
  while str.length > 0
    str_c += cipher.update(str.slice!(0, block_bits))
  end
  str_c += cipher.final
  return str_c
  #EncryptedData.new({content: str_c, key: key, iv: iv})

end

#aes256_pass(pass) ⇒ Object

def scrypt (pass, salt: @salt, cost: 14, length: DEFAULT_KEY_LENGTH) block_size = 8 parallelization = 1 octets = length.div(8) @kdf.scrypt(pass, salt: salt, N: 2**cost, r: block_size, p: parallelization, length: octets) end



126
127
128
# File 'lib/eco/data/crypto/encryption.rb', line 126

def aes256_pass(pass)
  self.pbkdf2(pass, length: 256)
end

#pbkdf2(pass, salt: @salt || "salt", iterations: 1000, length: DEFAULT_KEY_LENGTH, hash: "sha256") ⇒ Object

default hmac hash to "sha256" -> https://github.com/hueniverse/iron/issues/55



104
105
106
107
108
109
110
111
112
113
# File 'lib/eco/data/crypto/encryption.rb', line 104

def pbkdf2 (pass, salt: @salt || "salt", iterations: 1000, length: DEFAULT_KEY_LENGTH, hash: "sha256")
  octets = length.div(8)
  #puts "this has been called"

  #puts "pass: #{pass}"

  #puts "salt: #{salt}"

  #puts "iterations: #{iterations}"

  #puts "length: #{length}"

  #puts "hash: #{hash}"

  @pkcs5.pbkdf2_hmac(pass, salt, iterations, octets, hash)
end

#pbkdf2_sha1(pass, salt: @salt, iterations: 1000, length: DEFAULT_KEY_LENGTH) ⇒ Object



114
115
116
117
# File 'lib/eco/data/crypto/encryption.rb', line 114

def pbkdf2_sha1 (pass, salt: @salt, iterations: 1000, length: DEFAULT_KEY_LENGTH)
  #self.pbkdf2(pass, salt: salt, iterations: iternations, length: length, hash: "sha1")

  @pkcs5.pbkdf2_hmac(pass, salt, iterations, octets, "sha1")
end

#rsa_keygen(length = DEFAULT_RSA_LENGTH, filename: "rsa") ⇒ Object



169
170
171
172
173
174
# File 'lib/eco/data/crypto/encryption.rb', line 169

def rsa_keygen(length = DEFAULT_RSA_LENGTH, filename: "rsa")
  filename = "rsa" if !filename
  key =  @rsa.new(length)
  File.open('./' + filename + '.pem',"w") {|fd| fd << key.to_pem }
  File.open('./' + filename + '.pub',"w") {|fd| fd << key.public_key.to_pem }
end

#rsa_keygen_ssh(length = DEFAULT_RSA_LENGTH, filename: "rsa") ⇒ Object



175
176
177
178
179
180
181
182
183
# File 'lib/eco/data/crypto/encryption.rb', line 175

def rsa_keygen_ssh(length = DEFAULT_RSA_LENGTH, filename: "rsa")
  # to do conersion pem to ssh-rsa: https://stackoverflow.com/a/3162593/4352306

  # conversion explained here: http://blog.oddbit.com/2011/05/08/converting-openssh-public-keys/

  # much simpler developed in php here: https://stackoverflow.com/a/5524323/4352306

  filename = "rsa" if !filename
  key =  @rsa.new(length)
  File.open('./' + filename + '.der',"w") {|fd| fd << key.ssh_type }
  File.open('./' + filename + '.pub',"w") {|fd| fd << key.public_key.ssh_type }
end

#rsa_keypairs?(private_key, public_key) ⇒ Boolean

Returns:

  • (Boolean)


184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
# File 'lib/eco/data/crypto/encryption.rb', line 184

def rsa_keypairs?(private_key, public_key)
  str_original = "See, my mule don’t like people laughing"

  pub_key = @rsa.new(public_key)
  str_original.force_encoding(Encoding::UTF_8)
  encrypted_data = Base64.encode64(pub_key.public_encrypt(str_original))

  priv_key = @rsa.new(private_key)
  begin # see here: https://stackoverflow.com/a/13251160/4352306 (padding error when false pub key)

    decrypted_data = priv_key.private_decrypt(Base64.decode64(encrypted_data))
    # OpenSSL core Ruby library is written in C which uses different encoding (ASCII-8BIT)

    # that's why we force UTF-8 encoding (before and after encryption)

    # see this answer: https://stackoverflow.com/a/27326915/4352306

    decrypted_data.force_encoding(Encoding::UTF_8)
  rescue
    return false
  end

  puts "encrypted string: #{str_original}"
  puts "decrypted string: #{decrypted_data}"
  return (decrypted_data == str_original)
end

#sha256(str = nil) ⇒ Object



91
92
93
94
95
96
# File 'lib/eco/data/crypto/encryption.rb', line 91

def sha256 (str = nil)
  sha = @digest.SHA256.new
  digest = sha.digest(str) unless !str
  sha.reset
  digest
end

#sha512(str = nil) ⇒ Object



97
98
99
100
101
102
# File 'lib/eco/data/crypto/encryption.rb', line 97

def sha512 (str = nil)
  sha = @digest.SHA512.new
  digest = sha.digest(str) unless !str
  sha.reset
  digest
end