ID Management: Sanitize and clarify our ID tags #88555
Labels
No Label
Interest
Alembic
Interest
Animation & Rigging
Interest
Asset System
Interest
Audio
Interest
Automated Testing
Interest
Blender Asset Bundle
Interest
BlendFile
Interest
Code Documentation
Interest
Collada
Interest
Compatibility
Interest
Compositing
Interest
Core
Interest
Cycles
Interest
Dependency Graph
Interest
Development Management
Interest
EEVEE
Interest
Freestyle
Interest
Geometry Nodes
Interest
Grease Pencil
Interest
ID Management
Interest
Images & Movies
Interest
Import Export
Interest
Line Art
Interest
Masking
Interest
Metal
Interest
Modeling
Interest
Modifiers
Interest
Motion Tracking
Interest
Nodes & Physics
Interest
OpenGL
Interest
Overlay
Interest
Overrides
Interest
Performance
Interest
Physics
Interest
Pipeline, Assets & IO
Interest
Platforms, Builds & Tests
Interest
Python API
Interest
Render & Cycles
Interest
Render Pipeline
Interest
Sculpt, Paint & Texture
Interest
Text Editor
Interest
Translations
Interest
Triaging
Interest
Undo
Interest
USD
Interest
User Interface
Interest
UV Editing
Interest
VFX & Video
Interest
Video Sequencer
Interest
Viewport & EEVEE
Interest
Virtual Reality
Interest
Vulkan
Interest
Wayland
Interest
Workbench
Interest: X11
Legacy
Asset Browser Project
Legacy
Blender 2.8 Project
Legacy
Milestone 1: Basic, Local Asset Browser
Legacy
OpenGL Error
Meta
Good First Issue
Meta
Papercut
Meta
Retrospective
Meta
Security
Module
Animation & Rigging
Module
Core
Module
Development Management
Module
Grease Pencil
Module
Modeling
Module
Nodes & Physics
Module
Pipeline, Assets & IO
Module
Platforms, Builds & Tests
Module
Python API
Module
Render & Cycles
Module
Sculpt, Paint & Texture
Module
Triaging
Module
User Interface
Module
VFX & Video
Module
Viewport & EEVEE
Platform
FreeBSD
Platform
Linux
Platform
macOS
Platform
Windows
Severity
High
Severity
Low
Severity
Normal
Severity
Unbreak Now!
Status
Archived
Status
Confirmed
Status
Duplicate
Status
Needs Info from Developers
Status
Needs Information from User
Status
Needs Triage
Status
Resolved
Type
Bug
Type
Design
Type
Known Issue
Type
Patch
Type
Report
Type
To Do
No Milestone
No project
No Assignees
4 Participants
Notifications
Due Date
No due date set.
Dependencies
No dependencies set.
Reference: blender/blender#88555
Loading…
Reference in New Issue
Block a user
No description provided.
Delete Branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Our current handling of ID management flags and their meaning is a bit fuzzy currently, and needs cleanup, and documentation.
For example,
LIB_TAG_NO_MAIN
is often implicitly implyingLIB_TAG_NO_USER_REFCOUNT
, but not always - and is not always a proper behavior.The meaning and differences between
LIB_TAG_COPIED_ON_WRITE
,LIB_TAG_COPIED_ON_WRITE_EVAL_RESULT
andLIB_TAG_LOCALIZED
is not clear, and not documented at all.etc.
IMPORTANT: This task is a sister of #90610 (ID Management: Sanitize and clarify our ID creation/copy tags), both will be worked on together.
Existing Tags
Here is a list of current existing tags which roles/meanings are not fully clear, or are inconsistent across our code base, with proposed new definition and behaviors for them if needed.
Proposed Removal
LIB_TAG_LOCAL
is set to0
(so it's not actually a tag), and is only used in one place inreadfile.c
... This is both confusing and useless, think we should get rid of it. If we really want a named enum for0
, we should name it e.g.LIB_TAG_NONE
, but think it's not needed.Proposed Renames
Those tags have a fairly clear and valid role, but their name could be more precise/specific.
LIB_TAG_EXTERN
LIB_TAG_LINKED_DIRECT
LIB_TAG_INDIRECT
LIB_TAG_LINKED_INDIRECT
LIB_TAG_MISSING
LIB_TAG_LINKED_MISSING
LIB_TAG_NEED_EXPAND
LIB_TAG_READFILE_NEED_EXPAND
LIB_TAG_ID_LINK_PLACEHOLDER
LIB_TAG_READFILE_LINK_PLACEHOLDER
LIB_TAG_NEED_LINK
LIB_TAG_READFILE_NEED_LINK
Proposed Changes
The five tags (
NO_MAIN
,LOCALIZED
,COPIED_ON_WRITE
andCOPIED_ON_WRITE_EVAL_RESULT
, andTEMP_MAIN
) used to mark an ID as not inG_MAIN
are the most problematic ones, as they are:General Proposed Changes
NOT_ALLOCATED
orNO_USER_REFCOUNT
) from the 'no main' tags.TEMP_MAIN
, orNO_MAIN
, orLOCALIZED
, orCOPIED_ON_WRITE
).** This could be made clearer at API level by using a dedicated enum instead of passing tags?
G_MAIN
or not.G_MAIN
asserts on any unsupported cases:**
LOCALIZED
**
COPIED_ON_WRITE
**
COPIED_ON_WRITE_EVAL_RESULT
Regular IDs
For regular IDs (in
G_MAIN
), the following flags are forbidden:**
NOT_ALLOCATED
**
NO_USER_REFCOUNT
**
NO_MAIN
**
TEMP_MAIN
**
LOCALIZED
**
COPIED_ON_WRITE
**
COPIED_ON_WRITE_EVAL_RESULT
This is already the case in practice, but should be clearly documented in comments of those flags.
LIB_TAG_TEMP_MAIN
IDs with this flag are basically regular IDs, they are simply isolated out the
G_MAIN
.PROPOSAL
TEMP_MAIN
ones as well.** Only potential exception: Do we allow
NO_USER_REFCOUNT
for them? Think we should notLIB_TAG_NO_MAIN
The main issue with this tag is the current behavior it implies regarding ID refcounting. Some code (like ID remapping in
lib_remap.c
) assumes aNO_MAIN
id should not be refcounting its ID usages, but has a flag to force it to do so.Another issue is that parts of the code add
NO_MAIN
as some kind of generic 'out ofG_MAIN
' tag, on top of more specific/restrictive tags.PROPOSAL:
NO_MAIN
from refcounting ID usages or not.NO_MAIN
simply means 'not in a Main struct'.NO_USER_REFCOUNT
if necessary.NO_USER_REFCOUNT
is also cleared.NO_MAIN
ID should never share any data (like caches etc.) with any other ID, it should be purely independent.NO_MAIN
ID should always use ID management code for allocation, freeing, etc.** This implies that
NOT_ALLOCATED
is forbidden forNO_MAIN
IDs.NO_MAIN
ID should always be in a state that allows adding it back intoG_MAIN
or another tempMain
. In other words, it should always be possible to 'convert' it into aTEMP_MAIN
or regular ID with minimal, generic ID management work (like user refcounting).LIB_TAG_COPIED_ON_WRITE
&LIB_TAG_COPIED_ON_WRITE_EVAL_RESULT
Those flags roles and behaviors are fairly clear and valid. Just need to check and ensure that the exclusion rule with the other 'no main' tags is always applied. Besides that, they are managed by depsgraph and their scope is clearly defined and limited.
LIB_TAG_LOCALIZED
This flag usage is by far the worse. It is currently somewhat niche, not very well documented, and extremely fuzzy.
AFAICT, it is currently only effectively assigned through one code paths:
LIB_ID_CREATE_LOCAL
flag) (preview_get_localized_world
andduplicate_ids
inrender_preview.c
).**Those generate localized nodetrees (by calling
ntreeLocalize
innode.cc
), even though ID itself is duplicated withLIB_ID_COPY_LOCALIZE
, which impliesLIB_ID_CREATE_NO_MAIN
. bad, very bad.PROPOSAL:G_MAIN
. This has to be handled by the each IDType ID management code.BKE_libblock_management_main_add
) into any other type of ID (inG_MAIN
or other 'no main' ones).** They are very similar to CoW IDs: code creating them should be responsible to control their life time and destruction.
NOTE: It is unclear currently if there would be more usages (besides preview code) for those
LOCALIZED
IDs.Embedded ID case
Embedded IDs should share the same 'ID amangement' tags as their owner. See #69169 (Improve handling of embedded data-blocks (root nodetrees and master collections)) for details.
Changed status from 'Needs Triage' to: 'Confirmed'
Added subscriber: @mont29
Sanitize and clarify our ID management flagsto ID Management: Sanitize and clarify our ID tagsAdded subscriber: @JacquesLucke
Generally sounds good, haven't looked at everything in detail yet. I have one general question. Have you considered adding an enum for the different "modes" an ID can be in (Main, NoMain, COW, ...), instead of having a flag for each. This way it's easier to guarantee that an ID is in exactly one of these modes.
@JacquesLucke we could, but then we'd need to first add a
runtime
struct to ID... I'd rather not add yet another runtime field to this struct, we already have too many of those. Keeping using flags is less disruptive for now imho?Maybe we could emulate this enum on top of the existing flags. So we'd get and set the "mode" through some helper functions, but internally it still uses all the different flags "for legacy reasons". That would make the API a bit more self-documenting and reduces the risk of setting invalid flag combinations.
yes that sounds doable indeed.
Added subscriber: @brecht
I like the
LIB_TAG_LINKED
andLIB_TAG_READFILE
names much better.For the 'no main' tags, it would be good if they could all share a prefix somehow and have these be mutually exclusive. Some ideas for naming.
OWNER_NONE
(NO_MAIN)OWNER_MAIN
OWNER_ASSET_MAIN
(TEMP_MAIN, not sure if asset is correct or if this has a wider purpose)OWNER_DEPSGRAPH
(COPIED_ON_WRITE and COPIED_ON_WRITE_EVAL_RESULT)Then some flags available when
OWNER_DEPSGRAPH
is set:LIB_TAG_DEPSGRAPH_LOCALIZED
LIB_TAG_DEPSGRAPH_EVAL_RESULT
Not sure how practical it is to make such changes.
Added subscriber: @monique