libhsmd: Add status functions to report to whoever is listening

These are currently just shims that replicate the old behavior, but
when compiling as a library we can relink the status_* functions to
something that makes sense in the context of the user, and not assume
we're running as a subdaemon.
This commit is contained in:
Christian Decker 2021-04-20 22:37:07 +02:00 committed by Rusty Russell
parent b5a2ddd384
commit ac836bbd1b
3 changed files with 79 additions and 0 deletions

View File

@ -34,6 +34,8 @@
#include <common/memleak.h>
#include <common/node_id.h>
#include <common/status.h>
#include <common/status_wire.h>
#include <common/status_wiregen.h>
#include <common/subdaemon.h>
#include <common/type_to_string.h>
#include <common/utils.h>
@ -1925,6 +1927,44 @@ static struct io_plan *handle_memleak(struct io_conn *conn,
}
#endif /* DEVELOPER */
u8 *hsmd_status_bad_request(struct hsmd_client *client, const u8 *msg, const char *error)
{
/* Extract the pointer to the hsmd representation of the
* client which has access to the underlying connection. */
struct client *c = (struct client*)client->extra;
bad_req_fmt(c->conn, c, msg, "%s", error);
/* We often use `return hsmd_status_bad_request` to drop out, and NULL
* means we encountered an error. */
return NULL;
}
void hsmd_status_fmt(enum log_level level, const struct node_id *peer,
const char *fmt, ...)
{
va_list ap;
va_start(ap, fmt);
status_vfmt(level, peer, fmt, ap);
va_end(ap);
}
void hsmd_status_failed(enum status_failreason reason, const char *fmt, ...)
{
va_list ap;
char *str;
va_start(ap, fmt);
str = tal_vfmt(NULL, fmt, ap);
va_end(ap);
/* Give a nice backtrace when this happens! */
if (reason == STATUS_FAIL_INTERNAL_ERROR)
send_backtrace(str);
status_send_fatal(take(towire_status_fail(NULL, reason, str)));
}
/*~ This is the core of the HSM daemon: handling requests. */
static struct io_plan *handle_client(struct io_conn *conn, struct client *c)
{

View File

@ -120,6 +120,28 @@ bool check_client_capabilities(struct hsmd_client *client, enum hsmd_wire t)
return false;
}
/*~ ccan/compiler.h defines PRINTF_FMT as the gcc compiler hint so it will
* check that fmt and other trailing arguments really are the correct type.
*/
/* This function is used to format an error message before passing it
* to the library user specified hsmd_status_bad_request */
/* Temporarily pre-declare until we use the function, then we can make
* it static again. */
u8 *hsmd_status_bad_request_fmt(struct hsmd_client *client, const u8 *msg,
const char *fmt, ...) PRINTF_FMT(3, 4);
u8 *hsmd_status_bad_request_fmt(struct hsmd_client *client, const u8 *msg,
const char *fmt, ...)
{
va_list ap;
char *str;
va_start(ap, fmt);
str = tal_fmt(tmpctx, fmt, ap);
va_end(ap);
return hsmd_status_bad_request(client, msg, str);
}
u8 *hsmd_handle_client_message(const tal_t *ctx, struct hsmd_client *client,
const u8 *msg)
{

View File

@ -57,6 +57,23 @@ struct hsmd_client *hsmd_client_new_peer(const tal_t *ctx, u64 capabilities,
u8 *hsmd_handle_client_message(const tal_t *ctx, struct hsmd_client *client,
const u8 *msg);
/* Functions to report debugging information or errors. These must be
* implemented by the user of the library. */
u8 *hsmd_status_bad_request(struct hsmd_client *client, const u8 *msg,
const char *error);
/* Send a printf-style debugging trace. */
void hsmd_status_fmt(enum log_level level,
const struct node_id *peer,
const char *fmt, ...)
PRINTF_FMT(3,4);
#define hsmd_status_debug(...) \
hsmd_status_fmt(LOG_DBG, NULL, __VA_ARGS__)
void hsmd_status_failed(enum status_failreason code,
const char *fmt, ...) PRINTF_FMT(2,3);
/* The following declarations are here only temporarily while we migrate logic from hsmd.c to libhsmd.c */
/*~ Nobody will ever find it here! hsm_secret is our root secret, the bip32