diff --git a/channeld/channeld.c b/channeld/channeld.c
index 798056562a24..d22490cb7cff 100644
--- a/channeld/channeld.c
+++ b/channeld/channeld.c
@@ -1006,6 +1006,8 @@ static void handle_peer_add_htlc(struct peer *peer, const u8 *msg)
 	add_err = channel_add_htlc(peer->channel, REMOTE, id, amount,
 				   cltv_expiry, &payment_hash,
 				   onion_routing_packet, tlvs->blinding_point, &htlc, NULL,
+				   /* We just forward it :) smart ah? */
+				   tlvs->endorsed,
 				   /* We don't immediately fail incoming htlcs,
 				    * instead we wait and fail them after
 				    * they've been committed */
@@ -5622,9 +5624,12 @@ static void handle_funding_depth(struct peer *peer, const u8 *msg)
 	billboard_update(peer);
 }
 
+
+/* Offer an HTLC to the remote side. */
 static void handle_offer_htlc(struct peer *peer, const u8 *inmsg)
 {
 	u8 *msg;
+	bool *endorsed;
 	u32 cltv_expiry;
 	struct amount_msat amount;
 	struct sha256 payment_hash;
@@ -5641,25 +5646,27 @@ static void handle_offer_htlc(struct peer *peer, const u8 *inmsg)
 			      "funding not locked for offer_htlc");
 
 	if (!fromwire_channeld_offer_htlc(tmpctx, inmsg, &amount,
-					 &cltv_expiry, &payment_hash,
-					 onion_routing_packet, &blinding))
+					  &cltv_expiry, &payment_hash,
+					  onion_routing_packet, &blinding,
+					  &endorsed))
 		master_badmsg(WIRE_CHANNELD_OFFER_HTLC, inmsg);
-
 	if (blinding) {
 		tlvs = tlv_update_add_htlc_tlvs_new(tmpctx);
 		tlvs->blinding_point = tal_dup(tlvs, struct pubkey, blinding);
+		tlvs->endorsed = (u8 *) endorsed;
 	} else
 		tlvs = NULL;
 
 	e = channel_add_htlc(peer->channel, LOCAL, peer->htlc_id,
 			     amount, cltv_expiry, &payment_hash,
 			     onion_routing_packet, take(blinding), NULL,
-			     &htlc_fee, true);
-	status_debug("Adding HTLC %"PRIu64" amount=%s cltv=%u gave %s",
+			     &htlc_fee, endorsed, true);
+	status_debug("Adding HTLC %"PRIu64" amount=%s cltv=%u gave %s endorsed=%u",
 		     peer->htlc_id,
 		     type_to_string(tmpctx, struct amount_msat, &amount),
 		     cltv_expiry,
-		     channel_add_err_name(e));
+		     channel_add_err_name(e),
+		     endorsed ? *endorsed : 0);
 
 	switch (e) {
 	case CHANNEL_ERR_ADD_OK:
diff --git a/channeld/channeld_wire.csv b/channeld/channeld_wire.csv
index 53590a2e6ee6..b43b7341d32f 100644
--- a/channeld/channeld_wire.csv
+++ b/channeld/channeld_wire.csv
@@ -97,6 +97,7 @@ msgdata,channeld_offer_htlc,cltv_expiry,u32,
 msgdata,channeld_offer_htlc,payment_hash,sha256,
 msgdata,channeld_offer_htlc,onion_routing_packet,u8,1366
 msgdata,channeld_offer_htlc,blinding,?pubkey,
+msgdata,channeld_offer_htlc,endorsed,?bool,
 
 # Reply; synchronous since IDs have to increment.
 msgtype,channeld_offer_htlc_reply,1104
diff --git a/channeld/full_channel.c b/channeld/full_channel.c
index 45639328ce26..d366f4ecc63a 100644
--- a/channeld/full_channel.c
+++ b/channeld/full_channel.c
@@ -914,6 +914,7 @@ enum channel_add_err channel_add_htlc(struct channel *channel,
 				      const struct pubkey *blinding TAKES,
 				      struct htlc **htlcp,
 				      struct amount_sat *htlc_fee,
+				      const bool endorsed,
 				      bool err_immediate_failures)
 {
 	enum htlc_state state;
diff --git a/channeld/full_channel.h b/channeld/full_channel.h
index 05ebf8da0364..6cc7906a3dfb 100644
--- a/channeld/full_channel.h
+++ b/channeld/full_channel.h
@@ -132,6 +132,7 @@ enum channel_add_err channel_add_htlc(struct channel *channel,
 				      const struct pubkey *blinding TAKES,
 				      struct htlc **htlcp,
 				      struct amount_sat *htlc_fee,
+				      const bool endorsed,
 				      bool err_immediate_failures);
 
 /**
diff --git a/channeld/test/run-full_channel.c b/channeld/test/run-full_channel.c
index cfc1b213776e..6d3dafa12d3e 100644
--- a/channeld/test/run-full_channel.c
+++ b/channeld/test/run-full_channel.c
@@ -168,7 +168,7 @@ static const struct htlc **include_htlcs(struct channel *channel, enum side side
 		memset(&preimage, i, sizeof(preimage));
 		sha256(&hash, &preimage, sizeof(preimage));
 		e = channel_add_htlc(channel, sender, i, msatoshi, 500+i, &hash,
-				     dummy_routing, NULL, NULL, NULL, true);
+				     dummy_routing, NULL, NULL, NULL, false, true);
 		assert(e == CHANNEL_ERR_ADD_OK);
 		htlcs[i] = channel_get_htlc(channel, sender, i);
 	}
@@ -260,7 +260,7 @@ static void send_and_fulfill_htlc(struct channel *channel,
 	sha256(&rhash, &r, sizeof(r));
 
 	assert(channel_add_htlc(channel, sender, 1337, msatoshi, 900, &rhash,
-				dummy_routing, NULL, NULL, NULL, true)
+				dummy_routing, NULL, NULL, NULL, false, true)
 	       == CHANNEL_ERR_ADD_OK);
 	htlc = channel_get_htlc(channel, sender, 1337);
 	assert(htlc);
diff --git a/doc/lightningd-config.5.md b/doc/lightningd-config.5.md
index 177d6b624fd0..c0ab56a3fb2d 100644
--- a/doc/lightningd-config.5.md
+++ b/doc/lightningd-config.5.md
@@ -803,6 +803,11 @@ don't have to use a worst-case fee, but can bump the commitment transaction
 if it's needed.  Note that this means that we need to keep
 some funds aside: see `min-emergency-msat`.
 
+* **experimental-jamming-endorsement**
+
+  Specifying this option turn on part of the Channel Jamming mitigation
+to forward the `endorsed` inside `update_add_htl` lightning message.
+
 BUGS
 ----
 
diff --git a/lightningd/lightningd.h b/lightningd/lightningd.h
index b2de15072810..166ea6496090 100644
--- a/lightningd/lightningd.h
+++ b/lightningd/lightningd.h
@@ -388,6 +388,9 @@ struct lightningd {
 	/* --invoices-onchain-fallback */
 	bool unified_invoices;
 
+	/* --experimental-jamming */
+	bool experimental_jamming_endorsement;
+
 	/* For anchors: how much do we keep for spending close txs? */
 	struct amount_sat emergency_sat;
 
diff --git a/lightningd/options.c b/lightningd/options.c
index 417e801e142d..26a8c1241923 100644
--- a/lightningd/options.c
+++ b/lightningd/options.c
@@ -1622,6 +1622,10 @@ static void register_opts(struct lightningd *ld)
 	opt_register_noarg("--invoices-onchain-fallback",
 			   opt_set_bool, &ld->unified_invoices,
 			   "Include an onchain address in invoices and mark them as paid if payment is received on-chain");
+	opt_register_noarg("--experimental-jamming-endorsement",
+			   opt_set_bool, &ld->experimental_jamming_endorsement,
+			   "experimental: allow htlc endorsement to mitigate channel jamming (incomplete)");
+
 	clnopt_witharg("--database-upgrade", OPT_SHOWBOOL,
 		       opt_set_db_upgrade, NULL,
 		       ld,
diff --git a/lightningd/pay.c b/lightningd/pay.c
index 1e759c7fdaa0..90c2ffa4e220 100644
--- a/lightningd/pay.c
+++ b/lightningd/pay.c
@@ -17,6 +17,7 @@
 #include <lightningd/pay.h>
 #include <lightningd/peer_control.h>
 #include <lightningd/peer_htlcs.h>
+#include <stdbool.h>
 #include <wallet/invoices.h>
 
 /* Routing failure object */
@@ -730,7 +731,8 @@ static const u8 *send_onion(const tal_t *ctx, struct lightningd *ld,
 			    u64 partid,
 			    u64 groupid,
 			    struct channel *channel,
-			    struct htlc_out **hout)
+			    struct htlc_out **hout,
+	                    const bool *endorsed)
 {
 	const u8 *onion;
 	unsigned int base_expiry;
@@ -740,7 +742,8 @@ static const u8 *send_onion(const tal_t *ctx, struct lightningd *ld,
 	return send_htlc_out(ctx, channel, first_hop->amount,
 			     base_expiry + first_hop->delay,
 			     final_amount, payment_hash,
-			     blinding, partid, groupid, onion, NULL, hout);
+			     blinding, partid, groupid, onion, NULL, hout,
+			     endorsed);
 }
 
 static struct command_result *check_invoice_request_usage(struct command *cmd,
@@ -1060,6 +1063,7 @@ send_payment_core(struct lightningd *ld,
 		  struct secret *path_secrets,
 		  const struct sha256 *local_invreq_id)
 {
+	bool endorsed;
 	const struct wallet_payment *old_payment;
 	struct channel *channel;
 	const u8 *failmsg;
@@ -1105,9 +1109,21 @@ send_payment_core(struct lightningd *ld,
 			 fmt_amount_msat(tmpctx, first_hop->amount),
 			 fmt_amount_msat(tmpctx, msat));
 
+	/* BLIP-jamming #04:
+	 * A sending node:
+	 * - if it is the original source of the HTLC:
+	 *    - if it does not expect immediate fulfillment upon receipt by the
+	 *    final destination:
+	 *       - SHOULD set `endorsed` to `0`.
+	 * - otherwise:
+	 *    - SHOULD set `endorsed` to `1`.
+	 *
+	 * We wait that someone else smarted than me will provide the way to
+	 * calculate it for now it is just a placeholder. */
+	endorsed = false;
 	failmsg = send_onion(tmpctx, ld, packet, first_hop, msat,
 			     rhash, NULL, partid,
-			     group, channel, &hout);
+			     group, channel, &hout, &endorsed);
 
 	if (failmsg) {
 		fail = immediate_routing_failure(
diff --git a/lightningd/peer_htlcs.c b/lightningd/peer_htlcs.c
index 36b81760915c..2019e881a11a 100644
--- a/lightningd/peer_htlcs.c
+++ b/lightningd/peer_htlcs.c
@@ -610,7 +610,8 @@ const u8 *send_htlc_out(const tal_t *ctx,
 			u64 groupid,
 			const u8 *onion_routing_packet,
 			struct htlc_in *in,
-			struct htlc_out **houtp)
+			struct htlc_out **houtp,
+	                const bool *endorsed)
 {
 	u8 *msg;
 
@@ -652,7 +653,8 @@ const u8 *send_htlc_out(const tal_t *ctx,
 	}
 
 	msg = towire_channeld_offer_htlc(out, amount, cltv, payment_hash,
-					onion_routing_packet, blinding);
+					 onion_routing_packet, blinding,
+					 (bool *)endorsed);
 	subd_req(out->peer->ld, out->owner, take(msg), -1, 0, rcvd_htlc_reply,
 		 *houtp);
 
@@ -705,7 +707,8 @@ static void forward_htlc(struct htlc_in *hin,
 			 const struct short_channel_id *forward_scid,
 			 const struct channel_id *forward_to,
 			 const u8 next_onion[TOTAL_PACKET_SIZE(ROUTING_INFO_SIZE)],
-			 const struct pubkey *next_blinding)
+			 const struct pubkey *next_blinding,
+	                 const bool *endorsed)
 {
 	const u8 *failmsg;
 	struct lightningd *ld = hin->key.channel->peer->ld;
@@ -816,7 +819,7 @@ static void forward_htlc(struct htlc_in *hin,
 				outgoing_cltv_value, AMOUNT_MSAT(0),
 				&hin->payment_hash,
 				next_blinding, 0 /* partid */, 0 /* groupid */,
-				next_onion, hin, &hout);
+				next_onion, hin, &hout, endorsed);
 	if (!failmsg)
 		return;
 
@@ -844,6 +847,11 @@ struct htlc_accepted_hook_payload {
 	u8 *next_onion;
 	u64 failtlvtype;
 	size_t failtlvpos;
+	/* NULL if the jamming mitigation it is not
+	 * supported */
+	bool *endorsed;
+	/* FIXME: add the possibility to encode
+	 * and decode the raw tlvs */
 };
 
 /* We only handle the simplest cases here */
@@ -929,7 +937,8 @@ static bool htlc_accepted_hook_deserialize(struct htlc_accepted_hook_payload *re
 	struct htlc_in *hin = request->hin;
 	struct lightningd *ld = request->ld;
 	struct preimage payment_preimage;
-	const jsmntok_t *resulttok, *paykeytok, *payloadtok, *fwdtok;
+	const jsmntok_t *resulttok, *paykeytok,
+		*payloadtok, *fwdtok, *endorse_tok;
 	u8 *failonion;
 
 	if (!toks || !buffer)
@@ -981,6 +990,19 @@ static bool htlc_accepted_hook_deserialize(struct htlc_accepted_hook_payload *re
 		}
 	}
 
+	endorse_tok = json_get_member(buffer, toks, "endorsed");
+	if (endorse_tok) {
+		bool internal_endorsed;
+		tal_free(request->endorsed);
+		request->endorsed = tal(request, bool);
+		if (json_to_bool(buffer, endorse_tok, &internal_endorsed))
+			fatal("Bad endorsed for htlc_accepted"
+			      " hook: %.*s",
+			      endorse_tok->end - endorse_tok->start,
+			      buffer + endorse_tok->start);
+		*request->endorsed = internal_endorsed ? 1 : 0;
+	}
+
 	if (json_tok_streq(buffer, resulttok, "continue")) {
 		return true;
 	}
@@ -1103,6 +1125,8 @@ static void htlc_accepted_hook_serialize(struct htlc_accepted_hook_payload *p,
 	}
 	json_add_hex_talarr(s, "next_onion", p->next_onion);
 	json_add_secret(s, "shared_secret", hin->shared_secret);
+	if (p->endorsed != NULL)
+		json_add_bool(s, "endorsed", *p->endorsed == 1);
 	json_object_end(s);
 
 	if (p->fwd_channel_id)
@@ -1151,7 +1175,7 @@ htlc_accepted_hook_final(struct htlc_accepted_hook_payload *request STEALS)
 			     request->payload->forward_channel,
 			     request->fwd_channel_id,
 			     serialize_onionpacket(tmpctx, rs->next),
-			     request->next_blinding);
+			     request->next_blinding, request->endorsed);
 	} else
 		handle_localpay(hin,
 				request->payload->amt_to_forward,
@@ -1432,7 +1456,10 @@ static bool peer_accepted_htlc(const tal_t *ctx,
 	 * we're in hook */
 	hook_payload->fwd_channel_id
 		= calc_forwarding_channel(ld, hook_payload);
-
+	// FIXME(vincenzopalazzo): ok this do not looks right, the value of
+	// hook_payload->endorsed should came from the prious pear of from us
+	// if we are the sender.
+	hook_payload->endorsed = ld->experimental_jamming_endorsement ? false : NULL;
 	plugin_hook_call_htlc_accepted(ld, NULL, hook_payload);
 
 	/* Falling through here is ok, after all the HTLC locked */
diff --git a/lightningd/peer_htlcs.h b/lightningd/peer_htlcs.h
index 688dd23ad7ed..a3ee73e4f978 100644
--- a/lightningd/peer_htlcs.h
+++ b/lightningd/peer_htlcs.h
@@ -37,7 +37,8 @@ const u8 *send_htlc_out(const tal_t *ctx,
 			u64 groupid,
 			const u8 *onion_routing_packet,
 			struct htlc_in *in,
-			struct htlc_out **houtp);
+			struct htlc_out **houtp,
+	                const bool *endorsed);
 
 void onchain_failed_our_htlc(const struct channel *channel,
 			     const struct htlc_stub *htlc,
diff --git a/wallet/test/run-wallet.c b/wallet/test/run-wallet.c
index a75112d205c4..328549359163 100644
--- a/wallet/test/run-wallet.c
+++ b/wallet/test/run-wallet.c
@@ -512,6 +512,9 @@ struct json_stream *json_stream_fail(struct command *cmd UNNEEDED,
 /* Generated stub for json_stream_success */
 struct json_stream *json_stream_success(struct command *cmd UNNEEDED)
 { fprintf(stderr, "json_stream_success called!\n"); abort(); }
+/* Generated stub for json_to_bool */
+bool json_to_bool(const char *buffer UNNEEDED, const jsmntok_t *tok UNNEEDED, bool *b UNNEEDED)
+{ fprintf(stderr, "json_to_bool called!\n"); abort(); }
 /* Generated stub for json_to_channel_id */
 bool json_to_channel_id(const char *buffer UNNEEDED, const jsmntok_t *tok UNNEEDED,
 			struct channel_id *cid UNNEEDED)
@@ -982,7 +985,7 @@ u8 *towire_channeld_got_commitsig_reply(const tal_t *ctx UNNEEDED)
 u8 *towire_channeld_got_revoke_reply(const tal_t *ctx UNNEEDED)
 { fprintf(stderr, "towire_channeld_got_revoke_reply called!\n"); abort(); }
 /* Generated stub for towire_channeld_offer_htlc */
-u8 *towire_channeld_offer_htlc(const tal_t *ctx UNNEEDED, struct amount_msat amount_msat UNNEEDED, u32 cltv_expiry UNNEEDED, const struct sha256 *payment_hash UNNEEDED, const u8 onion_routing_packet[1366] UNNEEDED, const struct pubkey *blinding UNNEEDED)
+u8 *towire_channeld_offer_htlc(const tal_t *ctx UNNEEDED, struct amount_msat amount_msat UNNEEDED, u32 cltv_expiry UNNEEDED, const struct sha256 *payment_hash UNNEEDED, const u8 onion_routing_packet[1366] UNNEEDED, const struct pubkey *blinding UNNEEDED, bool *endorsed UNNEEDED)
 { fprintf(stderr, "towire_channeld_offer_htlc called!\n"); abort(); }
 /* Generated stub for towire_channeld_sending_commitsig_reply */
 u8 *towire_channeld_sending_commitsig_reply(const tal_t *ctx UNNEEDED)
diff --git a/wire/extracted_peer_12_jamming.patch b/wire/extracted_peer_12_jamming.patch
new file mode 100644
index 000000000000..e0185bfa5c7a
--- /dev/null
+++ b/wire/extracted_peer_12_jamming.patch
@@ -0,0 +1,13 @@
+diff --git a/wire/peer_wire.csv b/wire/peer_wire.csv
+index 063d8cf07..f4ddcfcb5 100644
+--- a/wire/peer_wire.csv
++++ b/wire/peer_wire.csv
+@@ -245,6 +245,8 @@ msgdata,update_add_htlc,cltv_expiry,u32,
+ msgdata,update_add_htlc,onion_routing_packet,byte,1366
+ tlvtype,update_add_htlc_tlvs,blinding_point,0
+ tlvdata,update_add_htlc_tlvs,blinding_point,blinding,point,
++tlvtype,update_add_htlc_tlvs,endorsed,1
++tlvdata,update_add_htlc_tlvs,endorsed,endorsed,byte,
+ msgtype,update_fulfill_htlc,130
+ msgdata,update_fulfill_htlc,channel_id,channel_id,
+ msgdata,update_fulfill_htlc,id,u64,
diff --git a/wire/peer_wire.csv b/wire/peer_wire.csv
index 063d8cf07bd5..f4ddcfcb5d8c 100644
--- a/wire/peer_wire.csv
+++ b/wire/peer_wire.csv
@@ -245,6 +245,8 @@ msgdata,update_add_htlc,cltv_expiry,u32,
 msgdata,update_add_htlc,onion_routing_packet,byte,1366
 tlvtype,update_add_htlc_tlvs,blinding_point,0
 tlvdata,update_add_htlc_tlvs,blinding_point,blinding,point,
+tlvtype,update_add_htlc_tlvs,endorsed,1
+tlvdata,update_add_htlc_tlvs,endorsed,endorsed,byte,
 msgtype,update_fulfill_htlc,130
 msgdata,update_fulfill_htlc,channel_id,channel_id,
 msgdata,update_fulfill_htlc,id,u64,