Bug 1672419 (CVE-2019-7310)
| Summary: | CVE-2019-7310 poppler: heap-based buffer over-read in XRef::getEntry in XRef.cc | ||
|---|---|---|---|
| Product: | [Other] Security Response | Reporter: | Laura Pardo <lpardo> |
| Component: | vulnerability | Assignee: | Red Hat Product Security <security-response-team> |
| Status: | CLOSED ERRATA | QA Contact: | |
| Severity: | medium | Docs Contact: | |
| Priority: | medium | ||
| Version: | unspecified | CC: | mkasik |
| Target Milestone: | --- | Keywords: | Security |
| Target Release: | --- | ||
| Hardware: | All | ||
| OS: | Linux | ||
| Whiteboard: | |||
| Fixed In Version: | Doc Type: | If docs needed, set a value | |
| Doc Text: | Story Points: | --- | |
| Clone Of: | Environment: | ||
| Last Closed: | 2019-08-06 13:21:49 UTC | Type: | --- |
| Regression: | --- | Mount Type: | --- |
| Documentation: | --- | CRM: | |
| Verified Versions: | Category: | --- | |
| oVirt Team: | --- | RHEL 7.3 requirements from Atomic Host: | |
| Cloudforms Team: | --- | Target Upstream Version: | |
| Embargoed: | |||
| Bug Depends On: | 1672420, 1672421, 1673699, 1673700, 1717779 | ||
| Bug Blocks: | 1672422 | ||
|
Description
Laura Pardo
2019-02-04 21:32:38 UTC
Created mingw-poppler tracking bugs for this issue: Affects: fedora-all [bug 1672421] Created poppler tracking bugs for this issue: Affects: fedora-all [bug 1672420] Easy to reproduce:
```
==28176== Invalid read of size 4
==28176== at 0x4FA62B1: XRef::getEntry(int, bool) (XRef.cc:1609)
==28176== by 0x4F89FF6: Parser::makeStream(Object*, unsigned char*, CryptAlgorithm, int, int, int, int, bool) (Parser.cc:207)
==28176== by 0x4F8A8F7: Parser::getObj(Object*, bool, unsigned char*, CryptAlgorithm, int, int, int, int, bool) (Parser.cc:131)
==28176== by 0x4F6FA84: Hints::readTables(BaseStream*, Linearization*, XRef*, SecurityHandler*) (Hints.cc:145)
==28176== by 0x4F8B474: PDFDoc::getHints() (PDFDoc.cc:607)
==28176== by 0x4F90518: PDFDoc::parsePage(int) (PDFDoc.cc:1890)
==28176== by 0x4F90769: PDFDoc::getPage(int) (PDFDoc.cc:1931)
==28176== by 0x4087C5: getPageMediaWidth (PDFDoc.h:126)
==28176== by 0x4087C5: main (pdftocairo.cc:1014)
==28176== Address 0x9ffd444 is 28 bytes before a block of size 16 in arena "client"
==28176==
==28176== Invalid read of size 4
==28176== at 0x4F8A003: Parser::makeStream(Object*, unsigned char*, CryptAlgorithm, int, int, int, int, bool) (Parser.cc:205)
==28176== by 0x4F8A8F7: Parser::getObj(Object*, bool, unsigned char*, CryptAlgorithm, int, int, int, int, bool) (Parser.cc:131)
==28176== by 0x4F6FA84: Hints::readTables(BaseStream*, Linearization*, XRef*, SecurityHandler*) (Hints.cc:145)
==28176== by 0x4F8B474: PDFDoc::getHints() (PDFDoc.cc:607)
==28176== by 0x4F90518: PDFDoc::parsePage(int) (PDFDoc.cc:1890)
==28176== by 0x4F90769: PDFDoc::getPage(int) (PDFDoc.cc:1931)
==28176== by 0x4087C5: getPageMediaWidth (PDFDoc.h:126)
==28176== by 0x4087C5: main (pdftocairo.cc:1014)
==28176== Address 0x9ffd448 is 24 bytes before a block of size 5 free'd
==28176== at 0x4C2ACBD: free (vg_replace_malloc.c:530)
==28176== by 0x4F96037: FlateStream::~FlateStream() (Stream.cc:4521)
==28176== by 0x4F96078: FlateStream::~FlateStream() (Stream.cc:4524)
==28176== by 0x4F83E73: Object::free() (Object.cc:145)
==28176== by 0x4FA5CBB: XRef::readXRef(long long*, std::vector<long long, std::allocator<long long> >*, std::vector<int, std::allocator<int> >*) (XRef.cc:562)
==28176== by 0x4FA5DEF: XRef::XRef(BaseStream*, long long, long long, bool*, bool) (XRef.cc:342)
==28176== by 0x4F8F327: PDFDoc::setup(GooString*, GooString*) (PDFDoc.cc:260)
==28176== by 0x4F8F627: PDFDoc::PDFDoc(GooString*, GooString*, GooString*, void*) (PDFDoc.cc:165)
==28176== by 0x4F829E3: LocalPDFDocBuilder::buildPDFDoc(GooString const&, GooString*, GooString*, void*) (LocalPDFDocBuilder.cc:31)
```
Looks like a negative index can get passed to XRef::getEntry by an attacker.
```c
XRefEntry *XRef::getEntry(int i, GBool complainIfMissing)
{
if (i >= size || entries[i].type == xrefEntryNone) {
if ((!xRefStream) && mainXRefEntriesOffset) {
if (!parseEntry(mainXRefEntriesOffset + 20*i, &entries[i])) {
error(errSyntaxError, -1, "Failed to parse XRef entry [{0:d}].", i);
}
} else {
...
return &entries[i];
```
Presumably, valgrind/ASAN is asserting when the entries[i] load occurs. Could then return a negative entry back to the caller.
Unclear if this could lead to code execution, but rated the CVSS a bit higher to account for my uncertainty.
This issue has been addressed in the following products: Red Hat Enterprise Linux 7 Via RHSA-2019:2022 https://access.redhat.com/errata/RHSA-2019:2022 This bug is now closed. Further updates for individual products will be reflected on the CVE page(s): https://access.redhat.com/security/cve/cve-2019-7310 This issue has been addressed in the following products: Red Hat Enterprise Linux 8 Via RHSA-2019:2713 https://access.redhat.com/errata/RHSA-2019:2713 |