driver_nl80211_event.c 76 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355235623572358235923602361236223632364236523662367236823692370237123722373237423752376237723782379238023812382238323842385238623872388238923902391239223932394239523962397239823992400240124022403240424052406240724082409241024112412241324142415241624172418241924202421242224232424242524262427242824292430243124322433243424352436243724382439244024412442244324442445244624472448244924502451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499250025012502250325042505250625072508250925102511251225132514251525162517251825192520252125222523252425252526252725282529253025312532253325342535253625372538253925402541254225432544254525462547254825492550255125522553255425552556255725582559256025612562256325642565256625672568256925702571257225732574257525762577257825792580258125822583258425852586258725882589259025912592259325942595259625972598259926002601260226032604260526062607260826092610261126122613261426152616261726182619
  1. /*
  2. * Driver interaction with Linux nl80211/cfg80211 - Event processing
  3. * Copyright (c) 2002-2017, Jouni Malinen <j@w1.fi>
  4. * Copyright (c) 2007, Johannes Berg <johannes@sipsolutions.net>
  5. * Copyright (c) 2009-2010, Atheros Communications
  6. *
  7. * This software may be distributed under the terms of the BSD license.
  8. * See README for more details.
  9. */
  10. #include "includes.h"
  11. #include <netlink/genl/genl.h>
  12. #include "utils/common.h"
  13. #include "utils/eloop.h"
  14. #include "common/qca-vendor.h"
  15. #include "common/qca-vendor-attr.h"
  16. #include "common/ieee802_11_defs.h"
  17. #include "common/ieee802_11_common.h"
  18. #include "driver_nl80211.h"
  19. static const char * nl80211_command_to_string(enum nl80211_commands cmd)
  20. {
  21. #define C2S(x) case x: return #x;
  22. switch (cmd) {
  23. C2S(NL80211_CMD_UNSPEC)
  24. C2S(NL80211_CMD_GET_WIPHY)
  25. C2S(NL80211_CMD_SET_WIPHY)
  26. C2S(NL80211_CMD_NEW_WIPHY)
  27. C2S(NL80211_CMD_DEL_WIPHY)
  28. C2S(NL80211_CMD_GET_INTERFACE)
  29. C2S(NL80211_CMD_SET_INTERFACE)
  30. C2S(NL80211_CMD_NEW_INTERFACE)
  31. C2S(NL80211_CMD_DEL_INTERFACE)
  32. C2S(NL80211_CMD_GET_KEY)
  33. C2S(NL80211_CMD_SET_KEY)
  34. C2S(NL80211_CMD_NEW_KEY)
  35. C2S(NL80211_CMD_DEL_KEY)
  36. C2S(NL80211_CMD_GET_BEACON)
  37. C2S(NL80211_CMD_SET_BEACON)
  38. C2S(NL80211_CMD_START_AP)
  39. C2S(NL80211_CMD_STOP_AP)
  40. C2S(NL80211_CMD_GET_STATION)
  41. C2S(NL80211_CMD_SET_STATION)
  42. C2S(NL80211_CMD_NEW_STATION)
  43. C2S(NL80211_CMD_DEL_STATION)
  44. C2S(NL80211_CMD_GET_MPATH)
  45. C2S(NL80211_CMD_SET_MPATH)
  46. C2S(NL80211_CMD_NEW_MPATH)
  47. C2S(NL80211_CMD_DEL_MPATH)
  48. C2S(NL80211_CMD_SET_BSS)
  49. C2S(NL80211_CMD_SET_REG)
  50. C2S(NL80211_CMD_REQ_SET_REG)
  51. C2S(NL80211_CMD_GET_MESH_CONFIG)
  52. C2S(NL80211_CMD_SET_MESH_CONFIG)
  53. C2S(NL80211_CMD_SET_MGMT_EXTRA_IE)
  54. C2S(NL80211_CMD_GET_REG)
  55. C2S(NL80211_CMD_GET_SCAN)
  56. C2S(NL80211_CMD_TRIGGER_SCAN)
  57. C2S(NL80211_CMD_NEW_SCAN_RESULTS)
  58. C2S(NL80211_CMD_SCAN_ABORTED)
  59. C2S(NL80211_CMD_REG_CHANGE)
  60. C2S(NL80211_CMD_AUTHENTICATE)
  61. C2S(NL80211_CMD_ASSOCIATE)
  62. C2S(NL80211_CMD_DEAUTHENTICATE)
  63. C2S(NL80211_CMD_DISASSOCIATE)
  64. C2S(NL80211_CMD_MICHAEL_MIC_FAILURE)
  65. C2S(NL80211_CMD_REG_BEACON_HINT)
  66. C2S(NL80211_CMD_JOIN_IBSS)
  67. C2S(NL80211_CMD_LEAVE_IBSS)
  68. C2S(NL80211_CMD_TESTMODE)
  69. C2S(NL80211_CMD_CONNECT)
  70. C2S(NL80211_CMD_ROAM)
  71. C2S(NL80211_CMD_DISCONNECT)
  72. C2S(NL80211_CMD_SET_WIPHY_NETNS)
  73. C2S(NL80211_CMD_GET_SURVEY)
  74. C2S(NL80211_CMD_NEW_SURVEY_RESULTS)
  75. C2S(NL80211_CMD_SET_PMKSA)
  76. C2S(NL80211_CMD_DEL_PMKSA)
  77. C2S(NL80211_CMD_FLUSH_PMKSA)
  78. C2S(NL80211_CMD_REMAIN_ON_CHANNEL)
  79. C2S(NL80211_CMD_CANCEL_REMAIN_ON_CHANNEL)
  80. C2S(NL80211_CMD_SET_TX_BITRATE_MASK)
  81. C2S(NL80211_CMD_REGISTER_FRAME)
  82. C2S(NL80211_CMD_FRAME)
  83. C2S(NL80211_CMD_FRAME_TX_STATUS)
  84. C2S(NL80211_CMD_SET_POWER_SAVE)
  85. C2S(NL80211_CMD_GET_POWER_SAVE)
  86. C2S(NL80211_CMD_SET_CQM)
  87. C2S(NL80211_CMD_NOTIFY_CQM)
  88. C2S(NL80211_CMD_SET_CHANNEL)
  89. C2S(NL80211_CMD_SET_WDS_PEER)
  90. C2S(NL80211_CMD_FRAME_WAIT_CANCEL)
  91. C2S(NL80211_CMD_JOIN_MESH)
  92. C2S(NL80211_CMD_LEAVE_MESH)
  93. C2S(NL80211_CMD_UNPROT_DEAUTHENTICATE)
  94. C2S(NL80211_CMD_UNPROT_DISASSOCIATE)
  95. C2S(NL80211_CMD_NEW_PEER_CANDIDATE)
  96. C2S(NL80211_CMD_GET_WOWLAN)
  97. C2S(NL80211_CMD_SET_WOWLAN)
  98. C2S(NL80211_CMD_START_SCHED_SCAN)
  99. C2S(NL80211_CMD_STOP_SCHED_SCAN)
  100. C2S(NL80211_CMD_SCHED_SCAN_RESULTS)
  101. C2S(NL80211_CMD_SCHED_SCAN_STOPPED)
  102. C2S(NL80211_CMD_SET_REKEY_OFFLOAD)
  103. C2S(NL80211_CMD_PMKSA_CANDIDATE)
  104. C2S(NL80211_CMD_TDLS_OPER)
  105. C2S(NL80211_CMD_TDLS_MGMT)
  106. C2S(NL80211_CMD_UNEXPECTED_FRAME)
  107. C2S(NL80211_CMD_PROBE_CLIENT)
  108. C2S(NL80211_CMD_REGISTER_BEACONS)
  109. C2S(NL80211_CMD_UNEXPECTED_4ADDR_FRAME)
  110. C2S(NL80211_CMD_SET_NOACK_MAP)
  111. C2S(NL80211_CMD_CH_SWITCH_NOTIFY)
  112. C2S(NL80211_CMD_START_P2P_DEVICE)
  113. C2S(NL80211_CMD_STOP_P2P_DEVICE)
  114. C2S(NL80211_CMD_CONN_FAILED)
  115. C2S(NL80211_CMD_SET_MCAST_RATE)
  116. C2S(NL80211_CMD_SET_MAC_ACL)
  117. C2S(NL80211_CMD_RADAR_DETECT)
  118. C2S(NL80211_CMD_GET_PROTOCOL_FEATURES)
  119. C2S(NL80211_CMD_UPDATE_FT_IES)
  120. C2S(NL80211_CMD_FT_EVENT)
  121. C2S(NL80211_CMD_CRIT_PROTOCOL_START)
  122. C2S(NL80211_CMD_CRIT_PROTOCOL_STOP)
  123. C2S(NL80211_CMD_GET_COALESCE)
  124. C2S(NL80211_CMD_SET_COALESCE)
  125. C2S(NL80211_CMD_CHANNEL_SWITCH)
  126. C2S(NL80211_CMD_VENDOR)
  127. C2S(NL80211_CMD_SET_QOS_MAP)
  128. C2S(NL80211_CMD_ADD_TX_TS)
  129. C2S(NL80211_CMD_DEL_TX_TS)
  130. C2S(NL80211_CMD_EXTERNAL_AUTH)
  131. C2S(NL80211_CMD_STA_OPMODE_CHANGED)
  132. default:
  133. return "NL80211_CMD_UNKNOWN";
  134. }
  135. #undef C2S
  136. }
  137. static void mlme_event_auth(struct wpa_driver_nl80211_data *drv,
  138. const u8 *frame, size_t len)
  139. {
  140. const struct ieee80211_mgmt *mgmt;
  141. union wpa_event_data event;
  142. if (!(drv->capa.flags & WPA_DRIVER_FLAGS_SME) &&
  143. drv->force_connect_cmd) {
  144. /*
  145. * Avoid reporting two association events that would confuse
  146. * the core code.
  147. */
  148. wpa_printf(MSG_DEBUG,
  149. "nl80211: Ignore auth event when using driver SME");
  150. return;
  151. }
  152. wpa_printf(MSG_DEBUG, "nl80211: Authenticate event");
  153. mgmt = (const struct ieee80211_mgmt *) frame;
  154. if (len < 24 + sizeof(mgmt->u.auth)) {
  155. wpa_printf(MSG_DEBUG, "nl80211: Too short association event "
  156. "frame");
  157. return;
  158. }
  159. os_memcpy(drv->auth_bssid, mgmt->sa, ETH_ALEN);
  160. os_memset(drv->auth_attempt_bssid, 0, ETH_ALEN);
  161. os_memset(&event, 0, sizeof(event));
  162. os_memcpy(event.auth.peer, mgmt->sa, ETH_ALEN);
  163. event.auth.auth_type = le_to_host16(mgmt->u.auth.auth_alg);
  164. event.auth.auth_transaction =
  165. le_to_host16(mgmt->u.auth.auth_transaction);
  166. event.auth.status_code = le_to_host16(mgmt->u.auth.status_code);
  167. if (len > 24 + sizeof(mgmt->u.auth)) {
  168. event.auth.ies = mgmt->u.auth.variable;
  169. event.auth.ies_len = len - 24 - sizeof(mgmt->u.auth);
  170. }
  171. wpa_supplicant_event(drv->ctx, EVENT_AUTH, &event);
  172. }
  173. static void nl80211_parse_wmm_params(struct nlattr *wmm_attr,
  174. struct wmm_params *wmm_params)
  175. {
  176. struct nlattr *wmm_info[NL80211_STA_WME_MAX + 1];
  177. static struct nla_policy wme_policy[NL80211_STA_WME_MAX + 1] = {
  178. [NL80211_STA_WME_UAPSD_QUEUES] = { .type = NLA_U8 },
  179. };
  180. if (!wmm_attr ||
  181. nla_parse_nested(wmm_info, NL80211_STA_WME_MAX, wmm_attr,
  182. wme_policy) ||
  183. !wmm_info[NL80211_STA_WME_UAPSD_QUEUES])
  184. return;
  185. wmm_params->uapsd_queues =
  186. nla_get_u8(wmm_info[NL80211_STA_WME_UAPSD_QUEUES]);
  187. wmm_params->info_bitmap |= WMM_PARAMS_UAPSD_QUEUES_INFO;
  188. }
  189. static void mlme_event_assoc(struct wpa_driver_nl80211_data *drv,
  190. const u8 *frame, size_t len, struct nlattr *wmm)
  191. {
  192. const struct ieee80211_mgmt *mgmt;
  193. union wpa_event_data event;
  194. u16 status;
  195. int ssid_len;
  196. if (!(drv->capa.flags & WPA_DRIVER_FLAGS_SME) &&
  197. drv->force_connect_cmd) {
  198. /*
  199. * Avoid reporting two association events that would confuse
  200. * the core code.
  201. */
  202. wpa_printf(MSG_DEBUG,
  203. "nl80211: Ignore assoc event when using driver SME");
  204. return;
  205. }
  206. wpa_printf(MSG_DEBUG, "nl80211: Associate event");
  207. mgmt = (const struct ieee80211_mgmt *) frame;
  208. if (len < 24 + sizeof(mgmt->u.assoc_resp)) {
  209. wpa_printf(MSG_DEBUG, "nl80211: Too short association event "
  210. "frame");
  211. return;
  212. }
  213. status = le_to_host16(mgmt->u.assoc_resp.status_code);
  214. if (status != WLAN_STATUS_SUCCESS) {
  215. os_memset(&event, 0, sizeof(event));
  216. event.assoc_reject.bssid = mgmt->bssid;
  217. if (len > 24 + sizeof(mgmt->u.assoc_resp)) {
  218. event.assoc_reject.resp_ies =
  219. (u8 *) mgmt->u.assoc_resp.variable;
  220. event.assoc_reject.resp_ies_len =
  221. len - 24 - sizeof(mgmt->u.assoc_resp);
  222. }
  223. event.assoc_reject.status_code = status;
  224. wpa_supplicant_event(drv->ctx, EVENT_ASSOC_REJECT, &event);
  225. return;
  226. }
  227. drv->associated = 1;
  228. os_memcpy(drv->bssid, mgmt->sa, ETH_ALEN);
  229. os_memcpy(drv->prev_bssid, mgmt->sa, ETH_ALEN);
  230. os_memset(&event, 0, sizeof(event));
  231. event.assoc_info.resp_frame = frame;
  232. event.assoc_info.resp_frame_len = len;
  233. if (len > 24 + sizeof(mgmt->u.assoc_resp)) {
  234. event.assoc_info.resp_ies = (u8 *) mgmt->u.assoc_resp.variable;
  235. event.assoc_info.resp_ies_len =
  236. len - 24 - sizeof(mgmt->u.assoc_resp);
  237. }
  238. event.assoc_info.freq = drv->assoc_freq;
  239. /* When this association was initiated outside of wpa_supplicant,
  240. * drv->ssid needs to be set here to satisfy later checking. */
  241. ssid_len = nl80211_get_assoc_ssid(drv, drv->ssid);
  242. if (ssid_len > 0) {
  243. drv->ssid_len = ssid_len;
  244. wpa_printf(MSG_DEBUG,
  245. "nl80211: Set drv->ssid based on scan res info to '%s'",
  246. wpa_ssid_txt(drv->ssid, drv->ssid_len));
  247. }
  248. nl80211_parse_wmm_params(wmm, &event.assoc_info.wmm_params);
  249. wpa_supplicant_event(drv->ctx, EVENT_ASSOC, &event);
  250. }
  251. static void mlme_event_connect(struct wpa_driver_nl80211_data *drv,
  252. enum nl80211_commands cmd, struct nlattr *status,
  253. struct nlattr *addr, struct nlattr *req_ie,
  254. struct nlattr *resp_ie,
  255. struct nlattr *timed_out,
  256. struct nlattr *timeout_reason,
  257. struct nlattr *authorized,
  258. struct nlattr *key_replay_ctr,
  259. struct nlattr *ptk_kck,
  260. struct nlattr *ptk_kek,
  261. struct nlattr *subnet_status,
  262. struct nlattr *fils_erp_next_seq_num,
  263. struct nlattr *fils_pmk,
  264. struct nlattr *fils_pmkid)
  265. {
  266. union wpa_event_data event;
  267. const u8 *ssid = NULL;
  268. u16 status_code;
  269. int ssid_len;
  270. if (drv->capa.flags & WPA_DRIVER_FLAGS_SME) {
  271. /*
  272. * Avoid reporting two association events that would confuse
  273. * the core code.
  274. */
  275. wpa_printf(MSG_DEBUG, "nl80211: Ignore connect event (cmd=%d) "
  276. "when using userspace SME", cmd);
  277. return;
  278. }
  279. drv->connect_reassoc = 0;
  280. status_code = status ? nla_get_u16(status) : WLAN_STATUS_SUCCESS;
  281. if (cmd == NL80211_CMD_CONNECT) {
  282. wpa_printf(MSG_DEBUG,
  283. "nl80211: Connect event (status=%u ignore_next_local_disconnect=%d)",
  284. status_code, drv->ignore_next_local_disconnect);
  285. } else if (cmd == NL80211_CMD_ROAM) {
  286. wpa_printf(MSG_DEBUG, "nl80211: Roam event");
  287. }
  288. os_memset(&event, 0, sizeof(event));
  289. if (cmd == NL80211_CMD_CONNECT && status_code != WLAN_STATUS_SUCCESS) {
  290. if (addr)
  291. event.assoc_reject.bssid = nla_data(addr);
  292. if (drv->ignore_next_local_disconnect) {
  293. drv->ignore_next_local_disconnect = 0;
  294. if (!event.assoc_reject.bssid ||
  295. (os_memcmp(event.assoc_reject.bssid,
  296. drv->auth_attempt_bssid,
  297. ETH_ALEN) != 0)) {
  298. /*
  299. * Ignore the event that came without a BSSID or
  300. * for the old connection since this is likely
  301. * not relevant to the new Connect command.
  302. */
  303. wpa_printf(MSG_DEBUG,
  304. "nl80211: Ignore connection failure event triggered during reassociation");
  305. return;
  306. }
  307. }
  308. if (resp_ie) {
  309. event.assoc_reject.resp_ies = nla_data(resp_ie);
  310. event.assoc_reject.resp_ies_len = nla_len(resp_ie);
  311. }
  312. event.assoc_reject.status_code = status_code;
  313. event.assoc_reject.timed_out = timed_out != NULL;
  314. if (timed_out && timeout_reason) {
  315. enum nl80211_timeout_reason reason;
  316. reason = nla_get_u32(timeout_reason);
  317. switch (reason) {
  318. case NL80211_TIMEOUT_SCAN:
  319. event.assoc_reject.timeout_reason = "scan";
  320. break;
  321. case NL80211_TIMEOUT_AUTH:
  322. event.assoc_reject.timeout_reason = "auth";
  323. break;
  324. case NL80211_TIMEOUT_ASSOC:
  325. event.assoc_reject.timeout_reason = "assoc";
  326. break;
  327. default:
  328. break;
  329. }
  330. }
  331. if (fils_erp_next_seq_num)
  332. event.assoc_reject.fils_erp_next_seq_num =
  333. nla_get_u16(fils_erp_next_seq_num);
  334. wpa_supplicant_event(drv->ctx, EVENT_ASSOC_REJECT, &event);
  335. return;
  336. }
  337. drv->associated = 1;
  338. if (addr) {
  339. os_memcpy(drv->bssid, nla_data(addr), ETH_ALEN);
  340. os_memcpy(drv->prev_bssid, drv->bssid, ETH_ALEN);
  341. }
  342. if (req_ie) {
  343. event.assoc_info.req_ies = nla_data(req_ie);
  344. event.assoc_info.req_ies_len = nla_len(req_ie);
  345. if (cmd == NL80211_CMD_ROAM) {
  346. ssid = get_ie(event.assoc_info.req_ies,
  347. event.assoc_info.req_ies_len,
  348. WLAN_EID_SSID);
  349. if (ssid && ssid[1] > 0 && ssid[1] <= 32) {
  350. drv->ssid_len = ssid[1];
  351. os_memcpy(drv->ssid, ssid + 2, ssid[1]);
  352. wpa_printf(MSG_DEBUG,
  353. "nl80211: Set drv->ssid based on req_ie to '%s'",
  354. wpa_ssid_txt(drv->ssid,
  355. drv->ssid_len));
  356. }
  357. }
  358. }
  359. if (resp_ie) {
  360. event.assoc_info.resp_ies = nla_data(resp_ie);
  361. event.assoc_info.resp_ies_len = nla_len(resp_ie);
  362. }
  363. event.assoc_info.freq = nl80211_get_assoc_freq(drv);
  364. if ((!ssid || ssid[1] == 0 || ssid[1] > 32) &&
  365. (ssid_len = nl80211_get_assoc_ssid(drv, drv->ssid)) > 0) {
  366. /* When this connection was initiated outside of wpa_supplicant,
  367. * drv->ssid needs to be set here to satisfy later checking. */
  368. drv->ssid_len = ssid_len;
  369. wpa_printf(MSG_DEBUG,
  370. "nl80211: Set drv->ssid based on scan res info to '%s'",
  371. wpa_ssid_txt(drv->ssid, drv->ssid_len));
  372. }
  373. if (authorized && nla_get_u8(authorized)) {
  374. event.assoc_info.authorized = 1;
  375. wpa_printf(MSG_DEBUG, "nl80211: connection authorized");
  376. }
  377. if (key_replay_ctr) {
  378. event.assoc_info.key_replay_ctr = nla_data(key_replay_ctr);
  379. event.assoc_info.key_replay_ctr_len = nla_len(key_replay_ctr);
  380. }
  381. if (ptk_kck) {
  382. event.assoc_info.ptk_kck = nla_data(ptk_kck);
  383. event.assoc_info.ptk_kck_len = nla_len(ptk_kck);
  384. }
  385. if (ptk_kek) {
  386. event.assoc_info.ptk_kek = nla_data(ptk_kek);
  387. event.assoc_info.ptk_kek_len = nla_len(ptk_kek);
  388. }
  389. if (subnet_status) {
  390. /*
  391. * At least for now, this is only available from
  392. * QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_SUBNET_STATUS and that
  393. * attribute has the same values 0, 1, 2 as are used in the
  394. * variable here, so no mapping between different values are
  395. * needed.
  396. */
  397. event.assoc_info.subnet_status = nla_get_u8(subnet_status);
  398. }
  399. if (fils_erp_next_seq_num)
  400. event.assoc_info.fils_erp_next_seq_num =
  401. nla_get_u16(fils_erp_next_seq_num);
  402. if (fils_pmk) {
  403. event.assoc_info.fils_pmk = nla_data(fils_pmk);
  404. event.assoc_info.fils_pmk_len = nla_len(fils_pmk);
  405. }
  406. if (fils_pmkid)
  407. event.assoc_info.fils_pmkid = nla_data(fils_pmkid);
  408. wpa_supplicant_event(drv->ctx, EVENT_ASSOC, &event);
  409. }
  410. static void mlme_event_disconnect(struct wpa_driver_nl80211_data *drv,
  411. struct nlattr *reason, struct nlattr *addr,
  412. struct nlattr *by_ap)
  413. {
  414. union wpa_event_data data;
  415. unsigned int locally_generated = by_ap == NULL;
  416. if (drv->capa.flags & WPA_DRIVER_FLAGS_SME) {
  417. /*
  418. * Avoid reporting two disassociation events that could
  419. * confuse the core code.
  420. */
  421. wpa_printf(MSG_DEBUG, "nl80211: Ignore disconnect "
  422. "event when using userspace SME");
  423. return;
  424. }
  425. if (drv->ignore_next_local_disconnect) {
  426. drv->ignore_next_local_disconnect = 0;
  427. if (locally_generated) {
  428. wpa_printf(MSG_DEBUG, "nl80211: Ignore disconnect "
  429. "event triggered during reassociation");
  430. return;
  431. }
  432. wpa_printf(MSG_WARNING, "nl80211: Was expecting local "
  433. "disconnect but got another disconnect "
  434. "event first");
  435. }
  436. wpa_printf(MSG_DEBUG, "nl80211: Disconnect event");
  437. nl80211_mark_disconnected(drv);
  438. os_memset(&data, 0, sizeof(data));
  439. if (reason)
  440. data.deauth_info.reason_code = nla_get_u16(reason);
  441. data.deauth_info.locally_generated = by_ap == NULL;
  442. wpa_supplicant_event(drv->ctx, EVENT_DEAUTH, &data);
  443. }
  444. static int calculate_chan_offset(int width, int freq, int cf1, int cf2)
  445. {
  446. int freq1 = 0;
  447. switch (convert2width(width)) {
  448. case CHAN_WIDTH_20_NOHT:
  449. case CHAN_WIDTH_20:
  450. return 0;
  451. case CHAN_WIDTH_40:
  452. freq1 = cf1 - 10;
  453. break;
  454. case CHAN_WIDTH_80:
  455. freq1 = cf1 - 30;
  456. break;
  457. case CHAN_WIDTH_160:
  458. freq1 = cf1 - 70;
  459. break;
  460. case CHAN_WIDTH_UNKNOWN:
  461. case CHAN_WIDTH_80P80:
  462. /* FIXME: implement this */
  463. return 0;
  464. }
  465. return (abs(freq - freq1) / 20) % 2 == 0 ? 1 : -1;
  466. }
  467. static void mlme_event_ch_switch(struct wpa_driver_nl80211_data *drv,
  468. struct nlattr *ifindex, struct nlattr *freq,
  469. struct nlattr *type, struct nlattr *bw,
  470. struct nlattr *cf1, struct nlattr *cf2)
  471. {
  472. struct i802_bss *bss;
  473. union wpa_event_data data;
  474. int ht_enabled = 1;
  475. int chan_offset = 0;
  476. int ifidx;
  477. wpa_printf(MSG_DEBUG, "nl80211: Channel switch event");
  478. if (!freq)
  479. return;
  480. ifidx = nla_get_u32(ifindex);
  481. bss = get_bss_ifindex(drv, ifidx);
  482. if (bss == NULL) {
  483. wpa_printf(MSG_WARNING, "nl80211: Unknown ifindex (%d) for channel switch, ignoring",
  484. ifidx);
  485. return;
  486. }
  487. if (type) {
  488. enum nl80211_channel_type ch_type = nla_get_u32(type);
  489. wpa_printf(MSG_DEBUG, "nl80211: Channel type: %d", ch_type);
  490. switch (ch_type) {
  491. case NL80211_CHAN_NO_HT:
  492. ht_enabled = 0;
  493. break;
  494. case NL80211_CHAN_HT20:
  495. break;
  496. case NL80211_CHAN_HT40PLUS:
  497. chan_offset = 1;
  498. break;
  499. case NL80211_CHAN_HT40MINUS:
  500. chan_offset = -1;
  501. break;
  502. }
  503. } else if (bw && cf1) {
  504. /* This can happen for example with VHT80 ch switch */
  505. chan_offset = calculate_chan_offset(nla_get_u32(bw),
  506. nla_get_u32(freq),
  507. nla_get_u32(cf1),
  508. cf2 ? nla_get_u32(cf2) : 0);
  509. } else {
  510. wpa_printf(MSG_WARNING, "nl80211: Unknown secondary channel information - following channel definition calculations may fail");
  511. }
  512. os_memset(&data, 0, sizeof(data));
  513. data.ch_switch.freq = nla_get_u32(freq);
  514. data.ch_switch.ht_enabled = ht_enabled;
  515. data.ch_switch.ch_offset = chan_offset;
  516. if (bw)
  517. data.ch_switch.ch_width = convert2width(nla_get_u32(bw));
  518. if (cf1)
  519. data.ch_switch.cf1 = nla_get_u32(cf1);
  520. if (cf2)
  521. data.ch_switch.cf2 = nla_get_u32(cf2);
  522. bss->freq = data.ch_switch.freq;
  523. drv->assoc_freq = data.ch_switch.freq;
  524. wpa_supplicant_event(bss->ctx, EVENT_CH_SWITCH, &data);
  525. }
  526. static void mlme_timeout_event(struct wpa_driver_nl80211_data *drv,
  527. enum nl80211_commands cmd, struct nlattr *addr)
  528. {
  529. union wpa_event_data event;
  530. enum wpa_event_type ev;
  531. if (nla_len(addr) != ETH_ALEN)
  532. return;
  533. wpa_printf(MSG_DEBUG, "nl80211: MLME event %d; timeout with " MACSTR,
  534. cmd, MAC2STR((u8 *) nla_data(addr)));
  535. if (cmd == NL80211_CMD_AUTHENTICATE)
  536. ev = EVENT_AUTH_TIMED_OUT;
  537. else if (cmd == NL80211_CMD_ASSOCIATE)
  538. ev = EVENT_ASSOC_TIMED_OUT;
  539. else
  540. return;
  541. os_memset(&event, 0, sizeof(event));
  542. os_memcpy(event.timeout_event.addr, nla_data(addr), ETH_ALEN);
  543. wpa_supplicant_event(drv->ctx, ev, &event);
  544. }
  545. static void mlme_event_mgmt(struct i802_bss *bss,
  546. struct nlattr *freq, struct nlattr *sig,
  547. const u8 *frame, size_t len)
  548. {
  549. struct wpa_driver_nl80211_data *drv = bss->drv;
  550. const struct ieee80211_mgmt *mgmt;
  551. union wpa_event_data event;
  552. u16 fc, stype;
  553. int ssi_signal = 0;
  554. int rx_freq = 0;
  555. wpa_printf(MSG_MSGDUMP, "nl80211: Frame event");
  556. mgmt = (const struct ieee80211_mgmt *) frame;
  557. if (len < 24) {
  558. wpa_printf(MSG_DEBUG, "nl80211: Too short management frame");
  559. return;
  560. }
  561. fc = le_to_host16(mgmt->frame_control);
  562. stype = WLAN_FC_GET_STYPE(fc);
  563. if (sig)
  564. ssi_signal = (s32) nla_get_u32(sig);
  565. os_memset(&event, 0, sizeof(event));
  566. if (freq) {
  567. event.rx_mgmt.freq = nla_get_u32(freq);
  568. rx_freq = drv->last_mgmt_freq = event.rx_mgmt.freq;
  569. }
  570. wpa_printf(MSG_DEBUG,
  571. "nl80211: RX frame da=" MACSTR " sa=" MACSTR " bssid=" MACSTR
  572. " freq=%d ssi_signal=%d fc=0x%x seq_ctrl=0x%x stype=%u (%s) len=%u",
  573. MAC2STR(mgmt->da), MAC2STR(mgmt->sa), MAC2STR(mgmt->bssid),
  574. rx_freq, ssi_signal, fc,
  575. le_to_host16(mgmt->seq_ctrl), stype, fc2str(fc),
  576. (unsigned int) len);
  577. event.rx_mgmt.frame = frame;
  578. event.rx_mgmt.frame_len = len;
  579. event.rx_mgmt.ssi_signal = ssi_signal;
  580. event.rx_mgmt.drv_priv = bss;
  581. wpa_supplicant_event(drv->ctx, EVENT_RX_MGMT, &event);
  582. }
  583. static void mlme_event_mgmt_tx_status(struct wpa_driver_nl80211_data *drv,
  584. struct nlattr *cookie, const u8 *frame,
  585. size_t len, struct nlattr *ack)
  586. {
  587. union wpa_event_data event;
  588. const struct ieee80211_hdr *hdr;
  589. u16 fc;
  590. wpa_printf(MSG_DEBUG, "nl80211: Frame TX status event");
  591. if (!is_ap_interface(drv->nlmode)) {
  592. u64 cookie_val;
  593. if (!cookie)
  594. return;
  595. cookie_val = nla_get_u64(cookie);
  596. wpa_printf(MSG_DEBUG, "nl80211: Action TX status:"
  597. " cookie=0x%llx%s (ack=%d)",
  598. (long long unsigned int) cookie_val,
  599. cookie_val == drv->send_action_cookie ?
  600. " (match)" : " (unknown)", ack != NULL);
  601. if (cookie_val != drv->send_action_cookie)
  602. return;
  603. }
  604. hdr = (const struct ieee80211_hdr *) frame;
  605. fc = le_to_host16(hdr->frame_control);
  606. os_memset(&event, 0, sizeof(event));
  607. event.tx_status.type = WLAN_FC_GET_TYPE(fc);
  608. event.tx_status.stype = WLAN_FC_GET_STYPE(fc);
  609. event.tx_status.dst = hdr->addr1;
  610. event.tx_status.data = frame;
  611. event.tx_status.data_len = len;
  612. event.tx_status.ack = ack != NULL;
  613. wpa_supplicant_event(drv->ctx, EVENT_TX_STATUS, &event);
  614. }
  615. static void mlme_event_deauth_disassoc(struct wpa_driver_nl80211_data *drv,
  616. enum wpa_event_type type,
  617. const u8 *frame, size_t len)
  618. {
  619. const struct ieee80211_mgmt *mgmt;
  620. union wpa_event_data event;
  621. const u8 *bssid = NULL;
  622. u16 reason_code = 0;
  623. if (type == EVENT_DEAUTH)
  624. wpa_printf(MSG_DEBUG, "nl80211: Deauthenticate event");
  625. else
  626. wpa_printf(MSG_DEBUG, "nl80211: Disassociate event");
  627. mgmt = (const struct ieee80211_mgmt *) frame;
  628. if (len >= 24) {
  629. bssid = mgmt->bssid;
  630. if ((drv->capa.flags & WPA_DRIVER_FLAGS_SME) &&
  631. !drv->associated &&
  632. os_memcmp(bssid, drv->auth_bssid, ETH_ALEN) != 0 &&
  633. os_memcmp(bssid, drv->auth_attempt_bssid, ETH_ALEN) != 0 &&
  634. os_memcmp(bssid, drv->prev_bssid, ETH_ALEN) == 0) {
  635. /*
  636. * Avoid issues with some roaming cases where
  637. * disconnection event for the old AP may show up after
  638. * we have started connection with the new AP.
  639. * In case of locally generated event clear
  640. * ignore_next_local_deauth as well, to avoid next local
  641. * deauth event be wrongly ignored.
  642. */
  643. if (!os_memcmp(mgmt->sa, drv->first_bss->addr,
  644. ETH_ALEN)) {
  645. wpa_printf(MSG_DEBUG,
  646. "nl80211: Received a locally generated deauth event. Clear ignore_next_local_deauth flag");
  647. drv->ignore_next_local_deauth = 0;
  648. } else {
  649. wpa_printf(MSG_DEBUG,
  650. "nl80211: Ignore deauth/disassoc event from old AP " MACSTR " when already authenticating with " MACSTR,
  651. MAC2STR(bssid),
  652. MAC2STR(drv->auth_attempt_bssid));
  653. }
  654. return;
  655. }
  656. if (!(drv->capa.flags & WPA_DRIVER_FLAGS_SME) &&
  657. drv->connect_reassoc && drv->associated &&
  658. os_memcmp(bssid, drv->prev_bssid, ETH_ALEN) == 0 &&
  659. os_memcmp(bssid, drv->auth_attempt_bssid, ETH_ALEN) != 0) {
  660. /*
  661. * Avoid issues with some roaming cases where
  662. * disconnection event for the old AP may show up after
  663. * we have started connection with the new AP.
  664. */
  665. wpa_printf(MSG_DEBUG,
  666. "nl80211: Ignore deauth/disassoc event from old AP "
  667. MACSTR
  668. " when already connecting with " MACSTR,
  669. MAC2STR(bssid),
  670. MAC2STR(drv->auth_attempt_bssid));
  671. return;
  672. }
  673. if (drv->associated != 0 &&
  674. os_memcmp(bssid, drv->bssid, ETH_ALEN) != 0 &&
  675. os_memcmp(bssid, drv->auth_bssid, ETH_ALEN) != 0) {
  676. /*
  677. * We have presumably received this deauth as a
  678. * response to a clear_state_mismatch() outgoing
  679. * deauth. Don't let it take us offline!
  680. */
  681. wpa_printf(MSG_DEBUG, "nl80211: Deauth received "
  682. "from Unknown BSSID " MACSTR " -- ignoring",
  683. MAC2STR(bssid));
  684. return;
  685. }
  686. }
  687. nl80211_mark_disconnected(drv);
  688. os_memset(&event, 0, sizeof(event));
  689. /* Note: Same offset for Reason Code in both frame subtypes */
  690. if (len >= 24 + sizeof(mgmt->u.deauth))
  691. reason_code = le_to_host16(mgmt->u.deauth.reason_code);
  692. if (type == EVENT_DISASSOC) {
  693. event.disassoc_info.locally_generated =
  694. !os_memcmp(mgmt->sa, drv->first_bss->addr, ETH_ALEN);
  695. event.disassoc_info.addr = bssid;
  696. event.disassoc_info.reason_code = reason_code;
  697. if (frame + len > mgmt->u.disassoc.variable) {
  698. event.disassoc_info.ie = mgmt->u.disassoc.variable;
  699. event.disassoc_info.ie_len = frame + len -
  700. mgmt->u.disassoc.variable;
  701. }
  702. } else {
  703. event.deauth_info.locally_generated =
  704. !os_memcmp(mgmt->sa, drv->first_bss->addr, ETH_ALEN);
  705. if (drv->ignore_deauth_event) {
  706. wpa_printf(MSG_DEBUG, "nl80211: Ignore deauth event due to previous forced deauth-during-auth");
  707. drv->ignore_deauth_event = 0;
  708. if (event.deauth_info.locally_generated)
  709. drv->ignore_next_local_deauth = 0;
  710. return;
  711. }
  712. if (drv->ignore_next_local_deauth) {
  713. drv->ignore_next_local_deauth = 0;
  714. if (event.deauth_info.locally_generated) {
  715. wpa_printf(MSG_DEBUG, "nl80211: Ignore deauth event triggered due to own deauth request");
  716. return;
  717. }
  718. wpa_printf(MSG_WARNING, "nl80211: Was expecting local deauth but got another disconnect event first");
  719. }
  720. event.deauth_info.addr = bssid;
  721. event.deauth_info.reason_code = reason_code;
  722. if (frame + len > mgmt->u.deauth.variable) {
  723. event.deauth_info.ie = mgmt->u.deauth.variable;
  724. event.deauth_info.ie_len = frame + len -
  725. mgmt->u.deauth.variable;
  726. }
  727. }
  728. wpa_supplicant_event(drv->ctx, type, &event);
  729. }
  730. static void mlme_event_unprot_disconnect(struct wpa_driver_nl80211_data *drv,
  731. enum wpa_event_type type,
  732. const u8 *frame, size_t len)
  733. {
  734. const struct ieee80211_mgmt *mgmt;
  735. union wpa_event_data event;
  736. u16 reason_code = 0;
  737. if (type == EVENT_UNPROT_DEAUTH)
  738. wpa_printf(MSG_DEBUG, "nl80211: Unprot Deauthenticate event");
  739. else
  740. wpa_printf(MSG_DEBUG, "nl80211: Unprot Disassociate event");
  741. if (len < 24)
  742. return;
  743. mgmt = (const struct ieee80211_mgmt *) frame;
  744. os_memset(&event, 0, sizeof(event));
  745. /* Note: Same offset for Reason Code in both frame subtypes */
  746. if (len >= 24 + sizeof(mgmt->u.deauth))
  747. reason_code = le_to_host16(mgmt->u.deauth.reason_code);
  748. if (type == EVENT_UNPROT_DISASSOC) {
  749. event.unprot_disassoc.sa = mgmt->sa;
  750. event.unprot_disassoc.da = mgmt->da;
  751. event.unprot_disassoc.reason_code = reason_code;
  752. } else {
  753. event.unprot_deauth.sa = mgmt->sa;
  754. event.unprot_deauth.da = mgmt->da;
  755. event.unprot_deauth.reason_code = reason_code;
  756. }
  757. wpa_supplicant_event(drv->ctx, type, &event);
  758. }
  759. static void mlme_event(struct i802_bss *bss,
  760. enum nl80211_commands cmd, struct nlattr *frame,
  761. struct nlattr *addr, struct nlattr *timed_out,
  762. struct nlattr *freq, struct nlattr *ack,
  763. struct nlattr *cookie, struct nlattr *sig,
  764. struct nlattr *wmm)
  765. {
  766. struct wpa_driver_nl80211_data *drv = bss->drv;
  767. const u8 *data;
  768. size_t len;
  769. if (timed_out && addr) {
  770. mlme_timeout_event(drv, cmd, addr);
  771. return;
  772. }
  773. if (frame == NULL) {
  774. wpa_printf(MSG_DEBUG,
  775. "nl80211: MLME event %d (%s) without frame data",
  776. cmd, nl80211_command_to_string(cmd));
  777. return;
  778. }
  779. data = nla_data(frame);
  780. len = nla_len(frame);
  781. if (len < 4 + 2 * ETH_ALEN) {
  782. wpa_printf(MSG_MSGDUMP, "nl80211: MLME event %d (%s) on %s("
  783. MACSTR ") - too short",
  784. cmd, nl80211_command_to_string(cmd), bss->ifname,
  785. MAC2STR(bss->addr));
  786. return;
  787. }
  788. wpa_printf(MSG_MSGDUMP, "nl80211: MLME event %d (%s) on %s(" MACSTR
  789. ") A1=" MACSTR " A2=" MACSTR, cmd,
  790. nl80211_command_to_string(cmd), bss->ifname,
  791. MAC2STR(bss->addr), MAC2STR(data + 4),
  792. MAC2STR(data + 4 + ETH_ALEN));
  793. if (cmd != NL80211_CMD_FRAME_TX_STATUS && !(data[4] & 0x01) &&
  794. os_memcmp(bss->addr, data + 4, ETH_ALEN) != 0 &&
  795. (is_zero_ether_addr(bss->rand_addr) ||
  796. os_memcmp(bss->rand_addr, data + 4, ETH_ALEN) != 0) &&
  797. os_memcmp(bss->addr, data + 4 + ETH_ALEN, ETH_ALEN) != 0) {
  798. wpa_printf(MSG_MSGDUMP, "nl80211: %s: Ignore MLME frame event "
  799. "for foreign address", bss->ifname);
  800. return;
  801. }
  802. wpa_hexdump(MSG_MSGDUMP, "nl80211: MLME event frame",
  803. nla_data(frame), nla_len(frame));
  804. switch (cmd) {
  805. case NL80211_CMD_AUTHENTICATE:
  806. mlme_event_auth(drv, nla_data(frame), nla_len(frame));
  807. break;
  808. case NL80211_CMD_ASSOCIATE:
  809. mlme_event_assoc(drv, nla_data(frame), nla_len(frame), wmm);
  810. break;
  811. case NL80211_CMD_DEAUTHENTICATE:
  812. mlme_event_deauth_disassoc(drv, EVENT_DEAUTH,
  813. nla_data(frame), nla_len(frame));
  814. break;
  815. case NL80211_CMD_DISASSOCIATE:
  816. mlme_event_deauth_disassoc(drv, EVENT_DISASSOC,
  817. nla_data(frame), nla_len(frame));
  818. break;
  819. case NL80211_CMD_FRAME:
  820. mlme_event_mgmt(bss, freq, sig, nla_data(frame),
  821. nla_len(frame));
  822. break;
  823. case NL80211_CMD_FRAME_TX_STATUS:
  824. mlme_event_mgmt_tx_status(drv, cookie, nla_data(frame),
  825. nla_len(frame), ack);
  826. break;
  827. case NL80211_CMD_UNPROT_DEAUTHENTICATE:
  828. mlme_event_unprot_disconnect(drv, EVENT_UNPROT_DEAUTH,
  829. nla_data(frame), nla_len(frame));
  830. break;
  831. case NL80211_CMD_UNPROT_DISASSOCIATE:
  832. mlme_event_unprot_disconnect(drv, EVENT_UNPROT_DISASSOC,
  833. nla_data(frame), nla_len(frame));
  834. break;
  835. default:
  836. break;
  837. }
  838. }
  839. static void mlme_event_michael_mic_failure(struct i802_bss *bss,
  840. struct nlattr *tb[])
  841. {
  842. union wpa_event_data data;
  843. wpa_printf(MSG_DEBUG, "nl80211: MLME event Michael MIC failure");
  844. os_memset(&data, 0, sizeof(data));
  845. if (tb[NL80211_ATTR_MAC]) {
  846. wpa_hexdump(MSG_DEBUG, "nl80211: Source MAC address",
  847. nla_data(tb[NL80211_ATTR_MAC]),
  848. nla_len(tb[NL80211_ATTR_MAC]));
  849. data.michael_mic_failure.src = nla_data(tb[NL80211_ATTR_MAC]);
  850. }
  851. if (tb[NL80211_ATTR_KEY_SEQ]) {
  852. wpa_hexdump(MSG_DEBUG, "nl80211: TSC",
  853. nla_data(tb[NL80211_ATTR_KEY_SEQ]),
  854. nla_len(tb[NL80211_ATTR_KEY_SEQ]));
  855. }
  856. if (tb[NL80211_ATTR_KEY_TYPE]) {
  857. enum nl80211_key_type key_type =
  858. nla_get_u32(tb[NL80211_ATTR_KEY_TYPE]);
  859. wpa_printf(MSG_DEBUG, "nl80211: Key Type %d", key_type);
  860. if (key_type == NL80211_KEYTYPE_PAIRWISE)
  861. data.michael_mic_failure.unicast = 1;
  862. } else
  863. data.michael_mic_failure.unicast = 1;
  864. if (tb[NL80211_ATTR_KEY_IDX]) {
  865. u8 key_id = nla_get_u8(tb[NL80211_ATTR_KEY_IDX]);
  866. wpa_printf(MSG_DEBUG, "nl80211: Key Id %d", key_id);
  867. }
  868. wpa_supplicant_event(bss->ctx, EVENT_MICHAEL_MIC_FAILURE, &data);
  869. }
  870. static void mlme_event_join_ibss(struct wpa_driver_nl80211_data *drv,
  871. struct nlattr *tb[])
  872. {
  873. unsigned int freq;
  874. union wpa_event_data event;
  875. if (tb[NL80211_ATTR_MAC] == NULL) {
  876. wpa_printf(MSG_DEBUG, "nl80211: No address in IBSS joined "
  877. "event");
  878. return;
  879. }
  880. os_memcpy(drv->bssid, nla_data(tb[NL80211_ATTR_MAC]), ETH_ALEN);
  881. drv->associated = 1;
  882. wpa_printf(MSG_DEBUG, "nl80211: IBSS " MACSTR " joined",
  883. MAC2STR(drv->bssid));
  884. freq = nl80211_get_assoc_freq(drv);
  885. if (freq) {
  886. wpa_printf(MSG_DEBUG, "nl80211: IBSS on frequency %u MHz",
  887. freq);
  888. drv->first_bss->freq = freq;
  889. }
  890. os_memset(&event, 0, sizeof(event));
  891. event.assoc_info.freq = freq;
  892. wpa_supplicant_event(drv->ctx, EVENT_ASSOC, &event);
  893. }
  894. static void mlme_event_remain_on_channel(struct wpa_driver_nl80211_data *drv,
  895. int cancel_event, struct nlattr *tb[])
  896. {
  897. unsigned int freq, chan_type, duration;
  898. union wpa_event_data data;
  899. u64 cookie;
  900. if (tb[NL80211_ATTR_WIPHY_FREQ])
  901. freq = nla_get_u32(tb[NL80211_ATTR_WIPHY_FREQ]);
  902. else
  903. freq = 0;
  904. if (tb[NL80211_ATTR_WIPHY_CHANNEL_TYPE])
  905. chan_type = nla_get_u32(tb[NL80211_ATTR_WIPHY_CHANNEL_TYPE]);
  906. else
  907. chan_type = 0;
  908. if (tb[NL80211_ATTR_DURATION])
  909. duration = nla_get_u32(tb[NL80211_ATTR_DURATION]);
  910. else
  911. duration = 0;
  912. if (tb[NL80211_ATTR_COOKIE])
  913. cookie = nla_get_u64(tb[NL80211_ATTR_COOKIE]);
  914. else
  915. cookie = 0;
  916. wpa_printf(MSG_DEBUG, "nl80211: Remain-on-channel event (cancel=%d "
  917. "freq=%u channel_type=%u duration=%u cookie=0x%llx (%s))",
  918. cancel_event, freq, chan_type, duration,
  919. (long long unsigned int) cookie,
  920. cookie == drv->remain_on_chan_cookie ? "match" : "unknown");
  921. if (cookie != drv->remain_on_chan_cookie)
  922. return; /* not for us */
  923. if (cancel_event)
  924. drv->pending_remain_on_chan = 0;
  925. os_memset(&data, 0, sizeof(data));
  926. data.remain_on_channel.freq = freq;
  927. data.remain_on_channel.duration = duration;
  928. wpa_supplicant_event(drv->ctx, cancel_event ?
  929. EVENT_CANCEL_REMAIN_ON_CHANNEL :
  930. EVENT_REMAIN_ON_CHANNEL, &data);
  931. }
  932. static void mlme_event_ft_event(struct wpa_driver_nl80211_data *drv,
  933. struct nlattr *tb[])
  934. {
  935. union wpa_event_data data;
  936. os_memset(&data, 0, sizeof(data));
  937. if (tb[NL80211_ATTR_IE]) {
  938. data.ft_ies.ies = nla_data(tb[NL80211_ATTR_IE]);
  939. data.ft_ies.ies_len = nla_len(tb[NL80211_ATTR_IE]);
  940. }
  941. if (tb[NL80211_ATTR_IE_RIC]) {
  942. data.ft_ies.ric_ies = nla_data(tb[NL80211_ATTR_IE_RIC]);
  943. data.ft_ies.ric_ies_len = nla_len(tb[NL80211_ATTR_IE_RIC]);
  944. }
  945. if (tb[NL80211_ATTR_MAC])
  946. os_memcpy(data.ft_ies.target_ap,
  947. nla_data(tb[NL80211_ATTR_MAC]), ETH_ALEN);
  948. wpa_printf(MSG_DEBUG, "nl80211: FT event target_ap " MACSTR,
  949. MAC2STR(data.ft_ies.target_ap));
  950. wpa_supplicant_event(drv->ctx, EVENT_FT_RESPONSE, &data);
  951. }
  952. static void send_scan_event(struct wpa_driver_nl80211_data *drv, int aborted,
  953. struct nlattr *tb[], int external_scan)
  954. {
  955. union wpa_event_data event;
  956. struct nlattr *nl;
  957. int rem;
  958. struct scan_info *info;
  959. #define MAX_REPORT_FREQS 50
  960. int freqs[MAX_REPORT_FREQS];
  961. int num_freqs = 0;
  962. if (!external_scan && drv->scan_for_auth) {
  963. drv->scan_for_auth = 0;
  964. wpa_printf(MSG_DEBUG, "nl80211: Scan results for missing "
  965. "cfg80211 BSS entry");
  966. wpa_driver_nl80211_authenticate_retry(drv);
  967. return;
  968. }
  969. os_memset(&event, 0, sizeof(event));
  970. info = &event.scan_info;
  971. info->aborted = aborted;
  972. info->external_scan = external_scan;
  973. info->nl_scan_event = 1;
  974. if (tb[NL80211_ATTR_SCAN_SSIDS]) {
  975. nla_for_each_nested(nl, tb[NL80211_ATTR_SCAN_SSIDS], rem) {
  976. struct wpa_driver_scan_ssid *s =
  977. &info->ssids[info->num_ssids];
  978. s->ssid = nla_data(nl);
  979. s->ssid_len = nla_len(nl);
  980. wpa_printf(MSG_DEBUG, "nl80211: Scan probed for SSID '%s'",
  981. wpa_ssid_txt(s->ssid, s->ssid_len));
  982. info->num_ssids++;
  983. if (info->num_ssids == WPAS_MAX_SCAN_SSIDS)
  984. break;
  985. }
  986. }
  987. if (tb[NL80211_ATTR_SCAN_FREQUENCIES]) {
  988. char msg[300], *pos, *end;
  989. int res;
  990. pos = msg;
  991. end = pos + sizeof(msg);
  992. *pos = '\0';
  993. nla_for_each_nested(nl, tb[NL80211_ATTR_SCAN_FREQUENCIES], rem)
  994. {
  995. freqs[num_freqs] = nla_get_u32(nl);
  996. res = os_snprintf(pos, end - pos, " %d",
  997. freqs[num_freqs]);
  998. if (!os_snprintf_error(end - pos, res))
  999. pos += res;
  1000. num_freqs++;
  1001. if (num_freqs == MAX_REPORT_FREQS - 1)
  1002. break;
  1003. }
  1004. info->freqs = freqs;
  1005. info->num_freqs = num_freqs;
  1006. wpa_printf(MSG_DEBUG, "nl80211: Scan included frequencies:%s",
  1007. msg);
  1008. }
  1009. if (tb[NL80211_ATTR_SCAN_START_TIME_TSF] &&
  1010. tb[NL80211_ATTR_SCAN_START_TIME_TSF_BSSID]) {
  1011. info->scan_start_tsf =
  1012. nla_get_u64(tb[NL80211_ATTR_SCAN_START_TIME_TSF]);
  1013. os_memcpy(info->scan_start_tsf_bssid,
  1014. nla_data(tb[NL80211_ATTR_SCAN_START_TIME_TSF_BSSID]),
  1015. ETH_ALEN);
  1016. }
  1017. wpa_supplicant_event(drv->ctx, EVENT_SCAN_RESULTS, &event);
  1018. }
  1019. static void nl80211_cqm_event(struct wpa_driver_nl80211_data *drv,
  1020. struct nlattr *tb[])
  1021. {
  1022. static struct nla_policy cqm_policy[NL80211_ATTR_CQM_MAX + 1] = {
  1023. [NL80211_ATTR_CQM_RSSI_THOLD] = { .type = NLA_U32 },
  1024. [NL80211_ATTR_CQM_RSSI_HYST] = { .type = NLA_U8 },
  1025. [NL80211_ATTR_CQM_RSSI_THRESHOLD_EVENT] = { .type = NLA_U32 },
  1026. [NL80211_ATTR_CQM_PKT_LOSS_EVENT] = { .type = NLA_U32 },
  1027. [NL80211_ATTR_CQM_TXE_RATE] = { .type = NLA_U32 },
  1028. [NL80211_ATTR_CQM_TXE_PKTS] = { .type = NLA_U32 },
  1029. [NL80211_ATTR_CQM_TXE_INTVL] = { .type = NLA_U32 },
  1030. [NL80211_ATTR_CQM_BEACON_LOSS_EVENT] = { .type = NLA_FLAG },
  1031. };
  1032. struct nlattr *cqm[NL80211_ATTR_CQM_MAX + 1];
  1033. enum nl80211_cqm_rssi_threshold_event event;
  1034. union wpa_event_data ed;
  1035. struct wpa_signal_info sig;
  1036. int res;
  1037. if (tb[NL80211_ATTR_CQM] == NULL ||
  1038. nla_parse_nested(cqm, NL80211_ATTR_CQM_MAX, tb[NL80211_ATTR_CQM],
  1039. cqm_policy)) {
  1040. wpa_printf(MSG_DEBUG, "nl80211: Ignore invalid CQM event");
  1041. return;
  1042. }
  1043. os_memset(&ed, 0, sizeof(ed));
  1044. if (cqm[NL80211_ATTR_CQM_PKT_LOSS_EVENT]) {
  1045. if (!tb[NL80211_ATTR_MAC])
  1046. return;
  1047. os_memcpy(ed.low_ack.addr, nla_data(tb[NL80211_ATTR_MAC]),
  1048. ETH_ALEN);
  1049. ed.low_ack.num_packets =
  1050. nla_get_u32(cqm[NL80211_ATTR_CQM_PKT_LOSS_EVENT]);
  1051. wpa_printf(MSG_DEBUG, "nl80211: Packet loss event for " MACSTR
  1052. " (num_packets %u)",
  1053. MAC2STR(ed.low_ack.addr), ed.low_ack.num_packets);
  1054. wpa_supplicant_event(drv->ctx, EVENT_STATION_LOW_ACK, &ed);
  1055. return;
  1056. }
  1057. if (cqm[NL80211_ATTR_CQM_BEACON_LOSS_EVENT]) {
  1058. wpa_printf(MSG_DEBUG, "nl80211: Beacon loss event");
  1059. wpa_supplicant_event(drv->ctx, EVENT_BEACON_LOSS, NULL);
  1060. return;
  1061. }
  1062. if (cqm[NL80211_ATTR_CQM_TXE_RATE] &&
  1063. cqm[NL80211_ATTR_CQM_TXE_PKTS] &&
  1064. cqm[NL80211_ATTR_CQM_TXE_INTVL] &&
  1065. cqm[NL80211_ATTR_MAC]) {
  1066. wpa_printf(MSG_DEBUG, "nl80211: CQM TXE event for " MACSTR
  1067. " (rate: %u pkts: %u interval: %u)",
  1068. MAC2STR((u8 *) nla_data(cqm[NL80211_ATTR_MAC])),
  1069. nla_get_u32(cqm[NL80211_ATTR_CQM_TXE_RATE]),
  1070. nla_get_u32(cqm[NL80211_ATTR_CQM_TXE_PKTS]),
  1071. nla_get_u32(cqm[NL80211_ATTR_CQM_TXE_INTVL]));
  1072. return;
  1073. }
  1074. if (cqm[NL80211_ATTR_CQM_RSSI_THRESHOLD_EVENT] == NULL) {
  1075. wpa_printf(MSG_DEBUG,
  1076. "nl80211: Not a CQM RSSI threshold event");
  1077. return;
  1078. }
  1079. event = nla_get_u32(cqm[NL80211_ATTR_CQM_RSSI_THRESHOLD_EVENT]);
  1080. if (event == NL80211_CQM_RSSI_THRESHOLD_EVENT_HIGH) {
  1081. wpa_printf(MSG_DEBUG, "nl80211: Connection quality monitor "
  1082. "event: RSSI high");
  1083. ed.signal_change.above_threshold = 1;
  1084. } else if (event == NL80211_CQM_RSSI_THRESHOLD_EVENT_LOW) {
  1085. wpa_printf(MSG_DEBUG, "nl80211: Connection quality monitor "
  1086. "event: RSSI low");
  1087. ed.signal_change.above_threshold = 0;
  1088. } else {
  1089. wpa_printf(MSG_DEBUG,
  1090. "nl80211: Unknown CQM RSSI threshold event: %d",
  1091. event);
  1092. return;
  1093. }
  1094. res = nl80211_get_link_signal(drv, &sig);
  1095. if (res == 0) {
  1096. ed.signal_change.current_signal = sig.current_signal;
  1097. ed.signal_change.current_txrate = sig.current_txrate;
  1098. wpa_printf(MSG_DEBUG, "nl80211: Signal: %d dBm txrate: %d",
  1099. sig.current_signal, sig.current_txrate);
  1100. }
  1101. res = nl80211_get_link_noise(drv, &sig);
  1102. if (res == 0) {
  1103. ed.signal_change.current_noise = sig.current_noise;
  1104. wpa_printf(MSG_DEBUG, "nl80211: Noise: %d dBm",
  1105. sig.current_noise);
  1106. }
  1107. wpa_supplicant_event(drv->ctx, EVENT_SIGNAL_CHANGE, &ed);
  1108. }
  1109. static void nl80211_new_peer_candidate(struct wpa_driver_nl80211_data *drv,
  1110. struct nlattr **tb)
  1111. {
  1112. const u8 *addr;
  1113. union wpa_event_data data;
  1114. if (drv->nlmode != NL80211_IFTYPE_MESH_POINT ||
  1115. !tb[NL80211_ATTR_MAC] || !tb[NL80211_ATTR_IE])
  1116. return;
  1117. addr = nla_data(tb[NL80211_ATTR_MAC]);
  1118. wpa_printf(MSG_DEBUG, "nl80211: New peer candidate " MACSTR,
  1119. MAC2STR(addr));
  1120. os_memset(&data, 0, sizeof(data));
  1121. data.mesh_peer.peer = addr;
  1122. data.mesh_peer.ies = nla_data(tb[NL80211_ATTR_IE]);
  1123. data.mesh_peer.ie_len = nla_len(tb[NL80211_ATTR_IE]);
  1124. wpa_supplicant_event(drv->ctx, EVENT_NEW_PEER_CANDIDATE, &data);
  1125. }
  1126. static void nl80211_new_station_event(struct wpa_driver_nl80211_data *drv,
  1127. struct i802_bss *bss,
  1128. struct nlattr **tb)
  1129. {
  1130. u8 *addr;
  1131. union wpa_event_data data;
  1132. if (tb[NL80211_ATTR_MAC] == NULL)
  1133. return;
  1134. addr = nla_data(tb[NL80211_ATTR_MAC]);
  1135. wpa_printf(MSG_DEBUG, "nl80211: New station " MACSTR, MAC2STR(addr));
  1136. if (is_ap_interface(drv->nlmode) && drv->device_ap_sme) {
  1137. u8 *ies = NULL;
  1138. size_t ies_len = 0;
  1139. if (tb[NL80211_ATTR_IE]) {
  1140. ies = nla_data(tb[NL80211_ATTR_IE]);
  1141. ies_len = nla_len(tb[NL80211_ATTR_IE]);
  1142. }
  1143. wpa_hexdump(MSG_DEBUG, "nl80211: Assoc Req IEs", ies, ies_len);
  1144. drv_event_assoc(bss->ctx, addr, ies, ies_len, 0);
  1145. return;
  1146. }
  1147. if (drv->nlmode != NL80211_IFTYPE_ADHOC)
  1148. return;
  1149. os_memset(&data, 0, sizeof(data));
  1150. os_memcpy(data.ibss_rsn_start.peer, addr, ETH_ALEN);
  1151. wpa_supplicant_event(bss->ctx, EVENT_IBSS_RSN_START, &data);
  1152. }
  1153. static void nl80211_del_station_event(struct wpa_driver_nl80211_data *drv,
  1154. struct i802_bss *bss,
  1155. struct nlattr **tb)
  1156. {
  1157. u8 *addr;
  1158. union wpa_event_data data;
  1159. if (tb[NL80211_ATTR_MAC] == NULL)
  1160. return;
  1161. addr = nla_data(tb[NL80211_ATTR_MAC]);
  1162. wpa_printf(MSG_DEBUG, "nl80211: Delete station " MACSTR,
  1163. MAC2STR(addr));
  1164. if (is_ap_interface(drv->nlmode) && drv->device_ap_sme) {
  1165. drv_event_disassoc(bss->ctx, addr);
  1166. return;
  1167. }
  1168. if (drv->nlmode != NL80211_IFTYPE_ADHOC)
  1169. return;
  1170. os_memset(&data, 0, sizeof(data));
  1171. os_memcpy(data.ibss_peer_lost.peer, addr, ETH_ALEN);
  1172. wpa_supplicant_event(bss->ctx, EVENT_IBSS_PEER_LOST, &data);
  1173. }
  1174. static void nl80211_rekey_offload_event(struct wpa_driver_nl80211_data *drv,
  1175. struct nlattr **tb)
  1176. {
  1177. struct nlattr *rekey_info[NUM_NL80211_REKEY_DATA];
  1178. static struct nla_policy rekey_policy[NUM_NL80211_REKEY_DATA] = {
  1179. [NL80211_REKEY_DATA_KEK] = {
  1180. .minlen = NL80211_KEK_LEN,
  1181. .maxlen = NL80211_KEK_LEN,
  1182. },
  1183. [NL80211_REKEY_DATA_KCK] = {
  1184. .minlen = NL80211_KCK_LEN,
  1185. .maxlen = NL80211_KCK_LEN,
  1186. },
  1187. [NL80211_REKEY_DATA_REPLAY_CTR] = {
  1188. .minlen = NL80211_REPLAY_CTR_LEN,
  1189. .maxlen = NL80211_REPLAY_CTR_LEN,
  1190. },
  1191. };
  1192. union wpa_event_data data;
  1193. if (!tb[NL80211_ATTR_MAC] ||
  1194. !tb[NL80211_ATTR_REKEY_DATA] ||
  1195. nla_parse_nested(rekey_info, MAX_NL80211_REKEY_DATA,
  1196. tb[NL80211_ATTR_REKEY_DATA], rekey_policy) ||
  1197. !rekey_info[NL80211_REKEY_DATA_REPLAY_CTR])
  1198. return;
  1199. os_memset(&data, 0, sizeof(data));
  1200. data.driver_gtk_rekey.bssid = nla_data(tb[NL80211_ATTR_MAC]);
  1201. wpa_printf(MSG_DEBUG, "nl80211: Rekey offload event for BSSID " MACSTR,
  1202. MAC2STR(data.driver_gtk_rekey.bssid));
  1203. data.driver_gtk_rekey.replay_ctr =
  1204. nla_data(rekey_info[NL80211_REKEY_DATA_REPLAY_CTR]);
  1205. wpa_hexdump(MSG_DEBUG, "nl80211: Rekey offload - Replay Counter",
  1206. data.driver_gtk_rekey.replay_ctr, NL80211_REPLAY_CTR_LEN);
  1207. wpa_supplicant_event(drv->ctx, EVENT_DRIVER_GTK_REKEY, &data);
  1208. }
  1209. static void nl80211_pmksa_candidate_event(struct wpa_driver_nl80211_data *drv,
  1210. struct nlattr **tb)
  1211. {
  1212. struct nlattr *cand[NUM_NL80211_PMKSA_CANDIDATE];
  1213. static struct nla_policy cand_policy[NUM_NL80211_PMKSA_CANDIDATE] = {
  1214. [NL80211_PMKSA_CANDIDATE_INDEX] = { .type = NLA_U32 },
  1215. [NL80211_PMKSA_CANDIDATE_BSSID] = {
  1216. .minlen = ETH_ALEN,
  1217. .maxlen = ETH_ALEN,
  1218. },
  1219. [NL80211_PMKSA_CANDIDATE_PREAUTH] = { .type = NLA_FLAG },
  1220. };
  1221. union wpa_event_data data;
  1222. wpa_printf(MSG_DEBUG, "nl80211: PMKSA candidate event");
  1223. if (!tb[NL80211_ATTR_PMKSA_CANDIDATE] ||
  1224. nla_parse_nested(cand, MAX_NL80211_PMKSA_CANDIDATE,
  1225. tb[NL80211_ATTR_PMKSA_CANDIDATE], cand_policy) ||
  1226. !cand[NL80211_PMKSA_CANDIDATE_INDEX] ||
  1227. !cand[NL80211_PMKSA_CANDIDATE_BSSID])
  1228. return;
  1229. os_memset(&data, 0, sizeof(data));
  1230. os_memcpy(data.pmkid_candidate.bssid,
  1231. nla_data(cand[NL80211_PMKSA_CANDIDATE_BSSID]), ETH_ALEN);
  1232. data.pmkid_candidate.index =
  1233. nla_get_u32(cand[NL80211_PMKSA_CANDIDATE_INDEX]);
  1234. data.pmkid_candidate.preauth =
  1235. cand[NL80211_PMKSA_CANDIDATE_PREAUTH] != NULL;
  1236. wpa_supplicant_event(drv->ctx, EVENT_PMKID_CANDIDATE, &data);
  1237. }
  1238. static void nl80211_client_probe_event(struct wpa_driver_nl80211_data *drv,
  1239. struct nlattr **tb)
  1240. {
  1241. union wpa_event_data data;
  1242. wpa_printf(MSG_DEBUG, "nl80211: Probe client event");
  1243. if (!tb[NL80211_ATTR_MAC] || !tb[NL80211_ATTR_ACK])
  1244. return;
  1245. os_memset(&data, 0, sizeof(data));
  1246. os_memcpy(data.client_poll.addr,
  1247. nla_data(tb[NL80211_ATTR_MAC]), ETH_ALEN);
  1248. wpa_supplicant_event(drv->ctx, EVENT_DRIVER_CLIENT_POLL_OK, &data);
  1249. }
  1250. static void nl80211_tdls_oper_event(struct wpa_driver_nl80211_data *drv,
  1251. struct nlattr **tb)
  1252. {
  1253. union wpa_event_data data;
  1254. wpa_printf(MSG_DEBUG, "nl80211: TDLS operation event");
  1255. if (!tb[NL80211_ATTR_MAC] || !tb[NL80211_ATTR_TDLS_OPERATION])
  1256. return;
  1257. os_memset(&data, 0, sizeof(data));
  1258. os_memcpy(data.tdls.peer, nla_data(tb[NL80211_ATTR_MAC]), ETH_ALEN);
  1259. switch (nla_get_u8(tb[NL80211_ATTR_TDLS_OPERATION])) {
  1260. case NL80211_TDLS_SETUP:
  1261. wpa_printf(MSG_DEBUG, "nl80211: TDLS setup request for peer "
  1262. MACSTR, MAC2STR(data.tdls.peer));
  1263. data.tdls.oper = TDLS_REQUEST_SETUP;
  1264. break;
  1265. case NL80211_TDLS_TEARDOWN:
  1266. wpa_printf(MSG_DEBUG, "nl80211: TDLS teardown request for peer "
  1267. MACSTR, MAC2STR(data.tdls.peer));
  1268. data.tdls.oper = TDLS_REQUEST_TEARDOWN;
  1269. break;
  1270. case NL80211_TDLS_DISCOVERY_REQ:
  1271. wpa_printf(MSG_DEBUG,
  1272. "nl80211: TDLS discovery request for peer " MACSTR,
  1273. MAC2STR(data.tdls.peer));
  1274. data.tdls.oper = TDLS_REQUEST_DISCOVER;
  1275. break;
  1276. default:
  1277. wpa_printf(MSG_DEBUG, "nl80211: Unsupported TDLS operatione "
  1278. "event");
  1279. return;
  1280. }
  1281. if (tb[NL80211_ATTR_REASON_CODE]) {
  1282. data.tdls.reason_code =
  1283. nla_get_u16(tb[NL80211_ATTR_REASON_CODE]);
  1284. }
  1285. wpa_supplicant_event(drv->ctx, EVENT_TDLS, &data);
  1286. }
  1287. static void nl80211_stop_ap(struct wpa_driver_nl80211_data *drv,
  1288. struct nlattr **tb)
  1289. {
  1290. wpa_supplicant_event(drv->ctx, EVENT_INTERFACE_UNAVAILABLE, NULL);
  1291. }
  1292. static void nl80211_connect_failed_event(struct wpa_driver_nl80211_data *drv,
  1293. struct nlattr **tb)
  1294. {
  1295. union wpa_event_data data;
  1296. u32 reason;
  1297. wpa_printf(MSG_DEBUG, "nl80211: Connect failed event");
  1298. if (!tb[NL80211_ATTR_MAC] || !tb[NL80211_ATTR_CONN_FAILED_REASON])
  1299. return;
  1300. os_memset(&data, 0, sizeof(data));
  1301. os_memcpy(data.connect_failed_reason.addr,
  1302. nla_data(tb[NL80211_ATTR_MAC]), ETH_ALEN);
  1303. reason = nla_get_u32(tb[NL80211_ATTR_CONN_FAILED_REASON]);
  1304. switch (reason) {
  1305. case NL80211_CONN_FAIL_MAX_CLIENTS:
  1306. wpa_printf(MSG_DEBUG, "nl80211: Max client reached");
  1307. data.connect_failed_reason.code = MAX_CLIENT_REACHED;
  1308. break;
  1309. case NL80211_CONN_FAIL_BLOCKED_CLIENT:
  1310. wpa_printf(MSG_DEBUG, "nl80211: Blocked client " MACSTR
  1311. " tried to connect",
  1312. MAC2STR(data.connect_failed_reason.addr));
  1313. data.connect_failed_reason.code = BLOCKED_CLIENT;
  1314. break;
  1315. default:
  1316. wpa_printf(MSG_DEBUG, "nl8021l: Unknown connect failed reason "
  1317. "%u", reason);
  1318. return;
  1319. }
  1320. wpa_supplicant_event(drv->ctx, EVENT_CONNECT_FAILED_REASON, &data);
  1321. }
  1322. static void nl80211_radar_event(struct wpa_driver_nl80211_data *drv,
  1323. struct nlattr **tb)
  1324. {
  1325. union wpa_event_data data;
  1326. enum nl80211_radar_event event_type;
  1327. if (!tb[NL80211_ATTR_WIPHY_FREQ] || !tb[NL80211_ATTR_RADAR_EVENT])
  1328. return;
  1329. os_memset(&data, 0, sizeof(data));
  1330. data.dfs_event.freq = nla_get_u32(tb[NL80211_ATTR_WIPHY_FREQ]);
  1331. event_type = nla_get_u32(tb[NL80211_ATTR_RADAR_EVENT]);
  1332. /* Check HT params */
  1333. if (tb[NL80211_ATTR_WIPHY_CHANNEL_TYPE]) {
  1334. data.dfs_event.ht_enabled = 1;
  1335. data.dfs_event.chan_offset = 0;
  1336. switch (nla_get_u32(tb[NL80211_ATTR_WIPHY_CHANNEL_TYPE])) {
  1337. case NL80211_CHAN_NO_HT:
  1338. data.dfs_event.ht_enabled = 0;
  1339. break;
  1340. case NL80211_CHAN_HT20:
  1341. break;
  1342. case NL80211_CHAN_HT40PLUS:
  1343. data.dfs_event.chan_offset = 1;
  1344. break;
  1345. case NL80211_CHAN_HT40MINUS:
  1346. data.dfs_event.chan_offset = -1;
  1347. break;
  1348. }
  1349. }
  1350. /* Get VHT params */
  1351. if (tb[NL80211_ATTR_CHANNEL_WIDTH])
  1352. data.dfs_event.chan_width =
  1353. convert2width(nla_get_u32(
  1354. tb[NL80211_ATTR_CHANNEL_WIDTH]));
  1355. if (tb[NL80211_ATTR_CENTER_FREQ1])
  1356. data.dfs_event.cf1 = nla_get_u32(tb[NL80211_ATTR_CENTER_FREQ1]);
  1357. if (tb[NL80211_ATTR_CENTER_FREQ2])
  1358. data.dfs_event.cf2 = nla_get_u32(tb[NL80211_ATTR_CENTER_FREQ2]);
  1359. wpa_printf(MSG_DEBUG, "nl80211: DFS event on freq %d MHz, ht: %d, offset: %d, width: %d, cf1: %dMHz, cf2: %dMHz",
  1360. data.dfs_event.freq, data.dfs_event.ht_enabled,
  1361. data.dfs_event.chan_offset, data.dfs_event.chan_width,
  1362. data.dfs_event.cf1, data.dfs_event.cf2);
  1363. switch (event_type) {
  1364. case NL80211_RADAR_DETECTED:
  1365. wpa_supplicant_event(drv->ctx, EVENT_DFS_RADAR_DETECTED, &data);
  1366. break;
  1367. case NL80211_RADAR_CAC_FINISHED:
  1368. wpa_supplicant_event(drv->ctx, EVENT_DFS_CAC_FINISHED, &data);
  1369. break;
  1370. case NL80211_RADAR_CAC_ABORTED:
  1371. wpa_supplicant_event(drv->ctx, EVENT_DFS_CAC_ABORTED, &data);
  1372. break;
  1373. case NL80211_RADAR_NOP_FINISHED:
  1374. wpa_supplicant_event(drv->ctx, EVENT_DFS_NOP_FINISHED, &data);
  1375. break;
  1376. case NL80211_RADAR_PRE_CAC_EXPIRED:
  1377. wpa_supplicant_event(drv->ctx, EVENT_DFS_PRE_CAC_EXPIRED,
  1378. &data);
  1379. break;
  1380. default:
  1381. wpa_printf(MSG_DEBUG, "nl80211: Unknown radar event %d "
  1382. "received", event_type);
  1383. break;
  1384. }
  1385. }
  1386. static void nl80211_spurious_frame(struct i802_bss *bss, struct nlattr **tb,
  1387. int wds)
  1388. {
  1389. struct wpa_driver_nl80211_data *drv = bss->drv;
  1390. union wpa_event_data event;
  1391. if (!tb[NL80211_ATTR_MAC])
  1392. return;
  1393. os_memset(&event, 0, sizeof(event));
  1394. event.rx_from_unknown.bssid = bss->addr;
  1395. event.rx_from_unknown.addr = nla_data(tb[NL80211_ATTR_MAC]);
  1396. event.rx_from_unknown.wds = wds;
  1397. wpa_supplicant_event(drv->ctx, EVENT_RX_FROM_UNKNOWN, &event);
  1398. }
  1399. #ifdef CONFIG_DRIVER_NL80211_QCA
  1400. static void qca_nl80211_avoid_freq(struct wpa_driver_nl80211_data *drv,
  1401. const u8 *data, size_t len)
  1402. {
  1403. u32 i, count;
  1404. union wpa_event_data event;
  1405. struct wpa_freq_range *range = NULL;
  1406. const struct qca_avoid_freq_list *freq_range;
  1407. freq_range = (const struct qca_avoid_freq_list *) data;
  1408. if (len < sizeof(freq_range->count))
  1409. return;
  1410. count = freq_range->count;
  1411. if (len < sizeof(freq_range->count) +
  1412. count * sizeof(struct qca_avoid_freq_range)) {
  1413. wpa_printf(MSG_DEBUG, "nl80211: Ignored too short avoid frequency list (len=%u)",
  1414. (unsigned int) len);
  1415. return;
  1416. }
  1417. if (count > 0) {
  1418. range = os_calloc(count, sizeof(struct wpa_freq_range));
  1419. if (range == NULL)
  1420. return;
  1421. }
  1422. os_memset(&event, 0, sizeof(event));
  1423. for (i = 0; i < count; i++) {
  1424. unsigned int idx = event.freq_range.num;
  1425. range[idx].min = freq_range->range[i].start_freq;
  1426. range[idx].max = freq_range->range[i].end_freq;
  1427. wpa_printf(MSG_DEBUG, "nl80211: Avoid frequency range: %u-%u",
  1428. range[idx].min, range[idx].max);
  1429. if (range[idx].min > range[idx].max) {
  1430. wpa_printf(MSG_DEBUG, "nl80211: Ignore invalid frequency range");
  1431. continue;
  1432. }
  1433. event.freq_range.num++;
  1434. }
  1435. event.freq_range.range = range;
  1436. wpa_supplicant_event(drv->ctx, EVENT_AVOID_FREQUENCIES, &event);
  1437. os_free(range);
  1438. }
  1439. static enum hostapd_hw_mode get_qca_hw_mode(u8 hw_mode)
  1440. {
  1441. switch (hw_mode) {
  1442. case QCA_ACS_MODE_IEEE80211B:
  1443. return HOSTAPD_MODE_IEEE80211B;
  1444. case QCA_ACS_MODE_IEEE80211G:
  1445. return HOSTAPD_MODE_IEEE80211G;
  1446. case QCA_ACS_MODE_IEEE80211A:
  1447. return HOSTAPD_MODE_IEEE80211A;
  1448. case QCA_ACS_MODE_IEEE80211AD:
  1449. return HOSTAPD_MODE_IEEE80211AD;
  1450. case QCA_ACS_MODE_IEEE80211ANY:
  1451. return HOSTAPD_MODE_IEEE80211ANY;
  1452. default:
  1453. return NUM_HOSTAPD_MODES;
  1454. }
  1455. }
  1456. static void qca_nl80211_acs_select_ch(struct wpa_driver_nl80211_data *drv,
  1457. const u8 *data, size_t len)
  1458. {
  1459. struct nlattr *tb[QCA_WLAN_VENDOR_ATTR_ACS_MAX + 1];
  1460. union wpa_event_data event;
  1461. wpa_printf(MSG_DEBUG,
  1462. "nl80211: ACS channel selection vendor event received");
  1463. if (nla_parse(tb, QCA_WLAN_VENDOR_ATTR_ACS_MAX,
  1464. (struct nlattr *) data, len, NULL) ||
  1465. !tb[QCA_WLAN_VENDOR_ATTR_ACS_PRIMARY_CHANNEL] ||
  1466. !tb[QCA_WLAN_VENDOR_ATTR_ACS_SECONDARY_CHANNEL])
  1467. return;
  1468. os_memset(&event, 0, sizeof(event));
  1469. event.acs_selected_channels.pri_channel =
  1470. nla_get_u8(tb[QCA_WLAN_VENDOR_ATTR_ACS_PRIMARY_CHANNEL]);
  1471. event.acs_selected_channels.sec_channel =
  1472. nla_get_u8(tb[QCA_WLAN_VENDOR_ATTR_ACS_SECONDARY_CHANNEL]);
  1473. if (tb[QCA_WLAN_VENDOR_ATTR_ACS_VHT_SEG0_CENTER_CHANNEL])
  1474. event.acs_selected_channels.vht_seg0_center_ch =
  1475. nla_get_u8(tb[QCA_WLAN_VENDOR_ATTR_ACS_VHT_SEG0_CENTER_CHANNEL]);
  1476. if (tb[QCA_WLAN_VENDOR_ATTR_ACS_VHT_SEG0_CENTER_CHANNEL])
  1477. event.acs_selected_channels.vht_seg1_center_ch =
  1478. nla_get_u8(tb[QCA_WLAN_VENDOR_ATTR_ACS_VHT_SEG1_CENTER_CHANNEL]);
  1479. if (tb[QCA_WLAN_VENDOR_ATTR_ACS_CHWIDTH])
  1480. event.acs_selected_channels.ch_width =
  1481. nla_get_u16(tb[QCA_WLAN_VENDOR_ATTR_ACS_CHWIDTH]);
  1482. if (tb[QCA_WLAN_VENDOR_ATTR_ACS_HW_MODE]) {
  1483. u8 hw_mode = nla_get_u8(tb[QCA_WLAN_VENDOR_ATTR_ACS_HW_MODE]);
  1484. event.acs_selected_channels.hw_mode = get_qca_hw_mode(hw_mode);
  1485. if (event.acs_selected_channels.hw_mode == NUM_HOSTAPD_MODES ||
  1486. event.acs_selected_channels.hw_mode ==
  1487. HOSTAPD_MODE_IEEE80211ANY) {
  1488. wpa_printf(MSG_DEBUG,
  1489. "nl80211: Invalid hw_mode %d in ACS selection event",
  1490. hw_mode);
  1491. return;
  1492. }
  1493. }
  1494. wpa_printf(MSG_INFO,
  1495. "nl80211: ACS Results: PCH: %d SCH: %d BW: %d VHT0: %d VHT1: %d HW_MODE: %d",
  1496. event.acs_selected_channels.pri_channel,
  1497. event.acs_selected_channels.sec_channel,
  1498. event.acs_selected_channels.ch_width,
  1499. event.acs_selected_channels.vht_seg0_center_ch,
  1500. event.acs_selected_channels.vht_seg1_center_ch,
  1501. event.acs_selected_channels.hw_mode);
  1502. /* Ignore ACS channel list check for backwards compatibility */
  1503. wpa_supplicant_event(drv->ctx, EVENT_ACS_CHANNEL_SELECTED, &event);
  1504. }
  1505. static void qca_nl80211_key_mgmt_auth(struct wpa_driver_nl80211_data *drv,
  1506. const u8 *data, size_t len)
  1507. {
  1508. struct nlattr *tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_MAX + 1];
  1509. u8 *bssid;
  1510. wpa_printf(MSG_DEBUG,
  1511. "nl80211: Key management roam+auth vendor event received");
  1512. if (nla_parse(tb, QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_MAX,
  1513. (struct nlattr *) data, len, NULL) ||
  1514. !tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_BSSID] ||
  1515. nla_len(tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_BSSID]) != ETH_ALEN ||
  1516. !tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_REQ_IE] ||
  1517. !tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_RESP_IE] ||
  1518. !tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_AUTHORIZED])
  1519. return;
  1520. bssid = nla_data(tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_BSSID]);
  1521. wpa_printf(MSG_DEBUG, " * roam BSSID " MACSTR, MAC2STR(bssid));
  1522. mlme_event_connect(drv, NL80211_CMD_ROAM, NULL,
  1523. tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_BSSID],
  1524. tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_REQ_IE],
  1525. tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_RESP_IE],
  1526. NULL, NULL,
  1527. tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_AUTHORIZED],
  1528. tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_KEY_REPLAY_CTR],
  1529. tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_PTK_KCK],
  1530. tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_PTK_KEK],
  1531. tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_SUBNET_STATUS],
  1532. tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_FILS_ERP_NEXT_SEQ_NUM],
  1533. tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_PMK],
  1534. tb[QCA_WLAN_VENDOR_ATTR_ROAM_AUTH_PMKID]);
  1535. }
  1536. static void qca_nl80211_dfs_offload_radar_event(
  1537. struct wpa_driver_nl80211_data *drv, u32 subcmd, u8 *msg, int length)
  1538. {
  1539. union wpa_event_data data;
  1540. struct nlattr *tb[NL80211_ATTR_MAX + 1];
  1541. wpa_printf(MSG_DEBUG,
  1542. "nl80211: DFS offload radar vendor event received");
  1543. if (nla_parse(tb, NL80211_ATTR_MAX,
  1544. (struct nlattr *) msg, length, NULL))
  1545. return;
  1546. if (!tb[NL80211_ATTR_WIPHY_FREQ]) {
  1547. wpa_printf(MSG_INFO,
  1548. "nl80211: Error parsing WIPHY_FREQ in FS offload radar vendor event");
  1549. return;
  1550. }
  1551. os_memset(&data, 0, sizeof(data));
  1552. data.dfs_event.freq = nla_get_u32(tb[NL80211_ATTR_WIPHY_FREQ]);
  1553. wpa_printf(MSG_DEBUG, "nl80211: DFS event on freq %d MHz",
  1554. data.dfs_event.freq);
  1555. /* Check HT params */
  1556. if (tb[NL80211_ATTR_WIPHY_CHANNEL_TYPE]) {
  1557. data.dfs_event.ht_enabled = 1;
  1558. data.dfs_event.chan_offset = 0;
  1559. switch (nla_get_u32(tb[NL80211_ATTR_WIPHY_CHANNEL_TYPE])) {
  1560. case NL80211_CHAN_NO_HT:
  1561. data.dfs_event.ht_enabled = 0;
  1562. break;
  1563. case NL80211_CHAN_HT20:
  1564. break;
  1565. case NL80211_CHAN_HT40PLUS:
  1566. data.dfs_event.chan_offset = 1;
  1567. break;
  1568. case NL80211_CHAN_HT40MINUS:
  1569. data.dfs_event.chan_offset = -1;
  1570. break;
  1571. }
  1572. }
  1573. /* Get VHT params */
  1574. if (tb[NL80211_ATTR_CHANNEL_WIDTH])
  1575. data.dfs_event.chan_width =
  1576. convert2width(nla_get_u32(
  1577. tb[NL80211_ATTR_CHANNEL_WIDTH]));
  1578. if (tb[NL80211_ATTR_CENTER_FREQ1])
  1579. data.dfs_event.cf1 = nla_get_u32(tb[NL80211_ATTR_CENTER_FREQ1]);
  1580. if (tb[NL80211_ATTR_CENTER_FREQ2])
  1581. data.dfs_event.cf2 = nla_get_u32(tb[NL80211_ATTR_CENTER_FREQ2]);
  1582. wpa_printf(MSG_DEBUG, "nl80211: DFS event on freq %d MHz, ht: %d, "
  1583. "offset: %d, width: %d, cf1: %dMHz, cf2: %dMHz",
  1584. data.dfs_event.freq, data.dfs_event.ht_enabled,
  1585. data.dfs_event.chan_offset, data.dfs_event.chan_width,
  1586. data.dfs_event.cf1, data.dfs_event.cf2);
  1587. switch (subcmd) {
  1588. case QCA_NL80211_VENDOR_SUBCMD_DFS_OFFLOAD_RADAR_DETECTED:
  1589. wpa_supplicant_event(drv->ctx, EVENT_DFS_RADAR_DETECTED, &data);
  1590. break;
  1591. case QCA_NL80211_VENDOR_SUBCMD_DFS_OFFLOAD_CAC_STARTED:
  1592. wpa_supplicant_event(drv->ctx, EVENT_DFS_CAC_STARTED, &data);
  1593. break;
  1594. case QCA_NL80211_VENDOR_SUBCMD_DFS_OFFLOAD_CAC_FINISHED:
  1595. wpa_supplicant_event(drv->ctx, EVENT_DFS_CAC_FINISHED, &data);
  1596. break;
  1597. case QCA_NL80211_VENDOR_SUBCMD_DFS_OFFLOAD_CAC_ABORTED:
  1598. wpa_supplicant_event(drv->ctx, EVENT_DFS_CAC_ABORTED, &data);
  1599. break;
  1600. case QCA_NL80211_VENDOR_SUBCMD_DFS_OFFLOAD_CAC_NOP_FINISHED:
  1601. wpa_supplicant_event(drv->ctx, EVENT_DFS_NOP_FINISHED, &data);
  1602. break;
  1603. default:
  1604. wpa_printf(MSG_DEBUG,
  1605. "nl80211: Unknown DFS offload radar event %d received",
  1606. subcmd);
  1607. break;
  1608. }
  1609. }
  1610. static void qca_nl80211_scan_trigger_event(struct wpa_driver_nl80211_data *drv,
  1611. u8 *data, size_t len)
  1612. {
  1613. struct nlattr *tb[QCA_WLAN_VENDOR_ATTR_SCAN_MAX + 1];
  1614. u64 cookie = 0;
  1615. union wpa_event_data event;
  1616. struct scan_info *info;
  1617. if (nla_parse(tb, QCA_WLAN_VENDOR_ATTR_SCAN_MAX,
  1618. (struct nlattr *) data, len, NULL) ||
  1619. !tb[QCA_WLAN_VENDOR_ATTR_SCAN_COOKIE])
  1620. return;
  1621. cookie = nla_get_u64(tb[QCA_WLAN_VENDOR_ATTR_SCAN_COOKIE]);
  1622. if (cookie != drv->vendor_scan_cookie) {
  1623. /* External scan trigger event, ignore */
  1624. return;
  1625. }
  1626. /* Cookie match, own scan */
  1627. os_memset(&event, 0, sizeof(event));
  1628. info = &event.scan_info;
  1629. info->external_scan = 0;
  1630. info->nl_scan_event = 0;
  1631. drv->scan_state = SCAN_STARTED;
  1632. wpa_supplicant_event(drv->ctx, EVENT_SCAN_STARTED, &event);
  1633. }
  1634. static void send_vendor_scan_event(struct wpa_driver_nl80211_data *drv,
  1635. int aborted, struct nlattr *tb[],
  1636. int external_scan)
  1637. {
  1638. union wpa_event_data event;
  1639. struct nlattr *nl;
  1640. int rem;
  1641. struct scan_info *info;
  1642. int freqs[MAX_REPORT_FREQS];
  1643. int num_freqs = 0;
  1644. os_memset(&event, 0, sizeof(event));
  1645. info = &event.scan_info;
  1646. info->aborted = aborted;
  1647. info->external_scan = external_scan;
  1648. if (tb[QCA_WLAN_VENDOR_ATTR_SCAN_SSIDS]) {
  1649. nla_for_each_nested(nl,
  1650. tb[QCA_WLAN_VENDOR_ATTR_SCAN_SSIDS], rem) {
  1651. struct wpa_driver_scan_ssid *s =
  1652. &info->ssids[info->num_ssids];
  1653. s->ssid = nla_data(nl);
  1654. s->ssid_len = nla_len(nl);
  1655. wpa_printf(MSG_DEBUG,
  1656. "nl80211: Scan probed for SSID '%s'",
  1657. wpa_ssid_txt(s->ssid, s->ssid_len));
  1658. info->num_ssids++;
  1659. if (info->num_ssids == WPAS_MAX_SCAN_SSIDS)
  1660. break;
  1661. }
  1662. }
  1663. if (tb[QCA_WLAN_VENDOR_ATTR_SCAN_FREQUENCIES]) {
  1664. char msg[300], *pos, *end;
  1665. int res;
  1666. pos = msg;
  1667. end = pos + sizeof(msg);
  1668. *pos = '\0';
  1669. nla_for_each_nested(nl,
  1670. tb[QCA_WLAN_VENDOR_ATTR_SCAN_FREQUENCIES],
  1671. rem) {
  1672. freqs[num_freqs] = nla_get_u32(nl);
  1673. res = os_snprintf(pos, end - pos, " %d",
  1674. freqs[num_freqs]);
  1675. if (!os_snprintf_error(end - pos, res))
  1676. pos += res;
  1677. num_freqs++;
  1678. if (num_freqs == MAX_REPORT_FREQS - 1)
  1679. break;
  1680. }
  1681. info->freqs = freqs;
  1682. info->num_freqs = num_freqs;
  1683. wpa_printf(MSG_DEBUG, "nl80211: Scan included frequencies:%s",
  1684. msg);
  1685. }
  1686. wpa_supplicant_event(drv->ctx, EVENT_SCAN_RESULTS, &event);
  1687. }
  1688. static void qca_nl80211_scan_done_event(struct wpa_driver_nl80211_data *drv,
  1689. u8 *data, size_t len)
  1690. {
  1691. struct nlattr *tb[QCA_WLAN_VENDOR_ATTR_SCAN_MAX + 1];
  1692. u64 cookie = 0;
  1693. enum scan_status status;
  1694. int external_scan;
  1695. if (nla_parse(tb, QCA_WLAN_VENDOR_ATTR_SCAN_MAX,
  1696. (struct nlattr *) data, len, NULL) ||
  1697. !tb[QCA_WLAN_VENDOR_ATTR_SCAN_STATUS] ||
  1698. !tb[QCA_WLAN_VENDOR_ATTR_SCAN_COOKIE])
  1699. return;
  1700. status = nla_get_u8(tb[QCA_WLAN_VENDOR_ATTR_SCAN_STATUS]);
  1701. if (status >= VENDOR_SCAN_STATUS_MAX)
  1702. return; /* invalid status */
  1703. cookie = nla_get_u64(tb[QCA_WLAN_VENDOR_ATTR_SCAN_COOKIE]);
  1704. if (cookie != drv->vendor_scan_cookie) {
  1705. /* Event from an external scan, get scan results */
  1706. external_scan = 1;
  1707. } else {
  1708. external_scan = 0;
  1709. if (status == VENDOR_SCAN_STATUS_NEW_RESULTS)
  1710. drv->scan_state = SCAN_COMPLETED;
  1711. else
  1712. drv->scan_state = SCAN_ABORTED;
  1713. eloop_cancel_timeout(wpa_driver_nl80211_scan_timeout, drv,
  1714. drv->ctx);
  1715. drv->vendor_scan_cookie = 0;
  1716. drv->last_scan_cmd = 0;
  1717. }
  1718. send_vendor_scan_event(drv, (status == VENDOR_SCAN_STATUS_ABORTED), tb,
  1719. external_scan);
  1720. }
  1721. static void qca_nl80211_p2p_lo_stop_event(struct wpa_driver_nl80211_data *drv,
  1722. u8 *data, size_t len)
  1723. {
  1724. struct nlattr *tb[QCA_WLAN_VENDOR_ATTR_P2P_LISTEN_OFFLOAD_MAX + 1];
  1725. union wpa_event_data event;
  1726. wpa_printf(MSG_DEBUG,
  1727. "nl80211: P2P listen offload stop vendor event received");
  1728. if (nla_parse(tb, QCA_WLAN_VENDOR_ATTR_P2P_LISTEN_OFFLOAD_MAX,
  1729. (struct nlattr *) data, len, NULL) ||
  1730. !tb[QCA_WLAN_VENDOR_ATTR_P2P_LISTEN_OFFLOAD_STOP_REASON])
  1731. return;
  1732. os_memset(&event, 0, sizeof(event));
  1733. event.p2p_lo_stop.reason_code =
  1734. nla_get_u8(tb[QCA_WLAN_VENDOR_ATTR_P2P_LISTEN_OFFLOAD_STOP_REASON]);
  1735. wpa_printf(MSG_DEBUG,
  1736. "nl80211: P2P Listen offload stop reason: %d",
  1737. event.p2p_lo_stop.reason_code);
  1738. wpa_supplicant_event(drv->ctx, EVENT_P2P_LO_STOP, &event);
  1739. }
  1740. #endif /* CONFIG_DRIVER_NL80211_QCA */
  1741. static void nl80211_vendor_event_qca(struct wpa_driver_nl80211_data *drv,
  1742. u32 subcmd, u8 *data, size_t len)
  1743. {
  1744. switch (subcmd) {
  1745. case QCA_NL80211_VENDOR_SUBCMD_TEST:
  1746. wpa_hexdump(MSG_DEBUG, "nl80211: QCA test event", data, len);
  1747. break;
  1748. #ifdef CONFIG_DRIVER_NL80211_QCA
  1749. case QCA_NL80211_VENDOR_SUBCMD_AVOID_FREQUENCY:
  1750. qca_nl80211_avoid_freq(drv, data, len);
  1751. break;
  1752. case QCA_NL80211_VENDOR_SUBCMD_KEY_MGMT_ROAM_AUTH:
  1753. qca_nl80211_key_mgmt_auth(drv, data, len);
  1754. break;
  1755. case QCA_NL80211_VENDOR_SUBCMD_DO_ACS:
  1756. qca_nl80211_acs_select_ch(drv, data, len);
  1757. break;
  1758. case QCA_NL80211_VENDOR_SUBCMD_DFS_OFFLOAD_CAC_STARTED:
  1759. case QCA_NL80211_VENDOR_SUBCMD_DFS_OFFLOAD_CAC_FINISHED:
  1760. case QCA_NL80211_VENDOR_SUBCMD_DFS_OFFLOAD_CAC_ABORTED:
  1761. case QCA_NL80211_VENDOR_SUBCMD_DFS_OFFLOAD_CAC_NOP_FINISHED:
  1762. case QCA_NL80211_VENDOR_SUBCMD_DFS_OFFLOAD_RADAR_DETECTED:
  1763. qca_nl80211_dfs_offload_radar_event(drv, subcmd, data, len);
  1764. break;
  1765. case QCA_NL80211_VENDOR_SUBCMD_TRIGGER_SCAN:
  1766. qca_nl80211_scan_trigger_event(drv, data, len);
  1767. break;
  1768. case QCA_NL80211_VENDOR_SUBCMD_SCAN_DONE:
  1769. qca_nl80211_scan_done_event(drv, data, len);
  1770. break;
  1771. case QCA_NL80211_VENDOR_SUBCMD_P2P_LISTEN_OFFLOAD_STOP:
  1772. qca_nl80211_p2p_lo_stop_event(drv, data, len);
  1773. break;
  1774. #endif /* CONFIG_DRIVER_NL80211_QCA */
  1775. default:
  1776. wpa_printf(MSG_DEBUG,
  1777. "nl80211: Ignore unsupported QCA vendor event %u",
  1778. subcmd);
  1779. break;
  1780. }
  1781. }
  1782. static void nl80211_vendor_event(struct wpa_driver_nl80211_data *drv,
  1783. struct nlattr **tb)
  1784. {
  1785. u32 vendor_id, subcmd, wiphy = 0;
  1786. int wiphy_idx;
  1787. u8 *data = NULL;
  1788. size_t len = 0;
  1789. if (!tb[NL80211_ATTR_VENDOR_ID] ||
  1790. !tb[NL80211_ATTR_VENDOR_SUBCMD])
  1791. return;
  1792. vendor_id = nla_get_u32(tb[NL80211_ATTR_VENDOR_ID]);
  1793. subcmd = nla_get_u32(tb[NL80211_ATTR_VENDOR_SUBCMD]);
  1794. if (tb[NL80211_ATTR_WIPHY])
  1795. wiphy = nla_get_u32(tb[NL80211_ATTR_WIPHY]);
  1796. wpa_printf(MSG_DEBUG, "nl80211: Vendor event: wiphy=%u vendor_id=0x%x subcmd=%u",
  1797. wiphy, vendor_id, subcmd);
  1798. if (tb[NL80211_ATTR_VENDOR_DATA]) {
  1799. data = nla_data(tb[NL80211_ATTR_VENDOR_DATA]);
  1800. len = nla_len(tb[NL80211_ATTR_VENDOR_DATA]);
  1801. wpa_hexdump(MSG_MSGDUMP, "nl80211: Vendor data", data, len);
  1802. }
  1803. wiphy_idx = nl80211_get_wiphy_index(drv->first_bss);
  1804. if (wiphy_idx >= 0 && wiphy_idx != (int) wiphy) {
  1805. wpa_printf(MSG_DEBUG, "nl80211: Ignore vendor event for foreign wiphy %u (own: %d)",
  1806. wiphy, wiphy_idx);
  1807. return;
  1808. }
  1809. switch (vendor_id) {
  1810. case OUI_QCA:
  1811. nl80211_vendor_event_qca(drv, subcmd, data, len);
  1812. break;
  1813. default:
  1814. wpa_printf(MSG_DEBUG, "nl80211: Ignore unsupported vendor event");
  1815. break;
  1816. }
  1817. }
  1818. static void nl80211_reg_change_event(struct wpa_driver_nl80211_data *drv,
  1819. struct nlattr *tb[])
  1820. {
  1821. union wpa_event_data data;
  1822. enum nl80211_reg_initiator init;
  1823. wpa_printf(MSG_DEBUG, "nl80211: Regulatory domain change");
  1824. if (tb[NL80211_ATTR_REG_INITIATOR] == NULL)
  1825. return;
  1826. os_memset(&data, 0, sizeof(data));
  1827. init = nla_get_u8(tb[NL80211_ATTR_REG_INITIATOR]);
  1828. wpa_printf(MSG_DEBUG, " * initiator=%d", init);
  1829. switch (init) {
  1830. case NL80211_REGDOM_SET_BY_CORE:
  1831. data.channel_list_changed.initiator = REGDOM_SET_BY_CORE;
  1832. break;
  1833. case NL80211_REGDOM_SET_BY_USER:
  1834. data.channel_list_changed.initiator = REGDOM_SET_BY_USER;
  1835. break;
  1836. case NL80211_REGDOM_SET_BY_DRIVER:
  1837. data.channel_list_changed.initiator = REGDOM_SET_BY_DRIVER;
  1838. break;
  1839. case NL80211_REGDOM_SET_BY_COUNTRY_IE:
  1840. data.channel_list_changed.initiator = REGDOM_SET_BY_COUNTRY_IE;
  1841. break;
  1842. }
  1843. if (tb[NL80211_ATTR_REG_TYPE]) {
  1844. enum nl80211_reg_type type;
  1845. type = nla_get_u8(tb[NL80211_ATTR_REG_TYPE]);
  1846. wpa_printf(MSG_DEBUG, " * type=%d", type);
  1847. switch (type) {
  1848. case NL80211_REGDOM_TYPE_COUNTRY:
  1849. data.channel_list_changed.type = REGDOM_TYPE_COUNTRY;
  1850. break;
  1851. case NL80211_REGDOM_TYPE_WORLD:
  1852. data.channel_list_changed.type = REGDOM_TYPE_WORLD;
  1853. break;
  1854. case NL80211_REGDOM_TYPE_CUSTOM_WORLD:
  1855. data.channel_list_changed.type =
  1856. REGDOM_TYPE_CUSTOM_WORLD;
  1857. break;
  1858. case NL80211_REGDOM_TYPE_INTERSECTION:
  1859. data.channel_list_changed.type =
  1860. REGDOM_TYPE_INTERSECTION;
  1861. break;
  1862. }
  1863. }
  1864. if (tb[NL80211_ATTR_REG_ALPHA2]) {
  1865. os_strlcpy(data.channel_list_changed.alpha2,
  1866. nla_get_string(tb[NL80211_ATTR_REG_ALPHA2]),
  1867. sizeof(data.channel_list_changed.alpha2));
  1868. wpa_printf(MSG_DEBUG, " * alpha2=%s",
  1869. data.channel_list_changed.alpha2);
  1870. }
  1871. wpa_supplicant_event(drv->ctx, EVENT_CHANNEL_LIST_CHANGED, &data);
  1872. }
  1873. static void nl80211_external_auth(struct wpa_driver_nl80211_data *drv,
  1874. struct nlattr **tb)
  1875. {
  1876. union wpa_event_data event;
  1877. enum nl80211_external_auth_action act;
  1878. if (!tb[NL80211_ATTR_AKM_SUITES] ||
  1879. !tb[NL80211_ATTR_EXTERNAL_AUTH_ACTION] ||
  1880. !tb[NL80211_ATTR_BSSID] ||
  1881. !tb[NL80211_ATTR_SSID])
  1882. return;
  1883. os_memset(&event, 0, sizeof(event));
  1884. act = nla_get_u32(tb[NL80211_ATTR_EXTERNAL_AUTH_ACTION]);
  1885. switch (act) {
  1886. case NL80211_EXTERNAL_AUTH_START:
  1887. event.external_auth.action = EXT_AUTH_START;
  1888. break;
  1889. case NL80211_EXTERNAL_AUTH_ABORT:
  1890. event.external_auth.action = EXT_AUTH_ABORT;
  1891. break;
  1892. default:
  1893. return;
  1894. }
  1895. event.external_auth.key_mgmt_suite =
  1896. nla_get_u32(tb[NL80211_ATTR_AKM_SUITES]);
  1897. event.external_auth.ssid_len = nla_len(tb[NL80211_ATTR_SSID]);
  1898. if (event.external_auth.ssid_len > SSID_MAX_LEN)
  1899. return;
  1900. os_memcpy(event.external_auth.ssid, nla_data(tb[NL80211_ATTR_SSID]),
  1901. event.external_auth.ssid_len);
  1902. os_memcpy(event.external_auth.bssid, nla_data(tb[NL80211_ATTR_BSSID]),
  1903. ETH_ALEN);
  1904. wpa_printf(MSG_DEBUG,
  1905. "nl80211: External auth action: %u, AKM: 0x%x",
  1906. event.external_auth.action,
  1907. event.external_auth.key_mgmt_suite);
  1908. wpa_supplicant_event(drv->ctx, EVENT_EXTERNAL_AUTH, &event);
  1909. }
  1910. static void nl80211_port_authorized(struct wpa_driver_nl80211_data *drv,
  1911. struct nlattr **tb)
  1912. {
  1913. const u8 *addr;
  1914. if (!tb[NL80211_ATTR_MAC] ||
  1915. nla_len(tb[NL80211_ATTR_MAC]) != ETH_ALEN) {
  1916. wpa_printf(MSG_DEBUG,
  1917. "nl80211: Ignore port authorized event without BSSID");
  1918. return;
  1919. }
  1920. addr = nla_data(tb[NL80211_ATTR_MAC]);
  1921. if (os_memcmp(addr, drv->bssid, ETH_ALEN) != 0) {
  1922. wpa_printf(MSG_DEBUG,
  1923. "nl80211: Ignore port authorized event for " MACSTR
  1924. " (not the currently connected BSSID " MACSTR ")",
  1925. MAC2STR(addr), MAC2STR(drv->bssid));
  1926. return;
  1927. }
  1928. wpa_supplicant_event(drv->ctx, EVENT_PORT_AUTHORIZED, NULL);
  1929. }
  1930. static void nl80211_sta_opmode_change_event(struct wpa_driver_nl80211_data *drv,
  1931. struct nlattr **tb)
  1932. {
  1933. union wpa_event_data ed;
  1934. u8 smps_mode, max_bw;
  1935. if (!tb[NL80211_ATTR_MAC] ||
  1936. (!tb[NL80211_ATTR_CHANNEL_WIDTH] &&
  1937. !tb[NL80211_ATTR_SMPS_MODE] &&
  1938. !tb[NL80211_ATTR_NSS]))
  1939. return;
  1940. ed.sta_opmode.smps_mode = SMPS_INVALID;
  1941. ed.sta_opmode.chan_width = CHAN_WIDTH_UNKNOWN;
  1942. ed.sta_opmode.rx_nss = 0xff;
  1943. ed.sta_opmode.addr = nla_data(tb[NL80211_ATTR_MAC]);
  1944. if (tb[NL80211_ATTR_SMPS_MODE]) {
  1945. smps_mode = nla_get_u32(tb[NL80211_ATTR_SMPS_MODE]);
  1946. switch (smps_mode) {
  1947. case NL80211_SMPS_OFF:
  1948. ed.sta_opmode.smps_mode = SMPS_OFF;
  1949. break;
  1950. case NL80211_SMPS_STATIC:
  1951. ed.sta_opmode.smps_mode = SMPS_STATIC;
  1952. break;
  1953. case NL80211_SMPS_DYNAMIC:
  1954. ed.sta_opmode.smps_mode = SMPS_DYNAMIC;
  1955. break;
  1956. default:
  1957. ed.sta_opmode.smps_mode = SMPS_INVALID;
  1958. break;
  1959. }
  1960. }
  1961. if (tb[NL80211_ATTR_CHANNEL_WIDTH]) {
  1962. max_bw = nla_get_u32(tb[NL80211_ATTR_CHANNEL_WIDTH]);
  1963. switch (max_bw) {
  1964. case NL80211_CHAN_WIDTH_20_NOHT:
  1965. ed.sta_opmode.chan_width = CHAN_WIDTH_20_NOHT;
  1966. break;
  1967. case NL80211_CHAN_WIDTH_20:
  1968. ed.sta_opmode.chan_width = CHAN_WIDTH_20;
  1969. break;
  1970. case NL80211_CHAN_WIDTH_40:
  1971. ed.sta_opmode.chan_width = CHAN_WIDTH_40;
  1972. break;
  1973. case NL80211_CHAN_WIDTH_80:
  1974. ed.sta_opmode.chan_width = CHAN_WIDTH_80;
  1975. break;
  1976. case NL80211_CHAN_WIDTH_80P80:
  1977. ed.sta_opmode.chan_width = CHAN_WIDTH_80P80;
  1978. break;
  1979. case NL80211_CHAN_WIDTH_160:
  1980. ed.sta_opmode.chan_width = CHAN_WIDTH_160;
  1981. break;
  1982. default:
  1983. ed.sta_opmode.chan_width = CHAN_WIDTH_UNKNOWN;
  1984. break;
  1985. }
  1986. }
  1987. if (tb[NL80211_ATTR_NSS])
  1988. ed.sta_opmode.rx_nss = nla_get_u8(tb[NL80211_ATTR_NSS]);
  1989. wpa_supplicant_event(drv->ctx, EVENT_STATION_OPMODE_CHANGED, &ed);
  1990. }
  1991. static void do_process_drv_event(struct i802_bss *bss, int cmd,
  1992. struct nlattr **tb)
  1993. {
  1994. struct wpa_driver_nl80211_data *drv = bss->drv;
  1995. union wpa_event_data data;
  1996. int external_scan_event = 0;
  1997. wpa_printf(MSG_DEBUG, "nl80211: Drv Event %d (%s) received for %s",
  1998. cmd, nl80211_command_to_string(cmd), bss->ifname);
  1999. if (cmd == NL80211_CMD_ROAM &&
  2000. (drv->capa.flags & WPA_DRIVER_FLAGS_KEY_MGMT_OFFLOAD)) {
  2001. /*
  2002. * Device will use roam+auth vendor event to indicate
  2003. * roaming, so ignore the regular roam event.
  2004. */
  2005. wpa_printf(MSG_DEBUG,
  2006. "nl80211: Ignore roam event (cmd=%d), device will use vendor event roam+auth",
  2007. cmd);
  2008. return;
  2009. }
  2010. if (drv->ap_scan_as_station != NL80211_IFTYPE_UNSPECIFIED &&
  2011. (cmd == NL80211_CMD_NEW_SCAN_RESULTS ||
  2012. cmd == NL80211_CMD_SCAN_ABORTED)) {
  2013. wpa_driver_nl80211_set_mode(drv->first_bss,
  2014. drv->ap_scan_as_station);
  2015. drv->ap_scan_as_station = NL80211_IFTYPE_UNSPECIFIED;
  2016. }
  2017. switch (cmd) {
  2018. case NL80211_CMD_TRIGGER_SCAN:
  2019. wpa_dbg(drv->ctx, MSG_DEBUG, "nl80211: Scan trigger");
  2020. drv->scan_state = SCAN_STARTED;
  2021. if (drv->scan_for_auth) {
  2022. /*
  2023. * Cannot indicate EVENT_SCAN_STARTED here since we skip
  2024. * EVENT_SCAN_RESULTS in scan_for_auth case and the
  2025. * upper layer implementation could get confused about
  2026. * scanning state.
  2027. */
  2028. wpa_printf(MSG_DEBUG, "nl80211: Do not indicate scan-start event due to internal scan_for_auth");
  2029. break;
  2030. }
  2031. wpa_supplicant_event(drv->ctx, EVENT_SCAN_STARTED, NULL);
  2032. break;
  2033. case NL80211_CMD_START_SCHED_SCAN:
  2034. wpa_dbg(drv->ctx, MSG_DEBUG, "nl80211: Sched scan started");
  2035. drv->scan_state = SCHED_SCAN_STARTED;
  2036. break;
  2037. case NL80211_CMD_SCHED_SCAN_STOPPED:
  2038. wpa_dbg(drv->ctx, MSG_DEBUG, "nl80211: Sched scan stopped");
  2039. drv->scan_state = SCHED_SCAN_STOPPED;
  2040. wpa_supplicant_event(drv->ctx, EVENT_SCHED_SCAN_STOPPED, NULL);
  2041. break;
  2042. case NL80211_CMD_NEW_SCAN_RESULTS:
  2043. wpa_dbg(drv->ctx, MSG_DEBUG,
  2044. "nl80211: New scan results available");
  2045. if (drv->last_scan_cmd != NL80211_CMD_VENDOR)
  2046. drv->scan_state = SCAN_COMPLETED;
  2047. drv->scan_complete_events = 1;
  2048. if (drv->last_scan_cmd == NL80211_CMD_TRIGGER_SCAN) {
  2049. eloop_cancel_timeout(wpa_driver_nl80211_scan_timeout,
  2050. drv, drv->ctx);
  2051. drv->last_scan_cmd = 0;
  2052. } else {
  2053. external_scan_event = 1;
  2054. }
  2055. send_scan_event(drv, 0, tb, external_scan_event);
  2056. break;
  2057. case NL80211_CMD_SCHED_SCAN_RESULTS:
  2058. wpa_dbg(drv->ctx, MSG_DEBUG,
  2059. "nl80211: New sched scan results available");
  2060. drv->scan_state = SCHED_SCAN_RESULTS;
  2061. send_scan_event(drv, 0, tb, 0);
  2062. break;
  2063. case NL80211_CMD_SCAN_ABORTED:
  2064. wpa_dbg(drv->ctx, MSG_DEBUG, "nl80211: Scan aborted");
  2065. if (drv->last_scan_cmd != NL80211_CMD_VENDOR)
  2066. drv->scan_state = SCAN_ABORTED;
  2067. if (drv->last_scan_cmd == NL80211_CMD_TRIGGER_SCAN) {
  2068. /*
  2069. * Need to indicate that scan results are available in
  2070. * order not to make wpa_supplicant stop its scanning.
  2071. */
  2072. eloop_cancel_timeout(wpa_driver_nl80211_scan_timeout,
  2073. drv, drv->ctx);
  2074. drv->last_scan_cmd = 0;
  2075. } else {
  2076. external_scan_event = 1;
  2077. }
  2078. send_scan_event(drv, 1, tb, external_scan_event);
  2079. break;
  2080. case NL80211_CMD_AUTHENTICATE:
  2081. case NL80211_CMD_ASSOCIATE:
  2082. case NL80211_CMD_DEAUTHENTICATE:
  2083. case NL80211_CMD_DISASSOCIATE:
  2084. case NL80211_CMD_FRAME_TX_STATUS:
  2085. case NL80211_CMD_UNPROT_DEAUTHENTICATE:
  2086. case NL80211_CMD_UNPROT_DISASSOCIATE:
  2087. mlme_event(bss, cmd, tb[NL80211_ATTR_FRAME],
  2088. tb[NL80211_ATTR_MAC], tb[NL80211_ATTR_TIMED_OUT],
  2089. tb[NL80211_ATTR_WIPHY_FREQ], tb[NL80211_ATTR_ACK],
  2090. tb[NL80211_ATTR_COOKIE],
  2091. tb[NL80211_ATTR_RX_SIGNAL_DBM],
  2092. tb[NL80211_ATTR_STA_WME]);
  2093. break;
  2094. case NL80211_CMD_CONNECT:
  2095. case NL80211_CMD_ROAM:
  2096. mlme_event_connect(drv, cmd,
  2097. tb[NL80211_ATTR_STATUS_CODE],
  2098. tb[NL80211_ATTR_MAC],
  2099. tb[NL80211_ATTR_REQ_IE],
  2100. tb[NL80211_ATTR_RESP_IE],
  2101. tb[NL80211_ATTR_TIMED_OUT],
  2102. tb[NL80211_ATTR_TIMEOUT_REASON],
  2103. NULL, NULL, NULL,
  2104. tb[NL80211_ATTR_FILS_KEK],
  2105. NULL,
  2106. tb[NL80211_ATTR_FILS_ERP_NEXT_SEQ_NUM],
  2107. tb[NL80211_ATTR_PMK],
  2108. tb[NL80211_ATTR_PMKID]);
  2109. break;
  2110. case NL80211_CMD_CH_SWITCH_NOTIFY:
  2111. mlme_event_ch_switch(drv,
  2112. tb[NL80211_ATTR_IFINDEX],
  2113. tb[NL80211_ATTR_WIPHY_FREQ],
  2114. tb[NL80211_ATTR_WIPHY_CHANNEL_TYPE],
  2115. tb[NL80211_ATTR_CHANNEL_WIDTH],
  2116. tb[NL80211_ATTR_CENTER_FREQ1],
  2117. tb[NL80211_ATTR_CENTER_FREQ2]);
  2118. break;
  2119. case NL80211_CMD_DISCONNECT:
  2120. mlme_event_disconnect(drv, tb[NL80211_ATTR_REASON_CODE],
  2121. tb[NL80211_ATTR_MAC],
  2122. tb[NL80211_ATTR_DISCONNECTED_BY_AP]);
  2123. break;
  2124. case NL80211_CMD_MICHAEL_MIC_FAILURE:
  2125. mlme_event_michael_mic_failure(bss, tb);
  2126. break;
  2127. case NL80211_CMD_JOIN_IBSS:
  2128. mlme_event_join_ibss(drv, tb);
  2129. break;
  2130. case NL80211_CMD_REMAIN_ON_CHANNEL:
  2131. mlme_event_remain_on_channel(drv, 0, tb);
  2132. break;
  2133. case NL80211_CMD_CANCEL_REMAIN_ON_CHANNEL:
  2134. mlme_event_remain_on_channel(drv, 1, tb);
  2135. break;
  2136. case NL80211_CMD_NOTIFY_CQM:
  2137. nl80211_cqm_event(drv, tb);
  2138. break;
  2139. case NL80211_CMD_REG_CHANGE:
  2140. nl80211_reg_change_event(drv, tb);
  2141. break;
  2142. case NL80211_CMD_REG_BEACON_HINT:
  2143. wpa_printf(MSG_DEBUG, "nl80211: Regulatory beacon hint");
  2144. os_memset(&data, 0, sizeof(data));
  2145. data.channel_list_changed.initiator = REGDOM_BEACON_HINT;
  2146. wpa_supplicant_event(drv->ctx, EVENT_CHANNEL_LIST_CHANGED,
  2147. &data);
  2148. break;
  2149. case NL80211_CMD_NEW_STATION:
  2150. nl80211_new_station_event(drv, bss, tb);
  2151. break;
  2152. case NL80211_CMD_DEL_STATION:
  2153. nl80211_del_station_event(drv, bss, tb);
  2154. break;
  2155. case NL80211_CMD_SET_REKEY_OFFLOAD:
  2156. nl80211_rekey_offload_event(drv, tb);
  2157. break;
  2158. case NL80211_CMD_PMKSA_CANDIDATE:
  2159. nl80211_pmksa_candidate_event(drv, tb);
  2160. break;
  2161. case NL80211_CMD_PROBE_CLIENT:
  2162. nl80211_client_probe_event(drv, tb);
  2163. break;
  2164. case NL80211_CMD_TDLS_OPER:
  2165. nl80211_tdls_oper_event(drv, tb);
  2166. break;
  2167. case NL80211_CMD_CONN_FAILED:
  2168. nl80211_connect_failed_event(drv, tb);
  2169. break;
  2170. case NL80211_CMD_FT_EVENT:
  2171. mlme_event_ft_event(drv, tb);
  2172. break;
  2173. case NL80211_CMD_RADAR_DETECT:
  2174. nl80211_radar_event(drv, tb);
  2175. break;
  2176. case NL80211_CMD_STOP_AP:
  2177. nl80211_stop_ap(drv, tb);
  2178. break;
  2179. case NL80211_CMD_VENDOR:
  2180. nl80211_vendor_event(drv, tb);
  2181. break;
  2182. case NL80211_CMD_NEW_PEER_CANDIDATE:
  2183. nl80211_new_peer_candidate(drv, tb);
  2184. break;
  2185. case NL80211_CMD_PORT_AUTHORIZED:
  2186. nl80211_port_authorized(drv, tb);
  2187. break;
  2188. case NL80211_CMD_STA_OPMODE_CHANGED:
  2189. nl80211_sta_opmode_change_event(drv, tb);
  2190. break;
  2191. default:
  2192. wpa_dbg(drv->ctx, MSG_DEBUG, "nl80211: Ignored unknown event "
  2193. "(cmd=%d)", cmd);
  2194. break;
  2195. }
  2196. }
  2197. int process_global_event(struct nl_msg *msg, void *arg)
  2198. {
  2199. struct nl80211_global *global = arg;
  2200. struct genlmsghdr *gnlh = nlmsg_data(nlmsg_hdr(msg));
  2201. struct nlattr *tb[NL80211_ATTR_MAX + 1];
  2202. struct wpa_driver_nl80211_data *drv, *tmp;
  2203. int ifidx = -1, wiphy_idx = -1, wiphy_idx_rx = -1;
  2204. struct i802_bss *bss;
  2205. u64 wdev_id = 0;
  2206. int wdev_id_set = 0;
  2207. int wiphy_idx_set = 0;
  2208. nla_parse(tb, NL80211_ATTR_MAX, genlmsg_attrdata(gnlh, 0),
  2209. genlmsg_attrlen(gnlh, 0), NULL);
  2210. if (tb[NL80211_ATTR_IFINDEX])
  2211. ifidx = nla_get_u32(tb[NL80211_ATTR_IFINDEX]);
  2212. else if (tb[NL80211_ATTR_WDEV]) {
  2213. wdev_id = nla_get_u64(tb[NL80211_ATTR_WDEV]);
  2214. wdev_id_set = 1;
  2215. } else if (tb[NL80211_ATTR_WIPHY]) {
  2216. wiphy_idx_rx = nla_get_u32(tb[NL80211_ATTR_WIPHY]);
  2217. wiphy_idx_set = 1;
  2218. }
  2219. dl_list_for_each_safe(drv, tmp, &global->interfaces,
  2220. struct wpa_driver_nl80211_data, list) {
  2221. for (bss = drv->first_bss; bss; bss = bss->next) {
  2222. if (wiphy_idx_set)
  2223. wiphy_idx = nl80211_get_wiphy_index(bss);
  2224. if ((ifidx == -1 && !wiphy_idx_set && !wdev_id_set) ||
  2225. ifidx == bss->ifindex ||
  2226. (wiphy_idx_set && wiphy_idx == wiphy_idx_rx) ||
  2227. (wdev_id_set && bss->wdev_id_set &&
  2228. wdev_id == bss->wdev_id)) {
  2229. do_process_drv_event(bss, gnlh->cmd, tb);
  2230. return NL_SKIP;
  2231. }
  2232. }
  2233. wpa_printf(MSG_DEBUG,
  2234. "nl80211: Ignored event (cmd=%d) for foreign interface (ifindex %d wdev 0x%llx)",
  2235. gnlh->cmd, ifidx, (long long unsigned int) wdev_id);
  2236. }
  2237. return NL_SKIP;
  2238. }
  2239. int process_bss_event(struct nl_msg *msg, void *arg)
  2240. {
  2241. struct i802_bss *bss = arg;
  2242. struct genlmsghdr *gnlh = nlmsg_data(nlmsg_hdr(msg));
  2243. struct nlattr *tb[NL80211_ATTR_MAX + 1];
  2244. nla_parse(tb, NL80211_ATTR_MAX, genlmsg_attrdata(gnlh, 0),
  2245. genlmsg_attrlen(gnlh, 0), NULL);
  2246. wpa_printf(MSG_DEBUG, "nl80211: BSS Event %d (%s) received for %s",
  2247. gnlh->cmd, nl80211_command_to_string(gnlh->cmd),
  2248. bss->ifname);
  2249. switch (gnlh->cmd) {
  2250. case NL80211_CMD_FRAME:
  2251. case NL80211_CMD_FRAME_TX_STATUS:
  2252. mlme_event(bss, gnlh->cmd, tb[NL80211_ATTR_FRAME],
  2253. tb[NL80211_ATTR_MAC], tb[NL80211_ATTR_TIMED_OUT],
  2254. tb[NL80211_ATTR_WIPHY_FREQ], tb[NL80211_ATTR_ACK],
  2255. tb[NL80211_ATTR_COOKIE],
  2256. tb[NL80211_ATTR_RX_SIGNAL_DBM],
  2257. tb[NL80211_ATTR_STA_WME]);
  2258. break;
  2259. case NL80211_CMD_UNEXPECTED_FRAME:
  2260. nl80211_spurious_frame(bss, tb, 0);
  2261. break;
  2262. case NL80211_CMD_UNEXPECTED_4ADDR_FRAME:
  2263. nl80211_spurious_frame(bss, tb, 1);
  2264. break;
  2265. case NL80211_CMD_EXTERNAL_AUTH:
  2266. nl80211_external_auth(bss->drv, tb);
  2267. break;
  2268. default:
  2269. wpa_printf(MSG_DEBUG, "nl80211: Ignored unknown event "
  2270. "(cmd=%d)", gnlh->cmd);
  2271. break;
  2272. }
  2273. return NL_SKIP;
  2274. }