проблема с обертыванием библиотеки extern "C" в пространстве имен - PullRequest
7 голосов
/ 25 августа 2011

Я использую библиотеку C (libgretl) из C ++, и некоторые ее функции конфликтуют с моим кодом, поэтому я хотел обернуть ее в пространство имен, например:

namespace libgretl {
extern "C" {
    #include <gretl/libgretl.h>
}}

Однако этоне компилируется, я получаю "неопределенные" ошибки из файлов gcc (используя mingw32 с gcc 4.5.2 в Windows).Первые ошибки происходят из следующего блока кода файла c ++ / cstddef:

_GLIBCXX_BEGIN_NAMESPACE(std)
  using ::ptrdiff_t;
  using ::size_t;
_GLIBCXX_END_NAMESPACE

, где макросы расширяются соответственно до namespace std { и }.После этого возникает больше ошибок.

Пропуск директивы extern "C" не помогает.Использование анонимного пространства имен уменьшает количество ошибок, но все равно не компилируется.

Поэтому мой вопрос заключается в том, есть ли способ включить такую ​​библиотеку C и поместить ее функции в пространство имен, не изменяяgcc или исходные файлы библиотеки?

Спасибо.

Михал

Ответы [ 3 ]

7 голосов
/ 25 августа 2011

Вы не можете сделать это.Пространства имен - это не просто декорации исходного кода, они компилируются в символы объектов компилятором.

Собственная функция C foo () в библиотеке будет доступна по символу _foo в объектном файле, но вызов bar :: foo ()сгенерировать ссылку, например, на @ N3barfoo.В результате возникнет ошибка компоновщика.

Вы можете создать «прокси» функции в отдельном исходном файле, включая исходный заголовок библиотеки только в этом источнике и поместить все прокси функции в пространство имен.

2 голосов
/ 25 августа 2011

Вы не можете просто обернуть пространство имен вокруг внешнего объявления, и оно появится в этом пространстве имен ... элемент (функция, глобальный) должен быть построен в этом пространстве имен с самого начала.Поскольку C не поддерживает разрешение пространства имен, это не могло иметь место.

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

Чтобы сослаться на элемент, не принадлежащий пространству имен, который конфликтует с вашим собственным элементом пространства имен, см. ::item().

1 голос
/ 25 августа 2011

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

Вы по-прежнему можете инкапсулировать свой собственный код в пространство имен.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...