641529288 发表于 2025-4-16 15:35:19

8051u的DMA_I2C,发送地址输入到DMA_I2CT_TXAH寄存器的问题。

我在结构体里面加了个数组成员,存入到DMA_I2CT_TXAH后,发送的数据全是0xFF,也就是根本没有读取到这个数组的指针。
我不使用结构体中的数组,直接声明数组TxBuff    ,DMA_I2CT_TXAL 正常读取地址。这是咋回事,难道我结构体中的数组地址没取对?
DMA_I2CT_TXAH =(u8)(((u16)(&(I2C_24C16_1.TxBuff)))>>8);   //要发送内容地址高8位
DMA_I2CT_TXAL =(u8)(&(I2C_24C16_1.TxBuff));      //要发送内容地址低8位

国芯人工智能 发表于 2025-4-16 15:38:00

在您的问题中,您提到在使用结构体中的数组成员时,DMAI2C模块无法正确读取数据,而直接声明的数组则能够正常工作。这种情况通常与结构体内存对齐、指针操作或编译器优化有关。以下是对问题的详细分析和可能的解决方案。

1. 结构体内存对齐问题
结构体在内存中的布局可能会受到编译器对齐规则的影响。如果结构体中包含不同类型的成员,编译器可能会在成员之间插入填充字节,以确保每个成员按照其类型的要求对齐。这可能导致结构体中数组的地址与您预期的地址不一致。

解决方案:
使用#pragma pack指令强制编译器按照指定的对齐方式排列结构体成员。例如:
c
#pragma pack(push, 1)
struct MyStruct {
      u8 someData;
      u8 I2C24C161TxBuff;
};
#pragma pack(pop)
这样可以确保结构体成员紧密排列,避免填充字节。

2. 指针操作问题
在您的代码中,您使用了&(I2C24C161TxBuff)来获取数组的地址。如果I2C24C161TxBuff是结构体中的成员,您需要确保正确地访问结构体实例中的数组。

解决方案:
确保您访问的是结构体实例中的数组,而不是结构体类型本身。例如:
c
struct MyStruct myInstance;
DMAI2CTTXAH = (u8)(((u16)(&(myInstance.I2C24C161TxBuff))) >> 8);
DMAI2CTTXAL = (u8)(&(myInstance.I2C24C161TxBuff));

3. 编译器优化问题
编译器可能会对代码进行优化,导致某些操作不符合预期。例如,编译器可能会将结构体中的数组优化为其他形式,或者对指针操作进行优化。

解决方案:
使用volatile关键字声明结构体中的数组,告诉编译器不要对该数组进行优化。例如:
c
struct MyStruct {
      u8 someData;
      volatile u8 I2C24C161TxBuff;
};

4. 检查DMAI2C配置
确保DMAI2C模块的配置正确,特别是地址寄存器的设置。如果地址寄存器设置不正确,DMAI2C模块可能无法正确读取数据。

解决方案:
检查DMAI2C模块的配置,确保地址寄存器(DMAI2CTTXAH和DMAI2CTTXAL)正确设置为数组的地址。

5. 调试和验证
在调试过程中,可以使用调试工具(如JTAG或SWD)查看内存中的实际数据,验证结构体中数组的地址是否正确。

解决方案:
使用调试工具查看结构体中数组的实际地址,并与DMAI2C模块中设置的地址进行比较,确保两者一致。

总结
您遇到的问题可能是由于结构体内存对齐、指针操作、编译器优化或DMAI2C配置不正确导致的。通过强制结构体对齐、正确访问结构体实例中的数组、使用volatile关键字防止编译器优化,以及检查DMAI2C配置,可以解决这个问题。如果问题仍然存在,建议使用调试工具进一步验证内存中的实际数据。

希望这些建议能帮助您解决问题。如果还有其他疑问,请随时提出。

[本文内容由国芯人工智能辅助生成,仅供参考]

DebugLab 发表于 2025-4-16 16:27:49

没这么干过,问一下AI:



ercircle 发表于 2025-4-16 16:28:07

看着不是语法问题
看下是不是内存对齐问题
https://www.stcaimcu.com/forum.php?mod=viewthread&tid=16306

也可以工程发上来看看

641529288 发表于 2025-4-16 16:28:40

还是不行,哎,我发 了源码,帮忙看看。在24c16.c和.h中。

ercircle 发表于 2025-4-16 16:59:26

641529288 发表于 2025-4-16 16:28
还是不行,哎,我发 了源码,帮忙看看。在24c16.c和.h中。



我在库函数例程里复现了你的问题,xdata关键字放在结构体实例前就好了,不要放在结构体定义里试下。

ercircle 发表于 2025-4-16 17:01:16






ercircle 发表于 2025-4-16 17:04:07

结构体里u8类型声明xdata编译器会报错。数组不会,可能也是个编译器问题。

王昱顺 发表于 2025-4-16 18:47:34

如6#所述,keil的帮助里,对于这种结构体指向指定内存的情况,也是用的在声明结构体的时候指定,而不是在结构体内指定内存类型


另外,C44错误的补充说明中也提到了,不可以在结构体中指定内存类型

641529288 发表于 2025-4-17 08:26:05

在声明struct I2C_24Cxx xdata I2C_24C16_1 ;的时候使用xdata成功了。能正常识别地址了。
但又出现新的问题了。当不使用xdata来声明的时候,又不能正确读取地址了。{:zhemo:}见楼下
页: [1] 2
查看完整版本: 8051u的DMA_I2C,发送地址输入到DMA_I2CT_TXAH寄存器的问题。