Yes, that matches my expectation. We can isolate the effect to DLL loading.
We can build a simple DLL using zig as follows.
julia> using zig_jll
julia> write("add.zig",
"""
export fn add(a: i32, b: i32) i32 {
return a + b;
}
""")
56
julia> zig = zig_jll.zig();
julia> run(`$zig build-lib -dynamic -lc add.zig`);
julia> using Libdl
julia> @time dlopen("./libadd.so") # probably add.dll for you
Ptr{Nothing} @0x0000000000c39e10
julia> libadd = :libadd
:libadd
julia> @ccall libadd.add(5::Int32, 5::Int32)::Int32
10
Later I will expand this to build an executable that loads the DLL with timings. Then we’ll know if this is Julia specific or not.
julia> write("testdll.zig",
"""
const std = @import("std");
pub fn main() !void {
const start = std.time.microTimestamp();
var lib = try std.DynLib.open("libadd.dll");
const stop = std.time.microTimestamp();
const elapsed = stop - start;
const add = lib.lookup(*fn (i32,i32) i32, "add").?;
std.debug.print("add {} in {}\\n", .{add(5,6), elapsed});
}
""")
332
julia> run(`$zig build-exe testdll.zig`);
julia> run(`.\testdll.exe`)