This project has been created as part of the 42 curriculum by jcosta-a
This repository contains my implementation of ft_printf, a project from the 42 common core curriculum at 42 Lisboa, completed in 2026.
ft_printf is a custom re-implementation of the standard C printf function, built on top of the previously developed libft library. The goal is to understand variadic functions in C and replicate the core formatting behaviour of printf without relying on it.
The function parses a format string and, for each % conversion specifier encountered, retrieves and prints the corresponding argument from the variadic argument list. The total number of characters printed is tracked and returned, mirroring the behaviour of the original printf.
The implementation is intentionally minimal and readable. ft_printf iterates over the format string character by character. When it encounters a %, it advances one position and delegates the printing to a helper function if_print, which dispatches to the appropriate output function based on the specifier character.
All output is handled by functions inherited from libft — extended with new helpers for unsigned integers, hexadecimal (lower and upper case), and pointers. Each output function returns the number of bytes written, which is accumulated into total_print and ultimately returned by ft_printf, exactly like the real printf.
For the %p (pointer) specifier, a dedicated static helper ft_puthex_long_fd is used internally to handle the full 64-bit address range. It is declared static because it is only needed within that translation unit, keeping the library's public interface clean.
Supported conversion specifiers:
| Specifier | Output |
|---|---|
%c |
Single character |
%s |
String ((null) if pointer is NULL) |
%d |
Signed decimal integer |
%i |
Signed decimal integer |
%u |
Unsigned decimal integer |
%x |
Unsigned hexadecimal (lowercase) |
%X |
Unsigned hexadecimal (uppercase) |
%p |
Pointer address ((nil) if NULL) |
%% |
Literal % character |
- Language: C
- Compiler:
ccwith-Wall -Wextra -Werrorflags - Standard: All files must follow the 42 Norm
- Header: Every
.cfile includes the mandatory 42 header - Authorized Functions:
malloc,free,write,va_start,va_arg,va_copy,va_end - No global variables or
forloops allowed - Dependency: Built on top of
libft
| Function | Prototype | Description |
|---|---|---|
ft_printf |
int ft_printf(const char *str, ...) |
Parses the format string and prints each argument according to its specifier. Returns the total number of characters printed, or -1 if str is NULL. |
| Function | Prototype | Description |
|---|---|---|
ft_putnbru_fd |
int ft_putnbru_fd(unsigned int n, int fd) |
Writes an unsigned decimal integer to fd. Returns character count. |
ft_puthex_fd |
int ft_puthex_fd(unsigned int n, int fd) |
Writes an unsigned integer as lowercase hexadecimal to fd. Returns character count. |
ft_puthex_up_fd |
int ft_puthex_up_fd(unsigned int n, int fd) |
Writes an unsigned integer as uppercase hexadecimal to fd. Returns character count. |
ft_putpointer_fd |
int ft_putpointer_fd(unsigned long n, int fd) |
Writes a pointer address prefixed with 0x to fd. Prints (nil) if address is 0. Returns character count. |
All
fd-based functions inherited fromlibft(ft_putchar_fd,ft_putstr_fd,ft_putnbr_fd) were updated to returnint— the number of characters written — to enable accurate tracking oftotal_print.
Clone the repository and run make to compile the library:
git clone https://gitlab.com/ja-de_42-lisboa/1-common-core/ft_printf
cd ft_printf
makeThis generates libftprintf.a — the static library archive, which already contains libft bundled inside.
| Rule | Description |
|---|---|
make / make all |
Compiles libft, then bundles it with ft_printf into libftprintf.a. |
make clean |
Removes object files (.o) from both ft_printf and libft. |
make fclean |
Removes object files and the libftprintf.a archive. |
make re |
Runs fclean then all. |
To use ft_printf in another project, include the header and link the archive:
cc -Wall -Wextra -Werror main.c libftprintf.a -o my_program
./my_programMake sure ft_printf.h and libftprintf.a are accessible from your project's directory (or adjust the -L and -I paths accordingly).
Source main code:
#include "ft_printf.h"
int main(void)
{
int n;
n = ft_printf("Hello, %s! You are %d years old.\n", "world", 42);
ft_printf("Characters printed: %d\n", n);
ft_printf("Pointer: %p\n", &n);
ft_printf("Hex: %x | %X\n", 255, 255);
return (0);
}Expected Output:
Hello, world! You are 42 years old.
Characters printed: 36
Pointer: 0x[address]
Hex: ff | FF
- man7.org — Linux man pages — Manual pages for
printf,stdarg, and related functions (e.g.man 3 printf,man 3 stdarg). - cppreference — printf — Detailed specification of
printfconversion specifiers and return behaviour. - 42 Norm — norminette — The official 42 coding style enforcer. Every file must pass norminette before submission.
| Video | Topic |
|---|---|
| Variadic Functions in C — Jacob Sorber | How va_list, va_start, va_arg, and va_end work under the hood — the core mechanism behind ft_printf. |
| Funções Variádicas e Algoritmos em C — David Buzatto | A walkthrough of how printf parses format strings and dispatches to type-specific formatters on variadic functions. |
AI was used during this project for the following purposes:
- Concept clarification: understanding the exact behaviour of edge cases such as
%pwith a NULL pointer,%swith a NULL string, and the return value ofprintfon failure. - Code review: verifying that output functions correctly return the number of characters written and that
total_printaccurately mirrors realprintfbehaviour. - README writing: Drafting and structuring this README document.
AI was not used to generate or write any C source code submitted as part of this project.
Developed by Jonathan Alves — 42 Lisboa, 2026