ec2_amitools 1.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/README.md +54 -0
- data/bin/console +14 -0
- data/bin/ec2-ami-tools-version +6 -0
- data/bin/ec2-bundle-image +6 -0
- data/bin/ec2-bundle-vol +6 -0
- data/bin/ec2-delete-bundle +6 -0
- data/bin/ec2-download-bundle +6 -0
- data/bin/ec2-migrate-bundle +6 -0
- data/bin/ec2-migrate-manifest +6 -0
- data/bin/ec2-unbundle +6 -0
- data/bin/ec2-upload-bundle +6 -0
- data/bin/setup +8 -0
- data/etc/ec2/amitools/cert-ec2-cn-north-1.pem +28 -0
- data/etc/ec2/amitools/cert-ec2-gov.pem +17 -0
- data/etc/ec2/amitools/cert-ec2.pem +23 -0
- data/etc/ec2/amitools/mappings.csv +9 -0
- data/lib/ec2/amitools/bundle.rb +251 -0
- data/lib/ec2/amitools/bundle_base.rb +58 -0
- data/lib/ec2/amitools/bundleimage.rb +94 -0
- data/lib/ec2/amitools/bundleimageparameters.rb +42 -0
- data/lib/ec2/amitools/bundlemachineparameters.rb +60 -0
- data/lib/ec2/amitools/bundleparameters.rb +120 -0
- data/lib/ec2/amitools/bundlevol.rb +240 -0
- data/lib/ec2/amitools/bundlevolparameters.rb +164 -0
- data/lib/ec2/amitools/crypto.rb +379 -0
- data/lib/ec2/amitools/decryptmanifest.rb +20 -0
- data/lib/ec2/amitools/defaults.rb +12 -0
- data/lib/ec2/amitools/deletebundle.rb +212 -0
- data/lib/ec2/amitools/deletebundleparameters.rb +78 -0
- data/lib/ec2/amitools/downloadbundle.rb +161 -0
- data/lib/ec2/amitools/downloadbundleparameters.rb +84 -0
- data/lib/ec2/amitools/exception.rb +86 -0
- data/lib/ec2/amitools/fileutil.rb +219 -0
- data/lib/ec2/amitools/format.rb +127 -0
- data/lib/ec2/amitools/instance-data.rb +97 -0
- data/lib/ec2/amitools/manifest_wrapper.rb +132 -0
- data/lib/ec2/amitools/manifestv20070829.rb +361 -0
- data/lib/ec2/amitools/manifestv20071010.rb +403 -0
- data/lib/ec2/amitools/manifestv3.rb +331 -0
- data/lib/ec2/amitools/mapids.rb +148 -0
- data/lib/ec2/amitools/migratebundle.rb +222 -0
- data/lib/ec2/amitools/migratebundleparameters.rb +173 -0
- data/lib/ec2/amitools/migratemanifest.rb +225 -0
- data/lib/ec2/amitools/migratemanifestparameters.rb +118 -0
- data/lib/ec2/amitools/minimalec2.rb +116 -0
- data/lib/ec2/amitools/parameter_exceptions.rb +34 -0
- data/lib/ec2/amitools/parameters_base.rb +168 -0
- data/lib/ec2/amitools/region.rb +93 -0
- data/lib/ec2/amitools/s3toolparameters.rb +183 -0
- data/lib/ec2/amitools/showversion.rb +12 -0
- data/lib/ec2/amitools/syschecks.rb +27 -0
- data/lib/ec2/amitools/tool_base.rb +224 -0
- data/lib/ec2/amitools/unbundle.rb +107 -0
- data/lib/ec2/amitools/unbundleparameters.rb +65 -0
- data/lib/ec2/amitools/uploadbundle.rb +361 -0
- data/lib/ec2/amitools/uploadbundleparameters.rb +108 -0
- data/lib/ec2/amitools/util.rb +532 -0
- data/lib/ec2/amitools/version.rb +33 -0
- data/lib/ec2/amitools/xmlbuilder.rb +237 -0
- data/lib/ec2/amitools/xmlutil.rb +55 -0
- data/lib/ec2/common/constants.rb +16 -0
- data/lib/ec2/common/curl.rb +110 -0
- data/lib/ec2/common/headers.rb +95 -0
- data/lib/ec2/common/headersv4.rb +173 -0
- data/lib/ec2/common/http.rb +333 -0
- data/lib/ec2/common/s3support.rb +231 -0
- data/lib/ec2/common/signature.rb +68 -0
- data/lib/ec2/oem/LICENSE.txt +58 -0
- data/lib/ec2/oem/open4.rb +399 -0
- data/lib/ec2/platform/base/architecture.rb +26 -0
- data/lib/ec2/platform/base/constants.rb +54 -0
- data/lib/ec2/platform/base/pipeline.rb +181 -0
- data/lib/ec2/platform/base.rb +57 -0
- data/lib/ec2/platform/current.rb +55 -0
- data/lib/ec2/platform/linux/architecture.rb +35 -0
- data/lib/ec2/platform/linux/constants.rb +23 -0
- data/lib/ec2/platform/linux/fstab.rb +99 -0
- data/lib/ec2/platform/linux/identity.rb +16 -0
- data/lib/ec2/platform/linux/image.rb +811 -0
- data/lib/ec2/platform/linux/mtab.rb +74 -0
- data/lib/ec2/platform/linux/pipeline.rb +40 -0
- data/lib/ec2/platform/linux/rsync.rb +114 -0
- data/lib/ec2/platform/linux/tar.rb +124 -0
- data/lib/ec2/platform/linux/uname.rb +50 -0
- data/lib/ec2/platform/linux.rb +83 -0
- data/lib/ec2/platform/solaris/architecture.rb +28 -0
- data/lib/ec2/platform/solaris/constants.rb +30 -0
- data/lib/ec2/platform/solaris/fstab.rb +43 -0
- data/lib/ec2/platform/solaris/identity.rb +16 -0
- data/lib/ec2/platform/solaris/image.rb +327 -0
- data/lib/ec2/platform/solaris/mtab.rb +29 -0
- data/lib/ec2/platform/solaris/pipeline.rb +40 -0
- data/lib/ec2/platform/solaris/rsync.rb +24 -0
- data/lib/ec2/platform/solaris/tar.rb +36 -0
- data/lib/ec2/platform/solaris/uname.rb +21 -0
- data/lib/ec2/platform/solaris.rb +38 -0
- data/lib/ec2/platform.rb +69 -0
- data/lib/ec2/version.rb +8 -0
- data/lib/ec2_amitools +1 -0
- data/lib/ec2_amitools.rb +7 -0
- metadata +184 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: 61e05c7c7f9a080bb9b10d5a15e481da80ae6aa0
|
4
|
+
data.tar.gz: d4285e6efa71a9cd56e7f7952594c249ae178384
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: 53819c3f2ab95eb3d778f8216b9411e48da84384947859058e77390af355ff8fca42ea8424d97cf4f68b07d981e4356333ce7084404a743b9d878374fb862c80
|
7
|
+
data.tar.gz: 6ebc9c3a6fa31f1654aae27a5321c2031451058585a0799303b5beba885d840206c2d1a30416cee6f6156d6b8616ef4223aea2e10ad714f746034eefca3c97fd
|
data/README.md
ADDED
@@ -0,0 +1,54 @@
|
|
1
|
+
# ec2_amitools
|
2
|
+
|
3
|
+
Install Amazon's EC2 AMI Tools as gem.
|
4
|
+
|
5
|
+
## Origins
|
6
|
+
|
7
|
+
Source files for this library were taken from here: http://s3.amazonaws.com/ec2-downloads/ec2-ami-tools-1.5.7.zip
|
8
|
+
More info about original installation from AWS: http://docs.aws.amazon.com/AWSEC2/latest/UserGuide/set-up-ami-tools.html
|
9
|
+
|
10
|
+
## Dependencies
|
11
|
+
|
12
|
+
- curl
|
13
|
+
- gzip
|
14
|
+
- mkfifo
|
15
|
+
- openssl
|
16
|
+
- rsync
|
17
|
+
- Ruby 2.0.0 or later
|
18
|
+
- tee
|
19
|
+
|
20
|
+
For more info take a look at: https://github.com/sfate/ec2_amitools/blob/master/readme-install.txt
|
21
|
+
|
22
|
+
## Installation
|
23
|
+
|
24
|
+
Add this line to your application's Gemfile:
|
25
|
+
|
26
|
+
```ruby
|
27
|
+
gem 'ec2_amitools'
|
28
|
+
```
|
29
|
+
|
30
|
+
And then execute:
|
31
|
+
|
32
|
+
$ bundle
|
33
|
+
|
34
|
+
Or install it yourself as:
|
35
|
+
|
36
|
+
$ gem install ec2_amitools
|
37
|
+
|
38
|
+
## Usage
|
39
|
+
|
40
|
+
http://docs.aws.amazon.com/AWSEC2/latest/UserGuide/ami-tools-commands.html
|
41
|
+
|
42
|
+
## Development
|
43
|
+
|
44
|
+
After checking out the repo, run `bin/setup` to install dependencies. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
|
45
|
+
|
46
|
+
To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, push git commits and tags, and push the `.gem` file to [rubygems.org](https://rubygems.org).
|
47
|
+
|
48
|
+
## Contributing
|
49
|
+
|
50
|
+
Bug reports and pull requests are welcome on GitHub at https://github.com/sfate/ec2_amitools
|
51
|
+
|
52
|
+
## License - Amazon Software License
|
53
|
+
|
54
|
+
http://github.com/sfate/ec2_amitools/blob/master/license.txt
|
data/bin/console
ADDED
@@ -0,0 +1,14 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
require "bundler/setup"
|
4
|
+
require "ec2_amitools"
|
5
|
+
|
6
|
+
# You can add fixtures and/or initialization code here to make experimenting
|
7
|
+
# with your gem easier. You can also use a different console, if you like.
|
8
|
+
|
9
|
+
# (If you use this, don't forget to add pry to your Gemfile!)
|
10
|
+
# require "pry"
|
11
|
+
# Pry.start
|
12
|
+
|
13
|
+
require "irb"
|
14
|
+
IRB.start(__FILE__)
|
data/bin/ec2-bundle-vol
ADDED
data/bin/ec2-unbundle
ADDED
data/bin/setup
ADDED
@@ -0,0 +1,28 @@
|
|
1
|
+
-----BEGIN CERTIFICATE-----
|
2
|
+
MIIEwTCCA6mgAwIBAgIJALBg5STuwebSMA0GCSqGSIb3DQEBBQUAMIGbMQswCQYD
|
3
|
+
VQQGEwJaQTEVMBMGA1UECBMMV2VzdGVybiBDYXBlMRIwEAYDVQQHEwlDYXBlIFRv
|
4
|
+
d24xHDAaBgNVBAoTE0FtYXpvbiBXZWIgU2VydmljZXMxDDAKBgNVBAsTA0VDMjEW
|
5
|
+
MBQGA1UEAxMNQU1JIE1hbmlmZXN0czEdMBsGCSqGSIb3DQEJARYOYWVzQGFtYXpv
|
6
|
+
bi5jb20wHhcNMTMwODI4MTAxNTEwWhcNMTkwMjE4MTAxNTEwWjCBmzELMAkGA1UE
|
7
|
+
BhMCWkExFTATBgNVBAgTDFdlc3Rlcm4gQ2FwZTESMBAGA1UEBxMJQ2FwZSBUb3du
|
8
|
+
MRwwGgYDVQQKExNBbWF6b24gV2ViIFNlcnZpY2VzMQwwCgYDVQQLEwNFQzIxFjAU
|
9
|
+
BgNVBAMTDUFNSSBNYW5pZmVzdHMxHTAbBgkqhkiG9w0BCQEWDmFlc0BhbWF6b24u
|
10
|
+
Y29tMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA601VE9anUnkM5weg
|
11
|
+
THEUqNkT7fwaKKoTM+oV6n0h5D4LF/qY7IuS7YlxP308P00yE6In4ZHHvc1E/X1e
|
12
|
+
s36t7ojdlx8Pg0jzFLir27BWSl+ddZGJLl0u8FFzJUPmqeiQZW3mKosOqAoj/C5h
|
13
|
+
svXnSmLGxd619eGz2+Kel38LPhwzA8PZeNhil/eK53oo/h7dZvRUtH2+zbYXxq5Q
|
14
|
+
2tsRN1Ef4QaNeKHSdupo8eFNUnmSgeEYz1RC/2QDn6MK7uXijOft4G6iEO4c+PeR
|
15
|
+
wLyBW8YMla2SJk1n4z4gmSJ21uCZ0Bv0A2j/3f+JmgNo4QLIAl/UBWBTT+eSAFYw
|
16
|
+
LVDlrwIDAQABo4IBBDCCAQAwHQYDVR0OBBYEFJSvQRrRg2O1O/kSOEKH2z18OFfH
|
17
|
+
MIHQBgNVHSMEgcgwgcWAFJSvQRrRg2O1O/kSOEKH2z18OFfHoYGhpIGeMIGbMQsw
|
18
|
+
CQYDVQQGEwJaQTEVMBMGA1UECBMMV2VzdGVybiBDYXBlMRIwEAYDVQQHEwlDYXBl
|
19
|
+
IFRvd24xHDAaBgNVBAoTE0FtYXpvbiBXZWIgU2VydmljZXMxDDAKBgNVBAsTA0VD
|
20
|
+
MjEWMBQGA1UEAxMNQU1JIE1hbmlmZXN0czEdMBsGCSqGSIb3DQEJARYOYWVzQGFt
|
21
|
+
YXpvbi5jb22CCQCwYOUk7sHm0jAMBgNVHRMEBTADAQH/MA0GCSqGSIb3DQEBBQUA
|
22
|
+
A4IBAQACBMJpb8N7cT0PP3u814D1Ngd2vqEv6aB8saklT44kWwAXDcILVtPd09ae
|
23
|
+
8q1oWSKpWlGo9Z8gUS92QXMIMxSZCxDdN4MflYWGio5HFvpS/msHVkK9H80nypSd
|
24
|
+
pLS3FP0arr/3tETS8TIhs4aISwUUfHm0W7WrmLaQz8TyfuktVtPrKIMmWgXiJmCo
|
25
|
+
HQkuFe4rjx0y7r8CGQocwo79+m+35aLip44jWB4yLuUgp0wVhT5nxfG/iNX2lUiP
|
26
|
+
Bw/yCpzeJoLBWvFDlunBNu2s0Y3ddFdnlna/k7CQM1Js6+OGQBMh1zTtJlPkkHj3
|
27
|
+
mbaTR6i5yro01FowChTryrRTVfMe
|
28
|
+
-----END CERTIFICATE-----
|
@@ -0,0 +1,17 @@
|
|
1
|
+
-----BEGIN CERTIFICATE-----
|
2
|
+
MIICvzCCAigCCQD3V6lFvX6dzDANBgkqhkiG9w0BAQUFADCBozELMAkGA1UEBhMC
|
3
|
+
VVMxCzAJBgNVBAgTAldBMRAwDgYDVQQHEwdTZWF0dGxlMRMwEQYDVQQKEwpBbWF6
|
4
|
+
b24uY29tMRYwFAYDVQQLEw1FQzIgQXV0aG9yaXR5MRowGAYDVQQDExFFQzIgQU1J
|
5
|
+
IEF1dGhvcml0eTEsMCoGCSqGSIb3DQEJARYdZWMyLWFtaS1nb3Ytd2VzdC0xQGFt
|
6
|
+
YXpvbi5jb20wHhcNMTEwODEyMTcyNjE1WhcNMjEwODA5MTcyNjE1WjCBozELMAkG
|
7
|
+
A1UEBhMCVVMxCzAJBgNVBAgTAldBMRAwDgYDVQQHEwdTZWF0dGxlMRMwEQYDVQQK
|
8
|
+
EwpBbWF6b24uY29tMRYwFAYDVQQLEw1FQzIgQXV0aG9yaXR5MRowGAYDVQQDExFF
|
9
|
+
QzIgQU1JIEF1dGhvcml0eTEsMCoGCSqGSIb3DQEJARYdZWMyLWFtaS1nb3Ytd2Vz
|
10
|
+
dC0xQGFtYXpvbi5jb20wgZ8wDQYJKoZIhvcNAQEBBQADgY0AMIGJAoGBANshKnhw
|
11
|
+
DUZ2/6VJwVTsXMUI1CGd5rpSpSLUCHGuqII+BDUvnp/sPxd1u6+I1QrbaaBAOm6+
|
12
|
+
evM77M7vNJXY3+JW00VOs9NgPEXBmn6UV4R1P7DljKurWGmRp8Fj1yVU4sSgZqqv
|
13
|
+
74SyhD0Z4ASczVcOiTZICeuQoJwmeZ8F20oLAgMBAAEwDQYJKoZIhvcNAQEFBQAD
|
14
|
+
gYEAH3vpkD80ngP1e18UYSVBCODArik+aeUPAzJrPDYorrnffbamks50IMTktyiu
|
15
|
+
za1JuplrvVsAKcQhyoPOq69bwRDg4L8VOXSCjjvsNuEhHL603h8jn6ghEouPCPl7
|
16
|
+
8s4Sr5XikmAgwFcPb/frNnLuZsSol08tISgPOlFg4KLv/bo=
|
17
|
+
-----END CERTIFICATE-----
|
@@ -0,0 +1,23 @@
|
|
1
|
+
-----BEGIN CERTIFICATE-----
|
2
|
+
MIIDzjCCAzegAwIBAgIJALDnZV+lpZdSMA0GCSqGSIb3DQEBBQUAMIGhMQswCQYD
|
3
|
+
VQQGEwJaQTEVMBMGA1UECBMMV2VzdGVybiBDYXBlMRIwEAYDVQQHEwlDYXBlIFRv
|
4
|
+
d24xJzAlBgNVBAoTHkFtYXpvbiBEZXZlbG9wbWVudCBDZW50cmUgKFNBKTEMMAoG
|
5
|
+
A1UECxMDQUVTMREwDwYDVQQDEwhBRVMgVGVzdDEdMBsGCSqGSIb3DQEJARYOYWVz
|
6
|
+
QGFtYXpvbi5jb20wHhcNMDUwODA5MTYwMTA5WhcNMDYwODA5MTYwMTA5WjCBoTEL
|
7
|
+
MAkGA1UEBhMCWkExFTATBgNVBAgTDFdlc3Rlcm4gQ2FwZTESMBAGA1UEBxMJQ2Fw
|
8
|
+
ZSBUb3duMScwJQYDVQQKEx5BbWF6b24gRGV2ZWxvcG1lbnQgQ2VudHJlIChTQSkx
|
9
|
+
DDAKBgNVBAsTA0FFUzERMA8GA1UEAxMIQUVTIFRlc3QxHTAbBgkqhkiG9w0BCQEW
|
10
|
+
DmFlc0BhbWF6b24uY29tMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQC8v/X5
|
11
|
+
zZv8CAVfNmvBM0br/RUcf1wU8xC5d2otFQQsQKB3qiWoj3oHeOWskOlTPFVZ8N+/
|
12
|
+
hEaMjyOUkg2+g6XEagCQtFCEBzUVoMjiQIBPiWj5CWkFtlav2zt33LZ0ErTND4xl
|
13
|
+
j7FQFqbaytHU9xuQcFO2p12bdITiBs5Kwoi9bQIDAQABo4IBCjCCAQYwHQYDVR0O
|
14
|
+
BBYEFPQnsX1kDVzPtX+38ACV8RhoYcw8MIHWBgNVHSMEgc4wgcuAFPQnsX1kDVzP
|
15
|
+
tX+38ACV8RhoYcw8oYGnpIGkMIGhMQswCQYDVQQGEwJaQTEVMBMGA1UECBMMV2Vz
|
16
|
+
dGVybiBDYXBlMRIwEAYDVQQHEwlDYXBlIFRvd24xJzAlBgNVBAoTHkFtYXpvbiBE
|
17
|
+
ZXZlbG9wbWVudCBDZW50cmUgKFNBKTEMMAoGA1UECxMDQUVTMREwDwYDVQQDEwhB
|
18
|
+
RVMgVGVzdDEdMBsGCSqGSIb3DQEJARYOYWVzQGFtYXpvbi5jb22CCQCw52VfpaWX
|
19
|
+
UjAMBgNVHRMEBTADAQH/MA0GCSqGSIb3DQEBBQUAA4GBAJJlWll4uGlrqBzeIw7u
|
20
|
+
M3RvomlxMESwGKb9gI+ZeORlnHAyZxvd9XngIcjPuU+8uc3wc10LRQUCn45a5hFs
|
21
|
+
zaCp9BSewLCCirn6awZn2tP8JlagSbjrN9YShStt8S3S/Jj+eBoRvc7jJnmEeMkx
|
22
|
+
O0wHOzp5ZHRDK7tGULD6jCfU
|
23
|
+
-----END CERTIFICATE-----
|
@@ -0,0 +1,9 @@
|
|
1
|
+
eu-west-1,us-east-1,manifest
|
2
|
+
ari-6b0d251f,ari-a23adfcb,initrd-2.6.20-1.3002.fc6xen.ari.manifest.xml
|
3
|
+
ari-7f0d250b,ari-b31cf9da,ec2-initrd-2.6.21.7-2.fc8xen.x86_64.manifest.xml
|
4
|
+
aki-6a0d251e,aki-a53adfcc,vmlinuz-2.6.20-1.3002.fc6xen.aki.manifest.xml
|
5
|
+
aki-550d2521,aki-9800e5f1,vmlinuz-2.6.18-xenU-ec2-v1.0.x86_64.aki.manifest.xml
|
6
|
+
aki-780d250c,aki-b51cf9dc,ec2-vmlinuz-2.6.21.7-2.fc8xen.x86_64.manifest.xml
|
7
|
+
ari-7d0d2509,ari-a51cf9cc,ec2-initrd-2.6.21.7-2.fc8xen.i386.manifest.xml
|
8
|
+
aki-540d2520,aki-9b00e5f2,vmlinuz-2.6.18-xenU-ec2-v1.0.i386.aki.manifest.xml
|
9
|
+
aki-7e0d250a,aki-a71cf9ce,ec2-vmlinuz-2.6.21.7-2.fc8xen.i386.manifest.xml
|
@@ -0,0 +1,251 @@
|
|
1
|
+
# Copyright 2008-2014 Amazon.com, Inc. or its affiliates. All Rights
|
2
|
+
# Reserved. Licensed under the Amazon Software License (the
|
3
|
+
# "License"). You may not use this file except in compliance with the
|
4
|
+
# License. A copy of the License is located at
|
5
|
+
# http://aws.amazon.com/asl or in the "license" file accompanying this
|
6
|
+
# file. This file is distributed on an "AS IS" BASIS, WITHOUT
|
7
|
+
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See
|
8
|
+
# the License for the specific language governing permissions and
|
9
|
+
# limitations under the License.
|
10
|
+
|
11
|
+
require 'open-uri'
|
12
|
+
require 'ec2/amitools/fileutil'
|
13
|
+
require 'ec2/amitools/manifestv20071010'
|
14
|
+
require 'ec2/amitools/instance-data'
|
15
|
+
require 'ec2/amitools/version'
|
16
|
+
require 'ec2/platform/current'
|
17
|
+
|
18
|
+
# Module containing utility methods for bundling an AMI.
|
19
|
+
module Bundle
|
20
|
+
class ImageType < String
|
21
|
+
MACHINE = new 'machine'
|
22
|
+
KERNEL = new 'kernel'
|
23
|
+
RAMDISK = new 'ramdisk'
|
24
|
+
VOLUME = new 'machine'
|
25
|
+
def ==(o)
|
26
|
+
self.object_id == o.object_id
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
|
31
|
+
CHUNK_SIZE = 10 * 1024 * 1024 # 10 MB in bytes.
|
32
|
+
|
33
|
+
def self.bundle_image( image_file,
|
34
|
+
user,
|
35
|
+
arch,
|
36
|
+
image_type,
|
37
|
+
destination,
|
38
|
+
user_private_key_path,
|
39
|
+
user_cert_path,
|
40
|
+
ec2_cert_path,
|
41
|
+
prefix,
|
42
|
+
optional_args,
|
43
|
+
debug = false,
|
44
|
+
inherit = true
|
45
|
+
)
|
46
|
+
begin
|
47
|
+
raise "invalid image-type #{image_type}" unless image_type.is_a? Bundle::ImageType
|
48
|
+
# Create named pipes.
|
49
|
+
digest_pipe = File::join('/tmp', "ec2-bundle-image-digest-pipe-#{$$}")
|
50
|
+
File::delete(digest_pipe) if File::exist?(digest_pipe)
|
51
|
+
unless system( "mkfifo #{digest_pipe}" )
|
52
|
+
raise "Error creating named pipe #{digest_pipe}"
|
53
|
+
end
|
54
|
+
|
55
|
+
# If the prefix differs from the file name create a symlink
|
56
|
+
# so that the file is tarred with the prefix name.
|
57
|
+
if prefix and File::basename( image_file ) != prefix
|
58
|
+
image_file_link = File::join( destination, prefix )
|
59
|
+
begin
|
60
|
+
FileUtils.ln_s(image_file, image_file_link)
|
61
|
+
rescue Exception => e
|
62
|
+
raise "Error creating symlink to image file, #{e.message}."
|
63
|
+
end
|
64
|
+
image_file = image_file_link
|
65
|
+
end
|
66
|
+
|
67
|
+
# Load and generate necessary keys.
|
68
|
+
name = prefix || File::basename( image_file )
|
69
|
+
manifest_file = File.join( destination, name + '.manifest.xml')
|
70
|
+
bundled_file_path = File::join( destination, name + '.tar.gz.enc' )
|
71
|
+
user_public_key = Crypto::certfile2pubkey( user_cert_path )
|
72
|
+
ec2_public_key = Crypto::certfile2pubkey( ec2_cert_path )
|
73
|
+
key = Format::bin2hex( Crypto::gensymkey )
|
74
|
+
iv = Format::bin2hex( Crypto::gensymkey )
|
75
|
+
|
76
|
+
# Bundle the AMI.
|
77
|
+
# The image file is tarred - to maintain sparseness, gzipped for
|
78
|
+
# compression and then encrypted with AES in CBC mode for
|
79
|
+
# confidentiality.
|
80
|
+
# To minimize disk I/O the file is read from disk once and
|
81
|
+
# piped via several processes. The tee is used to allow a
|
82
|
+
# digest of the file to be calculated without having to re-read
|
83
|
+
# it from disk.
|
84
|
+
tar = EC2::Platform::Current::Tar::Command.new.create.dereference.sparse
|
85
|
+
tar.owner(0).group(0)
|
86
|
+
tar.add(File::basename( image_file ), File::dirname( image_file ))
|
87
|
+
openssl = EC2::Platform::Current::Constants::Utility::OPENSSL
|
88
|
+
pipeline = EC2::Platform::Current::Pipeline.new('image-bundle-pipeline', debug)
|
89
|
+
pipeline.concat([
|
90
|
+
['tar', "#{openssl} sha1 < #{digest_pipe} & " + tar.expand],
|
91
|
+
['tee', "tee #{digest_pipe}"],
|
92
|
+
['gzip', 'gzip -9'],
|
93
|
+
['encrypt', "#{openssl} enc -e -aes-128-cbc -K #{key} -iv #{iv} > #{bundled_file_path}"]
|
94
|
+
])
|
95
|
+
digest = nil
|
96
|
+
begin
|
97
|
+
digest = pipeline.execute.split(/\s+/).last.strip
|
98
|
+
rescue EC2::Platform::Current::Pipeline::ExecutionError => e
|
99
|
+
$stderr.puts e.message
|
100
|
+
exit 1
|
101
|
+
end
|
102
|
+
|
103
|
+
# Split the bundled AMI.
|
104
|
+
# Splitting is not done as part of the compress, encrypt digest
|
105
|
+
# stream, so that the filenames of the parts can be easily
|
106
|
+
# tracked. The alternative is to create a dedicated output
|
107
|
+
# directory, but this leaves the user less choice.
|
108
|
+
parts = Bundle::split( bundled_file_path, name, destination )
|
109
|
+
|
110
|
+
# Sum the parts file sizes to get the encrypted file size.
|
111
|
+
bundled_size = 0
|
112
|
+
parts.each do |part|
|
113
|
+
bundled_size += File.size( File.join( destination, part ) )
|
114
|
+
end
|
115
|
+
|
116
|
+
# Encrypt key and iv.
|
117
|
+
padding = OpenSSL::PKey::RSA::PKCS1_PADDING
|
118
|
+
user_encrypted_key = user_public_key.public_encrypt( key, padding )
|
119
|
+
ec2_encrypted_key = ec2_public_key.public_encrypt( key, padding )
|
120
|
+
user_encrypted_iv = user_public_key.public_encrypt( iv, padding )
|
121
|
+
ec2_encrypted_iv = ec2_public_key.public_encrypt( iv, padding )
|
122
|
+
|
123
|
+
# Digest parts.
|
124
|
+
part_digest_list = Bundle::digest_parts( parts, destination )
|
125
|
+
|
126
|
+
# Launch-customization data
|
127
|
+
patch_in_instance_meta_data(image_type, optional_args) if inherit
|
128
|
+
|
129
|
+
# Sanity-check block-device-mappings
|
130
|
+
bdm = optional_args[:block_device_mapping]
|
131
|
+
if bdm.is_a? Hash
|
132
|
+
[ 'root', 'ami' ].each do |item|
|
133
|
+
if bdm[item].to_s.strip.empty?
|
134
|
+
$stdout.puts "Block-device-mapping has no '#{item}' entry. A launch-time default will be used."
|
135
|
+
end
|
136
|
+
end
|
137
|
+
end
|
138
|
+
|
139
|
+
|
140
|
+
# Create bundle manifest.
|
141
|
+
$stdout.puts 'Creating bundle manifest...'
|
142
|
+
manifest = ManifestV20071010.new()
|
143
|
+
manifest.init(optional_args.merge({:name => name,
|
144
|
+
:user => user,
|
145
|
+
:image_type => image_type.to_s,
|
146
|
+
:arch => arch,
|
147
|
+
:reserved => nil,
|
148
|
+
:parts => part_digest_list,
|
149
|
+
:size => File::size( image_file ),
|
150
|
+
:bundled_size => bundled_size,
|
151
|
+
:user_encrypted_key => Format::bin2hex( user_encrypted_key ),
|
152
|
+
:ec2_encrypted_key => Format::bin2hex( ec2_encrypted_key ),
|
153
|
+
:cipher_algorithm => Crypto::SYM_ALG,
|
154
|
+
:user_encrypted_iv => Format::bin2hex( user_encrypted_iv ),
|
155
|
+
:ec2_encrypted_iv => Format::bin2hex( ec2_encrypted_iv ),
|
156
|
+
:digest => digest,
|
157
|
+
:digest_algorithm => Crypto::DIGEST_ALG,
|
158
|
+
:privkey_filename => user_private_key_path,
|
159
|
+
:kernel_id => optional_args[:kernel_id],
|
160
|
+
:ramdisk_id => optional_args[:ramdisk_id],
|
161
|
+
:product_codes => optional_args[:product_codes],
|
162
|
+
:ancestor_ami_ids => optional_args[:ancestor_ami_ids],
|
163
|
+
:block_device_mapping => optional_args[:block_device_mapping],
|
164
|
+
:bundler_name => EC2Version::PKG_NAME,
|
165
|
+
:bundler_version => EC2Version::PKG_VERSION,
|
166
|
+
:bundler_release => EC2Version::PKG_RELEASE}))
|
167
|
+
|
168
|
+
# Write out the manifest file.
|
169
|
+
File.open( manifest_file, 'w' ) { |f| f.write( manifest.to_s ) }
|
170
|
+
$stdout.puts 'Bundle manifest is %s' % manifest_file
|
171
|
+
ensure
|
172
|
+
# Clean up.
|
173
|
+
if bundled_file_path and File.exist?( bundled_file_path )
|
174
|
+
File.delete( bundled_file_path )
|
175
|
+
end
|
176
|
+
File::delete( digest_pipe ) if digest_pipe and File::exist?(digest_pipe)
|
177
|
+
if image_file_link and File::exist?( image_file_link )
|
178
|
+
File::delete( image_file_link )
|
179
|
+
end
|
180
|
+
end
|
181
|
+
end
|
182
|
+
|
183
|
+
def self.patch_in_instance_meta_data(image_type, optional_args)
|
184
|
+
if (image_type == ImageType::VOLUME || image_type == ImageType::MACHINE )
|
185
|
+
instance_data = EC2::InstanceData.new
|
186
|
+
if !instance_data.instance_data_accessible
|
187
|
+
raise "Error accessing instance data. If you are not bundling on an EC2 instance use --no-inherit."
|
188
|
+
else
|
189
|
+
[
|
190
|
+
[:ancestor_ami_ids, instance_data.ancestor_ami_ids, Proc.new do |key, value|
|
191
|
+
if (optional_args[key].nil?)
|
192
|
+
ancestry = nil
|
193
|
+
if value.nil? or value.to_s.empty?
|
194
|
+
ancestry = []
|
195
|
+
elsif value.is_a? Array
|
196
|
+
ancestry = value
|
197
|
+
else
|
198
|
+
ancestry = [value]
|
199
|
+
end
|
200
|
+
ami_id = instance_data.ami_id
|
201
|
+
$stdout.puts "Unable to read instance meta-data for ami-id" if ami_id.nil?
|
202
|
+
ancestry << ami_id unless(ami_id.nil? or ancestry.include?(ami_id))
|
203
|
+
optional_args[key] = ancestry if ancestry && ancestry.length > 0
|
204
|
+
end
|
205
|
+
end],
|
206
|
+
[:kernel_id, instance_data.kernel_id, nil],
|
207
|
+
[:ramdisk_id, instance_data.ramdisk_id, nil],
|
208
|
+
[:product_codes, instance_data.product_codes, nil],
|
209
|
+
[:block_device_mapping, instance_data.block_device_mapping, nil],
|
210
|
+
].each do |key, value, block|
|
211
|
+
begin
|
212
|
+
if value.nil?
|
213
|
+
$stdout.puts "Unable to read instance meta-data for #{key.to_s.gsub('_','-')}"
|
214
|
+
block.call(key, value) if block
|
215
|
+
else
|
216
|
+
if block
|
217
|
+
block.call(key, value)
|
218
|
+
else
|
219
|
+
optional_args[key] ||= value
|
220
|
+
end
|
221
|
+
end
|
222
|
+
rescue
|
223
|
+
$stdout.puts "Unable to set #{key.to_s.gsub('_','-')} from instance meta-data"
|
224
|
+
end
|
225
|
+
end
|
226
|
+
end
|
227
|
+
end
|
228
|
+
end
|
229
|
+
|
230
|
+
def self.split( filename, prefix, destination )
|
231
|
+
$stdout.puts "Splitting #{filename}..."
|
232
|
+
part_filenames = FileUtil::split(filename,
|
233
|
+
prefix,
|
234
|
+
CHUNK_SIZE,
|
235
|
+
destination)
|
236
|
+
part_filenames.each { |name| puts "Created #{name}" }
|
237
|
+
part_filenames
|
238
|
+
end
|
239
|
+
|
240
|
+
def self.digest_parts( basenames, dir )
|
241
|
+
$stdout.puts 'Generating digests for each part...'
|
242
|
+
parts_digests = Array.new
|
243
|
+
basenames.each do |basename|
|
244
|
+
File.open(File.join(dir, basename)) do |f|
|
245
|
+
parts_digests << [basename, Crypto.digest( f )]
|
246
|
+
end
|
247
|
+
end
|
248
|
+
$stdout.puts 'Digests generated.'
|
249
|
+
parts_digests
|
250
|
+
end
|
251
|
+
end
|