Use preprocessor to "remove" prefix from function in C - c

I write a framework with lot of function that are named like that :
ICE_ModuleType_FunctionUse()
and everything else have ICE_ prefix (typename, define etc...)
And with preprocessor I would like to remove ICE_ to reduce function name lenght when the user know there is no conflict with other libs.
But the only working way I found was to write every function, type etc... by hand like that :
#define ModuleType_FunctionUse ICE_ModuleType_FunctionUse
Any Idea on how to easly do that ?

You could automatically create a new header file with a name like use_namespace_ICE.h for your clients to use. This file would have the required list of #defines, and can be generated using the utilities nm or dumpbin applied to your library.
For example, if foo.c is:
void ICE_ModuleType_FunctionUse(void) { /* code */ }
then:
cc -c -o foo.o foo.c
nm foo.o | grep ' T _ICE_' | sed 's/.* T _ICE_\(.*\)/#define \1 ICE_\1/'
yields:
#define ModuleType_FunctionUse ICE_ModuleType_FunctionUse

As the comments tell you, there is no way, or no easy way, to shorten identifiers once written in your source code. However, you can reduce the typing for things that still need to be written:
#define ModuleType_FunctionUse ICE_ModuleType_FunctionUse
This defines that the short name will be replaced with the longer name.

Related

C Makefile commands

I was trying to build a C project which has a rather unfamiliar way to define namespaces, eg. in file root.h
#define eval CRYPTO_NAMESPACE(eval)
And in the Makefile the following appears (rule for make all):
gcc -O3 -g -march=native -mtune=native -Wall -I. -Isubroutines -DKAT -DKATNUM='cat KATNUM' "-DCRYPTO_NAMESPACE(x)=x" "-D_CRYPTO_NAMESPACE(x)=_##x" -o kat nist/kat_kem.c nist/rng.c benes.c bm.c controlbits.c decrypt.c encrypt.c gf.c operations.c pk_gen.c root.c sk_gen.c synd.c transpose.c util.c -I${PWD}/subroutines -L${PWD}/libs/ -lXKCP -lcrypto -ldl
What do these options do:
"-DCRYPTO_NAMESPACE(x)=x" "-D_CRYPTO_NAMESPACE(x)=_##x"
I know that -DXXX=YYY is the same as #define XXX YYY. Now, why is it in double-quotes? Why it looks like a macro (may be it is)? Lastly, what does _##x mean?
The macro in the header:
#define eval CRYPTO_NAMESPACE(eval)
Replaces every token eval with CRYPTO_NAMESPACE(eval). So if the code contains
void eval(char *expr) {
...
the preprocessor output - without any other definition - would be
void CRYPTO_NAMESPACE(eval)(char *expr) {
...
The -D parameters effectively add two more definitions:
#define DCRYPTO_NAMESPACE(x) x
#define _CRYPTO_NAMESPACE(x) _##x
In our example, the first define causes the normal result to be re-written one more time:
void eval(char *expr) {
...
so we're back where we started. A different definition could be used to change the compiled name of the function. This definition makes the header definition a no-op.
The second macro uses the token concatenation operator ##. It adds a prefix underscore _ to the macro argument. E.g. if the code contained something like:
void _CRYPTO_NAMESPACE(foo)(int x) {
then the result is
void _foo(int x) {
At a higher level, these macros allow names of things (in the first case anything named eval and in the second, any name at all) to be transformed uniformly throughout the program. This is a fairly standard workaround for name collisions in big C programs. If you have two source code bases that have both defined the same public function name, macros like this can be used to add a prefix or suffix that changes one or both names in the compiled code without modifying either original code. This is an important capability for long-term configuration management where manually editing externally furnished code bases isn't a serious option.
A wild guess is that this treatment is given to eval because the likelihood of some other chunk of C also defining a function named eval is extremely high.

Display changed definitions of a header file in C

Lets say there is this code:
#ifndef TEST_H_
#define TEST_H_
#define NAME "John Doe"
#endif
The definition NAME is used in one of the .c files
void print_name()
{
printf("Name is: %s\n\n",NAME)
}
Is it possible to compile the program.. then change the value of NAME to "Johnny" and when the program is run again.. without compiling it, It prints "Johnny" instead of "John Doe"??
I am just curious to know if it is possible.
Thanks for any help or advice..
Not trivially. Included files get pasted into the source and the source nor the headers no longer technically exist in the binary output.
You can however edit the binary, and if you do it right (e.g., can't replace a 10-character string with a 3-character replacement as that'd misalign stuff), you can get it to work.
Example: (your example simplified):
#include <stdio.h>
int main()
{
printf("Name is: %s\n\n","John Doe");
}
Compile, run, edit, re-run:
$ gcc file.c
$ ./a.out
Name is: John Doe
$ sed -i 's/John Doe/Johnny\x00\x00/' a.out
$ ./a.out
Name is: Johnny
That depends on what you mean by not re-compiling. You need to change the program file somehow, but you can do that in various ways:
A hex editor other "direct" modification of the executable file, where you can look for the string "John Doe" and replace it with "Johny" (with extra null-byte padding), as described by PSkocik and MustacheMoses
Depending on the modification, I am fairly sure there are more specialized tools for attempting them. I don't know what they are, though.
You could also make NAME be an extern variable instead of a macro, with extern char *NAME; in a header file and char *NAME = "John Doe"; in a separate .c file. Then if you want to change the name, you just need to change it in the one, small, file where it's defined, re-compile that, and then just re-link with the rest of the program. That still involves some re-compiling, but it's a lot faster than re-compiling everything.
To make a recommendation I'd need to know your use case, but the third option I mention is a lot more common than just modifying an executable file directly.
Yes you can use something called a hex editor to change the contents of stored strings in the generated executable.
A macro is something that cannot change without recompiling again. It's not a variable or something you can operate on, so it's imposible to make a macro to give a different value than programmed, but to change the value and recompile.
You can give the macro different definitions, based on the value of another macro (one that you can pass the compiler on the command line when compiling) but anyway, you need to recompile the source again. This allows you to tweak the file without having to edit it, but never avoids you to recompile it again.
source.c
#include <stdio.h>
#ifndef VERSION
#define VERSION 0
#endif /* VERSION */
#if VERSION
#define NAME "John Doe"
#else
#define NAME "Johnny Guitar"
#endif
int main()
{
puts("the winner is " NAME);
} /* main */
that you can compile with
$ cc source.c
$ a.out
the winner is Johnny Guitar
$ _
or
$ cc -DVERSION=1 source.c
$ a.out
the winner is John Doe
$ -
It is possible if the program opens the header file, scans to find #define NAME line, then gets the value. Something like very simple preprocessor. And if you add #if or #ifdef conditions, the final value may be invalid.
Not. Definitions are part of the preprocessor and aren't not the C variables and symbols. During the preprocessing definitions are textually replaced by their values
If you need to change something during the program execution you need the C variable
char NAME[] = "John Doe";
And you are done

List all functions declared in header but missing in the source file?

Question
Are there some linters/statical analyzers that warn/error on functions, that are declared in the header file but not implemented in the corresponding source file?
Lets say we have the following header (guard omitted):
/* example.h */
int doSomething(int i);
double doSomethingElse(double d);
And the following source:
/* example.c */
#require "example.h"
int doSomething(int i) {
return i + 1;
}
So is there some tool, that can tell me that doSomethingElse() is missing in example.c?
Why asking?
In an exercise we got some headerfiles with a fully fletched interface, and partially prepared sourcefiles, with some functions beeing fully provided, some functions beeing partially provided, and some missing.
For actually running and compiling this programm it was enough to complete the partially provided functions, but still there is some discrepancy between the defined interface in the header and the now provided functions in the source file.
I could go through all header/source pairs by hand and implement the missing funtions, but it would be nice to have some autogenerated todolist.
I'd just do it with grep etc.:
grep ');' foo.h | tr -d ';' | while read decl
do
if ! grep -q "$decl" foo.c
then
echo "not found: $decl"
fi
done
No, this isn't perfect, but it might work if your use case is as simple as you've outlined.

Conditional compilation: compile once if macro is present at least once

I'm writing a C program and would like to write a function so that, if a certain macro is used at least once, the function is compiled in the object file exactly once.
I was thinking of something in these lines:
#define CERTAIN_MACRO \
...some code here... \
#include "myfunction.h"
(adding my function code in myfunction.h, with suitable include guards in order to prevent multiple inclusion), or
#define CERTAIN_MACRO \
...some code here... \
#define USE_MY_FUNCTION
#ifdef USE_MY_FUNCTION
my function code
#endif
But neither works, because #define and #include are not allowed in macro-expanded code. Any suggestions?
Let the linker do the job it's meant to.
Place the function into its own source file and then build that into a library, say liboptional.a.
When it comes time to create the executable, use that library, for example:
gcc -o execfile file1.o file2.o -loptional
At the time the linker sees the -l optional, it will use the objects within that library to satisfy undefined references. Hence, if you're used the function in file1.o or file2.o, it will be included.

Pre-preprocessor

I want to have a C pre-preprocessor which is filtering some #define statements from the sourcecode without changing anything else.
Why? This should be used to remove some client specific code from the sources if the source is handed out to another client.
Does anyone know of an existing solution?
Thanks!
Simon
You can use something like awk instead of CPP ? Add some flags in your code surrounding the piece of code to be removed. For example:
(...)
//BEGIN_REMOVE_THIS_CODE
printf("secret code");
//END_REMOVE_THIS_CODE
(...)
then write a awk script to remove this code, something like...
BEGIN { write=1;}
/^\/\/BEGIN_REMOVE_THIS_CODE/ { write=0; next;}
/^\/\/END_REMOVE_THIS_CODE/ { write=1; next;}
{
if(write==1) print $0;
}
I recommend using an additional macro language layer for code filtering, like filepp. You may use a C preprocessor friendly syntax to express which parts belongs to which clients.
//%ifdef CLIENT_A
code for client A
//%endif
//%ifdef CLIENT_B
code for client B
//%endif
//%if "CLIENT_A" || "CLIENT_B"
code for client A and B
//%endif
The '//%' prefix enables You to compile the code unmodified. You may run filepp before You giving out the code to a client.
This sounds like what I asked about in Is there a C pre-processor which eliminates ifdef blocks based on values defined. The best answer I got was sunifdef, or 'Son of unifdef', which has worked reliably for me on some excessively contorted conditional code (the accumulated crud from over 20 years of development on a wide variety of platforms with an inadequate theory of how to do platform-specific compilation).
I don't think you need a preprocessor for this. If you don't have nested #ifdef's in your code, any regex engine can remove anything that is located between #ifdef CLIENT and #endif (use non-greedy matching to match first #endif, not last).
I would put the client specific code in a separate directory or possibly part of a different project that would need to be checked out of the source control.
Put a function call that would be stubbed out or (I forget the proper term) loosely linked so that another function can be put in its place.
If you're using gcc, then you can use:
gcc <insert files here> -E
The -E option tells gcc to only preprocess the sources, and not to compile them.
Or, you could use grep to filter out specific files and let the preprocessor loose on them only.
grep -r '#define CLIENT_CODE' ./*.h
You can also try unifdef which is rather simpler than sunifdef.
Why don't you do something like:
client_a_specific_functions_definition.c
double discount_for_paying_upfront() { return 0.1; };
// ...
client_b_specific_functions_definition.c
double discount_for_paying_upfront() { return 0.05; };
// ...
When you hand out the code it is just a matter of selecting the right file with their specific definitions.
Then you would create a header file to include it where you need to access the client specific code with something like:
client_functions.h
#pragma once
double discount_for_paying_upfront();
#define stringify(x) #x
#define FILE2(a) stringify(client_##a##_specific_functions_definition.c)
#define FILE(a) FILE2(a)
#include FILE(CLIENT_NAME)
#undef stringify
#undef FILE2
#undef FILE
Then say you #include "client_functions.h" in your main.c. You could compile it with:
gcc -DCLIENT_NAME=a main.c -o a.exe
gcc -DCLIENT_NAME=b main.c -o b.exe
as far as I know... the preprocessor can be run as a separate step (using the correct compiler optios) . This way you can do whatever you want with the processed code.

Resources