@@ -1291,6 +1291,104 @@ function code_typed_opaque_closure(@nospecialize(oc::Core.OpaqueClosure);
12911291 end
12921292end
12931293
1294+ """
1295+ code_ircode(f, [types])
1296+
1297+ Return an array of pairs of `IRCode` and inferred return type if type inference succeeds.
1298+ The `Method` is included instead of `IRCode` otherwise.
1299+
1300+ See also: [`code_typed`](@ref)
1301+
1302+ # Internal Keyword Arguments
1303+
1304+ This section should be considered internal, and is only for who understands Julia compiler
1305+ internals.
1306+
1307+ - `world=Base.get_world_counter()`: optional, controls the world age to use when looking up
1308+ methods, use current world age if not specified.
1309+ - `interp=Core.Compiler.NativeInterpreter(world)`: optional, controls the interpreter to
1310+ use, use the native interpreter Julia uses if not specified.
1311+ - `optimize_until`: optional, controls the optimization passes to run. If it is a string,
1312+ it specifies the name of the pass up to which the optimizer is run. If it is an integer,
1313+ it specifies the number of passes to run. If it is `nothing` (default), all passes are
1314+ run.
1315+
1316+ # Example
1317+
1318+ One can put the argument types in a tuple to get the corresponding `code_ircode`.
1319+
1320+ ```jldoctest
1321+ julia> Base.code_ircode(+, (Float64, Int64))
1322+ 1-element Vector{Any}:
1323+ 388 1 ─ %1 = Base.sitofp(Float64, _3)::Float64
1324+ │ %2 = Base.add_float(_2, %1)::Float64
1325+ └── return %2
1326+ => Float64
1327+
1328+ julia> Base.code_ircode(+, (Float64, Int64); optimize_until = "compact 1")
1329+ 1-element Vector{Any}:
1330+ 388 1 ─ %1 = Base.promote(_2, _3)::Tuple{Float64, Float64}
1331+ │ %2 = Core._apply_iterate(Base.iterate, Base.:+, %1)::Float64
1332+ └── return %2
1333+ => Float64
1334+ ```
1335+ """
1336+ function code_ircode (
1337+ @nospecialize (f),
1338+ @nospecialize (types = default_tt (f));
1339+ world = get_world_counter (),
1340+ interp = Core. Compiler. NativeInterpreter (world),
1341+ optimize_until:: Union{Integer,AbstractString,Nothing} = nothing ,
1342+ )
1343+ if isa (f, Core. OpaqueClosure)
1344+ error (" OpaqueClosure not supported" )
1345+ end
1346+ ft = Core. Typeof (f)
1347+ if isa (types, Type)
1348+ u = unwrap_unionall (types)
1349+ tt = rewrap_unionall (Tuple{ft,u. parameters... }, types)
1350+ else
1351+ tt = Tuple{ft,types... }
1352+ end
1353+ return code_ircode_by_type (tt; world, interp, optimize_until)
1354+ end
1355+
1356+ """
1357+ code_ircode_by_type(types::Type{<:Tuple}; ...)
1358+
1359+ Similar to [`code_ircode`](@ref), except the argument is a tuple type describing
1360+ a full signature to query.
1361+ """
1362+ function code_ircode_by_type (
1363+ @nospecialize (tt:: Type );
1364+ world = get_world_counter (),
1365+ interp = Core. Compiler. NativeInterpreter (world),
1366+ optimize_until:: Union{Integer,AbstractString,Nothing} = nothing ,
1367+ )
1368+ ccall (:jl_is_in_pure_context , Bool, ()) &&
1369+ error (" code reflection cannot be used from generated functions" )
1370+ tt = to_tuple_type (tt)
1371+ matches = _methods_by_ftype (tt, - 1 , world):: Vector
1372+ asts = []
1373+ for match in matches
1374+ match = match:: Core.MethodMatch
1375+ meth = func_for_method_checked (match. method, tt, match. sparams)
1376+ (code, ty) = Core. Compiler. typeinf_ircode (
1377+ interp,
1378+ meth,
1379+ match. spec_types,
1380+ match. sparams,
1381+ optimize_until,
1382+ )
1383+ if code === nothing
1384+ push! (asts, meth => Any)
1385+ else
1386+ push! (asts, code => ty)
1387+ end
1388+ end
1389+ return asts
1390+ end
1391+
12941392function return_types (@nospecialize (f), @nospecialize (types= default_tt (f));
12951393 world = get_world_counter (),
12961394 interp = Core. Compiler. NativeInterpreter (world))
0 commit comments