Blender  V3.3
lib_query.c
Go to the documentation of this file.
1 /* SPDX-License-Identifier: GPL-2.0-or-later
2  * Copyright 2014 Blender Foundation. All rights reserved. */
3 
8 #include <stdlib.h>
9 
10 #include "DNA_anim_types.h"
11 
12 #include "BLI_ghash.h"
13 #include "BLI_linklist_stack.h"
14 #include "BLI_listbase.h"
15 #include "BLI_utildefines.h"
16 
17 #include "BKE_anim_data.h"
18 #include "BKE_idprop.h"
19 #include "BKE_idtype.h"
20 #include "BKE_lib_id.h"
21 #include "BKE_lib_query.h"
22 #include "BKE_main.h"
23 #include "BKE_node.h"
24 
25 /* status */
26 enum {
27  IDWALK_STOP = 1 << 0,
28 };
29 
30 typedef struct LibraryForeachIDData {
42 
44  int flag;
46  int cb_flag;
49 
50  /* Function to call for every ID pointers of current processed data, and its opaque user data
51  * pointer. */
53  void *user_data;
56  int status;
57 
58  /* To handle recursion. */
59  GSet *ids_handled; /* All IDs that are either already done, or still in ids_todo stack. */
60  BLI_LINKSTACK_DECLARE(ids_todo, ID *);
62 
64 {
65  return (data->status & IDWALK_STOP) != 0;
66 }
67 
69 {
71  return;
72  }
73 
74  const int flag = data->flag;
75  ID *old_id = *id_pp;
76 
77  /* Update the callback flags with the ones defined (or forbidden) in `data` by the generic
78  * caller code. */
79  cb_flag = ((cb_flag | data->cb_flag) & ~data->cb_flag_clear);
80 
81  /* Update the callback flags with some extra information regarding overrides: all 'loopback',
82  * 'internal', 'embedded' etc. ID pointers are never overridable. */
85  }
86 
87  const int callback_return = data->callback(
88  &(struct LibraryIDLinkCallbackData){.user_data = data->user_data,
89  .bmain = data->bmain,
90  .id_owner = data->owner_id,
91  .id_self = data->self_id,
92  .id_pointer = id_pp,
93  .cb_flag = cb_flag});
94  if (flag & IDWALK_READONLY) {
95  BLI_assert(*(id_pp) == old_id);
96  }
97  if (old_id && (flag & IDWALK_RECURSE)) {
98  if (BLI_gset_add((data)->ids_handled, old_id)) {
99  if (!(callback_return & IDWALK_RET_STOP_RECURSION)) {
100  BLI_LINKSTACK_PUSH(data->ids_todo, old_id);
101  }
102  }
103  }
104  if (callback_return & IDWALK_RET_STOP_ITER) {
105  data->status |= IDWALK_STOP;
106  }
107 }
108 
110 {
111  return data->flag;
112 }
113 
115  const int cb_flag,
116  const bool do_replace)
117 {
118  const int cb_flag_backup = data->cb_flag;
119  if (do_replace) {
120  data->cb_flag = cb_flag;
121  }
122  else {
123  data->cb_flag |= cb_flag;
124  }
125  return cb_flag_backup;
126 }
127 
128 static bool library_foreach_ID_link(Main *bmain,
129  ID *id_owner,
130  ID *id,
132  void *user_data,
133  int flag,
134  LibraryForeachIDData *inherit_data);
135 
137 {
138  BLI_assert(id_prop->type == IDP_ID);
139 
141  const int cb_flag = IDWALK_CB_USER | ((id_prop->flag & IDP_FLAG_OVERRIDABLE_LIBRARY) ?
142  0 :
144  BKE_LIB_FOREACHID_PROCESS_ID(data, id_prop->data.pointer, cb_flag);
145 }
146 
148 {
149  /* Needed e.g. for callbacks handling relationships. This call shall be absolutely read-only. */
150  ID *id = *id_pp;
151  const int flag = data->flag;
152 
155  return;
156  }
157  BLI_assert(id == *id_pp);
158 
159  if (id == NULL) {
160  return;
161  }
162 
163  if (flag & IDWALK_IGNORE_EMBEDDED_ID) {
164  /* Do Nothing. */
165  }
166  else if (flag & IDWALK_RECURSE) {
167  /* Defer handling into main loop, recursively calling BKE_library_foreach_ID_link in
168  * IDWALK_RECURSE case is troublesome, see T49553. */
169  /* XXX note that this breaks the 'owner id' thing now, we likely want to handle that
170  * differently at some point, but for now it should not be a problem in practice. */
171  if (BLI_gset_add(data->ids_handled, id)) {
172  BLI_LINKSTACK_PUSH(data->ids_todo, id);
173  }
174  }
175  else {
177  data->bmain, data->owner_id, id, data->callback, data->user_data, data->flag, data)) {
178  data->status |= IDWALK_STOP;
179  return;
180  }
181  }
182 }
183 
185 {
186  if (data->ids_handled != NULL) {
187  BLI_gset_free(data->ids_handled, NULL);
188  BLI_LINKSTACK_FREE(data->ids_todo);
189  }
190 }
191 
193 static bool library_foreach_ID_link(Main *bmain,
194  ID *id_owner,
195  ID *id,
197  void *user_data,
198  int flag,
199  LibraryForeachIDData *inherit_data)
200 {
201  LibraryForeachIDData data = {.bmain = bmain};
202 
203  BLI_assert(inherit_data == NULL || data.bmain == inherit_data->bmain);
204 
205  if (flag & IDWALK_RECURSE) {
206  /* For now, recursion implies read-only, and no internal pointers. */
207  flag |= IDWALK_READONLY;
209 
210  /* NOTE: This function itself should never be called recursively when IDWALK_RECURSE is set,
211  * see also comments in #BKE_library_foreach_ID_embedded.
212  * This is why we can always create this data here, and do not need to try and re-use it from
213  * `inherit_data`. */
215  BLI_LINKSTACK_INIT(data.ids_todo);
216 
217  BLI_gset_add(data.ids_handled, id);
218  }
219  else {
220  data.ids_handled = NULL;
221  }
222  data.flag = flag;
223  data.status = 0;
224  data.callback = callback;
225  data.user_data = user_data;
226 
227 #define CALLBACK_INVOKE_ID(check_id, cb_flag) \
228  { \
229  CHECK_TYPE_ANY((check_id), ID *, void *); \
230  BKE_lib_query_foreachid_process(&data, (ID **)&(check_id), (cb_flag)); \
231  if (BKE_lib_query_foreachid_iter_stop(&data)) { \
232  library_foreach_ID_data_cleanup(&data); \
233  return false; \
234  } \
235  } \
236  ((void)0)
237 
238 #define CALLBACK_INVOKE(check_id_super, cb_flag) \
239  { \
240  CHECK_TYPE(&((check_id_super)->id), ID *); \
241  BKE_lib_query_foreachid_process(&data, (ID **)&(check_id_super), (cb_flag)); \
242  if (BKE_lib_query_foreachid_iter_stop(&data)) { \
243  library_foreach_ID_data_cleanup(&data); \
244  return false; \
245  } \
246  } \
247  ((void)0)
248 
249  for (; id != NULL; id = (flag & IDWALK_RECURSE) ? BLI_LINKSTACK_POP(data.ids_todo) : NULL) {
250  data.self_id = id;
251  /* Note that we may call this functions sometime directly on an embedded ID, without any
252  * knowledge of the owner ID then.
253  * While not great, and that should be probably sanitized at some point, we cal live with it
254  * for now. */
255  data.owner_id = ((id->flag & LIB_EMBEDDED_DATA) != 0 && id_owner != NULL) ? id_owner :
256  data.self_id;
257 
258  /* inherit_data is non-NULL when this function is called for some sub-data ID
259  * (like root node-tree of a material).
260  * In that case, we do not want to generate those 'generic flags' from our current sub-data ID
261  * (the node tree), but re-use those generated for the 'owner' ID (the material). */
262  if (inherit_data == NULL) {
263  data.cb_flag = ID_IS_LINKED(id) ? IDWALK_CB_INDIRECT_USAGE : 0;
264  /* When an ID is defined as not refcounting its ID usages, it should never do it. */
265  data.cb_flag_clear = (id->tag & LIB_TAG_NO_USER_REFCOUNT) ?
267  0;
268  }
269  else {
270  data.cb_flag = inherit_data->cb_flag;
271  data.cb_flag_clear = inherit_data->cb_flag_clear;
272  }
273 
274  if (bmain != NULL && bmain->relations != NULL && (flag & IDWALK_READONLY) &&
275  (flag & IDWALK_DO_INTERNAL_RUNTIME_POINTERS) == 0 &&
276  (((bmain->relations->flag & MAINIDRELATIONS_INCLUDE_UI) == 0) ==
277  ((data.flag & IDWALK_INCLUDE_UI) == 0))) {
278  /* Note that this is minor optimization, even in worst cases (like id being an object with
279  * lots of drivers and constraints and modifiers, or material etc. with huge node tree),
280  * but we might as well use it (Main->relations is always assumed valid,
281  * it's responsibility of code creating it to free it,
282  * especially if/when it starts modifying Main database). */
284  id);
285  for (MainIDRelationsEntryItem *to_id_entry = entry->to_ids; to_id_entry != NULL;
286  to_id_entry = to_id_entry->next) {
288  &data, to_id_entry->id_pointer.to, to_id_entry->usage_flag);
291  return false;
292  }
293  }
294  continue;
295  }
296 
297  /* NOTE: ID.lib pointer is purposefully fully ignored here...
298  * We may want to add it at some point? */
299 
303  }
304 
305  if (id->override_library != NULL) {
310 
312  }
313 
317  &data);
320  return false;
321  }
322 
323  AnimData *adt = BKE_animdata_from_id(id);
324  if (adt) {
328  return false;
329  }
330  }
331 
332  const IDTypeInfo *id_type = BKE_idtype_get_info_from_id(id);
333  if (id_type->foreach_id != NULL) {
334  id_type->foreach_id(id, &data);
335 
338  return false;
339  }
340  }
341  }
342 
344  return true;
345 
346 #undef CALLBACK_INVOKE_ID
347 #undef CALLBACK_INVOKE
348 }
349 
351  Main *bmain, ID *id, LibraryIDLinkCallback callback, void *user_data, int flag)
352 {
353  library_foreach_ID_link(bmain, NULL, id, callback, user_data, flag, NULL);
354 }
355 
356 void BKE_library_update_ID_link_user(ID *id_dst, ID *id_src, const int cb_flag)
357 {
358  if (cb_flag & IDWALK_CB_USER) {
359  id_us_min(id_src);
360  id_us_plus(id_dst);
361  }
362  else if (cb_flag & IDWALK_CB_USER_ONE) {
363  id_us_ensure_real(id_dst);
364  }
365 }
366 
368 {
369  /* any type of ID can be used in custom props. */
370  if (id_owner->properties) {
371  return FILTER_ID_ALL;
372  }
373  const short id_type_owner = GS(id_owner->name);
374 
375  /* IDProps of armature bones and nodes, and bNode->id can use virtually any type of ID. */
376  if (ELEM(id_type_owner, ID_NT, ID_AR)) {
377  return FILTER_ID_ALL;
378  }
379 
380  /* Casting to non const.
381  * TODO(jbakker): We should introduce a ntree_id_has_tree function as we are actually not
382  * interested in the result. */
383  if (ntreeFromID((ID *)id_owner)) {
384  return FILTER_ID_ALL;
385  }
386 
387  if (BKE_animdata_from_id(id_owner)) {
388  /* AnimationData can use virtually any kind of data-blocks, through drivers especially. */
389  return FILTER_ID_ALL;
390  }
391 
392  if (ID_IS_OVERRIDE_LIBRARY_REAL(id_owner)) {
393  /* LibOverride data 'hierarchy root' can virtually point back to any type of ID. */
394  return FILTER_ID_ALL;
395  }
396 
397  switch ((ID_Type)id_type_owner) {
398  case ID_LI:
399  return FILTER_ID_LI;
400  case ID_SCE:
404  case ID_OB:
405  /* Could be more specific, but simpler to just always say 'yes' here. */
406  return FILTER_ID_ALL;
407  case ID_ME:
409  case ID_CU_LEGACY:
411  case ID_MB:
412  return FILTER_ID_MA;
413  case ID_MA:
414  return FILTER_ID_TE | FILTER_ID_GR;
415  case ID_TE:
416  return FILTER_ID_IM | FILTER_ID_OB;
417  case ID_LT:
418  return FILTER_ID_KE;
419  case ID_LA:
420  return FILTER_ID_TE;
421  case ID_CA:
422  return FILTER_ID_OB | FILTER_ID_IM;
423  case ID_KE:
424  /* Warning! key->from, could be more types in future? */
426  case ID_SCR:
427  return FILTER_ID_SCE;
428  case ID_WO:
429  return FILTER_ID_TE;
430  case ID_SPK:
431  return FILTER_ID_SO;
432  case ID_GR:
433  return FILTER_ID_OB | FILTER_ID_GR;
434  case ID_NT:
435  /* Could be more specific, but node.id has no type restriction... */
436  return FILTER_ID_ALL;
437  case ID_BR:
439  case ID_PA:
441  case ID_MC:
442  return FILTER_ID_GD | FILTER_ID_IM;
443  case ID_MSK:
444  /* WARNING! mask->parent.id, not typed. */
445  return FILTER_ID_MC;
446  case ID_LS:
447  return FILTER_ID_TE | FILTER_ID_OB;
448  case ID_LP:
449  return FILTER_ID_IM;
450  case ID_GD:
451  return FILTER_ID_MA;
452  case ID_WS:
453  return FILTER_ID_SCE;
454  case ID_CV:
455  return FILTER_ID_MA | FILTER_ID_OB;
456  case ID_PT:
457  return FILTER_ID_MA;
458  case ID_VO:
459  return FILTER_ID_MA;
460  case ID_SIM:
461  return FILTER_ID_OB | FILTER_ID_IM;
462  case ID_WM:
463  return FILTER_ID_SCE | FILTER_ID_WS;
464  case ID_IM:
465  case ID_VF:
466  case ID_TXT:
467  case ID_SO:
468  case ID_AR:
469  case ID_AC:
470  case ID_PAL:
471  case ID_PC:
472  case ID_CF:
473  /* Those types never use/reference other IDs... */
474  return 0;
475  case ID_IP:
476  /* Deprecated... */
477  return 0;
478  }
479 
481  return 0;
482 }
483 
484 bool BKE_library_id_can_use_idtype(ID *id_owner, const short id_type_used)
485 {
486  /* any type of ID can be used in custom props. */
487  if (id_owner->properties) {
488  return true;
489  }
490 
491  const short id_type_owner = GS(id_owner->name);
492  /* Exception for ID_LI as they don't exist as a filter. */
493  if (id_type_used == ID_LI) {
494  return id_type_owner == ID_LI;
495  }
496 
497  /* Exception: ID_KE aren't available as filter_id. */
498  if (id_type_used == ID_KE) {
499  return ELEM(id_type_owner, ID_ME, ID_CU_LEGACY, ID_LT);
500  }
501 
502  /* Exception: ID_SCR aren't available as filter_id. */
503  if (id_type_used == ID_SCR) {
504  return ELEM(id_type_owner, ID_WS);
505  }
506 
507  const uint64_t filter_id_type_used = BKE_idtype_idcode_to_idfilter(id_type_used);
508  const uint64_t can_be_used = BKE_library_id_can_use_filter_id(id_owner);
509  return (can_be_used & filter_id_type_used) != 0;
510 }
511 
512 /* ***** ID users iterator. ***** */
513 typedef struct IDUsersIter {
514  ID *id;
515 
517  int lb_idx;
518 
520  int count_direct, count_indirect; /* Set by callback. */
522 
524 {
525  ID **id_p = cb_data->id_pointer;
526  const int cb_flag = cb_data->cb_flag;
527  IDUsersIter *iter = cb_data->user_data;
528 
529  if (*id_p) {
530  /* 'Loopback' ID pointers (the ugly 'from' ones, like Key->from).
531  * Those are not actually ID usage, we can ignore them here.
532  */
533  if (cb_flag & IDWALK_CB_LOOPBACK) {
534  return IDWALK_RET_NOP;
535  }
536 
537  if (*id_p == iter->id) {
538 #if 0
539  printf(
540  "%s uses %s (refcounted: %d, userone: %d, used_one: %d, used_one_active: %d, "
541  "indirect_usage: %d)\n",
542  iter->curr_id->name,
543  iter->id->name,
544  (cb_flag & IDWALK_USER) ? 1 : 0,
545  (cb_flag & IDWALK_USER_ONE) ? 1 : 0,
546  (iter->id->tag & LIB_TAG_EXTRAUSER) ? 1 : 0,
547  (iter->id->tag & LIB_TAG_EXTRAUSER_SET) ? 1 : 0,
548  (cb_flag & IDWALK_INDIRECT_USAGE) ? 1 : 0);
549 #endif
550  if (cb_flag & IDWALK_CB_INDIRECT_USAGE) {
551  iter->count_indirect++;
552  }
553  else {
554  iter->count_direct++;
555  }
556  }
557  }
558 
559  return IDWALK_RET_NOP;
560 }
561 
562 int BKE_library_ID_use_ID(ID *id_user, ID *id_used)
563 {
564  IDUsersIter iter;
565 
566  /* We do not care about iter.lb_array/lb_idx here... */
567  iter.id = id_used;
568  iter.curr_id = id_user;
569  iter.count_direct = iter.count_indirect = 0;
570 
573 
574  return iter.count_direct + iter.count_indirect;
575 }
576 
577 static bool library_ID_is_used(Main *bmain, void *idv, const bool check_linked)
578 {
579  IDUsersIter iter;
580  ListBase *lb_array[INDEX_ID_MAX];
581  ID *id = idv;
582  int i = set_listbasepointers(bmain, lb_array);
583  bool is_defined = false;
584 
585  iter.id = id;
586  iter.count_direct = iter.count_indirect = 0;
587  while (i-- && !is_defined) {
588  ID *id_curr = lb_array[i]->first;
589 
590  if (!id_curr || !BKE_library_id_can_use_idtype(id_curr, GS(id->name))) {
591  continue;
592  }
593 
594  for (; id_curr && !is_defined; id_curr = id_curr->next) {
595  if (id_curr == id) {
596  /* We are not interested in self-usages (mostly from drivers or bone constraints...). */
597  continue;
598  }
599  iter.curr_id = id_curr;
601  bmain, id_curr, foreach_libblock_id_users_callback, &iter, IDWALK_READONLY);
602 
603  is_defined = ((check_linked ? iter.count_indirect : iter.count_direct) != 0);
604  }
605  }
606 
607  return is_defined;
608 }
609 
610 bool BKE_library_ID_is_locally_used(Main *bmain, void *idv)
611 {
612  return library_ID_is_used(bmain, idv, false);
613 }
614 
616 {
617  return library_ID_is_used(bmain, idv, true);
618 }
619 
620 void BKE_library_ID_test_usages(Main *bmain, void *idv, bool *is_used_local, bool *is_used_linked)
621 {
622  IDUsersIter iter;
623  ListBase *lb_array[INDEX_ID_MAX];
624  ID *id = idv;
625  int i = set_listbasepointers(bmain, lb_array);
626  bool is_defined = false;
627 
628  iter.id = id;
629  iter.count_direct = iter.count_indirect = 0;
630  while (i-- && !is_defined) {
631  ID *id_curr = lb_array[i]->first;
632 
633  if (!id_curr || !BKE_library_id_can_use_idtype(id_curr, GS(id->name))) {
634  continue;
635  }
636 
637  for (; id_curr && !is_defined; id_curr = id_curr->next) {
638  if (id_curr == id) {
639  /* We are not interested in self-usages (mostly from drivers or bone constraints...). */
640  continue;
641  }
642  iter.curr_id = id_curr;
644  bmain, id_curr, foreach_libblock_id_users_callback, &iter, IDWALK_READONLY);
645 
646  is_defined = (iter.count_direct != 0 && iter.count_indirect != 0);
647  }
648  }
649 
650  *is_used_local = (iter.count_direct != 0);
651  *is_used_linked = (iter.count_indirect != 0);
652 }
653 
654 /* ***** IDs usages.checking/tagging. ***** */
655 
656 /* Returns `true` if given ID is detected as part of at least one dependency loop, false otherwise.
657  */
659  const int tag,
660  const bool do_local_ids,
661  const bool do_linked_ids,
662  ID *id,
663  int *r_num_tagged)
664 {
665  /* We should never deal with embedded, not-in-main IDs here. */
666  BLI_assert((id->flag & LIB_EMBEDDED_DATA) == 0);
667 
669  id);
670 
671  if ((id_relations->tags & MAINIDRELATIONS_ENTRY_TAGS_PROCESSED) != 0) {
672  return false;
673  }
674  else if ((id_relations->tags & MAINIDRELATIONS_ENTRY_TAGS_INPROGRESS) != 0) {
675  /* This ID has not yet been fully processed. If this condition is reached, it means this is a
676  * dependency loop case. */
677  return true;
678  }
679 
680  if ((!do_linked_ids && ID_IS_LINKED(id)) || (!do_local_ids && !ID_IS_LINKED(id))) {
682  return false;
683  }
684 
685  if ((id->tag & tag) != 0) {
687  return false;
688  }
689 
690  if ((id->flag & LIB_FAKEUSER) != 0) {
691  /* This ID is forcefully kept around, and therefore never unused, no need to check it further.
692  */
694  return false;
695  }
696 
697  if (ELEM(GS(id->name), ID_WM, ID_WS, ID_SCE, ID_SCR, ID_LI)) {
698  /* Some 'root' ID types are never unused (even though they may not have actual users), unless
699  * their actual user-count is set to 0. */
701  return false;
702  }
703 
704  if (ELEM(GS(id->name), ID_IM)) {
705  /* Images which have a 'viewer' source (e.g. render results) should not be considered as
706  * orphaned/unused data. */
707  Image *image = (Image *)id;
708  if (image->source == IMA_SRC_VIEWER) {
710  return false;
711  }
712  }
713 
714  /* An ID user is 'valid' (i.e. may affect the 'used'/'not used' status of the ID it uses) if it
715  * does not match `ignored_usages`, and does match `required_usages`. */
716  const int ignored_usages = (IDWALK_CB_LOOPBACK | IDWALK_CB_EMBEDDED);
717  const int required_usages = (IDWALK_CB_USER | IDWALK_CB_USER_ONE);
718 
719  /* This ID may be tagged as unused if none of its users are 'valid', as defined above.
720  *
721  * First recursively check all its valid users, if all of them can be tagged as
722  * unused, then we can tag this ID as such too. */
723  bool has_valid_from_users = false;
724  bool is_part_of_dependency_loop = false;
726  for (MainIDRelationsEntryItem *id_from_item = id_relations->from_ids; id_from_item != NULL;
727  id_from_item = id_from_item->next) {
728  if ((id_from_item->usage_flag & ignored_usages) != 0 ||
729  (id_from_item->usage_flag & required_usages) == 0) {
730  continue;
731  }
732 
733  ID *id_from = id_from_item->id_pointer.from;
734  if ((id_from->flag & LIB_EMBEDDED_DATA) != 0) {
735  /* Directly 'by-pass' to actual real ID owner. */
736  const IDTypeInfo *type_info_from = BKE_idtype_get_info_from_id(id_from);
737  BLI_assert(type_info_from->owner_get != NULL);
738  id_from = type_info_from->owner_get(bmain, id_from, NULL);
739  }
740 
742  bmain, tag, do_local_ids, do_linked_ids, id_from, r_num_tagged)) {
743  /* Dependency loop case, ignore the `id_from` tag value here (as it should not be considered
744  * as valid yet), and presume that this is a 'valid user' case for now. . */
745  is_part_of_dependency_loop = true;
746  continue;
747  }
748  if ((id_from->tag & tag) == 0) {
749  has_valid_from_users = true;
750  break;
751  }
752  }
753  if (!has_valid_from_users && !is_part_of_dependency_loop) {
754  /* Tag the ID as unused, only in case it is not part of a dependency loop. */
755  id->tag |= tag;
756  if (r_num_tagged != NULL) {
757  r_num_tagged[INDEX_ID_NULL]++;
758  r_num_tagged[BKE_idtype_idcode_to_index(GS(id->name))]++;
759  }
760  }
761 
762  /* This ID is not being processed anymore.
763  *
764  * However, we can only tag is as sucessfully processed if either it was detected as part of a
765  * valid usage hierarchy, or, if detected as unused, if it was not part of a dependency loop.
766  *
767  * Otherwise, this is an undecided state, it will be resolved at the entry point of this
768  * recursive process for the root id (see below in #BKE_lib_query_unused_ids_tag calling code).
769  */
771  if (has_valid_from_users || !is_part_of_dependency_loop) {
773  }
774 
775  return is_part_of_dependency_loop;
776 }
777 
779  const int tag,
780  const bool do_local_ids,
781  const bool do_linked_ids,
782  const bool do_tag_recursive,
783  int *r_num_tagged)
784 {
785  /* First loop, to only check for immediately unused IDs (those with 0 user count).
786  * NOTE: It also takes care of clearing given tag for used IDs. */
787  ID *id;
788  FOREACH_MAIN_ID_BEGIN (bmain, id) {
789  if ((!do_linked_ids && ID_IS_LINKED(id)) || (!do_local_ids && !ID_IS_LINKED(id))) {
790  id->tag &= ~tag;
791  }
792  else if (id->us == 0) {
793  id->tag |= tag;
794  if (r_num_tagged != NULL) {
795  r_num_tagged[INDEX_ID_NULL]++;
796  r_num_tagged[BKE_idtype_idcode_to_index(GS(id->name))]++;
797  }
798  }
799  else {
800  id->tag &= ~tag;
801  }
802  }
804 
805  if (!do_tag_recursive) {
806  return;
807  }
808 
809  BKE_main_relations_create(bmain, 0);
810  FOREACH_MAIN_ID_BEGIN (bmain, id) {
812  bmain, tag, do_local_ids, do_linked_ids, id, r_num_tagged)) {
813  /* This root processed ID is part of one or more dependency loops.
814  *
815  * If it was not tagged, and its matching relations entry is not marked as processed, it
816  * means that it's the first encountered entry point of an 'unused archipelago' (i.e. the
817  * entry point to a set of IDs with relationships to each other, but no 'valid usage'
818  * relations to the current Blender file (like being part of a scene, etc.).
819  *
820  * So the entry can be tagged as processed, and the ID tagged as unused. */
821  if ((id->tag & tag) == 0) {
822  MainIDRelationsEntry *id_relations = BLI_ghash_lookup(
823  bmain->relations->relations_from_pointers, id);
824  if ((id_relations->tags & MAINIDRELATIONS_ENTRY_TAGS_PROCESSED) == 0) {
826  id->tag |= tag;
827  if (r_num_tagged != NULL) {
828  r_num_tagged[INDEX_ID_NULL]++;
829  r_num_tagged[BKE_idtype_idcode_to_index(GS(id->name))]++;
830  }
831  }
832  }
833  }
834 
835 #ifndef NDEBUG
836  /* Relation entry for the root processed ID should always be marked as processed now. */
837  MainIDRelationsEntry *id_relations = BLI_ghash_lookup(
838  bmain->relations->relations_from_pointers, id);
839  if ((id_relations->tags & MAINIDRELATIONS_ENTRY_TAGS_PROCESSED) == 0) {
840  BLI_assert((id_relations->tags & MAINIDRELATIONS_ENTRY_TAGS_PROCESSED) != 0);
841  }
842  BLI_assert((id_relations->tags & MAINIDRELATIONS_ENTRY_TAGS_INPROGRESS) == 0);
843 #endif
844  }
847 }
848 
850 {
851  ID *self_id = cb_data->id_self;
852  ID **id_p = cb_data->id_pointer;
853  const int cb_flag = cb_data->cb_flag;
854  bool *is_changed = cb_data->user_data;
855 
856  if (*id_p) {
857  /* The infamous 'from' pointers (Key.from, ...).
858  * those are not actually ID usage, so we ignore them here. */
859  if (cb_flag & IDWALK_CB_LOOPBACK) {
860  return IDWALK_RET_NOP;
861  }
862 
863  /* If checked id is used by an assumed used ID,
864  * then it is also used and not part of any linked archipelago. */
865  if (!(self_id->tag & LIB_TAG_DOIT) && ((*id_p)->tag & LIB_TAG_DOIT)) {
866  (*id_p)->tag &= ~LIB_TAG_DOIT;
867  *is_changed = true;
868  }
869  }
870 
871  return IDWALK_RET_NOP;
872 }
873 
874 void BKE_library_unused_linked_data_set_tag(Main *bmain, const bool do_init_tag)
875 {
876  ID *id;
877 
878  if (do_init_tag) {
879  FOREACH_MAIN_ID_BEGIN (bmain, id) {
880  if (id->lib && (id->tag & LIB_TAG_INDIRECT) != 0) {
881  id->tag |= LIB_TAG_DOIT;
882  }
883  else {
884  id->tag &= ~LIB_TAG_DOIT;
885  }
886  }
888  }
889 
890  for (bool do_loop = true; do_loop;) {
891  do_loop = false;
892  FOREACH_MAIN_ID_BEGIN (bmain, id) {
893  /* We only want to check that ID if it is currently known as used... */
894  if ((id->tag & LIB_TAG_DOIT) == 0) {
897  }
898  }
900  }
901 }
902 
904 {
905  ListBase *lb_array[INDEX_ID_MAX];
906 
907  bool do_loop = true;
908  while (do_loop) {
909  int i = set_listbasepointers(bmain, lb_array);
910  do_loop = false;
911 
912  while (i--) {
913  LISTBASE_FOREACH (ID *, id, lb_array[i]) {
914  if (!ID_IS_LINKED(id) || id->tag & LIB_TAG_DOIT) {
915  /* Local or non-indirectly-used ID (so far), no need to check it further. */
916  continue;
917  }
920  }
921  }
922  }
923 }
void BKE_animdata_foreach_id(struct AnimData *adt, struct LibraryForeachIDData *data)
Definition: anim_data.c:257
struct AnimData * BKE_animdata_from_id(const struct ID *id)
void IDP_foreach_property(struct IDProperty *id_property_root, int type_filter, IDPForeachPropertyCallback callback, void *user_data)
Definition: idprop.c:1117
uint64_t BKE_idtype_idcode_to_idfilter(short idcode)
Definition: idtype.c:206
int BKE_idtype_idcode_to_index(short idcode)
Definition: idtype.c:324
const struct IDTypeInfo * BKE_idtype_get_info_from_id(const struct ID *id)
void id_us_min(struct ID *id)
Definition: lib_id.c:313
void id_us_ensure_real(struct ID *id)
Definition: lib_id.c:260
void id_us_plus(struct ID *id)
Definition: lib_id.c:305
int(* LibraryIDLinkCallback)(LibraryIDLinkCallbackData *cb_data)
@ IDWALK_RECURSE
@ IDWALK_INCLUDE_UI
@ IDWALK_READONLY
@ IDWALK_DO_INTERNAL_RUNTIME_POINTERS
@ IDWALK_IGNORE_EMBEDDED_ID
@ IDWALK_CB_LOOPBACK
Definition: BKE_lib_query.h:54
@ IDWALK_CB_OVERRIDE_LIBRARY_NOT_OVERRIDABLE
Definition: BKE_lib_query.h:60
@ IDWALK_CB_USER_ONE
Definition: BKE_lib_query.h:79
@ IDWALK_CB_USER
Definition: BKE_lib_query.h:73
@ IDWALK_CB_INTERNAL
Definition: BKE_lib_query.h:67
@ IDWALK_CB_EMBEDDED
Definition: BKE_lib_query.h:48
@ IDWALK_CB_OVERRIDE_LIBRARY_REFERENCE
Definition: BKE_lib_query.h:57
@ IDWALK_CB_INDIRECT_USAGE
Definition: BKE_lib_query.h:41
@ IDWALK_RET_STOP_RECURSION
Definition: BKE_lib_query.h:87
@ IDWALK_RET_STOP_ITER
Definition: BKE_lib_query.h:85
@ IDWALK_RET_NOP
Definition: BKE_lib_query.h:83
#define BKE_LIB_FOREACHID_PROCESS_ID(_data, _id, _cb_flag)
#define FOREACH_MAIN_ID_END
Definition: BKE_main.h:367
int set_listbasepointers(struct Main *main, struct ListBase *lb[])
Definition: main.c:654
@ MAINIDRELATIONS_INCLUDE_UI
Definition: BKE_main.h:118
@ MAINIDRELATIONS_ENTRY_TAGS_PROCESSED
Definition: BKE_main.h:89
@ MAINIDRELATIONS_ENTRY_TAGS_INPROGRESS
Definition: BKE_main.h:100
void BKE_main_relations_create(struct Main *bmain, short flag)
Definition: main.c:276
void BKE_main_relations_free(struct Main *bmain)
Definition: main.c:311
#define FOREACH_MAIN_ID_BEGIN(_bmain, _id)
Definition: BKE_main.h:361
struct bNodeTree * ntreeFromID(struct ID *id)
Definition: node.cc:3231
#define BLI_assert_unreachable()
Definition: BLI_assert.h:93
#define BLI_assert(a)
Definition: BLI_assert.h:46
struct GSet GSet
Definition: BLI_ghash.h:340
unsigned int BLI_ghashutil_ptrhash(const void *key)
GSet * BLI_gset_new(GSetHashFP hashfp, GSetCmpFP cmpfp, const char *info) ATTR_MALLOC ATTR_WARN_UNUSED_RESULT
Definition: BLI_ghash.c:947
void * BLI_ghash_lookup(const GHash *gh, const void *key) ATTR_WARN_UNUSED_RESULT
Definition: BLI_ghash.c:734
bool BLI_ghashutil_ptrcmp(const void *a, const void *b)
void BLI_gset_free(GSet *gs, GSetKeyFreeFP keyfreefp)
Definition: BLI_ghash.c:1037
bool BLI_gset_add(GSet *gs, void *key)
Definition: BLI_ghash.c:969
#define LISTBASE_FOREACH(type, var, list)
Definition: BLI_listbase.h:336
#define ELEM(...)
@ IDP_TYPE_FILTER_ID
Definition: DNA_ID.h:155
#define FILTER_ID_OB
Definition: DNA_ID.h:916
#define FILTER_ID_MC
Definition: DNA_ID.h:912
@ IDP_ID
Definition: DNA_ID.h:142
#define FILTER_ID_ALL
Definition: DNA_ID.h:939
#define FILTER_ID_MA
Definition: DNA_ID.h:910
#define ID_IS_OVERRIDE_LIBRARY_REAL(_id)
Definition: DNA_ID.h:581
#define FILTER_ID_SO
Definition: DNA_ID.h:921
@ IDP_FLAG_OVERRIDABLE_LIBRARY
Definition: DNA_ID.h:172
#define FILTER_ID_CU_LEGACY
Definition: DNA_ID.h:903
#define FILTER_ID_BR
Definition: DNA_ID.h:901
@ INDEX_ID_NULL
Definition: DNA_ID.h:1057
@ INDEX_ID_MAX
Definition: DNA_ID.h:1058
#define FILTER_ID_WS
Definition: DNA_ID.h:928
#define FILTER_ID_VF
Definition: DNA_ID.h:924
#define ID_IS_LINKED(_id)
Definition: DNA_ID.h:566
#define FILTER_ID_GR
Definition: DNA_ID.h:905
#define FILTER_ID_TE
Definition: DNA_ID.h:922
#define FILTER_ID_LT
Definition: DNA_ID.h:909
#define FILTER_ID_LS
Definition: DNA_ID.h:908
#define FILTER_ID_ME
Definition: DNA_ID.h:913
#define FILTER_ID_MSK
Definition: DNA_ID.h:914
@ LIB_TAG_EXTRAUSER_SET
Definition: DNA_ID.h:700
@ LIB_TAG_NO_USER_REFCOUNT
Definition: DNA_ID.h:745
@ LIB_TAG_INDIRECT
Definition: DNA_ID.h:677
@ LIB_TAG_EXTRAUSER
Definition: DNA_ID.h:698
@ LIB_TAG_DOIT
Definition: DNA_ID.h:707
@ LIB_EMBEDDED_DATA
Definition: DNA_ID.h:635
@ LIB_FAKEUSER
Definition: DNA_ID.h:630
#define FILTER_ID_GD
Definition: DNA_ID.h:904
#define FILTER_ID_PC
Definition: DNA_ID.h:918
#define FILTER_ID_PAL
Definition: DNA_ID.h:917
#define FILTER_ID_KE
Definition: DNA_ID.h:934
#define FILTER_ID_IM
Definition: DNA_ID.h:906
#define FILTER_ID_SCE
Definition: DNA_ID.h:919
#define FILTER_ID_LI
Definition: DNA_ID.h:937
#define FILTER_ID_WO
Definition: DNA_ID.h:925
#define FILTER_ID_NT
Definition: DNA_ID.h:915
#define FILTER_ID_TXT
Definition: DNA_ID.h:923
ID_Type
Definition: DNA_ID_enums.h:44
@ ID_WM
Definition: DNA_ID_enums.h:72
@ ID_CA
Definition: DNA_ID_enums.h:56
@ ID_AR
Definition: DNA_ID_enums.h:66
@ ID_MC
Definition: DNA_ID_enums.h:73
@ ID_CF
Definition: DNA_ID_enums.h:78
@ ID_LI
Definition: DNA_ID_enums.h:46
@ ID_TE
Definition: DNA_ID_enums.h:52
@ ID_IM
Definition: DNA_ID_enums.h:53
@ ID_VO
Definition: DNA_ID_enums.h:83
@ ID_WS
Definition: DNA_ID_enums.h:79
@ ID_NT
Definition: DNA_ID_enums.h:68
@ ID_LA
Definition: DNA_ID_enums.h:55
@ ID_KE
Definition: DNA_ID_enums.h:58
@ ID_TXT
Definition: DNA_ID_enums.h:62
@ ID_SO
Definition: DNA_ID_enums.h:64
@ ID_SCE
Definition: DNA_ID_enums.h:45
@ ID_LS
Definition: DNA_ID_enums.h:75
@ ID_MSK
Definition: DNA_ID_enums.h:74
@ ID_GD
Definition: DNA_ID_enums.h:71
@ ID_CV
Definition: DNA_ID_enums.h:81
@ ID_PAL
Definition: DNA_ID_enums.h:76
@ ID_BR
Definition: DNA_ID_enums.h:69
@ ID_LP
Definition: DNA_ID_enums.h:80
@ ID_WO
Definition: DNA_ID_enums.h:59
@ ID_SIM
Definition: DNA_ID_enums.h:84
@ ID_MA
Definition: DNA_ID_enums.h:51
@ ID_AC
Definition: DNA_ID_enums.h:67
@ ID_SCR
Definition: DNA_ID_enums.h:60
@ ID_CU_LEGACY
Definition: DNA_ID_enums.h:49
@ ID_VF
Definition: DNA_ID_enums.h:61
@ ID_ME
Definition: DNA_ID_enums.h:48
@ ID_IP
Definition: DNA_ID_enums.h:57
@ ID_GR
Definition: DNA_ID_enums.h:65
@ ID_SPK
Definition: DNA_ID_enums.h:63
@ ID_MB
Definition: DNA_ID_enums.h:50
@ ID_LT
Definition: DNA_ID_enums.h:54
@ ID_OB
Definition: DNA_ID_enums.h:47
@ ID_PA
Definition: DNA_ID_enums.h:70
@ ID_PT
Definition: DNA_ID_enums.h:82
@ ID_PC
Definition: DNA_ID_enums.h:77
@ IMA_SRC_VIEWER
void * user_data
DEGForeachIDComponentCallback callback
depth_tx normal_tx diffuse_light_tx specular_light_tx volume_light_tx environment_tx ambient_occlusion_tx aov_value_tx in_weight_img image(1, GPU_R32F, Qualifier::WRITE, ImageType::FLOAT_2D_ARRAY, "out_weight_img") .image(3
#define GS(x)
Definition: iris.c:225
void BKE_lib_query_foreachid_process(LibraryForeachIDData *data, ID **id_pp, int cb_flag)
Definition: lib_query.c:68
void BKE_library_ID_test_usages(Main *bmain, void *idv, bool *is_used_local, bool *is_used_linked)
Definition: lib_query.c:620
static bool library_foreach_ID_link(Main *bmain, ID *id_owner, ID *id, LibraryIDLinkCallback callback, void *user_data, int flag, LibraryForeachIDData *inherit_data)
Definition: lib_query.c:193
void BKE_library_unused_linked_data_set_tag(Main *bmain, const bool do_init_tag)
Definition: lib_query.c:874
struct LibraryForeachIDData LibraryForeachIDData
bool BKE_library_ID_is_indirectly_used(Main *bmain, void *idv)
Definition: lib_query.c:615
void BKE_library_foreach_ID_embedded(LibraryForeachIDData *data, ID **id_pp)
Definition: lib_query.c:147
static bool library_ID_is_used(Main *bmain, void *idv, const bool check_linked)
Definition: lib_query.c:577
void BKE_library_foreach_ID_link(Main *bmain, ID *id, LibraryIDLinkCallback callback, void *user_data, int flag)
Definition: lib_query.c:350
static bool lib_query_unused_ids_tag_recurse(Main *bmain, const int tag, const bool do_local_ids, const bool do_linked_ids, ID *id, int *r_num_tagged)
Definition: lib_query.c:658
int BKE_library_ID_use_ID(ID *id_user, ID *id_used)
Definition: lib_query.c:562
static void library_foreach_ID_data_cleanup(LibraryForeachIDData *data)
Definition: lib_query.c:184
int BKE_lib_query_foreachid_process_flags_get(LibraryForeachIDData *data)
Definition: lib_query.c:109
@ IDWALK_STOP
Definition: lib_query.c:27
int BKE_lib_query_foreachid_process_callback_flag_override(LibraryForeachIDData *data, const int cb_flag, const bool do_replace)
Definition: lib_query.c:114
#define CALLBACK_INVOKE_ID(check_id, cb_flag)
void BKE_lib_query_idpropertiesForeachIDLink_callback(IDProperty *id_prop, void *user_data)
Definition: lib_query.c:136
static int foreach_libblock_id_users_callback(LibraryIDLinkCallbackData *cb_data)
Definition: lib_query.c:523
uint64_t BKE_library_id_can_use_filter_id(const ID *id_owner)
Definition: lib_query.c:367
void BKE_lib_query_unused_ids_tag(Main *bmain, const int tag, const bool do_local_ids, const bool do_linked_ids, const bool do_tag_recursive, int *r_num_tagged)
Definition: lib_query.c:778
void BKE_library_update_ID_link_user(ID *id_dst, ID *id_src, const int cb_flag)
Definition: lib_query.c:356
bool BKE_lib_query_foreachid_iter_stop(LibraryForeachIDData *data)
Definition: lib_query.c:63
struct IDUsersIter IDUsersIter
bool BKE_library_id_can_use_idtype(ID *id_owner, const short id_type_used)
Definition: lib_query.c:484
void BKE_library_indirectly_used_data_tag_clear(Main *bmain)
Definition: lib_query.c:903
bool BKE_library_ID_is_locally_used(Main *bmain, void *idv)
Definition: lib_query.c:610
static int foreach_libblock_used_linked_data_tag_clear_cb(LibraryIDLinkCallbackData *cb_data)
Definition: lib_query.c:849
unsigned __int64 uint64_t
Definition: stdint.h:90
struct ID * storage
Definition: DNA_ID.h:308
struct ID * hierarchy_root
Definition: DNA_ID.h:303
struct ID * reference
Definition: DNA_ID.h:294
void * pointer
Definition: DNA_ID.h:100
short flag
Definition: DNA_ID.h:109
IDPropertyData data
Definition: DNA_ID.h:117
char type
Definition: DNA_ID.h:108
IDTypeEmbeddedOwnerGetFunction owner_get
Definition: BKE_idtype.h:189
IDTypeForeachIDFunction foreach_id
Definition: BKE_idtype.h:174
int count_direct
Definition: lib_query.c:520
ListBase * lb_array[INDEX_ID_MAX]
Definition: lib_query.c:516
int count_indirect
Definition: lib_query.c:520
ID * curr_id
Definition: lib_query.c:519
Definition: DNA_ID.h:368
int tag
Definition: DNA_ID.h:387
struct Library * lib
Definition: DNA_ID.h:372
int us
Definition: DNA_ID.h:388
struct ID * newid
Definition: DNA_ID.h:370
IDProperty * properties
Definition: DNA_ID.h:409
IDOverrideLibrary * override_library
Definition: DNA_ID.h:412
struct ID * orig_id
Definition: DNA_ID.h:419
short flag
Definition: DNA_ID.h:383
void * next
Definition: DNA_ID.h:369
char name[66]
Definition: DNA_ID.h:378
BLI_LINKSTACK_DECLARE(ids_todo, ID *)
LibraryIDLinkCallback callback
Definition: lib_query.c:52
void * first
Definition: DNA_listBase.h:31
struct MainIDRelationsEntryItem * to_ids
Definition: BKE_main.h:68
struct MainIDRelationsEntryItem * from_ids
Definition: BKE_main.h:66
struct GHash * relations_from_pointers
Definition: BKE_main.h:107
Definition: BKE_main.h:121
struct MainIDRelations * relations
Definition: BKE_main.h:218