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.

[参考译文] RTOS:当外部 RAM 上的全局堆被启用时 FatFs (USB)停止工作(0x60000000)(TM4C129)

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

https://e2e.ti.com/support/microcontrollers/arm-based-microcontrollers-group/arm-based-microcontrollers/f/arm-based-microcontrollers-forum/594607/rtos-fatfs-usb-stops-to-work-when-global-heap-at-external-ram-is-enablad-0x60000000-tm4c129

Thread 中讨论的其他器件:SYSBIOS

工具/软件:TI-RTOS

这是 我们 的.cfg 配置。

VAR HeapMem = xdc.useModule('ti.sysbios.heaps.HeapMem');
var heapMemParams = new HeapMem.Params();
heapMemParams.size = 0x100000;
heapMemParams.sectionName =".external";
heapMemParams.buf = 0x60000000;
heapMemParams.instance.name ="SDRAM";
program.global.SDRAM = HeapMem.create (heapMemParams);

Memory.defaultHeapInstance = Program.global.SDRAM; <.--------------- 第 X 行

  启用此行 X 时,f_write() 函 数会锁定    usvhostenum.c (Tiware/usblib)中的 USBHCSDPipeRead (uint32_t ui32Pipe、uint8_t * pu8Data、uint32_t ui32Size)函数。

我已经使用   外部 RAM 通过 NDK 和其他 TI-RTOS 模块以及 我们使用 ( malloc 和 free)的函数测试了全局堆 、没有问题、但是

 FatFS 存在这个问题, 所以我必须禁用外部 RAM 中的堆  ,因为它可以正常工作, 这会导致  内部使用 malloc/free 的其他模块中的内存限制。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。
    系统中是否还有其他运行的东西? 您使用的是 TI-RTOS 的哪个版本? USBHCPepeRead 中的锁定是什么意思? 将哪些值传递到 USBHDPIPeRead 中?

    注意:我将把您的主题移至器件论坛。 我们将在明天再做一些我们的论坛布局、这将为它做准备。
  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    TI--RTOS 版本: tivac 2_16_00_08

    当 我执行 fwrite 时 ,程序会在 我暂停调试时锁定,它 会在   USBHCPDPIPeRad()内停止。

     为了隔离问题, 我们 执行 的程序只有一个任务, 即打开文件(fopen) 并写入 一些数据(fwrite)和关闭(fclose)。

    当堆位于内部 RAM 中时(无论  外部 RAM 中是否有静态变量),这个 prorgam 运行正常, mas 当我在外部 RAM 中启用全局堆时  

    出现问题。  在调试中、当      外部 RAM 中的全局堆时、我可以使文件 I/O 函数(fwrite()、fread (0)的内部缓冲区高于0x60000000、而在0x20000000以上、否则 、我假设 它 使用 malloc 来创建。

    我 还可以看到 FATF 驱动 程序调用 USBHMSCBlockWrite () ,它调用 USBHSCSIWrite10 , 它调用调用 USBHCSISendCommand,调用 调用 USBHCCDPIPEWrite (位于     调用 DMAUSBTransfer 的 USBHCCDPIPeRead 的同一文件中)。

    我想  、如果问题是在 DMAUSBTransfer()中、并且 Tiva-c 对地址  > 0x600000000的 USB 有一定的 DMA 限制吗?

    0x60000000

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

    uint32_t ui32Pipe = 0x19905440
    uint8_t * pui8Data = 0x20010288
    uint32_t ui32Size = 13

    程序在该循环中停止:

    while (1)

    //
    //检查设备是否已停止请求。
    //
    if (g_sUSBHCD.psUSBINPipes[ui32PipeIdx].iState =ePipeStoned)

    //
    //将大小归零,以便呼叫者知道没有数据
    //读取。
    //
    ui32Size = 0;

    //
    //也没有剩余的字节可读。
    //
    ui32RemainingBytes=0;

    //
    //如果正在使用 DMA,则禁用通道。
    //
    if (bUseDMA = true)

    USBLibDMAChannelDisable (
    G_sUSBHCD.psDMAInstance、
    g_sUSBHCD.psUSBINPipes[ui32PipeIdx].ui8DMAChannel);


    //
    //这是实际的端点号。
    //
    USBHCDClearFeature (
    G_sUSBHCD.psUSBINPipes[ui32PipeIdx].psDevice->ui32Address、
    ui32Pipe、USB_feature_ep_halt);

    //
    //如果出现失速,那么就没有更多的数据出现这种中断
    //输出。
    //
    中断;


    //
    //如果发生任何错误事件,则退出循环。
    //
    if (g_sUSBHCD.ui32IntEvents &(INT_EVENT_DISCONNECT |)
    INT_EVENT_VBUS_ERR |
    INT_EVENT_POWER_FAULT))

    //
    //将管道状态设置为错误。
    //
    G_sUSBHCD.psUSBINPipes[ui32PipeIdx].iState = ePipeError;

    //
    //需要设置为退出大型 while 循环。
    //
    ui32RemainingBytes=0;

    中断;


    //
    //如果数据就绪,则将其返回。
    //
    if (g_sUSBHCD.psUSBINPipes[ui32PipeIdx].iState =ePipeDataReady)

    //
    //如果不使用 DMA,则从 USB 读取数据。 否则
    //数据将已在缓冲区中。
    //
    if (bUseDMA == false)

    //
    //计算要传输和设置传输的字节
    //
    ui32BytesRead =
    ui32RemainingBytes >64? 64: ui32 RemainingBytes;

    //
    //确认数据是从端点读取的。
    //
    MAP_USBHostEndpointDataAck (USB0_BASE、ui32Endpoint);


    //
    //减去从剩余的字节中读取的字节数。
    //
    ui32RemainingBytes-= ui32BytesRead;

    //
    //如果读取的字节少于64字节,则这是一个短整型
    //数据包,不再返回任何数据。
    //
    if (ui32BytesRead < 64)

    //
    //减去未接收到的字节并退出
    //循环。
    //
    ui32Size = ui32Size - ui32RemainingBytes;
    中断;

    其他

    //
    //向前移动缓冲区以接收更多数据到
    //缓冲区。
    //
    pui8Data += 64;

    中断;

    否则、如果(g_sUSBHCD.psUSBINPipes[ui32PipeIdx].iState =ePipeError)

    //
    //发生错误,因此停止此事务并设置
    //字节数设为零。
    //
    ui32Size = 0;
    ui32RemainingBytes=0;

    中断;

    否则、if ((g_sUSBHCD.psUSBINPipes[ui32PipeIdx].iState =
    ePipeReadDMAWait)&&
    (USBLibDMAChannelStatus (g_sUSBHCD.psDMAInstance、
    G_sUSBHCD.psUSBINPipes[ui32PipeIdx].ui8DMAChannel)和
    USBLIBSTATUS_DMA_COMPLETE))

    中断;




    g_sUSBHCD.psUSBINPipes[ui32PipeIdx].iState 的值始终为 ePipeReadDma、因此程序永远不会退出循环。
  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

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

    USB 无法访问外部 RAM。 这是数据表中的表格  

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。
    谢谢、Todd -(抱歉)、但图表(正确)是否注意到"MCU 数据总线"无法访问 SRAM?

    如果这证明了这种情况-您可以描述一下放置在 SRAM 中的"原因和方式"数据-(似乎)将由 MCU 访问。 (这是一个 MCU -图表列出了 CPU - TM4C 不是 CPU。)
  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。
    这似乎有点奇怪。 我将向其中一位 TM4C 工程师提出这方面的问题。
  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。
    感谢您-感谢您-他们可能也希望(更正) CPU。 (CPU 很少有大量专用地址/数据线路、并且没有闪存和 ROM 存储器...)

    因此、在"匆忙的冲撞"下、数据通常通过"剪切/粘贴"到达、然后很难编辑。 (怀疑解释"CPU"和"无 SRAM 访问"的原因-两者都是(不太可能)))