fix [#29459] Crash making a linked object group local
authorCampbell Barton <ideasman42@gmail.com>
Wed, 30 Nov 2011 00:32:13 +0000 (00:32 +0000)
committerCampbell Barton <ideasman42@gmail.com>
Wed, 30 Nov 2011 00:32:13 +0000 (00:32 +0000)
was an error with make-local refactor & path updating.

19 files changed:
source/blender/blenkernel/BKE_library.h
source/blender/blenkernel/intern/action.c
source/blender/blenkernel/intern/armature.c
source/blender/blenkernel/intern/brush.c
source/blender/blenkernel/intern/camera.c
source/blender/blenkernel/intern/curve.c
source/blender/blenkernel/intern/image.c
source/blender/blenkernel/intern/lamp.c
source/blender/blenkernel/intern/lattice.c
source/blender/blenkernel/intern/library.c
source/blender/blenkernel/intern/material.c
source/blender/blenkernel/intern/mball.c
source/blender/blenkernel/intern/mesh.c
source/blender/blenkernel/intern/object.c
source/blender/blenkernel/intern/particle.c
source/blender/blenkernel/intern/speaker.c
source/blender/blenkernel/intern/texture.c
source/blender/blenkernel/intern/world.c
source/blender/editors/space_outliner/outliner_tools.c

index ade055a..e8d6c85 100644 (file)
@@ -49,7 +49,7 @@ void *alloc_libblock(struct ListBase *lb, short type, const char *name);
 void *copy_libblock(struct ID *id);
 void copy_libblock_data(struct ID *id, const struct ID *id_from, const short do_action);
 
-void BKE_id_lib_local_paths(struct Main *bmain, struct ID *id);
+void BKE_id_lib_local_paths(struct Main *bmain, struct Library *lib, struct ID *id);
 void id_lib_extern(struct ID *id);
 void BKE_library_filepath_set(struct Library *lib, const char *filepath);
 void id_us_plus(struct ID *id);
index 5fb03b7..767401a 100644 (file)
@@ -92,8 +92,8 @@ bAction *add_empty_action(const char name[])
 
 /* temp data for make_local_action */
 typedef struct tMakeLocalActionContext {
-       bAction *act;    /* original action */
-       bAction *actn;   /* new action */
+       bAction *act;       /* original action */
+       bAction *act_new;   /* new action */
        
        int is_lib;         /* some action users were libraries */
        int is_local;       /* some action users were not libraries */
@@ -117,9 +117,9 @@ static void make_localact_apply_cb(ID *id, AnimData *adt, void *mlac_ptr)
        
        if (adt->action == mlac->act) {
                if (id->lib == NULL) {
-                       adt->action = mlac->actn;
+                       adt->action = mlac->act_new;
                        
-                       id_us_plus(&mlac->actn->id);
+                       id_us_plus(&mlac->act_new->id);
                        id_us_min(&mlac->act->id);
                }
        }
@@ -146,10 +146,10 @@ void make_local_action(bAction *act)
                id_clear_lib_data(bmain, &act->id);
        }
        else if (mlac.is_local && mlac.is_lib) {
-               mlac.actn= copy_action(act);
-               mlac.actn->id.us= 0;
+               mlac.act_new= copy_action(act);
+               mlac.act_new->id.us= 0;
 
-               BKE_id_lib_local_paths(bmain, &mlac.actn->id);
+               BKE_id_lib_local_paths(bmain, act->id.lib, &mlac.act_new->id);
 
                BKE_animdata_main_cb(bmain, make_localact_apply_cb, &mlac);
        }
index a9c2972..2157bd5 100644 (file)
@@ -158,17 +158,17 @@ void make_local_armature(bArmature *arm)
                id_clear_lib_data(bmain, &arm->id);
        }
        else if(is_local && is_lib) {
-               bArmature *armn= copy_armature(arm);
-               armn->id.us= 0;
+               bArmature *arm_new= copy_armature(arm);
+               arm_new->id.us= 0;
 
                /* Remap paths of new ID using old library as base. */
-               BKE_id_lib_local_paths(bmain, &armn->id);
+               BKE_id_lib_local_paths(bmain, arm->id.lib, &arm_new->id);
 
                for(ob= bmain->object.first; ob; ob= ob->id.next) {
                        if(ob->data == arm) {
                                if(ob->id.lib==NULL) {
-                                       ob->data= armn;
-                                       armn->id.us++;
+                                       ob->data= arm_new;
+                                       arm_new->id.us++;
                                        arm->id.us--;
                                }
                        }
index 5303bad..7fac273 100644 (file)
@@ -224,17 +224,17 @@ void make_local_brush(Brush *brush)
                }
        }
        else if(is_local && is_lib) {
-               Brush *brushn= copy_brush(brush);
-               brushn->id.us= 1; /* only keep fake user */
-               brushn->id.flag |= LIB_FAKEUSER;
+               Brush *brush_new= copy_brush(brush);
+               brush_new->id.us= 1; /* only keep fake user */
+               brush_new->id.flag |= LIB_FAKEUSER;
 
                /* Remap paths of new ID using old library as base. */
-               BKE_id_lib_local_paths(bmain, &brush->id);
+               BKE_id_lib_local_paths(bmain, brush->id.lib, &brush_new->id);
                
                for(scene= bmain->scene.first; scene; scene=scene->id.next) {
                        if(paint_brush(&scene->toolsettings->imapaint.paint)==brush) {
                                if(scene->id.lib==NULL) {
-                                       paint_brush_set(&scene->toolsettings->imapaint.paint, brushn);
+                                       paint_brush_set(&scene->toolsettings->imapaint.paint, brush_new);
                                }
                        }
                }
index 08e8a80..2bd973d 100644 (file)
@@ -108,18 +108,18 @@ void make_local_camera(Camera *cam)
                id_clear_lib_data(bmain, &cam->id);
        }
        else if(is_local && is_lib) {
-               Camera *camn= copy_camera(cam);
+               Camera *cam_new= copy_camera(cam);
 
-               camn->id.us= 0;
+               cam_new->id.us= 0;
 
                /* Remap paths of new ID using old library as base. */
-               BKE_id_lib_local_paths(bmain, &camn->id);
+               BKE_id_lib_local_paths(bmain, cam->id.lib, &cam_new->id);
 
                for(ob= bmain->object.first; ob; ob= ob->id.next) {
                        if(ob->data == cam) {
                                if(ob->id.lib==NULL) {
-                                       ob->data= camn;
-                                       camn->id.us++;
+                                       ob->data= cam_new;
+                                       cam_new->id.us++;
                                        cam->id.us--;
                                }
                        }
index 358c63b..0f1c73c 100644 (file)
@@ -274,16 +274,16 @@ void make_local_curve(Curve *cu)
                extern_local_curve(cu);
        }
        else if(is_local && is_lib) {
-               Curve *cun= copy_curve(cu);
-               cun->id.us= 0;
+               Curve *cu_new= copy_curve(cu);
+               cu_new->id.us= 0;
 
-               BKE_id_lib_local_paths(bmain, &cun->id);
+               BKE_id_lib_local_paths(bmain, cu->id.lib, &cu_new->id);
 
                for(ob= bmain->object.first; ob; ob= ob->id.next) {
                        if(ob->data==cu) {
                                if(ob->id.lib==NULL) {
-                                       ob->data= cun;
-                                       cun->id.us++;
+                                       ob->data= cu_new;
+                                       cu_new->id.us++;
                                        cu->id.us--;
                                }
                        }
index c7f74f3..fb734ea 100644 (file)
@@ -385,19 +385,19 @@ void make_local_image(struct Image *ima)
                extern_local_image(ima);
        }
        else if(is_local && is_lib) {
-               Image *iman= copy_image(ima);
+               Image *ima_new= copy_image(ima);
 
-               iman->id.us= 0;
+               ima_new->id.us= 0;
 
                /* Remap paths of new ID using old library as base. */
-               BKE_id_lib_local_paths(bmain, &iman->id);
+               BKE_id_lib_local_paths(bmain, ima->id.lib, &ima_new->id);
 
                tex= bmain->tex.first;
                while(tex) {
                        if(tex->id.lib==NULL) {
                                if(tex->ima==ima) {
-                                       tex->ima = iman;
-                                       iman->id.us++;
+                                       tex->ima = ima_new;
+                                       ima_new->id.us++;
                                        ima->id.us--;
                                }
                        }
@@ -407,8 +407,8 @@ void make_local_image(struct Image *ima)
                while(brush) {
                        if(brush->id.lib==NULL) {
                                if(brush->clone.image==ima) {
-                                       brush->clone.image = iman;
-                                       iman->id.us++;
+                                       brush->clone.image = ima_new;
+                                       ima_new->id.us++;
                                        ima->id.us--;
                                }
                        }
@@ -429,11 +429,11 @@ void make_local_image(struct Image *ima)
 
                                                for(a=0; a<me->totface; a++, tface++) { 
                                                        if(tface->tpage == ima) {
-                                                               tface->tpage = iman;
-                                                               if(iman->id.us == 0) {
+                                                               tface->tpage = ima_new;
+                                                               if(ima_new->id.us == 0) {
                                                                        tface->tpage->id.us= 1;
                                                                }
-                                                               id_lib_extern((ID*)iman);
+                                                               id_lib_extern((ID*)ima_new);
                                                        }
                                                }
                                        }
index 4edd032..6b4cdc7 100644 (file)
@@ -184,19 +184,19 @@ void make_local_lamp(Lamp *la)
                id_clear_lib_data(bmain, &la->id);
        }
        else if(is_local && is_lib) {
-               Lamp *lan= copy_lamp(la);
-               lan->id.us= 0;
+               Lamp *la_new= copy_lamp(la);
+               la_new->id.us= 0;
 
                /* Remap paths of new ID using old library as base. */
-               BKE_id_lib_local_paths(bmain, &lan->id);
+               BKE_id_lib_local_paths(bmain, la->id.lib, &la_new->id);
 
                ob= bmain->object.first;
                while(ob) {
                        if(ob->data==la) {
                                
                                if(ob->id.lib==NULL) {
-                                       ob->data= lan;
-                                       lan->id.us++;
+                                       ob->data= la_new;
+                                       la_new->id.us++;
                                        la->id.us--;
                                }
                        }
index 7c9e2be..4f02fdd 100644 (file)
@@ -271,17 +271,17 @@ void make_local_lattice(Lattice *lt)
                id_clear_lib_data(bmain, &lt->id);
        }
        else if(is_local && is_lib) {
-               Lattice *ltn= copy_lattice(lt);
-               ltn->id.us= 0;
+               Lattice *lt_new= copy_lattice(lt);
+               lt_new->id.us= 0;
 
                /* Remap paths of new ID using old library as base. */
-               BKE_id_lib_local_paths(bmain, &ltn->id);
+               BKE_id_lib_local_paths(bmain, lt->id.lib, &lt_new->id);
 
                for(ob= bmain->object.first; ob; ob= ob->id.next) {
                        if(ob->data==lt) {
                                if(ob->id.lib==NULL) {
-                                       ob->data= ltn;
-                                       ltn->id.us++;
+                                       ob->data= lt_new;
+                                       lt_new->id.us++;
                                        lt->id.us--;
                                }
                        }
index 7332b89..7a4780e 100644 (file)
  * from id_make_local() but then the make local functions would not be self
  * contained.
  * also note that the id _must_ have a library - campbell */
-void BKE_id_lib_local_paths(Main *bmain, ID *id)
+void BKE_id_lib_local_paths(Main *bmain, Library *lib, ID *id)
 {
-       char *bpath_user_data[2]= {bmain->name, (id)->lib->filepath};
+       char *bpath_user_data[2]= {bmain->name, lib->filepath};
 
        bpath_traverse_id(bmain, id,
                                          bpath_relocate_visitor,
@@ -1278,7 +1278,7 @@ int new_id(ListBase *lb, ID *id, const char *tname)
    don't have other library users. */
 void id_clear_lib_data(Main *bmain, ID *id)
 {
-       BKE_id_lib_local_paths(bmain, id);
+       BKE_id_lib_local_paths(bmain, id->lib, id);
 
        id->lib= NULL;
        id->flag= LIB_LOCAL;
index ecf74b1..60ae860 100644 (file)
@@ -364,12 +364,12 @@ void make_local_material(Material *ma)
        }
        /* Both user and local, so copy. */
        else if(is_local && is_lib) {
-               Material *man= copy_material(ma);
+               Material *ma_new= copy_material(ma);
 
-               man->id.us= 0;
+               ma_new->id.us= 0;
 
                /* Remap paths of new ID using old library as base. */
-               BKE_id_lib_local_paths(bmain, &man->id);
+               BKE_id_lib_local_paths(bmain, ma->id.lib, &ma_new->id);
 
                /* do objects */
                ob= bmain->object.first;
@@ -378,8 +378,8 @@ void make_local_material(Material *ma)
                                for(a=0; a<ob->totcol; a++) {
                                        if(ob->mat[a]==ma) {
                                                if(ob->id.lib==NULL) {
-                                                       ob->mat[a]= man;
-                                                       man->id.us++;
+                                                       ob->mat[a]= ma_new;
+                                                       ma_new->id.us++;
                                                        ma->id.us--;
                                                }
                                        }
@@ -394,8 +394,8 @@ void make_local_material(Material *ma)
                                for(a=0; a<me->totcol; a++) {
                                        if(me->mat[a]==ma) {
                                                if(me->id.lib==NULL) {
-                                                       me->mat[a]= man;
-                                                       man->id.us++;
+                                                       me->mat[a]= ma_new;
+                                                       ma_new->id.us++;
                                                        ma->id.us--;
                                                }
                                        }
@@ -410,8 +410,8 @@ void make_local_material(Material *ma)
                                for(a=0; a<cu->totcol; a++) {
                                        if(cu->mat[a]==ma) {
                                                if(cu->id.lib==NULL) {
-                                                       cu->mat[a]= man;
-                                                       man->id.us++;
+                                                       cu->mat[a]= ma_new;
+                                                       ma_new->id.us++;
                                                        ma->id.us--;
                                                }
                                        }
@@ -426,8 +426,8 @@ void make_local_material(Material *ma)
                                for(a=0; a<mb->totcol; a++) {
                                        if(mb->mat[a]==ma) {
                                                if(mb->id.lib==NULL) {
-                                                       mb->mat[a]= man;
-                                                       man->id.us++;
+                                                       mb->mat[a]= ma_new;
+                                                       ma_new->id.us++;
                                                        ma->id.us--;
                                                }
                                        }
index 3e3f16d..0883ec1 100644 (file)
@@ -174,17 +174,17 @@ void make_local_mball(MetaBall *mb)
                extern_local_mball(mb);
        }
        else if(is_local && is_lib) {
-               MetaBall *mbn= copy_mball(mb);
-               mbn->id.us= 0;
+               MetaBall *mb_new= copy_mball(mb);
+               mb_new->id.us= 0;
 
                /* Remap paths of new ID using old library as base. */
-               BKE_id_lib_local_paths(bmain, &mbn->id);
+               BKE_id_lib_local_paths(bmain, mb->id.lib, &mb_new->id);
 
                for(ob= G.main->object.first; ob; ob= ob->id.next) {
                        if(ob->data == mb) {
                                if(ob->id.lib==NULL) {
-                                       ob->data= mbn;
-                                       mbn->id.us++;
+                                       ob->data= mb_new;
+                                       mb_new->id.us++;
                                        mb->id.us--;
                                }
                        }
index ec9d487..ab45aee 100644 (file)
@@ -298,17 +298,17 @@ void make_local_mesh(Mesh *me)
                expand_local_mesh(me);
        }
        else if(is_local && is_lib) {
-               Mesh *men= copy_mesh(me);
-               men->id.us= 0;
+               Mesh *me_new= copy_mesh(me);
+               me_new->id.us= 0;
 
 
                /* Remap paths of new ID using old library as base. */
-               BKE_id_lib_local_paths(bmain, &men->id);
+               BKE_id_lib_local_paths(bmain, me->id.lib, &me_new->id);
 
                for(ob= bmain->object.first; ob; ob= ob->id.next) {
                        if(me == ob->data) {
                                if(ob->id.lib==NULL) {
-                                       set_mesh(ob, men);
+                                       set_mesh(ob, me_new);
                                }
                        }
                }
index 887b840..7ebb63c 100644 (file)
@@ -1233,12 +1233,12 @@ void make_local_object(Object *ob)
                        extern_local_object(ob);
                }
                else if(is_local && is_lib) {
-                       Object *obn= copy_object(ob);
+                       Object *ob_new= copy_object(ob);
 
-                       obn->id.us= 0;
+                       ob_new->id.us= 0;
                        
                        /* Remap paths of new ID using old library as base. */
-                       BKE_id_lib_local_paths(bmain, &obn->id);
+                       BKE_id_lib_local_paths(bmain, ob->id.lib, &ob_new->id);
 
                        sce= bmain->scene.first;
                        while(sce) {
@@ -1246,8 +1246,8 @@ void make_local_object(Object *ob)
                                        base= sce->base.first;
                                        while(base) {
                                                if(base->object==ob) {
-                                                       base->object= obn;
-                                                       obn->id.us++;
+                                                       base->object= ob_new;
+                                                       ob_new->id.us++;
                                                        ob->id.us--;
                                                }
                                                base= base->next;
index 7c71df9..0f2d14e 100644 (file)
@@ -3643,20 +3643,20 @@ void make_local_particlesettings(ParticleSettings *part)
                expand_local_particlesettings(part);
        }
        else if(is_local && is_lib) {
-               ParticleSettings *partn= psys_copy_settings(part);
+               ParticleSettings *part_new= psys_copy_settings(part);
 
-               partn->id.us= 0;
+               part_new->id.us= 0;
 
                /* Remap paths of new ID using old library as base. */
-               BKE_id_lib_local_paths(bmain, &partn->id);
+               BKE_id_lib_local_paths(bmain, part->id.lib, &part_new->id);
 
                /* do objects */
                for(ob= bmain->object.first; ob; ob= ob->id.next) {
                        ParticleSystem *psys;
                        for(psys= ob->particlesystem.first; psys; psys=psys->next){
                                if(psys->part==part && ob->id.lib==0) {
-                                       psys->part= partn;
-                                       partn->id.us++;
+                                       psys->part= part_new;
+                                       part_new->id.us++;
                                        part->id.us--;
                                }
                        }
index a14233e..d2c8a80 100644 (file)
@@ -106,19 +106,19 @@ void make_local_speaker(Speaker *spk)
                id_clear_lib_data(bmain, &spk->id);
        }
        else if(is_local && is_lib) {
-               Speaker *spkn= copy_speaker(spk);
-               spkn->id.us= 0;
+               Speaker *spk_new= copy_speaker(spk);
+               spk_new->id.us= 0;
 
                /* Remap paths of new ID using old library as base. */
-               BKE_id_lib_local_paths(bmain, &spkn->id);
+               BKE_id_lib_local_paths(bmain, spk->id.lib, &spk_new->id);
 
                ob= bmain->object.first;
                while(ob) {
                        if(ob->data==spk) {
 
                                if(ob->id.lib==NULL) {
-                                       ob->data= spkn;
-                                       spkn->id.us++;
+                                       ob->data= spk_new;
+                                       spk_new->id.us++;
                                        spk->id.us--;
                                }
                        }
index a67a61c..1320532 100644 (file)
@@ -973,20 +973,20 @@ void make_local_texture(Tex *tex)
                extern_local_texture(tex);
        }
        else if(is_local && is_lib) {
-               Tex *texn= copy_texture(tex);
+               Tex *tex_new= copy_texture(tex);
 
-               texn->id.us= 0;
+               tex_new->id.us= 0;
 
                /* Remap paths of new ID using old library as base. */
-               BKE_id_lib_local_paths(bmain, &texn->id);
+               BKE_id_lib_local_paths(bmain, tex->id.lib, &tex_new->id);
                
                ma= bmain->mat.first;
                while(ma) {
                        for(a=0; a<MAX_MTEX; a++) {
                                if(ma->mtex[a] && ma->mtex[a]->tex==tex) {
                                        if(ma->id.lib==NULL) {
-                                               ma->mtex[a]->tex= texn;
-                                               texn->id.us++;
+                                               ma->mtex[a]->tex= tex_new;
+                                               tex_new->id.us++;
                                                tex->id.us--;
                                        }
                                }
@@ -998,8 +998,8 @@ void make_local_texture(Tex *tex)
                        for(a=0; a<MAX_MTEX; a++) {
                                if(la->mtex[a] && la->mtex[a]->tex==tex) {
                                        if(la->id.lib==NULL) {
-                                               la->mtex[a]->tex= texn;
-                                               texn->id.us++;
+                                               la->mtex[a]->tex= tex_new;
+                                               tex_new->id.us++;
                                                tex->id.us--;
                                        }
                                }
@@ -1011,8 +1011,8 @@ void make_local_texture(Tex *tex)
                        for(a=0; a<MAX_MTEX; a++) {
                                if(wrld->mtex[a] && wrld->mtex[a]->tex==tex) {
                                        if(wrld->id.lib==NULL) {
-                                               wrld->mtex[a]->tex= texn;
-                                               texn->id.us++;
+                                               wrld->mtex[a]->tex= tex_new;
+                                               tex_new->id.us++;
                                                tex->id.us--;
                                        }
                                }
@@ -1023,8 +1023,8 @@ void make_local_texture(Tex *tex)
                while(br) {
                        if(br->mtex.tex==tex) {
                                if(br->id.lib==NULL) {
-                                       br->mtex.tex= texn;
-                                       texn->id.us++;
+                                       br->mtex.tex= tex_new;
+                                       tex_new->id.us++;
                                        tex->id.us--;
                                }
                        }
@@ -1035,8 +1035,8 @@ void make_local_texture(Tex *tex)
                        for(a=0; a<MAX_MTEX; a++) {
                                if(pa->mtex[a] && pa->mtex[a]->tex==tex) {
                                        if(pa->id.lib==NULL) {
-                                               pa->mtex[a]->tex= texn;
-                                               texn->id.us++;
+                                               pa->mtex[a]->tex= tex_new;
+                                               tex_new->id.us++;
                                                tex->id.us--;
                                        }
                                }
index 1d6972b..b3f1e14 100644 (file)
@@ -190,17 +190,17 @@ void make_local_world(World *wrld)
                id_clear_lib_data(bmain, &wrld->id);
        }
        else if(is_local && is_lib) {
-               World *wrldn= copy_world(wrld);
-               wrldn->id.us= 0;
+               World *wrld_new= copy_world(wrld);
+               wrld_new->id.us= 0;
 
                /* Remap paths of new ID using old library as base. */
-               BKE_id_lib_local_paths(bmain, &wrldn->id);
+               BKE_id_lib_local_paths(bmain, wrld->id.lib, &wrld_new->id);
 
                for(sce= bmain->scene.first; sce; sce= sce->id.next) {
                        if(sce->world == wrld) {
                                if(sce->id.lib==NULL) {
-                                       sce->world= wrldn;
-                                       wrldn->id.us++;
+                                       sce->world= wrld_new;
+                                       wrld_new->id.us++;
                                        wrld->id.us--;
                                }
                        }
index f4e46d0..09a1256 100644 (file)
@@ -307,10 +307,15 @@ static void object_delete_cb(bContext *C, Scene *scene, TreeElement *te, TreeSto
        }
 }
 
-static void id_local_cb(bContext *UNUSED(C), Scene *UNUSED(scene), TreeElement *UNUSED(te), TreeStoreElem *UNUSED(tsep), TreeStoreElem *tselem)
+static void id_local_cb(bContext *C, Scene *UNUSED(scene), TreeElement *UNUSED(te), TreeStoreElem *UNUSED(tsep), TreeStoreElem *tselem)
 {
        if (tselem->id->lib && (tselem->id->flag & LIB_EXTERN)) {
-               id_clear_lib_data(NULL, tselem->id);
+               /* if the ID type has no special local function,
+                * just clear the lib */
+               if (id_make_local(tselem->id, FALSE) == FALSE) {
+                       Main *bmain= CTX_data_main(C);
+                       id_clear_lib_data(bmain, tselem->id);
+               }
        }
 }