|
86 | 86 | #define KIND_DESCRIPTOR_COMBO (0x00030000 | KIND_DESCRIPTOR) |
87 | 87 | #define KIND_DESCRIPTOR_ADDR (0x00040000 | KIND_DESCRIPTOR) |
88 | 88 | #define KIND_DESCRIPTOR_RAW (0x00050000 | KIND_DESCRIPTOR) |
| 89 | +#define KIND_DESCRIPTOR_RAW_TR (0x00100000 | KIND_DESCRIPTOR) |
89 | 90 |
|
90 | 91 | /* miniscript */ |
91 | 92 | #define KIND_MINISCRIPT_PK (0x00000100 | KIND_MINISCRIPT) |
@@ -2028,41 +2029,50 @@ static int analyze_address(ms_ctx *ctx, const char *str, size_t str_len, |
2028 | 2029 | static int analyze_pubkey_hex(ms_ctx *ctx, ms_node *node, |
2029 | 2030 | uint32_t flags, bool *is_hex) |
2030 | 2031 | { |
2031 | | - unsigned char pubkey[EC_PUBLIC_KEY_UNCOMPRESSED_LEN + 1]; |
2032 | | - size_t offset = flags & WALLY_MINISCRIPT_TAPSCRIPT ? 1 : 0; |
2033 | | - size_t written; |
2034 | | - |
2035 | | - *is_hex = false; |
2036 | | - if (offset) { |
2037 | | - if (node->data_len != EC_XONLY_PUBLIC_KEY_LEN * 2) |
| 2032 | + unsigned char pubkey[EC_PUBLIC_KEY_UNCOMPRESSED_LEN]; |
| 2033 | + size_t pubkey_len; |
| 2034 | + bool allow_xonly, make_xonly = false; |
| 2035 | + |
| 2036 | + *is_hex = wally_hex_n_to_bytes(node->data, node->data_len, |
| 2037 | + pubkey, sizeof(pubkey), &pubkey_len) == WALLY_OK; |
| 2038 | + if (!is_hex || pubkey_len > sizeof(pubkey)) |
| 2039 | + return WALLY_OK; /* Not hex, or too long */ |
| 2040 | + |
| 2041 | + if (wally_ec_public_key_verify(pubkey, pubkey_len) != WALLY_OK && |
| 2042 | + wally_ec_xonly_public_key_verify(pubkey, pubkey_len) != WALLY_OK) |
| 2043 | + return WALLY_OK; /* Not a valid pubkey */ |
| 2044 | + |
| 2045 | + make_xonly = node->parent && (node->parent->kind == KIND_DESCRIPTOR_RAW_TR); |
| 2046 | + allow_xonly = make_xonly || flags & WALLY_MINISCRIPT_TAPSCRIPT; |
| 2047 | + if (pubkey_len == EC_PUBLIC_KEY_UNCOMPRESSED_LEN && allow_xonly) |
| 2048 | + return WALLY_OK; /* Uncompressed key not allowed here */ |
| 2049 | + if (pubkey_len == EC_XONLY_PUBLIC_KEY_LEN && !allow_xonly) |
| 2050 | + return WALLY_OK; /* X-only not allowed here */ |
| 2051 | + if (pubkey_len != EC_XONLY_PUBLIC_KEY_LEN) { |
| 2052 | + if (flags & WALLY_MINISCRIPT_TAPSCRIPT) |
2038 | 2053 | return WALLY_OK; /* Only X-only pubkeys allowed under tapscript */ |
2039 | | - pubkey[0] = 2; /* Non-X-only pubkey prefix, for validation below */ |
2040 | | - } else { |
2041 | | - if (node->data_len != EC_PUBLIC_KEY_LEN * 2 && |
2042 | | - node->data_len != EC_PUBLIC_KEY_UNCOMPRESSED_LEN * 2) |
2043 | | - return WALLY_OK; /* Unknown public key size */ |
| 2054 | + if (make_xonly) { |
| 2055 | + /* Convert to x-only */ |
| 2056 | + --pubkey_len; |
| 2057 | + memmove(pubkey, pubkey + 1, pubkey_len); |
| 2058 | + } |
2044 | 2059 | } |
2045 | 2060 |
|
2046 | | - if (wally_hex_n_to_bytes(node->data, node->data_len, |
2047 | | - pubkey + offset, sizeof(pubkey) - offset, &written) != WALLY_OK || |
2048 | | - wally_ec_public_key_verify(pubkey, written + offset) != WALLY_OK) |
2049 | | - return WALLY_OK; /* Not hex, or not a pubkey */ |
2050 | | - |
2051 | | - if (!clone_bytes((unsigned char **)&node->data, pubkey + offset, written)) |
| 2061 | + if (!clone_bytes((unsigned char **)&node->data, pubkey, pubkey_len)) |
2052 | 2062 | return WALLY_ENOMEM; |
2053 | | - node->data_len = node->data_len / 2; |
2054 | | - if (node->data_len == EC_PUBLIC_KEY_UNCOMPRESSED_LEN) { |
| 2063 | + node->data_len = pubkey_len; |
| 2064 | + |
| 2065 | + if (pubkey_len == EC_PUBLIC_KEY_UNCOMPRESSED_LEN) { |
2055 | 2066 | node->flags |= WALLY_MS_IS_UNCOMPRESSED; |
2056 | 2067 | ctx->features |= WALLY_MS_IS_UNCOMPRESSED; |
2057 | 2068 | } |
2058 | | - if (node->data_len == EC_XONLY_PUBLIC_KEY_LEN) { |
| 2069 | + if (pubkey_len == EC_XONLY_PUBLIC_KEY_LEN) { |
2059 | 2070 | node->flags |= WALLY_MS_IS_X_ONLY; |
2060 | 2071 | ctx->features |= WALLY_MS_IS_X_ONLY; |
2061 | 2072 | } |
2062 | 2073 | ctx->features |= WALLY_MS_IS_RAW; |
2063 | 2074 | node->kind = KIND_PUBLIC_KEY; |
2064 | 2075 | node->flags |= WALLY_MS_IS_RAW; |
2065 | | - *is_hex = true; |
2066 | 2076 | return ctx_add_key_node(ctx, node); |
2067 | 2077 | } |
2068 | 2078 |
|
|
0 commit comments