[gnote] Fix a race condition causing a crash (Closes #584183)
- From: Hubert Figuière <hub src gnome org>
- To: svn-commits-list gnome org
- Subject: [gnote] Fix a race condition causing a crash (Closes #584183)
- Date: Thu, 4 Jun 2009 21:49:01 -0400 (EDT)
commit c5cd8d339699ff6bfa29fd111d569f9999213bfe
Author: Hubert Figuiere <hub figuiere net>
Date: Thu Jun 4 20:39:22 2009 -0400
Fix a race condition causing a crash (Closes #584183)
---
NEWS | 1 +
src/addins/bugzilla/bugzillanoteaddin.cpp | 1 -
src/addins/bugzilla/insertbugaction.cpp | 5 +-
src/addins/bugzilla/insertbugaction.hpp | 5 +-
src/note.cpp | 4 +-
src/notebuffer.cpp | 4 +-
src/notebuffer.hpp | 8 ++-
src/notetag.cpp | 2 +-
src/notetag.hpp | 8 ++--
src/undo.cpp | 78 +++++++++++++++--------------
src/undo.hpp | 42 +++++++++-------
11 files changed, 84 insertions(+), 74 deletions(-)
diff --git a/NEWS b/NEWS
index 0bc33d6..af730f2 100644
--- a/NEWS
+++ b/NEWS
@@ -8,6 +8,7 @@ Fixes:
* Remove libxml++. (Closes #579292) Possibly closes bug #579316.
* Some code cleanups.
+ * Fix a race condition causing a crash (Closes #584183)
Translations:
diff --git a/src/addins/bugzilla/bugzillanoteaddin.cpp b/src/addins/bugzilla/bugzillanoteaddin.cpp
index c475368..8d792d3 100644
--- a/src/addins/bugzilla/bugzillanoteaddin.cpp
+++ b/src/addins/bugzilla/bugzillanoteaddin.cpp
@@ -163,7 +163,6 @@ namespace bugzilla {
std::string string_id = boost::lexical_cast<std::string>(id);
buffer->undoer().add_undo_action (new InsertBugAction (cursor,
string_id,
- buffer,
link_tag));
std::vector<Glib::RefPtr<Gtk::TextTag> > tags;
diff --git a/src/addins/bugzilla/insertbugaction.cpp b/src/addins/bugzilla/insertbugaction.cpp
index 6fad6af..c510ec7 100644
--- a/src/addins/bugzilla/insertbugaction.cpp
+++ b/src/addins/bugzilla/insertbugaction.cpp
@@ -27,7 +27,6 @@ using gnote::InsertAction;
namespace bugzilla {
InsertBugAction::InsertBugAction(const Gtk::TextIter & start, const std::string & id,
- const Glib::RefPtr<Gtk::TextBuffer> &,
const BugzillaLink::Ptr & tag)
: m_tag(tag)
, m_offset(start.get_offset())
@@ -36,7 +35,7 @@ namespace bugzilla {
}
- void InsertBugAction::undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void InsertBugAction::undo (Gtk::TextBuffer * buffer)
{
// Tag images change the offset by one, but only when deleting.
Gtk::TextIter start_iter = buffer->get_iter_at_offset(m_offset);
@@ -51,7 +50,7 @@ namespace bugzilla {
}
- void InsertBugAction::redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void InsertBugAction::redo (Gtk::TextBuffer * buffer)
{
remove_split_tags (buffer);
diff --git a/src/addins/bugzilla/insertbugaction.hpp b/src/addins/bugzilla/insertbugaction.hpp
index 8689247..60fe0a8 100644
--- a/src/addins/bugzilla/insertbugaction.hpp
+++ b/src/addins/bugzilla/insertbugaction.hpp
@@ -33,10 +33,9 @@ class InsertBugAction
{
public:
InsertBugAction(const Gtk::TextIter & start, const std::string & id,
- const Glib::RefPtr<Gtk::TextBuffer> & buffer,
const BugzillaLink::Ptr & tag);
- void undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer);
- void redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer);
+ void undo (Gtk::TextBuffer * buffer);
+ void redo (Gtk::TextBuffer * buffer);
void merge (EditAction * action);
bool can_merge (const EditAction * action) const;
void destroy ();
diff --git a/src/note.cpp b/src/note.cpp
index 4595bf5..43764b0 100644
--- a/src/note.cpp
+++ b/src/note.cpp
@@ -955,7 +955,7 @@ namespace gnote {
// NOTE: Sharing the same TagTable means
// that formatting is duplicated between
// buffers.
- m_tag_table = NoteTagTable::Ptr(&NoteTagTable::instance());
+ m_tag_table = NoteTagTable::instance();
}
return m_tag_table;
}
@@ -964,7 +964,7 @@ namespace gnote {
{
if(!m_buffer) {
DBG_OUT("Creating buffer for %s", m_data.data().title().c_str());
- m_buffer = Glib::RefPtr<NoteBuffer>(new NoteBuffer(get_tag_table(), *this));
+ m_buffer = NoteBuffer::create(get_tag_table(), *this);
m_data.set_buffer(m_buffer);
m_buffer->signal_changed().connect(
diff --git a/src/notebuffer.cpp b/src/notebuffer.cpp
index e145d2e..d619bb3 100644
--- a/src/notebuffer.cpp
+++ b/src/notebuffer.cpp
@@ -47,10 +47,10 @@ namespace gnote {
NoteBuffer::NoteBuffer(const NoteTagTable::Ptr & tags, Note & note)
: Gtk::TextBuffer(tags)
- , m_undomanager(new UndoManager(Ptr(this)))
+ , m_undomanager(NULL)
, m_note(note)
{
-
+ m_undomanager = new UndoManager(this);
signal_insert().connect(sigc::mem_fun(*this, &NoteBuffer::text_insert_event));
signal_erase().connect(sigc::mem_fun(*this, &NoteBuffer::range_deleted_event));
signal_mark_set().connect(sigc::mem_fun(*this, &NoteBuffer::mark_set_event));
diff --git a/src/notebuffer.hpp b/src/notebuffer.hpp
index f4282f2..10453a1 100644
--- a/src/notebuffer.hpp
+++ b/src/notebuffer.hpp
@@ -41,7 +41,6 @@ namespace sharp {
namespace gnote {
- class NoteTagTable;
class Note;
class UndoManager;
@@ -55,7 +54,10 @@ public:
typedef sigc::signal<void, int, bool> ChangeDepthHandler;
bool get_enable_auto_bulleted_lists() const;
- NoteBuffer(const NoteTagTable::Ptr &, Note &);
+ static Ptr create(const NoteTagTable::Ptr & table, Note & note)
+ {
+ return Ptr(new NoteBuffer(table, note));
+ }
~NoteBuffer();
// Signal that text has been inserted, and any active tags have
@@ -107,6 +109,8 @@ public:
DepthNoteTag::Ptr find_depth_tag(Gtk::TextIter &);
protected:
+ NoteBuffer(const NoteTagTable::Ptr &, Note &);
+
virtual void on_apply_tag(const Glib::RefPtr<Gtk::TextTag> & tag,
const Gtk::TextIter &, const Gtk::TextIter &);
virtual void on_remove_tag(const Glib::RefPtr<Gtk::TextTag> & tag,
diff --git a/src/notetag.cpp b/src/notetag.cpp
index 3db4007..46eea2c 100644
--- a/src/notetag.cpp
+++ b/src/notetag.cpp
@@ -360,7 +360,7 @@ namespace gnote {
}
- NoteTagTable *NoteTagTable::s_instance = NULL;
+ NoteTagTable::Ptr NoteTagTable::s_instance;
void NoteTagTable::_init_common_tags()
{
diff --git a/src/notetag.hpp b/src/notetag.hpp
index 5321c5c..f2022ea 100644
--- a/src/notetag.hpp
+++ b/src/notetag.hpp
@@ -254,12 +254,12 @@ public:
typedef Glib::RefPtr<NoteTagTable> Ptr;
typedef sigc::slot<DynamicNoteTag::Ptr> Factory;
- static NoteTagTable & instance()
+ static const NoteTagTable::Ptr & instance()
{
if(!s_instance) {
- s_instance = new NoteTagTable;
+ s_instance = NoteTagTable::Ptr(new NoteTagTable);
}
- return *s_instance;
+ return s_instance;
}
static bool tag_is_serializable(const Glib::RefPtr<const Gtk::TextTag> & );
static bool tag_is_growable(const Glib::RefPtr<Gtk::TextTag> & );
@@ -285,7 +285,7 @@ protected:
private:
void _init_common_tags();
- static NoteTagTable *s_instance;
+ static NoteTagTable::Ptr s_instance;
std::map<std::string, Factory> m_tag_types;
std::list<Glib::RefPtr<Gtk::TextTag> > m_added_tags;
};
diff --git a/src/undo.cpp b/src/undo.cpp
index c3ce073..22bb6f0 100644
--- a/src/undo.cpp
+++ b/src/undo.cpp
@@ -52,7 +52,7 @@ namespace gnote {
}
void SplitterAction::split(Gtk::TextIter iter,
- const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ Gtk::TextBuffer * buffer)
{
Glib::SListHandle<Glib::RefPtr<Gtk::TextTag> > tag_list = iter.get_tags();
for(Glib::SListHandle<Glib::RefPtr<Gtk::TextTag> >::const_iterator tag_iter = tag_list.begin();
@@ -109,7 +109,7 @@ namespace gnote {
}
- void SplitterAction::apply_split_tag(const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void SplitterAction::apply_split_tag(Gtk::TextBuffer * buffer)
{
for(std::list<TagData>::const_iterator iter = m_splitTags.begin();
iter != m_splitTags.end(); ++iter) {
@@ -123,7 +123,7 @@ namespace gnote {
}
- void SplitterAction::remove_split_tags(const Glib::RefPtr<Gtk::TextBuffer> &buffer)
+ void SplitterAction::remove_split_tags(Gtk::TextBuffer *buffer)
{
for(std::list<TagData>::const_iterator iter = m_splitTags.begin();
iter != m_splitTags.end(); ++iter) {
@@ -147,7 +147,7 @@ namespace gnote {
}
- void InsertAction::undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void InsertAction::undo (Gtk::TextBuffer * buffer)
{
int tag_images = get_split_offset ();
@@ -164,7 +164,7 @@ namespace gnote {
}
- void InsertAction::redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void InsertAction::redo (Gtk::TextBuffer * buffer)
{
remove_split_tags (buffer);
@@ -244,7 +244,7 @@ namespace gnote {
}
- void EraseAction::undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void EraseAction::undo (Gtk::TextBuffer * buffer)
{
int tag_images = get_split_offset ();
@@ -262,7 +262,7 @@ namespace gnote {
}
- void EraseAction::redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void EraseAction::redo (Gtk::TextBuffer * buffer)
{
remove_split_tags (buffer);
@@ -360,7 +360,7 @@ namespace gnote {
}
- void TagApplyAction::undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void TagApplyAction::undo (Gtk::TextBuffer * buffer)
{
Gtk::TextIter start_iter, end_iter;
start_iter = buffer->get_iter_at_offset (m_start);
@@ -372,7 +372,7 @@ namespace gnote {
}
- void TagApplyAction::redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void TagApplyAction::redo (Gtk::TextBuffer * buffer)
{
Gtk::TextIter start_iter, end_iter;
start_iter = buffer->get_iter_at_offset (m_start);
@@ -411,7 +411,7 @@ namespace gnote {
}
- void TagRemoveAction::undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void TagRemoveAction::undo (Gtk::TextBuffer * buffer)
{
Gtk::TextIter start_iter, end_iter;
start_iter = buffer->get_iter_at_offset (m_start);
@@ -423,7 +423,7 @@ namespace gnote {
}
- void TagRemoveAction::redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void TagRemoveAction::redo (Gtk::TextBuffer * buffer)
{
Gtk::TextIter start_iter, end_iter;
start_iter = buffer->get_iter_at_offset (m_start);
@@ -459,37 +459,41 @@ namespace gnote {
}
- void ChangeDepthAction::undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void ChangeDepthAction::undo (Gtk::TextBuffer * buffer)
{
Gtk::TextIter iter = buffer->get_iter_at_line (m_line);
- NoteBuffer::Ptr note_buffer = NoteBuffer::Ptr::cast_dynamic(buffer);
- if (m_direction) {
- note_buffer->decrease_depth (iter);
- }
- else {
- note_buffer->increase_depth (iter);
- }
+ NoteBuffer* note_buffer = dynamic_cast<NoteBuffer*>(buffer);
+ if(note_buffer) {
+ if (m_direction) {
+ note_buffer->decrease_depth (iter);
+ }
+ else {
+ note_buffer->increase_depth (iter);
+ }
- buffer->move_mark (buffer->get_insert(), iter);
- buffer->move_mark (buffer->get_selection_bound(), iter);
+ buffer->move_mark (buffer->get_insert(), iter);
+ buffer->move_mark (buffer->get_selection_bound(), iter);
+ }
}
- void ChangeDepthAction::redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void ChangeDepthAction::redo (Gtk::TextBuffer * buffer)
{
Gtk::TextIter iter = buffer->get_iter_at_line (m_line);
- NoteBuffer::Ptr note_buffer = NoteBuffer::Ptr::cast_dynamic(buffer);
- if (m_direction) {
- note_buffer->increase_depth (iter);
- }
- else {
- note_buffer->decrease_depth (iter);
- }
+ NoteBuffer* note_buffer = dynamic_cast<NoteBuffer*>(buffer);
+ if(note_buffer) {
+ if (m_direction) {
+ note_buffer->increase_depth (iter);
+ }
+ else {
+ note_buffer->decrease_depth (iter);
+ }
- buffer->move_mark (buffer->get_insert(), iter);
- buffer->move_mark (buffer->get_selection_bound(), iter);
+ buffer->move_mark (buffer->get_insert(), iter);
+ buffer->move_mark (buffer->get_selection_bound(), iter);
+ }
}
@@ -520,13 +524,13 @@ namespace gnote {
}
- void InsertBulletAction::undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void InsertBulletAction::undo (Gtk::TextBuffer * buffer)
{
Gtk::TextIter iter = buffer->get_iter_at_offset (m_offset);
iter.forward_line ();
iter = buffer->get_iter_at_line (iter.get_line());
- NoteBuffer::Ptr::cast_dynamic(buffer)->remove_bullet (iter);
+ dynamic_cast<NoteBuffer*>(buffer)->remove_bullet (iter);
iter.forward_to_line_end ();
@@ -535,14 +539,14 @@ namespace gnote {
}
- void InsertBulletAction::redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer)
+ void InsertBulletAction::redo (Gtk::TextBuffer * buffer)
{
Gtk::TextIter iter = buffer->get_iter_at_offset (m_offset);
buffer->insert (iter, "\n");
- NoteBuffer::Ptr::cast_dynamic(buffer)->insert_bullet (iter,
- m_depth, m_direction);
+ dynamic_cast<NoteBuffer*>(buffer)->insert_bullet (iter,
+ m_depth, m_direction);
buffer->move_mark (buffer->get_insert(), iter);
buffer->move_mark (buffer->get_selection_bound(), iter);
@@ -566,7 +570,7 @@ namespace gnote {
}
- UndoManager::UndoManager(const NoteBuffer::Ptr & buffer)
+ UndoManager::UndoManager(NoteBuffer * buffer)
: m_frozen_cnt(0)
, m_try_merge(false)
, m_buffer(buffer)
diff --git a/src/undo.hpp b/src/undo.hpp
index 5dd7dc6..f44f539 100644
--- a/src/undo.hpp
+++ b/src/undo.hpp
@@ -42,8 +42,8 @@ namespace gnote {
class EditAction
{
public:
- virtual void undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer) = 0;
- virtual void redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer) = 0;
+ virtual void undo (Gtk::TextBuffer * buffer) = 0;
+ virtual void redo (Gtk::TextBuffer * buffer) = 0;
virtual void merge (EditAction * action) = 0;
virtual bool can_merge (const EditAction * action) const = 0;
virtual void destroy () = 0;
@@ -77,14 +77,14 @@ public:
{
return m_splitTags;
}
- void split(Gtk::TextIter iter, const Glib::RefPtr<Gtk::TextBuffer> &);
+ void split(Gtk::TextIter iter, Gtk::TextBuffer *);
void add_split_tag(const Gtk::TextIter &, const Gtk::TextIter &,
const Glib::RefPtr<Gtk::TextTag> tag);
protected:
SplitterAction();
int get_split_offset() const;
- void apply_split_tag(const Glib::RefPtr<Gtk::TextBuffer> &);
- void remove_split_tags(const Glib::RefPtr<Gtk::TextBuffer> &);
+ void apply_split_tag(Gtk::TextBuffer *);
+ void remove_split_tags(Gtk::TextBuffer *);
std::list<TagData> m_splitTags;
utils::TextRange m_chop;
};
@@ -97,8 +97,8 @@ class InsertAction
public:
InsertAction(const Gtk::TextIter & start, const std::string & text, int length,
const ChopBuffer::Ptr & chop_buf);
- virtual void undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer);
- virtual void redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer);
+ virtual void undo (Gtk::TextBuffer * buffer);
+ virtual void redo (Gtk::TextBuffer * buffer);
virtual void merge (EditAction * action);
virtual bool can_merge (const EditAction * action) const;
virtual void destroy ();
@@ -115,8 +115,8 @@ class EraseAction
public:
EraseAction(const Gtk::TextIter & start_iter, const Gtk::TextIter & end_iter,
const ChopBuffer::Ptr & chop_buf);
- virtual void undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer);
- virtual void redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer);
+ virtual void undo (Gtk::TextBuffer * buffer);
+ virtual void redo (Gtk::TextBuffer * buffer);
virtual void merge (EditAction * action);
virtual bool can_merge (const EditAction * action) const;
virtual void destroy ();
@@ -135,8 +135,8 @@ class TagApplyAction
{
public:
TagApplyAction(const Glib::RefPtr<Gtk::TextTag> &, const Gtk::TextIter & start, const Gtk::TextIter & end);
- virtual void undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer);
- virtual void redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer);
+ virtual void undo (Gtk::TextBuffer * buffer);
+ virtual void redo (Gtk::TextBuffer * buffer);
virtual void merge (EditAction * action);
virtual bool can_merge (const EditAction * action) const;
virtual void destroy ();
@@ -153,8 +153,8 @@ class TagRemoveAction
{
public:
TagRemoveAction(const Glib::RefPtr<Gtk::TextTag> &, const Gtk::TextIter & start, const Gtk::TextIter & end);
- virtual void undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer);
- virtual void redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer);
+ virtual void undo (Gtk::TextBuffer * buffer);
+ virtual void redo (Gtk::TextBuffer * buffer);
virtual void merge (EditAction * action);
virtual bool can_merge (const EditAction * action) const;
virtual void destroy ();
@@ -170,8 +170,8 @@ class ChangeDepthAction
{
public:
ChangeDepthAction(int line, bool direction);
- virtual void undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer);
- virtual void redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer);
+ virtual void undo (Gtk::TextBuffer * buffer);
+ virtual void redo (Gtk::TextBuffer * buffer);
virtual void merge (EditAction * action);
virtual bool can_merge (const EditAction * action) const;
virtual void destroy ();
@@ -187,8 +187,8 @@ class InsertBulletAction
{
public:
InsertBulletAction(int offset, int depth, Pango::Direction direction);
- virtual void undo (const Glib::RefPtr<Gtk::TextBuffer> & buffer);
- virtual void redo (const Glib::RefPtr<Gtk::TextBuffer> & buffer);
+ virtual void undo (Gtk::TextBuffer * buffer);
+ virtual void redo (Gtk::TextBuffer * buffer);
virtual void merge (EditAction * action);
virtual bool can_merge (const EditAction * action) const;
virtual void destroy ();
@@ -202,7 +202,11 @@ class UndoManager
: public boost::noncopyable
{
public:
- UndoManager(const NoteBuffer::Ptr & buffer);
+ /** the buffer it NOT owned by the UndoManager
+ * it is assume to have a longer life than UndoManager
+ * Actually the UndoManager belong to the buffer.
+ */
+ UndoManager(NoteBuffer * buffer);
~UndoManager();
bool get_can_undo()
{
@@ -251,7 +255,7 @@ private:
guint m_frozen_cnt;
bool m_try_merge;
- NoteBuffer::Ptr m_buffer;
+ NoteBuffer * m_buffer;
ChopBuffer::Ptr m_chop_buffer;
std::stack<EditAction *> m_undo_stack;
std::stack<EditAction *> m_redo_stack;
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]