Почему Eclipse CDT говорит: "Синтаксическая ошибка", но компиляция не проблема
Я работаю в существующем C-коде, который имеет пару строк с утверждениями, подобными этому:
struct collect_conn *tc = (struct collect_conn *)
((char *)c - offsetof(struct collect_conn, runicast_conn));
Структура collect_conn имеет следующие строки:
struct collect_conn {
struct runicast_conn runicast_conn;
struct announcement announcement;
const struct collect_callbacks *cb;
struct ctimer t;
uint16_t rtmetric;
uint8_t forwarding;
uint8_t seqno;
};
Я использую Eclipse CDT, и он отмечает линию оранжевой кривой кривой как "синтаксическую ошибку". Я думаю, что он отмечен как таковой индексом CDT.
Однако компиляция (вручную в терминале) не представляет проблемы.
Это немного неудобно, так как элементы в строке не индексируются (поэтому дерево иерархии вызовов не всегда правильно, или выделение элементов и т.д.)
Почему Ecipse не похожа на строку?
Ответы
Ответ 1
Eclipse CDT содержит собственный препроцессор/парсер для анализа кода и построения индекса. Однако при вызове сборки CDT вызывается в системный компилятор, например gcc. Могут быть незначительные различия между синтаксисом, принятым парсером CDT, и синтаксисом, принятым вашим компилятором. Когда это произойдет, парсер CDT может запутаться.
В моей системе макрос offsetof
расширяется в выражение, использующее ключевое слово __offsetof__
. Это ключевое слово не распознается CDT, поэтому возникает синтаксическая ошибка. Для решения этой проблемы парсер CDT имеет встроенный макрос для работы с __offsetof__
, который выглядит следующим образом:
#define __offsetof__(x) (x)
Это не кажется правильным, по крайней мере, в моей системе результатом является удаление ключевого слова __offsetof__
из источника, который все еще приводит к синтаксической ошибке.
Мне удалось избавиться от синтаксической ошибки, перейдя на страницу свойств Paths and Symbols и добавив макрос для __offsetof__
, который соответствует "foo". Это приводит к тому, что синтаксический анализатор рассматривает его просто вызов функции, которую он раньше не видел, но не синтаксическую ошибку.
В качестве альтернативы вы можете отключить отчет об ошибках синтаксиса в редакторе, перейдя в меню "Окно" > "Настройки" > "Основные" > "Редакторы" > "Текстовые редакторы" > "Аннотации" и снимите флажки для флажков индексирования C/С++.
Ответ 2
У меня исправлена проблема в eclipse CDT с настройками- > C/С++ → Языковые сопоставления: Добавить
Тип контента: C-заголовок
Язык: С++
Ответ 3
Кажется, парсер CDT не любит смещение части (struct...).
Если вы объявите collect_conn с помощью typedef, ошибка исчезнет. По крайней мере, для меня работает следующий код:
typedef struct {
struct runicast_conn runicast_conn;
struct announcement announcement;
const struct collect_callbacks *cb;
struct ctimer t;
uint16_t rtmetric;
uint8_t forwarding;
uint8_t seqno;
} collect_conn;
...
struct collect_conn *tc = (struct collect_conn *)
((char *)c - offsetof(collect_conn, runicast_conn));
Если вы не можете изменить оригинальное объявление, сделайте что-то вроде этого:
typedef struct collect_conn collect_conn_t;
Ответ 4
Возможно, это смущает, проверьте, есть ли у вас определение offsetof
в области, например. В противном случае вы можете попробовать упростить выражение, разбить его, используя, например, a #define
с offset
of или что-то.
Я думаю, что компилятор может предоставить встроенную версию offsetof
, в то время как компилятор Eclipses/code-parser может не работать. Если это так, вам нужно убедиться, что у вас есть определение, чтобы Eclipse мог правильно проанализировать ваш код.
Ответ 5
попробуйте переключить индексатор на "Полный индексор c/С++ (полный синтаксический анализ)" в "Настройки" → c/С++ → indexer
Ответ 6
У Iv была та же проблема. Существует 2 определения offsetof (один для C и один для С++). ИМО проблема исходит из того, что
Например, если я набираю
#ifndef __cplusplus
#endif
Eclipse будет серым. Это означает, что __cplusplus определен, но мой проект - C
К сожалению, я не нашел исправления.
Ответ 7
Я установил аналогичную проблему после проверки вкладки "Ошибки парсеров" в проекте Makefile в новом проекте "Мастер создания CDT", удаления CDT Visual C Error Parser (я использую gcc)
Ответ 8
Я видел, как Eclipse делал это несколько раз, и я использую его для Java. Обычно закрытие и открытие файла снова исправляет его для меня (сбрасывает все, что не так). Обычно это ошибка, которая была там, но была исправлена, и "кэш ошибок" не обновлен правильно.
Ответ 9
Я решил решить эту проблему. Сначала я открыл свойства проекта, а затем категорию C/С++ general- > Paths and Symbols. На вкладке "Символы" я добавил эту запись:
Symbol: offsetof(TYPE,MEMBER)
Value: ((ssize_t) &((TYPE *)0)->MEMBER)
Эти символы используются индексом, но не передаются компилятору (по крайней мере, в проектах Makefile, я не пробовал его в другом проекте C), поэтому он не переопределяет встроенное смещение GCC