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}
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 );
}
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.
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.
Related
After I enter a string in c and store it in for example char s[100], how can I compare that string to all function names in a math.h? For example, I enter pow and the result will look like this in stored form.
s[0]='p'
s[1]='o'
s[2]='w'
s[3]='\0'
Since my string is the equivalent of pow(), I want my program to recognise that and then call pow() during execution of my program. I know it is not that hard to do string comparison within the code, but that would mean that I would have to do string comparison for every function name in the library. I don't want to do that. How is it possible to compare my string against all names in the library without hard coding every comparison?
Thank you :)
You can't, not without doing work yourself. There are no names of functions present at runtime in general, and certainly not of functions you haven't called.
C is not a dynamic language, names are only used when compiling/linking.
Regular expressions in C
Try parsing the header files using FILE and use aforementioned link as a guide to check whether the function exists or not.
I tried to make a little sample about what I assume the questioner is looking for (eval.c):
#include <stdio.h>
#include <string.h>
#include <math.h>
#include <assert.h>
/* mapping function names to function pointers and number of parameters */
struct Entry {
const char *name; /* function name */
double (*pFunc)(); /* function pointer */
int nArgs; /* number of arguments */
} table[] = {
#define REGISTER(FUNC, N_ARGS) { #FUNC, &FUNC, N_ARGS }
REGISTER(atan2, 2),
REGISTER(pow, 2),
REGISTER(modf, 2),
REGISTER(sin, 1),
REGISTER(cos, 1)
#undef REGISTER
};
/* let compiler count the number of entries */
enum { sizeTable = sizeof table / sizeof *table };
void printUsage(const char *argv0)
{
int i;
printf(
"Usage:\n"
" %s FUNC\n"
" where FUNC must be one of:\n", argv0);
for (i = 0; i < sizeTable; ++i) printf(" - %s\n", table[i].name);
}
int main(int argc, char **argv)
{
int i;
char *func;
struct Entry *pEntry;
/* read command line argument */
if (argc <= 1) {
fprintf(stderr, "ERROR: Missing function argument!\n");
printUsage(argv[0]);
return -1;
}
func = argv[1];
/* find function by name */
for (i = 0; i < sizeTable && strcmp(func, table[i].name) != 0; ++i);
if (i >= sizeTable) {
fprintf(stderr, "ERROR! Unknown function '%s'!\n", func);
printUsage(argv[0]);
return -1;
}
/* perform found function on all (standard) input */
pEntry = table + i;
for (;;) { /* endless loop (bail out at EOF or error) */
switch (pEntry->nArgs) {
case 1: {
double arg1, result;
/* get one argument */
if (scanf("%lf", &arg1) != 1) {
int error;
if (error = !feof(stdin)) fprintf(stderr, "Input ERROR!\n");
return error; /* bail out at EOF or error */
}
/* compute */
result = (*pEntry->pFunc)(arg1);
/* output */
printf("%s(%f): %f\n", pEntry->name, arg1, result);
} break;
case 2: {
double arg1, arg2, result;
/* get two arguments */
if (scanf("%lf %lf", &arg1, &arg2) != 2) {
int error;
if (error = !feof(stdin)) fprintf(stderr, "Input ERROR!\n");
return error; /* bail out at EOF or error */
}
/* compute */
result = (*pEntry->pFunc)(arg1, arg2);
/* output */
printf("%s(%f, %f): %f\n", pEntry->name, arg1, arg2, result);
} break;
default: /* should never happen */
fprintf(stderr,
"ERROR! Functions with %d arguments not yet implemented!\n",
pEntry->nArgs);
assert(0);
return -1; /* bail out at error */
}
}
}
I compiled and tested this with gcc in cygwin on Windows (64 bit):
$ gcc -std=c11 -o eval eval.c
$ ./eval
ERROR: Missing function argument!
Usage:
./eval FUNC
where FUNC must be one of:
- atan2
- pow
- modf
- sin
- cos
$ echo "1 2 3 4 5 6 7 8 9 10" | ./eval pow
pow(1.000000, 2.000000): 1.000000
pow(3.000000, 4.000000): 81.000000
pow(5.000000, 6.000000): 15625.000000
pow(7.000000, 8.000000): 5764801.000000
pow(9.000000, 10.000000): 3486784401.000000
$ echo "1 2 3 4 5 6 7 8 9 10" | ./eval sin
sin(1.000000): 0.841471
sin(2.000000): 0.909297
sin(3.000000): 0.141120
sin(4.000000): -0.756802
sin(5.000000): -0.958924
sin(6.000000): -0.279415
sin(7.000000): 0.656987
sin(8.000000): 0.989358
sin(9.000000): 0.412118
sin(10.000000): -0.544021
The usage of this application: the name of the function to apply is provided as command line argument. The values (to apply function to) are provided via standard input. In the sample session, I used echo and a pipe (|) to redirect the output of echo to the input of eval. (If eval is called stand-alone the numbers may be typed in by keyboard.)
Notes:
The table does the actual mapping of strings to function pointers. To solve that issue about the number of parameters, I considered this in struct Entry also.
The REGISTER macro is a trick to use the identifier as string constant also. The #FUNC is a stringize macro-operation (a typical C trick to prevent errors due to typos).
The sizeTable is another trick to prevent redundant definitions. I let the compiler count the number of entries. Thus, new entries may be added and it still will work without any other editing.
The actual trick is to provide a function pointer where the arguments are "left out". When it is called, the correct number of arguments is used and it works. (assuming, of course, the table initialization has been implemented carefully.) However, it would be a pain to do this in C++ because the functions with distinct number of arguments would need an appropriate function pointer with matching signature - horrible casts would be necessary. (Try to compile this with g++ -std=c++11 -c eval.c to see what I mean.)
For a productive solution, I would sort the entries by names (lexicographically) and apply a binary search (or even use hashing to be faster and more sophisticated). For this sample, I wanted to keep it simple.
math.h provides a lot of functions in "float flavor" also. These may not be added to this sample without additional effort. To support other than double arguments
some type info had to been added to the table entries
the type info has to be considered somehow in the switch statement of evaluation.
...not to mention functions where argument types are distinct to each other (or return type). (I cannot remember whether math.h even provides such functions.)
Btw. this will work for non-math.h functions also...
I have read that C does not support dynamic function calls. My program has an ever growing number of test cases implemented as separate functions like -
int testcase1(void);
int testcase2(void);
int testcase3(void);
Each time I add a new test case, I also have have to add the call to my main function like -
int main(int argc, char **argv){
assert(!testcase1());
assert(!testcase2());
assert(!testcase3());
}
I would prefer to call something like assert(!testcase*()) where * matches any string which resolves to a valid function name in my program.
Can you think of a more convenient solution?
If you all your testcases have same signature then you can use an array of function pointers:
void (*func[])() = { testcase1, testcase2 };
for (size_t i = 0; i < sizeof(func)/sizeof(func[0]); i++) {
assert(!func[i]());
}
The best solution is likely to write a few extra lines of code when you add new test cases - it really isn't a big issue. I would recommend something along the lines of the function pointer array, as suggested in another answer.
However, just to show that everything is possible in C if you throw ugly macros at the problem, here is a not recommended alternative:
#include <assert.h>
#include <stdbool.h>
#include <stdio.h>
#define TEST_CASES \ // list of "x macros"
X(testcase1) \
X(testcase2) \
X(testcase3)
#define X(func) bool func (void); // declare function prototypes
TEST_CASES
#undef X
bool (*const test_cases[])(void) = // array of read-only function pointers
{
#define X(func) &func, // point at each function
TEST_CASES
#undef X
};
int main (void)
{
for(size_t i=0; i<sizeof(test_cases)/sizeof(test_cases[0]); i++)
{
assert(test_cases[i]());
}
}
bool testcase1 (void) { puts(__func__); return true; }
bool testcase2 (void) { puts(__func__); return true; }
bool testcase3 (void) { puts(__func__); return false; }
Output:
testcase1
testcase2
testcase3
Assertion failed!
For each new test case, you would only have to write a function definition and then add it to the "x macro" list TEST_CASES. However, you need very good reasons to introduce ugly tricks like these in production code!
You can use function pointers. Read also about closures (but C99 or C11 don't have them) and callbacks.
Many operating systems provide dynamic loading. On POSIX operating systems (such as Linux or MacOSX) you can get a function pointer (actually an address) from its name in some library (or in the program executable) using dlopen & dlsym. Other operating systems may provide similar functionalities.
At last, you should consider having your testing main function be generated by some script (or some program emitting C code), using metaprogramming techniques. So you would write something which generates the C code of your testing main having a long sequence of assert, and improve your build procedure (e.g. your Makefile if using make) to run appropriately that specialized C code generator. Details are of course specific to your code. You might add some conventions (e.g. add some special comment to be parsed by your test generator, etc...).
I decided to follow #Nominal Animal and #Basile Starynkevitch's approach. In mymainprog.c, I added -
int runtests(void){
void *testh;
int (*testp)(void);
char *dlmsg;
int rc;
char funcname[8];
int testnum;
testh = dlopen("libsmtests.so", RTLD_LAZY);
if (!testh){
printf("%s\n", dlerror());
return 1;
}
dlerror();
for (testnum =1; testnum < 1000; testnum++){
sprintf(funcname,"testcase%d", testnum);
*(void **) (&testp) = dlsym(testh, funcname);
dlmsg = dlerror();
if (dlmsg == NULL) {
rc = (*testp)();
printf("%s called, rc=%d\n", funcname, rc);
}
}
dlclose(testh);
return 0;
}
I add my testcases to a separate file (testcases.c) like this -
int testcase1(void){
return [some testcase expression]
}
int testcase2(void){
return [another testcase expression]
}
and then compile it as a shared library with position-independant code (-fPIC) to libsmtests.so. The advantage is slightly less typing since I don't need to code a call to testNNNN() after adding the implementation of a new functionint testcaseNNN(void) to testcases.c
I'm currently using a simple preprocessor switch to disable/enable my debug statements. I have printf retargeted to the UART output, and then define my print function in a globally included header (globals.h) to make it easy to disable all debugging like this:
#ifdef USE_UART
#define MY_PRINT(...) printf(__VA_ARGS__)
#else
#define MY_PRINT(...)
#endif
All my application files can then print debug messages over UART like this:
MY_PRINT("\t<<Battery Voltage: %d>>\r\n", vBat);
What I'm trying to do is have this be switched by external input (ie a button press) during run time. For example something like this:
void my_print(const char * pString){
if (uart_mode == UART_ON){
printf(pString);
}
}
Where uart_mode could be toggled via the external input. I'm having trouble figuring out how to pass variable arguements properly into printf through this function. Is this possible? Is there a better way to do it?
A decent approach that avoids conditionals at runtime (though it's still dynamic dispatch) and mimics function calls precisely (because it is a function call) would be:
typedef int (*printf_func_t)(const char *, ...);
int dummy_printf(const char *format, ...) {
return 0;
}
/* Set initial value based on initial uart_mode */
printf_func_t dynamic_printf = uart_mode == UART_ON ? &printf : &dummy_printf;
In some other toggle code (where uart_mode is changed), you'd just test and reassign:
dynamic_printf = uart_mode == UART_ON ? &printf : &dummy_printf;
Actual users then always call dynamic_printf in place of printf, and it calls whichever function is currently assigned to the function pointer. No read or test of uart_mode occurs when printing, it just calls whatever function is found at the time.
How about something like this:
#define MY_PRINT(...) \
do { \
if (uart_mode == UART_ON) \
printf(__VA_ARGS__); \
} while(0)
As David Schwartz said, that's what vprintf is for.
#include <stdarg.h>
void my_print(const char * pString, ...){
va_list args;
va_start(args, pString);
if (uart_mode == UART_ON){
vprintf(pString, args);
}
va_end(args);
}
Is it possible to silence a function?
For example:
#include <stdio.h>
int function(){
printf("BLAH!");
return 10;
}
int main(){
printf("%d", silence( function()) );
return 0;
}
And instead of:
BLAH!
10
I would get:
10
Is it possible? If positive how to do it?
An awfully complicated way to do almost what you want is to use the dup2() system call. This requires executing fflush(stdout); dup2(silentfd, stdout); before function() is called, and copying back afterwards: fflush(stdout); dup2(savedstdoutfd, stdout);. So it is not possible to do as just silence(function()), since this construct only allows to execute code after function() has already been executed.
The file descriptors silentfd and savedstdoutfd have to be prepared in advance (untested code):
int silentfd = open("/dev/null",O_WRONLY);
int savedstdoutfd = dup(stdout);
This is almost certainly not what you really want, but inasmuch as your question is phrased as “is it possible?”, the answer is “almost”.
use macro function and null device.
E.g. for windows
#include <stdio.h>
#define silence(x) (_stream = freopen("NUL:", "w", stdout), _ret_value = x,_stream = freopen("CON:", "w", stdout),_ret_value)
int _ret_value;
FILE *_stream;
int function(){
printf("BLAH!");
return 10;
}
int main(void){
printf("%d", silence( function()) );
return 0;
}
No its not possible. You could however try to temporarily redirect the stdout to something else. That may come close to what you want.
You can use this macro instead of printf to be able to prevent printing:
int flag=0;
#define PRINT(...) if(flag){printf(...)}
then use PRINT macro by considering the variable flag. If flag==1, the function will print and if flag==0, the function will not print.
With GCC extensions, you might consider having macros like
bool silent;
#define silence(X) ({int _x; quiet(); _x = (X); verbose(); _x; })
#define printf(Fmt,...) \
do{if (!silent) printf(Fmt,##__VA_ARGS__);}while(0)
that silence macro would work only if its argument X is a int expression (or use typeof) I also assume that the result of printf is never used. Recall that "recursive" macros are specially pre-processed, the inside occurrence of printf (in that printf macro) is left verbatim without macro-expansion.
Notice that silence cannot be a function (otherwise, its argument would have been evaluated before calling it). And you need GCC statement expressions extension to "remember" the result of the argument in some variable _x (you could generate that name using __COUNTER__ and preprocessor concatenation), to give it back as the value of silence macro invocation.
Then you need to define your functions quiet() and verbose(), perhaps something like
void quiet()
{
silent = true;
}
void verbose()
{
silent = false,
}
if you don't want to define printf as your macro, you could use freopen(3) on stdout (perhaps with "/dev/null" etc...) or do dup2(2) tricks (like suggested by Pascal Cuoq).
If your code base is huge, and you want something more serious and are willing to spend days or weeks of work, consider customizing your GCC compiler with a plugin or a MELT extension (or ask someone to do it). Notice that printf is known to GCC.
In reality, you should define your own macro like
#define myprintf(Fmt, ...) do{if (!silent) \
printf(Fmt,__VA_ARGS__);}while(0)
and just use myprintf instead of printf everywhere, this is a portable trick. Of course, I assume you are not passing printf as a function pointer.
For debugging, I actually recommend
#define dbgprintf(Fmt,...) do{if (wantdebug) \
printf("%s:%d:" Fmt "\n", __FILE__, __LINE__, \
##__VA_ARGS__);}while(0)
and then I use dbgprintf("i=%d",i) or simply dbgprintf("foo here") in my code.
I'm using ##__VA_ARGS__ which is a GCC extension to accept no variable arguments to a variadic macro. If you want strict C99, you will just say __VA_ARGS__ and every dbgprintf would need one argument after the format.
You could also re-implement your own printf function, but I don't advise doing that.
(Notice that things could be more complex, you can print using fputs not printf ....)
If you're designing the function do the following:
int function(void (*printer)(char *)){
if (!printer)
printer = printf;
printer("BLAH!");
return 10;
}
void silence(char *s){
return;
}
int main(int argc, char **argv){
printf("%d\n", function(silence));
return 0;
}
That should do what you're looking for. Unfortunately, I didn't test it and my C is probably a little bit rusty.
Of course if function isn't something you have control over, the answers already posted are all correct solutions.
Actually, if you're designing the function yourself, just do:
int function(int print){
if (print)
printf("BLAH!");
return 10;
}
function(0); /* Won't print anything */
function(!0); /* Will print "BLAH!" */
because 0 is false and any non-zero (or !0) value is true. My above suggestion is error prone since you'll have to be able to mimic the printf signature for silence or for any other function you wish to use.
Unfortunately if you have the function explicitly printing and call it like this then it will always print. if you want to silence the function completely you could simply comment out that line.You could even use a control statement so that it only prints IF and when a condition is met otherwise it stays blank and only returns the number.
I'm working on implementing a very, very basic component system in C, but now I am at a point where I want to 'dynamically' call some functions. The set-up is very easy: the main program is simply an endless while loop, in which some conditions are checked and in which a "process" function is called for each enabled component.
For example, now it works like this:
while (1) {
input_process();
network_process();
graphics_process();
}
But I want to separate it into separate components, and somehow define in a central place which parts are used. This could be done with simple defines, like so:
#define HAS_NETWORK
...
while (1) {
input_process();
#ifdef HAS_NETWORK
network_process();
#endif
graphics_process();
}
As you can see this is alright for 1 or maybe only a few components, but if I want to do this for all of these (input, network and graphics) and additional components in the future, I would have to put separate #ifdefs in there for each of them, and that's quite tedious.
In pseudo code, what I'm trying to accomplish is the following:
components = {'input', 'network', 'graphics'}
...
foreach component in components
execute component_process()
This way components could easily be added in the future.
I don't really mind if the checking is done compile time or run time (although I obviously prefer compile time, but I can imagine run time is easier to implement). I have no idea how to even start.
You need pointers to functions, create an array of pointers to functions and index it dynamically.
Here link about function pointers.
Compile-time solution: a pre-build step and include directive inside that loop, e.g.
while (1) {
#include "components.generated.c"
}
A basic script to generate that file might look like (Python):
components = ('input', 'networking', 'graphics')
# this could also be e.g. a glob on a directory or a config file
with open('components.generated.c', 'w') as fp:
for component in components:
print >>fp, '%s_process();' % component
Any decent build system will allow you to do that.
What's wrong with the ol' if condition?
if (hasNetwork)
{
network_process();
}
Function pointers are great!
typedef void (*process_fun)(void);
process_fun processes[] =
{ input_process, network_process, graphics_process };
#define NELEMS(A) (sizeof(A) / sizeof((A)[0]))
while (1) {
for (int i = 0; i < NELEMS(processes); i++)
processes[i]();
}
The NELEMS macro, which I learned from Dave Hanson, is also one of my favorites.
P.S. Avoid #ifdef at all costs :-)
At compile time with an X macro :
component.x is a file containing :
COMPONENT( graphic , "3D graphics rendering" )
COMPONENT( network , "Network" )
COMPONENT( other , "usefull stuff" )
#undef COMPONENT
Use it with :
#define COMPONENT( what , description ) what ## _process();
while (1)
{
#include "components.x"
}
And in another place for instance :
std::cout << "We use :\n" ;
#define COMPONENT( what , description )\
std::cout << #what << " : " << description << "\n" ;
#include "components.x"
and with this you can place the HAS_ defines in a single place in component.x :
#ifdef HAS_GRAPHIC
COMPONENT( graphic , "3D graphics rendering" )
#endif
#ifdef HAS_NETWORK
COMPONENT( network , "Network" )
#endif
#ifdef HAS_OTHER
COMPONENT( other , "usefull stuff" )
#endif
#undef COMPONENT
You can do this with an array of function pointers.Generally I try to avoid function pointers like the plague, but it may be your best bet.
Alternatively, you can create a component process function that takes an int argument, and then has a nasty switch statement... but for this to work, you need to keep adding to the component_process function.
Alternatively-alternatively, you could do this in C++, create a virtual Component class, that just has one method "process", with a bunch of subclasses, and you run through an array of components (actually objects of the subclasses) and call the process method.
your components should be an array of pointers to functions
enum components
{
input,
network,
graphics,
num_components
}
void process_audio()
{
}
void process_network()
{
}
void process_graphics()
{
}
void (*process_component[num_components])();
process_component[0] = &process_audio;
process_component[1] = &process_network
process_component[2] = &process_graphics;
for (int i = 0; i < num_components; i++)
process_component[i]();
Here's an example of the syntax to do this at runtime with an array of function pointers:
void f( void ) { puts( "f" ); }
void g( void ) { puts( "g" ); }
void h( void ) { puts( "h" ); }
void (*array[])(void) = { f, h, 0 };
int main(void) {
void (**t)(void);
for( t = array; *t; t++ )
(*t)();
}
Another possibility: Keep the loop as is, ie
while (1) {
input_process();
network_process();
graphics_process();
}
and add the following preprocessor directives to the file header:
#ifndef HAS_NETWORK
#define network_process() ((void)0)
#endif
#ifndef HAS_GRAPHICS
#define graphics_process() ((void)0)
#endif