Home | History | Annotate | Download | only in nexus
      1 /*
      2  * Copyright (C) 2008 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 #include <stdlib.h>
     18 #include <string.h>
     19 #include <errno.h>
     20 
     21 #define LOG_TAG "WifiController"
     22 #include <cutils/log.h>
     23 
     24 #include "Supplicant.h"
     25 #include "WifiController.h"
     26 #include "NetworkManager.h"
     27 #include "ResponseCode.h"
     28 #include "WifiNetwork.h"
     29 #include "ISupplicantEventHandler.h"
     30 #include "SupplicantState.h"
     31 #include "SupplicantStatus.h"
     32 #include "SupplicantAssociatingEvent.h"
     33 #include "SupplicantAssociatedEvent.h"
     34 #include "SupplicantConnectedEvent.h"
     35 #include "SupplicantScanResultsEvent.h"
     36 #include "SupplicantStateChangeEvent.h"
     37 #include "SupplicantConnectionTimeoutEvent.h"
     38 #include "SupplicantDisconnectedEvent.h"
     39 #include "WifiStatusPoller.h"
     40 
     41 WifiController::WifiController(PropertyManager *mPropMngr,
     42                                IControllerHandler *handlers,
     43                                char *modpath, char *modname, char *modargs) :
     44                 Controller("wifi", mPropMngr, handlers) {
     45     strncpy(mModulePath, modpath, sizeof(mModulePath));
     46     strncpy(mModuleName, modname, sizeof(mModuleName));
     47     strncpy(mModuleArgs, modargs, sizeof(mModuleArgs));
     48 
     49     mLatestScanResults = new ScanResultCollection();
     50     pthread_mutex_init(&mLatestScanResultsLock, NULL);
     51 
     52     pthread_mutex_init(&mLock, NULL);
     53 
     54     mSupplicant = new Supplicant(this, this);
     55     mActiveScan = false;
     56     mEnabled = false;
     57     mScanOnly = false;
     58     mPacketFilter = false;
     59     mBluetoothCoexScan = false;
     60     mBluetoothCoexMode = 0;
     61     mCurrentlyConnectedNetworkId = -1;
     62     mStatusPoller = new WifiStatusPoller(this);
     63     mRssiEventThreshold = 5;
     64     mLastLinkSpeed = 0;
     65 
     66     mSupplicantState = SupplicantState::UNKNOWN;
     67 
     68     mStaticProperties.propEnabled = new WifiEnabledProperty(this);
     69     mStaticProperties.propScanOnly = new WifiScanOnlyProperty(this);
     70     mStaticProperties.propAllowedChannels = new WifiAllowedChannelsProperty(this);
     71 
     72     mStaticProperties.propRssiEventThreshold =
     73             new IntegerPropertyHelper("RssiEventThreshold", false, &mRssiEventThreshold);
     74 
     75     mDynamicProperties.propSupplicantState = new WifiSupplicantStateProperty(this);
     76     mDynamicProperties.propActiveScan = new WifiActiveScanProperty(this);
     77     mDynamicProperties.propInterface = new WifiInterfaceProperty(this);
     78     mDynamicProperties.propSearching = new WifiSearchingProperty(this);
     79     mDynamicProperties.propPacketFilter = new WifiPacketFilterProperty(this);
     80     mDynamicProperties.propBluetoothCoexScan = new WifiBluetoothCoexScanProperty(this);
     81     mDynamicProperties.propBluetoothCoexMode = new WifiBluetoothCoexModeProperty(this);
     82     mDynamicProperties.propCurrentNetwork = new WifiCurrentNetworkProperty(this);
     83 
     84     mDynamicProperties.propRssi = new IntegerPropertyHelper("Rssi", true, &mLastRssi);
     85     mDynamicProperties.propLinkSpeed = new IntegerPropertyHelper("LinkSpeed", true, &mLastLinkSpeed);
     86 
     87     mDynamicProperties.propSuspended = new WifiSuspendedProperty(this);
     88     mDynamicProperties.propNetCount = new WifiNetCountProperty(this);
     89     mDynamicProperties.propTriggerScan = new WifiTriggerScanProperty(this);
     90 }
     91 
     92 int WifiController::start() {
     93     mPropMngr->attachProperty("wifi", mStaticProperties.propEnabled);
     94     mPropMngr->attachProperty("wifi", mStaticProperties.propScanOnly);
     95     mPropMngr->attachProperty("wifi", mStaticProperties.propAllowedChannels);
     96     mPropMngr->attachProperty("wifi", mStaticProperties.propRssiEventThreshold);
     97     return 0;
     98 }
     99 
    100 int WifiController::stop() {
    101     mPropMngr->detachProperty("wifi", mStaticProperties.propEnabled);
    102     mPropMngr->detachProperty("wifi", mStaticProperties.propScanOnly);
    103     mPropMngr->detachProperty("wifi", mStaticProperties.propAllowedChannels);
    104     mPropMngr->detachProperty("wifi", mStaticProperties.propRssiEventThreshold);
    105     return 0;
    106 }
    107 
    108 int WifiController::enable() {
    109 
    110     if (!isPoweredUp()) {
    111         LOGI("Powering up");
    112         sendStatusBroadcast("Powering up WiFi hardware");
    113         if (powerUp()) {
    114             LOGE("Powerup failed (%s)", strerror(errno));
    115             return -1;
    116         }
    117     }
    118 
    119     if (mModuleName[0] != '\0' && !isKernelModuleLoaded(mModuleName)) {
    120         LOGI("Loading driver");
    121         sendStatusBroadcast("Loading WiFi driver");
    122         if (loadKernelModule(mModulePath, mModuleArgs)) {
    123             LOGE("Kernel module load failed (%s)", strerror(errno));
    124             goto out_powerdown;
    125         }
    126     }
    127 
    128     if (!isFirmwareLoaded()) {
    129         LOGI("Loading firmware");
    130         sendStatusBroadcast("Loading WiFI firmware");
    131         if (loadFirmware()) {
    132             LOGE("Firmware load failed (%s)", strerror(errno));
    133             goto out_powerdown;
    134         }
    135     }
    136 
    137     if (!mSupplicant->isStarted()) {
    138         LOGI("Starting WPA Supplicant");
    139         sendStatusBroadcast("Starting WPA Supplicant");
    140         if (mSupplicant->start()) {
    141             LOGE("Supplicant start failed (%s)", strerror(errno));
    142             goto out_unloadmodule;
    143         }
    144     }
    145 
    146     if (Controller::bindInterface(mSupplicant->getInterfaceName())) {
    147         LOGE("Error binding interface (%s)", strerror(errno));
    148         goto out_unloadmodule;
    149     }
    150 
    151     if (mSupplicant->refreshNetworkList())
    152         LOGW("Error getting list of networks (%s)", strerror(errno));
    153 
    154     LOGW("TODO: Set # of allowed regulatory channels!");
    155 
    156     mPropMngr->attachProperty("wifi", mDynamicProperties.propSupplicantState);
    157     mPropMngr->attachProperty("wifi", mDynamicProperties.propActiveScan);
    158     mPropMngr->attachProperty("wifi", mDynamicProperties.propInterface);
    159     mPropMngr->attachProperty("wifi", mDynamicProperties.propSearching);
    160     mPropMngr->attachProperty("wifi", mDynamicProperties.propPacketFilter);
    161     mPropMngr->attachProperty("wifi", mDynamicProperties.propBluetoothCoexScan);
    162     mPropMngr->attachProperty("wifi", mDynamicProperties.propBluetoothCoexMode);
    163     mPropMngr->attachProperty("wifi", mDynamicProperties.propCurrentNetwork);
    164     mPropMngr->attachProperty("wifi", mDynamicProperties.propRssi);
    165     mPropMngr->attachProperty("wifi", mDynamicProperties.propLinkSpeed);
    166     mPropMngr->attachProperty("wifi", mDynamicProperties.propSuspended);
    167     mPropMngr->attachProperty("wifi", mDynamicProperties.propNetCount);
    168     mPropMngr->attachProperty("wifi", mDynamicProperties.propTriggerScan);
    169 
    170     LOGI("Enabled successfully");
    171     return 0;
    172 
    173 out_unloadmodule:
    174     if (mModuleName[0] != '\0' && !isKernelModuleLoaded(mModuleName)) {
    175         if (unloadKernelModule(mModuleName)) {
    176             LOGE("Unable to unload module after failure!");
    177         }
    178     }
    179 
    180 out_powerdown:
    181     if (powerDown()) {
    182         LOGE("Unable to powerdown after failure!");
    183     }
    184     return -1;
    185 }
    186 
    187 bool WifiController::getSuspended() {
    188     pthread_mutex_lock(&mLock);
    189     bool r = mSuspended;
    190     pthread_mutex_unlock(&mLock);
    191     return r;
    192 }
    193 
    194 int WifiController::setSuspend(bool suspend) {
    195 
    196     pthread_mutex_lock(&mLock);
    197     if (suspend == mSuspended) {
    198         LOGW("Suspended state already = %d", suspend);
    199         pthread_mutex_unlock(&mLock);
    200         return 0;
    201     }
    202 
    203     if (suspend) {
    204         mHandlers->onControllerSuspending(this);
    205 
    206         char tmp[80];
    207         LOGD("Suspending from supplicant state %s",
    208              SupplicantState::toString(mSupplicantState,
    209                                        tmp,
    210                                        sizeof(tmp)));
    211 
    212         if (mSupplicantState != SupplicantState::IDLE) {
    213             LOGD("Forcing Supplicant disconnect");
    214             if (mSupplicant->disconnect()) {
    215                 LOGW("Error disconnecting (%s)", strerror(errno));
    216             }
    217         }
    218 
    219         LOGD("Stopping Supplicant driver");
    220         if (mSupplicant->stopDriver()) {
    221             LOGE("Error stopping driver (%s)", strerror(errno));
    222             pthread_mutex_unlock(&mLock);
    223             return -1;
    224         }
    225     } else {
    226         LOGD("Resuming");
    227 
    228         if (mSupplicant->startDriver()) {
    229             LOGE("Error resuming driver (%s)", strerror(errno));
    230             pthread_mutex_unlock(&mLock);
    231             return -1;
    232         }
    233         // XXX: set regulatory max channels
    234         if (mScanOnly)
    235             mSupplicant->triggerScan();
    236         else
    237             mSupplicant->reconnect();
    238 
    239         mHandlers->onControllerResumed(this);
    240     }
    241 
    242     mSuspended = suspend;
    243     pthread_mutex_unlock(&mLock);
    244     LOGD("Suspend / Resume completed");
    245     return 0;
    246 }
    247 
    248 void WifiController::sendStatusBroadcast(const char *msg) {
    249     NetworkManager::Instance()->
    250                     getBroadcaster()->
    251                     sendBroadcast(ResponseCode::UnsolicitedInformational, msg, false);
    252 }
    253 
    254 int WifiController::disable() {
    255 
    256     mPropMngr->detachProperty("wifi", mDynamicProperties.propSupplicantState);
    257     mPropMngr->detachProperty("wifi", mDynamicProperties.propActiveScan);
    258     mPropMngr->detachProperty("wifi", mDynamicProperties.propInterface);
    259     mPropMngr->detachProperty("wifi", mDynamicProperties.propSearching);
    260     mPropMngr->detachProperty("wifi", mDynamicProperties.propPacketFilter);
    261     mPropMngr->detachProperty("wifi", mDynamicProperties.propBluetoothCoexScan);
    262     mPropMngr->detachProperty("wifi", mDynamicProperties.propBluetoothCoexMode);
    263     mPropMngr->detachProperty("wifi", mDynamicProperties.propCurrentNetwork);
    264     mPropMngr->detachProperty("wifi", mDynamicProperties.propRssi);
    265     mPropMngr->detachProperty("wifi", mDynamicProperties.propLinkSpeed);
    266     mPropMngr->detachProperty("wifi", mDynamicProperties.propSuspended);
    267     mPropMngr->detachProperty("wifi", mDynamicProperties.propNetCount);
    268 
    269     if (mSupplicant->isStarted()) {
    270         sendStatusBroadcast("Stopping WPA Supplicant");
    271         if (mSupplicant->stop()) {
    272             LOGE("Supplicant stop failed (%s)", strerror(errno));
    273             return -1;
    274         }
    275     } else
    276         LOGW("disable(): Supplicant not running?");
    277 
    278     if (mModuleName[0] != '\0' && isKernelModuleLoaded(mModuleName)) {
    279         sendStatusBroadcast("Unloading WiFi driver");
    280         if (unloadKernelModule(mModuleName)) {
    281             LOGE("Unable to unload module (%s)", strerror(errno));
    282             return -1;
    283         }
    284     }
    285 
    286     if (isPoweredUp()) {
    287         sendStatusBroadcast("Powering down WiFi hardware");
    288         if (powerDown()) {
    289             LOGE("Powerdown failed (%s)", strerror(errno));
    290             return -1;
    291         }
    292     }
    293     return 0;
    294 }
    295 
    296 int WifiController::loadFirmware() {
    297     return 0;
    298 }
    299 
    300 int WifiController::triggerScan() {
    301     pthread_mutex_lock(&mLock);
    302     if (verifyNotSuspended()) {
    303         pthread_mutex_unlock(&mLock);
    304         return -1;
    305     }
    306 
    307     switch (mSupplicantState) {
    308         case SupplicantState::DISCONNECTED:
    309         case SupplicantState::INACTIVE:
    310         case SupplicantState::SCANNING:
    311         case SupplicantState::IDLE:
    312             break;
    313         default:
    314             // Switch to scan only mode
    315             mSupplicant->setApScanMode(2);
    316             break;
    317     }
    318 
    319     int rc = mSupplicant->triggerScan();
    320     pthread_mutex_unlock(&mLock);
    321     return rc;
    322 }
    323 
    324 int WifiController::setActiveScan(bool active) {
    325     pthread_mutex_lock(&mLock);
    326     if (mActiveScan == active) {
    327         pthread_mutex_unlock(&mLock);
    328         return 0;
    329     }
    330     mActiveScan = active;
    331 
    332     int rc = mSupplicant->setScanMode(active);
    333     pthread_mutex_unlock(&mLock);
    334     return rc;
    335 }
    336 
    337 WifiNetwork *WifiController::createNetwork() {
    338     pthread_mutex_lock(&mLock);
    339     WifiNetwork *wn = mSupplicant->createNetwork();
    340     pthread_mutex_unlock(&mLock);
    341     return wn;
    342 }
    343 
    344 int WifiController::removeNetwork(int networkId) {
    345     pthread_mutex_lock(&mLock);
    346     WifiNetwork *wn = mSupplicant->lookupNetwork(networkId);
    347 
    348     if (!wn) {
    349         pthread_mutex_unlock(&mLock);
    350         return -1;
    351     }
    352     int rc = mSupplicant->removeNetwork(wn);
    353     pthread_mutex_unlock(&mLock);
    354     return rc;
    355 }
    356 
    357 ScanResultCollection *WifiController::createScanResults() {
    358     ScanResultCollection *d = new ScanResultCollection();
    359     ScanResultCollection::iterator i;
    360 
    361     pthread_mutex_lock(&mLatestScanResultsLock);
    362     for (i = mLatestScanResults->begin(); i != mLatestScanResults->end(); ++i)
    363         d->push_back((*i)->clone());
    364 
    365     pthread_mutex_unlock(&mLatestScanResultsLock);
    366     return d;
    367 }
    368 
    369 WifiNetworkCollection *WifiController::createNetworkList() {
    370     return mSupplicant->createNetworkList();
    371 }
    372 
    373 int WifiController::setPacketFilter(bool enable) {
    374     int rc;
    375 
    376     pthread_mutex_lock(&mLock);
    377     if (enable)
    378         rc = mSupplicant->enablePacketFilter();
    379     else
    380         rc = mSupplicant->disablePacketFilter();
    381 
    382     if (!rc)
    383         mPacketFilter = enable;
    384     pthread_mutex_unlock(&mLock);
    385     return rc;
    386 }
    387 
    388 int WifiController::setBluetoothCoexistenceScan(bool enable) {
    389     int rc;
    390 
    391     pthread_mutex_lock(&mLock);
    392 
    393     if (enable)
    394         rc = mSupplicant->enableBluetoothCoexistenceScan();
    395     else
    396         rc = mSupplicant->disableBluetoothCoexistenceScan();
    397 
    398     if (!rc)
    399         mBluetoothCoexScan = enable;
    400     pthread_mutex_unlock(&mLock);
    401     return rc;
    402 }
    403 
    404 int WifiController::setScanOnly(bool scanOnly) {
    405     pthread_mutex_lock(&mLock);
    406     int rc = mSupplicant->setApScanMode((scanOnly ? 2 : 1));
    407     if (!rc)
    408         mScanOnly = scanOnly;
    409     if (!mSuspended) {
    410         if (scanOnly)
    411             mSupplicant->disconnect();
    412         else
    413             mSupplicant->reconnect();
    414     }
    415     pthread_mutex_unlock(&mLock);
    416     return rc;
    417 }
    418 
    419 int WifiController::setBluetoothCoexistenceMode(int mode) {
    420     pthread_mutex_lock(&mLock);
    421     int rc = mSupplicant->setBluetoothCoexistenceMode(mode);
    422     if (!rc)
    423         mBluetoothCoexMode = mode;
    424     pthread_mutex_unlock(&mLock);
    425     return rc;
    426 }
    427 
    428 void WifiController::onAssociatingEvent(SupplicantAssociatingEvent *evt) {
    429     LOGD("onAssociatingEvent(%s, %s, %d)",
    430          (evt->getBssid() ? evt->getBssid() : "n/a"),
    431          (evt->getSsid() ? evt->getSsid() : "n/a"),
    432          evt->getFreq());
    433 }
    434 
    435 void WifiController::onAssociatedEvent(SupplicantAssociatedEvent *evt) {
    436     LOGD("onAssociatedEvent(%s)", evt->getBssid());
    437 }
    438 
    439 void WifiController::onConnectedEvent(SupplicantConnectedEvent *evt) {
    440     LOGD("onConnectedEvent(%s, %d)", evt->getBssid(), evt->getReassociated());
    441     SupplicantStatus *ss = mSupplicant->getStatus();
    442     WifiNetwork *wn;
    443 
    444     if (ss->getWpaState() != SupplicantState::COMPLETED) {
    445         char tmp[32];
    446 
    447         LOGW("onConnected() with SupplicantState = %s!",
    448              SupplicantState::toString(ss->getWpaState(), tmp,
    449              sizeof(tmp)));
    450         return;
    451     }
    452 
    453     if (ss->getId() == -1) {
    454         LOGW("onConnected() with id = -1!");
    455         return;
    456     }
    457 
    458     mCurrentlyConnectedNetworkId = ss->getId();
    459     if (!(wn = mSupplicant->lookupNetwork(ss->getId()))) {
    460         LOGW("Error looking up connected network id %d (%s)",
    461              ss->getId(), strerror(errno));
    462         return;
    463     }
    464 
    465     delete ss;
    466     mHandlers->onInterfaceConnected(this);
    467 }
    468 
    469 void WifiController::onScanResultsEvent(SupplicantScanResultsEvent *evt) {
    470     char *reply;
    471 
    472     if (!(reply = (char *) malloc(4096))) {
    473         LOGE("Out of memory");
    474         return;
    475     }
    476 
    477     mNumScanResultsSinceLastStateChange++;
    478     if (mNumScanResultsSinceLastStateChange >= 3)
    479         mIsSupplicantSearching = false;
    480 
    481     size_t len = 4096;
    482 
    483     if (mSupplicant->sendCommand("SCAN_RESULTS", reply, &len)) {
    484         LOGW("onScanResultsEvent: Error getting scan results (%s)",
    485              strerror(errno));
    486         free(reply);
    487         return;
    488     }
    489 
    490     pthread_mutex_lock(&mLatestScanResultsLock);
    491     if (!mLatestScanResults->empty()) {
    492         ScanResultCollection::iterator i;
    493 
    494         for (i = mLatestScanResults->begin();
    495              i !=mLatestScanResults->end(); ++i) {
    496             delete *i;
    497         }
    498         mLatestScanResults->clear();
    499     }
    500 
    501     char *linep;
    502     char *linep_next = NULL;
    503 
    504     if (!strtok_r(reply, "\n", &linep_next)) {
    505         free(reply);
    506         pthread_mutex_unlock(&mLatestScanResultsLock);
    507         return;
    508     }
    509 
    510     while((linep = strtok_r(NULL, "\n", &linep_next)))
    511         mLatestScanResults->push_back(new ScanResult(linep));
    512 
    513     // Switch handling of scan results back to normal mode
    514     mSupplicant->setApScanMode(1);
    515 
    516     char *tmp;
    517     asprintf(&tmp, "Scan results ready (%d)", mLatestScanResults->size());
    518     NetworkManager::Instance()->getBroadcaster()->
    519                                 sendBroadcast(ResponseCode::ScanResultsReady,
    520                                               tmp, false);
    521     free(tmp);
    522     pthread_mutex_unlock(&mLatestScanResultsLock);
    523     free(reply);
    524 }
    525 
    526 void WifiController::onStateChangeEvent(SupplicantStateChangeEvent *evt) {
    527     char tmp[32];
    528     char tmp2[32];
    529 
    530     if (evt->getState() == mSupplicantState)
    531         return;
    532 
    533     LOGD("onStateChangeEvent(%s -> %s)",
    534          SupplicantState::toString(mSupplicantState, tmp, sizeof(tmp)),
    535          SupplicantState::toString(evt->getState(), tmp2, sizeof(tmp2)));
    536 
    537     if (evt->getState() != SupplicantState::SCANNING) {
    538         mIsSupplicantSearching = true;
    539         mNumScanResultsSinceLastStateChange = 0;
    540     }
    541 
    542     char *tmp3;
    543     asprintf(&tmp3,
    544              "Supplicant state changed from %d (%s) -> %d (%s)",
    545              mSupplicantState, tmp, evt->getState(), tmp2);
    546 
    547     mSupplicantState = evt->getState();
    548 
    549     if (mSupplicantState == SupplicantState::COMPLETED) {
    550         mStatusPoller->start();
    551     } else if (mStatusPoller->isStarted()) {
    552         mStatusPoller->stop();
    553     }
    554 
    555     NetworkManager::Instance()->getBroadcaster()->
    556                                 sendBroadcast(ResponseCode::SupplicantStateChange,
    557                                               tmp3, false);
    558     free(tmp3);
    559 }
    560 
    561 void WifiController::onConnectionTimeoutEvent(SupplicantConnectionTimeoutEvent *evt) {
    562     LOGD("onConnectionTimeoutEvent(%s)", evt->getBssid());
    563 }
    564 
    565 void WifiController::onDisconnectedEvent(SupplicantDisconnectedEvent *evt) {
    566     mCurrentlyConnectedNetworkId = -1;
    567     mHandlers->onInterfaceDisconnected(this);
    568 }
    569 
    570 #if 0
    571 void WifiController::onTerminatingEvent(SupplicantEvent *evt) {
    572     LOGD("onTerminatingEvent(%s)", evt->getEvent());
    573 }
    574 
    575 void WifiController::onPasswordChangedEvent(SupplicantEvent *evt) {
    576     LOGD("onPasswordChangedEvent(%s)", evt->getEvent());
    577 }
    578 
    579 void WifiController::onEapNotificationEvent(SupplicantEvent *evt) {
    580     LOGD("onEapNotificationEvent(%s)", evt->getEvent());
    581 }
    582 
    583 void WifiController::onEapStartedEvent(SupplicantEvent *evt) {
    584     LOGD("onEapStartedEvent(%s)", evt->getEvent());
    585 }
    586 
    587 void WifiController::onEapMethodEvent(SupplicantEvent *evt) {
    588     LOGD("onEapMethodEvent(%s)", evt->getEvent());
    589 }
    590 
    591 void WifiController::onEapSuccessEvent(SupplicantEvent *evt) {
    592     LOGD("onEapSuccessEvent(%s)", evt->getEvent());
    593 }
    594 
    595 void WifiController::onEapFailureEvent(SupplicantEvent *evt) {
    596     LOGD("onEapFailureEvent(%s)", evt->getEvent());
    597 }
    598 
    599 void WifiController::onLinkSpeedEvent(SupplicantEvent *evt) {
    600     LOGD("onLinkSpeedEvent(%s)", evt->getEvent());
    601 }
    602 
    603 void WifiController::onDriverStateEvent(SupplicantEvent *evt) {
    604     LOGD("onDriverStateEvent(%s)", evt->getEvent());
    605 }
    606 #endif
    607 
    608 void WifiController::onStatusPollInterval() {
    609     pthread_mutex_lock(&mLock);
    610     int rssi;
    611     if (mSupplicant->getRssi(&rssi)) {
    612         LOGE("Failed to get rssi (%s)", strerror(errno));
    613         pthread_mutex_unlock(&mLock);
    614         return;
    615     }
    616 
    617     if (abs(mLastRssi - rssi) > mRssiEventThreshold) {
    618         char *tmp3;
    619         asprintf(&tmp3, "RSSI changed from %d -> %d",
    620                  mLastRssi, rssi);
    621         mLastRssi = rssi;
    622         NetworkManager::Instance()->getBroadcaster()->
    623                                sendBroadcast(ResponseCode::RssiChange,
    624                                              tmp3, false);
    625         free(tmp3);
    626     }
    627 
    628     int linkspeed = mSupplicant->getLinkSpeed();
    629     if (linkspeed != mLastLinkSpeed) {
    630         char *tmp3;
    631         asprintf(&tmp3, "Link speed changed from %d -> %d",
    632                  mLastLinkSpeed, linkspeed);
    633         mLastLinkSpeed = linkspeed;
    634         NetworkManager::Instance()->getBroadcaster()->
    635                                sendBroadcast(ResponseCode::LinkSpeedChange,
    636                                              tmp3, false);
    637         free(tmp3);
    638 
    639     }
    640     pthread_mutex_unlock(&mLock);
    641 }
    642 
    643 int WifiController::verifyNotSuspended() {
    644     if (mSuspended) {
    645         errno = ESHUTDOWN;
    646         return -1;
    647     }
    648     return 0;
    649 }
    650 
    651 /*
    652  * Property inner classes
    653  */
    654 
    655 WifiController::WifiIntegerProperty::WifiIntegerProperty(WifiController *c,
    656                                                          const char *name,
    657                                                          bool ro,
    658                                                          int elements) :
    659                 IntegerProperty(name, ro, elements) {
    660     mWc = c;
    661 }
    662 
    663 WifiController::WifiStringProperty::WifiStringProperty(WifiController *c,
    664                                                        const char *name,
    665                                                        bool ro, int elements) :
    666                 StringProperty(name, ro, elements) {
    667     mWc = c;
    668 }
    669 
    670 WifiController::WifiEnabledProperty::WifiEnabledProperty(WifiController *c) :
    671                 WifiIntegerProperty(c, "Enabled", false, 1) {
    672 }
    673 
    674 int WifiController::WifiEnabledProperty::get(int idx, int *buffer) {
    675     *buffer = mWc->mEnabled;
    676     return 0;
    677 }
    678 int WifiController::WifiEnabledProperty::set(int idx, int value) {
    679     int rc = (value ? mWc->enable() : mWc->disable());
    680     if (!rc)
    681         mWc->mEnabled = value;
    682     return rc;
    683 }
    684 
    685 WifiController::WifiScanOnlyProperty::WifiScanOnlyProperty(WifiController *c) :
    686                 WifiIntegerProperty(c, "ScanOnly", false, 1) {
    687 }
    688 int WifiController::WifiScanOnlyProperty::get(int idx, int *buffer) {
    689     *buffer = mWc->mScanOnly;
    690     return 0;
    691 }
    692 int WifiController::WifiScanOnlyProperty::set(int idx, int value) {
    693     return mWc->setScanOnly(value == 1);
    694 }
    695 
    696 WifiController::WifiAllowedChannelsProperty::WifiAllowedChannelsProperty(WifiController *c) :
    697                 WifiIntegerProperty(c, "AllowedChannels", false, 1) {
    698 }
    699 int WifiController::WifiAllowedChannelsProperty::get(int idx, int *buffer) {
    700     *buffer = mWc->mNumAllowedChannels;
    701     return 0;
    702 }
    703 int WifiController::WifiAllowedChannelsProperty::set(int idx, int value) {
    704     // XXX: IMPL
    705     errno = ENOSYS;
    706     return -1;
    707 }
    708 
    709 WifiController::WifiSupplicantStateProperty::WifiSupplicantStateProperty(WifiController *c) :
    710                 WifiStringProperty(c, "SupplicantState", true, 1) {
    711 }
    712 int WifiController::WifiSupplicantStateProperty::get(int idx, char *buffer, size_t max) {
    713     if (!SupplicantState::toString(mWc->mSupplicantState, buffer, max))
    714         return -1;
    715     return 0;
    716 }
    717 
    718 WifiController::WifiActiveScanProperty::WifiActiveScanProperty(WifiController *c) :
    719                 WifiIntegerProperty(c, "ActiveScan", false, 1) {
    720 }
    721 int WifiController::WifiActiveScanProperty::get(int idx, int *buffer) {
    722     *buffer = mWc->mActiveScan;
    723     return 0;
    724 }
    725 int WifiController::WifiActiveScanProperty::set(int idx, int value) {
    726     return mWc->setActiveScan(value);
    727 }
    728 
    729 WifiController::WifiInterfaceProperty::WifiInterfaceProperty(WifiController *c) :
    730                 WifiStringProperty(c, "Interface", true, 1) {
    731 }
    732 int WifiController::WifiInterfaceProperty::get(int idx, char *buffer, size_t max) {
    733     strncpy(buffer, (mWc->getBoundInterface() ? mWc->getBoundInterface() : "none"), max);
    734     return 0;
    735 }
    736 
    737 WifiController::WifiSearchingProperty::WifiSearchingProperty(WifiController *c) :
    738                 WifiIntegerProperty(c, "Searching", true, 1) {
    739 }
    740 int WifiController::WifiSearchingProperty::get(int idx, int *buffer) {
    741     *buffer = mWc->mIsSupplicantSearching;
    742     return 0;
    743 }
    744 
    745 WifiController::WifiPacketFilterProperty::WifiPacketFilterProperty(WifiController *c) :
    746                 WifiIntegerProperty(c, "PacketFilter", false, 1) {
    747 }
    748 int WifiController::WifiPacketFilterProperty::get(int idx, int *buffer) {
    749     *buffer = mWc->mPacketFilter;
    750     return 0;
    751 }
    752 int WifiController::WifiPacketFilterProperty::set(int idx, int value) {
    753     return mWc->setPacketFilter(value);
    754 }
    755 
    756 WifiController::WifiBluetoothCoexScanProperty::WifiBluetoothCoexScanProperty(WifiController *c) :
    757                 WifiIntegerProperty(c, "BluetoothCoexScan", false, 1) {
    758 }
    759 int WifiController::WifiBluetoothCoexScanProperty::get(int idx, int *buffer) {
    760     *buffer = mWc->mBluetoothCoexScan;
    761     return 0;
    762 }
    763 int WifiController::WifiBluetoothCoexScanProperty::set(int idx, int value) {
    764     return mWc->setBluetoothCoexistenceScan(value == 1);
    765 }
    766 
    767 WifiController::WifiBluetoothCoexModeProperty::WifiBluetoothCoexModeProperty(WifiController *c) :
    768                 WifiIntegerProperty(c, "BluetoothCoexMode", false, 1) {
    769 }
    770 int WifiController::WifiBluetoothCoexModeProperty::get(int idx, int *buffer) {
    771     *buffer = mWc->mBluetoothCoexMode;
    772     return 0;
    773 }
    774 int WifiController::WifiBluetoothCoexModeProperty::set(int idx, int value) {
    775     return mWc->setBluetoothCoexistenceMode(value);
    776 }
    777 
    778 WifiController::WifiCurrentNetworkProperty::WifiCurrentNetworkProperty(WifiController *c) :
    779                 WifiIntegerProperty(c, "CurrentlyConnectedNetworkId", true, 1) {
    780 }
    781 int WifiController::WifiCurrentNetworkProperty::get(int idx, int *buffer) {
    782     *buffer = mWc->mCurrentlyConnectedNetworkId;
    783     return 0;
    784 }
    785 
    786 WifiController::WifiSuspendedProperty::WifiSuspendedProperty(WifiController *c) :
    787                 WifiIntegerProperty(c, "Suspended", false, 1) {
    788 }
    789 int WifiController::WifiSuspendedProperty::get(int idx, int *buffer) {
    790     *buffer = mWc->getSuspended();
    791     return 0;
    792 }
    793 int WifiController::WifiSuspendedProperty::set(int idx, int value) {
    794     return mWc->setSuspend(value == 1);
    795 }
    796 
    797 WifiController::WifiNetCountProperty::WifiNetCountProperty(WifiController *c) :
    798                 WifiIntegerProperty(c, "NetCount", true, 1) {
    799 }
    800 int WifiController::WifiNetCountProperty::get(int idx, int *buffer) {
    801     pthread_mutex_lock(&mWc->mLock);
    802     *buffer = mWc->mSupplicant->getNetworkCount();
    803     pthread_mutex_unlock(&mWc->mLock);
    804     return 0;
    805 }
    806 
    807 WifiController::WifiTriggerScanProperty::WifiTriggerScanProperty(WifiController *c) :
    808                 WifiIntegerProperty(c, "TriggerScan", false, 1) {
    809 }
    810 int WifiController::WifiTriggerScanProperty::get(int idx, int *buffer) {
    811     // XXX: Need action type
    812     *buffer = 0;
    813     return 0;
    814 }
    815 
    816 int WifiController::WifiTriggerScanProperty::set(int idx, int value) {
    817     return mWc->triggerScan();
    818 }
    819 
    820