qmi.c 83 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272227322742275227622772278227922802281228222832284228522862287228822892290229122922293229422952296229722982299230023012302230323042305230623072308230923102311231223132314231523162317231823192320232123222323232423252326232723282329233023312332233323342335233623372338233923402341234223432344234523462347234823492350235123522353235423552356235723582359236023612362236323642365236623672368236923702371237223732374237523762377237823792380238123822383238423852386238723882389239023912392239323942395239623972398239924002401240224032404240524062407240824092410241124122413241424152416241724182419242024212422242324242425242624272428242924302431243224332434243524362437243824392440244124422443244424452446244724482449245024512452245324542455245624572458245924602461246224632464246524662467246824692470247124722473247424752476247724782479248024812482248324842485248624872488248924902491249224932494249524962497249824992500250125022503250425052506250725082509251025112512251325142515251625172518251925202521252225232524252525262527252825292530253125322533253425352536253725382539254025412542254325442545254625472548254925502551255225532554255525562557255825592560256125622563256425652566256725682569257025712572257325742575257625772578257925802581258225832584258525862587258825892590259125922593259425952596259725982599260026012602260326042605260626072608260926102611261226132614261526162617261826192620262126222623262426252626262726282629263026312632263326342635263626372638263926402641264226432644264526462647264826492650265126522653265426552656265726582659266026612662266326642665266626672668266926702671267226732674267526762677267826792680268126822683268426852686268726882689269026912692269326942695269626972698269927002701270227032704270527062707270827092710271127122713271427152716271727182719272027212722272327242725272627272728272927302731273227332734273527362737273827392740274127422743274427452746274727482749275027512752275327542755275627572758275927602761276227632764276527662767276827692770277127722773277427752776277727782779278027812782278327842785278627872788278927902791279227932794279527962797279827992800280128022803280428052806280728082809281028112812281328142815281628172818281928202821282228232824282528262827282828292830283128322833283428352836283728382839284028412842284328442845284628472848284928502851285228532854285528562857285828592860286128622863286428652866286728682869287028712872287328742875287628772878287928802881288228832884288528862887288828892890289128922893289428952896289728982899290029012902290329042905290629072908290929102911291229132914291529162917291829192920292129222923292429252926292729282929293029312932293329342935293629372938293929402941294229432944294529462947294829492950295129522953295429552956295729582959296029612962296329642965296629672968296929702971297229732974297529762977297829792980298129822983298429852986298729882989299029912992299329942995299629972998299930003001300230033004300530063007300830093010301130123013301430153016301730183019302030213022302330243025302630273028302930303031303230333034303530363037303830393040304130423043304430453046304730483049305030513052305330543055305630573058305930603061306230633064306530663067306830693070307130723073307430753076307730783079308030813082308330843085308630873088308930903091309230933094309530963097309830993100310131023103310431053106310731083109311031113112311331143115311631173118311931203121312231233124312531263127312831293130313131323133313431353136313731383139314031413142314331443145314631473148314931503151315231533154315531563157315831593160316131623163316431653166316731683169317031713172317331743175317631773178317931803181318231833184318531863187318831893190319131923193319431953196319731983199320032013202320332043205320632073208320932103211321232133214321532163217321832193220322132223223322432253226322732283229323032313232323332343235323632373238323932403241324232433244324532463247324832493250325132523253325432553256325732583259326032613262326332643265326632673268326932703271327232733274327532763277327832793280328132823283328432853286328732883289329032913292329332943295329632973298
  1. // SPDX-License-Identifier: BSD-3-Clause-Clear
  2. /*
  3. * Copyright (c) 2018-2019 The Linux Foundation. All rights reserved.
  4. * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
  5. */
  6. #include <linux/elf.h>
  7. #include "qmi.h"
  8. #include "core.h"
  9. #include "debug.h"
  10. #include <linux/of.h>
  11. #include <linux/of_address.h>
  12. #include <linux/ioport.h>
  13. #include <linux/firmware.h>
  14. #include <linux/of_device.h>
  15. #include <linux/of_irq.h>
  16. #define SLEEP_CLOCK_SELECT_INTERNAL_BIT 0x02
  17. #define HOST_CSTATE_BIT 0x04
  18. #define PLATFORM_CAP_PCIE_GLOBAL_RESET 0x08
  19. #define PLATFORM_CAP_PCIE_PME_D3COLD 0x10
  20. #define FW_BUILD_ID_MASK "QC_IMAGE_VERSION_STRING="
  21. bool ath11k_cold_boot_cal = 1;
  22. EXPORT_SYMBOL(ath11k_cold_boot_cal);
  23. module_param_named(cold_boot_cal, ath11k_cold_boot_cal, bool, 0644);
  24. MODULE_PARM_DESC(cold_boot_cal,
  25. "Decrease the channel switch time but increase the driver load time (Default: true)");
  26. static struct qmi_elem_info qmi_wlanfw_host_cap_req_msg_v01_ei[] = {
  27. {
  28. .data_type = QMI_OPT_FLAG,
  29. .elem_len = 1,
  30. .elem_size = sizeof(u8),
  31. .array_type = NO_ARRAY,
  32. .tlv_type = 0x10,
  33. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  34. num_clients_valid),
  35. },
  36. {
  37. .data_type = QMI_UNSIGNED_4_BYTE,
  38. .elem_len = 1,
  39. .elem_size = sizeof(u32),
  40. .array_type = NO_ARRAY,
  41. .tlv_type = 0x10,
  42. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  43. num_clients),
  44. },
  45. {
  46. .data_type = QMI_OPT_FLAG,
  47. .elem_len = 1,
  48. .elem_size = sizeof(u8),
  49. .array_type = NO_ARRAY,
  50. .tlv_type = 0x11,
  51. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  52. wake_msi_valid),
  53. },
  54. {
  55. .data_type = QMI_UNSIGNED_4_BYTE,
  56. .elem_len = 1,
  57. .elem_size = sizeof(u32),
  58. .array_type = NO_ARRAY,
  59. .tlv_type = 0x11,
  60. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  61. wake_msi),
  62. },
  63. {
  64. .data_type = QMI_OPT_FLAG,
  65. .elem_len = 1,
  66. .elem_size = sizeof(u8),
  67. .array_type = NO_ARRAY,
  68. .tlv_type = 0x12,
  69. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  70. gpios_valid),
  71. },
  72. {
  73. .data_type = QMI_DATA_LEN,
  74. .elem_len = 1,
  75. .elem_size = sizeof(u8),
  76. .array_type = NO_ARRAY,
  77. .tlv_type = 0x12,
  78. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  79. gpios_len),
  80. },
  81. {
  82. .data_type = QMI_UNSIGNED_4_BYTE,
  83. .elem_len = QMI_WLFW_MAX_NUM_GPIO_V01,
  84. .elem_size = sizeof(u32),
  85. .array_type = VAR_LEN_ARRAY,
  86. .tlv_type = 0x12,
  87. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  88. gpios),
  89. },
  90. {
  91. .data_type = QMI_OPT_FLAG,
  92. .elem_len = 1,
  93. .elem_size = sizeof(u8),
  94. .array_type = NO_ARRAY,
  95. .tlv_type = 0x13,
  96. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  97. nm_modem_valid),
  98. },
  99. {
  100. .data_type = QMI_UNSIGNED_1_BYTE,
  101. .elem_len = 1,
  102. .elem_size = sizeof(u8),
  103. .array_type = NO_ARRAY,
  104. .tlv_type = 0x13,
  105. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  106. nm_modem),
  107. },
  108. {
  109. .data_type = QMI_OPT_FLAG,
  110. .elem_len = 1,
  111. .elem_size = sizeof(u8),
  112. .array_type = NO_ARRAY,
  113. .tlv_type = 0x14,
  114. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  115. bdf_support_valid),
  116. },
  117. {
  118. .data_type = QMI_UNSIGNED_1_BYTE,
  119. .elem_len = 1,
  120. .elem_size = sizeof(u8),
  121. .array_type = NO_ARRAY,
  122. .tlv_type = 0x14,
  123. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  124. bdf_support),
  125. },
  126. {
  127. .data_type = QMI_OPT_FLAG,
  128. .elem_len = 1,
  129. .elem_size = sizeof(u8),
  130. .array_type = NO_ARRAY,
  131. .tlv_type = 0x15,
  132. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  133. bdf_cache_support_valid),
  134. },
  135. {
  136. .data_type = QMI_UNSIGNED_1_BYTE,
  137. .elem_len = 1,
  138. .elem_size = sizeof(u8),
  139. .array_type = NO_ARRAY,
  140. .tlv_type = 0x15,
  141. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  142. bdf_cache_support),
  143. },
  144. {
  145. .data_type = QMI_OPT_FLAG,
  146. .elem_len = 1,
  147. .elem_size = sizeof(u8),
  148. .array_type = NO_ARRAY,
  149. .tlv_type = 0x16,
  150. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  151. m3_support_valid),
  152. },
  153. {
  154. .data_type = QMI_UNSIGNED_1_BYTE,
  155. .elem_len = 1,
  156. .elem_size = sizeof(u8),
  157. .array_type = NO_ARRAY,
  158. .tlv_type = 0x16,
  159. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  160. m3_support),
  161. },
  162. {
  163. .data_type = QMI_OPT_FLAG,
  164. .elem_len = 1,
  165. .elem_size = sizeof(u8),
  166. .array_type = NO_ARRAY,
  167. .tlv_type = 0x17,
  168. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  169. m3_cache_support_valid),
  170. },
  171. {
  172. .data_type = QMI_UNSIGNED_1_BYTE,
  173. .elem_len = 1,
  174. .elem_size = sizeof(u8),
  175. .array_type = NO_ARRAY,
  176. .tlv_type = 0x17,
  177. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  178. m3_cache_support),
  179. },
  180. {
  181. .data_type = QMI_OPT_FLAG,
  182. .elem_len = 1,
  183. .elem_size = sizeof(u8),
  184. .array_type = NO_ARRAY,
  185. .tlv_type = 0x18,
  186. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  187. cal_filesys_support_valid),
  188. },
  189. {
  190. .data_type = QMI_UNSIGNED_1_BYTE,
  191. .elem_len = 1,
  192. .elem_size = sizeof(u8),
  193. .array_type = NO_ARRAY,
  194. .tlv_type = 0x18,
  195. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  196. cal_filesys_support),
  197. },
  198. {
  199. .data_type = QMI_OPT_FLAG,
  200. .elem_len = 1,
  201. .elem_size = sizeof(u8),
  202. .array_type = NO_ARRAY,
  203. .tlv_type = 0x19,
  204. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  205. cal_cache_support_valid),
  206. },
  207. {
  208. .data_type = QMI_UNSIGNED_1_BYTE,
  209. .elem_len = 1,
  210. .elem_size = sizeof(u8),
  211. .array_type = NO_ARRAY,
  212. .tlv_type = 0x19,
  213. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  214. cal_cache_support),
  215. },
  216. {
  217. .data_type = QMI_OPT_FLAG,
  218. .elem_len = 1,
  219. .elem_size = sizeof(u8),
  220. .array_type = NO_ARRAY,
  221. .tlv_type = 0x1A,
  222. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  223. cal_done_valid),
  224. },
  225. {
  226. .data_type = QMI_UNSIGNED_1_BYTE,
  227. .elem_len = 1,
  228. .elem_size = sizeof(u8),
  229. .array_type = NO_ARRAY,
  230. .tlv_type = 0x1A,
  231. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  232. cal_done),
  233. },
  234. {
  235. .data_type = QMI_OPT_FLAG,
  236. .elem_len = 1,
  237. .elem_size = sizeof(u8),
  238. .array_type = NO_ARRAY,
  239. .tlv_type = 0x1B,
  240. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  241. mem_bucket_valid),
  242. },
  243. {
  244. .data_type = QMI_UNSIGNED_4_BYTE,
  245. .elem_len = 1,
  246. .elem_size = sizeof(u32),
  247. .array_type = NO_ARRAY,
  248. .tlv_type = 0x1B,
  249. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  250. mem_bucket),
  251. },
  252. {
  253. .data_type = QMI_OPT_FLAG,
  254. .elem_len = 1,
  255. .elem_size = sizeof(u8),
  256. .array_type = NO_ARRAY,
  257. .tlv_type = 0x1C,
  258. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  259. mem_cfg_mode_valid),
  260. },
  261. {
  262. .data_type = QMI_UNSIGNED_1_BYTE,
  263. .elem_len = 1,
  264. .elem_size = sizeof(u8),
  265. .array_type = NO_ARRAY,
  266. .tlv_type = 0x1C,
  267. .offset = offsetof(struct qmi_wlanfw_host_cap_req_msg_v01,
  268. mem_cfg_mode),
  269. },
  270. {
  271. .data_type = QMI_EOTI,
  272. .array_type = NO_ARRAY,
  273. .tlv_type = QMI_COMMON_TLV_TYPE,
  274. },
  275. };
  276. static struct qmi_elem_info qmi_wlanfw_host_cap_resp_msg_v01_ei[] = {
  277. {
  278. .data_type = QMI_STRUCT,
  279. .elem_len = 1,
  280. .elem_size = sizeof(struct qmi_response_type_v01),
  281. .array_type = NO_ARRAY,
  282. .tlv_type = 0x02,
  283. .offset = offsetof(struct qmi_wlanfw_host_cap_resp_msg_v01, resp),
  284. .ei_array = qmi_response_type_v01_ei,
  285. },
  286. {
  287. .data_type = QMI_EOTI,
  288. .array_type = NO_ARRAY,
  289. .tlv_type = QMI_COMMON_TLV_TYPE,
  290. },
  291. };
  292. static struct qmi_elem_info qmi_wlanfw_ind_register_req_msg_v01_ei[] = {
  293. {
  294. .data_type = QMI_OPT_FLAG,
  295. .elem_len = 1,
  296. .elem_size = sizeof(u8),
  297. .array_type = NO_ARRAY,
  298. .tlv_type = 0x10,
  299. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  300. fw_ready_enable_valid),
  301. },
  302. {
  303. .data_type = QMI_UNSIGNED_1_BYTE,
  304. .elem_len = 1,
  305. .elem_size = sizeof(u8),
  306. .array_type = NO_ARRAY,
  307. .tlv_type = 0x10,
  308. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  309. fw_ready_enable),
  310. },
  311. {
  312. .data_type = QMI_OPT_FLAG,
  313. .elem_len = 1,
  314. .elem_size = sizeof(u8),
  315. .array_type = NO_ARRAY,
  316. .tlv_type = 0x11,
  317. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  318. initiate_cal_download_enable_valid),
  319. },
  320. {
  321. .data_type = QMI_UNSIGNED_1_BYTE,
  322. .elem_len = 1,
  323. .elem_size = sizeof(u8),
  324. .array_type = NO_ARRAY,
  325. .tlv_type = 0x11,
  326. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  327. initiate_cal_download_enable),
  328. },
  329. {
  330. .data_type = QMI_OPT_FLAG,
  331. .elem_len = 1,
  332. .elem_size = sizeof(u8),
  333. .array_type = NO_ARRAY,
  334. .tlv_type = 0x12,
  335. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  336. initiate_cal_update_enable_valid),
  337. },
  338. {
  339. .data_type = QMI_UNSIGNED_1_BYTE,
  340. .elem_len = 1,
  341. .elem_size = sizeof(u8),
  342. .array_type = NO_ARRAY,
  343. .tlv_type = 0x12,
  344. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  345. initiate_cal_update_enable),
  346. },
  347. {
  348. .data_type = QMI_OPT_FLAG,
  349. .elem_len = 1,
  350. .elem_size = sizeof(u8),
  351. .array_type = NO_ARRAY,
  352. .tlv_type = 0x13,
  353. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  354. msa_ready_enable_valid),
  355. },
  356. {
  357. .data_type = QMI_UNSIGNED_1_BYTE,
  358. .elem_len = 1,
  359. .elem_size = sizeof(u8),
  360. .array_type = NO_ARRAY,
  361. .tlv_type = 0x13,
  362. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  363. msa_ready_enable),
  364. },
  365. {
  366. .data_type = QMI_OPT_FLAG,
  367. .elem_len = 1,
  368. .elem_size = sizeof(u8),
  369. .array_type = NO_ARRAY,
  370. .tlv_type = 0x14,
  371. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  372. pin_connect_result_enable_valid),
  373. },
  374. {
  375. .data_type = QMI_UNSIGNED_1_BYTE,
  376. .elem_len = 1,
  377. .elem_size = sizeof(u8),
  378. .array_type = NO_ARRAY,
  379. .tlv_type = 0x14,
  380. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  381. pin_connect_result_enable),
  382. },
  383. {
  384. .data_type = QMI_OPT_FLAG,
  385. .elem_len = 1,
  386. .elem_size = sizeof(u8),
  387. .array_type = NO_ARRAY,
  388. .tlv_type = 0x15,
  389. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  390. client_id_valid),
  391. },
  392. {
  393. .data_type = QMI_UNSIGNED_4_BYTE,
  394. .elem_len = 1,
  395. .elem_size = sizeof(u32),
  396. .array_type = NO_ARRAY,
  397. .tlv_type = 0x15,
  398. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  399. client_id),
  400. },
  401. {
  402. .data_type = QMI_OPT_FLAG,
  403. .elem_len = 1,
  404. .elem_size = sizeof(u8),
  405. .array_type = NO_ARRAY,
  406. .tlv_type = 0x16,
  407. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  408. request_mem_enable_valid),
  409. },
  410. {
  411. .data_type = QMI_UNSIGNED_1_BYTE,
  412. .elem_len = 1,
  413. .elem_size = sizeof(u8),
  414. .array_type = NO_ARRAY,
  415. .tlv_type = 0x16,
  416. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  417. request_mem_enable),
  418. },
  419. {
  420. .data_type = QMI_OPT_FLAG,
  421. .elem_len = 1,
  422. .elem_size = sizeof(u8),
  423. .array_type = NO_ARRAY,
  424. .tlv_type = 0x17,
  425. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  426. fw_mem_ready_enable_valid),
  427. },
  428. {
  429. .data_type = QMI_UNSIGNED_1_BYTE,
  430. .elem_len = 1,
  431. .elem_size = sizeof(u8),
  432. .array_type = NO_ARRAY,
  433. .tlv_type = 0x17,
  434. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  435. fw_mem_ready_enable),
  436. },
  437. {
  438. .data_type = QMI_OPT_FLAG,
  439. .elem_len = 1,
  440. .elem_size = sizeof(u8),
  441. .array_type = NO_ARRAY,
  442. .tlv_type = 0x18,
  443. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  444. fw_init_done_enable_valid),
  445. },
  446. {
  447. .data_type = QMI_UNSIGNED_1_BYTE,
  448. .elem_len = 1,
  449. .elem_size = sizeof(u8),
  450. .array_type = NO_ARRAY,
  451. .tlv_type = 0x18,
  452. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  453. fw_init_done_enable),
  454. },
  455. {
  456. .data_type = QMI_OPT_FLAG,
  457. .elem_len = 1,
  458. .elem_size = sizeof(u8),
  459. .array_type = NO_ARRAY,
  460. .tlv_type = 0x19,
  461. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  462. rejuvenate_enable_valid),
  463. },
  464. {
  465. .data_type = QMI_UNSIGNED_1_BYTE,
  466. .elem_len = 1,
  467. .elem_size = sizeof(u8),
  468. .array_type = NO_ARRAY,
  469. .tlv_type = 0x19,
  470. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  471. rejuvenate_enable),
  472. },
  473. {
  474. .data_type = QMI_OPT_FLAG,
  475. .elem_len = 1,
  476. .elem_size = sizeof(u8),
  477. .array_type = NO_ARRAY,
  478. .tlv_type = 0x1A,
  479. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  480. xo_cal_enable_valid),
  481. },
  482. {
  483. .data_type = QMI_UNSIGNED_1_BYTE,
  484. .elem_len = 1,
  485. .elem_size = sizeof(u8),
  486. .array_type = NO_ARRAY,
  487. .tlv_type = 0x1A,
  488. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  489. xo_cal_enable),
  490. },
  491. {
  492. .data_type = QMI_OPT_FLAG,
  493. .elem_len = 1,
  494. .elem_size = sizeof(u8),
  495. .array_type = NO_ARRAY,
  496. .tlv_type = 0x1B,
  497. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  498. cal_done_enable_valid),
  499. },
  500. {
  501. .data_type = QMI_UNSIGNED_1_BYTE,
  502. .elem_len = 1,
  503. .elem_size = sizeof(u8),
  504. .array_type = NO_ARRAY,
  505. .tlv_type = 0x1B,
  506. .offset = offsetof(struct qmi_wlanfw_ind_register_req_msg_v01,
  507. cal_done_enable),
  508. },
  509. {
  510. .data_type = QMI_EOTI,
  511. .array_type = NO_ARRAY,
  512. .tlv_type = QMI_COMMON_TLV_TYPE,
  513. },
  514. };
  515. static struct qmi_elem_info qmi_wlanfw_ind_register_resp_msg_v01_ei[] = {
  516. {
  517. .data_type = QMI_STRUCT,
  518. .elem_len = 1,
  519. .elem_size = sizeof(struct qmi_response_type_v01),
  520. .array_type = NO_ARRAY,
  521. .tlv_type = 0x02,
  522. .offset = offsetof(struct qmi_wlanfw_ind_register_resp_msg_v01,
  523. resp),
  524. .ei_array = qmi_response_type_v01_ei,
  525. },
  526. {
  527. .data_type = QMI_OPT_FLAG,
  528. .elem_len = 1,
  529. .elem_size = sizeof(u8),
  530. .array_type = NO_ARRAY,
  531. .tlv_type = 0x10,
  532. .offset = offsetof(struct qmi_wlanfw_ind_register_resp_msg_v01,
  533. fw_status_valid),
  534. },
  535. {
  536. .data_type = QMI_UNSIGNED_8_BYTE,
  537. .elem_len = 1,
  538. .elem_size = sizeof(u64),
  539. .array_type = NO_ARRAY,
  540. .tlv_type = 0x10,
  541. .offset = offsetof(struct qmi_wlanfw_ind_register_resp_msg_v01,
  542. fw_status),
  543. },
  544. {
  545. .data_type = QMI_EOTI,
  546. .array_type = NO_ARRAY,
  547. .tlv_type = QMI_COMMON_TLV_TYPE,
  548. },
  549. };
  550. static struct qmi_elem_info qmi_wlanfw_mem_cfg_s_v01_ei[] = {
  551. {
  552. .data_type = QMI_UNSIGNED_8_BYTE,
  553. .elem_len = 1,
  554. .elem_size = sizeof(u64),
  555. .array_type = NO_ARRAY,
  556. .tlv_type = 0,
  557. .offset = offsetof(struct qmi_wlanfw_mem_cfg_s_v01, offset),
  558. },
  559. {
  560. .data_type = QMI_UNSIGNED_4_BYTE,
  561. .elem_len = 1,
  562. .elem_size = sizeof(u32),
  563. .array_type = NO_ARRAY,
  564. .tlv_type = 0,
  565. .offset = offsetof(struct qmi_wlanfw_mem_cfg_s_v01, size),
  566. },
  567. {
  568. .data_type = QMI_UNSIGNED_1_BYTE,
  569. .elem_len = 1,
  570. .elem_size = sizeof(u8),
  571. .array_type = NO_ARRAY,
  572. .tlv_type = 0,
  573. .offset = offsetof(struct qmi_wlanfw_mem_cfg_s_v01, secure_flag),
  574. },
  575. {
  576. .data_type = QMI_EOTI,
  577. .array_type = NO_ARRAY,
  578. .tlv_type = QMI_COMMON_TLV_TYPE,
  579. },
  580. };
  581. static struct qmi_elem_info qmi_wlanfw_mem_seg_s_v01_ei[] = {
  582. {
  583. .data_type = QMI_UNSIGNED_4_BYTE,
  584. .elem_len = 1,
  585. .elem_size = sizeof(u32),
  586. .array_type = NO_ARRAY,
  587. .tlv_type = 0,
  588. .offset = offsetof(struct qmi_wlanfw_mem_seg_s_v01,
  589. size),
  590. },
  591. {
  592. .data_type = QMI_SIGNED_4_BYTE_ENUM,
  593. .elem_len = 1,
  594. .elem_size = sizeof(enum qmi_wlanfw_mem_type_enum_v01),
  595. .array_type = NO_ARRAY,
  596. .tlv_type = 0,
  597. .offset = offsetof(struct qmi_wlanfw_mem_seg_s_v01, type),
  598. },
  599. {
  600. .data_type = QMI_DATA_LEN,
  601. .elem_len = 1,
  602. .elem_size = sizeof(u8),
  603. .array_type = NO_ARRAY,
  604. .tlv_type = 0,
  605. .offset = offsetof(struct qmi_wlanfw_mem_seg_s_v01, mem_cfg_len),
  606. },
  607. {
  608. .data_type = QMI_STRUCT,
  609. .elem_len = QMI_WLANFW_MAX_NUM_MEM_CFG_V01,
  610. .elem_size = sizeof(struct qmi_wlanfw_mem_cfg_s_v01),
  611. .array_type = VAR_LEN_ARRAY,
  612. .tlv_type = 0,
  613. .offset = offsetof(struct qmi_wlanfw_mem_seg_s_v01, mem_cfg),
  614. .ei_array = qmi_wlanfw_mem_cfg_s_v01_ei,
  615. },
  616. {
  617. .data_type = QMI_EOTI,
  618. .array_type = NO_ARRAY,
  619. .tlv_type = QMI_COMMON_TLV_TYPE,
  620. },
  621. };
  622. static struct qmi_elem_info qmi_wlanfw_request_mem_ind_msg_v01_ei[] = {
  623. {
  624. .data_type = QMI_DATA_LEN,
  625. .elem_len = 1,
  626. .elem_size = sizeof(u8),
  627. .array_type = NO_ARRAY,
  628. .tlv_type = 0x01,
  629. .offset = offsetof(struct qmi_wlanfw_request_mem_ind_msg_v01,
  630. mem_seg_len),
  631. },
  632. {
  633. .data_type = QMI_STRUCT,
  634. .elem_len = ATH11K_QMI_WLANFW_MAX_NUM_MEM_SEG_V01,
  635. .elem_size = sizeof(struct qmi_wlanfw_mem_seg_s_v01),
  636. .array_type = VAR_LEN_ARRAY,
  637. .tlv_type = 0x01,
  638. .offset = offsetof(struct qmi_wlanfw_request_mem_ind_msg_v01,
  639. mem_seg),
  640. .ei_array = qmi_wlanfw_mem_seg_s_v01_ei,
  641. },
  642. {
  643. .data_type = QMI_EOTI,
  644. .array_type = NO_ARRAY,
  645. .tlv_type = QMI_COMMON_TLV_TYPE,
  646. },
  647. };
  648. static struct qmi_elem_info qmi_wlanfw_mem_seg_resp_s_v01_ei[] = {
  649. {
  650. .data_type = QMI_UNSIGNED_8_BYTE,
  651. .elem_len = 1,
  652. .elem_size = sizeof(u64),
  653. .array_type = NO_ARRAY,
  654. .tlv_type = 0,
  655. .offset = offsetof(struct qmi_wlanfw_mem_seg_resp_s_v01, addr),
  656. },
  657. {
  658. .data_type = QMI_UNSIGNED_4_BYTE,
  659. .elem_len = 1,
  660. .elem_size = sizeof(u32),
  661. .array_type = NO_ARRAY,
  662. .tlv_type = 0,
  663. .offset = offsetof(struct qmi_wlanfw_mem_seg_resp_s_v01, size),
  664. },
  665. {
  666. .data_type = QMI_SIGNED_4_BYTE_ENUM,
  667. .elem_len = 1,
  668. .elem_size = sizeof(enum qmi_wlanfw_mem_type_enum_v01),
  669. .array_type = NO_ARRAY,
  670. .tlv_type = 0,
  671. .offset = offsetof(struct qmi_wlanfw_mem_seg_resp_s_v01, type),
  672. },
  673. {
  674. .data_type = QMI_UNSIGNED_1_BYTE,
  675. .elem_len = 1,
  676. .elem_size = sizeof(u8),
  677. .array_type = NO_ARRAY,
  678. .tlv_type = 0,
  679. .offset = offsetof(struct qmi_wlanfw_mem_seg_resp_s_v01, restore),
  680. },
  681. {
  682. .data_type = QMI_EOTI,
  683. .array_type = NO_ARRAY,
  684. .tlv_type = QMI_COMMON_TLV_TYPE,
  685. },
  686. };
  687. static struct qmi_elem_info qmi_wlanfw_respond_mem_req_msg_v01_ei[] = {
  688. {
  689. .data_type = QMI_DATA_LEN,
  690. .elem_len = 1,
  691. .elem_size = sizeof(u8),
  692. .array_type = NO_ARRAY,
  693. .tlv_type = 0x01,
  694. .offset = offsetof(struct qmi_wlanfw_respond_mem_req_msg_v01,
  695. mem_seg_len),
  696. },
  697. {
  698. .data_type = QMI_STRUCT,
  699. .elem_len = ATH11K_QMI_WLANFW_MAX_NUM_MEM_SEG_V01,
  700. .elem_size = sizeof(struct qmi_wlanfw_mem_seg_resp_s_v01),
  701. .array_type = VAR_LEN_ARRAY,
  702. .tlv_type = 0x01,
  703. .offset = offsetof(struct qmi_wlanfw_respond_mem_req_msg_v01,
  704. mem_seg),
  705. .ei_array = qmi_wlanfw_mem_seg_resp_s_v01_ei,
  706. },
  707. {
  708. .data_type = QMI_EOTI,
  709. .array_type = NO_ARRAY,
  710. .tlv_type = QMI_COMMON_TLV_TYPE,
  711. },
  712. };
  713. static struct qmi_elem_info qmi_wlanfw_respond_mem_resp_msg_v01_ei[] = {
  714. {
  715. .data_type = QMI_STRUCT,
  716. .elem_len = 1,
  717. .elem_size = sizeof(struct qmi_response_type_v01),
  718. .array_type = NO_ARRAY,
  719. .tlv_type = 0x02,
  720. .offset = offsetof(struct qmi_wlanfw_respond_mem_resp_msg_v01,
  721. resp),
  722. .ei_array = qmi_response_type_v01_ei,
  723. },
  724. {
  725. .data_type = QMI_EOTI,
  726. .array_type = NO_ARRAY,
  727. .tlv_type = QMI_COMMON_TLV_TYPE,
  728. },
  729. };
  730. static struct qmi_elem_info qmi_wlanfw_cap_req_msg_v01_ei[] = {
  731. {
  732. .data_type = QMI_EOTI,
  733. .array_type = NO_ARRAY,
  734. .tlv_type = QMI_COMMON_TLV_TYPE,
  735. },
  736. };
  737. static struct qmi_elem_info qmi_wlanfw_device_info_req_msg_v01_ei[] = {
  738. {
  739. .data_type = QMI_EOTI,
  740. .array_type = NO_ARRAY,
  741. .tlv_type = QMI_COMMON_TLV_TYPE,
  742. },
  743. };
  744. static struct qmi_elem_info qmi_wlfw_device_info_resp_msg_v01_ei[] = {
  745. {
  746. .data_type = QMI_STRUCT,
  747. .elem_len = 1,
  748. .elem_size = sizeof(struct qmi_response_type_v01),
  749. .array_type = NO_ARRAY,
  750. .tlv_type = 0x02,
  751. .offset = offsetof(struct qmi_wlanfw_device_info_resp_msg_v01,
  752. resp),
  753. .ei_array = qmi_response_type_v01_ei,
  754. },
  755. {
  756. .data_type = QMI_OPT_FLAG,
  757. .elem_len = 1,
  758. .elem_size = sizeof(u8),
  759. .array_type = NO_ARRAY,
  760. .tlv_type = 0x10,
  761. .offset = offsetof(struct qmi_wlanfw_device_info_resp_msg_v01,
  762. bar_addr_valid),
  763. },
  764. {
  765. .data_type = QMI_UNSIGNED_8_BYTE,
  766. .elem_len = 1,
  767. .elem_size = sizeof(u64),
  768. .array_type = NO_ARRAY,
  769. .tlv_type = 0x10,
  770. .offset = offsetof(struct qmi_wlanfw_device_info_resp_msg_v01,
  771. bar_addr),
  772. },
  773. {
  774. .data_type = QMI_OPT_FLAG,
  775. .elem_len = 1,
  776. .elem_size = sizeof(u8),
  777. .array_type = NO_ARRAY,
  778. .tlv_type = 0x11,
  779. .offset = offsetof(struct qmi_wlanfw_device_info_resp_msg_v01,
  780. bar_size_valid),
  781. },
  782. {
  783. .data_type = QMI_UNSIGNED_4_BYTE,
  784. .elem_len = 1,
  785. .elem_size = sizeof(u32),
  786. .array_type = NO_ARRAY,
  787. .tlv_type = 0x11,
  788. .offset = offsetof(struct qmi_wlanfw_device_info_resp_msg_v01,
  789. bar_size),
  790. },
  791. {
  792. .data_type = QMI_EOTI,
  793. .array_type = NO_ARRAY,
  794. .tlv_type = QMI_COMMON_TLV_TYPE,
  795. },
  796. };
  797. static struct qmi_elem_info qmi_wlanfw_rf_chip_info_s_v01_ei[] = {
  798. {
  799. .data_type = QMI_UNSIGNED_4_BYTE,
  800. .elem_len = 1,
  801. .elem_size = sizeof(u32),
  802. .array_type = NO_ARRAY,
  803. .tlv_type = 0,
  804. .offset = offsetof(struct qmi_wlanfw_rf_chip_info_s_v01,
  805. chip_id),
  806. },
  807. {
  808. .data_type = QMI_UNSIGNED_4_BYTE,
  809. .elem_len = 1,
  810. .elem_size = sizeof(u32),
  811. .array_type = NO_ARRAY,
  812. .tlv_type = 0,
  813. .offset = offsetof(struct qmi_wlanfw_rf_chip_info_s_v01,
  814. chip_family),
  815. },
  816. {
  817. .data_type = QMI_EOTI,
  818. .array_type = NO_ARRAY,
  819. .tlv_type = QMI_COMMON_TLV_TYPE,
  820. },
  821. };
  822. static struct qmi_elem_info qmi_wlanfw_rf_board_info_s_v01_ei[] = {
  823. {
  824. .data_type = QMI_UNSIGNED_4_BYTE,
  825. .elem_len = 1,
  826. .elem_size = sizeof(u32),
  827. .array_type = NO_ARRAY,
  828. .tlv_type = 0,
  829. .offset = offsetof(struct qmi_wlanfw_rf_board_info_s_v01,
  830. board_id),
  831. },
  832. {
  833. .data_type = QMI_EOTI,
  834. .array_type = NO_ARRAY,
  835. .tlv_type = QMI_COMMON_TLV_TYPE,
  836. },
  837. };
  838. static struct qmi_elem_info qmi_wlanfw_soc_info_s_v01_ei[] = {
  839. {
  840. .data_type = QMI_UNSIGNED_4_BYTE,
  841. .elem_len = 1,
  842. .elem_size = sizeof(u32),
  843. .array_type = NO_ARRAY,
  844. .tlv_type = 0,
  845. .offset = offsetof(struct qmi_wlanfw_soc_info_s_v01, soc_id),
  846. },
  847. {
  848. .data_type = QMI_EOTI,
  849. .array_type = NO_ARRAY,
  850. .tlv_type = QMI_COMMON_TLV_TYPE,
  851. },
  852. };
  853. static struct qmi_elem_info qmi_wlanfw_fw_version_info_s_v01_ei[] = {
  854. {
  855. .data_type = QMI_UNSIGNED_4_BYTE,
  856. .elem_len = 1,
  857. .elem_size = sizeof(u32),
  858. .array_type = NO_ARRAY,
  859. .tlv_type = 0,
  860. .offset = offsetof(struct qmi_wlanfw_fw_version_info_s_v01,
  861. fw_version),
  862. },
  863. {
  864. .data_type = QMI_STRING,
  865. .elem_len = ATH11K_QMI_WLANFW_MAX_TIMESTAMP_LEN_V01 + 1,
  866. .elem_size = sizeof(char),
  867. .array_type = NO_ARRAY,
  868. .tlv_type = 0,
  869. .offset = offsetof(struct qmi_wlanfw_fw_version_info_s_v01,
  870. fw_build_timestamp),
  871. },
  872. {
  873. .data_type = QMI_EOTI,
  874. .array_type = NO_ARRAY,
  875. .tlv_type = QMI_COMMON_TLV_TYPE,
  876. },
  877. };
  878. static struct qmi_elem_info qmi_wlanfw_cap_resp_msg_v01_ei[] = {
  879. {
  880. .data_type = QMI_STRUCT,
  881. .elem_len = 1,
  882. .elem_size = sizeof(struct qmi_response_type_v01),
  883. .array_type = NO_ARRAY,
  884. .tlv_type = 0x02,
  885. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01, resp),
  886. .ei_array = qmi_response_type_v01_ei,
  887. },
  888. {
  889. .data_type = QMI_OPT_FLAG,
  890. .elem_len = 1,
  891. .elem_size = sizeof(u8),
  892. .array_type = NO_ARRAY,
  893. .tlv_type = 0x10,
  894. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  895. chip_info_valid),
  896. },
  897. {
  898. .data_type = QMI_STRUCT,
  899. .elem_len = 1,
  900. .elem_size = sizeof(struct qmi_wlanfw_rf_chip_info_s_v01),
  901. .array_type = NO_ARRAY,
  902. .tlv_type = 0x10,
  903. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  904. chip_info),
  905. .ei_array = qmi_wlanfw_rf_chip_info_s_v01_ei,
  906. },
  907. {
  908. .data_type = QMI_OPT_FLAG,
  909. .elem_len = 1,
  910. .elem_size = sizeof(u8),
  911. .array_type = NO_ARRAY,
  912. .tlv_type = 0x11,
  913. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  914. board_info_valid),
  915. },
  916. {
  917. .data_type = QMI_STRUCT,
  918. .elem_len = 1,
  919. .elem_size = sizeof(struct qmi_wlanfw_rf_board_info_s_v01),
  920. .array_type = NO_ARRAY,
  921. .tlv_type = 0x11,
  922. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  923. board_info),
  924. .ei_array = qmi_wlanfw_rf_board_info_s_v01_ei,
  925. },
  926. {
  927. .data_type = QMI_OPT_FLAG,
  928. .elem_len = 1,
  929. .elem_size = sizeof(u8),
  930. .array_type = NO_ARRAY,
  931. .tlv_type = 0x12,
  932. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  933. soc_info_valid),
  934. },
  935. {
  936. .data_type = QMI_STRUCT,
  937. .elem_len = 1,
  938. .elem_size = sizeof(struct qmi_wlanfw_soc_info_s_v01),
  939. .array_type = NO_ARRAY,
  940. .tlv_type = 0x12,
  941. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  942. soc_info),
  943. .ei_array = qmi_wlanfw_soc_info_s_v01_ei,
  944. },
  945. {
  946. .data_type = QMI_OPT_FLAG,
  947. .elem_len = 1,
  948. .elem_size = sizeof(u8),
  949. .array_type = NO_ARRAY,
  950. .tlv_type = 0x13,
  951. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  952. fw_version_info_valid),
  953. },
  954. {
  955. .data_type = QMI_STRUCT,
  956. .elem_len = 1,
  957. .elem_size = sizeof(struct qmi_wlanfw_fw_version_info_s_v01),
  958. .array_type = NO_ARRAY,
  959. .tlv_type = 0x13,
  960. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  961. fw_version_info),
  962. .ei_array = qmi_wlanfw_fw_version_info_s_v01_ei,
  963. },
  964. {
  965. .data_type = QMI_OPT_FLAG,
  966. .elem_len = 1,
  967. .elem_size = sizeof(u8),
  968. .array_type = NO_ARRAY,
  969. .tlv_type = 0x14,
  970. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  971. fw_build_id_valid),
  972. },
  973. {
  974. .data_type = QMI_STRING,
  975. .elem_len = ATH11K_QMI_WLANFW_MAX_BUILD_ID_LEN_V01 + 1,
  976. .elem_size = sizeof(char),
  977. .array_type = NO_ARRAY,
  978. .tlv_type = 0x14,
  979. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  980. fw_build_id),
  981. },
  982. {
  983. .data_type = QMI_OPT_FLAG,
  984. .elem_len = 1,
  985. .elem_size = sizeof(u8),
  986. .array_type = NO_ARRAY,
  987. .tlv_type = 0x15,
  988. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  989. num_macs_valid),
  990. },
  991. {
  992. .data_type = QMI_UNSIGNED_1_BYTE,
  993. .elem_len = 1,
  994. .elem_size = sizeof(u8),
  995. .array_type = NO_ARRAY,
  996. .tlv_type = 0x15,
  997. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  998. num_macs),
  999. },
  1000. {
  1001. .data_type = QMI_OPT_FLAG,
  1002. .elem_len = 1,
  1003. .elem_size = sizeof(u8),
  1004. .array_type = NO_ARRAY,
  1005. .tlv_type = 0x16,
  1006. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  1007. voltage_mv_valid),
  1008. },
  1009. {
  1010. .data_type = QMI_UNSIGNED_4_BYTE,
  1011. .elem_len = 1,
  1012. .elem_size = sizeof(u32),
  1013. .array_type = NO_ARRAY,
  1014. .tlv_type = 0x16,
  1015. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  1016. voltage_mv),
  1017. },
  1018. {
  1019. .data_type = QMI_OPT_FLAG,
  1020. .elem_len = 1,
  1021. .elem_size = sizeof(u8),
  1022. .array_type = NO_ARRAY,
  1023. .tlv_type = 0x17,
  1024. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  1025. time_freq_hz_valid),
  1026. },
  1027. {
  1028. .data_type = QMI_UNSIGNED_4_BYTE,
  1029. .elem_len = 1,
  1030. .elem_size = sizeof(u32),
  1031. .array_type = NO_ARRAY,
  1032. .tlv_type = 0x17,
  1033. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  1034. time_freq_hz),
  1035. },
  1036. {
  1037. .data_type = QMI_OPT_FLAG,
  1038. .elem_len = 1,
  1039. .elem_size = sizeof(u8),
  1040. .array_type = NO_ARRAY,
  1041. .tlv_type = 0x18,
  1042. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  1043. otp_version_valid),
  1044. },
  1045. {
  1046. .data_type = QMI_UNSIGNED_4_BYTE,
  1047. .elem_len = 1,
  1048. .elem_size = sizeof(u32),
  1049. .array_type = NO_ARRAY,
  1050. .tlv_type = 0x18,
  1051. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  1052. otp_version),
  1053. },
  1054. {
  1055. .data_type = QMI_OPT_FLAG,
  1056. .elem_len = 1,
  1057. .elem_size = sizeof(u8),
  1058. .array_type = NO_ARRAY,
  1059. .tlv_type = 0x19,
  1060. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  1061. eeprom_read_timeout_valid),
  1062. },
  1063. {
  1064. .data_type = QMI_UNSIGNED_4_BYTE,
  1065. .elem_len = 1,
  1066. .elem_size = sizeof(u32),
  1067. .array_type = NO_ARRAY,
  1068. .tlv_type = 0x19,
  1069. .offset = offsetof(struct qmi_wlanfw_cap_resp_msg_v01,
  1070. eeprom_read_timeout),
  1071. },
  1072. {
  1073. .data_type = QMI_EOTI,
  1074. .array_type = NO_ARRAY,
  1075. .tlv_type = QMI_COMMON_TLV_TYPE,
  1076. },
  1077. };
  1078. static struct qmi_elem_info qmi_wlanfw_bdf_download_req_msg_v01_ei[] = {
  1079. {
  1080. .data_type = QMI_UNSIGNED_1_BYTE,
  1081. .elem_len = 1,
  1082. .elem_size = sizeof(u8),
  1083. .array_type = NO_ARRAY,
  1084. .tlv_type = 0x01,
  1085. .offset = offsetof(struct qmi_wlanfw_bdf_download_req_msg_v01,
  1086. valid),
  1087. },
  1088. {
  1089. .data_type = QMI_OPT_FLAG,
  1090. .elem_len = 1,
  1091. .elem_size = sizeof(u8),
  1092. .array_type = NO_ARRAY,
  1093. .tlv_type = 0x10,
  1094. .offset = offsetof(struct qmi_wlanfw_bdf_download_req_msg_v01,
  1095. file_id_valid),
  1096. },
  1097. {
  1098. .data_type = QMI_SIGNED_4_BYTE_ENUM,
  1099. .elem_len = 1,
  1100. .elem_size = sizeof(enum qmi_wlanfw_cal_temp_id_enum_v01),
  1101. .array_type = NO_ARRAY,
  1102. .tlv_type = 0x10,
  1103. .offset = offsetof(struct qmi_wlanfw_bdf_download_req_msg_v01,
  1104. file_id),
  1105. },
  1106. {
  1107. .data_type = QMI_OPT_FLAG,
  1108. .elem_len = 1,
  1109. .elem_size = sizeof(u8),
  1110. .array_type = NO_ARRAY,
  1111. .tlv_type = 0x11,
  1112. .offset = offsetof(struct qmi_wlanfw_bdf_download_req_msg_v01,
  1113. total_size_valid),
  1114. },
  1115. {
  1116. .data_type = QMI_UNSIGNED_4_BYTE,
  1117. .elem_len = 1,
  1118. .elem_size = sizeof(u32),
  1119. .array_type = NO_ARRAY,
  1120. .tlv_type = 0x11,
  1121. .offset = offsetof(struct qmi_wlanfw_bdf_download_req_msg_v01,
  1122. total_size),
  1123. },
  1124. {
  1125. .data_type = QMI_OPT_FLAG,
  1126. .elem_len = 1,
  1127. .elem_size = sizeof(u8),
  1128. .array_type = NO_ARRAY,
  1129. .tlv_type = 0x12,
  1130. .offset = offsetof(struct qmi_wlanfw_bdf_download_req_msg_v01,
  1131. seg_id_valid),
  1132. },
  1133. {
  1134. .data_type = QMI_UNSIGNED_4_BYTE,
  1135. .elem_len = 1,
  1136. .elem_size = sizeof(u32),
  1137. .array_type = NO_ARRAY,
  1138. .tlv_type = 0x12,
  1139. .offset = offsetof(struct qmi_wlanfw_bdf_download_req_msg_v01,
  1140. seg_id),
  1141. },
  1142. {
  1143. .data_type = QMI_OPT_FLAG,
  1144. .elem_len = 1,
  1145. .elem_size = sizeof(u8),
  1146. .array_type = NO_ARRAY,
  1147. .tlv_type = 0x13,
  1148. .offset = offsetof(struct qmi_wlanfw_bdf_download_req_msg_v01,
  1149. data_valid),
  1150. },
  1151. {
  1152. .data_type = QMI_DATA_LEN,
  1153. .elem_len = 1,
  1154. .elem_size = sizeof(u16),
  1155. .array_type = NO_ARRAY,
  1156. .tlv_type = 0x13,
  1157. .offset = offsetof(struct qmi_wlanfw_bdf_download_req_msg_v01,
  1158. data_len),
  1159. },
  1160. {
  1161. .data_type = QMI_UNSIGNED_1_BYTE,
  1162. .elem_len = QMI_WLANFW_MAX_DATA_SIZE_V01,
  1163. .elem_size = sizeof(u8),
  1164. .array_type = VAR_LEN_ARRAY,
  1165. .tlv_type = 0x13,
  1166. .offset = offsetof(struct qmi_wlanfw_bdf_download_req_msg_v01,
  1167. data),
  1168. },
  1169. {
  1170. .data_type = QMI_OPT_FLAG,
  1171. .elem_len = 1,
  1172. .elem_size = sizeof(u8),
  1173. .array_type = NO_ARRAY,
  1174. .tlv_type = 0x14,
  1175. .offset = offsetof(struct qmi_wlanfw_bdf_download_req_msg_v01,
  1176. end_valid),
  1177. },
  1178. {
  1179. .data_type = QMI_UNSIGNED_1_BYTE,
  1180. .elem_len = 1,
  1181. .elem_size = sizeof(u8),
  1182. .array_type = NO_ARRAY,
  1183. .tlv_type = 0x14,
  1184. .offset = offsetof(struct qmi_wlanfw_bdf_download_req_msg_v01,
  1185. end),
  1186. },
  1187. {
  1188. .data_type = QMI_OPT_FLAG,
  1189. .elem_len = 1,
  1190. .elem_size = sizeof(u8),
  1191. .array_type = NO_ARRAY,
  1192. .tlv_type = 0x15,
  1193. .offset = offsetof(struct qmi_wlanfw_bdf_download_req_msg_v01,
  1194. bdf_type_valid),
  1195. },
  1196. {
  1197. .data_type = QMI_UNSIGNED_1_BYTE,
  1198. .elem_len = 1,
  1199. .elem_size = sizeof(u8),
  1200. .array_type = NO_ARRAY,
  1201. .tlv_type = 0x15,
  1202. .offset = offsetof(struct qmi_wlanfw_bdf_download_req_msg_v01,
  1203. bdf_type),
  1204. },
  1205. {
  1206. .data_type = QMI_EOTI,
  1207. .array_type = NO_ARRAY,
  1208. .tlv_type = QMI_COMMON_TLV_TYPE,
  1209. },
  1210. };
  1211. static struct qmi_elem_info qmi_wlanfw_bdf_download_resp_msg_v01_ei[] = {
  1212. {
  1213. .data_type = QMI_STRUCT,
  1214. .elem_len = 1,
  1215. .elem_size = sizeof(struct qmi_response_type_v01),
  1216. .array_type = NO_ARRAY,
  1217. .tlv_type = 0x02,
  1218. .offset = offsetof(struct qmi_wlanfw_bdf_download_resp_msg_v01,
  1219. resp),
  1220. .ei_array = qmi_response_type_v01_ei,
  1221. },
  1222. {
  1223. .data_type = QMI_EOTI,
  1224. .array_type = NO_ARRAY,
  1225. .tlv_type = QMI_COMMON_TLV_TYPE,
  1226. },
  1227. };
  1228. static struct qmi_elem_info qmi_wlanfw_m3_info_req_msg_v01_ei[] = {
  1229. {
  1230. .data_type = QMI_UNSIGNED_8_BYTE,
  1231. .elem_len = 1,
  1232. .elem_size = sizeof(u64),
  1233. .array_type = NO_ARRAY,
  1234. .tlv_type = 0x01,
  1235. .offset = offsetof(struct qmi_wlanfw_m3_info_req_msg_v01, addr),
  1236. },
  1237. {
  1238. .data_type = QMI_UNSIGNED_4_BYTE,
  1239. .elem_len = 1,
  1240. .elem_size = sizeof(u32),
  1241. .array_type = NO_ARRAY,
  1242. .tlv_type = 0x02,
  1243. .offset = offsetof(struct qmi_wlanfw_m3_info_req_msg_v01, size),
  1244. },
  1245. {
  1246. .data_type = QMI_EOTI,
  1247. .array_type = NO_ARRAY,
  1248. .tlv_type = QMI_COMMON_TLV_TYPE,
  1249. },
  1250. };
  1251. static struct qmi_elem_info qmi_wlanfw_m3_info_resp_msg_v01_ei[] = {
  1252. {
  1253. .data_type = QMI_STRUCT,
  1254. .elem_len = 1,
  1255. .elem_size = sizeof(struct qmi_response_type_v01),
  1256. .array_type = NO_ARRAY,
  1257. .tlv_type = 0x02,
  1258. .offset = offsetof(struct qmi_wlanfw_m3_info_resp_msg_v01, resp),
  1259. .ei_array = qmi_response_type_v01_ei,
  1260. },
  1261. {
  1262. .data_type = QMI_EOTI,
  1263. .array_type = NO_ARRAY,
  1264. .tlv_type = QMI_COMMON_TLV_TYPE,
  1265. },
  1266. };
  1267. static struct qmi_elem_info qmi_wlanfw_ce_tgt_pipe_cfg_s_v01_ei[] = {
  1268. {
  1269. .data_type = QMI_UNSIGNED_4_BYTE,
  1270. .elem_len = 1,
  1271. .elem_size = sizeof(u32),
  1272. .array_type = NO_ARRAY,
  1273. .tlv_type = 0,
  1274. .offset = offsetof(struct qmi_wlanfw_ce_tgt_pipe_cfg_s_v01,
  1275. pipe_num),
  1276. },
  1277. {
  1278. .data_type = QMI_SIGNED_4_BYTE_ENUM,
  1279. .elem_len = 1,
  1280. .elem_size = sizeof(enum qmi_wlanfw_pipedir_enum_v01),
  1281. .array_type = NO_ARRAY,
  1282. .tlv_type = 0,
  1283. .offset = offsetof(struct qmi_wlanfw_ce_tgt_pipe_cfg_s_v01,
  1284. pipe_dir),
  1285. },
  1286. {
  1287. .data_type = QMI_UNSIGNED_4_BYTE,
  1288. .elem_len = 1,
  1289. .elem_size = sizeof(u32),
  1290. .array_type = NO_ARRAY,
  1291. .tlv_type = 0,
  1292. .offset = offsetof(struct qmi_wlanfw_ce_tgt_pipe_cfg_s_v01,
  1293. nentries),
  1294. },
  1295. {
  1296. .data_type = QMI_UNSIGNED_4_BYTE,
  1297. .elem_len = 1,
  1298. .elem_size = sizeof(u32),
  1299. .array_type = NO_ARRAY,
  1300. .tlv_type = 0,
  1301. .offset = offsetof(struct qmi_wlanfw_ce_tgt_pipe_cfg_s_v01,
  1302. nbytes_max),
  1303. },
  1304. {
  1305. .data_type = QMI_UNSIGNED_4_BYTE,
  1306. .elem_len = 1,
  1307. .elem_size = sizeof(u32),
  1308. .array_type = NO_ARRAY,
  1309. .tlv_type = 0,
  1310. .offset = offsetof(struct qmi_wlanfw_ce_tgt_pipe_cfg_s_v01,
  1311. flags),
  1312. },
  1313. {
  1314. .data_type = QMI_EOTI,
  1315. .array_type = NO_ARRAY,
  1316. .tlv_type = QMI_COMMON_TLV_TYPE,
  1317. },
  1318. };
  1319. static struct qmi_elem_info qmi_wlanfw_ce_svc_pipe_cfg_s_v01_ei[] = {
  1320. {
  1321. .data_type = QMI_UNSIGNED_4_BYTE,
  1322. .elem_len = 1,
  1323. .elem_size = sizeof(u32),
  1324. .array_type = NO_ARRAY,
  1325. .tlv_type = 0,
  1326. .offset = offsetof(struct qmi_wlanfw_ce_svc_pipe_cfg_s_v01,
  1327. service_id),
  1328. },
  1329. {
  1330. .data_type = QMI_SIGNED_4_BYTE_ENUM,
  1331. .elem_len = 1,
  1332. .elem_size = sizeof(enum qmi_wlanfw_pipedir_enum_v01),
  1333. .array_type = NO_ARRAY,
  1334. .tlv_type = 0,
  1335. .offset = offsetof(struct qmi_wlanfw_ce_svc_pipe_cfg_s_v01,
  1336. pipe_dir),
  1337. },
  1338. {
  1339. .data_type = QMI_UNSIGNED_4_BYTE,
  1340. .elem_len = 1,
  1341. .elem_size = sizeof(u32),
  1342. .array_type = NO_ARRAY,
  1343. .tlv_type = 0,
  1344. .offset = offsetof(struct qmi_wlanfw_ce_svc_pipe_cfg_s_v01,
  1345. pipe_num),
  1346. },
  1347. {
  1348. .data_type = QMI_EOTI,
  1349. .array_type = NO_ARRAY,
  1350. .tlv_type = QMI_COMMON_TLV_TYPE,
  1351. },
  1352. };
  1353. static struct qmi_elem_info qmi_wlanfw_shadow_reg_cfg_s_v01_ei[] = {
  1354. {
  1355. .data_type = QMI_UNSIGNED_2_BYTE,
  1356. .elem_len = 1,
  1357. .elem_size = sizeof(u16),
  1358. .array_type = NO_ARRAY,
  1359. .tlv_type = 0,
  1360. .offset = offsetof(struct qmi_wlanfw_shadow_reg_cfg_s_v01, id),
  1361. },
  1362. {
  1363. .data_type = QMI_UNSIGNED_2_BYTE,
  1364. .elem_len = 1,
  1365. .elem_size = sizeof(u16),
  1366. .array_type = NO_ARRAY,
  1367. .tlv_type = 0,
  1368. .offset = offsetof(struct qmi_wlanfw_shadow_reg_cfg_s_v01,
  1369. offset),
  1370. },
  1371. {
  1372. .data_type = QMI_EOTI,
  1373. .array_type = QMI_COMMON_TLV_TYPE,
  1374. },
  1375. };
  1376. static struct qmi_elem_info qmi_wlanfw_shadow_reg_v2_cfg_s_v01_ei[] = {
  1377. {
  1378. .data_type = QMI_UNSIGNED_4_BYTE,
  1379. .elem_len = 1,
  1380. .elem_size = sizeof(u32),
  1381. .array_type = NO_ARRAY,
  1382. .tlv_type = 0,
  1383. .offset = offsetof(struct qmi_wlanfw_shadow_reg_v2_cfg_s_v01,
  1384. addr),
  1385. },
  1386. {
  1387. .data_type = QMI_EOTI,
  1388. .array_type = NO_ARRAY,
  1389. .tlv_type = QMI_COMMON_TLV_TYPE,
  1390. },
  1391. };
  1392. static struct qmi_elem_info qmi_wlanfw_wlan_mode_req_msg_v01_ei[] = {
  1393. {
  1394. .data_type = QMI_UNSIGNED_4_BYTE,
  1395. .elem_len = 1,
  1396. .elem_size = sizeof(u32),
  1397. .array_type = NO_ARRAY,
  1398. .tlv_type = 0x01,
  1399. .offset = offsetof(struct qmi_wlanfw_wlan_mode_req_msg_v01,
  1400. mode),
  1401. },
  1402. {
  1403. .data_type = QMI_OPT_FLAG,
  1404. .elem_len = 1,
  1405. .elem_size = sizeof(u8),
  1406. .array_type = NO_ARRAY,
  1407. .tlv_type = 0x10,
  1408. .offset = offsetof(struct qmi_wlanfw_wlan_mode_req_msg_v01,
  1409. hw_debug_valid),
  1410. },
  1411. {
  1412. .data_type = QMI_UNSIGNED_1_BYTE,
  1413. .elem_len = 1,
  1414. .elem_size = sizeof(u8),
  1415. .array_type = NO_ARRAY,
  1416. .tlv_type = 0x10,
  1417. .offset = offsetof(struct qmi_wlanfw_wlan_mode_req_msg_v01,
  1418. hw_debug),
  1419. },
  1420. {
  1421. .data_type = QMI_EOTI,
  1422. .array_type = NO_ARRAY,
  1423. .tlv_type = QMI_COMMON_TLV_TYPE,
  1424. },
  1425. };
  1426. static struct qmi_elem_info qmi_wlanfw_wlan_mode_resp_msg_v01_ei[] = {
  1427. {
  1428. .data_type = QMI_STRUCT,
  1429. .elem_len = 1,
  1430. .elem_size = sizeof(struct qmi_response_type_v01),
  1431. .array_type = NO_ARRAY,
  1432. .tlv_type = 0x02,
  1433. .offset = offsetof(struct qmi_wlanfw_wlan_mode_resp_msg_v01,
  1434. resp),
  1435. .ei_array = qmi_response_type_v01_ei,
  1436. },
  1437. {
  1438. .data_type = QMI_EOTI,
  1439. .array_type = NO_ARRAY,
  1440. .tlv_type = QMI_COMMON_TLV_TYPE,
  1441. },
  1442. };
  1443. static struct qmi_elem_info qmi_wlanfw_wlan_cfg_req_msg_v01_ei[] = {
  1444. {
  1445. .data_type = QMI_OPT_FLAG,
  1446. .elem_len = 1,
  1447. .elem_size = sizeof(u8),
  1448. .array_type = NO_ARRAY,
  1449. .tlv_type = 0x10,
  1450. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_req_msg_v01,
  1451. host_version_valid),
  1452. },
  1453. {
  1454. .data_type = QMI_STRING,
  1455. .elem_len = QMI_WLANFW_MAX_STR_LEN_V01 + 1,
  1456. .elem_size = sizeof(char),
  1457. .array_type = NO_ARRAY,
  1458. .tlv_type = 0x10,
  1459. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_req_msg_v01,
  1460. host_version),
  1461. },
  1462. {
  1463. .data_type = QMI_OPT_FLAG,
  1464. .elem_len = 1,
  1465. .elem_size = sizeof(u8),
  1466. .array_type = NO_ARRAY,
  1467. .tlv_type = 0x11,
  1468. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_req_msg_v01,
  1469. tgt_cfg_valid),
  1470. },
  1471. {
  1472. .data_type = QMI_DATA_LEN,
  1473. .elem_len = 1,
  1474. .elem_size = sizeof(u8),
  1475. .array_type = NO_ARRAY,
  1476. .tlv_type = 0x11,
  1477. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_req_msg_v01,
  1478. tgt_cfg_len),
  1479. },
  1480. {
  1481. .data_type = QMI_STRUCT,
  1482. .elem_len = QMI_WLANFW_MAX_NUM_CE_V01,
  1483. .elem_size = sizeof(
  1484. struct qmi_wlanfw_ce_tgt_pipe_cfg_s_v01),
  1485. .array_type = VAR_LEN_ARRAY,
  1486. .tlv_type = 0x11,
  1487. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_req_msg_v01,
  1488. tgt_cfg),
  1489. .ei_array = qmi_wlanfw_ce_tgt_pipe_cfg_s_v01_ei,
  1490. },
  1491. {
  1492. .data_type = QMI_OPT_FLAG,
  1493. .elem_len = 1,
  1494. .elem_size = sizeof(u8),
  1495. .array_type = NO_ARRAY,
  1496. .tlv_type = 0x12,
  1497. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_req_msg_v01,
  1498. svc_cfg_valid),
  1499. },
  1500. {
  1501. .data_type = QMI_DATA_LEN,
  1502. .elem_len = 1,
  1503. .elem_size = sizeof(u8),
  1504. .array_type = NO_ARRAY,
  1505. .tlv_type = 0x12,
  1506. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_req_msg_v01,
  1507. svc_cfg_len),
  1508. },
  1509. {
  1510. .data_type = QMI_STRUCT,
  1511. .elem_len = QMI_WLANFW_MAX_NUM_SVC_V01,
  1512. .elem_size = sizeof(struct qmi_wlanfw_ce_svc_pipe_cfg_s_v01),
  1513. .array_type = VAR_LEN_ARRAY,
  1514. .tlv_type = 0x12,
  1515. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_req_msg_v01,
  1516. svc_cfg),
  1517. .ei_array = qmi_wlanfw_ce_svc_pipe_cfg_s_v01_ei,
  1518. },
  1519. {
  1520. .data_type = QMI_OPT_FLAG,
  1521. .elem_len = 1,
  1522. .elem_size = sizeof(u8),
  1523. .array_type = NO_ARRAY,
  1524. .tlv_type = 0x13,
  1525. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_req_msg_v01,
  1526. shadow_reg_valid),
  1527. },
  1528. {
  1529. .data_type = QMI_DATA_LEN,
  1530. .elem_len = 1,
  1531. .elem_size = sizeof(u8),
  1532. .array_type = NO_ARRAY,
  1533. .tlv_type = 0x13,
  1534. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_req_msg_v01,
  1535. shadow_reg_len),
  1536. },
  1537. {
  1538. .data_type = QMI_STRUCT,
  1539. .elem_len = QMI_WLANFW_MAX_NUM_SHADOW_REG_V01,
  1540. .elem_size = sizeof(struct qmi_wlanfw_shadow_reg_cfg_s_v01),
  1541. .array_type = VAR_LEN_ARRAY,
  1542. .tlv_type = 0x13,
  1543. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_req_msg_v01,
  1544. shadow_reg),
  1545. .ei_array = qmi_wlanfw_shadow_reg_cfg_s_v01_ei,
  1546. },
  1547. {
  1548. .data_type = QMI_OPT_FLAG,
  1549. .elem_len = 1,
  1550. .elem_size = sizeof(u8),
  1551. .array_type = NO_ARRAY,
  1552. .tlv_type = 0x14,
  1553. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_req_msg_v01,
  1554. shadow_reg_v2_valid),
  1555. },
  1556. {
  1557. .data_type = QMI_DATA_LEN,
  1558. .elem_len = 1,
  1559. .elem_size = sizeof(u8),
  1560. .array_type = NO_ARRAY,
  1561. .tlv_type = 0x14,
  1562. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_req_msg_v01,
  1563. shadow_reg_v2_len),
  1564. },
  1565. {
  1566. .data_type = QMI_STRUCT,
  1567. .elem_len = QMI_WLANFW_MAX_NUM_SHADOW_REG_V2_V01,
  1568. .elem_size = sizeof(struct qmi_wlanfw_shadow_reg_v2_cfg_s_v01),
  1569. .array_type = VAR_LEN_ARRAY,
  1570. .tlv_type = 0x14,
  1571. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_req_msg_v01,
  1572. shadow_reg_v2),
  1573. .ei_array = qmi_wlanfw_shadow_reg_v2_cfg_s_v01_ei,
  1574. },
  1575. {
  1576. .data_type = QMI_EOTI,
  1577. .array_type = NO_ARRAY,
  1578. .tlv_type = QMI_COMMON_TLV_TYPE,
  1579. },
  1580. };
  1581. static struct qmi_elem_info qmi_wlanfw_wlan_cfg_resp_msg_v01_ei[] = {
  1582. {
  1583. .data_type = QMI_STRUCT,
  1584. .elem_len = 1,
  1585. .elem_size = sizeof(struct qmi_response_type_v01),
  1586. .array_type = NO_ARRAY,
  1587. .tlv_type = 0x02,
  1588. .offset = offsetof(struct qmi_wlanfw_wlan_cfg_resp_msg_v01, resp),
  1589. .ei_array = qmi_response_type_v01_ei,
  1590. },
  1591. {
  1592. .data_type = QMI_EOTI,
  1593. .array_type = NO_ARRAY,
  1594. .tlv_type = QMI_COMMON_TLV_TYPE,
  1595. },
  1596. };
  1597. static struct qmi_elem_info qmi_wlanfw_mem_ready_ind_msg_v01_ei[] = {
  1598. {
  1599. .data_type = QMI_EOTI,
  1600. .array_type = NO_ARRAY,
  1601. },
  1602. };
  1603. static struct qmi_elem_info qmi_wlanfw_fw_ready_ind_msg_v01_ei[] = {
  1604. {
  1605. .data_type = QMI_EOTI,
  1606. .array_type = NO_ARRAY,
  1607. },
  1608. };
  1609. static struct qmi_elem_info qmi_wlanfw_cold_boot_cal_done_ind_msg_v01_ei[] = {
  1610. {
  1611. .data_type = QMI_EOTI,
  1612. .array_type = NO_ARRAY,
  1613. },
  1614. };
  1615. static struct qmi_elem_info qmi_wlanfw_wlan_ini_req_msg_v01_ei[] = {
  1616. {
  1617. .data_type = QMI_OPT_FLAG,
  1618. .elem_len = 1,
  1619. .elem_size = sizeof(u8),
  1620. .array_type = NO_ARRAY,
  1621. .tlv_type = 0x10,
  1622. .offset = offsetof(struct qmi_wlanfw_wlan_ini_req_msg_v01,
  1623. enablefwlog_valid),
  1624. },
  1625. {
  1626. .data_type = QMI_UNSIGNED_1_BYTE,
  1627. .elem_len = 1,
  1628. .elem_size = sizeof(u8),
  1629. .array_type = NO_ARRAY,
  1630. .tlv_type = 0x10,
  1631. .offset = offsetof(struct qmi_wlanfw_wlan_ini_req_msg_v01,
  1632. enablefwlog),
  1633. },
  1634. {
  1635. .data_type = QMI_EOTI,
  1636. .array_type = NO_ARRAY,
  1637. .tlv_type = QMI_COMMON_TLV_TYPE,
  1638. },
  1639. };
  1640. static struct qmi_elem_info qmi_wlanfw_wlan_ini_resp_msg_v01_ei[] = {
  1641. {
  1642. .data_type = QMI_STRUCT,
  1643. .elem_len = 1,
  1644. .elem_size = sizeof(struct qmi_response_type_v01),
  1645. .array_type = NO_ARRAY,
  1646. .tlv_type = 0x02,
  1647. .offset = offsetof(struct qmi_wlanfw_wlan_ini_resp_msg_v01,
  1648. resp),
  1649. .ei_array = qmi_response_type_v01_ei,
  1650. },
  1651. {
  1652. .data_type = QMI_EOTI,
  1653. .array_type = NO_ARRAY,
  1654. .tlv_type = QMI_COMMON_TLV_TYPE,
  1655. },
  1656. };
  1657. static struct qmi_elem_info qmi_wlfw_fw_init_done_ind_msg_v01_ei[] = {
  1658. {
  1659. .data_type = QMI_EOTI,
  1660. .array_type = NO_ARRAY,
  1661. },
  1662. };
  1663. static int ath11k_qmi_host_cap_send(struct ath11k_base *ab)
  1664. {
  1665. struct qmi_wlanfw_host_cap_req_msg_v01 req;
  1666. struct qmi_wlanfw_host_cap_resp_msg_v01 resp;
  1667. struct qmi_txn txn;
  1668. int ret = 0;
  1669. memset(&req, 0, sizeof(req));
  1670. memset(&resp, 0, sizeof(resp));
  1671. req.num_clients_valid = 1;
  1672. req.num_clients = 1;
  1673. req.mem_cfg_mode = ab->qmi.target_mem_mode;
  1674. req.mem_cfg_mode_valid = 1;
  1675. req.bdf_support_valid = 1;
  1676. req.bdf_support = 1;
  1677. if (ab->hw_params.m3_fw_support) {
  1678. req.m3_support_valid = 1;
  1679. req.m3_support = 1;
  1680. req.m3_cache_support_valid = 1;
  1681. req.m3_cache_support = 1;
  1682. } else {
  1683. req.m3_support_valid = 0;
  1684. req.m3_support = 0;
  1685. req.m3_cache_support_valid = 0;
  1686. req.m3_cache_support = 0;
  1687. }
  1688. req.cal_done_valid = 1;
  1689. req.cal_done = ab->qmi.cal_done;
  1690. if (ab->hw_params.internal_sleep_clock) {
  1691. req.nm_modem_valid = 1;
  1692. /* Notify firmware that this is non-qualcomm platform. */
  1693. req.nm_modem |= HOST_CSTATE_BIT;
  1694. /* Notify firmware about the sleep clock selection,
  1695. * nm_modem_bit[1] is used for this purpose. Host driver on
  1696. * non-qualcomm platforms should select internal sleep
  1697. * clock.
  1698. */
  1699. req.nm_modem |= SLEEP_CLOCK_SELECT_INTERNAL_BIT;
  1700. }
  1701. if (ab->hw_params.global_reset)
  1702. req.nm_modem |= PLATFORM_CAP_PCIE_GLOBAL_RESET;
  1703. req.nm_modem |= PLATFORM_CAP_PCIE_PME_D3COLD;
  1704. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi host cap request\n");
  1705. ret = qmi_txn_init(&ab->qmi.handle, &txn,
  1706. qmi_wlanfw_host_cap_resp_msg_v01_ei, &resp);
  1707. if (ret < 0)
  1708. goto out;
  1709. ret = qmi_send_request(&ab->qmi.handle, NULL, &txn,
  1710. QMI_WLANFW_HOST_CAP_REQ_V01,
  1711. QMI_WLANFW_HOST_CAP_REQ_MSG_V01_MAX_LEN,
  1712. qmi_wlanfw_host_cap_req_msg_v01_ei, &req);
  1713. if (ret < 0) {
  1714. qmi_txn_cancel(&txn);
  1715. ath11k_warn(ab, "failed to send host capability request: %d\n", ret);
  1716. goto out;
  1717. }
  1718. ret = qmi_txn_wait(&txn, msecs_to_jiffies(ATH11K_QMI_WLANFW_TIMEOUT_MS));
  1719. if (ret < 0)
  1720. goto out;
  1721. if (resp.resp.result != QMI_RESULT_SUCCESS_V01) {
  1722. ath11k_warn(ab, "host capability request failed: %d %d\n",
  1723. resp.resp.result, resp.resp.error);
  1724. ret = -EINVAL;
  1725. goto out;
  1726. }
  1727. out:
  1728. return ret;
  1729. }
  1730. static int ath11k_qmi_fw_ind_register_send(struct ath11k_base *ab)
  1731. {
  1732. struct qmi_wlanfw_ind_register_req_msg_v01 *req;
  1733. struct qmi_wlanfw_ind_register_resp_msg_v01 *resp;
  1734. struct qmi_handle *handle = &ab->qmi.handle;
  1735. struct qmi_txn txn;
  1736. int ret;
  1737. req = kzalloc(sizeof(*req), GFP_KERNEL);
  1738. if (!req)
  1739. return -ENOMEM;
  1740. resp = kzalloc(sizeof(*resp), GFP_KERNEL);
  1741. if (!resp) {
  1742. ret = -ENOMEM;
  1743. goto resp_out;
  1744. }
  1745. req->client_id_valid = 1;
  1746. req->client_id = QMI_WLANFW_CLIENT_ID;
  1747. req->fw_ready_enable_valid = 1;
  1748. req->fw_ready_enable = 1;
  1749. req->cal_done_enable_valid = 1;
  1750. req->cal_done_enable = 1;
  1751. req->fw_init_done_enable_valid = 1;
  1752. req->fw_init_done_enable = 1;
  1753. req->pin_connect_result_enable_valid = 0;
  1754. req->pin_connect_result_enable = 0;
  1755. /* WCN6750 doesn't request for DDR memory via QMI,
  1756. * instead it uses a fixed 12MB reserved memory
  1757. * region in DDR.
  1758. */
  1759. if (!ab->hw_params.fixed_fw_mem) {
  1760. req->request_mem_enable_valid = 1;
  1761. req->request_mem_enable = 1;
  1762. req->fw_mem_ready_enable_valid = 1;
  1763. req->fw_mem_ready_enable = 1;
  1764. }
  1765. ret = qmi_txn_init(handle, &txn,
  1766. qmi_wlanfw_ind_register_resp_msg_v01_ei, resp);
  1767. if (ret < 0)
  1768. goto out;
  1769. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi indication register request\n");
  1770. ret = qmi_send_request(&ab->qmi.handle, NULL, &txn,
  1771. QMI_WLANFW_IND_REGISTER_REQ_V01,
  1772. QMI_WLANFW_IND_REGISTER_REQ_MSG_V01_MAX_LEN,
  1773. qmi_wlanfw_ind_register_req_msg_v01_ei, req);
  1774. if (ret < 0) {
  1775. qmi_txn_cancel(&txn);
  1776. ath11k_warn(ab, "failed to send indication register request: %d\n",
  1777. ret);
  1778. goto out;
  1779. }
  1780. ret = qmi_txn_wait(&txn, msecs_to_jiffies(ATH11K_QMI_WLANFW_TIMEOUT_MS));
  1781. if (ret < 0) {
  1782. ath11k_warn(ab, "failed to register fw indication: %d\n", ret);
  1783. goto out;
  1784. }
  1785. if (resp->resp.result != QMI_RESULT_SUCCESS_V01) {
  1786. ath11k_warn(ab, "firmware indication register request failed: %d %d\n",
  1787. resp->resp.result, resp->resp.error);
  1788. ret = -EINVAL;
  1789. goto out;
  1790. }
  1791. out:
  1792. kfree(resp);
  1793. resp_out:
  1794. kfree(req);
  1795. return ret;
  1796. }
  1797. static int ath11k_qmi_respond_fw_mem_request(struct ath11k_base *ab)
  1798. {
  1799. struct qmi_wlanfw_respond_mem_req_msg_v01 *req;
  1800. struct qmi_wlanfw_respond_mem_resp_msg_v01 resp;
  1801. struct qmi_txn txn;
  1802. int ret = 0, i;
  1803. bool delayed;
  1804. req = kzalloc(sizeof(*req), GFP_KERNEL);
  1805. if (!req)
  1806. return -ENOMEM;
  1807. memset(&resp, 0, sizeof(resp));
  1808. /* For QCA6390 by default FW requests a block of ~4M contiguous
  1809. * DMA memory, it's hard to allocate from OS. So host returns
  1810. * failure to FW and FW will then request multiple blocks of small
  1811. * chunk size memory.
  1812. */
  1813. if (!(ab->hw_params.fixed_mem_region ||
  1814. test_bit(ATH11K_FLAG_FIXED_MEM_RGN, &ab->dev_flags)) &&
  1815. ab->qmi.target_mem_delayed) {
  1816. delayed = true;
  1817. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi delays mem_request %d\n",
  1818. ab->qmi.mem_seg_count);
  1819. memset(req, 0, sizeof(*req));
  1820. } else {
  1821. delayed = false;
  1822. req->mem_seg_len = ab->qmi.mem_seg_count;
  1823. for (i = 0; i < req->mem_seg_len ; i++) {
  1824. req->mem_seg[i].addr = ab->qmi.target_mem[i].paddr;
  1825. req->mem_seg[i].size = ab->qmi.target_mem[i].size;
  1826. req->mem_seg[i].type = ab->qmi.target_mem[i].type;
  1827. ath11k_dbg(ab, ATH11K_DBG_QMI,
  1828. "qmi req mem_seg[%d] %pad %u %u\n", i,
  1829. &ab->qmi.target_mem[i].paddr,
  1830. ab->qmi.target_mem[i].size,
  1831. ab->qmi.target_mem[i].type);
  1832. }
  1833. }
  1834. ret = qmi_txn_init(&ab->qmi.handle, &txn,
  1835. qmi_wlanfw_respond_mem_resp_msg_v01_ei, &resp);
  1836. if (ret < 0)
  1837. goto out;
  1838. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi respond memory request delayed %i\n",
  1839. delayed);
  1840. ret = qmi_send_request(&ab->qmi.handle, NULL, &txn,
  1841. QMI_WLANFW_RESPOND_MEM_REQ_V01,
  1842. QMI_WLANFW_RESPOND_MEM_REQ_MSG_V01_MAX_LEN,
  1843. qmi_wlanfw_respond_mem_req_msg_v01_ei, req);
  1844. if (ret < 0) {
  1845. qmi_txn_cancel(&txn);
  1846. ath11k_warn(ab, "failed to respond qmi memory request: %d\n",
  1847. ret);
  1848. goto out;
  1849. }
  1850. ret = qmi_txn_wait(&txn, msecs_to_jiffies(ATH11K_QMI_WLANFW_TIMEOUT_MS));
  1851. if (ret < 0) {
  1852. ath11k_warn(ab, "failed to wait qmi memory request: %d\n", ret);
  1853. goto out;
  1854. }
  1855. if (resp.resp.result != QMI_RESULT_SUCCESS_V01) {
  1856. /* the error response is expected when
  1857. * target_mem_delayed is true.
  1858. */
  1859. if (delayed && resp.resp.error == 0)
  1860. goto out;
  1861. ath11k_warn(ab, "qmi respond memory request failed: %d %d\n",
  1862. resp.resp.result, resp.resp.error);
  1863. ret = -EINVAL;
  1864. goto out;
  1865. }
  1866. out:
  1867. kfree(req);
  1868. return ret;
  1869. }
  1870. static void ath11k_qmi_free_target_mem_chunk(struct ath11k_base *ab)
  1871. {
  1872. int i;
  1873. for (i = 0; i < ab->qmi.mem_seg_count; i++) {
  1874. if ((ab->hw_params.fixed_mem_region ||
  1875. test_bit(ATH11K_FLAG_FIXED_MEM_RGN, &ab->dev_flags)) &&
  1876. ab->qmi.target_mem[i].iaddr)
  1877. iounmap(ab->qmi.target_mem[i].iaddr);
  1878. if (!ab->qmi.target_mem[i].vaddr)
  1879. continue;
  1880. dma_free_coherent(ab->dev,
  1881. ab->qmi.target_mem[i].prev_size,
  1882. ab->qmi.target_mem[i].vaddr,
  1883. ab->qmi.target_mem[i].paddr);
  1884. ab->qmi.target_mem[i].vaddr = NULL;
  1885. }
  1886. }
  1887. static int ath11k_qmi_alloc_target_mem_chunk(struct ath11k_base *ab)
  1888. {
  1889. int i;
  1890. struct target_mem_chunk *chunk;
  1891. ab->qmi.target_mem_delayed = false;
  1892. for (i = 0; i < ab->qmi.mem_seg_count; i++) {
  1893. chunk = &ab->qmi.target_mem[i];
  1894. /* Firmware reloads in coldboot/firmware recovery.
  1895. * in such case, no need to allocate memory for FW again.
  1896. */
  1897. if (chunk->vaddr) {
  1898. if (chunk->prev_type == chunk->type &&
  1899. chunk->prev_size == chunk->size)
  1900. continue;
  1901. /* cannot reuse the existing chunk */
  1902. dma_free_coherent(ab->dev, chunk->prev_size,
  1903. chunk->vaddr, chunk->paddr);
  1904. chunk->vaddr = NULL;
  1905. }
  1906. chunk->vaddr = dma_alloc_coherent(ab->dev,
  1907. chunk->size,
  1908. &chunk->paddr,
  1909. GFP_KERNEL | __GFP_NOWARN);
  1910. if (!chunk->vaddr) {
  1911. if (ab->qmi.mem_seg_count <= ATH11K_QMI_FW_MEM_REQ_SEGMENT_CNT) {
  1912. ath11k_dbg(ab, ATH11K_DBG_QMI,
  1913. "qmi dma allocation failed (%d B type %u), will try later with small size\n",
  1914. chunk->size,
  1915. chunk->type);
  1916. ath11k_qmi_free_target_mem_chunk(ab);
  1917. ab->qmi.target_mem_delayed = true;
  1918. return 0;
  1919. }
  1920. ath11k_err(ab, "failed to allocate dma memory for qmi (%d B type %u)\n",
  1921. chunk->size,
  1922. chunk->type);
  1923. return -EINVAL;
  1924. }
  1925. chunk->prev_type = chunk->type;
  1926. chunk->prev_size = chunk->size;
  1927. }
  1928. return 0;
  1929. }
  1930. static int ath11k_qmi_assign_target_mem_chunk(struct ath11k_base *ab)
  1931. {
  1932. struct device *dev = ab->dev;
  1933. struct device_node *hremote_node = NULL;
  1934. struct resource res;
  1935. u32 host_ddr_sz;
  1936. int i, idx, ret;
  1937. for (i = 0, idx = 0; i < ab->qmi.mem_seg_count; i++) {
  1938. switch (ab->qmi.target_mem[i].type) {
  1939. case HOST_DDR_REGION_TYPE:
  1940. hremote_node = of_parse_phandle(dev->of_node, "memory-region", 0);
  1941. if (!hremote_node) {
  1942. ath11k_dbg(ab, ATH11K_DBG_QMI,
  1943. "qmi fail to get hremote_node\n");
  1944. return -ENODEV;
  1945. }
  1946. ret = of_address_to_resource(hremote_node, 0, &res);
  1947. of_node_put(hremote_node);
  1948. if (ret) {
  1949. ath11k_dbg(ab, ATH11K_DBG_QMI,
  1950. "qmi fail to get reg from hremote\n");
  1951. return ret;
  1952. }
  1953. if (res.end - res.start + 1 < ab->qmi.target_mem[i].size) {
  1954. ath11k_dbg(ab, ATH11K_DBG_QMI,
  1955. "qmi fail to assign memory of sz\n");
  1956. return -EINVAL;
  1957. }
  1958. ab->qmi.target_mem[idx].paddr = res.start;
  1959. ab->qmi.target_mem[idx].iaddr =
  1960. ioremap(ab->qmi.target_mem[idx].paddr,
  1961. ab->qmi.target_mem[i].size);
  1962. if (!ab->qmi.target_mem[idx].iaddr)
  1963. return -EIO;
  1964. ab->qmi.target_mem[idx].size = ab->qmi.target_mem[i].size;
  1965. host_ddr_sz = ab->qmi.target_mem[i].size;
  1966. ab->qmi.target_mem[idx].type = ab->qmi.target_mem[i].type;
  1967. idx++;
  1968. break;
  1969. case BDF_MEM_REGION_TYPE:
  1970. ab->qmi.target_mem[idx].paddr = ab->hw_params.bdf_addr;
  1971. ab->qmi.target_mem[idx].vaddr = NULL;
  1972. ab->qmi.target_mem[idx].size = ab->qmi.target_mem[i].size;
  1973. ab->qmi.target_mem[idx].type = ab->qmi.target_mem[i].type;
  1974. idx++;
  1975. break;
  1976. case CALDB_MEM_REGION_TYPE:
  1977. if (ab->qmi.target_mem[i].size > ATH11K_QMI_CALDB_SIZE) {
  1978. ath11k_warn(ab, "qmi mem size is low to load caldata\n");
  1979. return -EINVAL;
  1980. }
  1981. if (ath11k_cold_boot_cal && ab->hw_params.cold_boot_calib) {
  1982. if (hremote_node) {
  1983. ab->qmi.target_mem[idx].paddr =
  1984. res.start + host_ddr_sz;
  1985. ab->qmi.target_mem[idx].iaddr =
  1986. ioremap(ab->qmi.target_mem[idx].paddr,
  1987. ab->qmi.target_mem[i].size);
  1988. if (!ab->qmi.target_mem[idx].iaddr)
  1989. return -EIO;
  1990. } else {
  1991. ab->qmi.target_mem[idx].paddr =
  1992. ATH11K_QMI_CALDB_ADDRESS;
  1993. }
  1994. } else {
  1995. ab->qmi.target_mem[idx].paddr = 0;
  1996. ab->qmi.target_mem[idx].vaddr = NULL;
  1997. }
  1998. ab->qmi.target_mem[idx].size = ab->qmi.target_mem[i].size;
  1999. ab->qmi.target_mem[idx].type = ab->qmi.target_mem[i].type;
  2000. idx++;
  2001. break;
  2002. default:
  2003. ath11k_warn(ab, "qmi ignore invalid mem req type %d\n",
  2004. ab->qmi.target_mem[i].type);
  2005. break;
  2006. }
  2007. }
  2008. ab->qmi.mem_seg_count = idx;
  2009. return 0;
  2010. }
  2011. static int ath11k_qmi_request_device_info(struct ath11k_base *ab)
  2012. {
  2013. struct qmi_wlanfw_device_info_req_msg_v01 req = {};
  2014. struct qmi_wlanfw_device_info_resp_msg_v01 resp = {};
  2015. struct qmi_txn txn;
  2016. void __iomem *bar_addr_va;
  2017. int ret;
  2018. /* device info message req is only sent for hybrid bus devices */
  2019. if (!ab->hw_params.hybrid_bus_type)
  2020. return 0;
  2021. ret = qmi_txn_init(&ab->qmi.handle, &txn,
  2022. qmi_wlfw_device_info_resp_msg_v01_ei, &resp);
  2023. if (ret < 0)
  2024. goto out;
  2025. ret = qmi_send_request(&ab->qmi.handle, NULL, &txn,
  2026. QMI_WLANFW_DEVICE_INFO_REQ_V01,
  2027. QMI_WLANFW_DEVICE_INFO_REQ_MSG_V01_MAX_LEN,
  2028. qmi_wlanfw_device_info_req_msg_v01_ei, &req);
  2029. if (ret < 0) {
  2030. qmi_txn_cancel(&txn);
  2031. ath11k_warn(ab, "failed to send qmi target device info request: %d\n",
  2032. ret);
  2033. goto out;
  2034. }
  2035. ret = qmi_txn_wait(&txn, msecs_to_jiffies(ATH11K_QMI_WLANFW_TIMEOUT_MS));
  2036. if (ret < 0) {
  2037. ath11k_warn(ab, "failed to wait qmi target device info request: %d\n",
  2038. ret);
  2039. goto out;
  2040. }
  2041. if (resp.resp.result != QMI_RESULT_SUCCESS_V01) {
  2042. ath11k_warn(ab, "qmi device info request failed: %d %d\n",
  2043. resp.resp.result, resp.resp.error);
  2044. ret = -EINVAL;
  2045. goto out;
  2046. }
  2047. if (!resp.bar_addr_valid || !resp.bar_size_valid) {
  2048. ath11k_warn(ab, "qmi device info response invalid: %d %d\n",
  2049. resp.resp.result, resp.resp.error);
  2050. ret = -EINVAL;
  2051. goto out;
  2052. }
  2053. if (!resp.bar_addr ||
  2054. resp.bar_size != ATH11K_QMI_DEVICE_BAR_SIZE) {
  2055. ath11k_warn(ab, "qmi device info invalid address and size: %llu %u\n",
  2056. resp.bar_addr, resp.bar_size);
  2057. ret = -EINVAL;
  2058. goto out;
  2059. }
  2060. bar_addr_va = devm_ioremap(ab->dev, resp.bar_addr, resp.bar_size);
  2061. if (!bar_addr_va) {
  2062. ath11k_warn(ab, "qmi device info ioremap failed\n");
  2063. ab->mem_len = 0;
  2064. ret = -EIO;
  2065. goto out;
  2066. }
  2067. ab->mem = bar_addr_va;
  2068. ab->mem_len = resp.bar_size;
  2069. return 0;
  2070. out:
  2071. return ret;
  2072. }
  2073. static int ath11k_qmi_request_target_cap(struct ath11k_base *ab)
  2074. {
  2075. struct qmi_wlanfw_cap_req_msg_v01 req;
  2076. struct qmi_wlanfw_cap_resp_msg_v01 resp;
  2077. struct qmi_txn txn;
  2078. int ret = 0;
  2079. int r;
  2080. char *fw_build_id;
  2081. int fw_build_id_mask_len;
  2082. memset(&req, 0, sizeof(req));
  2083. memset(&resp, 0, sizeof(resp));
  2084. ret = qmi_txn_init(&ab->qmi.handle, &txn, qmi_wlanfw_cap_resp_msg_v01_ei,
  2085. &resp);
  2086. if (ret < 0)
  2087. goto out;
  2088. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi target cap request\n");
  2089. ret = qmi_send_request(&ab->qmi.handle, NULL, &txn,
  2090. QMI_WLANFW_CAP_REQ_V01,
  2091. QMI_WLANFW_CAP_REQ_MSG_V01_MAX_LEN,
  2092. qmi_wlanfw_cap_req_msg_v01_ei, &req);
  2093. if (ret < 0) {
  2094. qmi_txn_cancel(&txn);
  2095. ath11k_warn(ab, "failed to send qmi cap request: %d\n",
  2096. ret);
  2097. goto out;
  2098. }
  2099. ret = qmi_txn_wait(&txn, msecs_to_jiffies(ATH11K_QMI_WLANFW_TIMEOUT_MS));
  2100. if (ret < 0) {
  2101. ath11k_warn(ab, "failed to wait qmi cap request: %d\n", ret);
  2102. goto out;
  2103. }
  2104. if (resp.resp.result != QMI_RESULT_SUCCESS_V01) {
  2105. ath11k_warn(ab, "qmi cap request failed: %d %d\n",
  2106. resp.resp.result, resp.resp.error);
  2107. ret = -EINVAL;
  2108. goto out;
  2109. }
  2110. if (resp.chip_info_valid) {
  2111. ab->qmi.target.chip_id = resp.chip_info.chip_id;
  2112. ab->qmi.target.chip_family = resp.chip_info.chip_family;
  2113. }
  2114. if (resp.board_info_valid)
  2115. ab->qmi.target.board_id = resp.board_info.board_id;
  2116. else
  2117. ab->qmi.target.board_id = 0xFF;
  2118. if (resp.soc_info_valid)
  2119. ab->qmi.target.soc_id = resp.soc_info.soc_id;
  2120. if (resp.fw_version_info_valid) {
  2121. ab->qmi.target.fw_version = resp.fw_version_info.fw_version;
  2122. strscpy(ab->qmi.target.fw_build_timestamp,
  2123. resp.fw_version_info.fw_build_timestamp,
  2124. sizeof(ab->qmi.target.fw_build_timestamp));
  2125. }
  2126. if (resp.fw_build_id_valid)
  2127. strscpy(ab->qmi.target.fw_build_id, resp.fw_build_id,
  2128. sizeof(ab->qmi.target.fw_build_id));
  2129. if (resp.eeprom_read_timeout_valid) {
  2130. ab->qmi.target.eeprom_caldata =
  2131. resp.eeprom_read_timeout;
  2132. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi cal data supported from eeprom\n");
  2133. }
  2134. fw_build_id = ab->qmi.target.fw_build_id;
  2135. fw_build_id_mask_len = strlen(FW_BUILD_ID_MASK);
  2136. if (!strncmp(fw_build_id, FW_BUILD_ID_MASK, fw_build_id_mask_len))
  2137. fw_build_id = fw_build_id + fw_build_id_mask_len;
  2138. ath11k_info(ab, "chip_id 0x%x chip_family 0x%x board_id 0x%x soc_id 0x%x\n",
  2139. ab->qmi.target.chip_id, ab->qmi.target.chip_family,
  2140. ab->qmi.target.board_id, ab->qmi.target.soc_id);
  2141. ath11k_info(ab, "fw_version 0x%x fw_build_timestamp %s fw_build_id %s",
  2142. ab->qmi.target.fw_version,
  2143. ab->qmi.target.fw_build_timestamp,
  2144. fw_build_id);
  2145. r = ath11k_core_check_smbios(ab);
  2146. if (r)
  2147. ath11k_dbg(ab, ATH11K_DBG_QMI, "SMBIOS bdf variant name not set.\n");
  2148. r = ath11k_core_check_dt(ab);
  2149. if (r)
  2150. ath11k_dbg(ab, ATH11K_DBG_QMI, "DT bdf variant name not set.\n");
  2151. out:
  2152. return ret;
  2153. }
  2154. static int ath11k_qmi_load_file_target_mem(struct ath11k_base *ab,
  2155. const u8 *data, u32 len, u8 type)
  2156. {
  2157. struct qmi_wlanfw_bdf_download_req_msg_v01 *req;
  2158. struct qmi_wlanfw_bdf_download_resp_msg_v01 resp;
  2159. struct qmi_txn txn;
  2160. const u8 *temp = data;
  2161. void __iomem *bdf_addr = NULL;
  2162. int ret;
  2163. u32 remaining = len;
  2164. req = kzalloc(sizeof(*req), GFP_KERNEL);
  2165. if (!req)
  2166. return -ENOMEM;
  2167. memset(&resp, 0, sizeof(resp));
  2168. if (ab->hw_params.fixed_bdf_addr) {
  2169. bdf_addr = ioremap(ab->hw_params.bdf_addr, ab->hw_params.fw.board_size);
  2170. if (!bdf_addr) {
  2171. ath11k_warn(ab, "qmi ioremap error for bdf_addr\n");
  2172. ret = -EIO;
  2173. goto err_free_req;
  2174. }
  2175. }
  2176. while (remaining) {
  2177. req->valid = 1;
  2178. req->file_id_valid = 1;
  2179. req->file_id = ab->qmi.target.board_id;
  2180. req->total_size_valid = 1;
  2181. req->total_size = remaining;
  2182. req->seg_id_valid = 1;
  2183. req->data_valid = 1;
  2184. req->bdf_type = type;
  2185. req->bdf_type_valid = 1;
  2186. req->end_valid = 1;
  2187. req->end = 0;
  2188. if (remaining > QMI_WLANFW_MAX_DATA_SIZE_V01) {
  2189. req->data_len = QMI_WLANFW_MAX_DATA_SIZE_V01;
  2190. } else {
  2191. req->data_len = remaining;
  2192. req->end = 1;
  2193. }
  2194. if (ab->hw_params.fixed_bdf_addr ||
  2195. type == ATH11K_QMI_FILE_TYPE_EEPROM) {
  2196. req->data_valid = 0;
  2197. req->end = 1;
  2198. req->data_len = ATH11K_QMI_MAX_BDF_FILE_NAME_SIZE;
  2199. } else {
  2200. memcpy(req->data, temp, req->data_len);
  2201. }
  2202. if (ab->hw_params.fixed_bdf_addr) {
  2203. if (type == ATH11K_QMI_FILE_TYPE_CALDATA)
  2204. bdf_addr += ab->hw_params.fw.cal_offset;
  2205. memcpy_toio(bdf_addr, temp, len);
  2206. }
  2207. ret = qmi_txn_init(&ab->qmi.handle, &txn,
  2208. qmi_wlanfw_bdf_download_resp_msg_v01_ei,
  2209. &resp);
  2210. if (ret < 0)
  2211. goto err_iounmap;
  2212. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi bdf download req fixed addr type %d\n",
  2213. type);
  2214. ret = qmi_send_request(&ab->qmi.handle, NULL, &txn,
  2215. QMI_WLANFW_BDF_DOWNLOAD_REQ_V01,
  2216. QMI_WLANFW_BDF_DOWNLOAD_REQ_MSG_V01_MAX_LEN,
  2217. qmi_wlanfw_bdf_download_req_msg_v01_ei, req);
  2218. if (ret < 0) {
  2219. qmi_txn_cancel(&txn);
  2220. goto err_iounmap;
  2221. }
  2222. ret = qmi_txn_wait(&txn, msecs_to_jiffies(ATH11K_QMI_WLANFW_TIMEOUT_MS));
  2223. if (ret < 0) {
  2224. ath11k_warn(ab, "failed to wait board file download request: %d\n",
  2225. ret);
  2226. goto err_iounmap;
  2227. }
  2228. if (resp.resp.result != QMI_RESULT_SUCCESS_V01) {
  2229. ath11k_warn(ab, "board file download request failed: %d %d\n",
  2230. resp.resp.result, resp.resp.error);
  2231. ret = -EINVAL;
  2232. goto err_iounmap;
  2233. }
  2234. if (ab->hw_params.fixed_bdf_addr ||
  2235. type == ATH11K_QMI_FILE_TYPE_EEPROM) {
  2236. remaining = 0;
  2237. } else {
  2238. remaining -= req->data_len;
  2239. temp += req->data_len;
  2240. req->seg_id++;
  2241. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi bdf download request remaining %i\n",
  2242. remaining);
  2243. }
  2244. }
  2245. err_iounmap:
  2246. if (ab->hw_params.fixed_bdf_addr)
  2247. iounmap(bdf_addr);
  2248. err_free_req:
  2249. kfree(req);
  2250. return ret;
  2251. }
  2252. static int ath11k_qmi_load_bdf_qmi(struct ath11k_base *ab,
  2253. bool regdb)
  2254. {
  2255. struct device *dev = ab->dev;
  2256. char filename[ATH11K_QMI_MAX_BDF_FILE_NAME_SIZE];
  2257. const struct firmware *fw_entry;
  2258. struct ath11k_board_data bd;
  2259. u32 fw_size, file_type;
  2260. int ret = 0, bdf_type;
  2261. const u8 *tmp;
  2262. memset(&bd, 0, sizeof(bd));
  2263. if (regdb) {
  2264. ret = ath11k_core_fetch_regdb(ab, &bd);
  2265. } else {
  2266. ret = ath11k_core_fetch_bdf(ab, &bd);
  2267. if (ret)
  2268. ath11k_warn(ab, "qmi failed to fetch board file: %d\n", ret);
  2269. }
  2270. if (ret)
  2271. goto out;
  2272. if (regdb)
  2273. bdf_type = ATH11K_QMI_BDF_TYPE_REGDB;
  2274. else if (bd.len >= SELFMAG && memcmp(bd.data, ELFMAG, SELFMAG) == 0)
  2275. bdf_type = ATH11K_QMI_BDF_TYPE_ELF;
  2276. else
  2277. bdf_type = ATH11K_QMI_BDF_TYPE_BIN;
  2278. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi bdf_type %d\n", bdf_type);
  2279. fw_size = min_t(u32, ab->hw_params.fw.board_size, bd.len);
  2280. ret = ath11k_qmi_load_file_target_mem(ab, bd.data, fw_size, bdf_type);
  2281. if (ret < 0) {
  2282. ath11k_warn(ab, "qmi failed to load bdf file\n");
  2283. goto out;
  2284. }
  2285. /* QCA6390/WCN6855 does not support cal data, skip it */
  2286. if (bdf_type == ATH11K_QMI_BDF_TYPE_ELF || bdf_type == ATH11K_QMI_BDF_TYPE_REGDB)
  2287. goto out;
  2288. if (ab->qmi.target.eeprom_caldata) {
  2289. file_type = ATH11K_QMI_FILE_TYPE_EEPROM;
  2290. tmp = filename;
  2291. fw_size = ATH11K_QMI_MAX_BDF_FILE_NAME_SIZE;
  2292. } else {
  2293. file_type = ATH11K_QMI_FILE_TYPE_CALDATA;
  2294. /* cal-<bus>-<id>.bin */
  2295. snprintf(filename, sizeof(filename), "cal-%s-%s.bin",
  2296. ath11k_bus_str(ab->hif.bus), dev_name(dev));
  2297. fw_entry = ath11k_core_firmware_request(ab, filename);
  2298. if (!IS_ERR(fw_entry))
  2299. goto success;
  2300. fw_entry = ath11k_core_firmware_request(ab, ATH11K_DEFAULT_CAL_FILE);
  2301. if (IS_ERR(fw_entry)) {
  2302. ret = PTR_ERR(fw_entry);
  2303. ath11k_warn(ab,
  2304. "qmi failed to load CAL data file:%s\n",
  2305. filename);
  2306. goto out;
  2307. }
  2308. success:
  2309. fw_size = min_t(u32, ab->hw_params.fw.board_size, fw_entry->size);
  2310. tmp = fw_entry->data;
  2311. }
  2312. ret = ath11k_qmi_load_file_target_mem(ab, tmp, fw_size, file_type);
  2313. if (ret < 0) {
  2314. ath11k_warn(ab, "qmi failed to load caldata\n");
  2315. goto out_qmi_cal;
  2316. }
  2317. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi caldata type: %u\n", file_type);
  2318. out_qmi_cal:
  2319. if (!ab->qmi.target.eeprom_caldata)
  2320. release_firmware(fw_entry);
  2321. out:
  2322. ath11k_core_free_bdf(ab, &bd);
  2323. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi BDF download sequence completed\n");
  2324. return ret;
  2325. }
  2326. static int ath11k_qmi_m3_load(struct ath11k_base *ab)
  2327. {
  2328. struct m3_mem_region *m3_mem = &ab->qmi.m3_mem;
  2329. const struct firmware *fw;
  2330. char path[100];
  2331. int ret;
  2332. fw = ath11k_core_firmware_request(ab, ATH11K_M3_FILE);
  2333. if (IS_ERR(fw)) {
  2334. ret = PTR_ERR(fw);
  2335. ath11k_core_create_firmware_path(ab, ATH11K_M3_FILE,
  2336. path, sizeof(path));
  2337. ath11k_err(ab, "failed to load %s: %d\n", path, ret);
  2338. return ret;
  2339. }
  2340. if (m3_mem->vaddr || m3_mem->size)
  2341. goto skip_m3_alloc;
  2342. m3_mem->vaddr = dma_alloc_coherent(ab->dev,
  2343. fw->size, &m3_mem->paddr,
  2344. GFP_KERNEL);
  2345. if (!m3_mem->vaddr) {
  2346. ath11k_err(ab, "failed to allocate memory for M3 with size %zu\n",
  2347. fw->size);
  2348. release_firmware(fw);
  2349. return -ENOMEM;
  2350. }
  2351. skip_m3_alloc:
  2352. memcpy(m3_mem->vaddr, fw->data, fw->size);
  2353. m3_mem->size = fw->size;
  2354. release_firmware(fw);
  2355. return 0;
  2356. }
  2357. static void ath11k_qmi_m3_free(struct ath11k_base *ab)
  2358. {
  2359. struct m3_mem_region *m3_mem = &ab->qmi.m3_mem;
  2360. if (!ab->hw_params.m3_fw_support || !m3_mem->vaddr)
  2361. return;
  2362. dma_free_coherent(ab->dev, m3_mem->size,
  2363. m3_mem->vaddr, m3_mem->paddr);
  2364. m3_mem->vaddr = NULL;
  2365. m3_mem->size = 0;
  2366. }
  2367. static int ath11k_qmi_wlanfw_m3_info_send(struct ath11k_base *ab)
  2368. {
  2369. struct m3_mem_region *m3_mem = &ab->qmi.m3_mem;
  2370. struct qmi_wlanfw_m3_info_req_msg_v01 req;
  2371. struct qmi_wlanfw_m3_info_resp_msg_v01 resp;
  2372. struct qmi_txn txn;
  2373. int ret = 0;
  2374. memset(&req, 0, sizeof(req));
  2375. memset(&resp, 0, sizeof(resp));
  2376. if (ab->hw_params.m3_fw_support) {
  2377. ret = ath11k_qmi_m3_load(ab);
  2378. if (ret) {
  2379. ath11k_err(ab, "failed to load m3 firmware: %d", ret);
  2380. return ret;
  2381. }
  2382. req.addr = m3_mem->paddr;
  2383. req.size = m3_mem->size;
  2384. } else {
  2385. req.addr = 0;
  2386. req.size = 0;
  2387. }
  2388. ret = qmi_txn_init(&ab->qmi.handle, &txn,
  2389. qmi_wlanfw_m3_info_resp_msg_v01_ei, &resp);
  2390. if (ret < 0)
  2391. goto out;
  2392. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi m3 info req\n");
  2393. ret = qmi_send_request(&ab->qmi.handle, NULL, &txn,
  2394. QMI_WLANFW_M3_INFO_REQ_V01,
  2395. QMI_WLANFW_M3_INFO_REQ_MSG_V01_MAX_MSG_LEN,
  2396. qmi_wlanfw_m3_info_req_msg_v01_ei, &req);
  2397. if (ret < 0) {
  2398. qmi_txn_cancel(&txn);
  2399. ath11k_warn(ab, "failed to send m3 information request: %d\n",
  2400. ret);
  2401. goto out;
  2402. }
  2403. ret = qmi_txn_wait(&txn, msecs_to_jiffies(ATH11K_QMI_WLANFW_TIMEOUT_MS));
  2404. if (ret < 0) {
  2405. ath11k_warn(ab, "failed to wait m3 information request: %d\n", ret);
  2406. goto out;
  2407. }
  2408. if (resp.resp.result != QMI_RESULT_SUCCESS_V01) {
  2409. ath11k_warn(ab, "m3 info request failed: %d %d\n",
  2410. resp.resp.result, resp.resp.error);
  2411. ret = -EINVAL;
  2412. goto out;
  2413. }
  2414. out:
  2415. return ret;
  2416. }
  2417. static int ath11k_qmi_wlanfw_mode_send(struct ath11k_base *ab,
  2418. u32 mode)
  2419. {
  2420. struct qmi_wlanfw_wlan_mode_req_msg_v01 req;
  2421. struct qmi_wlanfw_wlan_mode_resp_msg_v01 resp;
  2422. struct qmi_txn txn;
  2423. int ret = 0;
  2424. memset(&req, 0, sizeof(req));
  2425. memset(&resp, 0, sizeof(resp));
  2426. req.mode = mode;
  2427. req.hw_debug_valid = 1;
  2428. req.hw_debug = 0;
  2429. ret = qmi_txn_init(&ab->qmi.handle, &txn,
  2430. qmi_wlanfw_wlan_mode_resp_msg_v01_ei, &resp);
  2431. if (ret < 0)
  2432. goto out;
  2433. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi wlan mode req mode %d\n", mode);
  2434. ret = qmi_send_request(&ab->qmi.handle, NULL, &txn,
  2435. QMI_WLANFW_WLAN_MODE_REQ_V01,
  2436. QMI_WLANFW_WLAN_MODE_REQ_MSG_V01_MAX_LEN,
  2437. qmi_wlanfw_wlan_mode_req_msg_v01_ei, &req);
  2438. if (ret < 0) {
  2439. qmi_txn_cancel(&txn);
  2440. ath11k_warn(ab, "failed to send wlan mode request (mode %d): %d\n",
  2441. mode, ret);
  2442. goto out;
  2443. }
  2444. ret = qmi_txn_wait(&txn, msecs_to_jiffies(ATH11K_QMI_WLANFW_TIMEOUT_MS));
  2445. if (ret < 0) {
  2446. if (mode == ATH11K_FIRMWARE_MODE_OFF && ret == -ENETRESET) {
  2447. ath11k_warn(ab, "WLFW service is dis-connected\n");
  2448. return 0;
  2449. }
  2450. ath11k_warn(ab, "failed to wait wlan mode request (mode %d): %d\n",
  2451. mode, ret);
  2452. goto out;
  2453. }
  2454. if (resp.resp.result != QMI_RESULT_SUCCESS_V01) {
  2455. ath11k_warn(ab, "wlan mode request failed (mode: %d): %d %d\n",
  2456. mode, resp.resp.result, resp.resp.error);
  2457. ret = -EINVAL;
  2458. goto out;
  2459. }
  2460. out:
  2461. return ret;
  2462. }
  2463. static int ath11k_qmi_wlanfw_wlan_cfg_send(struct ath11k_base *ab)
  2464. {
  2465. struct qmi_wlanfw_wlan_cfg_req_msg_v01 *req;
  2466. struct qmi_wlanfw_wlan_cfg_resp_msg_v01 resp;
  2467. struct ce_pipe_config *ce_cfg;
  2468. struct service_to_pipe *svc_cfg;
  2469. struct qmi_txn txn;
  2470. int ret = 0, pipe_num;
  2471. ce_cfg = (struct ce_pipe_config *)ab->qmi.ce_cfg.tgt_ce;
  2472. svc_cfg = (struct service_to_pipe *)ab->qmi.ce_cfg.svc_to_ce_map;
  2473. req = kzalloc(sizeof(*req), GFP_KERNEL);
  2474. if (!req)
  2475. return -ENOMEM;
  2476. memset(&resp, 0, sizeof(resp));
  2477. req->host_version_valid = 1;
  2478. strscpy(req->host_version, ATH11K_HOST_VERSION_STRING,
  2479. sizeof(req->host_version));
  2480. req->tgt_cfg_valid = 1;
  2481. /* This is number of CE configs */
  2482. req->tgt_cfg_len = ab->qmi.ce_cfg.tgt_ce_len;
  2483. for (pipe_num = 0; pipe_num < req->tgt_cfg_len ; pipe_num++) {
  2484. req->tgt_cfg[pipe_num].pipe_num = ce_cfg[pipe_num].pipenum;
  2485. req->tgt_cfg[pipe_num].pipe_dir = ce_cfg[pipe_num].pipedir;
  2486. req->tgt_cfg[pipe_num].nentries = ce_cfg[pipe_num].nentries;
  2487. req->tgt_cfg[pipe_num].nbytes_max = ce_cfg[pipe_num].nbytes_max;
  2488. req->tgt_cfg[pipe_num].flags = ce_cfg[pipe_num].flags;
  2489. }
  2490. req->svc_cfg_valid = 1;
  2491. /* This is number of Service/CE configs */
  2492. req->svc_cfg_len = ab->qmi.ce_cfg.svc_to_ce_map_len;
  2493. for (pipe_num = 0; pipe_num < req->svc_cfg_len; pipe_num++) {
  2494. req->svc_cfg[pipe_num].service_id = svc_cfg[pipe_num].service_id;
  2495. req->svc_cfg[pipe_num].pipe_dir = svc_cfg[pipe_num].pipedir;
  2496. req->svc_cfg[pipe_num].pipe_num = svc_cfg[pipe_num].pipenum;
  2497. }
  2498. req->shadow_reg_valid = 0;
  2499. /* set shadow v2 configuration */
  2500. if (ab->hw_params.supports_shadow_regs) {
  2501. req->shadow_reg_v2_valid = 1;
  2502. req->shadow_reg_v2_len = min_t(u32,
  2503. ab->qmi.ce_cfg.shadow_reg_v2_len,
  2504. QMI_WLANFW_MAX_NUM_SHADOW_REG_V2_V01);
  2505. memcpy(&req->shadow_reg_v2, ab->qmi.ce_cfg.shadow_reg_v2,
  2506. sizeof(u32) * req->shadow_reg_v2_len);
  2507. } else {
  2508. req->shadow_reg_v2_valid = 0;
  2509. }
  2510. ret = qmi_txn_init(&ab->qmi.handle, &txn,
  2511. qmi_wlanfw_wlan_cfg_resp_msg_v01_ei, &resp);
  2512. if (ret < 0)
  2513. goto out;
  2514. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi wlan cfg req\n");
  2515. ret = qmi_send_request(&ab->qmi.handle, NULL, &txn,
  2516. QMI_WLANFW_WLAN_CFG_REQ_V01,
  2517. QMI_WLANFW_WLAN_CFG_REQ_MSG_V01_MAX_LEN,
  2518. qmi_wlanfw_wlan_cfg_req_msg_v01_ei, req);
  2519. if (ret < 0) {
  2520. qmi_txn_cancel(&txn);
  2521. ath11k_warn(ab, "failed to send wlan config request: %d\n",
  2522. ret);
  2523. goto out;
  2524. }
  2525. ret = qmi_txn_wait(&txn, msecs_to_jiffies(ATH11K_QMI_WLANFW_TIMEOUT_MS));
  2526. if (ret < 0) {
  2527. ath11k_warn(ab, "failed to wait wlan config request: %d\n", ret);
  2528. goto out;
  2529. }
  2530. if (resp.resp.result != QMI_RESULT_SUCCESS_V01) {
  2531. ath11k_warn(ab, "wlan config request failed: %d %d\n",
  2532. resp.resp.result, resp.resp.error);
  2533. ret = -EINVAL;
  2534. goto out;
  2535. }
  2536. out:
  2537. kfree(req);
  2538. return ret;
  2539. }
  2540. static int ath11k_qmi_wlanfw_wlan_ini_send(struct ath11k_base *ab, bool enable)
  2541. {
  2542. int ret;
  2543. struct qmi_txn txn;
  2544. struct qmi_wlanfw_wlan_ini_req_msg_v01 req = {};
  2545. struct qmi_wlanfw_wlan_ini_resp_msg_v01 resp = {};
  2546. req.enablefwlog_valid = true;
  2547. req.enablefwlog = enable ? 1 : 0;
  2548. ret = qmi_txn_init(&ab->qmi.handle, &txn,
  2549. qmi_wlanfw_wlan_ini_resp_msg_v01_ei, &resp);
  2550. if (ret < 0)
  2551. goto out;
  2552. ret = qmi_send_request(&ab->qmi.handle, NULL, &txn,
  2553. QMI_WLANFW_WLAN_INI_REQ_V01,
  2554. QMI_WLANFW_WLAN_INI_REQ_MSG_V01_MAX_LEN,
  2555. qmi_wlanfw_wlan_ini_req_msg_v01_ei, &req);
  2556. if (ret < 0) {
  2557. ath11k_warn(ab, "qmi failed to send wlan ini request, err = %d\n",
  2558. ret);
  2559. qmi_txn_cancel(&txn);
  2560. goto out;
  2561. }
  2562. ret = qmi_txn_wait(&txn, msecs_to_jiffies(ATH11K_QMI_WLANFW_TIMEOUT_MS));
  2563. if (ret < 0) {
  2564. ath11k_warn(ab, "qmi failed wlan ini request, err = %d\n", ret);
  2565. goto out;
  2566. }
  2567. if (resp.resp.result != QMI_RESULT_SUCCESS_V01) {
  2568. ath11k_warn(ab, "qmi wlan ini request failed, result: %d, err: %d\n",
  2569. resp.resp.result, resp.resp.error);
  2570. ret = -EINVAL;
  2571. }
  2572. out:
  2573. return ret;
  2574. }
  2575. void ath11k_qmi_firmware_stop(struct ath11k_base *ab)
  2576. {
  2577. int ret;
  2578. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi firmware stop\n");
  2579. ret = ath11k_qmi_wlanfw_mode_send(ab, ATH11K_FIRMWARE_MODE_OFF);
  2580. if (ret < 0) {
  2581. ath11k_warn(ab, "qmi failed to send wlan mode off: %d\n", ret);
  2582. return;
  2583. }
  2584. }
  2585. int ath11k_qmi_firmware_start(struct ath11k_base *ab,
  2586. u32 mode)
  2587. {
  2588. int ret;
  2589. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi firmware start\n");
  2590. if (ab->hw_params.fw_wmi_diag_event) {
  2591. ret = ath11k_qmi_wlanfw_wlan_ini_send(ab, true);
  2592. if (ret < 0) {
  2593. ath11k_warn(ab, "qmi failed to send wlan fw ini:%d\n", ret);
  2594. return ret;
  2595. }
  2596. }
  2597. ret = ath11k_qmi_wlanfw_wlan_cfg_send(ab);
  2598. if (ret < 0) {
  2599. ath11k_warn(ab, "qmi failed to send wlan cfg: %d\n", ret);
  2600. return ret;
  2601. }
  2602. ret = ath11k_qmi_wlanfw_mode_send(ab, mode);
  2603. if (ret < 0) {
  2604. ath11k_warn(ab, "qmi failed to send wlan fw mode: %d\n", ret);
  2605. return ret;
  2606. }
  2607. return 0;
  2608. }
  2609. static int ath11k_qmi_process_coldboot_calibration(struct ath11k_base *ab)
  2610. {
  2611. int timeout;
  2612. int ret;
  2613. ret = ath11k_qmi_wlanfw_mode_send(ab, ATH11K_FIRMWARE_MODE_COLD_BOOT);
  2614. if (ret < 0) {
  2615. ath11k_warn(ab, "qmi failed to send wlan fw mode: %d\n", ret);
  2616. return ret;
  2617. }
  2618. ath11k_dbg(ab, ATH11K_DBG_QMI, "Coldboot calibration wait started\n");
  2619. timeout = wait_event_timeout(ab->qmi.cold_boot_waitq,
  2620. (ab->qmi.cal_done == 1),
  2621. ATH11K_COLD_BOOT_FW_RESET_DELAY);
  2622. if (timeout <= 0) {
  2623. ath11k_warn(ab, "coldboot calibration timed out\n");
  2624. return 0;
  2625. }
  2626. ath11k_dbg(ab, ATH11K_DBG_QMI, "Coldboot calibration done\n");
  2627. return 0;
  2628. }
  2629. static int
  2630. ath11k_qmi_driver_event_post(struct ath11k_qmi *qmi,
  2631. enum ath11k_qmi_event_type type,
  2632. void *data)
  2633. {
  2634. struct ath11k_qmi_driver_event *event;
  2635. event = kzalloc(sizeof(*event), GFP_ATOMIC);
  2636. if (!event)
  2637. return -ENOMEM;
  2638. event->type = type;
  2639. event->data = data;
  2640. spin_lock(&qmi->event_lock);
  2641. list_add_tail(&event->list, &qmi->event_list);
  2642. spin_unlock(&qmi->event_lock);
  2643. queue_work(qmi->event_wq, &qmi->event_work);
  2644. return 0;
  2645. }
  2646. static int ath11k_qmi_event_mem_request(struct ath11k_qmi *qmi)
  2647. {
  2648. struct ath11k_base *ab = qmi->ab;
  2649. int ret;
  2650. ret = ath11k_qmi_respond_fw_mem_request(ab);
  2651. if (ret < 0) {
  2652. ath11k_warn(ab, "qmi failed to respond fw mem req: %d\n", ret);
  2653. return ret;
  2654. }
  2655. return ret;
  2656. }
  2657. static int ath11k_qmi_event_load_bdf(struct ath11k_qmi *qmi)
  2658. {
  2659. struct ath11k_base *ab = qmi->ab;
  2660. int ret;
  2661. ret = ath11k_qmi_request_target_cap(ab);
  2662. if (ret < 0) {
  2663. ath11k_warn(ab, "failed to request qmi target capabilities: %d\n",
  2664. ret);
  2665. return ret;
  2666. }
  2667. ret = ath11k_qmi_request_device_info(ab);
  2668. if (ret < 0) {
  2669. ath11k_warn(ab, "failed to request qmi device info: %d\n", ret);
  2670. return ret;
  2671. }
  2672. if (ab->hw_params.supports_regdb)
  2673. ath11k_qmi_load_bdf_qmi(ab, true);
  2674. ret = ath11k_qmi_load_bdf_qmi(ab, false);
  2675. if (ret < 0) {
  2676. ath11k_warn(ab, "failed to load board data file: %d\n", ret);
  2677. return ret;
  2678. }
  2679. return 0;
  2680. }
  2681. static int ath11k_qmi_event_server_arrive(struct ath11k_qmi *qmi)
  2682. {
  2683. struct ath11k_base *ab = qmi->ab;
  2684. int ret;
  2685. ret = ath11k_qmi_fw_ind_register_send(ab);
  2686. if (ret < 0) {
  2687. ath11k_warn(ab, "failed to send qmi firmware indication: %d\n",
  2688. ret);
  2689. return ret;
  2690. }
  2691. ret = ath11k_qmi_host_cap_send(ab);
  2692. if (ret < 0) {
  2693. ath11k_warn(ab, "failed to send qmi host cap: %d\n", ret);
  2694. return ret;
  2695. }
  2696. if (!ab->hw_params.fixed_fw_mem)
  2697. return ret;
  2698. ret = ath11k_qmi_event_load_bdf(qmi);
  2699. if (ret < 0) {
  2700. ath11k_warn(ab, "qmi failed to download BDF:%d\n", ret);
  2701. return ret;
  2702. }
  2703. return ret;
  2704. }
  2705. static void ath11k_qmi_msg_mem_request_cb(struct qmi_handle *qmi_hdl,
  2706. struct sockaddr_qrtr *sq,
  2707. struct qmi_txn *txn,
  2708. const void *data)
  2709. {
  2710. struct ath11k_qmi *qmi = container_of(qmi_hdl, struct ath11k_qmi, handle);
  2711. struct ath11k_base *ab = qmi->ab;
  2712. const struct qmi_wlanfw_request_mem_ind_msg_v01 *msg = data;
  2713. int i, ret;
  2714. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi firmware request memory request\n");
  2715. if (msg->mem_seg_len == 0 ||
  2716. msg->mem_seg_len > ATH11K_QMI_WLANFW_MAX_NUM_MEM_SEG_V01)
  2717. ath11k_warn(ab, "invalid memory segment length: %u\n",
  2718. msg->mem_seg_len);
  2719. ab->qmi.mem_seg_count = msg->mem_seg_len;
  2720. for (i = 0; i < qmi->mem_seg_count ; i++) {
  2721. ab->qmi.target_mem[i].type = msg->mem_seg[i].type;
  2722. ab->qmi.target_mem[i].size = msg->mem_seg[i].size;
  2723. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi mem seg type %d size %d\n",
  2724. msg->mem_seg[i].type, msg->mem_seg[i].size);
  2725. }
  2726. if (ab->hw_params.fixed_mem_region ||
  2727. test_bit(ATH11K_FLAG_FIXED_MEM_RGN, &ab->dev_flags)) {
  2728. ret = ath11k_qmi_assign_target_mem_chunk(ab);
  2729. if (ret) {
  2730. ath11k_warn(ab, "failed to assign qmi target memory: %d\n",
  2731. ret);
  2732. return;
  2733. }
  2734. } else {
  2735. ret = ath11k_qmi_alloc_target_mem_chunk(ab);
  2736. if (ret) {
  2737. ath11k_warn(ab, "failed to allocate qmi target memory: %d\n",
  2738. ret);
  2739. return;
  2740. }
  2741. }
  2742. ath11k_qmi_driver_event_post(qmi, ATH11K_QMI_EVENT_REQUEST_MEM, NULL);
  2743. }
  2744. static void ath11k_qmi_msg_mem_ready_cb(struct qmi_handle *qmi_hdl,
  2745. struct sockaddr_qrtr *sq,
  2746. struct qmi_txn *txn,
  2747. const void *decoded)
  2748. {
  2749. struct ath11k_qmi *qmi = container_of(qmi_hdl, struct ath11k_qmi, handle);
  2750. struct ath11k_base *ab = qmi->ab;
  2751. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi firmware memory ready indication\n");
  2752. ath11k_qmi_driver_event_post(qmi, ATH11K_QMI_EVENT_FW_MEM_READY, NULL);
  2753. }
  2754. static void ath11k_qmi_msg_fw_ready_cb(struct qmi_handle *qmi_hdl,
  2755. struct sockaddr_qrtr *sq,
  2756. struct qmi_txn *txn,
  2757. const void *decoded)
  2758. {
  2759. struct ath11k_qmi *qmi = container_of(qmi_hdl, struct ath11k_qmi, handle);
  2760. struct ath11k_base *ab = qmi->ab;
  2761. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi firmware ready\n");
  2762. if (!ab->qmi.cal_done) {
  2763. ab->qmi.cal_done = 1;
  2764. wake_up(&ab->qmi.cold_boot_waitq);
  2765. }
  2766. ath11k_qmi_driver_event_post(qmi, ATH11K_QMI_EVENT_FW_READY, NULL);
  2767. }
  2768. static void ath11k_qmi_msg_cold_boot_cal_done_cb(struct qmi_handle *qmi_hdl,
  2769. struct sockaddr_qrtr *sq,
  2770. struct qmi_txn *txn,
  2771. const void *decoded)
  2772. {
  2773. struct ath11k_qmi *qmi = container_of(qmi_hdl,
  2774. struct ath11k_qmi, handle);
  2775. struct ath11k_base *ab = qmi->ab;
  2776. ab->qmi.cal_done = 1;
  2777. wake_up(&ab->qmi.cold_boot_waitq);
  2778. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi cold boot calibration done\n");
  2779. }
  2780. static void ath11k_qmi_msg_fw_init_done_cb(struct qmi_handle *qmi_hdl,
  2781. struct sockaddr_qrtr *sq,
  2782. struct qmi_txn *txn,
  2783. const void *decoded)
  2784. {
  2785. struct ath11k_qmi *qmi = container_of(qmi_hdl,
  2786. struct ath11k_qmi, handle);
  2787. struct ath11k_base *ab = qmi->ab;
  2788. ath11k_qmi_driver_event_post(qmi, ATH11K_QMI_EVENT_FW_INIT_DONE, NULL);
  2789. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi firmware init done\n");
  2790. }
  2791. static const struct qmi_msg_handler ath11k_qmi_msg_handlers[] = {
  2792. {
  2793. .type = QMI_INDICATION,
  2794. .msg_id = QMI_WLFW_REQUEST_MEM_IND_V01,
  2795. .ei = qmi_wlanfw_request_mem_ind_msg_v01_ei,
  2796. .decoded_size = sizeof(struct qmi_wlanfw_request_mem_ind_msg_v01),
  2797. .fn = ath11k_qmi_msg_mem_request_cb,
  2798. },
  2799. {
  2800. .type = QMI_INDICATION,
  2801. .msg_id = QMI_WLFW_FW_MEM_READY_IND_V01,
  2802. .ei = qmi_wlanfw_mem_ready_ind_msg_v01_ei,
  2803. .decoded_size = sizeof(struct qmi_wlanfw_fw_mem_ready_ind_msg_v01),
  2804. .fn = ath11k_qmi_msg_mem_ready_cb,
  2805. },
  2806. {
  2807. .type = QMI_INDICATION,
  2808. .msg_id = QMI_WLFW_FW_READY_IND_V01,
  2809. .ei = qmi_wlanfw_fw_ready_ind_msg_v01_ei,
  2810. .decoded_size = sizeof(struct qmi_wlanfw_fw_ready_ind_msg_v01),
  2811. .fn = ath11k_qmi_msg_fw_ready_cb,
  2812. },
  2813. {
  2814. .type = QMI_INDICATION,
  2815. .msg_id = QMI_WLFW_COLD_BOOT_CAL_DONE_IND_V01,
  2816. .ei = qmi_wlanfw_cold_boot_cal_done_ind_msg_v01_ei,
  2817. .decoded_size =
  2818. sizeof(struct qmi_wlanfw_fw_cold_cal_done_ind_msg_v01),
  2819. .fn = ath11k_qmi_msg_cold_boot_cal_done_cb,
  2820. },
  2821. {
  2822. .type = QMI_INDICATION,
  2823. .msg_id = QMI_WLFW_FW_INIT_DONE_IND_V01,
  2824. .ei = qmi_wlfw_fw_init_done_ind_msg_v01_ei,
  2825. .decoded_size =
  2826. sizeof(struct qmi_wlfw_fw_init_done_ind_msg_v01),
  2827. .fn = ath11k_qmi_msg_fw_init_done_cb,
  2828. },
  2829. /* end of list */
  2830. {},
  2831. };
  2832. static int ath11k_qmi_ops_new_server(struct qmi_handle *qmi_hdl,
  2833. struct qmi_service *service)
  2834. {
  2835. struct ath11k_qmi *qmi = container_of(qmi_hdl, struct ath11k_qmi, handle);
  2836. struct ath11k_base *ab = qmi->ab;
  2837. struct sockaddr_qrtr *sq = &qmi->sq;
  2838. int ret;
  2839. sq->sq_family = AF_QIPCRTR;
  2840. sq->sq_node = service->node;
  2841. sq->sq_port = service->port;
  2842. ret = kernel_connect(qmi_hdl->sock, (struct sockaddr *)sq,
  2843. sizeof(*sq), 0);
  2844. if (ret) {
  2845. ath11k_warn(ab, "failed to connect to qmi remote service: %d\n", ret);
  2846. return ret;
  2847. }
  2848. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi wifi fw qmi service connected\n");
  2849. ath11k_qmi_driver_event_post(qmi, ATH11K_QMI_EVENT_SERVER_ARRIVE, NULL);
  2850. return ret;
  2851. }
  2852. static void ath11k_qmi_ops_del_server(struct qmi_handle *qmi_hdl,
  2853. struct qmi_service *service)
  2854. {
  2855. struct ath11k_qmi *qmi = container_of(qmi_hdl, struct ath11k_qmi, handle);
  2856. struct ath11k_base *ab = qmi->ab;
  2857. ath11k_dbg(ab, ATH11K_DBG_QMI, "qmi wifi fw del server\n");
  2858. ath11k_qmi_driver_event_post(qmi, ATH11K_QMI_EVENT_SERVER_EXIT, NULL);
  2859. }
  2860. static const struct qmi_ops ath11k_qmi_ops = {
  2861. .new_server = ath11k_qmi_ops_new_server,
  2862. .del_server = ath11k_qmi_ops_del_server,
  2863. };
  2864. static void ath11k_qmi_driver_event_work(struct work_struct *work)
  2865. {
  2866. struct ath11k_qmi *qmi = container_of(work, struct ath11k_qmi,
  2867. event_work);
  2868. struct ath11k_qmi_driver_event *event;
  2869. struct ath11k_base *ab = qmi->ab;
  2870. int ret;
  2871. spin_lock(&qmi->event_lock);
  2872. while (!list_empty(&qmi->event_list)) {
  2873. event = list_first_entry(&qmi->event_list,
  2874. struct ath11k_qmi_driver_event, list);
  2875. list_del(&event->list);
  2876. spin_unlock(&qmi->event_lock);
  2877. if (test_bit(ATH11K_FLAG_UNREGISTERING, &ab->dev_flags)) {
  2878. kfree(event);
  2879. return;
  2880. }
  2881. switch (event->type) {
  2882. case ATH11K_QMI_EVENT_SERVER_ARRIVE:
  2883. ret = ath11k_qmi_event_server_arrive(qmi);
  2884. if (ret < 0)
  2885. set_bit(ATH11K_FLAG_QMI_FAIL, &ab->dev_flags);
  2886. break;
  2887. case ATH11K_QMI_EVENT_SERVER_EXIT:
  2888. set_bit(ATH11K_FLAG_CRASH_FLUSH, &ab->dev_flags);
  2889. set_bit(ATH11K_FLAG_RECOVERY, &ab->dev_flags);
  2890. break;
  2891. case ATH11K_QMI_EVENT_REQUEST_MEM:
  2892. ret = ath11k_qmi_event_mem_request(qmi);
  2893. if (ret < 0)
  2894. set_bit(ATH11K_FLAG_QMI_FAIL, &ab->dev_flags);
  2895. break;
  2896. case ATH11K_QMI_EVENT_FW_MEM_READY:
  2897. ret = ath11k_qmi_event_load_bdf(qmi);
  2898. if (ret < 0) {
  2899. set_bit(ATH11K_FLAG_QMI_FAIL, &ab->dev_flags);
  2900. break;
  2901. }
  2902. ret = ath11k_qmi_wlanfw_m3_info_send(ab);
  2903. if (ret < 0) {
  2904. ath11k_warn(ab,
  2905. "failed to send qmi m3 info req: %d\n", ret);
  2906. set_bit(ATH11K_FLAG_QMI_FAIL, &ab->dev_flags);
  2907. }
  2908. break;
  2909. case ATH11K_QMI_EVENT_FW_INIT_DONE:
  2910. clear_bit(ATH11K_FLAG_QMI_FAIL, &ab->dev_flags);
  2911. if (test_bit(ATH11K_FLAG_REGISTERED, &ab->dev_flags)) {
  2912. ath11k_hal_dump_srng_stats(ab);
  2913. queue_work(ab->workqueue, &ab->restart_work);
  2914. break;
  2915. }
  2916. if (ath11k_cold_boot_cal && ab->qmi.cal_done == 0 &&
  2917. ab->hw_params.cold_boot_calib) {
  2918. ath11k_qmi_process_coldboot_calibration(ab);
  2919. } else {
  2920. clear_bit(ATH11K_FLAG_CRASH_FLUSH,
  2921. &ab->dev_flags);
  2922. clear_bit(ATH11K_FLAG_RECOVERY, &ab->dev_flags);
  2923. ret = ath11k_core_qmi_firmware_ready(ab);
  2924. if (ret) {
  2925. set_bit(ATH11K_FLAG_QMI_FAIL, &ab->dev_flags);
  2926. break;
  2927. }
  2928. set_bit(ATH11K_FLAG_REGISTERED, &ab->dev_flags);
  2929. }
  2930. break;
  2931. case ATH11K_QMI_EVENT_FW_READY:
  2932. /* For targets requiring a FW restart upon cold
  2933. * boot completion, there is no need to process
  2934. * FW ready; such targets will receive FW init
  2935. * done message after FW restart.
  2936. */
  2937. if (ab->hw_params.cbcal_restart_fw)
  2938. break;
  2939. clear_bit(ATH11K_FLAG_CRASH_FLUSH,
  2940. &ab->dev_flags);
  2941. clear_bit(ATH11K_FLAG_RECOVERY, &ab->dev_flags);
  2942. ath11k_core_qmi_firmware_ready(ab);
  2943. set_bit(ATH11K_FLAG_REGISTERED, &ab->dev_flags);
  2944. break;
  2945. case ATH11K_QMI_EVENT_COLD_BOOT_CAL_DONE:
  2946. break;
  2947. default:
  2948. ath11k_warn(ab, "invalid qmi event type: %d", event->type);
  2949. break;
  2950. }
  2951. kfree(event);
  2952. spin_lock(&qmi->event_lock);
  2953. }
  2954. spin_unlock(&qmi->event_lock);
  2955. }
  2956. int ath11k_qmi_init_service(struct ath11k_base *ab)
  2957. {
  2958. int ret;
  2959. memset(&ab->qmi.target, 0, sizeof(struct target_info));
  2960. memset(&ab->qmi.target_mem, 0, sizeof(struct target_mem_chunk));
  2961. ab->qmi.ab = ab;
  2962. ab->qmi.target_mem_mode = ab->hw_params.fw_mem_mode;
  2963. ret = qmi_handle_init(&ab->qmi.handle, ATH11K_QMI_RESP_LEN_MAX,
  2964. &ath11k_qmi_ops, ath11k_qmi_msg_handlers);
  2965. if (ret < 0) {
  2966. ath11k_warn(ab, "failed to initialize qmi handle: %d\n", ret);
  2967. return ret;
  2968. }
  2969. ab->qmi.event_wq = alloc_workqueue("ath11k_qmi_driver_event",
  2970. WQ_UNBOUND, 1);
  2971. if (!ab->qmi.event_wq) {
  2972. ath11k_err(ab, "failed to allocate workqueue\n");
  2973. return -EFAULT;
  2974. }
  2975. INIT_LIST_HEAD(&ab->qmi.event_list);
  2976. spin_lock_init(&ab->qmi.event_lock);
  2977. INIT_WORK(&ab->qmi.event_work, ath11k_qmi_driver_event_work);
  2978. ret = qmi_add_lookup(&ab->qmi.handle, ATH11K_QMI_WLFW_SERVICE_ID_V01,
  2979. ATH11K_QMI_WLFW_SERVICE_VERS_V01,
  2980. ab->qmi.service_ins_id);
  2981. if (ret < 0) {
  2982. ath11k_warn(ab, "failed to add qmi lookup: %d\n", ret);
  2983. destroy_workqueue(ab->qmi.event_wq);
  2984. return ret;
  2985. }
  2986. return ret;
  2987. }
  2988. void ath11k_qmi_deinit_service(struct ath11k_base *ab)
  2989. {
  2990. qmi_handle_release(&ab->qmi.handle);
  2991. cancel_work_sync(&ab->qmi.event_work);
  2992. destroy_workqueue(ab->qmi.event_wq);
  2993. ath11k_qmi_m3_free(ab);
  2994. ath11k_qmi_free_target_mem_chunk(ab);
  2995. }
  2996. EXPORT_SYMBOL(ath11k_qmi_deinit_service);
  2997. void ath11k_qmi_free_resource(struct ath11k_base *ab)
  2998. {
  2999. ath11k_qmi_free_target_mem_chunk(ab);
  3000. ath11k_qmi_m3_free(ab);
  3001. }