pax_global_header 0000666 0000000 0000000 00000000064 14024143525 0014512 g ustar 00root root 0000000 0000000 52 comment=215bbe4c607a647dbe8fadc95bce4789d8819384
aws-ec2-instance-connect-config-1.1.14/ 0000775 0000000 0000000 00000000000 14024143525 0017533 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/.github/ 0000775 0000000 0000000 00000000000 14024143525 0021073 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/.github/PULL_REQUEST_TEMPLATE.md 0000664 0000000 0000000 00000000251 14024143525 0024672 0 ustar 00root root 0000000 0000000 *Issue #, if available:*
*Description of changes:*
By submitting this pull request, I confirm that my contribution is made under the terms of the Apache 2.0 license.
aws-ec2-instance-connect-config-1.1.14/.gitignore 0000664 0000000 0000000 00000000015 14024143525 0021517 0 ustar 00root root 0000000 0000000 out
rpmbuild
aws-ec2-instance-connect-config-1.1.14/CODE_OF_CONDUCT.md 0000664 0000000 0000000 00000000467 14024143525 0022341 0 ustar 00root root 0000000 0000000 ## Code of Conduct
This project has adopted the [Amazon Open Source Code of Conduct](https://aws.github.io/code-of-conduct).
For more information see the [Code of Conduct FAQ](https://aws.github.io/code-of-conduct-faq) or contact
opensource-codeofconduct@amazon.com with any additional questions or comments.
aws-ec2-instance-connect-config-1.1.14/CONTRIBUTING.md 0000664 0000000 0000000 00000007103 14024143525 0021765 0 ustar 00root root 0000000 0000000 # Contributing Guidelines
Thank you for your interest in contributing to our project. Whether it's a bug report, new feature, correction, or additional
documentation, we greatly value feedback and contributions from our community.
Please read through this document before submitting any issues or pull requests to ensure we have all the necessary
information to effectively respond to your bug report or contribution.
## Reporting Bugs/Feature Requests
We welcome you to use the GitHub issue tracker to report bugs or suggest features.
When filing an issue, please check [existing open](https://github.com/awslabs/aws-ec2-instance-connect-config/issues), or [recently closed](https://github.com/awslabs/aws-ec2-instance-connect-config/issues?utf8=%E2%9C%93&q=is%3Aissue%20is%3Aclosed%20), issues to make sure somebody else hasn't already
reported the issue. Please try to include as much information as you can. Details like these are incredibly useful:
* A reproducible test case or series of steps
* The version of our code being used
* Any modifications you've made relevant to the bug
* Anything unusual about your environment or deployment
## Contributing via Pull Requests
Contributions via pull requests are much appreciated. Before sending us a pull request, please ensure that:
1. You are working against the latest source on the *master* branch.
2. You check existing open, and recently merged, pull requests to make sure someone else hasn't addressed the problem already.
3. You open an issue to discuss any significant work - we would hate for your time to be wasted.
To send us a pull request, please:
1. Fork the repository.
2. Modify the source; please focus on the specific change you are contributing. If you also reformat all the code, it will be hard for us to focus on your change.
3. Ensure local tests pass.
4. Commit to your fork using clear commit messages.
5. Send us a pull request, answering any default questions in the pull request interface.
6. Pay attention to any automated CI failures reported in the pull request, and stay involved in the conversation.
GitHub provides additional document on [forking a repository](https://help.github.com/articles/fork-a-repo/) and
[creating a pull request](https://help.github.com/articles/creating-a-pull-request/).
## Finding contributions to work on
Looking at the existing issues is a great way to find something to contribute on. As our projects, by default, use the default GitHub issue labels ((enhancement/bug/duplicate/help wanted/invalid/question/wontfix), looking at any ['help wanted'](https://github.com/awslabs/aws-ec2-instance-connect-config/labels/help%20wanted) issues is a great place to start.
## Code of Conduct
This project has adopted the [Amazon Open Source Code of Conduct](https://aws.github.io/code-of-conduct).
For more information see the [Code of Conduct FAQ](https://aws.github.io/code-of-conduct-faq) or contact
opensource-codeofconduct@amazon.com with any additional questions or comments.
## Security issue notifications
If you discover a potential security issue in this project we ask that you notify AWS/Amazon Security via our [vulnerability reporting page](http://aws.amazon.com/security/vulnerability-reporting/). Please do **not** create a public github issue.
## Licensing
See the [LICENSE](https://github.com/awslabs/aws-ec2-instance-connect-config/blob/master/LICENSE) file for our project's licensing. We will ask you to confirm the licensing of your contribution.
We may ask you to sign a [Contributor License Agreement (CLA)](http://en.wikipedia.org/wiki/Contributor_License_Agreement) for larger changes.
aws-ec2-instance-connect-config-1.1.14/LICENSE 0000664 0000000 0000000 00000026136 14024143525 0020550 0 ustar 00root root 0000000 0000000
Apache License
Version 2.0, January 2004
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS
APPENDIX: How to apply the Apache License to your work.
To apply the Apache License to your work, attach the following
boilerplate notice, with the fields enclosed by brackets "[]"
replaced with your own identifying information. (Don't include
the brackets!) The text should be enclosed in the appropriate
comment syntax for the file format. We also recommend that a
file or class name and description of purpose be included on the
same "printed page" as the copyright notice for easier
identification within third-party archives.
Copyright [yyyy] [name of copyright owner]
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
aws-ec2-instance-connect-config-1.1.14/Makefile 0000664 0000000 0000000 00000001561 14024143525 0021176 0 ustar 00root root 0000000 0000000 VERSION_FILE=./VERSION
pkgver=$(shell cat $(VERSION_FILE))
version = $(firstword $(subst -, ,$(pkgver)))
release = $(lastword $(subst -, ,$(pkgver)))
default: clean ;
deb:
./bin/make_deb.sh $(version) $(release)
rpm:
./bin/make_rpm.sh $(version) $(release)
docker-build-rpm:
mkdir -p out
docker build -f docker/generic/Dockerfile . -t eic-rpm-builder -q
docker run -i --mount type=bind,source="$(shell pwd)/out",target=/out eic-rpm-builder
docker-build-deb:
mkdir -p out
docker build -f docker/ubuntu/Dockerfile . -t eic-deb-builder -q
docker run -i --mount type=bind,source="$(shell pwd)/out",target=/out eic-deb-builder
docker-build:: docker-build-rpm docker-build-deb
clean:
$(shell rm -rf ec2-instance-connect*)
$(shell rm -rf ./rpmbuild/SOURCES)
$(shell rm -rf ./deb-src)
$(shell rm -rf ./srpm_results)
$(shell rm -rf ./rpm_results)
$(shell rm -rf ./out)
aws-ec2-instance-connect-config-1.1.14/NOTICE 0000664 0000000 0000000 00000000151 14024143525 0020434 0 ustar 00root root 0000000 0000000 AWS Ec2 Instance Connect Config
Copyright 2018 Amazon.com, Inc. or its affiliates. All Rights Reserved.
aws-ec2-instance-connect-config-1.1.14/README.md 0000664 0000000 0000000 00000022625 14024143525 0021021 0 ustar 00root root 0000000 0000000 # AWS EC2 Instance Connect Configuration
This package contains the EC2 instance configuration and scripts necessary to enable AWS EC2 Instance Connect.
## AuthorizedKeysCommand
The AuthorizedKeysCommand is split into three parts:
* eic_run_authorized_keys is the main entry point and wraps the rest in a 5 second timeout
* eic_curl_authorized_keys, which is the entry point for sshd on an ssh call
* eic_parse_authorized_keys, which is the main authorized keys command logic
This split is intentional - as parse takes all necessary pieces as command inputs is can be unit tested independently. curl, however, obviously needs to curl EC2 Instance Metadata Service and so cannot be tested without mocking the actual service.
### eic_curl_authorized_keys
The curl script verifies we are actually running on an EC2 instance and cURLs relevant information from EC2 Instance Metadata Service and send it to parse.
Note that it must make several curl commands to proceed. If it cannot do so it fast-fails to prevent blocking the ssh daemon.
The command also queries several OCSP staples from EC2 Instance Metadata Service.
These OCSP staples are provided from the AWS EC2 Instance Connect Service to avoid needing to query each CRL or OCSP authority at ssh calltime as that would have major performance implications.
The staples are passed to and used by parse_authorized_keys to check certificate validity without the need for extra external calls.
### eic_parse_authorized_keys
In addition to the fields required to complete all the below process, a key fingerprint may be provided. If a key fingerprint is specified then only ssh keys found matching that fingerprint will be returned.
#### Certificate Validation
The core idea behind AWS EC2 Instance Connect is that all ssh keys vended have been trusted by AWS. This can be verified by checking each key's signature (more on that later) and vetting the signing certificate used.
The signing certificate goes through a deep verification flow that checks:
* The CN matches the service
* The certificate trust chain can be verified up through the Amazon Trust Services Certificate Authority
* The entire certificate chain is valid - ie, none of them have been revoked
The first and second are done via standard openssl checks. The third, however, does not query the relevant CRLs or OCSP authorities at runtime to avoid adding a network call to sshd.
Instead, OCSP staples are expected to be provided by the invoker (i.e., eic_curl_authorized_keys).
As OCSP staples are cryptographically signed and can be verified against a trusted authority these are considered a sufficient validity check.
#### Key Processing
The keys are expected to be presented to the script in the format
# Key Metadata
# Key Metadata
# Key Metadata
[ssh key]
signature
Currently, the expected metadata is, in order,
1. Expiration timestamp
2. Instance ID
3. IAM Caller
4. Request ID
Once this data has been loaded, the following checks are run:
* Has the expiration timestamp passed?
* Is the instance ID correct?
* Does the signature match the provided data?
* If a specific key fingerprint was provided to search for, does this key match that fingerprint?
The signature is specifically expected to be for the *entire* key blob - all metadata entries plus the ssh key. It should have been generated by the AWS EC2 Instance Connect service's private key, which is verified using the vetted signing certificate.
If all of these checks pass then the key will be presented to the ssh daemon. Otherwise, it will be ignored and the next key will be processed.
Any time a key is provided to the ssh daemon it will be logged to the system authpriv log for auditing purposes.
## Host Key Harvesting
The fourth script, eic_harvest_hostkeys, has no direct relation to the AuthorizedKeysCommand. Instead, it is used to pass the instance's ssh host keys back to the EC2 Instance Connect Service.
This is necessary to establish trust for the EC2 Console for the console's one-click in-browser ssh terminal feature.
### systemd Module
The systemd module provided for host key harvesting is a basic one-shot to invoke eic_harvest_hostkeys.
### eic_harvest_host_keys
The host key harvesting script has to run similar logic to eic_curl_authorized_keys to get some basic information from Instance Metadata Service about the instance itself.
It then reads the ssh host keys on the machine, then creates and signs an AWS Signature Version 4 POST request which is sent to our
service at `https://ec2-instance-connect.${region}.${domain}/PutEC2HostKeys/` with the host keys in the payload.
## Unit Testing
As parse_authorized_keys requires a valid certificate, CA, and OCSP staples, unit testing is a somewhat involved process.
This has been automated to a convenient entry point: `bin/unit_test_suite.sh`. This will
1. Invoke `bin/unit-test/setup_certificates.sh` to generate a test CA and trust chain
2. Invoke `bin/unit-test/generate_ocsp.sh` to generate OCSP staples for the certificates
3. Iterate over unit-test/input/direct and unit-test/input/unsigned and test all entries via `bin/unit-test/test_authorized_keys.sh`, expecting the matching contents of unit-test/expected-output
unit-test/input/direct's contents are passed directly as-is as they are not expected to contain valid signatures.
unit-test/input/unsigned's contents, however, are expected to get far enough in the process to (potentially) need a valid signature. As such, signatures are generated on-the-fly using the pre-generated certificate's private key.
The structure of unit-test/input/unsigned, rather than files, is directories to test. The directory's contents should be in a numeric order that the test script will iterate.
Each file should have *one* test key blob to sign.
The actual test input will be the result of generating signatures for each file and constructing an imitation of the service's key bundle.
## End-to-End Testing
Integration testing requires running these scriptlets on an actual EC2 instance. This has been scripted for your convenience.
To run integration tests against a given platform (eg, RHEL or Ubuntu):
1. Build a test package (for example, `make deb`)
2. Select an AMI of the platform you desire (for example, the latest Ubuntu AMI)
3. Configure your VPC for testing
* Configure an EC2 keypair. Make sure to save the private key!
* Configure your security group to allow SSH from your test-run machine
* Set your subnet to auto-assign public IPs. Testing currently requires SSHing via public IP.
4. Determine the appropriate EC2 username for your platform (see below)
5. Determine the "config name" for your platform (see below)
6. Determine instance types you would like to test (or all supported in your subnet's zone)
7. The actual tests are invoked by the following command:
`./bin/integration_test_suite.sh -r [region] -a [ami id] -u [ec2 username] -k [ec2 keypair name] -s [subnet id] -g [security group id] -l [config name] -p [/path/to/private/key] -i [/path/to/test/package] [-t [instance,type,list]] [-d [/output/directory]]`
This will run all tests under the integration-test/test directory against all requested instance types (or all types in the zone if not specified). Any error output will be written in files pathed /path/instance-type/test-name in the output directory. An output directory will be autogenerated if none is specified.
EC2 usernames and "config names" for each supported platform is as follows:
| Platform | EC2 Username | "Config" Name |
| --- | --- | --- |
| Amazon Linux | ec2-user | amazon-linux |
| Ubuntu | ubuntu | ubuntu |
| RHEL | ec2-user | rhel |
Again, please note that if you do not specify instance types then all supported by the subnet's zone will be run. This can take a very long time. It is therefore recommended you specify at least one Nitro and at least one non-Nitro instance type, such as t2.micro and m5.large.
## Building RPM/Debian Packaging
If desired, this scripting can be added to an EC2 instance for further testing. A convenience pair of scripts - bin/make_rpm.sh and bin/make_deb.sh - have been provided to quickly build test packages.
Each may be invoked via `make rpm` and `make deb` respectively.
Debian packaging in particular requires you have a GPG key configured on your system.
Be sure to update VERSION! If you use the same VERSION as the latest public release then test instances will not see it as an update!
### [EXPERIMENTAL] Docker Container Build
You can build .rpm packages using Docker via `make docker-build-rpm` and .deb packages via `make docker-build-deb`. You can run both via `make docker-build`. The built packages will be in the `out` directory. This currently does not support the Amazon-proprietary build process.
**Debian packaging tools are intended for testing purposes only. Please follow standard Debian process to submit patches.**
### Why is it generic.rpm?
"generic.rpm" is used internally to differentiate the specfile for Fedora/RHEL/CentOS from Amazon Linux.
There is a separate Amazon-proprietary rpmspec and build process optimized for Amazon Linux.
## Why UNIX shell?
This package is intended as a simple reference implementation of the instance-side pieces of the EC2 Instance Connect feature, though as time has gone on it has become much more complex than originally intended.
Amazon is considering reimplementation in another language for the future but for the time being we will continue to iterate on the shell implementation.
## License
This library is licensed under the Apache 2.0 License.
aws-ec2-instance-connect-config-1.1.14/VERSION 0000664 0000000 0000000 00000000007 14024143525 0020600 0 ustar 00root root 0000000 0000000 1.1-14
aws-ec2-instance-connect-config-1.1.14/bin/ 0000775 0000000 0000000 00000000000 14024143525 0020303 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/bin/integration-test/ 0000775 0000000 0000000 00000000000 14024143525 0023603 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/bin/integration-test/get_zone_instance_types.sh 0000775 0000000 0000000 00000002123 14024143525 0031062 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
# Load the list of instance types supported in a given zone.
# XXX: The mechanism for this is based on reserved instances. This may not be exhaustive in every zone.
region=$1
zone=$2
raw=$(aws ec2 describe-reserved-instances-offerings --filters "Name=availability-zone,Values=$zone" --region "${region}")
types=$(echo "{$raw}" | grep "InstanceType" | cut -d '"' -f 4)
echo "${types}"
aws-ec2-instance-connect-config-1.1.14/bin/integration-test/run_instance.sh 0000775 0000000 0000000 00000006312 14024143525 0026634 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
# Attempts to launch an instance to the given specification
# Outputs instance ID on success or where it failed otherwise
while getopts ":t:r:a:k:s:g:n:o:p:" opt ; do
case "${opt}" in
t)
instance_type="${OPTARG}"
;;
r)
region="${OPTARG}"
;;
a)
ami_id="${OPTARG}"
;;
k)
key_name="${OPTARG}"
;;
s)
subnet_id="${OPTARG}"
;;
g)
security_group_id="${OPTARG}"
;;
n)
name_tag="${OPTARG}"
;;
o)
osuser="${OPTARG}"
;;
p)
private_key="${OPTARG}"
;;
*)
echo "Usage: $0 -t instance-type -r aws-region -a ami -k ec2-key-pair -s subnet -g security-group -n name-tag-value"
exit 1
;;
esac
done
launch_output=$(aws ec2 run-instances --region "${region}" --image-id "${ami_id}" --key-name "${key_name}" --security-group-ids "${security_group_id}" --subnet-id "${subnet_id}" --instance-initiated-shutdown-behavior "terminate" --instance-type "${instance_type}" --tag-specifications "[{\"ResourceType\":\"instance\",\"Tags\":[{\"Key\":\"Name\",\"Value\":\"${name_tag}\"}]}]")
launch_code=$?
if [ "${launch_code}" -ne 0 ] ; then
echo "Instance launch failed!"
exit "${launch_code}"
fi
instance_id=$(echo "${launch_output}" | grep \"InstanceId\" | cut -d '"' -f 4)
running=0
try="0"
# Wait up to 5 minutes for the instance to come up, checking every 5 seconds
while [ $try -lt 60 ] ; do
aws ec2 describe-instances --instance-ids "${instance_id}" | grep "Name" | grep -q "running"
launch_code=$?
if [ "${launch_code}" -eq 0 ] ; then
try="60"
running=1
else
try=$((try+1))
sleep 5
fi
done
if [ $running -eq 0 ] ; then
echo "Timed out waiting for instance to enter 'running' state"
exit 1
fi
# Wait a bit extra to let sshd come up
ssh_try="0"
public_ip=$(aws ec2 describe-instances --instance-ids "${instance_id}" | grep "PublicIp" | cut -d '"' -f 4 | uniq)
while [ $ssh_try -lt 30 ] ; do
ssh -q -i "${private_key}" -o StrictHostKeyChecking=no "${osuser}@${public_ip}" exit 2>&1
launch_code="${?}"
if [ "${launch_code}" -eq 0 ] ; then
# Everything's ready
echo "${instance_id}"
exit 0
fi
ssh_try=$((ssh_try+1))
sleep 10
done
echo "Timed out waiting for sshd to start on instance (or keypair is misconfigured)"
exit 1
aws-ec2-instance-connect-config-1.1.14/bin/integration-test/run_test_sweep.sh 0000775 0000000 0000000 00000003607 14024143525 0027216 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
TOPDIR=$(dirname "$( cd "$( dirname "$( dirname "${BASH_SOURCE[0]}" )" )" && pwd)")
while getopts ":i:p:k:u:z:o:l:f:" opt ; do
case "${opt}" in
i)
instance_id="${OPTARG}"
;;
p)
public_ip="${OPTARG}"
;;
k)
keypath="${OPTARG}"
;;
u)
osuser="${OPTARG}"
;;
z)
zone="${OPTARG}"
;;
o)
output_directory="${OPTARG}"
;;
l)
distro="${OPTARG}"
;;
f)
package_path="${OPTARG}"
;;
*)
;;
esac
done
overall_success=0
for testscript in "${TOPDIR}"/integration-test/test/* ; do
filename="${testscript##*/}"
test_output=$($testscript -i "${instance_id}" -p "${public_ip}" -z "${zone}" -u "${osuser}" -k "${keypath}" -l "${distro}" -t "${package_path}")
test_exit="${?}"
if [ "${test_exit}" -ne 0 ] ; then
echo "${test_output}" > "${output_directory}/${filename}"
echo "Test ${filename} FAILED"
overall_success=1
else
echo "Test ${filename} PASSED"
fi
done
exit "${overall_success}"
aws-ec2-instance-connect-config-1.1.14/bin/integration_test_suite.sh 0000775 0000000 0000000 00000014421 14024143525 0025437 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
# Runs our full suite of integration tests against all known instance types
# Basic string concat w/ newline
concat () {
printf "%s\n%s" "${1}" "${2}"
}
TOPDIR=$(dirname "$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd)")
if [ $# -lt 8 ] ; then
echo "Usage: $0 -r region -a ami -k ec2-key-pair -s subnet -g security-group -p /private/key/path -u ec2-os-user -l ami-linux-distro-name -i /path/to/package/file [-d /test/output/directory] [-t instance,types,list]"
exit 1
fi
types_specified=0
while getopts ":r:a:k:s:g:d:p:t:u:l:i:" opt ; do
case "${opt}" in
r)
region="${OPTARG}"
;;
a)
ami_id="${OPTARG}"
;;
k)
key_name="${OPTARG}"
;;
s)
subnet_id="${OPTARG}"
;;
g)
security_group_id="${OPTARG}"
;;
d)
output_directory="${OPTARG}"
;;
p)
private_key="${OPTARG}"
;;
t)
IFS=',' read -r -a instance_types <<< "${OPTARG}"
types_specified=1
;;
u)
osuser="${OPTARG}"
;;
l)
distro="${OPTARG}"
;;
i)
package_path="${OPTARG}"
;;
*)
echo "Usage: $0 -r region -a ami -k ec2-key-pair -s subnet -g security-group -p /private/key/path -u ec2-os-user -l ami-linux-distro-name -i /path/to/package/file [-d /test/output/directory] [-t instance,types,list]"
exit 1
;;
esac
done
# Ensure we have config for this distro
if [ ! -f "${TOPDIR}/integration-test/config/${distro}" ] ; then
echo "Unsupported distro ${distro} will not be tested"
exit 1
fi
source "${TOPDIR}/integration-test/config/${distro}"
package_name="${package_path##*/}"
if [ -z "${output_directory}" ] ; then
timestamp=$(/bin/date -u "+%Y-%m-%d_%H:%M:%S")
# TODO: Better autogenerated directory. Include AMI/test name?
output_directory="/tmp/eic_integ_test_${timestamp}"
echo "No output directory set. Creating & using ${output_directory}"
mkdir "${output_directory}"
fi
# Fetch information about the subnet (AZ, etc)
subnet_output=$(aws ec2 describe-subnets --subnet-ids "${subnet_id}")
subnet_status=$?
if [ "${subnet_status}" -ne 0 ] ; then
echo "Failed to query subnet information:"
echo "${subnet_output}"
exit "${subnet_status}"
fi
zone=$(echo "${subnet_output}" | grep "\"AvailabilityZone\"" | cut -d '"' -f 4)
if [ $types_specified -eq 0 ] ; then
echo "Instance types not specified. Will test all supported in this subnet."
instance_types=$("${TOPDIR}/bin/integration-test/get_zone_instance_types.sh" "${region}" "${zone}")
IFS=$'\n' read -d '' -r -a instance_types <<< "${instance_types}"
fi
overall_exit=0
for instance_type in "${instance_types[@]}" ; do
echo "Testing ${instance_type}"
mkdir "${output_directory}/${instance_type}"
output=""
instance_exit=0
# Run instance
launch_output=$("${TOPDIR}/bin/integration-test/run_instance.sh" -t "${instance_type}" -a "${ami_id}" -k "${key_name}" -s "${subnet_id}" -g "${security_group_id}" -n "EIC Integration Test ${instance_type}" -r "${region}" -o "${osuser}" -p "${private_key}")
launch_status=$?
if [ "${launch_status}" -ne 0 ] ; then
output=$(concat "${output}" "${launch_output}")
instance_exit=1
else
instance_id=$launch_output
public_ip=$(aws ec2 describe-instances --instance-ids "${instance_id}" | grep "PublicIp" | cut -d '"' -f 4 | uniq)
# scp the package file to the instance and install it
output=$(concat "${output}" "scping package file to instance")
scp_out=$(scp -i "${private_key}" -o StrictHostKeyChecking=no "${package_path}" "${osuser}@${public_ip}:/tmp/${package_name}" 2>&1)
install_status=$?
output=$(concat "${output}" "${scp_out}")
if [ "${install_status}" -eq 0 ] ; then
# FIXME: Ubuntu AMIs fail here due to dpkg lock contention
ssh -i "${private_key}" -o StrictHostKeyChecking=no "${osuser}@${public_ip}" "${INSTALL} /tmp/${package_name}" 1>/dev/null 2>&1
install_status=$?
output=$(concat "${output}" "${scp_out}")
else
output=$(concat "${output}" "Failed to scp package to instance.")
instance_exit=1
fi
if [ "${install_status}" -ne 0 ] ; then
output=$(concat "${output}" "Failed to install EIC package on instance.")
instance_exit=1
else
# Run the actual tests
"${TOPDIR}/bin/integration-test/run_test_sweep.sh" -i "${instance_id}" -p "${public_ip}" -k "${private_key}" -u "${osuser}" -z "${zone}" -o "${output_directory}/${instance_type}" -l "${distro}" -f "${package_path}"
test_exit=$?
if [ "${test_exit}" -ne 0 ] ; then
overall_exit=1
else
rmdir "${output_directory}/${instance_type}"
fi
fi
# Terminate the instance
aws ec2 terminate-instances --instance-ids "${instance_id}" 1>/dev/null
fi
if [ "${instance_exit}" -ne 0 ] ; then
echo "Could not run tests on instance."
echo "${output}" > "${output_directory}/${instance_type}/setup"
overall_exit=1
fi
done
if [ "${overall_exit}" -ne 0 ] ; then
echo "Some instance types failed. Please check the contents of ${output_directory} for details."
else
echo "All instance types passed! Removing failed output directory since it is empty."
rmdir "${output_directory}"
fi
exit "${overall_exit}"
aws-ec2-instance-connect-config-1.1.14/bin/make_deb.sh 0000775 0000000 0000000 00000004737 14024143525 0022404 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
# XXX: This script builds a local 3.0 (native) package for testing purposes.
# Any actual patches should be developed and submitted using apt-source and Quilt.
# Note: this will only work on a system with dpkg build tools installed (ie, Debian & its derivatives)
# It is also strongly recommended you install devtools (dch, etc) to assist with package building
# You are *REQUIRED* to have debhelper and devscripts installed!
if [ $# -ne 2 ] ; then
echo "Usage: make_deb.sh [version] [release]"
echo " ie, make_deb.sh [1.1] [1]"
exit 1
fi
md5 () {
echo -n "${1}" | md5sum | sed 's/\s.*$//'
}
sha1 () {
echo -n "${1}" | sha1sum | sed 's/\s.*$//'
}
sha256 () {
echo -n "${1}" | sha256sum | sed 's/\s.*$//'
}
TOPDIR=$(dirname "$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )")
version=$1
release=$2
pkgdir="${TOPDIR}/ec2-instance-connect-${version}-${release}"
# Copy source files
mkdir "${pkgdir}"
mkdir -p "${pkgdir}/ec2-instance-connect"
cp "${TOPDIR}"/src/bin/* "${pkgdir}/ec2-instance-connect/"
# Dump /bin, /usr/bin, etc from binary paths names since we want to use $PATH on Ubuntu/etc
sed -i "s%/usr/bin/%%g" "${pkgdir}"/ec2-instance-connect/*
sed -i "s%^/bin/%%g" "${pkgdir}"/ec2-instance-connect/*
sed -i "s%\([^\#][^\!]\)/bin/%\1%g" "${pkgdir}"/ec2-instance-connect/*
# Copy ec2-instance-connect service file
cp -r "${TOPDIR}/src/deb_systemd/ec2-instance-connect.service" "${pkgdir}/"
cp -r "${TOPDIR}/src/ec2-instance-connect.preset" "${pkgdir}/95-ec2-instance-connect.preset"
mkdir "${pkgdir}/debian"
cp -r "${TOPDIR}"/debian/* "${pkgdir}/debian/"
sed -i "s/\!VERSION\!/${version}-${release}/" "${pkgdir}/debian/control"
# Do the actual packaging
return_dir=$(pwd)
cd "${pkgdir}" || exit 1
debuild
# Clean up
cd "${return_dir}" || exit 1
rm -rf "${pkgdir}"
aws-ec2-instance-connect-config-1.1.14/bin/make_rpm.sh 0000775 0000000 0000000 00000005323 14024143525 0022440 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
# Note: this will only work on a system with rpm build tools installed (ie, RHEL & its derivatives)
if [ $# -ne 2 ] ; then
echo "Usage: make_rpm.sh [version] [release]"
echo " ie, make_rpm.sh [1.1] [1]"
exit 1
fi
TOPDIR=$(dirname "$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )")
BUILDDIR="${TOPDIR}/rpmbuild"
mkdir -p "${BUILDDIR}"
version="${1}"
release="${2}"
mkdir -p "${BUILDDIR}"/{BUILD,RPMS,SOURCES,SPECS,SRPMS,ec2-instance-connect-"${version}",tmp}
mkdir -p "${BUILDDIR}/ec2-instance-connect-${version}/opt/aws/bin"
cp "${TOPDIR}"/rpmsrc/SPECS/generic.spec "${BUILDDIR}/SPECS/ec2-instance-connect.spec"
cp "${TOPDIR}"/src/bin/* "${BUILDDIR}/ec2-instance-connect-${version}/opt/aws/bin/"
cp "${TOPDIR}"/rpmsrc/.rpmmacros "${BUILDDIR}/"
/bin/sed -i "s%^ca_path=/etc/ssl/certs$%ca_path=/etc/ssl/certs/ca-bundle.crt%" "${BUILDDIR}/ec2-instance-connect-${version}/opt/aws/bin/eic_curl_authorized_keys"
# Trick rpmbuild into thinking this is homedir to read .rpmmacros
REALHOME="${HOME}"
export HOME="${BUILDDIR}"
function cleanup {
export HOME="${REALHOME}"
rm -rf "${BUILDDIR}"/{BUILD,SOURCES,tmp}
rm -rf "${BUILDDIR}/BUILDROOT" # In case we got far enough for this to exist
rm -rf "${BUILDDIR}/ec2-instance-connect-${version}"
}
trap cleanup EXIT
cp "${TOPDIR}/src/rpm_systemd/ec2-instance-connect.service" "${BUILDDIR}/SOURCES/"
cp "${TOPDIR}/src/ec2-instance-connect.preset" "${BUILDDIR}/SOURCES"
ls "${BUILDDIR}/SOURCES"
cd "${BUILDDIR}" || exit 1 # Will ensure some paths are set correctly in rpmbuild
# Compress the scripts
tar -czf "${BUILDDIR}/SOURCES/ec2-instance-connect-${version}.tar.gz" "ec2-instance-connect-${version}/"
# Fill in the placeholders
sed -i "s/\!VERSION\!/${version}/" "${BUILDDIR}/SPECS/ec2-instance-connect.spec"
sed -i "s/\!RELEASE\!/${release}/" "${BUILDDIR}/SPECS/ec2-instance-connect.spec"
# Build the package
rpmbuild -ba "${BUILDDIR}/SPECS/ec2-instance-connect.spec"
cp "${BUILDDIR}/RPMS/noarch/ec2-instance-connect-${version}-${release}.noarch.rpm" "${TOPDIR}/"
aws-ec2-instance-connect-config-1.1.14/bin/make_tarball.sh 0000775 0000000 0000000 00000002462 14024143525 0023264 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
TOPDIR=$(dirname "$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )")
verrel="$(cat "${TOPDIR}/VERSION")"
version="${verrel%-*}"
pkgver="ec2-instance-connect-${version}"
mkdir -p "${TOPDIR}/${pkgver}/opt/aws/bin"
cp "${TOPDIR}"/src/bin/* "${TOPDIR}/${pkgver}/opt/aws/bin/"
if [ $# -eq 1 ] ; then # TODO: better check. Low-priority.
/bin/sed -i "s%^ca_path=/etc/ssl/certs$%ca_path=/etc/ssl/certs/ca-bundle.crt%" "${TOPDIR}/${pkgver}/opt/aws/bin/eic_curl_authorized_keys"
fi
tar -czf "${TOPDIR}/${pkgver}.tar.gz" -C "${TOPDIR}" "${pkgver}/"
rm -rf "${TOPDIR:?}/${pkgver:?}"/*
rmdir "${TOPDIR}/${pkgver}"
aws-ec2-instance-connect-config-1.1.14/bin/unit-test/ 0000775 0000000 0000000 00000000000 14024143525 0022237 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/bin/unit-test/generate_ocsp.sh 0000775 0000000 0000000 00000003265 14024143525 0025422 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
# Unit test helper to generate an OCSP response in the desired location
if [ -z "${1}" ] ; then
echo "No openssl provided"
exit 1
fi
if [ -z "${2}" ] ; then
echo "No certificate file provided"
exit 2
fi
if [ -z "${3}" ] ; then
echo "No CA filepath provided (do not include file extension - this path will be used with .crt, .key, and .cdb.index)"
exit 3
fi
if [ -z "${4}" ] ; then
echo "No output file specified"
exit 4
fi
tmpfile=$(mktemp /dev/shm/tmp-XXXXXXXX)
# Generate the OCSP request
"${1}" ocsp -no_nonce -issuer "${3}.crt" -cert "${2}" -VAfile "${3}".crt -reqout "${tmpfile}"
# Generate the response
# Yes, we're using the CA to sign the response as well. Since this is for unit testing use we don't need strict security.
"${1}" ocsp -index "${3}.db.index" -rsigner "${3}.crt" -rkey "${3}.key" -CA "${3}.crt" -VAfile "${3}.crt" -reqin "${tmpfile}" -respout "${4}" > /dev/null 2>&1
# Drop the request, we don't need it anymore
rm -f "${tmpfile}"
aws-ec2-instance-connect-config-1.1.14/bin/unit-test/setup_certificates.sh 0000775 0000000 0000000 00000012234 14024143525 0026465 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
# Quick script to generate a CA, intermediate, and end certificate
if [ -z "${1}" ] ; then
echo "No openssl provided"
exit 1
fi
if [ -z "${2}" ] ; then
echo "No target directory provided"
exit 2
fi
OPENSSL="${1}"
certpath="${2}"
# Configure the CA
mkdir -p "${certpath}/ca.db.certs"
touch "${certpath}/ca.db.index"
echo 01 > "${certpath}/ca.db.serial"
cat > "${certpath}/ca.conf" <<'EOF'
default_ca = ca_default
[ca_default]
dir = REPLACE_WITH_CERTPATH
certs = $dir
new_certs_dir = $dir/ca.db.certs
database = $dir/ca.db.index
serial = $dir/ca.db.serial
RANDFILE = $dir/ca.db.rand
certificate = $dir/ca.crt
private_key = $dir/ca.key
default_days = 1
default_crl_days = 1
default_md = sha256
preserve = no
policy = generic_policy
x509_extensions = usr_cert
[generic_policy]
countryName = optional
stateOrProvinceName = optional
localityName = optional
organizationName = optional
organizationalUnitName = optional
commonName = supplied
emailAddress = optional
[usr_cert]
authorityInfoAccess = OCSP;URI:http://localhost:8080
subjectKeyIdentifier=hash
authorityKeyIdentifier=keyid,issuer
[v3_ocsp]
basicConstraints = CA:FALSE
keyUsage = nonRepudiation, digitalSignature, keyEncipherment
extendedKeyUsage = OCSPSigning
[v3_ca]
subjectKeyIdentifier=hash
authorityKeyIdentifier=keyid:always,issuer:always
basicConstraints = CA:TRUE
[req]
distinguished_name = req_distinguished_name
[req_distinguished_name]
EOF
sed -i "s|REPLACE_WITH_CERTPATH|${certpath}|" "${certpath}/ca.conf"
# Generate the CA
"${OPENSSL}" genrsa -out "${certpath}/ca.key" 2048 > /dev/null 2>&1
"${OPENSSL}" req -x509 -new -nodes -key "${certpath}/ca.key" -sha256 -days 1 -out "${certpath}/ca.crt" -subj "/CN=managedssh.amazonaws.com" > /dev/null 2>&1
"${OPENSSL}" x509 -in "${certpath}/ca.crt" -outform PEM -out "${certpath}/ca.pem"
subject=$("${OPENSSL}" x509 -noout -subject -in "${certpath}/ca.pem" | sed -n -e 's/^.*CN=//p')
# Add "# subject" to start
sed -i '1s;^;# '"$subject"'\n;' "${certpath}/ca.crt"
# Configure the intermediary
mkdir -p "${certpath}/intermediate.db.certs"
touch "${certpath}/intermediate.db.index"
echo 01 > "${certpath}/intermediate.db.serial"
cat > "${certpath}/intermediate.conf" <<'EOF'
default_ca = ca_default
[ca_default]
dir = REPLACE_WITH_CERTPATH
certs = $dir
new_certs_dir = $dir/intermediate.db.certs
database = $dir/intermediate.db.index
serial = $dir/intermediate.db.serial
RANDFILE = $dir/intermediate.db.rand
certificate = $dir/intermediate.crt
private_key = $dir/intermediate.key
default_days = 1
default_crl_days = 1
default_md = sha256
preserve = no
policy = generic_policy
x509_extensions = usr_cert
[generic_policy]
countryName = optional
stateOrProvinceName = optional
localityName = optional
organizationName = optional
organizationalUnitName = optional
commonName = supplied
emailAddress = optional
[usr_cert]
authorityInfoAccess = OCSP;URI:http://localhost:8080
subjectKeyIdentifier=hash
authorityKeyIdentifier=keyid,issuer
[v3_ocsp]
basicConstraints = CA:FALSE
keyUsage = nonRepudiation, digitalSignature, keyEncipherment
extendedKeyUsage = OCSPSigning
[req]
distinguished_name = req_distinguished_name
[req_distinguished_name]
EOF
sed -i "s|REPLACE_WITH_CERTPATH|${certpath}|" "${certpath}/intermediate.conf"
# Generate & sign the intermediary
"${OPENSSL}" genrsa -out "${certpath}/intermediate.key" 2048 > /dev/null 2>&1
"${OPENSSL}" req -new -nodes -config "${certpath}/ca.conf" -key "${certpath}/intermediate.key" -out "${certpath}/intermediate.csr" -extensions v3_ocsp -subj "/CN=intermediate.managedssh.amazonaws.com" > /dev/null 2>&1
yes | "${OPENSSL}" ca -config "${certpath}/ca.conf" -in "${certpath}/intermediate.csr" -cert "${certpath}/ca.crt" -keyfile "${certpath}/ca.key" -out "${certpath}/intermediate.crt" -extensions v3_ocsp -extensions v3_ca > /dev/null 2>&1
"${OPENSSL}" x509 -in "${certpath}/intermediate.crt" -outform PEM -out "${certpath}/intermediate.pem"
# Generate and sign the test cert
"${OPENSSL}" genrsa -out "${certpath}/unittest.key" 2048 > /dev/null 2>&1
"${OPENSSL}" req -new -nodes -config "${certpath}/intermediate.conf" -key "${certpath}/unittest.key" -out "${certpath}/unittest.csr" -subj "/CN=unittest.managedssh.amazonaws.com" > /dev/null 2>&1
yes | "${OPENSSL}" ca -config "${certpath}/intermediate.conf" -in "${certpath}/unittest.csr" -cert "${certpath}/intermediate.crt" -keyfile "${certpath}/intermediate.key" -out "${certpath}/unittest.crt" > /dev/null 2>&1
"${OPENSSL}" x509 -in "${certpath}/unittest.crt" -outform PEM -out "${certpath}/unittest.pem"
aws-ec2-instance-connect-config-1.1.14/bin/unit-test/sign_data.sh 0000775 0000000 0000000 00000003370 14024143525 0024532 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
# Unit test helper. Takes a directory containing key blobs in files, signs the data in each, and consolidates into a final output.
if [ -z "${1}" ] ; then
echo "No openssl provided"
exit 1
fi
if [ -z "${2}" ] ; then
echo "Signing key not provided."
exit 2
fi
if [ -z "${3}" ] ; then
echo "Input directory not provided."
exit 3
fi
if [ -z "${4}" ] ; then
echo "Target file not provided."
exit 4
fi
OPENSSL="${1}"
private_key="${2}"
input_dir="${3}"
target="${4}"
signing_temp=$(mktemp -d /dev/shm/tmp-XXXXXXXX)
trap 'rm -rf "${signing_temp}"' EXIT
for file in "${input_dir}"/* ; do
# Generate the signature
"${OPENSSL}" dgst -sha256 -sigopt rsa_padding_mode:pss -sigopt rsa_pss_saltlen:32 -sign "${private_key}" -out "${signing_temp}/signature" "${file}"
# Base64 encode it
base64 "${signing_temp}/signature" > "${signing_temp}/encoded"
# Add the input file dump & its signature to the target
cat "${file}" "${signing_temp}/encoded" >> "${target}"
# Append a newline
echo >> "${target}"
done
aws-ec2-instance-connect-config-1.1.14/bin/unit-test/test_authorized_keys.sh 0000775 0000000 0000000 00000005000 14024143525 0027041 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
# Authorized keys command unit test script. Takes the script to test, certificate, CA, input, and expected output.
# TODO: Switch to named args/getopts
if [ -z "${1}" ] ; then
echo "No openssl provided"
exit 1
fi
if [ -z "${2}" ] ; then
echo "Script file not provided"
exit 2
fi
if [ -z "${3}" ] ; then
echo "No certificate file provided"
exit 3
fi
if [ -z "${4}" ] ; then
echo "No CA file provided"
exit 4
fi
if [ -z "${5}" ] ; then
echo "OCSP responses directory not provided"
exit 5
fi
if [ -z "${6}" ] ; then
echo "No input file provided"
exit 6
fi
if [ -z "${7}" ] ; then
echo "No expected output file provided"
exit 7
fi
OPENSSL=$1
certificate=$(cat "${3}")
filename="${6##*/}"
expected_output=$(cat "${7}")
expected_exit=0
if [ -z "${expected_output}" ] ; then
# If expected output is empty then we expect the script not to exit success
expected_exit=255
fi
testdir=$(mktemp -d /dev/shm/tmp-XXXXXXXX)
# The key fingerprint is for a pre-generated ssh key used in several test inputs
# Some test inputs contain other keys as well
# The test outputs, however, *only* match this key - we expect the other keys to be rejected
test_output=$(${2} -x true -p "${6}" -o "${OPENSSL}" -d "${testdir}" -s "${certificate}" -i "i-abcd1234" -c "unittest.managedssh.amazonaws.com" -a "${4}" -v "${5}" -f "SHA256:F3e4S8/QjcVquqrvmyq9AWAhOxIXfpbpnmDVFdA0sPU")
test_status=$?
exit_status=0
if [[ $test_status -eq $expected_exit && "${test_output}" = "${expected_output}" ]] ; then
echo "${filename} PASSED"
else
echo "${filename} FAILED"
echo "EXPECTED: exit ${expected_exit} with output"
echo "${expected_output}"
echo "ACTUAL: exit ${test_status} with output"
echo "${test_output}"
exit_status=1
fi
rm -rf "${testdir}"
exit "${exit_status}"
aws-ec2-instance-connect-config-1.1.14/bin/unit_test_suite.sh 0000775 0000000 0000000 00000006336 14024143525 0024101 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
# Script to run our entire unit test suite.
# Iterates over the contents of test/input/direct and test/input/unsigned and validates we get the matching contents of unit-test/expected-output
OPENSSL="/usr/bin/openssl"
TOPDIR=$(dirname "$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd)")
tmpdir=$(mktemp -d /dev/shm/tmp-XXXXXXXX)
trap 'rm -rf "${tmpdir}"' EXIT
# Generate test certificates
"${TOPDIR}/bin/unit-test/setup_certificates.sh" "${OPENSSL}" "${tmpdir}"
# Combine unittest & intermediate into the trust chain for the actual AuthorizedKeysCommand
cat "${tmpdir}/unittest.pem" "${tmpdir}/intermediate.pem" "${tmpdir}/ca.pem" > "${tmpdir}/chain.pem"
intermediate_fingerprint="$(openssl x509 -noout -fingerprint -sha1 -inform pem -in "${tmpdir}/intermediate.pem" | sed -n 's/SHA1 Fingerprint=\(.*\)/\1/p' | tr -d ':')"
unittest_fingerprint="$(openssl x509 -noout -fingerprint -sha1 -inform pem -in "${tmpdir}"/unittest.pem | sed -n 's/SHA1 Fingerprint=\(.*\)/\1/p' | tr -d ':')"
# Generate OCSP for those certificates
"${TOPDIR}/bin/unit-test/generate_ocsp.sh" "${OPENSSL}" "${tmpdir}/intermediate.crt" "${tmpdir}/ca" "${tmpdir}/${intermediate_fingerprint}"
"${TOPDIR}/bin/unit-test/generate_ocsp.sh" "${OPENSSL}" "${tmpdir}/unittest.crt" "${tmpdir}/intermediate" "${tmpdir}/${unittest_fingerprint}"
exit_status=0
# Direct input tests
for testfile in "${TOPDIR}"/unit-test/input/direct/* ; do
filename="${testfile##*/}"
"${TOPDIR}/bin/unit-test/test_authorized_keys.sh" "${OPENSSL}" "${TOPDIR}/src/bin/eic_parse_authorized_keys" "${tmpdir}/chain.pem" "${tmpdir}/ca.crt" "${tmpdir}" "${testfile}" "${TOPDIR}/unit-test/expected-output/${filename}"
result="${?}"
if [ "${result}" -ne 0 ] ; then
exit_status=1
fi
done
# Tests that require signing input data
for testdir in "${TOPDIR}"/unit-test/input/unsigned/* ; do
# Generate signatures for key blobs
filename="${testdir##*/}"
if [ "$("${TOPDIR}/bin/unit-test/sign_data.sh" "${OPENSSL}" "${tmpdir}/unittest.key" "${testdir}" "${tmpdir}/${filename}")" ] ; then
echo "Unable to run test ${filename}: signature generation failed"
else
# Run the actual test
"${TOPDIR}/bin/unit-test/test_authorized_keys.sh" "${OPENSSL}" "${TOPDIR}/src/bin/eic_parse_authorized_keys" "${tmpdir}/chain.pem" "${tmpdir}/ca.crt" "${tmpdir}" "${tmpdir}/${filename}" "${TOPDIR}/unit-test/expected-output/${filename}"
result="${?}"
if [ "${result}" -ne 0 ] ; then
exit_status=1
fi
fi
done
rm -rf "${tmpdir:?}"
exit "${exit_status}"
aws-ec2-instance-connect-config-1.1.14/debian/ 0000775 0000000 0000000 00000000000 14024143525 0020755 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/debian/changelog 0000664 0000000 0000000 00000007516 14024143525 0022640 0 ustar 00root root 0000000 0000000 ec2-instance-connect (1.1.14) xenial; urgency=high
* Ensure failure to run host key harvesting does not leave instances in degraded state
-- Paul Oh Fri, 26 Feb 2021 10:00:00 -0400
ec2-instance-connect (1.1.13) xenial; urgency=high
* Verify that domain returned from IMDS is an AWS domain
-- Jacob Meisler Thu, 22 Oct 2020 00:00:00 -0400
ec2-instance-connect (1.1.12) xenial; urgency=high
* Adding support for Instance Metadata Service Version 2
* Modifying cURL invocation to avoid need for eval
* Cleaning up shellcheck catches
-- Daniel Anderson Tue, 19 Nov 2019 10:38:09 -0800
ec2-instance-connect (1.1.11) xenial; urgency=high
* Removing errant write to /tmp
* Cleaning up bad bash practices, including umask race condition
-- Daniel Anderson Wed, 21 Aug 2019 12:31:23 -0700
ec2-instance-connect (1.1.10) xenial; urgency=medium
* Fix for an update to openssl (or dependencies) affecting behavior of CApath option on openssl verify
* Fixing Nitro behavior of hostkey harvesting and post-installation systemd hooks
* Adding additional licensing headers
-- Daniel Anderson Wed, 3 Jul 2019 15:24:28 -0700
ec2-instance-connect (1.1.9) xenial; urgency=low
[ Daniel Anderson ]
* Improved mechanism for detection if script is running on an EC2 instance
* postinst: Removed modification of sshd_config introduced in 1.1-8
* postinst: Better checks for existing AuthorizedKeysCommand* configuration
[ Mathieu Trudel-Lapierre ]
* debian/postinst: Fix regexes for matching/ignoring comments in sshd_config.
-- Daniel Anderson Fri, 21 Jun 2019 16:43:06 -0400
ec2-instance-connect (1.1.8) xenial; urgency=low
* postinst: Better detection of existing user customization
-- Daniel Anderson Wed, 24 Apr 2019 17:36:31 -0800
ec2-instance-connect (1.1.7) xenial; urgency=low
* Minor configuration change
-- Daniel Anderson Fri, 29 Mar 2019 16:09:51 -0800
ec2-instance-connect (1.1.6) xenial; urgency=low
* Verification of EC2 hypervisor UUID
-- Daniel Anderson Wed, 20 Mar 2019 17:02:44 -0800
ec2-instance-connect (1.1.5) xenial; urgency=low
* Additional checks to enforce scripts only run on EC2 instances
-- Daniel Anderson Fri, 15 Mar 2019 11:20:03 -0800
ec2-instance-connect (1.1.4) xenial; urgency=high
* Fixed a bug in reading instance-identity credentials
* Removed AWS CLI dependency
* Hardened error handling
* Cleaned up package to Canonical's release standards
-- Daniel Anderson Wed, 30 Jan 2019 13:30:03 -0800
ec2-instance-connect (1.1.3) xenial; urgency=medium
* Fixing an issue with the hostkey harvesting script - it was using default creds instead of instance-identity
-- Daniel Anderson Fri, 21 Dec 2018 13:30:03 -0800
ec2-instance-connect (1.1.2) xenial; urgency=high
* Initial Debian package version based on RPM packaging
-- Daniel Anderson Fri, 7 Dec 2018 11:37:15 -0800
ec2-instance-connect (1.1.1) UNRELEASED; urgency=low
* Hostkey harvesting for EC2 Instance Connect.
-- Anshumali Prasad Tue, 23 Oct 2018 21:49:58 +0000
ec2-instance-connect (1.0.3) UNRELEASED; urgency=low
* Updating exit status on no-data case, improving support for newer openssl versions
-- Daniel Anderson Mon, 22 Oct 2018 12:49:33 -0700
ec2-instance-connect (1.0.2) UNRELEASED; urgency=low
* Cleaning up package requirements & post installation hook
-- Daniel Anderson Tue, 9 Oct 2018 15:45:03 -0700
ec2-instance-connect (1.0.1) UNRELEASED; urgency=low
* Initial package build for EC2 Instance Connect targeting Amazon Linux 2
-- Daniel Anderson Tue, 12 Jun 2018 15:45:34 -0700
aws-ec2-instance-connect-config-1.1.14/debian/compat 0000664 0000000 0000000 00000000001 14024143525 0022152 0 ustar 00root root 0000000 0000000 9 aws-ec2-instance-connect-config-1.1.14/debian/control 0000664 0000000 0000000 00000002215 14024143525 0022360 0 ustar 00root root 0000000 0000000 Source: ec2-instance-connect
Section: net
Priority: optional
Standards-Version: 4.1.4
Maintainer: Ubuntu Developers
XSBC-Original-Maintainer: Daniel Anderson
Build-Depends: debhelper (>= 10)
Package: ec2-instance-connect
Architecture: all
Homepage: https://aws.amazon.com/
Pre-Depends: adduser
Depends: ca-certificates, coreutils (>=8.0), curl, openssh-server (>=6.9.0), openssl, ${misc:Depends}
Description: Configures ssh daemon to accept EC2 Instance Connect ssh keys
EC2 Instance Connect is a service that publishes ssh keys for use by EC2
instances based on AWS Credentials. These keys are consumed by on-instance
configuration provided by this package. The ssh daemon will query EC2
Instance Metadata service for user-keys at ssh calltime, validate any if
present as well as validating their signature, and if all checks pass return
will include them in the authorized keys list.
.
In addition, there is an agent that harvests instance ssh host keys and
passes them back to the service. This is for authentication purposes by
the EC2 console to open an in-browser ssh terminal connection.
aws-ec2-instance-connect-config-1.1.14/debian/copyright 0000664 0000000 0000000 00000001710 14024143525 0022707 0 ustar 00root root 0000000 0000000 Format: https://www.debian.org/doc/packaging-manuals/copyright-format/1.0/
Upstream-Name: ec2-instance-connect
Upstream-Contact: Daniel Anderson
Source: https://github.com/awslabs/aws-ec2-instance-connect-config/
Files: *
Copyright: 2017-2019 Daniel Anderson
License: Apache2.0
.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
.
http://aws.amazon.com/apache2.0/
.
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
.
On Debian systems, the complete text of the Apache License 2.0 can
be found in "/usr/share/common-licenses/Apache-2.0" aws-ec2-instance-connect-config-1.1.14/debian/install 0000664 0000000 0000000 00000000242 14024143525 0022344 0 ustar 00root root 0000000 0000000 ec2-instance-connect/* usr/share/ec2-instance-connect/
ec2-instance-connect.service lib/systemd/system/
95-ec2-instance-connect.preset lib/systemd/system-preset/
aws-ec2-instance-connect-config-1.1.14/debian/postinst 0000775 0000000 0000000 00000004047 14024143525 0022573 0 ustar 00root root 0000000 0000000 #!/bin/sh
set -e
#DEBHELPER#
case "$1" in
configure)
EXEC_OVERRIDE='ExecStart=/usr/sbin/sshd -D -o "AuthorizedKeysCommand /usr/share/ec2-instance-connect/eic_run_authorized_keys %%u %%f" -o "AuthorizedKeysCommandUser ec2-instance-connect" $SSHD_OPTS'
modified=1
# If there is nothing in the AuthorizedKeysCommand field of sshd_config *and* nothing in any sshd override, add our config
if ! grep -q '^[^#]*AuthorizedKeysCommand[[:blank:]]\+.*$' /etc/ssh/sshd_config ; then
if ! grep -q '^[^#]*AuthorizedKeysCommandUser[[:blank:]]\+.*$' /etc/ssh/sshd_config ; then
if ! grep -q '^[^#]*AuthorizedKeysCommandRunAs[[:blank:]]\+.*$' /etc/ssh/sshd_config ; then
# If systemd unit contains AKC don't override it
if ! grep -q "AuthorizedKeysCommand" /lib/systemd/system/ssh.service ; then
can_modify=1
if [ -d /lib/systemd/system/ssh.service.d ] ; then
# If *any* override contains an ExecStart, don't override it
if ! grep -Rq "ExecStart" /lib/systemd/system/ssh.service.d/ ; then
can_modify=0
fi
else
# Or there are no overrides
mkdir /lib/systemd/system/ssh.service.d
can_modify=0
fi
if [ $can_modify -eq 0 ] ; then
# Add our configuration
printf "%s\n%s\n%s\n" "[Service]" "ExecStart=" "${EXEC_OVERRIDE}" > /lib/systemd/system/ssh.service.d/ec2-instance-connect.conf
modified=0
fi
fi
fi
fi
fi
if [ $modified -eq 0 ] ; then
systemctl daemon-reload
echo "sshd override added, restarting daemon"
deb-systemd-invoke restart ssh.service
fi
;;
esac
aws-ec2-instance-connect-config-1.1.14/debian/postrm 0000775 0000000 0000000 00000000501 14024143525 0022223 0 ustar 00root root 0000000 0000000 #!/bin/sh
set -e
#DEBHELPER#
case "$1" in
purge|remove|abort-install|disappear)
deb-systemd-helper purge ec2-instance-connect
# Delete system user
deluser --system --quiet ec2-instance-connect
echo "Deleted system user ec2-instance-connect"
;;
*)
exit 0
;;
esac
aws-ec2-instance-connect-config-1.1.14/debian/preinst 0000775 0000000 0000000 00000000710 14024143525 0022365 0 ustar 00root root 0000000 0000000 #!/bin/sh
set -e
#DEBHELPER#
case "$1" in
install)
# Create/configure system user
# /usr/bin/getent passwd ec2-instance-connect || /usr/sbin/useradd -r -M -s /sbin/nologin ec2-instance-connect
getent passwd ec2-instance-connect || adduser --system --disabled-login --shell /usr/sbin/nologin --no-create-home --home /nonexistent --quiet ec2-instance-connect
echo "Created system user ec2-instance-connect"
;;
esac
aws-ec2-instance-connect-config-1.1.14/debian/prerm 0000775 0000000 0000000 00000001426 14024143525 0022033 0 ustar 00root root 0000000 0000000 #!/bin/sh
set -e
#DEBHELPER#
case "$1" in
remove|deconfigure)
modified=1
# Remove EC2 Instance Connect sshd override if present
if [ -f /lib/systemd/system/ssh.service.d/ec2-instance-connect.conf ] ; then
rm -f /lib/systemd/system/ssh.service.d/ec2-instance-connect.conf
if [ -z "$(ls -A /lib/systemd/system/ssh.service.d)" ] ; then
# There were no other overrides, clean up
rmdir /lib/systemd/system/ssh.service.d
fi
modified=0
fi
if [ $modified -eq 0 ] ; then
systemctl daemon-reload
# Restart sshd
echo "sshd override removed, restarting daemon..."
deb-systemd-invoke restart ssh.service
fi
;;
esac
aws-ec2-instance-connect-config-1.1.14/debian/rules 0000775 0000000 0000000 00000000245 14024143525 0022036 0 ustar 00root root 0000000 0000000 #!/usr/bin/make -f
# See debhelper(7) (uncomment to disable)
# output every command that modifies files on the build system.
#DH_VERBOSE=1
%:
dh $@ --with systemd
aws-ec2-instance-connect-config-1.1.14/debian/source/ 0000775 0000000 0000000 00000000000 14024143525 0022255 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/debian/source/format 0000664 0000000 0000000 00000000015 14024143525 0023464 0 ustar 00root root 0000000 0000000 3.0 (native)
aws-ec2-instance-connect-config-1.1.14/docker/ 0000775 0000000 0000000 00000000000 14024143525 0021002 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/docker/generic/ 0000775 0000000 0000000 00000000000 14024143525 0022416 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/docker/generic/Dockerfile 0000664 0000000 0000000 00000000405 14024143525 0024407 0 ustar 00root root 0000000 0000000 FROM amazonlinux:2.0.20180622.1
RUN yum install -y rpmbuild rpmdevtools make --skip-broken
COPY src /build/src
COPY bin /build/bin
COPY rpmsrc /build/rpmsrc
COPY VERSION /build/VERSION
COPY Makefile /build/Makefile
WORKDIR /build
RUN make rpm
CMD cp *.rpm /out aws-ec2-instance-connect-config-1.1.14/docker/ubuntu/ 0000775 0000000 0000000 00000000000 14024143525 0022324 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/docker/ubuntu/Dockerfile 0000664 0000000 0000000 00000000436 14024143525 0024321 0 ustar 00root root 0000000 0000000 FROM ubuntu:20.04
ARG DEBIAN_FRONTEND=noninteractive
RUN apt-get update
RUN apt-get install -y devscripts debhelper
COPY src /build/src
COPY bin /build/bin
COPY debian /build/debian
COPY VERSION /build/VERSION
COPY Makefile /build/Makefile
WORKDIR /build
RUN make deb
CMD cp *.deb /out aws-ec2-instance-connect-config-1.1.14/integration-test/ 0000775 0000000 0000000 00000000000 14024143525 0023033 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/integration-test/config/ 0000775 0000000 0000000 00000000000 14024143525 0024300 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/integration-test/config/amazon-linux 0000664 0000000 0000000 00000000233 14024143525 0026643 0 ustar 00root root 0000000 0000000 INSTALL="sudo yum -y install"
REMOVE="sudo yum -y remove"
SSHD_CONFIG_MODIFIED="1"
SCRIPT_PATH="/opt/aws/bin"
SSHD_SERVICE="sshd"
MISSING_SSHD_NEWLINE="0"
aws-ec2-instance-connect-config-1.1.14/integration-test/config/rhel 0000664 0000000 0000000 00000000233 14024143525 0025153 0 ustar 00root root 0000000 0000000 INSTALL="sudo yum -y install"
REMOVE="sudo yum -y remove"
SSHD_CONFIG_MODIFIED="0"
SCRIPT_PATH="/opt/aws/bin"
SSHD_SERVICE="sshd"
MISSING_SSHD_NEWLINE="1"
aws-ec2-instance-connect-config-1.1.14/integration-test/config/ubuntu 0000664 0000000 0000000 00000000234 14024143525 0025544 0 ustar 00root root 0000000 0000000 INSTALL="sudo apt-get -y install"
REMOVE="sudo apt-get -y remove"
SSHD_CONFIG_MODIFIED="0"
SCRIPT_PATH="/etc/share/ec2-instance-connect"
SSHD_SERVICE="ssh"
aws-ec2-instance-connect-config-1.1.14/integration-test/test/ 0000775 0000000 0000000 00000000000 14024143525 0024012 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/integration-test/test/custom_config.sh 0000775 0000000 0000000 00000007650 14024143525 0027220 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
# Test that package uninstall removes customizations and reinstall re-adds them
TOPDIR=$(dirname "$( cd "$( dirname "$( dirname "${BASH_SOURCE[0]}" )" )" && pwd)")
while getopts ":i:p:z:u:k:l:t:" opt ; do
case "${opt}" in
i)
instance_id="${OPTARG}"
;;
p)
public_ip="${OPTARG}"
;;
z)
zone="${OPTARG}"
;;
u)
osuser="${OPTARG}"
;;
k)
private_key="${OPTARG}"
;;
l)
distro="${OPTARG}"
;;
t)
package_path="${OPTARG}"
;;
*)
;;
esac
done
source "${TOPDIR}/integration-test/config/${distro}"
package_name="${package_path##*/}"
# Construct the test script
scriptfile=$(mktemp /tmp/tmp-XXXXXXXX)
trap 'rm -f "${scriptfile}"' EXIT
if [ "${SSHD_CONFIG_MODIFIED}" -ne 0 ] ; then
config_check="\"\$(sudo grep \"^AuthorizedKeysCommand[[:blank:]]/opt/aws/bin/eic_run_authorized_keys[[:blank:]]%u[[:blank:]]%f$\" /etc/ssh/sshd_config)\""
else
config_check="-f /lib/systemd/system/${SSHD_SERVICE}.service.d/ec2-instance-connect.conf"
fi
echo '#!/bin/bash' > "${scriptfile}"
echo "set -e" >> "${scriptfile}"
printf "%s\n%s\n" "echo \"Uninstalling package\"" "${REMOVE} ec2-instance-connect 2>&1" >> "${scriptfile}"
printf "%s\n%s\n%s\n%s\n" "if [ ${config_check} ] ; then" "echo \"Package was not installed or deconfigured correctly\"" "exit 1" "fi" >> "${scriptfile}"
# We need an extra newline before the custom AKC due to some distros, eg RHEL, not having a newline at end of file
printf "%s\n%s\n" "echo \"Adding override config to sshd_config\"" "printf \"\n%s\n\" \"AuthorizedKeysCommand exit\" | sudo tee -a /etc/ssh/sshd_config" >> "${scriptfile}"
printf "%s\n%s\n" "echo \"Installing package\"" "${INSTALL} /tmp/${package_name} 2>&1" >> "${scriptfile}"
printf "%s\n%s\n%s\n%s\n" "if [ ${config_check} ] ; then" "echo \"Package overwrote existing customizations!\"" "exit 1" "fi" >> "${scriptfile}"
echo "scping test script to instance"
scp -i "${private_key}" -o StrictHostKeyChecking=no "${scriptfile}" "${osuser}@${public_ip}:/tmp/eic_custom_config_test.sh" 2>&1
scp_result="${?}"
if [ "${scp_result}" -ne 0 ] ; then
exit 1
fi
echo "Running test script"
fail=0
ssh -i "${private_key}" -o StrictHostKeyChecking=no "${osuser}@${public_ip}" 'chmod +x /tmp/eic_custom_config_test.sh ; /tmp/eic_custom_config_test.sh' 2>&1
test_result="${?}"
if [ "${test_result}" -ne 0 ] ; then
fail=1
fi
if [ "${fail}" -eq 0 ] ; then
echo "Invoking EIC end-to-end test for final validation"
"${TOPDIR}/integration-test/test/ssh_test.sh" -i "${instance_id}" -p "${public_ip}" -z "${zone}" -u "${osuser}" -k "${private_key}" -l "${distro}" -t "${package_path}" 2>&1
ssh_result="${?}"
if [ "${ssh_result}" -eq 0 ] ; then
echo "ssh via EIC succeeded but should have failed!"
fail=1
fi
fi
# Reset back to start-of-test conditions
clean_cmd="${REMOVE} ec2-instance-connect 2>&1 ; sudo sed -i \"\~^AuthorizedKeysCommand[[:blank:]]exit\$~d\" /etc/ssh/sshd_config ; ${INSTALL} /tmp/${package_name} 2>&1"
ssh -i "${private_key}" -o StrictHostKeyChecking=no "${osuser}@${public_ip}" "${clean_cmd}"
exit $fail
aws-ec2-instance-connect-config-1.1.14/integration-test/test/hostkey_test.sh 0000775 0000000 0000000 00000014240 14024143525 0027077 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
# Test of EIC host key harvesting mechanism. Regenerate rsa host key, re-trigger harvest, and ensure new key is returned.
# NOTE THIS TEST REQUIRES THE EC2 OS USER HAVE SUDO PERMISSION FOR SSH HOST KEY REGENERATION AND RESTARTING HOST KEY HARVEST
while getopts ":i:p:z:u:k:l:t:" opt ; do
case "${opt}" in
i)
instance_id="${OPTARG}"
;;
p)
public_ip="${OPTARG}"
;;
z)
zone="${OPTARG}"
;;
u)
osuser="${OPTARG}"
;;
k)
private_key="${OPTARG}"
;;
l)
distro="${OPTARG}"
;;
t)
package_path="${OPTARG}"
;;
*)
;;
esac
done
scriptfile=$(mktemp /tmp/tmp-XXXXXXXX)
trap 'rm -f "${scriptfile}"' EXIT
cat > "${scriptfile}" << 'EOF'
#!/bin/bash
set -e
echo "Generating new host key"
keydir=$(mktemp -d /tmp/tmp-XXXXXXXX)
trap 'rm -rf "${keydir}"' EXIT
keyfile="${keydir}/eic_test_host_key"
ssh-keygen -t rsa -f "${keyfile}" -P '' -N '' -C '' -q
echo "Moving new host key to /etc/ssh"
sudo mv /etc/ssh/ssh_host_rsa_key /etc/ssh/ssh_host_rsa_key.bak
sudo mv /etc/ssh/ssh_host_rsa_key.pub /etc/ssh/ssh_host_rsa_key.pub.bak
sudo mv "${keyfile}" /etc/ssh/ssh_host_rsa_key
sudo mv "${keyfile}.pub" /etc/ssh/ssh_host_rsa_key.pub
sudo chmod 640 /etc/ssh/ssh_host_rsa_key
sudo chmod 644 /etc/ssh/ssh_host_rsa_key.pub
pubkey=$(cat /etc/ssh/ssh_host_rsa_key.pub | awk '{$1=$1};1')
echo "Retriggering host key harvesting"
sudo systemctl restart ec2-instance-connect.service
echo "Retrieving keys from service"
sign () {
printf "${2}" | openssl dgst -binary -hex -sha256 -mac HMAC -macopt hexkey:"${1}" | sed 's/.* //'
}
getsigv4key () {
local base=$(echo -n "AWS4${1}" | od -A n -t x1 | sed ':a;N;$!ba;s/[\n ]//g')
local kdate=$(sign "${base}" "${2}")
local kregion=$(sign "${kdate}" "${3}")
local kservice=$(sign "${kregion}" "${4}")
sign "${kservice}" "aws4_request"
}
IMDS_TOKEN="$(/usr/bin/curl -s -f -m 1 -X PUT "http://169.254.169.254/latest/api/token" -H "X-aws-ec2-metadata-token-ttl-seconds: 5")"
accountId=$(/usr/bin/curl -s -f -m 1 -H "X-aws-ec2-metadata-token: ${IMDS_TOKEN}" "http://169.254.169.254/latest/dynamic/instance-identity/document" | grep -oP '(?<="accountId" : ")[^"]*(?=")')
domain=$(/usr/bin/curl -s -f -m 1 -H "X-aws-ec2-metadata-token: ${IMDS_TOKEN}" "http://169.254.169.254/latest/meta-data/services/domain/")
zone=$(/usr/bin/curl -s -f -m 1 -H "X-aws-ec2-metadata-token: ${IMDS_TOKEN}" "http://169.254.169.254/latest/meta-data/placement/availability-zone/")
region=$(echo "${zone}" | sed -n 's/\(\([a-z]\+-\)\+[0-9]\+\).*/\1/p')
instance=$(/usr/bin/curl -s -f -m 1 -H "X-aws-ec2-metadata-token: ${IMDS_TOKEN}" "http://169.254.169.254/latest/meta-data/instance-id/")
val='{"AccountID":"'${accountId}'","AvailabilityZone":"'${zone}'","InstanceId":"'${instance}'"}'
creds=$(/usr/bin/curl -s -f -m 1 -H "X-aws-ec2-metadata-token: ${IMDS_TOKEN}" "http://169.254.169.254/latest/meta-data/identity-credentials/ec2/security-credentials/ec2-instance/")
AWS_ACCESS_KEY_ID=$(echo "${creds}" | sed -n 's/.*"AccessKeyId" : "\(.*\)",/\1/p')
AWS_SECRET_ACCESS_KEY=$(echo "${creds}" | sed -n 's/.*"SecretAccessKey" : "\(.*\)",/\1/p')
AWS_SESSION_TOKEN=$(echo "${creds}" | sed -n 's/.*"Token" : "\(.*\)",/\1/p')
host="ec2-instance-connect.${region}.${domain}"
endpoint="https://${host}"
timestamp=$(date -u "+%Y-%m-%d %H:%M:%S")
isoTimestamp=$(date -ud "${timestamp}" "+%Y%m%dT%H%M%SZ")
isoDate=$(date -ud "${timestamp}" "+%Y%m%d")
canonicalQuery=""
canonicalHeaders="host:${host}\nx-amz-date:${isoTimestamp}\nx-amz-security-token:${AWS_SESSION_TOKEN}\n"
signedHeaders="host;x-amz-date;x-amz-security-token"
payloadHash=$(echo -n "${val}" | sha256sum | sed 's/\s.*$//')
canonicalRequest="$(printf "POST\n/GetEC2HostKeys/\n%s\n${canonicalHeaders}\n${signedHeaders}\n%s" "${canonicalQuery}" "${payloadHash}")"
requestHash=$(echo -n "${canonicalRequest}" | sha256sum | sed 's/\s.*$//')
credentialScope="${isoDate}/${region}/ec2-instance-connect/aws4_request"
toSign="AWS4-HMAC-SHA256\n${isoTimestamp}\n${credentialScope}\n${requestHash}"
signingKey=$(getsigv4key "${AWS_SECRET_ACCESS_KEY}" "${isoDate}" "${region}" "ec2-instance-connect")
signature=$(sign "${signingKey}" "${toSign}")
authorizationHeader="AWS4-HMAC-SHA256 Credential=${AWS_ACCESS_KEY_ID}/${credentialScope}, SignedHeaders=${signedHeaders}, Signature=${signature}"
host_keys=$(curl -X POST -H "Content-Encoding: amz-1.0" -H "Authorization: ${authorizationHeader}" -H "Content-Type: application/json" -H "x-amz-content-sha256: ${payloadHash}" -H "x-amz-date: ${isoTimestamp}" -H "x-amz-security-token: ${AWS_SESSION_TOKEN}" -H "x-amz-target: com.amazon.aws.sshaccessproxyservice.AWSEC2InstanceConnectService.GetEC2HostKeys" -d "${val}" "${endpoint}/GetEC2HostKeys/" 2>/dev/null)
echo "Verifying new key was harvested"
rsa_key=$(echo "ssh-rsa$(echo "${host_keys}" | sed -e 's/.*ssh-rsa\(.*\)\".*/\1/')")
if [ "${rsa_key}" = "${pubkey}" ] ; then
echo "SUCCESS"
exit 0
else
echo "FAILURE"
exit 1
fi
EOF
echo "scping test script to instance"
scp -i "${private_key}" -o StrictHostKeyChecking=no "${scriptfile}" "${osuser}@${public_ip}:/tmp/eic_host_key_test.sh" 2>&1
ssh_status=$?
if [ $ssh_status -eq 0 ] ; then
echo "Running test script"
ssh -i "${private_key}" -o StrictHostKeyChecking=no "${osuser}@${public_ip}" 'chmod +x /tmp/eic_host_key_test.sh ; /tmp/eic_host_key_test.sh' 2>&1
ssh_status=$?
fi
exit "${ssh_status}"
aws-ec2-instance-connect-config-1.1.14/integration-test/test/ssh_test.sh 0000775 0000000 0000000 00000005472 14024143525 0026215 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
# Basic EIC functionality test: push a key and ssh to the instance
while getopts ":i:p:z:u:" opt ; do
case "${opt}" in
i)
instance_id="${OPTARG}"
;;
p)
public_ip="${OPTARG}"
;;
z)
zone="${OPTARG}"
;;
u)
osuser="${OPTARG}"
;;
k)
private_key="${OPTARG}"
;;
l)
distro="${OPTARG}"
;;
t)
package_path="${OPTARG}"
;;
*)
;;
esac
done
echo "Testing EC2 Instance Connect end-to-end ssh functionality..."
keydir=$(mktemp -d /tmp/tmp-XXXXXXXX)
trap 'rm -rf "${keydir}"' EXIT
keyfile="${keydir}/eic_test_key"
ssh-keygen -t rsa -b 2048 -f "${keyfile}" -P "" -q
# We will make 3 tries as certain elements (eg network calls) may cause transient failure
try="0"
success=1
while [ $try -lt 3 ] ; do
# Make 3 attempts to push a key
awstry="0"
while [ $awstry -lt 3 ] ; do
aws ec2-instance-connect send-ssh-public-key --region us-west-2 --instance-id "${instance_id}" --availability-zone "${zone}" --instance-os-user "${osuser}" --ssh-public-key "file://${keyfile}.pub" 1>/dev/null
aws_code=$?
if [ $aws_code -ne 0 ] ; then
sleep 5
awstry=$((awstry+1))
echo "${instance_id} EIC call ${awstry} failed"
else
awstry="3"
fi
done
sshtry="0"
# Make 3 attempts to ssh
while [ $sshtry -lt 3 ] ; do
ssh -q -i "${keyfile}" -o StrictHostKeyChecking=no "${osuser}@${public_ip}" exit 2>&1
success=$?
if [ $success -eq 0 ] ; then
echo "${instance_id} ssh succeeded!"
sshtry="3"
try="3"
else
sleep 5
sshtry=$((sshtry+1))
echo "${instance_id} ssh call ${sshtry} failed"
fi
done
if [ $success -ne 0 ] ; then
try=$((try+1))
echo "${instance_id} EIC test attempt ${try} failed"
fi
done
if [ $success -eq 0 ] ; then
echo "SUCCESS"
else
echo "FAILURE"
fi
exit $success
aws-ec2-instance-connect-config-1.1.14/integration-test/test/uninstall_reinstall.sh 0000775 0000000 0000000 00000006244 14024143525 0030445 0 ustar 00root root 0000000 0000000 #!/bin/bash
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
# Test that package uninstall removes customizations and reinstall re-adds them
TOPDIR=$(dirname "$( cd "$( dirname "$( dirname "${BASH_SOURCE[0]}" )" )" && pwd)")
while getopts ":i:p:z:u:k:l:t:" opt ; do
case "${opt}" in
i)
instance_id="${OPTARG}"
;;
p)
public_ip="${OPTARG}"
;;
z)
zone="${OPTARG}"
;;
u)
osuser="${OPTARG}"
;;
k)
private_key="${OPTARG}"
;;
l)
distro="${OPTARG}"
;;
t)
package_path="${OPTARG}"
;;
*)
;;
esac
done
source "${TOPDIR}/integration-test/config/${distro}"
package_name="${package_path##*/}"
# Construct the test script
scriptfile=$(mktemp /tmp/tmp-XXXXXXXX)
trap 'rm -f "${scriptfile}"' EXIT
if [ "${SSHD_CONFIG_MODIFIED}" -ne 0 ] ; then
config_check="grep -q \"^AuthorizedKeysCommand[[:blank:]]/opt/aws/bin/eic_run_authorized_keys[[:blank:]]%u[[:blank:]]%f$\" /etc/ssh/sshd_config"
else
config_check="-f /lib/systemd/system/${SSHD_SERVICE}.service.d/ec2-instance-connect.conf"
fi
echo "#!/bin/bash" > "${scriptfile}"
echo "set -e" >> "${scriptfile}"
printf "%s\n%s\n" "echo \"Uninstalling package\"" "${REMOVE} ec2-instance-connect 2>&1" >> "${scriptfile}"
printf "%s\n%s\n%s\n%s\n" "if [ ${config_check} ] ; then" "echo \"Package was not installed or deconfigured correctly\"" "exit 1" "fi" >> "${scriptfile}"
printf "%s\n%s\n" "echo \"Reinstalling package\"" "${INSTALL} /tmp/${package_name} 2>&1" >> "${scriptfile}"
printf "%s\n%s\n%s\n%s\n" "if [ ! ${config_check} ] ; then" "echo \"Package not installed/configured correctly\"" "exit 1" "fi" >> "${scriptfile}"
echo "scping test script to instance"
scp -i "${private_key}" -o StrictHostKeyChecking=no "${scriptfile}" "${osuser}@${public_ip}:/tmp/eic_uninstall_reinstall_test.sh" 2>&1
scp_result="${?}"
if [ "${scp_result}" -ne 0 ] ; then
exit 1
fi
echo "Running test script"
ssh -i "${private_key}" -o StrictHostKeyChecking=no "${osuser}@${public_ip}" 'chmod +x /tmp/eic_uninstall_reinstall_test.sh ; /tmp/eic_uninstall_reinstall_test.sh' 2>&1
test_result="${?}"
if [ "${test_result}" -ne 0 ] ; then
exit 1
fi
echo "Invoking EIC end-to-end test for final validation"
"${TOPDIR}/integration-test/test/ssh_test.sh" -i "${instance_id}" -p "${public_ip}" -z "${zone}" -u "${osuser}" -k "${private_key}" -l "${distro}" -t "${package_path}" 2>&1
exit "${?}"
aws-ec2-instance-connect-config-1.1.14/rpmsrc/ 0000775 0000000 0000000 00000000000 14024143525 0021041 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/rpmsrc/.rpmmacros 0000664 0000000 0000000 00000000054 14024143525 0023044 0 ustar 00root root 0000000 0000000 %_topdir %(pwd)
%_tmppath %{_topdir}/tmp
aws-ec2-instance-connect-config-1.1.14/rpmsrc/SPECS/ 0000775 0000000 0000000 00000000000 14024143525 0021716 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/rpmsrc/SPECS/generic.spec 0000664 0000000 0000000 00000020405 14024143525 0024207 0 ustar 00root root 0000000 0000000 # Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
%define __spec_install_post %{nil}
%define debug_package %{nil}
%define __os_install_post %{_dbpath}/brp-compress
Summary: EC2 instance scripting and configuration for EC2 Instance Connect
Name: ec2-instance-connect
Version: !VERSION!
Release: !RELEASE!
License: ASL2.0
BuildArch: noarch
BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n)
BuildRequires: systemd
Source0: %{name}-%{version}.tar.gz
Source1: ec2-instance-connect.service
Source2: ec2-instance-connect.preset
Requires: openssh >= 6.9.0, coreutils, openssh-server >= 6.9.0, openssl, curl, systemd
Requires(pre): /usr/bin/getent, /usr/sbin/adduser, /usr/sbin/usermod, systemd, systemd-units
Requires(post): /bin/grep, /usr/bin/printf, openssh-server >= 6.9.0, systemd, systemd-units
Requires(preun): systemd, systemd-units
Requires(postun): /usr/sbin/userdel, systemd, systemd-units
%description
%{summary}
%prep
%setup -q
%build
# no-op
%install
/bin/rm -rf %{buildroot}
/bin/mkdir -p %{buildroot}
/usr/bin/install -D -m 644 %{SOURCE1} %{buildroot}%{_unitdir}/ec2-instance-connect.service
# While the former is the RHEL standard, both are populated. And not symlinked.
/usr/bin/install -D -m 644 %{SOURCE2} %{buildroot}/usr/lib/systemd/system-preset/95-ec2-instance-connect.preset
/usr/bin/install -D -m 644 %{SOURCE2} %{buildroot}/lib/systemd/system-preset/95-ec2-instance-connect.preset
/bin/mkdir -p %{buildroot}/lib/systemd/hostkey.d
/bin/echo 'ec2-instance-connect.service' > %{buildroot}/lib/systemd/hostkey.d/60-ec2-instance-connect.list
# in builddir
/bin/cp -a * %{buildroot}
%clean
/bin/rm -rf %{buildroot}
%files
%defattr(755, root, root, -)
/opt/aws/bin/eic_run_authorized_keys
/opt/aws/bin/eic_curl_authorized_keys
/opt/aws/bin/eic_parse_authorized_keys
/opt/aws/bin/eic_harvest_hostkeys
%defattr(644, root, root, -)
%{_unitdir}/ec2-instance-connect.service
/lib/systemd/hostkey.d/60-ec2-instance-connect.list
/lib/systemd/system-preset/95-ec2-instance-connect.preset
/usr/lib/systemd/system-preset/95-ec2-instance-connect.preset
%pre
# Create/configure system user
/usr/bin/getent passwd ec2-instance-connect || /usr/sbin/useradd -r -M -s /sbin/nologin ec2-instance-connect
/usr/sbin/usermod -L ec2-instance-connect
%post
%systemd_post ec2-instance-connect.service
# XXX: %system_post just loads any presets (ie, auto-enable/disable). It does NOT try to start the service!
/usr/bin/systemctl start ec2-instance-connect.service
modified=1
# Configure sshd to use EC2 Instance Connect's AuthorizedKeysCommand
EXEC_OVERRIDE='ExecStart=/usr/sbin/sshd -D -o "AuthorizedKeysCommand /opt/aws/bin/eic_run_authorized_keys %%%%u %%%%f" -o "AuthorizedKeysCommandUser ec2-instance-connect" $SSHD_OPTS'
# If there is nothing in the AuthorizedKeysCommand field of sshd_config *and* nothing in any sshd override, add our config
if ! /bin/grep -q '^[^#]*AuthorizedKeysCommand[[:blank:]]\+.*$' /etc/ssh/sshd_config ; then
if ! /bin/grep -q '^[^#]*AuthorizedKeysCommandUser[[:blank:]]\+.*$' /etc/ssh/sshd_config ; then
if ! /bin/grep -q '^[^#]*AuthorizedKeysCommandRunAs[[:blank:]]\+.*$' /etc/ssh/sshd_config ; then
# If systemd unit contains AKC don't override it
if ! /bin/grep -q "AuthorizedKeysCommand" /lib/systemd/system/sshd.service ; then
can_modify=1
if [ -d /lib/systemd/system/sshd.service.d ] ; then
# If *any* override contains an ExecStart, don't override it
if ! /bin/grep -Rq "ExecStart" /lib/systemd/system/sshd.service.d/ ; then
can_modify=0
fi
else
# Or there are no overrides
/bin/mkdir /lib/systemd/system/sshd.service.d
can_modify=0
fi
if [ $can_modify -eq 0 ] ; then
# Add our configuration
/usr/bin/printf "%s\n%s\n%s\n" "[Service]" "ExecStart=" "${EXEC_OVERRIDE}" > /lib/systemd/system/sshd.service.d/ec2-instance-connect.conf
modified=0
fi
fi
fi
fi
fi
if [ $modified -eq 0 ] ; then
# Restart sshd
systemctl daemon-reload
if /bin/systemctl is-active --quiet sshd ; then
/bin/systemctl restart sshd
fi
fi
%preun
%systemd_preun ec2-instance-connect.service
if [ $1 -eq 0 ] ; then
modified=1
# Remove EC2 Instance Connect sshd override if present
if [ -f /lib/systemd/system/sshd.service.d/ec2-instance-connect.conf ] ; then
/bin/rm -f /lib/systemd/system/sshd.service.d/ec2-instance-connect.conf
if [ -z "$(ls -A /lib/systemd/system/sshd.service.d)" ] ; then
# There were no other overrides, clean up
/bin/rmdir /lib/systemd/system/sshd.service.d
fi
modified=0
fi
# Restart sshd
if [ $modified -eq 0 ] ; then
/bin/systemctl daemon-reload
if /bin/systemctl is-active --quiet sshd ; then
/bin/systemctl restart sshd
fi
fi
fi
%postun
%systemd_postun_with_restart ec2-instance-connect.service
if [ $1 -eq 0 ] ; then
# Delete system user
/usr/sbin/userdel ec2-instance-connect
fi
%changelog
* Fri Feb 26 2021 Paul Oh 1.1-14
- Ensure failure to run host key harvesting does not leave instances in degraded state
* Thu Oct 22 2020 Jacob Meisler 1.1-13
- Verify that domain returned from IMDS is an AWS domain
* Tue Nov 19 2019 Daniel Anderson 1.1-12
- Adding support for Instance Metadata Service Version 2
- Modifying cURL invocation to avoid need for eval
- Cleaning up shellcheck catches
* Wed Aug 21 2019 Daniel Anderson 1.1-11
- Removing errant write to /tmp
- Cleaning up bad bash practices, including umask race condition
* Wed Jul 3 2019 Daniel Anderson 1.1-10
- Fix for an update to openssl (or dependencies) affecting behavior of CApath option on openssl verify
- Fixing Nitro behavior of hostkey harvesting and post-installation systemd hooks
* Wed May 15 2019 Daniel Anderson 1.1-9
- Fixing existing AuthorizedKeysCommand detection
- Adding additional licensing headers
- Improved mechanism for detection if script is running on an EC2 instance
* Wed Apr 24 2019 Daniel Anderson 1.1-8
- Better detection of existing user customization
* Fri Mar 29 2019 Daniel Anderson 1.1-7
- Change to Amazon Linux configuration
* Wed Mar 20 2019 Daniel Anderson 1.1-6
- Verification of EC2 hypervisor UUID
* Fri Mar 15 2019 Daniel Anderson 1.1-5
- Added slightly stronger checks that we're getting valid data from Instance Metadata Service/on an instance
* Wed Jan 30 2019 Daniel Anderson 1.1-4
- Fixed a bug in reading instance-identity credentials as part of hostkey harvesting and dropped AWS CLI dependency
- Added support for non-Amazon Linux yum distributions, such as RHEL and CentOS
- Hardened error handling
* Fri Dec 21 2018 Daniel Anderson 1.1-3
- Fixing an issue with the hostkey harvesting script - it was using default creds instead of instance-identity
* Fri Dec 7 2018 Daniel Anderson 1.1-2
- Minor changes to package build process to share code with Debian packaging
* Tue Oct 23 2018 Anshumali Prasad 1.1-1
- Hostkey harvesting for EC2 Instance Connect.
* Mon Oct 22 2018 Daniel Anderson 1.0-3
- Updating exit status on no-data case, improving support for newer openssl versions
* Tue Oct 9 2018 Daniel Anderson 1.0-2
- Cleaning up package requirements & post installation hook
* Wed Jun 13 2018 Daniel Anderson 1.0-1
- Initial RPM build for EC2 Instance Connect targeting Amazon Linux 2.
aws-ec2-instance-connect-config-1.1.14/src/ 0000775 0000000 0000000 00000000000 14024143525 0020322 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/src/bin/ 0000775 0000000 0000000 00000000000 14024143525 0021072 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/src/bin/eic_curl_authorized_keys 0000775 0000000 0000000 00000015266 14024143525 0026110 0 ustar 00root root 0000000 0000000 #!/bin/sh
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads and echoes EC2 Metadata to get the authorized keys blob for the user $1
set -e
# Set umask so only we can touch temp files
umask 077
IMDS="http://169.254.169.254/latest/meta-data"
# cURL wrapper to ensure we always use the desired flags
curl_cmd () {
/usr/bin/curl -s -f -m 1 -H "${1}" "${2}"
}
# Fetch the IMDSv2 access token. 5 seconds is overall AKC timeout so we use that.
IMDS_TOKEN="$(/usr/bin/curl -s -f -m 1 -X PUT "http://169.254.169.254/latest/api/token" -H "X-aws-ec2-metadata-token-ttl-seconds: 5")"
token_exit="${?}"
if [ "${token_exit}" -ne 0 ] ; then
/usr/bin/logger -i -p authpriv.info "EC2 Instance Connect failed to establish trust with Instance Metadata Service"
exit 255
fi
if [ -z "${IMDS_TOKEN}" ] ; then
# Fast fail
/usr/bin/logger -i -p authpriv.info "EC2 Instance Connect failed to get a token to invoke Instance Metadata Service"
exit 255
fi
IMDS_TOKEN_HEADER="X-aws-ec2-metadata-token: ${IMDS_TOKEN}"
# Verify the instance ID itself
# Note: if IMDSv1 is disabled here and IMDS_TOKEN is unset we fast-fail out right now.
instance=$(curl_cmd "${IMDS_TOKEN_HEADER}" "${IMDS}/instance-id/")
if [ -z "${instance}" ] ; then
exit 0
fi
# Validate the instance ID is i-abcd1234 (8 or 17 char, hex)
# We have it buffered to 32 chars to futureproof any further EC2 format changes (given some other EC2 resources are already 32 char)
/bin/echo "${instance}" | /usr/bin/head -n 1 | /bin/grep -Eq "^i-[0-9a-f]{8,32}$" || exit 0
# Verify we have an EC2 uuid
if [ ! -f /sys/hypervisor/uuid ] ; then
# Nitro, switch to DMI check
if [ ! -f /sys/devices/virtual/dmi/id/board_asset_tag ] ; then
# We're out of options. This is definitely not an instance.
/usr/bin/logger -i -p authpriv.info "EC2 Instance Connect was invoked on a non-instance and will do nothing."
exit 0
elif [ "$(/bin/cat /sys/devices/virtual/dmi/id/board_asset_tag)" != "${instance}" ] ; then
# The board_asset_tag does not match the instance id. This is not a valid instance.
/usr/bin/logger -i -p authpriv.info "EC2 Instance Connect was invoked on a non-instance and will do nothing."
exit 0
fi
elif [ "$(/usr/bin/cut -c1-3 < /sys/hypervisor/uuid)" != "ec2" ] ; then
# Leading bytes are not "ec2"
/usr/bin/logger -i -p authpriv.info "EC2 Instance Connect was invoked on a non-instance and will do nothing."
exit 0
fi
# At this point we're reasonably confident we're running on an EC2 instance.
OPENSSL=/usr/bin/openssl
if [ -z "${1}" ] ; then
# No user provided, not really anything to query for. Fail out.
/usr/bin/logger -i -p authpriv.info "EC2 Instance Connect was invoked without a user to authorize and will do nothing."
exit 1
fi
/usr/bin/id -u "${1}" > /dev/null 2>&1
id_exit="${?}"
if [ "${id_exit}" -ne 0 ] ; then
# User doesn't actually exist. Let sshd deal with it.
exit 0
fi
# Verify that we have active keys. Fast-exit if we do not.
keys_status="$(/usr/bin/curl -s -f -m 1 -H "${IMDS_TOKEN_HEADER}" -o /dev/null -I -w %{http_code} "${IMDS}/managed-ssh-keys/active-keys/${1}/")"
if [ "${keys_status}" != "200" ]
then
# No keys for this user. Nothing to do.
exit 0
fi
# We are not checking format here - that is parse_authorized_keys's job
zone=$(curl_cmd "${IMDS_TOKEN_HEADER}" "${IMDS}/placement/availability-zone/")
zone_exit="${?}"
if [ "${zone_exit}" -ne 0 ]
then
exit "${zone_exit}"
fi
# Validate the zone is aa-bb-#c (or aa-bb-cc-#d for special partitions like AWS GovCloud)
/bin/echo "${zone}" | /usr/bin/head -n 1 | /bin/grep -Eq "^([a-z]+-){2,3}[0-9][a-z]$" || exit 255
region=$(/bin/echo "${zone}" | /bin/sed -n 's/\(\([a-z]\+-\)\+[0-9]\+\).*/\1/p')
domain=$(curl_cmd "${IMDS_TOKEN_HEADER}" "${IMDS}/services/domain/")
domain_exit="${?}"
if [ "${domain_exit}" -ne 0 ]
then
exit "${domain_exit}"
fi
is_domain_valid=1
for valid_domain in amazonaws.com amazonaws.com.cn c2s.ic.gov sc2s.sgov.gov; do
if [ "$domain" = "$valid_domain" ]; then
is_domain_valid=0
break
fi
done
if [ $is_domain_valid -eq 1 ]; then
/usr/bin/logger -i -p authpriv.info "EC2 Instance Connect found an invalid domain and will do nothing."
exit 255
fi
expected_signer=$(/usr/bin/printf 'managed-ssh-signer.%s.%s' "${region}" "${domain}")
userpath=$(/bin/mktemp -d /dev/shm/eic-XXXXXXXX)
trap 'rm -rf "${userpath:?}"' EXIT
# Read the current signer cert
# This will overwrite whatever currently exists, so it will remain up-to-date
certificate=$(curl_cmd "${IMDS_TOKEN_HEADER}" "${IMDS}/managed-ssh-keys/signer-cert/")
cert_exit="${?}"
if [ "${cert_exit}" -ne 0 ] || [ -z "${certificate}" ]
then
exit "${cert_exit}"
fi
# parse_authorized_keys will verify this
# Read the signer OCSP staples
staple_paths=$(curl_cmd "${IMDS_TOKEN_HEADER}" "${IMDS}/managed-ssh-keys/signer-ocsp/")
staple_exit="${?}"
if [ "${staple_exit}" -ne 0 ]
then
exit "${staple_exit}"
fi
ocsp_path=$(/bin/mktemp -d "${userpath}/eic-ocsp-XXXXXXXX")
for word in $staple_paths
do
curl_cmd "${IMDS_TOKEN_HEADER}" "${IMDS}/managed-ssh-keys/signer-ocsp/${word}" | /usr/bin/base64 -d > "${ocsp_path}/${word}"
staple_exit="${?}"
if [ "${staple_exit}" -ne 0 ]
then
exit "${staple_exit}"
fi
/bin/chmod 400 "${ocsp_path}/${word}" # Disable access to staple file
done
# parse_authorized_keys will verify these
# Invoke key parser (will automagically echo the results)
keys_file="${userpath}/eic-keys"
curl_cmd "${IMDS_TOKEN_HEADER}" "${IMDS}/managed-ssh-keys/active-keys/${1}/" > "${keys_file}"
DIR="$( cd "$( dirname "${0}" )" && pwd )"
ca_path=/etc/ssl/certs
if [ -z "${2}" ] ; then
output="$("${DIR}/eic_parse_authorized_keys" -x false -p "${keys_file}" -o "${OPENSSL}" -d "${userpath}" -s "${certificate}" -i "${instance}" -c "${expected_signer}" -a "${ca_path}" -v "${ocsp_path}")"
exitcode=$? # not quote-escaped since this must be numeric 0-255
else
output="$("${DIR}/eic_parse_authorized_keys" -x false -p "${keys_file}" -o "${OPENSSL}" -d "${userpath}" -s "${certificate}" -i "${instance}" -c "${expected_signer}" -a "${ca_path}" -v "${ocsp_path}" -f "${2}")"
exitcode=$? # not quote-escaped since this must be numeric 0-255
fi
/bin/echo "${output}"
exit $exitcode
aws-ec2-instance-connect-config-1.1.14/src/bin/eic_harvest_hostkeys 0000775 0000000 0000000 00000016233 14024143525 0025252 0 ustar 00root root 0000000 0000000 #!/bin/sh
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
set -e
umask 077
# Fetch the IMDSv2 access token. 5 seconds is overall AKC timeout so we use that.
IMDS_TOKEN="$(/usr/bin/curl -s -f -m 1 -X PUT "http://169.254.169.254/latest/api/token" -H "X-aws-ec2-metadata-token-ttl-seconds: 5")"
if [ -z "${IMDS_TOKEN}" ] ; then
# Fast fail
exit 255
fi
# Verify the instance ID itself
instance=$(/usr/bin/curl -s -f -m 1 -H "X-aws-ec2-metadata-token: ${IMDS_TOKEN}" "http://169.254.169.254/latest/meta-data/instance-id/")
if [ -z "${instance}" ] ; then
exit 255
fi
# Validate the instance ID is i-abcd1234 (8 or 17 char, hex)
# We have it buffered to 32 chars to futureproof any further EC2 format changes (given some other EC2 resources are already 32 char)
/bin/echo "${instance}" | /usr/bin/head -n 1 | /bin/grep -Eq "^i-[0-9a-f]{8,32}$" || exit 255
# Verify we have an EC2 uuid
if [ ! -f /sys/hypervisor/uuid ] ; then
# Nitro, switch to DMI check
if [ ! -f /sys/devices/virtual/dmi/id/board_asset_tag ] ; then
# We're out of options. This is definitely not an instance.
exit 255
elif [ "$(/bin/cat /sys/devices/virtual/dmi/id/board_asset_tag)" != "${instance}" ] ; then
# The board_asset_tag does not match the instance id. This is not a valid instance.
exit 255
fi
elif [ "$(/usr/bin/cut -c1-3 < /sys/hypervisor/uuid)" != "ec2" ] ; then
# Leading bytes are not "ec2"
exit 255
fi
# Calculate the SHA256 of a given string
# sha256 [string]
sha256 () {
/bin/echo -n "${1}" | /usr/bin/sha256sum | /bin/sed 's/\s.*$//'
}
# Sign a message with a given key
# sign [key] [msg]
sign () {
/usr/bin/printf "${2}" | /usr/bin/openssl dgst -binary -hex -sha256 -mac HMAC -macopt hexkey:"${1}" | /bin/sed 's/.* //'
}
# Derive a sigv4 signing key for the given secret
# get_sigv4_key [key] [datestamp] [region name] [service name]
getsigv4key () {
base="$(/bin/echo -n "AWS4${1}" | /usr/bin/od -A n -t x1 | /bin/sed ':a;N;$!ba;s/[\n ]//g')"
kdate="$(sign "${base}" "${2}")"
kregion="$(sign "${kdate}" "${3}")"
kservice="$(sign "${kregion}" "${4}")"
sign "${kservice}" "aws4_request"
}
# Verify that we have instance identity credentials. Fast-exit if we do not.
creds_status="$(/usr/bin/curl -s -f -m 1 -H "X-aws-ec2-metadata-token: ${IMDS_TOKEN}" -o /dev/null -I -w %{http_code} "http://169.254.169.254/latest/meta-data/identity-credentials/ec2/security-credentials/ec2-instance/")"
if [ "${creds_status}" != "200" ]
then
# No keys for this user. Nothing to do.
exit 0
fi
#Iterates overs /etc/ssh to get the host keys
for file in /etc/ssh/*.pub; do
/usr/bin/test -r "${file}" || continue
key=$(/usr/bin/awk '{$1=$1};1' < "${file}")
keys="${keys:+${keys},}\"${key}\""
done
#Temporary path to store request parameters
userpath=$(/bin/mktemp -d /dev/shm/eic-hostkey-XXXXXXXX)
trap 'rm -rf "${userpath}"' EXIT
#Get zone information
zone=$(/usr/bin/curl -s -f -m 1 -H "X-aws-ec2-metadata-token: ${IMDS_TOKEN}" "http://169.254.169.254/latest/meta-data/placement/availability-zone/")
zone_exit="${?}"
if [ "${zone_exit}" -ne 0 ]
then
exit "${zone_exit}"
fi
# Validate the zone
/bin/echo "${zone}" | /usr/bin/head -n 1 | /bin/grep -Eq "^([a-z]+-){2,3}[0-9][a-z]$" || exit 255
# Get domain for calls
domain=$(/usr/bin/curl -s -f -m 1 -H "X-aws-ec2-metadata-token: ${IMDS_TOKEN}" "http://169.254.169.254/latest/meta-data/services/domain/")
domain_exit="${?}"
if [ "${domain_exit}" -ne 0 ]
then
exit "${domain_exit}"
fi
#Extract region from zone
region=$(/bin/echo "${zone}" | /bin/sed -n 's/\(\([a-z]\+-\)\+[0-9]\+\).*/\1/p')
hostkeys=$(/bin/echo "${keys:?}")
accountId=$(/usr/bin/curl -s -f -m 1 -H "X-aws-ec2-metadata-token: ${IMDS_TOKEN}" "http://169.254.169.254/latest/dynamic/instance-identity/document" | /bin/grep -oP '(?<="accountId" : ")[^"]*(?=")')
/bin/echo "${accountId}" | /usr/bin/head -n 1 | /bin/grep -Eq "^[0-9]{12}$" || exit 255
val='{"AccountID":"'${accountId}'","AvailabilityZone":"'${zone}'","HostKeys":['${hostkeys}'],"InstanceId":"'${instance}'"}'
# Pull the creds we need for the call
creds=$(/usr/bin/curl -s -f -m 1 -H "X-aws-ec2-metadata-token: ${IMDS_TOKEN}" "http://169.254.169.254/latest/meta-data/identity-credentials/ec2/security-credentials/ec2-instance/")
creds_exit="${?}"
if [ "${creds_exit}" -ne 0 ] ; then
# We failed to load instance-identity credentials
exit "${creds_exit}"
fi
AWS_ACCESS_KEY_ID=$(/bin/echo "${creds}" | /bin/sed -n 's/.*"AccessKeyId" : "\(.*\)",/\1/p')
AWS_SECRET_ACCESS_KEY=$(/bin/echo "${creds}" | /bin/sed -n 's/.*"SecretAccessKey" : "\(.*\)",/\1/p')
AWS_SESSION_TOKEN=$(/bin/echo "${creds}" | /bin/sed -n 's/.*"Token" : "\(.*\)",/\1/p')
unset creds
clearcreds () {
unset AWS_SESSION_TOKEN
unset AWS_SECRET_ACCESS_KEY
unset AWS_ACCESS_KEY_ID
}
trap clearcreds EXIT
# Generate, sign, and send the sigv4 request
host="ec2-instance-connect.${region}.${domain}"
endpoint="https://${host}"
timestamp=$(/bin/date -u "+%Y-%m-%d %H:%M:%S")
isoTimestamp=$(/bin/date -ud "${timestamp}" "+%Y%m%dT%H%M%SZ")
isoDate=$(/bin/date -ud "${timestamp}" "+%Y%m%d")
canonicalQuery="" # We are using POST data, not a querystring
canonicalHeaders="host:${host}\nx-amz-date:${isoTimestamp}\nx-amz-security-token:${AWS_SESSION_TOKEN}\n"
signedHeaders="host;x-amz-date;x-amz-security-token"
payloadHash=$(/bin/echo -n "${val}" | /usr/bin/sha256sum | /bin/sed 's/\s.*$//')
canonicalRequest="$(/usr/bin/printf "POST\n/PutEC2HostKeys/\n%s\n${canonicalHeaders}\n${signedHeaders}\n%s" "${canonicalQuery}" "${payloadHash}")"
requestHash=$(/bin/echo -n "${canonicalRequest}" | /usr/bin/sha256sum | /bin/sed 's/\s.*$//')
# Derive the signature
credentialScope="${isoDate}/${region}/ec2-instance-connect/aws4_request"
toSign="AWS4-HMAC-SHA256\n${isoTimestamp}\n${credentialScope}\n${requestHash}"
signingKey=$(getsigv4key "${AWS_SECRET_ACCESS_KEY}" "${isoDate}" "${region}" "ec2-instance-connect")
signature=$(sign "${signingKey}" "${toSign}")
authorizationHeader="AWS4-HMAC-SHA256 Credential=${AWS_ACCESS_KEY_ID}/${credentialScope}, SignedHeaders=${signedHeaders}, Signature=${signature}"
# Attempt to publish host keys
# 5 second timeout helps avoid choking launches in private subnets (see https://github.com/aws/aws-ec2-instance-connect-config/issues/8)
/usr/bin/curl -sS -m 5 -X POST -H "Content-Encoding: amz-1.0" -H "Authorization: ${authorizationHeader}" -H "Content-Type: application/json" -H "x-amz-content-sha256: ${payloadHash}" -H "x-amz-date: ${isoTimestamp}" -H "x-amz-security-token: ${AWS_SESSION_TOKEN}" -H "x-amz-target: com.amazon.aws.sshaccessproxyservice.AWSEC2InstanceConnectService.PutEC2HostKeys" -d "${val}" "${endpoint}/PutEC2HostKeys/"
unset AWS_SESSION_TOKEN
unset AWS_SECRET_ACCESS_KEY
unset AWS_ACCESS_KEY_ID
aws-ec2-instance-connect-config-1.1.14/src/bin/eic_parse_authorized_keys 0000775 0000000 0000000 00000036520 14024143525 0026251 0 ustar 00root root 0000000 0000000 #!/bin/sh
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Reads authorized keys blob $3 and prints verified, unexpired keys
# Openssl to use provided as $1
# Signer public key file path provided as $2
set -e
# Set umask so only we can touch temp files
umask 077
# Failure reporting & exit
# Format: fail [is_debug] [message]
fail () {
if [ "${1}" = true ] ; then
/bin/echo "${2}"
else
/usr/bin/logger -i -p authpriv.info "${2}"
fi
exit 1
}
# Helper to determine if a string starts with a given prefix
# Format: startswith [string] [prefix]
startswith () {
[ "${1#${2}}x" != "${1}x" ]
}
# Helper function to strip out a prefix from a string
# Format: removeprefix [string] [prefix]
removeprefix () {
/usr/bin/printf '%s' "${1#${2}}"
}
# Helper to verify an arbitrary ocsp response body given the certificate and issuer
# Format: verifyocsp [is_debug] [openssl command] [certificate] [issuer] [ocsp directory]
verifyocsp() {
# First check if this cert is already trusted
cname=$("${2}" x509 -noout -subject -in "${3}" 2>/dev/null | /bin/sed -n -e 's/^.*CN[[:blank:]]*=[[:blank:]]*//p')
fingerprint=$("${2}" x509 -noout -fingerprint -sha1 -inform pem -in "${3}" 2>/dev/null | /bin/sed -n 's/SHA1 Fingerprint[[:space:]]*=[[:space:]]*\(.*\)/\1/p' | tr -d ':')
ocsp_out=$("${2}" ocsp -no_nonce -issuer "${4}" -cert "${3}" -VAfile "${4}" -respin "${5}/${fingerprint}" 2>/dev/null)
ocsp_exit="${?}"
if [ "${ocsp_exit}" -ne 0 ] || ! startswith "${ocsp_out}" "${3}: good" ; then
fail "${1}" "EC2 Instance Connect could not verify certificate ${cname} has not been revoked. No keys have been trusted."
fi
}
while getopts ":x:p:o:d:s:i:c:a:v:f:" o; do
case "${o}" in
x)
is_debug="${OPTARG}"
;;
p)
keys_path="${OPTARG}"
;;
o)
OPENSSL="${OPTARG}"
;;
d)
tmpdir="${OPTARG}"
;;
s)
signer="${OPTARG}"
;;
i)
current_instance_id="${OPTARG}"
;;
c)
expected_cn="${OPTARG}"
;;
a)
ca_path="${OPTARG}"
;;
v)
ocsp_dir_path="${OPTARG}"
;;
f)
expected_key="${OPTARG}"
;;
*)
/bin/echo "Usage: $0 [-x debug] [-r key read command] [-o openssl command] [-d tmpdir] [-s signer certificate] [-i instance id] [-c cname] [-a ca path] [-v ocsp dir] [-f key fingerprint]"
exit 1
;;
esac
done
# Verify we have sufficient inputs
if [ $# -lt 1 ] ; then
# No args whatsoever
# Unit test log (ignored by sshd)
/bin/echo "Usage: $0 [-x debug] [-r key read command] [-o openssl command] [-d tmpdir] [-s signer certificate] [-i instance id] [-c cname] [-a ca path] [-v ocsp dir] [-f key fingerprint]"
# System log
/usr/bin/logger -i -p authpriv.info "Unable to run EC2 Instance Connect: insufficient args provided. Please check your sshd configuration."
exit 1
fi
# Verify the signer certificate we have been provided - CN, trust chain, and revocation status
# Split the chain into pieces
/bin/echo "${signer}" | /usr/bin/awk -v dir="${tmpdir}" 'split_after==1{n++;split_after=0} /-----END CERTIFICATE-----/ {split_after=1} {print > dir "/cert" n ".pem"}'
# We want visibility into the CA bundle so we can skip verifying entries in the chain that are already trusted
if [ -d "${ca_path}" ] ; then
ca_path_dir=$ca_path
else
ca_path_dir=$(dirname "${ca_path}")
fi
ca_bundles_dir=$(/bin/mktemp -d "${tmpdir}/eic-cert-XXXXXXXX")
end=$(/usr/bin/find "${tmpdir}" -maxdepth 1 -type f -name "cert*.pem" -regextype sed -regex ".*/cert[0-9]\+\.pem" | wc -l)
if [ "${end}" -gt 0 ] ; then
# First see if we already have them
for i in $(/usr/bin/seq 1 "${end}") ; do
subject=$("${OPENSSL}" x509 -noout -subject -in "${tmpdir}/cert${i}.pem" | /bin/sed -n -e 's/^.*CN[[:space:]]*=[[:space:]]*//p')
underscored=$(/bin/echo "${subject}" | /usr/bin/tr -s ' ' '_') 2>/dev/null
if [ -f "${ca_path_dir}/${underscored}.pem" ] ; then
# We already have it
/bin/cp "${ca_path_dir}/${underscored}.pem" "${ca_bundles_dir}/${underscored}"
else
if [ ! -d "${ca_path}" ] ; then
# Try to pull this CN from the CA bundle
/bin/sed -n -e '/#[[:space:]]'"$subject"'$/,$p' "${ca_path}" 2>/dev/null | /bin/sed '/-----END[[:space:]]CERTIFICATE-----.*/,$d' | /bin/sed -n '1!p' > "${ca_bundles_dir}/${subject}"
if [ -s "${ca_bundles_dir}/${subject}" ] ; then
/bin/echo "-----END CERTIFICATE-----" >> "${ca_bundles_dir}/${subject}"
else
/bin/rm -f "${ca_bundles_dir}/${subject}"
fi
fi
fi
done
fi
# Build the intermediate trust chain
/bin/touch "${tmpdir}/ca-trust.pem"
for i in $(/usr/bin/seq 1 "${end}") ; do
/bin/cat "${tmpdir}/cert${i}.pem" >> "${tmpdir}/ca-trust.pem"
done
if [ -d "${ca_path}" ] ; then
subject=$("${OPENSSL}" x509 -noout -subject -in "${tmpdir}/cert${end}.pem" | /bin/sed -n -e 's/^.*CN[[:space:]]*=[[:space:]]*//p')
underscored=$(/bin/echo "${subject}" | /usr/bin/tr -s ' ' '_') 2>/dev/null
/bin/cat "${ca_bundles_dir}/${underscored}" >> "${tmpdir}/ca-trust.pem" 2>/dev/null
else
/bin/cat "${ca_path}" >> "${tmpdir}/ca-trust.pem" 2>/dev/null
fi
# At this point ca-trust is final
/bin/chmod 400 "${tmpdir}/ca-trust.pem"
# Verify the CN
signer_cn=$("${OPENSSL}" x509 -noout -subject -in "${tmpdir}/cert.pem" | /bin/sed -n -e 's/^.*CN[[:space:]]*=[[:space:]]*//p')
if [ "${signer_cn}" != "${expected_cn}" ] ; then
fail "${is_debug}" "EC2 Instance Connect encountered an unrecognized signer certificate. No keys have been trusted."
fi
# Verify the trust chain
if [ -d "${ca_path}" ] ; then
verify_out=$("${OPENSSL}" verify -x509_strict -CApath "${ca_path}" -CAfile "${tmpdir}/ca-trust.pem" "${tmpdir}/cert.pem")
verify_status=$?
else
# If the CA path is not a directory then do not use it - openssl will throw errors on versions 1.1.1+
verify_out=$("${OPENSSL}" verify -x509_strict -CAfile "${tmpdir}/ca-trust.pem" "${tmpdir}/cert.pem")
verify_status=$?
fi
if [ $verify_status -ne 0 ] || [ "${verify_out}" != "${tmpdir}/cert.pem: OK" ] ; then
fail "${is_debug}" "EC2 Instance Connect could not verify the signer trust chain. No keys have been trusted."
fi
# Verify no certificates have been revoked
# Iterate from first to second-to-last cert & validate OCSP staples
/bin/mv "${tmpdir}/cert.pem" "${tmpdir}/cert0.pem" # Better naming consistency for loop
for i in $(/usr/bin/seq 0 $((end - 1))) ; do
subject=$("${OPENSSL}" x509 -noout -subject -in "${tmpdir}/cert${i}.pem" | /bin/sed -n -e 's/^.*CN[[:space:]]*=[[:space:]]*//p')
if [ -f "${ca_bundles_dir}/${subject}" ] ; then
# If we encounter a certificate that's in the CA bundle we can skip the rest as implicitly trusted
hash=$("${OPENSSL}" x509 -hash -noout -in "${tmpdir}/cert${i}.pem" 2>/dev/null)
trusted_hash=$("${OPENSSL}" x509 -hash -noout -in "${ca_bundles_dir}/${subject}" 2>/dev/null)
fingerprint=$("${OPENSSL}" x509 -noout -fingerprint -sha1 -in "${tmpdir}/cert${i}.pem" 2>/dev/null | /bin/sed -n 's/SHA1 Fingerprint[[:space:]]*=[[:space:]]*\(.*\)/\1/p' | tr -d ':')
trusted_fingerprint=$("${OPENSSL}" x509 -noout -fingerprint -sha1 -in "${ca_bundles_dir}/${subject}" 2>/dev/null | /bin/sed -n 's/SHA1 Fingerprint[[:space:]]*=[[:space:]]*\(.*\)/\1/p' | tr -d ':')
pkey=$("${OPENSSL}" x509 -pubkey -noout -in "${tmpdir}/cert${i}.pem")
trusted_pkey=$("${OPENSSL}" x509 -pubkey -noout -in "${ca_bundles_dir}/${subject}" )
if [ "${hash}" = "${trusted_hash}" ] && [ "${fingerprint}" = "${trusted_fingerprint}" ] && [ "${pkey}" = "${trusted_pkey}" ] ; then
# Already trusted, no need to OCSP verify
break
fi
fi
verifyocsp "${is_debug}" "${OPENSSL}" "${tmpdir}/cert${i}.pem" "${tmpdir}/cert$((i + 1)).pem" "${ocsp_dir_path}"
done
# At this point we no longer need the CA information
/bin/rm -rf "${ca_bundles_dir}"
# Extract cert public key
/bin/echo "${signer}" | "${OPENSSL}" x509 -pubkey -noout > "${tmpdir}/pubkey" 2>/dev/null
extract="${?}"
if [ "${extract}" -ne 0 ] ; then
fail "${is_debug}" "EC2 Instance Connect failed to extract the public key from the signer certificate. No keys have been trusted."
fi
# Begin actual parsing of authorized keys data
if [ -n "${expected_key+x}" ] ; then
# An expected fingerprint was given
if [ "${is_debug}" = false ] ; then
/usr/bin/logger -i -p authpriv.info "Querying EC2 Instance Connect keys for matching fingerprint: ${expected_key}"
fi
fi
# Set current time as expiration marker
curtime=$(/bin/date +%s)
# We want to prevent variables from leaving the parser's scope
# We also want to capture overall exit code
# We also need to redirect the input into our loop
# The simplest solution to all of the above is to take advantage of how sh pipes spawn a subprocess
output=$(
exitcode=255 # Exit code if no valid keys are provided
count=0
# Read loop - pull timestamp line at start of iteration
while read -r line
do
pathprefix="${tmpdir}/${count}"
# Clear our temp buffers to prevent any sort of injection
/bin/rm -f "${pathprefix}-key"
/bin/rm -f "${pathprefix}-signedData"
/bin/rm -f "${pathprefix}-sig"
/bin/rm -f "${pathprefix}-decoded"
# Pre-initialize key validation fields
timestamp=0
instance_id=""
caller=""
request=""
# We do not pre-initialize the actual key or signature fields
/bin/touch "${pathprefix}-signedData"
# Loop to read keys & parse out values
# This is not sub-shelled as we want to maintain variable scope with the outer loop
# Loop condition is until we reach a line that lacks the "#Key" format
while startswith "${line}" "#"
do
# Note that not all of these may be present depending on service deployments
# Similarly, this list is not meant to be exhaustive - there may be new fields to be checked in a later version
if startswith "${line}" "#Timestamp=" ; then
timestamp=$(removeprefix "${line}" "#Timestamp=")
elif startswith "${line}" "#Instance=" ; then
instance_id=$(removeprefix "${line}" "#Instance=")
elif startswith "${line}" "#Caller=" ; then
caller=$(removeprefix "${line}" "#Caller=")
elif startswith "${line}" "#Request=" ; then
request=$(removeprefix "${line}" "#Request=")
# Otherwise it's a #Key we don't recognize (i.e., this version of AuthorizedKeysCommand is outdated)
fi
# We verify on all fields in-order, whether we recognize them or not. Similarly, we don't force fields not present.
# As such we always add this to the signature verification file
/usr/bin/printf '%s\n' "${line}" >> "${pathprefix}-signedData"
# Read the next line
read -r line
done
# At this point, line should contain the key
if startswith "${line}" "ssh" ; then
key="${line}"
/usr/bin/printf '%s\n' "${key}" >> "${pathprefix}-signedData"
# At this point we do not need to modify signedData
/bin/chmod 400 "${pathprefix}-signedData"
# Read key signature - may be multi-line
encodedsigfile="${pathprefix}-sig"
/bin/touch "${encodedsigfile}"
read -r sigline || sigline=""
while [ "${sigline}" != "" ]
do
/usr/bin/printf '%s\n' "${sigline}" >> "${encodedsigfile}"
read -r sigline || sigline=""
done
/bin/chmod 400 "${encodedsigfile}"
/usr/bin/printf '%s\n' "${key}" > "${pathprefix}-key"
# Begin validation
if [ -n "${instance_id}" ] && [ "${timestamp}" -ne 0 ] ; then
fingerprint=$(/usr/bin/ssh-keygen -lf "${pathprefix}-key" | cut -d ' ' -f 2) # Get only the actual fingerprint, ignore key size & source
# If we were told to expect a specific key and this isn't it, skip it
if [ -z "${expected_key}" ] || [ "$fingerprint" = "${expected_key}" ] ; then
# Check instance ID matches & timestamp is still valid
if [ "${current_instance_id}" = "${instance_id}" ] && [ "${timestamp}" -gt "${curtime}" ] ; then
# Decode the signature
(/usr/bin/base64 --decode "${encodedsigfile}" > "${pathprefix}-decoded" || rm -f "${pathprefix}-decoded") 2>/dev/null
if [ -f "${pathprefix}-decoded" ] ; then
# Verify signature
$OPENSSL dgst -sha256 -sigopt rsa_padding_mode:pss -sigopt rsa_pss_saltlen:32 -verify "${tmpdir}/pubkey" -signature "${pathprefix}-decoded" "${pathprefix}-signedData" 1>/dev/null 2>/dev/null
verify="${?}"
if [ "${verify}" -eq 0 ] ; then
# Signature verified.
# Record this in syslog
callermessage="Providing ssh key from EC2 Instance Connect with fingerprint: ${fingerprint}"
if [ "${request}" != "" ] ; then
callermessage="${callermessage}, request-id: ${request}"
fi
if [ "${caller}" != "" ] ; then
callermessage="${callermessage}, for IAM principal: ${caller}"
fi
if [ "${is_debug}" = false ] ; then
/usr/bin/logger -i -p authpriv.info "${callermessage}"
fi
# Return key to the ssh daemon
/bin/echo "${key}"
exitcode=0
fi
fi
fi
fi
fi
else
# We didn't find a key. Skip until we hit a blank line or EOF
while [ "${line}" != "" ]
do
read -r line || line=""
done
fi
# Clean up any tempfiles
/bin/rm -f "${pathprefix}-key"
/bin/rm -f "${pathprefix}-signedData"
/bin/rm -f "${pathprefix}-sig"
/bin/rm -f "${pathprefix}-decoded"
count=$((count + 1))
done < "${keys_path}"
# This is the loop subprocess's exit code, not the script's
exit $exitcode
)
# Re-capture the exit code
exitcode=$?
# Print keys & exit
/bin/rm -rf "${tmpdir}/pubkey"
/bin/echo "${output}"
exit $exitcode
aws-ec2-instance-connect-config-1.1.14/src/bin/eic_run_authorized_keys 0000775 0000000 0000000 00000001467 14024143525 0025745 0 ustar 00root root 0000000 0000000 #!/bin/sh
# Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
# Quickie to wrap curl_authorized_keys in a timeout
# Necessary for older versions of openssh where AuthorizedKeysCommand must be a filepath
set -e
DIR="$( cd "$( dirname "${0}" )" && pwd )"
/usr/bin/timeout 5s "${DIR}/eic_curl_authorized_keys" "$@"
aws-ec2-instance-connect-config-1.1.14/src/deb_systemd/ 0000775 0000000 0000000 00000000000 14024143525 0022624 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/src/deb_systemd/ec2-instance-connect.service 0000664 0000000 0000000 00000001124 14024143525 0030106 0 ustar 00root root 0000000 0000000 [Unit]
Description=EC2 Instance Connect Host Key Harvesting
Before=ssh.service
After=network.target ssh-keygen.service
[Install]
WantedBy=multi-user.target
[Service]
Type=oneshot
# Prefixing the ExecStart executable with a '-' ignores any failure exit codes and considers it a success
# This is to avoid issues with the host key harvesting script during system startup
# and not leave the system in a degraded state.
# See Table 1 under ExecStart= for details https://www.freedesktop.org/software/systemd/man/systemd.service.html
ExecStart=-/usr/share/ec2-instance-connect/eic_harvest_hostkeys
aws-ec2-instance-connect-config-1.1.14/src/deb_systemd/ssh.service.d/ 0000775 0000000 0000000 00000000000 14024143525 0025302 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/src/deb_systemd/ssh.service.d/ec2-instance-connect.conf 0000664 0000000 0000000 00000000313 14024143525 0032050 0 ustar 00root root 0000000 0000000 [Service]
ExecStart=
ExecStart=/usr/sbin/sshd -D -o "AuthorizedKeysCommand /usr/share/ec2-instance-connect/eic_run_authorized_keys %%u %%f" -o "AuthorizedKeysCommandUser ec2-instance-connect" $SSHD_OPTS
aws-ec2-instance-connect-config-1.1.14/src/ec2-instance-connect.preset 0000664 0000000 0000000 00000000044 14024143525 0025446 0 ustar 00root root 0000000 0000000 enable ec2-instance-connect.service
aws-ec2-instance-connect-config-1.1.14/src/rpm_systemd/ 0000775 0000000 0000000 00000000000 14024143525 0022670 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/src/rpm_systemd/ec2-instance-connect.service 0000664 0000000 0000000 00000001103 14024143525 0030147 0 ustar 00root root 0000000 0000000 [Unit]
Description=EC2 Instance Connect Host Key Harvesting
Before=sshd.service
After=network.target sshd-keygen.service
[Install]
WantedBy=multi-user.target
[Service]
Type=oneshot
# Prefixing the ExecStart executable with a '-' ignores any failure exit codes and considers it a success
# This is to avoid issues with the host key harvesting script during system startup
# and not leave the system in a degraded state.
# See Table 1 under ExecStart= for details https://www.freedesktop.org/software/systemd/man/systemd.service.html
ExecStart=-/opt/aws/bin/eic_harvest_hostkeys
aws-ec2-instance-connect-config-1.1.14/src/rpm_systemd/sshd.service.d/ 0000775 0000000 0000000 00000000000 14024143525 0025512 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/src/rpm_systemd/sshd.service.d/ec2-instance-connect.conf 0000664 0000000 0000000 00000000270 14024143525 0032262 0 ustar 00root root 0000000 0000000 [Service]
ExecStart=
ExecStart=/usr/sbin/sshd -D -o "AuthorizedKeysCommand /opt/aws/bin/eic_run_authorized_keys %%u %%f" -o "AuthorizedKeysCommandUser ec2-instance-connect" $SSHD_OPTS
aws-ec2-instance-connect-config-1.1.14/unit-test/ 0000775 0000000 0000000 00000000000 14024143525 0021467 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/expected-output/ 0000775 0000000 0000000 00000000000 14024143525 0024626 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/expected-output/different-fingerprint 0000664 0000000 0000000 00000000000 14024143525 0031032 0 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/expected-output/empty 0000664 0000000 0000000 00000000000 14024143525 0025675 0 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/expected-output/expired-timestamp 0000664 0000000 0000000 00000000000 14024143525 0030200 0 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/expected-output/invalid-instance 0000664 0000000 0000000 00000000000 14024143525 0027767 0 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/expected-output/invalid-signature 0000664 0000000 0000000 00000000000 14024143525 0030164 0 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/expected-output/missing-data 0000664 0000000 0000000 00000000575 14024143525 0027140 0 ustar 00root root 0000000 0000000 ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
aws-ec2-instance-connect-config-1.1.14/unit-test/expected-output/mixed 0000664 0000000 0000000 00000002167 14024143525 0025665 0 ustar 00root root 0000000 0000000 ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
aws-ec2-instance-connect-config-1.1.14/unit-test/expected-output/valid-key 0000664 0000000 0000000 00000000575 14024143525 0026445 0 ustar 00root root 0000000 0000000 ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
aws-ec2-instance-connect-config-1.1.14/unit-test/input/ 0000775 0000000 0000000 00000000000 14024143525 0022626 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/input/direct/ 0000775 0000000 0000000 00000000000 14024143525 0024100 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/input/direct/empty 0000664 0000000 0000000 00000000000 14024143525 0025147 0 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/input/direct/invalid-signature 0000664 0000000 0000000 00000001035 14024143525 0027447 0 ustar 00root root 0000000 0000000 #Timestamp=2000000000
#Instance=i-abcd1234
#Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
this is not a valid signature
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/ 0000775 0000000 0000000 00000000000 14024143525 0024442 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/different-fingerprint/ 0000775 0000000 0000000 00000000000 14024143525 0030735 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/different-fingerprint/1 0000664 0000000 0000000 00000000777 14024143525 0031033 0 ustar 00root root 0000000 0000000 #Timestamp=2000000000
#Instance=i-abcd1234
#Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDIw1S08VWxugMRmPrMOCLbC/0oaOCvpYrzJBA9vQ2Mx68SwWb9Dt5TJ0c8/mIr5R/riHqUn1WxWuxpESbfT2wFd8wVDlp+sIElDCfVvJOY8O9KJL9OOeP8y+mnxAy9ZK2CnGH49P8fHlcPFs9xQGXB48rU2WY73KMGjg1COVdFZHiFNociNAKtpsrPuxK8HZ8pcRrmVFJHl8sgvH8/n8al+DFFebCyE2HIU5kQndWSMoYuBiNhlYDdte7HTxutyzFzawYHfObVoZnjQcIy9A66Zaf8qBt7vQn0LCxJ3FtTDwY+S9UTdenZ3G+Rq/mIB6Tmh2YAeVao72O7+ngEnAsX
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/expired-timestamp/ 0000775 0000000 0000000 00000000000 14024143525 0030103 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/expired-timestamp/1 0000664 0000000 0000000 00000000777 14024143525 0030201 0 ustar 00root root 0000000 0000000 #Timestamp=0000000000
#Instance=i-abcd1234
#Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/invalid-instance/ 0000775 0000000 0000000 00000000000 14024143525 0027672 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/invalid-instance/1 0000664 0000000 0000000 00000000777 14024143525 0027770 0 ustar 00root root 0000000 0000000 #Timestamp=2000000000
#Instance=i-mismatch
#Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/missing-data/ 0000775 0000000 0000000 00000000000 14024143525 0027022 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/missing-data/1 0000664 0000000 0000000 00000000751 14024143525 0027110 0 ustar 00root root 0000000 0000000 #Instance=i-abcd1234
#Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/missing-data/2 0000664 0000000 0000000 00000000752 14024143525 0027112 0 ustar 00root root 0000000 0000000 #Timestamp=2000000000
#Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/missing-data/3 0000664 0000000 0000000 00000000650 14024143525 0027110 0 ustar 00root root 0000000 0000000 #Timestamp=2000000000
#Instance=i-abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/missing-data/4 0000664 0000000 0000000 00000000202 14024143525 0027102 0 ustar 00root root 0000000 0000000 #Timestamp=2000000000
#Instance=i-abcd1234
#Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/mixed/ 0000775 0000000 0000000 00000000000 14024143525 0025550 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/mixed/1 0000664 0000000 0000000 00000000777 14024143525 0025646 0 ustar 00root root 0000000 0000000 #Timestamp=0000000000
#Instance=i-abcd1234
#Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/mixed/2 0000664 0000000 0000000 00000000777 14024143525 0025647 0 ustar 00root root 0000000 0000000 #Timestamp=2000000000
#Instance=i-abcd1234
#Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/mixed/3 0000664 0000000 0000000 00000000777 14024143525 0025650 0 ustar 00root root 0000000 0000000 #Timestamp=2000000000
#Instance=i-mismatch
#Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/mixed/4 0000664 0000000 0000000 00000000777 14024143525 0025651 0 ustar 00root root 0000000 0000000 #Timestamp=2000000000
#Instance=i-abcd1234
#Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDIw1S08VWxugMRmPrMOCLbC/0oaOCvpYrzJBA9vQ2Mx68SwWb9Dt5TJ0c8/mIr5R/riHqUn1WxWuxpESbfT2wFd8wVDlp+sIElDCfVvJOY8O9KJL9OOeP8y+mnxAy9ZK2CnGH49P8fHlcPFs9xQGXB48rU2WY73KMGjg1COVdFZHiFNociNAKtpsrPuxK8HZ8pcRrmVFJHl8sgvH8/n8al+DFFebCyE2HIU5kQndWSMoYuBiNhlYDdte7HTxutyzFzawYHfObVoZnjQcIy9A66Zaf8qBt7vQn0LCxJ3FtTDwY+S9UTdenZ3G+Rq/mIB6Tmh2YAeVao72O7+ngEnAsX
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/mixed/5 0000664 0000000 0000000 00000000777 14024143525 0025652 0 ustar 00root root 0000000 0000000 #Timestamp=2000000000
#Instance=i-abcd1234
#Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/mixed/6 0000664 0000000 0000000 00000000747 14024143525 0025650 0 ustar 00root root 0000000 0000000 #Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR ec2-user@localhost
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/mixed/7 0000664 0000000 0000000 00000000777 14024143525 0025654 0 ustar 00root root 0000000 0000000 #Timestamp=2000000000
#Instance=i-abcd1234
#Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR
aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/valid-key/ 0000775 0000000 0000000 00000000000 14024143525 0026327 5 ustar 00root root 0000000 0000000 aws-ec2-instance-connect-config-1.1.14/unit-test/input/unsigned/valid-key/1 0000664 0000000 0000000 00000000777 14024143525 0026425 0 ustar 00root root 0000000 0000000 #Timestamp=2000000000
#Instance=i-abcd1234
#Caller=arn:aws:iam::123412341234:role/myrole
#Request=1234abcd-1234-abcd-1234abcd1234
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDAQmefSRJyiAUSlICBKAO+4heV1kkA46PQm5ZQVxxhv7pF1yWWLhgFJ9IG9qmeeKIQ3bzKBzGv5UHSeJbuRfwY6ZtKynBfjzN1WRuYY2oaDjlh2vzK5WgvVttUJk8oAYcZM2h+aXpJtlWV95yqaTSD4XcuWOg3E3KCTcK2Xf/BaB4IN/pJF1SyuLg5ygWh0dKi4X+tH81aHcEg8pWfDLFkdKUF0d6GwIi+iCJxfb5bubY3/+0qYc0IqWOxa4vf6ggW7yI5m3mOX0kRuOAPEY/6fe4KfcGqLZvraKe1ZLYMgQUKuawhpPzooVeI/EtI3gtFDC0b8YAPjA2CUDc/3APR