From 6aa2f46b0815e63a4133784042aaa136e2482c24 Mon Sep 17 00:00:00 2001 From: Christian Ulrich Date: Sun, 15 Nov 2020 17:18:45 +0100 Subject: [PATCH] introduce base32 peer IDs --- base32.nim | 83 +++++++++++++++++++++++++++++++++++++++++++++++++++++ quicp2p.nim | 18 ++++++++++-- 2 files changed, 99 insertions(+), 2 deletions(-) create mode 100644 base32.nim diff --git a/base32.nim b/base32.nim new file mode 100644 index 0000000..bfa2a69 --- /dev/null +++ b/base32.nim @@ -0,0 +1,83 @@ +# +# Nim's Unofficial Library +# (c) Copyright 2015 Huy Doan +# +# See the file "LICENSE", included in this +# distribution, for details about the copyright. +# + +## This module implements a base32 encoder and decoder. + +const + VERSION* = "0.1.2" + + base32Chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZ234567=" + +proc encode*(s: openArray[char]; pad=true): string = + var i, j, idx, digit: int = 0 + var current, next: int + + var len = (s.len * 8 / 5).int + if len mod 8 != 0: + len += 8 - (len mod 8) + + result = newString(len) + + while i < s.len: + current = s[i].ord + + if idx > 3: + if i + 1 < s.len: + next = s[i+1].ord + else: + next = 0 + + digit = current and (0xFF shr idx) + idx = (idx + 5) mod 8 + digit = digit shl idx + digit = digit or (next shr (8 - idx)) + + i += 1 + else: + digit = (current shr (8 - (idx + 5))) and 0x1F + idx = (idx + 5) mod 8 + if idx == 0: + i += 1 + + result[j] = base32Chars[digit] + j += 1 + if pad: + for i in j..= 8: + bits -= 8 + result[idx] = char(buf shr bits and 0xFF) + idx += 1 + if idx < len: + setLen(result, idx) diff --git a/quicp2p.nim b/quicp2p.nim index f215826..fae2e5a 100644 --- a/quicp2p.nim +++ b/quicp2p.nim @@ -2,6 +2,7 @@ import asyncdispatch import asyncnet +import base32 import certificate import net import os @@ -68,6 +69,18 @@ proc getRelativeTimeout(ctx: QuicP2PContext): int32 = let delta = nextTimeout - now result = min(delta, int32.high).int32 +proc getPeerId(ctx: QuicP2PContext): string = + assert(ctx.tlsCtx.certificates.count == 2) + let firstCertAddr = cast[ByteAddress](ctx.tlsCtx.certificates.list) + let secondCertIovec = cast[ptr ptls_iovec_t](firstCertAddr + sizeof(ptls_iovec_t)) + var caCert = newString(secondCertIovec.len) + copyMem(caCert.cstring, secondCertIovec.base, secondCertIovec.len) + result = caCert.getPublicKey().encode(pad = false) + +proc getPeerId(conn: Connection): string = + assert(conn.certs.len() == 2) + result = conn.certs[1].getPublicKey().encode(pad = false) + proc onStopSending(stream: ptr quicly_stream_t, err: cint) {.cdecl.} = echo "onStopSending" discard quicly_close(stream.conn, 0x30000, "") @@ -84,7 +97,7 @@ proc onServerReceive(stream: ptr quicly_stream_t, offset: csize_t, src: pointer, var msg = newString(input.len) copyMem(addr msg[0], input.base, input.len) let conn = cast[Connection](quicly_get_data(stream.conn)[]) - echo &"client {conn.certs[1].getPublicKey().toHex()} sends \"{msg}\"" + echo &"client {conn.getPeerId()} sends \"{msg}\"" if quicly_sendstate_is_open(addr stream.sendstate) != 0 and input.len > 0: discard quicly_streambuf_egress_write(stream, input.base, input.len) if quicly_recvstate_transfer_complete(addr stream.recvstate) != 0: @@ -99,7 +112,7 @@ proc onClientReceive(stream: ptr quicly_stream_t, offset: csize_t, let msg = newString(input.len) copyMem(msg.cstring, input.base, input.len) let conn = cast[Connection](quicly_get_data(stream.conn)[]) - echo &"server {conn.certs[1].getPublicKey().toHex()} sends \"{msg}\"" + echo &"server {conn.getPeerId()} sends \"{msg}\"" if quicly_recvstate_transfer_complete(addr stream.recvstate) != 0: discard quicly_close(stream.conn, 0, "") quicly_streambuf_ingress_shift(stream, input.len) @@ -333,6 +346,7 @@ proc main() = usage() quit(1) + echo "My peer ID is ", ctx.getPeerId() while true: let nextTimeout = ctx.getRelativeTimeout() poll(nextTimeout)