Browse Source
Since we only care about the latest commits, we can simply associate a state with each HTLC, rather than using queues of HTLCs associated with each commitment transaction. This works far better in the context of a database. Signed-off-by: Rusty Russell <rusty@rustcorp.com.au>ppa-0.6.1
7 changed files with 303 additions and 14 deletions
@ -0,0 +1,159 @@ |
|||||
|
#include "htlc.h" |
||||
|
#include "log.h" |
||||
|
#include "peer.h" |
||||
|
#include "gen_htlc_state_names.h" |
||||
|
#include <ccan/array_size/array_size.h> |
||||
|
#include <inttypes.h> |
||||
|
|
||||
|
const char *htlc_state_name(enum htlc_state s) |
||||
|
{ |
||||
|
size_t i; |
||||
|
|
||||
|
for (i = 0; enum_htlc_state_names[i].name; i++) |
||||
|
if (enum_htlc_state_names[i].v == s) |
||||
|
return enum_htlc_state_names[i].name; |
||||
|
return "unknown"; |
||||
|
} |
||||
|
|
||||
|
/* This is the flags for each state. */ |
||||
|
static const int per_state_bits[] = { |
||||
|
[SENT_ADD_HTLC] = HTLC_ADDING + HTLC_LOCAL_F_OWNER |
||||
|
+ HTLC_REMOTE_F_PENDING, |
||||
|
|
||||
|
[SENT_ADD_COMMIT] = HTLC_ADDING + HTLC_LOCAL_F_OWNER |
||||
|
+ HTLC_REMOTE_F_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[RCVD_ADD_REVOCATION] = HTLC_ADDING + HTLC_LOCAL_F_OWNER |
||||
|
+ HTLC_REMOTE_F_COMMITTED |
||||
|
+ HTLC_REMOTE_F_REVOKED |
||||
|
+ HTLC_LOCAL_F_PENDING |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[RCVD_ADD_ACK_COMMIT] = HTLC_ADDING + HTLC_LOCAL_F_OWNER |
||||
|
+ HTLC_REMOTE_F_COMMITTED |
||||
|
+ HTLC_REMOTE_F_REVOKED |
||||
|
+ HTLC_LOCAL_F_COMMITTED |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[SENT_ADD_ACK_REVOCATION] = HTLC_LOCAL_F_OWNER |
||||
|
+ HTLC_REMOTE_F_COMMITTED |
||||
|
+ HTLC_REMOTE_F_REVOKED |
||||
|
+ HTLC_LOCAL_F_COMMITTED |
||||
|
+ HTLC_LOCAL_F_REVOKED |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[RCVD_REMOVE_HTLC] = HTLC_REMOVING + HTLC_LOCAL_F_OWNER |
||||
|
+ HTLC_LOCAL_F_PENDING + HTLC_LOCAL_F_COMMITTED |
||||
|
+ HTLC_REMOTE_F_COMMITTED |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[RCVD_REMOVE_COMMIT] = HTLC_REMOVING + HTLC_LOCAL_F_OWNER |
||||
|
+ HTLC_REMOTE_F_COMMITTED |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[SENT_REMOVE_REVOCATION] = HTLC_REMOVING + HTLC_LOCAL_F_OWNER |
||||
|
+ HTLC_REMOTE_F_COMMITTED |
||||
|
+ HTLC_LOCAL_F_REVOKED |
||||
|
+ HTLC_REMOTE_F_PENDING |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[SENT_REMOVE_ACK_COMMIT] = HTLC_REMOVING + HTLC_LOCAL_F_OWNER |
||||
|
+ HTLC_LOCAL_F_REVOKED |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[RCVD_REMOVE_ACK_REVOCATION] = HTLC_LOCAL_F_OWNER |
||||
|
+ HTLC_LOCAL_F_REVOKED |
||||
|
+ HTLC_REMOTE_F_REVOKED |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[RCVD_ADD_HTLC] = HTLC_ADDING + HTLC_REMOTE_F_OWNER |
||||
|
+ HTLC_LOCAL_F_PENDING, |
||||
|
|
||||
|
[RCVD_ADD_COMMIT] = HTLC_ADDING + HTLC_REMOTE_F_OWNER |
||||
|
+ HTLC_LOCAL_F_COMMITTED |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED, |
||||
|
|
||||
|
[SENT_ADD_REVOCATION] = HTLC_ADDING + HTLC_REMOTE_F_OWNER |
||||
|
+ HTLC_LOCAL_F_COMMITTED |
||||
|
+ HTLC_LOCAL_F_REVOKED |
||||
|
+ HTLC_REMOTE_F_PENDING |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED, |
||||
|
|
||||
|
[SENT_ADD_ACK_COMMIT] = HTLC_ADDING + HTLC_REMOTE_F_OWNER |
||||
|
+ HTLC_LOCAL_F_COMMITTED |
||||
|
+ HTLC_LOCAL_F_REVOKED |
||||
|
+ HTLC_REMOTE_F_COMMITTED |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[RCVD_ADD_ACK_REVOCATION] = HTLC_REMOTE_F_OWNER |
||||
|
+ HTLC_LOCAL_F_COMMITTED |
||||
|
+ HTLC_LOCAL_F_REVOKED |
||||
|
+ HTLC_REMOTE_F_COMMITTED |
||||
|
+ HTLC_REMOTE_F_REVOKED |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[SENT_REMOVE_HTLC] = HTLC_REMOVING + HTLC_REMOTE_F_OWNER |
||||
|
+ HTLC_REMOTE_F_PENDING |
||||
|
+ HTLC_LOCAL_F_COMMITTED |
||||
|
+ HTLC_REMOTE_F_COMMITTED |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[SENT_REMOVE_COMMIT] = HTLC_REMOVING + HTLC_REMOTE_F_OWNER |
||||
|
+ HTLC_LOCAL_F_COMMITTED |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[RCVD_REMOVE_REVOCATION] = HTLC_REMOVING + HTLC_REMOTE_F_OWNER |
||||
|
+ HTLC_LOCAL_F_COMMITTED |
||||
|
+ HTLC_REMOTE_F_REVOKED |
||||
|
+ HTLC_LOCAL_F_PENDING |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[RCVD_REMOVE_ACK_COMMIT] = HTLC_REMOVING + HTLC_REMOTE_F_OWNER |
||||
|
+ HTLC_REMOTE_F_REVOKED |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED, |
||||
|
|
||||
|
[SENT_REMOVE_ACK_REVOCATION] = HTLC_REMOTE_F_OWNER |
||||
|
+ HTLC_REMOTE_F_REVOKED |
||||
|
+ HTLC_LOCAL_F_REVOKED |
||||
|
+ HTLC_LOCAL_F_WAS_COMMITTED |
||||
|
+ HTLC_REMOTE_F_WAS_COMMITTED |
||||
|
}; |
||||
|
|
||||
|
int htlc_state_flags(enum htlc_state state) |
||||
|
{ |
||||
|
assert(state < ARRAY_SIZE(per_state_bits)); |
||||
|
assert(per_state_bits[state]); |
||||
|
return per_state_bits[state]; |
||||
|
} |
||||
|
|
||||
|
void htlc_changestate(struct htlc *h, |
||||
|
enum htlc_state oldstate, |
||||
|
enum htlc_state newstate) |
||||
|
{ |
||||
|
log_debug(h->peer->log, "htlc %"PRIu64": %s->%s", h->id, |
||||
|
htlc_state_name(h->state), htlc_state_name(newstate)); |
||||
|
assert(h->state == oldstate); |
||||
|
|
||||
|
/* You can only go to consecutive states. */ |
||||
|
assert(newstate == h->state + 1); |
||||
|
|
||||
|
/* You can't change sides. */ |
||||
|
assert((htlc_state_flags(h->state)&(HTLC_LOCAL_F_OWNER|HTLC_REMOTE_F_OWNER)) |
||||
|
== (htlc_state_flags(newstate)&(HTLC_LOCAL_F_OWNER|HTLC_REMOTE_F_OWNER))); |
||||
|
|
||||
|
h->state = newstate; |
||||
|
} |
@ -0,0 +1,34 @@ |
|||||
|
#ifndef LIGHTNING_DAEMON_HTLC_STATE_H |
||||
|
#define LIGHTNING_DAEMON_HTLC_STATE_H |
||||
|
#include "config.h" |
||||
|
|
||||
|
enum htlc_state { |
||||
|
/* When we add a new htlc, it goes in this order. */ |
||||
|
SENT_ADD_HTLC, |
||||
|
SENT_ADD_COMMIT, |
||||
|
RCVD_ADD_REVOCATION, |
||||
|
RCVD_ADD_ACK_COMMIT, |
||||
|
SENT_ADD_ACK_REVOCATION, |
||||
|
|
||||
|
/* When they remove an htlc, it goes from SENT_ADD_ACK_REVOCATION: */ |
||||
|
RCVD_REMOVE_HTLC, |
||||
|
RCVD_REMOVE_COMMIT, |
||||
|
SENT_REMOVE_REVOCATION, |
||||
|
SENT_REMOVE_ACK_COMMIT, |
||||
|
RCVD_REMOVE_ACK_REVOCATION, |
||||
|
|
||||
|
/* When they add a new htlc, it goes in this order. */ |
||||
|
RCVD_ADD_HTLC, |
||||
|
RCVD_ADD_COMMIT, |
||||
|
SENT_ADD_REVOCATION, |
||||
|
SENT_ADD_ACK_COMMIT, |
||||
|
RCVD_ADD_ACK_REVOCATION, |
||||
|
|
||||
|
/* When we remove an htlc, it goes from RCVD_ADD_ACK_REVOCATION: */ |
||||
|
SENT_REMOVE_HTLC, |
||||
|
SENT_REMOVE_COMMIT, |
||||
|
RCVD_REMOVE_REVOCATION, |
||||
|
RCVD_REMOVE_ACK_COMMIT, |
||||
|
SENT_REMOVE_ACK_REVOCATION |
||||
|
}; |
||||
|
#endif /* LIGHTNING_DAEMON_HTLC_STATE_H */ |
Loading…
Reference in new issue