I am running the following code in order to sign a string in c# using an rsa private key. I extracted the private key from an X.509 certificate and converted it with openssl rsa command.
public static byte[] doSign(string text)
    {
        RSACryptoServiceProvider csp = CreateRsaProviderFromPrivateKey(File.ReadAllText(@"Security\private.pem"));
        SHA1Managed sha1 = new SHA1Managed();
        byte[] data = Encoding.ASCII.GetBytes(text);
        byte[] hash = sha1.ComputeHash(data);
        return csp.SignHash(hash, CryptoConfig.MapNameToOID("SHA1"));
    }
    private static RSACryptoServiceProvider CreateRsaProviderFromPrivateKey(string privateKey)
    {
        List<string> lines = privateKey.Split('\n').ToList();
        string key = string.Join("",
            (
                from s in lines
                where !string.IsNullOrEmpty(s) && s[0] != '-'
                select s
             ).ToList().ToArray()).Replace("\n", "").Replace("\r", "");
        var privateKeyBits = System.Convert.FromBase64String(key);
        var RSA = new RSACryptoServiceProvider();
        var RSAparams = new RSAParameters();
        using (BinaryReader binr = new BinaryReader(new MemoryStream(privateKeyBits)))
        {
            byte bt = 0;
            ushort twobytes = 0;
            twobytes = binr.ReadUInt16();
            if (twobytes == 0x8130)
                binr.ReadByte();
            else if (twobytes == 0x8230)
                binr.ReadInt16();
            else
                throw new Exception("Unexpected value read binr.ReadUInt16()");
            twobytes = binr.ReadUInt16();
            if (twobytes != 0x0102)
                throw new Exception("Unexpected version");
            bt = binr.ReadByte();
            if (bt != 0x00)
                throw new Exception("Unexpected value read binr.ReadByte()");
            RSAparams.Modulus = binr.ReadBytes(GetIntegerSize(binr));
            RSAparams.Exponent = binr.ReadBytes(GetIntegerSize(binr));
            RSAparams.D = binr.ReadBytes(GetIntegerSize(binr));
            RSAparams.P = binr.ReadBytes(GetIntegerSize(binr));
            RSAparams.Q = binr.ReadBytes(GetIntegerSize(binr));
            RSAparams.DP = binr.ReadBytes(GetIntegerSize(binr));
            RSAparams.DQ = binr.ReadBytes(GetIntegerSize(binr));
            RSAparams.InverseQ = binr.ReadBytes(GetIntegerSize(binr));
        }
        RSA.ImportParameters(RSAparams);
        return RSA;
    }
I am then converting the signed string to an hexadecimal string and send it to a php page:
private void toPhp(string timestamp)
    {
        string data = idMachine + numberOfSignal + timestamp;
        //string signature = new Sign().IngApiGetToken(data);
        byte[] signatureBytes = Sign.doSign(data);
        string signature = Sign.toHex(Encoding.UTF8.GetString(signatureBytes));
        using (HttpClient client = new HttpClient())
        {
            string uri = "http://localhost/GCS/";
            var formContent = new FormUrlEncodedContent(new[]
            {
                new KeyValuePair<string, string>("data", data),
                new KeyValuePair<string, string>("signature", signature)
            });
            var res = client.PostAsync(uri, formContent).Result.Content.ReadAsStringAsync().Result;
            //textBox1.Text += "Hex: " + signature;
            textBox1.Text += Environment.NewLine;
            textBox1.Text += "---- Sending request to PHP ----";
            textBox1.Text += Environment.NewLine;
            textBox1.Text += res;
        }
    }
The php page verifies the signed string using the certificate and tries to sign itself the original data:
    $data = $_POST["data"];
$signature = $_POST["signature"];
$bin = $_POST["bin"];
if(!isset($_POST['bin'])){
    $signature = hex2bin($signature);
}
$pub_key = openssl_pkey_get_public("file://cert.pem"); 
echo "Data: ";
echo $data;
echo "\r\nSignature: ";
echo $signature;
echo "\r\nSignature to hex: ";
echo strtoupper(bin2hex($signature));
echo "\r\nResult: ";
echo openssl_verify ( $data , $signature , $pub_key); 
//Re-sign
$res = openssl_get_privatekey("file://private.pem");
openssl_sign($data, $newSignature, $res);
$hex = strtoupper(bin2hex($newSignature));
echo "\r\nString signed hex: $newSignature";
echo "\r\nString signed hex: $hex";
echo "\r\nResult: ";
echo openssl_verify ( $data , $newSignature , $pub_key); 
echo "\r\nComparing signed: ";
echo strcmp ($signature,$newSignature);
Below you can see the result printed by the php echos. As you can see, the signed strings are apparently identical, but the hexadecimal values are different.
---- Sending request to PHP ---- Data: 22-530057097401597056984 Signature: B���p E]%��.qנ�[��؋�� GX�%0�!f-�e"�+�Ӎ�lf�q�^��!����yN51�C�!��V�n�i���eECx������Q�=H33���9�#��Aw�ݘ�sa=f=6A�~��u��i/ui6�[�Z�F�+DБH����N�K�-/v�=�I�HM7� |Ҧ��e/v�����}vxB,k��Z4s�E��$ߘ�rVU^^}�:�)i�������X��"�68�X�Ӝ2{{sH Signature to hex: 42EFBFBDEFBFBDEFBFBD700D45175D250CEFBFBDEFBFBD2E0371D7A0EFBFBD5BEFBFBDEFBFBDD88BEFBFBDEFBFBD0D4758EFBFBD2530EFBFBD21662DEFBFBD106522EFBFBD2BEFBFBDD38DEFBFBD6C66EFBFBD71EFBFBD5EEFBFBD1FEFBFBD2110EFBFBDEFBFBDEFBFBDEFBFBD794E3531EFBFBD7F43EFBFBD21EFBFBDEFBFBD56EFBFBD6EEFBFBD69EFBFBDEFBFBDEFBFBD6545430578EFBFBDEFBFBDEFBFBDEFBFBDEFBFBD1613EFBFBD0C0251EFBFBD3D483333EFBFBDEFBFBDEFBFBD39EFBFBD23EFBFBDEFBFBD4177EFBFBDDD98EFBFBD7302613D663D3641EFBFBD7EEFBFBD11EFBFBD751AEFBFBDEFBFBD692F04756936EFBFBD5B111BEFBFBD5AEFBFBD0546EFBFBD2B44D09148EFBFBDEFBFBD04EFBFBDEFBFBD4EEFBFBD4BEFBFBD2D2F76EFBFBD3DEFBFBD49EFBFBD12484D37EFBFBD0A7CD2A6EFBFBDEFBFBD652F76EFBFBDEFBFBD1CEFBFBDEFBFBDEFBFBD7D7678422C106BEFBFBDEFBFBD5A3473EFBFBD45EFBFBDEFBFBD24DF98EFBFBD7256555E5E7DEFBFBD053AEFBFBD0B142969EFBFBDEFBFBDEFBFBDEFBFBDEFBFBDEFBFBDEFBFBD58EFBFBDEFBFBD2218EFBFBD3638EFBFBD58EFBFBDD39C327B7B1D13731348 Result: 0 String signed hex: B���p E]%��.qנ�[��؋�� GX�%0�!f-�e"�+�Ӎ�lf�q�^��!����yN51�C�!��V�n�i���eECx������Q�=H33���9�#��Aw�ݘ�sa=f=6A�~��u��i/ui6�[�Z�F�+DБH����N�K�-/v�=�I�HM7� |Ҧ��e/v�����}vxB,k��Z4s�E��$ߘ�rVU^^}�:�)i�������X��"�68�X�Ӝ2{{sH String signed hex: 4289AAE2700D45175D250C85ED9C2E0371D7A0D45BAEDDD88BA2F70D4758DC2530EC21662DA6106522E62BC2D38DAA6C668671975EF481BE1F8921108796ABBA794E3531C27F43BF2196DA56D96EB269B490B36545430578BDFA9CE2D91613850C0251D53D4833338FFDEF398D239FBD4177FCDD98A67302613D663D3641EB7EB611D8751ADAE6692F04756936B75B111B8D5AEB860546F92B44D0914888CB04F8EC4EA14BBC2D2F76AC3D84498D12484D37D30A7CD2A6C4ED652F76DAF11CD1F7A97D7678422C106B9B965A3473CC45819724DF98B77256555E5E7D87053ACD0B142969868ED5C0A3CDE65898D122188E3638E95897D39C327B7B1D13731348 Result: 1 Comparing signed: 1
Anyone can help about signing in C# in order to make the openssl_verify return 1? Thank you very much!
 
    