SBOMs in Action: Securing Your Golden AMIs From Build to Runtime
Learn how to build secure, immutable golden AMIs on AWS with SBOMs, Cosign signatures, and continuous validation for robust cloud security.
Join the DZone community and get the full member experience.
Join For FreeGolden Amazon Machine Images (AMIs) are the foundation for launching consistent and efficient instances in your AWS cloud environment. Ensuring their security and immutability is paramount. This guide delves into how Software Bill of Materials (SBOMs), cryptographic signing, and runtime validation create a robust framework for building and maintaining secure golden AMIs.
Steps Involved in Building Golden AMIs
Step | Description |
---|---|
Start with a Trusted Base Image | Begin by selecting a minimal, reputable base image, such as AWS-provided base AMIs that are regularly updated with the latest security patches. |
Add Necessary Packages | Install required packages using package managers like yum, apt, or pip. Ensure that packages are sourced from trusted repositories and specify version numbers for consistency. |
Configure Users and Permissions | Follow the Principle of Least Privilege when creating user accounts, removing unnecessary default users and groups. Configure SSH for key-based authentication and restrict root access. |
Functional Testing | Verify the functionality of installed software and applications, including network connectivity and essential system services, to ensure everything works as expected. |
Vulnerability Scanning | Utilize tools such as Amazon Inspector or Grype to scan the AMI for vulnerabilities. Address any critical findings promptly to mitigate potential security risks. |
Understanding Drift and Its Causes
AMI drift occurs when a running instance diverges from its original AMI configuration. This can result from ad-hoc administrator modifications, automated patching, configuration management tools like Puppet or Chef, and changes by application users. These deviations emphasize the need for ongoing monitoring and management of AMI configurations in cloud environments to maintain system consistency and security.
Detecting Drift With SBOMs
Once an EC2 instance is created from a golden AMI, maintaining its integrity is crucial. SBOMs (Software Bill of Materials) play a key role in detecting drift, which occurs when the software environment changes from its original state. By regularly generating and comparing SBOMs for the running instance against the original, any unauthorized modifications, updates, or anomalies can be quickly identified. This ensures that the instance remains consistent with the approved configuration, enhancing security and operational reliability.
Signing SBOMs for Trust and Verification
The cryptographic signing of your SBOMs adds a layer of trust and verification, ensuring:
- Authenticity: The SBOM originates from a trusted source.
- Integrity: The SBOM hasn't been tampered with.
Continuous Validation: Maintaining AMI Integrity at Runtime
Runtime validation, powered by SBOMs, continuously monitors the running instance, comparing its current state to the original signed SBOM. This proactive approach detects any unauthorized changes, triggering alerts for swift remediation.
Tools
Here are some of the tools that can be used for building AMI and validating the instances runtime.
Packer
Creates consistent machine images (VMs, Docker containers) across platforms from a single configuration, ensuring standardized environments and automating image creation.
Grype
Scans container images and file systems for vulnerabilities using Anchore's database, providing fast, detailed reports and integrating seamlessly into CI/CD pipelines.
Syft
Generates Software Bill of Materials (SBOM) from container images, revealing software components, dependencies, and licenses for enhanced security and regulatory compliance.
Cosign
Signs and verifies container images to ensure integrity and authenticity, protecting against unauthorized or tampered images and supporting various key management solutions.
Getting Started AMI Build Pipeline
Let’s dive into a simple example to demonstrate how to build a pipeline.
Workflow
Sample Code
Define Packer Template
{
"builders": [{
"type": "amazon-ebs",
"ami_name": "golden-ami-{{timestamp}}",
"instance_type": "t2.micro",
"region": "us-east-1",
"source_ami": "ami-0c55b159cbfafe1f0", // Amazon Linux 2 AMI (HVM), SSD Volume Type
// ... other configurations (VPC, subnet, etc.)
}],
"provisioners": [{
"type": "ansible",
"playbook_file": "./ansible/playbook.yml",
"user": "ec2-user" // Default user for Amazon Linux 2
}]
}
Provision With Ansible
Ansible automates configuration management. Create a playbook to install and configure software.
name Configure AMI
hosts all
becometrue
tasks
name Update apt cache
apt update_cache=yes
name Install required packages
apt name= item state=present
loop
curl
wget
git
name Install security packages
apt name= item state=present
loop
syft
grype
cosign
Setup Agents, File Systems and Permissions
hosts all
becomeyes
tasks
# Install CloudWatch Agent
name Install CloudWatch Agent
yum
name amazon-cloudwatch-agent
state present
name Start CloudWatch Agent
service
name amazon-cloudwatch-agent
state started
enabledyes
# Set up filesystem (Example: Creating a directory)
name Set up filesystem (Example Creating a directory)
file
path /data
state directory
mode'0755'
# Set permissions (Example: Granting user access)
name Set permissions (Example Granting user access)
file
path /data
owner ec2-user
group ec2-user
mode'u+rwx,g+rx,o+rx'
# ... other configurations (software installation, security hardening, etc.)
Functional Testing
---
name Test setup
hosts localhost
connection local
tasks
# Test: Check if Apache is installed and running
shell systemctl is-active --quiet httpd && systemctl is-enabled --quiet httpd
register httpd_status
failed_when not httpd_status.rc == 0
# Test: Check if port 80 is listening
wait_for
port80
# Test: Check drive size (Example: Root volume)
shell df -h /
register df_output
failed_when"'Size' not in df_output.stdout"
# Test: Check DHCP/IP connectivity
shell ping -c 1 8.8.8.8
register ping_result
failed_when ping_result.rc != 0
# Test: Check DNS resolution
uri
url http //www.google.com
method GET
status_code200
register dns_test_result
failed_when dns_test_result.status != 200
# Test: Check user existence
shell id ec2-user
register user_check_result
failed_when user_check_result.rc != 0
Generate and Sign SBOM
# Generate and sign SBOM
name Generate and sign SBOM
shell
syft -o cyclonedx dir:/ > /etc/sbom/golden.json
cosign generate-key-pair
cosign sign-blob --key cosign.key /etc/sbom/golden.json
cp cosign.pub /etc/sbom/cosign.pub # Store public key in AMI
Vulnerability Scanning
jobs
vulnerability_scan
commands
grype dir:/ --output json > grype_results.json
aws securityhub batch-import-findings --findings file://grype_results.json
Continuous SBOM Validation
Include a validation script in the AMI to run continuously and detect configuration drift. During validation packages introduced by docker containers should be excluded as they are installed as part of the workload.
GOLDEN_SBOM="/etc/sbom/golden.json"
NEW_SBOM="/tmp/current_sbom.json"
PUBLIC_KEY="/etc/sbom/cosign.pub"
# Exclude container filesystems from the scan
syft -o cyclonedx dir:/ --exclude '/var/lib/docker/**' --exclude '/run/containerd/**' --exclude '/var/run/docker.sock' > "$NEW_SBOM"
if ! cosign verify-blob --key "$PUBLIC_KEY" "$GOLDEN_SBOM"; then
# Alert: SBOM verification failed!
logger -t sbom_validation "SBOM verification failed!"
elif ! diff "$GOLDEN_SBOM" "$NEW_SBOM"; then
# Alert: SBOM drift detected!
logger -t sbom_validation "SBOM drift detected!"
fi
rm "$NEW_SBOM"
Configure the AMI to run the above script on a continuous basis using cron or another script that's running with sleep time.
Automate With CodeBuild
AWS CodeBuild automates AMI creation. Define build steps for Packer and Ansible integration.
version0.2
phases
install
runtime-versions
python3.8
commands
pip install ansible
curl -fsSL https://apt.releases.hashicorp.com/gpg | apt-key add -
"deb [arch=amd64] https://apt.releases.hashicorp.com $(lsb_release -cs) main" apt-add-repository
apt-get update && apt-get install packer
build
commands
packer init .
packer validate .
packer build .
Conclusion
In conclusion, integrating SBOMs and runtime validation into your AMI creation process not only fortifies your infrastructure against unauthorized changes but also enhances compliance and operational efficiency. By ensuring that your cloud images remain secure, consistent, and reliable, you lay a robust foundation for scaling and maintaining a resilient cloud environment.
Opinions expressed by DZone contributors are their own.
Comments