Skip to main content
Version: Next

RCaron.Jit

A project to compile RCaron to LINQ expression trees. Which then allows them to be compiled to IL, JITed and executed at speeds close to C# code.

This comes at the price of "dry" run times, which include needing to compile the code to an expression tree, then into IL, then JITing. For code that runs only once this is significantly slower than using the interpreter.

Usage

Currently it has no built-in way to be used from RCaron. You can manually build and load the RCaron.Jit project and use the functions in the RCaron.Jit.Hook type.

Issues

  • All variables have to be boxed to object in order to be assigned
  • The Compiler.CompileToBlock method is a little messy, and uses local methods, which end up creating heap allocations for closures

Not Implemented

  • Pipelines, because they'd still be painful for performance

Performance

The SimpleMathOp benchmark is $h = 2 * (2 + 3);

The Fibbonaci benchmark is:

rcaron
// it literally runs only 2 cycles of Fibonacci
$a = 0; $b = 1; $c = 0;
for($i = 0; $i < 2; $i++) {
$c = $a + $b;
$a = $b;
$b = $c;
}
rcaron
// it literally runs only 2 cycles of Fibonacci
$a = 0; $b = 1; $c = 0;
for($i = 0; $i < 2; $i++) {
$c = $a + $b;
$a = $b;
$b = $c;
}

Ran on power plan "Power Saver" on my laptop.

BenchmarkDotNet=v0.13.2, OS=Windows 11 (10.0.25300.1000) Intel Core i7-10750H CPU 2.60GHz, 1 CPU, 12 logical and 6 physical cores .NET SDK=7.0.200-preview.22628.1 [Host] : .NET 7.0.0 (7.0.22.51805), X64 RyuJIT AVX2 MediumRun : .NET 7.0.0 (7.0.22.51805), X64 RyuJIT AVX2 Job=MediumRun PowerPlanMode=00000000-0000-0000-0000-000000000000 IterationCount=15 LaunchCount=2 WarmupCount=10
BenchmarkDotNet=v0.13.2, OS=Windows 11 (10.0.25300.1000) Intel Core i7-10750H CPU 2.60GHz, 1 CPU, 12 logical and 6 physical cores .NET SDK=7.0.200-preview.22628.1 [Host] : .NET 7.0.0 (7.0.22.51805), X64 RyuJIT AVX2 MediumRun : .NET 7.0.0 (7.0.22.51805), X64 RyuJIT AVX2 Job=MediumRun PowerPlanMode=00000000-0000-0000-0000-000000000000 IterationCount=15 LaunchCount=2 WarmupCount=10
MethodMeanErrorStdDevRatioRatioSDAllocatedAlloc Ratio
SimpleMathOpFull4,878.9 ns68.12 ns97.70 ns1.000.003936 B1.00
SimpleMathOpParsed203.5 ns4.50 ns6.74 ns0.040.0096 B0.02
FibonacciFull14,268.9 ns79.44 ns113.94 ns2.930.049768 B2.48
FibonacciParsed2,797.4 ns11.55 ns17.28 ns0.570.011248 B0.32
SimpleMathOpFull_Jit420,898.9 ns1,451.15 ns2,127.07 ns86.311.6513282 B3.37
SimpleMathOpParsed_Jit366.7 ns2.04 ns3.06 ns0.080.0048 B0.01
FibonacciFull_Jit746,974.3 ns2,817.50 ns4,217.10 ns153.213.4725313 B6.43
FibonacciParsed_Jit185.2 ns0.54 ns0.79 ns0.040.00264 B0.07
SimpleMathOpFull_JitInterpret14,516.7 ns155.73 ns233.08 ns2.980.037296 B1.85
SimpleMathOpParsed_JitInterpret543.7 ns3.48 ns4.88 ns0.110.00192 B0.05
FibonacciFull_JitInterpret48,200.6 ns151.12 ns221.51 ns9.880.2218905 B4.80
FibonacciParsed_JitInterpret857.6 ns3.01 ns4.41 ns0.180.00336 B0.09