ARV 0 27 марта, 2009 Опубликовано 27 марта, 2009 · Жалоба собственно, вместо многократного повторения __attribute__ ((naked, section(".init7"))) для разных функций типа void foo(void) в разных файлах хочу сделать какой-то макрос, который сам бы это дело дописал перед каким-то автоматически сгенерированным идентификатором. в общем, пишем: initialize{тут код начальной инициализации} а получаем фактически что-то типа __attribute__ ((naked, section(".init7"))) void _name120097553(void){nen код начальной инициализации} подскажите, как сделать? ничего путнего не получается... проблема в формировании уникального идентификатора.... Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
_Pasha 0 27 марта, 2009 Опубликовано 27 марта, 2009 · Жалоба подскажите, как сделать? Если в файле по одному иниту, их можно обозвать одинаково. :) Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ARV 0 27 марта, 2009 Опубликовано 27 марта, 2009 · Жалоба Если в файле по одному иниту, их можно обозвать одинаково. :) увы, низзя... если функцию не объявлять static - то компоновщик обнаруживает наличие одинаковых идентификаторов... а если объявить static - не действует __attribute__ Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
solosh 0 27 марта, 2009 Опубликовано 27 марта, 2009 · Жалоба Попробуйте для создания уникальных имен использовать макросы __LINE__ и __FILE__ Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ARV 0 27 марта, 2009 Опубликовано 27 марта, 2009 · Жалоба Попробуйте для создания уникальных имен использовать макросы __LINE__ и __FILE__ так вот же ж :( их и пробовал... проблема в том, что как __LINE__ сконкатировать с символом? если я пишу так: #define initialize void init ## __LINE__ (void) то вместо ожидаемого void init_234(void) я получаю void init___LINE__(void) что неприемлемо... Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
solosh 0 27 марта, 2009 Опубликовано 27 марта, 2009 · Жалоба Нужен еще один проход препроцессора. Вот как раз Ваш случай: http://electronix.ru/forum/index.php?s=&am...st&p=361393 Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Petka 0 27 марта, 2009 Опубликовано 27 марта, 2009 · Жалоба так вот же ж :( их и пробовал... проблема в том, что как __LINE__ сконкатировать с символом? если я пишу так: #define initialize void init ## __LINE__ (void) то вместо ожидаемого void init_234(void) я получаю void init___LINE__(void) что неприемлемо... поколдуйте с двойным переопределением. например #define MY_LINE __LINE__ #define MY_LINE2 MY_LINE Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ARV 0 27 марта, 2009 Опубликовано 27 марта, 2009 · Жалоба Нужен еще один проход препроцессора. Вот как раз Ваш случай: http://electronix.ru/forum/index.php?s=&am...st&p=361393 да, случай как раз мой. но почему-то когда я вручную писал static для инициализирующей функции, она исключалась уборщиком мусора (-Wl,-gc-sections -ffunction-sections)... наверное потому, что не было атрибута used? спасибо за помощь! Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ReAl 0 27 марта, 2009 Опубликовано 27 марта, 2009 · Жалоба она исключалась уборщиком мусора (-Wl,-gc-sections -ffunction-sections)... наверное потому, что не было атрибута used?Да, именно поэтому. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
demiurg_spb 0 27 марта, 2009 Опубликовано 27 марта, 2009 · Жалоба А для чего, простите, весь сыр-бор. Чтобы лишь автоматизировать инициализацию какого-либо программного модуля? Если так, то Вы ребята далеко ушли от программирования на С. Что неужели трудно явно вызывать процедуру инициализации? А как быть с расстановкой очерёдности инициализации разных модулей? С простотой портирования? С наглядностью наконец? На мой взгляд происходит подмена понятия программирования. Извините, но хочется понять глубинный смысл сего явления. Ответ типа: мне удобно т.к. я догадался до такого "извращения" - не то, что хочется услышать:) Я сторонник глубинного понимания языка программирования, а не фишек линкера и прочего инструментария, входящего в комплект поставки компилятора. Да это знать и понимать тоже нужно, но использовать так... Уж если считаете, что Вам стал жать С используйте С++ с его конструкторами и деструкторами, шаблонами и всем-всем остальным что Вам будет нужно. Так будет честнее. ИМХО. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Сергей Борщ 123 28 марта, 2009 Опубликовано 28 марта, 2009 · Жалоба А для чего, простите, весь сыр-бор. Чтобы лишь автоматизировать инициализацию какого-либо программного модуля?Нет, периферии.Если так, то Вы ребята далеко ушли от программирования на С. Что неужели трудно явно вызывать процедуру инициализации?Трудно. На каждый вызов положить по ®call/ret и сохранение/восстановление контекста? Нафига? Если для этого есть специально разарботанный очень элегантный механизм. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
demiurg_spb 0 28 марта, 2009 Опубликовано 28 марта, 2009 · Жалоба Нет, периферии. ... Нафига? Если для этого есть специально разарботанный очень элегантный механизм. Я вас прекрасно понимаю с точки зрения экономии ПЗУ, слабо с точки зрения повышения быстродействия. И совсем никак с моей личной точки зрения. Поясню. У меня обычно пользователю доступны режимы работы устройства (пусть это будет пресловутый UART), так после изменения настроек нужно вызвать процедуру инициализации повторно. Так если эта процедура у меня уже физически есть, то зачем мне всё это? Да есть такая периферия которая не отдаётся на откуп юзеру, так с ней можно и через static inline или __attribute__((always_inline)) "бороться". Хотя тут уже не принципиально как. Спасибо за ответ. Для меня тема исчерпана. Ваш метод имеет право на жизнь:) 2 ARV: гляньте, тут тоже происходит формирование уникальных идентификаторов: #ifdef __cplusplus template<bool> struct CompileTimeError; template<> struct CompileTimeError<true> {}; # define STATIC_ASSERT(expr) (CompileTimeError<(expr) != 0>()) #else # define MY_JOIN_3_H(A,B,C) A##B##C # define MY_JOIN_3(A,B,C) MY_JOIN_3_H(A,B,C) # define STATIC_ASSERT_H(expr) typedef int MY_JOIN_3(static_assert_,__LINE__,_h) [(expr) ? 1 : -1] # define STATIC_ASSERT(expr) STATIC_ASSERT_H(expr) #endif Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ARV 0 28 марта, 2009 Опубликовано 28 марта, 2009 · Жалоба 2 demiurg_spb: спасибо, уже не надо, тем более, что принцип тот же самый, что и ранее, и даже тот же, о котором я сам думал... я лишь не сразу понял, что надо неоднократно макросы вкладывать друг в друга :) Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
demiurg_spb 0 28 марта, 2009 Опубликовано 28 марта, 2009 · Жалоба Да тут есть свой прикол. Я даже использую это в таком случае: Через makefile спускаю строку (имя файла) в зависимости от типа условной компиляции: ADD_COMPILE_FLAGS += -DLOW_LEVELX_H=low_level3.h ... CFLAGS += $(ADD_COMPILE_FLAGS) определяю макрос: // str macro #define STR(S) #S // STR(blabla) = "blabla" #define XSTR(S) STR(S) // STR(_version) = "v1.0" if _version = "v1.0" А в программе просто подключаю инклюдом нужный файл без всяких там #if #elif #endif #include XSTR(LOW_LEVELX_H) Мне нравится. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
_Pasha 0 28 марта, 2009 Опубликовано 28 марта, 2009 · Жалоба Мне нравится. +1 И мне :) Автору большое спасибо за тему. Познавательно. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться