Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
117 changes: 77 additions & 40 deletions attestation.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package attestation

import (
"encoding/asn1"
"fmt"
)

// OIDKeyAttestationExtension is the key attestation extension.
Expand All @@ -10,7 +11,7 @@ var OIDKeyAttestationExtension = asn1.ObjectIdentifier{1, 3, 6, 1, 4, 1, 11129,
// keyDescription reflects the ASN.1 data structure for KeyDescription.
//
// keyDescription ::= SEQUENCE {
// attestationVersion INTEGER, # KM2 value is 1. KM3 value is 2. KM4 value is 3.
// attestationVersion INTEGER, # Keymaster 2.0 = 1, 3.0 = 2, 4.0 = 3, 4.1 = 4; KeyMint 1.0 = 100, 2.0 = 200, 3.0 = 300, 4.0 = 400, 5.0 = 500.
// attestationSecurityLevel SecurityLevel,
// keymasterVersion INTEGER,
// keymasterSecurityLevel SecurityLevel,
Expand Down Expand Up @@ -67,8 +68,12 @@ func (v AttestationVersion) String() string {
return "KeyMint version 2.0"
case KAKeyMintVersion3:
return "KeyMint version 3.0"
case KAKeyMintVersion4:
return "KeyMint version 4.0"
case KAKeyMintVersion5:
return "KeyMint version 5.0"
default:
return ""
return fmt.Sprintf("unknown attestation version (%d)", uint(v))
}
}

Expand All @@ -80,6 +85,8 @@ const (
KAKeyMintVersion1 = 100 // KeyMint version 1.0
KAKeyMintVersion2 = 200 // KeyMint version 2.0
KAKeyMintVersion3 = 300 // KeyMint version 3.0
KAKeyMintVersion4 = 400 // KeyMint version 4.0
KAKeyMintVersion5 = 500 // KeyMint version 5.0
)

// KeymasterVersion is the version of the Keymaster or KeyMint hardware abstraction layer.
Expand All @@ -106,8 +113,12 @@ func (v KeymasterVersion) String() string {
return "KeyMint version 2.0"
case KeyMintVersion3:
return "KeyMint version 3.0"
case KeyMintVersion4:
return "KeyMint version 4.0"
case KeyMintVersion5:
return "KeyMint version 5.0"
default:
return ""
return fmt.Sprintf("unknown keymaster version (%d)", uint(v))
}
}

Expand All @@ -121,6 +132,8 @@ const (
KeyMintVersion1 = 100 // KeyMint version 1.0
KeyMintVersion2 = 200 // KeyMint version 2.0
KeyMintVersion3 = 300 // KeyMint version 3.0
KeyMintVersion4 = 400 // KeyMint version 4.0
KeyMintVersion5 = 500 // KeyMint version 5.0
)

// SecurityLevel reflects the ASN.1 data structure for SecurityLevel.
Expand Down Expand Up @@ -157,14 +170,19 @@ const (
// purpose [1] EXPLICIT SET OF INTEGER OPTIONAL,
// algorithm [2] EXPLICIT INTEGER OPTIONAL,
// keySize [3] EXPLICIT INTEGER OPTIONAL.
// blockMode [4] EXPLICIT SET OF INTEGER OPTIONAL,
// digest [5] EXPLICIT SET OF INTEGER OPTIONAL,
// padding [6] EXPLICIT SET OF INTEGER OPTIONAL,
// ecCurve [10] EXPLICIT INTEGER OPTIONAL,
// mlDsaVariant [11] EXPLICIT INTEGER OPTIONAL, # KM5
// rsaPublicExponent [200] EXPLICIT INTEGER OPTIONAL,
// mgfDigest [203] EXPLICIT SET OF INTEGER OPTIONAL,
// rollbackResistance [303] EXPLICIT NULL OPTIONAL, # KM4
// earlyBootOnly [305] EXPLICIT NULL OPTIONAL, # KM4
// activeDateTime [400] EXPLICIT INTEGER OPTIONAL
// originationExpireDateTime [401] EXPLICIT INTEGER OPTIONAL
// usageExpireDateTime [402] EXPLICIT INTEGER OPTIONAL
// usageCountLimit [405] EXPLICIT INTEGER OPTIONAL, # KM4
// noAuthRequired [503] EXPLICIT NULL OPTIONAL,
// userAuthType [504] EXPLICIT INTEGER OPTIONAL,
// authTimeout [505] EXPLICIT INTEGER OPTIONAL,
Expand All @@ -191,46 +209,57 @@ const (
// attestationIdModel [717] EXPLICIT OCTET_STRING OPTIONAL, # KM3
// vendorPatchLevel [718] EXPLICIT INTEGER OPTIONAL, # KM4
// bootPatchLevel [719] EXPLICIT INTEGER OPTIONAL, # KM4
// deviceUniqueAttestation [720] EXPLICIT NULL OPTIONAL, # KM4
// attestationIdSecondImei [723] EXPLICIT OCTET_STRING OPTIONAL, # KM3
// moduleHash [724] EXPLICIT OCTET_STRING OPTIONAL, # KM4
// }
type authorizationList struct {
Raw asn1.RawContent
Purpose []int32 `asn1:"explicit,optional,omitempty,set,tag:1"` // [1] EXPLICIT SET OF INTEGER OPTIONAL,
Algorithm asn1.RawValue `asn1:"explicit,optional,tag:2"` // [2] EXPLICIT INTEGER OPTIONAL,
KeySize asn1.RawValue `asn1:"explicit,optional,tag:3"` // [3] EXPLICIT INTEGER OPTIONAL.
Digest []int `asn1:"explicit,optional,omitempty,set,tag:5"` // [5] EXPLICIT SET OF INTEGER OPTIONAL,
Padding []int `asn1:"explicit,optional,omitempty,set,tag:6"` // [6] EXPLICIT SET OF INTEGER OPTIONAL,
EcCurve asn1.RawValue `asn1:"explicit,optional,tag:10"` // [10] EXPLICIT INTEGER OPTIONAL,
RsaPublicExponent asn1.RawValue `asn1:"explicit,optional,tag:200"` // [200] EXPLICIT INTEGER OPTIONAL,
RollbackResistance asn1.RawValue `asn1:"explicit,optional,tag:303"` // [303] EXPLICIT NULL OPTIONAL, # KM4
ActiveDateTime asn1.RawValue `asn1:"explicit,optional,tag:400"` // [400] EXPLICIT INTEGER OPTIONAL
OriginationExpireDateTime asn1.RawValue `asn1:"explicit,optional,tag:401"` // [401] EXPLICIT INTEGER OPTIONAL
UsageExpireDateTime asn1.RawValue `asn1:"explicit,optional,tag:402"` // [402] EXPLICIT INTEGER OPTIONAL
NoAuthRequired asn1.RawValue `asn1:"explicit,optional,tag:503"` // [503] EXPLICIT NULL OPTIONAL,
UserAuthType asn1.RawValue `asn1:"explicit,optional,tag:504"` // [504] EXPLICIT INTEGER OPTIONAL,
AuthTimeout asn1.RawValue `asn1:"explicit,optional,tag:505"` // [505] EXPLICIT INTEGER OPTIONAL,
AllowWhileOnBody asn1.RawValue `asn1:"explicit,optional,tag:506"` // [506] EXPLICIT NULL OPTIONAL,
TrustedUserPresenceRequired asn1.RawValue `asn1:"explicit,optional,tag:507"` // [507] EXPLICIT NULL OPTIONAL, # KM4
TrustedConfirmationRequired asn1.RawValue `asn1:"explicit,optional,tag:508"` // [508] EXPLICIT NULL OPTIONAL, # KM4
UnlockedDeviceRequired asn1.RawValue `asn1:"explicit,optional,tag:509"` // [509] EXPLICIT NULL OPTIONAL, # KM4
AllApplications asn1.RawValue `asn1:"explicit,optional,tag:600"` // [600] EXPLICIT NULL OPTIONAL,
ApplicationId []byte `asn1:"explicit,optional,omitempty,tag:601"` // [601] EXPLICIT OCTET_STRING OPTIONAL,
CreationDateTime asn1.RawValue `asn1:"explicit,optional,tag:701"` // [701] EXPLICIT INTEGER OPTIONAL,
Origin asn1.RawValue `asn1:"explicit,optional,tag:702"` // [702] EXPLICIT INTEGER OPTIONAL,
RollbackResistant asn1.RawValue `asn1:"explicit,optional,tag:703"` // [703] EXPLICIT NULL OPTIONAL, # KM2 and KM3 only.
RootOfTrust asn1.RawValue `asn1:"explicit,optional,tag:704"` // [704] EXPLICIT RootOfTrust OPTIONAL,
OsVersion asn1.RawValue `asn1:"explicit,optional,tag:705"` // [705] EXPLICIT INTEGER OPTIONAL,
OsPatchLevel asn1.RawValue `asn1:"explicit,optional,tag:706"` // [706] EXPLICIT INTEGER OPTIONAL,
AttestationApplicationId asn1.RawContent `asn1:"explicit,optional,tag:709"` // [709] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdBrand []byte `asn1:"explicit,optional,omitempty,tag:710"` // [710] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdDevice []byte `asn1:"explicit,optional,omitempty,tag:711"` // [711] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdProduct []byte `asn1:"explicit,optional,omitempty,tag:712"` // [712] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdSerial []byte `asn1:"explicit,optional,omitempty,tag:713"` // [713] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdImei []byte `asn1:"explicit,optional,omitempty,tag:714"` // [714] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdMeid []byte `asn1:"explicit,optional,omitempty,tag:715"` // [715] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdManufacturer []byte `asn1:"explicit,optional,omitempty,tag:716"` // [716] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdModel []byte `asn1:"explicit,optional,omitempty,tag:717"` // [717] EXPLICIT OCTET_STRING OPTIONAL, # KM3
VendorPatchLevel asn1.RawValue `asn1:"explicit,optional,tag:718"` // [718] EXPLICIT INTEGER OPTIONAL, # KM4
BootPatchLevel asn1.RawValue `asn1:"explicit,optional,tag:719"` // [719] EXPLICIT INTEGER OPTIONAL, # KM4
Purpose []int32 `asn1:"explicit,optional,omitempty,set,tag:1"` // [1] EXPLICIT SET OF INTEGER OPTIONAL,
Algorithm asn1.RawValue `asn1:"explicit,optional,tag:2"` // [2] EXPLICIT INTEGER OPTIONAL,
KeySize asn1.RawValue `asn1:"explicit,optional,tag:3"` // [3] EXPLICIT INTEGER OPTIONAL.
BlockMode []int `asn1:"explicit,optional,omitempty,set,tag:4"` // [4] EXPLICIT SET OF INTEGER OPTIONAL,
Digest []int `asn1:"explicit,optional,omitempty,set,tag:5"` // [5] EXPLICIT SET OF INTEGER OPTIONAL,
Padding []int `asn1:"explicit,optional,omitempty,set,tag:6"` // [6] EXPLICIT SET OF INTEGER OPTIONAL,
EcCurve asn1.RawValue `asn1:"explicit,optional,tag:10"` // [10] EXPLICIT INTEGER OPTIONAL,
MlDsaVariant asn1.RawValue `asn1:"explicit,optional,tag:11"` // [11] EXPLICIT INTEGER OPTIONAL, # KM5
RsaPublicExponent asn1.RawValue `asn1:"explicit,optional,tag:200"` // [200] EXPLICIT INTEGER OPTIONAL,
MgfDigest []int `asn1:"explicit,optional,omitempty,set,tag:203"` // [203] EXPLICIT SET OF INTEGER OPTIONAL,
RollbackResistance asn1.RawValue `asn1:"explicit,optional,tag:303"` // [303] EXPLICIT NULL OPTIONAL, # KM4
EarlyBootOnly asn1.RawValue `asn1:"explicit,optional,tag:305"` // [305] EXPLICIT NULL OPTIONAL, # KM4
ActiveDateTime asn1.RawValue `asn1:"explicit,optional,tag:400"` // [400] EXPLICIT INTEGER OPTIONAL
OriginationExpireDateTime asn1.RawValue `asn1:"explicit,optional,tag:401"` // [401] EXPLICIT INTEGER OPTIONAL
UsageExpireDateTime asn1.RawValue `asn1:"explicit,optional,tag:402"` // [402] EXPLICIT INTEGER OPTIONAL
UsageCountLimit asn1.RawValue `asn1:"explicit,optional,tag:405"` // [405] EXPLICIT INTEGER OPTIONAL, # KM4
NoAuthRequired asn1.RawValue `asn1:"explicit,optional,tag:503"` // [503] EXPLICIT NULL OPTIONAL,
UserAuthType asn1.RawValue `asn1:"explicit,optional,tag:504"` // [504] EXPLICIT INTEGER OPTIONAL,
AuthTimeout asn1.RawValue `asn1:"explicit,optional,tag:505"` // [505] EXPLICIT INTEGER OPTIONAL,
AllowWhileOnBody asn1.RawValue `asn1:"explicit,optional,tag:506"` // [506] EXPLICIT NULL OPTIONAL,
TrustedUserPresenceRequired asn1.RawValue `asn1:"explicit,optional,tag:507"` // [507] EXPLICIT NULL OPTIONAL, # KM4
TrustedConfirmationRequired asn1.RawValue `asn1:"explicit,optional,tag:508"` // [508] EXPLICIT NULL OPTIONAL, # KM4
UnlockedDeviceRequired asn1.RawValue `asn1:"explicit,optional,tag:509"` // [509] EXPLICIT NULL OPTIONAL, # KM4
AllApplications asn1.RawValue `asn1:"explicit,optional,tag:600"` // [600] EXPLICIT NULL OPTIONAL,
ApplicationId []byte `asn1:"explicit,optional,omitempty,tag:601"` // [601] EXPLICIT OCTET_STRING OPTIONAL,
CreationDateTime asn1.RawValue `asn1:"explicit,optional,tag:701"` // [701] EXPLICIT INTEGER OPTIONAL,
Origin asn1.RawValue `asn1:"explicit,optional,tag:702"` // [702] EXPLICIT INTEGER OPTIONAL,
RollbackResistant asn1.RawValue `asn1:"explicit,optional,tag:703"` // [703] EXPLICIT NULL OPTIONAL, # KM2 and KM3 only.
RootOfTrust asn1.RawValue `asn1:"explicit,optional,tag:704"` // [704] EXPLICIT RootOfTrust OPTIONAL,
OsVersion asn1.RawValue `asn1:"explicit,optional,tag:705"` // [705] EXPLICIT INTEGER OPTIONAL,
OsPatchLevel asn1.RawValue `asn1:"explicit,optional,tag:706"` // [706] EXPLICIT INTEGER OPTIONAL,
AttestationApplicationId asn1.RawContent `asn1:"explicit,optional,tag:709"` // [709] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdBrand []byte `asn1:"explicit,optional,omitempty,tag:710"` // [710] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdDevice []byte `asn1:"explicit,optional,omitempty,tag:711"` // [711] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdProduct []byte `asn1:"explicit,optional,omitempty,tag:712"` // [712] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdSerial []byte `asn1:"explicit,optional,omitempty,tag:713"` // [713] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdImei []byte `asn1:"explicit,optional,omitempty,tag:714"` // [714] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdMeid []byte `asn1:"explicit,optional,omitempty,tag:715"` // [715] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdManufacturer []byte `asn1:"explicit,optional,omitempty,tag:716"` // [716] EXPLICIT OCTET_STRING OPTIONAL, # KM3
AttestationIdModel []byte `asn1:"explicit,optional,omitempty,tag:717"` // [717] EXPLICIT OCTET_STRING OPTIONAL, # KM3
VendorPatchLevel asn1.RawValue `asn1:"explicit,optional,tag:718"` // [718] EXPLICIT INTEGER OPTIONAL, # KM4
BootPatchLevel asn1.RawValue `asn1:"explicit,optional,tag:719"` // [719] EXPLICIT INTEGER OPTIONAL, # KM4
DeviceUniqueAttestation asn1.RawValue `asn1:"explicit,optional,tag:720"` // [720] EXPLICIT NULL OPTIONAL, # KM4
AttestationIdSecondImei []byte `asn1:"explicit,optional,omitempty,tag:723"` // [723] EXPLICIT OCTET_STRING OPTIONAL, # KM3
ModuleHash []byte `asn1:"explicit,optional,omitempty,tag:724"` // [724] EXPLICIT OCTET_STRING OPTIONAL, # KM4
}

// AuthorizationList reflects the key pair's properties as defined in the Keymaster or KeyMint
Expand All @@ -240,14 +269,19 @@ type AuthorizationList struct {
Purpose []KeyPurpose
Algorithm *Algorithm
KeySize *int
BlockMode []BlockMode
Digest []Digest
Padding []PaddingMode
EcCurve *EcCurve
MlDsaVariant *int
RsaPublicExponent *int64
MgfDigest []Digest
RollbackResistance bool
EarlyBootOnly bool
ActiveDateTime *int64
OriginationExpireDateTime *int
UsageExpireDateTime *int64
UsageCountLimit *int
NoAuthRequired bool
UserAuthType *HardwareAuthenticatorType
AuthTimeout *int32
Expand All @@ -274,6 +308,9 @@ type AuthorizationList struct {
AttestationIdModel []byte
VendorPatchLevel *int
BootPatchLevel *int
DeviceUniqueAttestation bool
AttestationIdSecondImei []byte
ModuleHash []byte
}

// RootOfTrust reflects the ASN.1 data structure for RootOfTrust.
Expand Down
24 changes: 24 additions & 0 deletions cmd/attestation-cli/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -258,21 +258,33 @@ func printAuthorizationList(printer *printer, in attestation.AuthorizationList)
if v, ok := isNotEmpty(in.KeySize); ok {
printer.Printf("KeySize: %v\n", v)
}
if _, ok := isNotEmpty(in.BlockMode); ok {
printer.Printf("BlockMode: %v\n", in.BlockMode)
}
if _, ok := isNotEmpty(in.Digest); ok {
printer.Printf("Digest: %v\n", in.Digest)
}
if _, ok := isNotEmpty(in.MgfDigest); ok {
printer.Printf("MgfDigest: %v\n", in.MgfDigest)
}
if _, ok := isNotEmpty(in.Padding); ok {
printer.Printf("Padding: %v\n", in.Padding)
}
if v, ok := isNotEmpty(in.EcCurve); ok {
printer.Printf("EcCurve: %v (%d)\n", v, v)
}
if v, ok := isNotEmpty(in.MlDsaVariant); ok {
printer.Printf("MlDsaVariant: %v\n", v)
}
if v, ok := isNotEmpty(in.RsaPublicExponent); ok {
printer.Printf("RsaPublicExponent: %v\n", v)
}
if _, ok := isNotEmpty(in.RollbackResistance); ok {
printer.Printf("RollbackResistance: %t\n", in.RollbackResistance)
}
if _, ok := isNotEmpty(in.EarlyBootOnly); ok {
printer.Printf("EarlyBootOnly: %t\n", in.EarlyBootOnly)
}
if _, ok := isNotEmpty(in.ActiveDateTime); ok {
printer.Printf("ActiveDateTime: %v\n", in.ActiveDateTime)
}
Expand All @@ -282,6 +294,9 @@ func printAuthorizationList(printer *printer, in attestation.AuthorizationList)
if _, ok := isNotEmpty(in.UsageExpireDateTime); ok {
printer.Printf("UsageExpireDateTime: %v\n", in.UsageExpireDateTime)
}
if v, ok := isNotEmpty(in.UsageCountLimit); ok {
printer.Printf("UsageCountLimit: %v\n", v)
}
if _, ok := isNotEmpty(in.NoAuthRequired); ok {
printer.Printf("NoAuthRequired: %t\n", in.NoAuthRequired)
}
Expand Down Expand Up @@ -366,6 +381,15 @@ func printAuthorizationList(printer *printer, in attestation.AuthorizationList)
if v, ok := isNotEmpty(in.BootPatchLevel); ok {
printer.Printf("BootPatchLevel: %v\n", v)
}
if _, ok := isNotEmpty(in.DeviceUniqueAttestation); ok {
printer.Printf("DeviceUniqueAttestation: %t\n", in.DeviceUniqueAttestation)
}
if _, ok := isNotEmpty(in.AttestationIdSecondImei); ok {
printer.Printf("AttestationIdSecondImei: %s\n", in.AttestationIdSecondImei)
}
if _, ok := isNotEmpty(in.ModuleHash); ok {
printer.Printf("ModuleHash: %x\n", in.ModuleHash)
}
}

func printRootOfTrust(printer *printer, rot *attestation.RootOfTrust) {
Expand Down
Loading