This is the multi-page printable view of this section. Click here to print.
Requests for Comments
1 - DSR-RFC-01 Device Registration
Device registration is performed by the user after previous authentication.
1. High Level Flow
- At first start, the
TrustClient
generates the app/device identity key material and a correspondingCertificate Signing Request
. - The
TrustClient
then triggers the attestation of the key material, device and app with the help of thePlatform Attestation Service
and receives attestation results. - To register the device for themself, the user signs a Device Registration Token, containing the app/device identity and attestation results and the
Certificate Signing Request
with their electronic health card (EF.C.CH.AUT.E256
). Then theTrustClient
sends the Device Registration Token to theDevice Management Service (GMS)
. - With the help of the
Platform Attestation Service
, theDevice Management Service (GMS)
verifies the received attestations and key material. - The
Device Management Service (GMS)
sends theCertificate Signing Request
to theGMS CA
which then issues aTrust Client Certificate
- Finally, the
Device Management Service (GMS)
stores the app/device identity key material with the corresponding user identity in its database. - The
Device Management Service (GMS)
sents theTrust Client Certificate
to theTrustClient
.
2. Flow Details
@startuml DSR-RFC-01 Main Flow
autonumber "<b>[00]"
skinparam defaultFontSize 10
skinparam defaultFontName Helvetica
skinparam DefaultMonospacedFontName Courier
skinparam lengthAdjust none
participant TrustClient
participant Smartcard
participant GMS
activate TrustClient
TrustClient -> GMS ++: get ""nonce""
note right
Regular TLS
Server auth only
end note
GMS -> GMS: generate ""nonce""\n store ""nonce""
GMS -> TrustClient: return ""nonce""
TrustClient -> TrustClient: derive nonces\n\t""nonce_keypair_mTLS = SHA256(nonce | 'KEYPAIR_MTLS')""\n\t""nonce_CSR_mTLS = SHA256(nonce | 'CSR_MTLS')""\n\t""nonce_Integrity = SHA256(nonce | 'INTEGRITY')""\n\t""nonce_smartcard = SHA256(nonce | 'SMARTCARD')""\n\t""nonce_attest = SHA256(nonce | 'ATTEST')""
alt#FEFFD5 2.1.1 Create Android Device Registration
TrustClient -> TrustClient: generate key pair and\ncreate ""JWT_registration""
else 2.2.1 Create Apple Device Registration
TrustClient -> TrustClient: generate key pair and\ncreate ""JWT_registration""
end
TrustClient -> Smartcard ++: sign ""(JWT_registration, nonce_smartcard)""\n\twith ""PrK.CH.AUT.E256""/""EF.C.CH.AUT.E256""
return return JWS_registration_signed
TrustClient -> GMS: register device JWS(JWS_registration_signed)
GMS -> GMS: verify JWS_registration_signed
GMS -> GMS: check EF.C.CH.AUT.E256 validity
note left
gematik PKI OCSP
end note
alt#FEFFD5 2.1.2 Verify Android Device Registration
GMS -> GMS: verify ""JWS_registration_signed""\nextract Android specifics
else 2.2.2 Verify Apple Device Registration
GMS -> GMS: verify ""JWS_registration_signed""\nextract Apple specifics
end
GMS -> GMS: extract KVNR from EF.C.CH.AUT.E256\nin JWS_registration_signed
GMS -> GMS: create cert_mTLS(CSR, UUID_device, nonce)
alt#FEFFD5 Store Android Device Registration
GMS -> GMS: store\n\tKVNR\n\tUUID_device\n\tcert_mTLS\n\tcert_attest
else Store Apple Device Registration
GMS -> GMS: store\n\tKVNR\n\tUUID_device\n\tcert_mTLS\n\tattestation_statement
end
return return cert_mTLS
TrustClient -> TrustClient: store cert_mTLS
@enduml
2.1 Android specifics
2.1.1 Create Android Device Registration
@startuml
autonumber "<b>['2.1.1' 00]"
skinparam defaultFontSize 10
skinparam DefaultMonospacedFontName Courier
skinparam lengthAdjust none
activate TrustClient
participant PlayIntegrityAPI
group Android
TrustClient -> TrustClient: generate\n\t""keypair_attest""\n\t""attestCertChain(nonce_attest)""\n\t""keypair_mTLS""\n\t""keypair_mTLS_cert(nonce_keypair_mTLS)""\n\t""CSR(nonce_CSR_mTLS, keypair_mTLS)""
TrustClient -> PlayIntegrityAPI ++: perform IntegrityTokenRequest(nonce_Integrity)
return return integrityVerdict
TrustClient -> TrustClient: create\n\t""JWT_registration(""\n\t\t""TYPE_ANDROID,""\n\t\t""nonce,""\n\t\t""pubkey_mTLS,""\n\t\t""keypair_mTLS_cert,""\n\t\t""pubkey_attest,""\n\t\t""attestCertChain""\n\t\t""integrityVerdict,""\n\t\t""CSR""\n\t"")""
end
@enduml
2.1.2 Verify Android Device Registration
@startuml
autonumber "<b>['2.1.1' 00]"
skinparam defaultFontSize 10
skinparam DefaultMonospacedFontName Courier
skinparam lengthAdjust none
activate GMS
participant GoogleServer
group Android
GMS -> GMS: extract nonce, pubkey_mTLS, AttestCert_mTLS,\nintegrityVerdict, CSR from JWS_registration_signed
GMS -> GMS: verify attestCertChain and certification extension data
GMS -> GMS: verify AttestCert_mTLS and certification extension data
GMS -> GMS: verify AttestCert_mTLS was signed by pubkey_attest
GMS -> GoogleServer ++: get Key Attestation certificate revocation status list
return return CRL_json
GMS -> GMS: evaluate CRL_json
GMS -> GoogleServer ++: request integrity_verdict(integrityVerdict)
return return verdict_json
GMS -> GMS: evaluate verdict_json
end
@enduml
2.2 Apple specifics
2.2.1 Create Apple Device Registration
@startuml
autonumber "<b>['2.2.1' 00]"
skinparam defaultFontSize 10
skinparam DefaultMonospacedFontName Courier
skinparam lengthAdjust none
activate TrustClient
participant AppAttestAPI
group Apple
TrustClient -> TrustClient: generate\n\t""keypair_mTLS""\n\t""CSR(nonce_CSR_mTLS, keypair_mTLS)""
TrustClient -> AppAttestAPI ++: generate\n\t""keypair_attest(""\n\t\t""SHA256(nonce_Integrity | SHA256(pubkey_mTLS))""\n\t"")""
AppAttestAPI -> AppAttestAPI: attest
return return attestation_statement
TrustClient -> TrustClient: create\n\t""JWT_registration(""\n\t\t""TYPE_IOS,"",\n\t\t""nonce,""\n\t\t""pubkey_mTLS,""\n\t\t""attestation_statement,""\n\t\t""keyIdentifier_attest,""\n\t\t""CSR""\n\t"")""
end
@enduml
2.2.2 Verify Apple Device Registration
@startuml
autonumber "<b>['2.2.2' 00]"
skinparam defaultFontSize 10
skinparam DefaultMonospacedFontName Courier
skinparam lengthAdjust none
activate GMS
group Apple
GMS -> GMS: extract nonce, pubkey_mTLS, attestation_statement,\nkeyIdentifier_attest, CSR
GMS -> GMS: verify attestation_statement
end
@enduml
2 - DSR-RFC-02 Resource Access
Resource access can only be performed from the previously registered and fresh attested device.
1. High Level Flow
Policy Decision Point
regularly downloads, verifies, and installs the currently active policy fromPolicy Administration Point
as well as context information fromPolicy Information Point
.TrustClient
requests an attestation from the platform APIs.- Attestation results are transmitted to
Device Management Service (GMS)
in form of Device Attestation Token. Device Registration Service verifies the authenticity and integrity of the attestation and issues the Device Token TrustClient
connects to theeHealth Service
using TLS. Mutual authentication is performed using the client certificate issued in DSR-RFC-01Trust Client
sends theDevice Token
as bearer token bound to mTLS certificate or a OAuth2 Code to the eHealth Service’sPEP
. PEP verifies the authenticity of the Device Token and extracts the device information.PEP
uses device information and other available signals (e.g. HTTP request headers) as input to thePDP
.PDP
applies the policy against the device information and any other input provided to it by thePEP
.- Once
PDP
allowed the access by making the positive decision, thePEP
lets the eHealth Service to continue and provide resources and other functionalities to the client.
2. Flow Details
@startuml DSR-RFC-02 Main Flow
autonumber "<b>[00]"
skinparam defaultFontSize 10
skinparam defaultFontName Helvetica
skinparam DefaultMonospacedFontName Courier
skinparam lengthAdjust none
activate TrustClient
participant GMS
box "Policy Enforcement"
participant PEP
participant PDP
end box
participant Backend as "eHealth\nService"
TrustClient -> GMS++: ""GET /nonce""
note right
Regular TLS
Server auth only
end note
GMS -> GMS: generate ""nonce""\nstore ""nonce"" in session
GMS -> TrustClient --: ""nonce""
TrustClient -> TrustClient: generate\n ""pkceCodeVerifier""\n ""pkceCodeChallenge""
alt#FEFFD5 2.1.1 Create Android Device Attest
TrustClient -> TrustClient: Provide JWS_attest_signed
else 2.2.1 Create Apple Device Attest
TrustClient -> TrustClient: Provide JWS_attest_signed
end
TrustClient -> GMS ++ : ""JWS_attest_signed"" \n ""pkceCodeChallenge""
note right
Mutual TLS
end note
GMS -> GMS: check if device ID is known\n(find device registration)
GMS -> GMS: check if publicKey fingerprint from mTLS is\n"sub" claim at JWS_attest_signed
GMS -> GMS: verify JWS_attest_signed
GMS -> TrustClient: return auth_code
alt#FEFFD5 2.1.2 Verify Android Device Attest
GMS -> GMS: Provide device_token
else 2.2.2 Verify Apple Device Attest
GMS -> GMS: Provide device_token
end
GMS -> GMS: sign device_token(privKey_GMS)
... some delay ...
TrustClient -> GMS: ""auth_code""\n""pkceCodeVerifier""
note right
Mutual TLS
end note
GMS -> GMS: verify\n ""auth_code""\n ""pkceCodeVerifier""
return ""device_token""
note right
PKCE can also be performed by PEP
end note
TrustClient -> PEP ++: request resource(""device_token"")
hnote over PEP: authenticate user
PEP -> PEP: verify ""device_token""
PEP -> PEP: create \n""policy_decision_input""
PEP -> PDP: request \n""policy_decision""
PDP -> PEP: ""policy_decision""
Backend -[#8BC34A]> TrustClient: <font color="#8BC34A"><&circle-check*4.0>
/'
group Android
TrustClient -> TrustClient: trigger Play Integrity API(nonce_PlayIntegrityAPI),\n\tcreate keypair keypair_attest_derived(pubkey_mTLS),\n\tAttestCert_derived(nonce_attest_derived),\n\tcollect device_attributes_security
TrustClient -> TrustClient: create JWT_attest(\n\tTYPE_ANDROID,\n\tintegrity_verdict,\n\tAttestCert_derived,\n\tdevice_attributes_security,\n\tnonce)
TrustClient -> TrustClient: sign JWT_attest with keypair_attest_derived
end Android
group Apple
TrustClient -> TrustClient: trigger AppAttestAPI assertion(\n\tnonce_attest_derived | fingerprint(pubkey_mTLS)\n),\ncollect device_attributes_security
TrustClient -> TrustClient: create JWT_attest(\n\tTYPE_iOS,\n\tassertion,\n\tdevice_attributes_security,\n\tnonce)
TrustClient -> TrustClient: sign JWT_attest with keypair_attest_sign
end Apple
'/
@enduml
2.1 Android specifics
2.1.1 Create Android Device Attest
@startuml
autonumber "<b>['2.1.1' 00]"
skinparam defaultFontSize 10
skinparam DefaultMonospacedFontName Courier
skinparam lengthAdjust none
activate TrustClient
group Android
TrustClient -> TrustClient: trigger Play Integrity API(nonce_PlayIntegrityAPI),\n\tcreate keypair keypair_attest_derived(pubkey_mTLS),\n\tAttestCert_derived(nonce_attest_derived),\n\tcollect device_attributes_security
TrustClient -> TrustClient: create JWT_attest(\n\tTYPE_ANDROID,\n\tintegrity_verdict,\n\tAttestCert_derived,\n\tdevice_attributes_security,\n\tnonce)
TrustClient -> TrustClient: sign JWT_attest with keypair_attest_derived
end
2.1.2 Verify Android Device Attest
@startuml
autonumber "<b>['2.1.2' 00]"
skinparam defaultFontSize 10
skinparam DefaultMonospacedFontName Courier
skinparam lengthAdjust none
activate GMS
group Android
GMS -> GMS: extract\n\t""integrity_verdict""\n\t""AttestCert_derived""\n\t""device_attributes_security""
GMS -> GMS: verify\n\t""AttestCert_derived""\ncheck\n\t""AttestCert_derived is child""\n\t""of AttestCert_mTLS""
GMS -> GoogleServer ++: request\n\t""integrity_verdict(integrity_verdict)""
return return ""verdict_json""
GMS -> GMS: create\n\t""device_token(""\n\t""verdict_json,""\n\t""device_attributes_security,""\n\t""UUID_device <-> KVNR""\n\t"")""
end
2.2 Apple specifics
2.2.1 Create Apple Device Attest
@startuml
autonumber "<b>['2.2.1' 00]"
skinparam defaultFontSize 10
skinparam DefaultMonospacedFontName Courier
skinparam lengthAdjust none
activate TrustClient
group Apple
TrustClient -> TrustClient: trigger AppAttestAPI assertion(\n\tnonce_attest_derived | fingerprint(pubkey_mTLS)\n),\ncollect device_attributes_security
TrustClient -> TrustClient: create JWT_attest(\n\tTYPE_iOS,\n\tassertion,\n\tdevice_attributes_security,\n\tnonce)
TrustClient -> TrustClient: sign JWT_attest with keypair_attest_sign
end
2.2.2 Verify Apple Device Attest
@startuml
autonumber "<b>['2.2.2' 00]"
skinparam defaultFontSize 10
skinparam DefaultMonospacedFontName Courier
skinparam lengthAdjust none
activate GMS
group Apple
GMS -> GMS: extract assertion, device_attributes_security
GMS -> AppleCA ++ : verify assertion
return return result
group optional
GMS -> AppleBackEnd ++: assess fraud risk
return return assessment
end optional
GMS -> GMS: create device_token(\n\tassertion,\n\tdevice_attributes_security,\n\tUUID_device <-> KVNR\n)
end
2.1 - nginx Deployment
Using nginx as frontend proxy with subrequest
In our sample implementation we use nginx as frontend proxy. Each request is authorized using the auth_request
subrequest, which is handled by the PEP. If PEP returns any other response as 200
, the proxy access to the business backend will be denied by the nginx.
autonumber "<b>[0]"
skinparam defaultFontSize 10
skinparam defaultFontName Helvetica
skinparam DefaultMonospacedFontName Courier
skinparam lengthAdjust none
activate Frontend
box "Policy Enforcement"
participant "nginx" as Proxy
participant "dsr-pep" as PEP #Orange
end box
participant "dsr-fahdienst" as Backend
group Unauthorized
Frontend -> Proxy ++: ""GET /resource""
Proxy -> PEP ++: auth subrequest\n""GET /.../auth_request""
PEP -> PEP: missing token\nor session expired
PEP -> Proxy --: ""401 Unauthorized""\n""WWW-Authenticate: ...""
Proxy -> Frontend --: ""401 Unauthorized""\n""WWW-Authenticate: ...""
end
group Authorized
Frontend -> Proxy ++: ""GET /resource""\n""Authorization: Bearer {access_token}""
Proxy -> PEP ++: auth subrequest\n""GET /.../auth_request""
PEP -> PEP: ""access_token"" is valid
PEP -> Proxy --: ""200 OK""
Proxy -> Backend ++: ""proxy_pass GET /resource""
Backend -> Proxy --: Resource
Proxy -> Frontend --: Resource
end
deactivate Frontend
3 - DSR-RFC-03 Device Deletion
User can delete a device from any previously registered device.
Flow Details
@startuml DSR-RFC-03 Main Flow
autonumber "<b>[00]"
actor User as User
User -> FrontEnd: view devices
FrontEnd -> TrustClient: request devices
TrustClient --> GMS++: establish mTLS channel (cert_mTLS)
TrustClient -> GMS: GET ""/device-registrations""\n\t""userIdentifier={KVNR}""
GMS -> TrustClient: array ""DeviceRegistration""
TrustClient -> FrontEnd: devices list
FrontEnd -> User: show devices
User -> FrontEnd: delete device_X
FrontEnd -> TrustClient: delete device_X
TrustClient --> GMS: DELETE ""/device-registrations""\n\t""userIdentifier={KVNR}""\n\t""deviceIdentifier={device_X}""
GMS --> TrustClient--: 200 OK
TrustClient -> FrontEnd: deleted successfully
FrontEnd -> User: show remaining devices
@enduml
4 - DSR-RFC-04 Security Tokens
DSR utilizes several tokens in order to register and attest the devices. All tokens are implemented using JSON Web Token (JWT).
Device Registration Token (JWT_registration)
- sent from TrustClient to Device Management Service (GMS) during registration
- contains all needed information for registration
- signed with EF.C.CH.AUT.E256 (eGK)
- see DSR-RFC-01 for corresponding sequence diagram
|
|
Device Attestation Token (JWT_attest)
- sent from TrustClient to Device Management Service (GMS) for attestation
- contains attestation information
- signed with mTLS_privateKey, (Android), privateKey_attest (iOS)
- see DSR-RFC-02 for corresponding sequence diagram
|
|
Device Token (device_token)
- sent from Device Management Service (GMS) to TrustClient to PEP (or directly from GMS to PEP)
- contains standard values from OAuth2.0 Certificate-Bound Access Tokens and
- verdict_json ( Google Integrity API)
- assertion (iOS)
- device_attributes_security (see dsr-rfc-06)
- UUID_device ↔ KVNR relation
- signed with privateKey_GMS
- see DSR-RFC-02 for corresponding sequence diagram
|
|
Trust Client Certificate Signing Request (CRL)
- sent from TrustClient to Device Management Service (GMS) and then to GMS CA for requesting / issuing Cert_mTLS
- contains standardized information
- signed by TrustClient with privKey_mTLS
- see DSR-RFC-01 for corresponding sequence diagram
|
|
Trust Client Certificate (cert_mTLS)
- issued by Device Management Service (GMS) CA to TrustClient / device
- attests the device’s/app’s pubkey_mTLS (device identity)
- must contain KVNR
- see DSR-RFC-01 for corresponding sequence diagram
|
|
Session Token (session_token_fd)
- sent from health service (FD) to TrustClient after successful device rating
- allows using session for a defined period of time without another device attestation
- signed by health service (FD)
- see DSR-RFC-02 for corresponding sequence diagram
|
|
5 - DSR-RFC-05 UI Flows
Introduction
To demonstrate the integration of DSR in mobile applications we provide the sample implementations of Frontend and Trust Client for Google Android and Apple iOS.
Google Android Demo | Apple iOS Demo |
---|---|
Android Registration and Data Access
6 - DSR-RFC-06 Device Security Attributes
Introduction
This RFC defines which Zero Trust signals are collected on- and off-device for security rating.
Minimal Trust Base for Registration
Minimal/basic trust that is needed for a successful registration at GMS and thus for participating in the DSR. Is verified by GMS during registration process.
Android
Google Play Integrity API
Descriptions are partially taken from the Android Developers Play Integrity doucmentation.
Attribute | Expected Value | Description | |
---|---|---|---|
requestDetails: | |||
requestPackageName | is equal to packageName from token payload and from AppIntegrity | application package name the attestation was requested for check list with enrolled apps at GMS | |
nonce | nonce_Integrity | base64-encoded URL-safe no-wrap nonce provided by the developer | |
timestampMillis | t + 10 min < time of creation on device | timestamp in milliseconds when the request was made | |
appIntegrity: | |||
appRecognitionVerdict | PLAY_RECOGNIZED | app and certificate match the versions distributed by Google Play | |
packageName | must be in the list of available packages | package name of the app check list with enrolled apps at GMS | |
certificateSha256Digest | must be equal to the sha256 digest, defined in the available packages list | sha256 digest of app certificates check list with enrolled apps at GMS | |
versionCode | must be in the list of available packages | version of the app check list with enrolled apps at GMS | |
deviceIntegrity: | |||
deviceIntegrity | MEETS_DEVICE_INTEGRITY | app is running on an Android device powered by Google Play services, device passes system integrity checks and meets Android compatibility requirements | |
accountDetails: | |||
appLicensingVerdict | LICENSED | user has an app entitlement (user installed or bought your app on Google Play) |
Android Key & ID Attestation
Descriptions are partially taken from the Android Developers Key & ID Attestation article.
Attribute | Expected Value | Description |
---|---|---|
KeyDescription: | ||
attestationVersion | tbd | version of the key attestation feature. |
attestationSecurityLevel | TrustedEnvironment (1), StrongBox (2) | security level of the attestation |
keyMintVersion / keymasterVersion | tbd | security level of the attestation |
keyMintSecurityLevel / keymasterSecurityLevel | tbd | security level of the Keymaster/KeyMint implementation |
attestationChallenge | nonce_keypair_attest | challenge from creation |
softwareEnforced | out of scope for PoC | |
teeEnforced | out of scope for PoC |
iOS
App Attest Service
Descriptions are partially taken from the Apple Developer DeviceCheck documentation.
Attribute | Expected Value | Description | |
---|---|---|---|
Attestation: | |||
RP ID (32 bytes) | must be equal to the RP ID, defined in the available packages list at GMS | A hash of your app’s App ID, which is the concatenation of your 10-digit team identifier, a period, and your app’s CFBundleIdentifier value | |
counter (4 bytes) | ignored for PoC | value that reports the number of times your app has used the attested key to sign an assertion | |
aaguid (16 bytes) | production | App Attest–specific constant that indicates whether the attested key belongs to the development or production environment | |
credentialId (32 bytes) | must be equal to the key used to sign the mTLS public key | hash of the public key part of the attested cryptographic key pair |
Device Rating Attributes
Device security attributes that need to be provided by a device when trying to access a resource. GMS verifies token authenticity / integrity as well as app/Trust SDK info and forwards all information in device_token to PEP.
Android
Google Play Integrity API
see Minimal Trust Base for Registration.
Android Key & ID Attestation
see Minimal Trust Base for Registration.
Additional Security Attributes
Descriptions are partially taken from the Android Enterprise Developers Zero Trust signals documentation.
Attribute | Description | API | Root of Trust | Availability |
---|---|---|---|---|
Android version | Android version or API level / SDK version currently running on the device | Build.VERSION.SDK_INT | Software | >= Android 1.6 |
Android version (release) | Android version (API level) with which the device was released / CTS was passed | getprop('ro.product.first_api_level') | Software | TODO |
Patchlevel | OS patch level | Build.VERSION.SECURITY_PATCH | Software | >= Android 6.0 |
FDE / FBE | Indicates whether device encryption is supported and whether it is activated. | getprop('ro.crypto.state') | Software | TODO |
System PIN / password / pattern set | Indicates whether a PIN/pattern/password is set for the lock screen. | KeyguardManager.isDeviceSecure() , BiometricManager.canAuthenticate(BiometricManager.Authenticators.DEVICE_CREDENTIAL) , BiometricManager.canAuthenticate(BiometricManager.Authenticators.BIOMETRIC_STRONG) | Software | >= Android 6.0, >= Android 11, >= Android 12 |
System PIN / password / pattern quality | The Device Policy Manager can be used to query whether certain password complexity levels are currently being met. | DevicePolicyManager.getPasswordComplexity() , requires android.permission.REQUEST_PASSWORD_COMPLEXITY | Software | >= Android 10 |
Verified boot supported | Indicates whether VerifiedBoot is available on the device. | PackageManager.FEATURE_VERIFIED_BOOT | Software | >= Android 5.0 |
Mainline patch level | Indicates when the last mainline patch was installed. | PackageManager.getPackageInfo("com.google.android.modulemetadata", 0).versionName | Software | API level > 1 |
OEM / model | Returns information about manufacturer, model, etc. | BUILD.MODEL, BUILD.PRODUCT, BUILD.MANUFACTURER, BUILD.BOARD | Software | |
Biometric class | Returns information if class 3 biometrics is available. | BiometricManager.canAuthenticate(Authenticators#BIOMETRIC_STRONG) | Software | >= Android 12 |
iOS
App Attest Service
Descriptions are partially taken from the Apple Developer DeviceCheck documentation.
Attribute | Expected Value | Description | |
---|---|---|---|
Assertion: | |||
RP ID (32 bytes) | must be equal to the RP ID, defined in the available packages list at GMS | A hash of your app’s App ID, which is the concatenation of your 10-digit team identifier, a period, and your app’s CFBundleIdentifier value | |
counter (4 bytes) | ignored for PoC | value that reports the number of times your app has used the attested key to sign an assertion | Fraud Risk (optional): | tbd |
Additional Security Attributes
Attribute | Description | API | Root of Trust | Availability | |
---|---|---|---|---|---|
System Name | The name of the operating system running on the device. | UIDevice: var systemName: String { get } | Software | >= iOS 2.0 | |
System version | The current version of the operating system. | UIDevice: var systemVersion: String { get } | Software | >= iOS 2.0 | |
Model | Possible examples of model strings are ”iPhone” and ”iPod touch”. | UIDevice: var model: String { get } | Software | >= iOS 2.0 | |
identifierForVendor | An alphanumeric string that uniquely identifies a device to the app’s vendor. | UIDevice: var identifierForVendor: UUID? { get } | Software | >=iOS 6.0 | |
App Version | The current version of the App system. | tbd | Software | tbd |
7 - DSR-RFC-09 Health Service API
Structure of the Health Service
A concrete instance of a FD service is identified via FQDN
Application / Service | Provider | FQDN |
---|---|---|
DSR “dummy” health service | tbd | dsr.health-service.example.com |
The DSR “dummy” health service provides the following business APIs / resources
API | Version | URL |
---|---|---|
emergency data API | v1 | https://dsr.health-service.example.com/api/v1/notfalldaten |
ePrescription API | v1 | https://dsr.health-service.example.com/api/v1/erezept/ |
ePrescription API | v2 | https://dsr.health-service.example.com/api/v2/erezept/ |
Scaling and load balancing is done in the background, invisible to the clients.
API Documentation
see poc-dsr-fd on GitHub.
Test Data ePrescription API
Version | ID |
---|---|
v1 | 6c371ed4-f83a-47b4-8249-446852a5b382 |
v1 | 17e5970d-6e64-465f-be0c-ed0f5d7624a0 |
v2 | 00fa65b9-2e07-40c7-b8c5-fadf549c4ed7 |
v2 | 01e18e40-83a5-4986-819f-c68c2227b59d |
Test Data emergency data API
patientIdentifier |
---|
X123456 |
X234567 |
X345678 |
Input Data for Policy Decision Point
Input data for access decisions by the Policy Decision Point
is independent of the DSR “dummy” health Service or its APIs and results from the external sources. The Policy Enforcement Point
is responsible to determine appropriate input, verify and submit to the Policy Decision Point
for decision according to a JSON schema:
Input Example for iOS Devices
|
|
Input Example for Android Devices
|
|
The structural check of the device token
(signature, validity, mTLS fingerprint matching) is performed in the Policy Enforcement Point
before the Policy Decision Point
is called. The result of this check is passed to the Policy Decision Point
with the deviceTokenValid
attribute.
Access Decision / Verdict by the PDP
For example, the positive decision look like this:
|
|
A negative decision provides hints about which checks failed and looks like the following examples:
Failed Android Device
|
|
Failed iOS Device
|
|
8 - DSR-RFC-11 Mobile Vulnerability Management
Introduction
tbd
Example Vulnerabilities
Mali GPU Kernel Driver may elevate CPU RO pages to writable
Title | Mali GPU Kernel Driver may elevate CPU RO pages to writable |
CVEs |
|
Published | Spring 2022 Summer 2022 |
Severity | MEDIUM HIGH |
Description | A non-privileged user can get a write access to read-only memory pages; by forcing the kernel to reuse these pages as page tables, an attacker with native code execution in an app context could gain full access to the system, bypassing Android’s permissions model and allowing broad access to user data. |
Affected Devices | Devices with Mali GPU:
|
Needed Information to detect |
|
CPE (via NVD) | nn |
✅ Rule(s) for DSR | WARN all devices with MALI GPU && tbd Patchlevel |
References | https://googleprojectzero.blogspot.com/2022/11/mind-the-gap.html |
Samsung TrustZone Keymaster
Title | Samsung TrustZone Keymaster |
CVEs |
|
Published | Spring 2022 |
Severity | HIGH |
Description | KeyMaster in TEE:
|
Affected Devices |
|
CPE (via NVD) |
|
✅ Rule(s) for DSR |
|
Needed Information to detect |
|
References |
Internet to Baseband Remote Code Execution Vulnerabilities in Exynos Modems
Title | Internet to Baseband Remote Code Execution Vulnerabilities in Exynos Modems |
CVEs |
|
Published | Spring 2022 |
Severity | HIGH |
Description | KeyMaster in TEE:
|
Affected Devices | Devices with Exynos 1280, 2200, 5300 modem (CVE-2023-28613):
|
Needed Information to detect | Devices with Exynos 1280, 2200, 5300 modem (CVE-2023-28613):
|
CPE (via NVD) |
|
✅ Rule(s) for DSR | 1.-4.: allow an attacker to remotely compromise a phone at the baseband level with no user interaction, and require only that the attacker know the victim’s phone number 5.-??.: require either a malicious mobile network operator or an attacker with local access to the device |
References |
Smartphone Fingerprint Authentication Brute-force Attack
Title | Smartphone Fingerprint Authentication Brute-force Attack |
CVEs | nn |
Published | Spring 2023 |
Severity | HIGH |
Description | Smartphone Fingerprint Authentication to Brute-force Attack with physical access |
Affected Devices |
|
Needed Information to detect |
|
CPE (via NVD) | nn |
✅ Rule(s) for DSR | tbd |
References | https://arxiv.org/pdf/2305.10791.pdf |
Implementation
The implementation of the pipeline was carried out using the following resources:
The main.py file receives a list of “keywords” such as “python3 main.py samsung galaxy s6”. These keywords are searched for in a local redis-server instance, which contains all CPEs from NIST.
The found CPEs are formatted properly and queried with the nvdlib at the NIST CVE API. The found CVEs are processed and outputted.
Challenges
- The used API has a limited number of requests.
- Not all devices have “proper” CPEs.
- It is difficult to automatically determine if the found CVEs are fixed in the next patch.