Add a POSIX C LDK networking library
[ldk-c-bindings] / lightning-c-bindings / demo.cpp
1 extern "C" {
2 #include <lightning.h>
3
4 #ifdef REAL_NET
5 #include <ldk_net.h>
6 #endif
7 }
8 #include "include/lightningpp.hpp"
9
10 #include <assert.h>
11 #include <stdio.h>
12 #include <sys/socket.h>
13 #include <netinet/in.h>
14 #include <arpa/inet.h>
15 #include <unistd.h>
16
17 #include <atomic>
18 #include <chrono>
19 #include <functional>
20 #include <thread>
21 #include <mutex>
22 #include <vector>
23
24 const uint8_t valid_node_announcement[] = {
25         0x94, 0xe4, 0xf5, 0x61, 0x41, 0x24, 0x7d, 0x90, 0x23, 0xa0, 0xc8, 0x34, 0x8c, 0xc4, 0xca, 0x51,
26         0xd8, 0x17, 0x59, 0xff, 0x7d, 0xac, 0x8c, 0x9b, 0x63, 0x29, 0x1c, 0xe6, 0x12, 0x12, 0x93, 0xbd,
27         0x66, 0x4d, 0x6b, 0x9c, 0xfb, 0x35, 0xda, 0x16, 0x06, 0x3d, 0xf0, 0x8f, 0x8a, 0x39, 0x99, 0xa2,
28         0xf2, 0x5d, 0x12, 0x0f, 0x2b, 0x42, 0x1b, 0x8b, 0x9a, 0xfe, 0x33, 0x0c, 0xeb, 0x33, 0x5e, 0x52,
29         0xee, 0x99, 0xa1, 0x07, 0x06, 0xed, 0xf8, 0x48, 0x7a, 0xc6, 0xe5, 0xf5, 0x5e, 0x01, 0x3a, 0x41,
30         0x2f, 0x18, 0x94, 0x8a, 0x3b, 0x0a, 0x52, 0x3f, 0xbf, 0x61, 0xa9, 0xc5, 0x4f, 0x70, 0xee, 0xb8,
31         0x79, 0x23, 0xbb, 0x1a, 0x44, 0x7d, 0x91, 0xe6, 0x2a, 0xbc, 0xa1, 0x07, 0xbc, 0x65, 0x3b, 0x02,
32         0xd9, 0x1d, 0xb2, 0xf2, 0x3a, 0xcb, 0x75, 0x79, 0xc6, 0x66, 0xd8, 0xc1, 0x71, 0x29, 0xdf, 0x04,
33         0x60, 0xf4, 0xbf, 0x07, 0x7b, 0xb9, 0xc2, 0x11, 0x94, 0x6a, 0x28, 0xc2, 0xdd, 0xd8, 0x7b, 0x44,
34         0x8f, 0x08, 0xe3, 0xc8, 0xd8, 0xf4, 0x81, 0xb0, 0x9f, 0x94, 0xcb, 0xc8, 0xc1, 0x3c, 0xc2, 0x6e,
35         0x31, 0x26, 0xfc, 0x33, 0x16, 0x3b, 0xe0, 0xde, 0xa1, 0x16, 0x21, 0x9f, 0x89, 0xdd, 0x97, 0xa4,
36         0x41, 0xf2, 0x9f, 0x19, 0xb1, 0xae, 0x82, 0xf7, 0x85, 0x9a, 0xb7, 0x8f, 0xb7, 0x52, 0x7a, 0x72,
37         0xf1, 0x5e, 0x89, 0xe1, 0x8a, 0xcd, 0x40, 0xb5, 0x8e, 0xc3, 0xca, 0x42, 0x76, 0xa3, 0x6e, 0x1b,
38         0xf4, 0x87, 0x35, 0x30, 0x58, 0x43, 0x04, 0xd9, 0x2c, 0x50, 0x54, 0x55, 0x47, 0x6f, 0x70, 0x9b,
39         0x42, 0x1f, 0x91, 0xfc, 0xa1, 0xdb, 0x72, 0x53, 0x96, 0xc8, 0xe5, 0xcd, 0x0e, 0xcb, 0xa0, 0xfe,
40         0x6b, 0x08, 0x77, 0x48, 0xb7, 0xad, 0x4a, 0x69, 0x7c, 0xdc, 0xd8, 0x04, 0x28, 0x35, 0x9b, 0x73,
41         0x00, 0x00, 0x43, 0x49, 0x7f, 0xd7, 0xf8, 0x26, 0x95, 0x71, 0x08, 0xf4, 0xa3, 0x0f, 0xd9, 0xce,
42         0xc3, 0xae, 0xba, 0x79, 0x97, 0x20, 0x84, 0xe9, 0x0e, 0xad, 0x01, 0xea, 0x33, 0x09, 0x00, 0x00,
43         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x5b, 0xe5, 0xe9, 0x47, 0x82,
44         0x09, 0x67, 0x4a, 0x96, 0xe6, 0x0f, 0x1f, 0x03, 0x7f, 0x61, 0x76, 0x54, 0x0f, 0xd0, 0x01, 0xfa,
45         0x1d, 0x64, 0x69, 0x47, 0x70, 0xc5, 0x6a, 0x77, 0x09, 0xc4, 0x2c, 0x03, 0x5c, 0x4e, 0x0d, 0xec,
46         0x72, 0x15, 0xe2, 0x68, 0x33, 0x93, 0x87, 0x30, 0xe5, 0xe5, 0x05, 0xaa, 0x62, 0x50, 0x4d, 0xa8,
47         0x5b, 0xa5, 0x71, 0x06, 0xa4, 0x6b, 0x5a, 0x24, 0x04, 0xfc, 0x9d, 0x8e, 0x02, 0xba, 0x72, 0xa6,
48         0xe8, 0xba, 0x53, 0xe8, 0xb9, 0x71, 0xad, 0x0c, 0x98, 0x23, 0x96, 0x8a, 0xef, 0x4d, 0x78, 0xce,
49         0x8a, 0xf2, 0x55, 0xab, 0x43, 0xdf, 0xf8, 0x30, 0x03, 0xc9, 0x02, 0xfb, 0x8d, 0x02, 0x16, 0x34,
50         0x5b, 0xf8, 0x31, 0x16, 0x4a, 0x03, 0x75, 0x8e, 0xae, 0xa5, 0xe8, 0xb6, 0x6f, 0xee, 0x2b, 0xe7,
51         0x71, 0x0b, 0x8f, 0x19, 0x0e, 0xe8, 0x80, 0x24, 0x90, 0x32, 0xa2, 0x9e, 0xd6, 0x6e
52 };
53
54 // A simple block containing only one transaction (which is the channel-open transaction for the
55 // channel we'll create). This was originally created by printing additional data in a simple
56 // rust-lightning unit test.
57 const uint8_t channel_open_block[] = {
58         0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
59         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
60         0x00, 0x00, 0x00, 0x00, 0xa2, 0x47, 0xd2, 0xf8, 0xd4, 0xe0, 0x6a, 0x3f, 0xf9, 0x7a, 0x9a, 0x34,
61         0xbb, 0xa9, 0x96, 0xde, 0x63, 0x84, 0x5a, 0xce, 0xcf, 0x98, 0xb8, 0xbb, 0x75, 0x4c, 0x4f, 0x7d,
62         0xee, 0x4c, 0xa9, 0x5f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
63         0x01, // transaction count
64         0x02, 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
65         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
66         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
67         0x01, 0x40, 0x9c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x22, 0x00, 0x20, 0xd1, 0xd9, 0x13, 0xa9,
68         0x76, 0x09, 0x05, 0xa3, 0x4d, 0x13, 0x5b, 0x69, 0xaa, 0xe7, 0x79, 0x71, 0xb9, 0x75, 0xa1, 0xd0,
69         0x77, 0xcb, 0xa2, 0xf6, 0x6a, 0x25, 0x37, 0x3a, 0xaf, 0xdc, 0x11, 0x09, 0x01, 0x00, 0x00, 0x00,
70         0x00, 0x00
71 };
72
73 // The first transaction in the block is header (80 bytes) + transaction count (1 byte) into the block data.
74 const uint8_t channel_open_txid[] = {
75         0x02, 0xe0, 0x50, 0x05, 0x33, 0xd3, 0x29, 0x66, 0x0c, 0xb2, 0xcb, 0x1e, 0x7a, 0x4a, 0xc7, 0xc7,
76         0x8b, 0x02, 0x46, 0x7e, 0x30, 0x2c, 0xe6, 0x19, 0xce, 0x43, 0x3e, 0xdf, 0x43, 0x65, 0xae, 0xf9,
77 };
78
79 // Two blocks built on top of channel_open_block:
80 const uint8_t block_1[81] = {
81         0x01, 0x00, 0x00, 0x00, 0x0c, 0x7a, 0xc2, 0xdc, 0x08, 0xaf, 0x40, 0x7d, 0x58, 0x81, 0x9b, 0x44,
82         0xc7, 0xe0, 0x0f, 0x78, 0xc0, 0xd1, 0x01, 0xa2, 0x03, 0x16, 0x4a, 0x8d, 0x92, 0x66, 0x4e, 0xaf,
83         0x7f, 0xfc, 0x6e, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
84         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
85         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
86         0x00, // transaction count
87 };
88 const uint8_t block_2[81] = {
89         0x01, 0x00, 0x00, 0x00, 0x36, 0x0b, 0xf5, 0x46, 0x4a, 0xc7, 0x26, 0x4c, 0x4b, 0x36, 0xa6, 0x9d,
90         0x0e, 0xf0, 0x14, 0xfb, 0x8a, 0xcb, 0x20, 0x84, 0x18, 0xf3, 0xaa, 0x77, 0x32, 0x2d, 0xf7, 0x48,
91         0x62, 0x92, 0xb1, 0xb4, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
92         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
93         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
94         0x00, // transaction count
95 };
96
97 const LDKThirtyTwoBytes genesis_hash = { // We don't care particularly if this is "right"
98         .data = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1 }
99 };
100
101 void print_log(const void *this_arg, const char *record) {
102         printf("%p - %s\n", this_arg, record);
103 }
104
105 uint32_t get_fee(const void *this_arg, LDKConfirmationTarget target) {
106         if (target == LDKConfirmationTarget_Background) {
107                 return 253;
108         } else {
109                 return 507;
110         }
111         // Note that we don't call _free() on target, but that's OK, its unitary
112 }
113 // We use the same fee estimator globally:
114 const LDKFeeEstimator fee_est {
115         .this_arg = NULL,
116         .get_est_sat_per_1000_weight = get_fee,
117         .free = NULL,
118 };
119
120 static std::atomic_int num_txs_broadcasted(0);
121 void broadcast_tx(const void *this_arg, LDKTransaction tx) {
122         num_txs_broadcasted += 1;
123         //TODO
124         Transaction_free(tx);
125 }
126
127 struct NodeMonitors {
128         std::mutex mut;
129         std::vector<std::pair<LDK::OutPoint, LDK::ChannelMonitor>> mons;
130         LDKLogger* logger;
131
132         void ConnectBlock(const uint8_t (*header)[80], uint32_t height, LDKCVec_C2Tuple_usizeTransactionZZ tx_data, LDKBroadcasterInterface broadcast, LDKFeeEstimator fee_est) {
133                 std::unique_lock<std::mutex> l(mut);
134                 for (auto& mon : mons) {
135                         LDK::CVec_TransactionOutputsZ res = ChannelMonitor_block_connected(&mon.second, header, tx_data, height, broadcast, fee_est, *logger);
136                 }
137         }
138 };
139
140 LDKCResult_NoneChannelMonitorUpdateErrZ add_channel_monitor(const void *this_arg, LDKOutPoint funding_txo_arg, LDKChannelMonitor monitor_arg) {
141         // First bind the args to C++ objects so they auto-free
142         LDK::ChannelMonitor mon(std::move(monitor_arg));
143         LDK::OutPoint funding_txo(std::move(funding_txo_arg));
144
145         NodeMonitors* arg = (NodeMonitors*) this_arg;
146         std::unique_lock<std::mutex> l(arg->mut);
147
148         arg->mons.push_back(std::make_pair(std::move(funding_txo), std::move(mon)));
149         return CResult_NoneChannelMonitorUpdateErrZ_ok();
150 }
151 static std::atomic_int mons_updated(0);
152 LDKCResult_NoneChannelMonitorUpdateErrZ update_channel_monitor(const void *this_arg, LDKOutPoint funding_txo_arg, LDKChannelMonitorUpdate monitor_arg) {
153         // First bind the args to C++ objects so they auto-free
154         LDK::ChannelMonitorUpdate update(std::move(monitor_arg));
155         LDK::OutPoint funding_txo(std::move(funding_txo_arg));
156
157         NodeMonitors* arg = (NodeMonitors*) this_arg;
158         std::unique_lock<std::mutex> l(arg->mut);
159
160         bool updated = false;
161         for (auto& mon : arg->mons) {
162                 if (OutPoint_get_index(&mon.first) == OutPoint_get_index(&funding_txo) &&
163                                 !memcmp(OutPoint_get_txid(&mon.first), OutPoint_get_txid(&funding_txo), 32)) {
164                         updated = true;
165                         LDKBroadcasterInterface broadcaster = {
166                                 .broadcast_transaction = broadcast_tx,
167                         };
168                         LDK::CResult_NoneMonitorUpdateErrorZ res = ChannelMonitor_update_monitor(&mon.second, &update, &broadcaster, &fee_est, arg->logger);
169                         assert(res->result_ok);
170                 }
171         }
172         assert(updated);
173
174         mons_updated += 1;
175         return CResult_NoneChannelMonitorUpdateErrZ_ok();
176 }
177 LDKCVec_MonitorEventZ monitors_pending_monitor_events(const void *this_arg) {
178         NodeMonitors* arg = (NodeMonitors*) this_arg;
179         std::unique_lock<std::mutex> l(arg->mut);
180
181         if (arg->mons.size() == 0) {
182                 return LDKCVec_MonitorEventZ {
183                         .data = NULL,
184                         .datalen = 0,
185                 };
186         } else {
187                 // We only ever actually have one channel per node, plus concatenating two
188                 // Rust Vecs to each other from C++ will require a bit of effort.
189                 assert(arg->mons.size() == 1);
190                 return ChannelMonitor_get_and_clear_pending_monitor_events(&arg->mons[0].second);
191         }
192 }
193
194 struct EventQueue {
195         std::vector<LDK::Event> events;
196 };
197 void handle_event(const void *this_arg, LDKEvent event) {
198         EventQueue* arg = (EventQueue*) this_arg;
199         arg->events.push_back(std::move(event));
200 }
201
202 #ifdef REAL_NET
203 class PeersConnection {
204         void* node1_handler;
205         void* node2_handler;
206
207 public:
208         PeersConnection(LDK::ChannelManager& cm1, LDK::ChannelManager& cm2, LDK::PeerManager& net1, LDK::PeerManager& net2) {
209                 node1_handler = init_socket_handling(&net1);
210                 node2_handler = init_socket_handling(&net2);
211
212                 struct sockaddr_in listen_addr;
213                 listen_addr.sin_family = AF_INET;
214                 listen_addr.sin_addr.s_addr = htonl((127 << 8*3) | 1);
215                 listen_addr.sin_port = htons(10042);
216                 assert(!socket_bind(node2_handler, (sockaddr*)&listen_addr, sizeof(listen_addr)));
217
218                 assert(!socket_connect(node1_handler, ChannelManager_get_our_node_id(&cm2), (sockaddr*)&listen_addr, sizeof(listen_addr)));
219
220                 while (true) {
221                         // Wait for the initial handshakes to complete...
222                         LDK::CVec_PublicKeyZ peers_1 = PeerManager_get_peer_node_ids(&net1);
223                         LDK::CVec_PublicKeyZ peers_2 = PeerManager_get_peer_node_ids(&net2);
224                         if (peers_1->datalen == 1 && peers_2->datalen == 1) { break; }
225                         std::this_thread::yield();
226                 }
227
228                 // Connect twice, which should auto-disconnect, and is a good test of our disconnect pipeline
229                 assert(!socket_connect(node1_handler, ChannelManager_get_our_node_id(&cm2), (sockaddr*)&listen_addr, sizeof(listen_addr)));
230                 assert(!socket_connect(node1_handler, ChannelManager_get_our_node_id(&cm2), (sockaddr*)&listen_addr, sizeof(listen_addr)));
231
232                 // Then disconnect the "main" connection, while another connection is being made.
233                 PeerManager_disconnect_by_node_id(&net1, ChannelManager_get_our_node_id(&cm2), false);
234                 assert(!socket_connect(node1_handler, ChannelManager_get_our_node_id(&cm2), (sockaddr*)&listen_addr, sizeof(listen_addr)));
235
236                 // Wait for all our sockets to disconnect (making sure we disconnect any new connections)...
237                 while (true) {
238                         PeerManager_disconnect_by_node_id(&net1, ChannelManager_get_our_node_id(&cm2), false);
239                         // Wait for the peers to disconnect...
240                         LDK::CVec_PublicKeyZ peers_1 = PeerManager_get_peer_node_ids(&net1);
241                         LDK::CVec_PublicKeyZ peers_2 = PeerManager_get_peer_node_ids(&net2);
242                         if (peers_1->datalen == 0 && peers_2->datalen == 0) { break; }
243                         std::this_thread::yield();
244                 }
245
246                 // Finally make an actual connection and keep it this time
247                 assert(!socket_connect(node1_handler, ChannelManager_get_our_node_id(&cm2), (sockaddr*)&listen_addr, sizeof(listen_addr)));
248
249                 while (true) {
250                         // Wait for the initial handshakes to complete...
251                         LDK::CVec_PublicKeyZ peers_1 = PeerManager_get_peer_node_ids(&net1);
252                         LDK::CVec_PublicKeyZ peers_2 = PeerManager_get_peer_node_ids(&net2);
253                         if (peers_1->datalen == 1 && peers_2->datalen == 1) { break; }
254                         std::this_thread::yield();
255                 }
256         }
257         void stop() {
258                 interrupt_socket_handling(node1_handler);
259                 interrupt_socket_handling(node2_handler);
260         }
261 };
262
263 #else // REAL_NET
264
265 uintptr_t sock_send_data(void *this_arg, LDKu8slice data, bool resume_read) {
266         return write((int)((long)this_arg), data.data, data.datalen);
267 }
268 void sock_disconnect_socket(void *this_arg) {
269         close((int)((long)this_arg));
270 }
271 bool sock_eq(const void *this_arg, const LDKSocketDescriptor *other_arg) {
272         return this_arg == other_arg->this_arg;
273 }
274 uint64_t sock_hash(const void *this_arg) {
275         return (uint64_t)this_arg;
276 }
277 void sock_read_data_thread(int rdfd, LDKSocketDescriptor *peer_descriptor, LDKPeerManager *pm) {
278         unsigned char buf[1024];
279         LDKu8slice data;
280         data.data = buf;
281         ssize_t readlen = 0;
282         while ((readlen = read(rdfd, buf, 1024)) > 0) {
283                 data.datalen = readlen;
284                 LDK::CResult_boolPeerHandleErrorZ res = PeerManager_read_event(&*pm, peer_descriptor, data);
285                 if (!res->result_ok) {
286                         peer_descriptor->disconnect_socket(peer_descriptor->this_arg);
287                         return;
288                 }
289                 PeerManager_process_events(pm);
290         }
291         PeerManager_socket_disconnected(&*pm, peer_descriptor);
292 }
293
294 class PeersConnection {
295         int pipefds_1_to_2[2];
296         int pipefds_2_to_1[2];
297         std::thread t1, t2;
298         LDKSocketDescriptor sock1, sock2;
299
300 public:
301         PeersConnection(LDK::ChannelManager& cm1, LDK::ChannelManager& cm2, LDK::PeerManager& net1, LDK::PeerManager& net2) {
302                 assert(!pipe(pipefds_1_to_2));
303                 assert(!pipe(pipefds_2_to_1));
304
305                 sock1 = LDKSocketDescriptor {
306                         .this_arg = (void*)(long)pipefds_1_to_2[1],
307                         .send_data = sock_send_data,
308                         .disconnect_socket = sock_disconnect_socket,
309                         .eq = sock_eq,
310                         .hash = sock_hash,
311                         .clone = NULL,
312                         .free = NULL,
313                 };
314
315                 sock2 = LDKSocketDescriptor {
316                         .this_arg = (void*)(long)pipefds_2_to_1[1],
317                         .send_data = sock_send_data,
318                         .disconnect_socket = sock_disconnect_socket,
319                         .eq = sock_eq,
320                         .hash = sock_hash,
321                         .clone = NULL,
322                         .free = NULL,
323                 };
324
325                 t1 = std::thread(&sock_read_data_thread, pipefds_2_to_1[0], &sock1, &net1);
326                 t2 = std::thread(&sock_read_data_thread, pipefds_1_to_2[0], &sock2, &net2);
327
328                 // Note that we have to bind the result to a C++ class to make sure it gets free'd
329                 LDK::CResult_CVec_u8ZPeerHandleErrorZ con_res = PeerManager_new_outbound_connection(&net1, ChannelManager_get_our_node_id(&cm2), sock1);
330                 assert(con_res->result_ok);
331                 LDK::CResult_NonePeerHandleErrorZ con_res2 = PeerManager_new_inbound_connection(&net2, sock2);
332                 assert(con_res2->result_ok);
333
334                 auto writelen = write(pipefds_1_to_2[1], con_res->contents.result->data, con_res->contents.result->datalen);
335                 assert(writelen > 0 && uint64_t(writelen) == con_res->contents.result->datalen);
336
337                 while (true) {
338                         // Wait for the initial handshakes to complete...
339                         LDK::CVec_PublicKeyZ peers_1 = PeerManager_get_peer_node_ids(&net1);
340                         LDK::CVec_PublicKeyZ peers_2 = PeerManager_get_peer_node_ids(&net2);
341                         if (peers_1->datalen == 1 && peers_2->datalen ==1) { break; }
342                         std::this_thread::yield();
343                 }
344         }
345
346         void stop() {
347                 close(pipefds_1_to_2[0]);
348                 close(pipefds_2_to_1[0]);
349                 close(pipefds_1_to_2[1]);
350                 close(pipefds_2_to_1[1]);
351                 t1.join();
352                 t2.join();
353         }
354 };
355 #endif // !REAL_NET
356
357 int main() {
358         uint8_t channel_open_header[80];
359         uint8_t header_1[80];
360         uint8_t header_2[80];
361         memcpy(channel_open_header, channel_open_block, 80);
362         memcpy(header_1, block_1, 80);
363         memcpy(header_2, block_2, 80);
364
365         LDKPublicKey null_pk;
366         memset(&null_pk, 0, sizeof(null_pk));
367
368         LDKThirtyTwoBytes random_bytes;
369         LDKThirtyTwoBytes chain_tip;
370         memset(&chain_tip, 0, sizeof(chain_tip)); // channel_open_header's prev_blockhash is all-0s
371
372         LDKNetwork network = LDKNetwork_Testnet;
373
374         // Trait implementations:
375         LDKBroadcasterInterface broadcast {
376                 .this_arg = NULL,
377                 .broadcast_transaction = broadcast_tx,
378                 .free = NULL,
379         };
380
381         // Instantiate classes for the nodes that don't get reloaded on a ser-des reload
382         LDKLogger logger1 {
383                 .this_arg = (void*)1,
384                 .log = print_log,
385                 .free = NULL,
386         };
387
388         NodeMonitors mons1;
389         mons1.logger = &logger1;
390         LDKWatch mon1 {
391                 .this_arg = &mons1,
392                 .watch_channel = add_channel_monitor,
393                 .update_channel = update_channel_monitor,
394                 .release_pending_monitor_events = monitors_pending_monitor_events,
395                 .free = NULL,
396         };
397
398         LDK::NetGraphMsgHandler net_graph1 = NetGraphMsgHandler_new(genesis_hash, NULL, logger1);
399         LDKSecretKey node_secret1;
400
401         LDKLogger logger2 {
402                 .this_arg = (void*)2,
403                 .log = print_log,
404                 .free = NULL,
405         };
406
407         NodeMonitors mons2;
408         mons2.logger = &logger2;
409         LDKWatch mon2 {
410                 .this_arg = &mons2,
411                 .watch_channel = add_channel_monitor,
412                 .update_channel = update_channel_monitor,
413                 .release_pending_monitor_events = monitors_pending_monitor_events,
414                 .free = NULL,
415         };
416
417         LDK::NetGraphMsgHandler net_graph2 = NetGraphMsgHandler_new(genesis_hash, NULL, logger2);
418         LDKSecretKey node_secret2;
419
420         LDK::CVec_u8Z cm1_ser = LDKCVec_u8Z {}; // ChannelManager 1 serialization at the end of the ser-des scope
421         LDK::CVec_u8Z cm2_ser = LDKCVec_u8Z {}; // ChannelManager 2 serialization at the end of the ser-des scope
422
423         { // Scope for the ser-des reload
424                 // Instantiate classes for node 1:
425                 uint8_t node_seed[32];
426                 memset(&node_seed, 0, 32);
427                 LDK::KeysManager keys1 = KeysManager_new(&node_seed, 0, 0);
428                 LDK::KeysInterface keys_source1 = KeysManager_as_KeysInterface(&keys1);
429                 node_secret1 = keys_source1->get_node_secret(keys_source1->this_arg);
430
431                 LDK::ChannelManager cm1 = ChannelManager_new(fee_est, mon1, broadcast, logger1, KeysManager_as_KeysInterface(&keys1), UserConfig_default(), ChainParameters_new(network, BestBlock_new(chain_tip, 0)));
432
433                 LDK::CVec_ChannelDetailsZ channels = ChannelManager_list_channels(&cm1);
434                 assert(channels->datalen == 0);
435
436                 LDK::MessageHandler msg_handler1 = MessageHandler_new(ChannelManager_as_ChannelMessageHandler(&cm1), NetGraphMsgHandler_as_RoutingMessageHandler(&net_graph1));
437
438                 random_bytes = keys_source1->get_secure_random_bytes(keys_source1->this_arg);
439                 LDK::PeerManager net1 = PeerManager_new(std::move(msg_handler1), node_secret1, &random_bytes.data, logger1);
440
441                 // Demo getting a channel key and check that its returning real pubkeys:
442                 LDK::Sign chan_signer1 = keys_source1->get_channel_signer(keys_source1->this_arg, false, 42);
443                 chan_signer1->BaseSign.set_pubkeys(&chan_signer1->BaseSign); // Make sure pubkeys is defined
444                 LDKPublicKey payment_point = ChannelPublicKeys_get_payment_point(&chan_signer1->BaseSign.pubkeys);
445                 assert(memcmp(&payment_point, &null_pk, sizeof(null_pk)));
446
447                 // Instantiate classes for node 2:
448                 memset(&node_seed, 1, 32);
449                 LDK::KeysManager keys2 = KeysManager_new(&node_seed, 0, 0);
450                 LDK::KeysInterface keys_source2 = KeysManager_as_KeysInterface(&keys2);
451                 node_secret2 = keys_source2->get_node_secret(keys_source2->this_arg);
452
453                 LDK::ChannelHandshakeConfig handshake_config2 = ChannelHandshakeConfig_default();
454                 ChannelHandshakeConfig_set_minimum_depth(&handshake_config2, 2);
455                 LDK::UserConfig config2 = UserConfig_default();
456                 UserConfig_set_own_channel_config(&config2, std::move(handshake_config2));
457
458                 LDK::ChannelManager cm2 = ChannelManager_new(fee_est, mon2, broadcast, logger2, KeysManager_as_KeysInterface(&keys2), std::move(config2), ChainParameters_new(network, BestBlock_new(chain_tip, 0)));
459
460                 LDK::CVec_ChannelDetailsZ channels2 = ChannelManager_list_channels(&cm2);
461                 assert(channels2->datalen == 0);
462
463                 LDK::RoutingMessageHandler net_msgs2 = NetGraphMsgHandler_as_RoutingMessageHandler(&net_graph2);
464                 LDK::CResult_ChannelAnnouncementDecodeErrorZ chan_ann = ChannelAnnouncement_read(LDKu8slice { .data = valid_node_announcement, .datalen = sizeof(valid_node_announcement) });
465                 assert(chan_ann->result_ok);
466                 LDK::CResult_boolLightningErrorZ ann_res = net_msgs2->handle_channel_announcement(net_msgs2->this_arg, chan_ann->contents.result);
467                 assert(ann_res->result_ok);
468
469                 LDK::MessageHandler msg_handler2 = MessageHandler_new(ChannelManager_as_ChannelMessageHandler(&cm2), std::move(net_msgs2));
470
471                 random_bytes = keys_source2->get_secure_random_bytes(keys_source2->this_arg);
472                 LDK::PeerManager net2 = PeerManager_new(std::move(msg_handler2), node_secret2, &random_bytes.data, logger2);
473
474                 // Open a connection!
475                 PeersConnection conn(cm1, cm2, net1, net2);
476
477                 // Note that we have to bind the result to a C++ class to make sure it gets free'd
478                 LDK::CResult_NoneAPIErrorZ res = ChannelManager_create_channel(&cm1, ChannelManager_get_our_node_id(&cm2), 40000, 1000, 42, UserConfig_default());
479                 assert(res->result_ok);
480                 PeerManager_process_events(&net1);
481
482                 LDK::CVec_ChannelDetailsZ new_channels = ChannelManager_list_channels(&cm1);
483                 assert(new_channels->datalen == 1);
484                 LDKPublicKey chan_open_pk = ChannelDetails_get_remote_network_id(&new_channels->data[0]);
485                 assert(!memcmp(chan_open_pk.compressed_form, ChannelManager_get_our_node_id(&cm2).compressed_form, 33));
486
487                 while (true) {
488                         LDK::CVec_ChannelDetailsZ new_channels_2 = ChannelManager_list_channels(&cm2);
489                         if (new_channels_2->datalen == 1) {
490                                 // Sample getting our counterparty's init features (which used to be hard to do without a memory leak):
491                                 const LDK::InitFeatures init_feats = ChannelDetails_get_counterparty_features(&new_channels_2->data[0]);
492                                 assert(init_feats->inner != NULL);
493                                 break;
494                         }
495                         std::this_thread::yield();
496                 }
497
498                 LDKEventsProvider ev1 = ChannelManager_as_EventsProvider(&cm1);
499                 while (true) {
500                         EventQueue queue;
501                         LDKEventHandler handler = { .this_arg = &queue, .handle_event = handle_event, .free = NULL };
502                         ev1.process_pending_events(ev1.this_arg, handler);
503                         if (queue.events.size() == 1) {
504                                 assert(queue.events[0]->tag == LDKEvent_FundingGenerationReady);
505                                 assert(queue.events[0]->funding_generation_ready.user_channel_id == 42);
506                                 assert(queue.events[0]->funding_generation_ready.channel_value_satoshis == 40000);
507                                 assert(queue.events[0]->funding_generation_ready.output_script.datalen == 34);
508                                 assert(!memcmp(queue.events[0]->funding_generation_ready.output_script.data, channel_open_block + 58 + 81, 34));
509                                 LDKTransaction funding_transaction { .data = const_cast<uint8_t*>(channel_open_block + 81), .datalen = sizeof(channel_open_block) - 81, .data_is_owned = false };
510
511                                 LDK::CResult_NoneAPIErrorZ fund_res = ChannelManager_funding_transaction_generated(&cm1, &queue.events[0]->funding_generation_ready.temporary_channel_id.data, funding_transaction);
512                                 assert(fund_res->result_ok);
513                                 break;
514                         }
515                         std::this_thread::yield();
516                 }
517
518                 // We observe when the funding signed messages have been exchanged by
519                 // waiting for two monitors to be registered.
520                 assert(num_txs_broadcasted == 0);
521                 PeerManager_process_events(&net1);
522                 while (num_txs_broadcasted != 1) {
523                         std::this_thread::yield();
524                 }
525
526                 LDK::Listen listener1 = ChannelManager_as_Listen(&cm1);
527                 listener1->block_connected(listener1->this_arg, LDKu8slice { .data = channel_open_block, .datalen = sizeof(channel_open_block) }, 1);
528
529                 LDK::Listen listener2 = ChannelManager_as_Listen(&cm2);
530                 listener2->block_connected(listener2->this_arg, LDKu8slice { .data = channel_open_block, .datalen = sizeof(channel_open_block) }, 1);
531
532                 LDKCVec_C2Tuple_usizeTransactionZZ txdata { .data = (LDKC2Tuple_usizeTransactionZ*)malloc(sizeof(LDKC2Tuple_usizeTransactionZ)), .datalen = 1 };
533                 *txdata.data = C2Tuple_usizeTransactionZ_new(0, LDKTransaction { .data = (uint8_t*)channel_open_block + 81, .datalen = sizeof(channel_open_block) - 81, .data_is_owned = false });
534                 mons1.ConnectBlock(&channel_open_header, 1, txdata, broadcast, fee_est);
535
536                 txdata = LDKCVec_C2Tuple_usizeTransactionZZ { .data = (LDKC2Tuple_usizeTransactionZ*)malloc(sizeof(LDKC2Tuple_usizeTransactionZ)), .datalen = 1 };
537                 *txdata.data = C2Tuple_usizeTransactionZ_new(0, LDKTransaction { .data = (uint8_t*)channel_open_block + 81, .datalen = sizeof(channel_open_block) - 81, .data_is_owned = false });
538                 mons2.ConnectBlock(&channel_open_header, 1, txdata, broadcast, fee_est);
539
540                 listener1->block_connected(listener1->this_arg, LDKu8slice { .data = block_1, .datalen = sizeof(block_1) }, 2);
541                 listener2->block_connected(listener2->this_arg, LDKu8slice { .data = block_1, .datalen = sizeof(block_1) }, 2);
542                 mons1.ConnectBlock(&header_1, 2, LDKCVec_C2Tuple_usizeTransactionZZ { .data = NULL, .datalen = 0 }, broadcast, fee_est);
543                 mons2.ConnectBlock(&header_1, 2, LDKCVec_C2Tuple_usizeTransactionZZ { .data = NULL, .datalen = 0 }, broadcast, fee_est);
544
545                 listener1->block_connected(listener1->this_arg, LDKu8slice { .data = block_2, .datalen = sizeof(block_1) }, 3);
546                 listener2->block_connected(listener2->this_arg, LDKu8slice { .data = block_2, .datalen = sizeof(block_1) }, 3);
547                 mons1.ConnectBlock(&header_2, 3, LDKCVec_C2Tuple_usizeTransactionZZ { .data = NULL, .datalen = 0 }, broadcast, fee_est);
548                 mons2.ConnectBlock(&header_2, 3, LDKCVec_C2Tuple_usizeTransactionZZ { .data = NULL, .datalen = 0 }, broadcast, fee_est);
549
550                 PeerManager_process_events(&net1);
551                 PeerManager_process_events(&net2);
552
553                 // Now send funds from 1 to 2!
554                 while (true) {
555                         LDK::CVec_ChannelDetailsZ outbound_channels = ChannelManager_list_usable_channels(&cm1);
556                         if (outbound_channels->datalen == 1) {
557                                 const LDKChannelDetails *channel = &outbound_channels->data[0];
558                                 // Note that the channel ID is the same as the channel txid reversed as the output index is 0
559                                 uint8_t expected_chan_id[32];
560                                 for (int i = 0; i < 32; i++) { expected_chan_id[i] = channel_open_txid[31-i]; }
561                                 assert(!memcmp(ChannelDetails_get_channel_id(channel), expected_chan_id, 32));
562                                 assert(!memcmp(ChannelDetails_get_remote_network_id(channel).compressed_form,
563                                                 ChannelManager_get_our_node_id(&cm2).compressed_form, 33));
564                                 assert(ChannelDetails_get_channel_value_satoshis(channel) == 40000);
565                                 // We opened the channel with 1000 push_msat:
566                                 assert(ChannelDetails_get_outbound_capacity_msat(channel) == 40000*1000 - 1000);
567                                 assert(ChannelDetails_get_inbound_capacity_msat(channel) == 1000);
568                                 assert(ChannelDetails_get_is_usable(channel));
569                                 break;
570                         }
571                         std::this_thread::yield();
572                 }
573
574                 LDKCOption_u64Z min_value = {
575                         .tag = LDKCOption_u64Z_Some,
576                         .some = 5000,
577                 };
578                 LDK::CResult_InvoiceSignOrCreationErrorZ invoice = create_invoice_from_channelmanager(&cm2,
579                         KeysManager_as_KeysInterface(&keys2),
580                         LDKCurrency_Bitcoin, min_value,
581                         LDKStr {
582                                 .chars = (const uint8_t *)"Invoice Description",
583                                 .len =             strlen("Invoice Description"),
584                                 .chars_is_owned = false
585                         });
586                 assert(invoice->result_ok);
587                 LDKThirtyTwoBytes payment_hash;
588                 memcpy(payment_hash.data, Invoice_payment_hash(invoice->contents.result), 32);
589
590                 {
591                         LDK::CVec_ChannelDetailsZ outbound_channels = ChannelManager_list_usable_channels(&cm1);
592                         LDK::LockedNetworkGraph graph_2_locked = NetGraphMsgHandler_read_locked_graph(&net_graph2);
593                         LDK::NetworkGraph graph_2_ref = LockedNetworkGraph_graph(&graph_2_locked);
594                         LDK::CResult_RouteLightningErrorZ route = get_route(ChannelManager_get_our_node_id(&cm1), &graph_2_ref, ChannelManager_get_our_node_id(&cm2), LDKInvoiceFeatures {
595                                         .inner = NULL, .is_owned = false
596                                 }, &outbound_channels, Invoice_route_hints(invoice->contents.result),
597                                 5000, Invoice_min_final_cltv_expiry(invoice->contents.result), logger1);
598                         assert(route->result_ok);
599                         LDK::CResult_NonePaymentSendFailureZ send_res = ChannelManager_send_payment(&cm1, route->contents.result, payment_hash, Invoice_payment_secret(invoice->contents.result));
600                         assert(send_res->result_ok);
601                 }
602
603                 mons_updated = 0;
604                 PeerManager_process_events(&net1);
605                 while (mons_updated != 4) {
606                         std::this_thread::yield();
607                 }
608
609                 // Check that we received the payment!
610                 LDKEventsProvider ev2 = ChannelManager_as_EventsProvider(&cm2);
611                 while (true) {
612                         EventQueue queue;
613                         LDKEventHandler handler = { .this_arg = &queue, .handle_event = handle_event, .free = NULL };
614                         ev2.process_pending_events(ev2.this_arg, handler);
615                         if (queue.events.size() == 1) {
616                                 assert(queue.events[0]->tag == LDKEvent_PendingHTLCsForwardable);
617                                 break;
618                         }
619                         std::this_thread::yield();
620                 }
621                 ChannelManager_process_pending_htlc_forwards(&cm2);
622                 PeerManager_process_events(&net2);
623
624                 mons_updated = 0;
625                 LDKThirtyTwoBytes payment_preimage;
626                 {
627                         EventQueue queue;
628                         LDKEventHandler handler = { .this_arg = &queue, .handle_event = handle_event, .free = NULL };
629                         ev2.process_pending_events(ev2.this_arg, handler);
630                         assert(queue.events.size() == 1);
631                         assert(queue.events[0]->tag == LDKEvent_PaymentReceived);
632                         assert(!memcmp(queue.events[0]->payment_received.payment_hash.data, payment_hash.data, 32));
633                         assert(!memcmp(queue.events[0]->payment_received.payment_secret.data, Invoice_payment_secret(invoice->contents.result).data, 32));
634                         assert(queue.events[0]->payment_received.amt == 5000);
635                         memcpy(payment_preimage.data, queue.events[0]->payment_received.payment_preimage.data, 32);
636                         assert(ChannelManager_claim_funds(&cm2, payment_preimage));
637                 }
638                 PeerManager_process_events(&net2);
639                 // Wait until we've passed through a full set of monitor updates (ie new preimage + CS/RAA messages)
640                 while (mons_updated != 5) {
641                         std::this_thread::yield();
642                 }
643                 {
644                         EventQueue queue;
645                         LDKEventHandler handler = { .this_arg = &queue, .handle_event = handle_event, .free = NULL };
646                         ev1.process_pending_events(ev1.this_arg, handler);
647                         assert(queue.events.size() == 1);
648                         assert(queue.events[0]->tag == LDKEvent_PaymentSent);
649                         assert(!memcmp(queue.events[0]->payment_sent.payment_preimage.data, payment_preimage.data, 32));
650                 }
651
652                 conn.stop();
653
654                 cm1_ser = ChannelManager_write(&cm1);
655                 cm2_ser = ChannelManager_write(&cm2);
656         }
657
658         LDK::CVec_ChannelMonitorZ mons_list1 = LDKCVec_ChannelMonitorZ { .data = (LDKChannelMonitor*)malloc(sizeof(LDKChannelMonitor)), .datalen = 1 };
659         assert(mons1.mons.size() == 1);
660         mons_list1->data[0] = *& std::get<1>(mons1.mons[0]); // Note that we need a reference, thus need a raw clone here, which *& does.
661         mons_list1->data[0].is_owned = false; // XXX: God this sucks
662         uint8_t node_seed[32];
663         memset(&node_seed, 0, 32);
664         LDK::KeysManager keys1 = KeysManager_new(&node_seed, 1, 0);
665         LDK::KeysInterface keys_source1 = KeysManager_as_KeysInterface(&keys1);
666
667         LDK::ChannelManagerReadArgs cm1_args = ChannelManagerReadArgs_new(KeysManager_as_KeysInterface(&keys1), fee_est, mon1, broadcast, logger1, UserConfig_default(), std::move(mons_list1));
668         LDK::CResult_C2Tuple_BlockHashChannelManagerZDecodeErrorZ cm1_read =
669                 C2Tuple_BlockHashChannelManagerZ_read(LDKu8slice { .data = cm1_ser->data, .datalen = cm1_ser -> datalen}, std::move(cm1_args));
670         assert(cm1_read->result_ok);
671         LDK::ChannelManager cm1(std::move(cm1_read->contents.result->b));
672
673         LDK::CVec_ChannelMonitorZ mons_list2 = LDKCVec_ChannelMonitorZ { .data = (LDKChannelMonitor*)malloc(sizeof(LDKChannelMonitor)), .datalen = 1 };
674         assert(mons2.mons.size() == 1);
675         mons_list2->data[0] = *& std::get<1>(mons2.mons[0]); // Note that we need a reference, thus need a raw clone here, which *& does.
676         mons_list2->data[0].is_owned = false; // XXX: God this sucks
677         memset(&node_seed, 1, 32);
678         LDK::KeysManager keys2 = KeysManager_new(&node_seed, 1, 0);
679
680         LDK::ChannelManagerReadArgs cm2_args = ChannelManagerReadArgs_new(KeysManager_as_KeysInterface(&keys2), fee_est, mon2, broadcast, logger2, UserConfig_default(), std::move(mons_list2));
681         LDK::CResult_C2Tuple_BlockHashChannelManagerZDecodeErrorZ cm2_read =
682                 C2Tuple_BlockHashChannelManagerZ_read(LDKu8slice { .data = cm2_ser->data, .datalen = cm2_ser -> datalen}, std::move(cm2_args));
683         assert(cm2_read->result_ok);
684         LDK::ChannelManager cm2(std::move(cm2_read->contents.result->b));
685
686         // Attempt to close the channel...
687         uint8_t chan_id[32];
688         for (int i = 0; i < 32; i++) { chan_id[i] = channel_open_txid[31-i]; }
689         LDK::CResult_NoneAPIErrorZ close_res = ChannelManager_close_channel(&cm1, &chan_id);
690         assert(!close_res->result_ok); // Note that we can't close while disconnected!
691
692         // Open a connection!
693         LDK::MessageHandler msg_handler1 = MessageHandler_new(ChannelManager_as_ChannelMessageHandler(&cm1), NetGraphMsgHandler_as_RoutingMessageHandler(&net_graph1));
694         random_bytes = keys_source1->get_secure_random_bytes(keys_source1->this_arg);
695         LDK::PeerManager net1 = PeerManager_new(std::move(msg_handler1), node_secret1, &random_bytes.data, logger1);
696
697         LDK::MessageHandler msg_handler2 = MessageHandler_new(ChannelManager_as_ChannelMessageHandler(&cm2), NetGraphMsgHandler_as_RoutingMessageHandler(&net_graph2));
698         random_bytes = keys_source1->get_secure_random_bytes(keys_source1->this_arg);
699         LDK::PeerManager net2 = PeerManager_new(std::move(msg_handler2), node_secret2, &random_bytes.data, logger2);
700
701         PeersConnection conn(cm1, cm2, net1, net2);
702
703         while (true) {
704                 // Wait for the channels to be considered up once the reestablish messages are processed
705                 LDK::CVec_ChannelDetailsZ outbound_channels = ChannelManager_list_usable_channels(&cm1);
706                 if (outbound_channels->datalen == 1) {
707                         break;
708                 }
709         }
710
711         // Actually close the channel
712         num_txs_broadcasted = 0;
713         close_res = ChannelManager_close_channel(&cm1, &chan_id);
714         assert(close_res->result_ok);
715         PeerManager_process_events(&net1);
716         while (num_txs_broadcasted != 2) {
717                 std::this_thread::yield();
718         }
719         LDK::CVec_ChannelDetailsZ chans_after_close1 = ChannelManager_list_channels(&cm1);
720         assert(chans_after_close1->datalen == 0);
721         LDK::CVec_ChannelDetailsZ chans_after_close2 = ChannelManager_list_channels(&cm2);
722         assert(chans_after_close2->datalen == 0);
723
724         conn.stop();
725
726         // Few extra random tests:
727         LDKSecretKey sk;
728         memset(&sk, 42, 32);
729         LDKThirtyTwoBytes kdiv_params;
730         memset(&kdiv_params, 43, 32);
731         LDK::InMemorySigner signer = InMemorySigner_new(sk, sk, sk, sk, sk, random_bytes, 42, kdiv_params);
732 }