Соответствующие адреса двигателя DMA - PullRequest
0 голосов
/ 19 февраля 2019

Я использую TI AM5728 с ядром 4.1.13 и пытаюсь выполнить DMA с периферийного устройства GPMC в буфер, выделенный в моем драйвере.Я изо всех сил пытался понять, почему ничего не происходит, и это из-за моего непонимания «подходящих» адресов, которые необходимо указывать при настройке DMA.

Я настроил свой DTS таким образом, чтобы мое устройство было дочерним узлом консоли управления групповыми политиками:

&gpmc {
    pinctrl-names="default";
    pinctrl-0 = <&fpga_pins_default>; 
    ranges = <3 0 0x3000000 0x0100000>; /* fpga */

    hs_gpmc: fpga@3,0 { 
        reg = <3 0 0x100000>;

        #address-cells = <1>;
        #size-cells = <1>;
        interrupt-parent = <&gpio1>;
        interrupts = <29 IRQ_TYPE_EDGE_FALLING>;
        dmas = <&edma_xbar 4>;
        dma-names = "rxtx";
        compatible = "lgs,hs-fpga";

        bank-width = <2>;
        .
        . 
        .

Я считаю, что правильно делаю следующее, поскольку беру виртуальное ядроадрес и сопоставление его с адресом DMA:

/* Set up my buffer to store data FROM the GPMC*/
buf = devm_kzalloc(&pdev->dev, HS_GPMC_FPGA_LEN, (GFP_DMA | GFP_KERNEL));
/* Get a DMA address */
data->dma_start = dma_map_single(&pdev->dev, buf, HS_GPMC_FPGA_LEN, DMA_FROM_DEVICE);

Теперь я проверяю, получил ли я контроллер eDMA, запрашивая канал, который соответствует имени "rxtx", используемому общим узлом GPMC:

data->chan = dma_request_slave_channel(&pdev->dev, "rxtx");

и вот узел GPMC в DTS:

gpmc: gpmc@50000000 {
    compatible = "ti,am3352-gpmc";
    ti,hwmods = "gpmc";
    reg = <0x50000000 0x2000>;      /* device IO registers */
    interrupts = <GIC_SPI 15 IRQ_TYPE_LEVEL_HIGH>;
    dmas = <&edma_xbar 4>;
    dma-names = "rxtx";
    gpmc,num-cs = <8>;
    gpmc,num-waitpins = <2>;
    #address-cells = <2>;
    #size-cells = <1>;
    gpio-controller;
    #gpio-cells = <2>;
    interrupt-controller;
    #interrupt-cells = <2>;
    status = "disabled";
};

Наконец, я настроил eDMA:

memset(&data->cfg, 0, sizeof(data->cfg));
data->cfg.direction = DMA_DEV_TO_MEM;
data->cfg.src_addr = HS_GPMC_FPGA_DMA_START_ADDRESS;
data->cfg.src_maxburst = 2;
dmaengine_slave_config(data->chan, &data->cfg);

, где HS_GPMC_FPGA_DMA_START_ADDRESS установлен в 0x3000000 (начальный адресфизическая память моего устройства).

Однако, когда прерывание запускает мой драйвер для запуска транзакции DMA, я вижу, что базовые функции вызываются в драйвере edma, но транзакция GPMC никогда не выполняется и не выполняется.Вызван обратный вызов DMA.

Является ли 0x3000000 действительным адресом для передачи в механизм DMA?

...