Skip to content

backends: apply per-subproject language args to targets#15990

Open
MaxandreOgeret wants to merge 2 commits into
mesonbuild:masterfrom
MaxandreOgeret:fix-subproject-lang-args
Open

backends: apply per-subproject language args to targets#15990
MaxandreOgeret wants to merge 2 commits into
mesonbuild:masterfrom
MaxandreOgeret:fix-subproject-lang-args

Conversation

@MaxandreOgeret

@MaxandreOgeret MaxandreOgeret commented Jul 8, 2026

Copy link
Copy Markdown
Contributor

Fixes #13260.

Per-subproject language args like -Dsub:c_args=-DFOO (or c_args in the default_options of a subproject() call) are accepted and stored, but never reach the compile or link command.
They end up as augments in the option store and resolve fine through a subproject-qualified key - which is why get_option('c_args') inside the subproject returns the value - but arg collection uses CoreData.get_external_args() / get_external_link_args(), which build the OptionKey without a subproject, so the augment is never consulted.

Fix: resolve the value per target with the existing augment- and override-aware get_option_for_target() at the three target-context call sites. The global getters are unchanged where no target context exists (compiler checks, linker detection, modules).

Two side effects, noted in the release snippet: <lang>_args / <lang>_link_args in a target's override_options now take effect (previously validated but ignored), and the per-subproject value replaces the global one rather than appending, consistent with get_option().

Added a unit test where sources #error if their expected flag is missing; it fails without the fix.

--

The second commit deletes get_external_args() / get_external_link_args() as suggested by @dcbaker. Modules now pass their subproject, other callers keep the top-level value explicitly.

Compile and link args were collected via CoreData.get_external_args()
and get_external_link_args(), which build an OptionKey without a
subproject. Per-subproject values such as -Dsub:c_args=-DFOO or c_args
in the default_options of a subproject() call were stored as augments
in the option store but never consulted, so they silently never reached
the compile or link command.

Resolve the value per target with the existing augment- and
override-aware CoreData.get_option_for_target() at the three
target-context call sites. As a side effect, <lang>_args and
<lang>_link_args entries in a target's override_options now take
effect as well.

Fixes mesonbuild#13260.
@bonzini bonzini added this to the 1.13 milestone Jul 9, 2026
@dcbaker

dcbaker commented Jul 9, 2026

Copy link
Copy Markdown
Member

This makes me think that the interface for get_external_args is just a foot-gun and either needs to be removed or needs to take a subproject: SubProject required parameter.

@MaxandreOgeret

MaxandreOgeret commented Jul 9, 2026 via email

Copy link
Copy Markdown
Contributor Author

@dcbaker

dcbaker commented Jul 9, 2026

Copy link
Copy Markdown
Member

I think I'd like to see get_external_args and get_external_link_args just deleted and replaced by calls to get_option_for_target or get_option_value in a single PR. The interfaces are fundamentally broken, and looking at the link variant I can see at least two users in modules that are broken in the same way that the calls you replaced here are.

@MaxandreOgeret

MaxandreOgeret commented Jul 9, 2026 via email

Copy link
Copy Markdown
Contributor Author

These wrappers built the OptionKey without a subproject, so any caller
in a subproject context silently got the top-level value and
per-subproject augments (-Dsub:c_args=...) were ignored. Replace them
with explicit optstore.get_value_for() calls that state their subproject
at the call site.

Module callers (gnome, external_project) now pass the current
subproject, so g-ir-scanner, gtkdoc and external project env vars pick
up per-subproject language args. Compiler sanity checks, linker
detection, the MSVC dep prefix probe and cargo cfg parsing keep the
top-level value, but that choice is now visible at the call site.

The lru_cache on get_external_link_args is dropped; the lookup is a few
dict accesses. gnome's gir scanner appended env flags to the returned
list, mutating the cached (now stored) value; it copies the list now.
@MaxandreOgeret

MaxandreOgeret commented Jul 9, 2026

Copy link
Copy Markdown
Contributor Author

Done, deleted both getters, converted the remaining callers in this PR (modules pass their subproject, detection/sanity-check paths keep the top-level value)

Thanks a lot for taking time to review this :)

@dcbaker

dcbaker commented Jul 10, 2026

Copy link
Copy Markdown
Member

Thanks for doing all of that, I think the end result is much better!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Passing c_args to a subproject does not work

3 participants