Merge "Add SandboxedDetectionServiceBase interface"
This commit is contained in:
@@ -12472,17 +12472,17 @@ package android.service.voice {
|
||||
method @NonNull public android.service.voice.HotwordDetectedResult.Builder setScore(int);
|
||||
}
|
||||
|
||||
public abstract class HotwordDetectionService extends android.app.Service {
|
||||
public abstract class HotwordDetectionService extends android.app.Service implements android.service.voice.SandboxedDetectionServiceBase {
|
||||
ctor public HotwordDetectionService();
|
||||
method public static int getMaxCustomInitializationStatus();
|
||||
method @Deprecated public static int getMaxCustomInitializationStatus();
|
||||
method @Nullable public final android.os.IBinder onBind(@NonNull android.content.Intent);
|
||||
method public void onDetect(@NonNull android.service.voice.AlwaysOnHotwordDetector.EventPayload, long, @NonNull android.service.voice.HotwordDetectionService.Callback);
|
||||
method public void onDetect(@NonNull android.service.voice.HotwordDetectionService.Callback);
|
||||
method public void onDetect(@NonNull android.os.ParcelFileDescriptor, @NonNull android.media.AudioFormat, @Nullable android.os.PersistableBundle, @NonNull android.service.voice.HotwordDetectionService.Callback);
|
||||
method public void onStopDetection();
|
||||
method public void onUpdateState(@Nullable android.os.PersistableBundle, @Nullable android.os.SharedMemory, long, @Nullable java.util.function.IntConsumer);
|
||||
field public static final int INITIALIZATION_STATUS_SUCCESS = 0; // 0x0
|
||||
field public static final int INITIALIZATION_STATUS_UNKNOWN = 100; // 0x64
|
||||
field @Deprecated public static final int INITIALIZATION_STATUS_SUCCESS = 0; // 0x0
|
||||
field @Deprecated public static final int INITIALIZATION_STATUS_UNKNOWN = 100; // 0x64
|
||||
field public static final String SERVICE_INTERFACE = "android.service.voice.HotwordDetectionService";
|
||||
}
|
||||
|
||||
@@ -12529,6 +12529,13 @@ package android.service.voice {
|
||||
method @NonNull public android.service.voice.HotwordRejectedResult.Builder setConfidenceLevel(int);
|
||||
}
|
||||
|
||||
public interface SandboxedDetectionServiceBase {
|
||||
method public static int getMaxCustomInitializationStatus();
|
||||
method public void onUpdateState(@Nullable android.os.PersistableBundle, @Nullable android.os.SharedMemory, long, @Nullable java.util.function.IntConsumer);
|
||||
field public static final int INITIALIZATION_STATUS_SUCCESS = 0; // 0x0
|
||||
field public static final int INITIALIZATION_STATUS_UNKNOWN = 100; // 0x64
|
||||
}
|
||||
|
||||
public class VoiceInteractionService extends android.app.Service {
|
||||
method @NonNull public final android.service.voice.AlwaysOnHotwordDetector createAlwaysOnHotwordDetector(String, java.util.Locale, android.service.voice.AlwaysOnHotwordDetector.Callback);
|
||||
method @NonNull @RequiresPermission(android.Manifest.permission.MANAGE_HOTWORD_DETECTION) public final android.service.voice.AlwaysOnHotwordDetector createAlwaysOnHotwordDetector(String, java.util.Locale, @Nullable android.os.PersistableBundle, @Nullable android.os.SharedMemory, android.service.voice.AlwaysOnHotwordDetector.Callback);
|
||||
|
||||
@@ -2561,7 +2561,7 @@ package android.service.voice {
|
||||
method @NonNull public android.service.voice.AlwaysOnHotwordDetector.EventPayload.Builder setKeyphraseRecognitionExtras(@NonNull java.util.List<android.hardware.soundtrigger.SoundTrigger.KeyphraseRecognitionExtra>);
|
||||
}
|
||||
|
||||
public abstract class HotwordDetectionService extends android.app.Service {
|
||||
public abstract class HotwordDetectionService extends android.app.Service implements android.service.voice.SandboxedDetectionServiceBase {
|
||||
field public static final boolean ENABLE_PROXIMITY_RESULT = true;
|
||||
}
|
||||
|
||||
|
||||
@@ -33,7 +33,6 @@ import android.content.Intent;
|
||||
import android.hardware.soundtrigger.SoundTrigger;
|
||||
import android.media.AudioFormat;
|
||||
import android.media.AudioSystem;
|
||||
import android.os.Bundle;
|
||||
import android.os.IBinder;
|
||||
import android.os.IRemoteCallback;
|
||||
import android.os.ParcelFileDescriptor;
|
||||
@@ -72,22 +71,13 @@ import java.util.function.IntConsumer;
|
||||
* @hide
|
||||
*/
|
||||
@SystemApi
|
||||
public abstract class HotwordDetectionService extends Service {
|
||||
public abstract class HotwordDetectionService extends Service
|
||||
implements SandboxedDetectionServiceBase {
|
||||
private static final String TAG = "HotwordDetectionService";
|
||||
private static final boolean DBG = false;
|
||||
|
||||
private static final long UPDATE_TIMEOUT_MILLIS = 20000;
|
||||
|
||||
/** @hide */
|
||||
public static final String KEY_INITIALIZATION_STATUS = "initialization_status";
|
||||
|
||||
/**
|
||||
* The maximum number of initialization status for some application specific failed reasons.
|
||||
*
|
||||
* @hide
|
||||
*/
|
||||
public static final int MAXIMUM_NUMBER_OF_INITIALIZATION_STATUS_CUSTOM_ERROR = 2;
|
||||
|
||||
/**
|
||||
* Feature flag for Attention Service.
|
||||
*
|
||||
@@ -98,14 +88,22 @@ public abstract class HotwordDetectionService extends Service {
|
||||
|
||||
/**
|
||||
* Indicates that the updated status is successful.
|
||||
*
|
||||
* @deprecated Replaced with {@link SandboxedDetectionServiceBase#INITIALIZATION_STATUS_SUCCESS}
|
||||
*/
|
||||
public static final int INITIALIZATION_STATUS_SUCCESS = 0;
|
||||
@Deprecated
|
||||
public static final int INITIALIZATION_STATUS_SUCCESS =
|
||||
SandboxedDetectionServiceBase.INITIALIZATION_STATUS_SUCCESS;
|
||||
|
||||
/**
|
||||
* Indicates that the callback wasn’t invoked within the timeout.
|
||||
* This is used by system.
|
||||
*
|
||||
* @deprecated Replaced with {@link SandboxedDetectionServiceBase#INITIALIZATION_STATUS_UNKNOWN}
|
||||
*/
|
||||
public static final int INITIALIZATION_STATUS_UNKNOWN = 100;
|
||||
@Deprecated
|
||||
public static final int INITIALIZATION_STATUS_UNKNOWN =
|
||||
SandboxedDetectionServiceBase.INITIALIZATION_STATUS_UNKNOWN;
|
||||
|
||||
/**
|
||||
* Source for the given audio stream.
|
||||
@@ -254,8 +252,11 @@ public abstract class HotwordDetectionService extends Service {
|
||||
* Note: The value 0 is reserved for success.
|
||||
*
|
||||
* @hide
|
||||
* @deprecated Replaced with
|
||||
* {@link SandboxedDetectionServiceBase#getMaxCustomInitializationStatus()}
|
||||
*/
|
||||
@SystemApi
|
||||
@Deprecated
|
||||
public static int getMaxCustomInitializationStatus() {
|
||||
return MAXIMUM_NUMBER_OF_INITIALIZATION_STATUS_CUSTOM_ERROR;
|
||||
}
|
||||
@@ -305,21 +306,10 @@ public abstract class HotwordDetectionService extends Service {
|
||||
* {@link AlwaysOnHotwordDetector#updateState(PersistableBundle, SharedMemory)} requests an
|
||||
* update of the hotword detection parameters.
|
||||
*
|
||||
* @param options Application configuration data to provide to the
|
||||
* {@link HotwordDetectionService}. PersistableBundle does not allow any remotable objects or
|
||||
* other contents that can be used to communicate with other processes.
|
||||
* @param sharedMemory The unrestricted data blob to provide to the
|
||||
* {@link HotwordDetectionService}. Use this to provide the hotword models data or other
|
||||
* such data to the trusted process.
|
||||
* @param callbackTimeoutMillis Timeout in milliseconds for the operation to invoke the
|
||||
* statusCallback.
|
||||
* @param statusCallback Use this to return the updated result; the allowed values are
|
||||
* {@link #INITIALIZATION_STATUS_SUCCESS}, 1<->{@link #getMaxCustomInitializationStatus()}.
|
||||
* This is non-null only when the {@link HotwordDetectionService} is being initialized; and it
|
||||
* is null if the state is updated after that.
|
||||
*
|
||||
* {@inheritDoc}
|
||||
* @hide
|
||||
*/
|
||||
@Override
|
||||
@SystemApi
|
||||
public void onUpdateState(
|
||||
@Nullable PersistableBundle options,
|
||||
@@ -371,23 +361,8 @@ public abstract class HotwordDetectionService extends Service {
|
||||
|
||||
private void onUpdateStateInternal(@Nullable PersistableBundle options,
|
||||
@Nullable SharedMemory sharedMemory, IRemoteCallback callback) {
|
||||
IntConsumer intConsumer = null;
|
||||
if (callback != null) {
|
||||
intConsumer =
|
||||
value -> {
|
||||
if (value > getMaxCustomInitializationStatus()) {
|
||||
throw new IllegalArgumentException(
|
||||
"The initialization status is invalid for " + value);
|
||||
}
|
||||
try {
|
||||
Bundle status = new Bundle();
|
||||
status.putInt(KEY_INITIALIZATION_STATUS, value);
|
||||
callback.sendResult(status);
|
||||
} catch (RemoteException e) {
|
||||
throw e.rethrowFromSystemServer();
|
||||
}
|
||||
};
|
||||
}
|
||||
IntConsumer intConsumer =
|
||||
SandboxedDetectionServiceBase.createInitializationStatusConsumer(callback);
|
||||
onUpdateState(options, sharedMemory, UPDATE_TIMEOUT_MILLIS, intConsumer);
|
||||
}
|
||||
|
||||
|
||||
@@ -35,7 +35,7 @@ import android.util.AndroidException;
|
||||
import java.io.PrintWriter;
|
||||
|
||||
/**
|
||||
* Basic functionality for hotword detectors.
|
||||
* Basic functionality for sandboxed detectors.
|
||||
*
|
||||
* @hide
|
||||
*/
|
||||
@@ -81,7 +81,7 @@ public interface HotwordDetector {
|
||||
int DETECTOR_TYPE_TRUSTED_HOTWORD_SOFTWARE = 2;
|
||||
|
||||
/**
|
||||
* Starts hotword recognition.
|
||||
* Starts sandboxed detection recognition.
|
||||
* <p>
|
||||
* On calling this, the system streams audio from the device microphone to this application's
|
||||
* {@link HotwordDetectionService}. Audio is streamed until {@link #stopRecognition()} is
|
||||
@@ -107,7 +107,7 @@ public interface HotwordDetector {
|
||||
boolean startRecognition() throws IllegalDetectorStateException;
|
||||
|
||||
/**
|
||||
* Stops hotword recognition.
|
||||
* Stops sandboxed detection recognition.
|
||||
*
|
||||
* @return {@code true} if the request to stop recognition succeeded
|
||||
* @throws IllegalDetectorStateException Thrown when a caller has a target SDK of API level 33
|
||||
@@ -142,14 +142,13 @@ public interface HotwordDetector {
|
||||
@Nullable PersistableBundle options) throws IllegalDetectorStateException;
|
||||
|
||||
/**
|
||||
* Set configuration and pass read-only data to hotword detection service.
|
||||
* Set configuration and pass read-only data to sandboxed detection service.
|
||||
*
|
||||
* @param options Application configuration data to provide to the
|
||||
* {@link HotwordDetectionService}. PersistableBundle does not allow any remotable
|
||||
* objects or other contents that can be used to communicate with other processes.
|
||||
* @param sharedMemory The unrestricted data blob to provide to the
|
||||
* {@link HotwordDetectionService}. Use this to provide the hotword models data or other
|
||||
* such data to the trusted process.
|
||||
* @param options Application configuration data to provide to sandboxed detection services.
|
||||
* PersistableBundle does not allow any remotable objects or other contents that can be used to
|
||||
* communicate with other processes.
|
||||
* @param sharedMemory The unrestricted data blob to provide to sandboxed detection services.
|
||||
* Use this to provide model data or other such data to the trusted process.
|
||||
* @throws IllegalDetectorStateException Thrown when a caller has a target SDK of API level 33
|
||||
* or above and the detector is not able to perform the operation based on the
|
||||
* underlying state. This can be thrown even if the state has been checked before
|
||||
@@ -157,19 +156,19 @@ public interface HotwordDetector {
|
||||
* and the state of the detector can change concurrently to the caller calling this
|
||||
* method.
|
||||
* @throws IllegalStateException if this HotwordDetector wasn't specified to use a
|
||||
* {@link HotwordDetectionService} when it was created.
|
||||
* sandboxed detection service when it was created.
|
||||
*/
|
||||
void updateState(@Nullable PersistableBundle options, @Nullable SharedMemory sharedMemory)
|
||||
throws IllegalDetectorStateException;
|
||||
|
||||
/**
|
||||
* Invalidates this hotword detector so that any future calls to this result
|
||||
* Invalidates this detector so that any future calls to this result
|
||||
* in an {@link IllegalStateException} when a caller has a target SDK below API level 33
|
||||
* or an {@link IllegalDetectorStateException} when a caller has a target SDK of API level 33
|
||||
* or above.
|
||||
*
|
||||
* <p>If there are no other {@link HotwordDetector} instances linked to the
|
||||
* {@link HotwordDetectionService}, the service will be shutdown.
|
||||
* sandboxed detection service, the service will be shutdown.
|
||||
*/
|
||||
default void destroy() {
|
||||
throw new UnsupportedOperationException("Not implemented. Must override in a subclass.");
|
||||
@@ -249,9 +248,9 @@ public interface HotwordDetector {
|
||||
* short amount of time to report its initialization state.
|
||||
*
|
||||
* @param status Info about initialization state of {@link HotwordDetectionService}; the
|
||||
* allowed values are {@link HotwordDetectionService#INITIALIZATION_STATUS_SUCCESS},
|
||||
* 1<->{@link HotwordDetectionService#getMaxCustomInitializationStatus()},
|
||||
* {@link HotwordDetectionService#INITIALIZATION_STATUS_UNKNOWN}.
|
||||
* allowed values are {@link SandboxedDetectionServiceBase#INITIALIZATION_STATUS_SUCCESS},
|
||||
* 1<->{@link SandboxedDetectionServiceBase#getMaxCustomInitializationStatus()},
|
||||
* {@link SandboxedDetectionServiceBase#INITIALIZATION_STATUS_UNKNOWN}.
|
||||
*/
|
||||
void onHotwordDetectionServiceInitialized(int status);
|
||||
|
||||
|
||||
@@ -0,0 +1,119 @@
|
||||
/*
|
||||
* Copyright (C) 2022 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package android.service.voice;
|
||||
|
||||
import android.annotation.DurationMillisLong;
|
||||
import android.annotation.Nullable;
|
||||
import android.annotation.SystemApi;
|
||||
import android.os.Bundle;
|
||||
import android.os.IRemoteCallback;
|
||||
import android.os.PersistableBundle;
|
||||
import android.os.RemoteException;
|
||||
import android.os.SharedMemory;
|
||||
|
||||
import java.util.function.IntConsumer;
|
||||
|
||||
/**
|
||||
* Base for all sandboxed detection services, providing a common interface for initialization.
|
||||
*
|
||||
* @hide
|
||||
*/
|
||||
@SystemApi
|
||||
public interface SandboxedDetectionServiceBase {
|
||||
|
||||
/**
|
||||
* Indicates that the updated status is successful.
|
||||
*/
|
||||
int INITIALIZATION_STATUS_SUCCESS = 0;
|
||||
|
||||
/**
|
||||
* Indicates that the callback wasn’t invoked within the timeout.
|
||||
* This is used by system.
|
||||
*/
|
||||
int INITIALIZATION_STATUS_UNKNOWN = 100;
|
||||
|
||||
/** @hide */
|
||||
String KEY_INITIALIZATION_STATUS = "initialization_status";
|
||||
|
||||
/**
|
||||
* The maximum number of initialization status for some application specific failed reasons.
|
||||
*
|
||||
* @hide
|
||||
*/
|
||||
int MAXIMUM_NUMBER_OF_INITIALIZATION_STATUS_CUSTOM_ERROR = 2;
|
||||
|
||||
/**
|
||||
* Returns the maximum number of initialization status for some application specific failed
|
||||
* reasons.
|
||||
*
|
||||
* Note: The value 0 is reserved for success.
|
||||
*/
|
||||
static int getMaxCustomInitializationStatus() {
|
||||
return MAXIMUM_NUMBER_OF_INITIALIZATION_STATUS_CUSTOM_ERROR;
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a {@link IntConsumer} that sends the initialization status to the
|
||||
* {@link VoiceInteractionService} via {@link IRemoteCallback}.
|
||||
*
|
||||
* @hide
|
||||
*/
|
||||
static IntConsumer createInitializationStatusConsumer(IRemoteCallback callback) {
|
||||
IntConsumer intConsumer = null;
|
||||
if (callback != null) {
|
||||
intConsumer =
|
||||
value -> {
|
||||
if (value > SandboxedDetectionServiceBase
|
||||
.getMaxCustomInitializationStatus()) {
|
||||
throw new IllegalArgumentException(
|
||||
"The initialization status is invalid for " + value);
|
||||
}
|
||||
try {
|
||||
Bundle status = new Bundle();
|
||||
status.putInt(KEY_INITIALIZATION_STATUS, value);
|
||||
callback.sendResult(status);
|
||||
} catch (RemoteException e) {
|
||||
throw e.rethrowFromSystemServer();
|
||||
}
|
||||
};
|
||||
}
|
||||
return intConsumer;
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when sandboxed detectors that extend {@link HotwordDetector} are created or
|
||||
* {@link HotwordDetector#updateState(PersistableBundle, SharedMemory)} requests an
|
||||
* update of the sandboxed detection parameters.
|
||||
*
|
||||
* @param options Application configuration data to provide to sandboxed detection services.
|
||||
* PersistableBundle does not allow any remotable objects or other contents that can be used to
|
||||
* communicate with other processes.
|
||||
* @param sharedMemory The unrestricted data blob to provide to sandboxed detection services.
|
||||
* Use this to provide model data or other such data to the trusted process.
|
||||
* @param callbackTimeoutMillis Timeout in milliseconds for the operation to invoke the
|
||||
* statusCallback.
|
||||
* @param statusCallback Use this to return the updated result; the allowed values are
|
||||
* {@link #INITIALIZATION_STATUS_SUCCESS}, 1<->{@link #getMaxCustomInitializationStatus()}.
|
||||
* This is non-null only when sandboxed detection services are being initialized; and it
|
||||
* is null if the state is updated after that.
|
||||
*/
|
||||
void onUpdateState(
|
||||
@Nullable PersistableBundle options,
|
||||
@Nullable SharedMemory sharedMemory,
|
||||
@DurationMillisLong long callbackTimeoutMillis,
|
||||
@Nullable IntConsumer statusCallback);
|
||||
}
|
||||
Reference in New Issue
Block a user