I'm building a online game with a Phantom wallet login. My server is written in C++ and I want to make the signature verification there. The connection between client and server is a socket connection sending JSON.
For the client side, I went through the Phantom documentation. I retrieved the public key as a string and the signature as a uint8array, example values:
I found that Solana uses ED25519 signature, and I also found this website that implements the algorithm. And after trying multiple different entries to sign a message, I realized that the signature always contains characters that can be displayed. Therefore my first question is, why are there invalid characters (unable to be displayed) in my signature ? Example with the above signature: "�/���9H�q>�2/�'��R;�ֹ��^D�v�xB�����8?P)����ֹ[�7~�����Y~���w��".
Concerning the server side, I found some libraries to verify the signature:
But after multiple attempts, I could not find any valid set (message, public key and signature) that succeed the verification method int crypto_sign_open(byte *m,word64 *mlen,const byte *sm,word64 n,const byte *pk)
Therefore, my big question is, how do I verify this signature ? I did not find a proper example verifying a Phantom signature, especially in another language than Javascript.
Thank you in advance for your help!
I finally succeed verifying this signature. My first mistake was that, for ED25519 signature, the public key has to be 32 bytes. However, the Phantom public key contains 44 bytes. I found a post for which one of the answers says that the 44 bytes public key needs to be decoded in base 58 that gives us a 32 bytes key.
Secondly, in the server, the method to use to verify the signature was not the right one. Indeed the right one is: int crypto_sign_verify_detached(const unsigned char *sig, const unsigned char *m, unsigned long long mlen, const unsigned char *pk)
. The method is described here.
With these two changes, the verification works perfectly!