e9cc0dfc9726e8abe028747be0519c3cc67b0e06
[blender.git] / source / blender / blenkernel / intern / lib_remap.c
1 /*
2  * This program is free software; you can redistribute it and/or
3  * modify it under the terms of the GNU General Public License
4  * as published by the Free Software Foundation; either version 2
5  * of the License, or (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software Foundation,
14  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15  */
16
17 /** \file
18  * \ingroup bke
19  *
20  * Contains management of ID's for remapping.
21  */
22
23 #include "CLG_log.h"
24
25 #include "MEM_guardedalloc.h"
26
27 #include "BLI_utildefines.h"
28
29 #include "BLI_rect.h"
30
31 #include "DNA_object_types.h"
32
33 #include "BKE_animsys.h"
34 #include "BKE_armature.h"
35 #include "BKE_collection.h"
36 #include "BKE_curve.h"
37 #include "BKE_layer.h"
38 #include "BKE_lib_id.h"
39 #include "BKE_lib_query.h"
40 #include "BKE_lib_remap.h"
41 #include "BKE_material.h"
42 #include "BKE_main.h"
43 #include "BKE_mball.h"
44 #include "BKE_modifier.h"
45 #include "BKE_multires.h"
46 #include "BKE_node.h"
47 #include "BKE_object.h"
48
49 #include "lib_intern.h"
50
51 #include "DEG_depsgraph.h"
52 #include "DEG_depsgraph_build.h"
53
54 static CLG_LogRef LOG = {.identifier = "bke.lib_remap"};
55
56 BKE_library_free_window_manager_cb free_windowmanager_cb = NULL;
57
58 void BKE_library_callback_free_window_manager_set(BKE_library_free_window_manager_cb func)
59 {
60   free_windowmanager_cb = func;
61 }
62
63 BKE_library_free_notifier_reference_cb free_notifier_reference_cb = NULL;
64
65 void BKE_library_callback_free_notifier_reference_set(BKE_library_free_notifier_reference_cb func)
66 {
67   free_notifier_reference_cb = func;
68 }
69
70 BKE_library_remap_editor_id_reference_cb remap_editor_id_reference_cb = NULL;
71
72 void BKE_library_callback_remap_editor_id_reference_set(
73     BKE_library_remap_editor_id_reference_cb func)
74 {
75   remap_editor_id_reference_cb = func;
76 }
77
78 typedef struct IDRemap {
79   Main *bmain; /* Only used to trigger depsgraph updates in the right bmain. */
80   ID *old_id;
81   ID *new_id;
82   /** The ID in which we are replacing old_id by new_id usages. */
83   ID *id;
84   short flag;
85
86   /* 'Output' data. */
87   short status;
88   /** Number of direct usecases that could not be remapped (e.g.: obdata when in edit mode). */
89   int skipped_direct;
90   /** Number of indirect usecases that could not be remapped. */
91   int skipped_indirect;
92   /** Number of skipped usecases that refcount the datablock. */
93   int skipped_refcounted;
94 } IDRemap;
95
96 /* IDRemap->flag enums defined in BKE_lib.h */
97
98 /* IDRemap->status */
99 enum {
100   /* *** Set by callback. *** */
101   ID_REMAP_IS_LINKED_DIRECT = 1 << 0,    /* new_id is directly linked in current .blend. */
102   ID_REMAP_IS_USER_ONE_SKIPPED = 1 << 1, /* There was some skipped 'user_one' usages of old_id. */
103 };
104
105 static int foreach_libblock_remap_callback(void *user_data, ID *id_self, ID **id_p, int cb_flag)
106 {
107   if (cb_flag & IDWALK_CB_PRIVATE) {
108     return IDWALK_RET_NOP;
109   }
110
111   IDRemap *id_remap_data = user_data;
112   ID *old_id = id_remap_data->old_id;
113   ID *new_id = id_remap_data->new_id;
114   ID *id = id_remap_data->id;
115
116   if (!old_id) { /* Used to cleanup all IDs used by a specific one. */
117     BLI_assert(!new_id);
118     old_id = *id_p;
119   }
120
121   if (*id_p && (*id_p == old_id)) {
122     /* Better remap to NULL than not remapping at all,
123      * then we can handle it as a regular remap-to-NULL case. */
124     if ((cb_flag & IDWALK_CB_NEVER_SELF) && (new_id == id_self)) {
125       new_id = NULL;
126     }
127
128     const bool is_reference = (cb_flag & IDWALK_CB_OVERRIDE_LIBRARY_REFERENCE) != 0;
129     const bool is_indirect = (cb_flag & IDWALK_CB_INDIRECT_USAGE) != 0;
130     const bool skip_indirect = (id_remap_data->flag & ID_REMAP_SKIP_INDIRECT_USAGE) != 0;
131     /* Note: proxy usage implies LIB_TAG_EXTERN, so on this aspect it is direct,
132      * on the other hand since they get reset to lib data on file open/reload it is indirect too.
133      * Edit Mode is also a 'skip direct' case. */
134     const bool is_obj = (GS(id->name) == ID_OB);
135     const bool is_obj_proxy = (is_obj && (((Object *)id)->proxy || ((Object *)id)->proxy_group));
136     const bool is_obj_editmode = (is_obj && BKE_object_is_in_editmode((Object *)id));
137     const bool is_never_null = ((cb_flag & IDWALK_CB_NEVER_NULL) && (new_id == NULL) &&
138                                 (id_remap_data->flag & ID_REMAP_FORCE_NEVER_NULL_USAGE) == 0);
139     const bool skip_reference = (id_remap_data->flag & ID_REMAP_SKIP_OVERRIDE_LIBRARY) != 0;
140     const bool skip_never_null = (id_remap_data->flag & ID_REMAP_SKIP_NEVER_NULL_USAGE) != 0;
141
142 #ifdef DEBUG_PRINT
143     printf(
144         "In %s (lib %p): Remapping %s (%p) to %s (%p) "
145         "(is_indirect: %d, skip_indirect: %d, is_reference: %d, skip_reference: %d)\n",
146         id->name,
147         id->lib,
148         old_id->name,
149         old_id,
150         new_id ? new_id->name : "<NONE>",
151         new_id,
152         is_indirect,
153         skip_indirect,
154         is_reference,
155         skip_reference);
156 #endif
157
158     if ((id_remap_data->flag & ID_REMAP_FLAG_NEVER_NULL_USAGE) &&
159         (cb_flag & IDWALK_CB_NEVER_NULL)) {
160       id->tag |= LIB_TAG_DOIT;
161     }
162
163     /* Special hack in case it's Object->data and we are in edit mode, and new_id is not NULL
164      * (otherwise, we follow common NEVER_NULL flags).
165      * (skipped_indirect too). */
166     if ((is_never_null && skip_never_null) ||
167         (is_obj_editmode && (((Object *)id)->data == *id_p) && new_id != NULL) ||
168         (skip_indirect && is_indirect) || (is_reference && skip_reference)) {
169       if (is_indirect) {
170         id_remap_data->skipped_indirect++;
171         if (is_obj) {
172           Object *ob = (Object *)id;
173           if (ob->data == *id_p && ob->proxy != NULL) {
174             /* And another 'Proudly brought to you by Proxy Hell' hack!
175              * This will allow us to avoid clearing 'LIB_EXTERN' flag of obdata of proxies... */
176             id_remap_data->skipped_direct++;
177           }
178         }
179       }
180       else if (is_never_null || is_obj_editmode || is_reference) {
181         id_remap_data->skipped_direct++;
182       }
183       else {
184         BLI_assert(0);
185       }
186       if (cb_flag & IDWALK_CB_USER) {
187         id_remap_data->skipped_refcounted++;
188       }
189       else if (cb_flag & IDWALK_CB_USER_ONE) {
190         /* No need to count number of times this happens, just a flag is enough. */
191         id_remap_data->status |= ID_REMAP_IS_USER_ONE_SKIPPED;
192       }
193     }
194     else {
195       if (!is_never_null) {
196         *id_p = new_id;
197         DEG_id_tag_update_ex(id_remap_data->bmain,
198                              id_self,
199                              ID_RECALC_COPY_ON_WRITE | ID_RECALC_TRANSFORM | ID_RECALC_GEOMETRY);
200       }
201       if (cb_flag & IDWALK_CB_USER) {
202         /* NOTE: We don't user-count IDs which are not in the main database.
203          * This is because in certain conditions we can have data-blocks in
204          * the main which are referencing data-blocks outside of it.
205          * For example, BKE_mesh_new_from_object() called on an evaluated
206          * object will cause such situation.
207          */
208         if ((old_id->tag & LIB_TAG_NO_MAIN) == 0) {
209           id_us_min(old_id);
210         }
211         if (new_id != NULL && (new_id->tag & LIB_TAG_NO_MAIN) == 0) {
212           /* We do not want to handle LIB_TAG_INDIRECT/LIB_TAG_EXTERN here. */
213           new_id->us++;
214         }
215       }
216       else if (cb_flag & IDWALK_CB_USER_ONE) {
217         id_us_ensure_real(new_id);
218         /* We cannot affect old_id->us directly, LIB_TAG_EXTRAUSER(_SET)
219          * are assumed to be set as needed, that extra user is processed in final handling. */
220       }
221       if (!is_indirect || is_obj_proxy) {
222         id_remap_data->status |= ID_REMAP_IS_LINKED_DIRECT;
223       }
224       /* We need to remap proxy_from pointer of remapped proxy... sigh. */
225       if (is_obj_proxy && new_id != NULL) {
226         Object *ob = (Object *)id;
227         if (ob->proxy == (Object *)new_id) {
228           ob->proxy->proxy_from = ob;
229         }
230       }
231     }
232   }
233
234   return IDWALK_RET_NOP;
235 }
236
237 static void libblock_remap_data_preprocess(IDRemap *r_id_remap_data)
238 {
239   switch (GS(r_id_remap_data->id->name)) {
240     case ID_OB: {
241       ID *old_id = r_id_remap_data->old_id;
242       if (!old_id || GS(old_id->name) == ID_AR) {
243         Object *ob = (Object *)r_id_remap_data->id;
244         /* Object's pose holds reference to armature bones... sic */
245         /* Note that in theory, we should have to bother about
246          * linked/non-linked/never-null/etc. flags/states.
247          * Fortunately, this is just a tag, so we can accept to 'over-tag' a bit for pose recalc,
248          * and avoid another complex and risky condition nightmare like the one we have in
249          * foreach_libblock_remap_callback()... */
250         if (ob->pose && (!old_id || ob->data == old_id)) {
251           BLI_assert(ob->type == OB_ARMATURE);
252           ob->pose->flag |= POSE_RECALC;
253           /* We need to clear pose bone pointers immediately, things like undo writefile may be
254            * called before pose is actually recomputed, can lead to segfault... */
255           BKE_pose_clear_pointers(ob->pose);
256         }
257       }
258       break;
259     }
260     default:
261       break;
262   }
263 }
264
265 /**
266  * Can be called with both old_ob and new_ob being NULL,
267  * this means we have to check whole Main database then.
268  */
269 static void libblock_remap_data_postprocess_object_update(Main *bmain,
270                                                           Object *old_ob,
271                                                           Object *new_ob)
272 {
273   if (new_ob == NULL) {
274     /* In case we unlinked old_ob (new_ob is NULL), the object has already
275      * been removed from the scenes and their collections. We still have
276      * to remove the NULL children from collections not used in any scene. */
277     BKE_collections_object_remove_nulls(bmain);
278   }
279
280   BKE_main_collection_sync_remap(bmain);
281
282   if (old_ob == NULL) {
283     for (Object *ob = bmain->objects.first; ob != NULL; ob = ob->id.next) {
284       if (ob->type == OB_MBALL && BKE_mball_is_basis(ob)) {
285         DEG_id_tag_update(&ob->id, ID_RECALC_GEOMETRY);
286       }
287     }
288   }
289   else {
290     for (Object *ob = bmain->objects.first; ob != NULL; ob = ob->id.next) {
291       if (ob->type == OB_MBALL && BKE_mball_is_basis_for(ob, old_ob)) {
292         DEG_id_tag_update(&ob->id, ID_RECALC_GEOMETRY);
293         break; /* There is only one basis... */
294       }
295     }
296   }
297 }
298
299 /* Can be called with both old_collection and new_collection being NULL,
300  * this means we have to check whole Main database then. */
301 static void libblock_remap_data_postprocess_collection_update(Main *bmain,
302                                                               Collection *UNUSED(old_collection),
303                                                               Collection *new_collection)
304 {
305   if (new_collection == NULL) {
306     /* XXX Complex cases can lead to NULL pointers in other collections than old_collection,
307      * and BKE_main_collection_sync_remap() does not tolerate any of those, so for now always check
308      * whole existing collections for NULL pointers.
309      * I'd consider optimizing that whole collection remapping process a TODO for later. */
310     BKE_collections_child_remove_nulls(bmain, NULL /*old_collection*/);
311   }
312   else {
313     /* Temp safe fix, but a "tad" brute force... We should probably be able to use parents from
314      * old_collection instead? */
315     BKE_main_collections_parent_relations_rebuild(bmain);
316   }
317
318   BKE_main_collection_sync_remap(bmain);
319 }
320
321 static void libblock_remap_data_postprocess_obdata_relink(Main *bmain, Object *ob, ID *new_id)
322 {
323   if (ob->data == new_id) {
324     switch (GS(new_id->name)) {
325       case ID_ME:
326         multires_force_sculpt_rebuild(ob);
327         break;
328       case ID_CU:
329         BKE_curve_type_test(ob);
330         break;
331       default:
332         break;
333     }
334     test_object_modifiers(ob);
335     BKE_object_materials_test(bmain, ob, new_id);
336   }
337 }
338
339 static void libblock_remap_data_postprocess_nodetree_update(Main *bmain, ID *new_id)
340 {
341   /* Update all group nodes using a node group. */
342   ntreeUpdateAllUsers(bmain, new_id);
343 }
344
345 /**
346  * Execute the 'data' part of the remapping (that is, all ID pointers from other ID data-blocks).
347  *
348  * Behavior differs depending on whether given \a id is NULL or not:
349  * - \a id NULL: \a old_id must be non-NULL, \a new_id may be NULL (unlinking \a old_id) or not
350  *   (remapping \a old_id to \a new_id).
351  *   The whole \a bmain database is checked, and all pointers to \a old_id
352  *   are remapped to \a new_id.
353  * - \a id is non-NULL:
354  *   + If \a old_id is NULL, \a new_id must also be NULL,
355  *     and all ID pointers from \a id are cleared
356  *     (i.e. \a id does not references any other data-block anymore).
357  *   + If \a old_id is non-NULL, behavior is as with a NULL \a id, but only within given \a id.
358  *
359  * \param bmain: the Main data storage to operate on (must never be NULL).
360  * \param id: the data-block to operate on
361  * (can be NULL, in which case we operate over all IDs from given bmain).
362  * \param old_id: the data-block to dereference (may be NULL if \a id is non-NULL).
363  * \param new_id: the new data-block to replace \a old_id references with (may be NULL).
364  * \param r_id_remap_data: if non-NULL, the IDRemap struct to use
365  * (uselful to retrieve info about remapping process).
366  */
367 ATTR_NONNULL(1)
368 static void libblock_remap_data(
369     Main *bmain, ID *id, ID *old_id, ID *new_id, const short remap_flags, IDRemap *r_id_remap_data)
370 {
371   IDRemap id_remap_data;
372   const int foreach_id_flags = (remap_flags & ID_REMAP_NO_INDIRECT_PROXY_DATA_USAGE) != 0 ?
373                                    IDWALK_NO_INDIRECT_PROXY_DATA_USAGE :
374                                    IDWALK_NOP;
375
376   if (r_id_remap_data == NULL) {
377     r_id_remap_data = &id_remap_data;
378   }
379   r_id_remap_data->bmain = bmain;
380   r_id_remap_data->old_id = old_id;
381   r_id_remap_data->new_id = new_id;
382   r_id_remap_data->id = NULL;
383   r_id_remap_data->flag = remap_flags;
384   r_id_remap_data->status = 0;
385   r_id_remap_data->skipped_direct = 0;
386   r_id_remap_data->skipped_indirect = 0;
387   r_id_remap_data->skipped_refcounted = 0;
388
389   if (id) {
390 #ifdef DEBUG_PRINT
391     printf("\tchecking id %s (%p, %p)\n", id->name, id, id->lib);
392 #endif
393     r_id_remap_data->id = id;
394     libblock_remap_data_preprocess(r_id_remap_data);
395     BKE_library_foreach_ID_link(
396         NULL, id, foreach_libblock_remap_callback, (void *)r_id_remap_data, foreach_id_flags);
397   }
398   else {
399     /* Note that this is a very 'brute force' approach,
400      * maybe we could use some depsgraph to only process objects actually using given old_id...
401      * sounds rather unlikely currently, though, so this will do for now. */
402     ID *id_curr;
403
404     FOREACH_MAIN_ID_BEGIN (bmain, id_curr) {
405       if (BKE_library_id_can_use_idtype(id_curr, GS(old_id->name))) {
406         /* Note that we cannot skip indirect usages of old_id here (if requested),
407          * we still need to check it for the user count handling...
408          * XXX No more true (except for debug usage of those skipping counters). */
409         r_id_remap_data->id = id_curr;
410         libblock_remap_data_preprocess(r_id_remap_data);
411         BKE_library_foreach_ID_link(NULL,
412                                     id_curr,
413                                     foreach_libblock_remap_callback,
414                                     (void *)r_id_remap_data,
415                                     foreach_id_flags);
416       }
417     }
418     FOREACH_MAIN_ID_END;
419   }
420
421   /* XXX We may not want to always 'transfer' fake-user from old to new id...
422    *     Think for now it's desired behavior though,
423    *     we can always add an option (flag) to control this later if needed. */
424   if (old_id && (old_id->flag & LIB_FAKEUSER)) {
425     id_fake_user_clear(old_id);
426     id_fake_user_set(new_id);
427   }
428
429   id_us_clear_real(old_id);
430
431   if (new_id && (new_id->tag & LIB_TAG_INDIRECT) &&
432       (r_id_remap_data->status & ID_REMAP_IS_LINKED_DIRECT)) {
433     new_id->tag &= ~LIB_TAG_INDIRECT;
434     new_id->flag &= ~LIB_INDIRECT_WEAK_LINK;
435     new_id->tag |= LIB_TAG_EXTERN;
436   }
437
438 #ifdef DEBUG_PRINT
439   printf("%s: %d occurrences skipped (%d direct and %d indirect ones)\n",
440          __func__,
441          r_id_remap_data->skipped_direct + r_id_remap_data->skipped_indirect,
442          r_id_remap_data->skipped_direct,
443          r_id_remap_data->skipped_indirect);
444 #endif
445 }
446
447 /**
448  * Replace all references in given Main to \a old_id by \a new_id
449  * (if \a new_id is NULL, it unlinks \a old_id).
450  */
451 void BKE_libblock_remap_locked(Main *bmain, void *old_idv, void *new_idv, const short remap_flags)
452 {
453   IDRemap id_remap_data;
454   ID *old_id = old_idv;
455   ID *new_id = new_idv;
456   int skipped_direct, skipped_refcounted;
457
458   BLI_assert(old_id != NULL);
459   BLI_assert((new_id == NULL) || GS(old_id->name) == GS(new_id->name));
460   BLI_assert(old_id != new_id);
461
462   libblock_remap_data(bmain, NULL, old_id, new_id, remap_flags, &id_remap_data);
463
464   if (free_notifier_reference_cb) {
465     free_notifier_reference_cb(old_id);
466   }
467
468   /* We assume editors do not hold references to their IDs... This is false in some cases
469    * (Image is especially tricky here),
470    * editors' code is to handle refcount (id->us) itself then. */
471   if (remap_editor_id_reference_cb) {
472     remap_editor_id_reference_cb(old_id, new_id);
473   }
474
475   skipped_direct = id_remap_data.skipped_direct;
476   skipped_refcounted = id_remap_data.skipped_refcounted;
477
478   /* If old_id was used by some ugly 'user_one' stuff (like Image or Clip editors...), and user
479    * count has actually been incremented for that, we have to decrease once more its user count...
480    * unless we had to skip some 'user_one' cases. */
481   if ((old_id->tag & LIB_TAG_EXTRAUSER_SET) &&
482       !(id_remap_data.status & ID_REMAP_IS_USER_ONE_SKIPPED)) {
483     id_us_clear_real(old_id);
484   }
485
486   if (old_id->us - skipped_refcounted < 0) {
487     CLOG_ERROR(&LOG,
488                "Error in remapping process from '%s' (%p) to '%s' (%p): "
489                "wrong user count in old ID after process (summing up to %d)",
490                old_id->name,
491                old_id,
492                new_id ? new_id->name : "<NULL>",
493                new_id,
494                old_id->us - skipped_refcounted);
495     BLI_assert(0);
496   }
497
498   if (skipped_direct == 0) {
499     /* old_id is assumed to not be used directly anymore... */
500     if (old_id->lib && (old_id->tag & LIB_TAG_EXTERN)) {
501       old_id->tag &= ~LIB_TAG_EXTERN;
502       old_id->tag |= LIB_TAG_INDIRECT;
503     }
504   }
505
506   /* Some after-process updates.
507    * This is a bit ugly, but cannot see a way to avoid it.
508    * Maybe we should do a per-ID callback for this instead? */
509   switch (GS(old_id->name)) {
510     case ID_OB:
511       libblock_remap_data_postprocess_object_update(bmain, (Object *)old_id, (Object *)new_id);
512       break;
513     case ID_GR:
514       libblock_remap_data_postprocess_collection_update(
515           bmain, (Collection *)old_id, (Collection *)new_id);
516       break;
517     case ID_ME:
518     case ID_CU:
519     case ID_MB:
520       if (new_id) { /* Only affects us in case obdata was relinked (changed). */
521         for (Object *ob = bmain->objects.first; ob; ob = ob->id.next) {
522           libblock_remap_data_postprocess_obdata_relink(bmain, ob, new_id);
523         }
524       }
525       break;
526     default:
527       break;
528   }
529
530   /* Node trees may virtually use any kind of data-block... */
531   /* XXX Yuck!!!! nodetree update can do pretty much any thing when talking about py nodes,
532    *     including creating new data-blocks (see T50385), so we need to unlock main here. :(
533    *     Why can't we have re-entrent locks? */
534   BKE_main_unlock(bmain);
535   libblock_remap_data_postprocess_nodetree_update(bmain, new_id);
536   BKE_main_lock(bmain);
537
538   /* Full rebuild of DEG! */
539   DEG_relations_tag_update(bmain);
540 }
541
542 void BKE_libblock_remap(Main *bmain, void *old_idv, void *new_idv, const short remap_flags)
543 {
544   BKE_main_lock(bmain);
545
546   BKE_libblock_remap_locked(bmain, old_idv, new_idv, remap_flags);
547
548   BKE_main_unlock(bmain);
549 }
550
551 /**
552  * Unlink given \a id from given \a bmain
553  * (does not touch to indirect, i.e. library, usages of the ID).
554  *
555  * \param do_flag_never_null: If true, all IDs using \a idv in a 'non-NULL' way are flagged by
556  * #LIB_TAG_DOIT flag (quite obviously, 'non-NULL' usages can never be unlinked by this function).
557  */
558 void BKE_libblock_unlink(Main *bmain,
559                          void *idv,
560                          const bool do_flag_never_null,
561                          const bool do_skip_indirect)
562 {
563   const short remap_flags = (do_skip_indirect ? ID_REMAP_SKIP_INDIRECT_USAGE : 0) |
564                             (do_flag_never_null ? ID_REMAP_FLAG_NEVER_NULL_USAGE : 0);
565
566   BKE_main_lock(bmain);
567
568   BKE_libblock_remap_locked(bmain, idv, NULL, remap_flags);
569
570   BKE_main_unlock(bmain);
571 }
572
573 /**
574  * Similar to libblock_remap, but only affects IDs used by given \a idv ID.
575  *
576  * \param old_idv: Unlike BKE_libblock_remap, can be NULL,
577  * in which case all ID usages by given \a idv will be cleared.
578  * \param us_min_never_null: If \a true and new_id is NULL,
579  * 'NEVER_NULL' ID usages keep their old id, but this one still gets its user count decremented
580  * (needed when given \a idv is going to be deleted right after being unlinked).
581  */
582 /* Should be able to replace all _relink() funcs (constraints, rigidbody, etc.) ? */
583 /* XXX Arg! Naming... :(
584  *     _relink? avoids confusion with _remap, but is confusing with _unlink
585  *     _remap_used_ids?
586  *     _remap_datablocks?
587  *     BKE_id_remap maybe?
588  *     ... sigh
589  */
590 void BKE_libblock_relink_ex(
591     Main *bmain, void *idv, void *old_idv, void *new_idv, const short remap_flags)
592 {
593   ID *id = idv;
594   ID *old_id = old_idv;
595   ID *new_id = new_idv;
596
597   /* No need to lock here, we are only affecting given ID, not bmain database. */
598
599   BLI_assert(id);
600   if (old_id) {
601     BLI_assert((new_id == NULL) || GS(old_id->name) == GS(new_id->name));
602     BLI_assert(old_id != new_id);
603   }
604   else {
605     BLI_assert(new_id == NULL);
606   }
607
608   libblock_remap_data(bmain, id, old_id, new_id, remap_flags, NULL);
609
610   /* Some after-process updates.
611    * This is a bit ugly, but cannot see a way to avoid it.
612    * Maybe we should do a per-ID callback for this instead?
613    */
614   switch (GS(id->name)) {
615     case ID_SCE:
616     case ID_GR: {
617       if (old_id) {
618         switch (GS(old_id->name)) {
619           case ID_OB:
620             libblock_remap_data_postprocess_object_update(
621                 bmain, (Object *)old_id, (Object *)new_id);
622             break;
623           case ID_GR:
624             libblock_remap_data_postprocess_collection_update(
625                 bmain, (Collection *)old_id, (Collection *)new_id);
626             break;
627           default:
628             break;
629         }
630       }
631       else {
632         /* No choice but to check whole objects/collections. */
633         libblock_remap_data_postprocess_collection_update(bmain, NULL, NULL);
634         libblock_remap_data_postprocess_object_update(bmain, NULL, NULL);
635       }
636       break;
637     }
638     case ID_OB:
639       if (new_id) { /* Only affects us in case obdata was relinked (changed). */
640         libblock_remap_data_postprocess_obdata_relink(bmain, (Object *)id, new_id);
641       }
642       break;
643     default:
644       break;
645   }
646
647   DEG_relations_tag_update(bmain);
648 }
649
650 static int id_relink_to_newid_looper(void *UNUSED(user_data),
651                                      ID *UNUSED(self_id),
652                                      ID **id_pointer,
653                                      const int cb_flag)
654 {
655   if (cb_flag & IDWALK_CB_PRIVATE) {
656     return IDWALK_RET_NOP;
657   }
658
659   ID *id = *id_pointer;
660   if (id) {
661     /* See: NEW_ID macro */
662     if (id->newid) {
663       BKE_library_update_ID_link_user(id->newid, id, cb_flag);
664       *id_pointer = id->newid;
665     }
666     else if (id->tag & LIB_TAG_NEW) {
667       id->tag &= ~LIB_TAG_NEW;
668       BKE_libblock_relink_to_newid(id);
669     }
670   }
671   return IDWALK_RET_NOP;
672 }
673
674 /**
675  * Similar to #libblock_relink_ex,
676  * but is remapping IDs to their newid value if non-NULL, in given \a id.
677  *
678  * Very specific usage, not sure we'll keep it on the long run,
679  * currently only used in Object/Collection duplication code...
680  */
681 void BKE_libblock_relink_to_newid(ID *id)
682 {
683   if (ID_IS_LINKED(id)) {
684     return;
685   }
686
687   BKE_library_foreach_ID_link(NULL, id, id_relink_to_newid_looper, NULL, 0);
688 }