📄 pubcrypt.c
字号:
pubkey->e = bn_e; pubkey->n = bn_n; *rsa=pubkey; return 0; free_bn_n_out: if (bn_n) BN_free(bn_n); free_bn_e_out: if (bn_e) BN_free(bn_e); free_pubkey_out: if (pubkey) RSA_free(pubkey); return rc;}static intpcrypt_crypt_set_rsa_key(unsigned long cap,RSA *rsa) { int rc; int index; if ( (!(cap & RSA_CAPS)) || (!rsa) ) return -EINVAL; rc=get_rsa_key_index(cap,&index); if (rc) return rc;g_static_mutex_lock(&rsa_key_mutex); if (rsa_keys[index]) RSA_free(rsa_keys[index]); rsa_keys[index]=rsa;g_static_mutex_unlock(&rsa_key_mutex); return 0;}static int select_rsa_key_for_answer(unsigned long peer_cap,unsigned long *selected_key,int speed){ unsigned long candidates; int i; int added_num=1; int first=0; int key_type; if (!selected_key) return -EINVAL; candidates=(get_asymkey_part(peer_cap) & hostinfo_get_ipmsg_crypt_capability()); if (speed) { first=RSA_KEY_MAX-1; added_num=-1; } for (i=first; ((i>=0) && (i<RSA_KEY_MAX) && (!(key2ipmsg_key_type[i] & candidates))); i+=added_num); if (!( (i>=0) && (i<RSA_KEY_MAX) )) return -ENOENT; *selected_key=key2ipmsg_key_type[i]; dbg_out("Selected key name in ipmsg:0x%x\n",key2ipmsg_key_type[i]); return 0;}intpcrypt_get_rsa_key_length(unsigned long key_type,size_t *len){ size_t keylen; int rc; if (!len) return -EINVAL; switch (key_type) { case IPMSG_RSA_512: keylen=512; break; case IPMSG_RSA_1024: keylen=1024; break; default: /* デフォルトは, 2048 */ case IPMSG_RSA_2048: keylen=2048; break; } *len=keylen; rc=0; return rc;}int pcrypt_crypt_parse_anspubkey(const char *string,unsigned long *peer_cap,unsigned char **crypt_e,unsigned char **crypt_n){ char *val_e=NULL,*val_n=NULL; char *sp=NULL; char *ep=NULL; char *buffer; char *hex; ssize_t remains; unsigned long cap; size_t len; int rc=0; if ( (!string) || (!peer_cap) || (!crypt_e) || (!crypt_n) ) return -EINVAL; buffer=g_strdup(string); if (!buffer) return -ENOMEM; len=strlen(string); remains=len; /* * 暗号化能力 */ sp=buffer; ep=memchr(sp, ':', remains); if (!ep) { rc=-EINVAL; goto err_out; } *ep='\0'; remains =len - ((unsigned long)ep-(unsigned long)buffer); if (remains<=0) { rc=-EINVAL; goto err_out; } ++ep; cap=(unsigned long)strtol(sp, (char **)NULL, 16); dbg_out("parsed capability:%x\n",cap); sp=ep; /* * 公開指数 */ ep=memchr(sp, '-', remains); if (!ep) { rc=-EINVAL; goto err_out; } *ep='\0'; remains =len - ((unsigned long)ep-(unsigned long)buffer); if (remains<=0) { rc=-EINVAL; goto err_out; } ++ep; dbg_out("parsed public exponential:%s\n",sp); val_e=g_strdup(sp); if (!val_e) { rc = -ENOMEM; goto err_out; } sp=ep; /* *公開モジューロ(法) */ dbg_out("parsed public modulo:%s\n",sp); val_n=g_strdup(sp); if (!val_n) { rc = -ENOMEM; dbg_out("Error code:%d\n",rc); goto err_out; } /* *返却 */ *peer_cap = cap; *crypt_e = val_e; *crypt_n = val_n; rc=0;err_out: g_free(buffer); return rc;}int pcrypt_crypt_generate_anspubkey_string(unsigned long cap,const char **message_p){ int rc; char *buffer; char *string; char *hex_e,*hex_n; RSA *rsa=NULL; unsigned long skey_type=0,akey_type=0,sign_type=0; if ( (!message_p) && (!(cap & RSA_CAPS)) ) return -EINVAL; g_assert(!akey_type); rc=select_rsa_key_for_answer(cap, &akey_type, hostinfo_refer_ipmsg_crypt_policy_is_speed()); if (rc) return rc; dbg_out("RSA key:%x\n",akey_type); g_assert(!skey_type); rc=select_symmetric_key(cap, &skey_type, hostinfo_refer_ipmsg_crypt_policy_is_speed()); if (rc) return rc; dbg_out("sym key:%x\n",skey_type); g_assert(!sign_type); rc=select_signature(cap,&sign_type,hostinfo_refer_ipmsg_crypt_policy_is_speed()); if (rc) dbg_out("No sign:%x\n",sign_type); else dbg_out("Sign type:%x\n",sign_type); rc=pcrypt_crypt_refer_rsa_key(akey_type,&rsa); if (rc){ dbg_out("Can not find rsa key:%d\n",rc); return -EINVAL; } buffer=g_malloc(_MSG_BUF_SIZE); if (!buffer) return -ENOMEM; memset(buffer,0,_MSG_BUF_SIZE); rc=-ENOMEM; hex_e=BN_bn2hex(rsa->e); if (!hex_e) goto free_buffer_out; hex_n=BN_bn2hex(rsa->n); if (!hex_n) goto free_hex_n_out; dbg_out("hex-e:%s hex-n:%s\n",hex_e,hex_n); snprintf(buffer,_MSG_BUF_SIZE-1,"%x:%s-%s",(akey_type|skey_type|sign_type),hex_e,hex_n); dbg_out("Generated:%s\n",buffer); string=g_strdup(buffer); *message_p=string; rc=0; free_hex_n_out: if (hex_n) OPENSSL_free(hex_n); free_hex_e_out: if (hex_e) OPENSSL_free(hex_e); free_buffer_out: if (buffer) g_free(buffer); return rc;}int pcrypt_crypt_generate_getpubkey_string(unsigned long cap,const char **message_p){ char *buffer; char *string; if (!message_p) return -EINVAL; buffer=g_malloc(_MSG_BUF_SIZE); if (!buffer) return -ENOMEM; memset(buffer,0,_MSG_BUF_SIZE); snprintf(buffer,_MSG_BUF_SIZE-1,"%x",cap); dbg_out("Generated:%s\n",buffer); string=g_strdup(buffer); *message_p=string; if (buffer) g_free(buffer); return 0;}intpcrypt_crypt_refer_rsa_key_with_index(int index,RSA **rsa_p) { int rc; if ( (index<0) || (RSA_KEY_MAX<=index) ) return -EINVAL; rc=0;g_static_mutex_lock(&rsa_key_mutex); if (rsa_keys[index]) *rsa_p=rsa_keys[index]; else rc=-ENOENT;g_static_mutex_unlock(&rsa_key_mutex); return rc;}intpcrypt_crypt_refer_rsa_key(unsigned long cap,RSA **rsa_p) { int rc; int index; if (!(cap & RSA_CAPS)) return -EINVAL; rc=0; rc=get_rsa_key_index(cap,&index); if (rc) return rc;g_static_mutex_lock(&rsa_key_mutex); if (rsa_keys[index]) *rsa_p=rsa_keys[index]; else rc=-ENOENT;g_static_mutex_unlock(&rsa_key_mutex); return rc;}intpcrypt_crypt_init_keys(void) { int rc; int i; int keylen; RSA *rsa=NULL; ERR_load_crypto_strings(); for(i=0;key2ipmsg_key_type[i]>=0;++i) { rc=pcrypt_load_rsa_key(key2ipmsg_key_type[i],NULL); if (!rc) continue; /* 鍵をロードした */ dbg_out("Can not load key:rc=%d\n",rc); rc=generate_rsa_key(&rsa,key2ipmsg_key_type[i]); if (rc) { rc=pcrypt_get_rsa_key_length(key2ipmsg_key_type[i],&keylen); if (!rc) err_out("Can not generate key length:%d\n",keylen); else err_out("Can not generate key length invalid key index:%d\n",i); rsa_keys[i]=NULL; continue; } rc=pcrypt_crypt_set_rsa_key(key2ipmsg_key_type[i],rsa); if (rc) err_out("Can not set key length:%d\n",keylen); } return 0;}intpcrypt_crypt_release_keys(void) { int rc; int i; int keylen; ERR_free_strings(); for(i=0;key2ipmsg_key_type[i]>=0;++i) { rc=pcrypt_get_rsa_key_length(key2ipmsg_key_type[i],&keylen); if (!rc) dbg_out("clear key length:%d\n",keylen); rc=pcrypt_store_rsa_key(key2ipmsg_key_type[i],NULL); if (rc) err_out("Can not store key: length: %d\n",keylen); if (rsa_keys[i]){ RSA_free(rsa_keys[i]); rsa_keys[i]=NULL; } } return 0;}intpcrypt_encrypt_message(const unsigned long peer_cap,const char *peer_e,const char *peer_n,const char *plain,size_t plain_length,char **ret_buff,unsigned long *akey_type){ int rc; RSA *pubkey=NULL; BIGNUM *bn_encoded_key=NULL; size_t enc_len; size_t crypt_len; char *encrypted_key=NULL; char *encoded_key=NULL; char errbuf[1024]; unsigned long key_type; if ( (!peer_e) || (!peer_n) || (!plain) || (!ret_buff) ) return -EINVAL; rc=convert_peer_key(peer_e,peer_n,&pubkey); if (rc) return rc; rc=-ENOMEM; enc_len=RSA_size(pubkey); dbg_out("Public key:e=%s n=%s len=%d\n", peer_e, peer_n, enc_len); encrypted_key=g_malloc(enc_len); if (!encrypted_key) goto free_pubkey_out; rc=RSA_public_encrypt(plain_length, plain, encrypted_key, pubkey, RSA_PKCS1_PADDING); if (rc<=0) { rc=ERR_get_error(); err_out("Can not encrypt key with public key: err=%s\n", ERR_error_string(rc, errbuf)); rc *= -1; goto free_encrypted_key_out; } rc=select_asymmetric_key(peer_cap,pubkey,&key_type); if (rc) goto free_encrypted_key_out; rc=-ENOMEM; bn_encoded_key=BN_bin2bn(encrypted_key,enc_len,NULL); if (!bn_encoded_key) goto free_encrypted_key_out; encoded_key=BN_bn2hex(bn_encoded_key); if (!encoded_key) goto free_bn_encoded_key_out; *ret_buff=encoded_key; *akey_type=key_type; rc=0; free_bn_encoded_key_out: if (bn_encoded_key) BN_free(bn_encoded_key); free_encrypted_key_out: if (encrypted_key) g_free(encrypted_key); free_pubkey_out: if (pubkey) { BN_free(pubkey->n); BN_free(pubkey->e); pubkey->n=NULL; pubkey->e=NULL; RSA_free(pubkey); } return rc;}intpcrypt_decrypt_message(unsigned long cap,const char *encrypted_skey,char **ret_buff,size_t *decrypted_len){ int rc; RSA *privkey=NULL; char *decrypted_skey=NULL; size_t decrypted_skey_len; BIGNUM *bn_encrypted_key=NULL; size_t bn_encrypted_key_len; char *bin_skey=NULL; char errbuf[1024]; if ( (!encrypted_skey) || (!ret_buff) || (!decrypted_len) ) return -EINVAL; rc=pcrypt_crypt_refer_rsa_key(cap,&privkey); if (rc) return rc; rc=-ENOMEM; bn_encrypted_key=BN_new(); if (!bn_encrypted_key) goto no_free_out; rc=BN_hex2bn(&bn_encrypted_key, encrypted_skey); if (!rc) { rc=ERR_get_error(); err_out("Can not convert hex-key to BIGNUM: err=%s\n", ERR_error_string(rc, errbuf)); rc=-rc; goto free_bn_encrypted_key_out; } bn_encrypted_key_len=BN_num_bytes(bn_encrypted_key); rc=-ENOMEM; bin_skey=g_malloc(bn_encrypted_key_len); if (!bin_skey) goto free_bn_encrypted_key_out; rc=BN_bn2bin(bn_encrypted_key,bin_skey); if (!rc) { rc=ERR_get_error(); err_out("Can not convert BIGNUM:to binary err=%s\n", ERR_error_string(rc, errbuf)); rc=-rc; goto free_bin_skey_out; } decrypted_skey_len=BN_num_bytes(privkey->n); rc=-ENOMEM; decrypted_skey=g_malloc(decrypted_skey_len); if (!decrypted_skey) goto free_bin_skey_out; rc=RSA_private_decrypt(bn_encrypted_key_len, bin_skey, decrypted_skey, privkey, RSA_PKCS1_PADDING); if (rc<=0) { if (decrypted_skey) g_free(decrypted_skey); rc=ERR_get_error(); err_out("Can not decrypt secret key err=%s\n", ERR_error_string(rc, errbuf)); rc=-rc; goto free_bin_skey_out; } *decrypted_len=decrypted_skey_len; *ret_buff=decrypted_skey; rc=0; free_bin_skey_out: if (bin_skey) g_free(bin_skey); free_bn_encrypted_key_out: if (bn_encrypted_key) BN_free(bn_encrypted_key); no_free_out: return rc;}int pcrypt_sign(unsigned long cap,unsigned long sign_type,unsigned char *msg_str, unsigned char **ret_buff){ int rc; RSA *key=NULL; unsigned char *out=NULL; size_t out_len; unsigned char hash[MD5SHA1_DIGEST_LEN]; BIGNUM *bn_hash=NULL; unsigned char *hash_string=NULL; size_t msg_len;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -