2

I have a program to find the reciprocal of a number but the main program is written in C and the reciprocal function is written in c++.Next I have a header file reciprocal.hpp that has some of the conditional compilation code that makes the reciprocal function an extern function.Can someone please explain me what is there in the reciprocal.hpp program.

main.c

#include<stdio.h>
#include<stdlib.h>

int main(int argc,char **argv)
{
int i;
i = atoi(argv[1]);
printf("\nThe reciprocal of %d is %f\n",i,reciprocal(i));
return 0;
}

reciprocal.cpp

#include<cassert>
#include "reciprocal.hpp"

double reciprocal(int i)
{
assert( i != 0);
return 1.0/i;
}

reciprocal.hpp

#ifdef __cplusplus
extern "C"
{
#endif

extern double reciprocal(int i);

#ifdef __cplusplus
}
#endif

I don't understand what is happening in reciprocal.hpp.Please help!!

Martin York
  • 257,169
  • 86
  • 333
  • 562
station
  • 6,715
  • 14
  • 55
  • 89
  • 2
    Your question really is about C++. Tag replaced. I believe the `extern "C"` thingamaging prevents the C++ compiler from doing *name-mangling* – pmg Jul 19 '11 at 15:03
  • possible duplicate of [extern "C"](http://stackoverflow.com/questions/1041866/extern-c) – interjay Jul 19 '11 at 15:06
  • Also: http://stackoverflow.com/questions/67894/why-do-we-need-extern-c-include-foo-h-in-c – interjay Jul 19 '11 at 15:07
  • @interjay: Not an exact duplicate (but close) as this also deals with the pre-processor and how to handle the difference between C/C++ – Martin York Jul 19 '11 at 15:31
  • 1
    @pmg: It does a bit more. It forces the compiler to use the C ABI. This mean a couple of difference in how code is generated. For Example: passing parameters/return value on the stack in C (usually). passing parameters and return values via registers if the compiler deems this to be more efficient in C++(usually). As in all examples your mileage may very with compiler and optimization settings. – Martin York Jul 19 '11 at 15:33

2 Answers2

7

C++ compilers always define the __cplusplus symbol. So, what the header is doing is wrapping the prototype in

extern "C" { ... }

This tells the compiler not to perform name mangling on whatever is enclosed within that block. Now, the C code can refer to the function by its original name as if it were a C function.

Praetorian
  • 106,671
  • 19
  • 240
  • 328
  • why the need for two #ifdef __cplusplus – station Jul 19 '11 at 15:08
  • The `extern "C"` declaration only applies to the statement immediately following it. To make it apply to several statements you enclose all those statements within the `{}` block. The second `#ifdef` is to switch the closing brace in and out. – Praetorian Jul 19 '11 at 15:21
1

If you're referring to the ifdefs, they simply allow the function to be exported to C if the header is compiled as C++. The extern line simply defines a function prototype for reciprocal.

Michael Mior
  • 28,107
  • 9
  • 89
  • 113