1 /*
2 * Copyright (C) 2019 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16 #include <aidl/Gtest.h>
17 #include <aidl/Vintf.h>
18 #include <aidl/android/hardware/vibrator/BnVibratorCallback.h>
19 #include <aidl/android/hardware/vibrator/IVibrator.h>
20 #include <aidl/android/hardware/vibrator/IVibratorManager.h>
21
22 #include <android/binder_manager.h>
23 #include <android/binder_process.h>
24 #include <android/persistable_bundle_aidl.h>
25
26 #include <cmath>
27 #include <cstdlib>
28 #include <ctime>
29 #include <future>
30 #include <iomanip>
31 #include <iostream>
32 #include <random>
33
34 #include "persistable_bundle_utils.h"
35 #include "pwle_v2_utils.h"
36 #include "test_utils.h"
37
38 using aidl::android::hardware::vibrator::ActivePwle;
39 using aidl::android::hardware::vibrator::BnVibratorCallback;
40 using aidl::android::hardware::vibrator::Braking;
41 using aidl::android::hardware::vibrator::BrakingPwle;
42 using aidl::android::hardware::vibrator::CompositeEffect;
43 using aidl::android::hardware::vibrator::CompositePrimitive;
44 using aidl::android::hardware::vibrator::CompositePwleV2;
45 using aidl::android::hardware::vibrator::Effect;
46 using aidl::android::hardware::vibrator::EffectStrength;
47 using aidl::android::hardware::vibrator::FrequencyAccelerationMapEntry;
48 using aidl::android::hardware::vibrator::IVibrator;
49 using aidl::android::hardware::vibrator::IVibratorManager;
50 using aidl::android::hardware::vibrator::PrimitivePwle;
51 using aidl::android::hardware::vibrator::PwleV2Primitive;
52 using aidl::android::hardware::vibrator::VendorEffect;
53 using aidl::android::os::PersistableBundle;
54 using std::chrono::high_resolution_clock;
55
56 using namespace ::std::chrono_literals;
57
58 namespace pwle_v2_utils = aidl::android::hardware::vibrator::testing::pwlev2;
59
60 const std::vector<Effect> kEffects{ndk::enum_range<Effect>().begin(),
61 ndk::enum_range<Effect>().end()};
62 const std::vector<EffectStrength> kEffectStrengths{ndk::enum_range<EffectStrength>().begin(),
63 ndk::enum_range<EffectStrength>().end()};
64
65 const std::vector<Effect> kInvalidEffects = {
66 static_cast<Effect>(static_cast<int32_t>(kEffects.front()) - 1),
67 static_cast<Effect>(static_cast<int32_t>(kEffects.back()) + 1),
68 };
69
70 const std::vector<EffectStrength> kInvalidEffectStrengths = {
71 static_cast<EffectStrength>(static_cast<int8_t>(kEffectStrengths.front()) - 1),
72 static_cast<EffectStrength>(static_cast<int8_t>(kEffectStrengths.back()) + 1),
73 };
74
75 const std::vector<CompositePrimitive> kCompositePrimitives{
76 ndk::enum_range<CompositePrimitive>().begin(), ndk::enum_range<CompositePrimitive>().end()};
77
78 const std::vector<CompositePrimitive> kRequiredPrimitives = {
79 CompositePrimitive::CLICK, CompositePrimitive::LIGHT_TICK,
80 CompositePrimitive::QUICK_RISE, CompositePrimitive::SLOW_RISE,
81 CompositePrimitive::QUICK_FALL,
82 };
83
84 const std::vector<CompositePrimitive> kInvalidPrimitives = {
85 static_cast<CompositePrimitive>(static_cast<int32_t>(kCompositePrimitives.front()) - 1),
86 static_cast<CompositePrimitive>(static_cast<int32_t>(kCompositePrimitives.back()) + 1),
87 };
88
89 // Timeout to wait for vibration callback completion.
90 static constexpr std::chrono::milliseconds VIBRATION_CALLBACK_TIMEOUT = 100ms;
91
92 static constexpr int32_t VENDOR_EFFECTS_MIN_VERSION = 3;
93 static constexpr int32_t PWLE_V2_MIN_VERSION = 3;
94
findVibratorManagerNames()95 static std::vector<std::string> findVibratorManagerNames() {
96 std::vector<std::string> names;
97 constexpr auto callback = [](const char* instance, void* context) {
98 auto fullName = std::string(IVibratorManager::descriptor) + "/" + instance;
99 static_cast<std::vector<std::string>*>(context)->emplace_back(fullName);
100 };
101 AServiceManager_forEachDeclaredInstance(IVibratorManager::descriptor,
102 static_cast<void*>(&names), callback);
103 return names;
104 }
105
findUnmanagedVibratorNames()106 static std::vector<std::string> findUnmanagedVibratorNames() {
107 std::vector<std::string> names;
108 constexpr auto callback = [](const char* instance, void* context) {
109 auto fullName = std::string(IVibrator::descriptor) + "/" + instance;
110 static_cast<std::vector<std::string>*>(context)->emplace_back(fullName);
111 };
112 AServiceManager_forEachDeclaredInstance(IVibrator::descriptor, static_cast<void*>(&names),
113 callback);
114 return names;
115 }
116
117 class CompletionCallback : public BnVibratorCallback {
118 public:
CompletionCallback(const std::function<void ()> & callback)119 CompletionCallback(const std::function<void()> &callback) : mCallback(callback) {}
onComplete()120 ndk::ScopedAStatus onComplete() override {
121 mCallback();
122 return ndk::ScopedAStatus::ok();
123 }
124
125 private:
126 std::function<void()> mCallback;
127 };
128
129 class VibratorAidl : public testing::TestWithParam<std::tuple<int32_t, int32_t>> {
130 public:
SetUp()131 virtual void SetUp() override {
132 int32_t managerIdx = std::get<0>(GetParam());
133 int32_t vibratorId = std::get<1>(GetParam());
134
135 if (managerIdx < 0) {
136 // Testing a unmanaged vibrator, using vibratorId as index from registered HALs
137 std::vector<std::string> vibratorNames = findUnmanagedVibratorNames();
138 ASSERT_LT(vibratorId, vibratorNames.size());
139 vibrator = IVibrator::fromBinder(ndk::SpAIBinder(
140 AServiceManager_waitForService(vibratorNames[vibratorId].c_str())));
141 } else {
142 // Testing a managed vibrator, using vibratorId to retrieve it from the manager
143 std::vector<std::string> managerNames = findVibratorManagerNames();
144 ASSERT_LT(managerIdx, managerNames.size());
145 auto vibratorManager = IVibratorManager::fromBinder(ndk::SpAIBinder(
146 AServiceManager_waitForService(managerNames[managerIdx].c_str())));
147 EXPECT_OK(vibratorManager->getVibrator(vibratorId, &vibrator))
148 << "\n For vibrator id: " << vibratorId;
149 }
150
151 ASSERT_NE(vibrator, nullptr);
152 EXPECT_OK(vibrator->getInterfaceVersion(&version));
153 EXPECT_OK(vibrator->getCapabilities(&capabilities));
154 }
155
TearDown()156 virtual void TearDown() override {
157 // Reset vibrator state between tests.
158 EXPECT_OK(vibrator->off());
159 }
160
161 std::shared_ptr<IVibrator> vibrator;
162 int32_t version;
163 int32_t capabilities;
164 };
165
getResonantFrequencyHz(const std::shared_ptr<IVibrator> & vibrator,int32_t capabilities)166 static float getResonantFrequencyHz(const std::shared_ptr<IVibrator>& vibrator,
167 int32_t capabilities) {
168 float resonantFrequencyHz;
169 ndk::ScopedAStatus status = vibrator->getResonantFrequency(&resonantFrequencyHz);
170 if (capabilities & IVibrator::CAP_GET_RESONANT_FREQUENCY) {
171 EXPECT_OK(std::move(status));
172 EXPECT_GT(resonantFrequencyHz, 0);
173 } else {
174 EXPECT_UNKNOWN_OR_UNSUPPORTED(std::move(status));
175 }
176 return resonantFrequencyHz;
177 }
178
shouldValidateLegacyFrequencyControlResult(int32_t capabilities,int32_t version,ndk::ScopedAStatus & status)179 static bool shouldValidateLegacyFrequencyControlResult(int32_t capabilities, int32_t version,
180 ndk::ScopedAStatus& status) {
181 bool hasFrequencyControl = capabilities & IVibrator::CAP_FREQUENCY_CONTROL;
182 // Legacy frequency control APIs deprecated with PWLE V2 feature.
183 bool isDeprecated = version >= PWLE_V2_MIN_VERSION;
184 bool isUnknownOrUnsupported = status.getExceptionCode() == EX_UNSUPPORTED_OPERATION ||
185 status.getStatus() == STATUS_UNKNOWN_TRANSACTION;
186
187 // Validate if older HAL or if result is provided, even after deprecation.
188 return hasFrequencyControl && (!isDeprecated || !isUnknownOrUnsupported);
189 }
190
getFrequencyResolutionHz(const std::shared_ptr<IVibrator> & vibrator,int32_t capabilities,int32_t version)191 static float getFrequencyResolutionHz(const std::shared_ptr<IVibrator>& vibrator,
192 int32_t capabilities, int32_t version) {
193 float freqResolutionHz = -1;
194 ndk::ScopedAStatus status = vibrator->getFrequencyResolution(&freqResolutionHz);
195 if (shouldValidateLegacyFrequencyControlResult(capabilities, version, status)) {
196 EXPECT_OK(std::move(status));
197 EXPECT_GT(freqResolutionHz, 0);
198 } else {
199 EXPECT_UNKNOWN_OR_UNSUPPORTED(std::move(status));
200 }
201 return freqResolutionHz;
202 }
203
getFrequencyMinimumHz(const std::shared_ptr<IVibrator> & vibrator,int32_t capabilities,int32_t version)204 static float getFrequencyMinimumHz(const std::shared_ptr<IVibrator>& vibrator, int32_t capabilities,
205 int32_t version) {
206 float freqMinimumHz;
207 ndk::ScopedAStatus status = vibrator->getFrequencyMinimum(&freqMinimumHz);
208 if (shouldValidateLegacyFrequencyControlResult(capabilities, version, status)) {
209 EXPECT_OK(std::move(status));
210
211 float resonantFrequencyHz = getResonantFrequencyHz(vibrator, capabilities);
212
213 EXPECT_GT(freqMinimumHz, 0);
214 EXPECT_LE(freqMinimumHz, resonantFrequencyHz);
215 } else {
216 EXPECT_UNKNOWN_OR_UNSUPPORTED(std::move(status));
217 }
218 return freqMinimumHz;
219 }
220
getFrequencyMaximumHz(const std::shared_ptr<IVibrator> & vibrator,int32_t capabilities,int32_t version)221 static float getFrequencyMaximumHz(const std::shared_ptr<IVibrator>& vibrator, int32_t capabilities,
222 int32_t version) {
223 std::vector<float> bandwidthAmplitudeMap;
224 ndk::ScopedAStatus status = vibrator->getBandwidthAmplitudeMap(&bandwidthAmplitudeMap);
225 if (shouldValidateLegacyFrequencyControlResult(capabilities, version, status)) {
226 EXPECT_OK(std::move(status));
227 } else {
228 EXPECT_UNKNOWN_OR_UNSUPPORTED(std::move(status));
229 }
230
231 float freqMaximumHz = ((bandwidthAmplitudeMap.size() - 1) *
232 getFrequencyResolutionHz(vibrator, capabilities, version)) +
233 getFrequencyMinimumHz(vibrator, capabilities, version);
234 return freqMaximumHz;
235 }
236
getAmplitudeMin()237 static float getAmplitudeMin() {
238 return 0.0;
239 }
240
getAmplitudeMax()241 static float getAmplitudeMax() {
242 return 1.0;
243 }
244
composeValidActivePwle(const std::shared_ptr<IVibrator> & vibrator,int32_t capabilities,int32_t version)245 static ActivePwle composeValidActivePwle(const std::shared_ptr<IVibrator>& vibrator,
246 int32_t capabilities, int32_t version) {
247 float frequencyHz;
248 if (capabilities & IVibrator::CAP_GET_RESONANT_FREQUENCY) {
249 frequencyHz = getResonantFrequencyHz(vibrator, capabilities);
250 } else if (capabilities & IVibrator::CAP_FREQUENCY_CONTROL) {
251 if (version < PWLE_V2_MIN_VERSION) {
252 frequencyHz = getFrequencyMinimumHz(vibrator, capabilities, version);
253 } else {
254 frequencyHz = pwle_v2_utils::getPwleV2FrequencyMinHz(vibrator);
255 }
256 } else {
257 frequencyHz = 150.0; // default value commonly used
258 }
259
260 ActivePwle active;
261 active.startAmplitude = (getAmplitudeMin() + getAmplitudeMax()) / 2;
262 active.startFrequency = frequencyHz;
263 active.endAmplitude = (getAmplitudeMin() + getAmplitudeMax()) / 2;
264 active.endFrequency = frequencyHz;
265 vibrator->getPwlePrimitiveDurationMax(&(active.duration));
266
267 return active;
268 }
269
TEST_P(VibratorAidl,OnThenOffBeforeTimeout)270 TEST_P(VibratorAidl, OnThenOffBeforeTimeout) {
271 EXPECT_OK(vibrator->on(2000, nullptr /*callback*/));
272 sleep(1);
273 EXPECT_OK(vibrator->off());
274 }
275
TEST_P(VibratorAidl,OnWithCallback)276 TEST_P(VibratorAidl, OnWithCallback) {
277 if (!(capabilities & IVibrator::CAP_ON_CALLBACK))
278 return;
279
280 std::promise<void> completionPromise;
281 std::future<void> completionFuture{completionPromise.get_future()};
282 auto callback = ndk::SharedRefBase::make<CompletionCallback>(
283 [&completionPromise] { completionPromise.set_value(); });
284 uint32_t durationMs = 250;
285 auto timeout = std::chrono::milliseconds(durationMs) + VIBRATION_CALLBACK_TIMEOUT;
286 EXPECT_OK(vibrator->on(durationMs, callback));
287 EXPECT_EQ(completionFuture.wait_for(timeout), std::future_status::ready);
288 EXPECT_OK(vibrator->off());
289 }
290
TEST_P(VibratorAidl,OnCallbackNotSupported)291 TEST_P(VibratorAidl, OnCallbackNotSupported) {
292 if (!(capabilities & IVibrator::CAP_ON_CALLBACK)) {
293 auto callback = ndk::SharedRefBase::make<CompletionCallback>([] {});
294 EXPECT_UNKNOWN_OR_UNSUPPORTED(vibrator->on(250, callback));
295 }
296 }
297
TEST_P(VibratorAidl,ValidateEffect)298 TEST_P(VibratorAidl, ValidateEffect) {
299 std::vector<Effect> supported;
300 EXPECT_OK(vibrator->getSupportedEffects(&supported));
301
302 for (Effect effect : kEffects) {
303 bool isEffectSupported =
304 std::find(supported.begin(), supported.end(), effect) != supported.end();
305
306 for (EffectStrength strength : kEffectStrengths) {
307 int32_t lengthMs = 0;
308 ndk::ScopedAStatus status =
309 vibrator->perform(effect, strength, nullptr /*callback*/, &lengthMs);
310
311 if (isEffectSupported) {
312 EXPECT_OK(std::move(status))
313 << "\n For effect: " << toString(effect) << " " << toString(strength);
314 EXPECT_GT(lengthMs, 0);
315 usleep(lengthMs * 1000);
316 EXPECT_OK(vibrator->off());
317 } else {
318 EXPECT_UNKNOWN_OR_UNSUPPORTED(std::move(status))
319 << "\n For effect: " << toString(effect) << " " << toString(strength);
320 }
321 }
322 }
323 }
324
TEST_P(VibratorAidl,ValidateEffectWithCallback)325 TEST_P(VibratorAidl, ValidateEffectWithCallback) {
326 if (!(capabilities & IVibrator::CAP_PERFORM_CALLBACK))
327 return;
328
329 std::vector<Effect> supported;
330 EXPECT_OK(vibrator->getSupportedEffects(&supported));
331
332 for (Effect effect : kEffects) {
333 bool isEffectSupported =
334 std::find(supported.begin(), supported.end(), effect) != supported.end();
335
336 for (EffectStrength strength : kEffectStrengths) {
337 std::promise<void> completionPromise;
338 std::future<void> completionFuture{completionPromise.get_future()};
339 auto callback = ndk::SharedRefBase::make<CompletionCallback>(
340 [&completionPromise] { completionPromise.set_value(); });
341 int lengthMs = 0;
342 ndk::ScopedAStatus status = vibrator->perform(effect, strength, callback, &lengthMs);
343
344 if (isEffectSupported) {
345 EXPECT_OK(std::move(status))
346 << "\n For effect: " << toString(effect) << " " << toString(strength);
347 EXPECT_GT(lengthMs, 0);
348 } else {
349 EXPECT_UNKNOWN_OR_UNSUPPORTED(std::move(status))
350 << "\n For effect: " << toString(effect) << " " << toString(strength);
351 }
352
353 if (lengthMs <= 0) continue;
354
355 auto timeout = std::chrono::milliseconds(lengthMs) + VIBRATION_CALLBACK_TIMEOUT;
356 EXPECT_EQ(completionFuture.wait_for(timeout), std::future_status::ready);
357
358 EXPECT_OK(vibrator->off());
359 }
360 }
361 }
362
TEST_P(VibratorAidl,ValidateEffectWithCallbackNotSupported)363 TEST_P(VibratorAidl, ValidateEffectWithCallbackNotSupported) {
364 if (capabilities & IVibrator::CAP_PERFORM_CALLBACK)
365 return;
366
367 for (Effect effect : kEffects) {
368 for (EffectStrength strength : kEffectStrengths) {
369 auto callback = ndk::SharedRefBase::make<CompletionCallback>([] {});
370 int lengthMs;
371 EXPECT_UNKNOWN_OR_UNSUPPORTED(vibrator->perform(effect, strength, callback, &lengthMs))
372 << "\n For effect: " << toString(effect) << " " << toString(strength);
373 }
374 }
375 }
376
TEST_P(VibratorAidl,InvalidEffectsUnsupported)377 TEST_P(VibratorAidl, InvalidEffectsUnsupported) {
378 for (Effect effect : kInvalidEffects) {
379 for (EffectStrength strength : kEffectStrengths) {
380 int32_t lengthMs;
381 EXPECT_UNKNOWN_OR_UNSUPPORTED(
382 vibrator->perform(effect, strength, nullptr /*callback*/, &lengthMs))
383 << "\n For effect: " << toString(effect) << " " << toString(strength);
384 }
385 }
386 for (Effect effect : kEffects) {
387 for (EffectStrength strength : kInvalidEffectStrengths) {
388 int32_t lengthMs;
389 EXPECT_UNKNOWN_OR_UNSUPPORTED(
390 vibrator->perform(effect, strength, nullptr /*callback*/, &lengthMs))
391 << "\n For effect: " << toString(effect) << " " << toString(strength);
392 }
393 }
394 }
395
TEST_P(VibratorAidl,PerformVendorEffectSupported)396 TEST_P(VibratorAidl, PerformVendorEffectSupported) {
397 if ((capabilities & IVibrator::CAP_PERFORM_VENDOR_EFFECTS) == 0) return;
398
399 float scale = 0.0f;
400 float vendorScale = 0.0f;
401 for (EffectStrength strength : kEffectStrengths) {
402 PersistableBundle vendorData;
403 ::aidl::android::hardware::vibrator::testing::fillBasicData(&vendorData);
404
405 PersistableBundle nestedData;
406 ::aidl::android::hardware::vibrator::testing::fillBasicData(&nestedData);
407 vendorData.putPersistableBundle("test_nested_bundle", nestedData);
408
409 VendorEffect effect;
410 effect.vendorData = vendorData;
411 effect.strength = strength;
412 effect.scale = scale;
413 effect.vendorScale = vendorScale;
414 scale += 0.5f;
415 vendorScale += 0.2f;
416
417 auto callback = ndk::SharedRefBase::make<CompletionCallback>([] {});
418 ndk::ScopedAStatus status = vibrator->performVendorEffect(effect, callback);
419
420 // No expectations on the actual status, the effect might be refused with illegal argument
421 // or the vendor might return a service-specific error code.
422 EXPECT_TRUE(status.getExceptionCode() != EX_UNSUPPORTED_OPERATION &&
423 status.getStatus() != STATUS_UNKNOWN_TRANSACTION)
424 << status << "\n For vendor effect with strength" << toString(strength)
425 << " and scale " << effect.scale;
426
427 if (status.isOk()) {
428 // Generic vendor data should not trigger vibrations, but if it does trigger one
429 // then we make sure the vibrator is reset by triggering off().
430 EXPECT_OK(vibrator->off());
431 }
432 }
433 }
434
TEST_P(VibratorAidl,PerformVendorEffectStability)435 TEST_P(VibratorAidl, PerformVendorEffectStability) {
436 if ((capabilities & IVibrator::CAP_PERFORM_VENDOR_EFFECTS) == 0) return;
437
438 // Run some iterations of performVendorEffect with randomized vendor data to check basic
439 // stability of the implementation.
440 uint8_t iterations = 200;
441
442 for (EffectStrength strength : kEffectStrengths) {
443 float scale = 0.5f;
444 float vendorScale = 0.2f;
445 for (uint8_t i = 0; i < iterations; i++) {
446 PersistableBundle vendorData;
447 ::aidl::android::hardware::vibrator::testing::fillRandomData(&vendorData);
448
449 VendorEffect effect;
450 effect.vendorData = vendorData;
451 effect.strength = strength;
452 effect.scale = scale;
453 effect.vendorScale = vendorScale;
454 scale *= 2;
455 vendorScale *= 1.5f;
456
457 auto callback = ndk::SharedRefBase::make<CompletionCallback>([] {});
458 ndk::ScopedAStatus status = vibrator->performVendorEffect(effect, callback);
459
460 // No expectations on the actual status, the effect might be refused with illegal
461 // argument or the vendor might return a service-specific error code.
462 EXPECT_TRUE(status.getExceptionCode() != EX_UNSUPPORTED_OPERATION &&
463 status.getStatus() != STATUS_UNKNOWN_TRANSACTION)
464 << status << "\n For random vendor effect with strength " << toString(strength)
465 << " and scale " << effect.scale;
466
467 if (status.isOk()) {
468 // Random vendor data should not trigger vibrations, but if it does trigger one
469 // then we make sure the vibrator is reset by triggering off().
470 EXPECT_OK(vibrator->off());
471 }
472 }
473 }
474 }
475
TEST_P(VibratorAidl,PerformVendorEffectEmptyVendorData)476 TEST_P(VibratorAidl, PerformVendorEffectEmptyVendorData) {
477 if ((capabilities & IVibrator::CAP_PERFORM_VENDOR_EFFECTS) == 0) return;
478
479 for (EffectStrength strength : kEffectStrengths) {
480 VendorEffect effect;
481 effect.strength = strength;
482 effect.scale = 1.0f;
483 effect.vendorScale = 1.0f;
484
485 ndk::ScopedAStatus status = vibrator->performVendorEffect(effect, nullptr /*callback*/);
486
487 EXPECT_TRUE(status.getExceptionCode() == EX_SERVICE_SPECIFIC)
488 << status << "\n For vendor effect with strength " << toString(strength)
489 << " and scale " << effect.scale;
490 }
491 }
492
TEST_P(VibratorAidl,PerformVendorEffectInvalidScale)493 TEST_P(VibratorAidl, PerformVendorEffectInvalidScale) {
494 if ((capabilities & IVibrator::CAP_PERFORM_VENDOR_EFFECTS) == 0) return;
495
496 VendorEffect effect;
497 effect.strength = EffectStrength::MEDIUM;
498
499 effect.scale = -1.0f;
500 effect.vendorScale = 1.0f;
501 EXPECT_ILLEGAL_ARGUMENT(vibrator->performVendorEffect(effect, nullptr /*callback*/));
502
503 effect.scale = 1.0f;
504 effect.vendorScale = -1.0f;
505 EXPECT_ILLEGAL_ARGUMENT(vibrator->performVendorEffect(effect, nullptr /*callback*/));
506 }
507
TEST_P(VibratorAidl,PerformVendorEffectUnsupported)508 TEST_P(VibratorAidl, PerformVendorEffectUnsupported) {
509 if (version < VENDOR_EFFECTS_MIN_VERSION) {
510 EXPECT_EQ(capabilities & IVibrator::CAP_PERFORM_VENDOR_EFFECTS, 0)
511 << "Vibrator version " << version << " should not report vendor effects capability";
512 }
513 if (capabilities & IVibrator::CAP_PERFORM_VENDOR_EFFECTS) return;
514
515 for (EffectStrength strength : kEffectStrengths) {
516 VendorEffect effect;
517 effect.strength = strength;
518 effect.scale = 1.0f;
519 effect.vendorScale = 1.0f;
520
521 EXPECT_UNKNOWN_OR_UNSUPPORTED(vibrator->performVendorEffect(effect, nullptr /*callback*/))
522 << "\n For vendor effect with strength " << toString(strength);
523 }
524 }
525
TEST_P(VibratorAidl,ChangeVibrationAmplitude)526 TEST_P(VibratorAidl, ChangeVibrationAmplitude) {
527 if (capabilities & IVibrator::CAP_AMPLITUDE_CONTROL) {
528 EXPECT_OK(vibrator->setAmplitude(0.1f));
529 EXPECT_OK(vibrator->on(2000, nullptr /*callback*/));
530 EXPECT_OK(vibrator->setAmplitude(0.5f));
531 sleep(1);
532 EXPECT_OK(vibrator->setAmplitude(1.0f));
533 sleep(1);
534 EXPECT_OK(vibrator->off());
535 }
536 }
537
TEST_P(VibratorAidl,AmplitudeOutsideRangeFails)538 TEST_P(VibratorAidl, AmplitudeOutsideRangeFails) {
539 if (capabilities & IVibrator::CAP_AMPLITUDE_CONTROL) {
540 EXPECT_ILLEGAL_ARGUMENT(vibrator->setAmplitude(-1));
541 EXPECT_ILLEGAL_ARGUMENT(vibrator->setAmplitude(0));
542 EXPECT_ILLEGAL_ARGUMENT(vibrator->setAmplitude(1.1));
543 }
544 }
545
TEST_P(VibratorAidl,AmplitudeReturnsUnsupportedMatchingCapabilities)546 TEST_P(VibratorAidl, AmplitudeReturnsUnsupportedMatchingCapabilities) {
547 if ((capabilities & IVibrator::CAP_AMPLITUDE_CONTROL) == 0) {
548 EXPECT_UNKNOWN_OR_UNSUPPORTED(vibrator->setAmplitude(1));
549 }
550 }
551
TEST_P(VibratorAidl,ChangeVibrationExternalControl)552 TEST_P(VibratorAidl, ChangeVibrationExternalControl) {
553 if (capabilities & IVibrator::CAP_EXTERNAL_CONTROL) {
554 EXPECT_OK(vibrator->setExternalControl(true));
555 sleep(1);
556 EXPECT_OK(vibrator->setExternalControl(false));
557 sleep(1);
558 }
559 }
560
TEST_P(VibratorAidl,ExternalAmplitudeControl)561 TEST_P(VibratorAidl, ExternalAmplitudeControl) {
562 const bool supportsExternalAmplitudeControl =
563 (capabilities & IVibrator::CAP_EXTERNAL_AMPLITUDE_CONTROL) > 0;
564
565 if (capabilities & IVibrator::CAP_EXTERNAL_CONTROL) {
566 EXPECT_OK(vibrator->setExternalControl(true));
567
568 if (supportsExternalAmplitudeControl) {
569 EXPECT_OK(vibrator->setAmplitude(0.5));
570 } else {
571 EXPECT_UNKNOWN_OR_UNSUPPORTED(vibrator->setAmplitude(0.5));
572 }
573
574 EXPECT_OK(vibrator->setExternalControl(false));
575 } else {
576 EXPECT_FALSE(supportsExternalAmplitudeControl);
577 }
578 }
579
TEST_P(VibratorAidl,ExternalControlUnsupportedMatchingCapabilities)580 TEST_P(VibratorAidl, ExternalControlUnsupportedMatchingCapabilities) {
581 if ((capabilities & IVibrator::CAP_EXTERNAL_CONTROL) == 0) {
582 EXPECT_UNKNOWN_OR_UNSUPPORTED(vibrator->setExternalControl(true));
583 }
584 }
585
TEST_P(VibratorAidl,GetSupportedPrimitives)586 TEST_P(VibratorAidl, GetSupportedPrimitives) {
587 if (capabilities & IVibrator::CAP_COMPOSE_EFFECTS) {
588 std::vector<CompositePrimitive> supported;
589 EXPECT_OK(vibrator->getSupportedPrimitives(&supported));
590
591 for (CompositePrimitive primitive : kCompositePrimitives) {
592 bool isPrimitiveSupported =
593 std::find(supported.begin(), supported.end(), primitive) != supported.end();
594 bool isPrimitiveRequired =
595 std::find(kRequiredPrimitives.begin(), kRequiredPrimitives.end(), primitive) !=
596 kRequiredPrimitives.end();
597
598 EXPECT_TRUE(isPrimitiveSupported || !isPrimitiveRequired) << toString(primitive);
599 }
600 }
601 }
602
TEST_P(VibratorAidl,GetPrimitiveDuration)603 TEST_P(VibratorAidl, GetPrimitiveDuration) {
604 if (capabilities & IVibrator::CAP_COMPOSE_EFFECTS) {
605 std::vector<CompositePrimitive> supported;
606 EXPECT_OK(vibrator->getSupportedPrimitives(&supported));
607
608 for (CompositePrimitive primitive : kCompositePrimitives) {
609 bool isPrimitiveSupported =
610 std::find(supported.begin(), supported.end(), primitive) != supported.end();
611 int32_t duration;
612
613 if (isPrimitiveSupported) {
614 EXPECT_OK(vibrator->getPrimitiveDuration(primitive, &duration))
615 << "\n For primitive: " << toString(primitive) << " " << duration;
616 if (primitive != CompositePrimitive::NOOP) {
617 ASSERT_GT(duration, 0)
618 << "\n For primitive: " << toString(primitive) << " " << duration;
619 }
620 } else {
621 EXPECT_UNKNOWN_OR_UNSUPPORTED(vibrator->getPrimitiveDuration(primitive, &duration))
622 << "\n For primitive: " << toString(primitive);
623 }
624 }
625 }
626 }
627
TEST_P(VibratorAidl,ComposeValidPrimitives)628 TEST_P(VibratorAidl, ComposeValidPrimitives) {
629 if (!(capabilities & IVibrator::CAP_COMPOSE_EFFECTS)) {
630 GTEST_SKIP() << "CAP_COMPOSE_EFFECTS not supported";
631 }
632
633 std::vector<CompositePrimitive> supported;
634 int32_t maxDelay, maxSize;
635
636 EXPECT_OK(vibrator->getSupportedPrimitives(&supported));
637 EXPECT_OK(vibrator->getCompositionDelayMax(&maxDelay));
638 EXPECT_OK(vibrator->getCompositionSizeMax(&maxSize));
639
640 std::vector<CompositeEffect> composite;
641
642 for (int i = 0; i < supported.size(); i++) {
643 CompositePrimitive primitive = supported[i];
644 float t = static_cast<float>(i + 1) / supported.size();
645 CompositeEffect effect;
646
647 effect.delayMs = maxDelay * t;
648 effect.primitive = primitive;
649 effect.scale = t;
650
651 if (composite.size() == maxSize) {
652 break;
653 }
654 }
655
656 if (composite.size() != 0) {
657 EXPECT_OK(vibrator->compose(composite, nullptr));
658 EXPECT_OK(vibrator->off());
659 }
660 }
661
TEST_P(VibratorAidl,ComposeUnsupportedPrimitives)662 TEST_P(VibratorAidl, ComposeUnsupportedPrimitives) {
663 if (!(capabilities & IVibrator::CAP_COMPOSE_EFFECTS)) {
664 GTEST_SKIP() << "CAP_COMPOSE_EFFECTS not supported";
665 }
666
667 std::vector<CompositePrimitive> unsupported(kInvalidPrimitives);
668 std::vector<CompositePrimitive> supported;
669
670 EXPECT_OK(vibrator->getSupportedPrimitives(&supported));
671
672 for (CompositePrimitive primitive : kCompositePrimitives) {
673 bool isPrimitiveSupported =
674 std::find(supported.begin(), supported.end(), primitive) != supported.end();
675
676 if (!isPrimitiveSupported) {
677 unsupported.push_back(primitive);
678 }
679 }
680
681 for (CompositePrimitive primitive : unsupported) {
682 std::vector<CompositeEffect> composite(1);
683
684 for (CompositeEffect& effect : composite) {
685 effect.delayMs = 0;
686 effect.primitive = primitive;
687 effect.scale = 1.0f;
688 }
689 EXPECT_UNKNOWN_OR_UNSUPPORTED(vibrator->compose(composite, nullptr));
690 }
691 }
692
TEST_P(VibratorAidl,ComposeScaleBoundary)693 TEST_P(VibratorAidl, ComposeScaleBoundary) {
694 if (!(capabilities & IVibrator::CAP_COMPOSE_EFFECTS)) {
695 GTEST_SKIP() << "CAP_COMPOSE_EFFECTS not supported";
696 }
697
698 std::vector<CompositeEffect> composite(1);
699 CompositeEffect& effect = composite[0];
700
701 effect.delayMs = 0;
702 effect.primitive = CompositePrimitive::CLICK;
703
704 effect.scale = std::nextafter(0.0f, -1.0f);
705 EXPECT_ILLEGAL_ARGUMENT(vibrator->compose(composite, nullptr));
706
707 effect.scale = 0.0f;
708 EXPECT_OK(vibrator->compose(composite, nullptr));
709 EXPECT_OK(vibrator->off());
710
711 effect.scale = 1.0f;
712 EXPECT_OK(vibrator->compose(composite, nullptr));
713 EXPECT_OK(vibrator->off());
714
715 effect.scale = std::nextafter(1.0f, 2.0f);
716 EXPECT_ILLEGAL_ARGUMENT(vibrator->compose(composite, nullptr));
717 }
718
TEST_P(VibratorAidl,ComposeDelayBoundary)719 TEST_P(VibratorAidl, ComposeDelayBoundary) {
720 if (!(capabilities & IVibrator::CAP_COMPOSE_EFFECTS)) {
721 GTEST_SKIP() << "CAP_COMPOSE_EFFECTS not supported";
722 }
723
724 int32_t maxDelay;
725
726 EXPECT_OK(vibrator->getCompositionDelayMax(&maxDelay));
727
728 std::vector<CompositeEffect> composite(1);
729 CompositeEffect& effect = composite[0];
730
731 effect.primitive = CompositePrimitive::CLICK;
732 effect.scale = 1.0f;
733
734 effect.delayMs = 0;
735 EXPECT_OK(vibrator->compose(composite, nullptr));
736 EXPECT_OK(vibrator->off());
737
738 effect.delayMs = 1;
739 EXPECT_OK(vibrator->compose(composite, nullptr));
740 EXPECT_OK(vibrator->off());
741
742 effect.delayMs = maxDelay;
743 EXPECT_OK(vibrator->compose(composite, nullptr));
744 EXPECT_OK(vibrator->off());
745
746 effect.delayMs = maxDelay + 1;
747 EXPECT_ILLEGAL_ARGUMENT(vibrator->compose(composite, nullptr));
748 }
749
TEST_P(VibratorAidl,ComposeSizeBoundary)750 TEST_P(VibratorAidl, ComposeSizeBoundary) {
751 if (!(capabilities & IVibrator::CAP_COMPOSE_EFFECTS)) {
752 GTEST_SKIP() << "CAP_COMPOSE_EFFECTS not supported";
753 }
754
755 int32_t maxSize;
756
757 EXPECT_OK(vibrator->getCompositionSizeMax(&maxSize));
758
759 std::vector<CompositeEffect> composite(maxSize);
760 CompositeEffect effect;
761
762 effect.delayMs = 1;
763 effect.primitive = CompositePrimitive::CLICK;
764 effect.scale = 1.0f;
765
766 std::fill(composite.begin(), composite.end(), effect);
767 EXPECT_OK(vibrator->compose(composite, nullptr));
768 EXPECT_OK(vibrator->off());
769
770 composite.emplace_back(effect);
771 EXPECT_ILLEGAL_ARGUMENT(vibrator->compose(composite, nullptr));
772 }
773
TEST_P(VibratorAidl,ComposeCallback)774 TEST_P(VibratorAidl, ComposeCallback) {
775 if (!(capabilities & IVibrator::CAP_COMPOSE_EFFECTS)) {
776 GTEST_SKIP() << "CAP_COMPOSE_EFFECTS not supported";
777 }
778
779 std::vector<CompositePrimitive> supported;
780 EXPECT_OK(vibrator->getSupportedPrimitives(&supported));
781
782 for (CompositePrimitive primitive : supported) {
783 if (primitive == CompositePrimitive::NOOP) {
784 continue;
785 }
786
787 std::promise<void> completionPromise;
788 std::future<void> completionFuture{completionPromise.get_future()};
789 auto callback = ndk::SharedRefBase::make<CompletionCallback>(
790 [&completionPromise] { completionPromise.set_value(); });
791 CompositeEffect effect;
792 std::vector<CompositeEffect> composite;
793 int32_t durationMs;
794 std::chrono::milliseconds duration;
795 std::chrono::time_point<high_resolution_clock> start, end;
796 std::chrono::milliseconds elapsed;
797
798 effect.delayMs = 0;
799 effect.primitive = primitive;
800 effect.scale = 1.0f;
801 composite.emplace_back(effect);
802
803 EXPECT_OK(vibrator->getPrimitiveDuration(primitive, &durationMs))
804 << "\n For primitive: " << toString(primitive);
805 duration = std::chrono::milliseconds(durationMs);
806
807 start = high_resolution_clock::now();
808 EXPECT_OK(vibrator->compose(composite, callback))
809 << "\n For primitive: " << toString(primitive);
810
811 EXPECT_EQ(completionFuture.wait_for(duration + VIBRATION_CALLBACK_TIMEOUT),
812 std::future_status::ready)
813 << "\n For primitive: " << toString(primitive);
814 end = high_resolution_clock::now();
815
816 elapsed = std::chrono::duration_cast<std::chrono::milliseconds>(end - start);
817 EXPECT_GE(elapsed.count(), duration.count())
818 << "\n For primitive: " << toString(primitive);
819
820 EXPECT_OK(vibrator->off()) << "\n For primitive: " << toString(primitive);
821 }
822 }
823
TEST_P(VibratorAidl,AlwaysOn)824 TEST_P(VibratorAidl, AlwaysOn) {
825 if (capabilities & IVibrator::CAP_ALWAYS_ON_CONTROL) {
826 std::vector<Effect> supported;
827 EXPECT_OK(vibrator->getSupportedAlwaysOnEffects(&supported));
828
829 for (Effect effect : kEffects) {
830 bool isEffectSupported =
831 std::find(supported.begin(), supported.end(), effect) != supported.end();
832
833 for (EffectStrength strength : kEffectStrengths) {
834 ndk::ScopedAStatus status = vibrator->alwaysOnEnable(0, effect, strength);
835
836 if (isEffectSupported) {
837 EXPECT_OK(std::move(status))
838 << "\n For effect: " << toString(effect) << " " << toString(strength);
839 } else {
840 EXPECT_UNKNOWN_OR_UNSUPPORTED(std::move(status))
841 << "\n For effect: " << toString(effect) << " " << toString(strength);
842 }
843 }
844 }
845
846 EXPECT_OK(vibrator->alwaysOnDisable(0));
847 }
848 }
849
TEST_P(VibratorAidl,GetResonantFrequency)850 TEST_P(VibratorAidl, GetResonantFrequency) {
851 getResonantFrequencyHz(vibrator, capabilities);
852 }
853
TEST_P(VibratorAidl,GetQFactor)854 TEST_P(VibratorAidl, GetQFactor) {
855 float qFactor;
856 ndk::ScopedAStatus status = vibrator->getQFactor(&qFactor);
857 if (capabilities & IVibrator::CAP_GET_Q_FACTOR) {
858 EXPECT_OK(std::move(status));
859 ASSERT_GT(qFactor, 0);
860 } else {
861 EXPECT_UNKNOWN_OR_UNSUPPORTED(std::move(status));
862 }
863 }
864
TEST_P(VibratorAidl,GetFrequencyResolution)865 TEST_P(VibratorAidl, GetFrequencyResolution) {
866 getFrequencyResolutionHz(vibrator, capabilities, version);
867 }
868
TEST_P(VibratorAidl,GetFrequencyMinimum)869 TEST_P(VibratorAidl, GetFrequencyMinimum) {
870 getFrequencyMinimumHz(vibrator, capabilities, version);
871 }
872
TEST_P(VibratorAidl,GetBandwidthAmplitudeMap)873 TEST_P(VibratorAidl, GetBandwidthAmplitudeMap) {
874 std::vector<float> bandwidthAmplitudeMap;
875 ndk::ScopedAStatus status = vibrator->getBandwidthAmplitudeMap(&bandwidthAmplitudeMap);
876
877 if (shouldValidateLegacyFrequencyControlResult(capabilities, version, status)) {
878 EXPECT_OK(std::move(status));
879 ASSERT_FALSE(bandwidthAmplitudeMap.empty());
880
881 int minMapSize = (getResonantFrequencyHz(vibrator, capabilities) -
882 getFrequencyMinimumHz(vibrator, capabilities, version)) /
883 getFrequencyResolutionHz(vibrator, capabilities, version);
884 ASSERT_GT(bandwidthAmplitudeMap.size(), minMapSize);
885
886 for (float e : bandwidthAmplitudeMap) {
887 ASSERT_GE(e, 0.0);
888 ASSERT_LE(e, 1.0);
889 }
890 } else {
891 EXPECT_UNKNOWN_OR_UNSUPPORTED(std::move(status));
892 }
893 }
894
TEST_P(VibratorAidl,GetPwlePrimitiveDurationMax)895 TEST_P(VibratorAidl, GetPwlePrimitiveDurationMax) {
896 int32_t durationMs;
897 ndk::ScopedAStatus status = vibrator->getPwlePrimitiveDurationMax(&durationMs);
898 if (capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS) {
899 EXPECT_OK(std::move(status));
900 ASSERT_NE(durationMs, 0);
901 } else {
902 EXPECT_UNKNOWN_OR_UNSUPPORTED(std::move(status));
903 }
904 }
905
TEST_P(VibratorAidl,GetPwleCompositionSizeMax)906 TEST_P(VibratorAidl, GetPwleCompositionSizeMax) {
907 int32_t maxSize;
908 ndk::ScopedAStatus status = vibrator->getPwleCompositionSizeMax(&maxSize);
909 if (capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS) {
910 EXPECT_OK(std::move(status));
911 ASSERT_NE(maxSize, 0);
912 } else {
913 EXPECT_UNKNOWN_OR_UNSUPPORTED(std::move(status));
914 }
915 }
916
TEST_P(VibratorAidl,GetSupportedBraking)917 TEST_P(VibratorAidl, GetSupportedBraking) {
918 std::vector<Braking> supported;
919 ndk::ScopedAStatus status = vibrator->getSupportedBraking(&supported);
920 if (capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS) {
921 bool isDefaultNoneSupported =
922 std::find(supported.begin(), supported.end(), Braking::NONE) != supported.end();
923 EXPECT_OK(std::move(status));
924 ASSERT_TRUE(isDefaultNoneSupported);
925 } else {
926 EXPECT_UNKNOWN_OR_UNSUPPORTED(std::move(status));
927 }
928 }
929
TEST_P(VibratorAidl,ComposeValidPwle)930 TEST_P(VibratorAidl, ComposeValidPwle) {
931 if (capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS) {
932 ActivePwle firstActive = composeValidActivePwle(vibrator, capabilities, version);
933
934 std::vector<Braking> supported;
935 EXPECT_OK(vibrator->getSupportedBraking(&supported));
936 bool isClabSupported =
937 std::find(supported.begin(), supported.end(), Braking::CLAB) != supported.end();
938 BrakingPwle firstBraking;
939 firstBraking.braking = isClabSupported ? Braking::CLAB : Braking::NONE;
940 firstBraking.duration = 100;
941
942 ActivePwle secondActive = composeValidActivePwle(vibrator, capabilities, version);
943 if (capabilities & IVibrator::CAP_FREQUENCY_CONTROL) {
944 float minFrequencyHz = getFrequencyMinimumHz(vibrator, capabilities, version);
945 float maxFrequencyHz = getFrequencyMaximumHz(vibrator, capabilities, version);
946 float freqResolutionHz = getFrequencyResolutionHz(vibrator, capabilities, version);
947 // As of API 16 these APIs are deprecated and no longer required to be implemented
948 // with frequency control capability.
949 if (minFrequencyHz >= 0 && maxFrequencyHz >= 0 && freqResolutionHz >= 0) {
950 secondActive.startFrequency = minFrequencyHz + (freqResolutionHz / 2.0f);
951 secondActive.endFrequency = maxFrequencyHz - (freqResolutionHz / 3.0f);
952 }
953 }
954 BrakingPwle secondBraking;
955 secondBraking.braking = Braking::NONE;
956 secondBraking.duration = 10;
957
958 std::vector<PrimitivePwle> pwleQueue = {firstActive, firstBraking, secondActive,
959 secondBraking};
960
961 EXPECT_OK(vibrator->composePwle(pwleQueue, nullptr));
962 EXPECT_OK(vibrator->off());
963 }
964 }
965
TEST_P(VibratorAidl,ComposeValidPwleWithCallback)966 TEST_P(VibratorAidl, ComposeValidPwleWithCallback) {
967 if (!((capabilities & IVibrator::CAP_ON_CALLBACK) &&
968 (capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS)))
969 return;
970
971 std::promise<void> completionPromise;
972 std::future<void> completionFuture{completionPromise.get_future()};
973 auto callback = ndk::SharedRefBase::make<CompletionCallback>(
974 [&completionPromise] { completionPromise.set_value(); });
975 int32_t segmentDurationMaxMs;
976 vibrator->getPwlePrimitiveDurationMax(&segmentDurationMaxMs);
977 uint32_t durationMs = segmentDurationMaxMs * 2 + 100; // Sum of 2 active and 1 braking below
978 auto timeout = std::chrono::milliseconds(durationMs) + VIBRATION_CALLBACK_TIMEOUT;
979
980 ActivePwle active = composeValidActivePwle(vibrator, capabilities, version);
981
982 std::vector<Braking> supported;
983 EXPECT_OK(vibrator->getSupportedBraking(&supported));
984 bool isClabSupported =
985 std::find(supported.begin(), supported.end(), Braking::CLAB) != supported.end();
986 BrakingPwle braking;
987 braking.braking = isClabSupported ? Braking::CLAB : Braking::NONE;
988 braking.duration = 100;
989
990 std::vector<PrimitivePwle> pwleQueue = {active, braking, active};
991
992 EXPECT_OK(vibrator->composePwle(pwleQueue, callback));
993 EXPECT_EQ(completionFuture.wait_for(timeout), std::future_status::ready);
994 EXPECT_OK(vibrator->off());
995 }
996
TEST_P(VibratorAidl,ComposePwleSegmentBoundary)997 TEST_P(VibratorAidl, ComposePwleSegmentBoundary) {
998 if (capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS) {
999 std::vector<PrimitivePwle> pwleQueue;
1000 // test empty queue
1001 EXPECT_ILLEGAL_ARGUMENT(vibrator->composePwle(pwleQueue, nullptr));
1002
1003 ActivePwle active = composeValidActivePwle(vibrator, capabilities, version);
1004
1005 PrimitivePwle pwle;
1006 pwle = active;
1007 int segmentCountMax;
1008 vibrator->getPwleCompositionSizeMax(&segmentCountMax);
1009
1010 // Create PWLE queue with more segments than allowed
1011 for (int i = 0; i < segmentCountMax + 10; i++) {
1012 pwleQueue.emplace_back(std::move(pwle));
1013 }
1014
1015 EXPECT_ILLEGAL_ARGUMENT(vibrator->composePwle(pwleQueue, nullptr));
1016 }
1017 }
1018
TEST_P(VibratorAidl,ComposePwleAmplitudeParameterBoundary)1019 TEST_P(VibratorAidl, ComposePwleAmplitudeParameterBoundary) {
1020 if (capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS) {
1021 ActivePwle active = composeValidActivePwle(vibrator, capabilities, version);
1022 active.startAmplitude = getAmplitudeMax() + 1.0; // Amplitude greater than allowed
1023 active.endAmplitude = getAmplitudeMax() + 1.0; // Amplitude greater than allowed
1024
1025 std::vector<PrimitivePwle> pwleQueueGreater = {active};
1026
1027 EXPECT_ILLEGAL_ARGUMENT(vibrator->composePwle(pwleQueueGreater, nullptr));
1028
1029 active.startAmplitude = getAmplitudeMin() - 1.0; // Amplitude less than allowed
1030 active.endAmplitude = getAmplitudeMin() - 1.0; // Amplitude less than allowed
1031
1032 std::vector<PrimitivePwle> pwleQueueLess = {active};
1033
1034 EXPECT_ILLEGAL_ARGUMENT(vibrator->composePwle(pwleQueueLess, nullptr));
1035 }
1036 }
1037
TEST_P(VibratorAidl,ComposePwleFrequencyParameterBoundary)1038 TEST_P(VibratorAidl, ComposePwleFrequencyParameterBoundary) {
1039 if ((capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS) &&
1040 (capabilities & IVibrator::CAP_FREQUENCY_CONTROL)) {
1041 float freqMinimumHz = getFrequencyMinimumHz(vibrator, capabilities, version);
1042 float freqMaximumHz = getFrequencyMaximumHz(vibrator, capabilities, version);
1043 float freqResolutionHz = getFrequencyResolutionHz(vibrator, capabilities, version);
1044
1045 // As of API 16 these APIs are deprecated and no longer required to be implemented with
1046 // frequency control capability.
1047 if (freqMinimumHz < 0 || freqMaximumHz < 0 || freqResolutionHz < 0) {
1048 GTEST_SKIP() << "PWLE V1 is not supported, skipping test";
1049 return;
1050 }
1051
1052 ActivePwle active = composeValidActivePwle(vibrator, capabilities, version);
1053 active.startFrequency =
1054 freqMaximumHz + freqResolutionHz; // Frequency greater than allowed
1055 active.endFrequency = freqMaximumHz + freqResolutionHz; // Frequency greater than allowed
1056
1057 std::vector<PrimitivePwle> pwleQueueGreater = {active};
1058
1059 EXPECT_ILLEGAL_ARGUMENT(vibrator->composePwle(pwleQueueGreater, nullptr));
1060
1061 active.startFrequency = freqMinimumHz - freqResolutionHz; // Frequency less than allowed
1062 active.endFrequency = freqMinimumHz - freqResolutionHz; // Frequency less than allowed
1063
1064 std::vector<PrimitivePwle> pwleQueueLess = {active};
1065
1066 EXPECT_ILLEGAL_ARGUMENT(vibrator->composePwle(pwleQueueLess, nullptr));
1067 }
1068 }
1069
TEST_P(VibratorAidl,ComposePwleSegmentDurationBoundary)1070 TEST_P(VibratorAidl, ComposePwleSegmentDurationBoundary) {
1071 if (capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS) {
1072 ActivePwle active = composeValidActivePwle(vibrator, capabilities, version);
1073
1074 int32_t segmentDurationMaxMs;
1075 vibrator->getPwlePrimitiveDurationMax(&segmentDurationMaxMs);
1076 active.duration = segmentDurationMaxMs + 10; // Segment duration greater than allowed
1077
1078 std::vector<PrimitivePwle> pwleQueue = {active};
1079
1080 EXPECT_ILLEGAL_ARGUMENT(vibrator->composePwle(pwleQueue, nullptr));
1081 }
1082 }
1083
TEST_P(VibratorAidl,FrequencyToOutputAccelerationMapHasValidFrequencyRange)1084 TEST_P(VibratorAidl, FrequencyToOutputAccelerationMapHasValidFrequencyRange) {
1085 if (version < PWLE_V2_MIN_VERSION || !(capabilities & IVibrator::CAP_FREQUENCY_CONTROL)) {
1086 GTEST_SKIP() << "Frequency control is not supported, skipping test";
1087 return;
1088 }
1089
1090 std::vector<FrequencyAccelerationMapEntry> frequencyToOutputAccelerationMap;
1091 ndk::ScopedAStatus status =
1092 vibrator->getFrequencyToOutputAccelerationMap(&frequencyToOutputAccelerationMap);
1093 EXPECT_OK(std::move(status));
1094 ASSERT_FALSE(frequencyToOutputAccelerationMap.empty());
1095 auto sharpnessRange =
1096 pwle_v2_utils::getPwleV2SharpnessRange(vibrator, frequencyToOutputAccelerationMap);
1097 // Validate the curve provides a usable sharpness range, which is a range of frequencies
1098 // that are supported by the device.
1099 ASSERT_TRUE(sharpnessRange.first >= 0);
1100 // Validate that the sharpness range is a valid interval, not a single point.
1101 ASSERT_TRUE(sharpnessRange.first < sharpnessRange.second);
1102 }
1103
TEST_P(VibratorAidl,FrequencyToOutputAccelerationMapUnsupported)1104 TEST_P(VibratorAidl, FrequencyToOutputAccelerationMapUnsupported) {
1105 if ((capabilities & IVibrator::CAP_FREQUENCY_CONTROL)) return;
1106
1107 std::vector<FrequencyAccelerationMapEntry> frequencyToOutputAccelerationMap;
1108
1109 EXPECT_UNKNOWN_OR_UNSUPPORTED(
1110 vibrator->getFrequencyToOutputAccelerationMap(&frequencyToOutputAccelerationMap));
1111 }
1112
TEST_P(VibratorAidl,GetPwleV2PrimitiveDurationMaxMillis)1113 TEST_P(VibratorAidl, GetPwleV2PrimitiveDurationMaxMillis) {
1114 if (!(capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS_V2)) {
1115 GTEST_SKIP() << "PWLE V2 not supported, skipping test";
1116 return;
1117 }
1118
1119 int32_t durationMs;
1120 ndk::ScopedAStatus status = vibrator->getPwleV2PrimitiveDurationMaxMillis(&durationMs);
1121 EXPECT_OK(std::move(status));
1122 ASSERT_GT(durationMs, 0); // Ensure greater than zero
1123 ASSERT_GE(durationMs, pwle_v2_utils::COMPOSE_PWLE_V2_MIN_REQUIRED_PRIMITIVE_MAX_DURATION_MS);
1124 }
1125
TEST_P(VibratorAidl,GetPwleV2CompositionSizeMax)1126 TEST_P(VibratorAidl, GetPwleV2CompositionSizeMax) {
1127 if (!(capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS_V2)) {
1128 GTEST_SKIP() << "PWLE V2 not supported, skipping test";
1129 return;
1130 }
1131
1132 int32_t maxSize;
1133 ndk::ScopedAStatus status = vibrator->getPwleV2CompositionSizeMax(&maxSize);
1134 EXPECT_OK(std::move(status));
1135 ASSERT_GT(maxSize, 0); // Ensure greater than zero
1136 ASSERT_GE(maxSize, pwle_v2_utils::COMPOSE_PWLE_V2_MIN_REQUIRED_SIZE);
1137 }
1138
TEST_P(VibratorAidl,GetPwleV2PrimitiveDurationMinMillis)1139 TEST_P(VibratorAidl, GetPwleV2PrimitiveDurationMinMillis) {
1140 if (!(capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS_V2)) {
1141 GTEST_SKIP() << "PWLE V2 not supported, skipping test";
1142 return;
1143 }
1144
1145 int32_t durationMs;
1146 ndk::ScopedAStatus status = vibrator->getPwleV2PrimitiveDurationMinMillis(&durationMs);
1147 EXPECT_OK(std::move(status));
1148 ASSERT_GT(durationMs, 0); // Ensure greater than zero
1149 ASSERT_LE(durationMs, pwle_v2_utils::COMPOSE_PWLE_V2_MAX_ALLOWED_PRIMITIVE_MIN_DURATION_MS);
1150 }
1151
TEST_P(VibratorAidl,ValidatePwleV2DependencyOnFrequencyControl)1152 TEST_P(VibratorAidl, ValidatePwleV2DependencyOnFrequencyControl) {
1153 if (!(capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS_V2)) {
1154 GTEST_SKIP() << "PWLE V2 not supported, skipping test";
1155 return;
1156 }
1157
1158 // Check if frequency control is supported
1159 bool hasFrequencyControl = (capabilities & IVibrator::CAP_FREQUENCY_CONTROL) != 0;
1160 ASSERT_TRUE(hasFrequencyControl) << "Frequency control MUST be supported when PWLE V2 is.";
1161 }
1162
TEST_P(VibratorAidl,ComposeValidPwleV2Effect)1163 TEST_P(VibratorAidl, ComposeValidPwleV2Effect) {
1164 if (!(capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS_V2)) {
1165 GTEST_SKIP() << "PWLE V2 not supported, skipping test";
1166 return;
1167 }
1168
1169 EXPECT_OK(vibrator->composePwleV2(pwle_v2_utils::composeValidPwleV2Effect(vibrator), nullptr));
1170 EXPECT_OK(vibrator->off());
1171 }
1172
TEST_P(VibratorAidl,ComposePwleV2Unsupported)1173 TEST_P(VibratorAidl, ComposePwleV2Unsupported) {
1174 if (version < PWLE_V2_MIN_VERSION) {
1175 EXPECT_EQ(capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS_V2, 0)
1176 << "Vibrator version " << version << " should not report PWLE V2 capability.";
1177 }
1178 if ((capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS_V2)) return;
1179
1180 CompositePwleV2 composite;
1181 composite.pwlePrimitives.emplace_back(/*amplitude=*/1.0f, /*frequencyHz=*/100.0f,
1182 /*timeMillis=*/50);
1183
1184 EXPECT_UNKNOWN_OR_UNSUPPORTED(vibrator->composePwleV2(composite, nullptr));
1185 }
1186
TEST_P(VibratorAidl,ComposeValidPwleV2EffectWithCallback)1187 TEST_P(VibratorAidl, ComposeValidPwleV2EffectWithCallback) {
1188 if (!(capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS_V2)) {
1189 GTEST_SKIP() << "PWLE V2 not supported, skipping test";
1190 return;
1191 }
1192
1193 std::promise<void> completionPromise;
1194 std::future<void> completionFuture{completionPromise.get_future()};
1195 auto callback = ndk::SharedRefBase::make<CompletionCallback>(
1196 [&completionPromise] { completionPromise.set_value(); });
1197
1198 int32_t minDuration;
1199 EXPECT_OK(vibrator->getPwleV2PrimitiveDurationMinMillis(&minDuration));
1200 auto timeout = std::chrono::milliseconds(minDuration) + VIBRATION_CALLBACK_TIMEOUT;
1201 float minFrequency = pwle_v2_utils::getPwleV2FrequencyMinHz(vibrator);
1202
1203 CompositePwleV2 composite;
1204 composite.pwlePrimitives.emplace_back(/*amplitude=*/0.5, minFrequency, minDuration);
1205
1206 EXPECT_OK(vibrator->composePwleV2(composite, callback));
1207 EXPECT_EQ(completionFuture.wait_for(timeout), std::future_status::ready);
1208 EXPECT_OK(vibrator->off());
1209 }
1210
TEST_P(VibratorAidl,composePwleV2EffectWithTooManyPoints)1211 TEST_P(VibratorAidl, composePwleV2EffectWithTooManyPoints) {
1212 if (!(capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS_V2)) {
1213 GTEST_SKIP() << "PWLE V2 not supported, skipping test";
1214 return;
1215 }
1216
1217 EXPECT_ILLEGAL_ARGUMENT(vibrator->composePwleV2(
1218 pwle_v2_utils::composePwleV2EffectWithTooManyPoints(vibrator), nullptr));
1219 }
1220
TEST_P(VibratorAidl,composeInvalidPwleV2Effect)1221 TEST_P(VibratorAidl, composeInvalidPwleV2Effect) {
1222 if (!(capabilities & IVibrator::CAP_COMPOSE_PWLE_EFFECTS_V2)) {
1223 GTEST_SKIP() << "PWLE V2 not supported, skipping test";
1224 return;
1225 }
1226
1227 // Retrieve min and max durations
1228 int32_t minDurationMs, maxDurationMs;
1229 EXPECT_OK(vibrator->getPwleV2PrimitiveDurationMinMillis(&minDurationMs));
1230 EXPECT_OK(vibrator->getPwleV2PrimitiveDurationMaxMillis(&maxDurationMs));
1231
1232 CompositePwleV2 composePwle;
1233
1234 // Negative amplitude
1235 composePwle.pwlePrimitives.push_back(
1236 PwleV2Primitive(/*amplitude=*/-0.8f, /*frequency=*/100, minDurationMs));
1237 EXPECT_ILLEGAL_ARGUMENT(vibrator->composePwleV2(composePwle, nullptr))
1238 << "Composing PWLE V2 effect with negative amplitude should fail";
1239 composePwle.pwlePrimitives.clear();
1240
1241 // Amplitude exceeding 1.0
1242 composePwle.pwlePrimitives.push_back(
1243 PwleV2Primitive(/*amplitude=*/1.2f, /*frequency=*/100, minDurationMs));
1244 EXPECT_ILLEGAL_ARGUMENT(vibrator->composePwleV2(composePwle, nullptr))
1245 << "Composing PWLE V2 effect with amplitude greater than 1.0 should fail";
1246 composePwle.pwlePrimitives.clear();
1247
1248 // Duration exceeding maximum
1249 composePwle.pwlePrimitives.push_back(
1250 PwleV2Primitive(/*amplitude=*/0.2f, /*frequency=*/100, maxDurationMs + 10));
1251 EXPECT_ILLEGAL_ARGUMENT(vibrator->composePwleV2(composePwle, nullptr))
1252 << "Composing PWLE V2 effect with duration exceeding maximum should fail";
1253 composePwle.pwlePrimitives.clear();
1254
1255 // Negative duration
1256 composePwle.pwlePrimitives.push_back(
1257 PwleV2Primitive(/*amplitude=*/0.2f, /*frequency=*/100, /*time=*/-1));
1258 EXPECT_ILLEGAL_ARGUMENT(vibrator->composePwleV2(composePwle, nullptr))
1259 << "Composing PWLE V2 effect with negative duration should fail";
1260 composePwle.pwlePrimitives.clear();
1261
1262 // Frequency below minimum
1263 float minFrequency = pwle_v2_utils::getPwleV2FrequencyMinHz(vibrator);
1264 composePwle.pwlePrimitives.push_back(
1265 PwleV2Primitive(/*amplitude=*/0.2f, minFrequency - 1, minDurationMs));
1266 EXPECT_ILLEGAL_ARGUMENT(vibrator->composePwleV2(composePwle, nullptr))
1267 << "Composing PWLE V2 effect with frequency below minimum should fail";
1268 composePwle.pwlePrimitives.clear();
1269
1270 // Frequency above maximum
1271 float maxFrequency = pwle_v2_utils::getPwleV2FrequencyMaxHz(vibrator);
1272 composePwle.pwlePrimitives.push_back(
1273 PwleV2Primitive(/*amplitude=*/0.2f, maxFrequency + 1, minDurationMs));
1274 EXPECT_ILLEGAL_ARGUMENT(vibrator->composePwleV2(composePwle, nullptr))
1275 << "Composing PWLE V2 effect with frequency above maximum should fail";
1276 }
1277
GenerateVibratorMapping()1278 std::vector<std::tuple<int32_t, int32_t>> GenerateVibratorMapping() {
1279 std::vector<std::tuple<int32_t, int32_t>> tuples;
1280
1281 std::vector<std::string> managerNames = findVibratorManagerNames();
1282 std::vector<int32_t> vibratorIds;
1283 for (int i = 0; i < managerNames.size(); i++) {
1284 auto vibratorManager = IVibratorManager::fromBinder(
1285 ndk::SpAIBinder(AServiceManager_waitForService(managerNames[i].c_str())));
1286 if (vibratorManager->getVibratorIds(&vibratorIds).isOk()) {
1287 for (int32_t vibratorId : vibratorIds) {
1288 tuples.emplace_back(i, vibratorId);
1289 }
1290 }
1291 }
1292
1293 std::vector<std::string> vibratorNames = findUnmanagedVibratorNames();
1294 for (int i = 0; i < vibratorNames.size(); i++) {
1295 tuples.emplace_back(-1, i);
1296 }
1297
1298 return tuples;
1299 }
1300
PrintGeneratedTest(const testing::TestParamInfo<VibratorAidl::ParamType> & info)1301 std::string PrintGeneratedTest(const testing::TestParamInfo<VibratorAidl::ParamType> &info) {
1302 const auto &[managerIdx, vibratorId] = info.param;
1303 if (managerIdx < 0) {
1304 return std::string("TOP_LEVEL_VIBRATOR_") + std::to_string(vibratorId);
1305 }
1306 return std::string("MANAGER_") + std::to_string(managerIdx) + "_VIBRATOR_ID_" +
1307 std::to_string(vibratorId);
1308 }
1309
1310 GTEST_ALLOW_UNINSTANTIATED_PARAMETERIZED_TEST(VibratorAidl);
1311 INSTANTIATE_TEST_SUITE_P(Vibrator, VibratorAidl, testing::ValuesIn(GenerateVibratorMapping()),
1312 PrintGeneratedTest);
1313
main(int argc,char ** argv)1314 int main(int argc, char **argv) {
1315 // Random values are used in the implementation.
1316 std::srand(std::time(nullptr));
1317
1318 ::testing::InitGoogleTest(&argc, argv);
1319 ABinderProcess_setThreadPoolMaxThreadCount(1);
1320 ABinderProcess_startThreadPool();
1321 return RUN_ALL_TESTS();
1322 }
1323