This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

[参考译文] PROCESSOR-SDK-AM62A:如何在 Linux 中设置 GPIO 自动触发 DMA 传输?

Guru**** 2396115 points


请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

https://e2e.ti.com/support/processors-group/processors/f/processors-forum/1477988/processor-sdk-am62a-how-to-set-up-gpio-auto-trigger-a-dma-transfer-in-linux

器件型号:PROCESSOR-SDK-AM62A

工具与软件:

您好!

我的驱动程序和应用几乎成功地使用 DMA 通过 QSPI 接口从 ASIC 传输数据。 我仍然有两个问题、一个是在另一个帖子中查看的数据损坏、另一个问题是我的系统有太多的中断延迟、GPIO IRQ 处理程序无法可靠地启动 DMA 传输。  我希望、使用 GPIO 自动触发来启动 DMA 传输可以解决这个问题。   我看到了另一篇介绍 QNX 流程的文章、但我正在为操作系统使用 Linux。  有人能举个例子、说明如何在 Linux 中实现这一点吗?

我假设按顺序更改.dts 文件。  以下是驱动程序的节点。  要将 GPIO 中断更改为自动触发以及在驱动程序代码中更改、需要进行哪些更改?

谢谢!

胜利

对象0 (&O)
               状态="正常";
               pinctrl-names ="默认值";
               pinctrl-0 =<&MAIN_ospi0_PINS_DEFAULT>;
               兼容="SLQ、QSPI-NOR";
               REG =<0x00 0x0fc40000 0x00 0x100>、
                     <0x05 0x00000000 0x01 0x00000000>;

               时钟名称="slq-clk";

               memory-region =<&SLQ_Rx_region>;

               中断名称="SLQ-IRQ";
               INTERRUPT-PARENT =<&MAIN_GPIO0>;
               中断=<62 IRQ_TYPE_EDGE_FALLING>;
               GPIO-IRQ =<&MAIN_GPIO0 62 GPIO_ACTIVE_LOW>;

               maxwell0:am62x@0{
                       状态="正常";
                       IS-DUAL =<0>;
                       num-cs = 1>;
                       SPI-TX-BUS-WIDTH =<1>;
                       SPI-Rx-BUS-width =<4>;
                       兼容="Trimble、Maxwell-slq0"、"JEDEC、SPI-NOR";
                       REG =<0x0>;
                       spi-max-frequency =<50000000>;
                       CDN、读取延迟=<50>;
                       cdns, tshsl-ns =<4>;
                       cdns, tsd2d-ns =<4>;
                       cdns,tchsh-ns =<4>;
                       cdns, tslch-ns =<4>;
               };

};

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好、Victor:

    通过 GPIO 触发 DMA 需要在 L2G 模块中配置 GPIO 中断、但内核没有此功能的驱动程序、因此目前可以在 Linux 中直接使用 GPIO 触发 DMA。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!

    哪些与 L2G 模块相关的功能可用?  或许我可以破解一些能为我所用的东西。  任何帮助(例如此 L2G 模块的示例或代码)都将非常有用。

    我识别你的名字。  几年前、您帮助其他人完成了 GPMC DMA 的工作。  我接受了这项工作、并在我的系统上完成了这项工作。   借助该功能、我唯一面临的问题是会弹出一个不频繁的数据损坏。  我正尝试将其向下跟踪。

    谢谢!

    胜利

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好、Victor:

    提供哪些与 L2G 模块相关的功能?  或许我可以破解一些能为我所用的东西。  此 L2G 模块的任何帮助(例如示例或代码)都将非常有用。

    是的、它是"可堆叠的"。 让我们稍后再回来讨论这个问题。

    我承认您的名字。  几年前、您帮助其他人完成了 GPMC DMA 的工作。  我接受了这项工作、并在我的系统上完成了这项工作。  [报价]

    您是否参考了以下 e2e 主题?

    https://e2e.ti.com/support/processors-group/processors/f/processors-forum/1337943/am62a3-linux-dma-identifiers-for-gpmc-device-register-to-memory-transfer

    唯一一个与此功能有关的问题是将弹出少量损坏数据。  我正试图跟踪这一情况。

    我想知道数据损坏问题的更多详细信息、看看我们是否可以解决它、而不是对直接触发 DMA 的 GPIO 破解 L2G。

    问题是否似乎是 DMA 传输偶尔安排得较晚、导致数据源溢出? 如果是、您是否尝试过使用具有 CPU 隔离和 IRQ 关联性的 RT 内核? 我使用该方法解决了不同客户的 DMA 传输调度问题。

    [/quote]
  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!

    是的、我接管了 Craig Boardman 的工作、我能够使其工作。  但是、是否需要使用 GPIO 触发和 GPMC DMA 工作是两个不同的问题。

    由于这个问题、我需要 GPIO 触发器:

    https://e2e.ti.com/support/processors-group/processors/f/processors-forum/1476789/sk-am62-dma-has-corrupt-data-reading-using-ospi-controller/5671149#5671149

    由于缺少 GPIO 内核相关性、有时 GPIO 触发中断时、由于内核0上运行的其他中断、CPU 无法及时启动 DMA 传输。  我希望此自动触发器能够解决这个问题。   现在我的代码在 GPIO 触发之前设置 DMA 传输方式。 一旦 GPIO 触发、IRQ 处理程序只会调用 dma_async_issue_pending ()来启动 DMA 传输。  我认为、需要将函数移至 DMA 传输的设置位置、并更改为等待 GPIO 触发事件。  我还需要知道如何将 GPIO 触发事件破解给 L2G。

    至于我看到的损坏数据、它与 CPU 无法及时启动 DMA 进程无关。  我认为损坏的数据可能与 GPMC DMA 问题有关。

    GPMC DMA 数据损坏与数据溢出无关。  在此应用中、软件请求特定数量的数据、而我们的 ASIC 生成该数量的数据并停止。  不使用 DMA 时没有问题。  我们现在计划使用 FPGA 测试此应用、但要将测试代码添加到 FPGA 以生成已知模式、以便我们可以通过 DMA 验证数据是否损坏。

    BTW、还有一个您过去曾处理过的问题、我也曾发布过。   您已回答一个问题、即 DMA 应在循环模式下工作。  我在去年中间发布了一份关于如何使 DMA 在 SPI 传输的循环模式下工作的申请。 有人回答了、但从不跟进。  我有 DMA 可以工作、但问题是每次传输、我必须启动 DMA、这完全是在浪费时间。  我不知道为什么 TI 从不对我负责实施 DMA 循环模式。  您能否提供一些有关如何设置 DMA 以使用循环模式从 SPI 端口读取数据的见解?  目前、如果我尝试设置循环模式、内核将出错。

    谢谢!

    胜利

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好、Victor:

    很抱歉迟到了响应。 我在几天内完成要交付的工作、没有足够的时间查看您的问题。

    OSPI 接口不在我的支持范围内、我不熟悉它、但它的内核驱动程序似乎使用了与我为其他客户执行的 GPMC 驱动程序中使用的 UDMA 函数不同的功能、因此我不确定启用循环模式有多容易或可能。 我还需要查看 uDMA 驱动程序、以了解具体工作范围或是否可以为 OSPI DMA 请求启用 GPIO 直接触发。 如果不是在星期五、我希望下周能有时间。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!

    如果您能帮助 GPIO 触发器首先在 Linux 中正常工作、我将不胜感激。  如果您能向我展示如何破解代码、那么现在就足够了。

    我还没有在另一篇文章中听到关于 DMA 传输损坏的数据的消息。  我正在努力解决这一问题、看看这一问题是否更加普遍。  我发现的任何东西都将被放在那个帖子上。

    至于 SPI DMA 上的循环模式、它位于列表底部、因为它正在工作但效率不高。

    谢谢!

    胜利

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好、Victor:

    在花时间开始演示之前、请查看以下 e2e 主题、其中我帮助客户启用了 GPIO 触发 DMA。 该线程非常日志化、可能需要您花一些时间来消化。

    启用 GPIO 直接触发 DMA 的挑战之一是将 GPIO 组中断映射到 L2G 模块中的 DMA 通道。 我认为、该映射未记录在 TRM 中。

    https://e2e.ti.com/support/processors-group/processors/f/processors-forum/1200987/am625-rerouting-interrupt-to-dma-event-and-dma_dev_to_mem-channel-selection

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!

    虽然与 GPMC 接口有一些相似之处、但我在一些方面也有疑问。 当 ASIC 中的 FIFO 超过阈值时、数据传输从中断线路断言为低电平开始、而当从 FIFO 读取足够的数据时、中断线路断言为低电平。 使用 QSPI 从 FIFO 读取数据。

    低级驱动程序的工作方式是首先设置 DMA 传输、如下所示:

    Tx = dmaengine_prep_dma_memcpy (Rx_chan、dma_dst、dma_src、buffer_len、flags);
    如果(!TX){
       dev_err (dev、"device_prep_dma_memcpy error\n");
    }

    tx->callback = SLQ_Rx_DMA_CALLBACK;
    tx->callback_param = cqspi;
    Cookie = TX->TX_Submit (TX);
    reinit_completion (&rx_dma_complete);

    RET = DMA_SUBMIT_ERROR (Cookie);
    如果(ret){
       dev_err (dev、"dma_submit_error %d\n"、cookie);
    }

    软件随后暂停、直到中断有效;在 IRQ 处理程序中、通过调用 dma_asynchron_issue_pending (Rx_CHAN)来启动 DMA 传输。

    我有以下问题:

    1) 1)我的中断是一个下降沿。 DMASS0_INTAGGR_0寄存器的位31仅接受上升沿的脉冲事件。  我是否需要在中断线上插入触发器以生成上升沿?
    2) 2)我是否使用相同的 BCHAN_EVT_OFFSET 0xc400?  如果没有、我应该使用什么?
    3) 3)我使用 GPIO0_12。  我还使用 GPIO0_13和 GPIO0_14作为输入、但不用作中断。 因此、可以像在上一篇文章中那样使用相同的 GPIO 组中断。
    4) 4)我是否使用相同的 U-Boot 补丁?  我在 uboot 目录中也没有看到 rm-cfg.yam1文件。 如果我需要使用该补丁、 我需要确定该补丁的目标位置。
    5)我认为 uC->config.tr_trigger_type 需要设置为1或2。 但我无法设置它。  我在器件树的 OSPI 节点中添加了 DMA =<&MAIN_BCDMA 1 0 0>;。 但当我打印出 uC->config.tr_trigger_type 的值时、该值仍然为0。  以下是器件树中的 OSPI 节点。  我是否需要      在下面注释掉中断名称、中断父级、中断或 GPIO-IRQ?
     

    对象0 (&O)
           状态="正常";
           pinctrl-names ="默认值";
           pinctrl-0 =<&MAIN_ospi0_PINS_DEFAULT>;
           兼容="SLQ、QSPI-NOR";
           REG =<0x00 0x0fc40000 0x00 0x100>、
                 <0x05 0x00000000 0x01 0x00000000>;

           时钟名称="slq-clk";

           memory-region =<&SLQ_Rx_region>;

           DMA =<&MAIN_BCDMA 1 0 0>;
           DMA-names ="Rx";
           中断名称="SLQ-IRQ";
           INTERRUPT-PARENT =<&MAIN_GPIO0>;
           中断=<12 IRQ_TYPE_EDGE_FALLING>;
           GPIO-IRQ =<&MAIN_GPIO0 12 GPIO_ACTIVE_LOW>;

           maxwell0:am62x@0{
                   状态="正常";
                   IS-DUAL =<0>;
                   num-cs = 1>;
                   SPI-TX-BUS-WIDTH =<1>;
                   SPI-Rx-BUS-width =<4>;
                   兼容="Trimble、Maxwell-slq0"、"JEDEC、SPI-NOR";
                   REG =<0x0>;
                   spi-max-frequency =<50000000>;
                   CDN、读取延迟=<50>;
                   cdns, tshsl-ns =<4>;
                   cdns, tsd2d-ns =<4>;
                   cdns,tchsh-ns =<4>;
                   cdns, tslch-ns =<4>;
           };
    };


    这就是我现在要回答的所有问题。  我相信随着我的进一步发展、我会有更多的选择。

    谢谢!

    胜利

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好、Victor:

    我今天花了一些时间对此进行更深入的探讨。 我不太相信在没有 DMA 控制器的技术细节或者没有 TI 的密切技术支持的情况下、就可以完成这些工作。 但这些选项都不可用、除了 TRM、我们没有任何其他公共 DMA 文档、我们也不提供 SDK 中不提供的软件功能/特性支持。

    除了您询问的5个有关 GPIO 中断路由的问题外、第一个问题是 OSPI 驱动程序中的 dmaengine_prep_dma_memcpy ()间接调用的 DMA 函数 udma_prep_dma_memcpy ()不支持外部触发。 因此在发生 GPIO 中断事件之前、不会阻止它。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好、Victor:

    在离线电子邮件中、此项的要求是"GPIO 触发 OSPI 循环模式"。 我想确认这是否是您提出的问题。 该要求包括两项不相关的任务:为 OSPI 添加 DMA 循环模式、以及启用 GPIO 触发 DMA。

    如果需要这样做、我想询问 OSPI ASIC 用例的详细信息、以便将其移植到我的 EVM 设置中、从而实现循环模式和 GPIO 触发。

    您曾提到您不使用驱动程序 spi-cadence-quadspi.c、而是让您自己的驱动程序与 ASIC 通信。 您能否共享驱动程序代码? spi-cadence-quaspi.c 位于 SPI 框架中、实际上不能使用 DMA 循环模式。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    我使用了 spi-cadency-quadspi.c 来生成我自己的驱动程序。   它基本上是一个简化版本、其中它只需要处理一条消息。

    我将私下向您发送我的司机电子邮件。

    为了使您现在能够进入我所在的位置、您需要以某种方式生成10Hz GPIO 中断、这将启动该 DMA 传输。  您无需担心数据的发送。  数据帧的长度可以是1024个时钟。  一旦 OSPI 控制器发送出数据帧、您应该会获得 RX 完成中断。  由于您不必担心传入数据、因此您可以为下一个 GPIO 中断设置 DMA 传输。

    是的、我需要更改当前的 GPIO 中断来唤醒 IRQ 处理程序、以启动 DMA 传输到 GPIO 触发器自动启动 GPIO 传输。   由于 CPU0上有多个中断、因此该处理程序的中断延迟一直有效。

    我还需要循环模式、因为如果没有该模式、我必须在 RX 完成中断期间设置下一个传输。  我希望避免这项不必要的工作。

    希望在全部完成后、将没有 IRQ 处理程序、并且将只在初始化时执行一次用于启动 DMA 传输的 dmaengine...()调用。

    谢谢!

    胜利

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好、Victor:

    我将通过电子邮件私下向您发送我的驱动程序。

    谢谢、它将会很有帮助。

    为了让您立即走到我所在的位置、您需要以某种方式生成10Hz GPIO 中断、从而启动此 DMA 传输。  [报价]

    在初始驱动程序开发期间、我将使 GPIO 输出引脚环接到 GPIO 输入引脚、这样便可手动控制 GPIO 输入事件。 然后、我将使 PWM 引脚循环到 GPIO 输入引脚以获得10Hz 的 GPIO 中断。