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.

DM8168 MCBSP寄存器配置



你好,我参照mcbsp.c编写了个简单的字符设备,配置DM8168 MCBSP,配置寄存器失败。

写入RCR2寄存器 (0x47000118)的值为0x01后,读取值为0, 设置SPCR2( 0x470000110) 为0xc0, 读取值为0.

读取 XBUFFSTAT(0x470000B4) 的值为0x80 

请问还有哪些步骤需要操作,才能正常配置寄存器?

  • Tom,

    你用DVR RDK提供的mem_rdwr.out工具可以正确写入你在驱动里面配置的寄存器么?如果可以,请检查一下你的驱动。如果不可以,请检查一下mcbsp相关时钟等是否使能/配置。

  • 你好,

    我使用mem_rdwr.out工具进行了如下操作,

    加载驱动前使用mem_rdwr.out读取
    地址                   值                    寄存器
    0x48181400 (08302102)  CM_ALWON_L3_SLOW_CLKSTCTRL[12](CLKACTIVITY_MCBSP_AUX_GCLK=0)
    0x4818154C (00030000) CM_ALWON_MCBSP_CLKCTRL( MODULEMODE[1-0]=0      IDLEST[17-16]=3)

    加载我编写的驱动后,再次使用mem_rdwr.out读取

    地址                 值                    寄存器

    0x48181400 (08303102) CM_ALWON_L3_SLOW_CLKSTCTRL[12](CLKACTIVITY_MCBSP_AUX_GCLK=1)
    0x4818154C (00000002) CM_ALWON_MCBSP_CLKCTRL(  MODULEMODE[1-0]=2      IDLEST[17-16]=0)

    按照寄存器说明,是不是表示时钟已经使能?

    但是使用mem_rdwr.out对SYSCON(0x47000010)读取值为0x210,与驱动中 SYSCON(0x47000010)写入0x214,读取为0x210。

    使用mem_rdwr.out 对0x47000114写入 0xc,写入失败。

    请问还有些配置需要操作?

    ./mem_rdwr.out --rd 47000000 100

    0x47000000: EE6477D7
    0x47000004: 00000000
    0x47000008: 00000000
    0x4700000c: 00000000
    0x47000010: 00000210
    0x47000014: 00000000
    0x47000018: 00000000
    0x4700001c: 00000000
    0x47000020: 00000000
    0x47000024: 00000000
    0x47000028: 00002000
    0x4700002c: 00000001
    0x47000030: 00000000
    0x47000034: 00000000
    0x47000038: 00000000
    0x4700003c: 00000000
    0x47000040: 00000000
    0x47000044: 00000000
    0x47000048: 00000000
    0x4700004c: 00000000
    0x47000050: 00000000
    0x47000054: 00000000
    0x47000058: 00000000
    0x4700005c: 00000000
    0x47000060: 00000000
    0x47000064: 00000000
    0x47000068: 00000000
    0x4700006c: 00000000
    0x47000070: 00000000
    0x47000074: 00000000
    0x47000078: 00000000
    0x4700007c: 00000036
    0x47000080: 00000000
    0x47000084: 00000000
    0x47000088: 00000000
    0x4700008c: 00000000
    0x47000090: 00000000
    0x47000094: 00000000
    0x47000098: 00000000
    0x4700009c: 00000000
    0x470000a0: 00000112
    0x470000a4: 00000000
    0x470000a8: 00000000
    0x470000ac: 00001008
    0x470000b0: 00000808
    0x470000b4: 00000080
    0x470000b8: 00000000
    0x470000bc: 00000084
    0x470000c0: 00000000
    0x470000c4: 00000000
    0x470000c8: 00000000
    0x470000cc: 00000000
    0x470000d0: 00000000
    0x470000d4: 00000000
    0x470000d8: 00000000
    0x470000dc: 00000000
    0x470000e0: 00000000
    0x470000e4: 00000000
    0x470000e8: 00000000
    0x470000ec: 00000000
    0x470000f0: 00000000
    0x470000f4: 00000000
    0x470000f8: 00000000
    0x470000fc: 00000000
    0x47000100: 00000000
    0x47000104: 00000000
    0x47000108: 00000000
    0x4700010c: 00000000
    0x47000110: 00000000
    0x47000114: 00000000
    0x47000118: 00000000
    0x4700011c: 00000000
    0x47000120: 00000000
    0x47000124: 00000000
    0x47000128: 00000000
    0x4700012c: 00000000
    0x47000130: 00000000
    0x47000134: 00000000
    0x47000138: 00000000
    0x4700013c: 00000000
    0x47000140: 00000000
    0x47000144: 00000000
    0x47000148: 00000000
    0x4700014c: 00000000
    0x47000150: 00000000
    0x47000154: 00000000
    0x47000158: 00000000
    0x4700015c: 00000000
    0x47000160: 00000000
    0x47000164: 00000000
    0x47000168: 00000000
    0x4700016c: 00000000
    0x47000170: 00000000
    0x47000174: 00000000
    0x47000178: 00000000
    0x4700017c: 00000000
    0x47000180: 00000000
    0x47000184: 00000000
    0x47000188: 00000000
    0x4700018c: 00000000

  • 你好,

    你是否使用的是ti网站上最新的TRM?

    为什么要0x47000114写入0xc?这个寄存器的bit2/3都是状态值,而且bit2是只读的?

    114h SPCR1_REG McBSP Serial Port Control Register 1

    3 RSYNCERR Receive Synchronization Error.
    (Writing 0 to this bit clear the legacy receive interrupt if asserted due to RSYNCERROR condition).
          0 No synchronization error.
          1 Synchronization error detected by McBSP.


    2 RFULL Receive Shift Register (RSR [1,2]) Full.
              0 RB is not in overrun condition.
              1 DRR is not read, RB is full and RSR is also full with new word.

    也确认一下mcbsp的时钟源是否有选择:

    https://e2e.ti.com/support/dsp/davinci_digital_media_processors/f/716/t/468960

  • 你好:

          我寄存器基值改成0x47000100,通过poll模式已经可以接受数据,

    如下为寄存器配置值

    SYSCON:0x00000214
    DRR: 0x00000055
    DXR: 0x00000000
    SPCR2: 0x00000203
    SPCR1: 0x00000007
    RCR2: 0x00000000
    RCR1: 0x00000000
    XCR2: 0x00000001
    XCR1: 0x00000000
    SRGR2: 0x0000000f
    SRGR1: 0x00000101
    MCR2: 0x00000000
    MCR1: 0x00000000
    PCR0: 0x00000001
    RCERA: 0x00000000
    RCERB: 0x00000000
    PCR: 0x00000001
    THRSH2: 0x00000000
    THRSH1: 0x00000007
    XCCR: 0x00000000
    RCCR: 0x00000008
    XBUFFSTAT: 0x00000080
    RBUFFSTAT: 0x00000080
    WAKEUPEN: 0x00000408

    但是edma处理没有正常工作。RRDY位已经位1,TRM上mcbsp IRQ位86 ,edma 的MCBSP_RX 位15,均已申请。

    以为edma相关代码,请问设置上是否有问题?

    dev->rx_dma_buf = kzalloc(DMA_BLOCK_SIZE, GFP_KERNEL | GFP_DMA);
    if (!dev->rx_dma_buf){
    dev_err(dev->dev, "McBSP RX kzalloc() failed\n");
    return -ENOMEM;
    }

    r = edma_alloc_channel(dev->rx_dma_sync, ti816x_mcbsp_rx_edma_callback, dev, EVENTQ_0);
    if(r<0){
    dev_err(dev->dev,"Unable to request DMA channel for MCBSP RX\n");
    goto error_channel;
    }

    dev->rx_dma_channel = r;
    printk(KERN_INFO "McBSP RX EDMA on channel %d\n",dev->rx_dma_channel);

    dev->rx_dma_addr = dma_map_single(dev->dev, dev->rx_dma_buf, DMA_BLOCK_SIZE,DMA_FROM_DEVICE);
    if (dma_mapping_error(dev->dev, dev->rx_dma_addr)) {
    dev_err(dev->dev, "Couldn't DMA map a %d bytes RX buffer\n",DMA_BLOCK_SIZE);
    if (dev->rx_dma_buf != NULL)
    dma_unmap_single(NULL, dev->rx_dma_addr, DMA_BLOCK_SIZE, DMA_FROM_DEVICE);
    goto error_map;
    }

    edma_set_transfer_params(dev->rx_dma_channel,TI816x_DMA_DATA_TYPE_S32, 1, 1, 0, ASYNC);
    edma_set_src(dev->rx_dma_channel,dev->rx_reg, INCR, W8BIT);
    edma_set_dest(dev->rx_dma_channel,dev->rx_dma_addr, INCR, W8BIT);
    edma_set_src_index(dev->rx_dma_channel, 0, 0);
    edma_set_dest_index(dev->rx_dma_channel,TI816x_DMA_DATA_TYPE_S8, 0);

    edma_start(dev->rx_dma_channel);


  • 你好,

    请问你的fifo深度和EDMA的配置是否匹配?

    建议EDMA/fifo深度的部分参考mcasp的相关代码,这部分是类似的。

  • 你好:

    我EDMA 参数设置如下,B_CNT = 1;

    /* set to A-synchronized mode acnt*bcnt triger edma*/
    param.opt = TCINTEN | // Transfer complete interrupt is enabled
                         EDMA_TCC(channel) | // Transfer complete code
                          (0 << 8) | // FWID FIFO width is 8-bit
                          1; // Source address mode. Constant addressing (CONST) mode

    param.src = 0x47000000;    //TI816x_MCBSP_BASE + MCBSP_DRR ;

    param.a_b_cnt = (B_CNT << 16) | 0x1;
    param.dst = buf_phyaddr;
    param.src_dst_bidx = 0x00010000; // src_inx = 0 fix src register
    param.link_bcntrld =    (B_CNT << 16) | 0xFFFF ;
    param.src_dst_cidx = 0 ;
    param.ccnt = 1;

    但是 mcbsp rccr 寄存器设置如下,RDMAEN 置0,按照TRM的意思,应该是关闭DMA请求,但是配置EDMA参数,edma_start()后,rx_edma_callback还是能进入。请问是那部分寄存器设置有问题?还是EDMA配置有问题?

    //RCCR_RFULL_CYCLE;

  • Tom,

    你是想不使用EDMA来搬移McBSP的数据么?如果是,请disable/clear EER/EERH里面相应event的bit位。

  • 你好,

    我希望使用EDMA来搬移McBSP的数据。McBSP做salve模式,Master 为FPGA。

    但是在配置完McBSP寄存器和EDMA之后,无论FPGA是否发送数据,EDMA的rx_dma_callback 函数都能进入,而且状态为DMA_COMPLETED。

    这个很奇怪,所以我试着RDMAEN 置0,发现还能触发EDMA工作。

    还有一个疑问是:在调用完edma_start()后rx_dma_callback进入后,不会再次进入了。

    所以这个现象是EDMA配置有问题还是McBSP寄存器配置的问题。

    McBSP寄存器参数配置如下:

    mcbsp_config.rcr1 = RCR1_RFRLEN1(TI81XX_MCBSP_WORD_8) | 
                                       RCR1_RWDLEN1(TI81XX_MCBSP_WORD_8); 
    mcbsp_config.xcr1 = XCR1_XFRLEN1(TI81XX_MCBSP_WORD_8) | 
                                       XCR1_XWDLEN1(TI81XX_MCBSP_WORD_8); 
    mcbsp_config.rcr2 = RCR2_RDATDLY(1); 
    mcbsp_config.xcr2 = XCR2_XDATDLY(1);

    mcbsp_config.pcr0 = PCR_CLKRP; 
    mcbsp_config.srgr1 = SRGR1_FWID(1) | 
                                         SRGR1_CLKGDV(1) ; 
    mcbsp_config.srgr2 = SRGR2_FPER(16); 

    mcbsp_config.spcr1 = SPCR1_RINTM(0);
    mcbsp_config.spcr2 = SPCR2_FREE; 
    mcbsp_config.rccr = RCCR_RDMAEN; 


  • Tom,

    应该不需要吧。你有参考过mcasp相关部分么?是类似。