1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131 |
- From e0bcc29f91b8ed15b0f7611b31c773ba64447358 Mon Sep 17 00:00:00 2001
- From: Chuhong Yuan <hslester96@gmail.com>
- Date: Wed, 24 Jul 2019 19:27:45 +0800
- Subject: [PATCH] mwifiex: pcie: Use dev_get_drvdata
- Instead of using to_pci_dev + pci_get_drvdata,
- use dev_get_drvdata to make code simpler.
- Signed-off-by: Chuhong Yuan <hslester96@gmail.com>
- Signed-off-by: Kalle Valo <kvalo@codeaurora.org>
- (cherry picked from commit ffa4d78cbc2644b4867b8129b3fbb5ddcdfcdba2)
- Reason for cherry-picking this commit:
- to avoid conflicts when backporting incoming commits
- Signed-off-by: Tsuchiya Yuto (kitakar5525) <kitakar@gmail.com>
- Patchset: wifi
- ---
- drivers/net/wireless/marvell/mwifiex/pcie.c | 8 ++------
- 1 file changed, 2 insertions(+), 6 deletions(-)
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie.c b/drivers/net/wireless/marvell/mwifiex/pcie.c
- index 5907b34037c2..4e655038e3f3 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie.c
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie.c
- @@ -150,10 +150,8 @@ static bool mwifiex_pcie_ok_to_access_hw(struct mwifiex_adapter *adapter)
- static int mwifiex_pcie_suspend(struct device *dev)
- {
- struct mwifiex_adapter *adapter;
- - struct pcie_service_card *card;
- - struct pci_dev *pdev = to_pci_dev(dev);
- + struct pcie_service_card *card = dev_get_drvdata(dev);
-
- - card = pci_get_drvdata(pdev);
-
- /* Might still be loading firmware */
- wait_for_completion(&card->fw_done);
- @@ -195,10 +193,8 @@ static int mwifiex_pcie_suspend(struct device *dev)
- static int mwifiex_pcie_resume(struct device *dev)
- {
- struct mwifiex_adapter *adapter;
- - struct pcie_service_card *card;
- - struct pci_dev *pdev = to_pci_dev(dev);
- + struct pcie_service_card *card = dev_get_drvdata(dev);
-
- - card = pci_get_drvdata(pdev);
-
- if (!card->adapter) {
- dev_err(dev, "adapter structure is not valid\n");
- --
- 2.31.1
- From 25d84e2b6bdc2a118717477cc0ad8524ccf07266 Mon Sep 17 00:00:00 2001
- From: Tsuchiya Yuto <kitakar@gmail.com>
- Date: Mon, 28 Sep 2020 17:46:49 +0900
- Subject: [PATCH] mwifiex: pcie: add DMI-based quirk impl for Surface devices
- This commit adds quirk implementation based on DMI matching with DMI
- table for Surface devices.
- This implementation can be used for quirks later.
- Signed-off-by: Tsuchiya Yuto <kitakar@gmail.com>
- Patchset: wifi
- ---
- drivers/net/wireless/marvell/mwifiex/Makefile | 1 +
- drivers/net/wireless/marvell/mwifiex/pcie.c | 4 +
- drivers/net/wireless/marvell/mwifiex/pcie.h | 1 +
- .../wireless/marvell/mwifiex/pcie_quirks.c | 114 ++++++++++++++++++
- .../wireless/marvell/mwifiex/pcie_quirks.h | 11 ++
- 5 files changed, 131 insertions(+)
- create mode 100644 drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- create mode 100644 drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- diff --git a/drivers/net/wireless/marvell/mwifiex/Makefile b/drivers/net/wireless/marvell/mwifiex/Makefile
- index fdfd9bf15ed4..8a1e7c5b9c6e 100644
- --- a/drivers/net/wireless/marvell/mwifiex/Makefile
- +++ b/drivers/net/wireless/marvell/mwifiex/Makefile
- @@ -49,6 +49,7 @@ mwifiex_sdio-y += sdio.o
- obj-$(CONFIG_MWIFIEX_SDIO) += mwifiex_sdio.o
-
- mwifiex_pcie-y += pcie.o
- +mwifiex_pcie-y += pcie_quirks.o
- obj-$(CONFIG_MWIFIEX_PCIE) += mwifiex_pcie.o
-
- mwifiex_usb-y += usb.o
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie.c b/drivers/net/wireless/marvell/mwifiex/pcie.c
- index 4e655038e3f3..d56c9d7f36bd 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie.c
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie.c
- @@ -27,6 +27,7 @@
- #include "wmm.h"
- #include "11n.h"
- #include "pcie.h"
- +#include "pcie_quirks.h"
-
- #define PCIE_VERSION "1.0"
- #define DRV_NAME "Marvell mwifiex PCIe"
- @@ -261,6 +262,9 @@ static int mwifiex_pcie_probe(struct pci_dev *pdev,
- return ret;
- }
-
- + /* check quirks */
- + mwifiex_initialize_quirks(card);
- +
- if (mwifiex_add_card(card, &card->fw_done, &pcie_ops,
- MWIFIEX_PCIE, &pdev->dev)) {
- pr_err("%s failed\n", __func__);
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie.h b/drivers/net/wireless/marvell/mwifiex/pcie.h
- index 72d0c01ff359..f7e968306a0c 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie.h
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie.h
- @@ -393,6 +393,7 @@ struct pcie_service_card {
- unsigned long work_flags;
-
- bool pci_reset_ongoing;
- + unsigned long quirks;
- };
-
- static inline int
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- new file mode 100644
- index 000000000000..929aee2b0a60
- --- /dev/null
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- @@ -0,0 +1,114 @@
- +// SPDX-License-Identifier: GPL-2.0
- +/*
- + * File for PCIe quirks.
- + */
- +
- +/* The low-level PCI operations will be performed in this file. Therefore,
- + * let's use dev_*() instead of mwifiex_dbg() here to avoid troubles (e.g.
- + * to avoid using mwifiex_adapter struct before init or wifi is powered
- + * down, or causes NULL ptr deref).
- + */
- +
- +#include <linux/dmi.h>
- +
- +#include "pcie_quirks.h"
- +
- +/* quirk table based on DMI matching */
- +static const struct dmi_system_id mwifiex_quirk_table[] = {
- + {
- + .ident = "Surface Pro 4",
- + .matches = {
- + DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- + DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Pro 4"),
- + },
- + .driver_data = 0,
- + },
- + {
- + .ident = "Surface Pro 5",
- + .matches = {
- + /* match for SKU here due to generic product name "Surface Pro" */
- + DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- + DMI_EXACT_MATCH(DMI_PRODUCT_SKU, "Surface_Pro_1796"),
- + },
- + .driver_data = 0,
- + },
- + {
- + .ident = "Surface Pro 5 (LTE)",
- + .matches = {
- + /* match for SKU here due to generic product name "Surface Pro" */
- + DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- + DMI_EXACT_MATCH(DMI_PRODUCT_SKU, "Surface_Pro_1807"),
- + },
- + .driver_data = 0,
- + },
- + {
- + .ident = "Surface Pro 6",
- + .matches = {
- + DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- + DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Pro 6"),
- + },
- + .driver_data = 0,
- + },
- + {
- + .ident = "Surface Book 1",
- + .matches = {
- + DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- + DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Book"),
- + },
- + .driver_data = 0,
- + },
- + {
- + .ident = "Surface Book 2",
- + .matches = {
- + DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- + DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Book 2"),
- + },
- + .driver_data = 0,
- + },
- + {
- + .ident = "Surface Laptop 1",
- + .matches = {
- + DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- + DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Laptop"),
- + },
- + .driver_data = 0,
- + },
- + {
- + .ident = "Surface Laptop 2",
- + .matches = {
- + DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- + DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Laptop 2"),
- + },
- + .driver_data = 0,
- + },
- + {
- + .ident = "Surface 3",
- + .matches = {
- + DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- + DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface 3"),
- + },
- + .driver_data = 0,
- + },
- + {
- + .ident = "Surface Pro 3",
- + .matches = {
- + DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- + DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Pro 3"),
- + },
- + .driver_data = 0,
- + },
- + {}
- +};
- +
- +void mwifiex_initialize_quirks(struct pcie_service_card *card)
- +{
- + struct pci_dev *pdev = card->dev;
- + const struct dmi_system_id *dmi_id;
- +
- + dmi_id = dmi_first_match(mwifiex_quirk_table);
- + if (dmi_id)
- + card->quirks = (uintptr_t)dmi_id->driver_data;
- +
- + if (!card->quirks)
- + dev_info(&pdev->dev, "no quirks enabled\n");
- +}
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- new file mode 100644
- index 000000000000..5326ae7e5671
- --- /dev/null
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- @@ -0,0 +1,11 @@
- +/* SPDX-License-Identifier: GPL-2.0 */
- +/*
- + * Header file for PCIe quirks.
- + */
- +
- +#include "pcie.h"
- +
- +/* quirks */
- +// quirk flags can be added here
- +
- +void mwifiex_initialize_quirks(struct pcie_service_card *card);
- --
- 2.31.1
- From 94e02e6bd4d4a8017f3d8ff6336873ef5f46e36f Mon Sep 17 00:00:00 2001
- From: Tsuchiya Yuto <kitakar@gmail.com>
- Date: Tue, 29 Sep 2020 17:25:22 +0900
- Subject: [PATCH] mwifiex: pcie: add reset_d3cold quirk for Surface gen4+
- devices
- To reset mwifiex on Surface gen4+ (Pro 4 or later gen) devices, it
- seems that putting the wifi device into D3cold is required according
- to errata.inf file on Windows installation (Windows/INF/errata.inf).
- This patch adds a function that performs power-cycle (put into D3cold
- then D0) and call the function at the end of reset_prepare().
- Note: Need to also reset the parent device (bridge) of wifi on SB1;
- it might be because the bridge of wifi always reports it's in D3hot.
- When I tried to reset only the wifi device (not touching parent), it gave
- the following error and the reset failed:
- acpi device:4b: Cannot transition to power state D0 for parent in D3hot
- mwifiex_pcie 0000:03:00.0: can't change power state from D3cold to D0 (config space inaccessible)
- Signed-off-by: Tsuchiya Yuto <kitakar@gmail.com>
- Patchset: wifi
- ---
- drivers/net/wireless/marvell/mwifiex/pcie.c | 7 ++
- .../wireless/marvell/mwifiex/pcie_quirks.c | 73 +++++++++++++++++--
- .../wireless/marvell/mwifiex/pcie_quirks.h | 3 +-
- 3 files changed, 74 insertions(+), 9 deletions(-)
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie.c b/drivers/net/wireless/marvell/mwifiex/pcie.c
- index d56c9d7f36bd..408fe05b9384 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie.c
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie.c
- @@ -380,6 +380,13 @@ static void mwifiex_pcie_reset_prepare(struct pci_dev *pdev)
- mwifiex_shutdown_sw(adapter);
- clear_bit(MWIFIEX_IFACE_WORK_DEVICE_DUMP, &card->work_flags);
- clear_bit(MWIFIEX_IFACE_WORK_CARD_RESET, &card->work_flags);
- +
- + /* For Surface gen4+ devices, we need to put wifi into D3cold right
- + * before performing FLR
- + */
- + if (card->quirks & QUIRK_FW_RST_D3COLD)
- + mwifiex_pcie_reset_d3cold_quirk(pdev);
- +
- mwifiex_dbg(adapter, INFO, "%s, successful\n", __func__);
-
- card->pci_reset_ongoing = true;
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- index 929aee2b0a60..edc739c542fe 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- @@ -21,7 +21,7 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Pro 4"),
- },
- - .driver_data = 0,
- + .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- },
- {
- .ident = "Surface Pro 5",
- @@ -30,7 +30,7 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_SKU, "Surface_Pro_1796"),
- },
- - .driver_data = 0,
- + .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- },
- {
- .ident = "Surface Pro 5 (LTE)",
- @@ -39,7 +39,7 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_SKU, "Surface_Pro_1807"),
- },
- - .driver_data = 0,
- + .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- },
- {
- .ident = "Surface Pro 6",
- @@ -47,7 +47,7 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Pro 6"),
- },
- - .driver_data = 0,
- + .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- },
- {
- .ident = "Surface Book 1",
- @@ -55,7 +55,7 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Book"),
- },
- - .driver_data = 0,
- + .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- },
- {
- .ident = "Surface Book 2",
- @@ -63,7 +63,7 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Book 2"),
- },
- - .driver_data = 0,
- + .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- },
- {
- .ident = "Surface Laptop 1",
- @@ -71,7 +71,7 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Laptop"),
- },
- - .driver_data = 0,
- + .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- },
- {
- .ident = "Surface Laptop 2",
- @@ -79,7 +79,7 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Laptop 2"),
- },
- - .driver_data = 0,
- + .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- },
- {
- .ident = "Surface 3",
- @@ -111,4 +111,61 @@ void mwifiex_initialize_quirks(struct pcie_service_card *card)
-
- if (!card->quirks)
- dev_info(&pdev->dev, "no quirks enabled\n");
- + if (card->quirks & QUIRK_FW_RST_D3COLD)
- + dev_info(&pdev->dev, "quirk reset_d3cold enabled\n");
- +}
- +
- +static void mwifiex_pcie_set_power_d3cold(struct pci_dev *pdev)
- +{
- + dev_info(&pdev->dev, "putting into D3cold...\n");
- +
- + pci_save_state(pdev);
- + if (pci_is_enabled(pdev))
- + pci_disable_device(pdev);
- + pci_set_power_state(pdev, PCI_D3cold);
- +}
- +
- +static int mwifiex_pcie_set_power_d0(struct pci_dev *pdev)
- +{
- + int ret;
- +
- + dev_info(&pdev->dev, "putting into D0...\n");
- +
- + pci_set_power_state(pdev, PCI_D0);
- + ret = pci_enable_device(pdev);
- + if (ret) {
- + dev_err(&pdev->dev, "pci_enable_device failed\n");
- + return ret;
- + }
- + pci_restore_state(pdev);
- +
- + return 0;
- +}
- +
- +int mwifiex_pcie_reset_d3cold_quirk(struct pci_dev *pdev)
- +{
- + struct pci_dev *parent_pdev = pci_upstream_bridge(pdev);
- + int ret;
- +
- + /* Power-cycle (put into D3cold then D0) */
- + dev_info(&pdev->dev, "Using reset_d3cold quirk to perform FW reset\n");
- +
- + /* We need to perform power-cycle also for bridge of wifi because
- + * on some devices (e.g. Surface Book 1), the OS for some reasons
- + * can't know the real power state of the bridge.
- + * When tried to power-cycle only wifi, the reset failed with the
- + * following dmesg log:
- + * "Cannot transition to power state D0 for parent in D3hot".
- + */
- + mwifiex_pcie_set_power_d3cold(pdev);
- + mwifiex_pcie_set_power_d3cold(parent_pdev);
- +
- + ret = mwifiex_pcie_set_power_d0(parent_pdev);
- + if (ret)
- + return ret;
- + ret = mwifiex_pcie_set_power_d0(pdev);
- + if (ret)
- + return ret;
- +
- + return 0;
- }
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- index 5326ae7e5671..8b9dcb5070d8 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- @@ -6,6 +6,7 @@
- #include "pcie.h"
-
- /* quirks */
- -// quirk flags can be added here
- +#define QUIRK_FW_RST_D3COLD BIT(0)
-
- void mwifiex_initialize_quirks(struct pcie_service_card *card);
- +int mwifiex_pcie_reset_d3cold_quirk(struct pci_dev *pdev);
- --
- 2.31.1
- From 8cbafb423098c9c19014854564167d1b3a38ddb8 Mon Sep 17 00:00:00 2001
- From: Tsuchiya Yuto <kitakar@gmail.com>
- Date: Tue, 29 Sep 2020 17:32:22 +0900
- Subject: [PATCH] mwifiex: pcie: add reset_wsid quirk for Surface 3
- This commit adds reset_wsid quirk and uses this quirk for Surface 3 on
- card reset.
- To reset mwifiex on Surface 3, it seems that calling the _DSM method
- exists in \_SB.WSID [1] device is required.
- On Surface 3, calling the _DSM method removes/re-probes the card by
- itself. So, need to place the reset function before performing FLR and
- skip performing any other reset-related works.
- Note that Surface Pro 3 also has the WSID device [2], but it seems to need
- more work. This commit only supports Surface 3 yet.
- [1] https://github.com/linux-surface/acpidumps/blob/05cba925f3a515f222acb5b3551a032ddde958fe/surface_3/dsdt.dsl#L11947-L12011
- [2] https://github.com/linux-surface/acpidumps/blob/05cba925f3a515f222acb5b3551a032ddde958fe/surface_pro_3/dsdt.dsl#L12164-L12216
- Signed-off-by: Tsuchiya Yuto <kitakar@gmail.com>
- Patchset: wifi
- ---
- drivers/net/wireless/marvell/mwifiex/pcie.c | 10 +++
- .../wireless/marvell/mwifiex/pcie_quirks.c | 77 ++++++++++++++++++-
- .../wireless/marvell/mwifiex/pcie_quirks.h | 5 ++
- 3 files changed, 91 insertions(+), 1 deletion(-)
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie.c b/drivers/net/wireless/marvell/mwifiex/pcie.c
- index 408fe05b9384..290427c98630 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie.c
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie.c
- @@ -2817,6 +2817,16 @@ static void mwifiex_pcie_card_reset_work(struct mwifiex_adapter *adapter)
- {
- struct pcie_service_card *card = adapter->card;
-
- + /* On Surface 3, reset_wsid method removes then re-probes card by
- + * itself. So, need to place it here and skip performing any other
- + * reset-related works.
- + */
- + if (card->quirks & QUIRK_FW_RST_WSID_S3) {
- + mwifiex_pcie_reset_wsid_quirk(card->dev);
- + /* skip performing any other reset-related works */
- + return;
- + }
- +
- /* We can't afford to wait here; remove() might be waiting on us. If we
- * can't grab the device lock, maybe we'll get another chance later.
- */
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- index edc739c542fe..f0a6fa0a7ae5 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- @@ -9,10 +9,21 @@
- * down, or causes NULL ptr deref).
- */
-
- +#include <linux/acpi.h>
- #include <linux/dmi.h>
-
- #include "pcie_quirks.h"
-
- +/* For reset_wsid quirk */
- +#define ACPI_WSID_PATH "\\_SB.WSID"
- +#define WSID_REV 0x0
- +#define WSID_FUNC_WIFI_PWR_OFF 0x1
- +#define WSID_FUNC_WIFI_PWR_ON 0x2
- +/* WSID _DSM UUID: "534ea3bf-fcc2-4e7a-908f-a13978f0c7ef" */
- +static const guid_t wsid_dsm_guid =
- + GUID_INIT(0x534ea3bf, 0xfcc2, 0x4e7a,
- + 0x90, 0x8f, 0xa1, 0x39, 0x78, 0xf0, 0xc7, 0xef);
- +
- /* quirk table based on DMI matching */
- static const struct dmi_system_id mwifiex_quirk_table[] = {
- {
- @@ -87,7 +98,7 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface 3"),
- },
- - .driver_data = 0,
- + .driver_data = (void *)QUIRK_FW_RST_WSID_S3,
- },
- {
- .ident = "Surface Pro 3",
- @@ -113,6 +124,9 @@ void mwifiex_initialize_quirks(struct pcie_service_card *card)
- dev_info(&pdev->dev, "no quirks enabled\n");
- if (card->quirks & QUIRK_FW_RST_D3COLD)
- dev_info(&pdev->dev, "quirk reset_d3cold enabled\n");
- + if (card->quirks & QUIRK_FW_RST_WSID_S3)
- + dev_info(&pdev->dev,
- + "quirk reset_wsid for Surface 3 enabled\n");
- }
-
- static void mwifiex_pcie_set_power_d3cold(struct pci_dev *pdev)
- @@ -169,3 +183,64 @@ int mwifiex_pcie_reset_d3cold_quirk(struct pci_dev *pdev)
-
- return 0;
- }
- +
- +int mwifiex_pcie_reset_wsid_quirk(struct pci_dev *pdev)
- +{
- + acpi_handle handle;
- + union acpi_object *obj;
- + acpi_status status;
- +
- + dev_info(&pdev->dev, "Using reset_wsid quirk to perform FW reset\n");
- +
- + status = acpi_get_handle(NULL, ACPI_WSID_PATH, &handle);
- + if (ACPI_FAILURE(status)) {
- + dev_err(&pdev->dev, "No ACPI handle for path %s\n",
- + ACPI_WSID_PATH);
- + return -ENODEV;
- + }
- +
- + if (!acpi_has_method(handle, "_DSM")) {
- + dev_err(&pdev->dev, "_DSM method not found\n");
- + return -ENODEV;
- + }
- +
- + if (!acpi_check_dsm(handle, &wsid_dsm_guid,
- + WSID_REV, WSID_FUNC_WIFI_PWR_OFF)) {
- + dev_err(&pdev->dev,
- + "_DSM method doesn't support wifi power off func\n");
- + return -ENODEV;
- + }
- +
- + if (!acpi_check_dsm(handle, &wsid_dsm_guid,
- + WSID_REV, WSID_FUNC_WIFI_PWR_ON)) {
- + dev_err(&pdev->dev,
- + "_DSM method doesn't support wifi power on func\n");
- + return -ENODEV;
- + }
- +
- + /* card will be removed immediately after this call on Surface 3 */
- + dev_info(&pdev->dev, "turning wifi off...\n");
- + obj = acpi_evaluate_dsm(handle, &wsid_dsm_guid,
- + WSID_REV, WSID_FUNC_WIFI_PWR_OFF,
- + NULL);
- + if (!obj) {
- + dev_err(&pdev->dev,
- + "device _DSM execution failed for turning wifi off\n");
- + return -EIO;
- + }
- + ACPI_FREE(obj);
- +
- + /* card will be re-probed immediately after this call on Surface 3 */
- + dev_info(&pdev->dev, "turning wifi on...\n");
- + obj = acpi_evaluate_dsm(handle, &wsid_dsm_guid,
- + WSID_REV, WSID_FUNC_WIFI_PWR_ON,
- + NULL);
- + if (!obj) {
- + dev_err(&pdev->dev,
- + "device _DSM execution failed for turning wifi on\n");
- + return -EIO;
- + }
- + ACPI_FREE(obj);
- +
- + return 0;
- +}
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- index 8b9dcb5070d8..3ef7440418e3 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- @@ -7,6 +7,11 @@
-
- /* quirks */
- #define QUIRK_FW_RST_D3COLD BIT(0)
- +/* Surface 3 and Surface Pro 3 have the same _DSM method but need to
- + * be handled differently. Currently, only S3 is supported.
- + */
- +#define QUIRK_FW_RST_WSID_S3 BIT(1)
-
- void mwifiex_initialize_quirks(struct pcie_service_card *card);
- int mwifiex_pcie_reset_d3cold_quirk(struct pci_dev *pdev);
- +int mwifiex_pcie_reset_wsid_quirk(struct pci_dev *pdev);
- --
- 2.31.1
- From e42f6a01a7df6a9a72aebd65901c7eef31407299 Mon Sep 17 00:00:00 2001
- From: Tsuchiya Yuto <kitakar@gmail.com>
- Date: Wed, 30 Sep 2020 18:08:24 +0900
- Subject: [PATCH] mwifiex: pcie: (OEMB) add quirk for Surface 3 with broken DMI
- table
- (made referring to http://git.osdn.net/view?p=android-x86/kernel.git;a=commitdiff;h=18e2e857c57633b25b3b4120f212224a108cd883)
- On some Surface 3, the DMI table gets corrupted for unknown reasons
- and breaks existing DMI matching used for device-specific quirks.
- This commit adds the (broken) DMI info for the affected Surface 3.
- On affected systems, DMI info will look like this:
- $ grep . /sys/devices/virtual/dmi/id/{bios_vendor,board_name,board_vendor,\
- chassis_vendor,product_name,sys_vendor}
- /sys/devices/virtual/dmi/id/bios_vendor:American Megatrends Inc.
- /sys/devices/virtual/dmi/id/board_name:OEMB
- /sys/devices/virtual/dmi/id/board_vendor:OEMB
- /sys/devices/virtual/dmi/id/chassis_vendor:OEMB
- /sys/devices/virtual/dmi/id/product_name:OEMB
- /sys/devices/virtual/dmi/id/sys_vendor:OEMB
- Expected:
- $ grep . /sys/devices/virtual/dmi/id/{bios_vendor,board_name,board_vendor,\
- chassis_vendor,product_name,sys_vendor}
- /sys/devices/virtual/dmi/id/bios_vendor:American Megatrends Inc.
- /sys/devices/virtual/dmi/id/board_name:Surface 3
- /sys/devices/virtual/dmi/id/board_vendor:Microsoft Corporation
- /sys/devices/virtual/dmi/id/chassis_vendor:Microsoft Corporation
- /sys/devices/virtual/dmi/id/product_name:Surface 3
- /sys/devices/virtual/dmi/id/sys_vendor:Microsoft Corporation
- Signed-off-by: Tsuchiya Yuto <kitakar@gmail.com>
- Patchset: wifi
- ---
- drivers/net/wireless/marvell/mwifiex/pcie_quirks.c | 9 +++++++++
- 1 file changed, 9 insertions(+)
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- index f0a6fa0a7ae5..34dcd84f02a6 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- @@ -100,6 +100,15 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- },
- .driver_data = (void *)QUIRK_FW_RST_WSID_S3,
- },
- + {
- + .ident = "Surface 3",
- + .matches = {
- + DMI_EXACT_MATCH(DMI_BIOS_VENDOR, "American Megatrends Inc."),
- + DMI_EXACT_MATCH(DMI_SYS_VENDOR, "OEMB"),
- + DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "OEMB"),
- + },
- + .driver_data = (void *)QUIRK_FW_RST_WSID_S3,
- + },
- {
- .ident = "Surface Pro 3",
- .matches = {
- --
- 2.31.1
- From fb4379da8742af3aac84aa947883c18678500a7b Mon Sep 17 00:00:00 2001
- From: Tsuchiya Yuto <kitakar@gmail.com>
- Date: Sun, 4 Oct 2020 00:11:49 +0900
- Subject: [PATCH] mwifiex: pcie: disable bridge_d3 for Surface gen4+
- Currently, mwifiex fw will crash after suspend on recent kernel series.
- On Windows, it seems that the root port of wifi will never enter D3 state
- (stay on D0 state). And on Linux, disabling the D3 state for the
- bridge fixes fw crashing after suspend.
- This commit disables the D3 state of root port on driver initialization
- and fixes fw crashing after suspend.
- Signed-off-by: Tsuchiya Yuto <kitakar@gmail.com>
- Patchset: wifi
- ---
- drivers/net/wireless/marvell/mwifiex/pcie.c | 7 +++++
- .../wireless/marvell/mwifiex/pcie_quirks.c | 27 +++++++++++++------
- .../wireless/marvell/mwifiex/pcie_quirks.h | 1 +
- 3 files changed, 27 insertions(+), 8 deletions(-)
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie.c b/drivers/net/wireless/marvell/mwifiex/pcie.c
- index 290427c98630..d0e002cfc295 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie.c
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie.c
- @@ -230,6 +230,7 @@ static int mwifiex_pcie_probe(struct pci_dev *pdev,
- const struct pci_device_id *ent)
- {
- struct pcie_service_card *card;
- + struct pci_dev *parent_pdev = pci_upstream_bridge(pdev);
- int ret;
-
- pr_debug("info: vendor=0x%4.04X device=0x%4.04X rev=%d\n",
- @@ -271,6 +272,12 @@ static int mwifiex_pcie_probe(struct pci_dev *pdev,
- return -1;
- }
-
- + /* disable bridge_d3 for Surface gen4+ devices to fix fw crashing
- + * after suspend
- + */
- + if (card->quirks & QUIRK_NO_BRIDGE_D3)
- + parent_pdev->bridge_d3 = false;
- +
- return 0;
- }
-
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- index 34dcd84f02a6..a2aeb2af907e 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- @@ -32,7 +32,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Pro 4"),
- },
- - .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- + .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- + QUIRK_NO_BRIDGE_D3),
- },
- {
- .ident = "Surface Pro 5",
- @@ -41,7 +42,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_SKU, "Surface_Pro_1796"),
- },
- - .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- + .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- + QUIRK_NO_BRIDGE_D3),
- },
- {
- .ident = "Surface Pro 5 (LTE)",
- @@ -50,7 +52,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_SKU, "Surface_Pro_1807"),
- },
- - .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- + .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- + QUIRK_NO_BRIDGE_D3),
- },
- {
- .ident = "Surface Pro 6",
- @@ -58,7 +61,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Pro 6"),
- },
- - .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- + .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- + QUIRK_NO_BRIDGE_D3),
- },
- {
- .ident = "Surface Book 1",
- @@ -66,7 +70,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Book"),
- },
- - .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- + .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- + QUIRK_NO_BRIDGE_D3),
- },
- {
- .ident = "Surface Book 2",
- @@ -74,7 +79,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Book 2"),
- },
- - .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- + .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- + QUIRK_NO_BRIDGE_D3),
- },
- {
- .ident = "Surface Laptop 1",
- @@ -82,7 +88,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Laptop"),
- },
- - .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- + .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- + QUIRK_NO_BRIDGE_D3),
- },
- {
- .ident = "Surface Laptop 2",
- @@ -90,7 +97,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"),
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Laptop 2"),
- },
- - .driver_data = (void *)QUIRK_FW_RST_D3COLD,
- + .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- + QUIRK_NO_BRIDGE_D3),
- },
- {
- .ident = "Surface 3",
- @@ -136,6 +144,9 @@ void mwifiex_initialize_quirks(struct pcie_service_card *card)
- if (card->quirks & QUIRK_FW_RST_WSID_S3)
- dev_info(&pdev->dev,
- "quirk reset_wsid for Surface 3 enabled\n");
- + if (card->quirks & QUIRK_NO_BRIDGE_D3)
- + dev_info(&pdev->dev,
- + "quirk no_brigde_d3 enabled\n");
- }
-
- static void mwifiex_pcie_set_power_d3cold(struct pci_dev *pdev)
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- index 3ef7440418e3..a95ebac06e13 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- @@ -11,6 +11,7 @@
- * be handled differently. Currently, only S3 is supported.
- */
- #define QUIRK_FW_RST_WSID_S3 BIT(1)
- +#define QUIRK_NO_BRIDGE_D3 BIT(2)
-
- void mwifiex_initialize_quirks(struct pcie_service_card *card);
- int mwifiex_pcie_reset_d3cold_quirk(struct pci_dev *pdev);
- --
- 2.31.1
- From a6a98568c627c55302f52af4dfd4cb29f54d20a6 Mon Sep 17 00:00:00 2001
- From: =?UTF-8?q?Jonas=20Dre=C3=9Fler?= <verdre@v0yd.nl>
- Date: Tue, 10 Nov 2020 12:49:56 +0100
- Subject: [PATCH] mwifiex: Use non-posted PCI register writes
- On the 88W8897 card it's very important the TX ring write pointer is
- updated correctly to its new value before setting the TX ready
- interrupt, otherwise the firmware appears to crash (probably because
- it's trying to DMA-read from the wrong place).
- Since PCI uses "posted writes" when writing to a register, it's not
- guaranteed that a write will happen immediately. That means the pointer
- might be outdated when setting the TX ready interrupt, leading to
- firmware crashes especially when ASPM L1 and L1 substates are enabled
- (because of the higher link latency, the write will probably take
- longer).
- So fix those firmware crashes by always forcing non-posted writes. We do
- that by simply reading back the register after writing it, just as a lot
- of other drivers do.
- There are two reproducers that are fixed with this patch:
- 1) During rx/tx traffic and with ASPM L1 substates enabled (the enabled
- substates are platform dependent), the firmware crashes and eventually a
- command timeout appears in the logs. That crash is fixed by using a
- non-posted write in mwifiex_pcie_send_data().
- 2) When sending lots of commands to the card, waking it up from sleep in
- very quick intervals, the firmware eventually crashes. That crash
- appears to be fixed by some other non-posted write included here.
- Patchset: wifi
- ---
- drivers/net/wireless/marvell/mwifiex/pcie.c | 6 ++++++
- 1 file changed, 6 insertions(+)
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie.c b/drivers/net/wireless/marvell/mwifiex/pcie.c
- index d0e002cfc295..aae276fc1155 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie.c
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie.c
- @@ -88,6 +88,12 @@ static int mwifiex_write_reg(struct mwifiex_adapter *adapter, int reg, u32 data)
-
- iowrite32(data, card->pci_mmap1 + reg);
-
- + /* Do a read-back, which makes the write non-posted, ensuring the
- + * completion before returning.
- + * The firmware of the 88W8897 card is buggy and this avoids crashes.
- + */
- + ioread32(card->pci_mmap1 + reg);
- +
- return 0;
- }
-
- --
- 2.31.1
- From 60368a2865bcd77e2310d7df94a7cb174aca0c8b Mon Sep 17 00:00:00 2001
- From: =?UTF-8?q?Jonas=20Dre=C3=9Fler?= <verdre@v0yd.nl>
- Date: Tue, 3 Nov 2020 13:28:04 +0100
- Subject: [PATCH] mwifiex: Add quirk resetting the PCI bridge on MS Surface
- devices
- The most recent firmware of the 88W8897 card reports a hardcoded LTR
- value to the system during initialization, probably as an (unsuccessful)
- attempt of the developers to fix firmware crashes. This LTR value
- prevents most of the Microsoft Surface devices from entering deep
- powersaving states (either platform C-State 10 or S0ix state), because
- the exit latency of that state would be higher than what the card can
- tolerate.
- Turns out the card works just the same (including the firmware crashes)
- no matter if that hardcoded LTR value is reported or not, so it's kind
- of useless and only prevents us from saving power.
- To get rid of those hardcoded LTR reports, it's possible to reset the
- PCI bridge device after initializing the cards firmware. I'm not exactly
- sure why that works, maybe the power management subsystem of the PCH
- resets its stored LTR values when doing a function level reset of the
- bridge device. Doing the reset once after starting the wifi firmware
- works very well, probably because the firmware only reports that LTR
- value a single time during firmware startup.
- Patchset: wifi
- ---
- drivers/net/wireless/marvell/mwifiex/pcie.c | 12 +++++++++
- .../wireless/marvell/mwifiex/pcie_quirks.c | 26 +++++++++++++------
- .../wireless/marvell/mwifiex/pcie_quirks.h | 1 +
- 3 files changed, 31 insertions(+), 8 deletions(-)
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie.c b/drivers/net/wireless/marvell/mwifiex/pcie.c
- index aae276fc1155..6b06f2a76cdc 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie.c
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie.c
- @@ -1610,9 +1610,21 @@ mwifiex_pcie_send_boot_cmd(struct mwifiex_adapter *adapter, struct sk_buff *skb)
- static int mwifiex_pcie_init_fw_port(struct mwifiex_adapter *adapter)
- {
- struct pcie_service_card *card = adapter->card;
- + struct pci_dev *pdev = card->dev;
- + struct pci_dev *parent_pdev = pci_upstream_bridge(pdev);
- const struct mwifiex_pcie_card_reg *reg = card->pcie.reg;
- int tx_wrap = card->txbd_wrptr & reg->tx_wrap_mask;
-
- + /* Trigger a function level reset of the PCI bridge device, this makes
- + * the firmware of PCIe 88W8897 cards stop reporting a fixed LTR value
- + * that prevents the system from entering package C10 and S0ix powersaving
- + * states.
- + * We need to do it here because it must happen after firmware
- + * initialization and this function is called after that is done.
- + */
- + if (card->quirks & QUIRK_DO_FLR_ON_BRIDGE)
- + pci_reset_function(parent_pdev);
- +
- /* Write the RX ring read pointer in to reg->rx_rdptr */
- if (mwifiex_write_reg(adapter, reg->rx_rdptr, card->rxbd_rdptr |
- tx_wrap)) {
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- index a2aeb2af907e..6885575826a6 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.c
- @@ -33,7 +33,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Pro 4"),
- },
- .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- - QUIRK_NO_BRIDGE_D3),
- + QUIRK_NO_BRIDGE_D3 |
- + QUIRK_DO_FLR_ON_BRIDGE),
- },
- {
- .ident = "Surface Pro 5",
- @@ -43,7 +44,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_PRODUCT_SKU, "Surface_Pro_1796"),
- },
- .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- - QUIRK_NO_BRIDGE_D3),
- + QUIRK_NO_BRIDGE_D3 |
- + QUIRK_DO_FLR_ON_BRIDGE),
- },
- {
- .ident = "Surface Pro 5 (LTE)",
- @@ -53,7 +55,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_PRODUCT_SKU, "Surface_Pro_1807"),
- },
- .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- - QUIRK_NO_BRIDGE_D3),
- + QUIRK_NO_BRIDGE_D3 |
- + QUIRK_DO_FLR_ON_BRIDGE),
- },
- {
- .ident = "Surface Pro 6",
- @@ -62,7 +65,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Pro 6"),
- },
- .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- - QUIRK_NO_BRIDGE_D3),
- + QUIRK_NO_BRIDGE_D3 |
- + QUIRK_DO_FLR_ON_BRIDGE),
- },
- {
- .ident = "Surface Book 1",
- @@ -71,7 +75,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Book"),
- },
- .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- - QUIRK_NO_BRIDGE_D3),
- + QUIRK_NO_BRIDGE_D3 |
- + QUIRK_DO_FLR_ON_BRIDGE),
- },
- {
- .ident = "Surface Book 2",
- @@ -80,7 +85,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Book 2"),
- },
- .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- - QUIRK_NO_BRIDGE_D3),
- + QUIRK_NO_BRIDGE_D3 |
- + QUIRK_DO_FLR_ON_BRIDGE),
- },
- {
- .ident = "Surface Laptop 1",
- @@ -89,7 +95,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Laptop"),
- },
- .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- - QUIRK_NO_BRIDGE_D3),
- + QUIRK_NO_BRIDGE_D3 |
- + QUIRK_DO_FLR_ON_BRIDGE),
- },
- {
- .ident = "Surface Laptop 2",
- @@ -98,7 +105,8 @@ static const struct dmi_system_id mwifiex_quirk_table[] = {
- DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Surface Laptop 2"),
- },
- .driver_data = (void *)(QUIRK_FW_RST_D3COLD |
- - QUIRK_NO_BRIDGE_D3),
- + QUIRK_NO_BRIDGE_D3 |
- + QUIRK_DO_FLR_ON_BRIDGE),
- },
- {
- .ident = "Surface 3",
- @@ -147,6 +155,8 @@ void mwifiex_initialize_quirks(struct pcie_service_card *card)
- if (card->quirks & QUIRK_NO_BRIDGE_D3)
- dev_info(&pdev->dev,
- "quirk no_brigde_d3 enabled\n");
- + if (card->quirks & QUIRK_DO_FLR_ON_BRIDGE)
- + dev_info(&pdev->dev, "quirk do_flr_on_bridge enabled\n");
- }
-
- static void mwifiex_pcie_set_power_d3cold(struct pci_dev *pdev)
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- index a95ebac06e13..4ec2ae72f632 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie_quirks.h
- @@ -12,6 +12,7 @@
- */
- #define QUIRK_FW_RST_WSID_S3 BIT(1)
- #define QUIRK_NO_BRIDGE_D3 BIT(2)
- +#define QUIRK_DO_FLR_ON_BRIDGE BIT(3)
-
- void mwifiex_initialize_quirks(struct pcie_service_card *card);
- int mwifiex_pcie_reset_d3cold_quirk(struct pci_dev *pdev);
- --
- 2.31.1
- From 83ae97bafca23ecfdc1aa6c419fc0d5cc7e03087 Mon Sep 17 00:00:00 2001
- From: =?UTF-8?q?Jonas=20Dre=C3=9Fler?= <verdre@v0yd.nl>
- Date: Sun, 28 Mar 2021 21:10:06 +0200
- Subject: [PATCH] mwifiex: Try waking the firmware until we get an interrupt
- It seems that the firmware of the 88W8897 card sometimes ignores or
- misses when we try to wake it up by reading the firmware status
- register. This leads to the firmware wakeup timeout expiring and the
- driver resetting the card because we assume the firmware has hung up or
- crashed (unfortunately that's not unlikely with this card).
- Turns out that most of the time the firmware actually didn't hang up,
- but simply "missed" our wakeup request and doesn't send us an AWAKE
- event.
- Trying again to read the firmware status register after a short timeout
- usually makes the firmware wake we up as expected, so add a small retry
- loop to mwifiex_pm_wakeup_card() that looks at the interrupt status to
- check whether the card woke up.
- The number of tries and timeout lengths for this were determined
- experimentally: The firmware usually takes about 500 us to wake up
- after we attempt to read the status register. In some cases where the
- firmware is very busy (for example while doing a bluetooth scan) it
- might even miss our requests for multiple milliseconds, which is why
- after 15 tries the waiting time gets increased to 10 ms. The maximum
- number of tries it took to wake the firmware when testing this was
- around 20, so a maximum number of 50 tries should give us plenty of
- safety margin.
- A good reproducer for this issue is letting the firmware sleep and wake
- up in very short intervals, for example by pinging an device on the
- network every 0.1 seconds.
- Patchset: wifi
- ---
- drivers/net/wireless/marvell/mwifiex/pcie.c | 29 ++++++++++++++++-----
- 1 file changed, 23 insertions(+), 6 deletions(-)
- diff --git a/drivers/net/wireless/marvell/mwifiex/pcie.c b/drivers/net/wireless/marvell/mwifiex/pcie.c
- index 6b06f2a76cdc..45dc0bfe26ba 100644
- --- a/drivers/net/wireless/marvell/mwifiex/pcie.c
- +++ b/drivers/net/wireless/marvell/mwifiex/pcie.c
- @@ -518,6 +518,7 @@ static int mwifiex_pm_wakeup_card(struct mwifiex_adapter *adapter)
- {
- struct pcie_service_card *card = adapter->card;
- const struct mwifiex_pcie_card_reg *reg = card->pcie.reg;
- + int n_tries = 0;
-
- mwifiex_dbg(adapter, EVENT,
- "event: Wakeup device...\n");
- @@ -525,12 +526,28 @@ static int mwifiex_pm_wakeup_card(struct mwifiex_adapter *adapter)
- if (reg->sleep_cookie)
- mwifiex_pcie_dev_wakeup_delay(adapter);
-
- - /* Accessing fw_status register will wakeup device */
- - if (mwifiex_write_reg(adapter, reg->fw_status, FIRMWARE_READY_PCIE)) {
- - mwifiex_dbg(adapter, ERROR,
- - "Writing fw_status register failed\n");
- - return -1;
- - }
- + /* Access the fw_status register to wake up the device.
- + * Since the 88W8897 firmware sometimes appears to ignore or miss
- + * that wakeup request, we continue trying until we receive an
- + * interrupt from the card.
- + */
- + do {
- + if (mwifiex_write_reg(adapter, reg->fw_status, FIRMWARE_READY_PCIE)) {
- + mwifiex_dbg(adapter, ERROR,
- + "Writing fw_status register failed\n");
- + return -1;
- + }
- +
- + n_tries++;
- +
- + if (n_tries <= 15)
- + usleep_range(400, 700);
- + else
- + msleep(10);
- + } while (n_tries <= 50 && READ_ONCE(adapter->int_status) == 0);
- +
- + mwifiex_dbg(adapter, EVENT,
- + "event: Tried %d times until firmware woke up\n", n_tries);
-
- if (reg->sleep_cookie) {
- mwifiex_pcie_dev_wakeup_delay(adapter);
- --
- 2.31.1
- From a357a5a68cd9e95a81f5ecb40785cb583472fa6e Mon Sep 17 00:00:00 2001
- From: =?UTF-8?q?Jonas=20Dre=C3=9Fler?= <verdre@v0yd.nl>
- Date: Thu, 25 Mar 2021 11:33:02 +0100
- Subject: [PATCH] Bluetooth: btusb: Lower passive lescan interval on Marvell
- 88W8897
- The Marvell 88W8897 combined wifi and bluetooth card (pcie+usb version)
- is used in a lot of Microsoft Surface devices, and all those devices
- suffer from very low 2.4GHz wifi connection speeds while bluetooth is
- enabled. The reason for that is that the default passive scanning
- interval for Bluetooth Low Energy devices is quite high in Linux
- (interval of 60 msec and scan window of 30 msec, see hci_core.c), and
- the Marvell chip is known for its bad bt+wifi coexisting performance.
- So decrease that passive scan interval and make the scan window shorter
- on this particular device to allow for spending more time transmitting
- wifi signals: The new scan interval is 250 msec (0x190 * 0.625 msec) and
- the new scan window is 6.25 msec (0xa * 0,625 msec).
- This change has a very large impact on the 2.4GHz wifi speeds and gets
- it up to performance comparable with the Windows driver, which seems to
- apply a similar quirk.
- The interval and window length were tested and found to work very well
- with a lot of Bluetooth Low Energy devices, including the Surface Pen, a
- Bluetooth Speaker and two modern Bluetooth headphones. All devices were
- discovered immediately after turning them on. Even lower values were
- also tested, but they introduced longer delays until devices get
- discovered.
- Patchset: wifi
- ---
- drivers/bluetooth/btusb.c | 15 +++++++++++++++
- 1 file changed, 15 insertions(+)
- diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c
- index 1b0adf5c2376..283a90928f0e 100644
- --- a/drivers/bluetooth/btusb.c
- +++ b/drivers/bluetooth/btusb.c
- @@ -69,6 +69,7 @@ static struct usb_driver btusb_driver;
- #define BTUSB_BCM2045 0x40000
- #define BTUSB_IFNUM_2 0x80000
- #define BTUSB_CW6622 0x100000
- +#define BTUSB_LOWER_LESCAN_INTERVAL 0x200000
-
- static const struct usb_device_id btusb_table[] = {
- /* Generic Bluetooth USB device */
- @@ -341,6 +342,7 @@ static const struct usb_device_id blacklist_table[] = {
- { USB_DEVICE(0x1286, 0x2044), .driver_info = BTUSB_MARVELL },
- { USB_DEVICE(0x1286, 0x2046), .driver_info = BTUSB_MARVELL },
- { USB_DEVICE(0x1286, 0x204e), .driver_info = BTUSB_MARVELL },
- + { USB_DEVICE(0x1286, 0x204c), .driver_info = BTUSB_LOWER_LESCAN_INTERVAL },
-
- /* Intel Bluetooth devices */
- { USB_DEVICE(0x8087, 0x0025), .driver_info = BTUSB_INTEL_NEW },
- @@ -3105,6 +3107,19 @@ static int btusb_probe(struct usb_interface *intf,
- if (id->driver_info & BTUSB_MARVELL)
- hdev->set_bdaddr = btusb_set_bdaddr_marvell;
-
- + /* The Marvell 88W8897 combined wifi and bluetooth card is known for
- + * very bad bt+wifi coexisting performance.
- + *
- + * Decrease the passive BT Low Energy scan interval a bit
- + * (0x0190 * 0.625 msec = 250 msec) and make the scan window shorter
- + * (0x000a * 0,625 msec = 6.25 msec). This allows for significantly
- + * higher wifi throughput while passively scanning for BT LE devices.
- + */
- + if (id->driver_info & BTUSB_LOWER_LESCAN_INTERVAL) {
- + hdev->le_scan_interval = 0x0190;
- + hdev->le_scan_window = 0x000a;
- + }
- +
- if (id->driver_info & BTUSB_SWAVE) {
- set_bit(HCI_QUIRK_FIXUP_INQUIRY_MODE, &hdev->quirks);
- set_bit(HCI_QUIRK_BROKEN_LOCAL_COMMANDS, &hdev->quirks);
- --
- 2.31.1
- From 7311eeeecd80d3cb7bae088a83e53807895f4e71 Mon Sep 17 00:00:00 2001
- From: =?UTF-8?q?Jonas=20Dre=C3=9Fler?= <verdre@v0yd.nl>
- Date: Wed, 11 Nov 2020 12:31:26 +0100
- Subject: [PATCH] mwifiex: Small cleanup for handling virtual interface type
- changes
- Handle the obvious invalid virtual interface type changes with a general
- check instead of looking at the individual change.
- For type changes from P2P_CLIENT to P2P_GO and the other way round, this
- changes the behavior slightly: We now still do nothing, but return
- -EOPNOTSUPP instead of 0. Now that behavior was incorrect before and
- still is, because type changes between these two types are actually
- possible and supported, which we'll fix in a following commit.
- Patchset: wifi
- ---
- .../net/wireless/marvell/mwifiex/cfg80211.c | 39 +++++++------------
- 1 file changed, 14 insertions(+), 25 deletions(-)
- diff --git a/drivers/net/wireless/marvell/mwifiex/cfg80211.c b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- index 650191db25cb..5badf7fef37e 100644
- --- a/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- +++ b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- @@ -1145,6 +1145,20 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
- return -EBUSY;
- }
-
- + if (type == NL80211_IFTYPE_UNSPECIFIED) {
- + mwifiex_dbg(priv->adapter, INFO,
- + "%s: no new type specified, keeping old type %d\n",
- + dev->name, curr_iftype);
- + return 0;
- + }
- +
- + if (curr_iftype == type) {
- + mwifiex_dbg(priv->adapter, INFO,
- + "%s: interface already is of type %d\n",
- + dev->name, curr_iftype);
- + return 0;
- + }
- +
- switch (curr_iftype) {
- case NL80211_IFTYPE_ADHOC:
- switch (type) {
- @@ -1164,12 +1178,6 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
- case NL80211_IFTYPE_AP:
- return mwifiex_change_vif_to_ap(dev, curr_iftype, type,
- params);
- - case NL80211_IFTYPE_UNSPECIFIED:
- - mwifiex_dbg(priv->adapter, INFO,
- - "%s: kept type as IBSS\n", dev->name);
- - /* fall through */
- - case NL80211_IFTYPE_ADHOC: /* This shouldn't happen */
- - return 0;
- default:
- mwifiex_dbg(priv->adapter, ERROR,
- "%s: changing to %d not supported\n",
- @@ -1195,12 +1203,6 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
- case NL80211_IFTYPE_AP:
- return mwifiex_change_vif_to_ap(dev, curr_iftype, type,
- params);
- - case NL80211_IFTYPE_UNSPECIFIED:
- - mwifiex_dbg(priv->adapter, INFO,
- - "%s: kept type as STA\n", dev->name);
- - /* fall through */
- - case NL80211_IFTYPE_STATION: /* This shouldn't happen */
- - return 0;
- default:
- mwifiex_dbg(priv->adapter, ERROR,
- "%s: changing to %d not supported\n",
- @@ -1218,12 +1220,6 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
- case NL80211_IFTYPE_P2P_GO:
- return mwifiex_change_vif_to_p2p(dev, curr_iftype,
- type, params);
- - case NL80211_IFTYPE_UNSPECIFIED:
- - mwifiex_dbg(priv->adapter, INFO,
- - "%s: kept type as AP\n", dev->name);
- - /* fall through */
- - case NL80211_IFTYPE_AP: /* This shouldn't happen */
- - return 0;
- default:
- mwifiex_dbg(priv->adapter, ERROR,
- "%s: changing to %d not supported\n",
- @@ -1258,13 +1254,6 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
- return -EFAULT;
- return mwifiex_change_vif_to_ap(dev, curr_iftype, type,
- params);
- - case NL80211_IFTYPE_UNSPECIFIED:
- - mwifiex_dbg(priv->adapter, INFO,
- - "%s: kept type as P2P\n", dev->name);
- - /* fall through */
- - case NL80211_IFTYPE_P2P_CLIENT:
- - case NL80211_IFTYPE_P2P_GO:
- - return 0;
- default:
- mwifiex_dbg(priv->adapter, ERROR,
- "%s: changing to %d not supported\n",
- --
- 2.31.1
- From 7165cc0cf0a28627a5cd3db631af9c9b69093b8d Mon Sep 17 00:00:00 2001
- From: =?UTF-8?q?Jonas=20Dre=C3=9Fler?= <verdre@v0yd.nl>
- Date: Wed, 11 Nov 2020 12:44:39 +0100
- Subject: [PATCH] mwifiex: Use function to check whether interface type change
- is allowed
- Instead of bailing out in the function which is supposed to do the type
- change, detect invalid changes beforehand using a generic function and
- return an error if the change is not allowed.
- Patchset: wifi
- ---
- .../net/wireless/marvell/mwifiex/cfg80211.c | 139 ++++++++++++------
- 1 file changed, 92 insertions(+), 47 deletions(-)
- diff --git a/drivers/net/wireless/marvell/mwifiex/cfg80211.c b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- index 5badf7fef37e..e73334679992 100644
- --- a/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- +++ b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- @@ -943,6 +943,76 @@ mwifiex_init_new_priv_params(struct mwifiex_private *priv,
- return 0;
- }
-
- +static bool
- +is_vif_type_change_allowed(struct mwifiex_adapter *adapter,
- + enum nl80211_iftype old_iftype,
- + enum nl80211_iftype new_iftype)
- +{
- + switch (old_iftype) {
- + case NL80211_IFTYPE_ADHOC:
- + switch (new_iftype) {
- + case NL80211_IFTYPE_STATION:
- + return true;
- + case NL80211_IFTYPE_P2P_CLIENT:
- + case NL80211_IFTYPE_P2P_GO:
- + return adapter->curr_iface_comb.p2p_intf !=
- + adapter->iface_limit.p2p_intf;
- + case NL80211_IFTYPE_AP:
- + return adapter->curr_iface_comb.uap_intf !=
- + adapter->iface_limit.uap_intf;
- + default:
- + return false;
- + }
- +
- + case NL80211_IFTYPE_STATION:
- + switch (new_iftype) {
- + case NL80211_IFTYPE_ADHOC:
- + return true;
- + case NL80211_IFTYPE_P2P_CLIENT:
- + case NL80211_IFTYPE_P2P_GO:
- + return adapter->curr_iface_comb.p2p_intf !=
- + adapter->iface_limit.p2p_intf;
- + case NL80211_IFTYPE_AP:
- + return adapter->curr_iface_comb.uap_intf !=
- + adapter->iface_limit.uap_intf;
- + default:
- + return false;
- + }
- +
- + case NL80211_IFTYPE_AP:
- + switch (new_iftype) {
- + case NL80211_IFTYPE_ADHOC:
- + case NL80211_IFTYPE_STATION:
- + return adapter->curr_iface_comb.sta_intf !=
- + adapter->iface_limit.sta_intf;
- + case NL80211_IFTYPE_P2P_CLIENT:
- + case NL80211_IFTYPE_P2P_GO:
- + return adapter->curr_iface_comb.p2p_intf !=
- + adapter->iface_limit.p2p_intf;
- + default:
- + return false;
- + }
- +
- + case NL80211_IFTYPE_P2P_CLIENT:
- + case NL80211_IFTYPE_P2P_GO:
- + switch (new_iftype) {
- + case NL80211_IFTYPE_ADHOC:
- + case NL80211_IFTYPE_STATION:
- + return true;
- + case NL80211_IFTYPE_AP:
- + return adapter->curr_iface_comb.uap_intf !=
- + adapter->iface_limit.uap_intf;
- + default:
- + return false;
- + }
- +
- + default:
- + break;
- + }
- +
- + return false;
- +}
- +
- static int
- mwifiex_change_vif_to_p2p(struct net_device *dev,
- enum nl80211_iftype curr_iftype,
- @@ -959,13 +1029,6 @@ mwifiex_change_vif_to_p2p(struct net_device *dev,
-
- adapter = priv->adapter;
-
- - if (adapter->curr_iface_comb.p2p_intf ==
- - adapter->iface_limit.p2p_intf) {
- - mwifiex_dbg(adapter, ERROR,
- - "cannot create multiple P2P ifaces\n");
- - return -1;
- - }
- -
- mwifiex_dbg(adapter, INFO,
- "%s: changing role to p2p\n", dev->name);
-
- @@ -1031,15 +1094,6 @@ mwifiex_change_vif_to_sta_adhoc(struct net_device *dev,
-
- adapter = priv->adapter;
-
- - if ((curr_iftype != NL80211_IFTYPE_P2P_CLIENT &&
- - curr_iftype != NL80211_IFTYPE_P2P_GO) &&
- - (adapter->curr_iface_comb.sta_intf ==
- - adapter->iface_limit.sta_intf)) {
- - mwifiex_dbg(adapter, ERROR,
- - "cannot create multiple station/adhoc ifaces\n");
- - return -1;
- - }
- -
- if (type == NL80211_IFTYPE_STATION)
- mwifiex_dbg(adapter, INFO,
- "%s: changing role to station\n", dev->name);
- @@ -1090,13 +1144,6 @@ mwifiex_change_vif_to_ap(struct net_device *dev,
-
- adapter = priv->adapter;
-
- - if (adapter->curr_iface_comb.uap_intf ==
- - adapter->iface_limit.uap_intf) {
- - mwifiex_dbg(adapter, ERROR,
- - "cannot create multiple AP ifaces\n");
- - return -1;
- - }
- -
- mwifiex_dbg(adapter, INFO,
- "%s: changing role to AP\n", dev->name);
-
- @@ -1159,6 +1206,13 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
- return 0;
- }
-
- + if (!is_vif_type_change_allowed(priv->adapter, curr_iftype, type)) {
- + mwifiex_dbg(priv->adapter, ERROR,
- + "%s: change from type %d to %d is not allowed\n",
- + dev->name, curr_iftype, type);
- + return -EOPNOTSUPP;
- + }
- +
- switch (curr_iftype) {
- case NL80211_IFTYPE_ADHOC:
- switch (type) {
- @@ -1179,12 +1233,9 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
- return mwifiex_change_vif_to_ap(dev, curr_iftype, type,
- params);
- default:
- - mwifiex_dbg(priv->adapter, ERROR,
- - "%s: changing to %d not supported\n",
- - dev->name, type);
- - return -EOPNOTSUPP;
- + goto errnotsupp;
- }
- - break;
- +
- case NL80211_IFTYPE_STATION:
- switch (type) {
- case NL80211_IFTYPE_ADHOC:
- @@ -1204,12 +1255,9 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
- return mwifiex_change_vif_to_ap(dev, curr_iftype, type,
- params);
- default:
- - mwifiex_dbg(priv->adapter, ERROR,
- - "%s: changing to %d not supported\n",
- - dev->name, type);
- - return -EOPNOTSUPP;
- + goto errnotsupp;
- }
- - break;
- +
- case NL80211_IFTYPE_AP:
- switch (type) {
- case NL80211_IFTYPE_ADHOC:
- @@ -1221,12 +1269,9 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
- return mwifiex_change_vif_to_p2p(dev, curr_iftype,
- type, params);
- default:
- - mwifiex_dbg(priv->adapter, ERROR,
- - "%s: changing to %d not supported\n",
- - dev->name, type);
- - return -EOPNOTSUPP;
- + goto errnotsupp;
- }
- - break;
- +
- case NL80211_IFTYPE_P2P_CLIENT:
- case NL80211_IFTYPE_P2P_GO:
- switch (type) {
- @@ -1255,21 +1300,21 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
- return mwifiex_change_vif_to_ap(dev, curr_iftype, type,
- params);
- default:
- - mwifiex_dbg(priv->adapter, ERROR,
- - "%s: changing to %d not supported\n",
- - dev->name, type);
- - return -EOPNOTSUPP;
- + goto errnotsupp;
- }
- - break;
- +
- default:
- - mwifiex_dbg(priv->adapter, ERROR,
- - "%s: unknown iftype: %d\n",
- - dev->name, dev->ieee80211_ptr->iftype);
- - return -EOPNOTSUPP;
- + goto errnotsupp;
- }
-
-
- return 0;
- +
- +errnotsupp:
- + mwifiex_dbg(priv->adapter, ERROR,
- + "unsupported interface type transition: %d to %d\n",
- + curr_iftype, type);
- + return -EOPNOTSUPP;
- }
-
- static void
- --
- 2.31.1
- From 2904d85c0deee3362a69856847c3976fffa5117e Mon Sep 17 00:00:00 2001
- From: =?UTF-8?q?Jonas=20Dre=C3=9Fler?= <verdre@v0yd.nl>
- Date: Wed, 11 Nov 2020 13:33:04 +0100
- Subject: [PATCH] mwifiex: Run SET_BSS_MODE when changing from P2P to STATION
- vif-type
- We currently handle changing from the P2P to the STATION virtual
- interface type slightly different than changing from P2P to ADHOC: When
- changing to STATION, we don't send the SET_BSS_MODE command. We do send
- that command on all other type-changes though, and it probably makes
- sense to send the command since after all we just changed our BSS_MODE.
- Looking at prior changes to this part of the code, it seems that this is
- simply a leftover from old refactorings.
- Since sending the SET_BSS_MODE command is the only difference between
- mwifiex_change_vif_to_sta_adhoc() and the current code, we can now use
- mwifiex_change_vif_to_sta_adhoc() for both switching to ADHOC and
- STATION interface type.
- This does not fix any particular bug and just "looked right", so there's
- a small chance it might be a regression.
- Patchset: wifi
- ---
- .../net/wireless/marvell/mwifiex/cfg80211.c | 22 ++++---------------
- 1 file changed, 4 insertions(+), 18 deletions(-)
- diff --git a/drivers/net/wireless/marvell/mwifiex/cfg80211.c b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- index e73334679992..99da637692cc 100644
- --- a/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- +++ b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- @@ -1274,29 +1274,15 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
-
- case NL80211_IFTYPE_P2P_CLIENT:
- case NL80211_IFTYPE_P2P_GO:
- + if (mwifiex_cfg80211_deinit_p2p(priv))
- + return -EFAULT;
- +
- switch (type) {
- - case NL80211_IFTYPE_STATION:
- - if (mwifiex_cfg80211_deinit_p2p(priv))
- - return -EFAULT;
- - priv->adapter->curr_iface_comb.p2p_intf--;
- - priv->adapter->curr_iface_comb.sta_intf++;
- - dev->ieee80211_ptr->iftype = type;
- - if (mwifiex_deinit_priv_params(priv))
- - return -1;
- - if (mwifiex_init_new_priv_params(priv, dev, type))
- - return -1;
- - if (mwifiex_sta_init_cmd(priv, false, false))
- - return -1;
- - break;
- case NL80211_IFTYPE_ADHOC:
- - if (mwifiex_cfg80211_deinit_p2p(priv))
- - return -EFAULT;
- + case NL80211_IFTYPE_STATION:
- return mwifiex_change_vif_to_sta_adhoc(dev, curr_iftype,
- type, params);
- - break;
- case NL80211_IFTYPE_AP:
- - if (mwifiex_cfg80211_deinit_p2p(priv))
- - return -EFAULT;
- return mwifiex_change_vif_to_ap(dev, curr_iftype, type,
- params);
- default:
- --
- 2.31.1
- From 5cb6a0dd8de3ce090db62521a67f3df1f75835d3 Mon Sep 17 00:00:00 2001
- From: =?UTF-8?q?Jonas=20Dre=C3=9Fler?= <verdre@v0yd.nl>
- Date: Wed, 11 Nov 2020 14:42:54 +0100
- Subject: [PATCH] mwifiex: Use helper function for counting interface types
- Use a small helper function to increment and decrement the counter of
- the interface types we currently manage. This makes the code that
- actually changes and sets up the interface type a bit less messy and
- also helps avoiding mistakes in case someone increments/decrements a
- counter wrongly.
- Patchset: wifi
- ---
- .../net/wireless/marvell/mwifiex/cfg80211.c | 110 ++++++------------
- 1 file changed, 35 insertions(+), 75 deletions(-)
- diff --git a/drivers/net/wireless/marvell/mwifiex/cfg80211.c b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- index 99da637692cc..feb3a858d8c1 100644
- --- a/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- +++ b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- @@ -1013,6 +1013,32 @@ is_vif_type_change_allowed(struct mwifiex_adapter *adapter,
- return false;
- }
-
- +static void
- +update_vif_type_counter(struct mwifiex_adapter *adapter,
- + enum nl80211_iftype iftype,
- + int change)
- +{
- + switch (iftype) {
- + case NL80211_IFTYPE_UNSPECIFIED:
- + case NL80211_IFTYPE_ADHOC:
- + case NL80211_IFTYPE_STATION:
- + adapter->curr_iface_comb.sta_intf += change;
- + break;
- + case NL80211_IFTYPE_AP:
- + adapter->curr_iface_comb.uap_intf += change;
- + break;
- + case NL80211_IFTYPE_P2P_CLIENT:
- + case NL80211_IFTYPE_P2P_GO:
- + adapter->curr_iface_comb.p2p_intf += change;
- + break;
- + default:
- + mwifiex_dbg(adapter, ERROR,
- + "%s: Unsupported iftype passed: %d\n",
- + __func__, iftype);
- + break;
- + }
- +}
- +
- static int
- mwifiex_change_vif_to_p2p(struct net_device *dev,
- enum nl80211_iftype curr_iftype,
- @@ -1060,19 +1086,8 @@ mwifiex_change_vif_to_p2p(struct net_device *dev,
- if (mwifiex_sta_init_cmd(priv, false, false))
- return -1;
-
- - switch (curr_iftype) {
- - case NL80211_IFTYPE_STATION:
- - case NL80211_IFTYPE_ADHOC:
- - adapter->curr_iface_comb.sta_intf--;
- - break;
- - case NL80211_IFTYPE_AP:
- - adapter->curr_iface_comb.uap_intf--;
- - break;
- - default:
- - break;
- - }
- -
- - adapter->curr_iface_comb.p2p_intf++;
- + update_vif_type_counter(adapter, curr_iftype, -1);
- + update_vif_type_counter(adapter, type, +1);
- dev->ieee80211_ptr->iftype = type;
-
- return 0;
- @@ -1111,20 +1126,10 @@ mwifiex_change_vif_to_sta_adhoc(struct net_device *dev,
- if (mwifiex_sta_init_cmd(priv, false, false))
- return -1;
-
- - switch (curr_iftype) {
- - case NL80211_IFTYPE_P2P_CLIENT:
- - case NL80211_IFTYPE_P2P_GO:
- - adapter->curr_iface_comb.p2p_intf--;
- - break;
- - case NL80211_IFTYPE_AP:
- - adapter->curr_iface_comb.uap_intf--;
- - break;
- - default:
- - break;
- - }
- -
- - adapter->curr_iface_comb.sta_intf++;
- + update_vif_type_counter(adapter, curr_iftype, -1);
- + update_vif_type_counter(adapter, type, +1);
- dev->ieee80211_ptr->iftype = type;
- +
- return 0;
- }
-
- @@ -1157,20 +1162,8 @@ mwifiex_change_vif_to_ap(struct net_device *dev,
- if (mwifiex_sta_init_cmd(priv, false, false))
- return -1;
-
- - switch (curr_iftype) {
- - case NL80211_IFTYPE_P2P_CLIENT:
- - case NL80211_IFTYPE_P2P_GO:
- - adapter->curr_iface_comb.p2p_intf--;
- - break;
- - case NL80211_IFTYPE_STATION:
- - case NL80211_IFTYPE_ADHOC:
- - adapter->curr_iface_comb.sta_intf--;
- - break;
- - default:
- - break;
- - }
- -
- - adapter->curr_iface_comb.uap_intf++;
- + update_vif_type_counter(adapter, curr_iftype, -1);
- + update_vif_type_counter(adapter, type, +1);
- dev->ieee80211_ptr->iftype = type;
- return 0;
- }
- @@ -3091,23 +3084,7 @@ struct wireless_dev *mwifiex_add_virtual_intf(struct wiphy *wiphy,
- mwifiex_dev_debugfs_init(priv);
- #endif
-
- - switch (type) {
- - case NL80211_IFTYPE_UNSPECIFIED:
- - case NL80211_IFTYPE_STATION:
- - case NL80211_IFTYPE_ADHOC:
- - adapter->curr_iface_comb.sta_intf++;
- - break;
- - case NL80211_IFTYPE_AP:
- - adapter->curr_iface_comb.uap_intf++;
- - break;
- - case NL80211_IFTYPE_P2P_CLIENT:
- - adapter->curr_iface_comb.p2p_intf++;
- - break;
- - default:
- - /* This should be dead code; checked above */
- - mwifiex_dbg(adapter, ERROR, "type not supported\n");
- - return ERR_PTR(-EINVAL);
- - }
- + update_vif_type_counter(adapter, type, +1);
-
- return &priv->wdev;
-
- @@ -3173,24 +3150,7 @@ int mwifiex_del_virtual_intf(struct wiphy *wiphy, struct wireless_dev *wdev)
- /* Clear the priv in adapter */
- priv->netdev = NULL;
-
- - switch (priv->bss_mode) {
- - case NL80211_IFTYPE_UNSPECIFIED:
- - case NL80211_IFTYPE_STATION:
- - case NL80211_IFTYPE_ADHOC:
- - adapter->curr_iface_comb.sta_intf--;
- - break;
- - case NL80211_IFTYPE_AP:
- - adapter->curr_iface_comb.uap_intf--;
- - break;
- - case NL80211_IFTYPE_P2P_CLIENT:
- - case NL80211_IFTYPE_P2P_GO:
- - adapter->curr_iface_comb.p2p_intf--;
- - break;
- - default:
- - mwifiex_dbg(adapter, ERROR,
- - "del_virtual_intf: type not supported\n");
- - break;
- - }
- + update_vif_type_counter(adapter, priv->bss_mode, -1);
-
- priv->bss_mode = NL80211_IFTYPE_UNSPECIFIED;
-
- --
- 2.31.1
- From 70ef3297dc65f00ad9315ed7c2896cb0f7ee9cb5 Mon Sep 17 00:00:00 2001
- From: =?UTF-8?q?Jonas=20Dre=C3=9Fler?= <verdre@v0yd.nl>
- Date: Fri, 26 Mar 2021 15:56:58 +0100
- Subject: [PATCH] mwifiex: Update virtual interface counters right after
- setting bss_type
- In mwifiex_init_new_priv_params() we update our private driver state to
- reflect the currently selected virtual interface type. Most notably we
- set the bss_mode to the mode we're going to put the firmware in.
- Now after we updated the driver state we actually start talking to the
- firmware and instruct it to set up the new mode. Those commands can and
- will sometimes fail, in which case we return with an error from
- mwifiex_change_vif_to_*. We currently update our virtual interface type
- counters after this return, which means the code is never reached when a
- firmware error happens and we never update the counters. Since we have
- updated our bss_mode earlier though, the counters now no longer reflect
- the actual state of the driver.
- This will break things on the next virtual interface change, because the
- virtual interface type we're switching away from didn't get its counter
- incremented, and we end up decrementing a 0-counter.
- To fix this, simply update the virtual interface type counters right
- after updating our driver structures, so that they are always in sync.
- Patchset: wifi
- ---
- .../net/wireless/marvell/mwifiex/cfg80211.c | 25 +++++++++++--------
- 1 file changed, 14 insertions(+), 11 deletions(-)
- diff --git a/drivers/net/wireless/marvell/mwifiex/cfg80211.c b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- index feb3a858d8c1..54d9e789aa14 100644
- --- a/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- +++ b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- @@ -1063,6 +1063,10 @@ mwifiex_change_vif_to_p2p(struct net_device *dev,
- if (mwifiex_init_new_priv_params(priv, dev, type))
- return -1;
-
- + update_vif_type_counter(adapter, curr_iftype, -1);
- + update_vif_type_counter(adapter, type, +1);
- + dev->ieee80211_ptr->iftype = type;
- +
- switch (type) {
- case NL80211_IFTYPE_P2P_CLIENT:
- if (mwifiex_cfg80211_init_p2p_client(priv))
- @@ -1086,10 +1090,6 @@ mwifiex_change_vif_to_p2p(struct net_device *dev,
- if (mwifiex_sta_init_cmd(priv, false, false))
- return -1;
-
- - update_vif_type_counter(adapter, curr_iftype, -1);
- - update_vif_type_counter(adapter, type, +1);
- - dev->ieee80211_ptr->iftype = type;
- -
- return 0;
- }
-
- @@ -1120,16 +1120,17 @@ mwifiex_change_vif_to_sta_adhoc(struct net_device *dev,
- return -1;
- if (mwifiex_init_new_priv_params(priv, dev, type))
- return -1;
- +
- + update_vif_type_counter(adapter, curr_iftype, -1);
- + update_vif_type_counter(adapter, type, +1);
- + dev->ieee80211_ptr->iftype = type;
- +
- if (mwifiex_send_cmd(priv, HostCmd_CMD_SET_BSS_MODE,
- HostCmd_ACT_GEN_SET, 0, NULL, true))
- return -1;
- if (mwifiex_sta_init_cmd(priv, false, false))
- return -1;
-
- - update_vif_type_counter(adapter, curr_iftype, -1);
- - update_vif_type_counter(adapter, type, +1);
- - dev->ieee80211_ptr->iftype = type;
- -
- return 0;
- }
-
- @@ -1156,15 +1157,17 @@ mwifiex_change_vif_to_ap(struct net_device *dev,
- return -1;
- if (mwifiex_init_new_priv_params(priv, dev, type))
- return -1;
- +
- + update_vif_type_counter(adapter, curr_iftype, -1);
- + update_vif_type_counter(adapter, type, +1);
- + dev->ieee80211_ptr->iftype = type;
- +
- if (mwifiex_send_cmd(priv, HostCmd_CMD_SET_BSS_MODE,
- HostCmd_ACT_GEN_SET, 0, NULL, true))
- return -1;
- if (mwifiex_sta_init_cmd(priv, false, false))
- return -1;
-
- - update_vif_type_counter(adapter, curr_iftype, -1);
- - update_vif_type_counter(adapter, type, +1);
- - dev->ieee80211_ptr->iftype = type;
- return 0;
- }
- /*
- --
- 2.31.1
- From 0d2adbf9a64919cb5d0d23878e2ab904ba62d8ad Mon Sep 17 00:00:00 2001
- From: =?UTF-8?q?Jonas=20Dre=C3=9Fler?= <verdre@v0yd.nl>
- Date: Wed, 11 Nov 2020 13:42:40 +0100
- Subject: [PATCH] mwifiex: Allow switching interface type from P2P_CLIENT to
- P2P_GO
- It's possible to change virtual interface type between P2P_CLIENT and
- P2P_GO, the card supports that just fine, and it happens for example
- when using miracast with the miraclecast software.
- So allow type changes between P2P_CLIENT and P2P_GO and simply call into
- mwifiex_change_vif_to_p2p(), which handles this just fine. We have to
- call mwifiex_cfg80211_deinit_p2p() before though to make sure the old
- p2p mode is properly uninitialized.
- Patchset: wifi
- ---
- .../net/wireless/marvell/mwifiex/cfg80211.c | 36 +++++++++++++++++++
- 1 file changed, 36 insertions(+)
- diff --git a/drivers/net/wireless/marvell/mwifiex/cfg80211.c b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- index 54d9e789aa14..ec5ed00b4b89 100644
- --- a/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- +++ b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- @@ -994,11 +994,26 @@ is_vif_type_change_allowed(struct mwifiex_adapter *adapter,
- }
-
- case NL80211_IFTYPE_P2P_CLIENT:
- + switch (new_iftype) {
- + case NL80211_IFTYPE_ADHOC:
- + case NL80211_IFTYPE_STATION:
- + return true;
- + case NL80211_IFTYPE_P2P_GO:
- + return true;
- + case NL80211_IFTYPE_AP:
- + return adapter->curr_iface_comb.uap_intf !=
- + adapter->iface_limit.uap_intf;
- + default:
- + return false;
- + }
- +
- case NL80211_IFTYPE_P2P_GO:
- switch (new_iftype) {
- case NL80211_IFTYPE_ADHOC:
- case NL80211_IFTYPE_STATION:
- return true;
- + case NL80211_IFTYPE_P2P_CLIENT:
- + return true;
- case NL80211_IFTYPE_AP:
- return adapter->curr_iface_comb.uap_intf !=
- adapter->iface_limit.uap_intf;
- @@ -1269,6 +1284,24 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
- }
-
- case NL80211_IFTYPE_P2P_CLIENT:
- + if (mwifiex_cfg80211_deinit_p2p(priv))
- + return -EFAULT;
- +
- + switch (type) {
- + case NL80211_IFTYPE_ADHOC:
- + case NL80211_IFTYPE_STATION:
- + return mwifiex_change_vif_to_sta_adhoc(dev, curr_iftype,
- + type, params);
- + case NL80211_IFTYPE_P2P_GO:
- + return mwifiex_change_vif_to_p2p(dev, curr_iftype,
- + type, params);
- + case NL80211_IFTYPE_AP:
- + return mwifiex_change_vif_to_ap(dev, curr_iftype, type,
- + params);
- + default:
- + goto errnotsupp;
- + }
- +
- case NL80211_IFTYPE_P2P_GO:
- if (mwifiex_cfg80211_deinit_p2p(priv))
- return -EFAULT;
- @@ -1278,6 +1311,9 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
- case NL80211_IFTYPE_STATION:
- return mwifiex_change_vif_to_sta_adhoc(dev, curr_iftype,
- type, params);
- + case NL80211_IFTYPE_P2P_CLIENT:
- + return mwifiex_change_vif_to_p2p(dev, curr_iftype,
- + type, params);
- case NL80211_IFTYPE_AP:
- return mwifiex_change_vif_to_ap(dev, curr_iftype, type,
- params);
- --
- 2.31.1
- From ab87318470957c4883f0558866d455ec892e3a8c Mon Sep 17 00:00:00 2001
- From: =?UTF-8?q?Jonas=20Dre=C3=9Fler?= <verdre@v0yd.nl>
- Date: Fri, 26 Mar 2021 15:31:08 +0100
- Subject: [PATCH] mwifiex: Handle interface type changes from AP to STATION
- Looks like this case was simply overseen, so handle it, too.
- Patchset: wifi
- ---
- drivers/net/wireless/marvell/mwifiex/cfg80211.c | 1 +
- 1 file changed, 1 insertion(+)
- diff --git a/drivers/net/wireless/marvell/mwifiex/cfg80211.c b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- index ec5ed00b4b89..0fc554abfea3 100644
- --- a/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- +++ b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- @@ -1272,6 +1272,7 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
- case NL80211_IFTYPE_AP:
- switch (type) {
- case NL80211_IFTYPE_ADHOC:
- + case NL80211_IFTYPE_STATION:
- return mwifiex_change_vif_to_sta_adhoc(dev, curr_iftype,
- type, params);
- break;
- --
- 2.31.1
- From 43ae7dbec10ec94c1643bce67310511a618c870b Mon Sep 17 00:00:00 2001
- From: =?UTF-8?q?Jonas=20Dre=C3=9Fler?= <verdre@v0yd.nl>
- Date: Fri, 26 Mar 2021 15:32:16 +0100
- Subject: [PATCH] mwifiex: Properly initialize private structure on interface
- type changes
- When creating a new virtual interface in mwifiex_add_virtual_intf(), we
- update our internal driver states like bss_type, bss_priority, bss_role
- and bss_mode to reflect the mode the firmware will be set to.
- When switching virtual interface mode using
- mwifiex_init_new_priv_params() though, we currently only update bss_mode
- and bss_role. In order for the interface mode switch to actually work,
- we also need to update bss_type to its proper value, so do that.
- This fixes a crash of the firmware (because the driver tries to execute
- commands that are invalid in AP mode) when switching from station mode
- to AP mode.
- Patchset: wifi
- ---
- drivers/net/wireless/marvell/mwifiex/cfg80211.c | 10 +++++++---
- 1 file changed, 7 insertions(+), 3 deletions(-)
- diff --git a/drivers/net/wireless/marvell/mwifiex/cfg80211.c b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- index 0fc554abfea3..7c6d31eb058c 100644
- --- a/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- +++ b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- @@ -912,16 +912,20 @@ mwifiex_init_new_priv_params(struct mwifiex_private *priv,
- switch (type) {
- case NL80211_IFTYPE_STATION:
- case NL80211_IFTYPE_ADHOC:
- - priv->bss_role = MWIFIEX_BSS_ROLE_STA;
- + priv->bss_role = MWIFIEX_BSS_ROLE_STA;
- + priv->bss_type = MWIFIEX_BSS_TYPE_STA;
- break;
- case NL80211_IFTYPE_P2P_CLIENT:
- - priv->bss_role = MWIFIEX_BSS_ROLE_STA;
- + priv->bss_role = MWIFIEX_BSS_ROLE_STA;
- + priv->bss_type = MWIFIEX_BSS_TYPE_P2P;
- break;
- case NL80211_IFTYPE_P2P_GO:
- - priv->bss_role = MWIFIEX_BSS_ROLE_UAP;
- + priv->bss_role = MWIFIEX_BSS_ROLE_UAP;
- + priv->bss_type = MWIFIEX_BSS_TYPE_P2P;
- break;
- case NL80211_IFTYPE_AP:
- priv->bss_role = MWIFIEX_BSS_ROLE_UAP;
- + priv->bss_type = MWIFIEX_BSS_TYPE_UAP;
- break;
- default:
- mwifiex_dbg(adapter, ERROR,
- --
- 2.31.1
- From d0a26bd105768e953d343b6ee50cca59f4062962 Mon Sep 17 00:00:00 2001
- From: =?UTF-8?q?Jonas=20Dre=C3=9Fler?= <verdre@v0yd.nl>
- Date: Sat, 27 Mar 2021 12:19:14 +0100
- Subject: [PATCH] mwifiex: Fix copy-paste mistake when creating virtual
- interface
- The BSS priority here for a new P2P_CLIENT device was accidentally set
- to an enum that's certainly not meant for this. Since
- MWIFIEX_BSS_ROLE_STA is 0 anyway, we can just set the bss_priority to 0
- instead here.
- Patchset: wifi
- ---
- drivers/net/wireless/marvell/mwifiex/cfg80211.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
- diff --git a/drivers/net/wireless/marvell/mwifiex/cfg80211.c b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- index 7c6d31eb058c..16a94f06a518 100644
- --- a/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- +++ b/drivers/net/wireless/marvell/mwifiex/cfg80211.c
- @@ -3017,7 +3017,7 @@ struct wireless_dev *mwifiex_add_virtual_intf(struct wiphy *wiphy,
- priv->bss_type = MWIFIEX_BSS_TYPE_P2P;
-
- priv->frame_type = MWIFIEX_DATA_FRAME_TYPE_ETH_II;
- - priv->bss_priority = MWIFIEX_BSS_ROLE_STA;
- + priv->bss_priority = 0;
- priv->bss_role = MWIFIEX_BSS_ROLE_STA;
- priv->bss_started = 0;
-
- --
- 2.31.1
|