new file mode 100644
@@ -0,0 +1,128 @@
+From 0c87c8c8b1a74cac99ad8115f3050efcb7fbed35 Mon Sep 17 00:00:00 2001
+From: =?UTF-8?q?Jos=C3=A9=20Padilla?= <jpadilla@webapplicate.com>
+Date: Tue, 8 Sep 2026 15:10:07 -0400
+Subject: [PATCH] Merge commit from fork
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+Co-authored-by: José Padilla <jpadilla@users.noreply.github.com>
+
+CVE: CVE-2026-103001
+Upstream-Status: Backport [https://github.com/jpadilla/pyjwt/commit/0c87c8c8b1a74cac99ad8115f3050efcb7fbed35]
+
+(cherry picked from commit 0c87c8c8b1a74cac99ad8115f3050efcb7fbed35)
+Signed-off-by: Hetvi Thakar <hthakar@cisco.com>
+---
+ jwt/api_jwt.py | 20 +++++++++-------
+ tests/test_api_jwt.py | 56 +++++++++++++++++++++++++++++++++++++++++++
+ 2 files changed, 67 insertions(+), 9 deletions(-)
+
+diff --git a/jwt/api_jwt.py b/jwt/api_jwt.py
+index 429c2d7..f298ea9 100644
+--- a/jwt/api_jwt.py
++++ b/jwt/api_jwt.py
+@@ -76,16 +76,18 @@ class PyJWT:
+ if options is None:
+ return self.options
+
++ merged_options = cast("Options", dict(options))
++
+ # (defensive) set defaults for verify_x to False if verify_signature is False
+- if not options.get("verify_signature", True):
+- options["verify_exp"] = options.get("verify_exp", False)
+- options["verify_nbf"] = options.get("verify_nbf", False)
+- options["verify_iat"] = options.get("verify_iat", False)
+- options["verify_aud"] = options.get("verify_aud", False)
+- options["verify_iss"] = options.get("verify_iss", False)
+- options["verify_sub"] = options.get("verify_sub", False)
+- options["verify_jti"] = options.get("verify_jti", False)
+- return {**self.options, **options}
++ if not merged_options.get("verify_signature", True):
++ merged_options["verify_exp"] = merged_options.get("verify_exp", False)
++ merged_options["verify_nbf"] = merged_options.get("verify_nbf", False)
++ merged_options["verify_iat"] = merged_options.get("verify_iat", False)
++ merged_options["verify_aud"] = merged_options.get("verify_aud", False)
++ merged_options["verify_iss"] = merged_options.get("verify_iss", False)
++ merged_options["verify_sub"] = merged_options.get("verify_sub", False)
++ merged_options["verify_jti"] = merged_options.get("verify_jti", False)
++ return {**self.options, **merged_options}
+
+ def encode(
+ self,
+diff --git a/tests/test_api_jwt.py b/tests/test_api_jwt.py
+index 8b54204..dd28816 100644
+--- a/tests/test_api_jwt.py
++++ b/tests/test_api_jwt.py
+@@ -1,6 +1,7 @@
+ import json
+ import time
+ from calendar import timegm
++from collections.abc import MutableMapping
+ from datetime import datetime, timedelta, timezone
+ from decimal import Decimal
+
+@@ -38,6 +39,61 @@ def payload() -> dict[str, object]:
+
+
+ class TestJWT:
++ def test_decode_does_not_mutate_options_when_signature_verification_is_disabled(
++ self, jwt: PyJWT
++ ) -> None:
++ options: Options = {"verify_signature": False}
++ token = jwt.encode({"claim": "value"}, "a" * 32, algorithm="HS256")
++ original_options = options.copy()
++
++ jwt.decode(token, options=options)
++
++ assert options == original_options
++
++ def test_reused_options_do_not_disable_claim_verification(self, jwt: PyJWT) -> None:
++ options: Options = {"verify_signature": False}
++ token = jwt.encode({"exp": utc_timestamp() - 1}, "a" * 32, algorithm="HS256")
++
++ jwt.decode(token, options=options)
++ options["verify_signature"] = True
++
++ with pytest.raises(ExpiredSignatureError):
++ jwt.decode(token, "a" * 32, algorithms=["HS256"], options=options)
++
++ def test_decode_complete_preserves_mutable_mapping_input(self, jwt: PyJWT) -> None:
++ class MappingWithoutCopy(MutableMapping[str, object]):
++ def __init__(self, values: dict[str, object]) -> None:
++ self.values = values
++
++ def __getitem__(self, key: str) -> object:
++ return self.values[key]
++
++ def __setitem__(self, key: str, value: object) -> None:
++ self.values[key] = value
++
++ def __delitem__(self, key: str) -> None:
++ del self.values[key]
++
++ def __iter__(self):
++ return iter(self.values)
++
++ def __len__(self) -> int:
++ return len(self.values)
++
++ options = MappingWithoutCopy({"verify_signature": False})
++ token = jwt.encode({"claim": "value"}, "a" * 32, algorithm="HS256")
++
++ jwt.decode_complete(token, options=options) # type: ignore[arg-type]
++
++ assert dict(options) == {"verify_signature": False}
++
++ def test_constructor_does_not_mutate_options_input(self, jwt: PyJWT) -> None:
++ options: Options = {"verify_signature": False}
++
++ PyJWT(options=options)
++
++ assert options == {"verify_signature": False}
++
+ def test_jwt_with_options(self) -> None:
+ jwt = PyJWT(options={"verify_signature": False})
+ assert jwt.options["verify_signature"] is False
+--
+2.35.6
@@ -10,6 +10,7 @@ SRC_URI += "file://CVE-2026-48522.patch \
file://CVE-2026-48524.patch \
file://CVE-2026-48525.patch \
file://CVE-2026-48526.patch \
+ file://CVE-2026-103001.patch \
"
SRC_URI[sha256sum] = "c74a7a2adf861c04d002db713dd85f84beb242228e671280bf709d765b03672b"
@@ -25,4 +26,3 @@ RDEPENDS:${PN} = "\
"
BBCLASSEXTEND = "native nativesdk"
-