Commit: b8438a870dffb7a3ca3636d8bfa4e37dbf907c71
Author: Campbell Barton
Date:   Mon Nov 2 21:37:15 2015 +1100
Branches: blender-v2.76-release
https://developer.blender.org/rBb8438a870dffb7a3ca3636d8bfa4e37dbf907c71

Fix T46626: Crash generating previews

Brush.toggle_brush was allowed to be an invalid pointer,
it worked for the one operator that used it - but in general bad practice,
requiring a lookup on every access.

Ensure the pointer is kept valid now.

===================================================================

M       source/blender/blenkernel/BKE_brush.h
M       source/blender/blenkernel/intern/brush.c
M       source/blender/blenloader/intern/readfile.c
M       source/blender/editors/sculpt_paint/paint_ops.c
M       source/blender/makesrna/intern/rna_main_api.c

===================================================================

diff --git a/source/blender/blenkernel/BKE_brush.h 
b/source/blender/blenkernel/BKE_brush.h
index aff3fb0..ea7ad0f 100644
--- a/source/blender/blenkernel/BKE_brush.h
+++ b/source/blender/blenkernel/BKE_brush.h
@@ -44,6 +44,7 @@ struct Brush *BKE_brush_add(struct Main *bmain, const char 
*name, short ob_mode)
 struct Brush *BKE_brush_first_search(struct Main *bmain, short ob_mode);
 struct Brush *BKE_brush_copy(struct Brush *brush);
 void BKE_brush_make_local(struct Brush *brush);
+void BKE_brush_unlink(struct Main *bmain, struct Brush *brush);
 void BKE_brush_free(struct Brush *brush);
 
 void BKE_brush_sculpt_reset(struct Brush *brush);
diff --git a/source/blender/blenkernel/intern/brush.c 
b/source/blender/blenkernel/intern/brush.c
index e0ffd83..4d619c8 100644
--- a/source/blender/blenkernel/intern/brush.c
+++ b/source/blender/blenkernel/intern/brush.c
@@ -215,11 +215,27 @@ void BKE_brush_free(Brush *brush)
                MEM_freeN(brush->gradient);
 }
 
+/**
+ * \note Currently users don't remove brushes from the UI (as is done for 
scene, text... etc)
+ * This is only used by RNA, which can remove brushes.
+ */
+void BKE_brush_unlink(Main *bmain, Brush *brush)
+{
+       Brush *brush_iter;
+
+       for (brush_iter = bmain->brush.first; brush_iter; brush_iter = 
brush_iter->id.next) {
+               if (brush_iter->toggle_brush == brush) {
+                       brush_iter->toggle_brush = NULL;
+               }
+       }
+}
+
 static void extern_local_brush(Brush *brush)
 {
        id_lib_extern((ID *)brush->mtex.tex);
        id_lib_extern((ID *)brush->mask_mtex.tex);
        id_lib_extern((ID *)brush->clone.image);
+       id_lib_extern((ID *)brush->toggle_brush);
        id_lib_extern((ID *)brush->paint_curve);
 }
 
diff --git a/source/blender/blenloader/intern/readfile.c 
b/source/blender/blenloader/intern/readfile.c
index aeb3168..2da3f39 100644
--- a/source/blender/blenloader/intern/readfile.c
+++ b/source/blender/blenloader/intern/readfile.c
@@ -2131,6 +2131,7 @@ static void lib_link_brush(FileData *fd, Main *main)
                        brush->mtex.tex = newlibadr_us(fd, brush->id.lib, 
brush->mtex.tex);
                        brush->mask_mtex.tex = newlibadr_us(fd, brush->id.lib, 
brush->mask_mtex.tex);
                        brush->clone.image = newlibadr_us(fd, brush->id.lib, 
brush->clone.image);
+                       brush->toggle_brush = newlibadr(fd, brush->id.lib, 
brush->toggle_brush);
                        brush->paint_curve = newlibadr_us(fd, brush->id.lib, 
brush->paint_curve);
                }
        }
@@ -8771,6 +8772,7 @@ static void expand_brush(FileData *fd, Main *mainvar, 
Brush *brush)
        expand_doit(fd, mainvar, brush->mtex.tex);
        expand_doit(fd, mainvar, brush->mask_mtex.tex);
        expand_doit(fd, mainvar, brush->clone.image);
+       expand_doit(fd, mainvar, brush->toggle_brush);
        expand_doit(fd, mainvar, brush->paint_curve);
 }
 
diff --git a/source/blender/editors/sculpt_paint/paint_ops.c 
b/source/blender/editors/sculpt_paint/paint_ops.c
index 05eda4d..91e372b 100644
--- a/source/blender/editors/sculpt_paint/paint_ops.c
+++ b/source/blender/editors/sculpt_paint/paint_ops.c
@@ -407,12 +407,9 @@ static Brush *brush_tool_toggle(Main *bmain, Brush 
*brush_orig, const int tool,
                
                return br;
        }
-       else if (brush_orig->toggle_brush &&
-                BLI_findindex(bmain->brush.first, brush_orig->toggle_brush) != 
-1)
-       {
+       else if (brush_orig->toggle_brush) {
                /* if current brush is using the desired tool, try to toggle
-                * back to the previously selected brush (if it was set, and
-                * if it still exists) */
+                * back to the previously selected brush. */
                return brush_orig->toggle_brush;
        }
        else
diff --git a/source/blender/makesrna/intern/rna_main_api.c 
b/source/blender/makesrna/intern/rna_main_api.c
index b38f4fa..a677171 100644
--- a/source/blender/makesrna/intern/rna_main_api.c
+++ b/source/blender/makesrna/intern/rna_main_api.c
@@ -494,6 +494,7 @@ static void rna_Main_brushes_remove(Main *bmain, ReportList 
*reports, PointerRNA
 {
        Brush *brush = brush_ptr->data;
        if (ID_REAL_USERS(brush) <= 0) {
+               BKE_brush_unlink(bmain, brush);
                BKE_libblock_free(bmain, brush);
                RNA_POINTER_INVALIDATE(brush_ptr);
        }

_______________________________________________
Bf-blender-cvs mailing list
[email protected]
http://lists.blender.org/mailman/listinfo/bf-blender-cvs

Reply via email to