关于go语言的RSA加解密的介绍,这里有一篇文章,已经介绍的很完整了。
对应的go语言的加解密代码,参考git。
因为原文跨语言是跟php,我这里要跟c语言进行交互,所以,这里贴上c语言的例子。
参考原文:http://hayageek.com/rsa-encryption-decryption-openssl-c/
#include <openssl/pem.h> #include <openssl/ssl.h> #include <openssl/rsa.h> #include <openssl/evp.h> #include <openssl/bio.h> #include <openssl/err.h> #include <openssl/buffer.h> #include <stdio.h> #include <stdint.h> //编译 //gcc rsa_example.c -o example -L/usr/local/Cellar/openssl/1.0.2e/lib/ -lssl -lcrypto //openssl的base64编解码: https://gist.github.com/barrysteyn/7308212 int Base64Encode(const unsigned char* buffer, size_t length, char** b64text) { BIO *bio, *b64; BUF_MEM *bufferPtr; b64 = BIO_new(BIO_f_base64()); bio = BIO_new(BIO_s_mem()); bio = BIO_push(b64, bio); BIO_set_flags(bio, BIO_FLAGS_BASE64_NO_NL); BIO_write(bio, buffer, length); BIO_flush(bio); BIO_get_mem_ptr(bio, &bufferPtr); BIO_set_close(bio, BIO_NOCLOSE); BIO_free_all(bio); *b64text=(*bufferPtr).data; return (0); //success } int padding = RSA_PKCS1_PADDING; RSA * createRSA(unsigned char * key,int public) { RSA *rsa= NULL; BIO *keybio ; keybio = BIO_new_mem_buf(key, -1); if (keybio==NULL) { printf( "Failed to create key BIO"); return 0; } if(public) { rsa = PEM_read_bio_RSA_PUBKEY(keybio, &rsa,NULL, NULL); } else { rsa = PEM_read_bio_RSAPrivateKey(keybio, &rsa,NULL, NULL); } if(rsa == NULL) { printf( "Failed to create RSA"); } return rsa; } int public_encrypt(unsigned char * data,int data_len,unsigned char * key, unsigned char *encrypted) { RSA * rsa = createRSA(key,1); int result = RSA_public_encrypt(data_len,data,encrypted,rsa,padding); return result; } int private_decrypt(unsigned char * enc_data,int data_len,unsigned char * key, unsigned char *decrypted) { RSA * rsa = createRSA(key,0); int result = RSA_private_decrypt(data_len,enc_data,decrypted,rsa,padding); return result; } int private_encrypt(unsigned char * data,int data_len,unsigned char * key, unsigned char *encrypted) { RSA * rsa = createRSA(key,0); int result = RSA_private_encrypt(data_len,data,encrypted,rsa,padding); return result; } int public_decrypt(unsigned char * enc_data,int data_len,unsigned char * key, unsigned char *decrypted) { RSA * rsa = createRSA(key,1); int result = RSA_public_decrypt(data_len,enc_data,decrypted,rsa,padding); return result; } void printLastError(char *msg) { char * err = malloc(130);; ERR_load_crypto_strings(); ERR_error_string(ERR_get_error(), err); printf("%s ERROR: %s\n",msg, err); free(err); } int main(){ char plainText[2048/8] = "1024"; //原始数据为字符串1024;key length : 2048, 数据最长为 keylen/8个char char publicKey[]="-----BEGIN PUBLIC KEY-----\n""MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAy8Dbv8prpJ/0kKhlGeJY\n""ozo2t60EG8L0561g13R29LvMR5hyvGZlGJpmn65+A4xHXInJYiPuKzrKUnApeLZ+\n""vw1HocOAZtWK0z3r26uA8kQYOKX9Qt/DbCdvsF9wF8gRK0ptx9M6R13NvBxvVQAp\n""fc9jB9nTzphOgM4JiEYvlV8FLhg9yZovMYd6Wwf3aoXK891VQxTr/kQYoq1Yp+68\n""i6T4nNq7NWC+UNVjQHxNQMQMzU6lWCX8zyg3yH88OAQkUXIXKfQ+NkvYQ1cxaMoV\n""PpY72+eVthKzpMeyHkBn7ciumk5qgLTEJAfWZpe4f4eFZj/Rc8Y8Jj2IS5kVPjUy\n""wQIDAQAB\n""-----END PUBLIC KEY-----\n"; char privateKey[]="-----BEGIN RSA PRIVATE KEY-----\n""MIIEowIBAAKCAQEAy8Dbv8prpJ/0kKhlGeJYozo2t60EG8L0561g13R29LvMR5hy\n""vGZlGJpmn65+A4xHXInJYiPuKzrKUnApeLZ+vw1HocOAZtWK0z3r26uA8kQYOKX9\n""Qt/DbCdvsF9wF8gRK0ptx9M6R13NvBxvVQApfc9jB9nTzphOgM4JiEYvlV8FLhg9\n""yZovMYd6Wwf3aoXK891VQxTr/kQYoq1Yp+68i6T4nNq7NWC+UNVjQHxNQMQMzU6l\n""WCX8zyg3yH88OAQkUXIXKfQ+NkvYQ1cxaMoVPpY72+eVthKzpMeyHkBn7ciumk5q\n""gLTEJAfWZpe4f4eFZj/Rc8Y8Jj2IS5kVPjUywQIDAQABAoIBADhg1u1Mv1hAAlX8\n""omz1Gn2f4AAW2aos2cM5UDCNw1SYmj+9SRIkaxjRsE/C4o9sw1oxrg1/z6kajV0e\n""N/t008FdlVKHXAIYWF93JMoVvIpMmT8jft6AN/y3NMpivgt2inmmEJZYNioFJKZG\n""X+/vKYvsVISZm2fw8NfnKvAQK55yu+GRWBZGOeS9K+LbYvOwcrjKhHz66m4bedKd\n""gVAix6NE5iwmjNXktSQlJMCjbtdNXg/xo1/G4kG2p/MO1HLcKfe1N5FgBiXj3Qjl\n""vgvjJZkh1as2KTgaPOBqZaP03738VnYg23ISyvfT/teArVGtxrmFP7939EvJFKpF\n""1wTxuDkCgYEA7t0DR37zt+dEJy+5vm7zSmN97VenwQJFWMiulkHGa0yU3lLasxxu\n""m0oUtndIjenIvSx6t3Y+agK2F3EPbb0AZ5wZ1p1IXs4vktgeQwSSBdqcM8LZFDvZ\n""uPboQnJoRdIkd62XnP5ekIEIBAfOp8v2wFpSfE7nNH2u4CpAXNSF9HsCgYEA2l8D\n""JrDE5m9Kkn+J4l+AdGfeBL1igPF3DnuPoV67BpgiaAgI4h25UJzXiDKKoa706S0D\n""4XB74zOLX11MaGPMIdhlG+SgeQfNoC5lE4ZWXNyESJH1SVgRGT9nBC2vtL6bxCVV\n""WBkTeC5D6c/QXcai6yw6OYyNNdp0uznKURe1xvMCgYBVYYcEjWqMuAvyferFGV+5\n""nWqr5gM+yJMFM2bEqupD/HHSLoeiMm2O8KIKvwSeRYzNohKTdZ7FwgZYxr8fGMoG\n""PxQ1VK9DxCvZL4tRpVaU5Rmknud9hg9DQG6xIbgIDR+f79sb8QjYWmcFGc1SyWOA\n""SkjlykZ2yt4xnqi3BfiD9QKBgGqLgRYXmXp1QoVIBRaWUi55nzHg1XbkWZqPXvz1\n""I3uMLv1jLjJlHk3euKqTPmC05HoApKwSHeA0/gOBmg404xyAYJTDcCidTg6hlF96\n""ZBja3xApZuxqM62F6dV4FQqzFX0WWhWp5n301N33r0qR6FumMKJzmVJ1TA8tmzEF\n""yINRAoGBAJqioYs8rK6eXzA8ywYLjqTLu/yQSLBn/4ta36K8DyCoLNlNxSuox+A5\n""w6z2vEfRVQDq4Hm4vBzjdi3QfYLNkTiTqLcvgWZ+eX44ogXtdTDO7c+GeMKWz4XX\n""uJSUVL5+CVjKLjZEJ6Qc2WZLl94xSwL71E41H4YciVnSCQxVc4Jw\n""-----END RSA PRIVATE KEY-----\n"; unsigned char encrypted[4098]={}; unsigned char decrypted[4098]={}; int encrypted_length= public_encrypt(plainText,strlen(plainText),publicKey,encrypted); if(encrypted_length == -1) { printLastError("Public Encrypt failed "); exit(0); } printf("Encrypted length =%d\n",encrypted_length); char *b64text; Base64Encode( encrypted, encrypted_length, &b64text); printf("Base64Encode = %s\n", b64text); int decrypted_length = private_decrypt(encrypted,encrypted_length,privateKey, decrypted); if(decrypted_length == -1) { printLastError("Private Decrypt failed "); exit(0); } printf("Decrypted Text =%s\n",decrypted); printf("Decrypted Length =%d\n",decrypted_length); encrypted_length= private_encrypt(plainText,strlen(plainText),privateKey,encrypted); if(encrypted_length == -1) { printLastError("Private Encrypt failed"); exit(0); } printf("Encrypted length =%d\n",encrypted_length); decrypted_length = public_decrypt(encrypted,encrypted_length,publicKey, decrypted); if(decrypted_length == -1) { printLastError("Public Decrypt failed"); exit(0); } printf("Decrypted Text =%s\n",decrypted); printf("Decrypted Length =%d\n",decrypted_length); }
编译执行之后,可以得到加密之后的base64数据:
./example Encrypted length =256 Base64Encode = BXFuS6snRRhYUQhTYKG00UoGMzaptbZpaw7h+JEA+yP1sEd5dXaBEjdzzZ8jXRVfjigYFj41zEBSDsafxO440+vi/aODOAY1f4Q2dKf5eBLnXDyN9uT6uxCp67XgZC3YkN+iufMOKIEjSbb361kZrRLwl+6OUt4EYvkhmKl5YpklM+qQYyGW5xyCU5MYMUTXJoAthRTeNuoloSiZDQWKPH4i7bVfR/XDjXIA3iNWfoy5552L4AdtyRhRNvZ0RerbVtPqdWABvJX39hbskmGuzY9HtoxOQaoD0IWGHx29VmCM3JRrTvStnEKjYnUNT9ikbeK1gXX5JjU6HmLHbgPKUg== Decrypted Text =1024 Decrypted Length =4 Encrypted length =256 Decrypted Text =1024 Decrypted Length =4
把base64数据,传递给go语言(这里需要把对应的go语言的公钥、私钥替换成c语言中的示例),用私钥进行解密,可以得到对应的原始数据,这样验证 c 和 go之间的加解密OK。
go run rsa.go -d BXFuS6snRRhYUQhTYKG00UoGMzaptbZpaw7h+JEA+yP1sEd5dXaBEjdzzZ8jXRVfjigYFj41zEBSDsafxO440+vi/aODOAY1f4Q2dKf5eBLnXDyN9uT6uxCp67XgZC3YkN+iufMOKIEjSbb361kZrRLwl+6OUt4EYvkhmKl5YpklM+qQYyGW5xyCU5MYMUTXJoAthRTeNuoloSiZDQWKPH4i7bVfR/XDjXIA3iNWfoy5552L4AdtyRhRNvZ0RerbVtPqdWABvJX39hbskmGuzY9HtoxOQaoD0IWGHx29VmCM3JRrTvStnEKjYnUNT9ikbeK1gXX5JjU6HmLHbgPKUg== [1024]
时间: 2024-10-13 01:47:47