]> git.proxmox.com Git - mirror_ubuntu-jammy-kernel.git/commitdiff
Merge branch 'for-3.16-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/tj...
authorTejun Heo <tj@kernel.org>
Wed, 30 Jul 2014 16:49:04 +0000 (12:49 -0400)
committerTejun Heo <tj@kernel.org>
Wed, 30 Jul 2014 16:49:04 +0000 (12:49 -0400)
The scheduled ahci platform patches depend on change in
for-3.16-fixes.  Pull it into for-3.17.

Signed-off-by: Tejun Heo <tj@kernel.org>
1  2 
drivers/ata/ahci.h
drivers/ata/ahci_imx.c
drivers/ata/ahci_xgene.c
drivers/ata/libahci_platform.c

diff --combined drivers/ata/ahci.h
index 7137e1bbf04a27cf530619d16e565cc22ee887c0,5513296e5e2e15ebd43b8ecfc1f28df5bcdcf00c..2ed84e1c70ea54a6e38d9710c090635e5e5559d6
@@@ -53,7 -53,7 +53,7 @@@
  
  enum {
        AHCI_MAX_PORTS          = 32,
 -      AHCI_MAX_CLKS           = 3,
 +      AHCI_MAX_CLKS           = 4,
        AHCI_MAX_SG             = 168, /* hardware max is 64K */
        AHCI_DMA_BOUNDARY       = 0xffffffff,
        AHCI_MAX_CMDS           = 32,
@@@ -371,7 -371,9 +371,9 @@@ int ahci_do_softreset(struct ata_link *
                      int pmp, unsigned long deadline,
                      int (*check_ready)(struct ata_link *link));
  
+ unsigned int ahci_qc_issue(struct ata_queued_cmd *qc);
  int ahci_stop_engine(struct ata_port *ap);
+ void ahci_start_fis_rx(struct ata_port *ap);
  void ahci_start_engine(struct ata_port *ap);
  int ahci_check_ready(struct ata_link *link);
  int ahci_kick_engine(struct ata_port *ap);
diff --combined drivers/ata/ahci_imx.c
index e7be1f87d3e553cb8cc651b0d72ea034c70035f3,cac4360f272a75b3adad2d447e5a8762aeb7354e..1e5fa5f21aff05c55d71dbc800ad4d0c53952a93
@@@ -58,11 -58,12 +58,13 @@@ enum ahci_imx_type 
  struct imx_ahci_priv {
        struct platform_device *ahci_pdev;
        enum ahci_imx_type type;
+       struct clk *sata_clk;
+       struct clk *sata_ref_clk;
        struct clk *ahb_clk;
        struct regmap *gpr;
        bool no_device;
        bool first_time;
 +      u32 phy_params;
  };
  
  static int ahci_imx_hotplug;
@@@ -225,7 -226,7 +227,7 @@@ static int imx_sata_enable(struct ahci_
                        return ret;
        }
  
-       ret = ahci_platform_enable_clks(hpriv);
+       ret = clk_prepare_enable(imxpriv->sata_ref_clk);
        if (ret < 0)
                goto disable_regulator;
  
                                   IMX6Q_GPR13_SATA_TX_LVL_MASK |
                                   IMX6Q_GPR13_SATA_MPLL_CLK_EN |
                                   IMX6Q_GPR13_SATA_TX_EDGE_RATE,
 -                                 IMX6Q_GPR13_SATA_RX_EQ_VAL_3_0_DB |
 -                                 IMX6Q_GPR13_SATA_RX_LOS_LVL_SATA2M |
 -                                 IMX6Q_GPR13_SATA_RX_DPLL_MODE_2P_4F |
 -                                 IMX6Q_GPR13_SATA_SPD_MODE_3P0G |
 -                                 IMX6Q_GPR13_SATA_MPLL_SS_EN |
 -                                 IMX6Q_GPR13_SATA_TX_ATTEN_9_16 |
 -                                 IMX6Q_GPR13_SATA_TX_BOOST_3_33_DB |
 -                                 IMX6Q_GPR13_SATA_TX_LVL_1_025_V);
 +                                 imxpriv->phy_params);
                regmap_update_bits(imxpriv->gpr, IOMUXC_GPR13,
                                   IMX6Q_GPR13_SATA_MPLL_CLK_EN,
                                   IMX6Q_GPR13_SATA_MPLL_CLK_EN);
                ret = imx_sata_phy_reset(hpriv);
                if (ret) {
                        dev_err(dev, "failed to reset phy: %d\n", ret);
 -                      goto disable_regulator;
 +                      goto disable_clk;
                }
        }
  
  
        return 0;
  
 +disable_clk:
 +      clk_disable_unprepare(imxpriv->sata_ref_clk);
  disable_regulator:
        if (hpriv->target_pwr)
                regulator_disable(hpriv->target_pwr);
@@@ -287,7 -293,7 +289,7 @@@ static void imx_sata_disable(struct ahc
                                   !IMX6Q_GPR13_SATA_MPLL_CLK_EN);
        }
  
-       ahci_platform_disable_clks(hpriv);
+       clk_disable_unprepare(imxpriv->sata_ref_clk);
  
        if (hpriv->target_pwr)
                regulator_disable(hpriv->target_pwr);
@@@ -320,6 -326,9 +322,9 @@@ static void ahci_imx_error_handler(stru
        writel(reg_val | IMX_P0PHYCR_TEST_PDDQ, mmio + IMX_P0PHYCR);
        imx_sata_disable(hpriv);
        imxpriv->no_device = true;
+       dev_info(ap->dev, "no device found, disabling link.\n");
+       dev_info(ap->dev, "pass " MODULE_PARAM_PREFIX ".hotplug=1 to enable hotplug\n");
  }
  
  static int ahci_imx_softreset(struct ata_link *link, unsigned int *class,
@@@ -360,165 -369,6 +365,165 @@@ static const struct of_device_id imx_ah
  };
  MODULE_DEVICE_TABLE(of, imx_ahci_of_match);
  
 +struct reg_value {
 +      u32 of_value;
 +      u32 reg_value;
 +};
 +
 +struct reg_property {
 +      const char *name;
 +      const struct reg_value *values;
 +      size_t num_values;
 +      u32 def_value;
 +      u32 set_value;
 +};
 +
 +static const struct reg_value gpr13_tx_level[] = {
 +      {  937, IMX6Q_GPR13_SATA_TX_LVL_0_937_V },
 +      {  947, IMX6Q_GPR13_SATA_TX_LVL_0_947_V },
 +      {  957, IMX6Q_GPR13_SATA_TX_LVL_0_957_V },
 +      {  966, IMX6Q_GPR13_SATA_TX_LVL_0_966_V },
 +      {  976, IMX6Q_GPR13_SATA_TX_LVL_0_976_V },
 +      {  986, IMX6Q_GPR13_SATA_TX_LVL_0_986_V },
 +      {  996, IMX6Q_GPR13_SATA_TX_LVL_0_996_V },
 +      { 1005, IMX6Q_GPR13_SATA_TX_LVL_1_005_V },
 +      { 1015, IMX6Q_GPR13_SATA_TX_LVL_1_015_V },
 +      { 1025, IMX6Q_GPR13_SATA_TX_LVL_1_025_V },
 +      { 1035, IMX6Q_GPR13_SATA_TX_LVL_1_035_V },
 +      { 1045, IMX6Q_GPR13_SATA_TX_LVL_1_045_V },
 +      { 1054, IMX6Q_GPR13_SATA_TX_LVL_1_054_V },
 +      { 1064, IMX6Q_GPR13_SATA_TX_LVL_1_064_V },
 +      { 1074, IMX6Q_GPR13_SATA_TX_LVL_1_074_V },
 +      { 1084, IMX6Q_GPR13_SATA_TX_LVL_1_084_V },
 +      { 1094, IMX6Q_GPR13_SATA_TX_LVL_1_094_V },
 +      { 1104, IMX6Q_GPR13_SATA_TX_LVL_1_104_V },
 +      { 1113, IMX6Q_GPR13_SATA_TX_LVL_1_113_V },
 +      { 1123, IMX6Q_GPR13_SATA_TX_LVL_1_123_V },
 +      { 1133, IMX6Q_GPR13_SATA_TX_LVL_1_133_V },
 +      { 1143, IMX6Q_GPR13_SATA_TX_LVL_1_143_V },
 +      { 1152, IMX6Q_GPR13_SATA_TX_LVL_1_152_V },
 +      { 1162, IMX6Q_GPR13_SATA_TX_LVL_1_162_V },
 +      { 1172, IMX6Q_GPR13_SATA_TX_LVL_1_172_V },
 +      { 1182, IMX6Q_GPR13_SATA_TX_LVL_1_182_V },
 +      { 1191, IMX6Q_GPR13_SATA_TX_LVL_1_191_V },
 +      { 1201, IMX6Q_GPR13_SATA_TX_LVL_1_201_V },
 +      { 1211, IMX6Q_GPR13_SATA_TX_LVL_1_211_V },
 +      { 1221, IMX6Q_GPR13_SATA_TX_LVL_1_221_V },
 +      { 1230, IMX6Q_GPR13_SATA_TX_LVL_1_230_V },
 +      { 1240, IMX6Q_GPR13_SATA_TX_LVL_1_240_V }
 +};
 +
 +static const struct reg_value gpr13_tx_boost[] = {
 +      {    0, IMX6Q_GPR13_SATA_TX_BOOST_0_00_DB },
 +      {  370, IMX6Q_GPR13_SATA_TX_BOOST_0_37_DB },
 +      {  740, IMX6Q_GPR13_SATA_TX_BOOST_0_74_DB },
 +      { 1110, IMX6Q_GPR13_SATA_TX_BOOST_1_11_DB },
 +      { 1480, IMX6Q_GPR13_SATA_TX_BOOST_1_48_DB },
 +      { 1850, IMX6Q_GPR13_SATA_TX_BOOST_1_85_DB },
 +      { 2220, IMX6Q_GPR13_SATA_TX_BOOST_2_22_DB },
 +      { 2590, IMX6Q_GPR13_SATA_TX_BOOST_2_59_DB },
 +      { 2960, IMX6Q_GPR13_SATA_TX_BOOST_2_96_DB },
 +      { 3330, IMX6Q_GPR13_SATA_TX_BOOST_3_33_DB },
 +      { 3700, IMX6Q_GPR13_SATA_TX_BOOST_3_70_DB },
 +      { 4070, IMX6Q_GPR13_SATA_TX_BOOST_4_07_DB },
 +      { 4440, IMX6Q_GPR13_SATA_TX_BOOST_4_44_DB },
 +      { 4810, IMX6Q_GPR13_SATA_TX_BOOST_4_81_DB },
 +      { 5280, IMX6Q_GPR13_SATA_TX_BOOST_5_28_DB },
 +      { 5750, IMX6Q_GPR13_SATA_TX_BOOST_5_75_DB }
 +};
 +
 +static const struct reg_value gpr13_tx_atten[] = {
 +      {  8, IMX6Q_GPR13_SATA_TX_ATTEN_8_16 },
 +      {  9, IMX6Q_GPR13_SATA_TX_ATTEN_9_16 },
 +      { 10, IMX6Q_GPR13_SATA_TX_ATTEN_10_16 },
 +      { 12, IMX6Q_GPR13_SATA_TX_ATTEN_12_16 },
 +      { 14, IMX6Q_GPR13_SATA_TX_ATTEN_14_16 },
 +      { 16, IMX6Q_GPR13_SATA_TX_ATTEN_16_16 },
 +};
 +
 +static const struct reg_value gpr13_rx_eq[] = {
 +      {  500, IMX6Q_GPR13_SATA_RX_EQ_VAL_0_5_DB },
 +      { 1000, IMX6Q_GPR13_SATA_RX_EQ_VAL_1_0_DB },
 +      { 1500, IMX6Q_GPR13_SATA_RX_EQ_VAL_1_5_DB },
 +      { 2000, IMX6Q_GPR13_SATA_RX_EQ_VAL_2_0_DB },
 +      { 2500, IMX6Q_GPR13_SATA_RX_EQ_VAL_2_5_DB },
 +      { 3000, IMX6Q_GPR13_SATA_RX_EQ_VAL_3_0_DB },
 +      { 3500, IMX6Q_GPR13_SATA_RX_EQ_VAL_3_5_DB },
 +      { 4000, IMX6Q_GPR13_SATA_RX_EQ_VAL_4_0_DB },
 +};
 +
 +static const struct reg_property gpr13_props[] = {
 +      {
 +              .name = "fsl,transmit-level-mV",
 +              .values = gpr13_tx_level,
 +              .num_values = ARRAY_SIZE(gpr13_tx_level),
 +              .def_value = IMX6Q_GPR13_SATA_TX_LVL_1_025_V,
 +      }, {
 +              .name = "fsl,transmit-boost-mdB",
 +              .values = gpr13_tx_boost,
 +              .num_values = ARRAY_SIZE(gpr13_tx_boost),
 +              .def_value = IMX6Q_GPR13_SATA_TX_BOOST_3_33_DB,
 +      }, {
 +              .name = "fsl,transmit-atten-16ths",
 +              .values = gpr13_tx_atten,
 +              .num_values = ARRAY_SIZE(gpr13_tx_atten),
 +              .def_value = IMX6Q_GPR13_SATA_TX_ATTEN_9_16,
 +      }, {
 +              .name = "fsl,receive-eq-mdB",
 +              .values = gpr13_rx_eq,
 +              .num_values = ARRAY_SIZE(gpr13_rx_eq),
 +              .def_value = IMX6Q_GPR13_SATA_RX_EQ_VAL_3_0_DB,
 +      }, {
 +              .name = "fsl,no-spread-spectrum",
 +              .def_value = IMX6Q_GPR13_SATA_MPLL_SS_EN,
 +              .set_value = 0,
 +      },
 +};
 +
 +static u32 imx_ahci_parse_props(struct device *dev,
 +                              const struct reg_property *prop, size_t num)
 +{
 +      struct device_node *np = dev->of_node;
 +      u32 reg_value = 0;
 +      int i, j;
 +
 +      for (i = 0; i < num; i++, prop++) {
 +              u32 of_val;
 +
 +              if (prop->num_values == 0) {
 +                      if (of_property_read_bool(np, prop->name))
 +                              reg_value |= prop->set_value;
 +                      else
 +                              reg_value |= prop->def_value;
 +                      continue;
 +              }
 +
 +              if (of_property_read_u32(np, prop->name, &of_val)) {
 +                      dev_info(dev, "%s not specified, using %08x\n",
 +                              prop->name, prop->def_value);
 +                      reg_value |= prop->def_value;
 +                      continue;
 +              }
 +
 +              for (j = 0; j < prop->num_values; j++) {
 +                      if (prop->values[j].of_value == of_val) {
 +                              dev_info(dev, "%s value %u, using %08x\n",
 +                                      prop->name, of_val, prop->values[j].reg_value);
 +                              reg_value |= prop->values[j].reg_value;
 +                              break;
 +                      }
 +              }
 +
 +              if (j == prop->num_values) {
 +                      dev_err(dev, "DT property %s is not a valid value\n",
 +                              prop->name);
 +                      reg_value |= prop->def_value;
 +              }
 +      }
 +
 +      return reg_value;
 +}
 +
  static int imx_ahci_probe(struct platform_device *pdev)
  {
        struct device *dev = &pdev->dev;
        imxpriv->no_device = false;
        imxpriv->first_time = true;
        imxpriv->type = (enum ahci_imx_type)of_id->data;
+       imxpriv->sata_clk = devm_clk_get(dev, "sata");
+       if (IS_ERR(imxpriv->sata_clk)) {
+               dev_err(dev, "can't get sata clock.\n");
+               return PTR_ERR(imxpriv->sata_clk);
+       }
+       imxpriv->sata_ref_clk = devm_clk_get(dev, "sata_ref");
+       if (IS_ERR(imxpriv->sata_ref_clk)) {
+               dev_err(dev, "can't get sata_ref clock.\n");
+               return PTR_ERR(imxpriv->sata_ref_clk);
+       }
        imxpriv->ahb_clk = devm_clk_get(dev, "ahb");
        if (IS_ERR(imxpriv->ahb_clk)) {
                dev_err(dev, "can't get ahb clock.\n");
        }
  
        if (imxpriv->type == AHCI_IMX6Q) {
 +              u32 reg_value;
 +
                imxpriv->gpr = syscon_regmap_lookup_by_compatible(
                                                        "fsl,imx6q-iomuxc-gpr");
                if (IS_ERR(imxpriv->gpr)) {
                                "failed to find fsl,imx6q-iomux-gpr regmap\n");
                        return PTR_ERR(imxpriv->gpr);
                }
 +
 +              reg_value = imx_ahci_parse_props(dev, gpr13_props,
 +                                               ARRAY_SIZE(gpr13_props));
 +
 +              imxpriv->phy_params =
 +                                 IMX6Q_GPR13_SATA_RX_LOS_LVL_SATA2M |
 +                                 IMX6Q_GPR13_SATA_RX_DPLL_MODE_2P_4F |
 +                                 IMX6Q_GPR13_SATA_SPD_MODE_3P0G |
 +                                 reg_value;
        }
  
        hpriv = ahci_platform_get_resources(pdev);
  
        hpriv->plat_data = imxpriv;
  
-       ret = imx_sata_enable(hpriv);
+       ret = clk_prepare_enable(imxpriv->sata_clk);
        if (ret)
                return ret;
  
+       ret = imx_sata_enable(hpriv);
+       if (ret)
+               goto disable_clk;
        /*
         * Configure the HWINIT bits of the HOST_CAP and HOST_PORTS_IMPL,
         * and IP vendor specific register IMX_TIMER1MS.
        ret = ahci_platform_init_host(pdev, hpriv, &ahci_imx_port_info,
                                      0, 0, 0);
        if (ret)
-               imx_sata_disable(hpriv);
+               goto disable_sata;
+       return 0;
  
+ disable_sata:
+       imx_sata_disable(hpriv);
+ disable_clk:
+       clk_disable_unprepare(imxpriv->sata_clk);
        return ret;
  }
  
  static void ahci_imx_host_stop(struct ata_host *host)
  {
        struct ahci_host_priv *hpriv = host->private_data;
+       struct imx_ahci_priv *imxpriv = hpriv->plat_data;
  
        imx_sata_disable(hpriv);
+       clk_disable_unprepare(imxpriv->sata_clk);
  }
  
  #ifdef CONFIG_PM_SLEEP
diff --combined drivers/ata/ahci_xgene.c
index 997b4178249a42f4a731dd1913601b204ce67ce4,ee3a3659bd9ef2e173e6e1ac468d5bd88631ee9c..1cfbdca638d2e7e6e759f355a55e411894d82eb3
@@@ -67,9 -67,6 +67,9 @@@
  #define PORTAXICFG                    0x000000bc
  #define PORTAXICFG_OUTTRANS_SET(dst, src) \
                (((dst) & ~0x00f00000) | (((u32)(src) << 0x14) & 0x00f00000))
 +#define PORTRANSCFG                   0x000000c8
 +#define PORTRANSCFG_RXWM_SET(dst, src)                \
 +              (((dst) & ~0x0000007f) | (((u32)(src)) & 0x0000007f))
  
  /* SATA host controller AXI CSR */
  #define INT_SLV_TMOMASK                       0x00000010
@@@ -81,6 -78,7 +81,7 @@@
  struct xgene_ahci_context {
        struct ahci_host_priv *hpriv;
        struct device *dev;
+       u8 last_cmd[MAX_AHCI_CHN_PERCTR]; /* tracking the last command issued*/
        void __iomem *csr_core;         /* Core CSR address of IP */
        void __iomem *csr_diag;         /* Diag CSR address of IP */
        void __iomem *csr_axi;          /* AXI CSR address of IP */
@@@ -100,6 -98,50 +101,50 @@@ static int xgene_ahci_init_memram(struc
        return 0;
  }
  
+ /**
+  * xgene_ahci_restart_engine - Restart the dma engine.
+  * @ap : ATA port of interest
+  *
+  * Restarts the dma engine inside the controller.
+  */
+ static int xgene_ahci_restart_engine(struct ata_port *ap)
+ {
+       struct ahci_host_priv *hpriv = ap->host->private_data;
+       ahci_stop_engine(ap);
+       ahci_start_fis_rx(ap);
+       hpriv->start_engine(ap);
+       return 0;
+ }
+ /**
+  * xgene_ahci_qc_issue - Issue commands to the device
+  * @qc: Command to issue
+  *
+  * Due to Hardware errata for IDENTIFY DEVICE command, the controller cannot
+  * clear the BSY bit after receiving the PIO setup FIS. This results in the dma
+  * state machine goes into the CMFatalErrorUpdate state and locks up. By
+  * restarting the dma engine, it removes the controller out of lock up state.
+  */
+ static unsigned int xgene_ahci_qc_issue(struct ata_queued_cmd *qc)
+ {
+       struct ata_port *ap = qc->ap;
+       struct ahci_host_priv *hpriv = ap->host->private_data;
+       struct xgene_ahci_context *ctx = hpriv->plat_data;
+       int rc = 0;
+       if (unlikely(ctx->last_cmd[ap->port_no] == ATA_CMD_ID_ATA))
+               xgene_ahci_restart_engine(ap);
+       rc = ahci_qc_issue(qc);
+       /* Save the last command issued */
+       ctx->last_cmd[ap->port_no] = qc->tf.command;
+       return rc;
+ }
  /**
   * xgene_ahci_read_id - Read ID data from the specified device
   * @dev: device
   * @id: data buffer
   *
   * This custom read ID function is required due to the fact that the HW
-  * does not support DEVSLP and the controller state machine may get stuck
-  * after processing the ID query command.
+  * does not support DEVSLP.
   */
  static unsigned int xgene_ahci_read_id(struct ata_device *dev,
                                       struct ata_taskfile *tf, u16 *id)
  {
        u32 err_mask;
-       void __iomem *port_mmio = ahci_port_base(dev->link->ap);
  
        err_mask = ata_do_dev_read_id(dev, tf, id);
        if (err_mask)
         */
        id[ATA_ID_FEATURE_SUPP] &= ~(1 << 8);
  
-       /*
-        * Due to HW errata, restart the port if no other command active.
-        * Otherwise the controller may get stuck.
-        */
-       if (!readl(port_mmio + PORT_CMD_ISSUE)) {
-               writel(PORT_CMD_FIS_RX, port_mmio + PORT_CMD);
-               readl(port_mmio + PORT_CMD);    /* Force a barrier */
-               writel(PORT_CMD_FIS_RX | PORT_CMD_START, port_mmio + PORT_CMD);
-               readl(port_mmio + PORT_CMD);    /* Force a barrier */
-       }
        return 0;
  }
  
@@@ -163,11 -193,11 +196,11 @@@ static void xgene_ahci_set_phy_cfg(stru
        /* Disable fix rate */
        writel(0x0001fffe, mmio + PORTPHY1CFG);
        readl(mmio + PORTPHY1CFG); /* Force a barrier */
 -      writel(0x5018461c, mmio + PORTPHY2CFG);
 +      writel(0x28183219, mmio + PORTPHY2CFG);
        readl(mmio + PORTPHY2CFG); /* Force a barrier */
 -      writel(0x1c081907, mmio + PORTPHY3CFG);
 +      writel(0x13081008, mmio + PORTPHY3CFG);
        readl(mmio + PORTPHY3CFG); /* Force a barrier */
 -      writel(0x1c080815, mmio + PORTPHY4CFG);
 +      writel(0x00480815, mmio + PORTPHY4CFG);
        readl(mmio + PORTPHY4CFG); /* Force a barrier */
        /* Set window negotiation */
        val = readl(mmio + PORTPHY5CFG);
        val = PORTAXICFG_OUTTRANS_SET(val, 0xe); /* Set outstanding */
        writel(val, mmio + PORTAXICFG);
        readl(mmio + PORTAXICFG); /* Force a barrier */
 +      /* Set the watermark threshold of the receive FIFO */
 +      val = readl(mmio + PORTRANSCFG);
 +      val = PORTRANSCFG_RXWM_SET(val, 0x30);
 +      writel(val, mmio + PORTRANSCFG);
  }
  
  /**
@@@ -307,6 -333,7 +340,7 @@@ static struct ata_port_operations xgene
        .host_stop = xgene_ahci_host_stop,
        .hardreset = xgene_ahci_hardreset,
        .read_id = xgene_ahci_read_id,
+       .qc_issue = xgene_ahci_qc_issue,
  };
  
  static const struct ata_port_info xgene_ahci_port_info = {
@@@ -447,6 -474,16 +481,6 @@@ static int xgene_ahci_probe(struct plat
        /* Configure the host controller */
        xgene_ahci_hw_init(hpriv);
  
 -      /*
 -       * Setup DMA mask. This is preliminary until the DMA range is sorted
 -       * out.
 -       */
 -      rc = dma_set_mask_and_coherent(dev, DMA_BIT_MASK(64));
 -      if (rc) {
 -              dev_err(dev, "Unable to set dma mask\n");
 -              goto disable_resources;
 -      }
 -
        hflags = AHCI_HFLAG_NO_PMP | AHCI_HFLAG_YES_NCQ;
  
        rc = ahci_platform_init_host(pdev, hpriv, &xgene_ahci_port_info,
index a958a2b8fd936807916a2390d2717308f83c5375,b0077589f065889318bf92c564786db1d8171c6e..28840a2f470f03fd1d0e34f0c43db42800d24ca9
@@@ -250,8 -250,13 +250,13 @@@ struct ahci_host_priv *ahci_platform_ge
        if (IS_ERR(hpriv->phy)) {
                rc = PTR_ERR(hpriv->phy);
                switch (rc) {
-               case -ENODEV:
                case -ENOSYS:
+                       /* No PHY support. Check if PHY is required. */
+                       if (of_find_property(dev->of_node, "phys", NULL)) {
+                               dev_err(dev, "couldn't get sata-phy: ENOSYS\n");
+                               goto err_out;
+                       }
+               case -ENODEV:
                        /* continue normally */
                        hpriv->phy = NULL;
                        break;
@@@ -364,19 -369,6 +369,19 @@@ int ahci_platform_init_host(struct plat
                        ap->ops = &ata_dummy_port_ops;
        }
  
 +      if (hpriv->cap & HOST_CAP_64) {
 +              rc = dma_coerce_mask_and_coherent(dev, DMA_BIT_MASK(64));
 +              if (rc) {
 +                      rc = dma_coerce_mask_and_coherent(dev,
 +                                                        DMA_BIT_MASK(32));
 +                      if (rc) {
 +                              dev_err(dev, "Failed to enable 64-bit DMA.\n");
 +                              return rc;
 +                      }
 +                      dev_warn(dev, "Enable 32-bit DMA instead of 64-bit.\n");
 +              }
 +      }
 +
        rc = ahci_reset_controller(host);
        if (rc)
                return rc;