I would like to include one header file in both C and C++, and I have a function defined in C code and few functions defined in external library.
#if defined(__cplusplus)
extern "C" {
#endif
void func0();
#if !defined(__cplusplus)
extern {
#endif
void func1();
int func2(int);
} /* extern */
This code produces compilation error when compiled from C source file
error C2059: syntax error : '{'
Is it possible to fix syntax error directly or I have to use some macros?
EXTERNCPP void func0();
EXTERNC void func1();
EXTERNC int func2(int);
Edit 1:
I do not ask about
Effects of the extern keyword on C functions, I just ask if it is possible to fix syntax in easy way. If it is not possible, i could still remove it completely for C part
Edit 2:
To clarify what I want to get. If header is included
from C++:
extern "C" void func0();
extern "C" void func1();
extern "C" int func2(int);
from C:
void func0();
extern void func1();
extern int func2(int);
extern { is not needed.You need to remove it:-
#if defined(__cplusplus)
extern "C" {
#endif
void func0();
#if !defined(__cplusplus)
#endif
void func1();
int func2(int);
#if defined(__cplusplus)
}
#endif
You can simply omit the extern { line when compiling as a C header.
#if defined(__cplusplus)
extern "C" {
void func0();
#endif
#if !defined(__cplusplus)
void func1();
int func2(int);
#endif
#if defined(__cplusplus)
}
#endif
* [EDIT] answering your last edit:
void func0(); /* included in both versions */
#if defined(__cplusplus)
extern "C" {
void func1();
int func2(int);
#endif
#if !defined(__cplusplus)
extern void func1();
extern int func2(int);
#endif
#if defined(__cplusplus)
}
#endif
If you want to use func0 as extern in C:
#if defined(__cplusplus)
extern "C" {
void func0();
void func1();
int func2(int);
#endif
/* C block */
#if !defined(__cplusplus)
extern void func0();
extern void func1();
extern int func2(int);
#endif
#if defined(__cplusplus)
}
#endif
If you don't want to use it at all (from C) remove it from the C block
Related
I am using this:
// foo.h
#ifdef __cplusplus
extern "C" {
#endif
void foo();
#ifdef __cplusplus
}
#endif
//foo.cc
void foo() {
cout << "Hello World" << endl;
}
to link between my cgo process and c++ process. I want to access a golang function from my c++ function foo. My go looks like:
// #include "foo.h"
import "C"
func golangPart() {
//do stuff in go
}
func main() {
C.foo()
}
I want to access golangPart() from the c++. I have tried this:
//foo.h
void golangPart();
#ifdef __cplusplus
extern "C" {
#endif
void foo();
#ifdef __cplusplus
}
#endif
//foo.cc
void foo() {
golangPart();
}
But it gave me this error:
./foo.cc:42: undefined reference to `golangPart()'
collect2.exe: error: ld returned 1 exit status
This question already has answers here:
What is the effect of extern "C" in C++?
(17 answers)
Including C headers inside a C++ program
(5 answers)
Closed 5 years ago.
file1.c
int add(int a, int b)
{
return (a+b);
}
file2.cpp
void main()
{
int c;
c = add(1,2);
}
h1.h
extern "C" {
#include "stdio.h"
int add(int a,int b);
}
Case 1:
when i include h1.h in file1.c file then gcc compiler throw an error "expected '(' before string constant".
case 2:
when I include h1.h in file2.cpp file compilation work successfully
Question:
1) Does it mean that I can not include header file in C with extern "C" function in it??
2) Can I include header within extern"C" like shown below
extern "C" {
#include "abc.h"
#include "...h"
}
3) Can I put c++ functions definitions in header file with extern "C" so that i can call it in C file?
for example
a.cpp ( cpp file)
void test()
{
std::printf("this is a test function");
}
a.h (header file)
extern "C" {
void test();
}
b_c.c ( c file)
#include "a.h"
void main()
{
test();
}
Write a.h like this:
#pragma once
#ifdef __cplusplus
extern "C"
{
#endif
int add(int a,int b);
#ifdef __cplusplus
}
#endif
This way you can declare multiple functions - there is no need to prefix each one with extern C.
As others mentioned: extern C is a C++ thing, so it needs to "disappear" when seen by C compiler.
Since extern "C" is not understood by a C-compiler you need to create a header that can both be included in a C and C++ file.
E.g.
#ifdef __cplusplus
extern "C" int foo(int,int);
#else
int foo(int,int);
#endif
Instead of writing each function in " extern "C" {} ", can I write entire header file inside that block.
extern "C"
{
#include "myCfile.h"
}
I have tried this but Its not working at all, why it is not working ?
if we have to use 100 C functions in a c++ project, do we need provide all the functions in a
extern block, is there any other simple way ?
Ex:
extern "C"
{
void fun1();
void fun2();
void fun3();
void fun4();
void fun5();
.
.
.
.
fun100();
}
Is there any other simple way, like extern "C" { myCfunctions.h } ???
#include simply includes the specified header at the location of the #include. Whether it's valid depends on what "myCfile.h" contains. In particular, including any standard library headers in such a context is not valid, and may well break on commonly used implementations.
The usual way to handle this is to make the header itself safe to use from C++. A C-only header might contain
#ifndef H_MYCFILE
#define H_MYCFILE
#include <stddef.h>
void mycfunc1(void);
void mycfunc2(int i);
void mycfunc3(size_t s);
#endif
Adapting this to make it safe to use from C++:
#ifndef H_MYCFILE
#define H_MYCFILE
#include <stddef.h>
#ifdef __cplusplus
extern "C" {
#endif
void mycfunc1(void);
void mycfunc2(int i);
void mycfunc3(size_t s);
#ifdef __cplusplus
}
#endif
#endif
With such a header, you wouldn't be able to safely put the entire header in an extern "C" block. However, that header itself can make sure not to put #include <stddef.h> in an extern "C" block, but still to put all function declarations in a single extern "C" block, avoiding having to repeat it for each one.
You are doing something wrong.
Because
extern "C" { myCfunctions.h }
should work. See below sample program.
Lets go by example code.
ctest1.c
#include<stdio.h>
void ctest1(int *i)
{
printf("This is from ctest1\n"); // output of this is missing
*i=15;
return;
}
ctest2.c
#include<stdio.h>
void ctest2(int *i)
{
printf("This is from ctest2\n"); // output of this is missing
*i=100;
return;
}
ctest.h
void ctest1(int *);
void ctest2(int *);
Now lets make c library from that
gcc -Wall -c ctest1.c ctest2.c
ar -cvq libctest.a ctest1.o ctest2.o
Now lets make cpp based file which will use this c apis
prog.cpp
#include <iostream>
extern "C" {
#include"ctest.h"
}
using namespace std;
int main()
{
int x;
ctest1(&x);
std::cout << "Value is" << x;
ctest2(&x);
std::cout << "Value is" << x;
}
Now lets compile this c++ program with C library
g++ prog.cpp libctest.a
Output is :
Value is15Value is100
I have a .lib which has a function that I want to make into a DLL.
In the project properties, I have done 2 things,
1. In the C/C++ -> General -> Additional Directories: added the path for the .h file.
2. In the Linker-> General -> Additional Dependies: added the path for the .lib file
Then I made an .h file
#ifndef _DFUWRAPPER_H_
#define _DFUWRAPPER_H_
#include <windows.h>
#include "DFUEngine.h"
#ifdef __cplusplus
extern "C" {
#endif
__declspec(dllexport) void helloworld(void);
__declspec(dllexport) void InitDLL();
#ifdef __cplusplus
}
#endif
#endif
and made the .cpp file
#include "stdafx.h"
#include "stdio.h"
#include "DFUWrapper.h"
#ifdef _MANAGED
#pragma managed(push, off)
#endif
BOOL APIENTRY DllMain( HMODULE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
return TRUE;
}
#ifdef _MANAGED
#pragma managed(pop)
#endif
void helloworld(void)
{
printf("hello world DFU");
}
DFUEngine* PyDFUEngine()
{
return new DFUEngine();
}
void delDFUEngine(DFUEngine *DFUe)
{
DFUe->~DFUEngine();
}
void PyInitDLL(DFUEngine *DFUe)
{
return DFUe->InitDLL();
}
I made a test with the function helloword. I can see this function in the DLL but not the InitDLL function.
How can I come around this? Please help
Define the following in your DLL header file
#if defined (_MSC_VER)
#if defined (MY_DLL_EXPORTS)
#define MY_EXPORT __declspec(dllexport)
#else
#define MY_EXPORT __declspec(dllimport)
#endif
#else
#define MY_EXPORT
#endif
Declare your function using that macro
#ifdef __cplusplus
extern "C" {
#endif
MY_EXPORT void helloworld(void);
MY_EXPORT void InitDLL();
#ifdef __cplusplus
}
#endif
And in your .cpp
MY_EXPORT void helloworld(void)
{
printf("hello world DFU");
}
MY_EXPORT void InitDLL()
{
/// blahblah
}
Compile your DLL with MY_DLL_EXPORT defintion....
But be sure that it's not define when you want IMPORT ....
I like exporting functions from DLLs using .DEF files.
This has the added benefit of avoiding name mangling: not only the C++ complex mangling, but also the one happening with __stdcall and extern "C" functions (e.g. _myfunc#12).
You may want to simply add a DEF file for your DLL, e.g.:
LIBRARY MYDLL
EXPORTS
InitDLL #1
helloworld #2
... other functions ...
In my project there are 3 possible types of files: pure C/Objective-C, pure C++ or Objective-C++ code.
How to divide functions in .h file with #define directives into parts to make this file available for all these files? I don't want to rename all the .m files to .mm because of problems with refactoring.
I know that I can write .h file in C which uses C++ .cpp file using the following code:
#ifndef Chadstone_CCCWrapper_h
#define Chadstone_CCCWrapper_h
#ifdef __cplusplus
#include <string.h>
extern "C"
{
#endif
void minMaxCoordinates(char *c, float *minX, float *minY, float *maxX, float *maxY);
#ifdef __cplusplus
} /* extern "C" */
#endif
#endif
but what if I want to add functions with using of NSString or list<...>.
You can find it in standard pch-file genarated by Xcode:
#ifdef __OBJC__
#endif
Also you need use CF_EXPORT macro when declaring function to prevent linkage errors.
Example:
#ifndef SOME_H_FILE
#define SOME_H_FILE
#ifdef __OBJC__
#interface SomeObjClass: NSObject
#end
CF_EXPORT void SomeFunctionWithNSString(NSString* str);
#endif
#ifdef __cplusplus
class SomeCPlusPlustClass
{
};
CF_EXPORT void someFunctionWithList(const list<int>& intList);
#ifdef __OBJ__
CF_EXPORT void someComplicatedFunction(NSString* str, const list<int>& intList);
#endif
#endif
CF_EXPORT void someFunction();
typedef struct _SomeStruct
{
} SomeStruct;
#endif