{"api_version":"1","generated_at":"2026-09-17T23:17:25+00:00","cve":"CVE-2026-86861","urls":{"html":"https://cve.report/CVE-2026-86861","api":"https://cve.report/api/cve/CVE-2026-86861.json","docs":"https://cve.report/api","cve_org":"https://www.cve.org/CVERecord?id=CVE-2026-86861","nvd":"https://nvd.nist.gov/vuln/detail/CVE-2026-86861"},"summary":{"title":"pgAdmin 4: File Manager save_file writes through a symbolic link planted after the containment check","description":"pgAdmin 4's File Manager save_file endpoint, which backs saving from the Query Tool and ERD, validated the requested path with Filemanager.check_access_permission() and then opened the file for writing with a plain open() call. CVE-2026-7819 had previously hardened the separate file upload path by opening its target with O_NOFOLLOW, so that the kernel refuses to follow a symbolic link at the final path component, but save_file was left on an unprotected open(). A symbolic link already present when the check ran was rejected by the check itself; the remaining exposure was a link substituted at the final path component in the interval between the check and the write, at which point the write followed the link and landed outside the user's storage directory, creating or overwriting an arbitrary file as the operating-system account running pgAdmin.\n\nExploitation requires the ability to create or replace a symbolic link inside the requesting user's storage directory. pgAdmin exposes no interface that creates symbolic links, so this requires filesystem access to the pgAdmin host or to a shared or network-mounted storage backend, together with winning the timing window. The reporter did not achieve a write against a released version, having attempted approximately 63,000 racing requests without success; the reported defect is the uncovered write path rather than a demonstrated sandbox escape.\n\nThe fix routes save_file's write through the same O_NOFOLLOW-protected helper already used by the upload path, so both File Manager write sinks carry identical kernel-enforced protection, and reports a symbolic-link refusal explicitly instead of surfacing the underlying system error text. Note that files created by save_file are now given mode 0600, inheriting the behaviour introduced for uploads. The protection covers the final path component; substitution of an intermediate directory component is not addressed by this change.\n\nThis issue affects pgAdmin 4: from the introduction of the containment check in the File Manager save path before 9.18.","state":"PUBLISHED","assigner":"PostgreSQL","published_at":"2026-09-17 16:18:17","updated_at":"2026-09-17 20:18:50"},"problem_types":["CWE-59","CWE-367","CWE-367 CWE-367 Time-of-check Time-of-use (TOCTOU) Race Condition","CWE-59 CWE-59 Improper Link Resolution Before File Access ('Link Following')"],"metrics":[{"version":"4.0","source":"f86ef6dc-4d3a-42ad-8f28-e6d5547a5007","type":"Secondary","score":"6","severity":"MEDIUM","vector":"CVSS:4.0/AV:N/AC:H/AT:P/PR:L/UI:N/VC:N/VI:H/VA:L/SC:N/SI:N/SA:N/E:X/CR:X/IR:X/AR:X/MAV:X/MAC:X/MAT:X/MPR:X/MUI:X/MVC:X/MVI:X/MVA:X/MSC:X/MSI:X/MSA:X/S:X/AU:X/R:X/V:X/RE:X/U:X","data":{"version":"4.0","vectorString":"CVSS:4.0/AV:N/AC:H/AT:P/PR:L/UI:N/VC:N/VI:H/VA:L/SC:N/SI:N/SA:N/E:X/CR:X/IR:X/AR:X/MAV:X/MAC:X/MAT:X/MPR:X/MUI:X/MVC:X/MVI:X/MVA:X/MSC:X/MSI:X/MSA:X/S:X/AU:X/R:X/V:X/RE:X/U:X","baseScore":6,"baseSeverity":"MEDIUM","attackVector":"NETWORK","attackComplexity":"HIGH","attackRequirements":"PRESENT","privilegesRequired":"LOW","userInteraction":"NONE","vulnConfidentialityImpact":"NONE","vulnIntegrityImpact":"HIGH","vulnAvailabilityImpact":"LOW","subConfidentialityImpact":"NONE","subIntegrityImpact":"NONE","subAvailabilityImpact":"NONE","exploitMaturity":"NOT_DEFINED","confidentialityRequirement":"NOT_DEFINED","integrityRequirement":"NOT_DEFINED","availabilityRequirement":"NOT_DEFINED","modifiedAttackVector":"NOT_DEFINED","modifiedAttackComplexity":"NOT_DEFINED","modifiedAttackRequirements":"NOT_DEFINED","modifiedPrivilegesRequired":"NOT_DEFINED","modifiedUserInteraction":"NOT_DEFINED","modifiedVulnConfidentialityImpact":"NOT_DEFINED","modifiedVulnIntegrityImpact":"NOT_DEFINED","modifiedVulnAvailabilityImpact":"NOT_DEFINED","modifiedSubConfidentialityImpact":"NOT_DEFINED","modifiedSubIntegrityImpact":"NOT_DEFINED","modifiedSubAvailabilityImpact":"NOT_DEFINED","Safety":"NOT_DEFINED","Automatable":"NOT_DEFINED","Recovery":"NOT_DEFINED","valueDensity":"NOT_DEFINED","vulnerabilityResponseEffort":"NOT_DEFINED","providerUrgency":"NOT_DEFINED"}},{"version":"4.0","source":"CNA","type":"CVSS","score":"6","severity":"MEDIUM","vector":"CVSS:4.0/AV:N/AC:H/AT:P/PR:L/UI:N/VC:N/VI:H/VA:L/SC:N/SI:N/SA:N","data":{"baseScore":6,"baseSeverity":"MEDIUM","vectorString":"CVSS:4.0/AV:N/AC:H/AT:P/PR:L/UI:N/VC:N/VI:H/VA:L/SC:N/SI:N/SA:N","version":"4.0"}},{"version":"3.1","source":"f86ef6dc-4d3a-42ad-8f28-e6d5547a5007","type":"Secondary","score":"5.9","severity":"MEDIUM","vector":"CVSS:3.1/AV:N/AC:H/PR:L/UI:N/S:U/C:N/I:H/A:L","data":{"version":"3.1","vectorString":"CVSS:3.1/AV:N/AC:H/PR:L/UI:N/S:U/C:N/I:H/A:L","baseScore":5.9,"baseSeverity":"MEDIUM","attackVector":"NETWORK","attackComplexity":"HIGH","privilegesRequired":"LOW","userInteraction":"NONE","scope":"UNCHANGED","confidentialityImpact":"NONE","integrityImpact":"HIGH","availabilityImpact":"LOW"}},{"version":"3.1","source":"CNA","type":"CVSS","score":"5.9","severity":"MEDIUM","vector":"CVSS:3.1/AV:N/AC:H/PR:L/UI:N/S:U/C:N/I:H/A:L","data":{"attackComplexity":"HIGH","attackVector":"NETWORK","availabilityImpact":"LOW","baseScore":5.9,"baseSeverity":"MEDIUM","confidentialityImpact":"NONE","integrityImpact":"HIGH","privilegesRequired":"LOW","scope":"UNCHANGED","userInteraction":"NONE","vectorString":"CVSS:3.1/AV:N/AC:H/PR:L/UI:N/S:U/C:N/I:H/A:L","version":"3.1"}}],"references":[{"url":"https://github.com/pgadmin-org/pgadmin4/issues/10385","name":"https://github.com/pgadmin-org/pgadmin4/issues/10385","refsource":"f86ef6dc-4d3a-42ad-8f28-e6d5547a5007","tags":[],"title":"","mime":"","httpstatus":"","archivestatus":"0"},{"url":"https://www.cve.org/CVERecord?id=CVE-2026-86861","name":"CVE Program record","refsource":"CVE.ORG","tags":["canonical"]},{"url":"https://nvd.nist.gov/vuln/detail/CVE-2026-86861","name":"NVD vulnerability detail","refsource":"NVD","tags":["canonical","analysis"]}],"affected":[{"source":"CNA","vendor":"pgadmin.org","product":"pgAdmin 4","version":"affected 9.18 custom","platforms":[]}],"timeline":[],"solutions":[],"workarounds":[],"exploits":[],"credits":[{"source":"CNA","value":"sec-rex <secrex837@gmail.com>","lang":"en"},{"source":"CNA","value":"Dave Page <dpage@pgadmin.org>","lang":"en"},{"source":"CNA","value":"Ashesh Vashi <ashesh.vashi@enterprisedb.com>","lang":"en"}],"nvd_cpes":[],"vendor_comments":[],"enrichments":{"kev":null,"epss":null,"legacy_qids":[]},"source_records":{"cve_program":{"containers":{"adp":[{"metrics":[{"other":{"content":{"id":"CVE-2026-86861","options":[{"Exploitation":"none"},{"Automatable":"no"},{"Technical Impact":"partial"}],"role":"CISA Coordinator","timestamp":"2026-09-17T19:18:06.282518Z","version":"2.0.3"},"type":"ssvc"}}],"providerMetadata":{"dateUpdated":"2026-09-17T19:18:18.115Z","orgId":"134c704f-9b21-4f2e-91b3-4a467353bcc0","shortName":"CISA-ADP"},"title":"CISA ADP Vulnrichment"}],"cna":{"affected":[{"defaultStatus":"unaffected","modules":["File Manager"],"product":"pgAdmin 4","programFiles":["https://github.com/pgadmin-org/pgadmin4/blob/master/web/pgadmin/misc/file_manager/__init__.py"],"repo":"https://github.com/pgadmin-org/pgadmin4","vendor":"pgadmin.org","versions":[{"lessThan":"9.18","status":"affected","version":"0","versionType":"custom"}]}],"credits":[{"lang":"en","type":"finder","value":"sec-rex <secrex837@gmail.com>"},{"lang":"en","type":"remediation developer","value":"Dave Page <dpage@pgadmin.org>"},{"lang":"en","type":"remediation reviewer","value":"Ashesh Vashi <ashesh.vashi@enterprisedb.com>"}],"descriptions":[{"lang":"en","value":"pgAdmin 4's File Manager save_file endpoint, which backs saving from the Query Tool and ERD, validated the requested path with Filemanager.check_access_permission() and then opened the file for writing with a plain open() call. CVE-2026-7819 had previously hardened the separate file upload path by opening its target with O_NOFOLLOW, so that the kernel refuses to follow a symbolic link at the final path component, but save_file was left on an unprotected open(). A symbolic link already present when the check ran was rejected by the check itself; the remaining exposure was a link substituted at the final path component in the interval between the check and the write, at which point the write followed the link and landed outside the user's storage directory, creating or overwriting an arbitrary file as the operating-system account running pgAdmin.\n\nExploitation requires the ability to create or replace a symbolic link inside the requesting user's storage directory. pgAdmin exposes no interface that creates symbolic links, so this requires filesystem access to the pgAdmin host or to a shared or network-mounted storage backend, together with winning the timing window. The reporter did not achieve a write against a released version, having attempted approximately 63,000 racing requests without success; the reported defect is the uncovered write path rather than a demonstrated sandbox escape.\n\nThe fix routes save_file's write through the same O_NOFOLLOW-protected helper already used by the upload path, so both File Manager write sinks carry identical kernel-enforced protection, and reports a symbolic-link refusal explicitly instead of surfacing the underlying system error text. Note that files created by save_file are now given mode 0600, inheriting the behaviour introduced for uploads. The protection covers the final path component; substitution of an intermediate directory component is not addressed by this change.\n\nThis issue affects pgAdmin 4: from the introduction of the containment check in the File Manager save path before 9.18."}],"metrics":[{"cvssV3_1":{"attackComplexity":"HIGH","attackVector":"NETWORK","availabilityImpact":"LOW","baseScore":5.9,"baseSeverity":"MEDIUM","confidentialityImpact":"NONE","integrityImpact":"HIGH","privilegesRequired":"LOW","scope":"UNCHANGED","userInteraction":"NONE","vectorString":"CVSS:3.1/AV:N/AC:H/PR:L/UI:N/S:U/C:N/I:H/A:L","version":"3.1"},"format":"CVSS","scenarios":[{"lang":"en","value":"Threat model: an authenticated pgAdmin user who can also create or replace a symbolic link inside their own File Manager storage directory, which requires filesystem access to the pgAdmin host or to a shared or network-mounted storage backend, since pgAdmin exposes no primitive that creates symbolic links. Attack Complexity is High: the attacker must both obtain that separate primitive and win a narrow race between the containment check and the write, and the reporter did not succeed in approximately 63,000 attempts against a released version. Integrity is High because a successful write creates or overwrites an arbitrary file as the account running pgAdmin. Confidentiality is None, as the flaw permits writing but not reading. Availability is Low, reflecting that a chosen file may be clobbered without a general loss of service. Scope is Unchanged, consistent with the equivalent argument-injection write path, because the write occurs with the authority pgAdmin already holds."}]},{"cvssV4_0":{"baseScore":6,"baseSeverity":"MEDIUM","vectorString":"CVSS:4.0/AV:N/AC:H/AT:P/PR:L/UI:N/VC:N/VI:H/VA:L/SC:N/SI:N/SA:N","version":"4.0"},"format":"CVSS","scenarios":[{"lang":"en","value":"Same reasoning as the CVSS 3.1 entry. AT:P records that exploitation depends on a race condition the attacker does not control and on a symbolic-link primitive obtained outside pgAdmin. VI:H for arbitrary file creation and overwrite as the pgAdmin account, VC:N because nothing is read, VA:L for the loss of a clobbered file. SC:N/SI:N/SA:N because no distinct subsequent system is compromised by the flaw itself."}]}],"problemTypes":[{"descriptions":[{"cweId":"CWE-367","description":"CWE-367 Time-of-check Time-of-use (TOCTOU) Race Condition","lang":"en","type":"CWE"},{"cweId":"CWE-59","description":"CWE-59 Improper Link Resolution Before File Access ('Link Following')","lang":"en","type":"CWE"}]}],"providerMetadata":{"dateUpdated":"2026-09-17T15:30:51.232Z","orgId":"f86ef6dc-4d3a-42ad-8f28-e6d5547a5007","shortName":"PostgreSQL"},"references":[{"tags":["issue-tracking"],"url":"https://github.com/pgadmin-org/pgadmin4/issues/10385"}],"source":{"discovery":"EXTERNAL"},"title":"pgAdmin 4: File Manager save_file writes through a symbolic link planted after the containment check"}},"cveMetadata":{"assignerOrgId":"f86ef6dc-4d3a-42ad-8f28-e6d5547a5007","assignerShortName":"PostgreSQL","cveId":"CVE-2026-86861","datePublished":"2026-09-17T15:30:51.232Z","dateReserved":"2026-09-08T15:47:04.229Z","dateUpdated":"2026-09-17T19:18:18.115Z","state":"PUBLISHED"},"dataType":"CVE_RECORD","dataVersion":"5.2"},"nvd":{"publishedDate":"2026-09-17 16:18:17","lastModifiedDate":"2026-09-17 20:18:50","problem_types":["CWE-59","CWE-367","CWE-367 CWE-367 Time-of-check Time-of-use (TOCTOU) Race Condition","CWE-59 CWE-59 Improper Link Resolution Before File Access ('Link Following')"],"metrics":{"cvssMetricV40":[{"source":"f86ef6dc-4d3a-42ad-8f28-e6d5547a5007","type":"Secondary","cvssData":{"version":"4.0","vectorString":"CVSS:4.0/AV:N/AC:H/AT:P/PR:L/UI:N/VC:N/VI:H/VA:L/SC:N/SI:N/SA:N/E:X/CR:X/IR:X/AR:X/MAV:X/MAC:X/MAT:X/MPR:X/MUI:X/MVC:X/MVI:X/MVA:X/MSC:X/MSI:X/MSA:X/S:X/AU:X/R:X/V:X/RE:X/U:X","baseScore":6,"baseSeverity":"MEDIUM","attackVector":"NETWORK","attackComplexity":"HIGH","attackRequirements":"PRESENT","privilegesRequired":"LOW","userInteraction":"NONE","vulnConfidentialityImpact":"NONE","vulnIntegrityImpact":"HIGH","vulnAvailabilityImpact":"LOW","subConfidentialityImpact":"NONE","subIntegrityImpact":"NONE","subAvailabilityImpact":"NONE","exploitMaturity":"NOT_DEFINED","confidentialityRequirement":"NOT_DEFINED","integrityRequirement":"NOT_DEFINED","availabilityRequirement":"NOT_DEFINED","modifiedAttackVector":"NOT_DEFINED","modifiedAttackComplexity":"NOT_DEFINED","modifiedAttackRequirements":"NOT_DEFINED","modifiedPrivilegesRequired":"NOT_DEFINED","modifiedUserInteraction":"NOT_DEFINED","modifiedVulnConfidentialityImpact":"NOT_DEFINED","modifiedVulnIntegrityImpact":"NOT_DEFINED","modifiedVulnAvailabilityImpact":"NOT_DEFINED","modifiedSubConfidentialityImpact":"NOT_DEFINED","modifiedSubIntegrityImpact":"NOT_DEFINED","modifiedSubAvailabilityImpact":"NOT_DEFINED","Safety":"NOT_DEFINED","Automatable":"NOT_DEFINED","Recovery":"NOT_DEFINED","valueDensity":"NOT_DEFINED","vulnerabilityResponseEffort":"NOT_DEFINED","providerUrgency":"NOT_DEFINED"}}],"cvssMetricV31":[{"source":"f86ef6dc-4d3a-42ad-8f28-e6d5547a5007","type":"Secondary","cvssData":{"version":"3.1","vectorString":"CVSS:3.1/AV:N/AC:H/PR:L/UI:N/S:U/C:N/I:H/A:L","baseScore":5.9,"baseSeverity":"MEDIUM","attackVector":"NETWORK","attackComplexity":"HIGH","privilegesRequired":"LOW","userInteraction":"NONE","scope":"UNCHANGED","confidentialityImpact":"NONE","integrityImpact":"HIGH","availabilityImpact":"LOW"},"exploitabilityScore":1.6,"impactScore":4.2}],"ssvcV203":[{"source":"134c704f-9b21-4f2e-91b3-4a467353bcc0","ssvcData":{"timestamp":"2026-09-17T19:18:06.282518Z","id":"CVE-2026-86861","options":[{"exploitation":"none"},{"automatable":"no"},{"technicalImpact":"partial"}],"role":"CISA Coordinator","version":"2.0.3"}}]},"configurations":[]},"legacy_mitre":{"record":{"CveYear":"2026","CveId":"86861","Ordinal":"1","Title":"pgAdmin 4: File Manager save_file writes through a symbolic link","CVE":"CVE-2026-86861","Year":"2026"},"notes":[{"CveYear":"2026","CveId":"86861","Ordinal":"1","NoteData":"pgAdmin 4's File Manager save_file endpoint, which backs saving from the Query Tool and ERD, validated the requested path with Filemanager.check_access_permission() and then opened the file for writing with a plain open() call. CVE-2026-7819 had previously hardened the separate file upload path by opening its target with O_NOFOLLOW, so that the kernel refuses to follow a symbolic link at the final path component, but save_file was left on an unprotected open(). A symbolic link already present when the check ran was rejected by the check itself; the remaining exposure was a link substituted at the final path component in the interval between the check and the write, at which point the write followed the link and landed outside the user's storage directory, creating or overwriting an arbitrary file as the operating-system account running pgAdmin.\n\nExploitation requires the ability to create or replace a symbolic link inside the requesting user's storage directory. pgAdmin exposes no interface that creates symbolic links, so this requires filesystem access to the pgAdmin host or to a shared or network-mounted storage backend, together with winning the timing window. The reporter did not achieve a write against a released version, having attempted approximately 63,000 racing requests without success; the reported defect is the uncovered write path rather than a demonstrated sandbox escape.\n\nThe fix routes save_file's write through the same O_NOFOLLOW-protected helper already used by the upload path, so both File Manager write sinks carry identical kernel-enforced protection, and reports a symbolic-link refusal explicitly instead of surfacing the underlying system error text. Note that files created by save_file are now given mode 0600, inheriting the behaviour introduced for uploads. The protection covers the final path component; substitution of an intermediate directory component is not addressed by this change.\n\nThis issue affects pgAdmin 4: from the introduction of the containment check in the File Manager save path before 9.18.","Type":"Description","Title":"pgAdmin 4: File Manager save_file writes through a symbolic link"}]}}}