ADI 模拟读写寄存器求解惑
时间:10-02
整理:3721RD
点击:
问题是这样的,如下代码是一个读模拟寄存器堆的操作,有点问题一直弄不明白,不明白的地方在代码后注释了,希望大牛能帮忙解惑。
PUBLIC uint16 ADI_Analogdie_reg_read (uint32 addr)
{
uint32 cur_tick, next_tick;
uint32 adi_rd_data;
if (SCI_FALSE == ADI_IS_Analogdie_reg(addr) )
{
SCI_PASSERT(0, ("ADI_Analogdie_reg_read, addr = 0x%08x is error!", addr));/*assert to do*/
}
SCI_DisableIRQ();
SCI_DisableFIQ();
// wait write fifo empty before adi analog read
cur_tick = next_tick = SCI_GetTickCount();
while(ADI_FIFO_IS_EMPTY == 0)
{
if ( (next_tick - cur_tick) > 60)
{
TM_SendTestPointRequest (0x15170004, (next_tick - cur_tick));
SCI_PASSERT(0, ("ADI Wait fifo empty Timeout!"));/*assert to do*/
}
next_tick = SCI_GetTickCount();
}
// Set read address
REG32(ADI_ARM_RD_CMD) = ((addr)&ADI_ARMREG_ADDR_MASK) | ADI_ARMREG_FLAG_MASK; // ① 这里为什么要先发送一个命令?
// wait read operation complete, RD_data[31] will be cleared after the read operation complete
cur_tick = next_tick;
do
{
adi_rd_data = REG32(ADI_ARM_RD_DATA); // ②为什么这才开始读取数据
//Timeout
if ( (next_tick - cur_tick) > 60)
{
TM_SendTestPointRequest (0x15170002, (next_tick - cur_tick));
SCI_PASSERT(0, ("ADI Read Timeout!"));/*assert to do*/
}
next_tick = SCI_GetTickCount();
}
while(adi_rd_data & ADI_RD_CMD_BUSY_MASK); // ③这个忙标志位具体表示什么意思?是表示总线在忙吗?
// rd_data high part should be the address of the last read operation
if ((adi_rd_data & ADI_ARM_RD_ADDR_MASK) != ((addr & ADI_ARMREG_ADDR_MASK)<<16)) // ④高数据部分为什么一定要等于最后读操作的地址?
{
SCI_PASSERT(0, ("high 13bits rd_data (0x%x) != (0x%x)addr\n",adi_rd_data,addr));/*assert verified*/
}
SCI_RestoreFIQ();
SCI_RestoreIRQ();
return((uint16)(adi_rd_data & ADI_ARM_RD_DATA_MASK)); // ⑤为什么只返回一个半字?而不是字
}
最后⑥就是,为什么读之前与读之后一定要加中断关闭和开启,是为了在读期间锁定寄存器,不让其在读操作时被意外改变而读出不期望的值吗?这就带来一个我还是不理解的问题,就是写寄存器是通过中断写的吗?
以上6个地方实在不明白,请大牛解惑,或者帮忙推荐有什么书籍可以帮我更容易理解这方面的知识点。
查过展讯的datasheet ,SC6531模拟寄存器分为三种:MCU reg / DSP reg / share reg
另外原因是我看到其他寄存器读操作都是直接如下即可:
#define CHIP_REG_GET(reg_addr) (*(volatile uint32 *)(reg_addr))
问题比较多,希望有耐心的大牛解答一下。谢谢!
PUBLIC uint16 ADI_Analogdie_reg_read (uint32 addr)
{
uint32 cur_tick, next_tick;
uint32 adi_rd_data;
if (SCI_FALSE == ADI_IS_Analogdie_reg(addr) )
{
SCI_PASSERT(0, ("ADI_Analogdie_reg_read, addr = 0x%08x is error!", addr));/*assert to do*/
}
SCI_DisableIRQ();
SCI_DisableFIQ();
// wait write fifo empty before adi analog read
cur_tick = next_tick = SCI_GetTickCount();
while(ADI_FIFO_IS_EMPTY == 0)
{
if ( (next_tick - cur_tick) > 60)
{
TM_SendTestPointRequest (0x15170004, (next_tick - cur_tick));
SCI_PASSERT(0, ("ADI Wait fifo empty Timeout!"));/*assert to do*/
}
next_tick = SCI_GetTickCount();
}
// Set read address
REG32(ADI_ARM_RD_CMD) = ((addr)&ADI_ARMREG_ADDR_MASK) | ADI_ARMREG_FLAG_MASK; // ① 这里为什么要先发送一个命令?
// wait read operation complete, RD_data[31] will be cleared after the read operation complete
cur_tick = next_tick;
do
{
adi_rd_data = REG32(ADI_ARM_RD_DATA); // ②为什么这才开始读取数据
//Timeout
if ( (next_tick - cur_tick) > 60)
{
TM_SendTestPointRequest (0x15170002, (next_tick - cur_tick));
SCI_PASSERT(0, ("ADI Read Timeout!"));/*assert to do*/
}
next_tick = SCI_GetTickCount();
}
while(adi_rd_data & ADI_RD_CMD_BUSY_MASK); // ③这个忙标志位具体表示什么意思?是表示总线在忙吗?
// rd_data high part should be the address of the last read operation
if ((adi_rd_data & ADI_ARM_RD_ADDR_MASK) != ((addr & ADI_ARMREG_ADDR_MASK)<<16)) // ④高数据部分为什么一定要等于最后读操作的地址?
{
SCI_PASSERT(0, ("high 13bits rd_data (0x%x) != (0x%x)addr\n",adi_rd_data,addr));/*assert verified*/
}
SCI_RestoreFIQ();
SCI_RestoreIRQ();
return((uint16)(adi_rd_data & ADI_ARM_RD_DATA_MASK)); // ⑤为什么只返回一个半字?而不是字
}
最后⑥就是,为什么读之前与读之后一定要加中断关闭和开启,是为了在读期间锁定寄存器,不让其在读操作时被意外改变而读出不期望的值吗?这就带来一个我还是不理解的问题,就是写寄存器是通过中断写的吗?
以上6个地方实在不明白,请大牛解惑,或者帮忙推荐有什么书籍可以帮我更容易理解这方面的知识点。
查过展讯的datasheet ,SC6531模拟寄存器分为三种:MCU reg / DSP reg / share reg
另外原因是我看到其他寄存器读操作都是直接如下即可:
#define CHIP_REG_GET(reg_addr) (*(volatile uint32 *)(reg_addr))
问题比较多,希望有耐心的大牛解答一下。谢谢!
请把问题详细描述一下 , 可以加注释或者 说行号。
注释好了,之前不是很熟悉。帮忙解答一下,谢谢!
