#include "wificond/client_interface_binder.h"
#include "wificond/net/mlme_event.h"
#include "wificond/net/netlink_utils.h"
+#include "wificond/scanning/offload/offload_service_utils.h"
#include "wificond/scanning/scan_result.h"
#include "wificond/scanning/scan_utils.h"
#include "wificond/scanning/scanner_impl.h"
supplicant_manager_(supplicant_manager),
netlink_utils_(netlink_utils),
scan_utils_(scan_utils),
+ offload_service_utils_(new OffloadServiceUtils()),
mlme_event_handler_(new MlmeEventHandlerImpl(this)),
binder_(new ClientInterfaceBinder(this)),
is_associated_(false) {
wiphy_features_,
this,
netlink_utils_,
- scan_utils_);
+ scan_utils_,
+ offload_service_utils_);
}
ClientInterfaceImpl::~ClientInterfaceImpl() {
#include "android/net/wifi/IClientInterface.h"
#include "wificond/net/mlme_event_handler.h"
#include "wificond/net/netlink_utils.h"
+#include "wificond/scanning/offload/offload_service_utils.h"
#include "wificond/scanning/scanner_impl.h"
namespace android {
android::wifi_system::SupplicantManager* const supplicant_manager_;
NetlinkUtils* const netlink_utils_;
ScanUtils* const scan_utils_;
+ const std::shared_ptr<OffloadServiceUtils> offload_service_utils_;
const std::unique_ptr<MlmeEventHandlerImpl> mlme_event_handler_;
const android::sp<ClientInterfaceBinder> binder_;
android::sp<ScannerImpl> scanner_;
using android::wificond::OnNativeScanResultsReadyHandler;
using ::com::android::server::wifi::wificond::NativeScanResult;
using ::com::android::server::wifi::wificond::NativeScanStats;
-using namespace std::placeholders;
using std::vector;
+using std::weak_ptr;
+
+using namespace std::placeholders;
namespace {
const uint32_t kSubscriptionDelayMs = 5000;
}
}
-OffloadScanManager::OffloadScanManager(OffloadServiceUtils* utils,
+OffloadScanManager::OffloadScanManager(weak_ptr<OffloadServiceUtils> utils,
OnNativeScanResultsReadyHandler handler)
: wifi_offload_hal_(nullptr),
wifi_offload_callback_(nullptr),
subscription_enabled_(false),
offload_callback_handlers_(new OffloadCallbackHandlersImpl(this)),
scan_result_handler_(handler) {
- if (utils == nullptr) {
- LOG(ERROR) << "Invalid arguments for Offload ScanManager";
- return;
- }
+ auto offload_scan_utils = utils.lock();
if (scan_result_handler_ == nullptr) {
LOG(ERROR) << "Invalid Offload scan result handler";
return;
}
- wifi_offload_hal_ = utils->GetOffloadService();
+ wifi_offload_hal_ = offload_scan_utils->GetOffloadService();
if (wifi_offload_hal_ == nullptr) {
LOG(ERROR) << "No Offload Service available";
return;
}
- death_recipient_ = utils->GetOffloadDeathRecipient(
+ death_recipient_ = offload_scan_utils->GetOffloadDeathRecipient(
std::bind(&OffloadScanManager::OnObjectDeath, this, _1));
uint64_t cookie = reinterpret_cast<uint64_t>(wifi_offload_hal_.get());
auto link_to_death_status =
}
wifi_offload_callback_ =
- utils->GetOffloadCallback(offload_callback_handlers_.get());
+ offload_scan_utils->GetOffloadCallback(offload_callback_handlers_.get());
if (wifi_offload_callback_ == nullptr) {
LOG(ERROR) << "Invalid Offload callback object";
return;
return offload_status_;
}
-bool OffloadScanManager::isOffloadScanSupported() const {
- bool result = false;
-#ifdef WIFI_OFFLOAD_SCANS
- LOG(VERBOSE) << "Offload HAL supported";
- result = true;
-#endif
- return result;
-}
-
bool OffloadScanManager::getScanStats(NativeScanStats* native_scan_stats) {
if (getOffloadStatus() != OffloadScanManager::kNoError) {
LOG(WARNING) << "Unable to get scan stats due to Wifi Offload HAL error";
kTransactionFailed,
};
- explicit OffloadScanManager(OffloadServiceUtils* utils,
+ explicit OffloadScanManager(std::weak_ptr<OffloadServiceUtils> utils,
OnNativeScanResultsReadyHandler handler);
virtual ~OffloadScanManager();
/* Request start of offload scans with scan parameters and scan filter
::com::android::server::wifi::wificond::NativeScanStats* /* scanStats */);
/* Otain status of the Offload HAL service */
StatusCode getOffloadStatus() const;
- /* Check if Offload service is supported on this device */
- bool isOffloadScanSupported() const;
private:
void ReportScanResults(
return new OffloadDeathRecipient(handler);
}
+bool OffloadServiceUtils::IsOffloadScanSupported() const {
+ bool result = false;
+#ifdef WIFI_OFFLOAD_SCANS
+ LOG(VERBOSE) << "Offload HAL supported";
+ result = true;
+#endif
+ return result;
+}
+
OffloadDeathRecipient::OffloadDeathRecipient(
OffloadDeathRecipientHandler handler)
: handler_(handler) {}
virtual ~OffloadServiceUtils() = default;
virtual android::sp<android::hardware::wifi::offload::V1_0::IOffload>
GetOffloadService();
+ // Check if Offload scan is supported on this device.
+ virtual bool IsOffloadScanSupported() const;
virtual android::sp<OffloadCallback> GetOffloadCallback(
OffloadCallbackHandlers* handlers);
virtual OffloadDeathRecipient* GetOffloadDeathRecipient(
using std::string;
using std::vector;
+using std::weak_ptr;
using namespace std::placeholders;
const WiphyFeatures& wiphy_features,
ClientInterfaceImpl* client_interface,
NetlinkUtils* netlink_utils,
- ScanUtils* scan_utils)
+ ScanUtils* scan_utils,
+ weak_ptr<OffloadServiceUtils> offload_service_utils)
: valid_(true),
scan_started_(false),
pno_scan_started_(false),
this,
_1, _2));
offload_scan_manager_.reset(
- new OffloadScanManager(new OffloadServiceUtils(),
+ new OffloadScanManager(
+ offload_service_utils,
std::bind(&ScannerImpl::OnOffloadScanResult,
this, _1)));
- offload_scan_supported_ = offload_scan_manager_->isOffloadScanSupported();
+ offload_scan_supported_ = offload_service_utils.lock()->IsOffloadScanSupported();
}
ScannerImpl::~ScannerImpl() {
namespace wificond {
class ClientInterfaceImpl;
+class OffloadServiceUtils;
class ScanUtils;
class ScannerImpl : public android::net::wifi::BnWifiScannerImpl {
const WiphyFeatures& wiphy_features,
ClientInterfaceImpl* client_interface,
NetlinkUtils* netlink_utils,
- ScanUtils* scan_utils);
+ ScanUtils* scan_utils,
+ std::weak_ptr<OffloadServiceUtils> offload_service_utils);
~ScannerImpl();
// Returns a vector of available frequencies for 2.4GHz channels.
::android::binder::Status getAvailable2gChannels(
public:
MockOffloadServiceUtils();
~MockOffloadServiceUtils() override = default;
-
+ MOCK_CONST_METHOD0(IsOffloadScanSupported, bool());
MOCK_METHOD0(GetOffloadService,
sp<android::hardware::wifi::offload::V1_0::IOffload>());
MOCK_METHOD1(GetOffloadCallback,
MockScanUtils(NetlinkManager* netlink_manager);
~MockScanUtils() override = default;
+ MOCK_METHOD1(UnsubscribeScanResultNotification,
+ void(uint32_t interface_index));
MOCK_METHOD1(AbortScan, bool(uint32_t interface_index));
+ MOCK_METHOD1(StopScheduledScan, bool(uint32_t interface_index));
+ MOCK_METHOD2(SubscribeScanResultNotification,void(
+ uint32_t interface_index,
+ OnScanResultsReadyHandler handler));
MOCK_METHOD2(GetScanResult, bool(
uint32_t interface_index,
std::vector<::com::android::server::wifi::wificond::NativeScanResult>* out_scan_results));
const std::vector<uint32_t>& freqs,
int* error_code));
- MOCK_METHOD2(SubscribeScanResultNotification,void(
+ MOCK_METHOD8(StartScheduledScan, bool(
uint32_t interface_index,
- OnScanResultsReadyHandler handler));
-
- MOCK_METHOD1(UnsubscribeScanResultNotification,
- void(uint32_t interface_index));
+ uint32_t interval_ms,
+ int32_t rssi_threshold,
+ bool request_random_mac,
+ const std::vector<std::vector<uint8_t>>& scan_ssids,
+ const std::vector<std::vector<uint8_t>>& match_ssids,
+ const std::vector<uint32_t>& freqs,
+ int* error_code));
}; // class MockScanUtils
using testing::NiceMock;
using testing::_;
using testing::Invoke;
+using std::shared_ptr;
using std::unique_ptr;
using std::vector;
using std::bind;
sp<NiceMock<MockOffload>> mock_offload_{new NiceMock<MockOffload>()};
sp<OffloadCallback> offload_callback_;
sp<OffloadDeathRecipient> death_recipient_;
- unique_ptr<NiceMock<MockOffloadServiceUtils>> mock_offload_service_utils_{
+ shared_ptr<NiceMock<MockOffloadServiceUtils>> mock_offload_service_utils_{
new NiceMock<MockOffloadServiceUtils>()};
unique_ptr<OffloadScanManager> offload_scan_manager_;
OffloadStatus status;
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
death_recipient_->serviceDied(cookie_, mock_offload_);
EXPECT_EQ(OffloadScanManager::kNoService,
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
death_recipient_->serviceDied(kDeathCode, mock_offload_);
EXPECT_FALSE(OffloadScanManager::kNoService ==
}
/**
- * Testing OffloadScanManager with OffloadServiceUtils null argument
- */
-TEST_F(OffloadScanManagerTest, ServiceUtilsNotAvailableTest) {
- offload_scan_manager_.reset(new OffloadScanManager(nullptr, nullptr));
- EXPECT_EQ(OffloadScanManager::kNoService,
- offload_scan_manager_->getOffloadStatus());
-}
-
-/**
* Testing OffloadScanManager with no handle on Offloal HAL service
* and no registered handler for Offload Scan results
*/
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(nullptr));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
EXPECT_EQ(OffloadScanManager::kNoService,
offload_scan_manager_->getOffloadStatus());
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
EXPECT_EQ(OffloadScanManager::kNoError,
offload_scan_manager_->getOffloadStatus());
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[&callback_invoked](vector<NativeScanResult> scanResult) -> void {
callback_invoked = true;
}));
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
OffloadStatus status =
OffloadTestUtils::createOffloadStatus(OffloadStatusCode::ERROR);
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
EXPECT_CALL(*mock_offload_, subscribeScanResults(_, _));
EXPECT_CALL(*mock_offload_, configureScans(_, _, _));
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(nullptr));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
OffloadScanManager::ReasonCode reason_code = OffloadScanManager::kNone;
bool result = offload_scan_manager_->startScan(
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
OffloadStatus status =
OffloadTestUtils::createOffloadStatus(OffloadStatusCode::NO_CONNECTION);
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
EXPECT_CALL(*mock_offload_, subscribeScanResults(_, _)).Times(1);
EXPECT_CALL(*mock_offload_, configureScans(_, _, _)).Times(2);
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
EXPECT_CALL(*mock_offload_, subscribeScanResults(_, _));
EXPECT_CALL(*mock_offload_, configureScans(_, _, _));
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
OffloadScanManager::ReasonCode reason_code = OffloadScanManager::kNone;
bool result = offload_scan_manager_->stopScan(&reason_code);
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
EXPECT_CALL(*mock_offload_, subscribeScanResults(_, _));
EXPECT_CALL(*mock_offload_, configureScans(_, _, _));
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
EXPECT_CALL(*mock_offload_, getScanStats(_));
NativeScanStats stats;
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
OffloadStatus status =
OffloadTestUtils::createOffloadStatus(OffloadStatusCode::NO_CONNECTION);
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
EXPECT_CALL(*mock_offload_, subscribeScanResults(_, _)).Times(0);
EXPECT_CALL(*mock_offload_, configureScans(_, _, _)).Times(1);
ON_CALL(*mock_offload_service_utils_, GetOffloadService())
.WillByDefault(testing::Return(mock_offload_));
offload_scan_manager_.reset(new OffloadScanManager(
- mock_offload_service_utils_.get(),
+ mock_offload_service_utils_,
[](vector<NativeScanResult> scanResult) -> void {}));
status = OffloadTestUtils::createOffloadStatus(OffloadStatusCode::TIMEOUT);
EXPECT_CALL(*mock_offload_, getScanStats(_));
#include "wificond/tests/mock_client_interface_impl.h"
#include "wificond/tests/mock_netlink_manager.h"
#include "wificond/tests/mock_netlink_utils.h"
+#include "wificond/tests/mock_offload_service_utils.h"
#include "wificond/tests/mock_scan_utils.h"
using ::android::binder::Status;
using ::android::wifi_system::MockInterfaceTool;
using ::android::wifi_system::MockSupplicantManager;
using ::com::android::server::wifi::wificond::SingleScanSettings;
+using ::com::android::server::wifi::wificond::PnoSettings;
using ::com::android::server::wifi::wificond::NativeScanResult;
using ::testing::Invoke;
using ::testing::NiceMock;
using ::testing::Return;
using ::testing::_;
+using std::shared_ptr;
+using std::unique_ptr;
using std::vector;
using namespace std::placeholders;
class ScannerTest : public ::testing::Test {
protected:
+ void SetUp() override {
+ ON_CALL(*offload_service_utils_, IsOffloadScanSupported()).WillByDefault(
+ Return(false));
+ netlink_scanner_.reset(new ScannerImpl(
+ kFakeWiphyIndex, kFakeInterfaceIndex,
+ scan_capabilities_, wiphy_features_,
+ &client_interface_impl_,
+ &netlink_utils_, &scan_utils_, offload_service_utils_));
+ }
+
+ unique_ptr<ScannerImpl> netlink_scanner_;
NiceMock<MockNetlinkManager> netlink_manager_;
NiceMock<MockNetlinkUtils> netlink_utils_{&netlink_manager_};
NiceMock<MockScanUtils> scan_utils_{&netlink_manager_};
NiceMock<MockSupplicantManager> supplicant_manager_;
NiceMock<MockClientInterfaceImpl> client_interface_impl_{
&if_tool_, &supplicant_manager_, &netlink_utils_, &scan_utils_};
+ shared_ptr<NiceMock<MockOffloadServiceUtils>> offload_service_utils_{
+ new NiceMock<MockOffloadServiceUtils>()};
ScanCapabilities scan_capabilities_;
WiphyFeatures wiphy_features_;
- ScannerImpl scanner_{
- kFakeWiphyIndex, kFakeInterfaceIndex,
- scan_capabilities_, wiphy_features_,
- &client_interface_impl_,
- &netlink_utils_, &scan_utils_};
};
TEST_F(ScannerTest, TestSingleScan) {
EXPECT_CALL(scan_utils_, Scan(_, _, _, _, _)).WillOnce(Return(true));
bool success = false;
- EXPECT_TRUE(scanner_.scan(SingleScanSettings(), &success).isOk());
+ EXPECT_TRUE(netlink_scanner_->scan(SingleScanSettings(), &success).isOk());
EXPECT_TRUE(success);
}
ReturnErrorCodeForScanRequest, EBUSY, _1, _2, _3, _4, _5)));
bool success = false;
- EXPECT_TRUE(scanner_.scan(SingleScanSettings(), &success).isOk());
+ EXPECT_TRUE(netlink_scanner_->scan(SingleScanSettings(), &success).isOk());
EXPECT_FALSE(success);
}
bool success_ignored;
EXPECT_DEATH(
- scanner_.scan(SingleScanSettings(), &success_ignored),
+ netlink_scanner_->scan(SingleScanSettings(), &success_ignored),
"Driver is in a bad state*");
}
TEST_F(ScannerTest, TestAbortScan) {
bool single_scan_success = false;
EXPECT_CALL(scan_utils_, Scan(_, _, _, _, _)).WillOnce(Return(true));
- EXPECT_TRUE(scanner_.scan(SingleScanSettings(),
+ EXPECT_TRUE(netlink_scanner_->scan(SingleScanSettings(),
&single_scan_success).isOk());
EXPECT_TRUE(single_scan_success);
EXPECT_CALL(scan_utils_, AbortScan(_));
- EXPECT_TRUE(scanner_.abortScan().isOk());
+ EXPECT_TRUE(netlink_scanner_->abortScan().isOk());
}
TEST_F(ScannerTest, TestAbortScanNotIssuedIfNoOngoingScan) {
EXPECT_CALL(scan_utils_, AbortScan(_)).Times(0);
- EXPECT_TRUE(scanner_.abortScan().isOk());
+ EXPECT_TRUE(netlink_scanner_->abortScan().isOk());
}
TEST_F(ScannerTest, TestGetScanResults) {
vector<NativeScanResult> scan_results;
EXPECT_CALL(scan_utils_, GetScanResult(_, _)).WillOnce(Return(true));
- EXPECT_TRUE(scanner_.getScanResults(&scan_results).isOk());
+ EXPECT_TRUE(netlink_scanner_->getScanResults(&scan_results).isOk());
}
-//TODO(b/33452931): Add more test cases for ScannerImpl.
+TEST_F(ScannerTest, TestStartPnoScanViaNetlink) {
+ bool success = false;
+ EXPECT_CALL(scan_utils_, StartScheduledScan(_, _, _, _, _, _, _, _)).
+ WillOnce(Return(true));
+ EXPECT_TRUE(netlink_scanner_->startPnoScan(PnoSettings(), &success).isOk());
+ EXPECT_TRUE(success);
+}
+
+TEST_F(ScannerTest, TestStopPnoScanViaNetlink) {
+ bool success = false;
+ // StopScheduledScan() will be called no matter if there is an ongoing
+ // scheduled scan or not. This is for making the system more robust.
+ EXPECT_CALL(scan_utils_, StopScheduledScan(_)).WillOnce(Return(true));
+ EXPECT_TRUE(netlink_scanner_->stopPnoScan(&success).isOk());
+ EXPECT_TRUE(success);
+}
} // namespace wificond
} // namespace android