summaryrefslogtreecommitdiff
path: root/mimetypes/err.c
diff options
context:
space:
mode:
Diffstat (limited to 'mimetypes/err.c')
-rw-r--r--mimetypes/err.c150
1 files changed, 150 insertions, 0 deletions
diff --git a/mimetypes/err.c b/mimetypes/err.c
new file mode 100644
index 0000000..39f25a5
--- /dev/null
+++ b/mimetypes/err.c
@@ -0,0 +1,150 @@
+#ifdef HAVE_CONFIG_H
+# include <config.h>
+#endif
+#include <stdlib.h>
+#include <stdarg.h>
+#include <errno.h>
+#include "mtint.h"
+
+ssize_t
+mimetypes_error_format (char **pbuf, size_t *psize,
+ struct locus_range const *lr, char const *fmt,
+ va_list ap)
+{
+ char *buf;
+ size_t buflen;
+ ssize_t n;
+ int rc;
+
+ if (lr)
+ {
+ n = locus_range_format (pbuf, psize, lr);
+ if (n == -1)
+ return -1;
+ buf = *pbuf;
+ buflen = *psize;
+ }
+ else
+ {
+ buf = *pbuf;
+ buflen = *psize;
+ if (buflen == 0)
+ buflen = 512; /* Initial allocation */
+
+ buf = calloc (1, buflen);
+ if (buf == NULL)
+ {
+ errno = ENOMEM;
+ return -1;
+ }
+ }
+
+ for (;;)
+ {
+ va_list aq;
+
+ va_copy(aq, ap);
+ n = vsnprintf (buf, buflen, fmt, aq);
+ va_end(aq);
+
+ if (n < 0 || n >= buflen || !memchr (buf, '\0', n + 1))
+ {
+ char *newbuf;
+ size_t newlen = buflen * 2;
+ if (newlen < buflen)
+ {
+ errno = ENOMEM;
+ rc = -1;
+ break;
+ }
+ newbuf = realloc (buf, newlen);
+ if (newbuf == NULL)
+ {
+ errno = ENOMEM;
+ rc = -1;
+ break;
+ }
+ buflen = newlen;
+ buf = newbuf;
+ }
+ else
+ break;
+ }
+
+ if (rc)
+ {
+ if (!*pbuf)
+ {
+ /* We made first allocation, now free it */
+ free (buf);
+ buf = NULL;
+ buflen = 0;
+ }
+ }
+
+ *pbuf = buf;
+ *psize = buflen;
+ return rc;
+}
+
+
+static void
+default_error_printer (char const *msg)
+{
+ fprintf (stderr, "%s\n", msg);
+}
+
+void (*mimetypes_error_printer) (char const *) = default_error_printer;
+
+void
+mimetypes_error_at (struct locus_range const *lr, char const *fmt, ...)
+{
+ va_list ap;
+ char *buf = NULL;
+ size_t buflen = 0;
+ ssize_t n;
+
+ va_start (ap, fmt);
+ n = mimetypes_error_format (&buf, &buflen, lr, fmt, ap);
+ va_end (ap);
+
+ if (n < 0)
+ return;
+
+ mimetypes_error_printer (buf);
+
+ free (buf);
+}
+
+void
+mimetypes_error (char const *fmt, ...)
+{
+ va_list ap;
+ char *buf = NULL;
+ size_t buflen = 0;
+ ssize_t n;
+
+ va_start (ap, fmt);
+ n = mimetypes_error_format (&buf, &buflen, NULL, fmt, ap);
+ va_end (ap);
+
+ if (n < 0)
+ return;
+
+ mimetypes_error_printer (buf);
+
+ free (buf);
+}
+
+void
+print_locus_range (FILE *fp, struct locus_range const *lr)
+{
+ char *buf = NULL;
+ size_t buflen = 0;
+ ssize_t n;
+ n = locus_range_format (&buf, &buflen, lr);
+ if (n < 0)
+ return;
+ fwrite (buf, buflen, 1, fp);
+ free (buf);
+}

Return to:

Send suggestions and report system problems to the System administrator.