Skip to content

Commit 8ba3e83

Browse files
committed
Reorder PathBuildingHop fields somewhat
Given `PathBuildingHop` is now an even multiple of cache lines, we can pick which fields "fall off" the cache line we have visible when dealing with hops, which we do here.
1 parent e2f34cb commit 8ba3e83

File tree

1 file changed

+21
-13
lines changed

1 file changed

+21
-13
lines changed

lightning/src/routing/router.rs

Lines changed: 21 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1311,15 +1311,15 @@ fn iter_equal<I1: Iterator, I2: Iterator>(mut iter_a: I1, mut iter_b: I2)
13111311
/// Fee values should be updated only in the context of the whole path, see update_value_and_recompute_fees.
13121312
/// These fee values are useful to choose hops as we traverse the graph "payee-to-payer".
13131313
#[derive(Clone)]
1314+
#[repr(C)] // Force fields to appear in the order we define them.
13141315
struct PathBuildingHop<'a> {
13151316
candidate: CandidateRouteHop<'a>,
1316-
fee_msat: u64,
1317-
1318-
/// All the fees paid *after* this channel on the way to the destination
1319-
next_hops_fee_msat: u64,
1320-
/// Fee paid for the use of the current channel (see candidate.fees()).
1321-
/// The value will be actually deducted from the counterparty balance on the previous link.
1322-
hop_use_fee_msat: u64,
1317+
/// If we've already processed a node as the best node, we shouldn't process it again. Normally
1318+
/// we'd just ignore it if we did as all channels would have a higher new fee, but because we
1319+
/// may decrease the amounts in use as we walk the graph, the actual calculated fee may
1320+
/// decrease as well. Thus, we have to explicitly track which nodes have been processed and
1321+
/// avoid processing them again.
1322+
was_processed: bool,
13231323
/// Used to compare channels when choosing the for routing.
13241324
/// Includes paying for the use of a hop and the following hops, as well as
13251325
/// an estimated cost of reaching this hop.
@@ -1331,12 +1331,20 @@ struct PathBuildingHop<'a> {
13311331
/// All penalties incurred from this channel on the way to the destination, as calculated using
13321332
/// channel scoring.
13331333
path_penalty_msat: u64,
1334-
/// If we've already processed a node as the best node, we shouldn't process it again. Normally
1335-
/// we'd just ignore it if we did as all channels would have a higher new fee, but because we
1336-
/// may decrease the amounts in use as we walk the graph, the actual calculated fee may
1337-
/// decrease as well. Thus, we have to explicitly track which nodes have been processed and
1338-
/// avoid processing them again.
1339-
was_processed: bool,
1334+
1335+
// The last 16 bytes are on the next cache line by default in glibc's malloc. Thus, we should
1336+
// only place fields which are not hot there. Luckily, the next three fields are only read if
1337+
// we end up on the selected path, and only in the final path layout phase, so we don't care
1338+
// too much if reading them is slow.
1339+
1340+
fee_msat: u64,
1341+
1342+
/// All the fees paid *after* this channel on the way to the destination
1343+
next_hops_fee_msat: u64,
1344+
/// Fee paid for the use of the current channel (see candidate.fees()).
1345+
/// The value will be actually deducted from the counterparty balance on the previous link.
1346+
hop_use_fee_msat: u64,
1347+
13401348
#[cfg(all(not(ldk_bench), any(test, fuzzing)))]
13411349
// In tests, we apply further sanity checks on cases where we skip nodes we already processed
13421350
// to ensure it is specifically in cases where the fee has gone down because of a decrease in

0 commit comments

Comments
 (0)