У меня проблемы с оптимизацией во встроенном C-приложении.Адрес указателя неожиданно меняется на 0x0 и нарушает мой код.
Я использую инструментарий GNU MCU Eclipse ARM Embedded GCC.Я использую датчик, с которым я общаюсь через SPI.Датчик имеет 8 конфигурационных регистров по 16 бит каждый.Я храню локальную копию конфигураций в структуре с именем hallsensor_zTleConfig. Я регулярно читаю сохраненную конфигурацию датчика («zTleSensorConfig») и сравниваю ее с локальной копией, чтобы определить, не произошло ли повреждение памяти.
БезОптимизация, этот процесс работает.
При оптимизации в приведенном ниже коде указатель на главную / локальную копию неожиданно меняется на 0x0 без видимой причины.
// Master copy of configuration of the TLE chips
static TLE5012B_zCONFIG hallsensor_zTleConfig[ HALLSENSOR_COUNT ];
static void Hallsensor_VerifyConfig( HALLSENSOR_eUNIT eUnit )
{
TLE5012B_zCONFIG zTleSensorConfig;
uint16* pu16MasterConfigPointer = &hallsensor_zTleConfig[ eUnit ];
uint16* pu16SensorConfigPointer = &zTleSensorConfig;
uint8 u8Index;
// Read all configuration parameters
(void)Hallsensor_ReadRegister( TLE5012B_MOD_2, &zTleSensorConfig, sizeof( TLE5012B_zCONFIG ) );
// Copy over configurations modified by Auto-calibration and reserved bits
hallsensor_zTleConfig[ eUnit ].zMod3.u12ANG_BASE = zTleSensorConfig.zMod3.u12ANG_BASE;
hallsensor_zTleConfig[ eUnit ].zSynch.i12AmpSynch = zTleSensorConfig.zSynch.i12AmpSynch;
hallsensor_zTleConfig[ eUnit ].zOffsetX.i12XOffset = zTleSensorConfig.zOffsetX.i12XOffset;
hallsensor_zTleConfig[ eUnit ].zOffsetY.i12YOffset = zTleSensorConfig.zOffsetY.i12YOffset;
hallsensor_zTleConfig[ eUnit ].zMod4.u7TCO_X_T = zTleSensorConfig.zMod4.u7TCO_X_T;
hallsensor_zTleConfig[ eUnit ].zTcoY.u7TCO_Y_T = zTleSensorConfig.zTcoY.u7TCO_Y_T;
hallsensor_zTleConfig[ eUnit ].zMod2.u1Reserved = zTleSensorConfig.zMod2.u1Reserved;
hallsensor_zTleConfig[ eUnit ].zMod4.u1Reserved = zTleSensorConfig.zMod4.u1Reserved;
hallsensor_zTleConfig[ eUnit ].zOffsetX.u4Reserved = zTleSensorConfig.zOffsetX.u4Reserved;
hallsensor_zTleConfig[ eUnit ].zOffsetY.u4Reserved = zTleSensorConfig.zOffsetY.u4Reserved;
hallsensor_zTleConfig[ eUnit ].zSynch.u4Reserved = zTleSensorConfig.zSynch.u4Reserved;
// Compare local Master config setting to sensor settings and look for corrupted data
for ( u8Index = 0; u8Index < TLE5012B_CONFIG_REG_COUNT; u8Index++ )
{
// Configuration invalid?
if ( pu16MasterConfigPointer[u8Index] != pu16SensorConfigPointer[u8Index] )
{
hallsensor_bConfigOk[ eUnit ] = FALSE;
}
}
// Data corrupted?
if ( !hallsensor_bConfigOk[ eUnit ] )
{
// Do stuff
}
}
В началеФункция pu16MasterConfigPointer и pu16SensorConfigPointer правильно содержат адрес соответствующих структур.Однако непосредственно перед первым циклом for значение pu16MasterConfigPointer изменяется на 0x0, и все условия цикла for приводят к значению TRUE.
Я пробовал множество комбинаций volatile для различных переменных и указателей, и результаты по-прежнему нарушают код в различных другихспособы (например, цикл for не разветвляется для оператора if, смотрящего на код asm, приводящий к тому, что оператор всегда переходит в "hallsensor_bConfigOk [eUnit] = FALSE;")
PS: хороший ресурс, чтобы узнать о том, как защититьВаш код от проблем оптимизации был бы очень кстати.
Снимок экрана отладчика с указателем = 0x0 с кодом asm
![enter image description here](https://i.stack.imgur.com/OjI9R.png)