quickstart →

Fastest GitHub Actions runners: disk I/O.

fio inside the job workspace of 93 runners from 9 providers, 2 to 12 vCPU. These are the disk's limits. A build goes through the Linux page cache and often never reaches them.

Fastest QD1 read, x64 at 4 vCPU 82,138 Blacksmith 4 vCPU · reads/s
Fastest QD1 read, arm64 at 4 vCPU 24,897 Blacksmith 4 vCPU · reads/s
GitHub at 4 vCPU 6,744 x64 QD1 reads/s on GitHub 4-core
Fastest synced writes, x64 at 4 vCPU 18,224 Blacksmith 4 vCPU · writes/s · nobarrier mount
tmpfs, for scale 1.2M QD1 reads/s on RunsOn r8a.2xlarge · tmpfs: the workspace in RAM

Latency per provider

Each provider's best disk, RunsOn once per storage (the Storage pill). QD1 is one 4k read at a time: what a database or a cold read pays. Most build steps batch their I/O through the page cache. tmpfs is RAM, not a disk: add it to see the gap on the same scale.

QD1 random readx64 · 4k, one request in flight · IOPS, higher is better
  1. Blacksmith4 vCPUVM disk82,138, p99 14 µs, ×1.00
  2. Namespace8 vCPU8x32 · VM disk78,677, p99 12 µs, ×0.96
  3. StarSling8 vCPUVM disk56,745, p99 17 µs, ×0.69
  4. Avrea2 vCPUVM disk45,837, p99 17 µs, ×0.56
  5. Warpbuild8 vCPUVM disk27,503, p99 48 µs, ×0.33
  6. RunsOn8 vCPUi7i.2xlarge · local NVMe11,608, p99 293 µs, ×0.14
  7. Ubicloud8 vCPUpremium · VM disk11,190, p99 136 µs, ×0.14
  8. GitHub8 vCPUVM disk7,901, p99 202 µs, ×0.10
  9. RunsOn2 vCPUr8a.large · EBS gp31,844, p99 799 µs, ×0.02
  10. AWS CodeBuild4 vCPUmedium · EBS1,763, p99 725 µs, ×0.02

Blacksmith and Namespace lead x64 QD1 read, within 5% (82,138 and 78,677).tmpfs for scale: 1,154,342 on RunsOn r8a.2xlarge · tmpfs.

Synced writesx64 · 4k + fdatasync · IOPS, higher is better
  1. Blacksmith8 vCPUVM disk · nobarrier18,934, p99 21 µs, ×1.00
  2. Namespace8 vCPU8x32 · VM disk18,160, p99 21 µs, ×0.96
  3. RunsOn2 vCPUi7i.large · local NVMe13,194, p99 34 µs, ×0.70
  4. Avrea4 vCPUVM disk8,676, p99 36 µs, ×0.46
  5. Ubicloud8 vCPUpremium · VM disk4,485, p99 261 µs, ×0.24
  6. GitHub2 vCPUVM disk · nobarrier4,336, p99 210 µs, ×0.23
  7. StarSling8 vCPUVM disk3,146, p99 28 µs, ×0.17
  8. Warpbuild2 vCPUVM disk2,084, p99 119 µs, ×0.11
  9. AWS CodeBuild2 vCPUsmall · EBS564, p99 995 µs, ×0.03
  10. RunsOn2 vCPUm8azn.large · EBS gp3 · nobarrier542, p99 979 µs, ×0.03

Blacksmith and Namespace lead x64 synced writes, within 5% (18,934 and 18,160).volatile and nobarrier mounts make each flush cheaper by making it less durable.

QD1 random readx64 at 2 vCPU · 4k, one request in flight · IOPS, higher is better
  1. Blacksmith2 vCPUVM disk78,754, p99 17 µs, ×1.00
  2. Namespace2 vCPU2x8 · VM disk77,442, p99 13 µs, ×0.98
  3. Avrea2 vCPUVM disk45,837, p99 17 µs, ×0.58
  4. Warpbuild2 vCPUVM disk24,646, p99 59 µs, ×0.31
  5. RunsOn2 vCPUi7i.large · local NVMe11,384, p99 313 µs, ×0.14
  6. GitHub2 vCPUVM disk7,066, p99 222 µs, ×0.09
  7. Ubicloud2 vCPUpremium · VM disk6,564, p99 1,597 µs, ×0.08
  8. RunsOn2 vCPUr8a.large · EBS gp31,844, p99 799 µs, ×0.02
  9. AWS CodeBuild2 vCPUsmall · EBS1,758, p99 823 µs, ×0.02

Blacksmith and Namespace lead x64 2 vCPU QD1 read, within 5% (78,754 and 77,442).tmpfs for scale: 1,154,342 on RunsOn r8a.2xlarge · tmpfs.

Synced writesx64 at 2 vCPU · 4k + fdatasync · IOPS, higher is better
  1. Blacksmith2 vCPUVM disk · nobarrier18,223, p99 26 µs, ×1.00
  2. Namespace2 vCPU2x8 · VM disk17,813, p99 23 µs, ×0.98
  3. RunsOn2 vCPUi7i.large · local NVMe13,194, p99 34 µs, ×0.72
  4. Avrea2 vCPUVM disk8,144, p99 42 µs, ×0.45
  5. GitHub2 vCPUVM disk · nobarrier4,336, p99 210 µs, ×0.24
  6. Ubicloud2 vCPUpremium · VM disk2,450, p99 1,794 µs, ×0.13
  7. Warpbuild2 vCPUVM disk2,084, p99 119 µs, ×0.11
  8. AWS CodeBuild2 vCPUsmall · EBS564, p99 995 µs, ×0.03
  9. RunsOn2 vCPUm8azn.large · EBS gp3 · nobarrier542, p99 979 µs, ×0.03

Blacksmith and Namespace lead x64 2 vCPU synced writes, within 5% (18,223 and 17,813).volatile and nobarrier mounts make each flush cheaper by making it less durable.

QD1 random readx64 at 4 vCPU · 4k, one request in flight · IOPS, higher is better
  1. Blacksmith4 vCPUVM disk82,138, p99 14 µs, ×1.00
  2. Namespace4 vCPU4x8 · VM disk77,281, p99 13 µs, ×0.94
  3. StarSling4 vCPUVM disk55,952, p99 18 µs, ×0.68
  4. Avrea4 vCPUVM disk43,283, p99 20 µs, ×0.53
  5. Warpbuild4 vCPUVM disk18,011, p99 64 µs, ×0.22
  6. RunsOn4 vCPUi7i.xlarge · local NVMe11,437, p99 301 µs, ×0.14
  7. Ubicloud4 vCPUpremium · VM disk8,758, p99 569 µs, ×0.11
  8. GitHub4 vCPUnetwork disk6,744, p99 289 µs, ×0.08
  9. RunsOn4 vCPUm8azn.xlarge · EBS gp31,817, p99 872 µs, ×0.02
  10. AWS CodeBuild4 vCPUmedium · EBS1,763, p99 725 µs, ×0.02

Fastest x64 4 vCPU QD1 read: Blacksmith (82,138), ahead of Namespace (77,281).tmpfs for scale: 1,154,342 on RunsOn r8a.2xlarge · tmpfs.

Synced writesx64 at 4 vCPU · 4k + fdatasync · IOPS, higher is better
  1. Blacksmith4 vCPUVM disk · nobarrier18,224, p99 26 µs, ×1.00
  2. Namespace4 vCPU4x8 · VM disk17,744, p99 21 µs, ×0.97
  3. RunsOn4 vCPUi7i.xlarge · local NVMe12,450, p99 36 µs, ×0.68
  4. Avrea4 vCPUVM disk8,676, p99 36 µs, ×0.48
  5. GitHub4 vCPUnetwork disk · nobarrier3,382, p99 297 µs, ×0.19
  6. StarSling4 vCPUVM disk2,902, p99 29 µs, ×0.16
  7. Warpbuild4 vCPUVM disk1,987, p99 118 µs, ×0.11
  8. Ubicloud4 vCPUpremium · VM disk1,395, p99 3,850 µs, ×0.08
  9. AWS CodeBuild4 vCPUmedium · EBS561, p99 995 µs, ×0.03
  10. RunsOn4 vCPUm8azn.xlarge · EBS gp3 · nobarrier541, p99 963 µs, ×0.03

Blacksmith and Namespace lead x64 4 vCPU synced writes, within 5% (18,224 and 17,744).volatile and nobarrier mounts make each flush cheaper by making it less durable.

QD1 random readx64 at 8 vCPU · 4k, one request in flight · IOPS, higher is better
  1. Blacksmith8 vCPUVM disk81,150, p99 13 µs, ×1.00
  2. Namespace8 vCPU8x32 · VM disk78,677, p99 12 µs, ×0.97
  3. StarSling8 vCPUVM disk56,745, p99 17 µs, ×0.70
  4. Avrea8 vCPUVM disk42,313, p99 19 µs, ×0.52
  5. Warpbuild8 vCPUVM disk27,503, p99 48 µs, ×0.34
  6. RunsOn8 vCPUi7i.2xlarge · local NVMe11,608, p99 293 µs, ×0.14
  7. Ubicloud8 vCPUpremium · VM disk11,190, p99 136 µs, ×0.14
  8. GitHub8 vCPUVM disk7,901, p99 202 µs, ×0.10
  9. RunsOn8 vCPUc8a.2xlarge · EBS gp31,781, p99 856 µs, ×0.02
  10. AWS CodeBuild8 vCPUlarge · EBS1,752, p99 782 µs, ×0.02

Blacksmith and Namespace lead x64 8 vCPU QD1 read, within 5% (81,150 and 78,677).tmpfs for scale: 1,154,342 on RunsOn r8a.2xlarge · tmpfs.

Synced writesx64 at 8 vCPU · 4k + fdatasync · IOPS, higher is better
  1. Blacksmith8 vCPUVM disk · nobarrier18,934, p99 21 µs, ×1.00
  2. Namespace8 vCPU8x32 · VM disk18,160, p99 21 µs, ×0.96
  3. RunsOn8 vCPUi7i.2xlarge · local NVMe11,713, p99 38 µs, ×0.62
  4. Avrea8 vCPUVM disk7,510, p99 44 µs, ×0.40
  5. Ubicloud8 vCPUpremium · VM disk4,485, p99 261 µs, ×0.24
  6. GitHub8 vCPUVM disk · nobarrier4,032, p99 259 µs, ×0.21
  7. StarSling8 vCPUVM disk3,146, p99 28 µs, ×0.17
  8. Warpbuild8 vCPUVM disk2,067, p99 116 µs, ×0.11
  9. AWS CodeBuild8 vCPUlarge · EBS562, p99 987 µs, ×0.03
  10. RunsOn8 vCPUc8a.2xlarge · EBS gp3 · nobarrier540, p99 971 µs, ×0.03

Blacksmith and Namespace lead x64 8 vCPU synced writes, within 5% (18,934 and 18,160).volatile and nobarrier mounts make each flush cheaper by making it less durable.

QD1 random readarm64 · 4k, one request in flight · IOPS, higher is better
  1. Warpbuild6 vCPUxfast (Apple M4 Pro) · VM disk26,620, p99 79 µs, ×1.00
  2. Blacksmith8 vCPUVM disk26,166, p99 33 µs, ×0.98
  3. Avrea8 vCPUVM disk19,778, p99 53 µs, ×0.74
  4. Namespace4 vCPUApple silicon 4x16 · VM disk19,715, p99 85 µs, ×0.74
  5. RunsOn8 vCPUm9gd.2xlarge · local NVMe13,508, p99 81 µs, ×0.51
  6. Ubicloud2 vCPUstandard · VM disk9,339, p99 334 µs, ×0.35
  7. GitHub4 vCPUnetwork disk8,202, p99 206 µs, ×0.31
  8. Warpbuild4 vCPUEBS1,816, p99 823 µs, ×0.07
  9. RunsOn8 vCPUm9g.2xlarge · EBS gp31,810, p99 766 µs, ×0.07

Warpbuild and Blacksmith lead arm64 QD1 read, within 5% (26,620 and 26,166).tmpfs for scale: 685,593 on RunsOn r9g.xlarge · tmpfs.

Synced writesarm64 · 4k + fdatasync · IOPS, higher is better
  1. RunsOn8 vCPUm9gd.2xlarge · local NVMe17,500, p99 19 µs, ×1.00
  2. Warpbuild12 vCPUxfast (Apple M4 Pro) · VM disk · nobarrier8,582, p99 68 µs, ×0.49
  3. Blacksmith8 vCPUVM disk · nobarrier7,834, p99 57 µs, ×0.45
  4. GitHub4 vCPUnetwork disk · nobarrier4,381, p99 281 µs, ×0.25
  5. Ubicloud2 vCPUstandard · VM disk4,319, p99 453 µs, ×0.25
  6. Avrea2 vCPUVM disk4,250, p99 56 µs, ×0.24
  7. Namespace8 vCPU8x16 · VM disk4,078, p99 161 µs, ×0.23
  8. RunsOn4 vCPUm9g.xlarge · EBS gp3 · nobarrier543, p99 987 µs, ×0.03
  9. Warpbuild8 vCPUEBS · nobarrier539, p99 922 µs, ×0.03

Fastest arm64 synced writes: RunsOn m9gd.2xlarge · NVMe (17,500), ahead of Warpbuild (8,582).volatile and nobarrier mounts make each flush cheaper by making it less durable.

QD1 random readarm64 at 2 vCPU · 4k, one request in flight · IOPS, higher is better
  1. Blacksmith2 vCPUVM disk23,450, p99 43 µs, ×1.00
  2. Avrea2 vCPUVM disk17,564, p99 58 µs, ×0.75
  3. Namespace2 vCPU2x8 · VM disk16,193, p99 95 µs, ×0.69
  4. RunsOn2 vCPUm9gd.large · local NVMe13,492, p99 81 µs, ×0.58
  5. Ubicloud2 vCPUstandard · VM disk9,339, p99 334 µs, ×0.40
  6. GitHub2 vCPUVM disk5,791, p99 232 µs, ×0.25
  7. Warpbuild2 vCPUEBS1,809, p99 823 µs, ×0.08
  8. RunsOn2 vCPUm9g.large · EBS gp31,788, p99 766 µs, ×0.08

Fastest arm64 2 vCPU QD1 read: Blacksmith (23,450), ahead of Avrea (17,564).tmpfs for scale: 685,593 on RunsOn r9g.xlarge · tmpfs.

Synced writesarm64 at 2 vCPU · 4k + fdatasync · IOPS, higher is better
  1. RunsOn2 vCPUm9gd.large · local NVMe7,267, p99 49 µs, ×1.00
  2. Blacksmith2 vCPUVM disk · nobarrier6,384, p99 95 µs, ×0.88
  3. Ubicloud2 vCPUstandard · VM disk4,319, p99 453 µs, ×0.59
  4. Avrea2 vCPUVM disk4,250, p99 56 µs, ×0.58
  5. Namespace2 vCPU2x8 · VM disk3,567, p99 212 µs, ×0.49
  6. GitHub2 vCPUVM disk · nobarrier2,568, p99 371 µs, ×0.35
  7. RunsOn2 vCPUm9g.large · EBS gp3 · nobarrier542, p99 987 µs, ×0.07
  8. Warpbuild2 vCPUEBS · nobarrier538, p99 995 µs, ×0.07

Fastest arm64 2 vCPU synced writes: RunsOn m9gd.large · NVMe (7,267), ahead of Blacksmith (6,384).volatile and nobarrier mounts make each flush cheaper by making it less durable.

QD1 random readarm64 at 4 vCPU · 4k, one request in flight · IOPS, higher is better
  1. Blacksmith4 vCPUVM disk24,897, p99 39 µs, ×1.00
  2. Namespace4 vCPUApple silicon 4x16 · VM disk19,715, p99 85 µs, ×0.79
  3. Avrea4 vCPUVM disk19,322, p99 57 µs, ×0.78
  4. RunsOn4 vCPUm9gd.xlarge · local NVMe13,052, p99 112 µs, ×0.52
  5. GitHub4 vCPUnetwork disk8,202, p99 206 µs, ×0.33
  6. Ubicloud4 vCPUstandard · VM disk7,432, p99 594 µs, ×0.30
  7. Warpbuild4 vCPUEBS1,816, p99 823 µs, ×0.07
  8. RunsOn4 vCPUc8g.xlarge · EBS gp31,777, p99 987 µs, ×0.07

Fastest arm64 4 vCPU QD1 read: Blacksmith (24,897), ahead of Namespace (19,715).tmpfs for scale: 685,593 on RunsOn r9g.xlarge · tmpfs.

Synced writesarm64 at 4 vCPU · 4k + fdatasync · IOPS, higher is better
  1. RunsOn4 vCPUm9gd.xlarge · local NVMe13,696, p99 50 µs, ×1.00
  2. Blacksmith4 vCPUVM disk · nobarrier7,280, p99 75 µs, ×0.53
  3. GitHub4 vCPUnetwork disk · nobarrier4,381, p99 281 µs, ×0.32
  4. Avrea4 vCPUVM disk3,920, p99 55 µs, ×0.29
  5. Namespace4 vCPU4x8 · VM disk3,761, p99 202 µs, ×0.27
  6. Ubicloud4 vCPUstandard · VM disk1,888, p99 3,260 µs, ×0.14
  7. RunsOn4 vCPUm9g.xlarge · EBS gp3 · nobarrier543, p99 987 µs, ×0.04
  8. Warpbuild4 vCPUEBS · nobarrier539, p99 979 µs, ×0.04

Fastest arm64 4 vCPU synced writes: RunsOn m9gd.xlarge · NVMe (13,696), ahead of Blacksmith (7,280).volatile and nobarrier mounts make each flush cheaper by making it less durable.

QD1 random readarm64 at 8 vCPU · 4k, one request in flight · IOPS, higher is better
  1. Blacksmith8 vCPUVM disk26,166, p99 33 µs, ×1.00
  2. Avrea8 vCPUVM disk19,778, p99 53 µs, ×0.76
  3. Namespace8 vCPU8x16 · VM disk16,819, p99 90 µs, ×0.64
  4. RunsOn8 vCPUm9gd.2xlarge · local NVMe13,508, p99 81 µs, ×0.52
  5. Ubicloud8 vCPUstandard · VM disk9,278, p99 358 µs, ×0.35
  6. RunsOn8 vCPUm9g.2xlarge · EBS gp31,810, p99 766 µs, ×0.07
  7. Warpbuild8 vCPUEBS1,807, p99 717 µs, ×0.07

Fastest arm64 8 vCPU QD1 read: Blacksmith (26,166), ahead of Avrea (19,778).tmpfs for scale: 685,593 on RunsOn r9g.xlarge · tmpfs.

Synced writesarm64 at 8 vCPU · 4k + fdatasync · IOPS, higher is better
  1. RunsOn8 vCPUm9gd.2xlarge · local NVMe17,500, p99 19 µs, ×1.00
  2. Blacksmith8 vCPUVM disk · nobarrier7,834, p99 57 µs, ×0.45
  3. Namespace8 vCPU8x16 · VM disk4,078, p99 161 µs, ×0.23
  4. Avrea8 vCPUVM disk3,832, p99 56 µs, ×0.22
  5. Ubicloud8 vCPUstandard · VM disk3,732, p99 995 µs, ×0.21
  6. RunsOn8 vCPUm9g.2xlarge · EBS gp3 · nobarrier542, p99 995 µs, ×0.03
  7. Warpbuild8 vCPUEBS · nobarrier539, p99 922 µs, ×0.03

Fastest arm64 8 vCPU synced writes: RunsOn m9gd.2xlarge · NVMe (17,500), ahead of Blacksmith (7,834).volatile and nobarrier mounts make each flush cheaper by making it less durable.

What the numbers say

Extremes on x64, and RAM against disk.

  • On x64, one small read at a time (4k, QD1) comes back 82,138 times a second on Blacksmith 4 vCPU and 1,425 on RunsOn m8azn.xlarge · gp3 1000 MiB/s, 58× apart; p99 latency is 14 µs against 1,020 µs.
  • Synced 4k writes on x64 run from 498 per second on RunsOn m8i.2xlarge · EBS gp3 (workspace mounted nobarrier) to 18,934 on Blacksmith 8 vCPU (workspace mounted nobarrier).
  • r8a.large with tmpfs ($0.0010/min at spot) answers 1,105,119 QD1 reads and 424,773 synced writes per second: 91× and 32× the best local NVMe at 2 vCPU (i7i.large, $0.0010) and 599× and 785× default EBS gp3 (r8a.large, $0.0010); its workspace is 23 GiB, from RAM. (EC2 storage suite) What that does to real builds.
More findings22: arm64, NVMe vs EBS, provisioned gp3, tmpfs, storage classes
  • On arm64, one small read at a time (4k, QD1) comes back 26,620 times a second on Warpbuild xfast (Apple M4 Pro) 6 vCPU and 1,560 on RunsOn m9g.xlarge · EBS gp3, 17× apart; p99 latency is 79 µs against 971 µs.
  • Synced 4k writes on arm64 run from 537 per second on RunsOn c8g.large · EBS gp3 (workspace mounted nobarrier) to 17,500 on RunsOn m9gd.2xlarge · local NVMe.
  • Same Xeon 6975P-C CPU, different disk: m8id.2xlarge on local NVMe answers 10,804 QD1 reads and 7,522 synced writes per second, m8i.2xlarge on EBS gp3 1,539 and 498.
  • Same Xeon 6975P-C CPU, different disk: m8id.large on local NVMe answers 11,093 QD1 reads and 5,545 synced writes per second, m8i-flex.large on EBS gp3 1,745 and 532.
  • Same Xeon 6975P-C CPU, different disk: m8id.xlarge on local NVMe answers 11,015 QD1 reads and 7,898 synced writes per second, m8i-flex.xlarge on EBS gp3 1,707 and 527.
  • Same Neoverse-V3 CPU, different disk: m9gd.2xlarge on local NVMe answers 13,508 QD1 reads and 17,500 synced writes per second, m9g.2xlarge on EBS gp3 1,810 and 542.
  • Same Neoverse-V3 CPU, different disk: m9gd.xlarge on local NVMe answers 13,052 QD1 reads and 13,696 synced writes per second, m9g.xlarge on EBS gp3 1,560 and 543.
  • Same Neoverse-V3 CPU, different disk: m9gd.large on local NVMe answers 13,492 QD1 reads and 7,267 synced writes per second, m9g.large on EBS gp3 1,788 and 542.
  • Provisioning gp3 at 1000 MiB/s on m8a.2xlarge takes sequential reads from 402 MiB/s to 1,002 MiB/s (2.5×); QD1 reads barely move (1,791 → 1,792 IOPS): it buys bandwidth, not latency.
  • Provisioning gp3 at 1000 MiB/s on m8azn.xlarge takes sequential reads from 401 MiB/s to 1,001 MiB/s (2.5×); QD1 reads go (1,817 → 1,425 IOPS).
  • tmpfs on m8a.2xlarge is not a disk at all: 1,153,230 QD1 reads and 427,176 synced writes per second, from RAM. The workspace is 46 GiB, sized by memory.
  • tmpfs on m9g.2xlarge is not a disk at all: 664,023 QD1 reads and 301,114 synced writes per second, from RAM. The workspace is 46 GiB, sized by memory.
  • tmpfs on m9g.xlarge is not a disk at all: 682,673 QD1 reads and 303,641 synced writes per second, from RAM. The workspace is 23 GiB, sized by memory.
  • tmpfs on r8a.2xlarge is not a disk at all: 1,154,342 QD1 reads and 430,563 synced writes per second, from RAM. The workspace is 92 GiB, sized by memory.
  • tmpfs on r8a.xlarge is not a disk at all: 1,109,976 QD1 reads and 431,794 synced writes per second, from RAM. The workspace is 46 GiB, sized by memory.
  • tmpfs on r9g.large is not a disk at all: 634,536 QD1 reads and 300,213 synced writes per second, from RAM. The workspace is 23 GiB, sized by memory.
  • tmpfs on r9g.xlarge is not a disk at all: 685,593 QD1 reads and 301,758 synced writes per second, from RAM. The workspace is 46 GiB, sized by memory.
  • tmpfs: 635k–1.2M QD1 reads and 300k–432k synced writes per second across 8 runners (8 RunsOn configurations).
  • VM disk: 5.8k–82k QD1 reads and 926–19k synced writes per second across 43 runners from 7 providers (6 Avrea runners, 6 Blacksmith runners, 3 GitHub runners, 12 Namespace runners, 2 StarSling x64 runners, 9 Ubicloud runners and 5 Warpbuild runners).
  • local NVMe: 11k–14k QD1 reads and 5.5k–18k synced writes per second across 9 runners (9 RunsOn configurations).
  • network disk: 6.7k–8.2k QD1 reads and 3.4k–4.4k synced writes per second across 2 runners (2 GitHub runners).
  • EBS: 1.4k–1.8k QD1 reads and 498–564 synced writes per second across 31 runners from 3 providers (3 AWS CodeBuild x64 runners, 25 RunsOn configurations and 3 Warpbuild configurations).

Reading these numbers

fio measures what a disk can do. Whether a job gets there depends on the job.

What each column says about a job

  • QD1 reads and synced writes: databases, SQLite-backed tests and anything that flushes each write. Every flush waits for the storage, and a network disk pays a round trip each time.
  • Random writes at depth and sequential throughput: docker build layers, package installs and cache archives. They batch their writes and run into the disk's ceiling, not its latency.
  • None of them: compile jobs. A compiler waits for the CPU, and it reads its files back from the page cache.

Every runner

Each provider's best disk first; its other machines sit behind +N more. Bars are log scale.

One request at a time 4k, 32 in flight Sequential, 1M
Runner QD1 read ↑p99 ↓Sync write ↑Read ↑Write ↑Read ↑Write ↑
x6457 runners, 9 providers
Blacksmith 4 vCPU 16 GB VM disk EPYC · model hidden nobarrier 82,138 14 µs 18,224 769,525 253,803 6.5 GiB/s 2.0 GiB/s
8 vCPU 8 vCPU 32 GB VM disk EPYC · model hidden nobarrier 81,150 13 µs 18,934 625,138 328,609 6.5 GiB/s 2.0 GiB/s
2 vCPU 2 vCPU 8 GB VM disk EPYC · model hidden nobarrier 78,754 17 µs 18,223 780,194 190,198 7.1 GiB/s 2.1 GiB/s
Namespace 8x32 8 vCPU 32 GB VM disk EPYC · model hidden 78,677 12 µs 18,160 1,106,358 536,857 4.1 GiB/s 2.9 GiB/s
8x16 8 vCPU 16 GB VM disk EPYC · model hidden 76,839 13 µs 17,698 1,109,002 538,065 4.1 GiB/s 2.9 GiB/s
4x16 4 vCPU 16 GB VM disk EPYC · model hidden 77,169 13 µs 17,693 994,526 433,713 4.1 GiB/s 2.9 GiB/s
4x8 4 vCPU 8 GB VM disk EPYC · model hidden 77,281 13 µs 17,744 992,094 429,133 4.1 GiB/s 2.9 GiB/s
2x8 2 vCPU 8 GB VM disk EPYC · model hidden 77,442 13 µs 17,813 350,533 222,814 3.9 GiB/s 2.8 GiB/s
StarSling 8 vCPU 32 GB VM disk EPYC · model hidden 56,745 17 µs 3,146 231,481 40,717 2.4 GiB/s 2.7 GiB/s
4 vCPU 4 vCPU 16 GB VM disk EPYC · model hidden 55,952 18 µs 2,902 243,587 42,697 3.9 GiB/s 3.3 GiB/s
Avrea 2 vCPU 8 GB VM disk EPYC 4585PX 45,837 17 µs 8,144 377,847 303,429 12.0 GiB/s 7.2 GiB/s
8 vCPU 8 vCPU 32 GB VM disk EPYC 4585PX 42,313 19 µs 7,510 296,449 147,459 6.6 GiB/s 3.3 GiB/s
4 vCPU 4 vCPU 16 GB VM disk EPYC 4585PX 43,283 20 µs 8,676 439,265 224,464 7.3 GiB/s 5.5 GiB/s
Warpbuild 8 vCPU 32 GB VM disk Ryzen 9 9950X 27,503 48 µs 2,067 163,423 50,132 7.9 GiB/s 5.1 GiB/s
4 vCPU 4 vCPU 16 GB VM disk Ryzen 9 9950X 18,011 64 µs 1,987 134,981 37,360 6.7 GiB/s 5.1 GiB/s
2 vCPU 2 vCPU 8 GB VM disk Ryzen 9 9950X 24,646 59 µs 2,084 152,215 53,614 7.0 GiB/s 4.5 GiB/s
RunsOn i7i.2xlarge 8 vCPU 64 GB local NVMe Xeon 8559C 11,608 293 µs 11,713 300,465 165,111 2.0 GiB/s 1.5 GiB/s
m8azn.3xlarge 12 vCPU 48 GB EBS gp3 EPYC 9R05 nobarrier 1,780 807 µs 540 2,997 2,993 401 MiB/s 401 MiB/s
c8a.2xlarge 8 vCPU 16 GB EBS gp3 EPYC 9R45 nobarrier 1,781 856 µs 540 2,995 2,992 401 MiB/s 401 MiB/s
m8a.2xlarge 8 vCPU 32 GB EBS gp3 EPYC 9R45 nobarrier 1,679 905 µs 539 2,994 2,994 401 MiB/s 401 MiB/s
m8a.2xlarge 8 vCPU 32 GB gp3 1000 MiB/s EPYC 9R45 nobarrier 1,774 872 µs 540 15,996 15,992 1,001 MiB/s 1,001 MiB/s
m8a.2xlarge 8 vCPU 32 GB tmpfs EPYC 9R45 1,153,230 <1 µs 427,176 4,255,814 3,787,945 18.1 GiB/s 9.9 GiB/s
r8a.2xlarge 8 vCPU 64 GB tmpfs EPYC 9R45 1,154,342 <1 µs 430,563 4,231,165 3,828,376 18.5 GiB/s 10.1 GiB/s
m8azn.xlarge 4 vCPU 16 GB EBS gp3 EPYC 9R05 nobarrier 1,817 872 µs 541 2,994 2,991 401 MiB/s 401 MiB/s
m8azn.xlarge 4 vCPU 16 GB gp3 1000 MiB/s EPYC 9R05 nobarrier 1,425 1,020 µs 541 15,994 15,992 1,001 MiB/s 1,001 MiB/s
m8i.2xlarge 8 vCPU 32 GB EBS gp3 Xeon 6975P-C nobarrier 1,539 1,036 µs 498 2,993 2,994 401 MiB/s 401 MiB/s
m8i-flex.2xlarge 8 vCPU 32 GB EBS gp3 Xeon 6975P-C nobarrier 1,748 893 µs 521 2,993 2,995 401 MiB/s 401 MiB/s
m8a.xlarge 4 vCPU 16 GB EBS gp3 EPYC 9R45 nobarrier 1,771 848 µs 540 2,994 2,991 401 MiB/s 401 MiB/s
m8id.2xlarge 8 vCPU 32 GB local NVMe Xeon 6975P-C 10,804 239 µs 7,522 134,258 67,071 905 MiB/s 432 MiB/s
c8a.xlarge 4 vCPU 8 GB EBS gp3 EPYC 9R45 nobarrier 1,790 799 µs 541 2,995 2,992 401 MiB/s 401 MiB/s
r8a.xlarge 4 vCPU 32 GB tmpfs EPYC 9R45 1,109,976 <1 µs 431,794 4,213,197 3,801,248 18.2 GiB/s 10.0 GiB/s
m8azn.large 2 vCPU 8 GB EBS gp3 EPYC 9R05 nobarrier 1,782 856 µs 542 2,994 2,992 401 MiB/s 401 MiB/s
i7i.xlarge 4 vCPU 32 GB local NVMe Xeon 8559C 11,437 301 µs 12,450 150,053 82,489 1,010 MiB/s 788 MiB/s
m8id.xlarge 4 vCPU 16 GB local NVMe Xeon 6975P-C 11,015 217 µs 7,898 67,089 33,525 451 MiB/s 215 MiB/s
m8i-flex.xlarge 4 vCPU 16 GB EBS gp3 Xeon 6975P-C nobarrier 1,707 848 µs 527 2,994 2,992 401 MiB/s 401 MiB/s
r8a.large 2 vCPU 16 GB EBS gp3 EPYC 9R45 nobarrier 1,844 799 µs 541 2,994 2,992 401 MiB/s 401 MiB/s
m8i.xlarge 4 vCPU 16 GB EBS gp3 Xeon 6975P-C nobarrier 1,676 832 µs 523 2,992 2,994 401 MiB/s 401 MiB/s
m8a.large 2 vCPU 8 GB EBS gp3 EPYC 9R45 nobarrier 1,826 774 µs 541 2,994 2,992 401 MiB/s 401 MiB/s
r8a.large 2 vCPU 16 GB tmpfs EPYC 9R45 1,105,119 <1 µs 424,773 2,206,009 1,943,626 18.1 GiB/s 9.9 GiB/s
c8a.large 2 vCPU 4 GB EBS gp3 EPYC 9R45 nobarrier 1,819 741 µs 541 2,994 2,992 401 MiB/s 401 MiB/s
m8id.large 2 vCPU 8 GB local NVMe Xeon 6975P-C 11,093 216 µs 5,545 33,542 16,752 226 MiB/s 108 MiB/s
m8i.large 2 vCPU 8 GB EBS gp3 Xeon 6975P-C nobarrier 1,718 872 µs 535 2,992 2,994 401 MiB/s 401 MiB/s
m8i-flex.large 2 vCPU 8 GB EBS gp3 Xeon 6975P-C nobarrier 1,745 881 µs 532 2,994 2,993 401 MiB/s 401 MiB/s
i7i.large 2 vCPU 16 GB local NVMe Xeon 8559C 11,384 313 µs 13,194 75,022 41,229 503 MiB/s 395 MiB/s
t8i.medium 2 vCPU 4 GB EBS gp3 Xeon 6975P-C nobarrier 1,750 807 µs 519 3,016 2,998 401 MiB/s 401 MiB/s
Ubicloud premium 8 vCPU 32 GB VM disk Ryzen 9 7950X3D 11,190 136 µs 4,485 374,058 22,032 3.8 GiB/s 1.7 GiB/s
standard 8 vCPU 8 vCPU 32 GB VM disk EPYC 9454P 8,407 469 µs 1,270 251,230 13,012 2.4 GiB/s 716 MiB/s
premium 4 vCPU 4 vCPU 16 GB VM disk Ryzen 9 7950X3D 8,758 569 µs 1,395 169,052 10,804 2.4 GiB/s 537 MiB/s
standard 4 vCPU 4 vCPU 16 GB VM disk EPYC 9454 8,648 528 µs 926 189,378 12,781 2.5 GiB/s 578 MiB/s
standard 2 vCPU 2 vCPU 8 GB VM disk EPYC 9454P 6,445 1,106 µs 1,870 105,928 60,814 2.5 GiB/s 622 MiB/s
premium 2 vCPU 2 vCPU 8 GB VM disk Ryzen 9 7950X3D 6,564 1,597 µs 2,450 129,551 64,617 2.6 GiB/s 849 MiB/s
GitHub 8 vCPU 32 GB VM disk EPYC 9V45 nobarrier 7,901 202 µs 4,032 38,946 18,331 784 MiB/s 532 MiB/s
4-core 4 vCPU 16 GB network disk EPYC 9V45 nobarrier 6,744 289 µs 3,382 19,578 9,322 394 MiB/s 247 MiB/s
2-core 2 vCPU 8 GB VM disk EPYC 9V74 nobarrier 7,066 222 µs 4,336 9,378 9,098 199 MiB/s 199 MiB/s
AWS CodeBuild medium 4 vCPU 8 GB EBS Xeon 8488C 1,763 725 µs 561 2,990 2,970 252 MiB/s 252 MiB/s
large 8 vCPU 16 GB EBS Xeon 8488C 1,752 782 µs 562 2,993 2,975 252 MiB/s 251 MiB/s
small 2 vCPU 3 GB EBS Xeon 8488C 1,758 823 µs 564 2,988 2,963 252 MiB/s 252 MiB/s
arm6436 runners, 7 providers
Warpbuild xfast (Apple M4 Pro) 6 vCPU 14 GB VM disk nobarrier 26,620 79 µs 8,488 340,451 5,369 20.1 GiB/s 27.0 GiB/s
xfast (Apple M4 Pro) 12 vCPU 12 vCPU 28 GB VM disk nobarrier 23,397 53 µs 8,582 326,216 4,460 21.1 GiB/s 25.1 GiB/s
8 vCPU 8 vCPU 32 GB EBS Neoverse-V2 nobarrier 1,807 717 µs 539 4,994 4,993 401 MiB/s 401 MiB/s
4 vCPU 4 vCPU 16 GB EBS Neoverse-V2 nobarrier 1,816 823 µs 539 4,193 4,194 302 MiB/s 302 MiB/s
2 vCPU 2 vCPU 8 GB EBS Neoverse-V2 nobarrier 1,809 823 µs 538 4,194 4,193 302 MiB/s 301 MiB/s
Blacksmith 8 vCPU 32 GB VM disk Ampere-1a nobarrier 26,166 33 µs 7,834 259,773 29,073 1.6 GiB/s 993 MiB/s
4 vCPU 4 vCPU 16 GB VM disk Ampere-1a nobarrier 24,897 39 µs 7,280 171,567 27,356 1.6 GiB/s 873 MiB/s
2 vCPU 2 vCPU 6 GB VM disk Ampere-1a nobarrier 23,450 43 µs 6,384 74,915 27,167 1.6 GiB/s 823 MiB/s
Avrea 8 vCPU 32 GB VM disk Apple M5 Max · as stated by the provider 19,778 53 µs 3,832 139,536 16,707 36.8 GiB/s 15.9 GiB/s
4 vCPU 4 vCPU 16 GB VM disk Apple M5 Max · as stated by the provider 19,322 57 µs 3,920 146,579 15,160 31.5 GiB/s 16.0 GiB/s
2 vCPU 2 vCPU 8 GB VM disk Apple M5 Max · as stated by the provider 17,564 58 µs 4,250 166,747 11,109 30.4 GiB/s 12.7 GiB/s
Namespace Apple silicon 4x16 4 vCPU 16 GB VM disk CPU not reported 19,715 85 µs 3,461 148,271 13,347 30.9 GiB/s 14.8 GiB/s
Apple silicon 2x8 2 vCPU 8 GB VM disk CPU not reported 17,652 92 µs 3,695 160,201 28,352 33.8 GiB/s 14.2 GiB/s
8x16 8 vCPU 16 GB VM disk Ampere-1a 16,819 90 µs 4,078 188,179 46,180 965 MiB/s 746 MiB/s
8x32 8 vCPU 32 GB VM disk Ampere-1a 16,284 98 µs 3,974 186,558 40,849 956 MiB/s 763 MiB/s
4x8 4 vCPU 8 GB VM disk Ampere-1a 17,048 90 µs 3,761 144,342 32,144 973 MiB/s 741 MiB/s
4x16 4 vCPU 16 GB VM disk Ampere-1a 16,649 90 µs 3,647 141,434 32,119 964 MiB/s 750 MiB/s
2x8 2 vCPU 8 GB VM disk Ampere-1a 16,193 95 µs 3,567 79,835 24,244 941 MiB/s 696 MiB/s
RunsOn m9gd.2xlarge 8 vCPU 32 GB local NVMe Neoverse-V3 13,508 81 µs 17,500 174,573 87,209 1.1 GiB/s 561 MiB/s
m9g.2xlarge 8 vCPU 32 GB tmpfs Neoverse-V3 664,023 <1 µs 301,114 2,676,737 2,518,860 14.1 GiB/s 9.7 GiB/s
m9g.2xlarge 8 vCPU 32 GB EBS gp3 Neoverse-V3 nobarrier 1,810 766 µs 542 2,995 2,992 401 MiB/s 401 MiB/s
c8g.2xlarge 8 vCPU 16 GB EBS gp3 Neoverse-V2 nobarrier 1,721 946 µs 539 2,994 2,992 401 MiB/s 401 MiB/s
m9gd.xlarge 4 vCPU 16 GB local NVMe Neoverse-V3 13,052 112 µs 13,696 87,221 43,590 585 MiB/s 281 MiB/s
m9g.xlarge 4 vCPU 16 GB EBS gp3 Neoverse-V3 nobarrier 1,560 971 µs 543 2,994 2,992 401 MiB/s 401 MiB/s
m9g.xlarge 4 vCPU 16 GB tmpfs Neoverse-V3 682,673 <1 µs 303,641 2,737,595 2,553,373 15.7 GiB/s 10.1 GiB/s
r9g.xlarge 4 vCPU 32 GB tmpfs Neoverse-V3 685,593 <1 µs 301,758 2,723,360 2,518,108 14.7 GiB/s 9.3 GiB/s
c8g.xlarge 4 vCPU 8 GB EBS gp3 Neoverse-V2 nobarrier 1,777 987 µs 538 2,994 2,993 401 MiB/s 401 MiB/s
m9gd.large 2 vCPU 8 GB local NVMe Neoverse-V3 13,492 81 µs 7,267 43,607 21,783 293 MiB/s 141 MiB/s
r9g.large 2 vCPU 16 GB tmpfs Neoverse-V3 634,536 <1 µs 300,213 1,218,242 1,203,310 13.2 GiB/s 8.5 GiB/s
m9g.large 2 vCPU 8 GB EBS gp3 Neoverse-V3 nobarrier 1,788 766 µs 542 2,993 2,994 401 MiB/s 401 MiB/s
c8g.large 2 vCPU 4 GB EBS gp3 Neoverse-V2 nobarrier 1,739 954 µs 537 2,993 2,994 401 MiB/s 401 MiB/s
Ubicloud standard 2 vCPU 8 GB VM disk Neoverse-N1 9,339 334 µs 4,319 93,227 39,464 937 MiB/s 576 MiB/s
standard 8 vCPU 8 vCPU 32 GB VM disk Neoverse-N1 9,278 358 µs 3,732 223,613 117,930 889 MiB/s 451 MiB/s
standard 4 vCPU 4 vCPU 16 GB VM disk Neoverse-N1 7,432 594 µs 1,888 173,246 46,361 798 MiB/s 428 MiB/s
GitHub 4 vCPU 16 GB network disk Neoverse-N2 nobarrier 8,202 206 µs 4,381 19,579 12,039 394 MiB/s 337 MiB/s
2-core 2 vCPU 8 GB VM disk Neoverse-N2 nobarrier 5,791 232 µs 2,568 9,383 5,717 199 MiB/s 143 MiB/s
  • IOPS are 4k blocks, medians of finished jobs
  • bold best disk measured on the arch (tmpfs is RAM, left out); its bar is tinted once it has 3 runs
  • volatile, nobarrier: cheaper, less durable flushes

Pick the disk per job on RunsOn

How it's measured

Methodology

fio runs inside the job, in GITHUB_WORKSPACE: the disk a build writes to, on the filesystem the provider mounted there. Every runner is compared, whatever its shape.

fio settingsblock sizes, queue depths, mounts
  • QD1 random read: 4k blocks, one request in flight; IOPS and p99 latency.
  • Sync write: 4k writes, each followed by fdatasync.
  • Random read and write: 4k blocks, 4 jobs with 32 requests in flight each.
  • Sequential read and write: 1M blocks, 32 requests in flight.
  • The workspace filesystem, its size and its mount options come from the job's own mount table.
  • Earlier versions of this page used a different harness and other fio settings on 2 vCPU runners; those numbers are gone rather than mixed in.