[poppler] 2 commits - config.h.cmake ConfigureChecks.cmake poppler/PageLabelInfo.cc poppler/PageLabelInfo_p.h qt5/tests
GitLab Mirror
gitlab-mirror at kemper.freedesktop.org
Mon Oct 1 23:47:10 UTC 2018
ConfigureChecks.cmake | 2 ++
config.h.cmake | 3 +++
poppler/PageLabelInfo.cc | 7 ++++---
poppler/PageLabelInfo_p.h | 34 ++++++++++++++++++++++++++++++++++
qt5/tests/check_pagelabelinfo.cpp | 20 ++++++++++++++++++++
5 files changed, 63 insertions(+), 3 deletions(-)
New commits:
commit a6f88881d41f064a4c2438d4e1b532872a879b0c
Author: Adam Reichold <adam.reichold at t-online.de>
Date: Sun Sep 23 09:56:51 2018 +0200
Put (optional) usage of codecvt behind a configure check s.t. we at least compile even if we do not properly handle the unicode page label.
diff --git a/ConfigureChecks.cmake b/ConfigureChecks.cmake
index 6a910394..fa0f1403 100644
--- a/ConfigureChecks.cmake
+++ b/ConfigureChecks.cmake
@@ -4,6 +4,7 @@
# For details see the accompanying COPYING-CMAKE-SCRIPTS file.
include(CheckIncludeFile)
+include(CheckIncludeFileCXX)
include(CheckIncludeFiles)
include(CheckSymbolExists)
include(CheckFunctionExists)
@@ -17,6 +18,7 @@ check_include_files(stdlib.h HAVE_STDLIB_H)
check_include_files(sys/mman.h HAVE_SYS_MMAN_H)
check_include_files(sys/stat.h HAVE_SYS_STAT_H)
check_include_files(unistd.h HAVE_UNISTD_H)
+check_include_file_cxx(codecvt HAVE_CODECVT)
check_function_exists(fseek64 HAVE_FSEEK64)
check_function_exists(fseeko HAVE_FSEEKO)
diff --git a/config.h.cmake b/config.h.cmake
index 74355a69..7989cbfb 100644
--- a/config.h.cmake
+++ b/config.h.cmake
@@ -117,6 +117,9 @@
/* Define to 1 if you have the <unistd.h> header file. */
#cmakedefine HAVE_UNISTD_H 1
+/* Define to 1 if you have the <codecvt> header file. */
+#cmakedefine HAVE_CODECVT
+
/* Define to 1 if you have a big endian machine */
#cmakedefine WORDS_BIGENDIAN 1
diff --git a/poppler/PageLabelInfo_p.h b/poppler/PageLabelInfo_p.h
index 36abe0e1..6553c325 100644
--- a/poppler/PageLabelInfo_p.h
+++ b/poppler/PageLabelInfo_p.h
@@ -14,20 +14,19 @@
/* http://mathworld.wolfram.com/RomanNumerals.html */
+#include "config.h"
+
+#ifdef HAVE_CODECVT
#include <locale>
#include <codecvt>
+#endif
#include "goo/GooString.h"
#include "Error.h"
static std::pair<int,bool> fromDecimal(const char *const begin, const char *const end, const bool unicode) {
- if (!unicode) {
- char *parsed;
- const int number = std::strtol(begin, &parsed, 10);
- if (parsed >= end) {
- return std::make_pair(number, true);
- }
- } else {
+#ifdef HAVE_CODECVT
+ if (unicode) {
std::wstring_convert<std::codecvt_utf16<wchar_t>> converter;
const auto str = converter.from_bytes(begin, end);
@@ -43,8 +42,13 @@ static std::pair<int,bool> fromDecimal(const char *const begin, const char *cons
return std::make_pair(number, true);
}
}
+#else
+ (void)unicode;
+#endif
- return std::make_pair(0, false);
+ char *parsed;
+ const int number = std::strtol(begin, &parsed, 10);
+ return std::make_pair(number, parsed >= end);
}
static int fromRoman(const char *buffer) {
commit 65c8bc1eefea0b99e46d4190dc61ead216088283
Author: Adam Reichold <adam.reichold at t-online.de>
Date: Sun Sep 23 00:45:04 2018 +0200
Parse Unicode decimals as well as ASCII decimals when resolving page labels.
diff --git a/poppler/PageLabelInfo.cc b/poppler/PageLabelInfo.cc
index 96c4c333..3053aa05 100644
--- a/poppler/PageLabelInfo.cc
+++ b/poppler/PageLabelInfo.cc
@@ -102,8 +102,9 @@ GBool PageLabelInfo::labelToIndex(GooString *label, int *index) const
{
const char *const str = label->getCString();
const std::size_t strLen = label->getLength();
- char *end;
+ const bool strUnicode = label->hasUnicodeMarker();
int number;
+ bool ok;
for (const auto& interval : intervals) {
const std::size_t prefixLen = interval.prefix.size();
@@ -112,8 +113,8 @@ GBool PageLabelInfo::labelToIndex(GooString *label, int *index) const
switch (interval.style) {
case Interval::Arabic:
- number = strtol(str + prefixLen, &end, 10);
- if (*end == '\0' && number - interval.first < interval.length) {
+ std::tie(number, ok) = fromDecimal(str + prefixLen, str + strLen, strUnicode);
+ if (ok && number - interval.first < interval.length) {
*index = interval.base + number - interval.first;
return gTrue;
}
diff --git a/poppler/PageLabelInfo_p.h b/poppler/PageLabelInfo_p.h
index 34823cc6..36abe0e1 100644
--- a/poppler/PageLabelInfo_p.h
+++ b/poppler/PageLabelInfo_p.h
@@ -14,9 +14,39 @@
/* http://mathworld.wolfram.com/RomanNumerals.html */
+#include <locale>
+#include <codecvt>
+
#include "goo/GooString.h"
#include "Error.h"
+static std::pair<int,bool> fromDecimal(const char *const begin, const char *const end, const bool unicode) {
+ if (!unicode) {
+ char *parsed;
+ const int number = std::strtol(begin, &parsed, 10);
+ if (parsed >= end) {
+ return std::make_pair(number, true);
+ }
+ } else {
+ std::wstring_convert<std::codecvt_utf16<wchar_t>> converter;
+ const auto str = converter.from_bytes(begin, end);
+
+ // Skip BOM since wcstol seems unable to handle it.
+ const wchar_t *c_str = str.c_str();
+ if (*c_str == wchar_t{0xfeff}) {
+ ++c_str;
+ }
+
+ wchar_t *parsed;
+ const int number = std::wcstol(c_str, &parsed, 10);
+ if (parsed >= str.data() + str.size()) {
+ return std::make_pair(number, true);
+ }
+ }
+
+ return std::make_pair(0, false);
+}
+
static int fromRoman(const char *buffer) {
int digit_value, prev_digit_value, value;
int i;
diff --git a/qt5/tests/check_pagelabelinfo.cpp b/qt5/tests/check_pagelabelinfo.cpp
index a428e059..1b13be95 100644
--- a/qt5/tests/check_pagelabelinfo.cpp
+++ b/qt5/tests/check_pagelabelinfo.cpp
@@ -1,17 +1,37 @@
#include <QtTest/QtTest>
+#include <poppler-private.h>
+
#include "PageLabelInfo_p.h"
class TestPageLabelInfo : public QObject
{
Q_OBJECT
private slots:
+ void testFromDecimal();
+ void testFromDecimalUnicode();
void testToRoman();
void testFromRoman();
void testToLatin();
void testFromLatin();
};
+void TestPageLabelInfo::testFromDecimal()
+{
+ std::string str{"2342"};
+ const auto res = fromDecimal(str.data(), str.data() + str.size(), false);
+ QCOMPARE(res.first, 2342);
+ QCOMPARE(res.second, true);
+}
+
+void TestPageLabelInfo::testFromDecimalUnicode()
+{
+ std::unique_ptr<GooString> str(Poppler::QStringToUnicodeGooString(QString::fromLocal8Bit("2342")));
+ const auto res = fromDecimal(str->getCString(), str->getCString() + str->getLength(), str->hasUnicodeMarker());
+ QCOMPARE(res.first, 2342);
+ QCOMPARE(res.second, true);
+}
+
void TestPageLabelInfo::testToRoman()
{
GooString str;
More information about the poppler
mailing list