[AWS IoT Core] CA証明書をSNI_ONLYモードで登録してみました

2022.07.17

1 はじめに

CX事業本部 デリバリー部の平内(SIN)です。

AWS IoT Coreでは、初回接続時に自動的に証明書をプロビジョニングできるJust-in-Time Provisioning (JITP)Just-in-Time Registration (JITR) が利用可能ですが、この機能を利用するためには、予めCA証明書の登録必要です。

これまで、CA証明書の登録には、「検証証明書」が必要でした。

「検証証明書」は、CAの所有を証明するもので、作成のためにCAの秘密鍵が必要になります。 しかし、開発者とCA管理者が同一でない場合、秘密鍵を使用する作業は、ちょっと困難な場合があったと思います。

今回、「検証証明書」なしで、CA証明書を登録できる手段が提供されました。
AWS IoT Core が、異なる AWS アカウントへの IoT デバイスのプロビジョニングと認証局の登録を簡素化して一般提供を開始
Simplify multi-account device provisioning and certificate authority registration when using AWS IoT Core

CAの登録モードは、以下の2つとなってます。

  • DEFAULT:検証証明書あり
  • SNI_ONLY:検証証明書なし

また、これまで、別のアカウントであっても、同一リージョンで同一のCA証明書を登録することができず、複数アカウント(ITG,STG,PRDなど)でシステム構築する場合などに、一定の制約となっていましたが、SNI_ONLYであれば、この制限もなくなっています。

今回は、SNI_ONLYモードでのCA証明書の登録手順を確認してみました。

2 SNI_ONLYモードでのCA証明書登録

作業は、以下の通りです。

  • 構成ファイルを作成します。

rootca_openssl.conf

[ v3_ca ]
basicConstraints = CA:TRUE
  • CA用の秘密鍵を作成します
% openssl genrsa -out rootCA.key 2048
  • CA証明書を作成します
% openssl req -new -sha256 -key rootCA.key -nodes -out rootCA.csr
% openssl x509 -req -days 1024 -extfile rootCA_openssl.conf -extensions \
 v3_ca -in rootCA.csr -signkey rootCA.key -out rootCA.pem
  • CA証明書をSNI_ONLYモードで登録します
% aws iot register-ca-certificate --ca-certificate file://rootCA.pem --certificate-mode SNI_ONLY --set-as-active --allow-auto-registration --region ap-northeast-1
{
    "certificateArn": "arn:aws:iot:ap-northeast-1:xxxxxxxxxxxx:cacert/5e87xxxxxx3a6a",
    "certificateId": "5e87xxxxxx3a6a"
}
  • AWSコンソールから、登録されている証明書が確認できます

  • certificateModeが、SNI_ONLYとなっていることを確認できます
% aws iot describe-ca-certificate --region ap-northeast-1 --certificate-id 5e87xxxxxxxxxxx33a6a
{
    "certificateDescription": {
        "certificateArn": "arn:aws:iot:ap-northeast-1:xxxxxxxx:cacert/5e87xxxxx3a6a",
        "certificateId": "5e87xxxxxx3a6a",
        "status": "ACTIVE",
        "certificatePem": "-----BEGIN CERTIFICATE-----\n
        xxxxxxxxxxx
        \n-----END CERTIFICATE-----\n",
        "ownedBy": "xxxxxxxxxxxx",
        "creationDate": "2022-07-17T01:37:29.720000+09:00",
        "autoRegistrationStatus": "ENABLE",
        "lastModifiedDate": "2022-07-17T01:37:29.720000+09:00",
        "customerVersion": 1,
        "generationId": "2f73e1ad-5805-4e89-ad26-aaae9ea2e07a",
        "validity": {
            "notBefore": "2022-07-17T01:36:52+09:00",
            "notAfter": "2025-05-06T01:36:52+09:00"
        },
        "certificateMode": "SNI_ONLY"
    }
}

3 SNI_ONLYモードのCA証明書でJITR

続いて、登録したSNI_ONLYモードのCA証明書でJITRを試してみました。

作業は、以下のブログを参照させて頂きました。

  • デバイス用の秘密鍵を作成します
% openssl genrsa -out deviceCert.key 2048
  • デバイス用の証明書を作成します
% openssl req -new -key deviceCert.key -out deviceCert.csr
% openssl x509 -req -in deviceCert.csr -CA rootCA.pem -CAkey rootCA.key -CAcreateserial -out deviceCert.crt -days 365 -sha256
% cat deviceCert.crt rootCA.pem > deviceCertAndCACert.crt
  • mosquittoで接続(1度目失敗)
% mosquitto_pub --cafile root.cert --cert deviceCertAndCACert.crt --key deviceCert.key -h a10wed1626vai6-ats.iot.ap-northeast-1.amazonaws.com -p 8883 -q 1 -t foo/bar -i clientID --tls-version tlsv1.2 -m "Hello" -d
Client clientID sending CONNECT
Error: The connection was lost.
  • mosquittoで接続(2度目以降は成功)
% mosquitto_pub --cafile root.cert --cert deviceCertAndCACert.crt --key deviceCert.key -h a10wed1626vai6-ats.iot.ap-northeast-1.amazonaws.com -p 8883 -q 1 -t foo/bar -i clientID --tls-version tlsv1.2 -m "Hello" -d
Client clientID sending CONNECT
Client clientID received CONNACK (0)
Client clientID sending PUBLISH (d0, q1, r0, m1, 'foo/bar', ... (5 bytes))
Client clientID received PUBACK (Mid: 1, RC:0)
Client clientID sending DISCONNECT
  • AWS コンソールで、登録されている証明書を確認できます

  • 自動プロビジョニング されたデバイス用の証明書もcertificateModeが、SNI_ONLYとなっていることを確認できます
% aws iot describe-certificate --region ap-northeast-1 --certificate-id 9fd2aebdfe32ea570205f5219601031619fbc46f5d1508beb978037c9b8caaa5
{
    "certificateDescription": {
        "certificateArn": "arn:aws:iot:ap-northeast-1:xxxxxxxxxxxx:cert/9fd2xxxxcaaa5",
        "certificateId": "9fd2xxxxxxxcaaa5",
        "caCertificateId": "5e87xxxxxx33a6a",
        "status": "ACTIVE",
        "certificatePem": "-----BEGIN CERTIFICATE-----\n
        ==\n-----END CERTIFICATE-----\n",
        "ownedBy": "xxxxxxxxxxxx",
        "creationDate": "2022-07-17T02:05:53.626000+09:00",
        "lastModifiedDate": "2022-07-17T02:05:55.574000+09:00",
        "customerVersion": 2,
        "transferData": {},
        "generationId": "59dceea4-bcca-483a-a263-b325db1125a9",
        "validity": {
            "notBefore": "2022-07-17T01:57:41+09:00",
            "notAfter": "2023-07-17T01:57:41+09:00"
        },
        "certificateMode": "SNI_ONLY"
    }
}

4 別アカウントへの登録

上記で作成したCA証明書を、同一リージョンの別アカウントにSNI_ONLYモードで登録してみましたが、まったく問題なく登録できることを確認しました。

% aws iot register-ca-certificate --ca-certificate file://rootCA.pem --certificate-mode SNI_ONLY --set-as-active --allow-auto-registration --region ap-northeast-1
{
    "certificateArn": "arn:aws:iot:ap-northeast-1:yyyyyyyyyyyy:cacert/5e876xxxxxx33a6a",
    "certificateId": "5e87xxxxxx33a6a"
}

CA証明書IDは、証明書のHASHなので、どちらのアカウントでも同じとなります。  

5 最後に、

今回は、SNI_ONLYモードでのCA証明書の登録手順を確認してみました。

現在、AWSコンソール上では、SNI_ONLYモードでの登録は、できないようです。また、AWS CLIのバージョンが古い場合、対応されていないので注意が必要です。

% aws --v
aws-cli/2.4.21 Python/3.8.8 Darwin/19.6.0 exe/x86_64 prompt/off
% aws iot register-ca-certificate --ca-certificate file://rootCA.pem --certificate-mode SNI_ONLY --set-as-active --allow-auto-registration --region ap-northeast-1

aws: error: the following arguments are required: --verification-certificate