Skip to content

InteractiveUtils: Support callable objects as functions in introspection macros #58905

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

Open
wants to merge 10 commits into
base: master
Choose a base branch
from

Conversation

serenity4
Copy link
Member

Follow-up to the follow-up #57911, building on the changes to introspection functions to support signature tuples being provided as a single argument.

This enables support for calls of the form

@code_typed (::Returns{Int})(1)
@code_llvm (::Base.Fix2{typeof(+), Float64})(::Int)

by providing an extra use_signature_tuple::Bool = false parameter in gen_call_with_extracted_types. Setting this parameter to true changes the code generation from $fcn(f, Tuple{argtypes...}) to $fcn(Tuple{f, argtypes...}) (where $fcn can be e.g. code_typed, code_llvm etc).

topolarity and others added 7 commits July 3, 2025 13:49
This allows you to call, e.g., `code_typed((Foo, Int, Int))` to query
the code for `(::Foo)(::Int, ::Int)`
This allows you to call, e.g., `code_typed((Foo, Int, Int))` to query
the code for `(::Foo)(::Int, ::Int)`
@serenity4 serenity4 requested a review from topolarity July 4, 2025 14:40
@serenity4 serenity4 changed the title Support callable objects as functions in introspection macros InteractiveUtils: Support callable objects as functions in introspection macros Jul 4, 2025
@serenity4 serenity4 self-assigned this Jul 4, 2025
@topolarity
Copy link
Member

Has this impacted OpaqueClosure support on accident?

julia> const oc = Base.Experimental.@opaque Tuple{Int,Int}->Int (x,y)->(x+y)
(::Int64, ::Int64)->::Int64

julia> @code_typed oc(1,2)
OpaqueClosure(...) @ Core none:0 => Any

@serenity4
Copy link
Member Author

Oh, I think we had a branch on isa(f, OpaqueClosure) in the two-argument form of code_typed 🤔

@serenity4
Copy link
Member Author

serenity4 commented Jul 7, 2025

Perhaps we can have that branch for tt.parameters[1] <: OpaqueClosure for code_typed(tt::Type{<:Tuple})?

@topolarity
Copy link
Member

topolarity commented Jul 7, 2025

Yeah, that's why I ended up adding ArgInfo in #58891

I wonder if some equivalent should be moved into base/reflection.jl (or yeah, alternatively we could just make it the standard behavior of code_typed(::Type{<:Tuple}))

@serenity4
Copy link
Member Author

The tricky bit with opaque closures is that because every "method" can't be distinguished by their type alone, we need to provide the values to reflection functions (whereas at least for callables, we still use types)

To support that with the current implementation, we can use the 2-argument form for code_typed(f, tt) when we have an OpaqueClosure as first argument. The downside is that the macro will have to generate code for both code_typed(argtypes) and code_typed(f, tt) because we'll only know at runtime which branch should be taken.

It seems cleaner to use the ArgInfo form, but we can't assume the user function supports a method for it, otherwise all packages relying on gen_call_with_extracted_types_and_kwargs will stop working. Although, we could at least construct ArgInfo internally, then use a higher-order function to call a one-argument/two-argument method for a given function based on the type of arg0, so long as we never leak that internal structure to the user. I can give it a try.

@topolarity
Copy link
Member

otherwise all packages relying on gen_call_with_extracted_types_and_kwargs will stop working.

Isn't that already an issue with switching to the 1-arg form from the 2-arg form?

@serenity4
Copy link
Member Author

Isn't that already an issue with switching to the 1-arg form from the 2-arg form?

That's exactly why I only generate the 1-arg form conditionally on a non-default parameter being set. We could have a parameter that indicates whether or not to dispatch on ArgInfo, though.

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.

2 participants