Lines Matching +full:hb +full:- +full:ahci
1 // SPDX-License-Identifier: GPL-2.0-only
3 * Calxeda Highbank AHCI SATA platform driver
6 * based on the AHCI SATA platform driver by Jeff Garzik and Anton Vorontsov
25 #include "ahci.h"
53 /* Each of the 6 phys can have up to 4 sata ports attached to i. Map 0-based
91 return 1 << (3 * pdata->port_to_sgpio[port] + shift); in sgpio_bit_shift()
97 pdata->sgpio_pattern |= sgpio_bit_shift(pdata, port, in ecx_parse_sgpio()
100 pdata->sgpio_pattern &= ~sgpio_bit_shift(pdata, port, in ecx_parse_sgpio()
103 pdata->sgpio_pattern |= sgpio_bit_shift(pdata, port, in ecx_parse_sgpio()
106 pdata->sgpio_pattern &= ~sgpio_bit_shift(pdata, port, in ecx_parse_sgpio()
109 pdata->sgpio_pattern |= sgpio_bit_shift(pdata, port, in ecx_parse_sgpio()
112 pdata->sgpio_pattern &= ~sgpio_bit_shift(pdata, port, in ecx_parse_sgpio()
122 gpiod_set_value(pdata->sgpio_gpiod[SCLOCK], 1); in ecx_led_cycle_clock()
124 gpiod_set_value(pdata->sgpio_gpiod[SCLOCK], 0); in ecx_led_cycle_clock()
131 struct ahci_host_priv *hpriv = ap->host->private_data; in ecx_transmit_led_message()
132 struct ecx_plat_data *pdata = hpriv->plat_data; in ecx_transmit_led_message()
133 struct ahci_port_priv *pp = ap->private_data; in ecx_transmit_led_message()
142 emp = &pp->em_priv[pmp]; in ecx_transmit_led_message()
144 return -EINVAL; in ecx_transmit_led_message()
146 if (!(hpriv->em_msg_type & EM_MSG_TYPE_LED)) in ecx_transmit_led_message()
150 ecx_parse_sgpio(pdata, ap->port_no, state); in ecx_transmit_led_message()
151 sgpio_out = pdata->sgpio_pattern; in ecx_transmit_led_message()
152 for (i = 0; i < pdata->pre_clocks; i++) in ecx_transmit_led_message()
155 gpiod_set_value(pdata->sgpio_gpiod[SLOAD], 1); in ecx_transmit_led_message()
157 gpiod_set_value(pdata->sgpio_gpiod[SLOAD], 0); in ecx_transmit_led_message()
159 * bit-bang out the SGPIO pattern, by consuming a bit and then in ecx_transmit_led_message()
162 for (i = 0; i < (SGPIO_SIGNALS * pdata->n_ports); i++) { in ecx_transmit_led_message()
163 gpiod_set_value(pdata->sgpio_gpiod[SDATA], sgpio_out & 1); in ecx_transmit_led_message()
167 for (i = 0; i < pdata->post_clocks; i++) in ecx_transmit_led_message()
171 emp->led_state = state; in ecx_transmit_led_message()
181 struct device_node *np = dev->of_node; in highbank_set_em_messages()
182 struct ecx_plat_data *pdata = hpriv->plat_data; in highbank_set_em_messages()
196 pdata->sgpio_gpiod[i] = gpiod; in highbank_set_em_messages()
198 of_property_read_u32_array(np, "calxeda,led-order", in highbank_set_em_messages()
199 pdata->port_to_sgpio, in highbank_set_em_messages()
200 pdata->n_ports); in highbank_set_em_messages()
201 if (of_property_read_u32(np, "calxeda,pre-clocks", &pdata->pre_clocks)) in highbank_set_em_messages()
202 pdata->pre_clocks = 0; in highbank_set_em_messages()
203 if (of_property_read_u32(np, "calxeda,post-clocks", in highbank_set_em_messages()
204 &pdata->post_clocks)) in highbank_set_em_messages()
205 pdata->post_clocks = 0; in highbank_set_em_messages()
208 hpriv->em_loc = 0; in highbank_set_em_messages()
209 hpriv->em_buf_sz = 4; in highbank_set_em_messages()
210 hpriv->em_msg_type = EM_MSG_TYPE_LED; in highbank_set_em_messages()
211 pi->flags |= ATA_FLAG_EM | ATA_FLAG_SW_ACTIVITY; in highbank_set_em_messages()
328 struct device_node *sata_node = dev->of_node; in highbank_initialize_phys()
340 "calxeda,port-phys", "#phy-cells", in highbank_initialize_phys()
362 of_property_read_u32_array(sata_node, "calxeda,tx-atten", in highbank_initialize_phys()
377 * Also, the default 2 second time-out on a failed drive is too long in
379 * uses a much shorter time-out period and never experiences a time out
380 * issue. Reducing the time-out to 500ms improves the responsiveness.
381 * The other timing constants were kept the same as the stock AHCI driver.
389 struct ata_port *ap = link->ap; in ahci_highbank_hardreset()
390 struct ahci_port_priv *pp = ap->private_data; in ahci_highbank_hardreset()
391 struct ahci_host_priv *hpriv = ap->host->private_data; in ahci_highbank_hardreset()
392 u8 *d2h_fis = pp->rx_fis + RX_FIS_D2H_REG; in ahci_highbank_hardreset()
399 hpriv->stop_engine(ap); in ahci_highbank_hardreset()
402 ata_tf_init(link->device, &tf); in ahci_highbank_hardreset()
407 highbank_cphy_disable_overrides(link->ap->port_no); in ahci_highbank_hardreset()
409 highbank_cphy_override_lane(link->ap->port_no); in ahci_highbank_hardreset()
418 } while (!online && retry--); in ahci_highbank_hardreset()
420 hpriv->start_engine(ap); in ahci_highbank_hardreset()
446 { .compatible = "calxeda,hb-ahci" },
453 struct device *dev = &pdev->dev; in ahci_highbank_probe()
468 return -EINVAL; in ahci_highbank_probe()
475 return -EINVAL; in ahci_highbank_probe()
480 return -ENOMEM; in ahci_highbank_probe()
485 return -ENOMEM; in ahci_highbank_probe()
488 hpriv->irq = irq; in ahci_highbank_probe()
489 hpriv->flags |= (unsigned long)pi.private_data; in ahci_highbank_probe()
491 hpriv->mmio = devm_ioremap(dev, mem->start, resource_size(mem)); in ahci_highbank_probe()
492 if (!hpriv->mmio) { in ahci_highbank_probe()
494 return -ENOMEM; in ahci_highbank_probe()
497 rc = highbank_initialize_phys(dev, hpriv->mmio); in ahci_highbank_probe()
505 if (hpriv->cap & HOST_CAP_NCQ) in ahci_highbank_probe()
508 if (hpriv->cap & HOST_CAP_PMP) in ahci_highbank_probe()
511 if (hpriv->cap & HOST_CAP_64) in ahci_highbank_probe()
519 n_ports = max(ahci_nr_ports(hpriv->cap), fls(hpriv->port_map)); in ahci_highbank_probe()
521 pdata->n_ports = n_ports; in ahci_highbank_probe()
522 hpriv->plat_data = pdata; in ahci_highbank_probe()
527 rc = -ENOMEM; in ahci_highbank_probe()
531 host->private_data = hpriv; in ahci_highbank_probe()
533 if (!(hpriv->cap & HOST_CAP_SSS) || ahci_ignore_sss) in ahci_highbank_probe()
534 host->flags |= ATA_HOST_PARALLEL_SCAN; in ahci_highbank_probe()
536 for (i = 0; i < host->n_ports; i++) { in ahci_highbank_probe()
537 struct ata_port *ap = host->ports[i]; in ahci_highbank_probe()
540 ata_port_desc(ap, "port 0x%x", 0x100 + ap->port_no * 0x80); in ahci_highbank_probe()
543 if (ap->flags & ATA_FLAG_EM) in ahci_highbank_probe()
544 ap->em_message_type = hpriv->em_msg_type; in ahci_highbank_probe()
546 /* disabled/not-implemented port */ in ahci_highbank_probe()
547 if (!(hpriv->port_map & (1 << i))) in ahci_highbank_probe()
548 ap->ops = &ata_dummy_port_ops; in ahci_highbank_probe()
571 struct ahci_host_priv *hpriv = host->private_data; in ahci_highbank_suspend()
572 void __iomem *mmio = hpriv->mmio; in ahci_highbank_suspend()
575 if (hpriv->flags & AHCI_HFLAG_NO_SUSPEND) { in ahci_highbank_suspend()
577 return -EIO; in ahci_highbank_suspend()
581 * AHCI spec rev1.1 section 8.3.3: in ahci_highbank_suspend()
599 if (dev->power.power_state.event == PM_EVENT_SUSPEND) { in ahci_highbank_resume()
619 .name = "highbank-ahci",
628 MODULE_DESCRIPTION("Calxeda Highbank AHCI SATA platform driver");