Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fully initialize all members of structs IdentifierActions, GeneratedCode and DefaultIdentifierActions #88021

Merged
merged 1 commit into from
Feb 9, 2024

Conversation

Chubercik
Copy link
Contributor

@Chubercik Chubercik commented Feb 6, 2024

Fixes #88015.

This one simple change

- ShaderCompiler::DefaultIdentifierActions actions;
+ ShaderCompiler::DefaultIdentifierActions actions = {};

is enough for Godot to compile on my setup, however, @akien-mga pointed out that this might be an issue in other places in the code here. He proposed an alternative fix (changing the struct code to fully initialize all its members), but I'd like to wait for the rendering team to voice their opinions about this.

EDIT: I went ahead with the alternative fix (and then some more for completeness' sake).

@Chubercik Chubercik requested a review from a team as a code owner February 6, 2024 13:44
@AThousandShips AThousandShips added this to the 4.3 milestone Feb 6, 2024
@akien-mga
Copy link
Member

Yeah I think you might have similar warnings in the other places if you do a clean build. At any rate, it doesn't make much sense IMO to initialize it only here and not everywhere else. So I think changing the struct to make sure it's always fully initialized would be the best option.

WDYT @clayjohn @BastiaanOlij ?

@AThousandShips
Copy link
Member

I think the issue might be the two texture modes in this struct

@Chubercik
Copy link
Contributor Author

Chubercik commented Feb 6, 2024

So

ShaderLanguage::TextureFilter default_filter = ShaderLanguage::TextureFilter::FILTER_DEFAULT;
ShaderLanguage::TextureRepeat default_repeat = ShaderLanguage::TextureRepeat::REPEAT_DEFAULT;

should fix the issue?

Edit: This is the bare minimum to fix the issue at hand, more initializations were added in the PR for completeness' sake.

@AThousandShips
Copy link
Member

AThousandShips commented Feb 6, 2024

I'd suggest initialising the values in the IdentifierActions struct as well while at it, like the uniforms pointer there and the booleans

@Chubercik
Copy link
Contributor Author

Think I'm gonna need some help here - I assume uniforms should be initialized to nullptr, given that it's a pointer, but what about the other values you speak of: they're of type HashMap, not sure what the syntax would look like here..

@AThousandShips
Copy link
Member

Not those, the bool values, the maps should be untouched they have default initialization

@Chubercik
Copy link
Contributor Author

Are we talking about the same bools?

HashMap<StringName, Pair<int *, int>> render_mode_values;
HashMap<StringName, bool *> render_mode_flags;
HashMap<StringName, bool *> usage_flag_pointers;
HashMap<StringName, bool *> write_flag_pointers;

I considered these lines of code, but the bool (and one int) pointers are inside HashMaps and I'm not sure what would initialization of those alone look like.

bool uses_global_textures;
bool uses_fragment_time;
bool uses_vertex_time;
bool uses_screen_texture_mipmaps;
bool uses_screen_texture;
bool uses_depth_texture;
bool uses_normal_roughness_texture;

If you were talking about these bools, they're in a different struct 😅

@AThousandShips
Copy link
Member

Yes I was talking about the GeneratedCode my bad :)

@Chubercik
Copy link
Contributor Author

Chubercik commented Feb 6, 2024

That's fine, one more question:

struct Texture {
	StringName name;
	ShaderLanguage::DataType type;
	ShaderLanguage::ShaderNode::Uniform::Hint hint;
	bool use_color = false;
	ShaderLanguage::TextureFilter filter;
	ShaderLanguage::TextureRepeat repeat;
	bool global;
	int array_size;
};

This snippet is from within GeneratedCode, should I also initialize type, hint, filter, etc. here?

@AThousandShips
Copy link
Member

I'd say yes, prefer to have everything basically intialized, false for bool, 0 for int and what ever default enum value applies

@clayjohn
Copy link
Member

clayjohn commented Feb 6, 2024

Yeah I think you might have similar warnings in the other places if you do a clean build. At any rate, it doesn't make much sense IMO to initialize it only here and not everywhere else. So I think changing the struct to make sure it's always fully initialized would be the best option.

WDYT @clayjohn @BastiaanOlij ?

This case is a bit unique. I think it is fully initialized in other areas property-by-property. The difference is that here we don't care about the actions so we left them all empty.

@Chubercik Chubercik changed the title Fix initialization of actions in material_storage.cpp Fully initialize all members of structs IdentifierActions, GeneratedCode and DefaultIdentifierActions Feb 6, 2024
@Chubercik
Copy link
Contributor Author

Hope I picked sane defaults for enums.

@BastiaanOlij
Copy link
Contributor

Yeah I think you might have similar warnings in the other places if you do a clean build. At any rate, it doesn't make much sense IMO to initialize it only here and not everywhere else. So I think changing the struct to make sure it's always fully initialized would be the best option.

WDYT @clayjohn @BastiaanOlij ?

I'm not against it, I've ran into problems before with compiler difference where some zero out structs and others keep junk data in there and caused sudden crashes. So if we're checking on that with compiler checks, might as well. I think the only issue with defining defaults in the structs is that there may be confusion when structs come from 3rd party APIs (like Vulkan and OpenXR). But we don't really have control over that.

@RandomShaper
Copy link
Member

I'd say yes, prefer to have everything basically intialized, false for bool, 0 for int and what ever default enum value applies

I agree and would like to add that, when the default value for an enum type is not relevant (you just want to avoid garbage) or when it's clear (somewhat fuzzy, I know) what's the natual default, I'd also find = {} acceptable.

Regarding 3rd-part structs, in the rendering driver code, for instance, I've chosen to do = {} on every Vulkan and D3D12 structs, to ensure C-like APIs don't provide garbage data.

Copy link
Member

@akien-mga akien-mga left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good to me.

Rendering headers are some of the last ones where we don't systematically initialize every struct members, and they have a lot of structs. So I'd like someone from the rendering team to sign off on this before merging, just in case I'm missing good reasons to keep those uninitialized.

@akien-mga akien-mga merged commit e9e5437 into godotengine:master Feb 9, 2024
16 checks passed
@akien-mga
Copy link
Member

Thanks!

@akien-mga
Copy link
Member

Cherry-picked for 4.2.2.

@akien-mga akien-mga added topic:shaders and removed cherrypick:4.2 Considered for cherry-picking into a future 4.2.x release topic:rendering labels Apr 16, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Compilation in dev mode fails on a warning about using an uninitialized variable
6 participants