Skip to content

Commit ad315bc

Browse files
committed
Honor the per-peer fee policy at the skim site
The forwarding skim now reads the peer's granted policy from the SCID store instead of hard-coding Flat(Standard). A peer with no grant resolves to Standard, so the skim is byte-for-byte the historical 2% for everyone the issuer set has not waived. This is the read side that makes the persisted grant actually take effect; before it, a verified ZeroFee was stored and then ignored. The lookup is hoisted out of the per-HTLC loop because the policy is keyed by peer, not by HTLC, so it is one store read per batch rather than one per forward. A zero skim is now two distinct cases, so the log is split. ZeroFee is the expected path and logs at info. Any other tier skimming nothing means the fee would have consumed the whole HTLC, which keeps the error-level log: a forward of the full amount that we expected to take a cut on. Previously ZeroFee was unreachable, so the single error log was correct; now that a grant can legitimately waive the fee, the error would be noise.
1 parent 95c6c0b commit ad315bc

1 file changed

Lines changed: 24 additions & 8 deletions

File tree

lightning-liquidity/src/lsps4/service.rs

Lines changed: 24 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -782,6 +782,14 @@ where
782782
skimmed_fee_msat: u64,
783783
}
784784

785+
// The peer's granted policy, looked up once. Peers with no grant resolve to Standard, so
786+
// the skim matches the historical 2% for everyone the issuer set hasn't waived.
787+
let policy = self
788+
.scid_store
789+
.get_policy(&their_node_id)
790+
.unwrap_or(FeePolicy::Flat(FeeTier::Standard));
791+
let is_zero_fee = matches!(policy, FeePolicy::Flat(FeeTier::ZeroFee));
792+
785793
let mut computed_htlcs: Vec<ComputedHtlc> = htlcs
786794
.drain(..)
787795
.map(|htlc| {
@@ -792,18 +800,26 @@ where
792800

793801
let htlc_id = htlc.id();
794802
let skimmed_fee_msat = resolve_skim(
795-
&FeePolicy::Flat(FeeTier::Standard),
803+
&policy,
796804
expected_outbound_msat,
797805
self.config.forwarding_fee_proportional_millionths,
798806
);
799807
if skimmed_fee_msat == 0 {
800-
// The policy here is always Flat(Standard), so a zero skim can only mean the
801-
// fee would have consumed the entire HTLC; it is never a ZeroFee waiver yet.
802-
log_error!(
803-
self.logger,
804-
"Standard skim would have consumed the entire HTLC {:?}; forwarding the full amount.",
805-
htlc_id
806-
);
808+
if is_zero_fee {
809+
log_info!(
810+
self.logger,
811+
"Zero-fee policy for HTLC {:?}; forwarding the full amount.",
812+
htlc_id
813+
);
814+
} else {
815+
// A non-zero-fee tier skimmed nothing only because the fee would have
816+
// consumed the entire HTLC; forward it intact rather than break it.
817+
log_error!(
818+
self.logger,
819+
"Skim would have consumed the entire HTLC {:?}; forwarding the full amount.",
820+
htlc_id
821+
);
822+
}
807823
}
808824

809825
let amount_to_forward_msat = expected_outbound_msat.saturating_sub(skimmed_fee_msat);

0 commit comments

Comments
 (0)