summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--core/fpdfapi/edit/cpdf_creator.cpp169
-rw-r--r--core/fpdfapi/edit/cpdf_creator.h29
2 files changed, 109 insertions, 89 deletions
diff --git a/core/fpdfapi/edit/cpdf_creator.cpp b/core/fpdfapi/edit/cpdf_creator.cpp
index f8beccbad3..94b8608c71 100644
--- a/core/fpdfapi/edit/cpdf_creator.cpp
+++ b/core/fpdfapi/edit/cpdf_creator.cpp
@@ -350,20 +350,20 @@ void CPDF_Creator::InitNewObjNumOffsets() {
}
}
-int32_t CPDF_Creator::WriteDoc_Stage1() {
- ASSERT(m_iStage > -1 || m_iStage < 20);
- if (m_iStage == 0) {
+CPDF_Creator::Stage CPDF_Creator::WriteDoc_Stage1() {
+ ASSERT(m_iStage > Stage::kInvalid || m_iStage < Stage::kInitWriteObjs20);
+ if (m_iStage == Stage::kInit0) {
if (!m_pParser || (m_bSecurityChanged && m_IsOriginal))
m_IsIncremental = false;
const CPDF_Dictionary* pDict = m_pDocument->GetRoot();
m_pMetadata = pDict ? pDict->GetDirectObjectFor("Metadata") : nullptr;
- m_iStage = 10;
+ m_iStage = Stage::kWriteHeader10;
}
- if (m_iStage == 10) {
+ if (m_iStage == Stage::kWriteHeader10) {
if (!m_IsIncremental) {
if (!m_Archive->WriteString("%PDF-1."))
- return -1;
+ return Stage::kInvalid;
int32_t version = 7;
if (m_FileVersion)
@@ -373,15 +373,15 @@ int32_t CPDF_Creator::WriteDoc_Stage1() {
if (!m_Archive->WriteDWord(version % 10) ||
!m_Archive->WriteString("\r\n%\xA1\xB3\xC5\xD7\r\n")) {
- return -1;
+ return Stage::kInvalid;
}
- m_iStage = 20;
+ m_iStage = Stage::kInitWriteObjs20;
} else {
m_SavedOffset = m_pParser->GetFileAccess()->GetSize();
- m_iStage = 15;
+ m_iStage = Stage::kWriteIncremental15;
}
}
- if (m_iStage == 15) {
+ if (m_iStage == Stage::kWriteIncremental15) {
if (m_IsOriginal && m_SavedOffset > 0) {
RetainPtr<IFX_SeekableReadStream> pSrcFile = m_pParser->GetFileAccess();
std::vector<uint8_t> buffer(4096);
@@ -391,10 +391,10 @@ int32_t CPDF_Creator::WriteDoc_Stage1() {
if (!pSrcFile->ReadBlock(buffer.data(),
m_Archive->CurrentOffset() - src_size,
block_size)) {
- return -1;
+ return Stage::kInvalid;
}
if (!m_Archive->WriteBlock(buffer.data(), block_size))
- return -1;
+ return Stage::kInvalid;
src_size -= block_size;
}
@@ -407,59 +407,61 @@ int32_t CPDF_Creator::WriteDoc_Stage1() {
m_ObjectOffsets[num] = m_pParser->GetObjectPositionOrZero(num);
}
}
- m_iStage = 20;
+ m_iStage = Stage::kInitWriteObjs20;
}
InitNewObjNumOffsets();
return m_iStage;
}
-int32_t CPDF_Creator::WriteDoc_Stage2() {
- ASSERT(m_iStage >= 20 || m_iStage < 30);
- if (m_iStage == 20) {
+CPDF_Creator::Stage CPDF_Creator::WriteDoc_Stage2() {
+ ASSERT(m_iStage >= Stage::kInitWriteObjs20 ||
+ m_iStage < Stage::kInitWriteXRefs80);
+ if (m_iStage == Stage::kInitWriteObjs20) {
if (!m_IsIncremental && m_pParser) {
m_CurObjNum = 0;
- m_iStage = 21;
+ m_iStage = Stage::kWriteOldObjs21;
} else {
- m_iStage = 25;
+ m_iStage = Stage::kInitWriteNewObjs25;
}
}
- if (m_iStage == 21) {
+ if (m_iStage == Stage::kWriteOldObjs21) {
if (!WriteOldObjs())
- return -1;
+ return Stage::kInvalid;
- m_iStage = 25;
+ m_iStage = Stage::kInitWriteNewObjs25;
}
- if (m_iStage == 25) {
+ if (m_iStage == Stage::kInitWriteNewObjs25) {
m_CurObjNum = 0;
- m_iStage = 26;
+ m_iStage = Stage::kWriteNewObjs26;
}
- if (m_iStage == 26) {
+ if (m_iStage == Stage::kWriteNewObjs26) {
if (!WriteNewObjs())
- return -1;
+ return Stage::kInvalid;
- m_iStage = 27;
+ m_iStage = Stage::kWriteEncryptDict27;
}
- if (m_iStage == 27) {
+ if (m_iStage == Stage::kWriteEncryptDict27) {
if (m_pEncryptDict && m_pEncryptDict->IsInline()) {
m_dwLastObjNum += 1;
FX_FILESIZE saveOffset = m_Archive->CurrentOffset();
if (!WriteIndirectObj(m_dwLastObjNum, m_pEncryptDict.Get()))
- return -1;
+ return Stage::kInvalid;
m_ObjectOffsets[m_dwLastObjNum] = saveOffset;
if (m_IsIncremental)
m_NewObjNumArray.push_back(m_dwLastObjNum);
}
- m_iStage = 80;
+ m_iStage = Stage::kInitWriteXRefs80;
}
return m_iStage;
}
-int32_t CPDF_Creator::WriteDoc_Stage3() {
- ASSERT(m_iStage >= 80 || m_iStage < 90);
+CPDF_Creator::Stage CPDF_Creator::WriteDoc_Stage3() {
+ ASSERT(m_iStage >= Stage::kInitWriteXRefs80 ||
+ m_iStage < Stage::kWriteTrailerAndFinish90);
uint32_t dwLastObjNum = m_dwLastObjNum;
- if (m_iStage == 80) {
+ if (m_iStage == Stage::kInitWriteXRefs80) {
m_XrefStart = m_Archive->CurrentOffset();
if (!m_IsIncremental || !m_pParser->IsXRefStream()) {
if (!m_IsIncremental || m_pParser->GetLastXRefOffset() == 0) {
@@ -468,22 +470,22 @@ int32_t CPDF_Creator::WriteDoc_Stage3() {
? "xref\r\n"
: "xref\r\n0 1\r\n0000000000 65535 f\r\n";
if (!m_Archive->WriteString(str.AsStringView()))
- return -1;
+ return Stage::kInvalid;
m_CurObjNum = 1;
- m_iStage = 81;
+ m_iStage = Stage::kWriteXrefsNotIncremental81;
} else {
if (!m_Archive->WriteString("xref\r\n"))
- return -1;
+ return Stage::kInvalid;
m_CurObjNum = 0;
- m_iStage = 82;
+ m_iStage = Stage::kWriteXrefsIncremental82;
}
} else {
- m_iStage = 90;
+ m_iStage = Stage::kWriteTrailerAndFinish90;
}
}
- if (m_iStage == 81) {
+ if (m_iStage == Stage::kWriteXrefsNotIncremental81) {
ByteString str;
uint32_t i = m_CurObjNum;
uint32_t j;
@@ -504,19 +506,19 @@ int32_t CPDF_Creator::WriteDoc_Stage3() {
str = ByteString::Format("%d %d\r\n", i, j - i);
if (!m_Archive->WriteString(str.AsStringView()))
- return -1;
+ return Stage::kInvalid;
while (i < j) {
str = ByteString::Format("%010d 00000 n\r\n", m_ObjectOffsets[i++]);
if (!m_Archive->WriteString(str.AsStringView()))
- return -1;
+ return Stage::kInvalid;
}
if (i > dwLastObjNum)
break;
}
- m_iStage = 90;
+ m_iStage = Stage::kWriteTrailerAndFinish90;
}
- if (m_iStage == 82) {
+ if (m_iStage == Stage::kWriteXrefsIncremental82) {
ByteString str;
uint32_t iCount = pdfium::CollectionSize<uint32_t>(m_NewObjNumArray);
uint32_t i = m_CurObjNum;
@@ -538,31 +540,31 @@ int32_t CPDF_Creator::WriteDoc_Stage3() {
str = ByteString::Format("%d %d\r\n", objnum, j - i);
if (!m_Archive->WriteString(str.AsStringView()))
- return -1;
+ return Stage::kInvalid;
while (i < j) {
objnum = m_NewObjNumArray[i++];
str = ByteString::Format("%010d 00000 n\r\n", m_ObjectOffsets[objnum]);
if (!m_Archive->WriteString(str.AsStringView()))
- return -1;
+ return Stage::kInvalid;
}
}
- m_iStage = 90;
+ m_iStage = Stage::kWriteTrailerAndFinish90;
}
return m_iStage;
}
-int32_t CPDF_Creator::WriteDoc_Stage4() {
- ASSERT(m_iStage >= 90);
+CPDF_Creator::Stage CPDF_Creator::WriteDoc_Stage4() {
+ ASSERT(m_iStage >= Stage::kWriteTrailerAndFinish90);
bool bXRefStream = m_IsIncremental && m_pParser->IsXRefStream();
if (!bXRefStream) {
if (!m_Archive->WriteString("trailer\r\n<<"))
- return -1;
+ return Stage::kInvalid;
} else {
if (!m_Archive->WriteDWord(m_pDocument->GetLastObjNum() + 1) ||
!m_Archive->WriteString(" 0 obj <<")) {
- return -1;
+ return Stage::kInvalid;
}
}
@@ -579,79 +581,79 @@ int32_t CPDF_Creator::WriteDoc_Stage4() {
}
if (!m_Archive->WriteString(("/")) ||
!m_Archive->WriteString(PDF_NameEncode(key).AsStringView())) {
- return -1;
+ return Stage::kInvalid;
}
if (!pValue->WriteTo(m_Archive.get()))
- return -1;
+ return Stage::kInvalid;
}
} else {
if (!m_Archive->WriteString("\r\n/Root ") ||
!m_Archive->WriteDWord(m_pDocument->GetRoot()->GetObjNum()) ||
!m_Archive->WriteString(" 0 R\r\n")) {
- return -1;
+ return Stage::kInvalid;
}
if (m_pDocument->GetInfo()) {
if (!m_Archive->WriteString("/Info ") ||
!m_Archive->WriteDWord(m_pDocument->GetInfo()->GetObjNum()) ||
!m_Archive->WriteString(" 0 R\r\n")) {
- return -1;
+ return Stage::kInvalid;
}
}
}
if (m_pEncryptDict) {
if (!m_Archive->WriteString("/Encrypt"))
- return -1;
+ return Stage::kInvalid;
uint32_t dwObjNum = m_pEncryptDict->GetObjNum();
if (dwObjNum == 0)
dwObjNum = m_pDocument->GetLastObjNum() + 1;
if (!m_Archive->WriteString(" ") || !m_Archive->WriteDWord(dwObjNum) ||
!m_Archive->WriteString(" 0 R ")) {
- return -1;
+ return Stage::kInvalid;
}
}
if (!m_Archive->WriteString("/Size ") ||
!m_Archive->WriteDWord(m_dwLastObjNum + (bXRefStream ? 2 : 1))) {
- return -1;
+ return Stage::kInvalid;
}
if (m_IsIncremental) {
FX_FILESIZE prev = m_pParser->GetLastXRefOffset();
if (prev) {
if (!m_Archive->WriteString("/Prev "))
- return -1;
+ return Stage::kInvalid;
char offset_buf[20];
memset(offset_buf, 0, sizeof(offset_buf));
FXSYS_i64toa(prev, offset_buf, 10);
if (!m_Archive->WriteBlock(offset_buf, strlen(offset_buf)))
- return -1;
+ return Stage::kInvalid;
}
}
if (m_pIDArray) {
if (!m_Archive->WriteString(("/ID")) ||
!m_pIDArray->WriteTo(m_Archive.get())) {
- return -1;
+ return Stage::kInvalid;
}
}
if (!bXRefStream) {
if (!m_Archive->WriteString(">>"))
- return -1;
+ return Stage::kInvalid;
} else {
if (!m_Archive->WriteString("/W[0 4 1]/Index["))
- return -1;
+ return Stage::kInvalid;
if (m_IsIncremental && m_pParser && m_pParser->GetLastXRefOffset() == 0) {
uint32_t i = 0;
for (i = 0; i < m_dwLastObjNum; i++) {
if (!pdfium::ContainsKey(m_ObjectOffsets, i))
continue;
if (!m_Archive->WriteDWord(i) || !m_Archive->WriteString(" 1 "))
- return -1;
+ return Stage::kInvalid;
}
if (!m_Archive->WriteString("]/Length ") ||
!m_Archive->WriteDWord(m_dwLastObjNum * 5) ||
!m_Archive->WriteString(">>stream\r\n")) {
- return -1;
+ return Stage::kInvalid;
}
for (i = 0; i < m_dwLastObjNum; i++) {
auto it = m_ObjectOffsets.find(i);
@@ -665,33 +667,33 @@ int32_t CPDF_Creator::WriteDoc_Stage4() {
for (i = 0; i < count; i++) {
if (!m_Archive->WriteDWord(m_NewObjNumArray[i]) ||
!m_Archive->WriteString(" 1 ")) {
- return -1;
+ return Stage::kInvalid;
}
}
if (!m_Archive->WriteString("]/Length ") ||
!m_Archive->WriteDWord(count * 5) ||
!m_Archive->WriteString(">>stream\r\n")) {
- return -1;
+ return Stage::kInvalid;
}
for (i = 0; i < count; ++i)
OutputIndex(m_Archive.get(), m_ObjectOffsets[m_NewObjNumArray[i]]);
}
if (!m_Archive->WriteString("\r\nendstream"))
- return -1;
+ return Stage::kInvalid;
}
if (!m_Archive->WriteString("\r\nstartxref\r\n"))
- return -1;
+ return Stage::kInvalid;
char offset_buf[20];
memset(offset_buf, 0, sizeof(offset_buf));
FXSYS_i64toa(m_XrefStart, offset_buf, 10);
if (!m_Archive->WriteBlock(offset_buf, strlen(offset_buf)) ||
!m_Archive->WriteString("\r\n%%EOF\r\n")) {
- return -1;
+ return Stage::kInvalid;
}
- m_iStage = 100;
+ m_iStage = Stage::kComplete100;
return m_iStage;
}
@@ -699,13 +701,13 @@ bool CPDF_Creator::Create(uint32_t flags) {
m_IsIncremental = !!(flags & FPDFCREATE_INCREMENTAL);
m_IsOriginal = !(flags & FPDFCREATE_NO_ORIGINAL);
- m_iStage = 0;
+ m_iStage = Stage::kInit0;
m_dwLastObjNum = m_pDocument->GetLastObjNum();
m_ObjectOffsets.clear();
m_NewObjNumArray.clear();
InitID();
- return Continue() > -1;
+ return Continue();
}
void CPDF_Creator::InitID() {
@@ -751,17 +753,17 @@ void CPDF_Creator::InitID() {
}
}
-int32_t CPDF_Creator::Continue() {
- if (m_iStage < 0)
- return m_iStage;
+bool CPDF_Creator::Continue() {
+ if (m_iStage < Stage::kInit0)
+ return false;
- int32_t iRet = 0;
- while (m_iStage < 100) {
- if (m_iStage < 20)
+ Stage iRet = Stage::kInit0;
+ while (m_iStage < Stage::kComplete100) {
+ if (m_iStage < Stage::kInitWriteObjs20)
iRet = WriteDoc_Stage1();
- else if (m_iStage < 30)
+ else if (m_iStage < Stage::kInitWriteXRefs80)
iRet = WriteDoc_Stage2();
- else if (m_iStage < 90)
+ else if (m_iStage < Stage::kWriteTrailerAndFinish90)
iRet = WriteDoc_Stage3();
else
iRet = WriteDoc_Stage4();
@@ -770,11 +772,12 @@ int32_t CPDF_Creator::Continue() {
break;
}
- if (iRet < 1 || m_iStage == 100) {
- m_iStage = -1;
- return iRet > 99 ? 0 : (iRet < 1 ? -1 : iRet);
+ if (iRet <= Stage::kInit0 || m_iStage == Stage::kComplete100) {
+ m_iStage = Stage::kInvalid;
+ return iRet > Stage::kInit0;
}
- return m_iStage;
+
+ return m_iStage > Stage::kInvalid;
}
bool CPDF_Creator::SetFileVersion(int32_t fileVersion) {
diff --git a/core/fpdfapi/edit/cpdf_creator.h b/core/fpdfapi/edit/cpdf_creator.h
index 9c760edeae..079f1c2666 100644
--- a/core/fpdfapi/edit/cpdf_creator.h
+++ b/core/fpdfapi/edit/cpdf_creator.h
@@ -38,16 +38,33 @@ class CPDF_Creator {
bool SetFileVersion(int32_t fileVersion);
private:
- int32_t Continue();
+ enum class Stage {
+ kInvalid = -1,
+ kInit0 = 0,
+ kWriteHeader10 = 10,
+ kWriteIncremental15 = 15,
+ kInitWriteObjs20 = 20,
+ kWriteOldObjs21 = 21,
+ kInitWriteNewObjs25 = 25,
+ kWriteNewObjs26 = 26,
+ kWriteEncryptDict27 = 27,
+ kInitWriteXRefs80 = 80,
+ kWriteXrefsNotIncremental81 = 81,
+ kWriteXrefsIncremental82 = 82,
+ kWriteTrailerAndFinish90 = 90,
+ kComplete100 = 100,
+ };
+
+ bool Continue();
void Clear();
void InitNewObjNumOffsets();
void InitID();
- int32_t WriteDoc_Stage1();
- int32_t WriteDoc_Stage2();
- int32_t WriteDoc_Stage3();
- int32_t WriteDoc_Stage4();
+ CPDF_Creator::Stage WriteDoc_Stage1();
+ CPDF_Creator::Stage WriteDoc_Stage2();
+ CPDF_Creator::Stage WriteDoc_Stage3();
+ CPDF_Creator::Stage WriteDoc_Stage4();
bool WriteOldIndirectObject(uint32_t objnum);
bool WriteOldObjs();
@@ -67,7 +84,7 @@ class CPDF_Creator {
uint32_t m_dwLastObjNum;
std::unique_ptr<IFX_ArchiveStream> m_Archive;
FX_FILESIZE m_SavedOffset = 0;
- int32_t m_iStage = -1;
+ Stage m_iStage = Stage::kInvalid;
uint32_t m_CurObjNum = 0;
FX_FILESIZE m_XrefStart = 0;
std::map<uint32_t, FX_FILESIZE> m_ObjectOffsets;