Skip to content

Instantly share code, notes, and snippets.

@StarSugar
Last active December 26, 2025 13:41
Show Gist options
  • Select an option

  • Save StarSugar/7baa30de9e58ddf5ef3237a14755ed8e to your computer and use it in GitHub Desktop.

Select an option

Save StarSugar/7baa30de9e58ddf5ef3237a14755ed8e to your computer and use it in GitHub Desktop.
#include <stdint.h>
#include <unistd.h>
#include <stdio.h>
#include <errno.h>
#include <stdarg.h>
#include <stdlib.h>
int cprint(intptr_t first, ...) {
va_list args, args2;
va_start(args, first);
size_t bufsiz, wrotelen, wholelen;
int fd, strresp, ret, malloc_buf_p;
char *buf, *fmt, a_buf[BUFSIZ];
buf = a_buf;
bufsiz = BUFSIZ;
strresp = 0;
malloc_buf_p = 0;
if (first == 0) {
buf = va_arg(args, char *);
bufsiz = va_arg(args, size_t);
fmt = va_arg(args, char *);
strresp = 1;
}
else if (first < FD_SETSIZE) {
fd = first;
fmt = va_arg(args, char *);
}
else {
fd = 1;
fmt = (char *)first;
}
retry:
va_copy(args2, args);
ret = vsnprintf(buf, bufsiz, fmt, args2);
va_end(args2);
if (ret <= 0 || strresp) {
goto final;
}
else if (ret >= bufsiz) {
buf = malloc(ret + 1);
if (buf == NULL)
return -errno;
bufsiz = ret + 1;
malloc_buf_p = 1;
goto retry;
}
wholelen = ret;
wrotelen = 0;
while (wrotelen < wholelen) {
ret = write(fd, buf + wrotelen, wholelen - wrotelen);
if (ret <= 0) return -errno;
wrotelen += ret;
}
ret = wholelen;
final:
if (malloc_buf_p)
free(buf);
va_end(args);
return ret;
}
#include <stdint.h>
int cprint(intptr_t first, ...);
/*
cprint(const char *fmt, ...); (1)
cprint(0, char *buf, size_t bufsiz, const char *fmt, ...); (2)
cprint(intptr_t fd, const char *fmt, ...) (3)
(1) same as printf
(2) except the first argument must be 0, same as snprintf
(3) The first argument must be a writable fd below FD_SETSIZE, like fprintf, but write to the fd
*/
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment