Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 65f7ea44 authored by Maya Erez's avatar Maya Erez
Browse files

wil6210: add support for spi slave reset



As SPI core is not being reset in SW reset, FW needs to disable it
before the reset, to ensure proper SPI re-initialization after the
reset.
Add a new WMI command to notify FW to reset SPI slave before
performing SW reset.

Change-Id: I12d23560dbb28daa64cbebec155847fe32625b63
Signed-off-by: default avatarMaya Erez <merez@codeaurora.org>
parent 580b80dd
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -1700,6 +1700,7 @@ int wil_reset(struct wil6210_priv *wil, bool load_fw)
	if (support_sensing_over_spi) {
		wil_dbg_misc(wil, "notify FW to enable SPI for sensing\n");
		wil_s(wil, RGF_USER_USAGE_6, BIT_SPI_SENSING_SUPPORT);
		wmi_reset_spi_slave(wil);
	}

	if (wil->platform_ops.notify) {
+1 −0
Original line number Diff line number Diff line
@@ -1485,5 +1485,6 @@ int wmi_addba_rx_resp_edma(struct wil6210_priv *wil, u8 mid, u8 cid,
			   u16 agg_wsize, u16 timeout);

void update_supported_bands(struct wil6210_priv *wil);
int wmi_reset_spi_slave(struct wil6210_priv *wil);

#endif /* __WIL6210_H__ */
+50 −3
Original line number Diff line number Diff line
@@ -33,6 +33,7 @@ MODULE_PARM_DESC(led_id,
#define WIL_WAIT_FOR_SUSPEND_RESUME_COMP 200
#define WIL_WMI_CALL_GENERAL_TO_MS 100
#define WIL_WMI_PCP_STOP_TO_MS 5000
#define WIL_WMI_SPI_SLAVE_RESET_TO_MS 500

/**
 * WMI event receiving - theory of operations
@@ -477,6 +478,8 @@ static const char *cmdid2name(u16 cmdid)
		return "WMI_UPDATE_FT_IES_CMD";
	case WMI_SET_VR_PROFILE_CMDID:
		return "WMI_SET_VR_PROFILE_CMD";
	case WMI_RESET_SPI_SLAVE_CMDID:
		return "WMI_RESET_SPI_SLAVE_CMD";
	default:
		return "Untracked CMD";
	}
@@ -623,6 +626,8 @@ static const char *eventid2name(u16 eventid)
		return "WMI_FT_REASSOC_STATUS_EVENT";
	case WMI_SET_VR_PROFILE_EVENTID:
		return "WMI_SET_VR_PROFILE_EVENT";
	case WMI_RESET_SPI_SLAVE_EVENTID:
		return "WMI_RESET_SPI_SLAVE_EVENT";
	default:
		return "Untracked EVENT";
	}
@@ -2060,8 +2065,9 @@ void wmi_recv_cmd(struct wil6210_priv *wil)
		    n - num_immed_reply, num_immed_reply);
}

int wmi_call(struct wil6210_priv *wil, u16 cmdid, u8 mid, void *buf, u16 len,
	     u16 reply_id, void *reply, u16 reply_size, int to_msec)
static int __wmi_call(struct wil6210_priv *wil, u16 cmdid, u8 mid, void *buf,
		      u16 len, u16 reply_id, void *reply, u16 reply_size,
		      int to_msec, bool force_send)
{
	int rc;
	unsigned long remain;
@@ -2077,7 +2083,7 @@ int wmi_call(struct wil6210_priv *wil, u16 cmdid, u8 mid, void *buf, u16 len,
	reinit_completion(&wil->wmi_call);
	spin_unlock_irqrestore(&wil->wmi_ev_lock, flags);

	rc = __wmi_send(wil, cmdid, mid, buf, len, false);
	rc = __wmi_send(wil, cmdid, mid, buf, len, force_send);
	if (rc)
		goto out;

@@ -2107,6 +2113,13 @@ int wmi_call(struct wil6210_priv *wil, u16 cmdid, u8 mid, void *buf, u16 len,
	return rc;
}

int wmi_call(struct wil6210_priv *wil, u16 cmdid, u8 mid, void *buf, u16 len,
	     u16 reply_id, void *reply, u16 reply_size, int to_msec)
{
	return __wmi_call(wil, cmdid, mid, buf, len, reply_id, reply,
			  reply_size, to_msec, false);
}

int wmi_echo(struct wil6210_priv *wil)
{
	struct wil6210_vif *vif = ndev_to_vif(wil->main_ndev);
@@ -4152,3 +4165,37 @@ int wmi_set_vr_profile(struct wil6210_priv *wil, u8 profile)

	return 0;
}

int wmi_reset_spi_slave(struct wil6210_priv *wil)
{
	struct net_device *ndev = wil->main_ndev;
	struct wil6210_vif *vif = ndev_to_vif(ndev);
	struct wmi_reset_spi_slave_cmd cmd = { {0} };
	struct {
		struct wmi_cmd_hdr wmi;
		struct wmi_reset_spi_slave_event evt;
	} __packed reply = {
		.evt = {.status = WMI_FW_STATUS_FAILURE},
	};
	int rc;

	if (!(ndev->flags & IFF_UP))
		return 0;

	/* Force sending SPI slave reset to guarantee safe SPI reset */
	rc = __wmi_call(wil, WMI_RESET_SPI_SLAVE_CMDID, vif->mid, &cmd,
			sizeof(cmd), WMI_RESET_SPI_SLAVE_EVENTID, &reply,
			sizeof(reply), WIL_WMI_SPI_SLAVE_RESET_TO_MS, true);
	if (rc) {
		wil_err(wil, "WMI_RESET_SPI_SLAVE_CMDID failed, rc %d\n", rc);
		return rc;
	}

	if (reply.evt.status != WMI_FW_STATUS_SUCCESS) {
		wil_err(wil, "spi slave reset failed, status %d\n",
			reply.evt.status);
		return -EINVAL;
	}

	return 0;
}
+14 −0
Original line number Diff line number Diff line
@@ -136,6 +136,7 @@ enum wmi_command_id {
	WMI_RADAR_SET_MODE_CMDID			= 0x103,
	WMI_RADAR_CONTROL_CMDID				= 0x104,
	WMI_RADAR_PCI_CONTROL_CMDID			= 0x105,
	WMI_RESET_SPI_SLAVE_CMDID			= 0x106,
	WMI_MEM_READ_CMDID				= 0x800,
	WMI_MEM_WR_CMDID				= 0x801,
	WMI_ECHO_CMDID					= 0x803,
@@ -686,6 +687,11 @@ struct wmi_radar_pci_control_cmd {
	__le32 reserved;
} __packed;

/* WMI_RESET_SPI_SLAVE_CMDID */
struct wmi_reset_spi_slave_cmd {
	u8 reserved[4];
} __packed;

/* WMI_RF_MGMT_CMDID */
enum wmi_rf_mgmt_type {
	WMI_RF_MGMT_W_DISABLE	= 0x00,
@@ -1733,6 +1739,13 @@ struct wmi_radar_pci_control_event {
	u8 reserved[3];
} __packed;

/* WMI_RESET_SPI_SLAVE_EVENTID */
struct wmi_reset_spi_slave_event {
	/* wmi_fw_status */
	u8 status;
	u8 reserved[3];
} __packed;

/* WMI_SET_LONG_RANGE_CONFIG_CMDID */
struct wmi_set_long_range_config_cmd {
	__le32 reserved;
@@ -1971,6 +1984,7 @@ enum wmi_event_id {
	WMI_RADAR_SET_MODE_EVENTID			= 0x1103,
	WMI_RADAR_CONTROL_EVENTID			= 0x1104,
	WMI_RADAR_PCI_CONTROL_EVENTID			= 0x1105,
	WMI_RESET_SPI_SLAVE_EVENTID			= 0x1106,
	WMI_RD_MEM_RSP_EVENTID				= 0x1800,
	WMI_FW_READY_EVENTID				= 0x1801,
	WMI_EXIT_FAST_MEM_ACC_MODE_EVENTID		= 0x200,