commit 1c4fdce514d8209fe6a58dd0316472505c0f8c54 Author: Rusty Russell Date: Tue May 26 14:08:12 2015 +0930 Initial silly cmdline util to create an openchannel packet. Signed-off-by: Rusty Russell diff --git a/.gitignore b/.gitignore new file mode 100644 index 000000000..3c6b734f8 --- /dev/null +++ b/.gitignore @@ -0,0 +1,3 @@ +*~ +*.o +openchannel diff --git a/Makefile b/Makefile new file mode 100644 index 000000000..f80e48dfb --- /dev/null +++ b/Makefile @@ -0,0 +1,61 @@ +#! /usr/bin/make + +# Needs to have oneof support: Ubuntu vivid's is too old :( +PROTOCC:=protoc-c + +PROGRAMS := openchannel + +HELPER_OBJS := base58.o lightning.pb-c.o shadouble.o pkt.o +CCAN_OBJS := ccan-crypto-sha256.o ccan-crypto-shachain.o ccan-err.o ccan-tal.o ccan-tal-str.o ccan-take.o ccan-list.o ccan-str.o ccan-opt-helpers.o ccan-opt.o ccan-opt-parse.o ccan-opt-usage.o ccan-read_write_all.o ccan-str-hex.o + +OPENCHANNEL_OBJS := openchannel.o $(HELPER_OBJS) $(CCAN_OBJS) + +HEADERS := base58.h lightning.pb-c.h pd_channel.h pkt.h shadouble.h + +CCANDIR := ../ccan/ +CFLAGS := -g -Wall -I $(CCANDIR) #-I $(PROTO_INCLUDE_DIR) +LDLIBS := -lcrypto -lprotobuf-c + +default: openchannel + +lightning.pb-c.c lightning.pb-c.h: lightning.proto + $(PROTOCC) lightning.proto --c_out=. + +openchannel: $(OPENCHANNEL_OBJS) +$(OPENCHANNEL_OBJS): $(HEADERS) + +distclean: clean + $(RM) lightning.pb-c.c lightning.pb-c.h + +clean: + $(RM) $(OPENCHANNEL_OBJS) + +ccan-tal.o: $(CCANDIR)/ccan/tal/tal.c + $(CC) $(CFLAGS) -c -o $@ $< +ccan-tal-str.o: $(CCANDIR)/ccan/tal/str/str.c + $(CC) $(CFLAGS) -c -o $@ $< +ccan-take.o: $(CCANDIR)/ccan/take/take.c + $(CC) $(CFLAGS) -c -o $@ $< +ccan-list.o: $(CCANDIR)/ccan/list/list.c + $(CC) $(CFLAGS) -c -o $@ $< +ccan-read_write_all.o: $(CCANDIR)/ccan/read_write_all/read_write_all.c + $(CC) $(CFLAGS) -c -o $@ $< +ccan-str.o: $(CCANDIR)/ccan/str/str.c + $(CC) $(CFLAGS) -c -o $@ $< +ccan-opt.o: $(CCANDIR)/ccan/opt/opt.c + $(CC) $(CFLAGS) -c -o $@ $< +ccan-opt-helpers.o: $(CCANDIR)/ccan/opt/helpers.c + $(CC) $(CFLAGS) -c -o $@ $< +ccan-opt-parse.o: $(CCANDIR)/ccan/opt/parse.c + $(CC) $(CFLAGS) -c -o $@ $< +ccan-opt-usage.o: $(CCANDIR)/ccan/opt/usage.c + $(CC) $(CFLAGS) -c -o $@ $< +ccan-err.o: $(CCANDIR)/ccan/err/err.c + $(CC) $(CFLAGS) -c -o $@ $< +ccan-str-hex.o: $(CCANDIR)/ccan/str/hex/hex.c + $(CC) $(CFLAGS) -c -o $@ $< +ccan-crypto-shachain.o: $(CCANDIR)/ccan/crypto/shachain/shachain.c + $(CC) $(CFLAGS) -c -o $@ $< +ccan-crypto-sha256.o: $(CCANDIR)/ccan/crypto/sha256/sha256.c + $(CC) $(CFLAGS) -c -o $@ $< + diff --git a/base58.c b/base58.c new file mode 100644 index 000000000..c9918a604 --- /dev/null +++ b/base58.c @@ -0,0 +1,361 @@ +/* Converted to C by Rusty Russell, based on bitcoin source: */ +// Copyright (c) 2009-2010 Satoshi Nakamoto +// Copyright (c) 2009-2012 The Bitcoin Developers +// Distributed under the MIT/X11 software license, see the accompanying +// file COPYING or http://www.opensource.org/licenses/mit-license.php. +#include "base58.h" +#include "shadouble.h" +#include +#include +#include +#include +#include +#include + +static const char enc_16[] = "0123456789abcdef"; +static const char enc_58[] = + "123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz"; + +static char encode_char(unsigned long val, const char *enc) +{ + assert(val < strlen(enc)); + return enc[val]; +} + +static int decode_char(char c, const char *enc) +{ + const char *pos = strchr(enc, c); + if (!pos) + return -1; + return pos - enc; +} + +/* + * Encode a byte sequence as a base58-encoded string. This is a bit + * weird: returns pointer into buf (or NULL if wouldn't fit). + */ +static char *encode_base58(char *buf, size_t buflen, + const u8 *data, size_t data_len) +{ + char *p; + BIGNUM bn; + + /* Convert to a bignum. */ + BN_init(&bn); + BN_bin2bn(data, data_len, &bn); + + /* Add NUL terminator */ + if (!buflen) { + p = NULL; + goto out; + } + p = buf + buflen; + *(--p) = '\0'; + + /* Fill from the back, using a series of divides. */ + while (!BN_is_zero(&bn)) { + int rem = BN_div_word(&bn, 58); + if (--p < buf) { + p = NULL; + goto out; + } + *p = encode_char(rem, enc_58); + } + + /* Now, this is really weird. We pad with zeroes, but not at + * base 58, but in terms of zero bytes. This means that some + * encodings are shorter than others! */ + while (data_len && *data == '\0') { + if (--p < buf) { + p = NULL; + goto out; + } + *p = encode_char(0, enc_58); + data_len--; + data++; + } + +out: + BN_free(&bn); + return p; +} + +/* + * Decode a base_n-encoded string into a byte sequence. + */ +bool raw_decode_base_n(BIGNUM *bn, const char *src, size_t len, int base) +{ + const char *enc; + + BN_zero(bn); + + assert(base == 16 || base == 58); + switch (base) { + case 16: + enc = enc_16; + break; + case 58: + enc = enc_58; + break; + } + + while (len) { + char current = *src; + + if (base == 16) + current = tolower(current); /* TODO: Not in ccan. */ + int val = decode_char(current, enc); + if (val < 0) { + BN_free(bn); + return false; + } + BN_mul_word(bn, base); + BN_add_word(bn, val); + src++; + len--; + } + + return true; +} + +/* + * Decode a base58-encoded string into a byte sequence. + */ +bool raw_decode_base58(BIGNUM *bn, const char *src, size_t len) +{ + return raw_decode_base_n(bn, src, len, 58); +} + +void base58_get_checksum(u8 csum[4], const u8 buf[], size_t buflen) +{ + struct sha256_double sha_result; + + /* Form checksum, using double SHA2 (as per bitcoin standard) */ + sha256_double(&sha_result, buf, buflen); + + /* Use first four bytes of that as the checksum. */ + memcpy(csum, sha_result.sha.u.u8, 4); +} + +char *bitcoin_to_base58(const tal_t *ctx, bool test_net, + const struct bitcoin_address *addr) +{ + u8 buf[1 + RIPEMD160_DIGEST_LENGTH + 4]; + char out[BASE58_ADDR_MAX_LEN + 2], *p; + + buf[0] = test_net ? 111 : 0; + + BUILD_ASSERT(sizeof(*addr) == RIPEMD160_DIGEST_LENGTH); + memcpy(buf+1, addr, RIPEMD160_DIGEST_LENGTH); + + /* Append checksum */ + base58_get_checksum(buf + 1 + RIPEMD160_DIGEST_LENGTH, + buf, 1 + RIPEMD160_DIGEST_LENGTH); + + p = encode_base58(out, BASE58_ADDR_MAX_LEN, buf, sizeof(buf)); + return tal_strdup(ctx, p); +} + +bool bitcoin_from_base58(bool *test_net, + struct bitcoin_address *addr, + const char *base58, size_t base58_len) +{ + u8 buf[1 + RIPEMD160_DIGEST_LENGTH + 4]; + BIGNUM bn; + size_t len; + u8 csum[4]; + + BN_init(&bn); + if (!raw_decode_base58(&bn, base58, base58_len)) + return false; + + len = BN_num_bytes(&bn); + if (len > sizeof(buf)) + return false; + + memset(buf, 0, sizeof(buf)); + BN_bn2bin(&bn, buf + sizeof(buf) - len); + BN_free(&bn); + + if (buf[0] == 111) + *test_net = true; + else if (buf[0] == 0) + *test_net = false; + else + return false; + + base58_get_checksum(csum, buf, 1 + RIPEMD160_DIGEST_LENGTH); + if (memcmp(csum, buf + 1 + RIPEMD160_DIGEST_LENGTH, sizeof(csum)) != 0) + return false; + + BUILD_ASSERT(sizeof(*addr) == RIPEMD160_DIGEST_LENGTH); + memcpy(addr, buf+1, sizeof(*addr)); + return true; +} + +/* buf already contains version and ripemd160. Append checksum and encode */ +char *base58_with_check(char dest[BASE58_ADDR_MAX_LEN], + u8 buf[1 + RIPEMD160_DIGEST_LENGTH + 4]) +{ + /* Append checksum */ + base58_get_checksum(buf + 1 + RIPEMD160_DIGEST_LENGTH, + buf, 1 + RIPEMD160_DIGEST_LENGTH); + + /* Now encode. */ + return encode_base58(dest, BASE58_ADDR_MAX_LEN, buf, + 1 + RIPEMD160_DIGEST_LENGTH + 4); +} + +bool ripemd_from_base58(u8 *version, u8 ripemd160[RIPEMD160_DIGEST_LENGTH], + const char *base58) +{ + u8 buf[1 + RIPEMD160_DIGEST_LENGTH + 4]; + u8 csum[4]; + BIGNUM bn; + size_t len; + + /* Too long? Check here before doing arithmetic. */ + if (strlen(base58) > BASE58_ADDR_MAX_LEN - 1) + return false; + + BN_init(&bn); + /* Fails if it contains invalid characters. */ + if (!raw_decode_base58(&bn, base58, strlen(base58))) + return false; + + /* Too big? */ + len = BN_num_bytes(&bn); + if (len > sizeof(buf)) { + BN_free(&bn); + return false; + } + + /* Fill start with zeroes. */ + memset(buf, 0, sizeof(buf) - len); + BN_bn2bin(&bn, buf + sizeof(buf) - len); + BN_free(&bn); + + /* Check checksum is correct. */ + base58_get_checksum(csum, buf, sizeof(buf)); + if (memcmp(csum, buf + 1 + RIPEMD160_DIGEST_LENGTH, 4) != 0) + return false; + + *version = buf[0]; + memcpy(ripemd160, buf + 1, RIPEMD160_DIGEST_LENGTH); + return true; +} + +char *key_to_base58(const tal_t *ctx, bool test_net, EC_KEY *key) +{ + u8 buf[1 + 32 + 1 + 4]; + char out[BASE58_KEY_MAX_LEN + 2], *p; + const BIGNUM *bn = EC_KEY_get0_private_key(key); + int len; + + buf[0] = test_net ? 239 : 128; + + /* Make sure any zeroes are at the front of number (MSB) */ + len = BN_num_bytes(bn); + assert(len <= 32); + memset(buf + 1, 0, 32 - len); + BN_bn2bin(bn, buf + 1 + 32 - len); + + /* Mark this as a compressed key. */ + buf[1 + 32] = 1; + + /* Append checksum */ + base58_get_checksum(buf + 1 + 32 + 1, buf, 1 + 32 + 1); + + p = encode_base58(out, BASE58_KEY_MAX_LEN, buf, sizeof(buf)); + return tal_strdup(ctx, p); +} + +// Thus function based on bitcoin's key.cpp: +// Copyright (c) 2009-2012 The Bitcoin developers +// Distributed under the MIT/X11 software license, see the accompanying +// file COPYING or http://www.opensource.org/licenses/mit-license.php. +static bool EC_KEY_regenerate_key(EC_KEY *eckey, BIGNUM *priv_key) +{ + BN_CTX *ctx = NULL; + EC_POINT *pub_key = NULL; + const EC_GROUP *group = EC_KEY_get0_group(eckey); + + if ((ctx = BN_CTX_new()) == NULL) + return false; + + pub_key = EC_POINT_new(group); + if (pub_key == NULL) + return false; + + if (!EC_POINT_mul(group, pub_key, priv_key, NULL, NULL, ctx)) + return false; + + EC_KEY_set_private_key(eckey, priv_key); + EC_KEY_set_public_key(eckey, pub_key); + + BN_CTX_free(ctx); + EC_POINT_free(pub_key); + return true; +} + +EC_KEY *key_from_base58(const char *base58, size_t base58_len, + bool *test_net, struct bitcoin_compressed_pubkey *key) +{ + size_t keylen; + u8 keybuf[1 + 32 + 1 + 4], *pubkey; + u8 csum[4]; + EC_KEY *priv; + BIGNUM bn; + + BN_init(&bn); + if (!raw_decode_base58(&bn, base58, base58_len)) + return NULL; + + keylen = BN_num_bytes(&bn); + /* FIXME: Handle non-compressed keys! */ + if (keylen == 1 + 32 + 4) + goto fail_free_bn; + if (keylen != 1 + 32 + 1 + 4) + goto fail_free_bn; + BN_bn2bin(&bn, keybuf); + + base58_get_checksum(csum, keybuf, keylen - sizeof(csum)); + if (memcmp(csum, keybuf + keylen - sizeof(csum), sizeof(csum)) != 0) + goto fail_free_bn; + + /* Byte after key should be 1 to represent a compressed key. */ + if (keybuf[1 + 32] != 1) + goto fail_free_bn; + + if (keybuf[0] == 128) + *test_net = false; + else if (keybuf[0] == 239) + *test_net = true; + else + goto fail_free_bn; + + priv = EC_KEY_new_by_curve_name(NID_secp256k1); + /* We *always* used compressed form keys. */ + EC_KEY_set_conv_form(priv, POINT_CONVERSION_COMPRESSED); + + BN_free(&bn); + BN_init(&bn); + if (!BN_bin2bn(keybuf + 1, 32, &bn)) + goto fail_free_priv; + if (!EC_KEY_regenerate_key(priv, &bn)) + goto fail_free_priv; + + /* Save public key */ + pubkey = key->key; + keylen = i2o_ECPublicKey(priv, &pubkey); + assert(keylen == sizeof(key->key)); + + BN_free(&bn); + return priv; + +fail_free_priv: + EC_KEY_free(priv); +fail_free_bn: + BN_free(&bn); + return NULL; +} diff --git a/base58.h b/base58.h new file mode 100644 index 000000000..152127e4c --- /dev/null +++ b/base58.h @@ -0,0 +1,54 @@ +#ifndef LIGHTNING_BASE58_H +#define LIGHTNING_BASE58_H +/* FIXME: Use libsecpk1 */ +#include +#include +#include +#include +#include +#include +#include + +/* Encoding is version byte + ripemd160 + 4-byte checksum == 200 bits => 2^200. + * + * Now, 58^34 < 2^200, but 58^35 > 2^200. So 35 digits is sufficient, + * plus 1 terminator. + */ +#define BASE58_ADDR_MAX_LEN 36 + +/* For encoding private keys, it's 302 bits. + * 58^51 < 2^302, but 58^52 > 2^302. So 52 digits, plus one terminator. */ +#define BASE58_KEY_MAX_LEN 53 + +/* An ECDSA compressed public key. 33 chars long, even on ARM. */ +struct bitcoin_compressed_pubkey { + u8 key[33]; +} __attribute__((aligned(1))); + +/* An address is the RIPEMD160 of the SHA of the public key. */ +struct bitcoin_address { + u8 addr[RIPEMD160_DIGEST_LENGTH]; /* 20 */ +}; + +/* Bitcoin address encoded in base58, with version and checksum */ +char *bitcoin_to_base58(const tal_t *ctx, bool test_net, + const struct bitcoin_address *addr); +bool bitcoin_from_base58(bool *test_net, + struct bitcoin_address *addr, + const char *base58, size_t len); + +bool ripemd_from_base58(u8 *version, u8 ripemd160[RIPEMD160_DIGEST_LENGTH], + const char *base58); + +char *base58_with_check(char dest[BASE58_ADDR_MAX_LEN], + u8 buf[1 + RIPEMD160_DIGEST_LENGTH + 4]); + +char *key_to_base58(const tal_t *ctx, bool test_net, EC_KEY *key); +EC_KEY *key_from_base58(const char *base58, size_t base58_len, + bool *test_net, struct bitcoin_compressed_pubkey *key); + +bool raw_decode_base_n(BIGNUM *bn, const char *src, size_t len, int base); +bool raw_decode_base58(BIGNUM *bn, const char *src, size_t len); +void base58_get_checksum(u8 csum[4], const u8 buf[], size_t buflen); + +#endif /* PETTYCOIN_BASE58_H */ diff --git a/lightning.pb-c.c b/lightning.pb-c.c new file mode 100644 index 000000000..188f77dc2 --- /dev/null +++ b/lightning.pb-c.c @@ -0,0 +1,2051 @@ +/* Generated by the protocol buffer compiler. DO NOT EDIT! */ +/* Generated from: lightning.proto */ + +/* Do not generate deprecated warnings for self */ +#ifndef PROTOBUF_C__NO_DEPRECATED +#define PROTOBUF_C__NO_DEPRECATED +#endif + +#include "lightning.pb-c.h" +void sha256_hash__init + (Sha256Hash *message) +{ + static Sha256Hash init_value = SHA256_HASH__INIT; + *message = init_value; +} +size_t sha256_hash__get_packed_size + (const Sha256Hash *message) +{ + assert(message->base.descriptor == &sha256_hash__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t sha256_hash__pack + (const Sha256Hash *message, + uint8_t *out) +{ + assert(message->base.descriptor == &sha256_hash__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t sha256_hash__pack_to_buffer + (const Sha256Hash *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &sha256_hash__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +Sha256Hash * + sha256_hash__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (Sha256Hash *) + protobuf_c_message_unpack (&sha256_hash__descriptor, + allocator, len, data); +} +void sha256_hash__free_unpacked + (Sha256Hash *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &sha256_hash__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void bitcoin_output_id__init + (BitcoinOutputId *message) +{ + static BitcoinOutputId init_value = BITCOIN_OUTPUT_ID__INIT; + *message = init_value; +} +size_t bitcoin_output_id__get_packed_size + (const BitcoinOutputId *message) +{ + assert(message->base.descriptor == &bitcoin_output_id__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t bitcoin_output_id__pack + (const BitcoinOutputId *message, + uint8_t *out) +{ + assert(message->base.descriptor == &bitcoin_output_id__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t bitcoin_output_id__pack_to_buffer + (const BitcoinOutputId *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &bitcoin_output_id__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +BitcoinOutputId * + bitcoin_output_id__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (BitcoinOutputId *) + protobuf_c_message_unpack (&bitcoin_output_id__descriptor, + allocator, len, data); +} +void bitcoin_output_id__free_unpacked + (BitcoinOutputId *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &bitcoin_output_id__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void bitcoin_output__init + (BitcoinOutput *message) +{ + static BitcoinOutput init_value = BITCOIN_OUTPUT__INIT; + *message = init_value; +} +size_t bitcoin_output__get_packed_size + (const BitcoinOutput *message) +{ + assert(message->base.descriptor == &bitcoin_output__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t bitcoin_output__pack + (const BitcoinOutput *message, + uint8_t *out) +{ + assert(message->base.descriptor == &bitcoin_output__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t bitcoin_output__pack_to_buffer + (const BitcoinOutput *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &bitcoin_output__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +BitcoinOutput * + bitcoin_output__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (BitcoinOutput *) + protobuf_c_message_unpack (&bitcoin_output__descriptor, + allocator, len, data); +} +void bitcoin_output__free_unpacked + (BitcoinOutput *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &bitcoin_output__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void bitcoin_signature__init + (BitcoinSignature *message) +{ + static BitcoinSignature init_value = BITCOIN_SIGNATURE__INIT; + *message = init_value; +} +size_t bitcoin_signature__get_packed_size + (const BitcoinSignature *message) +{ + assert(message->base.descriptor == &bitcoin_signature__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t bitcoin_signature__pack + (const BitcoinSignature *message, + uint8_t *out) +{ + assert(message->base.descriptor == &bitcoin_signature__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t bitcoin_signature__pack_to_buffer + (const BitcoinSignature *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &bitcoin_signature__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +BitcoinSignature * + bitcoin_signature__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (BitcoinSignature *) + protobuf_c_message_unpack (&bitcoin_signature__descriptor, + allocator, len, data); +} +void bitcoin_signature__free_unpacked + (BitcoinSignature *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &bitcoin_signature__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void anchor__init + (Anchor *message) +{ + static Anchor init_value = ANCHOR__INIT; + *message = init_value; +} +size_t anchor__get_packed_size + (const Anchor *message) +{ + assert(message->base.descriptor == &anchor__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t anchor__pack + (const Anchor *message, + uint8_t *out) +{ + assert(message->base.descriptor == &anchor__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t anchor__pack_to_buffer + (const Anchor *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &anchor__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +Anchor * + anchor__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (Anchor *) + protobuf_c_message_unpack (&anchor__descriptor, + allocator, len, data); +} +void anchor__free_unpacked + (Anchor *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &anchor__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void open_channel__init + (OpenChannel *message) +{ + static OpenChannel init_value = OPEN_CHANNEL__INIT; + *message = init_value; +} +size_t open_channel__get_packed_size + (const OpenChannel *message) +{ + assert(message->base.descriptor == &open_channel__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t open_channel__pack + (const OpenChannel *message, + uint8_t *out) +{ + assert(message->base.descriptor == &open_channel__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t open_channel__pack_to_buffer + (const OpenChannel *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &open_channel__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +OpenChannel * + open_channel__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (OpenChannel *) + protobuf_c_message_unpack (&open_channel__descriptor, + allocator, len, data); +} +void open_channel__free_unpacked + (OpenChannel *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &open_channel__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void open_commit_sig__init + (OpenCommitSig *message) +{ + static OpenCommitSig init_value = OPEN_COMMIT_SIG__INIT; + *message = init_value; +} +size_t open_commit_sig__get_packed_size + (const OpenCommitSig *message) +{ + assert(message->base.descriptor == &open_commit_sig__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t open_commit_sig__pack + (const OpenCommitSig *message, + uint8_t *out) +{ + assert(message->base.descriptor == &open_commit_sig__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t open_commit_sig__pack_to_buffer + (const OpenCommitSig *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &open_commit_sig__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +OpenCommitSig * + open_commit_sig__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (OpenCommitSig *) + protobuf_c_message_unpack (&open_commit_sig__descriptor, + allocator, len, data); +} +void open_commit_sig__free_unpacked + (OpenCommitSig *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &open_commit_sig__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void open_anchor_sig__init + (OpenAnchorSig *message) +{ + static OpenAnchorSig init_value = OPEN_ANCHOR_SIG__INIT; + *message = init_value; +} +size_t open_anchor_sig__get_packed_size + (const OpenAnchorSig *message) +{ + assert(message->base.descriptor == &open_anchor_sig__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t open_anchor_sig__pack + (const OpenAnchorSig *message, + uint8_t *out) +{ + assert(message->base.descriptor == &open_anchor_sig__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t open_anchor_sig__pack_to_buffer + (const OpenAnchorSig *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &open_anchor_sig__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +OpenAnchorSig * + open_anchor_sig__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (OpenAnchorSig *) + protobuf_c_message_unpack (&open_anchor_sig__descriptor, + allocator, len, data); +} +void open_anchor_sig__free_unpacked + (OpenAnchorSig *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &open_anchor_sig__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void open_complete__init + (OpenComplete *message) +{ + static OpenComplete init_value = OPEN_COMPLETE__INIT; + *message = init_value; +} +size_t open_complete__get_packed_size + (const OpenComplete *message) +{ + assert(message->base.descriptor == &open_complete__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t open_complete__pack + (const OpenComplete *message, + uint8_t *out) +{ + assert(message->base.descriptor == &open_complete__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t open_complete__pack_to_buffer + (const OpenComplete *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &open_complete__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +OpenComplete * + open_complete__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (OpenComplete *) + protobuf_c_message_unpack (&open_complete__descriptor, + allocator, len, data); +} +void open_complete__free_unpacked + (OpenComplete *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &open_complete__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void update__init + (Update *message) +{ + static Update init_value = UPDATE__INIT; + *message = init_value; +} +size_t update__get_packed_size + (const Update *message) +{ + assert(message->base.descriptor == &update__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t update__pack + (const Update *message, + uint8_t *out) +{ + assert(message->base.descriptor == &update__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t update__pack_to_buffer + (const Update *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &update__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +Update * + update__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (Update *) + protobuf_c_message_unpack (&update__descriptor, + allocator, len, data); +} +void update__free_unpacked + (Update *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &update__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void update_accept__init + (UpdateAccept *message) +{ + static UpdateAccept init_value = UPDATE_ACCEPT__INIT; + *message = init_value; +} +size_t update_accept__get_packed_size + (const UpdateAccept *message) +{ + assert(message->base.descriptor == &update_accept__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t update_accept__pack + (const UpdateAccept *message, + uint8_t *out) +{ + assert(message->base.descriptor == &update_accept__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t update_accept__pack_to_buffer + (const UpdateAccept *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &update_accept__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +UpdateAccept * + update_accept__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (UpdateAccept *) + protobuf_c_message_unpack (&update_accept__descriptor, + allocator, len, data); +} +void update_accept__free_unpacked + (UpdateAccept *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &update_accept__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void update_complete__init + (UpdateComplete *message) +{ + static UpdateComplete init_value = UPDATE_COMPLETE__INIT; + *message = init_value; +} +size_t update_complete__get_packed_size + (const UpdateComplete *message) +{ + assert(message->base.descriptor == &update_complete__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t update_complete__pack + (const UpdateComplete *message, + uint8_t *out) +{ + assert(message->base.descriptor == &update_complete__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t update_complete__pack_to_buffer + (const UpdateComplete *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &update_complete__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +UpdateComplete * + update_complete__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (UpdateComplete *) + protobuf_c_message_unpack (&update_complete__descriptor, + allocator, len, data); +} +void update_complete__free_unpacked + (UpdateComplete *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &update_complete__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void new_anchor__init + (NewAnchor *message) +{ + static NewAnchor init_value = NEW_ANCHOR__INIT; + *message = init_value; +} +size_t new_anchor__get_packed_size + (const NewAnchor *message) +{ + assert(message->base.descriptor == &new_anchor__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t new_anchor__pack + (const NewAnchor *message, + uint8_t *out) +{ + assert(message->base.descriptor == &new_anchor__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t new_anchor__pack_to_buffer + (const NewAnchor *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &new_anchor__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +NewAnchor * + new_anchor__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (NewAnchor *) + protobuf_c_message_unpack (&new_anchor__descriptor, + allocator, len, data); +} +void new_anchor__free_unpacked + (NewAnchor *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &new_anchor__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void new_anchor_ack__init + (NewAnchorAck *message) +{ + static NewAnchorAck init_value = NEW_ANCHOR_ACK__INIT; + *message = init_value; +} +size_t new_anchor_ack__get_packed_size + (const NewAnchorAck *message) +{ + assert(message->base.descriptor == &new_anchor_ack__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t new_anchor_ack__pack + (const NewAnchorAck *message, + uint8_t *out) +{ + assert(message->base.descriptor == &new_anchor_ack__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t new_anchor_ack__pack_to_buffer + (const NewAnchorAck *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &new_anchor_ack__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +NewAnchorAck * + new_anchor_ack__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (NewAnchorAck *) + protobuf_c_message_unpack (&new_anchor_ack__descriptor, + allocator, len, data); +} +void new_anchor_ack__free_unpacked + (NewAnchorAck *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &new_anchor_ack__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void new_anchor_accept__init + (NewAnchorAccept *message) +{ + static NewAnchorAccept init_value = NEW_ANCHOR_ACCEPT__INIT; + *message = init_value; +} +size_t new_anchor_accept__get_packed_size + (const NewAnchorAccept *message) +{ + assert(message->base.descriptor == &new_anchor_accept__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t new_anchor_accept__pack + (const NewAnchorAccept *message, + uint8_t *out) +{ + assert(message->base.descriptor == &new_anchor_accept__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t new_anchor_accept__pack_to_buffer + (const NewAnchorAccept *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &new_anchor_accept__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +NewAnchorAccept * + new_anchor_accept__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (NewAnchorAccept *) + protobuf_c_message_unpack (&new_anchor_accept__descriptor, + allocator, len, data); +} +void new_anchor_accept__free_unpacked + (NewAnchorAccept *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &new_anchor_accept__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void new_anchor_complete__init + (NewAnchorComplete *message) +{ + static NewAnchorComplete init_value = NEW_ANCHOR_COMPLETE__INIT; + *message = init_value; +} +size_t new_anchor_complete__get_packed_size + (const NewAnchorComplete *message) +{ + assert(message->base.descriptor == &new_anchor_complete__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t new_anchor_complete__pack + (const NewAnchorComplete *message, + uint8_t *out) +{ + assert(message->base.descriptor == &new_anchor_complete__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t new_anchor_complete__pack_to_buffer + (const NewAnchorComplete *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &new_anchor_complete__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +NewAnchorComplete * + new_anchor_complete__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (NewAnchorComplete *) + protobuf_c_message_unpack (&new_anchor_complete__descriptor, + allocator, len, data); +} +void new_anchor_complete__free_unpacked + (NewAnchorComplete *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &new_anchor_complete__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void close_channel__init + (CloseChannel *message) +{ + static CloseChannel init_value = CLOSE_CHANNEL__INIT; + *message = init_value; +} +size_t close_channel__get_packed_size + (const CloseChannel *message) +{ + assert(message->base.descriptor == &close_channel__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t close_channel__pack + (const CloseChannel *message, + uint8_t *out) +{ + assert(message->base.descriptor == &close_channel__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t close_channel__pack_to_buffer + (const CloseChannel *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &close_channel__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +CloseChannel * + close_channel__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (CloseChannel *) + protobuf_c_message_unpack (&close_channel__descriptor, + allocator, len, data); +} +void close_channel__free_unpacked + (CloseChannel *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &close_channel__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void close_channel_complete__init + (CloseChannelComplete *message) +{ + static CloseChannelComplete init_value = CLOSE_CHANNEL_COMPLETE__INIT; + *message = init_value; +} +size_t close_channel_complete__get_packed_size + (const CloseChannelComplete *message) +{ + assert(message->base.descriptor == &close_channel_complete__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t close_channel_complete__pack + (const CloseChannelComplete *message, + uint8_t *out) +{ + assert(message->base.descriptor == &close_channel_complete__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t close_channel_complete__pack_to_buffer + (const CloseChannelComplete *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &close_channel_complete__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +CloseChannelComplete * + close_channel_complete__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (CloseChannelComplete *) + protobuf_c_message_unpack (&close_channel_complete__descriptor, + allocator, len, data); +} +void close_channel_complete__free_unpacked + (CloseChannelComplete *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &close_channel_complete__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void error__init + (Error *message) +{ + static Error init_value = ERROR__INIT; + *message = init_value; +} +size_t error__get_packed_size + (const Error *message) +{ + assert(message->base.descriptor == &error__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t error__pack + (const Error *message, + uint8_t *out) +{ + assert(message->base.descriptor == &error__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t error__pack_to_buffer + (const Error *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &error__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +Error * + error__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (Error *) + protobuf_c_message_unpack (&error__descriptor, + allocator, len, data); +} +void error__free_unpacked + (Error *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &error__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +void pkt__init + (Pkt *message) +{ + static Pkt init_value = PKT__INIT; + *message = init_value; +} +size_t pkt__get_packed_size + (const Pkt *message) +{ + assert(message->base.descriptor == &pkt__descriptor); + return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message)); +} +size_t pkt__pack + (const Pkt *message, + uint8_t *out) +{ + assert(message->base.descriptor == &pkt__descriptor); + return protobuf_c_message_pack ((const ProtobufCMessage*)message, out); +} +size_t pkt__pack_to_buffer + (const Pkt *message, + ProtobufCBuffer *buffer) +{ + assert(message->base.descriptor == &pkt__descriptor); + return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer); +} +Pkt * + pkt__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data) +{ + return (Pkt *) + protobuf_c_message_unpack (&pkt__descriptor, + allocator, len, data); +} +void pkt__free_unpacked + (Pkt *message, + ProtobufCAllocator *allocator) +{ + assert(message->base.descriptor == &pkt__descriptor); + protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator); +} +static const ProtobufCFieldDescriptor sha256_hash__field_descriptors[4] = +{ + { + "a", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_FIXED64, + 0, /* quantifier_offset */ + offsetof(Sha256Hash, a), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "b", + 2, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_FIXED64, + 0, /* quantifier_offset */ + offsetof(Sha256Hash, b), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "c", + 3, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_FIXED64, + 0, /* quantifier_offset */ + offsetof(Sha256Hash, c), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "d", + 4, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_FIXED64, + 0, /* quantifier_offset */ + offsetof(Sha256Hash, d), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned sha256_hash__field_indices_by_name[] = { + 0, /* field[0] = a */ + 1, /* field[1] = b */ + 2, /* field[2] = c */ + 3, /* field[3] = d */ +}; +static const ProtobufCIntRange sha256_hash__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 4 } +}; +const ProtobufCMessageDescriptor sha256_hash__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "sha256_hash", + "Sha256Hash", + "Sha256Hash", + "", + sizeof(Sha256Hash), + 4, + sha256_hash__field_descriptors, + sha256_hash__field_indices_by_name, + 1, sha256_hash__number_ranges, + (ProtobufCMessageInit) sha256_hash__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor bitcoin_output_id__field_descriptors[2] = +{ + { + "txid", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(BitcoinOutputId, txid), + &sha256_hash__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "output", + 2, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_UINT32, + 0, /* quantifier_offset */ + offsetof(BitcoinOutputId, output), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned bitcoin_output_id__field_indices_by_name[] = { + 1, /* field[1] = output */ + 0, /* field[0] = txid */ +}; +static const ProtobufCIntRange bitcoin_output_id__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 2 } +}; +const ProtobufCMessageDescriptor bitcoin_output_id__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "bitcoin_output_id", + "BitcoinOutputId", + "BitcoinOutputId", + "", + sizeof(BitcoinOutputId), + 2, + bitcoin_output_id__field_descriptors, + bitcoin_output_id__field_indices_by_name, + 1, bitcoin_output_id__number_ranges, + (ProtobufCMessageInit) bitcoin_output_id__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor bitcoin_output__field_descriptors[2] = +{ + { + "amount", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_UINT64, + 0, /* quantifier_offset */ + offsetof(BitcoinOutput, amount), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "script", + 2, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_BYTES, + 0, /* quantifier_offset */ + offsetof(BitcoinOutput, script), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned bitcoin_output__field_indices_by_name[] = { + 0, /* field[0] = amount */ + 1, /* field[1] = script */ +}; +static const ProtobufCIntRange bitcoin_output__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 2 } +}; +const ProtobufCMessageDescriptor bitcoin_output__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "bitcoin_output", + "BitcoinOutput", + "BitcoinOutput", + "", + sizeof(BitcoinOutput), + 2, + bitcoin_output__field_descriptors, + bitcoin_output__field_indices_by_name, + 1, bitcoin_output__number_ranges, + (ProtobufCMessageInit) bitcoin_output__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor bitcoin_signature__field_descriptors[1] = +{ + { + "der_then_sigtype", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_BYTES, + 0, /* quantifier_offset */ + offsetof(BitcoinSignature, der_then_sigtype), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned bitcoin_signature__field_indices_by_name[] = { + 0, /* field[0] = der_then_sigtype */ +}; +static const ProtobufCIntRange bitcoin_signature__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 1 } +}; +const ProtobufCMessageDescriptor bitcoin_signature__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "bitcoin_signature", + "BitcoinSignature", + "BitcoinSignature", + "", + sizeof(BitcoinSignature), + 1, + bitcoin_signature__field_descriptors, + bitcoin_signature__field_indices_by_name, + 1, bitcoin_signature__number_ranges, + (ProtobufCMessageInit) bitcoin_signature__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor anchor__field_descriptors[4] = +{ + { + "inputs", + 1, + PROTOBUF_C_LABEL_REPEATED, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Anchor, n_inputs), + offsetof(Anchor, inputs), + &bitcoin_output_id__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "anchor_change", + 2, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(Anchor, anchor_change), + &bitcoin_output__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "fee", + 8, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_UINT64, + 0, /* quantifier_offset */ + offsetof(Anchor, fee), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "min_confirms", + 10, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_UINT32, + 0, /* quantifier_offset */ + offsetof(Anchor, min_confirms), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned anchor__field_indices_by_name[] = { + 1, /* field[1] = anchor_change */ + 2, /* field[2] = fee */ + 0, /* field[0] = inputs */ + 3, /* field[3] = min_confirms */ +}; +static const ProtobufCIntRange anchor__number_ranges[3 + 1] = +{ + { 1, 0 }, + { 8, 2 }, + { 10, 3 }, + { 0, 4 } +}; +const ProtobufCMessageDescriptor anchor__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "anchor", + "Anchor", + "Anchor", + "", + sizeof(Anchor), + 4, + anchor__field_descriptors, + anchor__field_indices_by_name, + 3, anchor__number_ranges, + (ProtobufCMessageInit) anchor__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor open_channel__field_descriptors[7] = +{ + { + "seed", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_UINT64, + 0, /* quantifier_offset */ + offsetof(OpenChannel, seed), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "locktime_seconds", + 2, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_UINT32, + offsetof(OpenChannel, locktime_case), + offsetof(OpenChannel, locktime_seconds), + NULL, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "locktime_blocks", + 3, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_UINT32, + offsetof(OpenChannel, locktime_case), + offsetof(OpenChannel, locktime_blocks), + NULL, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "revocation_hash", + 4, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(OpenChannel, revocation_hash), + &sha256_hash__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "script_to_me", + 5, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_BYTES, + 0, /* quantifier_offset */ + offsetof(OpenChannel, script_to_me), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "commitment_fee", + 6, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_UINT64, + 0, /* quantifier_offset */ + offsetof(OpenChannel, commitment_fee), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "anchor", + 7, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(OpenChannel, anchor), + &anchor__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned open_channel__field_indices_by_name[] = { + 6, /* field[6] = anchor */ + 5, /* field[5] = commitment_fee */ + 2, /* field[2] = locktime_blocks */ + 1, /* field[1] = locktime_seconds */ + 3, /* field[3] = revocation_hash */ + 4, /* field[4] = script_to_me */ + 0, /* field[0] = seed */ +}; +static const ProtobufCIntRange open_channel__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 7 } +}; +const ProtobufCMessageDescriptor open_channel__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "open_channel", + "OpenChannel", + "OpenChannel", + "", + sizeof(OpenChannel), + 7, + open_channel__field_descriptors, + open_channel__field_indices_by_name, + 1, open_channel__number_ranges, + (ProtobufCMessageInit) open_channel__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor open_commit_sig__field_descriptors[1] = +{ + { + "sig", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(OpenCommitSig, sig), + &bitcoin_signature__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned open_commit_sig__field_indices_by_name[] = { + 0, /* field[0] = sig */ +}; +static const ProtobufCIntRange open_commit_sig__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 1 } +}; +const ProtobufCMessageDescriptor open_commit_sig__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "open_commit_sig", + "OpenCommitSig", + "OpenCommitSig", + "", + sizeof(OpenCommitSig), + 1, + open_commit_sig__field_descriptors, + open_commit_sig__field_indices_by_name, + 1, open_commit_sig__number_ranges, + (ProtobufCMessageInit) open_commit_sig__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor open_anchor_sig__field_descriptors[1] = +{ + { + "sig", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(OpenAnchorSig, sig), + &bitcoin_signature__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned open_anchor_sig__field_indices_by_name[] = { + 0, /* field[0] = sig */ +}; +static const ProtobufCIntRange open_anchor_sig__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 1 } +}; +const ProtobufCMessageDescriptor open_anchor_sig__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "open_anchor_sig", + "OpenAnchorSig", + "OpenAnchorSig", + "", + sizeof(OpenAnchorSig), + 1, + open_anchor_sig__field_descriptors, + open_anchor_sig__field_indices_by_name, + 1, open_anchor_sig__number_ranges, + (ProtobufCMessageInit) open_anchor_sig__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor open_complete__field_descriptors[1] = +{ + { + "blockid", + 1, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(OpenComplete, blockid), + &sha256_hash__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned open_complete__field_indices_by_name[] = { + 0, /* field[0] = blockid */ +}; +static const ProtobufCIntRange open_complete__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 1 } +}; +const ProtobufCMessageDescriptor open_complete__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "open_complete", + "OpenComplete", + "OpenComplete", + "", + sizeof(OpenComplete), + 1, + open_complete__field_descriptors, + open_complete__field_indices_by_name, + 1, open_complete__number_ranges, + (ProtobufCMessageInit) open_complete__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor update__field_descriptors[4] = +{ + { + "revocation_hash", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(Update, revocation_hash), + &sha256_hash__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "delta", + 2, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_SINT64, + 0, /* quantifier_offset */ + offsetof(Update, delta), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "sig", + 3, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(Update, sig), + &bitcoin_signature__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "old_anchor_sig", + 4, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(Update, old_anchor_sig), + &bitcoin_signature__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned update__field_indices_by_name[] = { + 1, /* field[1] = delta */ + 3, /* field[3] = old_anchor_sig */ + 0, /* field[0] = revocation_hash */ + 2, /* field[2] = sig */ +}; +static const ProtobufCIntRange update__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 4 } +}; +const ProtobufCMessageDescriptor update__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "update", + "Update", + "Update", + "", + sizeof(Update), + 4, + update__field_descriptors, + update__field_indices_by_name, + 1, update__number_ranges, + (ProtobufCMessageInit) update__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor update_accept__field_descriptors[3] = +{ + { + "sig", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(UpdateAccept, sig), + &bitcoin_signature__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "old_anchor_sig", + 2, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(UpdateAccept, old_anchor_sig), + &bitcoin_signature__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "revocation_preimage", + 3, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(UpdateAccept, revocation_preimage), + &sha256_hash__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned update_accept__field_indices_by_name[] = { + 1, /* field[1] = old_anchor_sig */ + 2, /* field[2] = revocation_preimage */ + 0, /* field[0] = sig */ +}; +static const ProtobufCIntRange update_accept__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 3 } +}; +const ProtobufCMessageDescriptor update_accept__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "update_accept", + "UpdateAccept", + "UpdateAccept", + "", + sizeof(UpdateAccept), + 3, + update_accept__field_descriptors, + update_accept__field_indices_by_name, + 1, update_accept__number_ranges, + (ProtobufCMessageInit) update_accept__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor update_complete__field_descriptors[1] = +{ + { + "revocation_preimage", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(UpdateComplete, revocation_preimage), + &sha256_hash__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned update_complete__field_indices_by_name[] = { + 0, /* field[0] = revocation_preimage */ +}; +static const ProtobufCIntRange update_complete__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 1 } +}; +const ProtobufCMessageDescriptor update_complete__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "update_complete", + "UpdateComplete", + "UpdateComplete", + "", + sizeof(UpdateComplete), + 1, + update_complete__field_descriptors, + update_complete__field_indices_by_name, + 1, update_complete__number_ranges, + (ProtobufCMessageInit) update_complete__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor new_anchor__field_descriptors[1] = +{ + { + "anchor", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(NewAnchor, anchor), + &anchor__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned new_anchor__field_indices_by_name[] = { + 0, /* field[0] = anchor */ +}; +static const ProtobufCIntRange new_anchor__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 1 } +}; +const ProtobufCMessageDescriptor new_anchor__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "new_anchor", + "NewAnchor", + "NewAnchor", + "", + sizeof(NewAnchor), + 1, + new_anchor__field_descriptors, + new_anchor__field_indices_by_name, + 1, new_anchor__number_ranges, + (ProtobufCMessageInit) new_anchor__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor new_anchor_ack__field_descriptors[1] = +{ + { + "sig", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(NewAnchorAck, sig), + &bitcoin_signature__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned new_anchor_ack__field_indices_by_name[] = { + 0, /* field[0] = sig */ +}; +static const ProtobufCIntRange new_anchor_ack__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 1 } +}; +const ProtobufCMessageDescriptor new_anchor_ack__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "new_anchor_ack", + "NewAnchorAck", + "NewAnchorAck", + "", + sizeof(NewAnchorAck), + 1, + new_anchor_ack__field_descriptors, + new_anchor_ack__field_indices_by_name, + 1, new_anchor_ack__number_ranges, + (ProtobufCMessageInit) new_anchor_ack__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor new_anchor_accept__field_descriptors[1] = +{ + { + "sig", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(NewAnchorAccept, sig), + &bitcoin_signature__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned new_anchor_accept__field_indices_by_name[] = { + 0, /* field[0] = sig */ +}; +static const ProtobufCIntRange new_anchor_accept__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 1 } +}; +const ProtobufCMessageDescriptor new_anchor_accept__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "new_anchor_accept", + "NewAnchorAccept", + "NewAnchorAccept", + "", + sizeof(NewAnchorAccept), + 1, + new_anchor_accept__field_descriptors, + new_anchor_accept__field_indices_by_name, + 1, new_anchor_accept__number_ranges, + (ProtobufCMessageInit) new_anchor_accept__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor new_anchor_complete__field_descriptors[1] = +{ + { + "revocation_preimage", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(NewAnchorComplete, revocation_preimage), + &sha256_hash__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned new_anchor_complete__field_indices_by_name[] = { + 0, /* field[0] = revocation_preimage */ +}; +static const ProtobufCIntRange new_anchor_complete__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 1 } +}; +const ProtobufCMessageDescriptor new_anchor_complete__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "new_anchor_complete", + "NewAnchorComplete", + "NewAnchorComplete", + "", + sizeof(NewAnchorComplete), + 1, + new_anchor_complete__field_descriptors, + new_anchor_complete__field_indices_by_name, + 1, new_anchor_complete__number_ranges, + (ProtobufCMessageInit) new_anchor_complete__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor close_channel__field_descriptors[1] = +{ + { + "sig", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(CloseChannel, sig), + &bitcoin_signature__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned close_channel__field_indices_by_name[] = { + 0, /* field[0] = sig */ +}; +static const ProtobufCIntRange close_channel__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 1 } +}; +const ProtobufCMessageDescriptor close_channel__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "close_channel", + "CloseChannel", + "CloseChannel", + "", + sizeof(CloseChannel), + 1, + close_channel__field_descriptors, + close_channel__field_indices_by_name, + 1, close_channel__number_ranges, + (ProtobufCMessageInit) close_channel__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor close_channel_complete__field_descriptors[1] = +{ + { + "sig", + 1, + PROTOBUF_C_LABEL_REQUIRED, + PROTOBUF_C_TYPE_MESSAGE, + 0, /* quantifier_offset */ + offsetof(CloseChannelComplete, sig), + &bitcoin_signature__descriptor, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned close_channel_complete__field_indices_by_name[] = { + 0, /* field[0] = sig */ +}; +static const ProtobufCIntRange close_channel_complete__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 1 } +}; +const ProtobufCMessageDescriptor close_channel_complete__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "close_channel_complete", + "CloseChannelComplete", + "CloseChannelComplete", + "", + sizeof(CloseChannelComplete), + 1, + close_channel_complete__field_descriptors, + close_channel_complete__field_indices_by_name, + 1, close_channel_complete__number_ranges, + (ProtobufCMessageInit) close_channel_complete__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor error__field_descriptors[1] = +{ + { + "problem", + 1, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_STRING, + 0, /* quantifier_offset */ + offsetof(Error, problem), + NULL, + NULL, + 0, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned error__field_indices_by_name[] = { + 0, /* field[0] = problem */ +}; +static const ProtobufCIntRange error__number_ranges[1 + 1] = +{ + { 1, 0 }, + { 0, 1 } +}; +const ProtobufCMessageDescriptor error__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "error", + "Error", + "Error", + "", + sizeof(Error), + 1, + error__field_descriptors, + error__field_indices_by_name, + 1, error__number_ranges, + (ProtobufCMessageInit) error__init, + NULL,NULL,NULL /* reserved[123] */ +}; +static const ProtobufCFieldDescriptor pkt__field_descriptors[14] = +{ + { + "update", + 1, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Pkt, pkt_case), + offsetof(Pkt, update), + &update__descriptor, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "update_accept", + 2, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Pkt, pkt_case), + offsetof(Pkt, update_accept), + &update_accept__descriptor, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "update_complete", + 3, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Pkt, pkt_case), + offsetof(Pkt, update_complete), + &update_complete__descriptor, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "open", + 201, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Pkt, pkt_case), + offsetof(Pkt, open), + &open_channel__descriptor, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "open_commit_sig", + 202, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Pkt, pkt_case), + offsetof(Pkt, open_commit_sig), + &open_commit_sig__descriptor, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "open_anchor_sig", + 203, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Pkt, pkt_case), + offsetof(Pkt, open_anchor_sig), + &open_anchor_sig__descriptor, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "open_complete", + 204, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Pkt, pkt_case), + offsetof(Pkt, open_complete), + &open_complete__descriptor, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "new_anchor", + 301, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Pkt, pkt_case), + offsetof(Pkt, new_anchor), + &new_anchor__descriptor, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "new_anchor_ack", + 302, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Pkt, pkt_case), + offsetof(Pkt, new_anchor_ack), + &new_anchor_ack__descriptor, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "new_anchor_accept", + 303, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Pkt, pkt_case), + offsetof(Pkt, new_anchor_accept), + &new_anchor_accept__descriptor, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "new_anchor_complete", + 304, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Pkt, pkt_case), + offsetof(Pkt, new_anchor_complete), + &new_anchor_complete__descriptor, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "close", + 401, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Pkt, pkt_case), + offsetof(Pkt, close), + &close_channel__descriptor, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "close_complete", + 402, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Pkt, pkt_case), + offsetof(Pkt, close_complete), + &close_channel_complete__descriptor, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, + { + "error", + 1000, + PROTOBUF_C_LABEL_OPTIONAL, + PROTOBUF_C_TYPE_MESSAGE, + offsetof(Pkt, pkt_case), + offsetof(Pkt, error), + &error__descriptor, + NULL, + 0 | PROTOBUF_C_FIELD_FLAG_ONEOF, /* flags */ + 0,NULL,NULL /* reserved1,reserved2, etc */ + }, +}; +static const unsigned pkt__field_indices_by_name[] = { + 11, /* field[11] = close */ + 12, /* field[12] = close_complete */ + 13, /* field[13] = error */ + 7, /* field[7] = new_anchor */ + 9, /* field[9] = new_anchor_accept */ + 8, /* field[8] = new_anchor_ack */ + 10, /* field[10] = new_anchor_complete */ + 3, /* field[3] = open */ + 5, /* field[5] = open_anchor_sig */ + 4, /* field[4] = open_commit_sig */ + 6, /* field[6] = open_complete */ + 0, /* field[0] = update */ + 1, /* field[1] = update_accept */ + 2, /* field[2] = update_complete */ +}; +static const ProtobufCIntRange pkt__number_ranges[5 + 1] = +{ + { 1, 0 }, + { 201, 3 }, + { 301, 7 }, + { 401, 11 }, + { 1000, 13 }, + { 0, 14 } +}; +const ProtobufCMessageDescriptor pkt__descriptor = +{ + PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC, + "pkt", + "Pkt", + "Pkt", + "", + sizeof(Pkt), + 14, + pkt__field_descriptors, + pkt__field_indices_by_name, + 5, pkt__number_ranges, + (ProtobufCMessageInit) pkt__init, + NULL,NULL,NULL /* reserved[123] */ +}; diff --git a/lightning.pb-c.h b/lightning.pb-c.h new file mode 100644 index 000000000..79ea350fd --- /dev/null +++ b/lightning.pb-c.h @@ -0,0 +1,933 @@ +/* Generated by the protocol buffer compiler. DO NOT EDIT! */ +/* Generated from: lightning.proto */ + +#ifndef PROTOBUF_C_lightning_2eproto__INCLUDED +#define PROTOBUF_C_lightning_2eproto__INCLUDED + +#include + +PROTOBUF_C__BEGIN_DECLS + +#if PROTOBUF_C_VERSION_NUMBER < 1000000 +# error This file was generated by a newer version of protoc-c which is incompatible with your libprotobuf-c headers. Please update your headers. +#elif 1001001 < PROTOBUF_C_MIN_COMPILER_VERSION +# error This file was generated by an older version of protoc-c which is incompatible with your libprotobuf-c headers. Please regenerate this file with a newer version of protoc-c. +#endif + + +typedef struct _Sha256Hash Sha256Hash; +typedef struct _BitcoinOutputId BitcoinOutputId; +typedef struct _BitcoinOutput BitcoinOutput; +typedef struct _BitcoinSignature BitcoinSignature; +typedef struct _Anchor Anchor; +typedef struct _OpenChannel OpenChannel; +typedef struct _OpenCommitSig OpenCommitSig; +typedef struct _OpenAnchorSig OpenAnchorSig; +typedef struct _OpenComplete OpenComplete; +typedef struct _Update Update; +typedef struct _UpdateAccept UpdateAccept; +typedef struct _UpdateComplete UpdateComplete; +typedef struct _NewAnchor NewAnchor; +typedef struct _NewAnchorAck NewAnchorAck; +typedef struct _NewAnchorAccept NewAnchorAccept; +typedef struct _NewAnchorComplete NewAnchorComplete; +typedef struct _CloseChannel CloseChannel; +typedef struct _CloseChannelComplete CloseChannelComplete; +typedef struct _Error Error; +typedef struct _Pkt Pkt; + + +/* --- enums --- */ + + +/* --- messages --- */ + +/* + * Protobufs don't have fixed-length fields, so this is a hack. + */ +struct _Sha256Hash +{ + ProtobufCMessage base; + uint64_t a; + uint64_t b; + uint64_t c; + uint64_t d; +}; +#define SHA256_HASH__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&sha256_hash__descriptor) \ + , 0, 0, 0, 0 } + + +/* + * Identifies a bitcoin output. + */ +struct _BitcoinOutputId +{ + ProtobufCMessage base; + /* + * This is the transaction ID. + */ + Sha256Hash *txid; + /* + * This is the output number. + */ + uint32_t output; +}; +#define BITCOIN_OUTPUT_ID__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&bitcoin_output_id__descriptor) \ + , NULL, 0 } + + +/* + * A bitcoin output + */ +struct _BitcoinOutput +{ + ProtobufCMessage base; + uint64_t amount; + ProtobufCBinaryData script; +}; +#define BITCOIN_OUTPUT__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&bitcoin_output__descriptor) \ + , 0, {0,NULL} } + + +/* + * A signature to use for a transaction; DER encoded with sigtype at the end. + */ +struct _BitcoinSignature +{ + ProtobufCMessage base; + ProtobufCBinaryData der_then_sigtype; +}; +#define BITCOIN_SIGNATURE__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&bitcoin_signature__descriptor) \ + , {0,NULL} } + + +/* + * All about an anchor transaction. + */ +struct _Anchor +{ + ProtobufCMessage base; + /* + * 0 or more unspent inputs we want to use for anchor. + */ + size_t n_inputs; + BitcoinOutputId **inputs; + /* + * Any change from anchor (in case we don't want to use them all) + */ + BitcoinOutput *anchor_change; + /* + * How much transaction fee we'll pay in the anchor tx. + */ + uint64_t fee; + /* + * How many confirmations on anchor before we'll use channel. + */ + uint32_t min_confirms; +}; +#define ANCHOR__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&anchor__descriptor) \ + , 0,NULL, NULL, 0, 0 } + + +typedef enum { + OPEN_CHANNEL__LOCKTIME__NOT_SET = 0, + OPEN_CHANNEL__LOCKTIME_LOCKTIME_SECONDS = 2, + OPEN_CHANNEL__LOCKTIME_LOCKTIME_BLOCKS = 3, +} OpenChannel__LocktimeCase; + +/* + * Set channel params. + */ +struct _OpenChannel +{ + ProtobufCMessage base; + /* + * Seed which sets order we create outputs for all transactions. + */ + uint64_t seed; + /* + * Hash seed for revoking commitment transactions. + */ + Sha256Hash *revocation_hash; + /* + * How to pay money to us. + */ + ProtobufCBinaryData script_to_me; + /* + * How much transaction fee we'll pay for commitment txs. + */ + uint64_t commitment_fee; + /* + * The anchor transaction details. + */ + Anchor *anchor; + OpenChannel__LocktimeCase locktime_case; + union { + uint32_t locktime_seconds; + uint32_t locktime_blocks; + }; +}; +#define OPEN_CHANNEL__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&open_channel__descriptor) \ + , 0, NULL, {0,NULL}, 0, NULL, OPEN_CHANNEL__LOCKTIME__NOT_SET, {} } + + +/* + * Supply signature for commitment tx + */ +struct _OpenCommitSig +{ + ProtobufCMessage base; + BitcoinSignature *sig; +}; +#define OPEN_COMMIT_SIG__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&open_commit_sig__descriptor) \ + , NULL } + + +/* + * Supply signature for anchor tx + */ +struct _OpenAnchorSig +{ + ProtobufCMessage base; + BitcoinSignature *sig; +}; +#define OPEN_ANCHOR_SIG__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&open_anchor_sig__descriptor) \ + , NULL } + + +/* + * Indicates we've seen transaction reach min-depth. + */ +struct _OpenComplete +{ + ProtobufCMessage base; + /* + * Block it went into. + */ + /* + * FIXME: add a merkle proof plus block headers here? + */ + Sha256Hash *blockid; +}; +#define OPEN_COMPLETE__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&open_complete__descriptor) \ + , NULL } + + +/* + * Let's spend some money in the channel! + */ +struct _Update +{ + ProtobufCMessage base; + /* + * Hash for which I will supply preimage to revoke this. + */ + Sha256Hash *revocation_hash; + /* + * Change in current payment to-me (implies reverse to-you). + */ + int64_t delta; + /* + * Signature for new commitment tx. + */ + BitcoinSignature *sig; + /* + * Signature for old anchor (if any) + */ + /* + * FIXME: optional HTLC ops. + */ + BitcoinSignature *old_anchor_sig; +}; +#define UPDATE__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&update__descriptor) \ + , NULL, 0, NULL, NULL } + + +/* + * OK, I accept that update. + */ +struct _UpdateAccept +{ + ProtobufCMessage base; + /* + * Signature for new commitment tx. + */ + BitcoinSignature *sig; + /* + * Signature for old anchor (if any) + */ + BitcoinSignature *old_anchor_sig; + /* + * Hash preimage which revokes old commitment tx. + */ + Sha256Hash *revocation_preimage; +}; +#define UPDATE_ACCEPT__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&update_accept__descriptor) \ + , NULL, NULL, NULL } + + +/* + * Complete the update. + */ +struct _UpdateComplete +{ + ProtobufCMessage base; + /* + * Hash preimage which revokes old commitment tx. + */ + Sha256Hash *revocation_preimage; +}; +#define UPDATE_COMPLETE__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&update_complete__descriptor) \ + , NULL } + + +/* + * Let's change the channel funding source. + */ +struct _NewAnchor +{ + ProtobufCMessage base; + /* + * The new anchor: previous anchor 2x2 input assumed. + */ + Anchor *anchor; +}; +#define NEW_ANCHOR__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&new_anchor__descriptor) \ + , NULL } + + +/* + * That seems OK to me! + */ +struct _NewAnchorAck +{ + ProtobufCMessage base; + BitcoinSignature *sig; +}; +#define NEW_ANCHOR_ACK__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&new_anchor_ack__descriptor) \ + , NULL } + + +/* + * Here's my signature on the new anchor to complete it. + */ +struct _NewAnchorAccept +{ + ProtobufCMessage base; + BitcoinSignature *sig; +}; +#define NEW_ANCHOR_ACCEPT__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&new_anchor_accept__descriptor) \ + , NULL } + + +/* + * Complete the transfer to new anchor (both ends need to send this, + * once they're happy that it's reached their required depth). + */ +struct _NewAnchorComplete +{ + ProtobufCMessage base; + Sha256Hash *revocation_preimage; +}; +#define NEW_ANCHOR_COMPLETE__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&new_anchor_complete__descriptor) \ + , NULL } + + +/* + * Begin cooperative close of channel. + */ +struct _CloseChannel +{ + ProtobufCMessage base; + /* + * This is our signature a new transaction which spends my current + * commitment tx output 0 (which is 2/2) to script_to_me. + */ + BitcoinSignature *sig; +}; +#define CLOSE_CHANNEL__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&close_channel__descriptor) \ + , NULL } + + +/* + * OK, here's my sig so you can broadcast it too. + */ +struct _CloseChannelComplete +{ + ProtobufCMessage base; + /* + * This is our signature a new transaction which spends your current + * commitment tx output 0 (which is 2/2) to your script_to_me. + */ + BitcoinSignature *sig; +}; +#define CLOSE_CHANNEL_COMPLETE__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&close_channel_complete__descriptor) \ + , NULL } + + +/* + * This means we're going to hang up; it's to help diagnose only! + */ +struct _Error +{ + ProtobufCMessage base; + char *problem; +}; +#define ERROR__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&error__descriptor) \ + , NULL } + + +typedef enum { + PKT__PKT__NOT_SET = 0, + PKT__PKT_OPEN = 201, + PKT__PKT_OPEN_COMMIT_SIG = 202, + PKT__PKT_OPEN_ANCHOR_SIG = 203, + PKT__PKT_OPEN_COMPLETE = 204, + PKT__PKT_UPDATE = 1, + PKT__PKT_UPDATE_ACCEPT = 2, + PKT__PKT_UPDATE_COMPLETE = 3, + PKT__PKT_NEW_ANCHOR = 301, + PKT__PKT_NEW_ANCHOR_ACK = 302, + PKT__PKT_NEW_ANCHOR_ACCEPT = 303, + PKT__PKT_NEW_ANCHOR_COMPLETE = 304, + PKT__PKT_CLOSE = 401, + PKT__PKT_CLOSE_COMPLETE = 402, + PKT__PKT_ERROR = 1000, +} Pkt__PktCase; + +/* + * This is the union which defines all of them + */ +struct _Pkt +{ + ProtobufCMessage base; + Pkt__PktCase pkt_case; + union { + /* + * Opening + */ + OpenChannel *open; + OpenCommitSig *open_commit_sig; + OpenAnchorSig *open_anchor_sig; + OpenComplete *open_complete; + /* + * Updating (most common) + */ + Update *update; + UpdateAccept *update_accept; + UpdateComplete *update_complete; + /* + * Topping up + */ + NewAnchor *new_anchor; + NewAnchorAck *new_anchor_ack; + NewAnchorAccept *new_anchor_accept; + NewAnchorComplete *new_anchor_complete; + /* + * Closing + */ + CloseChannel *close; + CloseChannelComplete *close_complete; + /* + * Unexpected issue. + */ + Error *error; + }; +}; +#define PKT__INIT \ + { PROTOBUF_C_MESSAGE_INIT (&pkt__descriptor) \ + , PKT__PKT__NOT_SET, {} } + + +/* Sha256Hash methods */ +void sha256_hash__init + (Sha256Hash *message); +size_t sha256_hash__get_packed_size + (const Sha256Hash *message); +size_t sha256_hash__pack + (const Sha256Hash *message, + uint8_t *out); +size_t sha256_hash__pack_to_buffer + (const Sha256Hash *message, + ProtobufCBuffer *buffer); +Sha256Hash * + sha256_hash__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void sha256_hash__free_unpacked + (Sha256Hash *message, + ProtobufCAllocator *allocator); +/* BitcoinOutputId methods */ +void bitcoin_output_id__init + (BitcoinOutputId *message); +size_t bitcoin_output_id__get_packed_size + (const BitcoinOutputId *message); +size_t bitcoin_output_id__pack + (const BitcoinOutputId *message, + uint8_t *out); +size_t bitcoin_output_id__pack_to_buffer + (const BitcoinOutputId *message, + ProtobufCBuffer *buffer); +BitcoinOutputId * + bitcoin_output_id__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void bitcoin_output_id__free_unpacked + (BitcoinOutputId *message, + ProtobufCAllocator *allocator); +/* BitcoinOutput methods */ +void bitcoin_output__init + (BitcoinOutput *message); +size_t bitcoin_output__get_packed_size + (const BitcoinOutput *message); +size_t bitcoin_output__pack + (const BitcoinOutput *message, + uint8_t *out); +size_t bitcoin_output__pack_to_buffer + (const BitcoinOutput *message, + ProtobufCBuffer *buffer); +BitcoinOutput * + bitcoin_output__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void bitcoin_output__free_unpacked + (BitcoinOutput *message, + ProtobufCAllocator *allocator); +/* BitcoinSignature methods */ +void bitcoin_signature__init + (BitcoinSignature *message); +size_t bitcoin_signature__get_packed_size + (const BitcoinSignature *message); +size_t bitcoin_signature__pack + (const BitcoinSignature *message, + uint8_t *out); +size_t bitcoin_signature__pack_to_buffer + (const BitcoinSignature *message, + ProtobufCBuffer *buffer); +BitcoinSignature * + bitcoin_signature__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void bitcoin_signature__free_unpacked + (BitcoinSignature *message, + ProtobufCAllocator *allocator); +/* Anchor methods */ +void anchor__init + (Anchor *message); +size_t anchor__get_packed_size + (const Anchor *message); +size_t anchor__pack + (const Anchor *message, + uint8_t *out); +size_t anchor__pack_to_buffer + (const Anchor *message, + ProtobufCBuffer *buffer); +Anchor * + anchor__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void anchor__free_unpacked + (Anchor *message, + ProtobufCAllocator *allocator); +/* OpenChannel methods */ +void open_channel__init + (OpenChannel *message); +size_t open_channel__get_packed_size + (const OpenChannel *message); +size_t open_channel__pack + (const OpenChannel *message, + uint8_t *out); +size_t open_channel__pack_to_buffer + (const OpenChannel *message, + ProtobufCBuffer *buffer); +OpenChannel * + open_channel__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void open_channel__free_unpacked + (OpenChannel *message, + ProtobufCAllocator *allocator); +/* OpenCommitSig methods */ +void open_commit_sig__init + (OpenCommitSig *message); +size_t open_commit_sig__get_packed_size + (const OpenCommitSig *message); +size_t open_commit_sig__pack + (const OpenCommitSig *message, + uint8_t *out); +size_t open_commit_sig__pack_to_buffer + (const OpenCommitSig *message, + ProtobufCBuffer *buffer); +OpenCommitSig * + open_commit_sig__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void open_commit_sig__free_unpacked + (OpenCommitSig *message, + ProtobufCAllocator *allocator); +/* OpenAnchorSig methods */ +void open_anchor_sig__init + (OpenAnchorSig *message); +size_t open_anchor_sig__get_packed_size + (const OpenAnchorSig *message); +size_t open_anchor_sig__pack + (const OpenAnchorSig *message, + uint8_t *out); +size_t open_anchor_sig__pack_to_buffer + (const OpenAnchorSig *message, + ProtobufCBuffer *buffer); +OpenAnchorSig * + open_anchor_sig__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void open_anchor_sig__free_unpacked + (OpenAnchorSig *message, + ProtobufCAllocator *allocator); +/* OpenComplete methods */ +void open_complete__init + (OpenComplete *message); +size_t open_complete__get_packed_size + (const OpenComplete *message); +size_t open_complete__pack + (const OpenComplete *message, + uint8_t *out); +size_t open_complete__pack_to_buffer + (const OpenComplete *message, + ProtobufCBuffer *buffer); +OpenComplete * + open_complete__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void open_complete__free_unpacked + (OpenComplete *message, + ProtobufCAllocator *allocator); +/* Update methods */ +void update__init + (Update *message); +size_t update__get_packed_size + (const Update *message); +size_t update__pack + (const Update *message, + uint8_t *out); +size_t update__pack_to_buffer + (const Update *message, + ProtobufCBuffer *buffer); +Update * + update__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void update__free_unpacked + (Update *message, + ProtobufCAllocator *allocator); +/* UpdateAccept methods */ +void update_accept__init + (UpdateAccept *message); +size_t update_accept__get_packed_size + (const UpdateAccept *message); +size_t update_accept__pack + (const UpdateAccept *message, + uint8_t *out); +size_t update_accept__pack_to_buffer + (const UpdateAccept *message, + ProtobufCBuffer *buffer); +UpdateAccept * + update_accept__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void update_accept__free_unpacked + (UpdateAccept *message, + ProtobufCAllocator *allocator); +/* UpdateComplete methods */ +void update_complete__init + (UpdateComplete *message); +size_t update_complete__get_packed_size + (const UpdateComplete *message); +size_t update_complete__pack + (const UpdateComplete *message, + uint8_t *out); +size_t update_complete__pack_to_buffer + (const UpdateComplete *message, + ProtobufCBuffer *buffer); +UpdateComplete * + update_complete__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void update_complete__free_unpacked + (UpdateComplete *message, + ProtobufCAllocator *allocator); +/* NewAnchor methods */ +void new_anchor__init + (NewAnchor *message); +size_t new_anchor__get_packed_size + (const NewAnchor *message); +size_t new_anchor__pack + (const NewAnchor *message, + uint8_t *out); +size_t new_anchor__pack_to_buffer + (const NewAnchor *message, + ProtobufCBuffer *buffer); +NewAnchor * + new_anchor__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void new_anchor__free_unpacked + (NewAnchor *message, + ProtobufCAllocator *allocator); +/* NewAnchorAck methods */ +void new_anchor_ack__init + (NewAnchorAck *message); +size_t new_anchor_ack__get_packed_size + (const NewAnchorAck *message); +size_t new_anchor_ack__pack + (const NewAnchorAck *message, + uint8_t *out); +size_t new_anchor_ack__pack_to_buffer + (const NewAnchorAck *message, + ProtobufCBuffer *buffer); +NewAnchorAck * + new_anchor_ack__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void new_anchor_ack__free_unpacked + (NewAnchorAck *message, + ProtobufCAllocator *allocator); +/* NewAnchorAccept methods */ +void new_anchor_accept__init + (NewAnchorAccept *message); +size_t new_anchor_accept__get_packed_size + (const NewAnchorAccept *message); +size_t new_anchor_accept__pack + (const NewAnchorAccept *message, + uint8_t *out); +size_t new_anchor_accept__pack_to_buffer + (const NewAnchorAccept *message, + ProtobufCBuffer *buffer); +NewAnchorAccept * + new_anchor_accept__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void new_anchor_accept__free_unpacked + (NewAnchorAccept *message, + ProtobufCAllocator *allocator); +/* NewAnchorComplete methods */ +void new_anchor_complete__init + (NewAnchorComplete *message); +size_t new_anchor_complete__get_packed_size + (const NewAnchorComplete *message); +size_t new_anchor_complete__pack + (const NewAnchorComplete *message, + uint8_t *out); +size_t new_anchor_complete__pack_to_buffer + (const NewAnchorComplete *message, + ProtobufCBuffer *buffer); +NewAnchorComplete * + new_anchor_complete__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void new_anchor_complete__free_unpacked + (NewAnchorComplete *message, + ProtobufCAllocator *allocator); +/* CloseChannel methods */ +void close_channel__init + (CloseChannel *message); +size_t close_channel__get_packed_size + (const CloseChannel *message); +size_t close_channel__pack + (const CloseChannel *message, + uint8_t *out); +size_t close_channel__pack_to_buffer + (const CloseChannel *message, + ProtobufCBuffer *buffer); +CloseChannel * + close_channel__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void close_channel__free_unpacked + (CloseChannel *message, + ProtobufCAllocator *allocator); +/* CloseChannelComplete methods */ +void close_channel_complete__init + (CloseChannelComplete *message); +size_t close_channel_complete__get_packed_size + (const CloseChannelComplete *message); +size_t close_channel_complete__pack + (const CloseChannelComplete *message, + uint8_t *out); +size_t close_channel_complete__pack_to_buffer + (const CloseChannelComplete *message, + ProtobufCBuffer *buffer); +CloseChannelComplete * + close_channel_complete__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void close_channel_complete__free_unpacked + (CloseChannelComplete *message, + ProtobufCAllocator *allocator); +/* Error methods */ +void error__init + (Error *message); +size_t error__get_packed_size + (const Error *message); +size_t error__pack + (const Error *message, + uint8_t *out); +size_t error__pack_to_buffer + (const Error *message, + ProtobufCBuffer *buffer); +Error * + error__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void error__free_unpacked + (Error *message, + ProtobufCAllocator *allocator); +/* Pkt methods */ +void pkt__init + (Pkt *message); +size_t pkt__get_packed_size + (const Pkt *message); +size_t pkt__pack + (const Pkt *message, + uint8_t *out); +size_t pkt__pack_to_buffer + (const Pkt *message, + ProtobufCBuffer *buffer); +Pkt * + pkt__unpack + (ProtobufCAllocator *allocator, + size_t len, + const uint8_t *data); +void pkt__free_unpacked + (Pkt *message, + ProtobufCAllocator *allocator); +/* --- per-message closures --- */ + +typedef void (*Sha256Hash_Closure) + (const Sha256Hash *message, + void *closure_data); +typedef void (*BitcoinOutputId_Closure) + (const BitcoinOutputId *message, + void *closure_data); +typedef void (*BitcoinOutput_Closure) + (const BitcoinOutput *message, + void *closure_data); +typedef void (*BitcoinSignature_Closure) + (const BitcoinSignature *message, + void *closure_data); +typedef void (*Anchor_Closure) + (const Anchor *message, + void *closure_data); +typedef void (*OpenChannel_Closure) + (const OpenChannel *message, + void *closure_data); +typedef void (*OpenCommitSig_Closure) + (const OpenCommitSig *message, + void *closure_data); +typedef void (*OpenAnchorSig_Closure) + (const OpenAnchorSig *message, + void *closure_data); +typedef void (*OpenComplete_Closure) + (const OpenComplete *message, + void *closure_data); +typedef void (*Update_Closure) + (const Update *message, + void *closure_data); +typedef void (*UpdateAccept_Closure) + (const UpdateAccept *message, + void *closure_data); +typedef void (*UpdateComplete_Closure) + (const UpdateComplete *message, + void *closure_data); +typedef void (*NewAnchor_Closure) + (const NewAnchor *message, + void *closure_data); +typedef void (*NewAnchorAck_Closure) + (const NewAnchorAck *message, + void *closure_data); +typedef void (*NewAnchorAccept_Closure) + (const NewAnchorAccept *message, + void *closure_data); +typedef void (*NewAnchorComplete_Closure) + (const NewAnchorComplete *message, + void *closure_data); +typedef void (*CloseChannel_Closure) + (const CloseChannel *message, + void *closure_data); +typedef void (*CloseChannelComplete_Closure) + (const CloseChannelComplete *message, + void *closure_data); +typedef void (*Error_Closure) + (const Error *message, + void *closure_data); +typedef void (*Pkt_Closure) + (const Pkt *message, + void *closure_data); + +/* --- services --- */ + + +/* --- descriptors --- */ + +extern const ProtobufCMessageDescriptor sha256_hash__descriptor; +extern const ProtobufCMessageDescriptor bitcoin_output_id__descriptor; +extern const ProtobufCMessageDescriptor bitcoin_output__descriptor; +extern const ProtobufCMessageDescriptor bitcoin_signature__descriptor; +extern const ProtobufCMessageDescriptor anchor__descriptor; +extern const ProtobufCMessageDescriptor open_channel__descriptor; +extern const ProtobufCMessageDescriptor open_commit_sig__descriptor; +extern const ProtobufCMessageDescriptor open_anchor_sig__descriptor; +extern const ProtobufCMessageDescriptor open_complete__descriptor; +extern const ProtobufCMessageDescriptor update__descriptor; +extern const ProtobufCMessageDescriptor update_accept__descriptor; +extern const ProtobufCMessageDescriptor update_complete__descriptor; +extern const ProtobufCMessageDescriptor new_anchor__descriptor; +extern const ProtobufCMessageDescriptor new_anchor_ack__descriptor; +extern const ProtobufCMessageDescriptor new_anchor_accept__descriptor; +extern const ProtobufCMessageDescriptor new_anchor_complete__descriptor; +extern const ProtobufCMessageDescriptor close_channel__descriptor; +extern const ProtobufCMessageDescriptor close_channel_complete__descriptor; +extern const ProtobufCMessageDescriptor error__descriptor; +extern const ProtobufCMessageDescriptor pkt__descriptor; + +PROTOBUF_C__END_DECLS + + +#endif /* PROTOBUF_C_lightning_2eproto__INCLUDED */ diff --git a/lightning.proto b/lightning.proto new file mode 100644 index 000000000..b83708f40 --- /dev/null +++ b/lightning.proto @@ -0,0 +1,181 @@ +// The outer layer handles encryption, authentication and message +// boundaries. + +// +// Helper Types +// + +// Protobufs don't have fixed-length fields, so this is a hack. +message sha256_hash { + required fixed64 a = 1; + required fixed64 b = 2; + required fixed64 c = 3; + required fixed64 d = 4; +} + +// Identifies a bitcoin output. +message bitcoin_output_id { + // This is the transaction ID. + required sha256_hash txid = 1; + // This is the output number. + required uint32 output = 2; +} + +// A bitcoin output +message bitcoin_output { + required uint64 amount = 1; + required bytes script = 2; +} + +// A signature to use for a transaction; DER encoded with sigtype at the end. +message bitcoin_signature { + required bytes der_then_sigtype = 1; +}; + +// All about an anchor transaction. +message anchor { + // 0 or more unspent inputs we want to use for anchor. + repeated bitcoin_output_id inputs = 1; + // Any change from anchor (in case we don't want to use them all) + optional bitcoin_output anchor_change = 2; + // How much transaction fee we'll pay in the anchor tx. + required uint64 fee = 8; + // How many confirmations on anchor before we'll use channel. + required uint32 min_confirms = 10; +} + +// +// Packet Types +// + +// Set channel params. +message open_channel { + // Seed which sets order we create outputs for all transactions. + required uint64 seed = 1; + // Relative locktime for outputs going to us. + oneof locktime { + uint32 locktime_seconds = 2; + uint32 locktime_blocks = 3; + } + // Hash seed for revoking commitment transactions. + required sha256_hash revocation_hash = 4; + // How to pay money to us. + required bytes script_to_me = 5; + // How much transaction fee we'll pay for commitment txs. + required uint64 commitment_fee = 6; + // The anchor transaction details. + required anchor anchor = 7; +} + +// Supply signature for commitment tx +message open_commit_sig { + required bitcoin_signature sig = 1; +} + +// Supply signature for anchor tx +message open_anchor_sig { + required bitcoin_signature sig = 1; +} + +// Indicates we've seen transaction reach min-depth. +message open_complete { + // Block it went into. + optional sha256_hash blockid = 1; + // FIXME: add a merkle proof plus block headers here? +} + +// Let's spend some money in the channel! +message update { + // Hash for which I will supply preimage to revoke this. + required sha256_hash revocation_hash = 1; + // Change in current payment to-me (implies reverse to-you). + required sint64 delta = 2; + // Signature for new commitment tx. + required bitcoin_signature sig = 3; + // Signature for old anchor (if any) + optional bitcoin_signature old_anchor_sig = 4; + // FIXME: optional HTLC ops. +} + +// OK, I accept that update. +message update_accept { + // Signature for new commitment tx. + required bitcoin_signature sig = 1; + // Signature for old anchor (if any) + optional bitcoin_signature old_anchor_sig = 2; + // Hash preimage which revokes old commitment tx. + required sha256_hash revocation_preimage = 3; +} + +// Complete the update. +message update_complete { + // Hash preimage which revokes old commitment tx. + required sha256_hash revocation_preimage = 1; +} + +// Let's change the channel funding source. +message new_anchor { + // The new anchor: previous anchor 2x2 input assumed. + required anchor anchor = 1; +} + +// That seems OK to me! +message new_anchor_ack { + required bitcoin_signature sig = 1; +} + +// Here's my signature on the new anchor to complete it. +message new_anchor_accept { + required bitcoin_signature sig = 1; +} + +// Complete the transfer to new anchor (both ends need to send this, +// once they're happy that it's reached their required depth). +message new_anchor_complete { + required sha256_hash revocation_preimage = 1; +} + +// Begin cooperative close of channel. +message close_channel { + // This is our signature a new transaction which spends my current + // commitment tx output 0 (which is 2/2) to script_to_me. + required bitcoin_signature sig = 1; +} + +// OK, here's my sig so you can broadcast it too. +message close_channel_complete { + // This is our signature a new transaction which spends your current + // commitment tx output 0 (which is 2/2) to your script_to_me. + required bitcoin_signature sig = 1; +} + +// This means we're going to hang up; it's to help diagnose only! +message error { + optional string problem = 1; +} + +// This is the union which defines all of them +message pkt { + oneof pkt { + // Opening + open_channel open = 201; + open_commit_sig open_commit_sig = 202; + open_anchor_sig open_anchor_sig = 203; + open_complete open_complete = 204; + // Updating (most common) + update update = 1; + update_accept update_accept = 2; + update_complete update_complete = 3; + // Topping up + new_anchor new_anchor = 301; + new_anchor_ack new_anchor_ack = 302; + new_anchor_accept new_anchor_accept = 303; + new_anchor_complete new_anchor_complete = 304; + // Closing + close_channel close = 401; + close_channel_complete close_complete = 402; + + // Unexpected issue. + error error = 1000; + } +} diff --git a/openchannel.c b/openchannel.c new file mode 100644 index 000000000..8e3534da4 --- /dev/null +++ b/openchannel.c @@ -0,0 +1,163 @@ +#include +#include +#include +#include +#include +#include +#include +#include "lightning.pb-c.h" +#include "base58.h" +#include "pkt.h" +#include +#include + +/* Bitcoin nodes are allowed to be 2 hours in the future. */ +#define LOCKTIME_MIN (2 * 60 * 60) + +static char *opt_set_bits(const char *arg, u64 *satoshi) +{ + unsigned long long ll; + char *ret = opt_set_ulonglongval_si(arg, &ll); + if (ret) + return ret; + *satoshi = ll * 100; + if (*satoshi / 100 != ll) + return "Invalid number of bits"; + return NULL; +} + +static void opt_show_bits(char buf[OPT_SHOW_LEN], const u64 *bits) +{ + unsigned long long ll = *bits / 100; + opt_show_ulonglongval_si(buf, &ll); +} + +static BitcoinOutputId *parse_anchor_input(const tal_t *ctx, const char *spec) +{ + BitcoinOutputId *o = tal(ctx, BitcoinOutputId); + struct sha256 txid; + const char *slash; + char *end; + long l; + + bitcoin_output_id__init(o); + + slash = strchr(spec, '/'); + if (!slash) + errx(1, "Expected / in /"); + o->output = l = strtol(slash + 1, &end, 10); + if (end == slash + 1 || *end || (int64_t)o->output != (int64_t)l) + errx(1, "Expected after /"); + + if (!hex_decode(spec, slash - spec, &txid, sizeof(txid))) + errx(1, "Expected 256-bit hex txid before /"); + + o->txid = proto_sha256_hash(o, &txid); + return o; +} + +static u8 *pay_to_pubkey(const tal_t *ctx, const struct bitcoin_address *addr) +{ + u8 *script = tal_arr(ctx, u8, 2 + 20 + 2); + script[0] = 0x76; /* OP_DUP */ + script[1] = 0xA9; /* OP_HASH160 */ + memcpy(script+2, addr, 20); + script[22] = 0x88; /* OP_EQUALVERIFY */ + script[23] = 0xAC; /* OP_CHECKSIG */ + + return script; +} + +/* FIXME: This is too weak, even for us! */ +static u64 weak_random64(void) +{ + return time(NULL); +} + +/* Simple helper to open a channel. */ +int main(int argc, char *argv[]) +{ + struct sha256 seed, revocation_hash; + struct bitcoin_address ouraddr; + EC_KEY *privkey; + struct pkt *pkt; + const tal_t *ctx = tal_arr(NULL, char, 0); + Anchor anchor = ANCHOR__INIT; + u64 commit_tx_fee; + unsigned int locktime_seconds; + bool testnet; + struct bitcoin_compressed_pubkey pubkey; + u8 *script_to_me; + size_t i; + + err_set_progname(argv[0]); + + /* Default values. */ + anchor.min_confirms = 3; + /* Remember, other side contributes to fee, too. */ + anchor.fee = 5000; + /* We only need this for involuntary close, so make it larger. */ + commit_tx_fee = 100000; + /* This means we have ~1 day before they can steal our money. */ + locktime_seconds = LOCKTIME_MIN + 24 * 60 * 60; + + opt_register_noarg("--help|-h", opt_usage_and_exit, + " /...\n" + "A test program to output openchannel on stdout.", + "Print this message."); + opt_register_arg("--min-anchor-confirms", + opt_set_uintval, opt_show_uintval, &anchor.min_confirms, + "Number of anchor confirmations before channel is active"); + opt_register_arg("--anchor-fee=", + opt_set_bits, opt_show_bits, &anchor.fee, + "100's of satoshi to pay for anchor"); + opt_register_arg("--commitment-fee=", + opt_set_bits, opt_show_bits, &commit_tx_fee, + "100's of satoshi to pay for commitment"); + opt_register_arg("--locktime=", + opt_set_uintval, opt_show_uintval, &locktime_seconds, + "Seconds to lock out our transaction redemption"); + /* FIXME: Implement change address and amount. */ + + opt_parse(&argc, argv, opt_log_stderr_exit); + + if (argc < 5) + opt_usage_and_exit(NULL); + + if (!hex_decode(argv[1], strlen(argv[1]), &seed, sizeof(seed))) + errx(1, "Invalid seed '%s' - need 256 hex bits", argv[1]); + + privkey = key_from_base58(argv[2], strlen(argv[2]), &testnet, &pubkey); + if (!privkey) + errx(1, "Invalid private key '%s'", argv[2]); + if (!testnet) + errx(1, "Private key '%s' not a testnet key!", argv[2]); + + if (!bitcoin_from_base58(&testnet, &ouraddr, argv[3], strlen(argv[3]))) + errx(1, "Invalid bitcoin address '%s'", argv[3]); + if (!testnet) + errx(1, "Bitcoin address '%s' not on testnet!", argv[3]); + + anchor.n_inputs = (argc - 4); + anchor.inputs = tal_arr(ctx, BitcoinOutputId *, anchor.n_inputs); + + for (i = 0; i < anchor.n_inputs; i++) + anchor.inputs[i] = parse_anchor_input(anchor.inputs, argv[i+4]); + + /* Get first revocation hash. */ + shachain_from_seed(&seed, 0, &revocation_hash); + + /* Make simple output script to pay to my pubkey. */ + script_to_me = pay_to_pubkey(ctx, &ouraddr); + + pkt = openchannel_pkt(ctx, weak_random64(), &revocation_hash, + tal_count(script_to_me), script_to_me, + commit_tx_fee, locktime_seconds, &anchor); + + if (!write_all(STDOUT_FILENO, pkt, + sizeof(pkt->len) + le32_to_cpu(pkt->len))) + err(1, "Writing out packet"); + + tal_free(ctx); + return 0; +} diff --git a/pd_channel.h b/pd_channel.h new file mode 100644 index 000000000..4926eb8e6 --- /dev/null +++ b/pd_channel.h @@ -0,0 +1,20 @@ +/* + * Poon-Dryja Generalized Channel Implementation. + * + * It's fairly symmetrical, but for clarity the api divides into + * client and server. + */ + +/* Construct the inputs they want to use. */ +struct input *pd_ask_anchor_inputs(void); + + + + +/* Client creates an unsigned transaction using their own funds: */ +struct tx *client_anchor_tx(struct input *spend, u64 amount); + +/* Then, from that we create an updatable commitment transaction, + * with two outputs (one is zero val). */ + + diff --git a/pkt.c b/pkt.c new file mode 100644 index 000000000..084b850ca --- /dev/null +++ b/pkt.c @@ -0,0 +1,55 @@ +#include +#include "pkt.h" + +static struct pkt *to_pkt(const tal_t *ctx, Pkt__PktCase type, void *msg) +{ + struct pkt *ret; + size_t len; + Pkt p = PKT__INIT; + + p.pkt_case = type; + /* This is a union, so doesn't matter which we assign. */ + p.error = msg; + + len = pkt__get_packed_size(&p); + ret = (struct pkt *)tal_arr(ctx, u8, sizeof(ret->len) + len); + ret->len = cpu_to_le32(len); + pkt__pack(&p, ret->data); + return ret; +} + +Sha256Hash *proto_sha256_hash(const tal_t *ctx, const struct sha256 *hash) +{ + Sha256Hash *h = tal(ctx, Sha256Hash); + sha256_hash__init(h); + + /* Kill me now... */ + memcpy(&h->a, hash->u.u8, 8); + memcpy(&h->b, hash->u.u8 + 8, 8); + memcpy(&h->c, hash->u.u8 + 16, 8); + memcpy(&h->d, hash->u.u8 + 24, 8); + return h; +} + +struct pkt *openchannel_pkt(const tal_t *ctx, + u64 seed, + const struct sha256 *revocation_hash, + size_t script_len, + const void *script, + u64 commitment_fee, + u32 rel_locktime_seconds, + Anchor *anchor) +{ + OpenChannel o = OPEN_CHANNEL__INIT; + + o.seed = seed; + o.revocation_hash = proto_sha256_hash(ctx, revocation_hash); + o.script_to_me.len = script_len; + o.script_to_me.data = (void *)script; + o.commitment_fee = commitment_fee; + o.anchor = anchor; + o.locktime_case = OPEN_CHANNEL__LOCKTIME_LOCKTIME_SECONDS; + o.locktime_seconds = rel_locktime_seconds; + + return to_pkt(ctx, PKT__PKT_OPEN, &o); +} diff --git a/pkt.h b/pkt.h new file mode 100644 index 000000000..84aded907 --- /dev/null +++ b/pkt.h @@ -0,0 +1,44 @@ +#ifndef LIGHTNING_PKT_H +#define LIGHTNING_PKT_H +/* Simple (non-threadsafe!) wrapper for protobufs. + * + * This could be a simple set of macros, if the protobuf-c people hadn't + * insisted on "prettifing" the names they generate into CamelCase. + */ +#include "lightning.pb-c.h" +#include +#include +#include + +/* A packet, ready to be de-protobuf'ed. */ +struct pkt { + le32 len; + u8 data[]; +}; + +struct sha256; + +/** + * tal_openchannel - create an openchannel message + * @ctx: tal context to allocate off. + * @seed: psuedo-random seed to shuffle inputs. + * @revocation_hash: first hash value generated from seed. + * @script_len, @script: the script which pays to us. + * @commitment_fee: the fee to use for commitment tx. + * @rel_locktime_seconds: relative seconds for commitment locktime. + * @anchor: the anchor transaction details. + */ +struct pkt *openchannel_pkt(const tal_t *ctx, + u64 seed, + const struct sha256 *revocation_hash, + size_t script_len, + const void *script, + u64 commitment_fee, + u32 rel_locktime_seconds, + Anchor *anchor); + + +/* Useful helper for allocating & populating a protobuf Sha256Hash */ +Sha256Hash *proto_sha256_hash(const tal_t *ctx, const struct sha256 *hash); + +#endif /* LIGHTNING_PKT_H */ diff --git a/shadouble.c b/shadouble.c new file mode 100644 index 000000000..8135430b5 --- /dev/null +++ b/shadouble.c @@ -0,0 +1,13 @@ +#include "shadouble.h" + +void sha256_double(struct sha256_double *shadouble, const void *p, size_t len) +{ + sha256(&shadouble->sha, (unsigned char *)p, len); + sha256(&shadouble->sha, &shadouble->sha, 1); +} + +void sha256_double_done(struct sha256_ctx *sha256, struct sha256_double *res) +{ + sha256_done(sha256, &res->sha); + sha256(&res->sha, &res->sha, 1); +} diff --git a/shadouble.h b/shadouble.h new file mode 100644 index 000000000..f19dbea8b --- /dev/null +++ b/shadouble.h @@ -0,0 +1,14 @@ +#ifndef LIGHTNING_SHADOUBLE_H +#define LIGHTNING_SHADOUBLE_H +#include "config.h" +#include + +/* To explicitly distinguish between single sha and bitcoin's standard double */ +struct sha256_double { + struct sha256 sha; +}; + +void sha256_double(struct sha256_double *shadouble, const void *p, size_t len); + +void sha256_double_done(struct sha256_ctx *sha256, struct sha256_double *res); +#endif /* PETTYCOIN_SHADOUBLE_H */