- r - 以节省内存的方式增长 data.frame
- ruby-on-rails - ruby/ruby on rails 内存泄漏检测
- android - 无法解析导入android.support.v7.app
- UNIX 域套接字与共享内存(映射文件)
我正在尝试使用 ripemd160
在 Swift 3(和/或 Objective-C )中散列一个字符串模拟以下 php 的输出:
$string = 'string';
$key = 'test';
hash_hmac('ripemd160', $string, $key);
// outputs: 37241f2513c60ae4d9b3b8d0d30517445f451fa5
到目前为止:
我试过调查 hash_hmac
我可以找到的功能,例如:
Implementing HMAC and SHA1 encryption in swift
enum HMACAlgorithm {
case MD5, SHA1, SHA224, SHA256, SHA384, SHA512, RIPEMD160
func toCCHmacAlgorithm() -> CCHmacAlgorithm {
var result: Int = 0
switch self {
case .MD5:
result = kCCHmacAlgMD5
case .SHA1:
result = kCCHmacAlgSHA1
case .SHA224:
result = kCCHmacAlgSHA224
case .SHA256:
result = kCCHmacAlgSHA256
case .SHA384:
result = kCCHmacAlgSHA384
case .SHA512:
result = kCCHmacAlgSHA512
case .RIPEMD160:
result = kCCHmacAlgRIPEMD160
}
return CCHmacAlgorithm(result)
}
func digestLength() -> Int {
var result: CInt = 0
switch self {
case .MD5:
result = CC_MD5_DIGEST_LENGTH
case .SHA1:
result = CC_SHA1_DIGEST_LENGTH
case .SHA224:
result = CC_SHA224_DIGEST_LENGTH
case .SHA256:
result = CC_SHA256_DIGEST_LENGTH
case .SHA384:
result = CC_SHA384_DIGEST_LENGTH
case .SHA512:
result = CC_SHA512_DIGEST_LENGTH
}
return Int(result)
}
}
extension String {
func hmac(algorithm: HMACAlgorithm, key: String) -> String {
let cKey = key.cString(using: String.Encoding.utf8)
let cData = self.cString(using: String.Encoding.utf8)
var result = [CUnsignedChar](repeating: 0, count: Int(algorithm.digestLength()))
CCHmac(algorithm.toCCHmacAlgorithm(), cKey!, Int(strlen(cKey!)), cData!, Int(strlen(cData!)), &result)
let hmacData:NSData = NSData(bytes: result, length: (Int(algorithm.digestLength())))
let hmacBase64 = hmacData.base64EncodedString(options: NSData.Base64EncodingOptions.lineLength76Characters)
return String(hmacBase64)
}
}
并实现:
let hmacResult: String = "myStringToHMAC".hmac(algorithm: HMACAlgorithm.SHA1, key: "foo")
这使我能够使用 hmac 和 <CommonCrypto/CommonHMAC.h>
提供的一种加密算法成功散列字符串
问题
问题是库不支持 ripemd160
,那么我该如何添加这种支持才能完成我的需要呢?
有一个问题与此完全相同,但在 Java here 中,您可以看到它是如何解决的,以及我正在寻找的问题,但这次使用的是 Swift 3:
Hash a string in Java emulating the php function hash_hmac using ripemd160 with a key
最佳答案
这是 RIPEMD-160 哈希函数和对应的 HMAC-RIPEMD-160 消息认证码。它已经过测试RIPEMD-160 page 上的所有测试向量(测试于macOS、32 位 iOS、64 位 iOS)。
Swift 3 的代码可以在编辑历史中找到。
这是引用实现的翻译 rmd160.h , rmd160.c从 RIPEMD-160 页面从 C 到 Swift。我翻译了辅助宏和 compress()
功能(算法的“心脏”)尽可能“逐字”。这让我能够复制/粘贴大的 C 代码段,只对 Swift 进行微小的调整。
update()
和finalize()
方法提供了一个流接口(interface),类似于CommonCrypto 函数。
RIPEMD160.swift:
import Foundation
public struct RIPEMD160 {
private var MDbuf: (UInt32, UInt32, UInt32, UInt32, UInt32)
private var buffer: Data
private var count: Int64 // Total # of bytes processed.
public init() {
MDbuf = (0x67452301, 0xefcdab89, 0x98badcfe, 0x10325476, 0xc3d2e1f0)
buffer = Data()
count = 0
}
private mutating func compress(_ X: UnsafePointer<UInt32>) {
// *** Helper functions (originally macros in rmd160.h) ***
/* ROL(x, n) cyclically rotates x over n bits to the left */
/* x must be of an unsigned 32 bits type and 0 <= n < 32. */
func ROL(_ x: UInt32, _ n: UInt32) -> UInt32 {
return (x << n) | ( x >> (32 - n))
}
/* the five basic functions F(), G() and H() */
func F(_ x: UInt32, _ y: UInt32, _ z: UInt32) -> UInt32 {
return x ^ y ^ z
}
func G(_ x: UInt32, _ y: UInt32, _ z: UInt32) -> UInt32 {
return (x & y) | (~x & z)
}
func H(_ x: UInt32, _ y: UInt32, _ z: UInt32) -> UInt32 {
return (x | ~y) ^ z
}
func I(_ x: UInt32, _ y: UInt32, _ z: UInt32) -> UInt32 {
return (x & z) | (y & ~z)
}
func J(_ x: UInt32, _ y: UInt32, _ z: UInt32) -> UInt32 {
return x ^ (y | ~z)
}
/* the ten basic operations FF() through III() */
func FF(_ a: inout UInt32, _ b: UInt32, _ c: inout UInt32, _ d: UInt32, _ e: UInt32, _ x: UInt32, _ s: UInt32) {
a = a &+ F(b, c, d) &+ x
a = ROL(a, s) &+ e
c = ROL(c, 10)
}
func GG(_ a: inout UInt32, _ b: UInt32, _ c: inout UInt32, _ d: UInt32, _ e: UInt32, _ x: UInt32, _ s: UInt32) {
a = a &+ G(b, c, d) &+ x &+ 0x5a827999
a = ROL(a, s) &+ e
c = ROL(c, 10)
}
func HH(_ a: inout UInt32, _ b: UInt32, _ c: inout UInt32, _ d: UInt32, _ e: UInt32, _ x: UInt32, _ s: UInt32) {
a = a &+ H(b, c, d) &+ x &+ 0x6ed9eba1
a = ROL(a, s) &+ e
c = ROL(c, 10)
}
func II(_ a: inout UInt32, _ b: UInt32, _ c: inout UInt32, _ d: UInt32, _ e: UInt32, _ x: UInt32, _ s: UInt32) {
a = a &+ I(b, c, d) &+ x &+ 0x8f1bbcdc
a = ROL(a, s) &+ e
c = ROL(c, 10)
}
func JJ(_ a: inout UInt32, _ b: UInt32, _ c: inout UInt32, _ d: UInt32, _ e: UInt32, _ x: UInt32, _ s: UInt32) {
a = a &+ J(b, c, d) &+ x &+ 0xa953fd4e
a = ROL(a, s) &+ e
c = ROL(c, 10)
}
func FFF(_ a: inout UInt32, _ b: UInt32, _ c: inout UInt32, _ d: UInt32, _ e: UInt32, _ x: UInt32, _ s: UInt32) {
a = a &+ F(b, c, d) &+ x
a = ROL(a, s) &+ e
c = ROL(c, 10)
}
func GGG(_ a: inout UInt32, _ b: UInt32, _ c: inout UInt32, _ d: UInt32, _ e: UInt32, _ x: UInt32, _ s: UInt32) {
a = a &+ G(b, c, d) &+ x &+ 0x7a6d76e9
a = ROL(a, s) &+ e
c = ROL(c, 10)
}
func HHH(_ a: inout UInt32, _ b: UInt32, _ c: inout UInt32, _ d: UInt32, _ e: UInt32, _ x: UInt32, _ s: UInt32) {
a = a &+ H(b, c, d) &+ x &+ 0x6d703ef3
a = ROL(a, s) &+ e
c = ROL(c, 10)
}
func III(_ a: inout UInt32, _ b: UInt32, _ c: inout UInt32, _ d: UInt32, _ e: UInt32, _ x: UInt32, _ s: UInt32) {
a = a &+ I(b, c, d) &+ x &+ 0x5c4dd124
a = ROL(a, s) &+ e
c = ROL(c, 10)
}
func JJJ(_ a: inout UInt32, _ b: UInt32, _ c: inout UInt32, _ d: UInt32, _ e: UInt32, _ x: UInt32, _ s: UInt32) {
a = a &+ J(b, c, d) &+ x &+ 0x50a28be6
a = ROL(a, s) &+ e
c = ROL(c, 10)
}
// *** The function starts here ***
var (aa, bb, cc, dd, ee) = MDbuf
var (aaa, bbb, ccc, ddd, eee) = MDbuf
/* round 1 */
FF(&aa, bb, &cc, dd, ee, X[ 0], 11)
FF(&ee, aa, &bb, cc, dd, X[ 1], 14)
FF(&dd, ee, &aa, bb, cc, X[ 2], 15)
FF(&cc, dd, &ee, aa, bb, X[ 3], 12)
FF(&bb, cc, &dd, ee, aa, X[ 4], 5)
FF(&aa, bb, &cc, dd, ee, X[ 5], 8)
FF(&ee, aa, &bb, cc, dd, X[ 6], 7)
FF(&dd, ee, &aa, bb, cc, X[ 7], 9)
FF(&cc, dd, &ee, aa, bb, X[ 8], 11)
FF(&bb, cc, &dd, ee, aa, X[ 9], 13)
FF(&aa, bb, &cc, dd, ee, X[10], 14)
FF(&ee, aa, &bb, cc, dd, X[11], 15)
FF(&dd, ee, &aa, bb, cc, X[12], 6)
FF(&cc, dd, &ee, aa, bb, X[13], 7)
FF(&bb, cc, &dd, ee, aa, X[14], 9)
FF(&aa, bb, &cc, dd, ee, X[15], 8)
/* round 2 */
GG(&ee, aa, &bb, cc, dd, X[ 7], 7)
GG(&dd, ee, &aa, bb, cc, X[ 4], 6)
GG(&cc, dd, &ee, aa, bb, X[13], 8)
GG(&bb, cc, &dd, ee, aa, X[ 1], 13)
GG(&aa, bb, &cc, dd, ee, X[10], 11)
GG(&ee, aa, &bb, cc, dd, X[ 6], 9)
GG(&dd, ee, &aa, bb, cc, X[15], 7)
GG(&cc, dd, &ee, aa, bb, X[ 3], 15)
GG(&bb, cc, &dd, ee, aa, X[12], 7)
GG(&aa, bb, &cc, dd, ee, X[ 0], 12)
GG(&ee, aa, &bb, cc, dd, X[ 9], 15)
GG(&dd, ee, &aa, bb, cc, X[ 5], 9)
GG(&cc, dd, &ee, aa, bb, X[ 2], 11)
GG(&bb, cc, &dd, ee, aa, X[14], 7)
GG(&aa, bb, &cc, dd, ee, X[11], 13)
GG(&ee, aa, &bb, cc, dd, X[ 8], 12)
/* round 3 */
HH(&dd, ee, &aa, bb, cc, X[ 3], 11)
HH(&cc, dd, &ee, aa, bb, X[10], 13)
HH(&bb, cc, &dd, ee, aa, X[14], 6)
HH(&aa, bb, &cc, dd, ee, X[ 4], 7)
HH(&ee, aa, &bb, cc, dd, X[ 9], 14)
HH(&dd, ee, &aa, bb, cc, X[15], 9)
HH(&cc, dd, &ee, aa, bb, X[ 8], 13)
HH(&bb, cc, &dd, ee, aa, X[ 1], 15)
HH(&aa, bb, &cc, dd, ee, X[ 2], 14)
HH(&ee, aa, &bb, cc, dd, X[ 7], 8)
HH(&dd, ee, &aa, bb, cc, X[ 0], 13)
HH(&cc, dd, &ee, aa, bb, X[ 6], 6)
HH(&bb, cc, &dd, ee, aa, X[13], 5)
HH(&aa, bb, &cc, dd, ee, X[11], 12)
HH(&ee, aa, &bb, cc, dd, X[ 5], 7)
HH(&dd, ee, &aa, bb, cc, X[12], 5)
/* round 4 */
II(&cc, dd, &ee, aa, bb, X[ 1], 11)
II(&bb, cc, &dd, ee, aa, X[ 9], 12)
II(&aa, bb, &cc, dd, ee, X[11], 14)
II(&ee, aa, &bb, cc, dd, X[10], 15)
II(&dd, ee, &aa, bb, cc, X[ 0], 14)
II(&cc, dd, &ee, aa, bb, X[ 8], 15)
II(&bb, cc, &dd, ee, aa, X[12], 9)
II(&aa, bb, &cc, dd, ee, X[ 4], 8)
II(&ee, aa, &bb, cc, dd, X[13], 9)
II(&dd, ee, &aa, bb, cc, X[ 3], 14)
II(&cc, dd, &ee, aa, bb, X[ 7], 5)
II(&bb, cc, &dd, ee, aa, X[15], 6)
II(&aa, bb, &cc, dd, ee, X[14], 8)
II(&ee, aa, &bb, cc, dd, X[ 5], 6)
II(&dd, ee, &aa, bb, cc, X[ 6], 5)
II(&cc, dd, &ee, aa, bb, X[ 2], 12)
/* round 5 */
JJ(&bb, cc, &dd, ee, aa, X[ 4], 9)
JJ(&aa, bb, &cc, dd, ee, X[ 0], 15)
JJ(&ee, aa, &bb, cc, dd, X[ 5], 5)
JJ(&dd, ee, &aa, bb, cc, X[ 9], 11)
JJ(&cc, dd, &ee, aa, bb, X[ 7], 6)
JJ(&bb, cc, &dd, ee, aa, X[12], 8)
JJ(&aa, bb, &cc, dd, ee, X[ 2], 13)
JJ(&ee, aa, &bb, cc, dd, X[10], 12)
JJ(&dd, ee, &aa, bb, cc, X[14], 5)
JJ(&cc, dd, &ee, aa, bb, X[ 1], 12)
JJ(&bb, cc, &dd, ee, aa, X[ 3], 13)
JJ(&aa, bb, &cc, dd, ee, X[ 8], 14)
JJ(&ee, aa, &bb, cc, dd, X[11], 11)
JJ(&dd, ee, &aa, bb, cc, X[ 6], 8)
JJ(&cc, dd, &ee, aa, bb, X[15], 5)
JJ(&bb, cc, &dd, ee, aa, X[13], 6)
/* parallel round 1 */
JJJ(&aaa, bbb, &ccc, ddd, eee, X[ 5], 8)
JJJ(&eee, aaa, &bbb, ccc, ddd, X[14], 9)
JJJ(&ddd, eee, &aaa, bbb, ccc, X[ 7], 9)
JJJ(&ccc, ddd, &eee, aaa, bbb, X[ 0], 11)
JJJ(&bbb, ccc, &ddd, eee, aaa, X[ 9], 13)
JJJ(&aaa, bbb, &ccc, ddd, eee, X[ 2], 15)
JJJ(&eee, aaa, &bbb, ccc, ddd, X[11], 15)
JJJ(&ddd, eee, &aaa, bbb, ccc, X[ 4], 5)
JJJ(&ccc, ddd, &eee, aaa, bbb, X[13], 7)
JJJ(&bbb, ccc, &ddd, eee, aaa, X[ 6], 7)
JJJ(&aaa, bbb, &ccc, ddd, eee, X[15], 8)
JJJ(&eee, aaa, &bbb, ccc, ddd, X[ 8], 11)
JJJ(&ddd, eee, &aaa, bbb, ccc, X[ 1], 14)
JJJ(&ccc, ddd, &eee, aaa, bbb, X[10], 14)
JJJ(&bbb, ccc, &ddd, eee, aaa, X[ 3], 12)
JJJ(&aaa, bbb, &ccc, ddd, eee, X[12], 6)
/* parallel round 2 */
III(&eee, aaa, &bbb, ccc, ddd, X[ 6], 9)
III(&ddd, eee, &aaa, bbb, ccc, X[11], 13)
III(&ccc, ddd, &eee, aaa, bbb, X[ 3], 15)
III(&bbb, ccc, &ddd, eee, aaa, X[ 7], 7)
III(&aaa, bbb, &ccc, ddd, eee, X[ 0], 12)
III(&eee, aaa, &bbb, ccc, ddd, X[13], 8)
III(&ddd, eee, &aaa, bbb, ccc, X[ 5], 9)
III(&ccc, ddd, &eee, aaa, bbb, X[10], 11)
III(&bbb, ccc, &ddd, eee, aaa, X[14], 7)
III(&aaa, bbb, &ccc, ddd, eee, X[15], 7)
III(&eee, aaa, &bbb, ccc, ddd, X[ 8], 12)
III(&ddd, eee, &aaa, bbb, ccc, X[12], 7)
III(&ccc, ddd, &eee, aaa, bbb, X[ 4], 6)
III(&bbb, ccc, &ddd, eee, aaa, X[ 9], 15)
III(&aaa, bbb, &ccc, ddd, eee, X[ 1], 13)
III(&eee, aaa, &bbb, ccc, ddd, X[ 2], 11)
/* parallel round 3 */
HHH(&ddd, eee, &aaa, bbb, ccc, X[15], 9)
HHH(&ccc, ddd, &eee, aaa, bbb, X[ 5], 7)
HHH(&bbb, ccc, &ddd, eee, aaa, X[ 1], 15)
HHH(&aaa, bbb, &ccc, ddd, eee, X[ 3], 11)
HHH(&eee, aaa, &bbb, ccc, ddd, X[ 7], 8)
HHH(&ddd, eee, &aaa, bbb, ccc, X[14], 6)
HHH(&ccc, ddd, &eee, aaa, bbb, X[ 6], 6)
HHH(&bbb, ccc, &ddd, eee, aaa, X[ 9], 14)
HHH(&aaa, bbb, &ccc, ddd, eee, X[11], 12)
HHH(&eee, aaa, &bbb, ccc, ddd, X[ 8], 13)
HHH(&ddd, eee, &aaa, bbb, ccc, X[12], 5)
HHH(&ccc, ddd, &eee, aaa, bbb, X[ 2], 14)
HHH(&bbb, ccc, &ddd, eee, aaa, X[10], 13)
HHH(&aaa, bbb, &ccc, ddd, eee, X[ 0], 13)
HHH(&eee, aaa, &bbb, ccc, ddd, X[ 4], 7)
HHH(&ddd, eee, &aaa, bbb, ccc, X[13], 5)
/* parallel round 4 */
GGG(&ccc, ddd, &eee, aaa, bbb, X[ 8], 15)
GGG(&bbb, ccc, &ddd, eee, aaa, X[ 6], 5)
GGG(&aaa, bbb, &ccc, ddd, eee, X[ 4], 8)
GGG(&eee, aaa, &bbb, ccc, ddd, X[ 1], 11)
GGG(&ddd, eee, &aaa, bbb, ccc, X[ 3], 14)
GGG(&ccc, ddd, &eee, aaa, bbb, X[11], 14)
GGG(&bbb, ccc, &ddd, eee, aaa, X[15], 6)
GGG(&aaa, bbb, &ccc, ddd, eee, X[ 0], 14)
GGG(&eee, aaa, &bbb, ccc, ddd, X[ 5], 6)
GGG(&ddd, eee, &aaa, bbb, ccc, X[12], 9)
GGG(&ccc, ddd, &eee, aaa, bbb, X[ 2], 12)
GGG(&bbb, ccc, &ddd, eee, aaa, X[13], 9)
GGG(&aaa, bbb, &ccc, ddd, eee, X[ 9], 12)
GGG(&eee, aaa, &bbb, ccc, ddd, X[ 7], 5)
GGG(&ddd, eee, &aaa, bbb, ccc, X[10], 15)
GGG(&ccc, ddd, &eee, aaa, bbb, X[14], 8)
/* parallel round 5 */
FFF(&bbb, ccc, &ddd, eee, aaa, X[12] , 8)
FFF(&aaa, bbb, &ccc, ddd, eee, X[15] , 5)
FFF(&eee, aaa, &bbb, ccc, ddd, X[10] , 12)
FFF(&ddd, eee, &aaa, bbb, ccc, X[ 4] , 9)
FFF(&ccc, ddd, &eee, aaa, bbb, X[ 1] , 12)
FFF(&bbb, ccc, &ddd, eee, aaa, X[ 5] , 5)
FFF(&aaa, bbb, &ccc, ddd, eee, X[ 8] , 14)
FFF(&eee, aaa, &bbb, ccc, ddd, X[ 7] , 6)
FFF(&ddd, eee, &aaa, bbb, ccc, X[ 6] , 8)
FFF(&ccc, ddd, &eee, aaa, bbb, X[ 2] , 13)
FFF(&bbb, ccc, &ddd, eee, aaa, X[13] , 6)
FFF(&aaa, bbb, &ccc, ddd, eee, X[14] , 5)
FFF(&eee, aaa, &bbb, ccc, ddd, X[ 0] , 15)
FFF(&ddd, eee, &aaa, bbb, ccc, X[ 3] , 13)
FFF(&ccc, ddd, &eee, aaa, bbb, X[ 9] , 11)
FFF(&bbb, ccc, &ddd, eee, aaa, X[11] , 11)
/* combine results */
MDbuf = (MDbuf.1 &+ cc &+ ddd,
MDbuf.2 &+ dd &+ eee,
MDbuf.3 &+ ee &+ aaa,
MDbuf.4 &+ aa &+ bbb,
MDbuf.0 &+ bb &+ ccc)
}
public mutating func update(data: Data) {
var X = [UInt32](repeating: 0, count: 16)
var pos = data.startIndex
var length = data.count
// Process remaining bytes from last call:
if buffer.count > 0 && buffer.count + length >= 64 {
let amount = 64 - buffer.count
buffer.append(data[..<amount])
X.withUnsafeMutableBytes {
_ = buffer.copyBytes(to: $0)
}
compress(X)
pos += amount
length -= amount
}
// Process 64 byte chunks:
while length >= 64 {
X.withUnsafeMutableBytes {
_ = data[pos..<pos+64].copyBytes(to: $0)
}
compress(X)
pos += 64
length -= 64
}
// Save remaining unprocessed bytes:
buffer = data[pos...]
count += Int64(data.count)
}
public mutating func finalize() -> Data {
var X = [UInt32](repeating: 0, count: 16)
/* append the bit m_n == 1 */
buffer.append(0x80)
X.withUnsafeMutableBytes {
_ = buffer.copyBytes(to: $0)
}
if (count & 63) > 55 {
/* length goes to next block */
compress(X)
X = [UInt32](repeating: 0, count: 16)
}
/* append length in bits */
let lswlen = UInt32(truncatingIfNeeded: count)
let mswlen = UInt32(UInt64(count) >> 32)
X[14] = lswlen << 3
X[15] = (lswlen >> 29) | (mswlen << 3)
compress(X)
buffer = Data()
let result = [MDbuf.0, MDbuf.1, MDbuf.2, MDbuf.3, MDbuf.4]
return result.withUnsafeBytes { Data($0) }
}
}
这里是计算消息散列的“一次性”函数(以 Data
形式给出)或者作为 String
):
RIPEMD160-Ext.swift:
import Foundation
public extension RIPEMD160 {
static func hash(message: Data) -> Data {
var md = RIPEMD160()
md.update(data: message)
return md.finalize()
}
static func hash(message: String) -> Data {
return RIPEMD160.hash(message: message.data(using: .utf8)!)
}
}
最后是对应的消息验证码。该算法被采取从伪代码在 Wikipedia: Hash-based message authentication code :
RIPEMD160-HMAC.swift:
import Foundation
public extension RIPEMD160 {
static func hmac(key: Data, message: Data) -> Data {
var key = key
key.count = 64 // Truncate to 64 bytes or fill-up with zeros.
let outerKeyPad = Data(key.map { $0 ^ 0x5c })
let innerKeyPad = Data(key.map { $0 ^ 0x36 })
var innerMd = RIPEMD160()
innerMd.update(data: innerKeyPad)
innerMd.update(data: message)
var outerMd = RIPEMD160()
outerMd.update(data: outerKeyPad)
outerMd.update(data: innerMd.finalize())
return outerMd.finalize()
}
static func hmac(key: Data, message: String) -> Data {
return RIPEMD160.hmac(key: key, message: message.data(using: .utf8)!)
}
static func hmac(key: String, message: String) -> Data {
return RIPEMD160.hmac(key: key.data(using: .utf8)!, message: message)
}
}
要将消息摘要打印为十六进制编码的字符串,请使用以下方法 How to convert Data to hex string in swift可以使用:
extension Data {
func hexEncodedString() -> String {
return map { String(format: "%02hhx", $0) }.joined()
}
}
示例 1:
let msg = "Hello World"
let hash = RIPEMD160.hash(message: msg).hexEncodedString()
print(hash) // a830d7beb04eb7549ce990fb7dc962e499a27230
示例 2(您的示例):
let hmac = RIPEMD160.hmac(key: "test", message: "string").hexEncodedString()
print(hmac) // 37241f2513c60ae4d9b3b8d0d30517445f451fa5
关于objective-c - Swift 使用 hash_hmac 和 ripemd160 散列字符串,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43091858/
我有生成 hash_hmac 的 php 代码 $concate=array(); $validation_token = hash_hmac('md5', implode("|", $concate
我正在开发一个新的 moodle 模块,它提供与 Windows Live 的集成。 使用实时身份验证时,我得到一个空白页面。打开 PHP 错误记录并获取: Fatal error: Call to
我需要签署我的亚马逊产品 API 请求,接受的代码如下。 base64_encode(hash_hmac('sha256', $request, $key, true)); 这在我使用 64 位 Li
阅读 this excellent answer关于密码散列和想知道如何实现它: The Wicked Flea写道: Generate a nonce for each user; this alo
我想知道,有没有办法在erlang中实现hash_hmac("sha256", $token, $signkey, true) (php)? 最佳答案 看看http://erlang.org/doc/
什么是等效的: hash_hmac('sha256', 'data', 'key') 如果我使用的是 openssl_*? openssl_digest 不接受 $key 参数。 最佳答案 此函数使用
$key = "12345678876543211234567887654321"; $iv = "1234567887654321"; $plaindata = "This is a test st
我正在尝试转换这个 php 函数: string hash_hmac ( string $algo , string $data , string $key [, bool $raw_output =
我刚刚从这个站点获得了一个函数,它描述了如何使用哈希生成安全密码。功能如下 function hash_password($password, $nonce) { global $site_key
我正在尝试为以下项目编写 python 身份验证机器人:https://comkort.com/page/private_api 没有完整的 php 示例。我猜有人可以把它放在这里。 只有一段php代
我是新来的,我有问题。 你能告诉我为什么 hex_hmac_sha1(Javascript 函数)不如 hash_hmac(PHP 函数)好吗。 如果是 A-z 字母就没问题,但其他字符就不行。 例如
我有以下 PHP 函数 public function encodePassword($raw, $salt) { return hash_hmac('sha1', $raw
我有在我的 PHP 应用程序中运行的代码。在 PHP 中,我使用以下代码对 url 进行签名: private static function __getHash($string) { ret
我在 stack-overflow 中看到了一些相同的问题,但它对我没有帮助。 我有这个 php 代码 $signature=base64_encode(hash_hmac("sha256", tri
我正在创建一个更安全的用户密码表,其中包含用户名、强随机盐和 PHP 中的加盐/散列密码,如下所示: $salt = bin2hex(openssl_random_pseudo_bytes(64));
我正在将 PHP 应用程序移植到 C++。 PHP 应用程序正在使用此函数: hash_hmac — Generate a keyed hash value using the HMAC method
我有生成 hash_hmac 的 php 代码 key = base64_encode(hash_hmac('sha1',$public_key, $private_key,TRUE)); 我已经尝试
我遇到 hash_hmac 和 AWS 签名版本 4 的问题。我正在使用他们在此处列出的示例:http://docs.aws.amazon.com/general/latest/gr/sigv4-ca
我正在移植一个php脚本到node,我对加密不是很了解。 php脚本使用了这个函数: hash_hmac('sha512', text, key); 因此,我需要在 Node js 中实现一个函数,以
这个问题在这里已经有了答案: Implementation HMAC-SHA1 in python (8 个回答) 关闭5年前。 我想将我的访问者转发到第 3 方支付网站。该第 3 方将处理他们的付款
我是一名优秀的程序员,十分优秀!