From: ben-linux@fluff.org (Ben Dooks)
To: linux-arm-kernel@lists.infradead.org
Subject: [PATCH v3] libata: pata_samsung_cf: Add Samsung PATA controller driver
Date: Fri, 11 Jun 2010 02:57:44 +0100 [thread overview]
Message-ID: <20100611015744.GC14272@trinity.fluff.org> (raw)
In-Reply-To: <4C10C1D6.8080708@ru.mvista.com>
On Thu, Jun 10, 2010 at 02:43:34PM +0400, Sergei Shtylyov wrote:
> Kukjin Kim wrote:
>
>> From: Abhilash Kesavan <a.kesavan@samsung.com>
>
>> Adds support for the Samsung PATA controller. This driver is based on the
>> Libata subsystem and references the earlier patches sent for IDE subsystem.
>
>> Signed-off-by: Abhilash Kesavan <a.kesavan@samsung.com>
>> Signed-off-by: Kukjin Kim <kgene.kim@samsung.com>
>
> [...]
>
>> diff --git a/drivers/ata/pata_samsung_cf.c b/drivers/ata/pata_samsung_cf.c
>> new file mode 100644
>> index 0000000..fef5515
>> --- /dev/null
>> +++ b/drivers/ata/pata_samsung_cf.c
>> @@ -0,0 +1,608 @@
>> +/* linux/drivers/ata/pata_samsung_cf.c
>
> File names in the heading comment are discouraged.
>
> [...]
>> +static void pata_s3c_set_piomode(struct ata_port *ap, struct ata_device *adev)
>> +{
>> + int mode = adev->pio_mode - XFER_PIO_0;
>> + struct s3c_ide_info *info = ap->host->private_data;
>> + ulong ata_cfg = readl(info->ide_addr + S3C_ATA_CFG);
>> + ulong piotime;
>> +
>> + /* Calculates timing parameters for PIO mode */
>> + piotime = pata_s3c_setup_timing(info, adev);
>
> In fact, for 8-bit (command) timing you should program the slowest
> mode of the two drives. However, with CF, you probably only have only one
> drive per channel...
>
>> +
>> + /* Enables IORDY if mode requires it */
>> + if (ata_pio_need_iordy(adev))
>> + ata_cfg |= S3C_ATA_CFG_IORDYEN;
>> + else
>> + ata_cfg &= ~S3C_ATA_CFG_IORDYEN;
>> +
>> + /* Host controller supports upto PIO4 only */
>> + if (mode >= 0 && mode <= 4) {
>
> No need to check -- you won't be passed a mode not specified by your pio_mask.
probably not even worth bthering with a WARN_ON() for this.
.> + writel(ata_cfg, info->ide_addr + S3C_ATA_CFG);
>> + writel(piotime, info->ide_addr + S3C_ATA_PIO_TIME);
>> + }
>> +}
>
> [...]
>
>> +/*
>> + * pata_s3c_data_xfer - Transfer data by PIO
>> + */
>> +unsigned int pata_s3c_data_xfer(struct ata_device *dev, unsigned char *buf,
>> + unsigned int buflen, int rw)
>> +{
>> + struct ata_port *ap = dev->link->ap;
>> + struct s3c_ide_info *info = ap->host->private_data;
>> + void __iomem *data_addr = ap->ioaddr.data_addr;
>> + unsigned int words = buflen >> 1, i;
>> + u16 *data_ptr = (u16 *)buf;
>> +
>> + if (rw == READ)
>> + for (i = 0; i < words; i++, data_ptr++) {
>> + wait_for_host_ready(info);
>> + *data_ptr = readw(data_addr);
>
> Why not just ignore the result?
possibly (void)readw(data_addr);
>> + wait_for_host_ready(info);
>> + *data_ptr = readw(info->ide_addr
>> + + S3C_ATA_PIO_RDATA);
>> + }
It would be nice to have a description of why we're throwing data
away from the FIFO.
>> + else
>> + for (i = 0; i < words; i++, data_ptr++) {
>> + wait_for_host_ready(info);
>> + writel(*data_ptr, data_addr);
>> + }
For the write case, would it be better to read the FIFO free lvel
and then then write that many words each time?
>> + return words << 1;
>> +}
>
> [...]
>
>> +static struct ata_port_operations pata_s3c_port_ops = {
>> + .inherits = &ata_sff_port_ops,
>> + .sff_check_status = pata_s3c_check_status,
>> + .sff_check_altstatus = pata_s3c_check_altstatus,
>> + .sff_tf_load = pata_s3c_tf_load,
>> + .sff_tf_read = pata_s3c_tf_read,
>> + .sff_data_xfer = pata_s3c_data_xfer,
>> + .sff_exec_command = pata_s3c_exec_command,
>> + .sff_dev_select = pata_s3c_dev_select,
>> + .sff_set_devctl = pata_s3c_set_devctl,
>
> I forgot: you also need to override the softreset() method as it
> accesses several taskfile registers and ioread8()/iowrite8() won't
> suffice -- Jeff was too quick to ack the patch. See ata_bus_softreset(),
> ata_devchk(), and ata_sff_wait_after_reset() for the accesses I'm talking
> about...
>
> [...]
>
>> +static int __devinit pata_s3c_probe(struct platform_device *pdev)
>> +{
>> + struct s3c_ide_platdata *pdata = pdev->dev.platform_data;
>> + struct device *dev = &pdev->dev;
>> + struct s3c_ide_info *info;
>> + struct resource *res;
>> + struct ata_port *ap;
>> + struct ata_host *host;
>> + enum s3c_cpu_type cpu_type;
>> + int ret;
>> +
>> + cpu_type = platform_get_device_id(pdev)->driver_data;
>> +
>> + info = devm_kzalloc(dev, sizeof(*info), GFP_KERNEL);
>> + if (!info) {
>> + dev_err(dev, "failed to allocate memory for device data\n");
>> + return -ENOMEM;
>> + }
>> +
>> + info->irq = platform_get_irq(pdev, 0);
>> + if (info->irq < 0) {
>> + dev_err(dev, "could not obtain irq number\n");
>> + ret = -EINVAL;
>> + goto release_device_mem;
>> + }
>> +
>> + res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
>> + if (res == NULL) {
>> + dev_err(dev, "failed to get mem resource\n");
>> + ret = -EINVAL;
>> + goto release_device_mem;
>> + }
>> +
>> + if (!request_mem_region(res->start, resource_size(res), DRV_NAME)) {
>
> Probably should call devm_request_mem_region() if you're using
> devm_ioremap()...
>
>> + dev_err(dev, "error requesting register region\n");
>> + return -EBUSY;
>> + }
>> +
>> + info->ide_addr = devm_ioremap(dev, res->start, resource_size(res));
>> + if (!info->ide_addr) {
>> + dev_err(dev, "failed to map IO base address\n");
>> + ret = -ENOMEM;
>> + goto release_mem;
>> + }
>> +
>> + info->clk = clk_get(&pdev->dev, "cfcon");
>> + if (IS_ERR(info->clk)) {
>> + dev_err(dev, "failed to get access to cf controller clock\n");
>> + ret = PTR_ERR(info->clk);
>> + info->clk = NULL;
We really need to get away from passing a clock name here.
--
Ben
Q: What's a light-year?
A: One-third less calories than a regular year.
next prev parent reply other threads:[~2010-06-11 1:57 UTC|newest]
Thread overview: 11+ messages / expand[flat|nested] mbox.gz Atom feed top
2010-06-10 7:50 [PATCH v3] libata: pata_samsung_cf: Add Samsung PATA controller driver Kukjin Kim
2010-06-10 8:52 ` Jeff Garzik
2010-06-10 8:56 ` Ben Dooks
2010-06-10 9:37 ` Jeff Garzik
2010-06-10 10:43 ` Sergei Shtylyov
2010-06-11 1:57 ` Ben Dooks [this message]
2010-06-11 7:29 ` Kukjin Kim
2010-06-11 9:48 ` Sergei Shtylyov
2010-06-14 6:57 ` Kukjin Kim
2010-06-11 2:24 ` Ben Dooks
2010-06-11 7:41 ` Kukjin Kim
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20100611015744.GC14272@trinity.fluff.org \
--to=ben-linux@fluff.org \
--cc=linux-arm-kernel@lists.infradead.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).