ECS Fargate Deep Dive Part 2: Firecracker in Action
2025-09-02
Introduction
In Part 1, we pulled back the curtain on how ECS Fargate works: Firecracker microVMs, ENIs, IAM, and the hidden host fleet.
Now it’s time to get hands-on. We’ll spin up Firecracker locally, boot a microVM, and even simulate the ENI networking model.
Why Should You Care?
Running Firecracker yourself helps you:
- See how AWS runs each Fargate task inside its own VM.
- Understand boot performance and why Fargate cold starts take 30–60s.
- Learn how ENIs map to VPC-level isolation.
- Debug networking limits by replicating them locally.
Scenario Overview
We’ll simulate a Fargate task locally:
- Launch a Firecracker microVM.
- Attach a minimal Linux root filesystem.
- Configure a TAP interface for networking (like an ENI).
- Map this setup back to ECS Fargate’s architecture.
Goal: see how isolation and networking work in practice.
Deep Dive: Step-by-Step Setup
Prerequisites
Run this on a Linux host (Ubuntu VM, EC2, or Multipass).
sudo apt-get update
sudo apt-get install -y git curl wget build-essential \
unzip cmake pkg-config libseccomp-dev
# Download Firecracker
curl -LOJ https://github.com/firecracker-microvm/firecracker/releases/download/v1.8.0/firecracker-v1.8.0-x86_64.tgz
tar -xvf firecracker-v1.8.0-x86_64.tgz
sudo mv release-v1.8.0-x86_64/firecracker /usr/local/bin/
### Kernel & RootFS
curl -LO https://s3.amazonaws.com/spec.ccfc.min/img/hello/kernel/vmlinux.bin
curl -LO https://s3.amazonaws.com/spec.ccfc.min/img/hello/fsfiles/x86_64/rootfs.ext4
### Launching a MicroVM
rm -f /tmp/firecracker.socket
firecracker --api-sock /tmp/firecracker.socket &
# VM config + boot source
curl --unix-socket /tmp/firecracker.socket -i \
-X PUT 'http://localhost/machine-config' \
-H 'Content-Type: application/json' \
-d '{"vcpu_count":1,"mem_size_mib":512,"ht_enabled":false}'
# Kernel
curl --unix-socket /tmp/firecracker.socket -i \
-X PUT 'http://localhost/boot-source' \
-H 'Content-Type: application/json' \
-d '{"kernel_image_path":"./vmlinux.bin","boot_args":"console=ttyS0 reboot=k panic=1 pci=off"}'
# RootFS
curl --unix-socket /tmp/firecracker.socket -i \
-X PUT 'http://localhost/drives/rootfs' \
-H 'Content-Type: application/json' \
-d '{"drive_id":"rootfs","path_on_host":"./rootfs.ext4","is_root_device":true,"is_read_only":false}'
## Start the VM
curl --unix-socket /tmp/firecracker.socket -i \
-X PUT 'http://localhost/actions' \
-H 'Content-Type: application/json' \
-d '{"action_type":"InstanceStart"}'
## You’ll see a minimal Linux VM booting instantly.
###Networking Simulation
### Fargate gives each task its own ENI. We’ll mimic this with a TAP device:
sudo ip tuntap add tap0 mode tap
sudo ip addr add 172.16.0.1/24 dev tap0
sudo ip link set tap0 up
### Attach it to Firecracker:
curl --unix-socket /tmp/firecracker.socket -i \
-X PUT 'http://localhost/network-interfaces/eth0' \
-H 'Content-Type: application/json' \
-d '{"iface_id":"eth0","host_dev_name":"tap0","guest_mac":"02:FC:00:00:00:01"}'
### Inside the VM, bring up eth0 and assign an IP. Now the microVM talks to the host — exactly how a Fargate task talks to your VPC.
Mapping Back to Fargate
-
Firecracker VM → Your Fargate task’s isolated runtime.
-
RootFS → Base container environment + ECS runtime + your container image.
-
TAP device → Equivalent of a VPC ENI.
-
API config → ECS Scheduler telling Fargate what to run.
Architecture
flowchart TD
subgraph LocalLab["Local Firecracker Lab"]
subgraph Firecracker["MicroVM"]
Kernel[Linux Kernel]
RootFS[RootFS + Container Runtime]
IF1[eth0 (TAP)]
end
Host["Linux Host"] --> Tap[tap0]
Tap --> IF1
end
subgraph AWSFargate["AWS Fargate Analogy"]
subgraph Task1["Fargate Task"]
MVM1[Firecracker microVM]
ENI1[ENI (VPC IP)]
end
VPC1[VPC Subnet + Security Group]
end
Tap -. maps to .-> ENI1
Firecracker -. maps to .-> MVM1
Host -. maps to .-> VPC1
Takeaways
-
Each Fargate task is a microVM, not just a container.
-
ENI-per-task makes tasks first-class citizens in your VPC.
-
Running Firecracker locally shows why Fargate cold starts exist.
-
Debugging ENIs locally helps anticipate VPC IP exhaustion issues.
Conclusion
By running Firecracker locally, you’ve just recreated the core of ECS Fargate. Every time you launch a task in AWS, the same steps happen — at massive scale, across AWS’s hidden fleet.
In Part 3, we’ll dive into real-world gotchas: ENI scaling limits, cold start tuning, and how observability works when you don’t control the host.