[fbreader] Prevent a crash in <aside> blocks

This commit is contained in:
Slava Monich 2019-11-28 00:52:04 +02:00
parent 556c3bd351
commit 85a121633b
4 changed files with 55 additions and 30 deletions

View file

@ -1,6 +1,6 @@
/* /*
* Copyright (C) 2004-2010 Geometer Plus <contact@geometerplus.com> * Copyright (C) 2004-2010 Geometer Plus <contact@geometerplus.com>
* Copyright (C) 2016 Slava Monich <slava.monich@jolla.com> * Copyright (C) 2016-2019 Slava Monich <slava.monich@jolla.com>
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by * it under the terms of the GNU General Public License as published by
@ -32,6 +32,8 @@ BookReader::BookReader(BookModel &model) : myModel(model) {
myTextParagraphExists = false; myTextParagraphExists = false;
myContentsParagraphExists = false; myContentsParagraphExists = false;
myBookTextParagraphExists = false;
myBookContentsParagraphExists = false;
myInsideTitle = false; myInsideTitle = false;
mySectionContainsRegularContents = false; mySectionContainsRegularContents = false;
@ -41,10 +43,20 @@ BookReader::~BookReader() {
} }
void BookReader::setMainTextModel() { void BookReader::setMainTextModel() {
myCurrentTextModel = myModel.myBookTextModel; if (myCurrentTextModel != myModel.myBookTextModel) {
myCurrentTextModel = myModel.myBookTextModel;
myTextParagraphExists = myBookTextParagraphExists;
myContentsParagraphExists = myBookContentsParagraphExists;
}
} }
void BookReader::setFootnoteTextModel(const std::string &id) { void BookReader::setFootnoteTextModel(const std::string &id) {
if (myCurrentTextModel == myModel.myBookTextModel) {
myBookTextParagraphExists = myTextParagraphExists;
myBookContentsParagraphExists = myContentsParagraphExists;
}
myTextParagraphExists = false;
myContentsParagraphExists = false;
std::map<std::string,shared_ptr<ZLTextModel> >::iterator it = myModel.myFootnotes.find(id); std::map<std::string,shared_ptr<ZLTextModel> >::iterator it = myModel.myFootnotes.find(id);
if (it != myModel.myFootnotes.end()) { if (it != myModel.myFootnotes.end()) {
myCurrentTextModel = (*it).second; myCurrentTextModel = (*it).second;
@ -54,6 +66,14 @@ void BookReader::setFootnoteTextModel(const std::string &id) {
} }
} }
void BookReader::setFootnoteTextModel(const std::string &id, const std::string &alt)
{
setFootnoteTextModel(id);
if (!alt.empty() && myModel.myFootnotes.find(alt) == myModel.myFootnotes.end()) {
myModel.myFootnotes.insert(std::make_pair(alt, myCurrentTextModel));
}
}
void BookReader::unsetTextModel() { void BookReader::unsetTextModel() {
myCurrentTextModel = 0; myCurrentTextModel = 0;
} }

View file

@ -1,5 +1,6 @@
/* /*
* Copyright (C) 2004-2010 Geometer Plus <contact@geometerplus.com> * Copyright (C) 2004-2010 Geometer Plus <contact@geometerplus.com>
* Copyright (C) 2016-2019 Slava Monich <slava.monich@jolla.com>
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by * it under the terms of the GNU General Public License as published by
@ -40,6 +41,7 @@ public:
void setMainTextModel(); void setMainTextModel();
void setFootnoteTextModel(const std::string &id); void setFootnoteTextModel(const std::string &id);
void setFootnoteTextModel(const std::string &id, const std::string &alt);
void unsetTextModel(); void unsetTextModel();
void insertEndOfSectionParagraph(); void insertEndOfSectionParagraph();
@ -91,6 +93,8 @@ private:
bool myTextParagraphExists; bool myTextParagraphExists;
bool myContentsParagraphExists; bool myContentsParagraphExists;
bool myBookTextParagraphExists;
bool myBookContentsParagraphExists;
std::stack<ZLTextTreeParagraph*> myTOCStack; std::stack<ZLTextTreeParagraph*> myTOCStack;
bool myLastTOCParagraphIsEmpty; bool myLastTOCParagraphIsEmpty;

View file

@ -1,6 +1,6 @@
/* /*
* Copyright (C) 2004-2010 Geometer Plus <contact@geometerplus.com> * Copyright (C) 2004-2010 Geometer Plus <contact@geometerplus.com>
* Copyright (C) 2016-2018 Slava Monich <slava.monich@jolla.com> * Copyright (C) 2016-2019 Slava Monich <slava.monich@jolla.com>
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by * it under the terms of the GNU General Public License as published by
@ -394,7 +394,7 @@ XHTMLTagFootnoteAction::XHTMLTagFootnoteAction() {
void XHTMLTagFootnoteAction::doAtStart(XHTMLReader &reader, const char **xmlattributes) { void XHTMLTagFootnoteAction::doAtStart(XHTMLReader &reader, const char **xmlattributes) {
const char *id = reader.attributeValue(xmlattributes, "id"); const char *id = reader.attributeValue(xmlattributes, "id");
if (id) { if (id) {
bookReader(reader).setFootnoteTextModel(id); bookReader(reader).setFootnoteTextModel(id, reader.myReferenceName + "#" + id);
} }
} }

View file

@ -1,6 +1,6 @@
/* /*
* Copyright (C) 2004-2010 Geometer Plus <contact@geometerplus.com> * Copyright (C) 2004-2010 Geometer Plus <contact@geometerplus.com>
* Copyright (C) 2016-2018 Slava Monich <slava.monich@jolla.com> * Copyright (C) 2016-2019 Slava Monich <slava.monich@jolla.com>
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by * it under the terms of the GNU General Public License as published by
@ -41,9 +41,9 @@ class XHTMLTagAction {
public: public:
virtual ~XHTMLTagAction(); virtual ~XHTMLTagAction();
virtual void doAtStart(XHTMLReader &reader, const char **xmlattributes); virtual void doAtStart(XHTMLReader &reader, const char **xmlattributes);
virtual void doAtEnd(XHTMLReader &reader); virtual void doAtEnd(XHTMLReader &reader);
protected: protected:
static BookReader &bookReader(XHTMLReader &reader); static BookReader &bookReader(XHTMLReader &reader);
@ -87,28 +87,28 @@ private:
bool processNamespaces() const; bool processNamespaces() const;
void haveContent(); void haveContent();
void beginParagraph(); void beginParagraph();
void endParagraph(); void endParagraph();
void applyStyles(ParseContext &context); void applyStyles(ParseContext &context);
void addStyleParagraph(const ZLTextStyleEntry &style); void addStyleParagraph(const ZLTextStyleEntry &style);
void addBottomMargin(short size, ZLTextStyleEntry::SizeUnit unit); void addBottomMargin(short size, ZLTextStyleEntry::SizeUnit unit);
bool elementHasTopMargin(const ParseContext &context) const; bool elementHasTopMargin(const ParseContext &context) const;
bool elementHasBottomMargin(const ParseContext &context) const; bool elementHasBottomMargin(const ParseContext &context) const;
void applyBottomMargins(); void applyBottomMargins();
void addPageBreak(); void addPageBreak();
private: private:
BookReader &myModelReader; BookReader &myModelReader;
std::string myPathPrefix; std::string myPathPrefix;
std::string myReferenceName; std::string myReferenceName;
std::string myReferenceDirName; std::string myReferenceDirName;
int myPreformatted; int myPreformatted;
StyleSheetTable myStyleSheetTable; StyleSheetTable myStyleSheetTable;
StyleSheetTable::ElementList myElementStack; StyleSheetTable::ElementList myElementStack;
StyleSheetTable::StyleList myStyleStack; StyleSheetTable::StyleList myStyleStack;
std::vector<ParseContext> myParseStack; std::vector<ParseContext> myParseStack;
std::vector<ZLTextStyleEntry> myBottomMargins; std::vector<ZLTextStyleEntry> myBottomMargins;
StyleSheetSingleStyleParser myStyleParser; StyleSheetSingleStyleParser myStyleParser;
shared_ptr<StyleSheetTableParser> myTableParser; shared_ptr<StyleSheetTableParser> myTableParser;
enum { enum {
@ -118,14 +118,15 @@ private:
} myReadState; } myReadState;
friend class XHTMLTagAction; friend class XHTMLTagAction;
friend class XHTMLTagStyleAction; friend class XHTMLTagStyleAction;
friend class XHTMLTagLinkAction; friend class XHTMLTagLinkAction;
friend class XHTMLTagHyperlinkAction; friend class XHTMLTagHyperlinkAction;
friend class XHTMLTagPreAction; friend class XHTMLTagPreAction;
friend class XHTMLTagControlAction; friend class XHTMLTagControlAction;
friend class XHTMLTagParagraphWithControlAction; friend class XHTMLTagParagraphWithControlAction;
friend class XHTMLTagBodyAction; friend class XHTMLTagBodyAction;
friend class XHTMLTagImageAction; friend class XHTMLTagImageAction;
friend class XHTMLTagFootnoteAction;
}; };
#endif /* __XHTMLREADER_H__ */ #endif /* __XHTMLREADER_H__ */