Quick answer: Compile on main thread with BurstCompiler.CompileFunctionPointer<T>. Pass the result into the job struct as a field. Invoke via fp.Invoke(...).
You declare a static method. Try to take its address inside a Burst-compiled job. NullReferenceException — pointer was never compiled.
The Fix
[BurstCompile]
public static class Behaviors {
public delegate void UpdateFn(ref float3 pos);
[BurstCompile, MonoPInvokeCallback(typeof(UpdateFn))]
public static void Walk(ref float3 pos) { pos.x += 0.1f; }
}
// Main thread setup
var walkFp = BurstCompiler.CompileFunctionPointer<Behaviors.UpdateFn>(Behaviors.Walk);
[BurstCompile]
public struct UpdateJob : IJob {
public FunctionPointer<Behaviors.UpdateFn> Walk;
public float3 Pos;
public void Execute() {
Walk.Invoke(ref Pos);
}
}
// Schedule
new UpdateJob { Walk = walkFp, Pos = default }.Run();
Compile once, reuse for many jobs. Compilation is JIT in Editor and AOT in builds; either way it must happen outside Burst code.
Verifying
Run job. Pos.x increments. Without compile call: NullReferenceException at Invoke.
“Compile once on main thread. Pass pointer in. Job dispatches.”
Related Issues
For NativeArray dispose, see dispose. For Burst determinism, see determinism.
Compile main. Pass pointer. Invoke flies.