AmiDARK
AmiDARK

Reputation: 23

C Get function line number from within 2 function calls

In the process of developing a small SDK, I need to create an "error handler". To make more effective I want to get the line number where the function was called and I don't know if it's possible in C (using GCC for compiling).

When a SDK function is called, the SDK function itself will call the error handler function if an error occurred.

With that I'd like to know if there is a way to know the line number from the user source code that called the function.

Example :

User.c :

main{ CallSDKFunction(); }

SDK.a file :

void CallSDKFunction( void ){ if ( ERROR ){ CallERRORHandler(); } }

... ... ...

void CallERRORHandler( void ){ // Here I want to know in which line in user.c the CallSDKFunction was called}

Upvotes: 2

Views: 181

Answers (3)

user3386109
user3386109

Reputation: 34829

One approach is to pass the __FILE__ and __LINE__ to the SDK function, and then have the SDK function pass them on to the error handler function. However, the user won't want to be bothered with that, so you need to define a macro in the SDK's header file that hides the details. The macro would look like this

#define CallSDKFunction(a,b) actualSDKFunction( __FILE__, __LINE__, a, b )

The user would call the SDK with code like this. Note that the user doesn't need to know that the __FILE__ and __LINE__ are being passed to the SDK function. The macro takes care of that.

int main( void )
{
    int a = 3;
    int b = 4;
    int result = CallSDKFunction( a, b );  
    printf( "%d\n", result );
}

And the SDK implementation would be something like this

int actualSDKFunction( const char *fileStr, int lineNum, int a, int b )
{
    if ( a+b > 5 )
        CallERRORHandler( fileStr, lineNum );
    return( a+b );
}

void CallERRORHandler( const char *fileStr, int lineNum )
{
    printf( "Bad values in file %s at line %d\n", fileStr, lineNum );
}

Upvotes: 1

Sourav Ghosh
Sourav Ghosh

Reputation: 134336

If I have understood your requirement properly, you can make use of __FILE__and __LINE__ MACRO to get the filename and the line number of any instruction. These two are standard predefined MACRO. You can check Online GCC reference.

Also, there is __func__ (C99) which gives you the current function name.

So, as you want, you can define the another function prototype (maybe in debug mode), which passes on (and accepts) the extra parameters like __FILE__, __LINE__, __func__ etc while making the function call. Then , you can have the caller function name and line displayed from the called function.

Alternatively, you can also have a look at backtrace() function. However, it is a GNU extension.

Upvotes: 1

M Oehm
M Oehm

Reputation: 29126

The C preprocessor has the special tokens __LINE__ and __FILE__, which expand to the current line (as integer) and the current file (as C string).

To make it work, you must declare a wrapper macro:

void error(int line, const char *file)
{
    fprintf(stderr, "Error in %s, line %d\n", file, line);
    // handle error
}

#define ERROR() error(__LINE__, __FILE__)

This will pass the information on the location of the macro invocation to the error handler.

Upvotes: 1

Related Questions