Ok I need some more help, nostr:nprofile1qy2hwumn8ghj7un9d3shjtnyv9kh2uewd9hj7qghwaehxw309aex2mrp0yh8qunfd4skctnwv46z7qgewaehxw309aex2mrp0yh8xmn0wf6zuum0vd5kzmp0qqsdr8lv2sp86ztsv4yz9q9wz7ng6zk40u84cta8fcj08kamrek9f9gsq8th3 nostr:nprofile1qyvhwumn8ghj7un9d3shjtndd3jkkafwdahxc6twv5hszyrhwden5te0vyhxummn9ekx7mp0qythwumn8ghj7ct5d3shxtnwdaehgu3wd3skuep0qqsyeqqz27jc32pgf8gynqtu90d2mxztykj94k0kmttxu37nk3lrktctmwr4h nostr:nprofile1qyd8wumn8ghj7urewfsk66ty9enxjct5dfskvtnrdakj7qgmwaehxw309aex2mrp0yh8wetnw3jhymnzw33jucm0d5hsqgpm7rrrljungc6q0tuh5hj7ue863q73qlheu4vywtzwhx42a7j9n5zr9h9m

I'm trying to decrypt an event using nip44, but I'm getting an "invalid hmac" warning on a valid payload (at least, according to the javascript implementation). Any hints? Code below.

func getNip44ConversationKey(sk string, pk string) []byte {

sk_bytes, _ := hex.DecodeString("02" + sk)

sk_obj := secp256k1.PrivKeyFromBytes(sk_bytes)

pk_bytes, _ := hex.DecodeString("02" + pk)

pk_obj, _ := secp256k1.ParsePubKey(pk_bytes)

return nip44.GenerateConversationKey(sk_obj, pk_obj)

}

func getNip44Rumor(sk string, wrap *nostr.Event) (*nostr.Event, error) {

wrap_key := getNip44ConversationKey(sk, wrap.PubKey)

nip44.Decrypt(wrap_key, wrap.Content) // invalid hmac

...

}

Reply to this note

Please Login to reply.

Discussion

I see your problem immediately. It's not written in rust.

😂😂😂

i see the problem in your seeing the problem: you aren't actually addressing the issue at all, thanks for your help

we are imperative programmers over here, we don't comprehend your unnecessary abstractions

have you tried assigning and checking any of the error values that are being ignored in the above code snippet yet? they might give you a hint where the code is failing.

haha... this is the reference impl for #golang of NIP-44

it is clearly doing something different to the javascript version, the HMAC comes out wrong , and when i make it skip the HMAC check it then says the padding is wrong, which is presumably the two parts of the function that are wrong (decrypt)

i'm literally going to have to look at another language version of this crazy scheme

honestly, i've never seen such a crappy piece of code, nor such an unclear specification as i have here... i suppose it's written in python too, fuck you all

if you are using that abomination that the security audit said had no bounds checking, i wouldn't actually trust it

i'm working on getting this going today so when i'm done i'll show you the fixed code

my guess though, is that the bytes have been mishandled somewhere just wouldn't doubt it's in the nip44 encryption code, did anyone actually test it? has it got test units?

nostr:nprofile1qy2hwumn8ghj7un9d3shjtnyv9kh2uewd9hj7qghwaehxw309aex2mrp0yh8qunfd4skctnwv46z7qgewaehxw309aex2mrp0yh8xmn0wf6zuum0vd5kzmp0qqsdr8lv2sp86ztsv4yz9q9wz7ng6zk40u84cta8fcj08kamrek9f9gsq8th3 have you actually tested that Go algorithm to see that it can decode outputs from other language versions?

also nostr:nprofile1qyfhwumn8ghj7mmxve3ksctfdch8qatz9uqsuamnwvaz7tmwdaejumr0dshszxthwden5te0dphkgmrzdajzumn0wd68yvfwvdhk6tcqyztuwzjyxe4x2dwpgken87tna2rdlhpd02va5cvvgrrywpddnr3jyhdw0my i presume that it's possible to send and receive NIP-44s through coracle from one coracle client to another, so i'm going to examine the coracle implementation, as it is clearly different to the one implemented in #golang

and the link on the page from the NIP-44 to the js/ts version is just a link to the nips repo, wth

i'm going with the idea that coracle is the authoritative client implementation because my task at the moment is to have my code function with it so i'm going to see what actual javascript code is in coracle for encrypting and decrypting these messages

i'm not gonna enjoy reading #javascript code but i will definitely make it possible for a #golang NIP-44 capable chat client to encode and decode

i kinda had hoped i'd have a bit more relaxed second half of february as a deadline is coming up but i think that maybe i'm going to put this chatbot thing on the backburner, stick to supporting NIP-44 and enforcing privacy with NIP-42 and to hell with this insane encryption scheme

you should have asked me how it's done and i'd have come up with a much clearer, simpler scheme that would have been implemented properly in Go instead of this sick joke that someone paid an inordinate amount of money to a crypto auditing company to basically not really tell us anything

Turn the underscore "_" thingies into variables ("err") and check them with

if err != nil {

panic(err)

}

So you can get better insight of what is actually failing.

i wrote a logging library so i could get that without using panics, runtime.Caller

it fails at the error that nostr:nprofile1qyfhwumn8ghj7mmxve3ksctfdch8qatz9uqsuamnwvaz7tmwdaejumr0dshszxthwden5te0dphkgmrzdajzumn0wd68yvfwvdhk6tcqyztuwzjyxe4x2dwpgken87tna2rdlhpd02va5cvvgrrywpddnr3jyhdw0my reports - the hmac is not being calculated correctly, more likely it's not being partitioned out of the raw bytes properly

come to think of it, the way it pulls that thing out is from the last 32 bytes of it but it doesn't require a multiple of anything, just a set of boundaries on the length

the whole NIP-44 is a clown show

The spec or the implementation?

the implementation

the spec is hard to read, i could try and write it based on the spec, i may yet, it's just not a high priority for me right now

i don't quit have my head wrapped around how it works but HMACs are annoying anyway, signatures do the same thing, and if the thing inside is signed and only the receiver can unpack that then there is security, and if the client can maintain the state of that, it could turn into a chain if you sent one or more future pubkeys to reply with, since the sender can identify a reply by that

but i think it's lower priority than getting everyone to fully support NIP-42 so the relays don't hand out these messages to anyone who hasn't proved they are the valid parties to the messages

Yeah, the HMAC thing was discussed in the audit. I don't fully understand why paul went that direction, but it does work as long as it's in an event

well i'm just telling you that that the go implementation is definitely divergent from the javascript version

and the javascript version seems to not be referred to by the NIP actually, i know your codebase has it but it's not pointed to by the NIP

there really should be an interop test for this, preferably one that uses randomly generated content so it's only repeatable if it's correct

The javascript version comes from paul miller's reference implementation, it's basically copied over into nostr-tools

of course i don't know it because javascript is the most abominable language ever invented, and i curse Griesemer, he only avoids hell by helping build Go

just because you don't handle errors doesn't mean nostr:nprofile1qyfhwumn8ghj7mmxve3ksctfdch8qatz9uqsuamnwvaz7tmwdaejumr0dshszxthwden5te0dphkgmrzdajzumn0wd68yvfwvdhk6tcqyztuwzjyxe4x2dwpgken87tna2rdlhpd02va5cvvgrrywpddnr3jyhdw0my didn't take the time to learn how to write go properly and understood teh principle of fail fast

there's a lot of dumbass things you do with your go code and i'm gonna keep grilling you about it until you fix it, fight me