Моя проблема в том, что я хочу вызвать некоторую шаблонную функцию в C.

Поэтому я объявил функцию extern "C" как функцию-оболочку, которая вызывает эту функцию-шаблон.

Я знаю, что мне нужно скомпилировать функцию-оболочку с помощью компилятора C ++, а затем я получаю объектный файл, который я могу связать с обычной c-программой.

Проблема в том, что я написал библиотеку C ++ только для заголовков, которую я хочу использовать в C, но в C я больше не могу создавать только заголовок библиотеки, когда мне нужно связать C-программу с функцией-оболочкой.

Так существует ли способ создания c-библиотеки только для заголовков, которая вызывает функцию шаблона c ++? Этот метод должен работать в GCC и это абсолютно не проблема, если он нестандартный, требует нескольких прагм, cli-параметров или чего-то еще.

Я думаю, возможным решением было бы вызвать gcc в C-режиме для файла, где в определенной строке возможен переход с C на C ++ внутри файла заголовка. Этот переключатель C ++ выполняет фактический вызов шаблона, а затем выполняется переключение обратно на C-компилятор. Есть ли какой-нибудь метод?

Например как это:

#include <iostream>

#define SWITCH_TO_CPP_COMPILER() /*TODO: is this possible?*/
#define SWITCH_BACK_TO_C_COMPILER() /*TODO: is this possible?*/

#ifdef __cplusplus
extern "C" {
#endif
    inline bool wrapper();
#ifdef __cplusplus
}
#endif


SWITCH_TO_CPP_COMPILER();

template<bool tmp>
constexpr bool template_func() noexcept {
    return tmp;
}

inline bool wrapper() {
    return template_func<true>();
}

SWITCH_BACK_TO_C_COMPILER()

#include <stdio.h>

int main() {
    printf("%d\n", wrapper());
}

Я уже посмотрел несколько вопросов, но они не дают ответа:

C Wrapper для C ++: как работать с шаблонами C ++?

как написать оболочку c вокруг кода c ++ для предоставления методов класса

Создайте оболочку C вокруг библиотеки C ++, которая может быть связана компоновщиком C

Обертка C вокруг библиотеки C ++ без ненужных файлов заголовков

1
byteunit 15 Сен 2018 в 09:17

2 ответа

Лучший ответ

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

Эта вещь не может быть только заголовком: заголовок жестко включен в файл, который его использует, и этот файл будет обрабатываться компилятором C, который затем должен иметь возможность анализировать / создавать экземпляр шаблона C ++ помимо оболочки функции, а это, очевидно, невозможно. Синтаксический анализ C ++ уже сложен, требовать переключения на другой язык прямо в воздухе - это совершенно безумно.

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

У вас уже есть зависимость от компилятора C ++ и, скорее всего, от стандартной библиотеки C ++, так что это не сильно изменится, кроме скорости компиляции в общей схеме вещей.

2
Matteo Italia 15 Сен 2018 в 06:49

Это в виду того, что Маттео написал в своем ответе:

Убежденный, что то, чего хочет OP, невозможно, я попытался найти весомый аргумент.

Я сравнил «Фазы перевода» для C и C ++.

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

Я почти не сомневаюсь, что любой компилятор может переключиться с C на C ++ и обратно в середине единицы перевода (если она соответствует стандарту).

2
Scheff 15 Сен 2018 в 07:00