2026-10-25: Menai performance improved again

Published: 2026-10-25

In the last week or so I've implemented quite a few new optimizations and a few bug fixes to older ones. There's better constant folding, better inter-procedural type analysis, better inlining, and a new instruction scheduling pass.

New benchmark data

Latest Menai benchmark numbers. Pretty-much everything is better, but there's something a little surprising about RUBIKS_LIST. I need to investigate.

BASE64-DECODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
standard-1k                       0.162          0.158
standard-64k                     11.705         11.509
url-1k                            0.165          0.158
url-64k                          11.621         11.507
──────────────────────────────────────────────────────


BASE64-ENCODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
standard-1k                       0.067          0.064
standard-64k                      5.034          4.988
unpadded-1k                       0.069          0.069
url-64k                           4.978          4.947
──────────────────────────────────────────────────────


BMP-DECODE
────────────────────────────────────────────────────────
Case                            mean (ms)       min (ms)
────────────────────────────────────────────────────────
truecolour-64x64                    0.311          0.291
truecolour-128x128                  1.364          1.338
truecolour-topdown-128x128          1.323          1.309
truecolour-alpha-128x128            1.587          1.581
padded-65x64                        0.310          0.296
────────────────────────────────────────────────────────


BMP-ENCODE
────────────────────────────────────────────────────────
Case                            mean (ms)       min (ms)
────────────────────────────────────────────────────────
truecolour-64x64                    0.795          0.741
truecolour-128x128                  7.509          7.485
truecolour-topdown-128x128          7.538          7.484
truecolour-alpha-128x128           10.528         10.466
padded-65x64                        0.823          0.808
────────────────────────────────────────────────────────


CALENDAR
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
short_5d                          0.023          0.020
month_20d                         0.076          0.075
quarter_60d                       0.202          0.199
year_250d                         0.855          0.833
months_600d                       1.543          1.492
──────────────────────────────────────────────────────


CSV-DECODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
plain-1000x10                     5.046          4.974
quoted-1000x10                    7.714          7.536
escaped-1000x10                   9.470          9.390
multiline-1000                    1.603          1.590
wide-100x100                      3.320          3.287
──────────────────────────────────────────────────────


CSV-ENCODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
plain-1000x10                     4.864          4.799
quoted-1000x10                   11.341         11.219
escaped-1000x10                   7.263          7.200
wide-100x100                      2.471          2.438
──────────────────────────────────────────────────────


DEFLATE-COMPRESS
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
text-4k                           0.827          0.799
text-32k                          3.857          3.739
incremental-16k                   5.596          5.482
runs-32k                         10.956         10.780
──────────────────────────────────────────────────────


DEFLATE-DECOMPRESS
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
text-4k                           0.314          0.301
text-32k                          0.512          0.490
incremental-16k                   0.712          0.696
stored-8k                         0.196          0.188
runs-32k                          1.628          1.577
──────────────────────────────────────────────────────


DOCX-DECODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
minimal                           0.507          0.490
document-100                      2.195          2.159
document-500                      9.394          9.316
document-2000                    36.609         36.469
styles-100                        3.295          3.207
numbering-9                       1.775          1.731
media-16                          4.494          4.416
full-500                         13.376         13.212
──────────────────────────────────────────────────────


DOCX-ENCODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
minimal                           0.073          0.064
document-100                      0.251          0.240
document-500                      0.978          0.966
styles-100                        0.385          0.377
numbering-9                       0.129          0.122
media-16                          0.276          0.265
full-500                          1.265          1.247
──────────────────────────────────────────────────────


HTML-DECODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
wide-1000                         5.202          5.175
deep-200                          0.453          0.446
attributes-500                    3.964          3.935
mixed-500                         4.116          4.078
entities-2000                    12.623         12.552
void-1000                        11.794         11.771
omitted-end-tags-1000             2.595          2.556
raw-text-500                      4.804          4.790
realistic-500                     8.511          8.446
──────────────────────────────────────────────────────


HTML-ENCODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
wide-1000                         1.681          1.644
deep-200                          0.210          0.171
attributes-500                    0.807          0.791
mixed-500                         1.951          1.937
void-1000                         3.723          3.699
escaping-2000                     4.015          3.963
declarations-1000                 0.532          0.525
──────────────────────────────────────────────────────


JSON-DECODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
object                            0.012          0.011
flat_array                        0.076          0.074
flat_object                       0.069          0.067
mixed_nested                      0.149          0.146
string_heavy                      0.053          0.052
numbers_array                     0.016          0.015
unicode_strings                   0.008          0.007
long_string                       0.064          0.063
deep_array                        0.132          0.131
──────────────────────────────────────────────────────


JSON-ENCODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
object                            0.011          0.009
flat_array                        0.014          0.012
flat_object                       0.029          0.028
mixed_nested                      0.057          0.055
string_heavy                      0.075          0.074
numbers_array                     0.009          0.008
unicode_strings                   0.003          0.003
long_string                       0.228          0.225
──────────────────────────────────────────────────────


PNG-DECODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
greyscale-64x64                   2.021          1.967
greyscale-alpha-64x64             8.039          7.969
palette-128x128                   5.459          5.413
truecolour-128x128               45.387         45.282
truecolour-alpha-128x128         61.102         60.812
truecolour-192x192              105.115        104.807
──────────────────────────────────────────────────────


PNG-ENCODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
truecolour-48x48                 18.796         18.675
truecolour-96x96                164.595        164.272
truecolour-alpha-96x96          285.242        284.833
──────────────────────────────────────────────────────


PPTX-DECODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
minimal                           1.031          1.003
slides-10                         4.046          4.003
slides-50                        17.374         17.278
slides-200                       67.603         67.289
shapes-50                        13.103         13.005
masters-8                         8.438          8.403
media-16                          8.008          7.920
theme-and-masters                 6.441          6.400
full-50                          77.273         76.999
──────────────────────────────────────────────────────


PPTX-ENCODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
minimal                           0.102          0.093
slides-10                         0.321          0.311
slides-50                         1.274          1.260
shapes-50                         1.257          1.224
masters-8                         0.645          0.634
media-16                          0.511          0.501
theme-and-masters                 0.492          0.478
full-50                           5.954          5.868
──────────────────────────────────────────────────────


REGEXP
───────────────────────────────────────────────────────
Case                           mean (ms)       min (ms)
───────────────────────────────────────────────────────
compile-per-line                   1.545          1.527
search-prefix-log                  0.031          0.029
search-class-numbers               0.035          0.034
search-alternation                 0.079          0.077
search-all-class                  11.287         11.189
search-all-prefix                  1.657          1.605
search-groups-log                  0.053          0.050
search-all-groups-numbers         34.679         34.224
split-whitespace                  13.308         13.220
replace-whitespace                77.362         76.491
replace-groups-dates              25.360         25.014
chained-per-line                   1.594          1.559
───────────────────────────────────────────────────────


RUBIKS_LIST
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
1-move                            0.067          0.063
2-move                            0.067          0.063
3-move                            0.147          0.143
4-move                            1.578          1.572
5-move                            5.114          5.104
6-move                           32.561         32.486
7-move                           72.619         72.609
──────────────────────────────────────────────────────


RUBIKS_VECTOR
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
1-move                            0.052          0.048
2-move                            0.052          0.048
3-move                            0.116          0.113
4-move                            1.202          1.196
5-move                            4.049          4.022
6-move                           25.910         25.864
7-move                           57.778         57.726
──────────────────────────────────────────────────────


SORT
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
n=10                              0.005          0.004
n=50                              0.031          0.030
n=100                             0.069          0.067
n=250                             0.199          0.198
n=500                             0.447          0.445
n=1000                            1.014          1.007
n=2500                            2.937          2.912
n=5000                            6.505          6.416
n=10000                          13.943         13.894
──────────────────────────────────────────────────────


STATS
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
vector-mean-n=100                 0.011          0.009
vector-mean-n=500                 0.053          0.049
vector-mean-n=1000                0.100          0.096
vector-mean-n=2500                0.267          0.264
vector-mean-n=5000                0.572          0.569
vector-mean-n=10000               1.171          1.166
vector-mean-n=25000               2.970          2.952
vector-summary-n=100              0.082          0.079
vector-summary-n=500              0.512          0.509
vector-summary-n=1000             1.137          1.128
vector-summary-n=2500             3.319          3.305
vector-summary-n=5000             7.229          7.198
vector-summary-n=10000           15.527         15.467
vector-summary-n=25000           43.172         43.070
list-mean-n=100                   0.011          0.010
list-mean-n=500                   0.051          0.050
list-mean-n=1000                  0.100          0.099
list-mean-n=2500                  0.283          0.278
list-mean-n=5000                  0.597          0.594
list-mean-n=10000                 1.189          1.187
list-mean-n=25000                 3.001          2.988
list-summary-n=100                0.082          0.080
list-summary-n=500                0.507          0.503
list-summary-n=1000               1.140          1.135
list-summary-n=2500               3.267          3.256
list-summary-n=5000               7.262          7.150
list-summary-n=10000             15.554         15.503
list-summary-n=25000             43.314         42.990
──────────────────────────────────────────────────────


STRING_OPS
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
search long/absent                0.017          0.015
search long/present               0.022          0.021
search short needle               0.022          0.021
search needle=haystack            0.181          0.178
hash 2000x8                       0.036          0.033
hash 2000x64                      0.098          0.096
hash 500x512                      0.202          0.198
──────────────────────────────────────────────────────


SUDOKU_LIST
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
Easy (36 givens)                 14.972         14.892
Medium (30 givens)                0.222          0.217
Hard (25 givens)               3196.802       3196.802
Expert (23 givens)              183.280        183.280
──────────────────────────────────────────────────────


SUDOKU_VECTOR
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
Easy (36 givens)                 10.390         10.365
Medium (30 givens)                0.156          0.152
Hard (25 givens)               2280.844       2280.844
Expert (23 givens)              131.745        131.745
──────────────────────────────────────────────────────


XML-DECODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
wide-1000                         2.431          2.414
deep-200                          0.228          0.220
attributes-500                    1.875          1.852
mixed-500                         2.910          2.889
entities-2000                     6.794          6.767
ooxml-500                         6.391          6.324
──────────────────────────────────────────────────────


XML-ENCODE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
wide-1000                         0.808          0.775
deep-200                          0.132          0.122
attributes-500                    0.758          0.745
mixed-500                         1.967          1.947
escaping-2000                     3.965          3.903
──────────────────────────────────────────────────────


ZIP-CREATE
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
single-deflate                    0.528          0.503
single-stored                     0.028          0.019
mixed-16                          3.738          3.709
many-128                         52.449         52.400
large-256k                       34.822         33.841
──────────────────────────────────────────────────────


ZIP-ENTRIES
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
single-deflate                    0.004          0.002
single-stored                     0.003          0.002
mixed-16                          0.014          0.012
many-128                          0.090          0.083
large-256k                        0.003          0.002
──────────────────────────────────────────────────────


ZIP-EXTRACT
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
single-deflate                    0.245          0.231
single-stored                     0.192          0.187
mixed-16                          0.565          0.554
many-128                          5.220          5.200
large-256k                        2.373          2.336
──────────────────────────────────────────────────────


ZLIB-COMPRESS
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
text-4k                           1.008          0.975
text-32k                          5.448          5.394
incremental-16k                   6.337          6.262
runs-32k                         12.616         12.535
──────────────────────────────────────────────────────


ZLIB-DECOMPRESS
──────────────────────────────────────────────────────
Case                          mean (ms)       min (ms)
──────────────────────────────────────────────────────
text-4k                           0.507          0.493
text-32k                          2.040          2.032
incremental-16k                   1.454          1.441
runs-32k                          3.081          3.041
──────────────────────────────────────────────────────