cake
Qu'ils mangent de la brioche ~ Let them eat cake.
—
a great princess
Cake is a C/C++ Makefile-based build system, aimed at providing quick and easy
development. It provides all the make
targets you know and love, with the
added bonus of being completely agnostic to the project itself.
Table of Contents
Usage
Installation
Getting started with Cake is as easy as:
wget https://raw.githubusercontent.com/kaplanz/cake/main/Makefile
Simply download the Makefile
into your C/C++ project directory
and compile away!
Dependencies
Cake tries to be POSIX compliant as much as possible, as a result, it should run on most Unix/Linux system out of the box. In most cases, you should already have all dependencies already installed on your system by default, however the full list is as follows:
Required
ar
: archive utility to create static librariesbasename
: basename utility to strip directory and suffix from filenamescc
: C compiler, e.g.gcc
,clang
c++
: C++ compiler, e.g.g++
,clang++
date
: date utility to get epoch timestampfind
: find utility to search for source files within directory treemake
: this is probably important to have (preferably GNU Make)realpath
: realpath utility to resolve relative paths
Optional
clang-format
: used for code formatting withmake fmt
clang-tidy
: used for code linting withmake (check|tidy)
git
: used to determine files to include inmake dist
tar
: used to create a distribution tarball withmake dist
Directory Structure
In order to correctly build your project, Cake expects the following directory structure:
.
├── Cake.mk
├── Makefile
├── include
│ └── foo
│ ├── bar.h
│ ├── baz.h
│ └── foo.h
├── src
│ ├── lib
│ │ └── foo
│ │ ├── bar.c
│ │ ├── baz.c
│ │ └── foo.cpp
│ └── main.cpp
└── test
└── test_foo.cpp
Cake.mk
See customization with Cake.mk
below.
include/
All headers must use the *.h
extension (unless otherwise
customized), and should be placed within the include/
directory. If they are to be included as a part of a library, it is good
practice to further place them within the library's subdirectory. However, this
is not strictly enforced.
src/
All source files must use either the *.c
or *.cpp
extensions (unless
otherwise customized).
In order to differentiate between binaries and libraries, Cake provides two
additional subdirectories for your source files; src/bin/
and src/lib/
. All
other "assorted" source files not placed in these designated subdirectories will
still be compiled to objects which are linked against binaries. (Note that
libraries are intended to compile standalone, and as a result are not linked
against these source objects.)
Lastly, the special file(s) src/main.c
or src/main.cpp
will be compiled into
a binary sharing the name of the package.
src/bin/
The src/bin/
directory is strictly for compiling objects to binaries.
Within src/bin/
, source files can be nested as desired, however, only
top-level source files could be built and run as a target.
Cake does not limit the amount of binaries that can be produced by a project.
For example, to compile and run the executable main
, the source file
src/main.{c,cpp}
should exist. This can be built and run as a target with
make main
, providing command line arguments through the ARGS
variable.
src/lib/
The src/lib/
directory is strictly for compiling libraries.
As such, any source files must be placed within a library subdirectory.
Cake does not limit the amount of libraries that can be produced by a project.
For example, to compile the library foo
, any source files should be placed in
lib/foo
(with headers in include/foo
). These will ultimately be compiled
both statically and dynamically to libfoo.a
and libfoo.so
respectively.
test/
The test/
directory is for any writing tests.
Any source files placed within test/
will be compiled to binaries, and linked
against all objects and libraries. To compile and run all tests, use the test
target with make test
.
After running a test, the result is printed to the console as either done
on
success, or failed
on failure. (Results are determined by the exit code, with
any non-zero indicating a failure.)
Build Configurations
Cake provides three different build configurations to use when compiling your project:
BASIC
: use the default build configurations; some optimizations and basic debug informationDEBUG
: build with fewer optimizations and maximum debug informationRELEASE
: build with more optimizations and without debug information
These can be specified as a customization.
Targets
To start compilation with Cake, often just running make
will be enough!
Cake automatically parses your project directories to gather source files and
targets, and also manages auto-dependency generation through your compiler.
To build specific targets, Cake provides the following Makefile goals:
Basic Goals
Default Goal
all
: alias forbuild
Alternate Builds Configurations
debug
: run the default goal using the debug configurationrelease
: run the default goal using the release configuration
Build Goals
build
,b
: build all targets;bin
,dep
,lib
,obj
rebuild
: clean and rebuild all targets; directly impliesclean
,build
bin
: build binaries; indirectly impliesdep
,obj
, staticlib
sdep
: generate dependency fileslib
: create both static and dynamic libraries; indirectly impliesdep
,obj
obj
: compile object files; indirectly impliesdep
run
,r
: build and run main binarytest
,t
: compile and run tests; indirectly impliesdep
,obj
, staticlib
s
Clean Goals
clean
: remove all files created by Cake; removesbin/
,lib/
, andbuild/
directoriesbinclean
: remove binaries build by Cake; removesbin/
andbuild/bin/
directoriesdepclean
: remove dependencies generated by Cake; removesbuild/dep/
directorylibclean
: remove libraries build by Cake; removeslib/
andbuild/lib/
directoriesobjclean
: remove objects compiled by Cake; removesbuild/obj/
directory
Install Goals
install
: install build targets (must have write permissions for$(LOCAL)
)uninstall
: uninstall build targets (must have write permissions for$(LOCAL)
)
Source Goals
check
,c
: check sources (default:clang-tidy
)dist
: create distribution tarball (placed inbuild/
)fix
: fix sources (default:clang-tidy
)fmt
: format sources (default:clang-format
)tag
: generate tag files (placed inbuild/
, default:ctags
)
Echo Goals
conifig
: print configurationhelp
: print help messageinfo
: print build information
Customization
In addition to its other powerful features, Cake aims to be highly customizable.
To that end, it provides the optional file Cake.mk
which is parsed before each
invocation.
The following options can be overridden either on the command line, through Make
variables, or in the Cake.mk
configuration file:
Package
NAME
: name of package; may not contain spaces (default: name of root directory)VERSION
: version of package (default: Unix timestamp)AUTHOR
: stores author information; used inmake about
Build
CONFIG
: build configuration to use; has priority (default:BASIC
)BASIC
: alternate way to specify default build configuration (default:1
)DEBUG
: alternate way to specify debug build configuration (default: not set)RELEASE
: alternate way to specify release build configuration (default: not set)
Compilers
CC
: compiler for C (default:cc
)CXX
: compiler for C++ (default:c++
)
Directories
BIN
: output binary directory (default:bin/
)BUILD
: build output directory (default:build/
)INCLUDE
: headers directory (default:include/
)LIB
: output library directory (default:lib/
)LOCAL
: installation directory (default:usr/local/
)ROOT
: root directory of project; change with caution (default:./
)SRC
: sources directory (default:src/
)TEST
: tests directory (default:test/
)
Extensions
.a
: file extension for static libraries (default:.a
).c
: file extension for C sources (default:.c
).cc
: file extension for C++ sources (default:.cpp
).d
: file extension for dependencies (default:.d
).h
: file extension for headers (default:.h
).o
: file extension for objects (default:.o
).so
: file extension for dynamic libraries (default:.so
)
Files
TAGFILE
: output tagfile (default:build/tags
)TARDIR
: tarball directory name; formatted to$(BUILD)/$(TARDIR).tar.gz
(default:$(NAME)-$(VERSION)
)DISTFILES
: list of files to include in distribution tarball (default: files tracked in git)
Flags
CFLAGS
: options for C compiler (default:-Wall -g -std=c18
)CPPFLAGS
: options for C/C++ preprocessor (default:-I/include
)CXXFLAGS
: options for C++ compiler (default:-Wall -g -std=c++17
)LDFLAGS
: options for linkerLDLIBS
: libraries for linker
Install
INSTALL
: files to be installed bymake install
NOINSTALL
: files to exclude for installation bymake install
License
This project is licensed under the terms of the MIT license.