Был рабочий проект для IAR 5.41. Все запускалось, все работало.
Поставил IAR 7.20.2(тоже самое и с IAR 7.30). Загрузил тот проект. Откомпилировал с теми же опциями. Запускаю отладчик и вижу удивительные вещи.
Стандартная процедура инициализации тактового генератора не работает.
Код
/* инициализация тактового генератора */
SCS_bit.OSCRANGE = 0; // 0 = The frequency range of the main oscillator is 1 MHz to 20 MHz
SCS_bit.OSCEN = 1; // 1 = The main oscillator is enabled, and will start up if the correct external circuitry is connected to the XTAL1 and XTAL2 pins.
while(!SCS_bit.OSCSTAT); // ожидание выставления
Зацикливается на while.
Стал смотреть ассемблер.
Код
//-------------------------------------------------------
// 115 /* инициализация тактового генератора */
// 116 SCS_bit.OSCRANGE = 0;
LDR R0,??DataTable0;; 0xe01fc1a0
BL __aeabi_uread4
LDR R1,??DataTable0;; 0xe01fc1a0
BICS R0,R0,#0x10
BL __aeabi_uwrite4
// 117 SCS_bit.OSCEN = 1;
LDR R0,??DataTable0;; 0xe01fc1a0
BL __aeabi_uread4
LDR R1,??DataTable0;; 0xe01fc1a0
ORRS R0,R0,#0x20
BL __aeabi_uwrite4
// 118 while(!SCS_bit.OSCSTAT);
И сравнил с тем, что компилирует IAR 5.41
Код
// 114 /* инициализация тактового генератора */
// 115 SCS_bit.OSCRANGE = 0; // 0 = The frequency range of the main oscillator is 1 MHz to 20 MHz
LDR R0,??DataTable0;; 0xe01fc1a0
LDR R0,[R0, #+0]
BICS R0,R0,#0x10
LDR R1,??DataTable0;; 0xe01fc1a0
STR R0,[R1, #+0]
// 116 SCS_bit.OSCEN = 1; // 1 = The main oscillator is enabled, and will start up if the correct external circuitry is connected to the XTAL1 and XTAL2 pins.
LDR R0,??DataTable0;; 0xe01fc1a0
LDR R0,[R0, #+0]
ORRS R0,R0,#0x20
LDR R1,??DataTable0;; 0xe01fc1a0
STR R0,[R1, #+0]
// 117 while(!SCS_bit.OSCSTAT); // ожидание выставления
Вижу, что добавились процедуры __aeabi_uread4 и __aeabi_uwrite4.
Раскрываем процедуру __aeabi_uwrite4

Та операция, которая выделена зеленым, приводит к тому, что выставленный уже бит OSCEN(и статус OSCSTAT тоже уже в 1) сбрасывается в 0, соответственно, сбрасывается и OSCSTAT. После этого благополучно прога зацикливается на проверке
Код
while(!SCS_bit.OSCSTAT);
Поигрался с опциями в проекте - не помогло. Посмотрел листинги файла main.c, в котором происходит инициализация, в IAR 5.41 и IAR 7.20, но листинги с опциями оказались одинаковыми, т.е. компилятор в IAR 7.20 стал по другому компилировать.
Листинг в IAR 5.41
Код
# Cpu mode = arm #
# Endian = little #
# Source file = F:\ARM\LPC\5.41\Gazochrom\main.c #
# Command line = F:\ARM\LPC\5.41\Gazochrom\main.c -D LPC2000_IAR -D #
# IAR_LPC_2378_SK -D FREERTOS_OVER_7_4_2 -D DEBUG -D #
# PACK_STRUCT_END= -lcN F:\ARM\LPC\5.41\Gazochrom\Debug\Li #
# st\ -lB F:\ARM\LPC\5.41\Gazochrom\Debug\List\ #
# --diag_suppress pa039,pa093,pe815,pe191,pa082,pe167,pe55 #
# 0,pe111,pe174 -o F:\ARM\LPC\5.41\Gazochrom\Debug\Obj\ #
# --no_cse --no_unroll --no_inline --no_code_motion #
# --no_tbaa --no_clustering --no_scheduling --debug #
# --endian=little --cpu=ARM7TDMI-S -e --fpu=None #
# --dlib_config "F:\IAR Systems\Embedded Workbench #
# 5.4\arm\INC\DLib_Config_Normal.h" -I #
# F:\ARM\LPC\5.41\Gazochrom\ -I #
# F:\ARM\LPC\5.41\Gazochrom\Include\ -I #
# F:\ARM\LPC\5.41\Gazochrom\Portable\Include\ -I #
# F:\ARM\LPC\5.41\Gazochrom\Connection\ETHERNET\Include\ #
# -I F:\ARM\LPC\5.41\Gazochrom\Connection\USB\modules\ -I #
# F:\ARM\LPC\5.41\Gazochrom\Connection\USB\app\ -I #
# F:\ARM\LPC\5.41\Gazochrom\SDCard\Include\ -I #
# F:\FreeRTOS\FreeRTOSV7.5.3\FreeRTOS\Source\include\ -I #
# "F:\IAR Systems\Embedded Workbench 5.4\arm\INC\" #
# --interwork --cpu_mode arm -On #
# List file = F:\ARM\LPC\5.41\Gazochrom\Debug\List\main.lst #
# Object file = F:\ARM\LPC\5.41\Gazochrom\Debug\Obj\main.o #
Листинг в IAR 7.20
Код
# Cpu mode = arm
# Endian = little
# Source file = F:\ARM\LPC\IAR_7\Gazochrom\main.c
# Command line =
# F:\ARM\LPC\IAR_7\Gazochrom\main.c -D LPC2000_IAR -D IAR_LPC_2378_SK -D
# FREERTOS_OVER_7_4_2 -D DEBUG -D PACK_STRUCT_END= -lcN
# F:\ARM\LPC\IAR_7\Gazochrom\Debug\List\ -lB
# F:\ARM\LPC\IAR_7\Gazochrom\Debug\List\ --diag_suppress
# pa039,pa093,pe815,pe191,pa082,pe167,pe550,pe111,pe174 -o
# F:\ARM\LPC\IAR_7\Gazochrom\Debug\Obj\ --no_cse --no_unroll --no_inline
# --no_code_motion --no_tbaa --no_clustering --no_scheduling --debug
# --endian=little --cpu=ARM7TDMI-S -e --fpu=None --dlib_config "F:\IAR
# Systems\Embedded Workbench 7.0\arm\INC\c\DLib_Config_Normal.h" -I
# F:\ARM\LPC\IAR_7\Gazochrom\ -I F:\ARM\LPC\IAR_7\Gazochrom\Include\ -I
# F:\ARM\LPC\IAR_7\Gazochrom\Portable\Include\ -I
# F:\ARM\LPC\IAR_7\Gazochrom\Connection\ETHERNET\Include\ -I
# F:\ARM\LPC\IAR_7\Gazochrom\Connection\USB\modules\ -I
# F:\ARM\LPC\IAR_7\Gazochrom\Connection\USB\app\ -I
# F:\ARM\LPC\IAR_7\Gazochrom\SDCard\Include\ -I
# F:\FreeRTOS\FreeRTOSV7.5.3\FreeRTOS\Source\include\ --interwork
# --cpu_mode arm -On
# List file = F:\ARM\LPC\IAR_7\Gazochrom\Debug\List\main.lst
# Object file = F:\ARM\LPC\IAR_7\Gazochrom\Debug\Obj\main.o
Немного изменил операции на C. Стало выглядеть так
Код
SCS &= ~(1 << SCS_OSCRANGE);
SCS |= 1 << SCS_OSCEN;
while (!(SCS & (1 << SCS_OSCSTAT)));
Но компилятор сделал тот же ассемблерный код с вызовами __aeabi-процедур, что и первоначально. Проблема не исчезла ((
Мало того, что появилась куча операций дополнительных(минус скорости), так еще делает невозможным работу программы.
ПС. Причина-то нашлась, но все равно вопросы остались
Видать, новый компилятор стал более строг к директивам. Использовалась директива
Код
#pragma pack(1)
. Описанная выше процедура подпадала под действие этой директивы, но компилятор от IAR 5.41 реагировал в данном конкретном месте программы иначе, чем компилятор от IAR 7.20.
Сообщение отредактировал M0HAX - Dec 6 2014, 11:23