Page 1 of 2

Using GCC's built-in functions instead of self-written ones

Posted: Sat Apr 30, 2016 4:26 am
by Neroku
Hello,

I've been using for a while my own functions like memset(), strcmp() and so on. After I found a bug in one of them I decide to use the GCC's built-in functions instead of mine. =;
In the section "Other Builtins" of the GCC's manual state the following:
GCC includes built-in versions of many of the functions in the standard C library. These functions come in two forms: one whose names start with the __builtin_ prefix, and the other without.
The ISO C90 functions abort, abs, acos, asin, atan2, atan, calloc, ceil, cosh, cos, exit, exp, fabs, floor, fmod, fprintf, fputs, frexp, fscanf, isalnum, isalpha, iscntrl, isdigit, isgraph, islower, isprint, ispunct, isspace, isupper, isxdigit, tolower, toupper, labs, ldexp, log10, log, malloc, memchr, memcmp, memcpy, memset, modf, pow, printf, putchar, puts, scanf, sinh, sin, snprintf, sprintf, sqrt, sscanf, strcat, strchr, strcmp, strcpy, strcspn, strlen, strncat, strncmp, strncpy, strpbrk, strrchr, strspn, strstr, tanh, tan, vfprintf, vprintf and vsprintf are all recognized as built-in functions unless -fno-builtin is specified
I am implicitly using the -fno-builtin compiler option by passing the -ffreestanding option to the compiler.
In the section "C Dialect Options" of the GCC's manual it is found the following:
-fno-builtin
-fno-builtin-function
Don't recognize built-in functions that do not begin with ‘__builtin_’ as prefix.
if you wish to enable built-in functions selectively when using -fno-builtin or -ffreestanding, you may define macros such as:

#define abs(n) __builtin_abs ((n))
#define strcpy(d, s) __builtin_strcpy ((d), (s))
What's written above is what I am doing, however I keep on getting error messages at linking similar to the one below:

Code: Select all

fat16.c:(.text+0x4fb): undefined reference to 'strncmp'
I am also linking all the objects against -lgcc (placing it at the very end of the line). It seems GCC is not linking these functions against its built-in functions :cry:
Any ideas? #-o


Thanks in advance

Re: Using GCC's built-in functions instead of self-written o

Posted: Sat Apr 30, 2016 4:51 am
by Octocontrabass
Many of these functions are only optimized in certain cases; if they are not optimized in a particular case, a call to the library function is emitted.

Re: Using GCC's built-in functions instead of self-written o

Posted: Sat Apr 30, 2016 7:01 am
by Neroku
Octocontrabass wrote:
Many of these functions are only optimized in certain cases; if they are not optimized in a particular case, a call to the library function is emitted.
I've just prepared an example where I expect the function to be optimized:

Code: Select all

size_t len;
len = strlen("foo");
...and I don't get now the undefined reference error message. =D>


My assumptions about GCC's built-in functions were wrong. ](*,)
Then, we must implement these functions in our code if we want to be able to use them for all the scenarios, mustn't we?


Thanks a lot.

Re: Using GCC's built-in functions instead of self-written o

Posted: Sat Apr 30, 2016 7:18 am
by gerryg400
That's correct. You need to have all the functions in your libc just in case gcc decides not to optimise. BTW, some of the optimisations call other functions. For example, printf() will often be optimised as puts() or putchar(). Basically gcc expects a conforming libc.

Re: Using GCC's built-in functions instead of self-written o

Posted: Sat Apr 30, 2016 8:03 am
by Neroku
I was mixing up basic concepts such as built-in functions and the libgcc.
Built-in functions are placed by the compiler (hence the name). Regarding the libgcc, from "The GCC low-level runtime library":
Most of the routines in libgcc handle arithmetic operations that the target processor cannot perform directly. This includes integer multiply and divide on some machines, and all floating-point and fixed-point operations on other machines. libgcc also includes routines for exception handling, and a handful of miscellaneous operations.
For that reason I wasn't able to find text-code-section symbols like memcpy or memset in the libgcc I was linking my object files against.

Thanks to all of you :D

Re: Using GCC's built-in functions instead of self-written o

Posted: Sat Apr 30, 2016 11:40 am
by glauxosdever
Hi,

https://gcc.gnu.org/onlinedocs/gcc/Standards.html wrote:Most of the compiler support routines used by GCC are present in libgcc, but there are a few exceptions. GCC requires the freestanding environment provide memcpy, memmove, memset and memcmp. Finally, if __builtin_trap is used, and the target does not implement the trap pattern, then GCC emits a call to abort.
So you actually need only memcmp(), memcpy(), memmove(), memset() and abort().

Also, I don't see why is writing a couple of string functions so hard and troublesome. They are at most 10 lines of C code on average. And if you have trouble implementing them correctly, there is the POSIX specification. For example here is the specification for memcmp().


Regards,
glauxosdever

Re: Using GCC's built-in functions instead of self-written o

Posted: Sat Apr 30, 2016 11:56 pm
by FallenAvatar
glauxosdever wrote:Hi,

https://gcc.gnu.org/onlinedocs/gcc/Standards.html wrote:Most of the compiler support routines used by GCC are present in libgcc, but there are a few exceptions. GCC requires the freestanding environment provide memcpy, memmove, memset and memcmp. Finally, if __builtin_trap is used, and the target does not implement the trap pattern, then GCC emits a call to abort.
So you actually need only memcmp(), memcpy(), memmove(), memset() and abort().

Also, I don't see why is writing a couple of string functions so hard and troublesome. They are at most 10 lines of C code on average. And if you have trouble implementing them correctly, there is the POSIX specification. For example here is the specification for memcmp().


Regards,
glauxosdever
How easy is it to implement them as effeciently as possible? (And who the heck mentioned POSIX? [which is outdated garbage at this point...])

- Monk

Re: Using GCC's built-in functions instead of self-written o

Posted: Sun May 01, 2016 4:02 am
by Neroku
glauxosdever wrote:
https://gcc.gnu.org/onlinedocs/gcc/Standards.html wrote:Most of the compiler support routines used by GCC are present in libgcc, but there are a few exceptions. GCC requires the freestanding environment provide memcpy, memmove, memset and memcmp. Finally, if __builtin_trap is used, and the target does not implement the trap pattern, then GCC emits a call to abort.
So you actually need only memcmp(), memcpy(), memmove(), memset() and abort().
Then, how I can use every time the string functions provided by GCC (i.e.: the built-in string functions)?
Seemingly, it only works when GCC is able to optimize the call to these functions, e.g.: when the string passed to strlen() can be determined at comile-time:
Octocontrabass wrote:
Many of these functions are only optimized in certain cases; if they are not optimized in a particular case, a call to the library function is emitted.
Besides, I don't find these string functions in the libgcc.

Code: Select all

nm libgcc.a | grep str
         U strlen
         U strlen
Am I making wrong assumptions?


Thanks in advanced

Re: Using GCC's built-in functions instead of self-written o

Posted: Sun May 01, 2016 4:34 am
by glauxosdever
Hi,

Neroku wrote:Then, how I can use every time the string functions provided by GCC (i.e.: the built-in string functions)?
Simple, you implement them. Or you use __builtin_function instead of function.

I still can't understand what is wrong with writing a couple of string functions. For example strlen() can be implemented like this:

Code: Select all

size_t strlen (const char* s)
{
	size_t i = 0;
	while (s[i] != '\0')
	{
		i += 1;
	}
	return i;
}
Is it really so hard? If so, writing an operating system is impossible compared to that.
tjmonk15 wrote:And who the heck mentioned POSIX? [which is outdated garbage at this point...]
POSIX specifies these functions most correctly. Man pages on your Linux system often have flaws.


Regards,
glauxosdever

Re: Using GCC's built-in functions instead of self-written o

Posted: Sun May 01, 2016 5:39 am
by Neroku
Hello glauxosdever,

let's go one step at a time:
  • glauxosdever wrote:I still can't understand what is wrong with writing a couple of string functions.
    I think you could be taking me wrong. The topic of this post is not about implementing your own string functions, but how to use the ones already provided.
    It is not as if I got stuck, since I can use my own functions, but I would really know what's going wrong here.
  • glauxosdever wrote:
    Neroku wrote:Then, how I can use every time the string functions provided by GCC (i.e.: the built-in string functions)?
    Simple, you implement them. Or you use __builtin_function instead of function.
    That's actually my problem. By writing just __builtin_function instead of function I don't get it working. For instance, I get the following regarding to the strncmp():

    Code: Select all

    fat16.c:(.text+0x4fb): undefined reference to 'strncmp'

I assume GCC only links against the built-in functions when it is not able to optimize the function call, otherwise it looks for a function in a library, just as Octocontrabass suggested:
Octocontrabass wrote:
Many of these functions are only optimized in certain cases; if they are not optimized in a particular case, a call to the library function is emitted.
But I may be wrong... #-o
Any ideas?


Thanks a lot

Re: Using GCC's built-in functions instead of self-written o

Posted: Sun May 01, 2016 9:22 am
by Octocontrabass
glauxosdever wrote:
Neroku wrote:Then, how I can use every time the string functions provided by GCC (i.e.: the built-in string functions)?
Simple, you implement them. Or you use __builtin_function instead of function.
Builtin functions are not replacements for C library functions. If you want to use a builtin function, you must also have a working implementation of that function in your C library.

Re: Using GCC's built-in functions instead of self-written o

Posted: Sun May 01, 2016 11:20 am
by glauxosdever
Hi,

Octocontrabass wrote:Builtin functions are not replacements for C library functions. If you want to use a builtin function, you must also have a working implementation of that function in your C library.
It seems you are right. I missed this point (emphasis mine):
https://gcc.gnu.org/onlinedocs/gcc/Other-Builtins.html wrote:GCC includes built-in versions of many of the functions in the standard C library. These functions come in two forms: one whose names start with the __builtin_ prefix, and the other without. Both forms have the same type (including prototype), the same address (when their address is taken), and the same meaning as the C library functions even if you specify the -fno-builtin option see C Dialect Options). Many of these functions are only optimized in certain cases; if they are not optimized in a particular case, a call to the library function is emitted.
Neroku wrote:It is not as if I got stuck, since I can use my own functions, but I would really know what's going wrong here.
Still, built-in functions are such a hassle, so you should better not rely on them. As for wanting to know what is wrong here, it is because these functions you are trying to use are nowhere declared and at the same time the built-ins emit a call to them, as proven just above.

I hope I helped. :)


Regards,
glauxosdever

Re: Using GCC's built-in functions instead of self-written o

Posted: Sun May 01, 2016 12:52 pm
by Rusky
To clarify a bit, the builtin functions are not actually functions. They are bits of compiler magic that let the compiler understand the intent of a function, and only come into play in cases where the optimizer feels like it's a good idea to generate some code inline. When the optimizer feels like it'd be better to call out to a full implementation, it needs a separate full implementation, since the builtin functions don't actually provide any code.

With that in mind, you need to provide your own implementations (or use a libc's), and then the builtin functions are just a way to get a free performance boost (either by turning or leaving on -fbuiltin or by calling __builtin_ functions).

Re: Using GCC's built-in functions instead of self-written o

Posted: Wed May 04, 2016 12:17 pm
by Neroku
Now, that I think the question is clear for all of us, I'm making my proposal: considering I want to let GCC replace the calls to my library functions with its built-in functions whenever possible.

I define a preprocessor macro for each function I want to let GCC to be replaced. This macro expands to the text __builtin_ prefixed to the actual function name. I surround the corresponding functions's prototype with a conditional directive checking against the inexistence of the just-defined preprocessor macro. Finally I provide the code for my function being preceded by the preprocessor directive #undef which does away with the previously defined macro.

For example, for strlen() I would proceed just as follows:
In the file string.h:

Code: Select all

#define strlen(s)    __builtin_strlen((s))
...
#ifndef strlen
size_t strlen(const char *);
#endif
In the file string.c:

Code: Select all

#include <string.h>

#undef strlen
size_t strlen(const char *s)
{
    // my implementation
    ...
}
Any suggestions are welcome.

Thank you, all of you.

Re: Using GCC's built-in functions instead of self-written o

Posted: Thu May 05, 2016 11:36 pm
by Combuster
I want to let GCC replace the calls to my library functions with its built-in functions whenever possible.
Why don't you just simply compile with optimisations enabled instead of doing all these ifdefs? That way you can't mess things up.