Я пытаюсь реализовать HOTP (rfc-4226) в Golang, и я изо всех сил пытаюсь создать действительный HOTP. Я могу сгенерировать его в java, но по какой-то причине моя реализация в Golang отличается. Вот образцы:
public static String constructOTP(final Long counter, final String key)
throws NoSuchAlgorithmException, DecoderException, InvalidKeyException {
final Mac mac = Mac.getInstance("HmacSHA512");
final byte[] binaryKey = Hex.decodeHex(key.toCharArray());
mac.init(new SecretKeySpec(binaryKey, "HmacSHA512"));
final byte[] b = ByteBuffer.allocate(8).putLong(counter).array();
byte[] computedOtp = mac.doFinal(b);
return new String(Hex.encodeHex(computedOtp));
}
и в Го:
func getOTP(counter uint64, key string) string {
str, err := hex.DecodeString(key)
if err != nil {
panic(err)
}
h := hmac.New(sha512.New, str)
bs := make([]byte, 8)
binary.BigEndian.PutUint64(bs, counter)
h.Write(bs)
return base64.StdEncoding.EncodeToString(h.Sum(nil))
}
Я считаю, что проблема в том, что строка Java: ByteBuffer.allocate(8).putLong(counter).array();
генерирует массив байтов, отличный от строки Go: binary.BigEndian.PutUint64(bs, counter)
.
В Java генерируется следующий массив байтов: 83 -116 -9 -98 115 -126 -3 -48
, а в Go: 83 140 247 158 115 130 253 207
.
Кто-нибудь знает разницу в двух строках и как я могу перенести строку java?