mirror of
https://github.com/ElementsProject/lightning.git
synced 2025-03-03 18:57:06 +01:00
sphinx: Add functions to decompress
Also implements a way to decompress an onion using the devtools/onion tool Changelog-Added: devtools: The `onion` tool can now generate, compress and decompress onions for rendez-vous routing
This commit is contained in:
parent
4724d55e80
commit
49a3321d7e
3 changed files with 64 additions and 0 deletions
|
@ -785,3 +785,27 @@ u8 *unwrap_onionreply(const tal_t *ctx,
|
||||||
return tal_free(final);
|
return tal_free(final);
|
||||||
return final;
|
return final;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
u8 *sphinx_decompress(const tal_t *ctx, const u8 *compressed,
|
||||||
|
struct secret *shared_secret)
|
||||||
|
{
|
||||||
|
size_t compressedlen = tal_bytelen(compressed);
|
||||||
|
size_t prefill_size = TOTAL_PACKET_SIZE - compressedlen;
|
||||||
|
u8 *dst;
|
||||||
|
int p = 0;
|
||||||
|
|
||||||
|
assert(prefill_size >= 0);
|
||||||
|
assert(compressedlen >= VERSION_SIZE + PUBKEY_SIZE + HMAC_SIZE);
|
||||||
|
dst = tal_arrz(ctx, u8, TOTAL_PACKET_SIZE);
|
||||||
|
write_buffer(
|
||||||
|
dst, compressed,
|
||||||
|
VERSION_SIZE + PUBKEY_SIZE + ROUTING_INFO_SIZE - prefill_size, &p);
|
||||||
|
|
||||||
|
/* We can just XOR here since we initialized the array with zeros. */
|
||||||
|
sphinx_prefill_stream_xor(dst + p, prefill_size, shared_secret);
|
||||||
|
p += prefill_size;
|
||||||
|
|
||||||
|
write_buffer(dst, compressed + compressedlen - HMAC_SIZE, HMAC_SIZE,
|
||||||
|
&p);
|
||||||
|
return dst;
|
||||||
|
}
|
||||||
|
|
|
@ -246,6 +246,13 @@ u8 *serialize_compressed_onion(const tal_t *ctx,
|
||||||
bool sphinx_path_set_rendezvous(struct sphinx_path *sp,
|
bool sphinx_path_set_rendezvous(struct sphinx_path *sp,
|
||||||
const struct node_id *rendezvous_id);
|
const struct node_id *rendezvous_id);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Given a compressed onion expand it by re-generating the prefiller and
|
||||||
|
* inserting it in the appropriate place.
|
||||||
|
*/
|
||||||
|
u8 *sphinx_decompress(const tal_t *ctx, const u8 *compressed,
|
||||||
|
struct secret *shared_secret);
|
||||||
|
|
||||||
#if DEVELOPER
|
#if DEVELOPER
|
||||||
/* Override to force us to reject valid onion packets */
|
/* Override to force us to reject valid onion packets */
|
||||||
extern bool dev_fail_process_onionpacket;
|
extern bool dev_fail_process_onionpacket;
|
||||||
|
|
|
@ -290,6 +290,30 @@ static void runtest(const char *filename)
|
||||||
tal_free(ctx);
|
tal_free(ctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void decompress(char *hexprivkey, char *hexonion)
|
||||||
|
{
|
||||||
|
struct privkey rendezvous_key;
|
||||||
|
size_t onionlen = hex_data_size(strlen(hexonion));
|
||||||
|
u8 *compressed, *decompressed;
|
||||||
|
struct pubkey ephkey;
|
||||||
|
struct secret shared_secret;
|
||||||
|
|
||||||
|
if (!hex_decode(hexprivkey, strlen(hexprivkey), &rendezvous_key, sizeof(rendezvous_key)))
|
||||||
|
errx(1, "Invalid private key hex '%s'", hexprivkey);
|
||||||
|
|
||||||
|
compressed = tal_arr(NULL, u8, onionlen);
|
||||||
|
if (!hex_decode(hexonion, strlen(hexonion), compressed, onionlen))
|
||||||
|
errx(1, "Invalid onion hex '%s'", hexonion);
|
||||||
|
|
||||||
|
if (onionlen < HMAC_SIZE + 1 + PUBKEY_SIZE)
|
||||||
|
errx(1, "Onion is too short to contain the version, ephemeral key and HMAC");
|
||||||
|
|
||||||
|
pubkey_from_der(compressed + 1, PUBKEY_SIZE, &ephkey);
|
||||||
|
|
||||||
|
decompressed = sphinx_decompress(NULL, compressed, &shared_secret);
|
||||||
|
printf("Decompressed Onion: %s\n", tal_hex(NULL, decompressed));
|
||||||
|
}
|
||||||
|
|
||||||
/* Tal wrappers for opt. */
|
/* Tal wrappers for opt. */
|
||||||
static void *opt_allocfn(size_t size)
|
static void *opt_allocfn(size_t size)
|
||||||
{
|
{
|
||||||
|
@ -353,6 +377,15 @@ int main(int argc, char **argv)
|
||||||
do_generate(argc, argv, assocdata, NULL);
|
do_generate(argc, argv, assocdata, NULL);
|
||||||
else
|
else
|
||||||
do_generate(argc, argv, assocdata, &rendezvous_id);
|
do_generate(argc, argv, assocdata, &rendezvous_id);
|
||||||
|
} else if (streq(method, "decompress")) {
|
||||||
|
if (argc != 4) {
|
||||||
|
errx(2,
|
||||||
|
"'%s decompress' requires a private key and a "
|
||||||
|
"compressed onion",
|
||||||
|
argv[0]);
|
||||||
|
}
|
||||||
|
|
||||||
|
decompress(argv[2], argv[3]);
|
||||||
} else if (streq(method, "decode")) {
|
} else if (streq(method, "decode")) {
|
||||||
do_decode(argc, argv, assocdata);
|
do_decode(argc, argv, assocdata);
|
||||||
} else {
|
} else {
|
||||||
|
|
Loading…
Add table
Reference in a new issue