/* See LICENSE file for copyright and license details. */
#include "common.h"
size_t
libpatch_create_timestamp(char *buf, size_t bufsize, const struct tm *tm,
uintmax_t subseconds, unsigned subseconds_decimals,
unsigned frac, int zone, enum libpatch_style style)
{
size_t guess, len, r;
const char *fmt;
frac = MIN(frac, subseconds_decimals);
if (style == LIBPATCH_STYLE_COPIED) {
fmt = "%a %b %e %T %Y";
guess = sizeof("aaa bbb 00 00:00:00 0000");
} else if (style == LIBPATCH_STYLE_UNIFIED) {
fmt = "%Y-%m-%d %H:%M:%S";
zone = 1;
guess = sizeof("0000-00-00 00:00:00");
} else {
errno = EINVAL;
return 0;
}
if (zone)
guess += sizeof(" +0000");
guess += (size_t)frac + (size_t)(frac > 0);
if (!bufsize)
return guess;
while (subseconds_decimals != frac) {
subseconds /= 10;
subseconds_decimals -= 1;
}
len = strftime(buf, bufsize, fmt, tm);
if (!len)
return bufsize < guess ? guess : bufsize + 16U;
if (frac) {
if (len < bufsize)
snprintf(&buf[len], bufsize - len, ".%0*ju", (int)frac, subseconds);
len += (size_t)frac + (size_t)(frac > 0);
}
if (zone) {
if (len < bufsize)
return bufsize < len + 7U ? len + 7U : bufsize + 16U;
len += r = strftime(&buf[len], bufsize - len, " %z", tm);
if (!r)
return bufsize < len + 7U ? len + 7U : bufsize + 16U;
}
return len + 1;
}