Создать пользовательский макрос, аналогичный __COUNTER__ в плагине GCC

#c #gcc #plugins #macros #preprocessor

#c #gcc #Плагины #макросы #препроцессор

Вопрос:

Я занимаюсь рефакторингом программы, которая требует, чтобы типы имели глобальный уникальный номер, который увеличивается на единицу для каждого объекта (т.Е.. максимальное уникальное число должно быть количеством типов, объявленных с этим идентификатором) во всем проекте ( __COUNTER__ работает только для текущего файла).

В настоящее время это выглядит так

 struct foo {
    static const int index = __GLOBAL_COUNTER__(TYPES, _3862e1e60a2749c2bfd2add9f3ddbb25);
};
  

Для этого запускается скрипт python, который запускает обычный процессор C , затем использует регулярное выражение для поиска использования __GLOBAL_COUNTER__ и заменяет их числом. Номер аргумента макроса — это имя используемого счетчика, а второй — UUID (чтобы значение было постоянным между включениями).

Проблемы с подходом заключаются в том, что использование макроса не работает должным образом при смешивании с другими макросами, а скрипт python и регулярное выражение могут заменять вещи, которые я не собираюсь (например, в строках). Также необходимость вручную генерировать UUID для каждого типа является громоздкой.

Итак, мой вопрос заключается в том, можно ли написать макрос в качестве плагина GCC для обеспечения этой функциональности и с чего мне следует начать. Я просмотрел документацию и прочитал часть исходного кода GCC, но ничего не нашел.

ПРИМЕЧАНИЕ: обычно это объединяется в другой макрос, чтобы сэкономить немного ввода

 #define TYPE_INDEX(x) static const int index = __GLOBAL_COUNTER__(TYPES, x);
  

Так что, если есть другие подходы, например, изменение синтаксиса, чтобы что-то вроде этого, если это проще, тоже сработало бы, но я не уверен, как бы я это сделал.

 indexed_struct foo {
};
  

Комментарии:

1. Я не знаю, возможно ли это, но я думаю, что если вы определите уникальные индексы для всех файлов, и если вы ИЛИ этот индекс и ГЛОБАЛЬНОЕ значение сразу после сдвига индекса файла в крайнее левое положение, вы сможете генерировать уникальные целочисленные значения для всего проекта. Также вы можете создать библиотечную функцию, чтобы не переписывать смещения и оринги. —> generate_unique_number(file_index, ГЛОБАЛЬНЫЙ )

2. Спасибо, но, к сожалению, у меня есть ограничение, требующее не только уникальных, но и последовательных индексов во время компиляции. Я думаю, что использую аналогичный подход, когда это ограничение не требуется (реализация грубой функции хеширования __FILE__ для создания идентификатора файла).

3. Вы должны создать UUID для каждого типа, это означает, что вы заранее знаете все типы. Почему бы вам не создать перечисление со всеми этими типами?