gpt4 book ai didi

java - iOS 中的 RSA SHA256 签名和 Java 上的验证

转载 作者:行者123 更新时间:2023-11-30 02:37:28 26 4
gpt4 key购买 nike

  1. 我使用 SecKeyGeneratePair 生成了 RSA key 对。 key 大小(以位为单位)为 2048。

    NSDictionary *privateAttributes = @{(NSString *)kSecAttrIsPermanent: @YES, (NSString *)kSecAttrApplicationTag: PrivTag};
    NSDictionary *publicAttributes = @{(NSString *)kSecAttrIsPermanent: @YES, (NSString *)kSecAttrApplicationTag: PubTag};

    NSDictionary *pairAttributes = @{(NSString *)kSecAttrKeyType: (NSString *)kSecAttrKeyTypeRSA, (NSString *)kSecAttrKeySizeInBits: @2048, (NSString *)kSecPublicKeyAttrs: publicAttributes, (NSString *)kSecPrivateKeyAttrs: privateAttributes};

    SecKeyRef publicKeyRef;
    SecKeyRef privateKeyRef;
    OSStatus osStatus = SecKeyGeneratePair((CFDictionaryRef)pairAttributes, &publicKeyRef, &privateKeyRef);
    switch (osStatus) {
    case noErr:
    break;
    default:
    break;
    }
  2. 创建 X.509 格式的公钥并将其发送到服务器。

  3. 使用 CC_SHA256 创建自定义字符串的 SHA256 摘要。

    NSMutableData *hash = [NSMutableData dataWithLength:(NSUInteger)CC_SHA256_DIGEST_LENGTH];
    NSData *data = [stringToSign dataUsingEncoding:NSUTF8StringEncoding];
    CC_SHA256(data.bytes, (CC_LONG)data.length, hash.mutableBytes);
  4. 使用 kSecPaddingPKCS1SHA256 通过 SecKeyRawSign 方法对字符串进行签名。

    // Sign the hash with the private key
    size_t blockSize = SecKeyGetBlockSize(privateKeyRef);

    NSUInteger hashDataLength = hash.length;
    const unsigned char *hashData = (const unsigned char *)hash.bytes;

    NSMutableData *result = [NSMutableData dataWithLength:blockSize];

    uint8_t *signedHashBytes = malloc(blockSize * sizeof(uint8_t));
    memset((void *) signedHashBytes, 0x0, blockSize);
    size_t encryptedDataLength = blockSize;

    OSStatus status = SecKeyRawSign(privateKeyRef, kSecPaddingPKCS1SHA256, hashData, hashDataLength, signedHashBytes, &encryptedDataLength);

    NSData *signedHash = [NSData dataWithBytes:(const void *) signedHashBytes length:(NSUInteger) encryptedDataLength];
  5. 对签名数据应用 base64 并将其发送到服务器。

  6. java服务器无法用公钥验证它。

我在 Swift 中有与上面相同的代码。作为调试步骤,我也导出了我的私钥,并尝试在 java 中遵循完全相同的步骤。直到第 3 步一切都是一样的。因此,iOS 创建与 java 应用程序相同的摘要。第四步,签名创建与 java 代码不同的输出。

这是java代码:

final Signature instance = Signature.getInstance("SHA256withRSA");
instance.initSign(privateKey);
instance.update(MessageDigest.getInstance("SHA-256").digest(rawString.toString().getBytes("UTF-8")));

最佳答案

iOS 和 Java 的数字签名 API 不同,但结果是相同的。

带有 kSecPaddingPKCS1SHA256 的 iOS SecKeyRawSign 使用 SHA256 摘要,但在 Java 中 Signature.sign 需要原始数据,并且它会生成摘要+pkcs1。使用

instance.update(rawString.toString().getBytes("UTF-8"));

关于java - iOS 中的 RSA SHA256 签名和 Java 上的验证,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42689108/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com