The snapdev project includes a set of base classes and functions that are header only (a.k.a. inline). A form of std library, if you you wish, but mostly geared toward helper functions we use all over the place.

The following are the features available at time of writing. It is not unlikely to grow every now and then.


If possible, change the current user to the root user. Once done, RAII kicks in and switches back to what was the current user earlier.

This class can also be used to switch to other users. It uses RAII so it is expected to be used within a block of code, not as a class member (i.e. it won't work as expected if you try to switch between multiple users within different classes—also it's not multi-thread safe).


The Binary ReSource serializer and deserializer. This object can be used to transform a structure to save it to disk and read it back from disk.

It supports all the native C++ types and strings, blobs, and recursive structure serialization.


A templated callback manager to add the ability to call functions on an event to any class without having to re-implement such code each and every time.

This is really only useful if you want to have more than one callback for a given event. It manages any number of callbacks for said event. If you only allow for one single callback, then you can just use an std::function<>.


An imlpementation of the std::string which re-implements the compare operators to use toupper(c) for each character.

Note: This implementation only works against strings that are ISO-8859-1 (latin1) if using "char". You may use the template with "wchar_t", "char16_t" and "char32_t" in order to make it work against a wider range of characters. The "wchar_t" may be 16 bits like "char16_t". Both may have characters in the upper plans that will fail the uppercase comparison.


Change a file owner and group by name.


Compute the intersection of two sets and return true if empty. The idea is that there is an algorithm to very quickly compute such a result without having to do any copy. Computing an intersection and then checking whether the set is empty would be much longer in most cases.


Allow for simple + and - binary operations against enumeration values. We use such in our tests to avoid the heavy casting necessary to do so otherwise. Just include this header, and then you can use the following with enumerations:

enum T a;
a + 3; // 3 can be any integral type or floating point that gets converted to int
a - 3;


This template is used to call a function once per element of a given container. The function signature needs to be:

func(int index, T::value_type const & item);

Note that an index is always available even for containers that usually do not offer an index (such as an std::map).


This helper class loads the contents of a file in a buffer (a string) and also has the ability to save that buffer back to that file or another file (a backup).

The file can be create in a directory which doesn't exist yet.

The file can be marked as temporary in which case the destruction of the file_contents object unlinks the file.


This function retrieve the name of the host on which your software is running.

It is similar to calling ::gethostname(), except that it takes care of throwing an exception if the name cannot be determined and the function returns an std::string and properly detects a few special cases.


Run the glob() function and return a list of strings. This is much more C++ friendly than the basic glob() function which allocates data that you'd have to take care off. It also automatically handles errors and recursivity to read a complete tree. It can also be used to stat() each file or call your own callback function, similar to an enumeration of files on your disk drive.


Template to check at compile time whether a class has a given member function.


Dealing with many hashing codes such as MD5 or SHA1 and we often need to convert them to or from strings. This files includes a couple of functions to do the conversions for us.


Since C++11, we can initialize constexpr structures at compile time. With C++14 and C++17, many features were added allowing even more code to run and make sure that your structures are valid.

This header includes basic templates that help with defining functions that help with creating structures that are constexpr (fully created at compile time) and fully verified.

An advance use of such initialization is found the advgetopt project.


Allow for literals of integer of 128 bits to be written as is.

This is particularly useful with UUID and similar numbers that make use of 128 bits.


Check whether the given stream is a TTY or not.

See the stream_fd.h function as well.


A set of templates to detect the type of smart pointer used: is_shared_ptr, is_weak_ptr, is_unique_ptr.


Detect whether a string is a literal.


Detect whether a class is a vector.


This template is used to join strings with a separator and optimized as it allocates the output buffer once.


In older versions of g++, the limits for __int128 and unsigned __int128 were not implemented. This header has the implementation as available in newer versions of the compiler. We will remove this at some point once we are sure that it is implemented and will remain so in g++.


A way to lock/unlock a file with an RAII class.


Compute the log base 2 or an integer. This function uses the find first bit available on the amd64 processors and it returns a number from 0 to 63. It's equivalent to:

floor(log(n) / log(2));

Just a lot faster.


Various useful math functions such as a fast implementation of an integral power, saturated add and subtract, swapping of 128 bit numbers.


A matrix implementation. It includes color matrices for many different types of monitors and TVs and some specialization for 4x4 matrices.


Search a needle in a haystack of buffers of any type T.


An equivalent to "mkdir -p ..." in C++. It also has the ability to change the owner and group of the child folder or any created folder.


Generate a list of mount points found at this time on your computer. Any type of container can be used to get the results.


When writing a function, you may know of areas that should never be reached and if so, that's an error. This allows you to mark that part of the code as never reached:


Then if you algorithm changes or you made a mistake to start with and that line of code is reached, it throws an error.


We have the warnings turned on in case you do not use some or all of the parameters of a function. That means you cannot compile that code by default.

If you clearly receive parameters you do not need, you can mark them as not used with this:

snap::NOT_USED(a, b, c, ...);

This way, we can clearly see that was the intend.


Transforms a string to a number at compile time.


Print an __int128 number in a standard output stream.


Output a stream to a buffer so it can be tested or used in some other way.

We use these feature a lot in our tests.


Various functions to handle paths. This may become much less useful as the C++ library now includes many such functions.

At this time, we have a function which very quickly extracts the basename found in a path. It can remove the path, a prefix and a suffix.


Many old C functions are very dangerous. You may know how to use strncat() (you probably don't), but that has created so many bugs, it's just not conceivable that it is still available in the C library.

So here we poison such functions. That includes sprintf() and strcpy() and variants.

We try to always include this file in all of our .cpp files from all of our projects that depend on snapdev (directly or indirectly). This way we avoid many issues.


Allow for comparing QString like strings in a case insensitive mode.

You can do the same with std::string using our libutf8 library (which also handles UTF-8 in various ways).


Various QString and QByteArray extensions we've created over the years to make it easier to handle std::string and Qt types together.


An RAII generic deleter, as the name says... It allows you to build smart pointers for things other than simple C++ pointers. For example, we offer the raii_fd_t type which allows you to handle a file descriptor where it automatically gets closed on destruction of your variable.

It works with std::unique_ptr<> and std::shared_ptr<>.


Three different functions to remove duplicates from a container. One expects the container to already be sorted. Another sorts the elements and then use the previous algorithm to remove the duplicates. Finally, we offer a (slow) function which does not require the container to be sorted.


Reverse a string (i.e first character is swaped with the last, the second with the one before last, etc.).


A recursive removal of files. This is equivalent to the:

rm -r this-folder

in a shell.


Safely assert a test result which can include side effects.

Often, the assert in C/C++ make use of a macro which is removed in release. This is great for speed since it eliminates all computation that happen in the assert, however, that means the debug and release code is not the same. If any side effects happen in the computation of the assertion flag, those side effects are gone from the release version and that means your debug test is the same as a release test would be.

This is an inline function which means the computations with no side effects will automatically be removed by the compiler as required and possible. The side effects will stay in place, however.


Use RAII to change to a directory and then restore to what that directory was once done.

Note: This is not thread safe since a process can only have one current working directory.


Temporary holds a bare pointer while you do further initialization. This can be useful in situations where a smart point does not work for that type of object initialization.


Setting an environment variable is notoriously unsafe. The C library added some better functions, but it still is not that great. You have things to be watching out for such as never freeing the string buffer unless you delete the variable.

This class allows you to make it safe without having to think too hard abot it.


Automatically saves the flags, width, and precision of a standard stream.

Note: this is not thread safe.


In many situation, you'd like to change a variable, run some code, and restore the variable to its old value. This can now be done safely.

WARNING: it is safe within one thread. If you have multiple threads handling that one variable, you probably need something much more complex.


Return the size of a bitfield in bits. This is like a sizeof() but for a structure bit field.


Create a static buffer on your stack. Try to use it. If the buffer is too small, ask to dynamically grow it. Try again.

This is useful for calling C functions which do not give you a way to determine the necessary amount of bytes necessary to get the result in all circumstances. In most cases, the static buffer will be enough and as a result this class makes the call a lot faster because it does not have to do a memory allocation.


Gather the basic Unix file descriptor (an integer) of a C++ file stream.

The file descriptor is not made available in C++ fstream related classes. This is by design since different operating systems use different schemes for such data. On Linux, the library makes use of the FILE * type. This class searches for that field and then calls the fileno() on that pointer.

The function returns -1 if the file descriptor cannot be determined. Note that our code supports several versions of the standard library used on Linux. In most likelihood, you are only using the latest now that we use C++23 and newer.


A preprocessor macro used to transform a parameter in a string.

This was taken (and simplified) from boost. This is the only function that many of our projects used and allows us to avoid installing libboost-dev while generating those packages, which is a big saving.


Various functions to handle paths. This may become much less useful as the C++ library now includes many such functions.

At this time, we have a function which very quickly extracts the basename found in a path. It can remove the path, a prefix and a suffix.


To replace many strings within a string, we use this function. This will replace all instances we find and you can specify any number of needles (strings to find) and replacements (found strings get replaced by this).

For example, you can replace all of the special HTML characters with a corresponding entity in one go:

snap::string_replace_many(html, { { "<", "&lt;" }, { ">", "&gt;" } });


Extended timespec class. This allows us to do simple math and other processing between timespec structures (addition, subtraction, get now(), compare, etc.).


Templates used to compute Unix timestamps at compile-time.


A set of template allowing you to parse a format string a la "printf(3)". This function lets you define the flags, whether numbers are accepted, and the letters supported by the format. In other words, it allows you to define your own formats.


Break strings at separators. For example, you can transform a file path in segments.


Transforms a string to lowercase. This is not working against UTF-8 strings. For those, look at the libutf8 library instead.


Convert integers and floating points to string literal at compile time.


Transforms a string to uppercase. This is not working against UTF-8 strings. For those, look at the libutf8 library instead.


Trim a string of unwanted characters at the start, end, within the string.


Generate a list of user group names.

Coverage Test Results

Access full page here.

The library has a test suite that covers 100% of the code, making it a little more certain that it does not include too many bugs. We try to run the tests each time we create a new version to ensure that it works as expected.


Snap! Websites
An Open Source CMS System in C++

Contact Us Directly