Grizzly 0 26 ноября, 2017 Опубликовано 26 ноября, 2017 · Жалоба Удивлен, что компилятор Keil с включенным стандартом C99 не выдал ошибки для такого кода: const uint32_t N = 20; static MyStruct_t Example[N]; В C в отличие от C++ const означает только read-only. Variable length array, появившийся в C99, применяется к локальным массивам в run-time. Почему в моем случае нет ошибки для глобального массива? Странное поведение. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
gazpar 1 26 ноября, 2017 Опубликовано 26 ноября, 2017 · Жалоба Удивлен, что компилятор Keil с включенным стандартом C99 не выдал ошибки для такого кода: const uint32_t N = 20; static MyStruct_t Example[N]; В C в отличие от C++ const означает только read-only. Variable length array, появившийся в C99, применяется к локальным массивам в run-time. Почему в моем случае нет ошибки для глобального массива? Странное поведение. Странно, почему для вас этот код странный. Всё ок. Попробуйте изменить значение N в рантайме (в цикле N присвоить значение индекса/итерации цикла)--> будет ошибка. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Grizzly 0 26 ноября, 2017 Опубликовано 26 ноября, 2017 · Жалоба Странно, почему для вас этот код странный. Всё ок. Попробуйте изменить значение N в рантайме (в цикле N присвоить значение индекса/итерации цикла)--> будет ошибка. Это я понимаю, что менять нельзя значение переменной. Более того, она должна быть объявлена const, иначе будет ошибка. Почему тогда приводятся во всех книгах/примерах определения размеров массивов через define? Я имею в виду Си. Наверное, час искал на форумах, но нигде не нашел примеров, чтобы определяли длину через const int. Мне самому именно такой метод нравится больше по сравнению с define. Сейчас задумался, правильно ли я понимаю стандарт и не допускаю ли ошибки. В C++ это обычная практика. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
k155la3 26 26 ноября, 2017 Опубликовано 26 ноября, 2017 · Жалоба . . . Попробуйте изменить значение N в рантайме (в цикле N присвоить значение индекса/итерации цикла)--> будет ошибка. . . . const с инициализацией размещается или во флеш, или реализуется оптимизатором как присваивание (если использование "разовое").Поэтому, если у компилятора есть совесть, до рантайма дойти не должно. Должна быть ошибка компилятора. . . . . Почему тогда приводятся во всех книгах/примерах определения размеров массивов через define? . . . Это не "определение", это "тупо подстановка" текста-цифров. Через #define - тк далее в коде это значение может еще много-где понадобиться (и измениться), а это удобно делать "централизованно" из одного #define. ------ А для "определения" - sizeof(). И такая конструкция вроде прокатывает: int a, b; float c; char ms[100]; const int bf_size = sizeof(a) + sizeof(b) + sizeof(ms); Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
one_eight_seven 3 26 ноября, 2017 Опубликовано 26 ноября, 2017 · Жалоба Неплохо бы указывать. в каком компиляторе это у вас нет ошибки. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Grizzly 0 26 ноября, 2017 Опубликовано 26 ноября, 2017 · Жалоба Неплохо бы указывать. в каком компиляторе это у вас нет ошибки. Arm Compiler 5.02 и 5.06. P.S. Если выбрать C90, то тоже ошибок нет. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
one_eight_seven 3 26 ноября, 2017 Опубликовано 26 ноября, 2017 · Жалоба мой gcc ругается на это сразу: "variable modified array 'MyArray' at file scopoe", если я ставлю (не структуту, просто int'овый массив), если я делаю глобальный массив int MyArray[int]. если же я включаю его в тело функции, то он сообщает, что "storage size of 'MyArray' isn't constant. В общем-то так было всегда., сколько я ни мучаю gcc Так что либо смотрите на настройки компиляции, либо бегите от этого компилятора, как от огня. Какой бы он хороший ни был, если он не соответствует документации, то вы не можете ждать от него детерминированного результата. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Grizzly 0 26 ноября, 2017 Опубликовано 26 ноября, 2017 · Жалоба От GCC я другого не ожидал :) Тут нет вопросов. Задал тоже просто массив int'ов для Arm Compiler. Такая же фигня. Для успокоения совести выбрал C99 и добавил определение массива в main(), создался VLA. Для C90 это вызвало ошибку. То есть использование стандартов Си изменяется в настройках корректно. При этом как для C90, так и для C99 в случае глобального массива ни ворнингов, ни ошибок :( Может быть, кто-то еще повторит подобное. Вдруг я где-то ошибся. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ViKo 1 26 ноября, 2017 Опубликовано 26 ноября, 2017 · Жалоба попробуйте компилировать с опцией --strict Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Grizzly 0 26 ноября, 2017 Опубликовано 26 ноября, 2017 · Жалоба попробуйте компилировать с опцией --strict Спасибо. Для C90 совсем всё плохо, миллион ошибок сразу. Для C99 много ошибок при компиляции CMSIS следующего вида: /core_cm3.c", line 58: Error: #667: "asm" function is nonstandard __ASM uint32_t __get_PSP(void) И еще неизвестно, сколько их будет дальше. Надо тогда попробовать сделать совсем маленький проектик. UPD.: Задал опцию --strict только для файла main.c, сразу получил ошибку в моем массиве :) Error: #28: expression must have a constant value А не подскажете, где-нибудь в документации Arm Compiler перечислены их фичи, отличные от стандарта? В общем-то так было всегда., сколько я ни мучаю gcc Так что либо смотрите на настройки компиляции, либо бегите от этого компилятора, как от огня. Какой бы он хороший ни был, если он не соответствует документации, то вы не можете ждать от него детерминированного результата. А вы с опциями --pedantic или --ansi компилируете? Хочу понять, в GCC изначально более жесткое соблюдение стандарта или нет... Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ViKo 1 26 ноября, 2017 Опубликовано 26 ноября, 2017 · Жалоба ARM Compiler armcc user guide. Есть на сайте ARM и Keil. Где что перечислено, не знаю. Я его только местами смотрел. Про --strict там конкретно написано, на что реагирует. Я его так и нашел по слову const. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Grizzly 0 26 ноября, 2017 Опубликовано 26 ноября, 2017 · Жалоба ARM Compiler armcc user guide. Есть на сайте ARM и Keil. Где что перечислено, не знаю. Я его только местами смотрел. Про --strict там конкретно написано, на что реагирует. Я его так и нашел по слову const. Ага, пасиб. Guide этот знаю, завтра почитаю подробнее. UPD.: Вот тут весь списочек: http://infocenter.arm.com/help/index.jsp?t...e/CHDGFDID.html Только сходу свой случай не нашел. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
one_eight_seven 3 26 ноября, 2017 Опубликовано 26 ноября, 2017 (изменено) · Жалоба А вы с опциями --pedantic или --ansi компилируете? Хочу понять, в GCC изначально более жесткое соблюдение стандарта или нет... Без опций. Собственно, листинг моего Makefile: CFLAGS=-g -Wall -O0 falsenoerror: falsenoerror.o сам код: #include <stdio.h> #include <stdint.h> const uint32_t N = 20; int main () { static int MyArray[N]; for (int i=0 i < N; i++) { MyArray[i] = i; print ("MyArray %d = %d", i, MyArray[i]) } return 0; } Естественно, если вынести строку static int MyArray[N]; из тела main, ничего не изменится. Изменено 26 ноября, 2017 пользователем one_eight_seven Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Grizzly 0 26 ноября, 2017 Опубликовано 26 ноября, 2017 · Жалоба Спасибо большое. Опередили. Отыскал свои проекты под GCC, но вы раньше показали пример. Читаю описания Arm Compiler, немало всяких дополнений там, отличных от стандарта. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться