Click here to Skip to main content
15,443,281 members
Please Sign up or sign in to vote.
0.00/5 (No votes)
See more:
Hi I wrote a webservice that server is written in php and client is written in c++, and I used openssl package for generating rsa pair key to secure data transferming.
At the first I wrote both client an server in php for preparing services and every things goes OK. but when I started transfer client php code into c++ I face into problems with openssl methods.
The big problem is that the signed data does not match in both php and c++ codes.
I get md5 of data and use openssl_sign method for signing md5 data and then append the sign at the end of plain data and send to client (In the past public key have been sent for client). in the client I did this progress again. but the sign dos not verify correctly.

What is wrong in may program?

please help, thanks.

php side (webservice) code:

PHP
function sign($cleartext)
	$msg_hash = md5($cleartext);
	$sig      = "";
				$ok       = openssl_sign($msg_hash, $sig, $this->private_key);
	if ($ok == 1)
	{
		$signed_data = $cleartext . "----SIGNATURE:----" . base64_encode($sig);
		//$signed_data = $this->encryptAES($signed_data, $this->password);
		return base64_encode(mysql_real_escape_string($signed_data));
	}
	elseif ($ok == 0)
	{
		$eroor = "bad";
		return base64_encode($eroor);
	}
	else
	{
		$eroor = "ugly, error checking signature";
		return base64_encode($eroor);
	}
}


and C++ side (client) Code:

C++
int Crypto::rsaVerify(string msgStr, const char *pk) {

	int length;

	char *pkStr = new char[this->publicKey.length() + 1];
	char *prStr = new char[this->publicKey.length() + 1];
	strcpy_s(pkStr, this->publicKey.length()+1,this->publicKey.c_str());


	this->setPubKey((unsigned char *)pkStr,strlen(pkStr));
	this->setPriKey((unsigned char *)prStr,strlen(prStr));

	// Find and Splite Data
	size_t current = 0;
	string delimiters = "----SIGNATURE:----";
	size_t next = msgStr.find( delimiters, current );
	string dataStr = msgStr.substr( current, next - current );
	char *msg = new char[dataStr.length() + 1];
	strcpy_s(msg, dataStr.length()+1,dataStr.c_str());

	// Find and Split sign
	string signData = msgStr.substr(next + delimiters.length(), msgStr.length());
	Coding *codingObj = new Coding();
	signData = codingObj->base64_decode(signData);
	char *signBuf = new char[signData.length() + 1];
	char *signBuf2 = new char[signData.length() + 1];
	strcpy_s(signBuf, signData.length()+1, signData.c_str());

	unsigned char *dataMD5 = new unsigned char [MD5_DIGEST_LENGTH];
	MD5((const unsigned char *)msg,strlen(msg),dataMD5);

	char md5String[MD5_DIGEST_LENGTH + 1];
	AsciiString2HexString(dataMD5,(unsigned char *)md5String, MD5_DIGEST_LENGTH);
	md5String[MD5_DIGEST_LENGTH] = '\0';

	unsigned char * key2;
	getPubKey(&key2);

	unsigned int signLen = 256;//strlen(msg1);
	char errorBuffer[120];

	if(RSA_verify(NID_sha1,(const unsigned char *)md5String, strlen(md5String),(const unsigned char *)signBuf,signLen,this->keyPair))
	{
		return 1;
	}
	else
	{
		ERR_error_string(ERR_get_error(), errorBuffer); 
	}
	if(RSA_verify(NID_sha1,(const unsigned char *)dataMD5, strlen((char *)dataMD5),(const unsigned char *)signBuf,signLen,this->keyPair))
	{
		return 1;
	}
	else
	{
		ERR_error_string(ERR_get_error(), errorBuffer); 
	}

	return 0;
}


C++
int Crypto::getPriKey(unsigned char **priKey) {

	BIO *bio = BIO_new(BIO_s_mem());
	PEM_write_bio_RSAPrivateKey(bio, this->keyPair, NULL, NULL, NULL, NULL, NULL);

	int priKeyLen = BIO_pending(bio);
	*priKey = (unsigned char*)malloc(priKeyLen);
	if(priKey == NULL) return FAILURE;

	BIO_read(bio, *priKey, priKeyLen);

	// Insert the NUL terminator
	(*priKey)[priKeyLen-1] = '\0';

	BIO_free_all(bio);

	return priKeyLen;
}
Posted
Updated 2-Oct-13 21:15pm
v3

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900