Skip to main content

Documentation Index

Fetch the complete documentation index at: https://docs.syntblaze.com/llms.txt

Use this file to discover all available pages before exploring further.

A function pointer is a variable that holds the memory address of executable code rather than a data value. In C, functions reside in the text (or code) segment of memory, and a function pointer stores the base address of a specific function’s machine instructions, enabling indirect invocation.

Syntax and Declaration

The declaration of a function pointer must strictly define the signature of the function it points to, including the return type and the parameter types.
return_type (*pointer_name)(parameter_type1, parameter_type2, ...);
The parentheses surrounding *pointer_name are mandatory due to operator precedence. Without them, the compiler interprets the statement as a function declaration returning a standard data pointer.

Assignment and Invocation

When assigning a function to a function pointer, the function’s identifier automatically decays into a pointer to its first instruction, analogous to array decay. The address-of operator (&) is optional but often used to explicitly denote intent. Similarly, when invoking the function via the pointer, explicit dereferencing (*) is optional.
int add(int a, int b) {
    return a + b;
}

int main() {
    // 1. Declaration
    int (*func_ptr)(int, int);

    // 2. Assignment
    func_ptr = &add;  // Explicit address-of
    func_ptr = add;   // Implicit decay (functionally identical)

    // 3. Invocation
    int res1 = (*func_ptr)(5, 3); // Explicit dereference
    int res2 = func_ptr(5, 3);    // Implicit dereference (functionally identical)

    return 0;
}

Type Aliasing (typedef)

Function pointer syntax becomes notoriously difficult to parse when nested, such as when a function returns a function pointer or accepts one as an argument. The typedef keyword is used to create a type alias for the function signature, abstracting the pointer syntax.
// Defines 'math_op' as a type representing a pointer to a function 
// taking two ints and returning an int.
typedef int (*math_op)(int, int);

int add(int a, int b) {
    return a + b;
}

int main() {
    // Declaration using the typedef
    math_op ptr = add;
    int result = ptr(10, 20);
    
    return 0;
}

Arrays of Function Pointers

Multiple function pointers sharing an identical signature can be stored contiguously in an array. The array subscript operator is evaluated before the function call operator.
int add(int a, int b) { return a + b; }
int subtract(int a, int b) { return a - b; }
int multiply(int a, int b) { return a * b; }
int divide(int a, int b) { return a / b; }

int main() {
    // Declaration and initialization of an array of 4 function pointers
    int (*op_array[4])(int, int) = {add, subtract, multiply, divide};

    // Invoking the function at index 2 (multiply)
    int result = op_array[2](10, 5); 
    
    return 0;
}

Memory and Type Safety Constraints

  • Strict Typing: A function pointer must strictly match the return type and parameter types of the target function. Invoking a function through an incompatible pointer corrupts the call stack and results in undefined behavior.
  • Data Pointer Incompatibility: The ISO C standard dictates that function pointers and data pointers (such as void *) are not guaranteed to be interchangeable or of the same size. Casting between a function pointer and a data pointer is undefined behavior in strict C, though certain POSIX extensions (like dlsym) mandate this conversion.
  • Lvalue Constraints: A dereferenced function pointer yields a function designator, which is not a modifiable lvalue. Attempting to assign a value to a dereferenced function pointer (e.g., *func_ptr = ...) violates C language constraints and results in a compile-time error. The compiler strictly prevents direct modification of the executable text segment through function pointer assignment.
Master C with Deep Grasping Methodology!Learn More