Merge "Add VTS for measurement type UTRAN ECNO"
diff --git a/audio/aidl/Android.bp b/audio/aidl/Android.bp
index c3647b0..7d474b2 100644
--- a/audio/aidl/Android.bp
+++ b/audio/aidl/Android.bp
@@ -132,6 +132,7 @@
"android.hardware.common-V2",
"android.hardware.common.fmq-V1",
"android.hardware.audio.common-V1",
+ "android.hardware.audio.effect-V1",
"android.media.audio.common.types-V2",
],
backend: {
@@ -169,6 +170,53 @@
],
}
+// Used for the standalone sounddose HAL
+aidl_interface {
+ name: "android.hardware.audio.core.sounddose",
+ defaults: [
+ "android.hardware.audio_defaults",
+ ],
+ srcs: [
+ "android/hardware/audio/core/ISoundDose.aidl",
+ ],
+ imports: [
+ "android.media.audio.common.types-V2",
+ ],
+ backend: {
+ // The C++ backend is disabled transitively due to use of FMQ by the core HAL.
+ cpp: {
+ enabled: false,
+ },
+ java: {
+ sdk_version: "module_current",
+ },
+ },
+ versions_with_info: [
+ // IMPORTANT: Update latest_android_hardware_audio_core_sounddose every time you
+ // add the latest frozen version to versions_with_info
+ ],
+}
+
+// Note: This should always be one version ahead of the last frozen version
+latest_android_hardware_audio_core_sounddose = "android.hardware.audio.core.sounddose-V1"
+
+// Modules that depend on android.hardware.audio.core.sounddose directly can include
+// the following cc_defaults to avoid explicitly managing dependency versions
+// across many scattered files.
+cc_defaults {
+ name: "latest_android_hardware_audio_core_sounddose_ndk_shared",
+ shared_libs: [
+ latest_android_hardware_audio_core_sounddose + "-ndk",
+ ],
+}
+
+cc_defaults {
+ name: "latest_android_hardware_audio_core_sounddose_ndk_static",
+ static_libs: [
+ latest_android_hardware_audio_core_sounddose + "-ndk",
+ ],
+}
+
aidl_interface {
name: "android.hardware.audio.effect",
defaults: [
diff --git a/audio/aidl/TEST_MAPPING b/audio/aidl/TEST_MAPPING
index b4607f9..dfd82c3 100644
--- a/audio/aidl/TEST_MAPPING
+++ b/audio/aidl/TEST_MAPPING
@@ -10,6 +10,9 @@
"name": "VtsHalAudioEffectTargetTest"
},
{
+ "name": "VtsHalDownmixTargetTest"
+ },
+ {
"name": "VtsHalEqualizerTargetTest"
},
{
diff --git a/audio/aidl/aidl_api/android.hardware.audio.core.sounddose/current/android/hardware/audio/core/ISoundDose.aidl b/audio/aidl/aidl_api/android.hardware.audio.core.sounddose/current/android/hardware/audio/core/ISoundDose.aidl
new file mode 100644
index 0000000..bc010ca
--- /dev/null
+++ b/audio/aidl/aidl_api/android.hardware.audio.core.sounddose/current/android/hardware/audio/core/ISoundDose.aidl
@@ -0,0 +1,52 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.audio.core;
+@VintfStability
+interface ISoundDose {
+ void setOutputRs2(float rs2ValueDbA);
+ float getOutputRs2();
+ void registerSoundDoseCallback(in android.hardware.audio.core.ISoundDose.IHalSoundDoseCallback callback);
+ const int DEFAULT_MAX_RS2 = 100;
+ const int MIN_RS2 = 80;
+ @VintfStability
+ interface IHalSoundDoseCallback {
+ oneway void onMomentaryExposureWarning(float currentDbA, in android.media.audio.common.AudioDevice audioDevice);
+ oneway void onNewMelValues(in android.hardware.audio.core.ISoundDose.IHalSoundDoseCallback.MelRecord melRecord, in android.media.audio.common.AudioDevice audioDevice);
+ @VintfStability
+ parcelable MelRecord {
+ float[] melValues;
+ long timestamp;
+ }
+ }
+}
diff --git a/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IModule.aidl b/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IModule.aidl
index ebfa94b..dd2279d 100644
--- a/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IModule.aidl
+++ b/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IModule.aidl
@@ -64,6 +64,8 @@
int generateHwAvSyncId();
android.hardware.audio.core.VendorParameter[] getVendorParameters(in @utf8InCpp String[] ids);
void setVendorParameters(in android.hardware.audio.core.VendorParameter[] parameters, boolean async);
+ void addDeviceEffect(int portConfigId, in android.hardware.audio.effect.IEffect effect);
+ void removeDeviceEffect(int portConfigId, in android.hardware.audio.effect.IEffect effect);
@VintfStability
parcelable OpenInputStreamArguments {
int portConfigId;
diff --git a/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IStreamCommon.aidl b/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IStreamCommon.aidl
index 8471c79..f0bf100 100644
--- a/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IStreamCommon.aidl
+++ b/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IStreamCommon.aidl
@@ -38,4 +38,6 @@
void updateHwAvSyncId(int hwAvSyncId);
android.hardware.audio.core.VendorParameter[] getVendorParameters(in @utf8InCpp String[] ids);
void setVendorParameters(in android.hardware.audio.core.VendorParameter[] parameters, boolean async);
+ void addEffect(in android.hardware.audio.effect.IEffect effect);
+ void removeEffect(in android.hardware.audio.effect.IEffect effect);
}
diff --git a/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IStreamIn.aidl b/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IStreamIn.aidl
index 98acf5f..68f1ff3 100644
--- a/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IStreamIn.aidl
+++ b/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IStreamIn.aidl
@@ -41,9 +41,13 @@
float getMicrophoneFieldDimension();
void setMicrophoneFieldDimension(float zoom);
void updateMetadata(in android.hardware.audio.common.SinkMetadata sinkMetadata);
+ float[] getHwGain();
+ void setHwGain(in float[] channelGains);
const int MIC_FIELD_DIMENSION_WIDE_ANGLE = -1;
const int MIC_FIELD_DIMENSION_NO_ZOOM = 0;
const int MIC_FIELD_DIMENSION_MAX_ZOOM = 1;
+ const int HW_GAIN_MIN = 0;
+ const int HW_GAIN_MAX = 1;
@Backing(type="int") @VintfStability
enum MicrophoneDirection {
UNSPECIFIED = 0,
diff --git a/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IStreamOut.aidl b/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IStreamOut.aidl
index 5ea2a12..092b801 100644
--- a/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IStreamOut.aidl
+++ b/audio/aidl/aidl_api/android.hardware.audio.core/current/android/hardware/audio/core/IStreamOut.aidl
@@ -36,4 +36,8 @@
interface IStreamOut {
android.hardware.audio.core.IStreamCommon getStreamCommon();
void updateMetadata(in android.hardware.audio.common.SourceMetadata sourceMetadata);
+ float[] getHwVolume();
+ void setHwVolume(in float[] channelVolumes);
+ const int HW_VOLUME_MIN = 0;
+ const int HW_VOLUME_MAX = 1;
}
diff --git a/audio/aidl/android/hardware/audio/core/IModule.aidl b/audio/aidl/android/hardware/audio/core/IModule.aidl
index 7facc6c..b278ac4 100644
--- a/audio/aidl/android/hardware/audio/core/IModule.aidl
+++ b/audio/aidl/android/hardware/audio/core/IModule.aidl
@@ -30,6 +30,7 @@
import android.hardware.audio.core.ModuleDebug;
import android.hardware.audio.core.StreamDescriptor;
import android.hardware.audio.core.VendorParameter;
+import android.hardware.audio.effect.IEffect;
import android.media.audio.common.AudioOffloadInfo;
import android.media.audio.common.AudioPort;
import android.media.audio.common.AudioPortConfig;
@@ -515,7 +516,8 @@
* @throws EX_ILLEGAL_ARGUMENT If the port config can not be found by the ID.
* @throws EX_ILLEGAL_STATE In the following cases:
* - If the port config has a stream opened on it;
- * - If the port config is used by a patch.
+ * - If the port config is used by a patch;
+ * - If the port config has an audio effect on it.
*/
void resetAudioPortConfig(int portConfigId);
@@ -728,4 +730,34 @@
* @throws EX_UNSUPPORTED_OPERATION If the module does not support vendor parameters.
*/
void setVendorParameters(in VendorParameter[] parameters, boolean async);
+
+ /**
+ * Apply an audio effect to a device port.
+ *
+ * The audio effect applies to all audio input or output on the specific
+ * configuration of the device audio port. The effect is inserted according
+ * to its insertion preference specified by the 'flags.insert' field of the
+ * EffectDescriptor.
+ *
+ * @param portConfigId The ID of the audio port config.
+ * @param effect The effect instance.
+ * @throws EX_ILLEGAL_ARGUMENT If the device port config can not be found by the ID,
+ * or the effect reference is invalid.
+ * @throws EX_UNSUPPORTED_OPERATION If the module does not support device port effects.
+ */
+ void addDeviceEffect(int portConfigId, in IEffect effect);
+
+ /**
+ * Stop applying an audio effect to a device port.
+ *
+ * Undo the action of the 'addDeviceEffect' method.
+ *
+ * @param portConfigId The ID of the audio port config.
+ * @param effect The effect instance.
+ * @throws EX_ILLEGAL_ARGUMENT If the device port config can not be found by the ID,
+ * or the effect reference is invalid, or the effect is
+ * not currently applied to the port config.
+ * @throws EX_UNSUPPORTED_OPERATION If the module does not support device port effects.
+ */
+ void removeDeviceEffect(int portConfigId, in IEffect effect);
}
diff --git a/audio/aidl/android/hardware/audio/core/IStreamCommon.aidl b/audio/aidl/android/hardware/audio/core/IStreamCommon.aidl
index 84f7309..533ef67 100644
--- a/audio/aidl/android/hardware/audio/core/IStreamCommon.aidl
+++ b/audio/aidl/android/hardware/audio/core/IStreamCommon.aidl
@@ -17,6 +17,7 @@
package android.hardware.audio.core;
import android.hardware.audio.core.VendorParameter;
+import android.hardware.audio.effect.IEffect;
/**
* This interface contains operations that are common to input and output
@@ -86,4 +87,30 @@
* @throws EX_UNSUPPORTED_OPERATION If the stream does not support vendor parameters.
*/
void setVendorParameters(in VendorParameter[] parameters, boolean async);
+
+ /**
+ * Apply an audio effect to the stream.
+ *
+ * This method is intended for the cases when the effect has an offload
+ * implementation, since software effects can be applied at the client side.
+ *
+ * @param effect The effect instance.
+ * @throws EX_ILLEGAL_ARGUMENT If the effect reference is invalid.
+ * @throws EX_ILLEGAL_STATE If the stream is closed.
+ * @throws EX_UNSUPPORTED_OPERATION If the module does not support audio effects.
+ */
+ void addEffect(in IEffect effect);
+
+ /**
+ * Stop applying an audio effect to the stream.
+ *
+ * Undo the action of the 'addEffect' method.
+ *
+ * @param effect The effect instance.
+ * @throws EX_ILLEGAL_ARGUMENT If the effect reference is invalid, or the effect is
+ * not currently applied to the stream.
+ * @throws EX_ILLEGAL_STATE If the stream is closed.
+ * @throws EX_UNSUPPORTED_OPERATION If the module does not support audio effects.
+ */
+ void removeEffect(in IEffect effect);
}
diff --git a/audio/aidl/android/hardware/audio/core/IStreamIn.aidl b/audio/aidl/android/hardware/audio/core/IStreamIn.aidl
index 92788a6..c2b3633 100644
--- a/audio/aidl/android/hardware/audio/core/IStreamIn.aidl
+++ b/audio/aidl/android/hardware/audio/core/IStreamIn.aidl
@@ -131,4 +131,38 @@
* @throws EX_ILLEGAL_STATE If the stream is closed.
*/
void updateMetadata(in SinkMetadata sinkMetadata);
+
+ const int HW_GAIN_MIN = 0;
+ const int HW_GAIN_MAX = 1;
+ /**
+ * Retrieve current gain applied in hardware.
+ *
+ * In case when the HAL module has a gain controller, this method returns
+ * the current value of its gain for each input channel.
+ *
+ * The valid range for gain is [0.0f, 1.0f], where 1.0f corresponds to unity
+ * gain, 0.0f corresponds to full mute (see HW_GAIN_* constants).
+ *
+ * @return Current gain values for each input channel.
+ * @throws EX_ILLEGAL_STATE If the stream is closed.
+ * @throws EX_UNSUPPORTED_OPERATION If hardware gain control is not supported.
+ */
+ float[] getHwGain();
+ /**
+ * Set gain applied in hardware.
+ *
+ * In case when the HAL module has a gain controller, this method sets the
+ * current value of its gain for each input channel.
+ *
+ * The valid range for gain is [0.0f, 1.0f], where 1.0f corresponds to unity
+ * gain, 0.0f corresponds to full mute (see HW_GAIN_* constants).
+ *
+ * @param gain Gain values for each input channel.
+ * @throws EX_ILLEGAL_ARGUMENT If the number of elements in the provided
+ * array does not match the channel count, or
+ * gain values are out of range.
+ * @throws EX_ILLEGAL_STATE If the stream is closed.
+ * @throws EX_UNSUPPORTED_OPERATION If hardware gain control is not supported.
+ */
+ void setHwGain(in float[] channelGains);
}
diff --git a/audio/aidl/android/hardware/audio/core/IStreamOut.aidl b/audio/aidl/android/hardware/audio/core/IStreamOut.aidl
index f7fc77a..85da00d 100644
--- a/audio/aidl/android/hardware/audio/core/IStreamOut.aidl
+++ b/audio/aidl/android/hardware/audio/core/IStreamOut.aidl
@@ -44,4 +44,46 @@
* @throws EX_ILLEGAL_STATE If the stream is closed.
*/
void updateMetadata(in SourceMetadata sourceMetadata);
+
+ const int HW_VOLUME_MIN = 0;
+ const int HW_VOLUME_MAX = 1;
+ /**
+ * Retrieve current attenuation applied in hardware.
+ *
+ * Hardware attenuation can be used in cases when the client can not, or is
+ * not allowed to modify the audio stream, for example because the stream is
+ * encoded.
+ *
+ * The valid range for attenuation is [0.0f, 1.0f], where 1.0f corresponds
+ * to unity gain, 0.0f corresponds to full mute (see HW_VOLUME_*
+ * constants). The returned array specifies attenuation for each output
+ * channel of the stream.
+ *
+ * Support of hardware volume control is optional.
+ *
+ * @return Current attenuation values for each output channel.
+ * @throws EX_ILLEGAL_STATE If the stream is closed.
+ * @throws EX_UNSUPPORTED_OPERATION If hardware volume control is not supported.
+ */
+ float[] getHwVolume();
+ /**
+ * Set attenuation applied in hardware.
+ *
+ * Hardware attenuation can be used in cases when the client can not, or is
+ * not allowed to modify the audio stream, for example because the stream is
+ * encoded.
+ *
+ * The valid range for attenuation is [0.0f, 1.0f], where 1.0f corresponds
+ * to unity gain, 0.0f corresponds to full mute (see HW_VOLUME_* constants).
+ *
+ * Support of hardware volume control is optional.
+ *
+ * @param channelVolumes Attenuation values for each output channel.
+ * @throws EX_ILLEGAL_ARGUMENT If the number of elements in the provided
+ * array does not match the channel count, or
+ * attenuation values are out of range.
+ * @throws EX_ILLEGAL_STATE If the stream is closed.
+ * @throws EX_UNSUPPORTED_OPERATION If hardware volume control is not supported.
+ */
+ void setHwVolume(in float[] channelVolumes);
}
diff --git a/audio/aidl/default/Android.bp b/audio/aidl/default/Android.bp
index b9b8cd8..a938551 100644
--- a/audio/aidl/default/Android.bp
+++ b/audio/aidl/default/Android.bp
@@ -29,6 +29,29 @@
],
}
+cc_library {
+ name: "libaudioservicesounddoseimpl",
+ vendor: true,
+ defaults: [
+ "latest_android_media_audio_common_types_ndk_shared",
+ "latest_android_hardware_audio_core_sounddose_ndk_shared",
+ "latest_android_hardware_audio_sounddose_ndk_shared",
+ ],
+ export_include_dirs: ["include"],
+ srcs: [
+ "SoundDose.cpp",
+ ],
+ shared_libs: [
+ "libbase",
+ "libbinder_ndk",
+ "libcutils",
+ "libutils",
+ ],
+ visibility: [
+ "//hardware/interfaces/audio/aidl/sounddose/default",
+ ],
+}
+
cc_library_static {
name: "libaudioserviceexampleimpl",
defaults: [
@@ -128,11 +151,12 @@
shared_libs: [
"libbassboostsw",
"libbundleaidl",
+ "libdownmixaidl",
"libdynamicsprocessingsw",
"libenvreverbsw",
"libequalizersw",
"libhapticgeneratorsw",
- "libloudnessenhancersw",
+ "libloudnessenhanceraidl",
"libpresetreverbsw",
"libtinyxml2",
"libvirtualizersw",
diff --git a/audio/aidl/default/Module.cpp b/audio/aidl/default/Module.cpp
index d52e328..4a424bd 100644
--- a/audio/aidl/default/Module.cpp
+++ b/audio/aidl/default/Module.cpp
@@ -969,4 +969,28 @@
return ndk::ScopedAStatus::fromExceptionCode(EX_UNSUPPORTED_OPERATION);
}
+ndk::ScopedAStatus Module::addDeviceEffect(
+ int32_t in_portConfigId,
+ const std::shared_ptr<::aidl::android::hardware::audio::effect::IEffect>& in_effect) {
+ if (in_effect == nullptr) {
+ LOG(DEBUG) << __func__ << ": port id " << in_portConfigId << ", null effect";
+ } else {
+ LOG(DEBUG) << __func__ << ": port id " << in_portConfigId << ", effect Binder "
+ << in_effect->asBinder().get();
+ }
+ return ndk::ScopedAStatus::fromExceptionCode(EX_UNSUPPORTED_OPERATION);
+}
+
+ndk::ScopedAStatus Module::removeDeviceEffect(
+ int32_t in_portConfigId,
+ const std::shared_ptr<::aidl::android::hardware::audio::effect::IEffect>& in_effect) {
+ if (in_effect == nullptr) {
+ LOG(DEBUG) << __func__ << ": port id " << in_portConfigId << ", null effect";
+ } else {
+ LOG(DEBUG) << __func__ << ": port id " << in_portConfigId << ", effect Binder "
+ << in_effect->asBinder().get();
+ }
+ return ndk::ScopedAStatus::fromExceptionCode(EX_UNSUPPORTED_OPERATION);
+}
+
} // namespace aidl::android::hardware::audio::core
diff --git a/audio/aidl/default/Stream.cpp b/audio/aidl/default/Stream.cpp
index 424c3e4..bb123a2 100644
--- a/audio/aidl/default/Stream.cpp
+++ b/audio/aidl/default/Stream.cpp
@@ -541,6 +541,28 @@
}
template <class Metadata, class StreamWorker>
+ndk::ScopedAStatus StreamCommonImpl<Metadata, StreamWorker>::addEffect(
+ const std::shared_ptr<::aidl::android::hardware::audio::effect::IEffect>& in_effect) {
+ if (in_effect == nullptr) {
+ LOG(DEBUG) << __func__ << ": null effect";
+ } else {
+ LOG(DEBUG) << __func__ << ": effect Binder" << in_effect->asBinder().get();
+ }
+ return ndk::ScopedAStatus::fromExceptionCode(EX_UNSUPPORTED_OPERATION);
+}
+
+template <class Metadata, class StreamWorker>
+ndk::ScopedAStatus StreamCommonImpl<Metadata, StreamWorker>::removeEffect(
+ const std::shared_ptr<::aidl::android::hardware::audio::effect::IEffect>& in_effect) {
+ if (in_effect == nullptr) {
+ LOG(DEBUG) << __func__ << ": null effect";
+ } else {
+ LOG(DEBUG) << __func__ << ": effect Binder" << in_effect->asBinder().get();
+ }
+ return ndk::ScopedAStatus::fromExceptionCode(EX_UNSUPPORTED_OPERATION);
+}
+
+template <class Metadata, class StreamWorker>
ndk::ScopedAStatus StreamCommonImpl<Metadata, StreamWorker>::close() {
LOG(DEBUG) << __func__;
if (!isClosed()) {
@@ -658,6 +680,17 @@
return ndk::ScopedAStatus::fromExceptionCode(EX_UNSUPPORTED_OPERATION);
}
+ndk::ScopedAStatus StreamIn::getHwGain(std::vector<float>* _aidl_return) {
+ LOG(DEBUG) << __func__;
+ (void)_aidl_return;
+ return ndk::ScopedAStatus::fromExceptionCode(EX_UNSUPPORTED_OPERATION);
+}
+
+ndk::ScopedAStatus StreamIn::setHwGain(const std::vector<float>& in_channelGains) {
+ LOG(DEBUG) << __func__ << ": gains " << ::android::internal::ToString(in_channelGains);
+ return ndk::ScopedAStatus::fromExceptionCode(EX_UNSUPPORTED_OPERATION);
+}
+
// static
ndk::ScopedAStatus StreamOut::createInstance(const SourceMetadata& sourceMetadata,
StreamContext context,
@@ -680,4 +713,15 @@
LOG(DEBUG) << __func__;
}
+ndk::ScopedAStatus StreamOut::getHwVolume(std::vector<float>* _aidl_return) {
+ LOG(DEBUG) << __func__;
+ (void)_aidl_return;
+ return ndk::ScopedAStatus::fromExceptionCode(EX_UNSUPPORTED_OPERATION);
+}
+
+ndk::ScopedAStatus StreamOut::setHwVolume(const std::vector<float>& in_channelVolumes) {
+ LOG(DEBUG) << __func__ << ": gains " << ::android::internal::ToString(in_channelVolumes);
+ return ndk::ScopedAStatus::fromExceptionCode(EX_UNSUPPORTED_OPERATION);
+}
+
} // namespace aidl::android::hardware::audio::core
diff --git a/audio/aidl/default/audio_effects_config.xml b/audio/aidl/default/audio_effects_config.xml
index d22c349..9491bc3 100644
--- a/audio/aidl/default/audio_effects_config.xml
+++ b/audio/aidl/default/audio_effects_config.xml
@@ -30,10 +30,11 @@
<libraries>
<library name="bassboostsw" path="libbassboostsw.so"/>
<library name="bundle" path="libbundleaidl.so"/>
+ <library name="downmix" path="libdownmixaidl.so"/>
<library name="dynamics_processingsw" path="libdynamicsprocessingsw.so"/>
<library name="equalizersw" path="libequalizersw.so"/>
<library name="haptic_generatorsw" path="libhapticgeneratorsw.so"/>
- <library name="loudness_enhancersw" path="libloudnessenhancersw.so"/>
+ <library name="loudness_enhancer" path="libloudnessenhanceraidl.so"/>
<library name="env_reverbsw" path="libenvreverbsw.so"/>
<library name="preset_reverbsw" path="libpresetreverbsw.so"/>
<library name="virtualizersw" path="libvirtualizersw.so"/>
@@ -65,9 +66,10 @@
<libsw library="bassboostsw" uuid="fa8181f2-588b-11ed-9b6a-0242ac120002"/>
<libsw library="bundle" uuid="8631f300-72e2-11df-b57e-0002a5d5c51b"/>
</effectProxy>
+ <effect name="downmix" library="downmix" uuid="93f04452-e4fe-41cc-91f9-e475b6d1d69f"/>
<effect name="dynamics_processing" library="dynamics_processingsw" uuid="fa818d78-588b-11ed-9b6a-0242ac120002"/>
<effect name="haptic_generator" library="haptic_generatorsw" uuid="fa819110-588b-11ed-9b6a-0242ac120002"/>
- <effect name="loudness_enhancer" library="loudness_enhancersw" uuid="fa819610-588b-11ed-9b6a-0242ac120002"/>
+ <effect name="loudness_enhancer" library="loudness_enhancer" uuid="fa415329-2034-4bea-b5dc-5b381c8d1e2c"/>
<effect name="env_reverb" library="env_reverbsw" uuid="fa819886-588b-11ed-9b6a-0242ac120002"/>
<effect name="preset_reverb" library="preset_reverbsw" uuid="fa8199c6-588b-11ed-9b6a-0242ac120002"/>
<effect name="virtualizer" library="virtualizersw" uuid="fa819d86-588b-11ed-9b6a-0242ac120002"/>
diff --git a/audio/aidl/default/downmix/Android.bp b/audio/aidl/default/downmix/Android.bp
new file mode 100644
index 0000000..230b2d8
--- /dev/null
+++ b/audio/aidl/default/downmix/Android.bp
@@ -0,0 +1,40 @@
+/*
+ * 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 {
+ // See: http://go/android-license-faq
+ // A large-scale-change added 'default_applicable_licenses' to import
+ // all of the 'license_kinds' from "hardware_interfaces_license"
+ // to get the below license kinds:
+ // SPDX-license-identifier-Apache-2.0
+ default_applicable_licenses: ["hardware_interfaces_license"],
+}
+
+cc_library_shared {
+ name: "libdownmixsw",
+ defaults: [
+ "aidlaudioeffectservice_defaults",
+ "latest_android_media_audio_common_types_ndk_shared",
+ "latest_android_hardware_audio_effect_ndk_shared",
+ ],
+ srcs: [
+ "DownmixSw.cpp",
+ ":effectCommonFile",
+ ],
+ visibility: [
+ "//hardware/interfaces/audio/aidl/default",
+ ],
+}
diff --git a/audio/aidl/default/downmix/DownmixSw.cpp b/audio/aidl/default/downmix/DownmixSw.cpp
new file mode 100644
index 0000000..7bb958d
--- /dev/null
+++ b/audio/aidl/default/downmix/DownmixSw.cpp
@@ -0,0 +1,170 @@
+/*
+ * 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.
+ */
+
+#include <cstddef>
+#define LOG_TAG "AHAL_DownmixSw"
+#include <Utils.h>
+#include <algorithm>
+#include <unordered_set>
+
+#include <android-base/logging.h>
+#include <fmq/AidlMessageQueue.h>
+
+#include "DownmixSw.h"
+
+using aidl::android::hardware::audio::effect::Descriptor;
+using aidl::android::hardware::audio::effect::DownmixSw;
+using aidl::android::hardware::audio::effect::IEffect;
+using aidl::android::hardware::audio::effect::kDownmixSwImplUUID;
+using aidl::android::hardware::audio::effect::State;
+using aidl::android::media::audio::common::AudioUuid;
+
+extern "C" binder_exception_t createEffect(const AudioUuid* in_impl_uuid,
+ std::shared_ptr<IEffect>* instanceSpp) {
+ if (!in_impl_uuid || *in_impl_uuid != kDownmixSwImplUUID) {
+ LOG(ERROR) << __func__ << "uuid not supported";
+ return EX_ILLEGAL_ARGUMENT;
+ }
+ if (instanceSpp) {
+ *instanceSpp = ndk::SharedRefBase::make<DownmixSw>();
+ LOG(DEBUG) << __func__ << " instance " << instanceSpp->get() << " created";
+ return EX_NONE;
+ } else {
+ LOG(ERROR) << __func__ << " invalid input parameter!";
+ return EX_ILLEGAL_ARGUMENT;
+ }
+}
+
+extern "C" binder_exception_t queryEffect(const AudioUuid* in_impl_uuid, Descriptor* _aidl_return) {
+ if (!in_impl_uuid || *in_impl_uuid != kDownmixSwImplUUID) {
+ LOG(ERROR) << __func__ << "uuid not supported";
+ return EX_ILLEGAL_ARGUMENT;
+ }
+ *_aidl_return = DownmixSw::kDescriptor;
+ return EX_NONE;
+}
+
+namespace aidl::android::hardware::audio::effect {
+
+const std::string DownmixSw::kEffectName = "DownmixSw";
+const Downmix::Capability DownmixSw::kCapability;
+const Descriptor DownmixSw::kDescriptor = {
+ .common = {.id = {.type = kDownmixTypeUUID,
+ .uuid = kDownmixSwImplUUID,
+ .proxy = std::nullopt},
+ .flags = {.type = Flags::Type::INSERT,
+ .insert = Flags::Insert::FIRST,
+ .volume = Flags::Volume::CTRL},
+ .name = kEffectName,
+ .implementor = "The Android Open Source Project"},
+ .capability = Capability::make<Capability::downmix>(kCapability)};
+
+ndk::ScopedAStatus DownmixSw::getDescriptor(Descriptor* _aidl_return) {
+ LOG(DEBUG) << __func__ << kDescriptor.toString();
+ *_aidl_return = kDescriptor;
+ return ndk::ScopedAStatus::ok();
+}
+
+ndk::ScopedAStatus DownmixSw::setParameterSpecific(const Parameter::Specific& specific) {
+ RETURN_IF(Parameter::Specific::downmix != specific.getTag(), EX_ILLEGAL_ARGUMENT,
+ "EffectNotSupported");
+ RETURN_IF(!mContext, EX_NULL_POINTER, "nullContext");
+
+ auto& dmParam = specific.get<Parameter::Specific::downmix>();
+ auto tag = dmParam.getTag();
+
+ switch (tag) {
+ case Downmix::type: {
+ RETURN_IF(mContext->setDmType(dmParam.get<Downmix::type>()) != RetCode::SUCCESS,
+ EX_ILLEGAL_ARGUMENT, "setTypeFailed");
+ return ndk::ScopedAStatus::ok();
+ }
+ default: {
+ LOG(ERROR) << __func__ << " unsupported tag: " << toString(tag);
+ return ndk::ScopedAStatus::fromExceptionCodeWithMessage(EX_ILLEGAL_ARGUMENT,
+ "DownmixTagNotSupported");
+ }
+ }
+}
+
+ndk::ScopedAStatus DownmixSw::getParameterSpecific(const Parameter::Id& id,
+ Parameter::Specific* specific) {
+ auto tag = id.getTag();
+ RETURN_IF(Parameter::Id::downmixTag != tag, EX_ILLEGAL_ARGUMENT, "wrongIdTag");
+ auto dmId = id.get<Parameter::Id::downmixTag>();
+ auto dmIdTag = dmId.getTag();
+ switch (dmIdTag) {
+ case Downmix::Id::commonTag:
+ return getParameterDownmix(dmId.get<Downmix::Id::commonTag>(), specific);
+ default:
+ LOG(ERROR) << __func__ << " unsupported tag: " << toString(tag);
+ return ndk::ScopedAStatus::fromExceptionCodeWithMessage(EX_ILLEGAL_ARGUMENT,
+ "DownmixTagNotSupported");
+ }
+}
+
+ndk::ScopedAStatus DownmixSw::getParameterDownmix(const Downmix::Tag& tag,
+ Parameter::Specific* specific) {
+ RETURN_IF(!mContext, EX_NULL_POINTER, "nullContext");
+ Downmix dmParam;
+ switch (tag) {
+ case Downmix::type: {
+ dmParam.set<Downmix::type>(mContext->getDmType());
+ break;
+ }
+ default: {
+ LOG(ERROR) << __func__ << " unsupported tag: " << toString(tag);
+ return ndk::ScopedAStatus::fromExceptionCodeWithMessage(EX_ILLEGAL_ARGUMENT,
+ "DownmixTagNotSupported");
+ }
+ }
+
+ specific->set<Parameter::Specific::downmix>(dmParam);
+ return ndk::ScopedAStatus::ok();
+}
+
+std::shared_ptr<EffectContext> DownmixSw::createContext(const Parameter::Common& common) {
+ if (mContext) {
+ LOG(DEBUG) << __func__ << " context already exist";
+ } else {
+ mContext = std::make_shared<DownmixSwContext>(1 /* statusFmqDepth */, common);
+ }
+
+ return mContext;
+}
+
+std::shared_ptr<EffectContext> DownmixSw::getContext() {
+ return mContext;
+}
+
+RetCode DownmixSw::releaseContext() {
+ if (mContext) {
+ mContext.reset();
+ }
+ return RetCode::SUCCESS;
+}
+
+// Processing method running in EffectWorker thread.
+IEffect::Status DownmixSw::effectProcessImpl(float* in, float* out, int samples) {
+ // TODO: get data buffer and process.
+ LOG(DEBUG) << __func__ << " in " << in << " out " << out << " samples " << samples;
+ for (int i = 0; i < samples; i++) {
+ *out++ = *in++;
+ }
+ return {STATUS_OK, samples, samples};
+}
+
+} // namespace aidl::android::hardware::audio::effect
diff --git a/audio/aidl/default/downmix/DownmixSw.h b/audio/aidl/default/downmix/DownmixSw.h
new file mode 100644
index 0000000..51546c1
--- /dev/null
+++ b/audio/aidl/default/downmix/DownmixSw.h
@@ -0,0 +1,75 @@
+/*
+ * 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.
+ */
+
+#pragma once
+
+#include <aidl/android/hardware/audio/effect/BnEffect.h>
+#include <fmq/AidlMessageQueue.h>
+#include <cstdlib>
+#include <memory>
+
+#include "effect-impl/EffectImpl.h"
+#include "effect-impl/EffectUUID.h"
+
+namespace aidl::android::hardware::audio::effect {
+
+class DownmixSwContext final : public EffectContext {
+ public:
+ DownmixSwContext(int statusDepth, const Parameter::Common& common)
+ : EffectContext(statusDepth, common) {
+ LOG(DEBUG) << __func__;
+ }
+
+ RetCode setDmType(Downmix::Type type) {
+ // TODO : Add implementation to apply new type
+ mType = type;
+ return RetCode::SUCCESS;
+ }
+ Downmix::Type getDmType() const { return mType; }
+
+ private:
+ Downmix::Type mType = Downmix::Type::STRIP;
+};
+
+class DownmixSw final : public EffectImpl {
+ public:
+ static const std::string kEffectName;
+ static const Downmix::Capability kCapability;
+ static const Descriptor kDescriptor;
+ DownmixSw() { LOG(DEBUG) << __func__; }
+ ~DownmixSw() {
+ cleanUp();
+ LOG(DEBUG) << __func__;
+ }
+
+ ndk::ScopedAStatus getDescriptor(Descriptor* _aidl_return) override;
+ ndk::ScopedAStatus setParameterSpecific(const Parameter::Specific& specific) override;
+ ndk::ScopedAStatus getParameterSpecific(const Parameter::Id& id,
+ Parameter::Specific* specific) override;
+
+ std::shared_ptr<EffectContext> createContext(const Parameter::Common& common) override;
+ std::shared_ptr<EffectContext> getContext() override;
+ RetCode releaseContext() override;
+
+ std::string getEffectName() override { return kEffectName; };
+ IEffect::Status effectProcessImpl(float* in, float* out, int sample) override;
+
+ private:
+ std::shared_ptr<DownmixSwContext> mContext;
+
+ ndk::ScopedAStatus getParameterDownmix(const Downmix::Tag& tag, Parameter::Specific* specific);
+};
+} // namespace aidl::android::hardware::audio::effect
diff --git a/audio/aidl/default/include/core-impl/Module.h b/audio/aidl/default/include/core-impl/Module.h
index 6baaa76..aa05d2a 100644
--- a/audio/aidl/default/include/core-impl/Module.h
+++ b/audio/aidl/default/include/core-impl/Module.h
@@ -92,6 +92,14 @@
std::vector<VendorParameter>* _aidl_return) override;
ndk::ScopedAStatus setVendorParameters(const std::vector<VendorParameter>& in_parameters,
bool in_async) override;
+ ndk::ScopedAStatus addDeviceEffect(
+ int32_t in_portConfigId,
+ const std::shared_ptr<::aidl::android::hardware::audio::effect::IEffect>& in_effect)
+ override;
+ ndk::ScopedAStatus removeDeviceEffect(
+ int32_t in_portConfigId,
+ const std::shared_ptr<::aidl::android::hardware::audio::effect::IEffect>& in_effect)
+ override;
void cleanUpPatch(int32_t patchId);
ndk::ScopedAStatus createStreamContext(
diff --git a/audio/aidl/default/include/core-impl/Stream.h b/audio/aidl/default/include/core-impl/Stream.h
index 5746f9d..a5d240f 100644
--- a/audio/aidl/default/include/core-impl/Stream.h
+++ b/audio/aidl/default/include/core-impl/Stream.h
@@ -212,6 +212,12 @@
std::vector<VendorParameter>* _aidl_return) = 0;
virtual ndk::ScopedAStatus setVendorParameters(
const std::vector<VendorParameter>& in_parameters, bool in_async) = 0;
+ virtual ndk::ScopedAStatus addEffect(
+ const std::shared_ptr<::aidl::android::hardware::audio::effect::IEffect>&
+ in_effect) = 0;
+ virtual ndk::ScopedAStatus removeEffect(
+ const std::shared_ptr<::aidl::android::hardware::audio::effect::IEffect>&
+ in_effect) = 0;
};
class StreamCommon : public BnStreamCommon {
@@ -242,6 +248,20 @@
return delegate != nullptr ? delegate->setVendorParameters(in_parameters, in_async)
: ndk::ScopedAStatus::fromExceptionCode(EX_ILLEGAL_STATE);
}
+ ndk::ScopedAStatus addEffect(
+ const std::shared_ptr<::aidl::android::hardware::audio::effect::IEffect>& in_effect)
+ override {
+ auto delegate = mDelegate.lock();
+ return delegate != nullptr ? delegate->addEffect(in_effect)
+ : ndk::ScopedAStatus::fromExceptionCode(EX_ILLEGAL_STATE);
+ }
+ ndk::ScopedAStatus removeEffect(
+ const std::shared_ptr<::aidl::android::hardware::audio::effect::IEffect>& in_effect)
+ override {
+ auto delegate = mDelegate.lock();
+ return delegate != nullptr ? delegate->removeEffect(in_effect)
+ : ndk::ScopedAStatus::fromExceptionCode(EX_ILLEGAL_STATE);
+ }
// It is possible that on the client side the proxy for IStreamCommon will outlive
// the IStream* instance, and the server side IStream* instance will get destroyed
// while this IStreamCommon instance is still alive.
@@ -257,6 +277,12 @@
std::vector<VendorParameter>* _aidl_return) override;
ndk::ScopedAStatus setVendorParameters(const std::vector<VendorParameter>& in_parameters,
bool in_async) override;
+ ndk::ScopedAStatus addEffect(
+ const std::shared_ptr<::aidl::android::hardware::audio::effect::IEffect>& in_effect)
+ override;
+ ndk::ScopedAStatus removeEffect(
+ const std::shared_ptr<::aidl::android::hardware::audio::effect::IEffect>& in_effect)
+ override;
ndk::ScopedAStatus getStreamCommon(std::shared_ptr<IStreamCommon>* _aidl_return);
ndk::ScopedAStatus init() {
@@ -305,6 +331,8 @@
return StreamCommonImpl<::aidl::android::hardware::audio::common::SinkMetadata,
StreamInWorker>::updateMetadata(in_sinkMetadata);
}
+ ndk::ScopedAStatus getHwGain(std::vector<float>* _aidl_return) override;
+ ndk::ScopedAStatus setHwGain(const std::vector<float>& in_channelGains) override;
public:
static ndk::ScopedAStatus createInstance(
@@ -337,6 +365,8 @@
return StreamCommonImpl<::aidl::android::hardware::audio::common::SourceMetadata,
StreamOutWorker>::updateMetadata(in_sourceMetadata);
}
+ ndk::ScopedAStatus getHwVolume(std::vector<float>* _aidl_return) override;
+ ndk::ScopedAStatus setHwVolume(const std::vector<float>& in_channelVolumes) override;
public:
static ndk::ScopedAStatus createInstance(
diff --git a/audio/aidl/default/include/effect-impl/EffectUUID.h b/audio/aidl/default/include/effect-impl/EffectUUID.h
index d3c7666..c9bb1f4 100644
--- a/audio/aidl/default/include/effect-impl/EffectUUID.h
+++ b/audio/aidl/default/include/effect-impl/EffectUUID.h
@@ -69,6 +69,12 @@
0x11ed,
0x9b6a,
{0x02, 0x42, 0xac, 0x12, 0x00, 0x02}};
+// 93f04452-e4fe-41cc-91f9-e475b6d1d69f
+static const AudioUuid kDownmixImplUUID = {static_cast<int32_t>(0x93f04452),
+ 0xe4fe,
+ 0x41cc,
+ 0x91f9,
+ {0xe4, 0x75, 0xb6, 0xd1, 0xd6, 0x9f}};
// 0bed4300-ddd6-11db-8f34-0002a5d5c51b.
static const AudioUuid kEqualizerTypeUUID = {static_cast<int32_t>(0x0bed4300),
0xddd6,
@@ -129,6 +135,12 @@
0x11ed,
0x9b6a,
{0x02, 0x42, 0xac, 0x12, 0x00, 0x02}};
+// fa415329-2034-4bea-b5dc-5b381c8d1e2c
+static const AudioUuid kLoudnessEnhancerImplUUID = {static_cast<int32_t>(0xfa415329),
+ 0x2034,
+ 0x4bea,
+ 0xb5dc,
+ {0x5b, 0x38, 0x1c, 0x8d, 0x1e, 0x2c}};
// c2e5d5f0-94bd-4763-9cac-4e234d06839e
static const AudioUuid kEnvReverbTypeUUID = {static_cast<int32_t>(0xc2e5d5f0),
0x94bd,
diff --git a/audio/aidl/sounddose/Android.bp b/audio/aidl/sounddose/Android.bp
new file mode 100644
index 0000000..85d6e21
--- /dev/null
+++ b/audio/aidl/sounddose/Android.bp
@@ -0,0 +1,70 @@
+/*
+ * 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 {
+ // See: http://go/android-license-faq
+ // A large-scale-change added 'default_applicable_licenses' to import
+ // all of the 'license_kinds' from "hardware_interfaces_license"
+ // to get the below license kinds:
+ // SPDX-license-identifier-Apache-2.0
+ default_applicable_licenses: ["hardware_interfaces_license"],
+}
+
+aidl_interface {
+ name: "android.hardware.audio.sounddose",
+ host_supported: true,
+ vendor_available: true,
+ stability: "vintf",
+ srcs: [
+ "android/hardware/audio/sounddose/ISoundDoseFactory.aidl",
+ ],
+ imports: [
+ latest_android_hardware_audio_core_sounddose,
+ ],
+ backend: {
+ // The C++ backend is disabled transitively due to use by core audio HAL.
+ cpp: {
+ enabled: false,
+ },
+ java: {
+ sdk_version: "module_current",
+ },
+ },
+ versions_with_info: [
+ // IMPORTANT: Update latest_android_hardware_audio_sounddose every time you
+ // add the latest frozen version to versions_with_info
+ ],
+}
+
+// Note: This should always be one version ahead of the last frozen version
+latest_android_hardware_audio_sounddose = "android.hardware.audio.sounddose-V1"
+
+// Modules that depend on android.hardware.audio.sounddose directly can include
+// the following cc_defaults to avoid explicitly managing dependency versions
+// across many scattered files.
+cc_defaults {
+ name: "latest_android_hardware_audio_sounddose_ndk_shared",
+ shared_libs: [
+ latest_android_hardware_audio_sounddose + "-ndk",
+ ],
+}
+
+cc_defaults {
+ name: "latest_android_hardware_audio_sounddose_ndk_static",
+ static_libs: [
+ latest_android_hardware_audio_sounddose + "-ndk",
+ ],
+}
diff --git a/audio/aidl/sounddose/aidl_api/android.hardware.audio.core.sounddose/current/android/hardware/audio/core/ISoundDose.aidl b/audio/aidl/sounddose/aidl_api/android.hardware.audio.core.sounddose/current/android/hardware/audio/core/ISoundDose.aidl
new file mode 100644
index 0000000..dff17e2
--- /dev/null
+++ b/audio/aidl/sounddose/aidl_api/android.hardware.audio.core.sounddose/current/android/hardware/audio/core/ISoundDose.aidl
@@ -0,0 +1,51 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.audio.core;
+@VintfStability
+interface ISoundDose {
+ void setOutputRs2(float rs2ValueDbA);
+ float getOutputRs2();
+ void registerSoundDoseCallback(in android.hardware.audio.core.ISoundDose.IHalSoundDoseCallback callback);
+ const int DEFAULT_MAX_RS2 = 100;
+ @VintfStability
+ interface IHalSoundDoseCallback {
+ oneway void onMomentaryExposureWarning(float currentDbA, in android.media.audio.common.AudioDevice audioDevice);
+ oneway void onNewMelValues(in android.hardware.audio.core.ISoundDose.IHalSoundDoseCallback.MelRecord melRecord, in android.media.audio.common.AudioDevice audioDevice);
+ @VintfStability
+ parcelable MelRecord {
+ float[] melValues;
+ long timestamp;
+ }
+ }
+}
diff --git a/audio/aidl/sounddose/aidl_api/android.hardware.audio.sounddose/current/android/hardware/audio/sounddose/ISoundDoseFactory.aidl b/audio/aidl/sounddose/aidl_api/android.hardware.audio.sounddose/current/android/hardware/audio/sounddose/ISoundDoseFactory.aidl
new file mode 100644
index 0000000..7dda011
--- /dev/null
+++ b/audio/aidl/sounddose/aidl_api/android.hardware.audio.sounddose/current/android/hardware/audio/sounddose/ISoundDoseFactory.aidl
@@ -0,0 +1,38 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.audio.sounddose;
+@VintfStability
+interface ISoundDoseFactory {
+ @nullable android.hardware.audio.core.ISoundDose getSoundDose(in @utf8InCpp String module);
+}
diff --git a/audio/aidl/sounddose/android/hardware/audio/sounddose/ISoundDoseFactory.aidl b/audio/aidl/sounddose/android/hardware/audio/sounddose/ISoundDoseFactory.aidl
new file mode 100644
index 0000000..3487237
--- /dev/null
+++ b/audio/aidl/sounddose/android/hardware/audio/sounddose/ISoundDoseFactory.aidl
@@ -0,0 +1,44 @@
+/*
+ * 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.hardware.audio.sounddose;
+
+import android.hardware.audio.core.ISoundDose;
+
+/**
+ * This interface is used to provide an easy way to implement the ISoundDose interface
+ * without switching the audio HAL to AIDL. The implementation is intended as a workaround
+ * for the certification with IEC62368-1 3rd edition and EN50332-3.
+ * Note that this interface will be deprecated in favor of the audio AIDL HAL.
+ */
+@VintfStability
+interface ISoundDoseFactory {
+ /**
+ * Retrieve the sound dose interface for a given audio HAL module name.
+ *
+ * If a device must comply to IEC62368-1 3rd edition audio safety requirements and is
+ * implementing audio offload decoding or other direct playback paths where volume control
+ * happens below the audio HAL, it must return an instance of the ISoundDose interface.
+ * The same instance must be returned during the lifetime of the HAL module.
+ * If the HAL module does not support sound dose, null must be returned, without throwing
+ * any errors.
+ *
+ * @param module for which we trigger sound dose updates.
+ * @return An instance of the ISoundDose interface implementation.
+ * @throws EX_ILLEGAL_STATE If there was an error creating an instance.
+ */
+ @nullable ISoundDose getSoundDose(in @utf8InCpp String module);
+}
diff --git a/audio/aidl/sounddose/default/Android.bp b/audio/aidl/sounddose/default/Android.bp
new file mode 100644
index 0000000..bd770fa
--- /dev/null
+++ b/audio/aidl/sounddose/default/Android.bp
@@ -0,0 +1,46 @@
+package {
+ // See: http://go/android-license-faq
+ // A large-scale-change added 'default_applicable_licenses' to import
+ // all of the 'license_kinds' from "hardware_interfaces_license"
+ // to get the below license kinds:
+ // SPDX-license-identifier-Apache-2.0
+ default_applicable_licenses: ["hardware_interfaces_license"],
+}
+
+cc_defaults {
+ name: "aidlsounddoseservice_defaults",
+ vendor: true,
+ header_libs: [
+ "libsounddoseaidl_headers",
+ ],
+}
+
+cc_library {
+ name: "libsounddoseserviceexampleimpl",
+ defaults: [
+ "aidlsounddoseservice_defaults",
+ "latest_android_media_audio_common_types_ndk_shared",
+ "latest_android_hardware_audio_core_sounddose_ndk_shared",
+ "latest_android_hardware_audio_sounddose_ndk_shared",
+ ],
+ export_include_dirs: ["include"],
+ srcs: [
+ "SoundDoseFactory.cpp",
+ ],
+ shared_libs: [
+ "libaudioservicesounddoseimpl",
+ "libbase",
+ "libbinder_ndk",
+ ],
+
+ visibility: [
+ "//hardware/interfaces/audio/common/all-versions/default/service",
+ ],
+}
+
+cc_library_headers {
+ name: "libsounddoseaidl_headers",
+ export_include_dirs: ["include"],
+ vendor_available: true,
+ host_supported: true,
+}
diff --git a/audio/aidl/sounddose/default/SoundDoseFactory.cpp b/audio/aidl/sounddose/default/SoundDoseFactory.cpp
new file mode 100644
index 0000000..50796d0
--- /dev/null
+++ b/audio/aidl/sounddose/default/SoundDoseFactory.cpp
@@ -0,0 +1,49 @@
+/*
+ * 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.
+ */
+
+#define LOG_TAG "AHAL_SoundDoseFactory"
+
+#include "SoundDoseFactory.h"
+
+#include <android-base/logging.h>
+#include <core-impl/SoundDose.h>
+
+namespace aidl::android::hardware::audio::sounddose {
+
+using ::aidl::android::hardware::audio::core::SoundDose;
+
+ndk::ScopedAStatus SoundDoseFactory::getSoundDose(const std::string& in_module,
+ std::shared_ptr<ISoundDose>* _aidl_return) {
+ auto soundDoseIt = mSoundDoseBinderMap.find(in_module);
+ if (soundDoseIt != mSoundDoseBinderMap.end()) {
+ *_aidl_return = ISoundDose::fromBinder(soundDoseIt->second);
+
+ LOG(DEBUG) << __func__
+ << ": returning cached instance of ISoundDose: " << _aidl_return->get()
+ << " for module " << in_module;
+ return ndk::ScopedAStatus::ok();
+ }
+
+ auto soundDose = ndk::SharedRefBase::make<SoundDose>();
+ mSoundDoseBinderMap[in_module] = soundDose->asBinder();
+ *_aidl_return = soundDose;
+
+ LOG(DEBUG) << __func__ << ": returning new instance of ISoundDose: " << _aidl_return->get()
+ << " for module " << in_module;
+ return ndk::ScopedAStatus::ok();
+}
+
+} // namespace aidl::android::hardware::audio::sounddose
diff --git a/audio/aidl/sounddose/default/include/SoundDoseFactory.h b/audio/aidl/sounddose/default/include/SoundDoseFactory.h
new file mode 100644
index 0000000..4cf3277
--- /dev/null
+++ b/audio/aidl/sounddose/default/include/SoundDoseFactory.h
@@ -0,0 +1,38 @@
+/*
+ * 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.
+ */
+
+#pragma once
+
+#include <aidl/android/hardware/audio/core/ISoundDose.h>
+#include <aidl/android/hardware/audio/sounddose/BnSoundDoseFactory.h>
+#include <android/binder_interface_utils.h>
+
+#include <unordered_map>
+
+namespace aidl::android::hardware::audio::sounddose {
+
+using ::aidl::android::hardware::audio::core::ISoundDose;
+
+class SoundDoseFactory : public BnSoundDoseFactory {
+ public:
+ ndk::ScopedAStatus getSoundDose(const std::string& module,
+ std::shared_ptr<ISoundDose>* _aidl_return) override;
+
+ private:
+ std::unordered_map<std::string, ndk::SpAIBinder> mSoundDoseBinderMap;
+};
+
+} // namespace aidl::android::hardware::audio::sounddose
diff --git a/audio/aidl/sounddose/vts/Android.bp b/audio/aidl/sounddose/vts/Android.bp
new file mode 100644
index 0000000..88be968
--- /dev/null
+++ b/audio/aidl/sounddose/vts/Android.bp
@@ -0,0 +1,36 @@
+package {
+ // See: http://go/android-license-faq
+ // A large-scale-change added 'default_applicable_licenses' to import
+ // all of the 'license_kinds' from "hardware_interfaces_license"
+ // to get the below license kinds:
+ // SPDX-license-identifier-Apache-2.0
+ default_applicable_licenses: ["hardware_interfaces_license"],
+}
+
+cc_test {
+ name: "VtsHalSoundDoseFactoryTargetTest",
+ defaults: [
+ "latest_android_hardware_audio_core_sounddose_ndk_static",
+ "latest_android_hardware_audio_sounddose_ndk_static",
+ "latest_android_media_audio_common_types_ndk_static",
+ "use_libaidlvintf_gtest_helper_static",
+ "VtsHalTargetTestDefaults",
+ ],
+ shared_libs: [
+ "libbinder_ndk",
+ "libcutils",
+ ],
+ srcs: [
+ "VtsHalSoundDoseFactoryTargetTest.cpp",
+ ],
+ cflags: [
+ "-Wall",
+ "-Wextra",
+ "-Werror",
+ "-Wthread-safety",
+ ],
+ test_suites: [
+ "general-tests",
+ "vts",
+ ],
+}
diff --git a/audio/aidl/sounddose/vts/TEST_MAPPING b/audio/aidl/sounddose/vts/TEST_MAPPING
new file mode 100644
index 0000000..bebeed9
--- /dev/null
+++ b/audio/aidl/sounddose/vts/TEST_MAPPING
@@ -0,0 +1,7 @@
+{
+ "presubmit": [
+ {
+ "name": "VtsHalSoundDoseFactoryTargetTest"
+ }
+ ]
+}
diff --git a/audio/aidl/sounddose/vts/VtsHalSoundDoseFactoryTargetTest.cpp b/audio/aidl/sounddose/vts/VtsHalSoundDoseFactoryTargetTest.cpp
new file mode 100644
index 0000000..7448c1f
--- /dev/null
+++ b/audio/aidl/sounddose/vts/VtsHalSoundDoseFactoryTargetTest.cpp
@@ -0,0 +1,96 @@
+/*
+ * 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.
+ */
+
+#define LOG_TAG "VtsHalSoundDose.Factory"
+#include <android-base/logging.h>
+
+#include <aidl/Gtest.h>
+#include <aidl/Vintf.h>
+#include <aidl/android/hardware/audio/sounddose/ISoundDoseFactory.h>
+#include <android/binder_manager.h>
+
+#include <memory>
+
+namespace android::hardware::audio::common::testing {
+
+namespace detail {
+
+inline ::testing::AssertionResult assertIsOk(const char* expr, const ::ndk::ScopedAStatus& status) {
+ if (status.isOk()) {
+ return ::testing::AssertionSuccess();
+ }
+ return ::testing::AssertionFailure()
+ << "Expected the transaction \'" << expr << "\' to succeed\n"
+ << " but it has failed with: " << status;
+}
+
+} // namespace detail
+
+} // namespace android::hardware::audio::common::testing
+
+// Test that the transaction status 'isOk'
+#define EXPECT_IS_OK(ret) \
+ EXPECT_PRED_FORMAT1(::android::hardware::audio::common::testing::detail::assertIsOk, ret)
+
+using namespace android;
+
+using aidl::android::hardware::audio::core::ISoundDose;
+using aidl::android::hardware::audio::sounddose::ISoundDoseFactory;
+
+class SoundDoseFactory : public testing::TestWithParam<std::string> {
+ public:
+ void SetUp() override { ASSERT_NO_FATAL_FAILURE(ConnectToService(GetParam())); }
+
+ void TearDown() override {}
+
+ void ConnectToService(const std::string& interfaceName) {
+ ndk::SpAIBinder binder =
+ ndk::SpAIBinder(AServiceManager_waitForService(interfaceName.c_str()));
+ if (binder == nullptr) {
+ LOG(ERROR) << "Failed to get service " << interfaceName;
+ } else {
+ LOG(DEBUG) << "Succeeded to get service " << interfaceName;
+ }
+ soundDoseFactory = ISoundDoseFactory::fromBinder(binder);
+ ASSERT_NE(soundDoseFactory, nullptr);
+ }
+
+ std::shared_ptr<ISoundDoseFactory> soundDoseFactory;
+};
+
+TEST_P(SoundDoseFactory, GetSoundDoseForSameModule) {
+ const std::string module = "primary";
+
+ std::shared_ptr<ISoundDose> soundDose1;
+ EXPECT_IS_OK(soundDoseFactory->getSoundDose(module, &soundDose1));
+
+ if (soundDose1 == nullptr) {
+ LOG(WARNING) << "Primary module does not support sound dose";
+ return;
+ }
+
+ std::shared_ptr<ISoundDose> soundDose2;
+ EXPECT_IS_OK(soundDoseFactory->getSoundDose(module, &soundDose2));
+ EXPECT_NE(nullptr, soundDose2);
+ EXPECT_EQ(soundDose1->asBinder(), soundDose2->asBinder())
+ << "getSoundDose must return the same interface for the same module";
+}
+
+INSTANTIATE_TEST_SUITE_P(
+ SoundDoseFactoryTest, SoundDoseFactory,
+ testing::ValuesIn(android::getAidlHalInstanceNames(ISoundDoseFactory::descriptor)),
+ android::PrintInstanceNameToString);
+GTEST_ALLOW_UNINSTANTIATED_PARAMETERIZED_TEST(SoundDoseFactory);
diff --git a/audio/aidl/vts/Android.bp b/audio/aidl/vts/Android.bp
index 4414e26..aeff615 100644
--- a/audio/aidl/vts/Android.bp
+++ b/audio/aidl/vts/Android.bp
@@ -24,6 +24,7 @@
"android.hardware.common-V2-ndk",
"android.hardware.common.fmq-V1-ndk",
"libaudioaidlcommon",
+ "libaidlcommonsupport",
],
header_libs: ["libaudioaidl_headers"],
cflags: [
@@ -73,6 +74,12 @@
}
cc_test {
+ name: "VtsHalDownmixTargetTest",
+ defaults: ["VtsHalAudioTargetTestDefaults"],
+ srcs: ["VtsHalDownmixTargetTest.cpp"],
+}
+
+cc_test {
name: "VtsHalEqualizerTargetTest",
defaults: ["VtsHalAudioTargetTestDefaults"],
srcs: ["VtsHalEqualizerTargetTest.cpp"],
diff --git a/audio/aidl/vts/VtsHalAudioCoreModuleTargetTest.cpp b/audio/aidl/vts/VtsHalAudioCoreModuleTargetTest.cpp
index d21b118..2508afd 100644
--- a/audio/aidl/vts/VtsHalAudioCoreModuleTargetTest.cpp
+++ b/audio/aidl/vts/VtsHalAudioCoreModuleTargetTest.cpp
@@ -82,6 +82,7 @@
using aidl::android::media::audio::common::AudioSource;
using aidl::android::media::audio::common::AudioUsage;
using aidl::android::media::audio::common::Void;
+using android::hardware::audio::common::getChannelCount;
using android::hardware::audio::common::isBitPositionFlagSet;
using android::hardware::audio::common::isTelephonyDeviceType;
using android::hardware::audio::common::StreamLogic;
@@ -189,6 +190,29 @@
AudioPortConfig mConfig;
};
+template <typename T>
+void GenerateTestArrays(size_t validElementCount, T validMin, T validMax,
+ std::vector<std::vector<T>>* validValues,
+ std::vector<std::vector<T>>* invalidValues) {
+ validValues->emplace_back(validElementCount, validMin);
+ validValues->emplace_back(validElementCount, validMax);
+ validValues->emplace_back(validElementCount, (validMin + validMax) / 2.f);
+ if (validElementCount > 0) {
+ invalidValues->emplace_back(validElementCount - 1, validMin);
+ }
+ invalidValues->emplace_back(validElementCount + 1, validMin);
+ for (auto m : {-2, -1, 2}) {
+ const auto invalidMin = m * validMin;
+ if (invalidMin < validMin || invalidMin > validMax) {
+ invalidValues->emplace_back(validElementCount, invalidMin);
+ }
+ const auto invalidMax = m * validMax;
+ if (invalidMax < validMin || invalidMax > validMax) {
+ invalidValues->emplace_back(validElementCount, invalidMax);
+ }
+ }
+}
+
template <typename PropType, class Instance, typename Getter, typename Setter>
void TestAccessors(Instance* inst, Getter getter, Setter setter,
const std::vector<PropType>& validValues,
@@ -202,13 +226,14 @@
ASSERT_TRUE(status.isOk()) << "Unexpected status from a getter: " << status;
*isSupported = true;
for (const auto v : validValues) {
- EXPECT_IS_OK((inst->*setter)(v)) << "for valid value: " << v;
+ EXPECT_IS_OK((inst->*setter)(v)) << "for a valid value: " << ::testing::PrintToString(v);
PropType currentValue{};
EXPECT_IS_OK((inst->*getter)(¤tValue));
EXPECT_EQ(v, currentValue);
}
for (const auto v : invalidValues) {
- EXPECT_STATUS(EX_ILLEGAL_ARGUMENT, (inst->*setter)(v)) << "for invalid value: " << v;
+ EXPECT_STATUS(EX_ILLEGAL_ARGUMENT, (inst->*setter)(v))
+ << "for an invalid value: " << ::testing::PrintToString(v);
}
EXPECT_IS_OK((inst->*setter)(initialValue)) << "Failed to restore the initial value";
}
@@ -1721,6 +1746,33 @@
}
}
+// See b/262930731. In the absence of offloaded effect implementations,
+// currently we can only pass a nullptr, and the HAL module must either reject
+// it as an invalid argument, or say that offloaded effects are not supported.
+TEST_P(AudioCoreModule, AddRemoveEffectInvalidArguments) {
+ ndk::ScopedAStatus addEffectStatus = module->addDeviceEffect(-1, nullptr);
+ ndk::ScopedAStatus removeEffectStatus = module->removeDeviceEffect(-1, nullptr);
+ const bool isSupported = addEffectStatus.getExceptionCode() != EX_UNSUPPORTED_OPERATION;
+ if (isSupported) {
+ EXPECT_EQ(EX_ILLEGAL_ARGUMENT, addEffectStatus.getExceptionCode());
+ EXPECT_EQ(EX_ILLEGAL_ARGUMENT, removeEffectStatus.getExceptionCode());
+ } else if (EX_UNSUPPORTED_OPERATION != removeEffectStatus.getExceptionCode()) {
+ GTEST_FAIL() << "addEffect and removeEffect must be either supported or not supported "
+ << "together";
+ } else {
+ GTEST_SKIP() << "Offloaded effects not supported";
+ }
+ // Test rejection of a nullptr effect with a valid device port Id.
+ ASSERT_NO_FATAL_FAILURE(SetUpModuleConfig());
+ const auto configs = moduleConfig->getPortConfigsForAttachedDevicePorts();
+ for (const auto& config : configs) {
+ WithAudioPortConfig portConfig(config);
+ ASSERT_NO_FATAL_FAILURE(portConfig.SetUp(module.get()));
+ EXPECT_STATUS(EX_ILLEGAL_ARGUMENT, module->addDeviceEffect(portConfig.getId(), nullptr));
+ EXPECT_STATUS(EX_ILLEGAL_ARGUMENT, module->removeDeviceEffect(portConfig.getId(), nullptr));
+ }
+}
+
class AudioCoreTelephony : public AudioCoreModuleBase, public testing::TestWithParam<std::string> {
public:
void SetUp() override {
@@ -1874,9 +1926,7 @@
}
WithStream<Stream> stream(portConfig.value());
ASSERT_NO_FATAL_FAILURE(stream.SetUpPortConfig(module.get()));
- // The buffer size of 1 frame should be impractically small, and thus
- // less than any minimum buffer size suggested by any HAL.
- for (long bufferSize : std::array<long, 4>{-1, 0, 1, std::numeric_limits<long>::max()}) {
+ for (long bufferSize : std::array<long, 3>{-1, 0, std::numeric_limits<long>::max()}) {
EXPECT_STATUS(EX_ILLEGAL_ARGUMENT, stream.SetUpNoChecks(module.get(), bufferSize))
<< "for the buffer size " << bufferSize;
EXPECT_EQ(nullptr, stream.get());
@@ -2019,6 +2069,79 @@
}
}
+ void HwGainHwVolume() {
+ const auto ports =
+ moduleConfig->getMixPorts(IOTraits<Stream>::is_input, false /*attachedOnly*/);
+ if (ports.empty()) {
+ GTEST_SKIP() << "No mix ports";
+ }
+ bool atLeastOneSupports = false;
+ for (const auto& port : ports) {
+ const auto portConfig = moduleConfig->getSingleConfigForMixPort(true, port);
+ if (!portConfig.has_value()) continue;
+ WithStream<Stream> stream(portConfig.value());
+ ASSERT_NO_FATAL_FAILURE(stream.SetUp(module.get(), kDefaultBufferSizeFrames));
+ std::vector<std::vector<float>> validValues, invalidValues;
+ bool isSupported = false;
+ if constexpr (IOTraits<Stream>::is_input) {
+ GenerateTestArrays<float>(getChannelCount(portConfig.value().channelMask.value()),
+ IStreamIn::HW_GAIN_MIN, IStreamIn::HW_GAIN_MAX,
+ &validValues, &invalidValues);
+ EXPECT_NO_FATAL_FAILURE(TestAccessors<std::vector<float>>(
+ stream.get(), &IStreamIn::getHwGain, &IStreamIn::setHwGain, validValues,
+ invalidValues, &isSupported));
+ } else {
+ GenerateTestArrays<float>(getChannelCount(portConfig.value().channelMask.value()),
+ IStreamOut::HW_VOLUME_MIN, IStreamOut::HW_VOLUME_MAX,
+ &validValues, &invalidValues);
+ EXPECT_NO_FATAL_FAILURE(TestAccessors<std::vector<float>>(
+ stream.get(), &IStreamOut::getHwVolume, &IStreamOut::setHwVolume,
+ validValues, invalidValues, &isSupported));
+ }
+ if (isSupported) atLeastOneSupports = true;
+ }
+ if (!atLeastOneSupports) {
+ GTEST_SKIP() << "Hardware gain / volume is not supported";
+ }
+ }
+
+ // See b/262930731. In the absence of offloaded effect implementations,
+ // currently we can only pass a nullptr, and the HAL module must either reject
+ // it as an invalid argument, or say that offloaded effects are not supported.
+ void AddRemoveEffectInvalidArguments() {
+ const auto ports =
+ moduleConfig->getMixPorts(IOTraits<Stream>::is_input, false /*attachedOnly*/);
+ if (ports.empty()) {
+ GTEST_SKIP() << "No mix ports";
+ }
+ bool atLeastOneSupports = false;
+ for (const auto& port : ports) {
+ const auto portConfig = moduleConfig->getSingleConfigForMixPort(true, port);
+ if (!portConfig.has_value()) continue;
+ WithStream<Stream> stream(portConfig.value());
+ ASSERT_NO_FATAL_FAILURE(stream.SetUp(module.get(), kDefaultBufferSizeFrames));
+ std::shared_ptr<IStreamCommon> streamCommon;
+ ASSERT_IS_OK(stream.get()->getStreamCommon(&streamCommon));
+ ASSERT_NE(nullptr, streamCommon);
+ ndk::ScopedAStatus addEffectStatus = streamCommon->addEffect(nullptr);
+ ndk::ScopedAStatus removeEffectStatus = streamCommon->removeEffect(nullptr);
+ const bool isSupported = addEffectStatus.getExceptionCode() != EX_UNSUPPORTED_OPERATION;
+ if (isSupported) {
+ EXPECT_EQ(EX_ILLEGAL_ARGUMENT, addEffectStatus.getExceptionCode());
+ EXPECT_EQ(EX_ILLEGAL_ARGUMENT, removeEffectStatus.getExceptionCode());
+ atLeastOneSupports = true;
+ } else if (EX_UNSUPPORTED_OPERATION != removeEffectStatus.getExceptionCode()) {
+ ADD_FAILURE()
+ << "addEffect and removeEffect must be either supported or not supported "
+ << "together";
+ atLeastOneSupports = true;
+ }
+ }
+ if (!atLeastOneSupports) {
+ GTEST_SKIP() << "Offloaded effects not supported";
+ }
+ }
+
void OpenTwiceSamePortConfigImpl(const AudioPortConfig& portConfig) {
WithStream<Stream> stream1(portConfig);
ASSERT_NO_FATAL_FAILURE(stream1.SetUp(module.get(), kDefaultBufferSizeFrames));
@@ -2095,6 +2218,8 @@
TEST_IN_AND_OUT_STREAM(UpdateHwAvSyncId);
TEST_IN_AND_OUT_STREAM(GetVendorParameters);
TEST_IN_AND_OUT_STREAM(SetVendorParameters);
+TEST_IN_AND_OUT_STREAM(HwGainHwVolume);
+TEST_IN_AND_OUT_STREAM(AddRemoveEffectInvalidArguments);
namespace aidl::android::hardware::audio::core {
std::ostream& operator<<(std::ostream& os, const IStreamIn::MicrophoneDirection& md) {
diff --git a/audio/aidl/vts/VtsHalDownmixTargetTest.cpp b/audio/aidl/vts/VtsHalDownmixTargetTest.cpp
new file mode 100644
index 0000000..8612660
--- /dev/null
+++ b/audio/aidl/vts/VtsHalDownmixTargetTest.cpp
@@ -0,0 +1,146 @@
+/*
+ * 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.
+ */
+
+#define LOG_TAG "VtsHalDownmixTargetTest"
+
+#include <Utils.h>
+#include <aidl/Vintf.h>
+#include "EffectHelper.h"
+
+using namespace android;
+
+using aidl::android::hardware::audio::effect::Capability;
+using aidl::android::hardware::audio::effect::Descriptor;
+using aidl::android::hardware::audio::effect::Downmix;
+using aidl::android::hardware::audio::effect::IEffect;
+using aidl::android::hardware::audio::effect::IFactory;
+using aidl::android::hardware::audio::effect::kDownmixTypeUUID;
+using aidl::android::hardware::audio::effect::kEffectNullUuid;
+using aidl::android::hardware::audio::effect::Parameter;
+
+/**
+ * Here we focus on specific parameter checking, general IEffect interfaces testing performed in
+ * VtsAudioEffectTargetTest.
+ */
+enum ParamName { PARAM_INSTANCE_NAME, PARAM_TYPE };
+using DownmixParamTestParam =
+ std::tuple<std::pair<std::shared_ptr<IFactory>, Descriptor>, Downmix::Type>;
+
+// Testing for enum values
+const std::vector<Downmix::Type> kTypeValues = {Downmix::Type::STRIP, Downmix::Type::FOLD};
+
+class DownmixParamTest : public ::testing::TestWithParam<DownmixParamTestParam>,
+ public EffectHelper {
+ public:
+ DownmixParamTest() : mParamType(std::get<PARAM_TYPE>(GetParam())) {
+ std::tie(mFactory, mDescriptor) = std::get<PARAM_INSTANCE_NAME>(GetParam());
+ }
+
+ void SetUp() override {
+ ASSERT_NE(nullptr, mFactory);
+ ASSERT_NO_FATAL_FAILURE(create(mFactory, mEffect, mDescriptor));
+
+ Parameter::Specific specific = getDefaultParamSpecific();
+ Parameter::Common common = EffectHelper::createParamCommon(
+ 0 /* session */, 1 /* ioHandle */, 44100 /* iSampleRate */, 44100 /* oSampleRate */,
+ kInputFrameCount /* iFrameCount */, kOutputFrameCount /* oFrameCount */);
+ IEffect::OpenEffectReturn ret;
+ ASSERT_NO_FATAL_FAILURE(open(mEffect, common, specific, &ret, EX_NONE));
+ ASSERT_NE(nullptr, mEffect);
+ }
+
+ void TearDown() override {
+ ASSERT_NO_FATAL_FAILURE(close(mEffect));
+ ASSERT_NO_FATAL_FAILURE(destroy(mFactory, mEffect));
+ }
+
+ static const long kInputFrameCount = 0x100, kOutputFrameCount = 0x100;
+ std::shared_ptr<IFactory> mFactory;
+ std::shared_ptr<IEffect> mEffect;
+ Descriptor mDescriptor;
+ Downmix::Type mParamType = Downmix::Type::STRIP;
+
+ void SetAndGetDownmixParameters() {
+ for (auto& it : mTags) {
+ auto& tag = it.first;
+ auto& dm = it.second;
+
+ // set parameter
+ Parameter expectParam;
+ Parameter::Specific specific;
+ specific.set<Parameter::Specific::downmix>(dm);
+ expectParam.set<Parameter::specific>(specific);
+ // All values are valid, set parameter should succeed
+ EXPECT_STATUS(EX_NONE, mEffect->setParameter(expectParam)) << expectParam.toString();
+
+ // get parameter
+ Parameter getParam;
+ Parameter::Id id;
+ Downmix::Id dmId;
+ dmId.set<Downmix::Id::commonTag>(tag);
+ id.set<Parameter::Id::downmixTag>(dmId);
+ EXPECT_STATUS(EX_NONE, mEffect->getParameter(id, &getParam));
+
+ EXPECT_EQ(expectParam, getParam);
+ }
+ }
+
+ void addTypeParam(Downmix::Type type) {
+ Downmix dm;
+ dm.set<Downmix::type>(type);
+ mTags.push_back({Downmix::type, dm});
+ }
+
+ Parameter::Specific getDefaultParamSpecific() {
+ Downmix dm = Downmix::make<Downmix::type>(Downmix::Type::STRIP);
+ Parameter::Specific specific = Parameter::Specific::make<Parameter::Specific::downmix>(dm);
+ return specific;
+ }
+
+ private:
+ std::vector<std::pair<Downmix::Tag, Downmix>> mTags;
+ void CleanUp() { mTags.clear(); }
+};
+
+TEST_P(DownmixParamTest, SetAndGetType) {
+ EXPECT_NO_FATAL_FAILURE(addTypeParam(mParamType));
+ SetAndGetDownmixParameters();
+}
+
+INSTANTIATE_TEST_SUITE_P(
+ DownmixTest, DownmixParamTest,
+ ::testing::Combine(testing::ValuesIn(EffectFactoryHelper::getAllEffectDescriptors(
+ IFactory::descriptor, kDownmixTypeUUID)),
+ testing::ValuesIn(kTypeValues)),
+ [](const testing::TestParamInfo<DownmixParamTest::ParamType>& info) {
+ auto descriptor = std::get<PARAM_INSTANCE_NAME>(info.param).second;
+ std::string type = std::to_string(static_cast<int>(std::get<PARAM_TYPE>(info.param)));
+ std::string name = "Implementor_" + descriptor.common.implementor + "_name_" +
+ descriptor.common.name + "_UUID_" +
+ descriptor.common.id.uuid.toString() + "_type" + type;
+ std::replace_if(
+ name.begin(), name.end(), [](const char c) { return !std::isalnum(c); }, '_');
+ return name;
+ });
+
+GTEST_ALLOW_UNINSTANTIATED_PARAMETERIZED_TEST(DownmixParamTest);
+
+int main(int argc, char** argv) {
+ ::testing::InitGoogleTest(&argc, argv);
+ ABinderProcess_setThreadPoolMaxThreadCount(1);
+ ABinderProcess_startThreadPool();
+ return RUN_ALL_TESTS();
+}
diff --git a/audio/common/all-versions/default/service/Android.bp b/audio/common/all-versions/default/service/Android.bp
index 9890be2..2fcfb23 100644
--- a/audio/common/all-versions/default/service/Android.bp
+++ b/audio/common/all-versions/default/service/Android.bp
@@ -38,9 +38,15 @@
name: "android.hardware.audio.service",
init_rc: ["android.hardware.audio.service.rc"],
+ vintf_fragments: ["android.hardware.audio.sounddose-aidl.xml"],
relative_install_path: "hw",
vendor: true,
+ defaults: [
+ "android_hardware_audio_config_defaults",
+ "latest_android_hardware_audio_sounddose_ndk_shared",
+ ],
+
srcs: ["service.cpp"],
cflags: [
@@ -50,6 +56,7 @@
],
shared_libs: [
+ "//hardware/interfaces/audio/aidl/sounddose/default:libsounddoseserviceexampleimpl",
"libcutils",
"libbinder",
"libbinder_ndk",
@@ -58,10 +65,6 @@
"libutils",
"libhardware",
],
-
- defaults: [
- "android_hardware_audio_config_defaults",
- ],
}
// Legacy service name, use android.hardware.audio.service instead
diff --git a/audio/common/all-versions/default/service/android.hardware.audio.sounddose-aidl.xml b/audio/common/all-versions/default/service/android.hardware.audio.sounddose-aidl.xml
new file mode 100644
index 0000000..a297bfb
--- /dev/null
+++ b/audio/common/all-versions/default/service/android.hardware.audio.sounddose-aidl.xml
@@ -0,0 +1,7 @@
+<manifest version="1.0" type="device">
+ <hal format="aidl">
+ <name>android.hardware.audio.sounddose</name>
+ <version>1</version>
+ <fqname>ISoundDoseFactory/default</fqname>
+ </hal>
+</manifest>
diff --git a/audio/common/all-versions/default/service/service.cpp b/audio/common/all-versions/default/service/service.cpp
index fbf6165..e79ad75 100644
--- a/audio/common/all-versions/default/service/service.cpp
+++ b/audio/common/all-versions/default/service/service.cpp
@@ -20,6 +20,10 @@
#include <string>
#include <vector>
+#include <SoundDoseFactory.h>
+#include <android-base/logging.h>
+#include <android/binder_ibinder_platform.h>
+#include <android/binder_manager.h>
#include <android/binder_process.h>
#include <binder/ProcessState.h>
#include <cutils/properties.h>
@@ -33,6 +37,8 @@
using InterfacesList = std::vector<std::string>;
+using aidl::android::hardware::audio::sounddose::SoundDoseFactory;
+
/** Try to register the provided factories in the provided order.
* If any registers successfully, do not register any other and return true.
* If all fail, return false.
@@ -164,5 +170,13 @@
}
}
+ // Register ISoundDoseFactory interface as a workaround for using the audio AIDL HAL
+ auto soundDoseDefault = ndk::SharedRefBase::make<SoundDoseFactory>();
+ const std::string soundDoseDefaultName =
+ std::string() + SoundDoseFactory::descriptor + "/default";
+ binder_status_t status = AServiceManager_addService(soundDoseDefault->asBinder().get(),
+ soundDoseDefaultName.c_str());
+ CHECK_EQ(STATUS_OK, status);
+
joinRpcThreadpool();
}
diff --git a/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/CameraMetadataSection.aidl b/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/CameraMetadataSection.aidl
index e28ecad..d99f16e 100644
--- a/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/CameraMetadataSection.aidl
+++ b/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/CameraMetadataSection.aidl
@@ -71,5 +71,6 @@
ANDROID_AUTOMOTIVE = 30,
ANDROID_AUTOMOTIVE_LENS = 31,
ANDROID_EXTENSION = 32,
+ ANDROID_JPEGR = 33,
VENDOR_SECTION = 32768,
}
diff --git a/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/CameraMetadataSectionStart.aidl b/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/CameraMetadataSectionStart.aidl
index a223309..0bcd846 100644
--- a/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/CameraMetadataSectionStart.aidl
+++ b/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/CameraMetadataSectionStart.aidl
@@ -71,5 +71,6 @@
ANDROID_AUTOMOTIVE_START = 1966080,
ANDROID_AUTOMOTIVE_LENS_START = 2031616,
ANDROID_EXTENSION_START = 2097152,
+ ANDROID_JPEGR_START = 2162688,
VENDOR_SECTION_START = -2147483648,
}
diff --git a/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/CameraMetadataTag.aidl b/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/CameraMetadataTag.aidl
index ecbfc93..b836dbe 100644
--- a/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/CameraMetadataTag.aidl
+++ b/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/CameraMetadataTag.aidl
@@ -335,4 +335,10 @@
ANDROID_HEIC_INFO_MAX_JPEG_APP_SEGMENTS_COUNT = 1900545,
ANDROID_AUTOMOTIVE_LOCATION = 1966080,
ANDROID_AUTOMOTIVE_LENS_FACING = 2031616,
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STREAM_CONFIGURATIONS = 2162688,
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_MIN_FRAME_DURATIONS = 2162689,
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STALL_DURATIONS = 2162690,
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STREAM_CONFIGURATIONS_MAXIMUM_RESOLUTION = 2162691,
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_MIN_FRAME_DURATIONS_MAXIMUM_RESOLUTION = 2162692,
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STALL_DURATIONS_MAXIMUM_RESOLUTION = 2162693,
}
diff --git a/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/JpegrAvailableJpegRStreamConfigurations.aidl b/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/JpegrAvailableJpegRStreamConfigurations.aidl
new file mode 100644
index 0000000..cd005b5
--- /dev/null
+++ b/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/JpegrAvailableJpegRStreamConfigurations.aidl
@@ -0,0 +1,43 @@
+/*
+ * 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.
+ *//*
+ * Autogenerated from camera metadata definitions in
+ * /system/media/camera/docs/metadata_definitions.xml
+ * *** DO NOT EDIT BY HAND ***
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.camera.metadata;
+@Backing(type="int") @VintfStability
+enum JpegrAvailableJpegRStreamConfigurations {
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STREAM_CONFIGURATIONS_OUTPUT = 0,
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STREAM_CONFIGURATIONS_INPUT = 1,
+}
diff --git a/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/JpegrAvailableJpegRStreamConfigurationsMaximumResolution.aidl b/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/JpegrAvailableJpegRStreamConfigurationsMaximumResolution.aidl
new file mode 100644
index 0000000..68028db
--- /dev/null
+++ b/camera/metadata/aidl/aidl_api/android.hardware.camera.metadata/current/android/hardware/camera/metadata/JpegrAvailableJpegRStreamConfigurationsMaximumResolution.aidl
@@ -0,0 +1,43 @@
+/*
+ * 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.
+ *//*
+ * Autogenerated from camera metadata definitions in
+ * /system/media/camera/docs/metadata_definitions.xml
+ * *** DO NOT EDIT BY HAND ***
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.camera.metadata;
+@Backing(type="int") @VintfStability
+enum JpegrAvailableJpegRStreamConfigurationsMaximumResolution {
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STREAM_CONFIGURATIONS_MAXIMUM_RESOLUTION_OUTPUT = 0,
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STREAM_CONFIGURATIONS_MAXIMUM_RESOLUTION_INPUT = 1,
+}
diff --git a/camera/metadata/aidl/android/hardware/camera/metadata/CameraMetadataSection.aidl b/camera/metadata/aidl/android/hardware/camera/metadata/CameraMetadataSection.aidl
index 0d79f0d..73bcc12 100644
--- a/camera/metadata/aidl/android/hardware/camera/metadata/CameraMetadataSection.aidl
+++ b/camera/metadata/aidl/android/hardware/camera/metadata/CameraMetadataSection.aidl
@@ -62,5 +62,6 @@
ANDROID_AUTOMOTIVE,
ANDROID_AUTOMOTIVE_LENS,
ANDROID_EXTENSION,
+ ANDROID_JPEGR,
VENDOR_SECTION = 0x8000,
}
diff --git a/camera/metadata/aidl/android/hardware/camera/metadata/CameraMetadataSectionStart.aidl b/camera/metadata/aidl/android/hardware/camera/metadata/CameraMetadataSectionStart.aidl
index 8f57128..75e7915 100644
--- a/camera/metadata/aidl/android/hardware/camera/metadata/CameraMetadataSectionStart.aidl
+++ b/camera/metadata/aidl/android/hardware/camera/metadata/CameraMetadataSectionStart.aidl
@@ -64,5 +64,6 @@
ANDROID_AUTOMOTIVE_START = CameraMetadataSection.ANDROID_AUTOMOTIVE << 16,
ANDROID_AUTOMOTIVE_LENS_START = CameraMetadataSection.ANDROID_AUTOMOTIVE_LENS << 16,
ANDROID_EXTENSION_START = CameraMetadataSection.ANDROID_EXTENSION << 16,
+ ANDROID_JPEGR_START = CameraMetadataSection.ANDROID_JPEGR << 16,
VENDOR_SECTION_START = CameraMetadataSection.VENDOR_SECTION << 16,
}
diff --git a/camera/metadata/aidl/android/hardware/camera/metadata/CameraMetadataTag.aidl b/camera/metadata/aidl/android/hardware/camera/metadata/CameraMetadataTag.aidl
index 2e9bde9..83e9230 100644
--- a/camera/metadata/aidl/android/hardware/camera/metadata/CameraMetadataTag.aidl
+++ b/camera/metadata/aidl/android/hardware/camera/metadata/CameraMetadataTag.aidl
@@ -2298,4 +2298,56 @@
* passenger seats.</p>
*/
ANDROID_AUTOMOTIVE_LENS_FACING = CameraMetadataSectionStart.ANDROID_AUTOMOTIVE_LENS_START,
+ /**
+ * android.jpegr.availableJpegRStreamConfigurations [static, enum[], ndk_public]
+ *
+ * <p>The available Jpeg/R stream
+ * configurations that this camera device supports
+ * (i.e. format, width, height, output/input stream).</p>
+ */
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STREAM_CONFIGURATIONS = CameraMetadataSectionStart.ANDROID_JPEGR_START,
+ /**
+ * android.jpegr.availableJpegRMinFrameDurations [static, int64[], ndk_public]
+ *
+ * <p>This lists the minimum frame duration for each
+ * format/size combination for Jpeg/R output formats.</p>
+ */
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_MIN_FRAME_DURATIONS,
+ /**
+ * android.jpegr.availableJpegRStallDurations [static, int64[], ndk_public]
+ *
+ * <p>This lists the maximum stall duration for each
+ * output format/size combination for Jpeg/R streams.</p>
+ */
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STALL_DURATIONS,
+ /**
+ * android.jpegr.availableJpegRStreamConfigurationsMaximumResolution [static, enum[], ndk_public]
+ *
+ * <p>The available Jpeg/R stream
+ * configurations that this camera device supports
+ * (i.e. format, width, height, output/input stream).</p>
+ */
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STREAM_CONFIGURATIONS_MAXIMUM_RESOLUTION,
+ /**
+ * android.jpegr.availableJpegRMinFrameDurationsMaximumResolution [static, int64[], ndk_public]
+ *
+ * <p>This lists the minimum frame duration for each
+ * format/size combination for Jpeg/R output formats for CaptureRequests where
+ * ANDROID_SENSOR_PIXEL_MODE is set to
+ * <a href="https://developer.android.com/reference/android/hardware/camera2/CameraMetadata.html#SENSOR_PIXEL_MODE_MAXIMUM_RESOLUTION">CameraMetadata#SENSOR_PIXEL_MODE_MAXIMUM_RESOLUTION</a>.</p>
+ *
+ * @see ANDROID_SENSOR_PIXEL_MODE
+ */
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_MIN_FRAME_DURATIONS_MAXIMUM_RESOLUTION,
+ /**
+ * android.jpegr.availableJpegRStallDurationsMaximumResolution [static, int64[], ndk_public]
+ *
+ * <p>This lists the maximum stall duration for each
+ * output format/size combination for Jpeg/R streams for CaptureRequests where
+ * ANDROID_SENSOR_PIXEL_MODE is set to
+ * <a href="https://developer.android.com/reference/android/hardware/camera2/CameraMetadata.html#SENSOR_PIXEL_MODE_MAXIMUM_RESOLUTION">CameraMetadata#SENSOR_PIXEL_MODE_MAXIMUM_RESOLUTION</a>.</p>
+ *
+ * @see ANDROID_SENSOR_PIXEL_MODE
+ */
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STALL_DURATIONS_MAXIMUM_RESOLUTION,
}
diff --git a/camera/metadata/aidl/android/hardware/camera/metadata/JpegrAvailableJpegRStreamConfigurations.aidl b/camera/metadata/aidl/android/hardware/camera/metadata/JpegrAvailableJpegRStreamConfigurations.aidl
new file mode 100644
index 0000000..911a062
--- /dev/null
+++ b/camera/metadata/aidl/android/hardware/camera/metadata/JpegrAvailableJpegRStreamConfigurations.aidl
@@ -0,0 +1,34 @@
+/*
+ * 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.
+ */
+
+/*
+ * Autogenerated from camera metadata definitions in
+ * /system/media/camera/docs/metadata_definitions.xml
+ * *** DO NOT EDIT BY HAND ***
+ */
+
+package android.hardware.camera.metadata;
+
+/**
+ * android.jpegr.availableJpegRStreamConfigurations enumeration values
+ * @see ANDROID_JPEGR_AVAILABLE_JPEG_R_STREAM_CONFIGURATIONS
+ */
+@VintfStability
+@Backing(type="int")
+enum JpegrAvailableJpegRStreamConfigurations {
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STREAM_CONFIGURATIONS_OUTPUT,
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STREAM_CONFIGURATIONS_INPUT,
+}
diff --git a/camera/metadata/aidl/android/hardware/camera/metadata/JpegrAvailableJpegRStreamConfigurationsMaximumResolution.aidl b/camera/metadata/aidl/android/hardware/camera/metadata/JpegrAvailableJpegRStreamConfigurationsMaximumResolution.aidl
new file mode 100644
index 0000000..9e78662
--- /dev/null
+++ b/camera/metadata/aidl/android/hardware/camera/metadata/JpegrAvailableJpegRStreamConfigurationsMaximumResolution.aidl
@@ -0,0 +1,34 @@
+/*
+ * 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.
+ */
+
+/*
+ * Autogenerated from camera metadata definitions in
+ * /system/media/camera/docs/metadata_definitions.xml
+ * *** DO NOT EDIT BY HAND ***
+ */
+
+package android.hardware.camera.metadata;
+
+/**
+ * android.jpegr.availableJpegRStreamConfigurationsMaximumResolution enumeration values
+ * @see ANDROID_JPEGR_AVAILABLE_JPEG_R_STREAM_CONFIGURATIONS_MAXIMUM_RESOLUTION
+ */
+@VintfStability
+@Backing(type="int")
+enum JpegrAvailableJpegRStreamConfigurationsMaximumResolution {
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STREAM_CONFIGURATIONS_MAXIMUM_RESOLUTION_OUTPUT,
+ ANDROID_JPEGR_AVAILABLE_JPEG_R_STREAM_CONFIGURATIONS_MAXIMUM_RESOLUTION_INPUT,
+}
diff --git a/compatibility_matrices/compatibility_matrix.current.xml b/compatibility_matrices/compatibility_matrix.current.xml
index a907f20..b2433e9 100644
--- a/compatibility_matrices/compatibility_matrix.current.xml
+++ b/compatibility_matrices/compatibility_matrix.current.xml
@@ -53,6 +53,14 @@
</interface>
</hal>
<hal format="aidl" optional="true">
+ <name>android.hardware.audio.sounddose</name>
+ <version>1</version>
+ <interface>
+ <name>ISoundDoseFactory</name>
+ <instance>default</instance>
+ </interface>
+ </hal>
+ <hal format="aidl" optional="true">
<name>android.hardware.authsecret</name>
<version>1</version>
<interface>
@@ -441,7 +449,7 @@
</hal>
<hal format="aidl" optional="false">
<name>android.hardware.power</name>
- <version>2-4</version>
+ <version>4</version>
<interface>
<name>IPower</name>
<instance>default</instance>
diff --git a/graphics/common/aidl/aidl_api/android.hardware.graphics.common/current/android/hardware/graphics/common/Dataspace.aidl b/graphics/common/aidl/aidl_api/android.hardware.graphics.common/current/android/hardware/graphics/common/Dataspace.aidl
index 668b033..563b6c1 100644
--- a/graphics/common/aidl/aidl_api/android.hardware.graphics.common/current/android/hardware/graphics/common/Dataspace.aidl
+++ b/graphics/common/aidl/aidl_api/android.hardware.graphics.common/current/android/hardware/graphics/common/Dataspace.aidl
@@ -94,5 +94,6 @@
DYNAMIC_DEPTH = 4098,
JPEG_APP_SEGMENTS = 4099,
HEIF = 4100,
+ JPEG_R = 4101,
BT709_FULL_RANGE = 146866176,
}
diff --git a/graphics/common/aidl/android/hardware/graphics/common/Dataspace.aidl b/graphics/common/aidl/android/hardware/graphics/common/Dataspace.aidl
index 5e9360f..b44e613 100644
--- a/graphics/common/aidl/android/hardware/graphics/common/Dataspace.aidl
+++ b/graphics/common/aidl/android/hardware/graphics/common/Dataspace.aidl
@@ -668,6 +668,19 @@
HEIF = 0x1004,
/**
+ * ISO/IEC TBD
+ *
+ * JPEG image with embedded 10-bit recovery map following the Jpeg/R specification.
+ *
+ * This value must always remain aligned with the public ImageFormat Jpeg/R definition and is
+ * valid with formats:
+ * HAL_PIXEL_FORMAT_BLOB: JPEG image encoded by Jpeg/R encoder according to ISO/IEC TBD.
+ * The image contains a standard SDR JPEG and a recovery map. Jpeg/R decoders can use the
+ * map to recover the 10-bit input image.
+ */
+ JPEG_R = 0x1005,
+
+ /**
* ITU-R Recommendation 709 (BT.709)
*
* High-definition television
diff --git a/graphics/composer/aidl/aidl_api/android.hardware.graphics.composer3/current/android/hardware/graphics/composer3/LayerCommand.aidl b/graphics/composer/aidl/aidl_api/android.hardware.graphics.composer3/current/android/hardware/graphics/composer3/LayerCommand.aidl
index 0c5fac9..6d32218 100644
--- a/graphics/composer/aidl/aidl_api/android.hardware.graphics.composer3/current/android/hardware/graphics/composer3/LayerCommand.aidl
+++ b/graphics/composer/aidl/aidl_api/android.hardware.graphics.composer3/current/android/hardware/graphics/composer3/LayerCommand.aidl
@@ -54,4 +54,5 @@
@nullable android.hardware.graphics.composer3.PerFrameMetadata[] perFrameMetadata;
@nullable android.hardware.graphics.composer3.PerFrameMetadataBlob[] perFrameMetadataBlob;
@nullable android.hardware.graphics.common.Rect[] blockingRegion;
+ @nullable int[] bufferSlotsToClear;
}
diff --git a/graphics/composer/aidl/android/hardware/graphics/composer3/LayerCommand.aidl b/graphics/composer/aidl/android/hardware/graphics/composer3/LayerCommand.aidl
index f3b67a9..fd50be9 100644
--- a/graphics/composer/aidl/android/hardware/graphics/composer3/LayerCommand.aidl
+++ b/graphics/composer/aidl/android/hardware/graphics/composer3/LayerCommand.aidl
@@ -258,4 +258,11 @@
* the screen.
*/
@nullable Rect[] blockingRegion;
+
+ /**
+ * Specifies which buffer slots should be cleared of buffer references
+ * because these buffers will no longer be used and the memory should
+ * be freed.
+ */
+ @nullable int[] bufferSlotsToClear;
}
diff --git a/graphics/composer/aidl/include/android/hardware/graphics/composer3/ComposerClientWriter.h b/graphics/composer/aidl/include/android/hardware/graphics/composer3/ComposerClientWriter.h
index e35d07b..22020c0 100644
--- a/graphics/composer/aidl/include/android/hardware/graphics/composer3/ComposerClientWriter.h
+++ b/graphics/composer/aidl/include/android/hardware/graphics/composer3/ComposerClientWriter.h
@@ -142,6 +142,14 @@
flushLayerCommand();
}
+ void setLayerBufferSlotsToClear(int64_t display, int64_t layer,
+ const std::vector<uint32_t>& slotsToClear) {
+ LayerCommand& layerCommand = getLayerCommand(display, layer);
+ for (auto slot : slotsToClear) {
+ layerCommand.bufferSlotsToClear.emplace(static_cast<int32_t>(slot));
+ }
+ }
+
void setLayerSurfaceDamage(int64_t display, int64_t layer, const std::vector<Rect>& damage) {
getLayerCommand(display, layer).damage.emplace(damage.begin(), damage.end());
}
diff --git a/graphics/composer/aidl/vts/VtsComposerClient.cpp b/graphics/composer/aidl/vts/VtsComposerClient.cpp
index 34cc802..00b578b 100644
--- a/graphics/composer/aidl/vts/VtsComposerClient.cpp
+++ b/graphics/composer/aidl/vts/VtsComposerClient.cpp
@@ -58,6 +58,12 @@
return verifyComposerCallbackParams() && destroyAllLayers();
}
+std::pair<ScopedAStatus, int32_t> VtsComposerClient::getInterfaceVersion() {
+ int32_t version = 1;
+ auto status = mComposerClient->getInterfaceVersion(&version);
+ return {std::move(status), version};
+}
+
std::pair<ScopedAStatus, VirtualDisplay> VtsComposerClient::createVirtualDisplay(
int32_t width, int32_t height, PixelFormat pixelFormat, int32_t bufferSlotCount) {
VirtualDisplay outVirtualDisplay;
diff --git a/graphics/composer/aidl/vts/VtsComposerClient.h b/graphics/composer/aidl/vts/VtsComposerClient.h
index 1883336..e61fde9 100644
--- a/graphics/composer/aidl/vts/VtsComposerClient.h
+++ b/graphics/composer/aidl/vts/VtsComposerClient.h
@@ -61,6 +61,8 @@
bool tearDown();
+ std::pair<ScopedAStatus, int32_t> getInterfaceVersion();
+
std::pair<ScopedAStatus, VirtualDisplay> createVirtualDisplay(int32_t width, int32_t height,
PixelFormat pixelFormat,
int32_t bufferSlotCount);
diff --git a/graphics/composer/aidl/vts/VtsHalGraphicsComposer3_ReadbackTest.cpp b/graphics/composer/aidl/vts/VtsHalGraphicsComposer3_ReadbackTest.cpp
index 93d9693..166127d 100644
--- a/graphics/composer/aidl/vts/VtsHalGraphicsComposer3_ReadbackTest.cpp
+++ b/graphics/composer/aidl/vts/VtsHalGraphicsComposer3_ReadbackTest.cpp
@@ -379,9 +379,16 @@
}
TEST_P(GraphicsCompositionTest, SetLayerBufferWithSlotsToClear) {
- const auto& [status, readbackBufferAttributes] =
+ const auto& [versionStatus, version] = mComposerClient->getInterfaceVersion();
+ ASSERT_TRUE(versionStatus.isOk());
+ if (version == 1) {
+ GTEST_SUCCEED() << "Device does not support the new API for clearing buffer slots";
+ return;
+ }
+
+ const auto& [readbackStatus, readbackBufferAttributes] =
mComposerClient->getReadbackBufferAttributes(getPrimaryDisplayId());
- if (!status.isOk()) {
+ if (!readbackStatus.isOk()) {
GTEST_SUCCEED() << "Readback not supported";
return;
}
@@ -396,9 +403,6 @@
// no fence needed for the readback buffer
ScopedFileDescriptor noFence(-1);
- sp<GraphicBuffer> clearSlotBuffer = allocateBuffer(1u, 1u, GRALLOC_USAGE_HW_COMPOSER);
- ASSERT_NE(nullptr, clearSlotBuffer);
-
// red buffer
uint64_t usage = GRALLOC_USAGE_SW_WRITE_OFTEN | GRALLOC_USAGE_SW_READ_OFTEN;
sp<GraphicBuffer> redBuffer = allocateBuffer(usage);
@@ -412,10 +416,16 @@
int blueFence;
ASSERT_NO_FATAL_FAILURE(ReadbackHelper::fillBufferAndGetFence(blueBuffer, BLUE, &blueFence));
+ // green buffer
+ sp<GraphicBuffer> greenBuffer = allocateBuffer(usage);
+ ASSERT_NE(nullptr, greenBuffer);
+ int greenFence;
+ ASSERT_NO_FATAL_FAILURE(ReadbackHelper::fillBufferAndGetFence(greenBuffer, GREEN, &greenFence));
+
// layer defaults
common::Rect rectFullDisplay = {0, 0, getDisplayWidth(), getDisplayHeight()};
int64_t display = getPrimaryDisplayId();
- auto [layerStatus, layer] = mComposerClient->createLayer(getPrimaryDisplayId(), 3);
+ const auto& [layerStatus, layer] = mComposerClient->createLayer(getPrimaryDisplayId(), 3);
ASSERT_TRUE(layerStatus.isOk());
mWriter->setLayerDisplayFrame(display, layer, rectFullDisplay);
mWriter->setLayerCompositionType(display, layer, Composition::DEVICE);
@@ -454,13 +464,12 @@
ReadbackHelper::compareColorToBuffer(RED, readbackBuffer, fence);
}
- // clear the slot for the blue buffer
- // should still be red
+ // change the layer to the green buffer
+ // should be green
{
auto status = mComposerClient->setReadbackBuffer(display, readbackBuffer->handle, noFence);
ASSERT_TRUE(status.isOk());
- mWriter->setLayerBufferWithNewCommand(display, layer, /*slot*/ 0, clearSlotBuffer->handle,
- /*fence*/ -1);
+ mWriter->setLayerBuffer(display, layer, /*slot*/ 2, greenBuffer->handle, greenFence);
mWriter->validateDisplay(display, ComposerClientWriter::kNoTimestamp);
execute();
ASSERT_TRUE(mReader.takeChangedCompositionTypes(display).empty());
@@ -469,17 +478,106 @@
execute();
auto [fenceStatus, fence] = mComposerClient->getReadbackBufferFence(display);
ASSERT_TRUE(fenceStatus.isOk());
- ReadbackHelper::compareColorToBuffer(RED, readbackBuffer, fence);
+ ReadbackHelper::compareColorToBuffer(GREEN, readbackBuffer, fence);
}
- // clear the slot for the red buffer, and set the buffer with the same slot to the blue buffer
+ // clear the slots for all buffers
+ // should still be green since the active buffer should not be cleared by the HAL implementation
+ {
+ auto status = mComposerClient->setReadbackBuffer(display, readbackBuffer->handle, noFence);
+ ASSERT_TRUE(status.isOk());
+ mWriter->setLayerBufferSlotsToClear(display, layer, /*slotsToClear*/ {0, 1, 2});
+ mWriter->validateDisplay(display, ComposerClientWriter::kNoTimestamp);
+ execute();
+ ASSERT_TRUE(mReader.takeChangedCompositionTypes(display).empty());
+ ASSERT_TRUE(mReader.takeErrors().empty());
+ mWriter->presentDisplay(display);
+ execute();
+ auto [fenceStatus, fence] = mComposerClient->getReadbackBufferFence(display);
+ ASSERT_TRUE(fenceStatus.isOk());
+ ReadbackHelper::compareColorToBuffer(GREEN, readbackBuffer, fence);
+ }
+
+ // clear the slot for the green buffer, and set the buffer with the same slot to the blue buffer
// should be blue
{
auto status = mComposerClient->setReadbackBuffer(display, readbackBuffer->handle, noFence);
ASSERT_TRUE(status.isOk());
- mWriter->setLayerBufferWithNewCommand(display, layer, /*slot*/ 1, clearSlotBuffer->handle,
- /*fence*/ -1);
- mWriter->setLayerBuffer(display, layer, /*slot*/ 1, blueBuffer->handle, blueFence);
+ mWriter->setLayerBufferSlotsToClear(display, layer, /*slotsToClear*/ {2});
+ mWriter->setLayerBuffer(display, layer, /*slot*/ 2, blueBuffer->handle, blueFence);
+ mWriter->validateDisplay(display, ComposerClientWriter::kNoTimestamp);
+ execute();
+ ASSERT_TRUE(mReader.takeChangedCompositionTypes(display).empty());
+ ASSERT_TRUE(mReader.takeErrors().empty());
+ mWriter->presentDisplay(display);
+ execute();
+ auto [fenceStatus, fence] = mComposerClient->getReadbackBufferFence(display);
+ ASSERT_TRUE(fenceStatus.isOk());
+ ReadbackHelper::compareColorToBuffer(BLUE, readbackBuffer, fence);
+ }
+}
+
+TEST_P(GraphicsCompositionTest, SetLayerBufferWithSlotsToClear_backwardsCompatible) {
+ const auto& [versionStatus, version] = mComposerClient->getInterfaceVersion();
+ ASSERT_TRUE(versionStatus.isOk());
+ if (version > 1) {
+ GTEST_SUCCEED() << "Device does not need a backwards compatible way to clear buffer slots";
+ return;
+ }
+
+ const auto& [readbackStatus, readbackBufferAttributes] =
+ mComposerClient->getReadbackBufferAttributes(getPrimaryDisplayId());
+ if (!readbackStatus.isOk()) {
+ GTEST_SUCCEED() << "Readback not supported";
+ return;
+ }
+
+ sp<GraphicBuffer> readbackBuffer;
+ ASSERT_NO_FATAL_FAILURE(ReadbackHelper::createReadbackBuffer(
+ readbackBufferAttributes, getPrimaryDisplay(), &readbackBuffer));
+ if (readbackBuffer == nullptr) {
+ GTEST_SUCCEED() << "Unsupported readback buffer attributes";
+ return;
+ }
+ // no fence needed for the readback buffer
+ ScopedFileDescriptor noFence(-1);
+
+ sp<GraphicBuffer> clearSlotBuffer = allocateBuffer(1u, 1u, GRALLOC_USAGE_HW_COMPOSER);
+ ASSERT_NE(nullptr, clearSlotBuffer);
+
+ // red buffer
+ uint64_t usage = GRALLOC_USAGE_SW_WRITE_OFTEN | GRALLOC_USAGE_SW_READ_OFTEN;
+ sp<GraphicBuffer> redBuffer = allocateBuffer(usage);
+ ASSERT_NE(nullptr, redBuffer);
+ int redFence;
+ ASSERT_NO_FATAL_FAILURE(ReadbackHelper::fillBufferAndGetFence(redBuffer, RED, &redFence));
+
+ // blue buffer
+ sp<GraphicBuffer> blueBuffer = allocateBuffer(usage);
+ ASSERT_NE(nullptr, blueBuffer);
+ int blueFence;
+ ASSERT_NO_FATAL_FAILURE(ReadbackHelper::fillBufferAndGetFence(blueBuffer, BLUE, &blueFence));
+
+ // green buffer
+ sp<GraphicBuffer> greenBuffer = allocateBuffer(usage);
+ ASSERT_NE(nullptr, greenBuffer);
+ int greenFence;
+ ASSERT_NO_FATAL_FAILURE(ReadbackHelper::fillBufferAndGetFence(greenBuffer, GREEN, &greenFence));
+
+ // layer defaults
+ common::Rect rectFullDisplay = {0, 0, getDisplayWidth(), getDisplayHeight()};
+ int64_t display = getPrimaryDisplayId();
+ const auto& [layerStatus, layer] = mComposerClient->createLayer(getPrimaryDisplayId(), 3);
+ ASSERT_TRUE(layerStatus.isOk());
+ mWriter->setLayerDisplayFrame(display, layer, rectFullDisplay);
+ mWriter->setLayerCompositionType(display, layer, Composition::DEVICE);
+
+ // set the layer to the blue buffer
+ // should be blue
+ {
+ auto status = mComposerClient->setReadbackBuffer(display, readbackBuffer->handle, noFence);
+ ASSERT_TRUE(status.isOk());
+ mWriter->setLayerBuffer(display, layer, /*slot*/ 0, blueBuffer->handle, blueFence);
mWriter->validateDisplay(display, ComposerClientWriter::kNoTimestamp);
execute();
ASSERT_TRUE(mReader.takeChangedCompositionTypes(display).empty());
@@ -491,27 +589,82 @@
ReadbackHelper::compareColorToBuffer(BLUE, readbackBuffer, fence);
}
- // clear the slot for the now-blue buffer
- // should be black (no buffer)
- // TODO(b/262037933) Ensure we never clear the active buffer's slot with the placeholder buffer
- // by setting the layer to the color black
+ // change the layer to the red buffer
+ // should be red
{
auto status = mComposerClient->setReadbackBuffer(display, readbackBuffer->handle, noFence);
ASSERT_TRUE(status.isOk());
- mWriter->setLayerBufferWithNewCommand(display, layer, /*slot*/ 1, clearSlotBuffer->handle,
- /*fence*/ -1);
+ mWriter->setLayerBuffer(display, layer, /*slot*/ 1, redBuffer->handle, redFence);
mWriter->validateDisplay(display, ComposerClientWriter::kNoTimestamp);
execute();
- if (!mReader.takeChangedCompositionTypes(display).empty()) {
- GTEST_SUCCEED();
- return;
- }
+ ASSERT_TRUE(mReader.takeChangedCompositionTypes(display).empty());
ASSERT_TRUE(mReader.takeErrors().empty());
mWriter->presentDisplay(display);
execute();
auto [fenceStatus, fence] = mComposerClient->getReadbackBufferFence(display);
ASSERT_TRUE(fenceStatus.isOk());
- ReadbackHelper::compareColorToBuffer(BLACK, readbackBuffer, fence);
+ ReadbackHelper::compareColorToBuffer(RED, readbackBuffer, fence);
+ }
+
+ // change the layer to the green buffer
+ // should be green
+ {
+ auto status = mComposerClient->setReadbackBuffer(display, readbackBuffer->handle, noFence);
+ ASSERT_TRUE(status.isOk());
+ mWriter->setLayerBuffer(display, layer, /*slot*/ 2, greenBuffer->handle, greenFence);
+ mWriter->validateDisplay(display, ComposerClientWriter::kNoTimestamp);
+ execute();
+ ASSERT_TRUE(mReader.takeChangedCompositionTypes(display).empty());
+ ASSERT_TRUE(mReader.takeErrors().empty());
+ mWriter->presentDisplay(display);
+ execute();
+ auto [fenceStatus, fence] = mComposerClient->getReadbackBufferFence(display);
+ ASSERT_TRUE(fenceStatus.isOk());
+ ReadbackHelper::compareColorToBuffer(GREEN, readbackBuffer, fence);
+ }
+
+ // clear the slot for the blue buffer
+ // should still be green
+ {
+ auto status = mComposerClient->setReadbackBuffer(display, readbackBuffer->handle, noFence);
+ ASSERT_TRUE(status.isOk());
+ mWriter->setLayerBufferWithNewCommand(display, layer, /*slot*/ 0, clearSlotBuffer->handle,
+ /*fence*/ -1);
+ // SurfaceFlinger will re-set the active buffer slot after other buffer slots are cleared
+ mWriter->setLayerBufferWithNewCommand(display, layer, /*slot*/ 2, /*handle*/ nullptr,
+ /*fence*/ -1);
+ mWriter->validateDisplay(display, ComposerClientWriter::kNoTimestamp);
+ execute();
+ ASSERT_TRUE(mReader.takeChangedCompositionTypes(display).empty());
+ ASSERT_TRUE(mReader.takeErrors().empty());
+ mWriter->presentDisplay(display);
+ execute();
+ auto [fenceStatus, fence] = mComposerClient->getReadbackBufferFence(display);
+ ASSERT_TRUE(fenceStatus.isOk());
+ ReadbackHelper::compareColorToBuffer(GREEN, readbackBuffer, fence);
+ }
+
+ // clear the slot for all buffers, and set the buffer with the same slot as the green buffer
+ // should be blue now
+ {
+ auto status = mComposerClient->setReadbackBuffer(display, readbackBuffer->handle, noFence);
+ ASSERT_TRUE(status.isOk());
+ mWriter->setLayerBufferWithNewCommand(display, layer, /*slot*/ 0, clearSlotBuffer->handle,
+ /*fence*/ -1);
+ mWriter->setLayerBufferWithNewCommand(display, layer, /*slot*/ 1, clearSlotBuffer->handle,
+ /*fence*/ -1);
+ // SurfaceFlinger will never clear the active buffer (slot 2), but will free up the
+ // buffer slot so it will be re-used for the next setLayerBuffer command
+ mWriter->setLayerBuffer(display, layer, /*slot*/ 2, blueBuffer->handle, blueFence);
+ mWriter->validateDisplay(display, ComposerClientWriter::kNoTimestamp);
+ execute();
+ ASSERT_TRUE(mReader.takeChangedCompositionTypes(display).empty());
+ ASSERT_TRUE(mReader.takeErrors().empty());
+ mWriter->presentDisplay(display);
+ execute();
+ auto [fenceStatus, fence] = mComposerClient->getReadbackBufferFence(display);
+ ASSERT_TRUE(fenceStatus.isOk());
+ ReadbackHelper::compareColorToBuffer(BLUE, readbackBuffer, fence);
}
}
diff --git a/graphics/composer/aidl/vts/VtsHalGraphicsComposer3_TargetTest.cpp b/graphics/composer/aidl/vts/VtsHalGraphicsComposer3_TargetTest.cpp
index 0f00fd6..7b852e0 100644
--- a/graphics/composer/aidl/vts/VtsHalGraphicsComposer3_TargetTest.cpp
+++ b/graphics/composer/aidl/vts/VtsHalGraphicsComposer3_TargetTest.cpp
@@ -1647,28 +1647,85 @@
}
TEST_P(GraphicsComposerAidlCommandTest, SetLayerBufferWithSlotsToClear) {
- auto clearSlotBuffer = allocate(1u, 1u, ::android::PIXEL_FORMAT_RGB_888);
- ASSERT_NE(nullptr, clearSlotBuffer);
- auto clearSlotBufferHandle = clearSlotBuffer->handle;
+ const auto& [versionStatus, version] = mComposerClient->getInterfaceVersion();
+ ASSERT_TRUE(versionStatus.isOk());
+ if (version == 1) {
+ GTEST_SUCCEED() << "Device does not support the new API for clearing buffer slots";
+ return;
+ }
+
+ const auto& [layerStatus, layer] =
+ mComposerClient->createLayer(getPrimaryDisplayId(), kBufferSlotCount);
+ EXPECT_TRUE(layerStatus.isOk());
+
+ auto& writer = getWriter(getPrimaryDisplayId());
const auto buffer1 = allocate(::android::PIXEL_FORMAT_RGBA_8888);
ASSERT_NE(nullptr, buffer1);
const auto handle1 = buffer1->handle;
- const auto& [layerStatus, layer] =
- mComposerClient->createLayer(getPrimaryDisplayId(), kBufferSlotCount);
- EXPECT_TRUE(layerStatus.isOk());
- auto& writer = getWriter(getPrimaryDisplayId());
writer.setLayerBuffer(getPrimaryDisplayId(), layer, /*slot*/ 0, handle1, /*acquireFence*/ -1);
execute();
ASSERT_TRUE(mReader.takeErrors().empty());
- // Ensure we can clear a buffer slot and then set that same slot with a new buffer
const auto buffer2 = allocate(::android::PIXEL_FORMAT_RGBA_8888);
ASSERT_NE(nullptr, buffer2);
const auto handle2 = buffer2->handle;
- writer.setLayerBufferWithNewCommand(getPrimaryDisplayId(), layer, /* slot */ 0,
+ writer.setLayerBuffer(getPrimaryDisplayId(), layer, /*slot*/ 1, handle2, /*acquireFence*/ -1);
+ execute();
+ ASSERT_TRUE(mReader.takeErrors().empty());
+
+ // Ensure we can clear the buffer slots and then set the active slot with a new buffer
+ const auto buffer3 = allocate(::android::PIXEL_FORMAT_RGBA_8888);
+ ASSERT_NE(nullptr, buffer3);
+ const auto handle3 = buffer3->handle;
+ writer.setLayerBufferSlotsToClear(getPrimaryDisplayId(), layer, /*slotsToClear*/ {0, 1});
+ writer.setLayerBuffer(getPrimaryDisplayId(), layer, /*slot*/ 1, handle3, /*acquireFence*/ -1);
+ execute();
+ ASSERT_TRUE(mReader.takeErrors().empty());
+}
+
+TEST_P(GraphicsComposerAidlCommandTest, SetLayerBufferWithSlotsToClear_backwardsCompatible) {
+ const auto& [versionStatus, version] = mComposerClient->getInterfaceVersion();
+ ASSERT_TRUE(versionStatus.isOk());
+ if (version > 1) {
+ GTEST_SUCCEED() << "Device does not need a backwards compatible way to clear buffer slots";
+ return;
+ }
+
+ auto clearSlotBuffer = allocate(1u, 1u, ::android::PIXEL_FORMAT_RGB_888);
+ ASSERT_NE(nullptr, clearSlotBuffer);
+ auto clearSlotBufferHandle = clearSlotBuffer->handle;
+
+ const auto& [layerStatus, layer] =
+ mComposerClient->createLayer(getPrimaryDisplayId(), kBufferSlotCount);
+ EXPECT_TRUE(layerStatus.isOk());
+
+ auto& writer = getWriter(getPrimaryDisplayId());
+
+ const auto buffer1 = allocate(::android::PIXEL_FORMAT_RGBA_8888);
+ ASSERT_NE(nullptr, buffer1);
+ const auto handle1 = buffer1->handle;
+ writer.setLayerBuffer(getPrimaryDisplayId(), layer, /*slot*/ 0, handle1, /*acquireFence*/ -1);
+ execute();
+ ASSERT_TRUE(mReader.takeErrors().empty());
+
+ const auto buffer2 = allocate(::android::PIXEL_FORMAT_RGBA_8888);
+ ASSERT_NE(nullptr, buffer2);
+ const auto handle2 = buffer2->handle;
+ EXPECT_TRUE(layerStatus.isOk());
+ writer.setLayerBuffer(getPrimaryDisplayId(), layer, /*slot*/ 1, handle2, /*acquireFence*/ -1);
+ execute();
+ ASSERT_TRUE(mReader.takeErrors().empty());
+
+ // Ensure we can clear a buffer slot and then set that same slot with a new buffer
+ const auto buffer3 = allocate(::android::PIXEL_FORMAT_RGBA_8888);
+ ASSERT_NE(nullptr, buffer3);
+ const auto handle3 = buffer2->handle;
+ // SurfaceFlinger will never clear the active buffer, instead it will clear non-active buffers
+ // and then re-use the active buffer's slot for the new buffer
+ writer.setLayerBufferWithNewCommand(getPrimaryDisplayId(), layer, /*slot*/ 0,
clearSlotBufferHandle, /*acquireFence*/ -1);
- writer.setLayerBuffer(getPrimaryDisplayId(), layer, /*slot*/ 0, handle2, /*acquireFence*/ -1);
+ writer.setLayerBuffer(getPrimaryDisplayId(), layer, /*slot*/ 1, handle3, /*acquireFence*/ -1);
execute();
ASSERT_TRUE(mReader.takeErrors().empty());
}
diff --git a/identity/support/Android.bp b/identity/support/Android.bp
index 4e3d1f7..3096fe5 100644
--- a/identity/support/Android.bp
+++ b/identity/support/Android.bp
@@ -65,57 +65,3 @@
],
test_suites: ["general-tests"],
}
-
-// --
-
-cc_library {
- name: "libcppbor",
- vendor_available: true,
- host_supported: true,
- srcs: [
- "src/cppbor.cpp",
- "src/cppbor_parse.cpp",
- ],
- export_include_dirs: [
- "include/cppbor",
- ],
- shared_libs: [
- "libbase",
- ],
-}
-
-cc_test {
- name: "cppbor_test",
- tidy_timeout_srcs: [
- "tests/cppbor_test.cpp",
- ],
- srcs: [
- "tests/cppbor_test.cpp",
- ],
- shared_libs: [
- "libcppbor_external",
- "libbase",
- ],
- static_libs: [
- "libgmock",
- ],
- test_suites: ["general-tests"],
-}
-
-cc_test_host {
- name: "cppbor_host_test",
- tidy_timeout_srcs: [
- "tests/cppbor_test.cpp",
- ],
- srcs: [
- "tests/cppbor_test.cpp",
- ],
- shared_libs: [
- "libcppbor_external",
- "libbase",
- ],
- static_libs: [
- "libgmock",
- ],
- test_suites: ["general-tests"],
-}
diff --git a/identity/support/include/cppbor/README.md b/identity/support/include/cppbor/README.md
deleted file mode 100644
index 723bfcf..0000000
--- a/identity/support/include/cppbor/README.md
+++ /dev/null
@@ -1,216 +0,0 @@
-CppBor: A Modern C++ CBOR Parser and Generator
-==============================================
-
-CppBor provides a natural and easy-to-use syntax for constructing and
-parsing CBOR messages. It does not (yet) support all features of
-CBOR, nor (yet) support validation against CDDL schemata, though both
-are planned. CBOR features that aren't supported include:
-
-* Indefinite length values
-* Semantic tagging
-* Floating point
-
-CppBor requires C++-17.
-
-## CBOR representation
-
-CppBor represents CBOR data items as instances of the `Item` class or,
-more precisely, as instances of subclasses of `Item`, since `Item` is a
-pure interface. The subclasses of `Item` correspond almost one-to-one
-with CBOR major types, and are named to match the CDDL names to which
-they correspond. They are:
-
-* `Uint` corresponds to major type 0, and can hold unsigned integers
- up through (2^64 - 1).
-* `Nint` corresponds to major type 1. It can only hold values from -1
- to -(2^63 - 1), since it's internal representation is an int64_t.
- This can be fixed, but it seems unlikely that applications will need
- the omitted range from -(2^63) to (2^64 - 1), since it's
- inconvenient to represent them in many programming languages.
-* `Int` is an abstract base of `Uint` and `Nint` that facilitates
- working with all signed integers representable with int64_t.
-* `Bstr` corresponds to major type 2, a byte string.
-* `Tstr` corresponds to major type 3, a text string.
-* `Array` corresponds to major type 4, an Array. It holds a
- variable-length array of `Item`s.
-* `Map` corresponds to major type 5, a Map. It holds a
- variable-length array of pairs of `Item`s.
-* `Simple` corresponds to major type 7. It's an abstract class since
- items require more specific type.
-* `Bool` is the only currently-implemented subclass of `Simple`.
-
-Note that major type 6, semantic tag, is not yet implemented.
-
-In practice, users of CppBor will rarely use most of these classes
-when generating CBOR encodings. This is because CppBor provides
-straightforward conversions from the obvious normal C++ types.
-Specifically, the following conversions are provided in appropriate
-contexts:
-
-* Signed and unsigned integers convert to `Uint` or `Nint`, as
- appropriate.
-* `std::string`, `std::string_view`, `const char*` and
- `std::pair<char iterator, char iterator>` convert to `Tstr`.
-* `std::vector<uint8_t>`, `std::pair<uint8_t iterator, uint8_t
- iterator>` and `std::pair<uint8_t*, size_t>` convert to `Bstr`.
-* `bool` converts to `Bool`.
-
-## CBOR generation
-
-### Complete tree generation
-
-The set of `encode` methods in `Item` provide the interface for
-producing encoded CBOR. The basic process for "complete tree"
-generation (as opposed to "incremental" generation, which is discussed
-below) is to construct an `Item` which models the data to be encoded,
-and then call one of the `encode` methods, whichever is convenient for
-the encoding destination. A trivial example:
-
-```
-cppbor::Uint val(0);
-std::vector<uint8_t> encoding = val.encode();
-```
-
- It's relatively rare that single values are encoded as above. More often, the
- "root" data item will be an `Array` or `Map` which contains a more complex structure.For example
- :
-
-``` using cppbor::Map;
-using cppbor::Array;
-
-std::vector<uint8_t> vec = // ...
- Map val("key1", Array(Map("key_a", 99 "key_b", vec), "foo"), "key2", true);
-std::vector<uint8_t> encoding = val.encode();
-```
-
-This creates a map with two entries, with `Tstr` keys "Outer1" and
-"Outer2", respectively. The "Outer1" entry has as its value an
-`Array` containing a `Map` and a `Tstr`. The "Outer2" entry has a
-`Bool` value.
-
-This example demonstrates how automatic conversion of C++ types to
-CppBor `Item` subclass instances is done. Where the caller provides a
-C++ or C string, a `Tstr` entry is added. Where the caller provides
-an integer literal or variable, a `Uint` or `Nint` is added, depending
-on whether the value is positive or negative.
-
-As an alternative, a more fluent-style API is provided for building up
-structures. For example:
-
-```
-using cppbor::Map;
-using cppbor::Array;
-
-std::vector<uint8_t> vec = // ...
- Map val();
-val.add("key1", Array().add(Map().add("key_a", 99).add("key_b", vec)).add("foo")).add("key2", true);
-std::vector<uint8_t> encoding = val.encode();
-```
-
- An advantage of this interface over the constructor -
- based creation approach above is that it need not be done all at once
- .The `add` methods return a reference to the object added to to allow calls to be chained,
- but chaining is not necessary; calls can be made
-sequentially, as the data to add is available.
-
-#### `encode` methods
-
-There are several variations of `Item::encode`, all of which
-accomplish the same task but output the encoded data in different
-ways, and with somewhat different performance characteristics. The
-provided options are:
-
-* `bool encode(uint8\_t** pos, const uint8\_t* end)` encodes into the
- buffer referenced by the range [`*pos`, end). `*pos` is moved. If
- the encoding runs out of buffer space before finishing, the method
- returns false. This is the most efficient way to encode, into an
- already-allocated buffer.
-* `void encode(EncodeCallback encodeCallback)` calls `encodeCallback`
- for each encoded byte. It's the responsibility of the implementor
- of the callback to behave safely in the event that the output buffer
- (if applicable) is exhausted. This is less efficient than the prior
- method because it imposes an additional function call for each byte.
-* `template </*...*/> void encode(OutputIterator i)`
- encodes into the provided iterator. SFINAE ensures that the
- template doesn't match for non-iterators. The implementation
- actually uses the callback-based method, plus has whatever overhead
- the iterator adds.
-* `std::vector<uint8_t> encode()` creates a new std::vector, reserves
- sufficient capacity to hold the encoding, and inserts the encoded
- bytes with a std::pushback_iterator and the previous method.
-* `std::string toString()` does the same as the previous method, but
- returns a string instead of a vector.
-
-### Incremental generation
-
-Incremental generation requires deeper understanding of CBOR, because
-the library can't do as much to ensure that the output is valid. The
-basic tool for intcremental generation is the `encodeHeader`
-function. There are two variations, one which writes into a buffer,
-and one which uses a callback. Both simply write out the bytes of a
-header. To construct the same map as in the above examples,
-incrementally, one might write:
-
-```
-using namespace cppbor; // For example brevity
-
-std::vector encoding;
-auto iter = std::back_inserter(result);
-encodeHeader(MAP, 2 /* # of map entries */, iter);
-std::string s = "key1";
-encodeHeader(TSTR, s.size(), iter);
-std::copy(s.begin(), s.end(), iter);
-encodeHeader(ARRAY, 2 /* # of array entries */, iter);
-Map().add("key_a", 99).add("key_b", vec).encode(iter)
-s = "foo";
-encodeHeader(TSTR, foo.size(), iter);
-std::copy(s.begin(), s.end(), iter);
-s = "key2";
-encodeHeader(TSTR, foo.size(), iter);
-std::copy(s.begin(), s.end(), iter);
-encodeHeader(SIMPLE, TRUE, iter);
-```
-
-As the above example demonstrates, the styles can be mixed -- Note the
-creation and encoding of the inner Map using the fluent style.
-
-## Parsing
-
-CppBor also supports parsing of encoded CBOR data, with the same
-feature set as encoding. There are two basic approaches to parsing,
-"full" and "stream"
-
-### Full parsing
-
-Full parsing means completely parsing a (possibly-compound) data
-item from a byte buffer. The `parse` functions that do not take a
-`ParseClient` pointer do this. They return a `ParseResult` which is a
-tuple of three values:
-
-* std::unique_ptr<Item> that points to the parsed item, or is nullptr
- if there was a parse error.
-* const uint8_t* that points to the byte after the end of the decoded
- item, or to the first unparseable byte in the event of an error.
-* std::string that is empty on success or contains an error message if
- a parse error occurred.
-
-Assuming a successful parse, you can then use `Item::type()` to
-discover the type of the parsed item (e.g. MAP), and then use the
-appropriate `Item::as*()` method (e.g. `Item::asMap()`) to get a
-pointer to an interface which allows you to retrieve specific values.
-
-### Stream parsing
-
-Stream parsing is more complex, but more flexible. To use
-StreamParsing, you must create your own subclass of `ParseClient` and
-call one of the `parse` functions that accepts it. See the
-`ParseClient` methods docstrings for details.
-
-One unusual feature of stream parsing is that the `ParseClient`
-callback methods not only provide the parsed Item, but also pointers
-to the portion of the buffer that encode that Item. This is useful
-if, for example, you want to find an element inside of a structure,
-and then copy the encoding of that sub-structure, without bothering to
-parse the rest.
-
-The full parser is implemented with the stream parser.
diff --git a/identity/support/include/cppbor/cppbor.h b/identity/support/include/cppbor/cppbor.h
deleted file mode 100644
index af5d82e..0000000
--- a/identity/support/include/cppbor/cppbor.h
+++ /dev/null
@@ -1,827 +0,0 @@
-/*
- * Copyright (c) 2019, 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.
- */
-
-#pragma once
-
-#include <cstdint>
-#include <functional>
-#include <iterator>
-#include <memory>
-#include <numeric>
-#include <string>
-#include <vector>
-
-namespace cppbor {
-
-enum MajorType : uint8_t {
- UINT = 0 << 5,
- NINT = 1 << 5,
- BSTR = 2 << 5,
- TSTR = 3 << 5,
- ARRAY = 4 << 5,
- MAP = 5 << 5,
- SEMANTIC = 6 << 5,
- SIMPLE = 7 << 5,
-};
-
-enum SimpleType {
- BOOLEAN,
- NULL_T, // Only two supported, as yet.
-};
-
-enum SpecialAddlInfoValues : uint8_t {
- FALSE = 20,
- TRUE = 21,
- NULL_V = 22,
- ONE_BYTE_LENGTH = 24,
- TWO_BYTE_LENGTH = 25,
- FOUR_BYTE_LENGTH = 26,
- EIGHT_BYTE_LENGTH = 27,
-};
-
-class Item;
-class Uint;
-class Nint;
-class Int;
-class Tstr;
-class Bstr;
-class Simple;
-class Bool;
-class Array;
-class Map;
-class Null;
-class Semantic;
-
-/**
- * Returns the size of a CBOR header that contains the additional info value addlInfo.
- */
-size_t headerSize(uint64_t addlInfo);
-
-/**
- * Encodes a CBOR header with the specified type and additional info into the range [pos, end).
- * Returns a pointer to one past the last byte written, or nullptr if there isn't sufficient space
- * to write the header.
- */
-uint8_t* encodeHeader(MajorType type, uint64_t addlInfo, uint8_t* pos, const uint8_t* end);
-
-using EncodeCallback = std::function<void(uint8_t)>;
-
-/**
- * Encodes a CBOR header with the specified type and additional info, passing each byte in turn to
- * encodeCallback.
- */
-void encodeHeader(MajorType type, uint64_t addlInfo, EncodeCallback encodeCallback);
-
-/**
- * Encodes a CBOR header with the specified type and additional info, writing each byte to the
- * provided OutputIterator.
- */
-template <typename OutputIterator,
- typename = std::enable_if_t<std::is_base_of_v<
- std::output_iterator_tag,
- typename std::iterator_traits<OutputIterator>::iterator_category>>>
-void encodeHeader(MajorType type, uint64_t addlInfo, OutputIterator iter) {
- return encodeHeader(type, addlInfo, [&](uint8_t v) { *iter++ = v; });
-}
-
-/**
- * Item represents a CBOR-encodeable data item. Item is an abstract interface with a set of virtual
- * methods that allow encoding of the item or conversion to the appropriate derived type.
- */
-class Item {
- public:
- virtual ~Item() {}
-
- /**
- * Returns the CBOR type of the item.
- */
- virtual MajorType type() const = 0;
-
- // These methods safely downcast an Item to the appropriate subclass.
- virtual const Int* asInt() const { return nullptr; }
- virtual const Uint* asUint() const { return nullptr; }
- virtual const Nint* asNint() const { return nullptr; }
- virtual const Tstr* asTstr() const { return nullptr; }
- virtual const Bstr* asBstr() const { return nullptr; }
- virtual const Simple* asSimple() const { return nullptr; }
- virtual const Map* asMap() const { return nullptr; }
- virtual const Array* asArray() const { return nullptr; }
- virtual const Semantic* asSemantic() const { return nullptr; }
-
- /**
- * Returns true if this is a "compound" item, i.e. one that contains one or more other items.
- */
- virtual bool isCompound() const { return false; }
-
- bool operator==(const Item& other) const&;
- bool operator!=(const Item& other) const& { return !(*this == other); }
-
- /**
- * Returns the number of bytes required to encode this Item into CBOR. Note that if this is a
- * complex Item, calling this method will require walking the whole tree.
- */
- virtual size_t encodedSize() const = 0;
-
- /**
- * Encodes the Item into buffer referenced by range [*pos, end). Returns a pointer to one past
- * the last position written. Returns nullptr if there isn't enough space to encode.
- */
- virtual uint8_t* encode(uint8_t* pos, const uint8_t* end) const = 0;
-
- /**
- * Encodes the Item by passing each encoded byte to encodeCallback.
- */
- virtual void encode(EncodeCallback encodeCallback) const = 0;
-
- /**
- * Clones the Item
- */
- virtual std::unique_ptr<Item> clone() const = 0;
-
- /**
- * Encodes the Item into the provided OutputIterator.
- */
- template <typename OutputIterator,
- typename = typename std::iterator_traits<OutputIterator>::iterator_category>
- void encode(OutputIterator i) const {
- return encode([&](uint8_t v) { *i++ = v; });
- }
-
- /**
- * Encodes the Item into a new std::vector<uint8_t>.
- */
- std::vector<uint8_t> encode() const {
- std::vector<uint8_t> retval;
- retval.reserve(encodedSize());
- encode(std::back_inserter(retval));
- return retval;
- }
-
- /**
- * Encodes the Item into a new std::string.
- */
- std::string toString() const {
- std::string retval;
- retval.reserve(encodedSize());
- encode([&](uint8_t v) { retval.push_back(v); });
- return retval;
- }
-
- /**
- * Encodes only the header of the Item.
- */
- inline uint8_t* encodeHeader(uint64_t addlInfo, uint8_t* pos, const uint8_t* end) const {
- return ::cppbor::encodeHeader(type(), addlInfo, pos, end);
- }
-
- /**
- * Encodes only the header of the Item.
- */
- inline void encodeHeader(uint64_t addlInfo, EncodeCallback encodeCallback) const {
- ::cppbor::encodeHeader(type(), addlInfo, encodeCallback);
- }
-};
-
-/**
- * Int is an abstraction that allows Uint and Nint objects to be manipulated without caring about
- * the sign.
- */
-class Int : public Item {
- public:
- bool operator==(const Int& other) const& { return value() == other.value(); }
-
- virtual int64_t value() const = 0;
-
- const Int* asInt() const override { return this; }
-};
-
-/**
- * Uint is a concrete Item that implements CBOR major type 0.
- */
-class Uint : public Int {
- public:
- static constexpr MajorType kMajorType = UINT;
-
- explicit Uint(uint64_t v) : mValue(v) {}
-
- bool operator==(const Uint& other) const& { return mValue == other.mValue; }
-
- MajorType type() const override { return kMajorType; }
- const Uint* asUint() const override { return this; }
-
- size_t encodedSize() const override { return headerSize(mValue); }
-
- int64_t value() const override { return mValue; }
- uint64_t unsignedValue() const { return mValue; }
-
- using Item::encode;
- uint8_t* encode(uint8_t* pos, const uint8_t* end) const override {
- return encodeHeader(mValue, pos, end);
- }
- void encode(EncodeCallback encodeCallback) const override {
- encodeHeader(mValue, encodeCallback);
- }
-
- virtual std::unique_ptr<Item> clone() const override { return std::make_unique<Uint>(mValue); }
-
- private:
- uint64_t mValue;
-};
-
-/**
- * Nint is a concrete Item that implements CBOR major type 1.
-
- * Note that it is incapable of expressing the full range of major type 1 values, becaue it can only
- * express values that fall into the range [std::numeric_limits<int64_t>::min(), -1]. It cannot
- * express values in the range [std::numeric_limits<int64_t>::min() - 1,
- * -std::numeric_limits<uint64_t>::max()].
- */
-class Nint : public Int {
- public:
- static constexpr MajorType kMajorType = NINT;
-
- explicit Nint(int64_t v);
-
- bool operator==(const Nint& other) const& { return mValue == other.mValue; }
-
- MajorType type() const override { return kMajorType; }
- const Nint* asNint() const override { return this; }
- size_t encodedSize() const override { return headerSize(addlInfo()); }
-
- int64_t value() const override { return mValue; }
-
- using Item::encode;
- uint8_t* encode(uint8_t* pos, const uint8_t* end) const override {
- return encodeHeader(addlInfo(), pos, end);
- }
- void encode(EncodeCallback encodeCallback) const override {
- encodeHeader(addlInfo(), encodeCallback);
- }
-
- virtual std::unique_ptr<Item> clone() const override { return std::make_unique<Nint>(mValue); }
-
- private:
- uint64_t addlInfo() const { return -1LL - mValue; }
-
- int64_t mValue;
-};
-
-/**
- * Bstr is a concrete Item that implements major type 2.
- */
-class Bstr : public Item {
- public:
- static constexpr MajorType kMajorType = BSTR;
-
- // Construct from a vector
- explicit Bstr(std::vector<uint8_t> v) : mValue(std::move(v)) {}
-
- // Construct from a string
- explicit Bstr(const std::string& v)
- : mValue(reinterpret_cast<const uint8_t*>(v.data()),
- reinterpret_cast<const uint8_t*>(v.data()) + v.size()) {}
-
- // Construct from a pointer/size pair
- explicit Bstr(const std::pair<const uint8_t*, size_t>& buf)
- : mValue(buf.first, buf.first + buf.second) {}
-
- // Construct from a pair of iterators
- template <typename I1, typename I2,
- typename = typename std::iterator_traits<I1>::iterator_category,
- typename = typename std::iterator_traits<I2>::iterator_category>
- explicit Bstr(const std::pair<I1, I2>& pair) : mValue(pair.first, pair.second) {}
-
- // Construct from an iterator range.
- template <typename I1, typename I2,
- typename = typename std::iterator_traits<I1>::iterator_category,
- typename = typename std::iterator_traits<I2>::iterator_category>
- Bstr(I1 begin, I2 end) : mValue(begin, end) {}
-
- bool operator==(const Bstr& other) const& { return mValue == other.mValue; }
-
- MajorType type() const override { return kMajorType; }
- const Bstr* asBstr() const override { return this; }
- size_t encodedSize() const override { return headerSize(mValue.size()) + mValue.size(); }
- using Item::encode;
- uint8_t* encode(uint8_t* pos, const uint8_t* end) const override;
- void encode(EncodeCallback encodeCallback) const override {
- encodeHeader(mValue.size(), encodeCallback);
- encodeValue(encodeCallback);
- }
-
- const std::vector<uint8_t>& value() const { return mValue; }
-
- virtual std::unique_ptr<Item> clone() const override { return std::make_unique<Bstr>(mValue); }
-
- private:
- void encodeValue(EncodeCallback encodeCallback) const;
-
- std::vector<uint8_t> mValue;
-};
-
-/**
- * Bstr is a concrete Item that implements major type 3.
- */
-class Tstr : public Item {
- public:
- static constexpr MajorType kMajorType = TSTR;
-
- // Construct from a string
- explicit Tstr(std::string v) : mValue(std::move(v)) {}
-
- // Construct from a string_view
- explicit Tstr(const std::string_view& v) : mValue(v) {}
-
- // Construct from a C string
- explicit Tstr(const char* v) : mValue(std::string(v)) {}
-
- // Construct from a pair of iterators
- template <typename I1, typename I2,
- typename = typename std::iterator_traits<I1>::iterator_category,
- typename = typename std::iterator_traits<I2>::iterator_category>
- explicit Tstr(const std::pair<I1, I2>& pair) : mValue(pair.first, pair.second) {}
-
- // Construct from an iterator range
- template <typename I1, typename I2,
- typename = typename std::iterator_traits<I1>::iterator_category,
- typename = typename std::iterator_traits<I2>::iterator_category>
- Tstr(I1 begin, I2 end) : mValue(begin, end) {}
-
- bool operator==(const Tstr& other) const& { return mValue == other.mValue; }
-
- MajorType type() const override { return kMajorType; }
- const Tstr* asTstr() const override { return this; }
- size_t encodedSize() const override { return headerSize(mValue.size()) + mValue.size(); }
- using Item::encode;
- uint8_t* encode(uint8_t* pos, const uint8_t* end) const override;
- void encode(EncodeCallback encodeCallback) const override {
- encodeHeader(mValue.size(), encodeCallback);
- encodeValue(encodeCallback);
- }
-
- const std::string& value() const { return mValue; }
-
- virtual std::unique_ptr<Item> clone() const override { return std::make_unique<Tstr>(mValue); }
-
- private:
- void encodeValue(EncodeCallback encodeCallback) const;
-
- std::string mValue;
-};
-
-/**
- * CompoundItem is an abstract Item that provides common functionality for Items that contain other
- * items, i.e. Arrays (CBOR type 4) and Maps (CBOR type 5).
- */
-class CompoundItem : public Item {
- public:
- bool operator==(const CompoundItem& other) const&;
-
- virtual size_t size() const { return mEntries.size(); }
-
- bool isCompound() const override { return true; }
-
- size_t encodedSize() const override {
- return std::accumulate(mEntries.begin(), mEntries.end(), headerSize(size()),
- [](size_t sum, auto& entry) { return sum + entry->encodedSize(); });
- }
-
- using Item::encode; // Make base versions visible.
- uint8_t* encode(uint8_t* pos, const uint8_t* end) const override;
- void encode(EncodeCallback encodeCallback) const override;
-
- virtual uint64_t addlInfo() const = 0;
-
- protected:
- std::vector<std::unique_ptr<Item>> mEntries;
-};
-
-/*
- * Array is a concrete Item that implements CBOR major type 4.
- *
- * Note that Arrays are not copyable. This is because copying them is expensive and making them
- * move-only ensures that they're never copied accidentally. If you actually want to copy an Array,
- * use the clone() method.
- */
-class Array : public CompoundItem {
- public:
- static constexpr MajorType kMajorType = ARRAY;
-
- Array() = default;
- Array(const Array& other) = delete;
- Array(Array&&) = default;
- Array& operator=(const Array&) = delete;
- Array& operator=(Array&&) = default;
-
- /**
- * Construct an Array from a variable number of arguments of different types. See
- * details::makeItem below for details on what types may be provided. In general, this accepts
- * all of the types you'd expect and doest the things you'd expect (integral values are addes as
- * Uint or Nint, std::string and char* are added as Tstr, bools are added as Bool, etc.).
- */
- template <typename... Args, typename Enable>
- Array(Args&&... args);
-
- /**
- * Append a single element to the Array, of any compatible type.
- */
- template <typename T>
- Array& add(T&& v) &;
- template <typename T>
- Array&& add(T&& v) &&;
-
- const std::unique_ptr<Item>& operator[](size_t index) const { return mEntries[index]; }
- std::unique_ptr<Item>& operator[](size_t index) { return mEntries[index]; }
-
- MajorType type() const override { return kMajorType; }
- const Array* asArray() const override { return this; }
-
- virtual std::unique_ptr<Item> clone() const override;
-
- uint64_t addlInfo() const override { return size(); }
-};
-
-/*
- * Map is a concrete Item that implements CBOR major type 5.
- *
- * Note that Maps are not copyable. This is because copying them is expensive and making them
- * move-only ensures that they're never copied accidentally. If you actually want to copy a
- * Map, use the clone() method.
- */
-class Map : public CompoundItem {
- public:
- static constexpr MajorType kMajorType = MAP;
-
- Map() = default;
- Map(const Map& other) = delete;
- Map(Map&&) = default;
- Map& operator=(const Map& other) = delete;
- Map& operator=(Map&&) = default;
-
- /**
- * Construct a Map from a variable number of arguments of different types. An even number of
- * arguments must be provided (this is verified statically). See details::makeItem below for
- * details on what types may be provided. In general, this accepts all of the types you'd
- * expect and doest the things you'd expect (integral values are addes as Uint or Nint,
- * std::string and char* are added as Tstr, bools are added as Bool, etc.).
- */
- template <typename... Args, typename Enable>
- Map(Args&&... args);
-
- /**
- * Append a key/value pair to the Map, of any compatible types.
- */
- template <typename Key, typename Value>
- Map& add(Key&& key, Value&& value) &;
- template <typename Key, typename Value>
- Map&& add(Key&& key, Value&& value) &&;
-
- size_t size() const override {
- assertInvariant();
- return mEntries.size() / 2;
- }
-
- template <typename Key, typename Enable>
- std::pair<std::unique_ptr<Item>&, bool> get(Key key);
-
- std::pair<const std::unique_ptr<Item>&, const std::unique_ptr<Item>&> operator[](
- size_t index) const {
- assertInvariant();
- return {mEntries[index * 2], mEntries[index * 2 + 1]};
- }
-
- std::pair<std::unique_ptr<Item>&, std::unique_ptr<Item>&> operator[](size_t index) {
- assertInvariant();
- return {mEntries[index * 2], mEntries[index * 2 + 1]};
- }
-
- MajorType type() const override { return kMajorType; }
- const Map* asMap() const override { return this; }
-
- virtual std::unique_ptr<Item> clone() const override;
-
- uint64_t addlInfo() const override { return size(); }
-
- private:
- void assertInvariant() const;
-};
-
-class Semantic : public CompoundItem {
- public:
- static constexpr MajorType kMajorType = SEMANTIC;
-
- template <typename T>
- explicit Semantic(uint64_t value, T&& child);
-
- Semantic(const Semantic& other) = delete;
- Semantic(Semantic&&) = default;
- Semantic& operator=(const Semantic& other) = delete;
- Semantic& operator=(Semantic&&) = default;
-
- size_t size() const override {
- assertInvariant();
- return 1;
- }
-
- size_t encodedSize() const override {
- return std::accumulate(mEntries.begin(), mEntries.end(), headerSize(mValue),
- [](size_t sum, auto& entry) { return sum + entry->encodedSize(); });
- }
-
- MajorType type() const override { return kMajorType; }
- const Semantic* asSemantic() const override { return this; }
-
- const std::unique_ptr<Item>& child() const {
- assertInvariant();
- return mEntries[0];
- }
-
- std::unique_ptr<Item>& child() {
- assertInvariant();
- return mEntries[0];
- }
-
- uint64_t value() const { return mValue; }
-
- uint64_t addlInfo() const override { return value(); }
-
- virtual std::unique_ptr<Item> clone() const override {
- assertInvariant();
- return std::make_unique<Semantic>(mValue, mEntries[0]->clone());
- }
-
- protected:
- Semantic() = default;
- Semantic(uint64_t value) : mValue(value) {}
- uint64_t mValue;
-
- private:
- void assertInvariant() const;
-};
-
-/**
- * Simple is abstract Item that implements CBOR major type 7. It is intended to be subclassed to
- * create concrete Simple types. At present only Bool is provided.
- */
-class Simple : public Item {
- public:
- static constexpr MajorType kMajorType = SIMPLE;
-
- bool operator==(const Simple& other) const&;
-
- virtual SimpleType simpleType() const = 0;
- MajorType type() const override { return kMajorType; }
-
- const Simple* asSimple() const override { return this; }
-
- virtual const Bool* asBool() const { return nullptr; };
- virtual const Null* asNull() const { return nullptr; };
-};
-
-/**
- * Bool is a concrete type that implements CBOR major type 7, with additional item values for TRUE
- * and FALSE.
- */
-class Bool : public Simple {
- public:
- static constexpr SimpleType kSimpleType = BOOLEAN;
-
- explicit Bool(bool v) : mValue(v) {}
-
- bool operator==(const Bool& other) const& { return mValue == other.mValue; }
-
- SimpleType simpleType() const override { return kSimpleType; }
- const Bool* asBool() const override { return this; }
-
- size_t encodedSize() const override { return 1; }
-
- using Item::encode;
- uint8_t* encode(uint8_t* pos, const uint8_t* end) const override {
- return encodeHeader(mValue ? TRUE : FALSE, pos, end);
- }
- void encode(EncodeCallback encodeCallback) const override {
- encodeHeader(mValue ? TRUE : FALSE, encodeCallback);
- }
-
- bool value() const { return mValue; }
-
- virtual std::unique_ptr<Item> clone() const override { return std::make_unique<Bool>(mValue); }
-
- private:
- bool mValue;
-};
-
-/**
- * Null is a concrete type that implements CBOR major type 7, with additional item value for NULL
- */
-class Null : public Simple {
- public:
- static constexpr SimpleType kSimpleType = NULL_T;
-
- explicit Null() {}
-
- SimpleType simpleType() const override { return kSimpleType; }
- const Null* asNull() const override { return this; }
-
- size_t encodedSize() const override { return 1; }
-
- using Item::encode;
- uint8_t* encode(uint8_t* pos, const uint8_t* end) const override {
- return encodeHeader(NULL_V, pos, end);
- }
- void encode(EncodeCallback encodeCallback) const override {
- encodeHeader(NULL_V, encodeCallback);
- }
-
- virtual std::unique_ptr<Item> clone() const override { return std::make_unique<Null>(); }
-};
-
-template <typename T>
-std::unique_ptr<T> downcastItem(std::unique_ptr<Item>&& v) {
- static_assert(std::is_base_of_v<Item, T> && !std::is_abstract_v<T>,
- "returned type is not an Item or is an abstract class");
- if (v && T::kMajorType == v->type()) {
- if constexpr (std::is_base_of_v<Simple, T>) {
- if (T::kSimpleType != v->asSimple()->simpleType()) {
- return nullptr;
- }
- }
- return std::unique_ptr<T>(static_cast<T*>(v.release()));
- } else {
- return nullptr;
- }
-}
-
-/**
- * Details. Mostly you shouldn't have to look below, except perhaps at the docstring for makeItem.
- */
-namespace details {
-
-template <typename T, typename V, typename Enable = void>
-struct is_iterator_pair_over : public std::false_type {};
-
-template <typename I1, typename I2, typename V>
-struct is_iterator_pair_over<
- std::pair<I1, I2>, V,
- typename std::enable_if_t<std::is_same_v<V, typename std::iterator_traits<I1>::value_type>>>
- : public std::true_type {};
-
-template <typename T, typename V, typename Enable = void>
-struct is_unique_ptr_of_subclass_of_v : public std::false_type {};
-
-template <typename T, typename P>
-struct is_unique_ptr_of_subclass_of_v<T, std::unique_ptr<P>,
- typename std::enable_if_t<std::is_base_of_v<T, P>>>
- : public std::true_type {};
-
-/* check if type is one of std::string (1), std::string_view (2), null-terminated char* (3) or pair
- * of iterators (4)*/
-template <typename T, typename Enable = void>
-struct is_text_type_v : public std::false_type {};
-
-template <typename T>
-struct is_text_type_v<
- T, typename std::enable_if_t<
- /* case 1 */ //
- std::is_same_v<std::remove_cv_t<std::remove_reference_t<T>>, std::string>
- /* case 2 */ //
- || std::is_same_v<std::remove_cv_t<std::remove_reference_t<T>>, std::string_view>
- /* case 3 */ //
- || std::is_same_v<std::remove_cv_t<std::decay_t<T>>, char*> //
- || std::is_same_v<std::remove_cv_t<std::decay_t<T>>, const char*>
- /* case 4 */
- || details::is_iterator_pair_over<T, char>::value>> : public std::true_type {};
-
-/**
- * Construct a unique_ptr<Item> from many argument types. Accepts:
- *
- * (a) booleans;
- * (b) integers, all sizes and signs;
- * (c) text strings, as defined by is_text_type_v above;
- * (d) byte strings, as std::vector<uint8_t>(d1), pair of iterators (d2) or pair<uint8_t*, size_T>
- * (d3); and
- * (e) Item subclass instances, including Array and Map. Items may be provided by naked pointer
- * (e1), unique_ptr (e2), reference (e3) or value (e3). If provided by reference or value, will
- * be moved if possible. If provided by pointer, ownership is taken.
- * (f) null pointer;
- */
-template <typename T>
-std::unique_ptr<Item> makeItem(T v) {
- Item* p = nullptr;
- if constexpr (/* case a */ std::is_same_v<T, bool>) {
- p = new Bool(v);
- } else if constexpr (/* case b */ std::is_integral_v<T>) { // b
- if (v < 0) {
- p = new Nint(v);
- } else {
- p = new Uint(static_cast<uint64_t>(v));
- }
- } else if constexpr (/* case c */ //
- details::is_text_type_v<T>::value) {
- p = new Tstr(v);
- } else if constexpr (/* case d1 */ //
- std::is_same_v<std::remove_cv_t<std::remove_reference_t<T>>,
- std::vector<uint8_t>>
- /* case d2 */ //
- || details::is_iterator_pair_over<T, uint8_t>::value
- /* case d3 */ //
- || std::is_same_v<std::remove_cv_t<std::remove_reference_t<T>>,
- std::pair<uint8_t*, size_t>>) {
- p = new Bstr(v);
- } else if constexpr (/* case e1 */ //
- std::is_pointer_v<T> &&
- std::is_base_of_v<Item, std::remove_pointer_t<T>>) {
- p = v;
- } else if constexpr (/* case e2 */ //
- details::is_unique_ptr_of_subclass_of_v<Item, T>::value) {
- p = v.release();
- } else if constexpr (/* case e3 */ //
- std::is_base_of_v<Item, T>) {
- p = new T(std::move(v));
- } else if constexpr (/* case f */ std::is_null_pointer_v<T>) {
- p = new Null();
- } else {
- // It's odd that this can't be static_assert(false), since it shouldn't be evaluated if one
- // of the above ifs matches. But static_assert(false) always triggers.
- static_assert(std::is_same_v<T, bool>, "makeItem called with unsupported type");
- }
- return std::unique_ptr<Item>(p);
-}
-
-} // namespace details
-
-template <typename... Args,
- /* Prevent use as copy ctor */ typename = std::enable_if_t<
- (sizeof...(Args)) != 1 ||
- !(std::is_same_v<Array, std::remove_cv_t<std::remove_reference_t<Args>>> || ...)>>
-Array::Array(Args&&... args) {
- mEntries.reserve(sizeof...(args));
- (mEntries.push_back(details::makeItem(std::forward<Args>(args))), ...);
-}
-
-template <typename T>
-Array& Array::add(T&& v) & {
- mEntries.push_back(details::makeItem(std::forward<T>(v)));
- return *this;
-}
-
-template <typename T>
-Array&& Array::add(T&& v) && {
- mEntries.push_back(details::makeItem(std::forward<T>(v)));
- return std::move(*this);
-}
-
-template <typename... Args,
- /* Prevent use as copy ctor */ typename = std::enable_if_t<(sizeof...(Args)) != 1>>
-Map::Map(Args&&... args) {
- static_assert((sizeof...(Args)) % 2 == 0, "Map must have an even number of entries");
- mEntries.reserve(sizeof...(args));
- (mEntries.push_back(details::makeItem(std::forward<Args>(args))), ...);
-}
-
-template <typename Key, typename Value>
-Map& Map::add(Key&& key, Value&& value) & {
- mEntries.push_back(details::makeItem(std::forward<Key>(key)));
- mEntries.push_back(details::makeItem(std::forward<Value>(value)));
- return *this;
-}
-
-template <typename Key, typename Value>
-Map&& Map::add(Key&& key, Value&& value) && {
- this->add(std::forward<Key>(key), std::forward<Value>(value));
- return std::move(*this);
-}
-
-template <typename Key, typename = std::enable_if_t<std::is_integral_v<Key> ||
- details::is_text_type_v<Key>::value>>
-std::pair<std::unique_ptr<Item>&, bool> Map::get(Key key) {
- assertInvariant();
- auto keyItem = details::makeItem(key);
- for (size_t i = 0; i < mEntries.size(); i += 2) {
- if (*keyItem == *mEntries[i]) {
- return {mEntries[i + 1], true};
- }
- }
- return {keyItem, false};
-}
-
-template <typename T>
-Semantic::Semantic(uint64_t value, T&& child) : mValue(value) {
- mEntries.reserve(1);
- mEntries.push_back(details::makeItem(std::forward<T>(child)));
-}
-
-} // namespace cppbor
diff --git a/identity/support/include/cppbor/cppbor_parse.h b/identity/support/include/cppbor/cppbor_parse.h
deleted file mode 100644
index 66cd5a3..0000000
--- a/identity/support/include/cppbor/cppbor_parse.h
+++ /dev/null
@@ -1,133 +0,0 @@
-/*
- * Copyright (c) 2019, 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.
- */
-
-#pragma once
-
-#include "cppbor.h"
-
-namespace cppbor {
-
-using ParseResult = std::tuple<std::unique_ptr<Item> /* result */, const uint8_t* /* newPos */,
- std::string /* errMsg */>;
-
-/**
- * Parse the first CBOR data item (possibly compound) from the range [begin, end).
- *
- * Returns a tuple of Item pointer, buffer pointer and error message. If parsing is successful, the
- * Item pointer is non-null, the buffer pointer points to the first byte after the
- * successfully-parsed item and the error message string is empty. If parsing fails, the Item
- * pointer is null, the buffer pointer points to the first byte that was unparseable (the first byte
- * of a data item header that is malformed in some way, e.g. an invalid value, or a length that is
- * too large for the remining buffer, etc.) and the string contains an error message describing the
- * problem encountered.
- */
-ParseResult parse(const uint8_t* begin, const uint8_t* end);
-
-/**
- * Parse the first CBOR data item (possibly compound) from the byte vector.
- *
- * Returns a tuple of Item pointer, buffer pointer and error message. If parsing is successful, the
- * Item pointer is non-null, the buffer pointer points to the first byte after the
- * successfully-parsed item and the error message string is empty. If parsing fails, the Item
- * pointer is null, the buffer pointer points to the first byte that was unparseable (the first byte
- * of a data item header that is malformed in some way, e.g. an invalid value, or a length that is
- * too large for the remining buffer, etc.) and the string contains an error message describing the
- * problem encountered.
- */
-inline ParseResult parse(const std::vector<uint8_t>& encoding) {
- return parse(encoding.data(), encoding.data() + encoding.size());
-}
-
-/**
- * Parse the first CBOR data item (possibly compound) from the range [begin, begin + size).
- *
- * Returns a tuple of Item pointer, buffer pointer and error message. If parsing is successful, the
- * Item pointer is non-null, the buffer pointer points to the first byte after the
- * successfully-parsed item and the error message string is empty. If parsing fails, the Item
- * pointer is null, the buffer pointer points to the first byte that was unparseable (the first byte
- * of a data item header that is malformed in some way, e.g. an invalid value, or a length that is
- * too large for the remining buffer, etc.) and the string contains an error message describing the
- * problem encountered.
- */
-inline ParseResult parse(const uint8_t* begin, size_t size) {
- return parse(begin, begin + size);
-}
-
-class ParseClient;
-
-/**
- * Parse the CBOR data in the range [begin, end) in streaming fashion, calling methods on the
- * provided ParseClient when elements are found.
- */
-void parse(const uint8_t* begin, const uint8_t* end, ParseClient* parseClient);
-
-/**
- * Parse the CBOR data in the vector in streaming fashion, calling methods on the
- * provided ParseClient when elements are found.
- */
-inline void parse(const std::vector<uint8_t>& encoding, ParseClient* parseClient) {
- return parse(encoding.data(), encoding.data() + encoding.size(), parseClient);
-}
-
-/**
- * A pure interface that callers of the streaming parse functions must implement.
- */
-class ParseClient {
- public:
- virtual ~ParseClient() {}
-
- /**
- * Called when an item is found. The Item pointer points to the found item; use type() and
- * the appropriate as*() method to examine the value. hdrBegin points to the first byte of the
- * header, valueBegin points to the first byte of the value and end points one past the end of
- * the item. In the case of header-only items, such as integers, and compound items (ARRAY,
- * MAP or SEMANTIC) whose end has not yet been found, valueBegin and end are equal and point to
- * the byte past the header.
- *
- * Note that for compound types (ARRAY, MAP, and SEMANTIC), the Item will have no content. For
- * Map and Array items, the size() method will return a correct value, but the index operators
- * are unsafe, and the object cannot be safely compared with another Array/Map.
- *
- * The method returns a ParseClient*. In most cases "return this;" will be the right answer,
- * but a different ParseClient may be returned, which the parser will begin using. If the method
- * returns nullptr, parsing will be aborted immediately.
- */
- virtual ParseClient* item(std::unique_ptr<Item>& item, const uint8_t* hdrBegin,
- const uint8_t* valueBegin, const uint8_t* end) = 0;
-
- /**
- * Called when the end of a compound item (MAP or ARRAY) is found. The item argument will be
- * the same one passed to the item() call -- and may be empty if item() moved its value out.
- * hdrBegin, valueBegin and end point to the beginning of the item header, the beginning of the
- * first contained value, and one past the end of the last contained value, respectively.
- *
- * Note that the Item will have no content.
- *
- * As with item(), itemEnd() can change the ParseClient by returning a different one, or end the
- * parsing by returning nullptr;
- */
- virtual ParseClient* itemEnd(std::unique_ptr<Item>& item, const uint8_t* hdrBegin,
- const uint8_t* valueBegin, const uint8_t* end) = 0;
-
- /**
- * Called when parsing encounters an error. position is set to the first unparsed byte (one
- * past the last successfully-parsed byte) and errorMessage contains an message explaining what
- * sort of error occurred.
- */
- virtual void error(const uint8_t* position, const std::string& errorMessage) = 0;
-};
-
-} // namespace cppbor
diff --git a/identity/support/src/cppbor.cpp b/identity/support/src/cppbor.cpp
deleted file mode 100644
index d289985..0000000
--- a/identity/support/src/cppbor.cpp
+++ /dev/null
@@ -1,225 +0,0 @@
-/*
- * Copyright (c) 2019, 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.
- */
-
-#include "cppbor.h"
-#include "cppbor_parse.h"
-
-#define LOG_TAG "CppBor"
-#include <android-base/logging.h>
-
-namespace cppbor {
-
-namespace {
-
-template <typename T, typename Iterator, typename = std::enable_if<std::is_unsigned<T>::value>>
-Iterator writeBigEndian(T value, Iterator pos) {
- for (unsigned i = 0; i < sizeof(value); ++i) {
- *pos++ = static_cast<uint8_t>(value >> (8 * (sizeof(value) - 1)));
- value = static_cast<T>(value << 8);
- }
- return pos;
-}
-
-template <typename T, typename = std::enable_if<std::is_unsigned<T>::value>>
-void writeBigEndian(T value, std::function<void(uint8_t)>& cb) {
- for (unsigned i = 0; i < sizeof(value); ++i) {
- cb(static_cast<uint8_t>(value >> (8 * (sizeof(value) - 1))));
- value = static_cast<T>(value << 8);
- }
-}
-
-} // namespace
-
-size_t headerSize(uint64_t addlInfo) {
- if (addlInfo < ONE_BYTE_LENGTH) return 1;
- if (addlInfo <= std::numeric_limits<uint8_t>::max()) return 2;
- if (addlInfo <= std::numeric_limits<uint16_t>::max()) return 3;
- if (addlInfo <= std::numeric_limits<uint32_t>::max()) return 5;
- return 9;
-}
-
-uint8_t* encodeHeader(MajorType type, uint64_t addlInfo, uint8_t* pos, const uint8_t* end) {
- size_t sz = headerSize(addlInfo);
- if (end - pos < static_cast<ssize_t>(sz)) return nullptr;
- switch (sz) {
- case 1:
- *pos++ = type | static_cast<uint8_t>(addlInfo);
- return pos;
- case 2:
- *pos++ = type | ONE_BYTE_LENGTH;
- *pos++ = static_cast<uint8_t>(addlInfo);
- return pos;
- case 3:
- *pos++ = type | TWO_BYTE_LENGTH;
- return writeBigEndian(static_cast<uint16_t>(addlInfo), pos);
- case 5:
- *pos++ = type | FOUR_BYTE_LENGTH;
- return writeBigEndian(static_cast<uint32_t>(addlInfo), pos);
- case 9:
- *pos++ = type | EIGHT_BYTE_LENGTH;
- return writeBigEndian(addlInfo, pos);
- default:
- CHECK(false); // Impossible to get here.
- return nullptr;
- }
-}
-
-void encodeHeader(MajorType type, uint64_t addlInfo, EncodeCallback encodeCallback) {
- size_t sz = headerSize(addlInfo);
- switch (sz) {
- case 1:
- encodeCallback(type | static_cast<uint8_t>(addlInfo));
- break;
- case 2:
- encodeCallback(type | ONE_BYTE_LENGTH);
- encodeCallback(static_cast<uint8_t>(addlInfo));
- break;
- case 3:
- encodeCallback(type | TWO_BYTE_LENGTH);
- writeBigEndian(static_cast<uint16_t>(addlInfo), encodeCallback);
- break;
- case 5:
- encodeCallback(type | FOUR_BYTE_LENGTH);
- writeBigEndian(static_cast<uint32_t>(addlInfo), encodeCallback);
- break;
- case 9:
- encodeCallback(type | EIGHT_BYTE_LENGTH);
- writeBigEndian(addlInfo, encodeCallback);
- break;
- default:
- CHECK(false); // Impossible to get here.
- }
-}
-
-bool Item::operator==(const Item& other) const& {
- if (type() != other.type()) return false;
- switch (type()) {
- case UINT:
- return *asUint() == *(other.asUint());
- case NINT:
- return *asNint() == *(other.asNint());
- case BSTR:
- return *asBstr() == *(other.asBstr());
- case TSTR:
- return *asTstr() == *(other.asTstr());
- case ARRAY:
- return *asArray() == *(other.asArray());
- case MAP:
- return *asMap() == *(other.asMap());
- case SIMPLE:
- return *asSimple() == *(other.asSimple());
- case SEMANTIC:
- return *asSemantic() == *(other.asSemantic());
- default:
- CHECK(false); // Impossible to get here.
- return false;
- }
-}
-
-Nint::Nint(int64_t v) : mValue(v) {
- CHECK(v < 0) << "Only negative values allowed";
-}
-
-bool Simple::operator==(const Simple& other) const& {
- if (simpleType() != other.simpleType()) return false;
-
- switch (simpleType()) {
- case BOOLEAN:
- return *asBool() == *(other.asBool());
- case NULL_T:
- return true;
- default:
- CHECK(false); // Impossible to get here.
- return false;
- }
-}
-
-uint8_t* Bstr::encode(uint8_t* pos, const uint8_t* end) const {
- pos = encodeHeader(mValue.size(), pos, end);
- if (!pos || end - pos < static_cast<ptrdiff_t>(mValue.size())) return nullptr;
- return std::copy(mValue.begin(), mValue.end(), pos);
-}
-
-void Bstr::encodeValue(EncodeCallback encodeCallback) const {
- for (auto c : mValue) {
- encodeCallback(c);
- }
-}
-
-uint8_t* Tstr::encode(uint8_t* pos, const uint8_t* end) const {
- pos = encodeHeader(mValue.size(), pos, end);
- if (!pos || end - pos < static_cast<ptrdiff_t>(mValue.size())) return nullptr;
- return std::copy(mValue.begin(), mValue.end(), pos);
-}
-
-void Tstr::encodeValue(EncodeCallback encodeCallback) const {
- for (auto c : mValue) {
- encodeCallback(static_cast<uint8_t>(c));
- }
-}
-
-bool CompoundItem::operator==(const CompoundItem& other) const& {
- return type() == other.type() //
- && addlInfo() == other.addlInfo() //
- // Can't use vector::operator== because the contents are pointers. std::equal lets us
- // provide a predicate that does the dereferencing.
- && std::equal(mEntries.begin(), mEntries.end(), other.mEntries.begin(),
- [](auto& a, auto& b) -> bool { return *a == *b; });
-}
-
-uint8_t* CompoundItem::encode(uint8_t* pos, const uint8_t* end) const {
- pos = encodeHeader(addlInfo(), pos, end);
- if (!pos) return nullptr;
- for (auto& entry : mEntries) {
- pos = entry->encode(pos, end);
- if (!pos) return nullptr;
- }
- return pos;
-}
-
-void CompoundItem::encode(EncodeCallback encodeCallback) const {
- encodeHeader(addlInfo(), encodeCallback);
- for (auto& entry : mEntries) {
- entry->encode(encodeCallback);
- }
-}
-
-void Map::assertInvariant() const {
- CHECK(mEntries.size() % 2 == 0);
-}
-
-std::unique_ptr<Item> Map::clone() const {
- assertInvariant();
- auto res = std::make_unique<Map>();
- for (size_t i = 0; i < mEntries.size(); i += 2) {
- res->add(mEntries[i]->clone(), mEntries[i + 1]->clone());
- }
- return res;
-}
-
-std::unique_ptr<Item> Array::clone() const {
- auto res = std::make_unique<Array>();
- for (size_t i = 0; i < mEntries.size(); i++) {
- res->add(mEntries[i]->clone());
- }
- return res;
-}
-
-void Semantic::assertInvariant() const {
- CHECK(mEntries.size() == 1);
-}
-
-} // namespace cppbor
diff --git a/identity/support/src/cppbor_parse.cpp b/identity/support/src/cppbor_parse.cpp
deleted file mode 100644
index c9ebb8a..0000000
--- a/identity/support/src/cppbor_parse.cpp
+++ /dev/null
@@ -1,351 +0,0 @@
-/*
- * Copyright (c) 2019, 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.
- */
-
-#include "cppbor_parse.h"
-
-#include <sstream>
-#include <stack>
-
-#define LOG_TAG "CppBor"
-#include <android-base/logging.h>
-
-namespace cppbor {
-
-namespace {
-
-std::string insufficientLengthString(size_t bytesNeeded, size_t bytesAvail,
- const std::string& type) {
- std::stringstream errStream;
- errStream << "Need " << bytesNeeded << " byte(s) for " << type << ", have " << bytesAvail
- << ".";
- return errStream.str();
-}
-
-template <typename T, typename = std::enable_if_t<std::is_unsigned_v<T>>>
-std::tuple<bool, uint64_t, const uint8_t*> parseLength(const uint8_t* pos, const uint8_t* end,
- ParseClient* parseClient) {
- if (pos + sizeof(T) > end) {
- parseClient->error(pos - 1, insufficientLengthString(sizeof(T), end - pos, "length field"));
- return {false, 0, pos};
- }
-
- const uint8_t* intEnd = pos + sizeof(T);
- T result = 0;
- do {
- result = static_cast<T>((result << 8) | *pos++);
- } while (pos < intEnd);
- return {true, result, pos};
-}
-
-std::tuple<const uint8_t*, ParseClient*> parseRecursively(const uint8_t* begin, const uint8_t* end,
- ParseClient* parseClient);
-
-std::tuple<const uint8_t*, ParseClient*> handleUint(uint64_t value, const uint8_t* hdrBegin,
- const uint8_t* hdrEnd,
- ParseClient* parseClient) {
- std::unique_ptr<Item> item = std::make_unique<Uint>(value);
- return {hdrEnd,
- parseClient->item(item, hdrBegin, hdrEnd /* valueBegin */, hdrEnd /* itemEnd */)};
-}
-
-std::tuple<const uint8_t*, ParseClient*> handleNint(uint64_t value, const uint8_t* hdrBegin,
- const uint8_t* hdrEnd,
- ParseClient* parseClient) {
- if (value > std::numeric_limits<int64_t>::max()) {
- parseClient->error(hdrBegin, "NINT values that don't fit in int64_t are not supported.");
- return {hdrBegin, nullptr /* end parsing */};
- }
- std::unique_ptr<Item> item = std::make_unique<Nint>(-1 - static_cast<uint64_t>(value));
- return {hdrEnd,
- parseClient->item(item, hdrBegin, hdrEnd /* valueBegin */, hdrEnd /* itemEnd */)};
-}
-
-std::tuple<const uint8_t*, ParseClient*> handleBool(uint64_t value, const uint8_t* hdrBegin,
- const uint8_t* hdrEnd,
- ParseClient* parseClient) {
- std::unique_ptr<Item> item = std::make_unique<Bool>(value == TRUE);
- return {hdrEnd,
- parseClient->item(item, hdrBegin, hdrEnd /* valueBegin */, hdrEnd /* itemEnd */)};
-}
-
-std::tuple<const uint8_t*, ParseClient*> handleNull(const uint8_t* hdrBegin, const uint8_t* hdrEnd,
- ParseClient* parseClient) {
- std::unique_ptr<Item> item = std::make_unique<Null>();
- return {hdrEnd,
- parseClient->item(item, hdrBegin, hdrEnd /* valueBegin */, hdrEnd /* itemEnd */)};
-}
-
-template <typename T>
-std::tuple<const uint8_t*, ParseClient*> handleString(uint64_t length, const uint8_t* hdrBegin,
- const uint8_t* valueBegin, const uint8_t* end,
- const std::string& errLabel,
- ParseClient* parseClient) {
- if (end - valueBegin < static_cast<ssize_t>(length)) {
- parseClient->error(hdrBegin, insufficientLengthString(length, end - valueBegin, errLabel));
- return {hdrBegin, nullptr /* end parsing */};
- }
-
- std::unique_ptr<Item> item = std::make_unique<T>(valueBegin, valueBegin + length);
- return {valueBegin + length,
- parseClient->item(item, hdrBegin, valueBegin, valueBegin + length)};
-}
-
-class IncompleteItem {
- public:
- virtual ~IncompleteItem() {}
- virtual void add(std::unique_ptr<Item> item) = 0;
-};
-
-class IncompleteArray : public Array, public IncompleteItem {
- public:
- IncompleteArray(size_t size) : mSize(size) {}
-
- // We return the "complete" size, rather than the actual size.
- size_t size() const override { return mSize; }
-
- void add(std::unique_ptr<Item> item) override {
- mEntries.reserve(mSize);
- mEntries.push_back(std::move(item));
- }
-
- private:
- size_t mSize;
-};
-
-class IncompleteMap : public Map, public IncompleteItem {
- public:
- IncompleteMap(size_t size) : mSize(size) {}
-
- // We return the "complete" size, rather than the actual size.
- size_t size() const override { return mSize; }
-
- void add(std::unique_ptr<Item> item) override {
- mEntries.reserve(mSize * 2);
- mEntries.push_back(std::move(item));
- }
-
- private:
- size_t mSize;
-};
-
-class IncompleteSemantic : public Semantic, public IncompleteItem {
- public:
- IncompleteSemantic(uint64_t value) : Semantic(value) {}
-
- // We return the "complete" size, rather than the actual size.
- size_t size() const override { return 1; }
-
- void add(std::unique_ptr<Item> item) override {
- mEntries.reserve(1);
- mEntries.push_back(std::move(item));
- }
-};
-
-std::tuple<const uint8_t*, ParseClient*> handleEntries(size_t entryCount, const uint8_t* hdrBegin,
- const uint8_t* pos, const uint8_t* end,
- const std::string& typeName,
- ParseClient* parseClient) {
- while (entryCount > 0) {
- --entryCount;
- if (pos == end) {
- parseClient->error(hdrBegin, "Not enough entries for " + typeName + ".");
- return {hdrBegin, nullptr /* end parsing */};
- }
- std::tie(pos, parseClient) = parseRecursively(pos, end, parseClient);
- if (!parseClient) return {hdrBegin, nullptr};
- }
- return {pos, parseClient};
-}
-
-std::tuple<const uint8_t*, ParseClient*> handleCompound(
- std::unique_ptr<Item> item, uint64_t entryCount, const uint8_t* hdrBegin,
- const uint8_t* valueBegin, const uint8_t* end, const std::string& typeName,
- ParseClient* parseClient) {
- parseClient =
- parseClient->item(item, hdrBegin, valueBegin, valueBegin /* don't know the end yet */);
- if (!parseClient) return {hdrBegin, nullptr};
-
- const uint8_t* pos;
- std::tie(pos, parseClient) =
- handleEntries(entryCount, hdrBegin, valueBegin, end, typeName, parseClient);
- if (!parseClient) return {hdrBegin, nullptr};
-
- return {pos, parseClient->itemEnd(item, hdrBegin, valueBegin, pos)};
-}
-
-std::tuple<const uint8_t*, ParseClient*> parseRecursively(const uint8_t* begin, const uint8_t* end,
- ParseClient* parseClient) {
- const uint8_t* pos = begin;
-
- MajorType type = static_cast<MajorType>(*pos & 0xE0);
- uint8_t tagInt = *pos & 0x1F;
- ++pos;
-
- bool success = true;
- uint64_t addlData;
- if (tagInt < ONE_BYTE_LENGTH || tagInt > EIGHT_BYTE_LENGTH) {
- addlData = tagInt;
- } else {
- switch (tagInt) {
- case ONE_BYTE_LENGTH:
- std::tie(success, addlData, pos) = parseLength<uint8_t>(pos, end, parseClient);
- break;
-
- case TWO_BYTE_LENGTH:
- std::tie(success, addlData, pos) = parseLength<uint16_t>(pos, end, parseClient);
- break;
-
- case FOUR_BYTE_LENGTH:
- std::tie(success, addlData, pos) = parseLength<uint32_t>(pos, end, parseClient);
- break;
-
- case EIGHT_BYTE_LENGTH:
- std::tie(success, addlData, pos) = parseLength<uint64_t>(pos, end, parseClient);
- break;
-
- default:
- CHECK(false); // It's impossible to get here
- break;
- }
- }
-
- if (!success) return {begin, nullptr};
-
- switch (type) {
- case UINT:
- return handleUint(addlData, begin, pos, parseClient);
-
- case NINT:
- return handleNint(addlData, begin, pos, parseClient);
-
- case BSTR:
- return handleString<Bstr>(addlData, begin, pos, end, "byte string", parseClient);
-
- case TSTR:
- return handleString<Tstr>(addlData, begin, pos, end, "text string", parseClient);
-
- case ARRAY:
- return handleCompound(std::make_unique<IncompleteArray>(addlData), addlData, begin, pos,
- end, "array", parseClient);
-
- case MAP:
- return handleCompound(std::make_unique<IncompleteMap>(addlData), addlData * 2, begin,
- pos, end, "map", parseClient);
-
- case SEMANTIC:
- return handleCompound(std::make_unique<IncompleteSemantic>(addlData), 1, begin, pos,
- end, "semantic", parseClient);
-
- case SIMPLE:
- switch (addlData) {
- case TRUE:
- case FALSE:
- return handleBool(addlData, begin, pos, parseClient);
- case NULL_V:
- return handleNull(begin, pos, parseClient);
- }
- }
- CHECK(false); // Impossible to get here.
- return {};
-}
-
-class FullParseClient : public ParseClient {
- public:
- virtual ParseClient* item(std::unique_ptr<Item>& item, const uint8_t*, const uint8_t*,
- const uint8_t* end) override {
- if (mParentStack.empty() && !item->isCompound()) {
- // This is the first and only item.
- mTheItem = std::move(item);
- mPosition = end;
- return nullptr; // We're done.
- }
-
- if (item->isCompound()) {
- // Starting a new compound data item, i.e. a new parent. Save it on the parent stack.
- // It's safe to save a raw pointer because the unique_ptr is guaranteed to stay in
- // existence until the corresponding itemEnd() call.
- assert(dynamic_cast<CompoundItem*>(item.get()));
- mParentStack.push(static_cast<CompoundItem*>(item.get()));
- return this;
- } else {
- appendToLastParent(std::move(item));
- return this;
- }
- }
-
- virtual ParseClient* itemEnd(std::unique_ptr<Item>& item, const uint8_t*, const uint8_t*,
- const uint8_t* end) override {
- CHECK(item->isCompound() && item.get() == mParentStack.top());
- mParentStack.pop();
-
- if (mParentStack.empty()) {
- mTheItem = std::move(item);
- mPosition = end;
- return nullptr; // We're done
- } else {
- appendToLastParent(std::move(item));
- return this;
- }
- }
-
- virtual void error(const uint8_t* position, const std::string& errorMessage) override {
- mPosition = position;
- mErrorMessage = errorMessage;
- }
-
- std::tuple<std::unique_ptr<Item> /* result */, const uint8_t* /* newPos */,
- std::string /* errMsg */>
- parseResult() {
- std::unique_ptr<Item> p = std::move(mTheItem);
- return {std::move(p), mPosition, std::move(mErrorMessage)};
- }
-
- private:
- void appendToLastParent(std::unique_ptr<Item> item) {
- auto parent = mParentStack.top();
- assert(dynamic_cast<IncompleteItem*>(parent));
- if (parent->type() == ARRAY) {
- static_cast<IncompleteArray*>(parent)->add(std::move(item));
- } else if (parent->type() == MAP) {
- static_cast<IncompleteMap*>(parent)->add(std::move(item));
- } else if (parent->type() == SEMANTIC) {
- static_cast<IncompleteSemantic*>(parent)->add(std::move(item));
- } else {
- CHECK(false); // Impossible to get here.
- }
- }
-
- std::unique_ptr<Item> mTheItem;
- std::stack<CompoundItem*> mParentStack;
- const uint8_t* mPosition = nullptr;
- std::string mErrorMessage;
-};
-
-} // anonymous namespace
-
-void parse(const uint8_t* begin, const uint8_t* end, ParseClient* parseClient) {
- parseRecursively(begin, end, parseClient);
-}
-
-std::tuple<std::unique_ptr<Item> /* result */, const uint8_t* /* newPos */,
- std::string /* errMsg */>
-parse(const uint8_t* begin, const uint8_t* end) {
- FullParseClient parseClient;
- parse(begin, end, &parseClient);
- return parseClient.parseResult();
-}
-
-} // namespace cppbor
diff --git a/identity/support/tests/cppbor_test.cpp b/identity/support/tests/cppbor_test.cpp
deleted file mode 100644
index 3eb5598..0000000
--- a/identity/support/tests/cppbor_test.cpp
+++ /dev/null
@@ -1,1013 +0,0 @@
-/*
- * Copyright (c) 2019, 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.
- */
-
-#include <iomanip>
-#include <sstream>
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "cppbor.h"
-#include "cppbor_parse.h"
-
-using namespace cppbor;
-using namespace std;
-
-using ::testing::_;
-using ::testing::AllOf;
-using ::testing::ByRef;
-using ::testing::InSequence;
-using ::testing::IsNull;
-using ::testing::NotNull;
-using ::testing::Return;
-using ::testing::Truly;
-using ::testing::Unused;
-
-string hexDump(const string& str) {
- stringstream s;
- for (auto c : str) {
- s << setfill('0') << setw(2) << hex << (static_cast<unsigned>(c) & 0xff);
- }
- return s.str();
-}
-
-TEST(SimpleValueTest, UnsignedValueSizes) {
- // Check that unsigned integers encode to correct lengths, and that encodedSize() is correct.
- vector<pair<uint64_t /* value */, size_t /* expected encoded size */>> testCases{
- {0, 1},
- {1, 1},
- {23, 1},
- {24, 2},
- {255, 2},
- {256, 3},
- {65535, 3},
- {65536, 5},
- {4294967295, 5},
- {4294967296, 9},
- {std::numeric_limits<uint64_t>::max(), 9},
- };
- for (auto& testCase : testCases) {
- Uint val(testCase.first);
- EXPECT_EQ(testCase.second, val.encodedSize()) << "Wrong size for value " << testCase.first;
- EXPECT_EQ(val.encodedSize(), val.toString().size())
- << "encodedSize and encoding disagree for value " << testCase.first;
- }
-}
-
-TEST(SimpleValueTest, UnsignedValueEncodings) {
- EXPECT_EQ("\x00"s, Uint(0u).toString());
- EXPECT_EQ("\x01"s, Uint(1u).toString());
- EXPECT_EQ("\x0a"s, Uint(10u).toString());
- EXPECT_EQ("\x17"s, Uint(23u).toString());
- EXPECT_EQ("\x18\x18"s, Uint(24u).toString());
- EXPECT_EQ("\x18\x19"s, Uint(25u).toString());
- EXPECT_EQ("\x18\x64"s, Uint(100u).toString());
- EXPECT_EQ("\x19\x03\xe8"s, Uint(1000u).toString());
- EXPECT_EQ("\x1a\x00\x0f\x42\x40"s, Uint(1000000u).toString());
- EXPECT_EQ("\x1b\x00\x00\x00\xe8\xd4\xa5\x10\x00"s, Uint(1000000000000u).toString());
- EXPECT_EQ("\x1B\x7f\xff\xff\xff\xff\xff\xff\xff"s,
- Uint(std::numeric_limits<int64_t>::max()).toString());
-}
-
-TEST(SimpleValueTest, NegativeValueEncodings) {
- EXPECT_EQ("\x20"s, Nint(-1).toString());
- EXPECT_EQ("\x28"s, Nint(-9).toString());
- EXPECT_EQ("\x29"s, Nint(-10).toString());
- EXPECT_EQ("\x36"s, Nint(-23).toString());
- EXPECT_EQ("\x37"s, Nint(-24).toString());
- EXPECT_EQ("\x38\x18"s, Nint(-25).toString());
- EXPECT_EQ("\x38\x62"s, Nint(-99).toString());
- EXPECT_EQ("\x38\x63"s, Nint(-100).toString());
- EXPECT_EQ("\x39\x03\xe6"s, Nint(-999).toString());
- EXPECT_EQ("\x39\x03\xe7"s, Nint(-1000).toString());
- EXPECT_EQ("\x3a\x00\x0f\x42\x3F"s, Nint(-1000000).toString());
- EXPECT_EQ("\x3b\x00\x00\x00\xe8\xd4\xa5\x0f\xff"s, Nint(-1000000000000).toString());
- EXPECT_EQ("\x3B\x7f\xff\xff\xff\xff\xff\xff\xff"s,
- Nint(std::numeric_limits<int64_t>::min()).toString());
-}
-
-TEST(SimpleValueDeathTest, NegativeValueEncodings) {
- EXPECT_DEATH(Nint(0), "");
- EXPECT_DEATH(Nint(1), "");
-}
-
-TEST(SimpleValueTest, BooleanEncodings) {
- EXPECT_EQ("\xf4"s, Bool(false).toString());
- EXPECT_EQ("\xf5"s, Bool(true).toString());
-}
-
-TEST(SimpleValueTest, ByteStringEncodings) {
- EXPECT_EQ("\x40", Bstr("").toString());
- EXPECT_EQ("\x41\x61", Bstr("a").toString());
- EXPECT_EQ("\x41\x41", Bstr("A").toString());
- EXPECT_EQ("\x44\x49\x45\x54\x46", Bstr("IETF").toString());
- EXPECT_EQ("\x42\x22\x5c", Bstr("\"\\").toString());
- EXPECT_EQ("\x42\xc3\xbc", Bstr("\xc3\xbc").toString());
- EXPECT_EQ("\x43\xe6\xb0\xb4", Bstr("\xe6\xb0\xb4").toString());
- EXPECT_EQ("\x44\xf0\x90\x85\x91", Bstr("\xf0\x90\x85\x91").toString());
- EXPECT_EQ("\x44\x01\x02\x03\x04", Bstr("\x01\x02\x03\x04").toString());
- EXPECT_EQ("\x44\x40\x40\x40\x40", Bstr("@@@@").toString());
-}
-
-TEST(SimpleValueTest, TextStringEncodings) {
- EXPECT_EQ("\x60"s, Tstr("").toString());
- EXPECT_EQ("\x61\x61"s, Tstr("a").toString());
- EXPECT_EQ("\x61\x41"s, Tstr("A").toString());
- EXPECT_EQ("\x64\x49\x45\x54\x46"s, Tstr("IETF").toString());
- EXPECT_EQ("\x62\x22\x5c"s, Tstr("\"\\").toString());
- EXPECT_EQ("\x62\xc3\xbc"s, Tstr("\xc3\xbc").toString());
- EXPECT_EQ("\x63\xe6\xb0\xb4"s, Tstr("\xe6\xb0\xb4").toString());
- EXPECT_EQ("\x64\xf0\x90\x85\x91"s, Tstr("\xf0\x90\x85\x91").toString());
- EXPECT_EQ("\x64\x01\x02\x03\x04"s, Tstr("\x01\x02\x03\x04").toString());
-}
-
-TEST(IsIteratorPairOverTest, All) {
- EXPECT_TRUE((
- details::is_iterator_pair_over<pair<string::iterator, string::iterator>, char>::value));
- EXPECT_TRUE((details::is_iterator_pair_over<pair<string::const_iterator, string::iterator>,
- char>::value));
- EXPECT_TRUE((details::is_iterator_pair_over<pair<string::iterator, string::const_iterator>,
- char>::value));
- EXPECT_TRUE((details::is_iterator_pair_over<pair<char*, char*>, char>::value));
- EXPECT_TRUE((details::is_iterator_pair_over<pair<const char*, char*>, char>::value));
- EXPECT_TRUE((details::is_iterator_pair_over<pair<char*, const char*>, char>::value));
- EXPECT_FALSE((details::is_iterator_pair_over<pair<string::iterator, string::iterator>,
- uint8_t>::value));
- EXPECT_FALSE((details::is_iterator_pair_over<pair<char*, char*>, uint8_t>::value));
- EXPECT_TRUE((details::is_iterator_pair_over<
- pair<vector<uint8_t>::iterator, vector<uint8_t>::iterator>, uint8_t>::value));
- EXPECT_TRUE((details::is_iterator_pair_over<
- pair<vector<uint8_t>::const_iterator, vector<uint8_t>::iterator>,
- uint8_t>::value));
- EXPECT_TRUE((details::is_iterator_pair_over<
- pair<vector<uint8_t>::iterator, vector<uint8_t>::const_iterator>,
- uint8_t>::value));
- EXPECT_TRUE((details::is_iterator_pair_over<pair<uint8_t*, uint8_t*>, uint8_t>::value));
- EXPECT_TRUE((details::is_iterator_pair_over<pair<const uint8_t*, uint8_t*>, uint8_t>::value));
- EXPECT_TRUE((details::is_iterator_pair_over<pair<uint8_t*, const uint8_t*>, uint8_t>::value));
- EXPECT_FALSE((details::is_iterator_pair_over<
- pair<vector<uint8_t>::iterator, vector<uint8_t>::iterator>, char>::value));
- EXPECT_FALSE((details::is_iterator_pair_over<pair<uint8_t*, const uint8_t*>, char>::value));
-}
-
-TEST(MakeEntryTest, Boolean) {
- EXPECT_EQ("\xf4"s, details::makeItem(false)->toString());
-}
-
-TEST(MakeEntryTest, Integers) {
- EXPECT_EQ("\x00"s, details::makeItem(static_cast<uint8_t>(0))->toString());
- EXPECT_EQ("\x00"s, details::makeItem(static_cast<uint16_t>(0))->toString());
- EXPECT_EQ("\x00"s, details::makeItem(static_cast<uint32_t>(0))->toString());
- EXPECT_EQ("\x00"s, details::makeItem(static_cast<uint64_t>(0))->toString());
- EXPECT_EQ("\x00"s, details::makeItem(static_cast<int8_t>(0))->toString());
- EXPECT_EQ("\x00"s, details::makeItem(static_cast<int16_t>(0))->toString());
- EXPECT_EQ("\x00"s, details::makeItem(static_cast<int32_t>(0))->toString());
- EXPECT_EQ("\x00"s, details::makeItem(static_cast<int64_t>(0))->toString());
- EXPECT_EQ("\x20"s, details::makeItem(static_cast<int8_t>(-1))->toString());
- EXPECT_EQ("\x20"s, details::makeItem(static_cast<int16_t>(-1))->toString());
- EXPECT_EQ("\x20"s, details::makeItem(static_cast<int32_t>(-1))->toString());
- EXPECT_EQ("\x20"s, details::makeItem(static_cast<int64_t>(-1))->toString());
-
- EXPECT_EQ("\x1b\xff\xff\xff\xff\xff\xff\xff\xff"s,
- details::makeItem(static_cast<uint64_t>(std::numeric_limits<uint64_t>::max()))
- ->toString());
-}
-
-TEST(MakeEntryTest, StdStrings) {
- string s1("hello");
- const string s2("hello");
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s, details::makeItem(s1)->toString()); // copy of string
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s,
- details::makeItem(s2)->toString()); // copy of const string
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s,
- details::makeItem(std::move(s1))->toString()); // move string
- EXPECT_EQ(0U, s1.size()); // Prove string was moved, not copied.
-}
-
-TEST(MakeEntryTest, StdStringViews) {
- string_view s1("hello");
- const string_view s2("hello");
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s, details::makeItem(s1)->toString());
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s, details::makeItem(s2)->toString());
-}
-
-TEST(MakeEntryTest, CStrings) {
- char s1[] = "hello";
- const char s2[] = "hello";
- const char* s3 = "hello";
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s, details::makeItem(s1)->toString());
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s, details::makeItem(s2)->toString());
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s, details::makeItem(s3)->toString());
-}
-
-TEST(MakeEntryTest, StringIteratorPairs) {
- // Use iterators from string to prove that "real" iterators work
- string s1 = "hello"s;
- pair<string::iterator, string::iterator> p1 = make_pair(s1.begin(), s1.end());
-
- const pair<string::iterator, string::iterator> p2 = p1;
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s, details::makeItem(p1)->toString());
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s, details::makeItem(p2)->toString());
-
- // Use char*s as iterators
- const char* s2 = "hello";
- pair p3 = make_pair(s2, s2 + 5);
- const pair p4 = p3;
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s, details::makeItem(p3)->toString());
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s, details::makeItem(p4)->toString());
-}
-
-TEST(MakeEntryTest, ByteStrings) {
- vector<uint8_t> v1 = {0x00, 0x01, 0x02};
- const vector<uint8_t> v2 = {0x00, 0x01, 0x02};
- EXPECT_EQ("\x43\x00\x01\x02"s, details::makeItem(v1)->toString()); // copy of vector
- EXPECT_EQ("\x43\x00\x01\x02"s, details::makeItem(v2)->toString()); // copy of const vector
- EXPECT_EQ("\x43\x00\x01\x02"s, details::makeItem(std::move(v1))->toString()); // move vector
- EXPECT_EQ(0U, v1.size()); // Prove vector was moved, not copied.
-}
-
-TEST(MakeEntryTest, ByteStringIteratorPairs) {
- using vec = vector<uint8_t>;
- using iter = vec::iterator;
- vec v1 = {0x00, 0x01, 0x02};
- pair<iter, iter> p1 = make_pair(v1.begin(), v1.end());
- const pair<iter, iter> p2 = make_pair(v1.begin(), v1.end());
- EXPECT_EQ("\x43\x00\x01\x02"s, details::makeItem(p1)->toString());
- EXPECT_EQ("\x43\x00\x01\x02"s, details::makeItem(p2)->toString());
-
- // Use uint8_t*s as iterators
- uint8_t v2[] = {0x00, 0x01, 0x02};
- uint8_t* v3 = v2;
- pair<uint8_t*, uint8_t*> p3 = make_pair(v2, v2 + 3);
- const pair<uint8_t*, uint8_t*> p4 = make_pair(v2, v2 + 3);
- pair<uint8_t*, uint8_t*> p5 = make_pair(v3, v3 + 3);
- const pair<uint8_t*, uint8_t*> p6 = make_pair(v3, v3 + 3);
- EXPECT_EQ("\x43\x00\x01\x02"s, details::makeItem(p3)->toString());
- EXPECT_EQ("\x43\x00\x01\x02"s, details::makeItem(p4)->toString());
- EXPECT_EQ("\x43\x00\x01\x02"s, details::makeItem(p5)->toString());
- EXPECT_EQ("\x43\x00\x01\x02"s, details::makeItem(p6)->toString());
-}
-
-TEST(MakeEntryTest, ByteStringBuffers) {
- uint8_t v1[] = {0x00, 0x01, 0x02};
- EXPECT_EQ("\x43\x00\x01\x02"s, details::makeItem(make_pair(v1, 3))->toString());
-}
-
-TEST(MakeEntryTest, ItemPointer) {
- Uint* p1 = new Uint(0);
- EXPECT_EQ("\x00"s, details::makeItem(p1)->toString());
- EXPECT_EQ("\x60"s, details::makeItem(new Tstr(string()))->toString());
-}
-
-TEST(MakeEntryTest, ItemReference) {
- Tstr str("hello"s);
- Tstr& strRef = str;
- const Tstr& strConstRef = str;
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s, details::makeItem(str)->toString());
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s, details::makeItem(strRef)->toString());
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s, details::makeItem(strConstRef)->toString());
- EXPECT_EQ("\x65\x68\x65\x6c\x6c\x6f"s, details::makeItem(std::move(str))->toString());
- EXPECT_EQ("\x60"s, details::makeItem(str)->toString()); // Prove that it moved
-
- EXPECT_EQ("\x00"s, details::makeItem(Uint(0))->toString());
-
- EXPECT_EQ("\x43\x00\x01\x02"s,
- details::makeItem(Bstr(vector<uint8_t>{0x00, 0x01, 0x02}))->toString());
-
- EXPECT_EQ("\x80"s, details::makeItem(Array())->toString());
- EXPECT_EQ("\xa0"s, details::makeItem(Map())->toString());
-}
-
-TEST(CompoundValueTest, ArrayOfInts) {
- EXPECT_EQ("\x80"s, Array().toString());
- Array(Uint(0)).toString();
-
- EXPECT_EQ("\x81\x00"s, Array(Uint(0U)).toString());
- EXPECT_EQ("\x82\x00\x01"s, Array(Uint(0), Uint(1)).toString());
- EXPECT_EQ("\x83\x00\x01\x38\x62"s, Array(Uint(0), Uint(1), Nint(-99)).toString());
-
- EXPECT_EQ("\x81\x00"s, Array(0).toString());
- EXPECT_EQ("\x82\x00\x01"s, Array(0, 1).toString());
- EXPECT_EQ("\x83\x00\x01\x38\x62"s, Array(0, 1, -99).toString());
-}
-
-TEST(CompoundValueTest, MapOfInts) {
- EXPECT_EQ("\xA0"s, Map().toString());
- EXPECT_EQ("\xA1\x00\x01"s, Map(Uint(0), Uint(1)).toString());
- // Maps with an odd number of arguments will fail to compile. Uncomment the next lines to test.
- // EXPECT_EQ("\xA1\x00"s, Map(Int(0)).toString());
- // EXPECT_EQ("\xA1\x00\x01\x02"s, Map(Int(0), Int(1), Int(2)).toString());
-}
-
-TEST(CompoundValueTest, MixedArray) {
- vector<uint8_t> vec = {3, 2, 1};
- EXPECT_EQ("\x84\x01\x20\x43\x03\x02\x01\x65\x68\x65\x6C\x6C\x6F"s,
- Array(Uint(1), Nint(-1), Bstr(vec), Tstr("hello")).toString());
-
- EXPECT_EQ("\x84\x01\x20\x43\x03\x02\x01\x65\x68\x65\x6C\x6C\x6F"s,
- Array(1, -1, vec, "hello").toString());
-}
-
-TEST(CompoundValueTest, MixedMap) {
- vector<uint8_t> vec = {3, 2, 1};
- EXPECT_EQ("\xA2\x01\x20\x43\x03\x02\x01\x65\x68\x65\x6C\x6C\x6F"s,
- Map(Uint(1), Nint(-1), Bstr(vec), Tstr("hello")).toString());
-
- EXPECT_EQ("\xA2\x01\x20\x43\x03\x02\x01\x65\x68\x65\x6C\x6C\x6F"s,
- Map(1, -1, vec, "hello").toString());
-}
-
-TEST(CompoundValueTest, NestedStructures) {
- vector<uint8_t> vec = {3, 2, 1};
-
- string expectedEncoding =
- "\xA2\x66\x4F\x75\x74\x65\x72\x31\x82\xA2\x66\x49\x6E\x6E\x65\x72\x31\x18\x63\x66\x49"
- "\x6E"
- "\x6E\x65\x72\x32\x43\x03\x02\x01\x63\x66\x6F\x6F\x66\x4F\x75\x74\x65\x72\x32\x0A"s;
-
- // Do it with explicitly-created Items
- EXPECT_EQ(expectedEncoding,
- Map(Tstr("Outer1"),
- Array( //
- Map(Tstr("Inner1"), Uint(99), Tstr("Inner2"), Bstr(vec)), Tstr("foo")),
- Tstr("Outer2"), //
- Uint(10))
- .toString());
- EXPECT_EQ(3U, vec.size());
-
- // Now just use convertible types
- EXPECT_EQ(expectedEncoding, Map("Outer1",
- Array(Map("Inner1", 99, //
- "Inner2", vec),
- "foo"),
- "Outer2", 10)
- .toString());
- EXPECT_EQ(3U, vec.size());
-
- // Finally, do it with the .add() method. This is slightly less efficient, but has the
- // advantage you can build a structure up incrementally, or somewhat fluently if you like.
- // First, fluently.
- EXPECT_EQ(expectedEncoding, Map().add("Outer1", Array().add(Map() //
- .add("Inner1", 99)
- .add("Inner2", vec))
- .add("foo"))
- .add("Outer2", 10)
- .toString());
- EXPECT_EQ(3U, vec.size());
-
- // Next, more incrementally
- Array arr;
- arr.add(Map() //
- .add("Inner1", 99)
- .add("Inner2", vec))
- .add("foo");
- EXPECT_EQ(3U, vec.size());
-
- Map m;
- m.add("Outer1", std::move(arr)); // Moving is necessary; Map and Array cannot be copied.
- m.add("Outer2", 10);
- auto s = m.toString();
- EXPECT_EQ(expectedEncoding, s);
-}
-
-TEST(EncodingMethodsTest, AllVariants) {
- Map map;
- map.add("key1", Array().add(Map() //
- .add("key_a", 9999999)
- .add("key_b", std::vector<uint8_t>{0x01, 0x02, 0x03})
- .add("key_c", std::numeric_limits<uint64_t>::max())
- .add("key_d", std::numeric_limits<int16_t>::min()))
- .add("foo"))
- .add("key2", true);
-
- std::vector<uint8_t> buf;
- buf.resize(map.encodedSize());
-
- EXPECT_EQ(buf.data() + buf.size(), map.encode(buf.data(), buf.data() + buf.size()));
-
- EXPECT_EQ(buf, map.encode());
-
- std::vector<uint8_t> buf2;
- map.encode(std::back_inserter(buf2));
- EXPECT_EQ(buf, buf2);
-
- auto iter = buf.begin();
- map.encode([&](uint8_t c) { EXPECT_EQ(c, *iter++); });
-}
-
-TEST(EncodingMethodsTest, UintWithTooShortBuf) {
- Uint val(100000);
- vector<uint8_t> buf(val.encodedSize() - 1);
- EXPECT_EQ(nullptr, val.encode(buf.data(), buf.data() + buf.size()));
-}
-
-TEST(EncodingMethodsTest, TstrWithTooShortBuf) {
- Tstr val("01234567890123456789012345"s);
- vector<uint8_t> buf(1);
- EXPECT_EQ(nullptr, val.encode(buf.data(), buf.data() + buf.size()));
-
- buf.resize(val.encodedSize() - 1);
- EXPECT_EQ(nullptr, val.encode(buf.data(), buf.data() + buf.size()));
-}
-
-TEST(EncodingMethodsTest, BstrWithTooShortBuf) {
- Bstr val("01234567890123456789012345"s);
- vector<uint8_t> buf(1);
- EXPECT_EQ(nullptr, val.encode(buf.data(), buf.data() + buf.size()));
-
- buf.resize(val.encodedSize() - 1);
- EXPECT_EQ(nullptr, val.encode(buf.data(), buf.data() + buf.size()));
-}
-
-TEST(EncodingMethodsTest, ArrayWithTooShortBuf) {
- Array val("a", 5, -100);
-
- std::vector<uint8_t> buf(val.encodedSize() - 1);
- EXPECT_EQ(nullptr, val.encode(buf.data(), buf.data() + buf.size()));
-}
-
-TEST(EncodingMethodsTest, MapWithTooShortBuf) {
- Map map;
- map.add("key1", Array().add(Map() //
- .add("key_a", 99)
- .add("key_b", std::vector<uint8_t>{0x01, 0x02, 0x03}))
- .add("foo"))
- .add("key2", true);
-
- std::vector<uint8_t> buf(map.encodedSize() - 1);
- EXPECT_EQ(nullptr, map.encode(buf.data(), buf.data() + buf.size()));
-}
-
-TEST(EqualityTest, Uint) {
- Uint val(99);
- EXPECT_EQ(val, Uint(99));
-
- EXPECT_NE(val, Uint(98));
- EXPECT_NE(val, Nint(-1));
- EXPECT_NE(val, Tstr("99"));
- EXPECT_NE(val, Bstr("99"));
- EXPECT_NE(val, Bool(false));
- EXPECT_NE(val, Array(99, 1));
- EXPECT_NE(val, Map(99, 1));
-}
-
-TEST(EqualityTest, Nint) {
- Nint val(-1);
- EXPECT_EQ(val, Nint(-1));
-
- EXPECT_NE(val, Uint(99));
- EXPECT_NE(val, Nint(-4));
- EXPECT_NE(val, Tstr("99"));
- EXPECT_NE(val, Bstr("99"));
- EXPECT_NE(val, Bool(false));
- EXPECT_NE(val, Array(99));
- EXPECT_NE(val, Map(99, 1));
-}
-
-TEST(EqualityTest, Tstr) {
- Tstr val("99");
- EXPECT_EQ(val, Tstr("99"));
-
- EXPECT_NE(val, Uint(99));
- EXPECT_NE(val, Nint(-1));
- EXPECT_NE(val, Nint(-4));
- EXPECT_NE(val, Tstr("98"));
- EXPECT_NE(val, Bstr("99"));
- EXPECT_NE(val, Bool(false));
- EXPECT_NE(val, Array(99, 1));
- EXPECT_NE(val, Map(99, 1));
-}
-
-TEST(EqualityTest, Bstr) {
- Bstr val("99");
- EXPECT_EQ(val, Bstr("99"));
-
- EXPECT_NE(val, Uint(99));
- EXPECT_NE(val, Nint(-1));
- EXPECT_NE(val, Nint(-4));
- EXPECT_NE(val, Tstr("99"));
- EXPECT_NE(val, Bstr("98"));
- EXPECT_NE(val, Bool(false));
- EXPECT_NE(val, Array(99, 1));
- EXPECT_NE(val, Map(99, 1));
-}
-
-TEST(EqualityTest, Bool) {
- Bool val(false);
- EXPECT_EQ(val, Bool(false));
-
- EXPECT_NE(val, Uint(99));
- EXPECT_NE(val, Nint(-1));
- EXPECT_NE(val, Nint(-4));
- EXPECT_NE(val, Tstr("99"));
- EXPECT_NE(val, Bstr("98"));
- EXPECT_NE(val, Bool(true));
- EXPECT_NE(val, Array(99, 1));
- EXPECT_NE(val, Map(99, 1));
-}
-
-TEST(EqualityTest, Array) {
- Array val(99, 1);
- EXPECT_EQ(val, Array(99, 1));
-
- EXPECT_NE(val, Uint(99));
- EXPECT_NE(val, Nint(-1));
- EXPECT_NE(val, Nint(-4));
- EXPECT_NE(val, Tstr("99"));
- EXPECT_NE(val, Bstr("98"));
- EXPECT_NE(val, Bool(true));
- EXPECT_NE(val, Array(99, 2));
- EXPECT_NE(val, Array(98, 1));
- EXPECT_NE(val, Array(99, 1, 2));
- EXPECT_NE(val, Map(99, 1));
-}
-
-TEST(EqualityTest, Map) {
- Map val(99, 1);
- EXPECT_EQ(val, Map(99, 1));
-
- EXPECT_NE(val, Uint(99));
- EXPECT_NE(val, Nint(-1));
- EXPECT_NE(val, Nint(-4));
- EXPECT_NE(val, Tstr("99"));
- EXPECT_NE(val, Bstr("98"));
- EXPECT_NE(val, Bool(true));
- EXPECT_NE(val, Array(99, 1));
- EXPECT_NE(val, Map(99, 2));
- EXPECT_NE(val, Map(99, 1, 99, 2));
-}
-
-TEST(ConvertTest, Uint) {
- unique_ptr<Item> item = details::makeItem(10);
-
- EXPECT_EQ(UINT, item->type());
- EXPECT_NE(nullptr, item->asInt());
- EXPECT_NE(nullptr, item->asUint());
- EXPECT_EQ(nullptr, item->asNint());
- EXPECT_EQ(nullptr, item->asTstr());
- EXPECT_EQ(nullptr, item->asBstr());
- EXPECT_EQ(nullptr, item->asSimple());
- EXPECT_EQ(nullptr, item->asMap());
- EXPECT_EQ(nullptr, item->asArray());
-
- EXPECT_EQ(10, item->asInt()->value());
- EXPECT_EQ(10, item->asUint()->value());
-}
-
-TEST(ConvertTest, Nint) {
- unique_ptr<Item> item = details::makeItem(-10);
-
- EXPECT_EQ(NINT, item->type());
- EXPECT_NE(nullptr, item->asInt());
- EXPECT_EQ(nullptr, item->asUint());
- EXPECT_NE(nullptr, item->asNint());
- EXPECT_EQ(nullptr, item->asTstr());
- EXPECT_EQ(nullptr, item->asBstr());
- EXPECT_EQ(nullptr, item->asSimple());
- EXPECT_EQ(nullptr, item->asMap());
- EXPECT_EQ(nullptr, item->asArray());
-
- EXPECT_EQ(-10, item->asInt()->value());
- EXPECT_EQ(-10, item->asNint()->value());
-}
-
-TEST(ConvertTest, Tstr) {
- unique_ptr<Item> item = details::makeItem("hello");
-
- EXPECT_EQ(TSTR, item->type());
- EXPECT_EQ(nullptr, item->asInt());
- EXPECT_EQ(nullptr, item->asUint());
- EXPECT_EQ(nullptr, item->asNint());
- EXPECT_NE(nullptr, item->asTstr());
- EXPECT_EQ(nullptr, item->asBstr());
- EXPECT_EQ(nullptr, item->asSimple());
- EXPECT_EQ(nullptr, item->asMap());
- EXPECT_EQ(nullptr, item->asArray());
-
- EXPECT_EQ("hello"s, item->asTstr()->value());
-}
-
-TEST(ConvertTest, Bstr) {
- vector<uint8_t> vec{0x23, 0x24, 0x22};
- unique_ptr<Item> item = details::makeItem(vec);
-
- EXPECT_EQ(BSTR, item->type());
- EXPECT_EQ(nullptr, item->asInt());
- EXPECT_EQ(nullptr, item->asUint());
- EXPECT_EQ(nullptr, item->asNint());
- EXPECT_EQ(nullptr, item->asTstr());
- EXPECT_NE(nullptr, item->asBstr());
- EXPECT_EQ(nullptr, item->asSimple());
- EXPECT_EQ(nullptr, item->asMap());
- EXPECT_EQ(nullptr, item->asArray());
-
- EXPECT_EQ(vec, item->asBstr()->value());
-}
-
-TEST(ConvertTest, Bool) {
- unique_ptr<Item> item = details::makeItem(false);
-
- EXPECT_EQ(SIMPLE, item->type());
- EXPECT_EQ(nullptr, item->asInt());
- EXPECT_EQ(nullptr, item->asUint());
- EXPECT_EQ(nullptr, item->asNint());
- EXPECT_EQ(nullptr, item->asTstr());
- EXPECT_EQ(nullptr, item->asBstr());
- EXPECT_NE(nullptr, item->asSimple());
- EXPECT_EQ(nullptr, item->asMap());
- EXPECT_EQ(nullptr, item->asArray());
-
- EXPECT_EQ(BOOLEAN, item->asSimple()->simpleType());
- EXPECT_NE(nullptr, item->asSimple()->asBool());
-
- EXPECT_FALSE(item->asSimple()->asBool()->value());
-}
-
-TEST(ConvertTest, Map) {
- unique_ptr<Item> item(new Map);
-
- EXPECT_EQ(MAP, item->type());
- EXPECT_EQ(nullptr, item->asInt());
- EXPECT_EQ(nullptr, item->asUint());
- EXPECT_EQ(nullptr, item->asNint());
- EXPECT_EQ(nullptr, item->asTstr());
- EXPECT_EQ(nullptr, item->asBstr());
- EXPECT_EQ(nullptr, item->asSimple());
- EXPECT_NE(nullptr, item->asMap());
- EXPECT_EQ(nullptr, item->asArray());
-
- EXPECT_EQ(0U, item->asMap()->size());
-}
-
-TEST(ConvertTest, Array) {
- unique_ptr<Item> item(new Array);
-
- EXPECT_EQ(ARRAY, item->type());
- EXPECT_EQ(nullptr, item->asInt());
- EXPECT_EQ(nullptr, item->asUint());
- EXPECT_EQ(nullptr, item->asNint());
- EXPECT_EQ(nullptr, item->asTstr());
- EXPECT_EQ(nullptr, item->asBstr());
- EXPECT_EQ(nullptr, item->asSimple());
- EXPECT_EQ(nullptr, item->asMap());
- EXPECT_NE(nullptr, item->asArray());
-
- EXPECT_EQ(0U, item->asArray()->size());
-}
-
-class MockParseClient : public ParseClient {
- public:
- MOCK_METHOD4(item, ParseClient*(std::unique_ptr<Item>& item, const uint8_t* hdrBegin,
- const uint8_t* valueBegin, const uint8_t* end));
- MOCK_METHOD4(itemEnd, ParseClient*(std::unique_ptr<Item>& item, const uint8_t* hdrBegin,
- const uint8_t* valueBegin, const uint8_t* end));
- MOCK_METHOD2(error, void(const uint8_t* position, const std::string& errorMessage));
-};
-
-MATCHER_P(IsType, value, std::string("Type ") + (negation ? "doesn't match" : "matches")) {
- return arg->type() == value;
-}
-
-MATCHER_P(MatchesItem, value, "") {
- return arg && *arg == value;
-}
-
-MATCHER_P(IsArrayOfSize, value, "") {
- return arg->type() == ARRAY && arg->asArray()->size() == value;
-}
-
-MATCHER_P(IsMapOfSize, value, "") {
- return arg->type() == MAP && arg->asMap()->size() == value;
-}
-
-TEST(StreamParseTest, Uint) {
- MockParseClient mpc;
-
- Uint val(100);
- auto encoded = val.encode();
- uint8_t* encBegin = encoded.data();
- uint8_t* encEnd = encoded.data() + encoded.size();
-
- EXPECT_CALL(mpc, item(MatchesItem(val), encBegin, encEnd, encEnd)).WillOnce(Return(&mpc));
- EXPECT_CALL(mpc, itemEnd(_, _, _, _)).Times(0);
- EXPECT_CALL(mpc, error(_, _)).Times(0);
-
- parse(encoded.data(), encoded.data() + encoded.size(), &mpc);
-}
-
-TEST(StreamParseTest, Nint) {
- MockParseClient mpc;
-
- Nint val(-10);
- auto encoded = val.encode();
- uint8_t* encBegin = encoded.data();
- uint8_t* encEnd = encoded.data() + encoded.size();
-
- EXPECT_CALL(mpc, item(MatchesItem(val), encBegin, encEnd, encEnd)).WillOnce(Return(&mpc));
-
- EXPECT_CALL(mpc, itemEnd(_, _, _, _)).Times(0);
- EXPECT_CALL(mpc, error(_, _)).Times(0);
-
- parse(encoded.data(), encoded.data() + encoded.size(), &mpc);
-}
-
-TEST(StreamParseTest, Bool) {
- MockParseClient mpc;
-
- Bool val(true);
- auto encoded = val.encode();
- uint8_t* encBegin = encoded.data();
- uint8_t* encEnd = encoded.data() + encoded.size();
-
- EXPECT_CALL(mpc, item(MatchesItem(val), encBegin, encEnd, encEnd)).WillOnce(Return(&mpc));
- EXPECT_CALL(mpc, itemEnd(_, _, _, _)).Times(0);
- EXPECT_CALL(mpc, error(_, _)).Times(0);
-
- parse(encoded.data(), encoded.data() + encoded.size(), &mpc);
-}
-
-TEST(StreamParseTest, Tstr) {
- MockParseClient mpc;
-
- Tstr val("Hello");
- auto encoded = val.encode();
- uint8_t* encBegin = encoded.data();
- uint8_t* encEnd = encoded.data() + encoded.size();
-
- EXPECT_CALL(mpc, item(MatchesItem(val), encBegin, encBegin + 1, encEnd)).WillOnce(Return(&mpc));
- EXPECT_CALL(mpc, itemEnd(_, _, _, _)).Times(0);
- EXPECT_CALL(mpc, error(_, _)).Times(0);
-
- parse(encoded.data(), encoded.data() + encoded.size(), &mpc);
-}
-
-TEST(StreamParseTest, Bstr) {
- MockParseClient mpc;
-
- Bstr val("Hello");
- auto encoded = val.encode();
- uint8_t* encBegin = encoded.data();
- uint8_t* encEnd = encoded.data() + encoded.size();
-
- EXPECT_CALL(mpc, item(MatchesItem(val), encBegin, encBegin + 1, encEnd)).WillOnce(Return(&mpc));
- EXPECT_CALL(mpc, itemEnd(_, _, _, _)).Times(0);
- EXPECT_CALL(mpc, error(_, _)).Times(0);
-
- parse(encoded.data(), encoded.data() + encoded.size(), &mpc);
-}
-
-TEST(StreamParseTest, Array) {
- MockParseClient mpc;
-
- Array val("Hello", 4, Array(-9, "Goodbye"), std::numeric_limits<uint64_t>::max());
- ASSERT_NE(val[2]->asArray(), nullptr);
- const Array& interior = *(val[2]->asArray());
- auto encoded = val.encode();
- uint8_t* encBegin = encoded.data();
- uint8_t* encEnd = encoded.data() + encoded.size();
-
- {
- InSequence s;
- const uint8_t* pos = encBegin;
- EXPECT_CALL(mpc, item(IsArrayOfSize(val.size()), pos, pos + 1, pos + 1))
- .WillOnce(Return(&mpc));
- ++pos;
- EXPECT_CALL(mpc, item(MatchesItem(ByRef(*val[0])), pos, pos + 1, pos + 6))
- .WillOnce(Return(&mpc));
- pos += 6;
- EXPECT_CALL(mpc, item(MatchesItem(ByRef(*val[1])), pos, pos + 1, pos + 1))
- .WillOnce(Return(&mpc));
- ++pos;
- const uint8_t* innerArrayBegin = pos;
- EXPECT_CALL(mpc, item(IsArrayOfSize(interior.size()), pos, pos + 1, pos + 1))
- .WillOnce(Return(&mpc));
- ++pos;
- EXPECT_CALL(mpc, item(MatchesItem(ByRef(*interior[0])), pos, pos + 1, pos + 1))
- .WillOnce(Return(&mpc));
- ++pos;
- EXPECT_CALL(mpc, item(MatchesItem(ByRef(*interior[1])), pos, pos + 1, pos + 8))
- .WillOnce(Return(&mpc));
- pos += 8;
- EXPECT_CALL(mpc, itemEnd(IsArrayOfSize(interior.size()), innerArrayBegin,
- innerArrayBegin + 1, pos))
- .WillOnce(Return(&mpc));
- EXPECT_CALL(mpc, item(MatchesItem(ByRef(*val[3])), pos, pos + 9, pos + 9))
- .WillOnce(Return(&mpc));
- EXPECT_CALL(mpc, itemEnd(IsArrayOfSize(val.size()), encBegin, encBegin + 1, encEnd))
- .WillOnce(Return(&mpc));
- }
-
- EXPECT_CALL(mpc, error(_, _)) //
- .Times(0);
-
- parse(encoded.data(), encoded.data() + encoded.size(), &mpc);
-}
-
-TEST(StreamParseTest, Map) {
- MockParseClient mpc;
-
- Map val("Hello", 4, Array(-9, "Goodbye"), std::numeric_limits<uint64_t>::max());
- ASSERT_NE(val[1].first->asArray(), nullptr);
- const Array& interior = *(val[1].first->asArray());
- auto encoded = val.encode();
- uint8_t* encBegin = encoded.data();
- uint8_t* encEnd = encoded.data() + encoded.size();
-
- {
- InSequence s;
- const uint8_t* pos = encBegin;
- EXPECT_CALL(mpc, item(_, pos, pos + 1, pos + 1)).WillOnce(Return(&mpc));
- ++pos;
- EXPECT_CALL(mpc, item(MatchesItem(ByRef(*val[0].first)), pos, pos + 1, pos + 6))
- .WillOnce(Return(&mpc));
- pos += 6;
- EXPECT_CALL(mpc, item(MatchesItem(ByRef(*val[0].second)), pos, pos + 1, pos + 1))
- .WillOnce(Return(&mpc));
- ++pos;
- const uint8_t* innerArrayBegin = pos;
- EXPECT_CALL(mpc, item(IsArrayOfSize(interior.size()), pos, pos + 1, pos + 1))
- .WillOnce(Return(&mpc));
- ++pos;
- EXPECT_CALL(mpc, item(MatchesItem(ByRef(*interior[0])), pos, pos + 1, pos + 1))
- .WillOnce(Return(&mpc));
- ++pos;
- EXPECT_CALL(mpc, item(MatchesItem(ByRef(*interior[1])), pos, pos + 1, pos + 8))
- .WillOnce(Return(&mpc));
- pos += 8;
- EXPECT_CALL(mpc, itemEnd(IsArrayOfSize(interior.size()), innerArrayBegin,
- innerArrayBegin + 1, pos))
- .WillOnce(Return(&mpc));
- EXPECT_CALL(mpc, item(MatchesItem(ByRef(*val[1].second)), pos, pos + 9, pos + 9))
- .WillOnce(Return(&mpc));
- EXPECT_CALL(mpc, itemEnd(IsMapOfSize(val.size()), encBegin, encBegin + 1, encEnd))
- .WillOnce(Return(&mpc));
- }
-
- EXPECT_CALL(mpc, error(_, _)) //
- .Times(0);
-
- parse(encoded.data(), encoded.data() + encoded.size(), &mpc);
-}
-
-TEST(StreamParseTest, Semantic) {
- MockParseClient mpc;
-
- vector<uint8_t> encoded;
- auto iter = back_inserter(encoded);
- encodeHeader(SEMANTIC, 0, iter);
- Uint(999).encode(iter);
-
- EXPECT_CALL(mpc, item(_, _, _, _)).Times(0);
- EXPECT_CALL(mpc, itemEnd(_, _, _, _)).Times(0);
- EXPECT_CALL(mpc, error(encoded.data(), "Semantic tags not supported"));
-
- parse(encoded.data(), encoded.data() + encoded.size(), &mpc);
-}
-
-TEST(FullParserTest, Uint) {
- Uint val(10);
-
- auto [item, pos, message] = parse(val.encode());
- EXPECT_THAT(item, MatchesItem(val));
-}
-
-TEST(FullParserTest, Nint) {
- Nint val(-10);
-
- auto [item, pos, message] = parse(val.encode());
- EXPECT_THAT(item, MatchesItem(val));
-
- vector<uint8_t> minNint = {0x3B, 0x7F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF};
-
- std::tie(item, pos, message) = parse(minNint);
- EXPECT_THAT(item, NotNull());
- EXPECT_EQ(item->asNint()->value(), std::numeric_limits<int64_t>::min());
-}
-
-TEST(FullParserTest, NintOutOfRange) {
- vector<uint8_t> outOfRangeNint = {0x3B, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF};
-
- auto [item, pos, message] = parse(outOfRangeNint);
- EXPECT_THAT(item, IsNull());
- EXPECT_EQ(pos, outOfRangeNint.data());
- EXPECT_EQ(message, "NINT values that don't fit in int64_t are not supported.");
-}
-
-TEST(FullParserTest, Tstr) {
- Tstr val("Hello");
-
- auto [item, pos, message] = parse(val.encode());
- EXPECT_THAT(item, MatchesItem(val));
-}
-
-TEST(FullParserTest, Bstr) {
- Bstr val("\x00\x01\0x02"s);
-
- auto [item, pos, message] = parse(val.encode());
- EXPECT_THAT(item, MatchesItem(val));
-}
-
-TEST(FullParserTest, Array) {
- Array val("hello", -4, 3);
-
- auto encoded = val.encode();
- auto [item, pos, message] = parse(encoded);
- EXPECT_THAT(item, MatchesItem(ByRef(val)));
- EXPECT_EQ(pos, encoded.data() + encoded.size());
- EXPECT_EQ("", message);
-
- // We've already checked it all, but walk it just for fun.
- ASSERT_NE(nullptr, item->asArray());
- const Array& arr = *(item->asArray());
- ASSERT_EQ(arr[0]->type(), TSTR);
- EXPECT_EQ(arr[0]->asTstr()->value(), "hello");
-}
-
-TEST(FullParserTest, Map) {
- Map val("hello", -4, 3, Bstr("hi"));
-
- auto [item, pos, message] = parse(val.encode());
- EXPECT_THAT(item, MatchesItem(ByRef(val)));
-}
-
-TEST(FullParserTest, Complex) {
- vector<uint8_t> vec = {0x01, 0x02, 0x08, 0x03};
- Map val("Outer1",
- Array(Map("Inner1", 99, //
- "Inner2", vec),
- "foo"),
- "Outer2", 10);
-
- std::unique_ptr<Item> item;
- const uint8_t* pos;
- std::string message;
- std::tie(item, pos, message) = parse(val.encode());
- EXPECT_THAT(item, MatchesItem(ByRef(val)));
-}
-
-TEST(FullParserTest, IncompleteUint) {
- Uint val(1000);
-
- auto encoding = val.encode();
- auto [item, pos, message] = parse(encoding.data(), encoding.size() - 1);
- EXPECT_EQ(nullptr, item.get());
- EXPECT_EQ(encoding.data(), pos);
- EXPECT_EQ("Need 2 byte(s) for length field, have 1.", message);
-}
-
-TEST(FullParserTest, IncompleteString) {
- Tstr val("hello");
-
- auto encoding = val.encode();
- auto [item, pos, message] = parse(encoding.data(), encoding.size() - 2);
- EXPECT_EQ(nullptr, item.get());
- EXPECT_EQ(encoding.data(), pos);
- EXPECT_EQ("Need 5 byte(s) for text string, have 3.", message);
-}
-
-TEST(FullParserTest, ArrayWithInsufficientEntries) {
- Array val(1, 2, 3, 4);
-
- auto encoding = val.encode();
- auto [item, pos, message] = parse(encoding.data(), encoding.size() - 1);
- EXPECT_EQ(nullptr, item.get());
- EXPECT_EQ(encoding.data(), pos);
- EXPECT_EQ("Not enough entries for array.", message);
-}
-
-TEST(FullParserTest, ArrayWithTruncatedEntry) {
- Array val(1, 2, 3, 400000);
-
- auto encoding = val.encode();
- auto [item, pos, message] = parse(encoding.data(), encoding.size() - 1);
- EXPECT_EQ(nullptr, item.get());
- EXPECT_EQ(encoding.data() + encoding.size() - 5, pos);
- EXPECT_EQ("Need 4 byte(s) for length field, have 3.", message);
-}
-
-TEST(FullParserTest, MapWithTruncatedEntry) {
- Map val(1, 2, 300000, 4);
-
- auto encoding = val.encode();
- auto [item, pos, message] = parse(encoding.data(), encoding.size() - 2);
- EXPECT_EQ(nullptr, item.get());
- EXPECT_EQ(encoding.data() + 3, pos);
- EXPECT_EQ("Need 4 byte(s) for length field, have 3.", message);
-}
-int main(int argc, char** argv) {
- ::testing::InitGoogleTest(&argc, argv);
- return RUN_ALL_TESTS();
-}
diff --git a/security/rkp/aidl/vts/functional/VtsRemotelyProvisionedComponentTests.cpp b/security/rkp/aidl/vts/functional/VtsRemotelyProvisionedComponentTests.cpp
index cb1c692..aebcf67 100644
--- a/security/rkp/aidl/vts/functional/VtsRemotelyProvisionedComponentTests.cpp
+++ b/security/rkp/aidl/vts/functional/VtsRemotelyProvisionedComponentTests.cpp
@@ -783,4 +783,20 @@
INSTANTIATE_REM_PROV_AIDL_TEST(CertificateRequestV2Test);
+using VsrRequirementTest = VtsRemotelyProvisionedComponentTests;
+
+INSTANTIATE_REM_PROV_AIDL_TEST(VsrRequirementTest);
+
+TEST_P(VsrRequirementTest, VsrEnforcementTest) {
+ RpcHardwareInfo hwInfo;
+ ASSERT_TRUE(provisionable_->getHardwareInfo(&hwInfo).isOk());
+ int vsr_api_level = get_vsr_api_level();
+ if (vsr_api_level < 34) {
+ GTEST_SKIP() << "Applies only to VSR API level 34 or newer, this device is: "
+ << vsr_api_level;
+ }
+ EXPECT_GE(hwInfo.versionNumber, 3)
+ << "VSR 14+ requires IRemotelyProvisionedComponent v3 or newer.";
+}
+
} // namespace aidl::android::hardware::security::keymint::test
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/IWifiNanIface.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/IWifiNanIface.aidl
index 070ca24..3dff5bf 100644
--- a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/IWifiNanIface.aidl
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/IWifiNanIface.aidl
@@ -50,6 +50,10 @@
void stopSubscribeRequest(in char cmdId, in byte sessionId);
void terminateDataPathRequest(in char cmdId, in int ndpInstanceId);
void transmitFollowupRequest(in char cmdId, in android.hardware.wifi.NanTransmitFollowupRequest msg);
+ void initiatePairingRequest(in char cmdId, in android.hardware.wifi.NanPairingRequest msg);
+ void respondToPairingIndicationRequest(in char cmdId, in android.hardware.wifi.NanRespondToPairingIndicationRequest msg);
+ void initiateBootstrappingRequest(in char cmdId, in android.hardware.wifi.NanBootstrappingRequest msg);
+ void respondToBootstrappingIndicationRequest(in char cmdId, in android.hardware.wifi.NanBootstrappingResponse msg);
const int MIN_DATA_PATH_CONFIG_PASSPHRASE_LENGTH = 8;
const int MAX_DATA_PATH_CONFIG_PASSPHRASE_LENGTH = 63;
}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/IWifiNanIfaceEventCallback.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/IWifiNanIfaceEventCallback.aidl
index 591cd8c..b6c9d1f 100644
--- a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/IWifiNanIfaceEventCallback.aidl
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/IWifiNanIfaceEventCallback.aidl
@@ -60,4 +60,12 @@
oneway void notifyStopSubscribeResponse(in char id, in android.hardware.wifi.NanStatus status);
oneway void notifyTerminateDataPathResponse(in char id, in android.hardware.wifi.NanStatus status);
oneway void notifyTransmitFollowupResponse(in char id, in android.hardware.wifi.NanStatus status);
+ oneway void eventPairingRequest(in android.hardware.wifi.NanPairingRequestInd event);
+ oneway void eventPairingConfirm(in android.hardware.wifi.NanPairingConfirmInd event);
+ oneway void notifyInitiatePairingResponse(in char id, in android.hardware.wifi.NanStatus status, in int pairingInstanceId);
+ oneway void notifyRespondToPairingIndicationResponse(in char id, in android.hardware.wifi.NanStatus status);
+ oneway void eventBootstrappingRequest(in android.hardware.wifi.NanBootstrappingRequestInd event);
+ oneway void eventBootstrappingConfirm(in android.hardware.wifi.NanBootstrappingConfirmInd event);
+ oneway void notifyInitiateBootstrappingResponse(in char id, in android.hardware.wifi.NanStatus status, in int bootstrappingInstanceId);
+ oneway void notifyRespondToBootstrappingIndicationResponse(in char id, in android.hardware.wifi.NanStatus status);
}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingConfirmInd.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingConfirmInd.aidl
new file mode 100644
index 0000000..65e85af
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingConfirmInd.aidl
@@ -0,0 +1,40 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@VintfStability
+parcelable NanBootstrappingConfirmInd {
+ int bootstrappingInstanceId;
+ boolean acceptRequest;
+ android.hardware.wifi.NanStatus reasonCode;
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingMethod.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingMethod.aidl
new file mode 100644
index 0000000..e5f0975
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingMethod.aidl
@@ -0,0 +1,48 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@Backing(type="int") @VintfStability
+enum NanBootstrappingMethod {
+ BOOTSTRAPPING_OPPORTUNISTIC_MASK = 1,
+ BOOTSTRAPPING_PIN_CODE_DISPLAY_MASK = 2,
+ BOOTSTRAPPING_PASSPHRASE_DISPLAY_MASK = 4,
+ BOOTSTRAPPING_QR_DISPLAY_MASK = 8,
+ BOOTSTRAPPING_NFC_TAG_MASK = 16,
+ BOOTSTRAPPING_PIN_CODE_KEYPAD_MASK = 32,
+ BOOTSTRAPPING_PASSPHRASE_KEYPAD_MASK = 64,
+ BOOTSTRAPPING_QR_SCAN_MASK = 128,
+ BOOTSTRAPPING_NFC_READER_MASK = 256,
+ BOOTSTRAPPING_SERVICE_MANAGED_MASK = 16384,
+ BOOTSTRAPPING_HANDSHAKE_SHIP_MASK = 32768,
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingRequest.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingRequest.aidl
new file mode 100644
index 0000000..2be8924
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingRequest.aidl
@@ -0,0 +1,40 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@VintfStability
+parcelable NanBootstrappingRequest {
+ int peerId;
+ byte[6] peerDiscMacAddr;
+ android.hardware.wifi.NanBootstrappingMethod requestBootstrappingMethod;
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingRequestInd.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingRequestInd.aidl
new file mode 100644
index 0000000..a4398e9
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingRequestInd.aidl
@@ -0,0 +1,42 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@VintfStability
+parcelable NanBootstrappingRequestInd {
+ byte discoverySessionId;
+ int peerId;
+ byte[6] peerDiscMacAddr;
+ int bootstrappingInstanceId;
+ android.hardware.wifi.NanBootstrappingMethod requestBootstrappingMethod;
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingResponse.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingResponse.aidl
new file mode 100644
index 0000000..6dd9b26
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanBootstrappingResponse.aidl
@@ -0,0 +1,39 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@VintfStability
+parcelable NanBootstrappingResponse {
+ int bootstrappingInstanceId;
+ boolean acceptRequest;
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanCapabilities.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanCapabilities.aidl
index c44654e..5b59945 100644
--- a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanCapabilities.aidl
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanCapabilities.aidl
@@ -49,4 +49,7 @@
int maxSubscribeInterfaceAddresses;
android.hardware.wifi.NanCipherSuiteType supportedCipherSuites;
boolean instantCommunicationModeSupportFlag;
+ boolean supports6g;
+ boolean supportsHe;
+ boolean supportsPairing;
}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanIdentityResolutionAttribute.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanIdentityResolutionAttribute.aidl
new file mode 100644
index 0000000..843107e
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanIdentityResolutionAttribute.aidl
@@ -0,0 +1,39 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@VintfStability
+parcelable NanIdentityResolutionAttribute {
+ byte[8] nonce;
+ byte[8] tag;
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanMatchInd.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanMatchInd.aidl
index ae430c4..6757bec 100644
--- a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanMatchInd.aidl
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanMatchInd.aidl
@@ -49,4 +49,6 @@
int rangingMeasurementInMm;
android.hardware.wifi.NanRangingIndication rangingIndicationType;
byte[] scid;
+ android.hardware.wifi.NanPairingConfig peerPairingConfig;
+ android.hardware.wifi.NanIdentityResolutionAttribute peerNira;
}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingAkm.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingAkm.aidl
new file mode 100644
index 0000000..05bbaee
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingAkm.aidl
@@ -0,0 +1,39 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@Backing(type="int") @VintfStability
+enum NanPairingAkm {
+ SAE = 0,
+ PASN = 1,
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingConfig.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingConfig.aidl
new file mode 100644
index 0000000..1c04a96
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingConfig.aidl
@@ -0,0 +1,41 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@VintfStability
+parcelable NanPairingConfig {
+ boolean enablePairingSetup;
+ boolean enablePairingCache;
+ boolean enablePairingVerification;
+ int supportedBootstrappingMethods;
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingConfirmInd.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingConfirmInd.aidl
new file mode 100644
index 0000000..8ecf22a
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingConfirmInd.aidl
@@ -0,0 +1,43 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@VintfStability
+parcelable NanPairingConfirmInd {
+ int pairingInstanceId;
+ boolean pairingSuccess;
+ android.hardware.wifi.NanStatus status;
+ android.hardware.wifi.NanPairingRequestType requestType;
+ boolean enablePairingCache;
+ android.hardware.wifi.NpkSecurityAssociation npksa;
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingRequest.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingRequest.aidl
new file mode 100644
index 0000000..2a644ae
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingRequest.aidl
@@ -0,0 +1,43 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@VintfStability
+parcelable NanPairingRequest {
+ int peerId;
+ byte[6] peerDiscMacAddr;
+ android.hardware.wifi.NanPairingRequestType requestType;
+ boolean enablePairingCache;
+ byte[16] pairingIdentityKey;
+ android.hardware.wifi.NanPairingSecurityConfig securityConfig;
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingRequestInd.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingRequestInd.aidl
new file mode 100644
index 0000000..66762b9
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingRequestInd.aidl
@@ -0,0 +1,44 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@VintfStability
+parcelable NanPairingRequestInd {
+ byte discoverySessionId;
+ int peerId;
+ byte[6] peerDiscMacAddr;
+ int pairingInstanceId;
+ android.hardware.wifi.NanPairingRequestType requestType;
+ boolean enablePairingCache;
+ android.hardware.wifi.NanIdentityResolutionAttribute peerNira;
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingRequestType.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingRequestType.aidl
new file mode 100644
index 0000000..9e73e80
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingRequestType.aidl
@@ -0,0 +1,39 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@Backing(type="int") @VintfStability
+enum NanPairingRequestType {
+ NAN_PAIRING_SETUP = 0,
+ NAN_PAIRING_VERIFICATION = 1,
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingSecurityConfig.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingSecurityConfig.aidl
new file mode 100644
index 0000000..45af25d
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingSecurityConfig.aidl
@@ -0,0 +1,41 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@VintfStability
+parcelable NanPairingSecurityConfig {
+ android.hardware.wifi.NanPairingSecurityType securityType;
+ byte[32] pmk;
+ byte[] passphrase;
+ android.hardware.wifi.NanPairingAkm akm;
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingSecurityType.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingSecurityType.aidl
new file mode 100644
index 0000000..a08a00f
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPairingSecurityType.aidl
@@ -0,0 +1,40 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@Backing(type="int") @VintfStability
+enum NanPairingSecurityType {
+ OPPORTUNISTIC = 0,
+ PMK = 1,
+ PASSPHRASE = 2,
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPublishRequest.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPublishRequest.aidl
index d8d6b1b..c49f5f9 100644
--- a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPublishRequest.aidl
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanPublishRequest.aidl
@@ -38,4 +38,6 @@
android.hardware.wifi.NanPublishType publishType;
android.hardware.wifi.NanTxType txType;
boolean autoAcceptDataPathRequests;
+ android.hardware.wifi.NanPairingConfig pairingConfig;
+ byte[16] identityKey;
}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanRespondToPairingIndicationRequest.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanRespondToPairingIndicationRequest.aidl
new file mode 100644
index 0000000..a58890c
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanRespondToPairingIndicationRequest.aidl
@@ -0,0 +1,43 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@VintfStability
+parcelable NanRespondToPairingIndicationRequest {
+ boolean acceptRequest;
+ int pairingInstanceId;
+ android.hardware.wifi.NanPairingRequestType requestType;
+ boolean enablePairingCache;
+ byte[16] pairingIdentityKey;
+ android.hardware.wifi.NanPairingSecurityConfig securityConfig;
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanStatusCode.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanStatusCode.aidl
index 9eaf518..0fe2245 100644
--- a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanStatusCode.aidl
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanStatusCode.aidl
@@ -47,4 +47,6 @@
ALREADY_ENABLED = 10,
FOLLOWUP_TX_QUEUE_FULL = 11,
UNSUPPORTED_CONCURRENCY_NAN_DISABLED = 12,
+ INVALID_PAIRING_ID = 13,
+ INVALID_BOOTSTRAPPING_ID = 14,
}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanSubscribeRequest.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanSubscribeRequest.aidl
index bf176a5..96be096 100644
--- a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanSubscribeRequest.aidl
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NanSubscribeRequest.aidl
@@ -41,4 +41,6 @@
boolean shouldUseSrf;
boolean isSsiRequiredForMatch;
android.hardware.wifi.MacAddress[] intfAddr;
+ android.hardware.wifi.NanPairingConfig pairingConfig;
+ byte[16] identityKey;
}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NpkSecurityAssociation.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NpkSecurityAssociation.aidl
new file mode 100644
index 0000000..c558716
--- /dev/null
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/NpkSecurityAssociation.aidl
@@ -0,0 +1,41 @@
+/*
+ * 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.
+ */
+///////////////////////////////////////////////////////////////////////////////
+// THIS FILE IS IMMUTABLE. DO NOT EDIT IN ANY CASE. //
+///////////////////////////////////////////////////////////////////////////////
+
+// This file is a snapshot of an AIDL file. Do not edit it manually. There are
+// two cases:
+// 1). this is a frozen version file - do not edit this in any case.
+// 2). this is a 'current' file. If you make a backwards compatible change to
+// the interface (from the latest frozen version), the build system will
+// prompt you to update this file with `m <name>-update-api`.
+//
+// You must not make a backward incompatible change to any AIDL file built
+// with the aidl_interface module type with versions property set. The module
+// type is used to build AIDL files in a way that they can be used across
+// independently updatable components of the system. If a device is shipped
+// with such a backward incompatible change, it has a high risk of breaking
+// later when a module using the interface is updated, e.g., Mainline modules.
+
+package android.hardware.wifi;
+@VintfStability
+parcelable NpkSecurityAssociation {
+ byte[16] peerNanIdentityKey;
+ byte[16] localNanIdentityKey;
+ byte[32] npk;
+ android.hardware.wifi.NanPairingAkm akm;
+}
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/RttBw.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/RttBw.aidl
index bd7efff..f5bf894 100644
--- a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/RttBw.aidl
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/RttBw.aidl
@@ -34,6 +34,7 @@
package android.hardware.wifi;
@Backing(type="int") @VintfStability
enum RttBw {
+ BW_UNSPECIFIED = 0,
BW_5MHZ = 1,
BW_10MHZ = 2,
BW_20MHZ = 4,
diff --git a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/RttResult.aidl b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/RttResult.aidl
index 743e0bd..8375dcb 100644
--- a/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/RttResult.aidl
+++ b/wifi/aidl/aidl_api/android.hardware.wifi/current/android/hardware/wifi/RttResult.aidl
@@ -57,4 +57,6 @@
int negotiatedBurstNum;
android.hardware.wifi.WifiInformationElement lci;
android.hardware.wifi.WifiInformationElement lcr;
+ int channelFreqMHz;
+ android.hardware.wifi.RttBw packetBw;
}
diff --git a/wifi/aidl/android/hardware/wifi/IWifiNanIface.aidl b/wifi/aidl/android/hardware/wifi/IWifiNanIface.aidl
index 45644b4..31c7ece 100644
--- a/wifi/aidl/android/hardware/wifi/IWifiNanIface.aidl
+++ b/wifi/aidl/android/hardware/wifi/IWifiNanIface.aidl
@@ -17,12 +17,16 @@
package android.hardware.wifi;
import android.hardware.wifi.IWifiNanIfaceEventCallback;
+import android.hardware.wifi.NanBootstrappingRequest;
+import android.hardware.wifi.NanBootstrappingResponse;
import android.hardware.wifi.NanConfigRequest;
import android.hardware.wifi.NanConfigRequestSupplemental;
import android.hardware.wifi.NanEnableRequest;
import android.hardware.wifi.NanInitiateDataPathRequest;
+import android.hardware.wifi.NanPairingRequest;
import android.hardware.wifi.NanPublishRequest;
import android.hardware.wifi.NanRespondToDataPathIndicationRequest;
+import android.hardware.wifi.NanRespondToPairingIndicationRequest;
import android.hardware.wifi.NanSubscribeRequest;
import android.hardware.wifi.NanTransmitFollowupRequest;
@@ -248,4 +252,62 @@
* |WifiStatusCode.ERROR_UNKNOWN|
*/
void transmitFollowupRequest(in char cmdId, in NanTransmitFollowupRequest msg);
+
+ /**
+ * Initiate a NAN pairing operation: Initiator.
+ * Asynchronous response is with |IWifiNanIfaceEventCallback.notifyInitiatePairingResponse|.
+ *
+ * @param cmdId Command Id to use for this invocation.
+ * @param msg Instance of |NanPairingRequest|.
+ * @throws ServiceSpecificException with one of the following values:
+ * |WifiStatusCode.ERROR_WIFI_IFACE_INVALID|,
+ * |WifiStatusCode.ERROR_INVALID_ARGS|,
+ * |WifiStatusCode.ERROR_UNKNOWN|
+ */
+ void initiatePairingRequest(in char cmdId, in NanPairingRequest msg);
+
+ /**
+ * Respond to a received request indication of NAN pairing setup operation.
+ * An indication is received by the Responder from the Initiator.
+ * Asynchronous response is with
+ * |IWifiNanIfaceEventCallback.notifyRespondToPairingIndicationResponse|.
+ *
+ * @param cmdId Command Id to use for this invocation.
+ * @param msg Instance of |NanRespondToPairingIndicationRequest|.
+ * @throws ServiceSpecificException with one of the following values:
+ * |WifiStatusCode.ERROR_WIFI_IFACE_INVALID|,
+ * |WifiStatusCode.ERROR_INVALID_ARGS|,
+ * |WifiStatusCode.ERROR_UNKNOWN|
+ */
+ void respondToPairingIndicationRequest(
+ in char cmdId, in NanRespondToPairingIndicationRequest msg);
+
+ /**
+ * Initiate a NAN pairing bootstrapping operation: Initiator.
+ * Asynchronous response is with
+ * |IWifiNanIfaceEventCallback.notifyInitiateBootstrappingResponse|.
+ *
+ * @param cmdId Command Id to use for this invocation.
+ * @param msg Instance of |NanBootstrappingRequest|.
+ * @throws ServiceSpecificException with one of the following values:
+ * |WifiStatusCode.ERROR_WIFI_IFACE_INVALID|,
+ * |WifiStatusCode.ERROR_INVALID_ARGS|,
+ * |WifiStatusCode.ERROR_UNKNOWN|
+ */
+ void initiateBootstrappingRequest(in char cmdId, in NanBootstrappingRequest msg);
+
+ /**
+ * Respond to a received request indication of NAN pairing bootstrapping operation.
+ * An indication is received by the Responder from the Initiator.
+ * Asynchronous response is with
+ * |IWifiNanIfaceEventCallback.notifyRespondToPairingIndicationResponse|.
+ *
+ * @param cmdId Command Id to use for this invocation.
+ * @param msg Instance of |notifyRespondToBootstrappingIndicationResponse|.
+ * @throws ServiceSpecificException with one of the following values:
+ * |WifiStatusCode.ERROR_WIFI_IFACE_INVALID|,
+ * |WifiStatusCode.ERROR_INVALID_ARGS|,
+ * |WifiStatusCode.ERROR_UNKNOWN|
+ */
+ void respondToBootstrappingIndicationRequest(in char cmdId, in NanBootstrappingResponse msg);
}
diff --git a/wifi/aidl/android/hardware/wifi/IWifiNanIfaceEventCallback.aidl b/wifi/aidl/android/hardware/wifi/IWifiNanIfaceEventCallback.aidl
index 470b7ba..6b06def 100644
--- a/wifi/aidl/android/hardware/wifi/IWifiNanIfaceEventCallback.aidl
+++ b/wifi/aidl/android/hardware/wifi/IWifiNanIfaceEventCallback.aidl
@@ -16,6 +16,8 @@
package android.hardware.wifi;
+import android.hardware.wifi.NanBootstrappingConfirmInd;
+import android.hardware.wifi.NanBootstrappingRequestInd;
import android.hardware.wifi.NanCapabilities;
import android.hardware.wifi.NanClusterEventInd;
import android.hardware.wifi.NanDataPathConfirmInd;
@@ -23,6 +25,8 @@
import android.hardware.wifi.NanDataPathScheduleUpdateInd;
import android.hardware.wifi.NanFollowupReceivedInd;
import android.hardware.wifi.NanMatchInd;
+import android.hardware.wifi.NanPairingConfirmInd;
+import android.hardware.wifi.NanPairingRequestInd;
import android.hardware.wifi.NanStatus;
/**
@@ -319,4 +323,95 @@
* |NanStatusCode.FOLLOWUP_TX_QUEUE_FULL|
*/
void notifyTransmitFollowupResponse(in char id, in NanStatus status);
+
+ /**
+ * Callback indicating that a NAN pairing setup/verification has been requested by
+ * an Initiator peer (received by the intended Responder).
+ *
+ * @param event NanPairingRequestInd containing event details.
+ */
+ void eventPairingRequest(in NanPairingRequestInd event);
+
+ /**
+ * Callback indicating that a NAN pairing setup/verification has been completed.
+ * Received by both Initiator and Responder.
+ *
+ * @param event NanPairingConfirmInd containing event details.
+ */
+ void eventPairingConfirm(in NanPairingConfirmInd event);
+
+ /**
+ * Callback invoked in response to an initiate NAN pairing request
+ * |IWifiNanIface.initiatePairingRequest|.
+ *
+ * @param cmdId Command Id corresponding to the original request.
+ * @param status NanStatus of the operation. Possible status codes are:
+ * |NanStatusCode.SUCCESS|
+ * |NanStatusCode.INVALID_ARGS|
+ * |NanStatusCode.INTERNAL_FAILURE|
+ * |NanStatusCode.PROTOCOL_FAILURE|
+ * |NanStatusCode.INVALID_PEER_ID|
+ * @param pairingInstanceId ID of the new pairing being negotiated (on successful status).
+ */
+ void notifyInitiatePairingResponse(in char id, in NanStatus status, in int pairingInstanceId);
+
+ /**
+ * Callback invoked in response to a respond to NAN pairing indication request
+ * |IWifiNanIface.respondToPairingIndicationRequest|.
+ *
+ * @param cmdId Command Id corresponding to the original request.
+ * @param status NanStatus of the operation. Possible status codes are:
+ * |NanStatusCode.SUCCESS|
+ * |NanStatusCode.INVALID_ARGS|
+ * |NanStatusCode.INTERNAL_FAILURE|
+ * |NanStatusCode.PROTOCOL_FAILURE|
+ * |NanStatusCode.INVALID_NDP_ID|
+ */
+ void notifyRespondToPairingIndicationResponse(in char id, in NanStatus status);
+
+ /**
+ * Callback indicating that a NAN bootstrapping setup has been requested by
+ * an Initiator peer (received by the intended Responder).
+ *
+ * @param event NanBootstrappingRequestInd containing event details.
+ */
+ void eventBootstrappingRequest(in NanBootstrappingRequestInd event);
+
+ /**
+ * Callback indicating that a NAN bootstrapping setuphas been completed.
+ * Received by Initiator.
+ *
+ * @param event NanBootstrappingConfirmInd containing event details.
+ */
+ void eventBootstrappingConfirm(in NanBootstrappingConfirmInd event);
+
+ /**
+ * Callback invoked in response to an initiate NAN pairing bootstrapping request
+ * |IWifiNanIface.initiateBootstrappingRequest|.
+ *
+ * @param cmdId Command Id corresponding to the original request.
+ * @param status NanStatus of the operation. Possible status codes are:
+ * |NanStatusCode.SUCCESS|
+ * |NanStatusCode.INVALID_ARGS|
+ * |NanStatusCode.INTERNAL_FAILURE|
+ * |NanStatusCode.PROTOCOL_FAILURE|
+ * |NanStatusCode.INVALID_PEER_ID|
+ * @param bootstrappingInstanceId ID of the new pairing being negotiated (on successful status).
+ */
+ void notifyInitiateBootstrappingResponse(
+ in char id, in NanStatus status, in int bootstrappingInstanceId);
+
+ /**
+ * Callback invoked in response to a respond to pairing bootstrapping indication request
+ * |IWifiNanIface.respondToBootstrappingIndicationRequest|.
+ *
+ * @param cmdId Command Id corresponding to the original request.
+ * @param status NanStatus of the operation. Possible status codes are:
+ * |NanStatusCode.SUCCESS|
+ * |NanStatusCode.INVALID_ARGS|
+ * |NanStatusCode.INTERNAL_FAILURE|
+ * |NanStatusCode.PROTOCOL_FAILURE|
+ * |NanStatusCode.INVALID_NDP_ID|
+ */
+ void notifyRespondToBootstrappingIndicationResponse(in char id, in NanStatus status);
}
diff --git a/wifi/aidl/android/hardware/wifi/NanBootstrappingConfirmInd.aidl b/wifi/aidl/android/hardware/wifi/NanBootstrappingConfirmInd.aidl
new file mode 100644
index 0000000..5a539ee
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanBootstrappingConfirmInd.aidl
@@ -0,0 +1,39 @@
+/*
+ * 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.hardware.wifi;
+
+import android.hardware.wifi.NanBootstrappingMethod;
+import android.hardware.wifi.NanStatus;
+
+@VintfStability
+parcelable NanBootstrappingConfirmInd {
+ /**
+ * Id of the bootstrapping session. Obtained as part of earlier
+ |IWifiNanIface.initiateBootstrappingRequest| success notification.
+ */
+ int bootstrappingInstanceId;
+
+ /**
+ * Indicate whether the bootstrapping method negotiation accept or not
+ */
+ boolean acceptRequest;
+
+ /**
+ * Failure reason if |acceptRequest| is false.
+ */
+ NanStatus reasonCode;
+}
diff --git a/wifi/aidl/android/hardware/wifi/NanBootstrappingMethod.aidl b/wifi/aidl/android/hardware/wifi/NanBootstrappingMethod.aidl
new file mode 100644
index 0000000..8960794
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanBootstrappingMethod.aidl
@@ -0,0 +1,36 @@
+/*
+ * 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.hardware.wifi;
+
+/**
+ * Pairing bootstrapping method flag
+ */
+@VintfStability
+@Backing(type="int")
+enum NanBootstrappingMethod {
+ BOOTSTRAPPING_OPPORTUNISTIC_MASK = 1 << 0,
+ BOOTSTRAPPING_PIN_CODE_DISPLAY_MASK = 1 << 1,
+ BOOTSTRAPPING_PASSPHRASE_DISPLAY_MASK = 1 << 2,
+ BOOTSTRAPPING_QR_DISPLAY_MASK = 1 << 3,
+ BOOTSTRAPPING_NFC_TAG_MASK = 1 << 4,
+ BOOTSTRAPPING_PIN_CODE_KEYPAD_MASK = 1 << 5,
+ BOOTSTRAPPING_PASSPHRASE_KEYPAD_MASK = 1 << 6,
+ BOOTSTRAPPING_QR_SCAN_MASK = 1 << 7,
+ BOOTSTRAPPING_NFC_READER_MASK = 1 << 8,
+ BOOTSTRAPPING_SERVICE_MANAGED_MASK = 1 << 14,
+ BOOTSTRAPPING_HANDSHAKE_SHIP_MASK = 1 << 15
+}
diff --git a/wifi/aidl/android/hardware/wifi/NanBootstrappingRequest.aidl b/wifi/aidl/android/hardware/wifi/NanBootstrappingRequest.aidl
new file mode 100644
index 0000000..d553245
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanBootstrappingRequest.aidl
@@ -0,0 +1,40 @@
+/*
+ * 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.hardware.wifi;
+
+import android.hardware.wifi.NanBootstrappingMethod;
+
+@VintfStability
+parcelable NanBootstrappingRequest {
+ /**
+ * ID of the peer. Obtained as part of an earlier |IWifiNanIfaceEventCallback.eventMatch| or
+ * |IWifiNanIfaceEventCallback.eventFollowupReceived|.
+ */
+ int peerId;
+
+ /**
+ * NAN management interface MAC address of the peer. Obtained as part of an earlier
+ * |IWifiNanIfaceEventCallback.eventMatch| or
+ * |IWifiNanIfaceEventCallback.eventFollowupReceived|.
+ */
+ byte[6] peerDiscMacAddr;
+
+ /**
+ * Bootstrapping method in the request, one of the |NanBootstrappingMethod|
+ */
+ NanBootstrappingMethod requestBootstrappingMethod;
+}
diff --git a/wifi/aidl/android/hardware/wifi/NanBootstrappingRequestInd.aidl b/wifi/aidl/android/hardware/wifi/NanBootstrappingRequestInd.aidl
new file mode 100644
index 0000000..e11122f
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanBootstrappingRequestInd.aidl
@@ -0,0 +1,54 @@
+/*
+ * 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.hardware.wifi;
+
+import android.hardware.wifi.NanBootstrappingMethod;
+
+/**
+ * NAN Data path request indication message structure.
+ * Event indication received by an intended Responder when a NAN
+ * data request initiated by an Initiator.
+ */
+@VintfStability
+parcelable NanBootstrappingRequestInd {
+ /**
+ * Discovery session (publish or subscribe) ID of a previously created discovery session. The
+ * bootstrapping request is received in the context of this discovery session.
+ * NAN Spec: Service Descriptor Attribute (SDA) / Instance ID
+ */
+ byte discoverySessionId;
+ /**
+ * A unique ID of the peer. Can be subsequently used in |IWifiNanIface.transmitFollowupRequest|
+ * or to set up a data-path.
+ */
+ int peerId;
+ /**
+ * MAC address of the Initiator peer. This is the MAC address of the peer's
+ * management/discovery NAN interface.
+ */
+ byte[6] peerDiscMacAddr;
+
+ /**
+ * ID of bootstrapping session. Used to identify the bootstrapping further negotiation/APIs.
+ */
+ int bootstrappingInstanceId;
+
+ /**
+ * Bootstrapping method in the incoming request, one of the |NanBootstrappingMethod|
+ */
+ NanBootstrappingMethod requestBootstrappingMethod;
+}
diff --git a/wifi/aidl/android/hardware/wifi/NanBootstrappingResponse.aidl b/wifi/aidl/android/hardware/wifi/NanBootstrappingResponse.aidl
new file mode 100644
index 0000000..0a7d621
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanBootstrappingResponse.aidl
@@ -0,0 +1,31 @@
+/*
+ * 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.hardware.wifi;
+
+import android.hardware.wifi.NanBootstrappingMethod;
+
+@VintfStability
+parcelable NanBootstrappingResponse {
+ /**
+ * ID of bootstrapping session. Used to identify the bootstrapping further negotiation/APIs.
+ */
+ int bootstrappingInstanceId;
+ /**
+ * True if accept the request, false otherwise.
+ */
+ boolean acceptRequest;
+}
diff --git a/wifi/aidl/android/hardware/wifi/NanCapabilities.aidl b/wifi/aidl/android/hardware/wifi/NanCapabilities.aidl
index 6042a05..0955b4c 100644
--- a/wifi/aidl/android/hardware/wifi/NanCapabilities.aidl
+++ b/wifi/aidl/android/hardware/wifi/NanCapabilities.aidl
@@ -82,7 +82,19 @@
*/
NanCipherSuiteType supportedCipherSuites;
/**
- * Flag to indicate id instant communication mode is supported.
+ * Flag to indicate if instant communication mode is supported.
*/
boolean instantCommunicationModeSupportFlag;
+ /**
+ * Flag to indicate if 6 GHz is supported.
+ */
+ boolean supports6g;
+ /**
+ * Flag to indicate if High Efficiency is supported.
+ */
+ boolean supportsHe;
+ /**
+ * Flag to indicate if NAN pairing is supported.
+ */
+ boolean supportsPairing;
}
diff --git a/wifi/aidl/android/hardware/wifi/NanIdentityResolutionAttribute.aidl b/wifi/aidl/android/hardware/wifi/NanIdentityResolutionAttribute.aidl
new file mode 100644
index 0000000..917feff
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanIdentityResolutionAttribute.aidl
@@ -0,0 +1,33 @@
+/*
+ * 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.hardware.wifi;
+
+/**
+ * NIRA for pairing identity resolution
+ */
+@VintfStability
+parcelable NanIdentityResolutionAttribute {
+ /**
+ * A random byte string to generate tag
+ */
+ byte[8] nonce;
+
+ /**
+ * A resolvable identity to identify Nan identity key
+ */
+ byte[8] tag;
+}
diff --git a/wifi/aidl/android/hardware/wifi/NanMatchInd.aidl b/wifi/aidl/android/hardware/wifi/NanMatchInd.aidl
index 896cde0..be2fa31 100644
--- a/wifi/aidl/android/hardware/wifi/NanMatchInd.aidl
+++ b/wifi/aidl/android/hardware/wifi/NanMatchInd.aidl
@@ -17,6 +17,8 @@
package android.hardware.wifi;
import android.hardware.wifi.NanCipherSuiteType;
+import android.hardware.wifi.NanIdentityResolutionAttribute;
+import android.hardware.wifi.NanPairingConfig;
import android.hardware.wifi.NanRangingIndication;
/**
@@ -126,4 +128,12 @@
* setting up the Secure Data Path.
*/
byte[] scid;
+ /**
+ * The config for NAN pairing set by the peer
+ */
+ NanPairingConfig peerPairingConfig;
+ /**
+ * The NIRA from peer for NAN pairing verification
+ */
+ NanIdentityResolutionAttribute peerNira;
}
diff --git a/wifi/aidl/android/hardware/wifi/NanPairingAkm.aidl b/wifi/aidl/android/hardware/wifi/NanPairingAkm.aidl
new file mode 100644
index 0000000..31eeb2b
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanPairingAkm.aidl
@@ -0,0 +1,22 @@
+/*
+ * 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.hardware.wifi;
+
+/**
+ * THe AKM used of NAN pairing
+ */
+@VintfStability @Backing(type="int") enum NanPairingAkm { SAE = 0, PASN=1 }
diff --git a/wifi/aidl/android/hardware/wifi/NanPairingConfig.aidl b/wifi/aidl/android/hardware/wifi/NanPairingConfig.aidl
new file mode 100644
index 0000000..4f9c3ae
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanPairingConfig.aidl
@@ -0,0 +1,42 @@
+/*
+ * 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.hardware.wifi;
+
+import android.hardware.wifi.NanBootstrappingMethod;
+
+/**
+ * The NAN pairing config
+ */
+@VintfStability
+parcelable NanPairingConfig {
+ /**
+ * Enable NAN pairing setup
+ */
+ boolean enablePairingSetup;
+ /**
+ * Enable cache NIK/NPK after NAN pairing setup
+ */
+ boolean enablePairingCache;
+ /**
+ * Enable NAN pairing verification with cached NIK/NPK
+ */
+ boolean enablePairingVerification;
+ /**
+ * The set of supported bootstrapping methods. The |NanBootstrappingMethod| bit fields are used.
+ */
+ int supportedBootstrappingMethods;
+}
diff --git a/wifi/aidl/android/hardware/wifi/NanPairingConfirmInd.aidl b/wifi/aidl/android/hardware/wifi/NanPairingConfirmInd.aidl
new file mode 100644
index 0000000..cd98c72
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanPairingConfirmInd.aidl
@@ -0,0 +1,55 @@
+/*
+ * 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.hardware.wifi;
+
+import android.hardware.wifi.NanDataPathChannelInfo;
+import android.hardware.wifi.NanPairingRequestType;
+import android.hardware.wifi.NanStatus;
+import android.hardware.wifi.NpkSecurityAssociation;
+
+/**
+ * NAN pairing confirmation indication structure. Event indication is
+ * received on both initiator and responder side when negotiation for a
+ * pairing finishes on success or failure.
+ */
+@VintfStability
+parcelable NanPairingConfirmInd {
+ /**
+ * ID of the pairing session.
+ */
+ int pairingInstanceId;
+ /**
+ * Indicates whether the pairing setup succeeded (true) or failed (false).
+ */
+ boolean pairingSuccess;
+ /**
+ * Failure reason if |pairingSuccess| is false.
+ */
+ NanStatus status;
+ /**
+ * Indicate the pairing session is of setup or verification
+ */
+ NanPairingRequestType requestType;
+ /**
+ * Whether should cache the negotiated NIK/NPK for future verification
+ */
+ boolean enablePairingCache;
+ /**
+ * The security association negotiated for the pairing, can be cached for future verification
+ */
+ NpkSecurityAssociation npksa;
+}
diff --git a/wifi/aidl/android/hardware/wifi/NanPairingRequest.aidl b/wifi/aidl/android/hardware/wifi/NanPairingRequest.aidl
new file mode 100644
index 0000000..6f1a072
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanPairingRequest.aidl
@@ -0,0 +1,56 @@
+/*
+ * 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.hardware.wifi;
+
+import android.hardware.wifi.NanPairingRequestType;
+import android.hardware.wifi.NanPairingSecurityConfig;
+
+/**
+ * NAN pairing initiate request
+ * Which can be used for setup(the initial pairing request) or
+ * verification(re-pairing for paired devices)
+ */
+@VintfStability
+parcelable NanPairingRequest {
+ /**
+ * ID of the peer. Obtained as part of an earlier |IWifiNanIfaceEventCallback.eventMatch| or
+ * |IWifiNanIfaceEventCallback.eventFollowupReceived|.
+ */
+ int peerId;
+ /**
+ * NAN management interface MAC address of the peer. Obtained as part of an earlier
+ * |IWifiNanIfaceEventCallback.eventMatch| or
+ * |IWifiNanIfaceEventCallback.eventFollowupReceived|.
+ */
+ byte[6] peerDiscMacAddr;
+ /**
+ * Indicate the pairing session is for setup or verification
+ */
+ NanPairingRequestType requestType;
+ /**
+ * Whether to cache the negotiated NIK/NPK for future verification
+ */
+ boolean enablePairingCache;
+ /**
+ * The Identity key for pairing, can be used for pairing verification
+ */
+ byte[16] pairingIdentityKey;
+ /**
+ * Security config used for the pairing
+ */
+ NanPairingSecurityConfig securityConfig;
+}
diff --git a/wifi/aidl/android/hardware/wifi/NanPairingRequestInd.aidl b/wifi/aidl/android/hardware/wifi/NanPairingRequestInd.aidl
new file mode 100644
index 0000000..f247e45
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanPairingRequestInd.aidl
@@ -0,0 +1,61 @@
+/*
+ * 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.hardware.wifi;
+
+import android.hardware.wifi.NanIdentityResolutionAttribute;
+import android.hardware.wifi.NanPairingRequestType;
+
+/**
+ * NAN pairing request indication message structure.
+ * Event indication received by an intended Responder when a
+ * pairing request initiated by an Initiator.
+ */
+@VintfStability
+parcelable NanPairingRequestInd {
+ /**
+ * Discovery session (publish or subscribe) ID of a previously created discovery session. The
+ * pairing request is received in the context of this discovery session.
+ * NAN Spec: Service Descriptor Attribute (SDA) / Instance ID
+ */
+ byte discoverySessionId;
+ /**
+ * A unique ID of the peer. Can be subsequently used in |IWifiNanIface.transmitFollowupRequest|
+ * or to set up a data-path.
+ */
+ int peerId;
+ /**
+ * MAC address of the Initiator peer. This is the MAC address of the peer's
+ * management/discovery NAN interface.
+ */
+ byte[6] peerDiscMacAddr;
+ /**
+ * ID of the NAN pairing Used to identify the pairing in further negotiation/APIs.
+ */
+ int pairingInstanceId;
+ /**
+ * Indicate the pairing session is of setup or verification
+ */
+ NanPairingRequestType requestType;
+ /**
+ * Whether should cache the negotiated NIK/NPK for future verification
+ */
+ boolean enablePairingCache;
+ /**
+ * The NIRA from peer for NAN pairing verification
+ */
+ NanIdentityResolutionAttribute peerNira;
+}
diff --git a/wifi/aidl/android/hardware/wifi/NanPairingRequestType.aidl b/wifi/aidl/android/hardware/wifi/NanPairingRequestType.aidl
new file mode 100644
index 0000000..a69d04e
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanPairingRequestType.aidl
@@ -0,0 +1,27 @@
+/*
+ * 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.hardware.wifi;
+
+/**
+ * Type of the request of pairing
+ */
+@VintfStability
+@Backing(type="int")
+enum NanPairingRequestType {
+ NAN_PAIRING_SETUP = 0,
+ NAN_PAIRING_VERIFICATION
+}
diff --git a/wifi/aidl/android/hardware/wifi/NanPairingSecurityConfig.aidl b/wifi/aidl/android/hardware/wifi/NanPairingSecurityConfig.aidl
new file mode 100644
index 0000000..273c07e
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanPairingSecurityConfig.aidl
@@ -0,0 +1,50 @@
+/*
+ * 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.hardware.wifi;
+
+import android.hardware.wifi.NanPairingAkm;
+import android.hardware.wifi.NanPairingSecurityType;
+
+/**
+ * Configuration of NAN data-path security.
+ */
+@VintfStability
+parcelable NanPairingSecurityConfig {
+ /**
+ * Security configuration of the NAN pairing. |NanPairingSecurityType.PMK| for verification.
+ * |NanPairingSecurityType.PASSPHRASE| and |NanPairingSecurityType.OPPORTUNISTIC| for setup
+ */
+ NanPairingSecurityType securityType;
+ /**
+ * Optional Pairwise Master Key (PMK). Must be specified (and is only used) if |securityType| is
+ * set to |NanDataPathSecurityType.PMK|.
+ * Ref: IEEE 802.11i
+ */
+ byte[32] pmk;
+ /**
+ * Optional Passphrase. Must be specified (and is only used) if |securityType| is set to
+ * |NanDataPathSecurityType.PASSPHRASE|.
+ * Min length: |IWifiNanIface.MIN_DATA_PATH_CONFIG_PASSPHRASE_LENGTH|
+ * Max length: |IWifiNanIface.MAX_DATA_PATH_CONFIG_PASSPHRASE_LENGTH|
+ * NAN Spec: Appendix: Mapping passphrase to PMK for NCS-SK Cipher Suites
+ */
+ byte[] passphrase;
+ /**
+ * The AKM for key exchange
+ */
+ NanPairingAkm akm;
+}
diff --git a/wifi/aidl/android/hardware/wifi/NanPairingSecurityType.aidl b/wifi/aidl/android/hardware/wifi/NanPairingSecurityType.aidl
new file mode 100644
index 0000000..0f97d51
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanPairingSecurityType.aidl
@@ -0,0 +1,28 @@
+/*
+ * 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.hardware.wifi;
+
+/**
+ * NAN pairing security configuration options.
+ */
+@VintfStability
+@Backing(type="int")
+enum NanPairingSecurityType {
+ OPPORTUNISTIC,
+ PMK,
+ PASSPHRASE,
+}
diff --git a/wifi/aidl/android/hardware/wifi/NanPublishRequest.aidl b/wifi/aidl/android/hardware/wifi/NanPublishRequest.aidl
index 6dd079c..956a7df 100644
--- a/wifi/aidl/android/hardware/wifi/NanPublishRequest.aidl
+++ b/wifi/aidl/android/hardware/wifi/NanPublishRequest.aidl
@@ -17,6 +17,7 @@
package android.hardware.wifi;
import android.hardware.wifi.NanDiscoveryCommonConfig;
+import android.hardware.wifi.NanPairingConfig;
import android.hardware.wifi.NanPublishType;
import android.hardware.wifi.NanTxType;
@@ -46,4 +47,12 @@
* the device must automatically accept the data-path request and complete the negotiation.
*/
boolean autoAcceptDataPathRequests;
+ /**
+ * The config for NAN pairing
+ */
+ NanPairingConfig pairingConfig;
+ /**
+ * The Identity key for pairing, will generate NIRA for verification by the peer
+ */
+ byte[16] identityKey;
}
diff --git a/wifi/aidl/android/hardware/wifi/NanRespondToPairingIndicationRequest.aidl b/wifi/aidl/android/hardware/wifi/NanRespondToPairingIndicationRequest.aidl
new file mode 100644
index 0000000..456b430
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NanRespondToPairingIndicationRequest.aidl
@@ -0,0 +1,53 @@
+/*
+ * 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.hardware.wifi;
+
+import android.hardware.wifi.NanPairingRequestType;
+import android.hardware.wifi.NanPairingSecurityConfig;
+
+/**
+ * Response to a pairing request from a peer.
+ */
+@VintfStability
+parcelable NanRespondToPairingIndicationRequest {
+ /**
+ * Accept (true) or reject (false) the request.
+ * NAN Spec: Data Path Attributes / NDP Attribute / Type and Status
+ */
+ boolean acceptRequest;
+ /**
+ * ID of the NAN pairing for which we're responding. Obtained as part of the request in
+ * |IWifiNanIfaceEventCallback.eventPairingRequest|.
+ */
+ int pairingInstanceId;
+ /**
+ * Indicate the pairing session is of setup or verification
+ */
+ NanPairingRequestType requestType;
+ /**
+ * Whether should cache the negotiated NIK/NPK for future verification
+ */
+ boolean enablePairingCache;
+ /**
+ * The Identity key for pairing, can be used for pairing verification
+ */
+ byte[16] pairingIdentityKey;
+ /**
+ * Security config used for the pairing
+ */
+ NanPairingSecurityConfig securityConfig;
+}
diff --git a/wifi/aidl/android/hardware/wifi/NanStatusCode.aidl b/wifi/aidl/android/hardware/wifi/NanStatusCode.aidl
index d63a50e..efce867 100644
--- a/wifi/aidl/android/hardware/wifi/NanStatusCode.aidl
+++ b/wifi/aidl/android/hardware/wifi/NanStatusCode.aidl
@@ -71,4 +71,12 @@
* Unsupported concurrency of NAN and another feature - NAN disabled.
*/
UNSUPPORTED_CONCURRENCY_NAN_DISABLED = 12,
+ /**
+ * If the pairing id is invalid
+ */
+ INVALID_PAIRING_ID = 13,
+ /**
+ * If the bootstrapping id is invalid
+ */
+ INVALID_BOOTSTRAPPING_ID = 14
}
diff --git a/wifi/aidl/android/hardware/wifi/NanSubscribeRequest.aidl b/wifi/aidl/android/hardware/wifi/NanSubscribeRequest.aidl
index 12c1170..0b246ed 100644
--- a/wifi/aidl/android/hardware/wifi/NanSubscribeRequest.aidl
+++ b/wifi/aidl/android/hardware/wifi/NanSubscribeRequest.aidl
@@ -18,6 +18,7 @@
import android.hardware.wifi.MacAddress;
import android.hardware.wifi.NanDiscoveryCommonConfig;
+import android.hardware.wifi.NanPairingConfig;
import android.hardware.wifi.NanSrfType;
import android.hardware.wifi.NanSubscribeType;
@@ -67,4 +68,12 @@
* NAN Spec: Service Descriptor Attribute (SDA) / Service Response Filter / Address Set
*/
MacAddress[] intfAddr;
+ /**
+ * Security config used for the pairing
+ */
+ NanPairingConfig pairingConfig;
+ /**
+ * The Identity key for pairing, will generate NIRA for verification by the peer
+ */
+ byte[16] identityKey;
}
diff --git a/wifi/aidl/android/hardware/wifi/NpkSecurityAssociation.aidl b/wifi/aidl/android/hardware/wifi/NpkSecurityAssociation.aidl
new file mode 100644
index 0000000..42612c0
--- /dev/null
+++ b/wifi/aidl/android/hardware/wifi/NpkSecurityAssociation.aidl
@@ -0,0 +1,42 @@
+/*
+ * 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.hardware.wifi;
+
+import android.hardware.wifi.NanPairingAkm;
+
+/**
+ * The security sssociation info after Aware Pairing setup.
+ */
+@VintfStability
+parcelable NpkSecurityAssociation {
+ /**
+ * The Aware pairing identity from the peer
+ */
+ byte[16] peerNanIdentityKey;
+ /**
+ * The Aware pairing identity for local device
+ */
+ byte[16] localNanIdentityKey;
+ /**
+ * The PMK is used in this security association
+ */
+ byte[32] npk;
+ /**
+ * The AKM is used for key exchange in this security sssociation
+ */
+ NanPairingAkm akm;
+}
diff --git a/wifi/aidl/android/hardware/wifi/RttBw.aidl b/wifi/aidl/android/hardware/wifi/RttBw.aidl
index 9d42dc0..be9ecbd 100644
--- a/wifi/aidl/android/hardware/wifi/RttBw.aidl
+++ b/wifi/aidl/android/hardware/wifi/RttBw.aidl
@@ -22,6 +22,7 @@
@VintfStability
@Backing(type="int")
enum RttBw {
+ BW_UNSPECIFIED = 0x0,
BW_5MHZ = 0x01,
BW_10MHZ = 0x02,
BW_20MHZ = 0x04,
diff --git a/wifi/aidl/android/hardware/wifi/RttResult.aidl b/wifi/aidl/android/hardware/wifi/RttResult.aidl
index 565cce7..6c45e2c 100644
--- a/wifi/aidl/android/hardware/wifi/RttResult.aidl
+++ b/wifi/aidl/android/hardware/wifi/RttResult.aidl
@@ -16,6 +16,7 @@
package android.hardware.wifi;
+import android.hardware.wifi.RttBw;
import android.hardware.wifi.RttStatus;
import android.hardware.wifi.RttType;
import android.hardware.wifi.WifiInformationElement;
@@ -132,4 +133,15 @@
* For 11mc only.
*/
WifiInformationElement lcr;
+ /**
+ * RTT channel frequency in MHz
+ * If frequency is unknown, this will be set to 0.
+ */
+ int channelFreqMHz;
+ /**
+ * RTT packet bandwidth.
+ * This value is an average bandwidth of the bandwidths of measurement
+ * frames. Cap the average close to a specific valid RttBw.
+ */
+ RttBw packetBw;
}
diff --git a/wifi/aidl/default/aidl_struct_util.cpp b/wifi/aidl/default/aidl_struct_util.cpp
index 3087d66..22319ae 100644
--- a/wifi/aidl/default/aidl_struct_util.cpp
+++ b/wifi/aidl/default/aidl_struct_util.cpp
@@ -1261,6 +1261,165 @@
CHECK(false);
}
+legacy_hal::NanPairingRequestType convertAidlNanPairingRequestTypeToLegacy(
+ NanPairingRequestType type) {
+ switch (type) {
+ case NanPairingRequestType::NAN_PAIRING_SETUP:
+ return legacy_hal::NAN_PAIRING_SETUP;
+ case NanPairingRequestType::NAN_PAIRING_VERIFICATION:
+ return legacy_hal::NAN_PAIRING_VERIFICATION;
+ }
+ LOG(FATAL);
+}
+
+NanPairingRequestType convertLegacyNanPairingRequestTypeToAidl(
+ legacy_hal::NanPairingRequestType type) {
+ switch (type) {
+ case legacy_hal::NAN_PAIRING_SETUP:
+ return NanPairingRequestType::NAN_PAIRING_SETUP;
+ case legacy_hal::NAN_PAIRING_VERIFICATION:
+ return NanPairingRequestType::NAN_PAIRING_VERIFICATION;
+ }
+ LOG(FATAL);
+}
+
+legacy_hal::Akm convertAidlAkmTypeToLegacy(NanPairingAkm type) {
+ switch (type) {
+ case NanPairingAkm::SAE:
+ return legacy_hal::SAE;
+ case NanPairingAkm::PASN:
+ return legacy_hal::PASN;
+ }
+ LOG(FATAL);
+}
+
+NanPairingAkm convertLegacyAkmTypeToAidl(legacy_hal::Akm type) {
+ switch (type) {
+ case legacy_hal::SAE:
+ return NanPairingAkm::SAE;
+ case legacy_hal::PASN:
+ return NanPairingAkm::PASN;
+ }
+ LOG(FATAL);
+}
+
+uint16_t convertAidlBootstrappingMethodToLegacy(NanBootstrappingMethod type) {
+ switch (type) {
+ case NanBootstrappingMethod::BOOTSTRAPPING_OPPORTUNISTIC_MASK:
+ return NAN_PAIRING_BOOTSTRAPPING_OPPORTUNISTIC_MASK;
+ case NanBootstrappingMethod::BOOTSTRAPPING_PIN_CODE_DISPLAY_MASK:
+ return NAN_PAIRING_BOOTSTRAPPING_PIN_CODE_DISPLAY_MASK;
+ case NanBootstrappingMethod::BOOTSTRAPPING_PASSPHRASE_DISPLAY_MASK:
+ return NAN_PAIRING_BOOTSTRAPPING_PASSPHRASE_DISPLAY_MASK;
+ case NanBootstrappingMethod::BOOTSTRAPPING_QR_DISPLAY_MASK:
+ return NAN_PAIRING_BOOTSTRAPPING_QR_DISPLAY_MASK;
+ case NanBootstrappingMethod::BOOTSTRAPPING_NFC_TAG_MASK:
+ return NAN_PAIRING_BOOTSTRAPPING_NFC_TAG_MASK;
+ case NanBootstrappingMethod::BOOTSTRAPPING_PIN_CODE_KEYPAD_MASK:
+ return NAN_PAIRING_BOOTSTRAPPING_PIN_CODE_KEYPAD_MASK;
+ case NanBootstrappingMethod::BOOTSTRAPPING_PASSPHRASE_KEYPAD_MASK:
+ return NAN_PAIRING_BOOTSTRAPPING_PASSPHRASE_KEYPAD_MASK;
+ case NanBootstrappingMethod::BOOTSTRAPPING_QR_SCAN_MASK:
+ return NAN_PAIRING_BOOTSTRAPPING_QR_SCAN_MASK;
+ case NanBootstrappingMethod::BOOTSTRAPPING_NFC_READER_MASK:
+ return NAN_PAIRING_BOOTSTRAPPING_NFC_READER_MASK;
+ case NanBootstrappingMethod::BOOTSTRAPPING_SERVICE_MANAGED_MASK:
+ return NAN_PAIRING_BOOTSTRAPPING_SERVICE_MANAGED_MASK;
+ case NanBootstrappingMethod::BOOTSTRAPPING_HANDSHAKE_SHIP_MASK:
+ return NAN_PAIRING_BOOTSTRAPPING_HANDSHAKE_SHIP_MASK;
+ }
+ LOG(FATAL);
+}
+
+NanBootstrappingMethod convertLegacyBootstrappingMethodToAidl(uint16_t type) {
+ switch (type) {
+ case NAN_PAIRING_BOOTSTRAPPING_OPPORTUNISTIC_MASK:
+ return NanBootstrappingMethod::BOOTSTRAPPING_OPPORTUNISTIC_MASK;
+ case NAN_PAIRING_BOOTSTRAPPING_PIN_CODE_DISPLAY_MASK:
+ return NanBootstrappingMethod::BOOTSTRAPPING_PIN_CODE_DISPLAY_MASK;
+ case NAN_PAIRING_BOOTSTRAPPING_PASSPHRASE_DISPLAY_MASK:
+ return NanBootstrappingMethod::BOOTSTRAPPING_PASSPHRASE_DISPLAY_MASK;
+ case NAN_PAIRING_BOOTSTRAPPING_QR_DISPLAY_MASK:
+ return NanBootstrappingMethod::BOOTSTRAPPING_QR_DISPLAY_MASK;
+ case NAN_PAIRING_BOOTSTRAPPING_NFC_TAG_MASK:
+ return NanBootstrappingMethod::BOOTSTRAPPING_NFC_TAG_MASK;
+ case NAN_PAIRING_BOOTSTRAPPING_PIN_CODE_KEYPAD_MASK:
+ return NanBootstrappingMethod::BOOTSTRAPPING_PIN_CODE_KEYPAD_MASK;
+ case NAN_PAIRING_BOOTSTRAPPING_PASSPHRASE_KEYPAD_MASK:
+ return NanBootstrappingMethod::BOOTSTRAPPING_PASSPHRASE_KEYPAD_MASK;
+ case NAN_PAIRING_BOOTSTRAPPING_QR_SCAN_MASK:
+ return NanBootstrappingMethod::BOOTSTRAPPING_QR_SCAN_MASK;
+ case NAN_PAIRING_BOOTSTRAPPING_NFC_READER_MASK:
+ return NanBootstrappingMethod::BOOTSTRAPPING_NFC_READER_MASK;
+ case NAN_PAIRING_BOOTSTRAPPING_SERVICE_MANAGED_MASK:
+ return NanBootstrappingMethod::BOOTSTRAPPING_SERVICE_MANAGED_MASK;
+ case NAN_PAIRING_BOOTSTRAPPING_HANDSHAKE_SHIP_MASK:
+ return NanBootstrappingMethod::BOOTSTRAPPING_HANDSHAKE_SHIP_MASK;
+ }
+ LOG(FATAL);
+ return {};
+}
+
+bool covertAidlPairingConfigToLegacy(const NanPairingConfig& aidl_config,
+ legacy_hal::NanPairingConfig* legacy_config) {
+ if (!legacy_config) {
+ LOG(ERROR) << "covertAidlPairingConfigToLegacy: legacy_config is null";
+ return false;
+ }
+ legacy_config->enable_pairing_setup = aidl_config.enablePairingSetup ? 0x1 : 0x0;
+ legacy_config->enable_pairing_cache = aidl_config.enablePairingCache ? 0x1 : 0x0;
+ legacy_config->enable_pairing_verification = aidl_config.enablePairingVerification ? 0x1 : 0x0;
+ legacy_config->supported_bootstrapping_methods = aidl_config.supportedBootstrappingMethods;
+ return true;
+}
+
+bool convertLegacyPairingConfigToAidl(const legacy_hal::NanPairingConfig& legacy_config,
+ NanPairingConfig* aidl_config) {
+ if (!aidl_config) {
+ LOG(ERROR) << "convertLegacyPairingConfigToAidl: aidl_nira is null";
+ return false;
+ }
+ *aidl_config = {};
+ aidl_config->enablePairingSetup = legacy_config.enable_pairing_setup == 0x1;
+ aidl_config->enablePairingCache = legacy_config.enable_pairing_cache == 0x1;
+ aidl_config->enablePairingVerification = legacy_config.enable_pairing_verification == 0x1;
+ aidl_config->supportedBootstrappingMethods = legacy_config.supported_bootstrapping_methods;
+ return true;
+}
+
+bool convertLegacyNiraToAidl(const legacy_hal::NanIdentityResolutionAttribute& legacy_nira,
+ NanIdentityResolutionAttribute* aidl_nira) {
+ if (!aidl_nira) {
+ LOG(ERROR) << "convertLegacyNiraToAidl: aidl_nira is null";
+ return false;
+ }
+ *aidl_nira = {};
+ aidl_nira->nonce = std::array<uint8_t, 8>();
+ std::copy(legacy_nira.nonce, legacy_nira.nonce + 8, std::begin(aidl_nira->nonce));
+ aidl_nira->tag = std::array<uint8_t, 8>();
+ std::copy(legacy_nira.tag, legacy_nira.tag + 8, std::begin(aidl_nira->tag));
+ return true;
+}
+
+bool convertLegacyNpsaToAidl(const legacy_hal::NpkSecurityAssociation& legacy_npsa,
+ NpkSecurityAssociation* aidl_npsa) {
+ if (!aidl_npsa) {
+ LOG(ERROR) << "convertLegacyNiraToAidl: aidl_nira is null";
+ return false;
+ }
+ *aidl_npsa = {};
+ aidl_npsa->peerNanIdentityKey = std::array<uint8_t, 16>();
+ std::copy(legacy_npsa.peer_nan_identity_key, legacy_npsa.peer_nan_identity_key + 16,
+ std::begin(aidl_npsa->peerNanIdentityKey));
+ aidl_npsa->localNanIdentityKey = std::array<uint8_t, 16>();
+ std::copy(legacy_npsa.local_nan_identity_key, legacy_npsa.local_nan_identity_key + 16,
+ std::begin(aidl_npsa->localNanIdentityKey));
+ aidl_npsa->npk = std::array<uint8_t, 32>();
+ std::copy(legacy_npsa.npk.pmk, legacy_npsa.npk.pmk + 32, std::begin(aidl_npsa->npk));
+ aidl_npsa->akm = convertLegacyAkmTypeToAidl(legacy_npsa.akm);
+ return true;
+}
+
NanStatusCode convertLegacyNanStatusTypeToAidl(legacy_hal::NanStatusType type) {
switch (type) {
case legacy_hal::NAN_STATUS_SUCCESS:
@@ -1289,6 +1448,10 @@
return NanStatusCode::FOLLOWUP_TX_QUEUE_FULL;
case legacy_hal::NAN_STATUS_UNSUPPORTED_CONCURRENCY_NAN_DISABLED:
return NanStatusCode::UNSUPPORTED_CONCURRENCY_NAN_DISABLED;
+ case legacy_hal::NAN_STATUS_INVALID_PAIRING_ID:
+ return NanStatusCode::INVALID_PAIRING_ID;
+ case legacy_hal::NAN_STATUS_INVALID_BOOTSTRAPPING_ID:
+ return NanStatusCode::INVALID_BOOTSTRAPPING_ID;
}
CHECK(false);
}
@@ -1679,6 +1842,12 @@
legacy_request->service_responder_policy = aidl_request.autoAcceptDataPathRequests
? legacy_hal::NAN_SERVICE_ACCEPT_POLICY_ALL
: legacy_hal::NAN_SERVICE_ACCEPT_POLICY_NONE;
+ memcpy(legacy_request->nan_identity_key, aidl_request.identityKey.data(), NAN_IDENTITY_KEY_LEN);
+ if (!covertAidlPairingConfigToLegacy(aidl_request.pairingConfig,
+ &legacy_request->nan_pairing_config)) {
+ LOG(ERROR) << "convertAidlNanPublishRequestToLegacy: invalid pairing config";
+ return false;
+ }
return true;
}
@@ -1819,7 +1988,12 @@
for (int i = 0; i < legacy_request->num_intf_addr_present; i++) {
memcpy(legacy_request->intf_addr[i], aidl_request.intfAddr[i].data.data(), 6);
}
-
+ memcpy(legacy_request->nan_identity_key, aidl_request.identityKey.data(), NAN_IDENTITY_KEY_LEN);
+ if (!covertAidlPairingConfigToLegacy(aidl_request.pairingConfig,
+ &legacy_request->nan_pairing_config)) {
+ LOG(ERROR) << "convertAidlNanSubscribeRequestToLegacy: invalid pairing config";
+ return false;
+ }
return true;
}
@@ -2068,7 +2242,9 @@
aidl_response->supportedCipherSuites =
static_cast<NanCipherSuiteType>(legacy_response.cipher_suites_supported);
aidl_response->instantCommunicationModeSupportFlag = legacy_response.is_instant_mode_supported;
-
+ aidl_response->supports6g = legacy_response.is_6g_supported;
+ aidl_response->supportsHe = legacy_response.is_he_supported;
+ aidl_response->supportsPairing = legacy_response.is_pairing_supported;
return true;
}
@@ -2105,6 +2281,16 @@
aidl_ind->rangingIndicationType =
static_cast<NanRangingIndication>(legacy_ind.range_info.ranging_event_type);
aidl_ind->scid = std::vector<uint8_t>(legacy_ind.scid, legacy_ind.scid + legacy_ind.scid_len);
+
+ if (!convertLegacyNiraToAidl(legacy_ind.nira, &aidl_ind->peerNira)) {
+ LOG(ERROR) << "convertLegacyNanMatchIndToAidl: invalid NIRA";
+ return false;
+ }
+ if (!convertLegacyPairingConfigToAidl(legacy_ind.peer_pairing_config,
+ &aidl_ind->peerPairingConfig)) {
+ LOG(ERROR) << "convertLegacyNanMatchIndToAidl: invalid pairing config";
+ return false;
+ }
return true;
}
@@ -2363,6 +2549,8 @@
return legacy_hal::WIFI_RTT_BW_160;
case RttBw::BW_320MHZ:
return legacy_hal::WIFI_RTT_BW_320;
+ case RttBw::BW_UNSPECIFIED:
+ return legacy_hal::WIFI_RTT_BW_UNSPECIFIED;
};
CHECK(false);
}
@@ -2383,6 +2571,8 @@
return RttBw::BW_160MHZ;
case legacy_hal::WIFI_RTT_BW_320:
return RttBw::BW_320MHZ;
+ case legacy_hal::WIFI_RTT_BW_UNSPECIFIED:
+ return RttBw::BW_UNSPECIFIED;
};
CHECK(false) << "Unknown legacy type: " << type;
}
@@ -2712,6 +2902,28 @@
if (!convertLegacyRttResultToAidl(*legacy_result, &aidl_result)) {
return false;
}
+ aidl_result.channelFreqMHz = 0;
+ aidl_result.packetBw = RttBw::BW_UNSPECIFIED;
+ aidl_results->push_back(aidl_result);
+ }
+ return true;
+}
+
+bool convertLegacyVectorOfRttResultV2ToAidl(
+ const std::vector<const legacy_hal::wifi_rtt_result_v2*>& legacy_results,
+ std::vector<RttResult>* aidl_results) {
+ if (!aidl_results) {
+ return false;
+ }
+ *aidl_results = {};
+ for (const auto legacy_result : legacy_results) {
+ RttResult aidl_result;
+ if (!convertLegacyRttResultToAidl(legacy_result->rtt_result, &aidl_result)) {
+ return false;
+ }
+ aidl_result.channelFreqMHz =
+ legacy_result->frequency != UNSPECIFIED ? legacy_result->frequency : 0;
+ aidl_result.packetBw = convertLegacyRttBwToAidl(legacy_result->packet_bw);
aidl_results->push_back(aidl_result);
}
return true;
@@ -2861,6 +3073,235 @@
return true;
}
+bool convertAidlNanPairingInitiatorRequestToLegacy(const NanPairingRequest& aidl_request,
+ legacy_hal::NanPairingRequest* legacy_request) {
+ if (!legacy_request) {
+ LOG(ERROR) << "convertAidlNanPairingInitiatorRequestToLegacy: "
+ "legacy_request is null";
+ return false;
+ }
+ *legacy_request = {};
+
+ legacy_request->requestor_instance_id = aidl_request.peerId;
+ memcpy(legacy_request->peer_disc_mac_addr, aidl_request.peerDiscMacAddr.data(), 6);
+ legacy_request->nan_pairing_request_type =
+ convertAidlNanPairingRequestTypeToLegacy(aidl_request.requestType);
+ legacy_request->enable_pairing_cache = aidl_request.enablePairingCache;
+
+ memcpy(legacy_request->nan_identity_key, aidl_request.pairingIdentityKey.data(),
+ NAN_IDENTITY_KEY_LEN);
+
+ legacy_request->is_opportunistic =
+ aidl_request.securityConfig.securityType == NanPairingSecurityType::OPPORTUNISTIC ? 1
+ : 0;
+ legacy_request->akm = convertAidlAkmTypeToLegacy(aidl_request.securityConfig.akm);
+ if (aidl_request.securityConfig.securityType == NanPairingSecurityType::PMK) {
+ legacy_request->key_info.key_type = legacy_hal::NAN_SECURITY_KEY_INPUT_PMK;
+ legacy_request->key_info.body.pmk_info.pmk_len = aidl_request.securityConfig.pmk.size();
+ if (legacy_request->key_info.body.pmk_info.pmk_len != NAN_PMK_INFO_LEN) {
+ LOG(ERROR) << "convertAidlNanPairingInitiatorRequestToLegacy: "
+ "invalid pmk_len";
+ return false;
+ }
+ memcpy(legacy_request->key_info.body.pmk_info.pmk, aidl_request.securityConfig.pmk.data(),
+ legacy_request->key_info.body.pmk_info.pmk_len);
+ }
+ if (aidl_request.securityConfig.securityType == NanPairingSecurityType::PASSPHRASE) {
+ legacy_request->key_info.key_type = legacy_hal::NAN_SECURITY_KEY_INPUT_PASSPHRASE;
+ legacy_request->key_info.body.passphrase_info.passphrase_len =
+ aidl_request.securityConfig.passphrase.size();
+ if (legacy_request->key_info.body.passphrase_info.passphrase_len <
+ NAN_SECURITY_MIN_PASSPHRASE_LEN) {
+ LOG(ERROR) << "convertAidlNanPairingInitiatorRequestToLegacy: "
+ "passphrase_len too small";
+ return false;
+ }
+ if (legacy_request->key_info.body.passphrase_info.passphrase_len >
+ NAN_SECURITY_MAX_PASSPHRASE_LEN) {
+ LOG(ERROR) << "convertAidlNanPairingInitiatorRequestToLegacy: "
+ "passphrase_len too large";
+ return false;
+ }
+ memcpy(legacy_request->key_info.body.passphrase_info.passphrase,
+ aidl_request.securityConfig.passphrase.data(),
+ legacy_request->key_info.body.passphrase_info.passphrase_len);
+ }
+
+ return true;
+}
+
+bool convertAidlNanPairingIndicationResponseToLegacy(
+ const NanRespondToPairingIndicationRequest& aidl_request,
+ legacy_hal::NanPairingIndicationResponse* legacy_request) {
+ if (!legacy_request) {
+ LOG(ERROR) << "convertAidlNanPairingIndicationResponseToLegacy: "
+ "legacy_request is null";
+ return false;
+ }
+ *legacy_request = {};
+
+ legacy_request->pairing_instance_id = aidl_request.pairingInstanceId;
+ legacy_request->nan_pairing_request_type =
+ convertAidlNanPairingRequestTypeToLegacy(aidl_request.requestType);
+ legacy_request->enable_pairing_cache = aidl_request.enablePairingCache;
+
+ memcpy(legacy_request->nan_identity_key, aidl_request.pairingIdentityKey.data(),
+ NAN_IDENTITY_KEY_LEN);
+
+ legacy_request->is_opportunistic =
+ aidl_request.securityConfig.securityType == NanPairingSecurityType::OPPORTUNISTIC ? 1
+ : 0;
+ legacy_request->akm = convertAidlAkmTypeToLegacy(aidl_request.securityConfig.akm);
+ legacy_request->rsp_code =
+ aidl_request.acceptRequest ? NAN_PAIRING_REQUEST_ACCEPT : NAN_PAIRING_REQUEST_REJECT;
+ if (aidl_request.securityConfig.securityType == NanPairingSecurityType::PMK) {
+ legacy_request->key_info.key_type = legacy_hal::NAN_SECURITY_KEY_INPUT_PMK;
+ legacy_request->key_info.body.pmk_info.pmk_len = aidl_request.securityConfig.pmk.size();
+ if (legacy_request->key_info.body.pmk_info.pmk_len != NAN_PMK_INFO_LEN) {
+ LOG(ERROR) << "convertAidlNanPairingIndicationResponseToLegacy: "
+ "invalid pmk_len";
+ return false;
+ }
+ memcpy(legacy_request->key_info.body.pmk_info.pmk, aidl_request.securityConfig.pmk.data(),
+ legacy_request->key_info.body.pmk_info.pmk_len);
+ }
+ if (aidl_request.securityConfig.securityType == NanPairingSecurityType::PASSPHRASE) {
+ legacy_request->key_info.key_type = legacy_hal::NAN_SECURITY_KEY_INPUT_PASSPHRASE;
+ legacy_request->key_info.body.passphrase_info.passphrase_len =
+ aidl_request.securityConfig.passphrase.size();
+ if (legacy_request->key_info.body.passphrase_info.passphrase_len <
+ NAN_SECURITY_MIN_PASSPHRASE_LEN) {
+ LOG(ERROR) << "convertAidlNanPairingIndicationResponseToLegacy: "
+ "passphrase_len too small";
+ return false;
+ }
+ if (legacy_request->key_info.body.passphrase_info.passphrase_len >
+ NAN_SECURITY_MAX_PASSPHRASE_LEN) {
+ LOG(ERROR) << "convertAidlNanPairingIndicationResponseToLegacy: "
+ "passphrase_len too large";
+ return false;
+ }
+ memcpy(legacy_request->key_info.body.passphrase_info.passphrase,
+ aidl_request.securityConfig.passphrase.data(),
+ legacy_request->key_info.body.passphrase_info.passphrase_len);
+ }
+
+ return true;
+}
+
+bool convertAidlNanBootstrappingInitiatorRequestToLegacy(
+ const NanBootstrappingRequest& aidl_request,
+ legacy_hal::NanBootstrappingRequest* legacy_request) {
+ if (!legacy_request) {
+ LOG(ERROR) << "convertAidlNanBootstrappingInitiatorRequestToLegacy: "
+ "legacy_request is null";
+ return false;
+ }
+ *legacy_request = {};
+
+ legacy_request->requestor_instance_id = aidl_request.peerId;
+ memcpy(legacy_request->peer_disc_mac_addr, aidl_request.peerDiscMacAddr.data(), 6);
+ legacy_request->request_bootstrapping_method =
+ convertAidlBootstrappingMethodToLegacy(aidl_request.requestBootstrappingMethod);
+
+ return true;
+}
+
+bool convertAidlNanBootstrappingIndicationResponseToLegacy(
+ const NanBootstrappingResponse& aidl_request,
+ legacy_hal::NanBootstrappingIndicationResponse* legacy_request) {
+ if (!legacy_request) {
+ LOG(ERROR) << "convertAidlNanBootstrappingIndicationResponseToLegacy: "
+ "legacy_request is null";
+ return false;
+ }
+ *legacy_request = {};
+
+ legacy_request->service_instance_id = aidl_request.bootstrappingInstanceId;
+ legacy_request->rsp_code = aidl_request.acceptRequest ? NAN_BOOTSTRAPPING_REQUEST_ACCEPT
+ : NAN_BOOTSTRAPPING_REQUEST_REJECT;
+
+ return true;
+}
+
+bool convertLegacyNanPairingRequestIndToAidl(const legacy_hal::NanPairingRequestInd& legacy_ind,
+ NanPairingRequestInd* aidl_ind) {
+ if (!aidl_ind) {
+ LOG(ERROR) << "convertLegacyNanPairingRequestIndToAidl: aidl_ind is null";
+ return false;
+ }
+ *aidl_ind = {};
+
+ aidl_ind->discoverySessionId = legacy_ind.publish_subscribe_id;
+ aidl_ind->peerId = legacy_ind.requestor_instance_id;
+ aidl_ind->peerDiscMacAddr = std::array<uint8_t, 6>();
+ std::copy(legacy_ind.peer_disc_mac_addr, legacy_ind.peer_disc_mac_addr + 6,
+ std::begin(aidl_ind->peerDiscMacAddr));
+ aidl_ind->pairingInstanceId = legacy_ind.pairing_instance_id;
+ aidl_ind->enablePairingCache = legacy_ind.enable_pairing_cache == 1;
+ aidl_ind->requestType =
+ convertLegacyNanPairingRequestTypeToAidl(legacy_ind.nan_pairing_request_type);
+ if (!convertLegacyNiraToAidl(legacy_ind.nira, &aidl_ind->peerNira)) {
+ return false;
+ }
+ return true;
+}
+
+bool convertLegacyNanPairingConfirmIndToAidl(const legacy_hal::NanPairingConfirmInd& legacy_ind,
+ NanPairingConfirmInd* aidl_ind) {
+ if (!aidl_ind) {
+ LOG(ERROR) << "convertLegacyNanPairingRequestIndToAidl: aidl_ind is null";
+ return false;
+ }
+ *aidl_ind = {};
+
+ aidl_ind->pairingInstanceId = legacy_ind.pairing_instance_id;
+ aidl_ind->enablePairingCache = legacy_ind.enable_pairing_cache == 1;
+ aidl_ind->requestType =
+ convertLegacyNanPairingRequestTypeToAidl(legacy_ind.nan_pairing_request_type);
+ aidl_ind->pairingSuccess = legacy_ind.rsp_code == NAN_PAIRING_REQUEST_ACCEPT;
+ aidl_ind->status.status = convertLegacyNanStatusTypeToAidl(legacy_ind.reason_code);
+ if (!convertLegacyNpsaToAidl(legacy_ind.npk_security_association, &aidl_ind->npksa)) {
+ return false;
+ }
+ return true;
+}
+
+bool convertLegacyNanBootstrappingRequestIndToAidl(
+ const legacy_hal::NanBootstrappingRequestInd& legacy_ind,
+ NanBootstrappingRequestInd* aidl_ind) {
+ if (!aidl_ind) {
+ LOG(ERROR) << "convertLegacyNanBootstrappingRequestIndToAidl: aidl_ind is null";
+ return false;
+ }
+ *aidl_ind = {};
+
+ aidl_ind->discoverySessionId = legacy_ind.publish_subscribe_id;
+ aidl_ind->peerId = legacy_ind.requestor_instance_id;
+ aidl_ind->peerDiscMacAddr = std::array<uint8_t, 6>();
+ std::copy(legacy_ind.peer_disc_mac_addr, legacy_ind.peer_disc_mac_addr + 6,
+ std::begin(aidl_ind->peerDiscMacAddr));
+ aidl_ind->bootstrappingInstanceId = legacy_ind.bootstrapping_instance_id;
+ aidl_ind->requestBootstrappingMethod =
+ convertLegacyBootstrappingMethodToAidl(legacy_ind.request_bootstrapping_method);
+ return true;
+}
+
+bool convertLegacyNanBootstrappingConfirmIndToAidl(
+ const legacy_hal::NanBootstrappingConfirmInd& legacy_ind,
+ NanBootstrappingConfirmInd* aidl_ind) {
+ if (!aidl_ind) {
+ LOG(ERROR) << "convertLegacyNanBootstrappingConfirmIndToAidl: aidl_ind is null";
+ return false;
+ }
+ *aidl_ind = {};
+
+ aidl_ind->bootstrappingInstanceId = legacy_ind.bootstrapping_instance_id;
+ aidl_ind->acceptRequest = legacy_ind.rsp_code == NAN_BOOTSTRAPPING_REQUEST_ACCEPT;
+ aidl_ind->reasonCode.status = convertLegacyNanStatusTypeToAidl(legacy_ind.reason_code);
+ return true;
+}
+
bool convertLegacyWifiChipCapabilitiesToAidl(
const legacy_hal::wifi_chip_capabilities& legacy_chip_capabilities,
WifiChipCapabilities& aidl_chip_capabilities) {
diff --git a/wifi/aidl/default/aidl_struct_util.h b/wifi/aidl/default/aidl_struct_util.h
index ac86755..e478fed 100644
--- a/wifi/aidl/default/aidl_struct_util.h
+++ b/wifi/aidl/default/aidl_struct_util.h
@@ -163,6 +163,9 @@
bool convertLegacyVectorOfRttResultToAidl(
const std::vector<const legacy_hal::wifi_rtt_result*>& legacy_results,
std::vector<RttResult>* aidl_results);
+bool convertLegacyVectorOfRttResultV2ToAidl(
+ const std::vector<const legacy_hal::wifi_rtt_result_v2*>& legacy_results,
+ std::vector<RttResult>* aidl_results);
uint32_t convertAidlWifiBandToLegacyMacBand(WifiBand band);
uint32_t convertAidlWifiIfaceModeToLegacy(uint32_t aidl_iface_mask);
uint32_t convertAidlUsableChannelFilterToLegacy(uint32_t aidl_filter_mask);
@@ -176,6 +179,27 @@
bool convertLegacyWifiChipCapabilitiesToAidl(
const legacy_hal::wifi_chip_capabilities& legacy_chip_capabilities,
WifiChipCapabilities& aidl_chip_capabilities);
+bool convertAidlNanPairingInitiatorRequestToLegacy(const NanPairingRequest& aidl_request,
+ legacy_hal::NanPairingRequest* legacy_request);
+bool convertAidlNanPairingIndicationResponseToLegacy(
+ const NanRespondToPairingIndicationRequest& aidl_response,
+ legacy_hal::NanPairingIndicationResponse* legacy_response);
+bool convertAidlNanBootstrappingInitiatorRequestToLegacy(
+ const NanBootstrappingRequest& aidl_request,
+ legacy_hal::NanBootstrappingRequest* legacy_request);
+bool convertAidlNanBootstrappingIndicationResponseToLegacy(
+ const NanBootstrappingResponse& aidl_response,
+ legacy_hal::NanBootstrappingIndicationResponse* legacy_response);
+bool convertLegacyNanPairingRequestIndToAidl(const legacy_hal::NanPairingRequestInd& legacy_ind,
+ NanPairingRequestInd* aidl_ind);
+bool convertLegacyNanPairingConfirmIndToAidl(const legacy_hal::NanPairingConfirmInd& legacy_ind,
+ NanPairingConfirmInd* aidl_ind);
+bool convertLegacyNanBootstrappingRequestIndToAidl(
+ const legacy_hal::NanBootstrappingRequestInd& legacy_ind,
+ NanBootstrappingRequestInd* aidl_ind);
+bool convertLegacyNanBootstrappingConfirmIndToAidl(
+ const legacy_hal::NanBootstrappingConfirmInd& legacy_ind,
+ NanBootstrappingConfirmInd* aidl_ind);
} // namespace aidl_struct_util
} // namespace wifi
} // namespace hardware
diff --git a/wifi/aidl/default/tests/aidl_struct_util_unit_tests.cpp b/wifi/aidl/default/tests/aidl_struct_util_unit_tests.cpp
index df788b8..9b9d96d 100644
--- a/wifi/aidl/default/tests/aidl_struct_util_unit_tests.cpp
+++ b/wifi/aidl/default/tests/aidl_struct_util_unit_tests.cpp
@@ -29,6 +29,12 @@
constexpr uint32_t kIfaceChannel2 = 5;
constexpr char kIfaceName1[] = "wlan0";
constexpr char kIfaceName2[] = "wlan1";
+constexpr uint8_t kMacAddress[] = {0x02, 0x12, 0x45, 0x56, 0xab, 0xcc};
+byte LCI[] = {0x27, 0x1A, 0x1, 0x00, 0x8, 0x01, 0x00, 0x08, 0x00, 0x10, 0x52,
+ 0x83, 0x4d, 0x12, 0xef, 0xd2, 0xb0, 0x8b, 0x9b, 0x4b, 0xf1, 0xcc,
+ 0x2c, 0x00, 0x00, 0x41, 0x06, 0x03, 0x06, 0x00, 0x80};
+byte LCR[] = {0x27, 0xE, 0x1, 0x00, 0xB, 0x01, 0x00, 0x0b, 0x00, 0x09,
+ 0x55, 0x53, 0x18, 0x05, 0x39, 0x34, 0x30, 0x34, 0x33};
} // namespace
namespace aidl {
@@ -764,6 +770,100 @@
radio_configurations_array3);
}
+void verifyRttResult(wifi_rtt_result* legacy_rtt_result_ptr, RttResult* aidl_results_ptr) {
+ EXPECT_EQ((int)legacy_rtt_result_ptr->burst_num, aidl_results_ptr->burstNum);
+ EXPECT_EQ((int)legacy_rtt_result_ptr->measurement_number, aidl_results_ptr->measurementNumber);
+ EXPECT_EQ((int)legacy_rtt_result_ptr->success_number, aidl_results_ptr->successNumber);
+ EXPECT_EQ(legacy_rtt_result_ptr->number_per_burst_peer, aidl_results_ptr->numberPerBurstPeer);
+ EXPECT_EQ(legacy_rtt_result_ptr->retry_after_duration, aidl_results_ptr->retryAfterDuration);
+ EXPECT_EQ(legacy_rtt_result_ptr->rssi, aidl_results_ptr->rssi);
+ EXPECT_EQ(legacy_rtt_result_ptr->rssi_spread, aidl_results_ptr->rssiSpread);
+ EXPECT_EQ(legacy_rtt_result_ptr->rtt, aidl_results_ptr->rtt);
+ EXPECT_EQ(legacy_rtt_result_ptr->rtt_sd, aidl_results_ptr->rttSd);
+ EXPECT_EQ(legacy_rtt_result_ptr->rtt_spread, aidl_results_ptr->rttSpread);
+ EXPECT_EQ(legacy_rtt_result_ptr->distance_mm, aidl_results_ptr->distanceInMm);
+ EXPECT_EQ(legacy_rtt_result_ptr->distance_sd_mm, aidl_results_ptr->distanceSdInMm);
+ EXPECT_EQ(legacy_rtt_result_ptr->distance_spread_mm, aidl_results_ptr->distanceSpreadInMm);
+ EXPECT_EQ(legacy_rtt_result_ptr->ts, aidl_results_ptr->timeStampInUs);
+ EXPECT_EQ(legacy_rtt_result_ptr->burst_duration, aidl_results_ptr->burstDurationInMs);
+ EXPECT_EQ(legacy_rtt_result_ptr->negotiated_burst_num, aidl_results_ptr->negotiatedBurstNum);
+ EXPECT_EQ(legacy_rtt_result_ptr->LCI->id, aidl_results_ptr->lci.id);
+ for (int i = 0; i < legacy_rtt_result_ptr->LCI->len; i++) {
+ EXPECT_EQ(legacy_rtt_result_ptr->LCI->data[i], aidl_results_ptr->lci.data[i]);
+ }
+ EXPECT_EQ(legacy_rtt_result_ptr->LCR->id, aidl_results_ptr->lcr.id);
+ for (int i = 0; i < legacy_rtt_result_ptr->LCR->len; i++) {
+ EXPECT_EQ(legacy_rtt_result_ptr->LCR->data[i], aidl_results_ptr->lcr.data[i]);
+ }
+}
+
+void fillLegacyRttResult(wifi_rtt_result* rtt_result_ptr) {
+ std::copy(std::begin(kMacAddress), std::end(kMacAddress), std::begin(rtt_result_ptr->addr));
+ rtt_result_ptr->burst_num = rand();
+ rtt_result_ptr->measurement_number = rand();
+ rtt_result_ptr->success_number = rand();
+ rtt_result_ptr->number_per_burst_peer = 0xF & rand();
+ rtt_result_ptr->status = RTT_STATUS_SUCCESS;
+ rtt_result_ptr->retry_after_duration = 0xF & rand();
+ rtt_result_ptr->type = RTT_TYPE_2_SIDED;
+ rtt_result_ptr->rssi = rand();
+ rtt_result_ptr->rssi_spread = rand();
+ rtt_result_ptr->rtt = rand();
+ rtt_result_ptr->rtt_sd = rand();
+ rtt_result_ptr->rtt_spread = rand();
+ rtt_result_ptr->distance_mm = rand();
+ rtt_result_ptr->distance_sd_mm = rand();
+ rtt_result_ptr->distance_spread_mm = rand();
+ rtt_result_ptr->burst_duration = rand();
+ rtt_result_ptr->negotiated_burst_num = rand();
+ rtt_result_ptr->LCI = (wifi_information_element*)LCI;
+ rtt_result_ptr->LCR = (wifi_information_element*)LCR;
+}
+
+TEST_F(AidlStructUtilTest, convertLegacyVectorOfRttResultToAidl) {
+ std::vector<const wifi_rtt_result*> rtt_results_vec;
+ wifi_rtt_result rttResults[2];
+
+ // fill legacy rtt results
+ for (int i = 0; i < 2; i++) {
+ fillLegacyRttResult(&rttResults[i]);
+ rtt_results_vec.push_back(&rttResults[i]);
+ }
+
+ std::vector<RttResult> aidl_results;
+ aidl_struct_util::convertLegacyVectorOfRttResultToAidl(rtt_results_vec, &aidl_results);
+
+ EXPECT_EQ(rtt_results_vec.size(), aidl_results.size());
+ for (size_t i = 0; i < rtt_results_vec.size(); i++) {
+ verifyRttResult(&rttResults[i], &aidl_results[i]);
+ EXPECT_EQ(aidl_results[i].channelFreqMHz, 0);
+ EXPECT_EQ(aidl_results[i].packetBw, RttBw::BW_UNSPECIFIED);
+ }
+}
+
+TEST_F(AidlStructUtilTest, convertLegacyVectorOfRttResultV2ToAidl) {
+ std::vector<const wifi_rtt_result_v2*> rtt_results_vec_v2;
+ wifi_rtt_result_v2 rttResults_v2[2];
+
+ // fill legacy rtt results v2
+ for (int i = 0; i < 2; i++) {
+ fillLegacyRttResult(&rttResults_v2[i].rtt_result);
+ rttResults_v2[i].frequency = 2412 + i * 5;
+ rttResults_v2[i].packet_bw = WIFI_RTT_BW_80;
+ rtt_results_vec_v2.push_back(&rttResults_v2[i]);
+ }
+
+ std::vector<RttResult> aidl_results;
+ aidl_struct_util::convertLegacyVectorOfRttResultV2ToAidl(rtt_results_vec_v2, &aidl_results);
+
+ EXPECT_EQ(rtt_results_vec_v2.size(), aidl_results.size());
+ for (size_t i = 0; i < rtt_results_vec_v2.size(); i++) {
+ verifyRttResult(&rttResults_v2[i].rtt_result, &aidl_results[i]);
+ EXPECT_EQ(aidl_results[i].channelFreqMHz, rttResults_v2[i].frequency);
+ EXPECT_EQ(aidl_results[i].packetBw, RttBw::BW_80MHZ);
+ }
+}
+
} // namespace wifi
} // namespace hardware
} // namespace android
diff --git a/wifi/aidl/default/tests/wifi_nan_iface_unit_tests.cpp b/wifi/aidl/default/tests/wifi_nan_iface_unit_tests.cpp
index d40801f..f81cab3 100644
--- a/wifi/aidl/default/tests/wifi_nan_iface_unit_tests.cpp
+++ b/wifi/aidl/default/tests/wifi_nan_iface_unit_tests.cpp
@@ -122,6 +122,18 @@
MOCK_METHOD1(eventDataPathTerminated, ndk::ScopedAStatus(int32_t));
MOCK_METHOD1(eventDataPathScheduleUpdate,
ndk::ScopedAStatus(const NanDataPathScheduleUpdateInd&));
+ MOCK_METHOD1(eventPairingConfirm, ndk::ScopedAStatus(const NanPairingConfirmInd&));
+ MOCK_METHOD1(eventPairingRequest, ndk::ScopedAStatus(const NanPairingRequestInd&));
+ MOCK_METHOD1(eventBootstrappingConfirm, ndk::ScopedAStatus(const NanBootstrappingConfirmInd&));
+ MOCK_METHOD1(eventBootstrappingRequest, ndk::ScopedAStatus(const NanBootstrappingRequestInd&));
+ MOCK_METHOD3(notifyInitiatePairingResponse,
+ ndk::ScopedAStatus(char16_t, const NanStatus&, int32_t));
+ MOCK_METHOD2(notifyRespondToPairingIndicationResponse,
+ ndk::ScopedAStatus(char16_t, const NanStatus&));
+ MOCK_METHOD3(notifyInitiateBootstrappingResponse,
+ ndk::ScopedAStatus(char16_t, const NanStatus&, int32_t));
+ MOCK_METHOD2(notifyRespondToBootstrappingIndicationResponse,
+ ndk::ScopedAStatus(char16_t, const NanStatus&));
};
class WifiNanIfaceTest : public Test {
diff --git a/wifi/aidl/default/wifi_legacy_hal.cpp b/wifi/aidl/default/wifi_legacy_hal.cpp
index 83f368e..54e91d4 100644
--- a/wifi/aidl/default/wifi_legacy_hal.cpp
+++ b/wifi/aidl/default/wifi_legacy_hal.cpp
@@ -181,11 +181,28 @@
// Callback to be invoked for rtt results results.
std::function<void(wifi_request_id, unsigned num_results, wifi_rtt_result* rtt_results[])>
on_rtt_results_internal_callback;
+std::function<void(wifi_request_id, unsigned num_results, wifi_rtt_result_v2* rtt_results_v2[])>
+ on_rtt_results_internal_callback_v2;
+
+void invalidateRttResultsCallbacks() {
+ on_rtt_results_internal_callback = nullptr;
+ on_rtt_results_internal_callback_v2 = nullptr;
+};
+
void onAsyncRttResults(wifi_request_id id, unsigned num_results, wifi_rtt_result* rtt_results[]) {
const auto lock = aidl_sync_util::acquireGlobalLock();
if (on_rtt_results_internal_callback) {
on_rtt_results_internal_callback(id, num_results, rtt_results);
- on_rtt_results_internal_callback = nullptr;
+ invalidateRttResultsCallbacks();
+ }
+}
+
+void onAsyncRttResultsV2(wifi_request_id id, unsigned num_results,
+ wifi_rtt_result_v2* rtt_results_v2[]) {
+ const auto lock = aidl_sync_util::acquireGlobalLock();
+ if (on_rtt_results_internal_callback_v2) {
+ on_rtt_results_internal_callback_v2(id, num_results, rtt_results_v2);
+ invalidateRttResultsCallbacks();
}
}
@@ -334,6 +351,40 @@
}
}
+std::function<void(const NanPairingRequestInd&)> on_nan_event_pairing_request_user_callback;
+void onAsyncNanEventPairingRequest(NanPairingRequestInd* event) {
+ const auto lock = aidl_sync_util::acquireGlobalLock();
+ if (on_nan_event_pairing_request_user_callback && event) {
+ on_nan_event_pairing_request_user_callback(*event);
+ }
+}
+
+std::function<void(const NanPairingConfirmInd&)> on_nan_event_pairing_confirm_user_callback;
+void onAsyncNanEventPairingConfirm(NanPairingConfirmInd* event) {
+ const auto lock = aidl_sync_util::acquireGlobalLock();
+ if (on_nan_event_pairing_confirm_user_callback && event) {
+ on_nan_event_pairing_confirm_user_callback(*event);
+ }
+}
+
+std::function<void(const NanBootstrappingRequestInd&)>
+ on_nan_event_bootstrapping_request_user_callback;
+void onAsyncNanEventBootstrappingRequest(NanBootstrappingRequestInd* event) {
+ const auto lock = aidl_sync_util::acquireGlobalLock();
+ if (on_nan_event_bootstrapping_request_user_callback && event) {
+ on_nan_event_bootstrapping_request_user_callback(*event);
+ }
+}
+
+std::function<void(const NanBootstrappingConfirmInd&)>
+ on_nan_event_bootstrapping_confirm_user_callback;
+void onAsyncNanEventBootstrappingConfirm(NanBootstrappingConfirmInd* event) {
+ const auto lock = aidl_sync_util::acquireGlobalLock();
+ if (on_nan_event_bootstrapping_confirm_user_callback && event) {
+ on_nan_event_bootstrapping_confirm_user_callback(*event);
+ }
+}
+
// Callbacks for the various TWT operations.
std::function<void(const TwtSetupResponse&)> on_twt_event_setup_response_callback;
void onAsyncTwtEventSetupResponse(TwtSetupResponse* event) {
@@ -1194,8 +1245,9 @@
wifi_error WifiLegacyHal::startRttRangeRequest(
const std::string& iface_name, wifi_request_id id,
const std::vector<wifi_rtt_config>& rtt_configs,
- const on_rtt_results_callback& on_results_user_callback) {
- if (on_rtt_results_internal_callback) {
+ const on_rtt_results_callback& on_results_user_callback,
+ const on_rtt_results_callback_v2& on_results_user_callback_v2) {
+ if (on_rtt_results_internal_callback || on_rtt_results_internal_callback_v2) {
return WIFI_ERROR_NOT_AVAILABLE;
}
@@ -1212,12 +1264,26 @@
on_results_user_callback(id, rtt_results_vec);
};
+ on_rtt_results_internal_callback_v2 = [on_results_user_callback_v2](
+ wifi_request_id id, unsigned num_results,
+ wifi_rtt_result_v2* rtt_results_v2[]) {
+ if (num_results > 0 && !rtt_results_v2) {
+ LOG(ERROR) << "Unexpected nullptr in RTT results";
+ return;
+ }
+ std::vector<const wifi_rtt_result_v2*> rtt_results_vec_v2;
+ std::copy_if(rtt_results_v2, rtt_results_v2 + num_results,
+ back_inserter(rtt_results_vec_v2),
+ [](wifi_rtt_result_v2* rtt_result_v2) { return rtt_result_v2 != nullptr; });
+ on_results_user_callback_v2(id, rtt_results_vec_v2);
+ };
+
std::vector<wifi_rtt_config> rtt_configs_internal(rtt_configs);
wifi_error status = global_func_table_.wifi_rtt_range_request(
id, getIfaceHandle(iface_name), rtt_configs.size(), rtt_configs_internal.data(),
- {onAsyncRttResults});
+ {onAsyncRttResults, onAsyncRttResultsV2});
if (status != WIFI_SUCCESS) {
- on_rtt_results_internal_callback = nullptr;
+ invalidateRttResultsCallbacks();
}
return status;
}
@@ -1225,7 +1291,7 @@
wifi_error WifiLegacyHal::cancelRttRangeRequest(
const std::string& iface_name, wifi_request_id id,
const std::vector<std::array<uint8_t, ETH_ALEN>>& mac_addrs) {
- if (!on_rtt_results_internal_callback) {
+ if (!on_rtt_results_internal_callback && !on_rtt_results_internal_callback_v2) {
return WIFI_ERROR_NOT_AVAILABLE;
}
static_assert(sizeof(mac_addr) == sizeof(std::array<uint8_t, ETH_ALEN>),
@@ -1239,7 +1305,7 @@
// If the request Id is wrong, don't stop the ongoing range request. Any
// other error should be treated as the end of rtt ranging.
if (status != WIFI_ERROR_INVALID_REQUEST_ID) {
- on_rtt_results_internal_callback = nullptr;
+ invalidateRttResultsCallbacks();
}
return status;
}
@@ -1298,6 +1364,12 @@
on_nan_event_tca_user_callback = user_callbacks.on_event_tca;
on_nan_event_beacon_sdf_payload_user_callback = user_callbacks.on_event_beacon_sdf_payload;
on_nan_event_data_path_request_user_callback = user_callbacks.on_event_data_path_request;
+ on_nan_event_pairing_request_user_callback = user_callbacks.on_event_pairing_request;
+ on_nan_event_pairing_confirm_user_callback = user_callbacks.on_event_pairing_confirm;
+ on_nan_event_bootstrapping_request_user_callback =
+ user_callbacks.on_event_bootstrapping_request;
+ on_nan_event_bootstrapping_confirm_user_callback =
+ user_callbacks.on_event_bootstrapping_confirm;
on_nan_event_data_path_confirm_user_callback = user_callbacks.on_event_data_path_confirm;
on_nan_event_data_path_end_user_callback = user_callbacks.on_event_data_path_end;
on_nan_event_transmit_follow_up_user_callback = user_callbacks.on_event_transmit_follow_up;
@@ -1305,16 +1377,29 @@
on_nan_event_range_report_user_callback = user_callbacks.on_event_range_report;
on_nan_event_schedule_update_user_callback = user_callbacks.on_event_schedule_update;
- return global_func_table_.wifi_nan_register_handler(
- getIfaceHandle(iface_name),
- {onAsyncNanNotifyResponse, onAsyncNanEventPublishReplied,
- onAsyncNanEventPublishTerminated, onAsyncNanEventMatch, onAsyncNanEventMatchExpired,
- onAsyncNanEventSubscribeTerminated, onAsyncNanEventFollowup,
- onAsyncNanEventDiscEngEvent, onAsyncNanEventDisabled, onAsyncNanEventTca,
- onAsyncNanEventBeaconSdfPayload, onAsyncNanEventDataPathRequest,
- onAsyncNanEventDataPathConfirm, onAsyncNanEventDataPathEnd,
- onAsyncNanEventTransmitFollowUp, onAsyncNanEventRangeRequest,
- onAsyncNanEventRangeReport, onAsyncNanEventScheduleUpdate});
+ return global_func_table_.wifi_nan_register_handler(getIfaceHandle(iface_name),
+ {onAsyncNanNotifyResponse,
+ onAsyncNanEventPublishReplied,
+ onAsyncNanEventPublishTerminated,
+ onAsyncNanEventMatch,
+ onAsyncNanEventMatchExpired,
+ onAsyncNanEventSubscribeTerminated,
+ onAsyncNanEventFollowup,
+ onAsyncNanEventDiscEngEvent,
+ onAsyncNanEventDisabled,
+ onAsyncNanEventTca,
+ onAsyncNanEventBeaconSdfPayload,
+ onAsyncNanEventDataPathRequest,
+ onAsyncNanEventDataPathConfirm,
+ onAsyncNanEventDataPathEnd,
+ onAsyncNanEventTransmitFollowUp,
+ onAsyncNanEventRangeRequest,
+ onAsyncNanEventRangeReport,
+ onAsyncNanEventScheduleUpdate,
+ onAsyncNanEventPairingRequest,
+ onAsyncNanEventPairingConfirm,
+ onAsyncNanEventBootstrappingRequest,
+ onAsyncNanEventBootstrappingConfirm});
}
wifi_error WifiLegacyHal::nanEnableRequest(const std::string& iface_name, transaction_id id,
@@ -1429,6 +1514,36 @@
&msg_internal);
}
+wifi_error WifiLegacyHal::nanPairingRequest(const std::string& iface_name, transaction_id id,
+ const NanPairingRequest& msg) {
+ NanPairingRequest msg_internal(msg);
+ return global_func_table_.wifi_nan_pairing_request(id, getIfaceHandle(iface_name),
+ &msg_internal);
+}
+
+wifi_error WifiLegacyHal::nanPairingIndicationResponse(const std::string& iface_name,
+ transaction_id id,
+ const NanPairingIndicationResponse& msg) {
+ NanPairingIndicationResponse msg_internal(msg);
+ return global_func_table_.wifi_nan_pairing_indication_response(id, getIfaceHandle(iface_name),
+ &msg_internal);
+}
+
+wifi_error WifiLegacyHal::nanBootstrappingRequest(const std::string& iface_name, transaction_id id,
+ const NanBootstrappingRequest& msg) {
+ NanBootstrappingRequest msg_internal(msg);
+ return global_func_table_.wifi_nan_bootstrapping_request(id, getIfaceHandle(iface_name),
+ &msg_internal);
+}
+
+wifi_error WifiLegacyHal::nanBootstrappingIndicationResponse(
+ const std::string& iface_name, transaction_id id,
+ const NanBootstrappingIndicationResponse& msg) {
+ NanBootstrappingIndicationResponse msg_internal(msg);
+ return global_func_table_.wifi_nan_bootstrapping_indication_response(
+ id, getIfaceHandle(iface_name), &msg_internal);
+}
+
typedef struct {
u8 num_ndp_instances;
NanDataPathId ndp_instance_id;
@@ -1734,7 +1849,7 @@
on_error_alert_internal_callback = nullptr;
on_radio_mode_change_internal_callback = nullptr;
on_subsystem_restart_internal_callback = nullptr;
- on_rtt_results_internal_callback = nullptr;
+ invalidateRttResultsCallbacks();
on_nan_notify_response_user_callback = nullptr;
on_nan_event_publish_terminated_user_callback = nullptr;
on_nan_event_match_user_callback = nullptr;
@@ -1746,6 +1861,10 @@
on_nan_event_tca_user_callback = nullptr;
on_nan_event_beacon_sdf_payload_user_callback = nullptr;
on_nan_event_data_path_request_user_callback = nullptr;
+ on_nan_event_pairing_request_user_callback = nullptr;
+ on_nan_event_pairing_confirm_user_callback = nullptr;
+ on_nan_event_bootstrapping_request_user_callback = nullptr;
+ on_nan_event_bootstrapping_confirm_user_callback = nullptr;
on_nan_event_data_path_confirm_user_callback = nullptr;
on_nan_event_data_path_end_user_callback = nullptr;
on_nan_event_transmit_follow_up_user_callback = nullptr;
diff --git a/wifi/aidl/default/wifi_legacy_hal.h b/wifi/aidl/default/wifi_legacy_hal.h
index c40118e..5620280 100644
--- a/wifi/aidl/default/wifi_legacy_hal.h
+++ b/wifi/aidl/default/wifi_legacy_hal.h
@@ -36,6 +36,7 @@
namespace legacy_hal {
// Import all the types defined inside the legacy HAL header files into this
// namespace.
+using ::Akm;
using ::chre_nan_rtt_state;
using ::frame_info;
using ::frame_type;
@@ -44,6 +45,8 @@
using ::FRAME_TYPE_UNKNOWN;
using ::fw_roaming_state_t;
using ::mac_addr;
+using ::NAN_BOOTSTRAPPING_INITIATOR_RESPONSE;
+using ::NAN_BOOTSTRAPPING_RESPONDER_RESPONSE;
using ::NAN_CHANNEL_24G_BAND;
using ::NAN_CHANNEL_5G_BAND_HIGH;
using ::NAN_CHANNEL_5G_BAND_LOW;
@@ -65,6 +68,10 @@
using ::NAN_MATCH_ALG_MATCH_CONTINUOUS;
using ::NAN_MATCH_ALG_MATCH_NEVER;
using ::NAN_MATCH_ALG_MATCH_ONCE;
+using ::NAN_PAIRING_INITIATOR_RESPONSE;
+using ::NAN_PAIRING_RESPONDER_RESPONSE;
+using ::NAN_PAIRING_SETUP;
+using ::NAN_PAIRING_VERIFICATION;
using ::NAN_PUBLISH_TYPE_SOLICITED;
using ::NAN_PUBLISH_TYPE_UNSOLICITED;
using ::NAN_PUBLISH_TYPE_UNSOLICITED_SOLICITED;
@@ -97,7 +104,9 @@
using ::NAN_STATUS_ALREADY_ENABLED;
using ::NAN_STATUS_FOLLOWUP_QUEUE_FULL;
using ::NAN_STATUS_INTERNAL_FAILURE;
+using ::NAN_STATUS_INVALID_BOOTSTRAPPING_ID;
using ::NAN_STATUS_INVALID_NDP_ID;
+using ::NAN_STATUS_INVALID_PAIRING_ID;
using ::NAN_STATUS_INVALID_PARAM;
using ::NAN_STATUS_INVALID_PUBLISH_SUBSCRIBE_ID;
using ::NAN_STATUS_INVALID_REQUESTOR_INSTANCE_ID;
@@ -117,6 +126,12 @@
using ::NAN_TX_TYPE_UNICAST;
using ::NAN_USE_SRF;
using ::NanBeaconSdfPayloadInd;
+using ::NanBootstrappingConfirmInd;
+using ::NanBootstrappingIndicationResponse;
+using ::NanBootstrappingRequest;
+using ::NanBootstrappingRequestInd;
+using ::NanBootstrappingRequestResponse;
+using ::NanBootstrappingResponseCode;
using ::NanCapabilities;
using ::NanChannelInfo;
using ::NanConfigRequest;
@@ -131,9 +146,18 @@
using ::NanDiscEngEventInd;
using ::NanEnableRequest;
using ::NanFollowupInd;
+using ::NanIdentityResolutionAttribute;
using ::NanMatchAlg;
using ::NanMatchExpiredInd;
using ::NanMatchInd;
+using ::NanPairingConfig;
+using ::NanPairingConfirmInd;
+using ::NanPairingIndicationResponse;
+using ::NanPairingRequest;
+using ::NanPairingRequestInd;
+using ::NanPairingRequestResponse;
+using ::NanPairingRequestType;
+using ::NanPairingResponseCode;
using ::NanPublishCancelRequest;
using ::NanPublishRequest;
using ::NanPublishTerminatedInd;
@@ -150,6 +174,8 @@
using ::NanTransmitFollowupInd;
using ::NanTransmitFollowupRequest;
using ::NanTxType;
+using ::NpkSecurityAssociation;
+using ::PASN;
using ::ROAMING_DISABLE;
using ::ROAMING_ENABLE;
using ::RTT_PEER_AP;
@@ -189,6 +215,7 @@
using ::RX_PKT_FATE_FW_DROP_OTHER;
using ::RX_PKT_FATE_FW_QUEUED;
using ::RX_PKT_FATE_SUCCESS;
+using ::SAE;
using ::ssid_t;
using ::transaction_id;
using ::TX_PKT_FATE_ACKED;
@@ -305,6 +332,7 @@
using ::WIFI_RTT_BW_40;
using ::WIFI_RTT_BW_5;
using ::WIFI_RTT_BW_80;
+using ::WIFI_RTT_BW_UNSPECIFIED;
using ::wifi_rtt_capabilities;
using ::wifi_rtt_config;
using ::wifi_rtt_preamble;
@@ -315,6 +343,7 @@
using ::WIFI_RTT_PREAMBLE_VHT;
using ::wifi_rtt_responder;
using ::wifi_rtt_result;
+using ::wifi_rtt_result_v2;
using ::wifi_rtt_status;
using ::wifi_rtt_type;
using ::wifi_rx_packet_fate;
@@ -412,6 +441,10 @@
std::function<void(const NanRangeRequestInd&)> on_event_range_request;
std::function<void(const NanRangeReportInd&)> on_event_range_report;
std::function<void(const NanDataPathScheduleUpdateInd&)> on_event_schedule_update;
+ std::function<void(const NanPairingRequestInd&)> on_event_pairing_request;
+ std::function<void(const NanPairingConfirmInd&)> on_event_pairing_confirm;
+ std::function<void(const NanBootstrappingRequestInd&)> on_event_bootstrapping_request;
+ std::function<void(const NanBootstrappingConfirmInd&)> on_event_bootstrapping_confirm;
};
// Full scan results contain IE info and are hence passed by reference, to
@@ -434,6 +467,8 @@
// the pointer.
using on_rtt_results_callback =
std::function<void(wifi_request_id, const std::vector<const wifi_rtt_result*>&)>;
+using on_rtt_results_callback_v2 =
+ std::function<void(wifi_request_id, const std::vector<const wifi_rtt_result_v2*>&)>;
// Callback for ring buffer data.
using on_ring_buffer_data_callback = std::function<void(
@@ -606,7 +641,8 @@
// RTT functions.
wifi_error startRttRangeRequest(const std::string& iface_name, wifi_request_id id,
const std::vector<wifi_rtt_config>& rtt_configs,
- const on_rtt_results_callback& on_results_callback);
+ const on_rtt_results_callback& on_results_callback,
+ const on_rtt_results_callback_v2& on_results_callback_v2);
wifi_error cancelRttRangeRequest(const std::string& iface_name, wifi_request_id id,
const std::vector<std::array<uint8_t, ETH_ALEN>>& mac_addrs);
std::pair<wifi_error, wifi_rtt_capabilities> getRttCapabilities(const std::string& iface_name);
@@ -653,6 +689,14 @@
const NanDataPathInitiatorRequest& msg);
wifi_error nanDataIndicationResponse(const std::string& iface_name, transaction_id id,
const NanDataPathIndicationResponse& msg);
+ wifi_error nanPairingRequest(const std::string& iface_name, transaction_id id,
+ const NanPairingRequest& msg);
+ wifi_error nanPairingIndicationResponse(const std::string& iface_name, transaction_id id,
+ const NanPairingIndicationResponse& msg);
+ wifi_error nanBootstrappingRequest(const std::string& iface_name, transaction_id id,
+ const NanBootstrappingRequest& msg);
+ wifi_error nanBootstrappingIndicationResponse(const std::string& iface_name, transaction_id id,
+ const NanBootstrappingIndicationResponse& msg);
wifi_error nanDataEnd(const std::string& iface_name, transaction_id id, uint32_t ndpInstanceId);
// AP functions.
wifi_error setCountryCode(const std::string& iface_name, const std::array<uint8_t, 2> code);
diff --git a/wifi/aidl/default/wifi_legacy_hal_stubs.cpp b/wifi/aidl/default/wifi_legacy_hal_stubs.cpp
index 7777894..a0cb2c0 100644
--- a/wifi/aidl/default/wifi_legacy_hal_stubs.cpp
+++ b/wifi/aidl/default/wifi_legacy_hal_stubs.cpp
@@ -126,6 +126,10 @@
populateStubFor(&hal_fn->wifi_nan_data_interface_delete);
populateStubFor(&hal_fn->wifi_nan_data_request_initiator);
populateStubFor(&hal_fn->wifi_nan_data_indication_response);
+ populateStubFor(&hal_fn->wifi_nan_pairing_request);
+ populateStubFor(&hal_fn->wifi_nan_pairing_indication_response);
+ populateStubFor(&hal_fn->wifi_nan_bootstrapping_request);
+ populateStubFor(&hal_fn->wifi_nan_bootstrapping_indication_response);
populateStubFor(&hal_fn->wifi_nan_data_end);
populateStubFor(&hal_fn->wifi_get_packet_filter_capabilities);
populateStubFor(&hal_fn->wifi_set_packet_filter);
diff --git a/wifi/aidl/default/wifi_nan_iface.cpp b/wifi/aidl/default/wifi_nan_iface.cpp
index 9edef09..ce6902d 100644
--- a/wifi/aidl/default/wifi_nan_iface.cpp
+++ b/wifi/aidl/default/wifi_nan_iface.cpp
@@ -205,6 +205,46 @@
}
break;
}
+ case legacy_hal::NAN_PAIRING_INITIATOR_RESPONSE: {
+ for (const auto& callback : shared_ptr_this->getEventCallbacks()) {
+ if (!callback->notifyInitiatePairingResponse(
+ id, nanStatus,
+ msg.body.pairing_request_response.paring_instance_id)
+ .isOk()) {
+ LOG(ERROR) << "Failed to invoke the callback";
+ }
+ }
+ break;
+ }
+ case legacy_hal::NAN_PAIRING_RESPONDER_RESPONSE: {
+ for (const auto& callback : shared_ptr_this->getEventCallbacks()) {
+ if (!callback->notifyRespondToPairingIndicationResponse(id, nanStatus).isOk()) {
+ LOG(ERROR) << "Failed to invoke the callback";
+ }
+ }
+ break;
+ }
+ case legacy_hal::NAN_BOOTSTRAPPING_INITIATOR_RESPONSE: {
+ for (const auto& callback : shared_ptr_this->getEventCallbacks()) {
+ if (!callback->notifyInitiateBootstrappingResponse(
+ id, nanStatus,
+ msg.body.bootstrapping_request_response
+ .bootstrapping_instance_id)
+ .isOk()) {
+ LOG(ERROR) << "Failed to invoke the callback";
+ }
+ }
+ break;
+ }
+ case legacy_hal::NAN_BOOTSTRAPPING_RESPONDER_RESPONSE: {
+ for (const auto& callback : shared_ptr_this->getEventCallbacks()) {
+ if (!callback->notifyRespondToBootstrappingIndicationResponse(id, nanStatus)
+ .isOk()) {
+ LOG(ERROR) << "Failed to invoke the callback";
+ }
+ }
+ break;
+ }
case legacy_hal::NAN_RESPONSE_BEACON_SDF_PAYLOAD:
/* fall through */
case legacy_hal::NAN_RESPONSE_TCA:
@@ -421,6 +461,85 @@
}
};
+ callback_handlers.on_event_pairing_request =
+ [weak_ptr_this](const legacy_hal::NanPairingRequestInd& msg) {
+ const auto shared_ptr_this = weak_ptr_this.lock();
+ if (!shared_ptr_this.get() || !shared_ptr_this->isValid()) {
+ LOG(ERROR) << "Callback invoked on an invalid object";
+ return;
+ }
+ NanPairingRequestInd aidl_struct;
+ if (!aidl_struct_util::convertLegacyNanPairingRequestIndToAidl(msg, &aidl_struct)) {
+ LOG(ERROR) << "Failed to convert nan capabilities response";
+ return;
+ }
+
+ for (const auto& callback : shared_ptr_this->getEventCallbacks()) {
+ if (!callback->eventPairingRequest(aidl_struct).isOk()) {
+ LOG(ERROR) << "Failed to invoke the callback";
+ }
+ }
+ };
+ callback_handlers.on_event_pairing_confirm =
+ [weak_ptr_this](const legacy_hal::NanPairingConfirmInd& msg) {
+ const auto shared_ptr_this = weak_ptr_this.lock();
+ if (!shared_ptr_this.get() || !shared_ptr_this->isValid()) {
+ LOG(ERROR) << "Callback invoked on an invalid object";
+ return;
+ }
+ NanPairingConfirmInd aidl_struct;
+ if (!aidl_struct_util::convertLegacyNanPairingConfirmIndToAidl(msg, &aidl_struct)) {
+ LOG(ERROR) << "Failed to convert nan capabilities response";
+ return;
+ }
+
+ for (const auto& callback : shared_ptr_this->getEventCallbacks()) {
+ if (!callback->eventPairingConfirm(aidl_struct).isOk()) {
+ LOG(ERROR) << "Failed to invoke the callback";
+ }
+ }
+ };
+ callback_handlers.on_event_bootstrapping_request =
+ [weak_ptr_this](const legacy_hal::NanBootstrappingRequestInd& msg) {
+ const auto shared_ptr_this = weak_ptr_this.lock();
+ if (!shared_ptr_this.get() || !shared_ptr_this->isValid()) {
+ LOG(ERROR) << "Callback invoked on an invalid object";
+ return;
+ }
+ NanBootstrappingRequestInd aidl_struct;
+ if (!aidl_struct_util::convertLegacyNanBootstrappingRequestIndToAidl(
+ msg, &aidl_struct)) {
+ LOG(ERROR) << "Failed to convert nan capabilities response";
+ return;
+ }
+
+ for (const auto& callback : shared_ptr_this->getEventCallbacks()) {
+ if (!callback->eventBootstrappingRequest(aidl_struct).isOk()) {
+ LOG(ERROR) << "Failed to invoke the callback";
+ }
+ }
+ };
+ callback_handlers.on_event_bootstrapping_confirm =
+ [weak_ptr_this](const legacy_hal::NanBootstrappingConfirmInd& msg) {
+ const auto shared_ptr_this = weak_ptr_this.lock();
+ if (!shared_ptr_this.get() || !shared_ptr_this->isValid()) {
+ LOG(ERROR) << "Callback invoked on an invalid object";
+ return;
+ }
+ NanBootstrappingConfirmInd aidl_struct;
+ if (!aidl_struct_util::convertLegacyNanBootstrappingConfirmIndToAidl(
+ msg, &aidl_struct)) {
+ LOG(ERROR) << "Failed to convert nan capabilities response";
+ return;
+ }
+
+ for (const auto& callback : shared_ptr_this->getEventCallbacks()) {
+ if (!callback->eventBootstrappingConfirm(aidl_struct).isOk()) {
+ LOG(ERROR) << "Failed to invoke the callback";
+ }
+ }
+ };
+
callback_handlers.on_event_beacon_sdf_payload =
[](const legacy_hal::NanBeaconSdfPayloadInd& /* msg */) {
LOG(ERROR) << "on_event_beacon_sdf_payload - should not be called";
@@ -611,6 +730,32 @@
in_ndpInstanceId);
}
+ndk::ScopedAStatus WifiNanIface::initiatePairingRequest(char16_t in_cmdId,
+ const NanPairingRequest& in_msg) {
+ return validateAndCall(this, WifiStatusCode::ERROR_WIFI_IFACE_INVALID,
+ &WifiNanIface::initiatePairingRequestInternal, in_cmdId, in_msg);
+}
+
+ndk::ScopedAStatus WifiNanIface::respondToPairingIndicationRequest(
+ char16_t in_cmdId, const NanRespondToPairingIndicationRequest& in_msg) {
+ return validateAndCall(this, WifiStatusCode::ERROR_WIFI_IFACE_INVALID,
+ &WifiNanIface::respondToPairingIndicationRequestInternal, in_cmdId,
+ in_msg);
+}
+
+ndk::ScopedAStatus WifiNanIface::initiateBootstrappingRequest(
+ char16_t in_cmdId, const NanBootstrappingRequest& in_msg) {
+ return validateAndCall(this, WifiStatusCode::ERROR_WIFI_IFACE_INVALID,
+ &WifiNanIface::initiateBootstrappingRequestInternal, in_cmdId, in_msg);
+}
+
+ndk::ScopedAStatus WifiNanIface::respondToBootstrappingIndicationRequest(
+ char16_t in_cmdId, const NanBootstrappingResponse& in_msg) {
+ return validateAndCall(this, WifiStatusCode::ERROR_WIFI_IFACE_INVALID,
+ &WifiNanIface::respondToBootstrappingIndicationRequestInternal, in_cmdId,
+ in_msg);
+}
+
std::pair<std::string, ndk::ScopedAStatus> WifiNanIface::getNameInternal() {
return {ifname_, ndk::ScopedAStatus::ok()};
}
@@ -744,6 +889,47 @@
legacy_hal_.lock()->nanDataEnd(ifname_, cmd_id, ndpInstanceId);
return createWifiStatusFromLegacyError(legacy_status);
}
+ndk::ScopedAStatus WifiNanIface::initiatePairingRequestInternal(char16_t cmd_id,
+ const NanPairingRequest& msg) {
+ legacy_hal::NanPairingRequest legacy_msg;
+ if (!aidl_struct_util::convertAidlNanPairingInitiatorRequestToLegacy(msg, &legacy_msg)) {
+ return createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS);
+ }
+ legacy_hal::wifi_error legacy_status =
+ legacy_hal_.lock()->nanPairingRequest(ifname_, cmd_id, legacy_msg);
+ return createWifiStatusFromLegacyError(legacy_status);
+}
+ndk::ScopedAStatus WifiNanIface::respondToPairingIndicationRequestInternal(
+ char16_t cmd_id, const NanRespondToPairingIndicationRequest& msg) {
+ legacy_hal::NanPairingIndicationResponse legacy_msg;
+ if (!aidl_struct_util::convertAidlNanPairingIndicationResponseToLegacy(msg, &legacy_msg)) {
+ return createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS);
+ }
+ legacy_hal::wifi_error legacy_status =
+ legacy_hal_.lock()->nanPairingIndicationResponse(ifname_, cmd_id, legacy_msg);
+ return createWifiStatusFromLegacyError(legacy_status);
+}
+ndk::ScopedAStatus WifiNanIface::initiateBootstrappingRequestInternal(
+ char16_t cmd_id, const NanBootstrappingRequest& msg) {
+ legacy_hal::NanBootstrappingRequest legacy_msg;
+ if (!aidl_struct_util::convertAidlNanBootstrappingInitiatorRequestToLegacy(msg, &legacy_msg)) {
+ return createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS);
+ }
+ legacy_hal::wifi_error legacy_status =
+ legacy_hal_.lock()->nanBootstrappingRequest(ifname_, cmd_id, legacy_msg);
+ return createWifiStatusFromLegacyError(legacy_status);
+}
+ndk::ScopedAStatus WifiNanIface::respondToBootstrappingIndicationRequestInternal(
+ char16_t cmd_id, const NanBootstrappingResponse& msg) {
+ legacy_hal::NanBootstrappingIndicationResponse legacy_msg;
+ if (!aidl_struct_util::convertAidlNanBootstrappingIndicationResponseToLegacy(msg,
+ &legacy_msg)) {
+ return createWifiStatus(WifiStatusCode::ERROR_INVALID_ARGS);
+ }
+ legacy_hal::wifi_error legacy_status =
+ legacy_hal_.lock()->nanBootstrappingIndicationResponse(ifname_, cmd_id, legacy_msg);
+ return createWifiStatusFromLegacyError(legacy_status);
+}
} // namespace wifi
} // namespace hardware
diff --git a/wifi/aidl/default/wifi_nan_iface.h b/wifi/aidl/default/wifi_nan_iface.h
index 1018905..591eca9 100644
--- a/wifi/aidl/default/wifi_nan_iface.h
+++ b/wifi/aidl/default/wifi_nan_iface.h
@@ -78,6 +78,14 @@
char16_t in_cmdId, const NanRespondToDataPathIndicationRequest& in_msg) override;
ndk::ScopedAStatus terminateDataPathRequest(char16_t in_cmdId,
int32_t in_ndpInstanceId) override;
+ ndk::ScopedAStatus initiatePairingRequest(char16_t in_cmdId,
+ const NanPairingRequest& in_msg) override;
+ ndk::ScopedAStatus respondToPairingIndicationRequest(
+ char16_t in_cmdId, const NanRespondToPairingIndicationRequest& in_msg) override;
+ ndk::ScopedAStatus initiateBootstrappingRequest(char16_t in_cmdId,
+ const NanBootstrappingRequest& in_msg) override;
+ ndk::ScopedAStatus respondToBootstrappingIndicationRequest(
+ char16_t in_cmdId, const NanBootstrappingResponse& in_msg) override;
protected:
// Accessible to child class in the gTest suite.
@@ -111,6 +119,14 @@
ndk::ScopedAStatus respondToDataPathIndicationRequestInternal(
char16_t cmd_id, const NanRespondToDataPathIndicationRequest& msg);
ndk::ScopedAStatus terminateDataPathRequestInternal(char16_t cmd_id, int32_t ndpInstanceId);
+ ndk::ScopedAStatus initiatePairingRequestInternal(char16_t cmd_id,
+ const NanPairingRequest& msg);
+ ndk::ScopedAStatus respondToPairingIndicationRequestInternal(
+ char16_t cmd_id, const NanRespondToPairingIndicationRequest& msg);
+ ndk::ScopedAStatus initiateBootstrappingRequestInternal(char16_t cmd_id,
+ const NanBootstrappingRequest& msg);
+ ndk::ScopedAStatus respondToBootstrappingIndicationRequestInternal(
+ char16_t cmd_id, const NanBootstrappingResponse& msg);
// Overridden in the gTest suite.
virtual std::set<std::shared_ptr<IWifiNanIfaceEventCallback>> getEventCallbacks();
diff --git a/wifi/aidl/default/wifi_rtt_controller.cpp b/wifi/aidl/default/wifi_rtt_controller.cpp
index 856c3cd..a5f6768 100644
--- a/wifi/aidl/default/wifi_rtt_controller.cpp
+++ b/wifi/aidl/default/wifi_rtt_controller.cpp
@@ -161,8 +161,28 @@
}
}
};
+ const auto& on_results_callback_v2 =
+ [weak_ptr_this](legacy_hal::wifi_request_id id,
+ const std::vector<const legacy_hal::wifi_rtt_result_v2*>& results) {
+ const auto shared_ptr_this = weak_ptr_this.lock();
+ if (!shared_ptr_this.get() || !shared_ptr_this->isValid()) {
+ LOG(ERROR) << "v2 Callback invoked on an invalid object";
+ return;
+ }
+ std::vector<RttResult> aidl_results;
+ if (!aidl_struct_util::convertLegacyVectorOfRttResultV2ToAidl(results,
+ &aidl_results)) {
+ LOG(ERROR) << "Failed to convert rtt results v2 to AIDL structs";
+ return;
+ }
+ for (const auto& callback : shared_ptr_this->getEventCallbacks()) {
+ if (!callback->onResults(id, aidl_results).isOk()) {
+ LOG(ERROR) << "Failed to invoke the v2 callback";
+ }
+ }
+ };
legacy_hal::wifi_error legacy_status = legacy_hal_.lock()->startRttRangeRequest(
- ifname_, cmd_id, legacy_configs, on_results_callback);
+ ifname_, cmd_id, legacy_configs, on_results_callback, on_results_callback_v2);
return createWifiStatusFromLegacyError(legacy_status);
}
diff --git a/wifi/aidl/vts/functional/wifi_nan_iface_aidl_test.cpp b/wifi/aidl/vts/functional/wifi_nan_iface_aidl_test.cpp
index 457d57a..654eb02 100644
--- a/wifi/aidl/vts/functional/wifi_nan_iface_aidl_test.cpp
+++ b/wifi/aidl/vts/functional/wifi_nan_iface_aidl_test.cpp
@@ -33,6 +33,8 @@
using aidl::android::hardware::wifi::IWifiNanIface;
using aidl::android::hardware::wifi::NanBandIndex;
using aidl::android::hardware::wifi::NanBandSpecificConfig;
+using aidl::android::hardware::wifi::NanBootstrappingConfirmInd;
+using aidl::android::hardware::wifi::NanBootstrappingRequestInd;
using aidl::android::hardware::wifi::NanCapabilities;
using aidl::android::hardware::wifi::NanClusterEventInd;
using aidl::android::hardware::wifi::NanConfigRequest;
@@ -46,6 +48,8 @@
using aidl::android::hardware::wifi::NanInitiateDataPathRequest;
using aidl::android::hardware::wifi::NanMatchAlg;
using aidl::android::hardware::wifi::NanMatchInd;
+using aidl::android::hardware::wifi::NanPairingConfirmInd;
+using aidl::android::hardware::wifi::NanPairingRequestInd;
using aidl::android::hardware::wifi::NanPublishRequest;
using aidl::android::hardware::wifi::NanPublishType;
using aidl::android::hardware::wifi::NanRespondToDataPathIndicationRequest;
@@ -96,6 +100,10 @@
NOTIFY_INITIATE_DATA_PATH_RESPONSE,
NOTIFY_RESPOND_TO_DATA_PATH_INDICATION_RESPONSE,
NOTIFY_TERMINATE_DATA_PATH_RESPONSE,
+ NOTIFY_INITIATE_PAIRING_RESPONSE,
+ NOTIFY_RESPOND_TO_PAIRING_INDICATION_RESPONSE,
+ NOTIFY_INITIATE_BOOTSTRAPPING_RESPONSE,
+ NOTIFY_RESPOND_TO_BOOTSTRAPPING_INDICATION_RESPONSE,
EVENT_CLUSTER_EVENT,
EVENT_DISABLED,
@@ -109,6 +117,10 @@
EVENT_DATA_PATH_CONFIRM,
EVENT_DATA_PATH_TERMINATED,
EVENT_DATA_PATH_SCHEDULE_UPDATE,
+ EVENT_PAIRING_REQUEST,
+ EVENT_PAIRING_CONFIRM,
+ EVENT_BOOTSTRAPPING_REQUEST,
+ EVENT_BOOTSTRAPPING_CONFIRM,
};
// Test code calls this function to wait for data/event callback.
@@ -214,6 +226,32 @@
parent_.notify();
return ndk::ScopedAStatus::ok();
}
+ ::ndk::ScopedAStatus eventPairingConfirm(const NanPairingConfirmInd& event) override {
+ parent_.callback_type_ = EVENT_PAIRING_CONFIRM;
+ parent_.nan_pairing_confirm_ind_ = event;
+ parent_.notify();
+ return ndk::ScopedAStatus::ok();
+ }
+ ::ndk::ScopedAStatus eventPairingRequest(const NanPairingRequestInd& event) override {
+ parent_.callback_type_ = EVENT_PAIRING_REQUEST;
+ parent_.nan_pairing_request_ind_ = event;
+ parent_.notify();
+ return ndk::ScopedAStatus::ok();
+ }
+ ::ndk::ScopedAStatus eventBootstrappingConfirm(
+ const NanBootstrappingConfirmInd& event) override {
+ parent_.callback_type_ = EVENT_BOOTSTRAPPING_CONFIRM;
+ parent_.nan_bootstrapping_confirm_ind_ = event;
+ parent_.notify();
+ return ndk::ScopedAStatus::ok();
+ }
+ ::ndk::ScopedAStatus eventBootstrappingRequest(
+ const NanBootstrappingRequestInd& event) override {
+ parent_.callback_type_ = EVENT_BOOTSTRAPPING_REQUEST;
+ parent_.nan_bootstrapping_request_ind_ = event;
+ parent_.notify();
+ return ndk::ScopedAStatus::ok();
+ }
::ndk::ScopedAStatus notifyCapabilitiesResponse(
char16_t id, const NanStatus& status,
const NanCapabilities& capabilities) override {
@@ -328,6 +366,40 @@
parent_.notify();
return ndk::ScopedAStatus::ok();
}
+ ::ndk::ScopedAStatus notifyInitiatePairingResponse(char16_t id, const NanStatus& status,
+ int32_t pairingInstanceId) override {
+ parent_.callback_type_ = NOTIFY_INITIATE_PAIRING_RESPONSE;
+ parent_.id_ = id;
+ parent_.status_ = status;
+ parent_.pairing_instance_id_ = pairingInstanceId;
+ parent_.notify();
+ return ndk::ScopedAStatus::ok();
+ }
+ ::ndk::ScopedAStatus notifyRespondToPairingIndicationResponse(
+ char16_t id, const NanStatus& status) override {
+ parent_.callback_type_ = NOTIFY_RESPOND_TO_PAIRING_INDICATION_RESPONSE;
+ parent_.id_ = id;
+ parent_.status_ = status;
+ parent_.notify();
+ return ndk::ScopedAStatus::ok();
+ }
+ ::ndk::ScopedAStatus notifyInitiateBootstrappingResponse(
+ char16_t id, const NanStatus& status, int32_t bootstrapppingInstanceId) override {
+ parent_.callback_type_ = NOTIFY_INITIATE_BOOTSTRAPPING_RESPONSE;
+ parent_.id_ = id;
+ parent_.status_ = status;
+ parent_.bootstrappping_instance_id_ = bootstrapppingInstanceId;
+ parent_.notify();
+ return ndk::ScopedAStatus::ok();
+ }
+ ::ndk::ScopedAStatus notifyRespondToBootstrappingIndicationResponse(
+ char16_t id, const NanStatus& status) override {
+ parent_.callback_type_ = NOTIFY_RESPOND_TO_BOOTSTRAPPING_INDICATION_RESPONSE;
+ parent_.id_ = id;
+ parent_.status_ = status;
+ parent_.notify();
+ return ndk::ScopedAStatus::ok();
+ }
private:
WifiNanIfaceAidlTest& parent_;
@@ -339,6 +411,8 @@
uint16_t id_;
uint8_t session_id_;
uint32_t ndp_instance_id_;
+ uint32_t pairing_instance_id_;
+ uint32_t bootstrappping_instance_id_;
uint32_t peer_id_;
NanCapabilities capabilities_;
NanClusterEventInd nan_cluster_event_ind_;
@@ -348,6 +422,10 @@
NanFollowupReceivedInd nan_followup_received_ind_;
NanMatchInd nan_match_ind_;
NanStatus status_;
+ NanPairingRequestInd nan_pairing_request_ind_;
+ NanPairingConfirmInd nan_pairing_confirm_ind_;
+ NanBootstrappingRequestInd nan_bootstrapping_request_ind_;
+ NanBootstrappingConfirmInd nan_bootstrapping_confirm_ind_;
const char* getInstanceName() { return GetParam().c_str(); }