CVE-2026-90269 (GCVE-0-2026-90269)

Vulnerability from cvelistv5 – Published: 2026-09-17 16:08 – Updated: 2026-09-17 16:08
VLAI
Title
bpf: Reject load-acquire from pointers requiring fault protection
Summary
In the Linux kernel, the following vulnerability has been resolved: bpf: Reject load-acquire from pointers requiring fault protection A BPF_LOAD_ACQ is not rewritten to a BPF_PROBE_MEM load by the verifier, unlike a regular BPF_LDX, so the JIT emits a plain load with no exception table entry and a fault panics the kernel instead of being handled. Reject the source pointer types that a BPF_LDX would have had that fault protection applied to, i.e. the ones bpf_convert_ctx_accesses() turns into BPF_PROBE_MEM: a bare PTR_TO_BTF_ID, PTR_TO_BTF_ID | PTR_UNTRUSTED, PTR_TO_BTF_ID | MEM_ALLOC | PTR_UNTRUSTED and PTR_TO_MEM | MEM_RDONLY | PTR_UNTRUSTED. This is reachable e.g. by loading ->mm out of a trusted task_struct yields an untrusted pointer to mm_struct, and it is NULL for a kernel thread: [...] SEC("tp_btf/sched_switch") int BPF_PROG(demo, bool preempt, struct task_struct *prev, struct task_struct *next) { struct mm_struct *mm = next->mm; /* untrusted */ out_ldx = (__u64)mm->pgd; /* BPF_LDX */ out_acq = load_acquire(&mm->pgd); /* BPF_LOAD_ACQ */ return 0; } [...] Both dereference the same pointer, but only the BPF_LDX is protected (x86-64 JIT, jump targets shown prog-relative): [...] ; out_ldx = (__u64)mm->pgd; 17: movq $-10485760, %r10 1e: movq %rsi, %r11 21: addq $184, %r11 28: subq %r10, %r11 2b: movabsq $140737498841088, %r10 35: cmpq %r10, %r11 38: ja 0x3e <-- kernel addr? 3a: xorl %edi, %edi <-- no: dst = 0, skip the load 3c: jmp 0x45 3e: movq 184(%rsi), %rdi <-- yes: load + extable entry [...] ; load_acquire(&mm->pgd) 53: movq %rsi, %rdi 56: movq 184(%rdi), %rax <-- no check, no extable entry [...] Note that BPF_PROBE_MEM is not visible in a bpftool xlated dump, as bpf_insn_prepare_dump() rewrites it back to BPF_MEM. A PTR_TRUSTED pointer is deliberately not on the list. Such a load is not converted either, but it does not need to be, since the pointer is guaranteed live, so load-acquire from it stays allowed. The check is gated on BPF_LOAD_ACQ so that atomic RMW and store-release error messages are unchanged; writes (RMW / store-release) to such pointers are already rejected elsewhere, so only load-acquire needs this.
Severity
No CVSS data available.
Impacted products
Vendor Product Version CPE status
Linux Linux Affected: 880442305a3908589bf4d6fc1d79edb577ee497c , < c4c8de3bf48d3756ab0f910fe5cc4937d70efdcd (git)
Affected: 880442305a3908589bf4d6fc1d79edb577ee497c , < 5f8ade6e9b7931fc9697394f1b2c4ae833f5ac18 (git)
Affected: 880442305a3908589bf4d6fc1d79edb577ee497c , < 7db0a00445f1a40bacfe9b747405c11cb5f10fc9 (git)
guessed Create a notification for this product.
Linux Linux Affected: 6.15
Unaffected: 0 , < 6.15 (semver)
Unaffected: 6.18.52 , ≤ 6.18.* (semver)
Unaffected: 7.2.6 , ≤ 7.2.* (semver)
Unaffected: 7.3-rc1 , ≤ * (original_commit_for_fix)
guessed Create a notification for this product.
Show details on NVD website

{
  "containers": {
    "cna": {
      "affected": [
        {
          "defaultStatus": "unaffected",
          "product": "Linux",
          "programFiles": [
            "kernel/bpf/verifier.c"
          ],
          "repo": "https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git",
          "vendor": "Linux",
          "versions": [
            {
              "lessThan": "c4c8de3bf48d3756ab0f910fe5cc4937d70efdcd",
              "status": "affected",
              "version": "880442305a3908589bf4d6fc1d79edb577ee497c",
              "versionType": "git"
            },
            {
              "lessThan": "5f8ade6e9b7931fc9697394f1b2c4ae833f5ac18",
              "status": "affected",
              "version": "880442305a3908589bf4d6fc1d79edb577ee497c",
              "versionType": "git"
            },
            {
              "lessThan": "7db0a00445f1a40bacfe9b747405c11cb5f10fc9",
              "status": "affected",
              "version": "880442305a3908589bf4d6fc1d79edb577ee497c",
              "versionType": "git"
            }
          ]
        },
        {
          "defaultStatus": "affected",
          "product": "Linux",
          "programFiles": [
            "kernel/bpf/verifier.c"
          ],
          "repo": "https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git",
          "vendor": "Linux",
          "versions": [
            {
              "status": "affected",
              "version": "6.15"
            },
            {
              "lessThan": "6.15",
              "status": "unaffected",
              "version": "0",
              "versionType": "semver"
            },
            {
              "lessThanOrEqual": "6.18.*",
              "status": "unaffected",
              "version": "6.18.52",
              "versionType": "semver"
            },
            {
              "lessThanOrEqual": "7.2.*",
              "status": "unaffected",
              "version": "7.2.6",
              "versionType": "semver"
            },
            {
              "lessThanOrEqual": "*",
              "status": "unaffected",
              "version": "7.3-rc1",
              "versionType": "original_commit_for_fix"
            }
          ]
        }
      ],
      "cpeApplicability": [
        {
          "nodes": [
            {
              "cpeMatch": [
                {
                  "criteria": "cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:*",
                  "versionEndExcluding": "6.18.52",
                  "versionStartIncluding": "6.15",
                  "vulnerable": true
                },
                {
                  "criteria": "cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:*",
                  "versionEndExcluding": "7.2.6",
                  "versionStartIncluding": "6.15",
                  "vulnerable": true
                },
                {
                  "criteria": "cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:*",
                  "versionEndExcluding": "7.3-rc1",
                  "versionStartIncluding": "6.15",
                  "vulnerable": true
                }
              ],
              "negate": false,
              "operator": "OR"
            }
          ]
        }
      ],
      "descriptions": [
        {
          "lang": "en",
          "value": "In the Linux kernel, the following vulnerability has been resolved:\n\nbpf: Reject load-acquire from pointers requiring fault protection\n\nA BPF_LOAD_ACQ is not rewritten to a BPF_PROBE_MEM load by the verifier,\nunlike a regular BPF_LDX, so the JIT emits a plain load with no exception\ntable entry and a fault panics the kernel instead of being handled.\n\nReject the source pointer types that a BPF_LDX would have had that fault\nprotection applied to, i.e. the ones bpf_convert_ctx_accesses() turns\ninto BPF_PROBE_MEM: a bare PTR_TO_BTF_ID, PTR_TO_BTF_ID | PTR_UNTRUSTED,\nPTR_TO_BTF_ID | MEM_ALLOC | PTR_UNTRUSTED and PTR_TO_MEM | MEM_RDONLY |\nPTR_UNTRUSTED.\n\nThis is reachable e.g. by loading -\u003emm out of a trusted task_struct\nyields an untrusted pointer to mm_struct, and it is NULL for a kernel\nthread:\n\n  [...]\n  SEC(\"tp_btf/sched_switch\")\n  int BPF_PROG(demo, bool preempt, struct task_struct *prev,\n               struct task_struct *next)\n  {\n      struct mm_struct *mm = next-\u003emm;  /* untrusted */\n\n      out_ldx = (__u64)mm-\u003epgd;         /* BPF_LDX      */\n      out_acq = load_acquire(\u0026mm-\u003epgd); /* BPF_LOAD_ACQ */\n      return 0;\n  }\n  [...]\n\nBoth dereference the same pointer, but only the BPF_LDX is protected\n(x86-64 JIT, jump targets shown prog-relative):\n\n  [...]\n  ; out_ldx = (__u64)mm-\u003epgd;\n  17:   movq    $-10485760, %r10\n  1e:   movq    %rsi, %r11\n  21:   addq    $184, %r11\n  28:   subq    %r10, %r11\n  2b:   movabsq $140737498841088, %r10\n  35:   cmpq    %r10, %r11\n  38:   ja      0x3e                 \u003c-- kernel addr?\n  3a:   xorl    %edi, %edi           \u003c-- no: dst = 0, skip the load\n  3c:   jmp     0x45\n  3e:   movq    184(%rsi), %rdi      \u003c-- yes: load + extable entry\n  [...]\n  ; load_acquire(\u0026mm-\u003epgd)\n  53:\tmovq    %rsi, %rdi\n  56:\tmovq    184(%rdi), %rax       \u003c-- no check, no extable entry\n  [...]\n\nNote that BPF_PROBE_MEM is not visible in a bpftool xlated dump, as\nbpf_insn_prepare_dump() rewrites it back to BPF_MEM.\n\nA PTR_TRUSTED pointer is deliberately not on the list. Such a load is\nnot converted either, but it does not need to be, since the pointer is\nguaranteed live, so load-acquire from it stays allowed.\n\nThe check is gated on BPF_LOAD_ACQ so that atomic RMW and store-release\nerror messages are unchanged; writes (RMW / store-release) to such\npointers are already rejected elsewhere, so only load-acquire needs this."
        }
      ],
      "providerMetadata": {
        "dateUpdated": "2026-09-17T16:08:03.996Z",
        "orgId": "416baaa9-dc9f-4396-8d5f-8c081fb06d67",
        "shortName": "Linux"
      },
      "references": [
        {
          "url": "https://git.kernel.org/stable/c/c4c8de3bf48d3756ab0f910fe5cc4937d70efdcd"
        },
        {
          "url": "https://git.kernel.org/stable/c/5f8ade6e9b7931fc9697394f1b2c4ae833f5ac18"
        },
        {
          "url": "https://git.kernel.org/stable/c/7db0a00445f1a40bacfe9b747405c11cb5f10fc9"
        }
      ],
      "title": "bpf: Reject load-acquire from pointers requiring fault protection",
      "x_generator": {
        "engine": "bippy-1.2.0"
      }
    }
  },
  "cveMetadata": {
    "assignerOrgId": "416baaa9-dc9f-4396-8d5f-8c081fb06d67",
    "assignerShortName": "Linux",
    "cveId": "CVE-2026-90269",
    "datePublished": "2026-09-17T16:08:03.996Z",
    "dateReserved": "2026-09-11T19:38:34.796Z",
    "dateUpdated": "2026-09-17T16:08:03.996Z",
    "state": "PUBLISHED"
  },
  "dataType": "CVE_RECORD",
  "dataVersion": "5.2",
  "vulnerability-lookup:meta": {
    "epss": {
      "cve": "CVE-2026-90269",
      "date": "2026-09-29",
      "epss": "0.00206",
      "percentile": "0.0961"
    },
    "nvd": {
      "cve": {
        "affected": [
          {
            "affectedData": [
              {
                "defaultStatus": "unaffected",
                "product": "Linux",
                "programFiles": [
                  "kernel/bpf/verifier.c"
                ],
                "repo": "https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git",
                "vendor": "Linux",
                "versions": [
                  {
                    "lessThan": "c4c8de3bf48d3756ab0f910fe5cc4937d70efdcd",
                    "status": "affected",
                    "version": "880442305a3908589bf4d6fc1d79edb577ee497c",
                    "versionType": "git"
                  },
                  {
                    "lessThan": "5f8ade6e9b7931fc9697394f1b2c4ae833f5ac18",
                    "status": "affected",
                    "version": "880442305a3908589bf4d6fc1d79edb577ee497c",
                    "versionType": "git"
                  },
                  {
                    "lessThan": "7db0a00445f1a40bacfe9b747405c11cb5f10fc9",
                    "status": "affected",
                    "version": "880442305a3908589bf4d6fc1d79edb577ee497c",
                    "versionType": "git"
                  }
                ]
              },
              {
                "defaultStatus": "affected",
                "product": "Linux",
                "programFiles": [
                  "kernel/bpf/verifier.c"
                ],
                "repo": "https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git",
                "vendor": "Linux",
                "versions": [
                  {
                    "status": "affected",
                    "version": "6.15"
                  },
                  {
                    "lessThan": "6.15",
                    "status": "unaffected",
                    "version": "0",
                    "versionType": "semver"
                  },
                  {
                    "lessThanOrEqual": "6.18.*",
                    "status": "unaffected",
                    "version": "6.18.52",
                    "versionType": "semver"
                  },
                  {
                    "lessThanOrEqual": "7.2.*",
                    "status": "unaffected",
                    "version": "7.2.6",
                    "versionType": "semver"
                  },
                  {
                    "lessThanOrEqual": "*",
                    "status": "unaffected",
                    "version": "7.3-rc1",
                    "versionType": "original_commit_for_fix"
                  }
                ]
              }
            ],
            "source": "416baaa9-dc9f-4396-8d5f-8c081fb06d67"
          }
        ],
        "cveTags": [],
        "descriptions": [
          {
            "lang": "en",
            "value": "In the Linux kernel, the following vulnerability has been resolved:\n\nbpf: Reject load-acquire from pointers requiring fault protection\n\nA BPF_LOAD_ACQ is not rewritten to a BPF_PROBE_MEM load by the verifier,\nunlike a regular BPF_LDX, so the JIT emits a plain load with no exception\ntable entry and a fault panics the kernel instead of being handled.\n\nReject the source pointer types that a BPF_LDX would have had that fault\nprotection applied to, i.e. the ones bpf_convert_ctx_accesses() turns\ninto BPF_PROBE_MEM: a bare PTR_TO_BTF_ID, PTR_TO_BTF_ID | PTR_UNTRUSTED,\nPTR_TO_BTF_ID | MEM_ALLOC | PTR_UNTRUSTED and PTR_TO_MEM | MEM_RDONLY |\nPTR_UNTRUSTED.\n\nThis is reachable e.g. by loading -\u003emm out of a trusted task_struct\nyields an untrusted pointer to mm_struct, and it is NULL for a kernel\nthread:\n\n  [...]\n  SEC(\"tp_btf/sched_switch\")\n  int BPF_PROG(demo, bool preempt, struct task_struct *prev,\n               struct task_struct *next)\n  {\n      struct mm_struct *mm = next-\u003emm;  /* untrusted */\n\n      out_ldx = (__u64)mm-\u003epgd;         /* BPF_LDX      */\n      out_acq = load_acquire(\u0026mm-\u003epgd); /* BPF_LOAD_ACQ */\n      return 0;\n  }\n  [...]\n\nBoth dereference the same pointer, but only the BPF_LDX is protected\n(x86-64 JIT, jump targets shown prog-relative):\n\n  [...]\n  ; out_ldx = (__u64)mm-\u003epgd;\n  17:   movq    $-10485760, %r10\n  1e:   movq    %rsi, %r11\n  21:   addq    $184, %r11\n  28:   subq    %r10, %r11\n  2b:   movabsq $140737498841088, %r10\n  35:   cmpq    %r10, %r11\n  38:   ja      0x3e                 \u003c-- kernel addr?\n  3a:   xorl    %edi, %edi           \u003c-- no: dst = 0, skip the load\n  3c:   jmp     0x45\n  3e:   movq    184(%rsi), %rdi      \u003c-- yes: load + extable entry\n  [...]\n  ; load_acquire(\u0026mm-\u003epgd)\n  53:\tmovq    %rsi, %rdi\n  56:\tmovq    184(%rdi), %rax       \u003c-- no check, no extable entry\n  [...]\n\nNote that BPF_PROBE_MEM is not visible in a bpftool xlated dump, as\nbpf_insn_prepare_dump() rewrites it back to BPF_MEM.\n\nA PTR_TRUSTED pointer is deliberately not on the list. Such a load is\nnot converted either, but it does not need to be, since the pointer is\nguaranteed live, so load-acquire from it stays allowed.\n\nThe check is gated on BPF_LOAD_ACQ so that atomic RMW and store-release\nerror messages are unchanged; writes (RMW / store-release) to such\npointers are already rejected elsewhere, so only load-acquire needs this."
          }
        ],
        "id": "CVE-2026-90269",
        "lastModified": "2026-09-17T17:17:23.460",
        "metrics": {},
        "published": "2026-09-17T17:17:23.460",
        "references": [
          {
            "source": "416baaa9-dc9f-4396-8d5f-8c081fb06d67",
            "url": "https://git.kernel.org/stable/c/5f8ade6e9b7931fc9697394f1b2c4ae833f5ac18"
          },
          {
            "source": "416baaa9-dc9f-4396-8d5f-8c081fb06d67",
            "url": "https://git.kernel.org/stable/c/7db0a00445f1a40bacfe9b747405c11cb5f10fc9"
          },
          {
            "source": "416baaa9-dc9f-4396-8d5f-8c081fb06d67",
            "url": "https://git.kernel.org/stable/c/c4c8de3bf48d3756ab0f910fe5cc4937d70efdcd"
          }
        ],
        "sourceIdentifier": "416baaa9-dc9f-4396-8d5f-8c081fb06d67",
        "vulnStatus": "Received"
      }
    },
    "suse_vex": {
      "aggregate_severity": "moderate",
      "current_release_date": "2026-09-22T16:29:40Z",
      "cve": "CVE-2026-90269",
      "id": "CVE-2026-90269",
      "initial_release_date": "2026-09-22T16:29:40Z",
      "product_status:known_affected": "12",
      "product_status:known_not_affected": "335",
      "source": "SUSE CSAF VEX",
      "status": "interim",
      "title": "SUSE CVE CVE-2026-90269",
      "url": "https://ftp.suse.com/pub/projects/security/csaf-vex/cve-2026-90269.json",
      "version": "2"
    }
  }
}



Log in or create an account to share your comment.




Tags
Taxonomy of the tags.


Loading…

Loading…

Loading…

Forecast uses a logistic model when the trend is rising, or an exponential decay model when the trend is falling. Fitted via linearized least squares.

Sightings

Author Source Type Date Other

Nomenclature

  • Seen: The vulnerability was mentioned, discussed, or observed by the user.
  • Confirmed: The vulnerability has been validated from an analyst's perspective.
  • Published Proof of Concept: A public proof of concept is available for this vulnerability.
  • Exploited: The vulnerability was observed as exploited by the user who reported the sighting.
  • Patched: The vulnerability was observed as successfully patched by the user who reported the sighting.
  • Not exploited: The vulnerability was not observed as exploited by the user who reported the sighting.
  • Not confirmed: The user expressed doubt about the validity of the vulnerability.
  • Not patched: The vulnerability was not observed as successfully patched by the user who reported the sighting.

Loading…

Loading…

Loading…

Related by attack behaviour

Vulnerabilities whose description is nearest to this one in the vector space of the CIRCL/vulnerability-attack-technique-biencoder model. This is a similarity search over the bi-encoder space (plain cosine), not a classification, and it has no measured accuracy.


Loading…