Updated ImpressionAttestation API signatures

1. Updated verifyImpressionToken to send back a boolean instead of an
integer. Updated docs
2. Added salt value to generateImpressionToken and verifyImpressionToken

Test: Builds
Bug: 155825630
Change-Id: I672500ef2337796775f9d9f32e626df69a886f9f
This commit is contained in:
chaviw
2020-11-19 11:08:47 -08:00
parent 203346d3f5
commit 2252f0b197
4 changed files with 45 additions and 43 deletions

View File

@@ -8957,11 +8957,8 @@ package android.service.attestation {
public abstract class ImpressionAttestationService extends android.app.Service {
ctor public ImpressionAttestationService();
method @NonNull public final android.os.IBinder onBind(@NonNull android.content.Intent);
method @Nullable public abstract android.service.attestation.ImpressionToken onGenerateImpressionToken(@NonNull android.hardware.HardwareBuffer, @NonNull android.graphics.Rect, @NonNull String);
method public abstract int onVerifyImpressionToken(@NonNull android.service.attestation.ImpressionToken);
field public static final int VERIFICATION_STATUS_APP_DECLARED = 2; // 0x2
field public static final int VERIFICATION_STATUS_OS_VERIFIED = 1; // 0x1
field public static final int VERIFICATION_STATUS_UNKNOWN = 0; // 0x0
method @Nullable public abstract android.service.attestation.ImpressionToken onGenerateImpressionToken(@NonNull String, @NonNull android.hardware.HardwareBuffer, @NonNull android.graphics.Rect, @NonNull String);
method public abstract boolean onVerifyImpressionToken(@NonNull String, @NonNull android.service.attestation.ImpressionToken);
}
public final class ImpressionToken implements android.os.Parcelable {

View File

@@ -18,8 +18,8 @@ package android.service.attestation;
import android.graphics.Rect;
import android.hardware.HardwareBuffer;
import android.service.attestation.ImpressionToken;
import android.os.RemoteCallback;
import android.service.attestation.ImpressionToken;
/**
* Service used to handle impression attestation requests.
@@ -31,22 +31,26 @@ oneway interface IImpressionAttestationService {
* Generates the impression token that can be used to validate that the system generated the
* token.
*
* @param screenshot The token for the window where the view is shown.
* @param salt The salt to use when generating the hmac. This should be unique to the caller so
* the token cannot be verified by any other process.
* @param screenshot The screenshot to generate the hash and add to the token.
* @param bounds The size and position of the content being attested in the window.
* @param hashAlgorithm The String for the hashing algorithm to use based on values in
* {@link #SERVICE_META_DATA_KEY_AVAILABLE_ALGORITHMS}.
* @param Callback The callback invoked to send back the impression token.
*/
void generateImpressionToken(in HardwareBuffer screenshot, in Rect bounds,
void generateImpressionToken(in String salt, in HardwareBuffer screenshot, in Rect bounds,
in String hashAlgorithm, in RemoteCallback callback);
/**
* Call to verify that the impressionToken passed in was generated by the system. The result
* will be sent in the callback as an integer with the key {@link #EXTRA_VERIFICATION_STATUS}
* and will be one of the values in {@link VerificationStatus}.
* will be sent in the callback as a boolean with the key {@link #EXTRA_VERIFICATION_STATUS}.
*
* @param salt The salt value to use when verifying the hmac. This should be the same value that
* was passed to {@link generateImpressionToken()} to generate the token.
* @param impressionToken The token to verify that it was generated by the system.
* @param callback The callback invoked to send back the verification status.
*/
void verifyImpressionToken(in ImpressionToken impressionToken, in RemoteCallback callback);
void verifyImpressionToken(in String salt, in ImpressionToken impressionToken,
in RemoteCallback callback);
}

View File

@@ -18,7 +18,6 @@ package android.service.attestation;
import static com.android.internal.util.function.pooled.PooledLambda.obtainMessage;
import android.annotation.IntDef;
import android.annotation.NonNull;
import android.annotation.Nullable;
import android.annotation.SystemApi;
@@ -50,22 +49,10 @@ public abstract class ImpressionAttestationService extends Service {
public static final String EXTRA_VERIFICATION_STATUS =
"android.service.attestation.extra.VERIFICATION_STATUS";
/** @hide */
@IntDef(prefix = {"VERIFICATION_STATUS_"}, value = {
VERIFICATION_STATUS_UNKNOWN,
VERIFICATION_STATUS_OS_VERIFIED,
VERIFICATION_STATUS_APP_DECLARED
})
public @interface VerificationStatus {
}
public static final int VERIFICATION_STATUS_UNKNOWN = 0;
public static final int VERIFICATION_STATUS_OS_VERIFIED = 1;
public static final int VERIFICATION_STATUS_APP_DECLARED = 2;
/**
* Manifest metadata key for the resource string array containing the names of all impression
* attestation algorithms provided by the service.
*
* @hide
*/
public static final String SERVICE_META_DATA_KEY_AVAILABLE_ALGORITHMS =
@@ -74,6 +61,7 @@ public abstract class ImpressionAttestationService extends Service {
/**
* The {@link Intent} action that must be declared as handled by a service in its manifest
* for the system to recognize it as an impression attestation providing service.
*
* @hide
*/
public static final String SERVICE_INTERFACE =
@@ -102,6 +90,8 @@ public abstract class ImpressionAttestationService extends Service {
* Generates the impression token that can be used to validate that the system
* generated the token.
*
* @param salt The salt to use when generating the hmac. This should be unique to the
* caller so the token cannot be verified by any other process.
* @param screenshot The screenshot buffer for the content to attest.
* @param bounds The size and position of the content being attested in the window.
* @param hashAlgorithm The String for the hashing algorithm to use based values in
@@ -110,51 +100,57 @@ public abstract class ImpressionAttestationService extends Service {
* Returns null when the arguments sent are invalid.
*/
@Nullable
public abstract ImpressionToken onGenerateImpressionToken(@NonNull HardwareBuffer screenshot,
@NonNull Rect bounds, @NonNull String hashAlgorithm);
public abstract ImpressionToken onGenerateImpressionToken(@NonNull String salt,
@NonNull HardwareBuffer screenshot, @NonNull Rect bounds,
@NonNull String hashAlgorithm);
/**
* Call to verify that the impressionToken passed in was generated by the system.
*
* @param salt The salt value to use when verifying the hmac. This should be the
* same value that was passed to
* {@link #onGenerateImpressionToken(String,
* HardwareBuffer, Rect, String)} to
* generate the token.
* @param impressionToken The token to verify that it was generated by the system.
* @return A {@link VerificationStatus} about whether the token was generated by the system.
* @return true if the token can be verified that it was generated by the system.
*/
public abstract @VerificationStatus int onVerifyImpressionToken(
public abstract boolean onVerifyImpressionToken(@NonNull String salt,
@NonNull ImpressionToken impressionToken);
private void generateImpressionToken(HardwareBuffer screenshot, Rect bounds,
private void generateImpressionToken(String salt, HardwareBuffer screenshot, Rect bounds,
String hashAlgorithm, RemoteCallback callback) {
ImpressionToken impressionToken = onGenerateImpressionToken(screenshot, bounds,
ImpressionToken impressionToken = onGenerateImpressionToken(salt, screenshot, bounds,
hashAlgorithm);
final Bundle data = new Bundle();
data.putParcelable(EXTRA_IMPRESSION_TOKEN, impressionToken);
callback.sendResult(data);
}
private void verifyImpressionToken(ImpressionToken impressionToken,
private void verifyImpressionToken(String salt, ImpressionToken impressionToken,
RemoteCallback callback) {
@VerificationStatus int verificationStatus = onVerifyImpressionToken(impressionToken);
boolean verificationStatus = onVerifyImpressionToken(salt, impressionToken);
final Bundle data = new Bundle();
data.putInt(EXTRA_VERIFICATION_STATUS, verificationStatus);
data.putBoolean(EXTRA_VERIFICATION_STATUS, verificationStatus);
callback.sendResult(data);
}
private final class ImpressionAttestationServiceWrapper extends
IImpressionAttestationService.Stub {
@Override
public void generateImpressionToken(HardwareBuffer screenshot, Rect bounds,
public void generateImpressionToken(String salt, HardwareBuffer screenshot, Rect bounds,
String hashAlgorithm, RemoteCallback callback) {
mHandler.sendMessage(
obtainMessage(ImpressionAttestationService::generateImpressionToken,
ImpressionAttestationService.this, screenshot, bounds, hashAlgorithm,
callback));
ImpressionAttestationService.this, salt, screenshot, bounds,
hashAlgorithm, callback));
}
@Override
public void verifyImpressionToken(ImpressionToken impressionToken,
public void verifyImpressionToken(String salt, ImpressionToken impressionToken,
RemoteCallback callback) {
mHandler.sendMessage(obtainMessage(ImpressionAttestationService::verifyImpressionToken,
ImpressionAttestationService.this, impressionToken, callback));
ImpressionAttestationService.this, salt, impressionToken, callback));
}
}
}

View File

@@ -47,6 +47,7 @@ import android.util.Slog;
import com.android.internal.annotations.GuardedBy;
import java.util.ArrayList;
import java.util.UUID;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.TimeUnit;
import java.util.function.BiConsumer;
@@ -78,6 +79,8 @@ public class ImpressionAttestationController {
private final Handler mHandler;
private final String mSalt;
private interface Command {
void run(IImpressionAttestationService service) throws RemoteException;
}
@@ -85,6 +88,7 @@ public class ImpressionAttestationController {
ImpressionAttestationController(Context context) {
mContext = context;
mHandler = new Handler(Looper.getMainLooper());
mSalt = UUID.randomUUID().toString();
}
String[] getSupportedImpressionAlgorithms() {
@@ -118,17 +122,17 @@ public class ImpressionAttestationController {
}
}
int verifyImpressionToken(ImpressionToken impressionToken) {
boolean verifyImpressionToken(ImpressionToken impressionToken) {
final SyncCommand syncCommand = new SyncCommand();
Bundle results = syncCommand.run((service, remoteCallback) -> {
try {
service.verifyImpressionToken(impressionToken, remoteCallback);
service.verifyImpressionToken(mSalt, impressionToken, remoteCallback);
} catch (RemoteException e) {
Slog.e(TAG, "Failed to invoke verifyImpressionToken command");
}
});
return results.getInt(ImpressionAttestationService.EXTRA_VERIFICATION_STATUS);
return results.getBoolean(ImpressionAttestationService.EXTRA_VERIFICATION_STATUS);
}
ImpressionToken generateImpressionToken(HardwareBuffer screenshot, Rect bounds,
@@ -136,7 +140,8 @@ public class ImpressionAttestationController {
final SyncCommand syncCommand = new SyncCommand();
Bundle results = syncCommand.run((service, remoteCallback) -> {
try {
service.generateImpressionToken(screenshot, bounds, hashAlgorithm, remoteCallback);
service.generateImpressionToken(mSalt, screenshot, bounds, hashAlgorithm,
remoteCallback);
} catch (RemoteException e) {
Slog.e(TAG, "Failed to invoke generateImpressionToken command", e);
}