Small snippets of code that I refer to in my daily work.
These assume that you are using C++14 and boost.
... like auto s = "this is a std::string"s;
using namespace std::literals;... like auto microseconds = 1000us;
using namespace std::chrono_literals;std::regex requires at least C++11. CTRE requires at least C++17.
#include <regex>
if (std::regex_match(string,std::regex("[a-zA-Z]*"))) {
    cout << "Matches\n";
}#include <ctre.hpp>
using namespace ctre::literals;
if ("[a-zA-Z]*"_ctre.match(string)) {
    cout << "Matches\n";
}#include <regex>
const auto result = regex_replace(str,std::regex("<"),"<");#include <regex>
const auto str = "Jul-18-2017";
std::smatch match;
if (std::regex_search(str,match,std::regex("([a-zA-Z]*)-([0-9]*)-([0-9]*)"))) {
	std::cout << "Month: " << match[1] << ", day: " << match[2] << ", year: " << match[3] << "\n";
} else {
	// No match
}#include <ctre.hpp>
using namespace ctre::literals;
const auto str = "Jul-18-2017";
if (const auto match="([a-zA-Z]*)-([0-9]*)-([0-9]*)"_ctre.match(str)) {
	std::cout << "Month: " <<  match.get<1>() << ", day: " <<  match.get<2>() << ", year: " <<  match.get<3>() << "\n";
} else {
	// No match
}#include <boost/tokenizer.hpp>
auto const tokens = boost::tokenizer<boost::char_separator<char>>(mystring,
    boost::char_separator<char>("\n"));
for (std::string const &t : tokens) {
    std::cout << t << std::endl;
}#include <boost/algorithm/string.hpp>
std::string const untrimmed = ...;
auto const trimmed = boost::trim_copy(untrimmed);#include <fstream>
auto ifs = std::ifstream(file);
auto const data = std::string(
    std::istreambuf_iterator<char>(ifs),
    std::istreambuf_iterator<char>()
);auto in = std::istream(...);
auto out = std::ostream(...);
out << in.rdbuf();#include <fstream>
std::string longstr;
{
    auto ifs = std::ifstream("/dev/urandom",std::ios::binary);
    auto isi = std::istream_iterator<char>(ifs);
    std::copy_n(isi,
        10'000'000,
        std::insert_iterator<std::string>(longstr,longstr.begin()));
}#include <boost/filesystem.hpp>
boost::filesystem::create_directories(boost::filesystem::path(file).parent_path());#include <boost/filesystem.hpp>
#include <boost/range/iterator_range.hpp>
std::string dir = ...;
for(auto const &f: boost::make_iterator_range(boost::filesystem::directory_iterator(dir))) {
    auto const file = f.path().string();
    std::cout << "Found file: " << file << std::endl;
}#include <boost/date_time/posix_time/posix_time.hpp>
auto const tm = boost::posix_time::to_tm(boost::posix_time::second_clock::local_time());auto request = boost::network::http::client::request("http://...");
request << boost::network::header("Connection","close");
auto const result = body(boost::network::http::client().get(request));Supports both GET and POST. Not complete code, just for illustration.
#include <curl/curl.h>
size_t WriteFct(void* contents,size_t size,size_t nmemb,void* userp) {
    std::string *const buf = static_cast<std::string*>(userp);
    *buf += std::string(static_cast<char*>(contents),size*nmemb);
    return size * nmemb;
}
void LoadWithCurl()
{
    const auto curl = curl_easy_init();
    if (!curl) {
        throw std::runtime_error("Error initializing the curl context");
    }
    // Close the curl session when done
    BOOST_SCOPE_EXIT_ALL(curl) {
        curl_easy_cleanup(curl);
    };
    // Configure the curl session
    std::string buf;
    char err[CURL_ERROR_SIZE] = "";
    curl_easy_setopt(curl,CURLOPT_URL,url.c_str());
    curl_easy_setopt(curl,CURLOPT_SSL_VERIFYPEER,0L);
    curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,WriteFct);
    curl_easy_setopt(curl,CURLOPT_WRITEDATA,static_cast<void*>(&buf));
    curl_easy_setopt(curl,CURLOPT_ERRORBUFFER,err);
    // Set the POST data (and activate POST) if requested by the caller
    if (postdata) {
        // Note: CURLOPT_POSTFIELDSIZE is restricted to 2 GB or less.
        curl_easy_setopt(curl,CURLOPT_POSTFIELDSIZE,postdata->size());
        curl_easy_setopt(curl,CURLOPT_POSTFIELDS,postdata->data());
    }
    // Perform the actual HTTP query
    const auto res1 = curl_easy_perform(curl);
    if (res1!=CURLE_OK) {
        throw std::runtime_error("Error accessing " + url + ": " + (err[0] ? err : curl_easy_strerror(res1)));
    }
    // Check the HTTP result status
    long status = -1;
    const auto res2 = curl_easy_getinfo(curl,CURLINFO_RESPONSE_CODE,&status);
    if (res2!=CURLE_OK) {
        throw std::runtime_error("Error getting HTTP result status: "s + curl_easy_strerror(res2));
    }
)#include <iostream>
#include <boost/iostreams/stream.hpp>
#include <boost/iostreams/device/file_descriptor.hpp>
// Output (file opened for writing)
int fd = ...;
boost::iostreams::file_descriptor_sink snk(fd,boost::iostreams::close_handle);
boost::iostreams::stream<boost::iostreams::file_descriptor_sink> os(snk);
os << "Hello World\n";
// Input (file opened for reading)
int fd = ...;
boost::iostreams::file_descriptor_source src(fd,boost::iostreams::close_handle);
boost::iostreams::stream<boost::iostreams::file_descriptor_source> is(src);
is >> myvariable;Download the Boost source to your home directory, then:
$ chmod a+wrx /usr/local/lib /usr/local/include
$ rm -f /usr/local/lib/*boost*
$ rm -rf /usr/local/include/boost
$ mkdir -p boost
$ cd boost
$ rm -fr build
$ mkdir build
$ rm -fr boost_*
$ tar xzf ~/boost_*.tar.gz
$ cd boost_*
$ ./bootstrap.sh --without-libraries=python
$ ./b2 --build-dir=~/boost/build $MINUSJ variant=release link=static threading=multi runtime-link=static installIt's surprisingly easy.
$ cd
$ mkdir gcc
$ cd gcc
$ wget ftp://ftp.fu-berlin.de/unix/languages/gcc/releases/gcc-9.1.0/gcc-9.1.0.tar.gz
$ tar xzf gcc-9.1.0.tar.gz
$ cd gcc-9.1.0
$ contrib/download_prerequisites
$ cd ~/gcc
$ mkdir build
$ cd build
$ ../gcc-9.1.0/configure --prefix=$HOME/gcc/install --disable-multilib
$ make
$ make install
$ ~/gcc/install/bin/g++ --version
g++ (GCC) 9.1.0
$ sudo update-alternatives --install /usr/bin/gcc gcc $HOME/gcc/install/bin/gcc 60 --slave /usr/bin/g++ g++ $HOME/gcc/install/bin/g++
$ sudo update-alternatives --config gcc
$ gcc --version
gcc (GCC) 9.1.0
$ g++ --version
g++ (GCC) 9.1.0To run executables built with gcc 9 (unless linked statically):
$ export LD_LIBRARY_PATH=$HOME/gcc/install/lib64:$LD_LIBRARY_PATH$ cd /opt
$ wget https://github.com/Kitware/CMake/releases/download/v3.14.5/cmake-3.14.5.tar.gz
$ tar xzf cmake-3.14.5.tar.gz
$ cd cmake-3.14.5
$ mkdir build
$ cd $_
$ cmake ..
$ make -j8
$ sudo mkdir -p -m 777 /usr/local/doc /usr/local/share
$ make install
$ cmake --version
cmake version 3.14.5
If there's no cmake already installed, do the following instead of invoking cmake (in the source directory, don't create a build directory):
$ ./bootstrap -- -DCMAKE_BUILD_TYPE:STRING=Release
More info: https://cmake.org/install/
git config --global alias.godlog "log --graph --oneline --decorate"This allows you to use "git diff" with Microsoft Office (Word, PowerPoint) and Libre Office (Writer, Calc, Impress) files stored in a git repository. The trick is to tell git how to extract plain text from these files, on which the regular diff can be used.
Install the conversion tools:
$ sudo apt install unoconv catdoc
Optionally, only needed for .pptx files:
$ pip install python-pptx- Copy 
git-pptx-textconv.pyfrom this repo to a location of your choice and make it executable 
Add the following to ~/.gitconfig:
[diff "doc"]
    textconv=catdoc
[diff "odt"]
    textconv=odt2txt
[diff "odp"]
    textconv=odp2txt
[diff "ods"]
    textconv=ods2txt
[diff "ppt"]
    textconv=catppt
[diff "pptx"]
    textconv=/location/of/git-pptx-textconv.py
Add the following to ~/.config/git/attributes (or, alternatively, to the .gitattributes file in the project root):
*.doc diff=doc
*.odp diff=odp
*.ods diff=ods
*.odt diff=odt
*.ppt diff=ppt
*.pptx diff=pptx
If git diff displays the following error:
Error: Unable to connect or start own listener. Aborting.
fatal: unable to read files to diff
then type unoconv -l and retry.
More information:
- http://www-verimag.imag.fr/~moy/opendocument/
 - https://git-scm.com/book/en/v2/Customizing-Git-Git-Attributes ("Diffing Binary Files" section)
 - https://stackoverflow.com/a/32259984/14667736 (original source of git-pptx-textconv.py, I only ported it to Python 3)
 - https://stackoverflow.com/questions/52873519/how-can-i-get-useful-git-diff-of-files-saved-by-libre-office-writer-with-output/65733260
 
... that is created from a Libre Office document which is managed in git as described in the previous section, using the tag-based version number generated by git describe. Tested with Libre Office 5 in Linux.
Preparation (once per document):
- Open the document in LibreOffice Writer
 - Move cursor to where the version number is to be displayed
 - Insert → Field → More fields ...
 - Variables → Set variable, Name: version, Value: 0.0, Format: Text, Insert, Close
 - To show the version number elsewhere: Insert → Field → More fields ... → Variables → Show variable, version, Insert, Close
 - Close and save the document
 - Add/commit the document to git
 
To convert the document into a PDF, replacing the "0.0" placeholder by the current git version number:
$ odt2pdf -o myname.pdf -F version=$(git describe --dirty --always) filename.odtAbout tag-based git version numbers: https://git-scm.com/docs/git-describe
... and be as portable as possible by switching off stuff like GNU language extensions.
set(CMAKE_CXX_STANDARD 14)
set(CMAKE_CXX_EXTENSIONS OFF)cmake_minimum_required (VERSION 3.5)
project (myproject CXX)
find_package (Threads REQUIRED)
add_executable (myproject ...)
target_link_libraries (myproject Threads::Threads)More: https://stackoverflow.com/questions/1620918/cmake-and-libpthread
set (EXECUTABLE_OUTPUT_PATH "${CMAKE_SOURCE_DIR}/build")find_program (CCACHE_FOUND ccache)
if (CCACHE_FOUND)
    set_property(GLOBAL PROPERTY RULE_LAUNCH_COMPILE ccache)
endif (CCACHE_FOUND)Where "Shell" means bash, or something sufficiently compatible.
Show the last command's exit status in the shell prompt, and show the prompt with a dark background to make it stand out better. When in a git repository, show the current git status: a cross if something needs to be committed, an up arrow if something needs to be pushed, a down arrow when something can be pulled, three stacked horizontal lines if there's a shash, a check mark if everything is clean.
Put the following into your .profile or .bashrc.
gitstatus() {
    if [ "$1" = "--color" ];then
        local RED=$(tput setaf 1)
        local BLU=$(tput setaf 6)
        local GRN=$(tput setaf 2)
        local OFF=$(tput sgr0)
    else
        local RED=""
        local BLU=""
        local GRN=""
        local OFF=""
    fi
    local S
    S=$(LANG=C git status -sb --porcelain 2>/dev/null) || return
    if [[ $S =~ [[:cntrl:]][^#] ]];then
        echo "${RED}×${OFF} "
    elif [[ $S =~ ^##.*\[behind ]];then
        echo "${BLU}↓${OFF} "
    elif [[ $S =~ ^##.*\[ahead ]];then
        echo "${BLU}↑${OFF} "
    elif git stash list | grep -q .;then
        echo "${BLU}≡${BLU} "
    else
        echo "${GRN}✓${OFF} "
    fi
}
gits() {
    local G
    find ${*:-.} -type d -name .git 2>/dev/null \
    | while read G;do
        local D=$(dirname "$G")
        (cd "$D" >/dev/null && git remote update &>/dev/null && echo "$(gitstatus --color)$D")
    done
}
PS1BEFORE=$(tput sgr0)$(tput rev)$(tput setaf 4)
PS1AFTER=$(tput sgr0)
PS1='\[$PS1BEFORE\]$? [\h:\w]\[$PS1AFTER\] $(gitstatus)\$ 'This also defines the gits command which recursively searches the current directory (or directories you specify on the command line) for git repositories and displays their status (cross, up/down arrow, check mark as described above).
$ gits
↑ ./afl-demo
✓ ./cloud-backup
✓ ./cmake-hello-world
✓ ./ecs
↑ ./helloworld
✓ ./itunes-in-nextcloud
× ./snippets
↓ ./ThreadPool
✓ ./version
PS1="\[\e]0;\h:\w\a\]$PS1"export HISTFILE="$HOME/.bash-history"
export HISTFILESIZE=
export HISTSIZE=Changing the history file name from the default .bash_history to something else (here, by using a dash instead of an underscore, but could be anything) prevents non-login shells (that use the default history size) from deleting our history.
Requires gawk (the Gnu implementation of awk, e. g. as Linux has it).
$ gawk 'BEGIN {print systime()}'
1497429720
$ gawk 'BEGIN {print mktime("2017 06 14 10 42 00")}'
1497429720
$ gawk 'BEGIN {print strftime("%F %T %Z",1497429720)}'
2017-06-14 10:42:00 CEST
$ gawk 'BEGIN {print strftime("%F %T %Z",1497429720,1)}'
2017-06-14 08:42:00 GMTMake key pair:
$ openssl req -newkey rsa:2048 -new -nodes -x509 -days 36500 -out cert.pem -keyout key.pemcert.pem is the certificate file (public key), used for encryption. key.pem is the private key file, used for decryption.
Encrypt:
$ openssl smime -encrypt -aes256 -binary -outform DER cert.pem <cleartext.dat  >ciphertext.datDecrypt:
$ openssl smime -decrypt -inform DER -inkey key.pem <ciphertext.dat >cleartext.dat
Show contents of a pem file:
$ openssl x509 -in filename.pem -text
Replace 11 and 22 with the range of pages you want to extract.
With pdftk:
$ pdftk your-input-file.pdf cat 11-22 output your-output-file.pdfpdftk can extract arbitrary collections of pages (e. g., use cat 1 3-5 8 to extract pages 1, 3, 4, 5, and 8).
With Ghostscript:
$ gs -sDEVICE=pdfwrite -dNOPAUSE -dBATCH -dSAFER \
	-dFirstPage=11 \
	-dLastPage=22 \
	-sOutputFile=your-output-file.pdf \
	your-input-file.pdf:set ff=unix
which is annoying as hell and completely different from the way Unix programs classically work.
In shell profile:
export SYSTEMD_PAGER=catThen:
$ sudo visudoAdd the following line in the "Defaults" section:
Defaults        env_keep += "SYSTEMD_PAGER"Make your mouse wheel work like on a Mac: Roll up to scroll up, roll down to scroll down.
Put the following into /usr/share/X11/xorg.conf.d/20-natural-scrolling.conf, then reboot:
Section "InputClass"
        Identifier "Natural Scrolling"
        MatchIsPointer "on"
        MatchDevicePath "/dev/input/event*"
        Option "VertScrollDelta" "-1"
        Option "HorizScrollDelta" "-1"
        Option "DialDelta" "-1"
EndSection
If this doesn't work, try:
$ xinput set-prop 9 275 19 and 275 are just examples, find the actual values as follows.
First, the 9 is the id of your mouse device, to be found like this:
$ xinput list
⎡ Virtual core pointer                    	id=2	[master pointer  (3)]
⎜   ↳ Virtual core XTEST pointer              	id=4	[slave  pointer  (2)]
⎜   ↳ Logitech USB-PS/2 Optical Mouse         	id=9	[slave  pointer  (2)]
⎣ Virtual core keyboard                   	id=3	[master keyboard (2)]
    ↳ Virtual core XTEST keyboard             	id=5	[slave  keyboard (3)]
    ↳ Power Button                            	id=6	[slave  keyboard (3)]
    ↳ Video Bus                               	id=7	[slave  keyboard (3)]
    ↳ Power Button                            	id=8	[slave  keyboard (3)]
    ↳ Eee PC WMI hotkeys                      	id=10	[slave  keyboard (3)]
    ↳ AT Translated Set 2 keyboard            	id=11	[slave  keyboard (3)]Once you got the 9, find the 275 like this:
$ xinput list-props 9 | grep -i natural
	libinput Natural Scrolling Enabled (275):	0
	libinput Natural Scrolling Enabled Default (276):	0Sources:
- https://wiki.archlinux.org/index.php/Libinput#Natural_scrolling
 - https://kofler.info/natural-scrolling-mit-dem-mausrad/#more-1956
 
Make your machine start up and shut down like a real computer.
In /etc/default/grub, remove quiet splash from GRUB_CMDLINE_LINUX_DEFAULT, so it's
GRUB_CMDLINE_LINUX_DEFAULT=""
Uncomment GRUB_GFXMODE and set it to one one more resolutions supported by your monitor, followed by auto, for example
GRUB_GFXMODE="1920x1080,640x480,auto"
Then:
$ sudo update-grubReboot and enjoy.
Sources:
- https://askubuntu.com/questions/25022/how-to-enable-boot-messages-to-be-printed-on-screen-during-boot-up
 - http://www.subdude-site.com/WebPages_Local/RefInfo/Computer/Linux/BootMessages_andGrub2/BootMessages_andGrub2.htm
 - https://askubuntu.com/questions/103516/grub2-use-maximum-detected-resolution#142332
 - https://www.gnu.org/software/grub/manual/grub/html_node/gfxmode.html
 
Access the files in your Nextcloud without syncing them to your harddisk, using Nextcloud's WebDAV interface. Doesn't require disk space to store your Nextcloud files locally. Doesn't use the Nextcloud client software.
Tested with Ubuntu 16.04. Will probably work with Owncloud or any other WebDAV-based file service.
The following examples assume that
mycloud.example.comis your Nextcloud servermynameis your Nextcloud user namemypasswordis your Nextcloud password
Preparation:
$ sudo apt install ca-certificates
$ sudo apt install davfs2
$ sudo mkdir /mnt/myname
$ sudo usermod -aG davfs2 $USERAdd the following line to /etc/fstab:
https://mycloud.example.com/remote.php/webdav /mnt/myname davfs user,noauto 0 0
If you want read-only access (you can read your cloud files but not change them):
https://mycloud.example.com/remote.php/webdav /mnt/myname davfs user,noauto,ro,dir_mode=555,file_mode=444 0 0
Add the following to /etc/davfs2/secrets:
/mnt/myname myname mypassword
Note: Every user on your Linux machine can mount your Nextcloud files, which may or may not be desired.
Finally, to mount your Nextcloud files:
$ sudo mount /mnt/mynameMore information: https://wiki.ubuntuusers.de/WebDAV/
Using it to back up your Nextcloud: https://gitlab.com/wolframroesler/back-up-nextcloud
$ sudo add-apt-repository ppa:maarten-baert/simplescreenrecorder
$ sudo apt-get update
$ sudo apt-get install simplescreenrecorderMore: http://www.maartenbaert.be/simplescreenrecorder/
$ drutil tray eject$ defaults write com.apple.desktopservices DSDontWriteNetworkStores trueLog off or reboot to activate.
To install software like a boss.
$ /usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"
$ brew analytics offMore information: http://brew.sh
You may like:
$ brew install htop
$ brew install treeTo use the boost C++ libraries. Requires the brew package manager desribed above.
$ brew install boost
$ ln -s /usr/local/Cellar/boost/1.67.0_1/ /usr/local/boostAnd update the symlink whenever a new boost version comes out. Why don't they install in /usr/local/boost directly like everyone else, or at least create the symlink automatically?
If you need to build different projects with different boost versions you can leave the symlink away and use an environment variable instead:
$ export BOOST_ROOT=/usr/local/Cellar/boost/1.67.0_1/set profiling=1;
select ...;
show profile;explain select ...;Useful in test cases, e. g. when testing where clauses constructed from user input. Causes a lot of load in the database that makes the application hang, hogs one more more CPUs, prevents new clients from connecting, and might require a DB bounce.
SELECT something
FROM somewhere
WHERE BENCHMARK(100000000000,ENCODE('a','b'))='c';Wolfram Rösler • [email protected] • https://gitlab.com/wolframroesler • https://twitter.com/wolframroesler • https://www.linkedin.com/in/wolframroesler/
