1 /* 2 * Copyright (C) 2017 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 17 #define LOG_TAG "VtsHalUsbV1_0TargetTest" 18 #include <android-base/logging.h> 19 20 #include <android/hardware/usb/1.0/types.h> 21 #include <android/hardware/usb/1.1/IUsb.h> 22 #include <android/hardware/usb/1.1/IUsbCallback.h> 23 #include <android/hardware/usb/1.1/types.h> 24 25 #include <VtsHalHidlTargetCallbackBase.h> 26 #include <VtsHalHidlTargetTestBase.h> 27 #include <log/log.h> 28 #include <stdlib.h> 29 #include <chrono> 30 #include <condition_variable> 31 #include <mutex> 32 33 using ::android::hardware::usb::V1_1::IUsbCallback; 34 using ::android::hardware::usb::V1_0::IUsb; 35 using ::android::hardware::usb::V1_0::PortDataRole; 36 using ::android::hardware::usb::V1_0::PortMode; 37 using ::android::hardware::usb::V1_1::PortMode_1_1; 38 using ::android::hardware::usb::V1_0::PortPowerRole; 39 using ::android::hardware::usb::V1_0::PortRole; 40 using ::android::hardware::usb::V1_0::PortRoleType; 41 using ::android::hardware::usb::V1_0::PortStatus; 42 using ::android::hardware::usb::V1_1::PortStatus_1_1; 43 using ::android::hardware::usb::V1_0::Status; 44 using ::android::hidl::base::V1_0::IBase; 45 using ::android::hardware::hidl_array; 46 using ::android::hardware::hidl_memory; 47 using ::android::hardware::hidl_string; 48 using ::android::hardware::hidl_vec; 49 using ::android::hardware::Return; 50 using ::android::hardware::Void; 51 using ::android::sp; 52 53 constexpr char kCallbackNameNotifyPortStatusChange_1_1[] = "notifyPortStatusChange_1_1"; 54 55 // Worst case wait time 20secs 56 #define WAIT_FOR_TIMEOUT std::chrono::milliseconds(20000) 57 58 class UsbClientCallbackArgs { 59 public: 60 // The last conveyed status of the USB ports. 61 // Stores information of currentt_data_role, power_role for all the USB ports 62 PortStatus_1_1 usb_last_port_status; 63 64 // Status of the last role switch operation. 65 Status usb_last_status; 66 67 // Identifier for the usb callback object. 68 // Stores the cookie of the last invoked usb callback object. 69 int last_usb_cookie; 70 }; 71 72 // Callback class for the USB HIDL hal. 73 // Usb Hal will call this object upon role switch or port query. 74 class UsbCallback : public ::testing::VtsHalHidlTargetCallbackBase<UsbClientCallbackArgs>, 75 public IUsbCallback { 76 int cookie; 77 78 public: 79 UsbCallback(int cookie) : cookie(cookie){}; 80 81 virtual ~UsbCallback() = default; 82 83 // V1_0 Callback method for the port status. 84 // This should not be called so not signalling the Test here assuming that 85 // the test thread will timeout 86 Return<void> notifyPortStatusChange(const hidl_vec<PortStatus>& /* currentPortStatus */, 87 Status /*retval*/) override { 88 return Void(); 89 }; 90 91 // This callback methode should be used. 92 Return<void> notifyPortStatusChange_1_1(const hidl_vec<PortStatus_1_1>& currentPortStatus, 93 Status retval) override { 94 UsbClientCallbackArgs arg; 95 if (retval == Status::SUCCESS) { 96 arg.usb_last_port_status.status.supportedModes = 97 currentPortStatus[0].status.supportedModes; 98 arg.usb_last_port_status.status.currentMode = currentPortStatus[0].status.currentMode; 99 } 100 arg.usb_last_status = retval; 101 arg.last_usb_cookie = cookie; 102 103 NotifyFromCallback(kCallbackNameNotifyPortStatusChange_1_1, arg); 104 return Void(); 105 } 106 107 // Callback method for the status of role switch operation. 108 // RoleSwitch operation has not changed since V1_0 so leaving 109 // the callback blank here. 110 Return<void> notifyRoleSwitchStatus(const hidl_string& /*portName*/, 111 const PortRole& /*newRole*/, Status /*retval*/) override { 112 return Void(); 113 }; 114 }; 115 116 // The main test class for the USB hidl HAL 117 class UsbHidlTest : public ::testing::VtsHalHidlTargetTestBase { 118 public: 119 virtual void SetUp() override { 120 ALOGI(__FUNCTION__); 121 usb = ::testing::VtsHalHidlTargetTestBase::getService<IUsb>(); 122 ASSERT_NE(usb, nullptr); 123 124 usb_cb_2 = new UsbCallback(2); 125 ASSERT_NE(usb_cb_2, nullptr); 126 usb_cb_2->SetWaitTimeout(kCallbackNameNotifyPortStatusChange_1_1, WAIT_FOR_TIMEOUT); 127 Return<void> ret = usb->setCallback(usb_cb_2); 128 ASSERT_TRUE(ret.isOk()); 129 } 130 131 virtual void TearDown() override { ALOGI("Teardown"); } 132 133 // USB hidl hal Proxy 134 sp<IUsb> usb; 135 136 // Callback objects for usb hidl 137 // Methods of these objects are called to notify port status updates. 138 sp<UsbCallback> usb_cb_1; 139 sp<UsbCallback> usb_cb_2; 140 }; 141 142 /* 143 * Test to see if setCallback on V1_1 callback object succeeds. 144 * Callback oject is created and registered. 145 * Check to see if the hidl transaction succeeded. 146 */ 147 TEST_F(UsbHidlTest, setCallback) { 148 usb_cb_1 = new UsbCallback(1); 149 ASSERT_NE(usb_cb_1, nullptr); 150 Return<void> ret = usb->setCallback(usb_cb_1); 151 ASSERT_TRUE(ret.isOk()); 152 } 153 154 /* 155 * Check to see if querying type-c 156 * port status succeeds. 157 * HAL service should call notifyPortStatusChange_1_1 158 * instead of notifyPortStatusChange of V1_0 interface 159 */ 160 TEST_F(UsbHidlTest, queryPortStatus) { 161 Return<void> ret = usb->queryPortStatus(); 162 ASSERT_TRUE(ret.isOk()); 163 auto res = usb_cb_2->WaitForCallback(kCallbackNameNotifyPortStatusChange_1_1); 164 EXPECT_TRUE(res.no_timeout); 165 EXPECT_EQ(2, res.args->last_usb_cookie); 166 EXPECT_EQ(PortMode::NONE, res.args->usb_last_port_status.status.currentMode); 167 EXPECT_EQ(PortMode::NONE, res.args->usb_last_port_status.status.supportedModes); 168 EXPECT_EQ(Status::SUCCESS, res.args->usb_last_status); 169 } 170 171 int main(int argc, char** argv) { 172 ::testing::InitGoogleTest(&argc, argv); 173 int status = RUN_ALL_TESTS(); 174 ALOGI("Test result = %d", status); 175 return status; 176 } 177