Sunday, October 4, 2026

How Autonomous AI Database Serverless on Oracle Database@AWS Uses Your AWS KMS Key for TDE

 

Valid as of October 4, 2026. Oracle Database@AWS is a relatively new service that's growing fast, with new features and improvements landing regularly. Some steps, screens, or limits may have been improved since this was written, so check the latest Oracle and AWS docs for the newest details.

Autonomous AI Database Serverless (ADB-S) on Oracle Database@AWS can protect its TDE master encryption key with an AWS KMS customer managed key in your own AWS account (ODB@AWS: Protect ADB-S).

In my previous post on Exadata, Exascale, and Autonomous Dedicated, the trick was OIDC federation: your own VM cluster proves who it is with a token from your OCI identity domain.

ADB-S works differently. You don't have a VM cluster. Oracle runs the infrastructure, so there's no resource of yours to carry an identity. ADB-S uses the classic AWS pattern for letting a SaaS vendor into your account instead: cross-account role assumption with an external ID.


The short version

  1. Oracle has an AWS role. Each ADB-S instance shows an "OCI trusted service account role ARN" in the AWS console. That role lives in an Oracle-owned AWS account.
  2. You create a role that trusts Oracle's account. It's an IAM role in your account whose trust policy allows Oracle's account to assume it, but only with the right external ID (your tenancy, compartment, or database OCID).
  3. Your KMS key policy lets your role use the key.
  4. At runtime, the service, acting as Oracle's role, calls STS AssumeRole on your role with the external ID, gets temporary credentials, and calls KMS to unwrap the master key.

No access keys are exchanged. You can revoke access at any time by changing your role's trust policy or the key policy.


Who trusts whom

PieceWhereWhat it does
OCI trusted service account roleOracle's AWS accountThe identity Oracle's service uses in AWS. You only need its ARN. Get it from ADB-S → Encryption → Edit → Customer managed key.
IAM policyYour AWS accountLets your role run kms:ListKeys and kms:ListAliases.
IAM roleYour AWS accountTrust policy: "Another AWS account" set to Oracle's account ID (taken from the role ARN), with Require external ID on. You can also restrict it to Oracle's exact role with aws:PrincipalArn.
KMS customer managed keyYour AWS accountSymmetric encrypt/decrypt key, backed by KMS or CloudHSM. Your role is added as a key user.
ODB network integrationsAWS AZSTS and AWS KMS service integrations must be turned on, the same as for Exadata.

The external ID: why it matters

Oracle's role serves many customers. Without an external ID, anyone who knew your role ARN could, in principle, configure their own ADB-S to point at it and have Oracle's role assume it for them. This is AWS's well-known confused deputy problem.

The external ID closes that gap. Your role only accepts the assume request when Oracle passes your OCID. You choose the scope in the console:

External ID typeWho can use your role
DATABASE_OCIDOnly that one ADB-S database. This is the tightest scope.
COMPARTMENT_OCIDAny ADB-S in that compartment
TENANCY_OCIDAny ADB-S in your tenancy. Oracle's walkthrough uses this one.

Pick the narrowest scope that fits how many databases share the role.


Setup, step by step

Following the ODB@AWS ADB-S page:

StepWhereWhat you do
1. NetworkAWS console → ODB networksTurn on STS and AWS KMS service integrations
2. Get Oracle's role ARNAWS console → ADB-S → Encryption → Edit → Customer managed keyCopy the OCI trusted service account role ARN. Also note your database, compartment, or tenancy OCID for the external ID.
3. IAM policyIAM → PoliciesAllow kms:ListKeys and kms:ListAliases
4. IAM roleIAM → Roles → Another AWS accountEnter Oracle's account ID, turn on Require external ID, and attach the policy from step 3. Optionally add an aws:PrincipalArn condition.
5. KMS keyKMS → Customer managed keysCreate a symmetric encrypt/decrypt key and add your role as a key user
6. Switch the databaseAWS console → ADB-S → Encryption → EditChoose Customer managed key, then enter the key ARN or ID, your role ARN, and the external ID type

After saving, the Key type changes to AWS KMS Key. Oracle notes that the change can take 30 minutes or more to show up in the AWS console.

What the role's trust policy looks like

This is a sketch based on the documented settings. Use the real ARN and OCID from your console:

{
  "Version": "2012-10-17",
  "Statement": [{
    "Effect": "Allow",
    "Principal": { "AWS": "arn:aws:iam::<oracle-account-id>:root" },
    "Action": "sts:AssumeRole",
    "Condition": {
      "StringEquals": { "sts:ExternalId": "<tenancy-or-compartment-or-database-ocid>" },
      "ArnLike":      { "aws:PrincipalArn": "<oci-trusted-service-account-role-arn>" }
    }
  }]
}
  • Principal plus sts:ExternalId is what the console wizard builds when you choose "Another AWS account" with "Require external ID".
  • The ArnLike / aws:PrincipalArn condition is the optional extra step Oracle mentions. It narrows the trust from "Oracle's whole AWS account" to "Oracle's specific ADB-S role". I'd add it.

What happens at runtime

  1. The service calls sts:AssumeRole, acting as Oracle's trusted role. It passes your role ARN and the external ID.
  2. STS checks your role's trust policy: is the caller Oracle's account or role, and does the external ID match?
  3. STS returns temporary credentials for your role.
  4. The service calls kms:Decrypt with those credentials to unwrap the TDE master key.
  5. KMS checks the key policy and logs the call in CloudTrail under your role's assumed-role session.
  6. The unwrapped master key is used in memory to unlock the tablespace keys. Your data never goes to KMS.

Oracle doesn't document the internal call sequence or how the service gets credentials for its own role. The flow above is the standard AWS cross-account pattern that the documented setup implies.


How this differs from Exadata, Exascale, and ADB-D


ExaDB-D / ExaDB-XS / ADB-DADB-S
Who proves identity to AWSYour VM cluster, through your OCI identity domain (OIDC)Oracle's AWS role, on behalf of the service
AWS-side setupCloudFormation creates an OIDC provider and a WebIdentity roleYou create an IAM policy and a role that trusts Oracle's account
STS callAssumeRoleWithWebIdentityAssumeRole with sts:ExternalId
OCI-side setupIdentity connector, registered AWS key, OCI policyNone; it's all set from the AWS console
ScopingRole limited to one VM cluster OCID (optional)External ID = database, compartment, or tenancy OCID
Where you rotateOracle console → Rotate (new MKID context)AWS KMS → Rotate now (key material rotation), or switch to another key
Cross-region with AWS KMSDocumented with Multi-Region keysNot supported (see below)

Rotation

The ODB@AWS page rotates the key on the AWS side: KMS → your key → Key material and rotations → Rotate now.

  • That rotates the KMS key's backing material while the key ARN stays the same.
  • AWS limits on-demand rotation to 25 times per key.
  • You can also turn on KMS automatic rotation.

The other option is to switch the database to a different KMS key in Edit Encryption. The OCI ADB-S docs treat choosing a different key as rotating the TDE master key (ADB-S AWS KMS docs). On the same ODB@AWS page, the OCI Vault section says you can't switch to a different customer-managed key more than twice in 24 hours. I'd assume the same throttle applies to AWS KMS keys, but that isn't stated.


Limitations and gotchas (as of today)

  • No cross-region. AWS KMS isn't supported for cross-region Autonomous Data Guard standbys (ADB-S docs). The ODB@AWS page also says restoring to a different region isn't supported with AWS customer managed keys. If cross-region DR is a must, check this before you choose AWS KMS.
  • Enable after provisioning. The OCI ADB-S docs say AWS KMS can't be chosen during creation. You create the database with an Oracle-managed key, then switch.
  • Commercial regions only.
  • Keep the trust chain intact. If you delete or disable the key, remove your role from the key policy, change the role's trust policy, or change the external ID, the database loses access to its master key. Treat all four as a kill switch, deliberately or by accident.
  • Use the narrowest external ID you can. DATABASE_OCID means one role per database. TENANCY_OCID is simpler but lets any ADB-S in your tenancy use the role.
  • Watch CloudTrail. Calls show up as your role's assumed-role session, so you can alert on unexpected Decrypt failures or use.

Sources

Content from Oracle and AWS documentation was paraphrased for this post. The diagrams are my own and show my understanding of the documented setup. The runtime call order and the trust policy JSON are inferred, not taken from Oracle.

Valid as of October 4, 2026. Oracle Database@AWS is adding capabilities quickly, so check the latest documentation for what's new.

No comments:

Post a Comment