← All CVEs NewScan detects
high

CVE-2026-89013

Dolibarr authorization bypass - hashp=shared skips token validation in document.php and viewimage.php, giving an unauthenticated caller arbitrary file read

Severity
high
Affected product
Dolibarr
Affected versions
Dolibarr ≥ 23.0.4, < 24.0.1
Fixed in
Dolibarr 24.0.1
Added to NewScan
2026-09-14
Detected by
NewScan — free, self-hosted

How NewScan reports it

COMPONENT VERSION RANGE

NewScan fingerprints Dolibarr from its response and reports this CVE when the detected version falls inside the affected range below.

Added 2026-09-13. CVSS 8.7 (v4) / 7.5 (v3.1), AV:N/PR:N - no account needed. htdocs/document.php and htdocs/viewimage.php treat the literal value `hashp=shared` as satisfying their authorization condition while simultaneously skipping the token check, so the share-link path becomes an open file reader: NVD names application logs, uploaded business documents, database backups carrying password hashes, and files belonging to OTHER multicompany entities - i.e. it crosses the tenant boundary on a multi-entity install. Bounds are NVD's own words taken literally, `Dolibarr 23.0.4 before 24.0.1`, with `ge` inclusive and `lt` exclusive; NVD has published NO cpeMatch configuration for this id yet (checked live 2026-09-13, the record carries descriptions and metrics only), so the description IS the range statement and a wider `lt` with no lower bound would call a patched 21.x vulnerable. VERSION-MATCH ONLY, deliberately: the bug is directly observable in-band - one GET with hashp=shared - but proving it means reading a real customer file out of a real install, which is exactly the line reproduce-before-record does not cross. The direct-oracle version is in docs/backlog.md, not here. Version source is the new Dolibarr tech_signatures body row, MEASURED live 2026-09-13 against dolibarr/dolibarr 24.0.0 on loopback (DOL_VERSION inline in the anonymous login page); 24.0.0 sits inside this row's range, so that container is the AFFECTED arm and the row was watched firing on it. The patched arm could not be measured live - Docker Hub publishes no 24.0.1 tag yet (only 24, 24.0.0, 24.0.0-php8.2, checked the same day) - so the boundary is pinned as fixtures on both sides of 24.0.1 in tests/integration/tech_version_from_checks.py, and a live 21.0.1 was run as the BELOW-RANGE arm to prove the `ge` bound abstains rather than assuming it.

References

Scan for this yourself — local, in-band scanning is free.

Get NewScan (FREE) →