(Thanks to @MartinR for encouraging me to pull my finger out on this answer and to correctly identify that you cannot just close stdout/stderr, as the next open()
will re-use those file descriptors, but to redirect stdout/stderr to the infamous /dev/null
).
logControl.h:
#pragma once
extern void stopLogging();
extern void startLogging();
logControl.c:
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
static int loggingStopped = 0;
static int oldStdout = -1;
static int oldStderr = -1;
void stopLogging() {
if (!loggingStopped) {
oldStdout = dup(1);
oldStderr = dup(2);
int devNull = open("/dev/null", O_WRONLY);
dup2(devNull, 1);
dup2(devNull, 2);
close(devNull);
loggingStopped = 1;
}
}
void startLogging() {
if (loggingStopped && oldStdout >= 0 && oldStderr >= 0) {
dup2(oldStdout, 1);
close(oldStdout);
oldStdout = -1;
dup2(oldStderr, 2);
close(oldStderr);
oldStderr = -1;
loggingStopped = 0;
}
}
This works at runtime, not compile time, which I believe is what you are asking. Simply call stopLogging()
or startLogging()
as required.
NOTE: There is no error-checking to speak of, so that could be improved perhaps.