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

Commit 4280529b authored by qctecmdr's avatar qctecmdr Committed by Gerrit - the friendly Code Review server
Browse files

Merge "msm: pcie: disable PCIe CLKREQ override during PCIe DRV resume"

parents 61779979 64c677c9
Loading
Loading
Loading
Loading
+44 −10
Original line number Diff line number Diff line
@@ -35,6 +35,7 @@
#include <linux/slab.h>
#include <linux/types.h>
#include <linux/uaccess.h>
#include <soc/qcom/subsystem_notif.h>

#include "../pci.h"

@@ -66,6 +67,10 @@
#define PCIE20_PARF_L1SUB_AHB_CLK_MAX_TIMER (0x180)
#define PCIE20_PARF_DEBUG_INT_EN (0x190)

#define PCIE20_PARF_CLKREQ_OVERRIDE (0x2b0)
#define PCIE20_PARF_CLKREQ_IN_VALUE (BIT(3))
#define PCIE20_PARF_CLKREQ_IN_ENABLE (BIT(1))

#define PCIE20_ELBI_SYS_CTRL (0x04)
#define PCIE20_ELBI_SYS_STTS (0x08)

@@ -6531,36 +6536,45 @@ static int msm_pcie_drv_rpmsg_probe(struct rpmsg_device *rpdev)
	return 0;
}

static void msm_pcie_drv_rpmsg_remove(struct rpmsg_device *rpdev)
static void msm_pcie_drv_notify_client(struct pcie_drv_sta *pcie_drv,
					enum msm_pcie_event event)
{
	struct pcie_drv_sta *pcie_drv = dev_get_drvdata(&rpdev->dev);
	struct msm_pcie_dev_t *pcie_dev = pcie_drv->msm_pcie_dev;
	int i;

	pcie_drv->rpdev = NULL;
	flush_work(&pcie_drv->drv_connect);

	for (i = 0; i < MAX_RC_NUM; i++, pcie_dev++) {
		struct msm_pcie_drv_info *drv_info = pcie_dev->drv_info;
		struct msm_pcie_register_event *event_reg =
			pcie_dev->event_reg;

		PCIE_DBG(pcie_dev, "PCIe: RC%d: event %d received\n",
			pcie_dev->rc_idx, event);

		/* does not support DRV or has not been probed yet */
		if (!drv_info)
			continue;

		if (!event_reg ||
		    !(event_reg->events & MSM_PCIE_EVENT_DRV_DISCONNECT))
		if (!event_reg || !(event_reg->events & event))
			continue;

		if (drv_info->ep_connected) {
			msm_pcie_notify_client(pcie_dev,
					       MSM_PCIE_EVENT_DRV_DISCONNECT);
			msm_pcie_notify_client(pcie_dev, event);
			if (event & MSM_PCIE_EVENT_DRV_DISCONNECT)
				drv_info->ep_connected = false;
		}
	}
}

static void msm_pcie_drv_rpmsg_remove(struct rpmsg_device *rpdev)
{
	struct pcie_drv_sta *pcie_drv = dev_get_drvdata(&rpdev->dev);

	pcie_drv->rpdev = NULL;
	flush_work(&pcie_drv->drv_connect);

	msm_pcie_drv_notify_client(pcie_drv, MSM_PCIE_EVENT_DRV_DISCONNECT);
}

static int msm_pcie_drv_rpmsg_cb(struct rpmsg_device *rpdev, void *data,
				int len, void *priv, u32 src)
{
@@ -6667,6 +6681,15 @@ static struct rpmsg_driver msm_pcie_drv_rpmsg_driver = {
	},
};

static void msm_pcie_early_notifier(void *data)
{
	struct pcie_drv_sta *pcie_drv = data;

	pcie_drv->rpdev = NULL;

	msm_pcie_drv_notify_client(pcie_drv, MSM_PCIE_EVENT_WAKEUP);
};

static void msm_pcie_drv_connect_worker(struct work_struct *work)
{
	struct pcie_drv_sta *pcie_drv = container_of(work, struct pcie_drv_sta,
@@ -6699,6 +6722,9 @@ static void msm_pcie_drv_connect_worker(struct work_struct *work)
				       MSM_PCIE_EVENT_DRV_CONNECT);
		drv_info->ep_connected = true;
	}

	subsys_register_early_notifier("adsp", PCIE_DRV_LAYER_NOTIF,
				msm_pcie_early_notifier, pcie_drv);
}

static int __init pcie_init(void)
@@ -7139,6 +7165,14 @@ static int msm_pcie_drv_resume(struct msm_pcie_dev_t *pcie_dev)
		}
	}

	/* always ungate clkreq */
	msm_pcie_write_reg_field(pcie_dev->parf,
				PCIE20_PARF_CLKREQ_OVERRIDE,
				PCIE20_PARF_CLKREQ_IN_ENABLE, 0);
	msm_pcie_write_reg_field(pcie_dev->parf,
				PCIE20_PARF_CLKREQ_OVERRIDE,
				PCIE20_PARF_CLKREQ_IN_VALUE, 0);

	pcie_dev->user_suspend = false;
	spin_lock_irq(&pcie_dev->cfg_lock);
	pcie_dev->cfg_access = true;
+1 −0
Original line number Diff line number Diff line
@@ -28,6 +28,7 @@ enum subsys_notif_type {

enum early_subsys_notif_type {
	XPORT_LAYER_NOTIF,
	PCIE_DRV_LAYER_NOTIF,
	NUM_EARLY_NOTIFS
};