| .. | .. |
|---|
| 1 | +// SPDX-License-Identifier: GPL-2.0+ |
|---|
| 1 | 2 | /* |
|---|
| 2 | 3 | * Copyright (C) 2015, Michael Lee <igvtee@gmail.com> |
|---|
| 3 | 4 | * MTK HSDMA support |
|---|
| 4 | | - * |
|---|
| 5 | | - * This program is free software; you can redistribute it and/or modify it |
|---|
| 6 | | - * under the terms of the GNU General Public License as published by the |
|---|
| 7 | | - * Free Software Foundation; either version 2 of the License, or (at your |
|---|
| 8 | | - * option) any later version. |
|---|
| 9 | | - * |
|---|
| 10 | 5 | */ |
|---|
| 11 | 6 | |
|---|
| 12 | 7 | #include <linux/dmaengine.h> |
|---|
| .. | .. |
|---|
| 191 | 186 | } |
|---|
| 192 | 187 | |
|---|
| 193 | 188 | static inline void mtk_hsdma_write(struct mtk_hsdam_engine *hsdma, |
|---|
| 194 | | - unsigned reg, u32 val) |
|---|
| 189 | + unsigned int reg, u32 val) |
|---|
| 195 | 190 | { |
|---|
| 196 | 191 | writel(val, hsdma->base + reg); |
|---|
| 197 | 192 | } |
|---|
| .. | .. |
|---|
| 213 | 208 | |
|---|
| 214 | 209 | static void hsdma_dump_reg(struct mtk_hsdam_engine *hsdma) |
|---|
| 215 | 210 | { |
|---|
| 216 | | - dev_dbg(hsdma->ddev.dev, "tbase %08x, tcnt %08x, " \ |
|---|
| 217 | | - "tctx %08x, tdtx: %08x, rbase %08x, " \ |
|---|
| 211 | + dev_dbg(hsdma->ddev.dev, "tbase %08x, tcnt %08x, " |
|---|
| 212 | + "tctx %08x, tdtx: %08x, rbase %08x, " |
|---|
| 218 | 213 | "rcnt %08x, rctx %08x, rdtx %08x\n", |
|---|
| 219 | 214 | mtk_hsdma_read(hsdma, HSDMA_REG_TX_BASE), |
|---|
| 220 | 215 | mtk_hsdma_read(hsdma, HSDMA_REG_TX_CNT), |
|---|
| .. | .. |
|---|
| 225 | 220 | mtk_hsdma_read(hsdma, HSDMA_REG_RX_CRX), |
|---|
| 226 | 221 | mtk_hsdma_read(hsdma, HSDMA_REG_RX_DRX)); |
|---|
| 227 | 222 | |
|---|
| 228 | | - dev_dbg(hsdma->ddev.dev, "info %08x, glo %08x, delay %08x, " \ |
|---|
| 229 | | - "intr_stat %08x, intr_mask %08x\n", |
|---|
| 223 | + dev_dbg(hsdma->ddev.dev, "info %08x, glo %08x, delay %08x, intr_stat %08x, intr_mask %08x\n", |
|---|
| 230 | 224 | mtk_hsdma_read(hsdma, HSDMA_REG_INFO), |
|---|
| 231 | 225 | mtk_hsdma_read(hsdma, HSDMA_REG_GLO_CFG), |
|---|
| 232 | 226 | mtk_hsdma_read(hsdma, HSDMA_REG_DELAY_INT), |
|---|
| .. | .. |
|---|
| 242 | 236 | int i; |
|---|
| 243 | 237 | |
|---|
| 244 | 238 | dev_dbg(hsdma->ddev.dev, "tx idx: %d, rx idx: %d\n", |
|---|
| 245 | | - chan->tx_idx, chan->rx_idx); |
|---|
| 239 | + chan->tx_idx, chan->rx_idx); |
|---|
| 246 | 240 | |
|---|
| 247 | 241 | for (i = 0; i < HSDMA_DESCS_NUM; i++) { |
|---|
| 248 | 242 | tx_desc = &chan->tx_ring[i]; |
|---|
| 249 | 243 | rx_desc = &chan->rx_ring[i]; |
|---|
| 250 | 244 | |
|---|
| 251 | | - dev_dbg(hsdma->ddev.dev, "%d tx addr0: %08x, flags %08x, " \ |
|---|
| 245 | + dev_dbg(hsdma->ddev.dev, "%d tx addr0: %08x, flags %08x, " |
|---|
| 252 | 246 | "tx addr1: %08x, rx addr0 %08x, flags %08x\n", |
|---|
| 253 | | - i, tx_desc->addr0, tx_desc->flags, \ |
|---|
| 247 | + i, tx_desc->addr0, tx_desc->flags, |
|---|
| 254 | 248 | tx_desc->addr1, rx_desc->addr0, rx_desc->flags); |
|---|
| 255 | 249 | } |
|---|
| 256 | 250 | } |
|---|
| .. | .. |
|---|
| 269 | 263 | /* init desc value */ |
|---|
| 270 | 264 | for (i = 0; i < HSDMA_DESCS_NUM; i++) { |
|---|
| 271 | 265 | chan->tx_ring[i].addr0 = 0; |
|---|
| 272 | | - chan->tx_ring[i].flags = HSDMA_DESC_LS0 | |
|---|
| 273 | | - HSDMA_DESC_DONE; |
|---|
| 266 | + chan->tx_ring[i].flags = HSDMA_DESC_LS0 | HSDMA_DESC_DONE; |
|---|
| 274 | 267 | } |
|---|
| 275 | 268 | for (i = 0; i < HSDMA_DESCS_NUM; i++) { |
|---|
| 276 | 269 | chan->rx_ring[i].addr0 = 0; |
|---|
| .. | .. |
|---|
| 419 | 412 | vchan_cookie_complete(&desc->vdesc); |
|---|
| 420 | 413 | chan_issued = gdma_next_desc(chan); |
|---|
| 421 | 414 | } |
|---|
| 422 | | - } else |
|---|
| 415 | + } else { |
|---|
| 423 | 416 | dev_dbg(hsdma->ddev.dev, "no desc to complete\n"); |
|---|
| 417 | + } |
|---|
| 424 | 418 | |
|---|
| 425 | 419 | if (chan_issued) |
|---|
| 426 | 420 | set_bit(chan->id, &hsdma->chan_issued); |
|---|
| .. | .. |
|---|
| 439 | 433 | if (likely(status & HSDMA_INT_RX_Q0)) |
|---|
| 440 | 434 | tasklet_schedule(&hsdma->task); |
|---|
| 441 | 435 | else |
|---|
| 442 | | - dev_dbg(hsdma->ddev.dev, "unhandle irq status %08x\n", |
|---|
| 443 | | - status); |
|---|
| 436 | + dev_dbg(hsdma->ddev.dev, "unhandle irq status %08x\n", status); |
|---|
| 444 | 437 | /* clean intr bits */ |
|---|
| 445 | 438 | mtk_hsdma_write(hsdma, HSDMA_REG_INT_STATUS, status); |
|---|
| 446 | 439 | |
|---|
| .. | .. |
|---|
| 457 | 450 | if (gdma_next_desc(chan)) { |
|---|
| 458 | 451 | set_bit(chan->id, &hsdma->chan_issued); |
|---|
| 459 | 452 | tasklet_schedule(&hsdma->task); |
|---|
| 460 | | - } else |
|---|
| 453 | + } else { |
|---|
| 461 | 454 | dev_dbg(hsdma->ddev.dev, "no desc to issue\n"); |
|---|
| 455 | + } |
|---|
| 462 | 456 | } |
|---|
| 463 | 457 | spin_unlock_bh(&chan->vchan.lock); |
|---|
| 464 | 458 | } |
|---|
| .. | .. |
|---|
| 473 | 467 | if (len <= 0) |
|---|
| 474 | 468 | return NULL; |
|---|
| 475 | 469 | |
|---|
| 476 | | - desc = kzalloc(sizeof(struct mtk_hsdma_desc), GFP_ATOMIC); |
|---|
| 470 | + desc = kzalloc(sizeof(*desc), GFP_ATOMIC); |
|---|
| 477 | 471 | if (!desc) { |
|---|
| 478 | 472 | dev_err(c->device->dev, "alloc memcpy decs error\n"); |
|---|
| 479 | 473 | return NULL; |
|---|
| .. | .. |
|---|
| 539 | 533 | mtk_hsdma_chan_done(hsdma, chan); |
|---|
| 540 | 534 | } |
|---|
| 541 | 535 | |
|---|
| 542 | | -static void mtk_hsdma_tasklet(unsigned long arg) |
|---|
| 536 | +static void mtk_hsdma_tasklet(struct tasklet_struct *t) |
|---|
| 543 | 537 | { |
|---|
| 544 | | - struct mtk_hsdam_engine *hsdma = (struct mtk_hsdam_engine *)arg; |
|---|
| 538 | + struct mtk_hsdam_engine *hsdma = from_tasklet(hsdma, t, task); |
|---|
| 545 | 539 | |
|---|
| 546 | 540 | mtk_hsdma_rx(hsdma); |
|---|
| 547 | 541 | mtk_hsdma_tx(hsdma); |
|---|
| .. | .. |
|---|
| 553 | 547 | int i; |
|---|
| 554 | 548 | |
|---|
| 555 | 549 | chan->tx_ring = dma_alloc_coherent(hsdma->ddev.dev, |
|---|
| 556 | | - 2 * HSDMA_DESCS_NUM * sizeof(*chan->tx_ring), |
|---|
| 550 | + 2 * HSDMA_DESCS_NUM * |
|---|
| 551 | + sizeof(*chan->tx_ring), |
|---|
| 557 | 552 | &chan->desc_addr, GFP_ATOMIC | __GFP_ZERO); |
|---|
| 558 | 553 | if (!chan->tx_ring) |
|---|
| 559 | 554 | goto no_mem; |
|---|
| .. | .. |
|---|
| 574 | 569 | { |
|---|
| 575 | 570 | if (chan->tx_ring) { |
|---|
| 576 | 571 | dma_free_coherent(hsdma->ddev.dev, |
|---|
| 577 | | - 2 * HSDMA_DESCS_NUM * sizeof(*chan->tx_ring), |
|---|
| 578 | | - chan->tx_ring, chan->desc_addr); |
|---|
| 572 | + 2 * HSDMA_DESCS_NUM * sizeof(*chan->tx_ring), |
|---|
| 573 | + chan->tx_ring, chan->desc_addr); |
|---|
| 579 | 574 | chan->tx_ring = NULL; |
|---|
| 580 | 575 | chan->rx_ring = NULL; |
|---|
| 581 | 576 | } |
|---|
| .. | .. |
|---|
| 655 | 650 | struct mtk_hsdma_chan *chan; |
|---|
| 656 | 651 | struct mtk_hsdam_engine *hsdma; |
|---|
| 657 | 652 | struct dma_device *dd; |
|---|
| 658 | | - struct resource *res; |
|---|
| 659 | 653 | int ret; |
|---|
| 660 | 654 | int irq; |
|---|
| 661 | 655 | void __iomem *base; |
|---|
| .. | .. |
|---|
| 669 | 663 | return -EINVAL; |
|---|
| 670 | 664 | |
|---|
| 671 | 665 | hsdma = devm_kzalloc(&pdev->dev, sizeof(*hsdma), GFP_KERNEL); |
|---|
| 672 | | - if (!hsdma) { |
|---|
| 673 | | - dev_err(&pdev->dev, "alloc dma device failed\n"); |
|---|
| 666 | + if (!hsdma) |
|---|
| 674 | 667 | return -EINVAL; |
|---|
| 675 | | - } |
|---|
| 676 | 668 | |
|---|
| 677 | | - res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
|---|
| 678 | | - base = devm_ioremap_resource(&pdev->dev, res); |
|---|
| 669 | + base = devm_platform_ioremap_resource(pdev, 0); |
|---|
| 679 | 670 | if (IS_ERR(base)) |
|---|
| 680 | 671 | return PTR_ERR(base); |
|---|
| 681 | 672 | hsdma->base = base + HSDMA_BASE_OFFSET; |
|---|
| 682 | | - tasklet_init(&hsdma->task, mtk_hsdma_tasklet, (unsigned long)hsdma); |
|---|
| 673 | + tasklet_setup(&hsdma->task, mtk_hsdma_tasklet); |
|---|
| 683 | 674 | |
|---|
| 684 | 675 | irq = platform_get_irq(pdev, 0); |
|---|
| 685 | | - if (irq < 0) { |
|---|
| 686 | | - dev_err(&pdev->dev, "failed to get irq\n"); |
|---|
| 676 | + if (irq < 0) |
|---|
| 687 | 677 | return -EINVAL; |
|---|
| 688 | | - } |
|---|
| 689 | 678 | ret = devm_request_irq(&pdev->dev, irq, mtk_hsdma_irq, |
|---|
| 690 | 679 | 0, dev_name(&pdev->dev), hsdma); |
|---|
| 691 | 680 | if (ret) { |
|---|