Search code examples
javagosha256dsa

generate a SHA256withDSA signature using Go and then verify it using Java


  1. Go sha256 orign data then DSA sign it
  2. print sign result by hex
  3. use Java SHA256withDSA to verify first step result return false
  4. i konw sha256 then DSA is difference SHA256withDSA
  5. how can i do in Go to generate a sign, that can be verified using sha256withdsa in Java ?
  6. do Go has any another third party library support ?

Go

package main

import (
    "crypto/dsa"
    "crypto/rand"
    "crypto/sha256"
    "encoding/asn1"
    "encoding/hex"
    "fmt"
    "golang.org/x/crypto/ssh"
    "math/big"
)

func main() {
    pemData := []byte("-----BEGIN DSA PRIVATE KEY-----\n" +
        "MIIBvAIBAAKBgQD9f1OBHXUSKVLfSpwu7OTn9hG3UjzvRADDHj+AtlEmaUVdQCJR\n" +
        "+1k9jVj6v8X1ujD2y5tVbNeBO4AdNG/yZmC3a5lQpaSfn+gEexAiwk+7qdf+t8Yb\n" +
        "+DtX58aophUPBPuD9tPFHsMCNVQTWhaRMvZ1864rYdcq7/IiAxmd0UgBxwIVAJdg\n" +
        "UI8VIwvMspK5gqLrhAvwWBz1AoGBAPfhoIXWmz3ey7yrXDa4V7l5lK+7+jrqgvlX\n" +
        "TAs9B4JnUVlXjrrUWU/mcQcQgYC0SRZxI+hMKBYTt88JMozIpuE8FnqLVHyNKOCj\n" +
        "rh4rs6Z1kW6jfwv6ITVi8ftiegEkO8yk8b6oUZCJqIPf4VrlnwaSi2ZegHtVJWQB\n" +
        "TDv+z0kqAoGBAIb9o0KPsjAdzjK571e1Mx7ZhEyJGrcxHiN2sW8IztEbqrKKiMxp\n" +
        "NlTwm234uBdtzVHE3uDWZpfHPMIRmwBjCYDFRowWWVRdhdFXZlpCyp1gMWqJ11dh\n" +
        "3FI3+O43DevRSyyuLRVCNQ1J3iVgwY5ndRpZU7n6y8DPH4/4EBT7KvnVAhR4Vwun\n" +
        "Fhu/+4AGaVeMEa814I3dqg==\n" +
        "-----END DSA PRIVATE KEY-----")

    p, _ := ssh.ParseRawPrivateKey(pemData)
    pp := p.(*dsa.PrivateKey)

    hashed := []byte{1}
    sha256 := sha256.New()
    sha256.Write(hashed)
    hashed = sha256.Sum(nil)
    r, s, _ := dsa.Sign(rand.Reader, pp, hashed)
    type dsaSignature struct {
        R, S *big.Int
    }
    var ss dsaSignature
    ss.S = s
    ss.R = r
    signatureBytes, _ := asn1.Marshal(ss)
    fmt.Println(hex.EncodeToString(signatureBytes))
}

Java

 @Test
    public void ttt() throws InvalidKeySpecException, NoSuchAlgorithmException, InvalidKeyException, SignatureException {
        String pubKey = "-----BEGIN PUBLIC KEY-----\n" +
                "MIIBuDCCASwGByqGSM44BAEwggEfAoGBAP1/U4EddRIpUt9KnC7s5Of2EbdSPO9E\n" +
                "AMMeP4C2USZpRV1AIlH7WT2NWPq/xfW6MPbLm1Vs14E7gB00b/JmYLdrmVClpJ+f\n" +
                "6AR7ECLCT7up1/63xhv4O1fnxqimFQ8E+4P208UewwI1VBNaFpEy9nXzrith1yrv\n" +
                "8iIDGZ3RSAHHAhUAl2BQjxUjC8yykrmCouuEC/BYHPUCgYEA9+GghdabPd7LvKtc\n" +
                "NrhXuXmUr7v6OuqC+VdMCz0HgmdRWVeOutRZT+ZxBxCBgLRJFnEj6EwoFhO3zwky\n" +
                "jMim4TwWeotUfI0o4KOuHiuzpnWRbqN/C/ohNWLx+2J6ASQ7zKTxvqhRkImog9/h\n" +
                "WuWfBpKLZl6Ae1UlZAFMO/7PSSoDgYUAAoGBAIb9o0KPsjAdzjK571e1Mx7ZhEyJ\n" +
                "GrcxHiN2sW8IztEbqrKKiMxpNlTwm234uBdtzVHE3uDWZpfHPMIRmwBjCYDFRowW\n" +
                "WVRdhdFXZlpCyp1gMWqJ11dh3FI3+O43DevRSyyuLRVCNQ1J3iVgwY5ndRpZU7n6\n" +
                "y8DPH4/4EBT7KvnV\n" +
                "-----END PUBLIC KEY-----";
        String publicKeyPEM = pubKey
                .replace("-----BEGIN PUBLIC KEY-----\n", "")
                .replaceAll(System.lineSeparator(), "")
                .replace("-----END PUBLIC KEY-----", "");
        byte[] publicEncoded = Base64.decodeBase64(publicKeyPEM);
        KeyFactory keyFactory1 = KeyFactory.getInstance("DSA");
        X509EncodedKeySpec publicKeySpec = new X509EncodedKeySpec(publicEncoded);
        DSAPublicKey pubKeyy = (DSAPublicKey) keyFactory1.generatePublic(publicKeySpec);

        Signature sig1 = Signature.getInstance("SHA256withDSA");
        sig1.initVerify(pubKeyy);
        byte[] orignData = new byte[]{1};
        sig1.update(orignData);
        boolean flag = sig1.verify(HexUtil.decodeHex("first step result"));
        System.out.println(flag);
    }

Solution

  • follow FIPS186-4 sections 4.6 and 4.7 golang should this

    hashed := []byte{1}
    pemData, _ := ioutil.ReadFile("config/secure/private.key")
    p, err := ssh.ParseRawPrivateKey(pemData)
    pp, ok := p.(*dsa.PrivateKey)
    h := sha256.New()
    h.Write(hashed)
    hashed := h.Sum(nil)
    if pp.Q.BitLen()/8 < len(hashed) {
        hashed = hashed[0 : pp.Q.BitLen()/8]
    }
    r, s, _ := dsa.Sign(rand.Reader, pp, hashed)
    var ss dsaSignature
    ss.S = s
    ss.R = r
    hashed, _ = asn1.Marshal(ss)