C Basics

Some basic concepts about the programming language C

01. Apr 2024

Tips

  • Use void in functions without parameters. For example: int main(void) { ... }
  • Use #pragma once at the beginning of a header file to prevent multiple inclusion.
  • Use the compiler flags -Wall, -Wextra and -Werror for additional hints.
  • Use the compiler flag -g to be able to debug your program with gdb.
  • Use the compiler flag -rdynamic the keep function names in binary exectuables.

Error Handling

Signal Handling

Create a function which handles the signal.

void handle_sigint() {
  // do nothing
}

Register the signal handler with sigaction().

struct sigaction sigint_action;
sigint_action.sa_handler = handle_sigint;
sigint_action.sa_flags = 0;
sigemptyset(&sigint_action.sa_mask);
sigaction(SIGINT, &sigint_action, NULL);

Segfault Backtracing

Create a function which handles the signal. Register the signal handler with sigaction() to the SIGSEGV signal. Specify a list of a certain length which will later correspond to the levels of backtracing. Print the backtrace with backtrace_symbols_fd() and call exit to stop the program.

void handle_segfault(int signal) {
  void *list[10];
  size_t size = backtrace(list, 10);
  fprintf(stderr, "ERROR: signal %d:\n", signal);
  backtrace_symbols_fd(list, size, STDERR_FILENO);
  exit(1);
}

The compiler flag -rdynamic is required in order to view the function names in the backtrace.

Localization

setlocale(LC_ALL, "de_DE.UTF-8");

Make sure you have the desired language installed on your system.

Use a custom shared library

The shared library gets linked during runtime. A shared library should start with the prefix lib.

  1. Copy the header file to /usr/local/include/.
  2. Compile the shared library with cc -o libtest -shared -fPIC libtest.c.
  3. Copy the shared library to /usr/local/lib/.
  4. Add the folder to /etc/ld.so.conf if the entry doesn't already exist.
  5. Run ldconfig to load the library. Check with ldconfig -p | grep libterm if the library was loaded correctly.
  6. Include the library with #include <libtest.h>.
  7. Compile your application with cc -o main -ltest main.c. Run ldd main to see if the library is listed as dependency.

The following Makefile show how to create simple install/uninstall options:

Makefile

default: build

build:
  cc -o libtest -shared -fPIC libtest.c

install: build
  sudo cp libtest.h /usr/local/include/
  sudo cp libtest.so /usr/local/lib/
  sudo ldconfig
  rm libtest.so

uninstall:
  sudo rm /usr/local/include/libtest.h
  sudo rm /usr/local/lib/libtest.so

clean:
  rm libtest.so

Libraries

  • curl: HTTP Client library
  • libpq-fe: Postgres Client library
  • openssl: SSL library
  • cmark: Markdown library
  • toml: TOML Parser libarry

Tools

  • man: View manuals for a specific topic
  • xxd: View binary files as hex
  • ldd: View binary dependecies
  • file: View file types

Books