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

Commit ad7a40e9 authored by Tony Truong's avatar Tony Truong Committed by Gerrit - the friendly Code Review server
Browse files

msm: pcie: add support to get PCIe PHY init sequence from DT



PCIe PHY varies between each chipset. Thus, the PHY init sequence on
each of these chipsets are also different. Therefore, add the support
to read PCIe PHY init sequence from devicetree.

Change-Id: I21c2ce2b7d3bf1541a5d3580db4bc40497701095
Signed-off-by: default avatarTony Truong <truong@codeaurora.org>
parent 0c3a23a4
Loading
Loading
Loading
Loading
+10 −0
Original line number Diff line number Diff line
@@ -73,6 +73,8 @@ Optional Properties:
  - qcom,n-fts: The number of fast training sequences sent when the link state
    is changed from L0s to L0.
  - qcom,pcie-phy-ver: version of PCIe PHY.
  - qcom,phy-sequence: The initialization sequence to bring up the PCIe PHY.
    Should be specified in groups (offset, value, delay).
  - qcom,use-19p2mhz-aux-clk: The frequency of PCIe AUX clock is 19.2MHz.
  - qcom,ep-wakeirq: The endpoint will issue wake signal when it is up, and the
    root complex has the capability to enumerate the endpoint for this case.
@@ -189,6 +191,14 @@ Example:
				"msi_20", "msi_21", "msi_22", "msi_23",
				"msi_24", "msi_25", "msi_26", "msi_27",
				"msi_28", "msi_29", "msi_30", "msi_31";

		qcom,phy-sequence = <0x804 0x01 0x00
					0x034 0x14 0x00
					0x138 0x30 0x00
					0x048 0x0f 0x00
					0x15c 0x06 0x00
					0x090 0x01 0x00
					0x808 0x03 0x00>;
		perst-gpio = <&msmgpio 70 0>;
		wake-gpio = <&msmgpio 69 0>;
		clkreq-gpio = <&msmgpio 68 0>;
+57 −1
Original line number Diff line number Diff line
@@ -502,6 +502,13 @@ struct msm_pcie_irq_info_t {
	uint32_t	    num;
};

/* phy info structure */
struct msm_pcie_phy_info_t {
	u32	offset;
	u32	val;
	u32	delay;
};

/* PCIe device info structure */
struct msm_pcie_device_info {
	u32			bdf;
@@ -615,6 +622,8 @@ struct msm_pcie_dev_t {
	u32				num_active_ep;
	u32				num_ep;
	bool				pending_ep_reg;
	u32				phy_len;
	struct msm_pcie_phy_info_t	*phy_sequence;
	u32		ep_shadow[MAX_DEVICE_NUM][PCIE_CONF_SPACE_DW];
	u32				  rc_shadow[PCIE_CONF_SPACE_DW];
	bool				 shadow_en;
@@ -1411,10 +1420,28 @@ static bool pcie_phy_is_ready(struct msm_pcie_dev_t *dev)
#else
static void pcie_phy_init(struct msm_pcie_dev_t *dev)
{
	int i;
	struct msm_pcie_phy_info_t *phy_seq;

	PCIE_DBG(dev,
		"RC%d: Initializing 14nm QMP phy - 19.2MHz with Common Mode Clock (SSC ON)\n",
		dev->rc_idx);

	if (dev->phy_sequence) {
		i =  dev->phy_len;
		phy_seq = dev->phy_sequence;
		while (i--) {
			msm_pcie_write_reg(dev->phy,
				phy_seq->offset,
				phy_seq->val);
			if (phy_seq->delay)
				usleep_range(phy_seq->delay,
					phy_seq->delay + 1);
			phy_seq++;
		}
		return;
	}

	if (dev->common_phy)
		msm_pcie_write_reg(dev->phy, PCIE_COM_POWER_DOWN_CONTROL, 0x01);

@@ -1772,6 +1799,8 @@ static void msm_pcie_show_status(struct msm_pcie_dev_t *dev)
		dev->num_active_ep);
	PCIE_DBG_FS(dev, "pending_ep_reg: %s\n",
		dev->pending_ep_reg ? "true" : "false");
	PCIE_DBG_FS(dev, "phy_len is %d",
		dev->phy_len);
	PCIE_DBG_FS(dev, "disable_pc is %d",
		dev->disable_pc);
	PCIE_DBG_FS(dev, "l0s_supported is %s supported\n",
@@ -3821,7 +3850,7 @@ void msm_pcie_config_msi_controller(struct msm_pcie_dev_t *dev)
static int msm_pcie_get_resources(struct msm_pcie_dev_t *dev,
					struct platform_device *pdev)
{
	int i, len, cnt, ret = 0;
	int i, len, cnt, ret = 0, size = 0;
	struct msm_pcie_vreg_info_t *vreg_info;
	struct msm_pcie_gpio_info_t *gpio_info;
	struct msm_pcie_clk_info_t  *clk_info;
@@ -3944,6 +3973,31 @@ static int msm_pcie_get_resources(struct msm_pcie_dev_t *dev,
		ret = 0;
	}

	of_get_property(pdev->dev.of_node, "qcom,phy-sequence", &size);
	if (size) {
		dev->phy_sequence = (struct msm_pcie_phy_info_t *)
			devm_kzalloc(&pdev->dev, size, GFP_KERNEL);

		if (dev->phy_sequence) {
			dev->phy_len =
				size / sizeof(*dev->phy_sequence);

			of_property_read_u32_array(pdev->dev.of_node,
				"qcom,phy-sequence",
				(unsigned int *)dev->phy_sequence,
				size / sizeof(dev->phy_sequence->offset));
		} else {
			PCIE_ERR(dev,
				"RC%d: Could not allocate memory for phy init sequence.\n",
				dev->rc_idx);
			ret = -ENOMEM;
			goto out;
		}
	} else {
		PCIE_DBG(dev, "RC%d: phy sequence is not present in DT\n",
			dev->rc_idx);
	}

	for (i = 0; i < MSM_PCIE_MAX_CLK; i++) {
		clk_info = &dev->clk[i];

@@ -5878,6 +5932,8 @@ static int msm_pcie_probe(struct platform_device *pdev)
	msm_pcie_dev[rc_idx].num_active_ep = 0;
	msm_pcie_dev[rc_idx].num_ep = 0;
	msm_pcie_dev[rc_idx].pending_ep_reg = false;
	msm_pcie_dev[rc_idx].phy_len = 0;
	msm_pcie_dev[rc_idx].phy_sequence = NULL;
	msm_pcie_dev[rc_idx].event_reg = NULL;
	msm_pcie_dev[rc_idx].linkdown_counter = 0;
	msm_pcie_dev[rc_idx].link_turned_on_counter = 0;