How to encrypt EBS volume

Sypalo.com

page.title

In this article, I will show you how to encrypt existing EBS volume using AWS web portal or PowerShell. You will need 1 hour(depends on your volume size) to follow these steps:

  • Go to https://console.aws.amazon.com/ec2 and navigate to instances
  • Stop instance which volume you want to encrypt
    Stopping the instance
  • Expand the bottom pane and switch to the «Storage» tab, so you see a link to the instance's volume at the bottom of the page
    Get attached volume id
  • Click on it and you will notice that volume isn't encrypted, so you have to right-click and select «Create snapshot»
    Create snapshot
  • Provide a name and a description to easily find the snapshot and click «Create Snapshot»
    Provide snapshot details
  • Navigate to snapshots, right-click on that one we created and select «Create Volume», notice that snapshot is not encrypted
    Create encrypted volume
  • To create encrypted volume from an unencrypted snapshot, select the same availability zone and checkmark the appropriate checkbox and click «Create Volume»
    Provide encrypted volume details
  • Once we have a volume created, go back to EC2 instances section and locate your instance
  • Write down current Device name attachement info, for Linux instances, it's usually /dev/xvda
  • Click on the currently attached volume, so you will be sent to the volumes section again, but filtered out to show you only one volume, so you won't misclick and disconnect a volume from another instance
  • Right-click on the volume and click «Detach Volume»
    Detach unencrypted volume
  • Right-click on encrypted volume and select «Attach Volume», notice it's encrypted
    Attach encrypted volume
  • Provide instance id you are attaching the volume to and the device name (you noted on step 15) and click attach
    Provide instance details

That's it, later you can remove unencrypted volume and snapshot

Encrypt existing EBS volume using PowerShell


Set-AWSCredential -AccessKey access_key_id -SecretKey secret_key -StoreAs aws_creds

$name = Read-Host "VM name"
$region = "eu-central-1"

$vm = (Get-EC2Instance -Region $region -ProfileName aws_creds).Instances | ? { ($_.tags | ? Key -eq Name).Value -eq $name }   

Write-Host "Stopping $name"
Stop-EC2Instance $vm -Region $region -ProfileName aws_creds
while ((Get-EC2Instance $vm -Region $region -ProfileName aws_creds).Instances.State.Name.Value -ne "stopped") {
	Start-Sleep -s 10
}

Write-Host "Creating $name snapshot"
$vol = Get-EC2Volume -Region $region -ProfileName aws_creds | ? { $_.Attachments.InstanceId -eq $vm.InstanceId }
$snapshot = New-EC2Snapshot $vol.VolumeId $name -Region $region -ProfileName aws_creds
while ((Get-EC2Snapshot -Region $region -ProfileName aws_creds | ? Description -eq $name).State -ne "completed") {
	Start-Sleep -s 10
}

Write-Host "Creating $name encrypted volume"
$tag = @{ Key="Name"; Value=$name }
$tagspec = new-object Amazon.EC2.Model.TagSpecification
$tagspec.ResourceType = "volume"
$tagspec.Tags.Add($tag)
$newvol = New-EC2Volume $snapshot.SnapshotId -Encrypted $true -TagSpecification $tagspec -AvailabilityZone $vol.AvailabilityZone -Region $region -ProfileName aws_creds   
	
Write-Host "Waiting for volume to become available"
while ((Get-EC2Volume -VolumeId $newvol.VolumeId -Region $region -ProfileName aws_creds).State -ne "available") {
	Start-Sleep -s 15
}
	
Write-Host "Detaching existing unencrypted volume from $name"
Dismount-EC2Volume -VolumeId $vol.VolumeId -Region $region -ProfileName aws_creds
Write-Host "Attaching encrypted volume to $name"
while ((Get-EC2Volume -VolumeId $vol.VolumeId -Region $region -ProfileName aws_creds).State -ne "available") {
	Start-Sleep -s 15
}
Add-EC2Volume -InstanceId $vm.InstanceId -VolumeId $newvol.VolumeId -Device $vm.RootDeviceName -Region $region -ProfileName aws_creds
	
Start-EC2Instance $vm -Region $region -ProfileName aws_creds

Write-Host "Removing $name unencrypted volume"
Remove-EC2Volume $vol -Region $region -ProfileName aws_creds