ed25519 공개 키 생성 차이
ed25519 암호화 패키지는 개인 키에서 공개 키를 생성하는 수단을 제공합니다. 그러나 사용자는 Go 구현으로 생성된 공개 키가 특정 사용 사례에서 예상되는 값과 일치하지 않는다는 것을 관찰했습니다.
근본 원인:
이러한 차이 ed25519 개인 키를 나타내는 데 사용되는 다양한 형식에서 발생합니다. Go 패키지는 개인 키가 32바이트 시드와 32바이트 공개 키의 연결로 표시되는 형식을 활용합니다. 반대로 예상 결과를 정의하는 테스트 벡터는 개인 키를 시드 해싱의 64바이트 출력으로 나타냅니다.
해결책:
해싱 프로세스를 반대로 하면 테스트 벡터 개인 키를 Go 구현과 호환되는 형식으로 변환하는 것이 불가능합니다. 또는 대체 개인 키 형식을 지원하는 Go 라이브러리의 수정된 버전을 생성할 수 있습니다.
수정된 라이브러리 코드:
다음 코드 조각은 사용자 정의 버전을 제공합니다. 대체 개인 키 형식을 지원하기 위한 Go 구현:
공개 키 생성:
<code class="go">// Generate the public key corresponding to the already hashed private // key. // // This code is mostly copied from GenerateKey in the // golang.org/x/crypto/ed25519 package, from after the SHA512 // calculation of the seed. func getPublicKey(privateKey []byte) []byte { var A edwards25519.ExtendedGroupElement var hBytes [32]byte copy(hBytes[:], privateKey) edwards25519.GeScalarMultBase(&A, &hBytes) var publicKeyBytes [32]byte A.ToBytes(&publicKeyBytes) return publicKeyBytes[:] }</code>
서명:
<code class="go">// Calculate the signature from the (pre hashed) private key, public key // and message. // // This code is mostly copied from the Sign function from // golang.org/x/crypto/ed25519, from after the SHA512 calculation of the // seed. func sign(privateKey, publicKey, message []byte) []byte { var privateKeyA [32]byte copy(privateKeyA[:], privateKey) // we need this in an array later var messageDigest, hramDigest [64]byte h := sha512.New() h.Write(privateKey[32:]) h.Write(message) h.Sum(messageDigest[:0]) var messageDigestReduced [32]byte edwards25519.ScReduce(&messageDigestReduced, &messageDigest) var R edwards25519.ExtendedGroupElement edwards25519.GeScalarMultBase(&R, &messageDigestReduced) var encodedR [32]byte R.ToBytes(&encodedR) h.Reset() h.Write(encodedR[:]) h.Write(publicKey) h.Write(message) h.Sum(hramDigest[:0]) var hramDigestReduced [32]byte edwards25519.ScReduce(&hramDigestReduced, &hramDigest) var s [32]byte edwards25519.ScMulAdd(&s, &hramDigestReduced, &privateKeyA, &messageDigestReduced) signature := make([]byte, 64) copy(signature[:], encodedR[:]) copy(signature[32:], s[:]) return signature }</code>
데모:
다음 코드는 예상되는 공개 키와 서명을 생성하기 위해 사용자 정의 함수를 사용하는 방법을 보여줍니다.
<code class="go">privateKeyHex := "e06d3183d14159228433ed599221b80bd0a5ce8352e4bdf0262f76786ef1c74db7e7a9fea2c0eb269d61e3b38e450a22e754941ac78479d6c54e1faf6037881d" expectedPublicKey := "77ff84905a91936367c01360803104f92432fcd904a43511876df5cdf3e7e548" expectedSig := "6834284b6b24c3204eb2fea824d82f88883a3d95e8b4a21b8c0ded553d17d17ddf9a8a7104b1258f30bed3787e6cb896fca78c58f8e03b5f18f14951a87d9a08" privateKey, _ := hex.DecodeString(privateKeyHex) publicKey := getPublicKey(privateKey) fmt.Printf("Calculated key: %x\n", publicKey) fmt.Printf("Expected key: %s\n", expectedPublicKey) keyMatches := expectedPublicKey == hex.EncodeToString(publicKey) fmt.Printf("Public key matches expected: %v\n", keyMatches) buffer := []byte("4:salt6:foobar3:seqi1e1:v12:Hello World!") calculatedSig := sign(privateKey, publicKey, buffer) fmt.Printf("Calculated sig: %x\n", calculatedSig) fmt.Printf("Expected sig: %s\n", expectedSig) sigMatches := expectedSig == hex.EncodeToString(calculatedSig) fmt.Printf("Signature matches expected: %v\n", sigMatches)</code>
이러한 사용자 정의를 통합하여 기능을 코드에 추가하면 대체 개인 키 형식으로 정의된 테스트 벡터를 처리하고 일치하지 않는 결과가 발생하지 않고 공개 키 생성 및 서명과 같은 작업을 수행할 수 있습니다.
위 내용은 ed25519의 Go 구현이 특정 경우에 예상과 다른 공개 키를 생성하는 이유는 무엇입니까?의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!