shithub: dav1d

Download patch

ref: f713e25030bbe8deaf6266246f78b4e5d3a05bf7
parent: 11da4086e59f81393255a1c1786a990f9fa565b9
author: James Almer <[email protected]>
date: Tue May 7 20:45:15 EDT 2019

Add a DAV1D_ERR define to negate errno values when needed

--- a/include/dav1d/common.h
+++ b/include/dav1d/common.h
@@ -28,6 +28,7 @@
 #ifndef DAV1D_COMMON_H
 #define DAV1D_COMMON_H
 
+#include <errno.h>
 #include <stddef.h>
 #include <stdint.h>
 
@@ -45,6 +46,12 @@
         #define DAV1D_API
       #endif
     #endif
+#endif
+
+#if EPERM > 0
+#define DAV1D_ERR(e) (-(e)) ///< Negate POSIX error code.
+#else
+#define DAV1D_ERR(e) (e)
 #endif
 
 /**
--- a/include/dav1d/data.h
+++ b/include/dav1d/data.h
@@ -62,7 +62,7 @@
  *                      be the $cookie input argument to this function.
  * @param        cookie Opaque parameter passed to free_callback().
  *
- * @return 0 on success. A negative errno value on error.
+ * @return 0 on success. A negative DAV1D_ERR value on error.
  */
 DAV1D_API int dav1d_data_wrap(Dav1dData *data, const uint8_t *buf, size_t sz,
                               void (*free_callback)(const uint8_t *buf, void *cookie),
@@ -87,7 +87,7 @@
  *                      function.
  * @param        cookie Opaque parameter passed to $free_callback.
  *
- * @return 0 on success. A negative errno value on error.
+ * @return 0 on success. A negative DAV1D_ERR value on error.
  */
 DAV1D_API int dav1d_data_wrap_user_data(Dav1dData *data,
                                         const uint8_t *user_data,
--- a/include/dav1d/dav1d.h
+++ b/include/dav1d/dav1d.h
@@ -90,7 +90,7 @@
  * @note The context must be freed using dav1d_close() when decoding is
  *       finished.
  *
- * @return 0 on success, or < 0 (a negative errno code) on error.
+ * @return 0 on success, or < 0 (a negative DAV1D_ERR code) on error.
  */
 DAV1D_API int dav1d_open(Dav1dContext **c_out, const Dav1dSettings *s);
 
@@ -101,7 +101,7 @@
  * @param buf The data to be parser.
  * @param sz  Size of the data.
  *
- * @return 0 on success, or < 0 (a negative errno code) on error.
+ * @return 0 on success, or < 0 (a negative DAV1D_ERR code) on error.
  *
  * @note It is safe to feed this function data containing other OBUs than a
  *       Sequence Header, as they will simply be ignored. If there is more than
@@ -119,11 +119,11 @@
  *
  * @return
  *         0: Success, and the data was consumed.
- *   -EAGAIN: The data can't be consumed. dav1d_get_picture() should be called
- *            to get one or more frames before the function can consume new
- *            data.
- *   other negative errno codes: Error during decoding or because of invalid
- *                               passed-in arguments.
+ *  DAV1D_ERR(EAGAIN): The data can't be consumed. dav1d_get_picture() should
+ *                     be called to get one or more frames before the function
+ *                     can consume new data.
+ *  other negative DAV1D_ERR codes: Error during decoding or because of invalid
+ *                                  passed-in arguments.
  */
 DAV1D_API int dav1d_send_data(Dav1dContext *c, Dav1dData *in);
 
@@ -136,10 +136,10 @@
  *
  * @return
  *         0: Success, and a frame is returned.
- *   -EAGAIN: Not enough data to output a frame. dav1d_send_data() should be
- *            called with new input.
- *   other negative errno codes: Error during decoding or because of invalid
- *                               passed-in arguments.
+ *  DAV1D_ERR(EAGAIN): Not enough data to output a frame. dav1d_send_data()
+ *                     should be called with new input.
+ *  other negative DAV1D_ERR codes: Error during decoding or because of invalid
+ *                                  passed-in arguments.
  *
  * @note To drain buffered frames from the decoder (i.e. on end of stream),
  *       call this function until it returns -EAGAIN.
--- a/include/dav1d/picture.h
+++ b/include/dav1d/picture.h
@@ -109,7 +109,7 @@
      *
      * @note No fields other than data, stride and allocator_data must be filled
      *       by this callback.
-     * @return 0 on success. A negative errno value on error.
+     * @return 0 on success. A negative DAV1D_ERR value on error.
      */
     int (*alloc_picture_callback)(Dav1dPicture *pic, void *cookie);
     /**
--- a/meson.build
+++ b/meson.build
@@ -30,7 +30,7 @@
                       'b_ndebug=if-release'],
     meson_version: '>= 0.47.0')
 
-dav1d_soname_version   = '1.0.1'
+dav1d_soname_version   = '1.1.0'
 dav1d_api_version_array    = dav1d_soname_version.split('.')
 dav1d_api_version_major    = dav1d_api_version_array[0]
 dav1d_api_version_minor    = dav1d_api_version_array[1]
--- a/src/cdf.c
+++ b/src/cdf.c
@@ -4181,7 +4181,7 @@
 {
     cdf->ref = dav1d_ref_create(sizeof(CdfContext) +
                                 (t != NULL) * sizeof(atomic_uint));
-    if (!cdf->ref) return -ENOMEM;
+    if (!cdf->ref) return DAV1D_ERR(ENOMEM);
     cdf->data.cdf = cdf->ref->data;
     if (t) {
         cdf->progress = (atomic_uint *) &cdf->data.cdf[1];
--- a/src/data.c
+++ b/src/data.c
@@ -58,12 +58,12 @@
                                                          void *cookie),
                              void *const cookie)
 {
-    validate_input_or_ret(buf != NULL, -EINVAL);
-    validate_input_or_ret(ptr != NULL, -EINVAL);
-    validate_input_or_ret(free_callback != NULL, -EINVAL);
+    validate_input_or_ret(buf != NULL, DAV1D_ERR(EINVAL));
+    validate_input_or_ret(ptr != NULL, DAV1D_ERR(EINVAL));
+    validate_input_or_ret(free_callback != NULL, DAV1D_ERR(EINVAL));
 
     buf->ref = dav1d_ref_wrap(ptr, free_callback, cookie);
-    if (!buf->ref) return -ENOMEM;
+    if (!buf->ref) return DAV1D_ERR(ENOMEM);
     buf->data = ptr;
     buf->sz = buf->m.size = sz;
     dav1d_data_props_set_defaults(&buf->m);
@@ -77,11 +77,11 @@
                                                                    void *cookie),
                                        void *const cookie)
 {
-    validate_input_or_ret(buf != NULL, -EINVAL);
-    validate_input_or_ret(free_callback != NULL, -EINVAL);
+    validate_input_or_ret(buf != NULL, DAV1D_ERR(EINVAL));
+    validate_input_or_ret(free_callback != NULL, DAV1D_ERR(EINVAL));
 
     buf->m.user_data.ref = dav1d_ref_wrap(user_data, free_callback, cookie);
-    if (!buf->m.user_data.ref) return -ENOMEM;
+    if (!buf->m.user_data.ref) return DAV1D_ERR(ENOMEM);
     buf->m.user_data.data = user_data;
 
     return 0;
--- a/src/decode.c
+++ b/src/decode.c
@@ -2566,7 +2566,7 @@
 
 int dav1d_decode_frame(Dav1dFrameContext *const f) {
     const Dav1dContext *const c = f->c;
-    int retval = -ENOMEM;
+    int retval = DAV1D_ERR(ENOMEM);
 
     if (f->n_tc > 1) {
         if (f->frame_hdr->tiling.cols * f->sbh > f->tile_thread.titsati_sz) {
@@ -2778,7 +2778,7 @@
         if (c->n_fc == 1 && f->frame_hdr->use_ref_frame_mvs)
             dav1d_init_ref_mv_tile_row(f->libaom_cm, 0, f->bw, 0, f->bh);
     }
-    retval = -EINVAL;
+    retval = DAV1D_ERR(EINVAL);
 
     // setup dequant tables
     init_quant_tables(f->seq_hdr, f->frame_hdr, f->frame_hdr->quant.yac, f->dq);
@@ -3115,7 +3115,7 @@
         default:
             dav1d_log(c, "Compiled without support for %d-bit decoding\n",
                     8 + 2 * f->seq_hdr->hbd);
-            res = -ENOPROTOOPT;
+            res = DAV1D_ERR(ENOPROTOOPT);
             goto error;
         }
     }
@@ -3142,7 +3142,7 @@
         if (f->frame_hdr->primary_ref_frame != DAV1D_PRIMARY_REF_NONE) {
             const int pri_ref = f->frame_hdr->refidx[f->frame_hdr->primary_ref_frame];
             if (!c->refs[pri_ref].p.p.data[0]) {
-                res = -EINVAL;
+                res = DAV1D_ERR(EINVAL);
                 goto error;
             }
         }
@@ -3158,7 +3158,7 @@
             {
                 for (int j = 0; j < i; j++)
                     dav1d_thread_picture_unref(&f->refp[j]);
-                res = -EINVAL;
+                res = DAV1D_ERR(EINVAL);
                 goto error;
             }
             dav1d_thread_picture_ref(&f->refp[i], &c->refs[refidx].p);
@@ -3255,7 +3255,7 @@
         f->mvs_ref = dav1d_ref_create(f->sb128h * 32 * f->b4_stride *
                                       sizeof(*f->mvs));
         if (!f->mvs_ref) {
-            res = -ENOMEM;
+            res = DAV1D_ERR(ENOMEM);
             goto error;
         }
         f->mvs = f->mvs_ref->data;
@@ -3318,7 +3318,7 @@
             // actually gets set elsewhere)
             f->cur_segmap_ref = dav1d_ref_create(f->b4_stride * 32 * f->sb128h);
             if (!f->cur_segmap_ref) {
-                res = -ENOMEM;
+                res = DAV1D_ERR(ENOMEM);
                 goto error;
             }
             f->cur_segmap = f->cur_segmap_ref->data;
@@ -3332,7 +3332,7 @@
             // We need to make a new map. Allocate one here and zero it out.
             f->cur_segmap_ref = dav1d_ref_create(f->b4_stride * 32 * f->sb128h);
             if (!f->cur_segmap_ref) {
-                res = -ENOMEM;
+                res = DAV1D_ERR(ENOMEM);
                 goto error;
             }
             f->cur_segmap = f->cur_segmap_ref->data;
--- a/src/lib.c
+++ b/src/lib.c
@@ -77,21 +77,21 @@
     static pthread_once_t initted = PTHREAD_ONCE_INIT;
     pthread_once(&initted, init_internal);
 
-    validate_input_or_ret(c_out != NULL, -EINVAL);
-    validate_input_or_ret(s != NULL, -EINVAL);
+    validate_input_or_ret(c_out != NULL, DAV1D_ERR(EINVAL));
+    validate_input_or_ret(s != NULL, DAV1D_ERR(EINVAL));
     validate_input_or_ret(s->n_tile_threads >= 1 &&
-                          s->n_tile_threads <= DAV1D_MAX_TILE_THREADS, -EINVAL);
+                          s->n_tile_threads <= DAV1D_MAX_TILE_THREADS, DAV1D_ERR(EINVAL));
     validate_input_or_ret(s->n_frame_threads >= 1 &&
-                          s->n_frame_threads <= DAV1D_MAX_FRAME_THREADS, -EINVAL);
+                          s->n_frame_threads <= DAV1D_MAX_FRAME_THREADS, DAV1D_ERR(EINVAL));
     validate_input_or_ret(s->allocator.alloc_picture_callback != NULL,
-                          -EINVAL);
+                          DAV1D_ERR(EINVAL));
     validate_input_or_ret(s->allocator.release_picture_callback != NULL,
-                          -EINVAL);
+                          DAV1D_ERR(EINVAL));
     validate_input_or_ret(s->operating_point >= 0 &&
-                          s->operating_point <= 31, -EINVAL);
+                          s->operating_point <= 31, DAV1D_ERR(EINVAL));
 
     pthread_attr_t thread_attr;
-    if (pthread_attr_init(&thread_attr)) return -ENOMEM;
+    if (pthread_attr_init(&thread_attr)) return DAV1D_ERR(ENOMEM);
     pthread_attr_setstacksize(&thread_attr, 512 * 1024);
 
     Dav1dContext *const c = *c_out = dav1d_alloc_aligned(sizeof(*c), 32);
@@ -193,7 +193,7 @@
 error:
     if (c) close_internal(c_out, 0);
     pthread_attr_destroy(&thread_attr);
-    return -ENOMEM;
+    return DAV1D_ERR(ENOMEM);
 }
 
 static void dummy_free(const uint8_t *const data, void *const user_data) {
@@ -206,7 +206,7 @@
     Dav1dData buf = { 0 };
     int res;
 
-    validate_input_or_ret(out != NULL, -EINVAL);
+    validate_input_or_ret(out != NULL, DAV1D_ERR(EINVAL));
 
     Dav1dSettings s;
     dav1d_default_settings(&s);
@@ -231,7 +231,7 @@
     }
 
     if (!c->seq_hdr) {
-        res = -EINVAL;
+        res = DAV1D_ERR(EINVAL);
         goto error;
     }
 
@@ -247,14 +247,14 @@
 
 int dav1d_send_data(Dav1dContext *const c, Dav1dData *const in)
 {
-    validate_input_or_ret(c != NULL, -EINVAL);
-    validate_input_or_ret(in != NULL, -EINVAL);
-    validate_input_or_ret(in->data == NULL || in->sz, -EINVAL);
+    validate_input_or_ret(c != NULL, DAV1D_ERR(EINVAL));
+    validate_input_or_ret(in != NULL, DAV1D_ERR(EINVAL));
+    validate_input_or_ret(in->data == NULL || in->sz, DAV1D_ERR(EINVAL));
 
     c->drain = 0;
 
     if (c->in.data)
-        return -EAGAIN;
+        return DAV1D_ERR(EAGAIN);
     dav1d_data_move_ref(&c->in, in);
 
     return 0;
@@ -343,7 +343,7 @@
         }
     } while (++drain_count < c->n_fc);
 
-    return -EAGAIN;
+    return DAV1D_ERR(EAGAIN);
 }
 
 int dav1d_get_picture(Dav1dContext *const c, Dav1dPicture *const out)
@@ -350,8 +350,8 @@
 {
     int res;
 
-    validate_input_or_ret(c != NULL, -EINVAL);
-    validate_input_or_ret(out != NULL, -EINVAL);
+    validate_input_or_ret(c != NULL, DAV1D_ERR(EINVAL));
+    validate_input_or_ret(out != NULL, DAV1D_ERR(EINVAL));
 
     const int drain = c->drain;
     c->drain = 1;
@@ -358,7 +358,7 @@
 
     Dav1dData *const in = &c->in;
     if (!in->data) {
-        if (c->n_fc == 1) return -EAGAIN;
+        if (c->n_fc == 1) return DAV1D_ERR(EAGAIN);
         return drain_picture(c, out);
     }
 
@@ -384,7 +384,7 @@
     if (c->n_fc > 1 && drain)
         return drain_picture(c, out);
 
-    return -EAGAIN;
+    return DAV1D_ERR(EAGAIN);
 }
 
 void dav1d_flush(Dav1dContext *const c) {
--- a/src/obu.c
+++ b/src/obu.c
@@ -284,7 +284,7 @@
 
 error:
     dav1d_log(c, "Error parsing sequence header\n");
-    return -EINVAL;
+    return DAV1D_ERR(EINVAL);
 }
 
 static int read_frame_size(Dav1dContext *const c, GetBits *const gb,
@@ -756,7 +756,7 @@
             // segmentation data from the reference frame.
             assert(hdr->primary_ref_frame != DAV1D_PRIMARY_REF_NONE);
             const int pri_ref = hdr->refidx[hdr->primary_ref_frame];
-            if (!c->refs[pri_ref].p.p.frame_hdr) return -EINVAL;
+            if (!c->refs[pri_ref].p.p.frame_hdr) return DAV1D_ERR(EINVAL);
             hdr->segmentation.seg_data =
                 c->refs[pri_ref].p.p.frame_hdr->segmentation.seg_data;
         }
@@ -818,7 +818,7 @@
             hdr->loopfilter.mode_ref_deltas = default_mode_ref_deltas;
         } else {
             const int ref = hdr->refidx[hdr->primary_ref_frame];
-            if (!c->refs[ref].p.p.frame_hdr) return -EINVAL;
+            if (!c->refs[ref].p.p.frame_hdr) return DAV1D_ERR(EINVAL);
             hdr->loopfilter.mode_ref_deltas =
                 c->refs[ref].p.p.frame_hdr->loopfilter.mode_ref_deltas;
         }
@@ -922,7 +922,7 @@
         int off_before_idx[2], off_after_idx;
         off_before_idx[0] = 0;
         for (int i = 0; i < 7; i++) {
-            if (!c->refs[hdr->refidx[i]].p.p.data[0]) return -EINVAL;
+            if (!c->refs[hdr->refidx[i]].p.p.data[0]) return DAV1D_ERR(EINVAL);
             const unsigned refpoc = c->refs[hdr->refidx[i]].p.p.frame_hdr->frame_offset;
 
             const int diff = get_poc_diff(seqhdr->order_hint_n_bits, refpoc, poc);
@@ -999,7 +999,7 @@
                 ref_gmv = &dav1d_default_wm_params;
             } else {
                 const int pri_ref = hdr->refidx[hdr->primary_ref_frame];
-                if (!c->refs[pri_ref].p.p.frame_hdr) return -EINVAL;
+                if (!c->refs[pri_ref].p.p.frame_hdr) return DAV1D_ERR(EINVAL);
                 ref_gmv = &c->refs[pri_ref].p.p.frame_hdr->gmv[i];
             }
             int32_t *const mat = hdr->gmv[i].matrix;
@@ -1122,7 +1122,7 @@
 
 error:
     dav1d_log(c, "Error parsing frame header\n");
-    return -EINVAL;
+    return DAV1D_ERR(EINVAL);
 }
 
 static void parse_tile_hdr(Dav1dContext *const c, GetBits *const gb) {
@@ -1227,7 +1227,7 @@
     switch (type) {
     case OBU_SEQ_HDR: {
         Dav1dRef *ref = dav1d_ref_create(sizeof(Dav1dSequenceHeader));
-        if (!ref) return -ENOMEM;
+        if (!ref) return DAV1D_ERR(ENOMEM);
         Dav1dSequenceHeader *seq_hdr = ref->data;
         memset(seq_hdr, 0, sizeof(*seq_hdr));
         if ((res = parse_seq_hdr(c, &gb, seq_hdr)) < 0) {
@@ -1236,7 +1236,7 @@
         }
         if (check_for_overrun(c, &gb, init_bit_pos, len)) {
             dav1d_ref_dec(&ref);
-            return -EINVAL;
+            return DAV1D_ERR(EINVAL);
         }
         // If we have read a sequence header which is different from
         // the old one, this is a new video sequence and can't use any
@@ -1273,7 +1273,7 @@
         if (!c->seq_hdr) goto error;
         if (!c->frame_hdr_ref) {
             c->frame_hdr_ref = dav1d_ref_create(sizeof(Dav1dFrameHeader));
-            if (!c->frame_hdr_ref) return -ENOMEM;
+            if (!c->frame_hdr_ref) return DAV1D_ERR(ENOMEM);
         }
         // ensure that the reference is writable
         assert(dav1d_ref_is_writable(c->frame_hdr_ref));
@@ -1295,7 +1295,7 @@
             dav1d_get_bits(&gb, 1);
             if (check_for_overrun(c, &gb, init_bit_pos, len)) {
                 c->frame_hdr = NULL;
-                return -EINVAL;
+                return DAV1D_ERR(EINVAL);
             }
 
             break;
@@ -1326,7 +1326,7 @@
         // Align to the next byte boundary and check for overrun.
         dav1d_bytealign_get_bits(&gb);
         if (check_for_overrun(c, &gb, init_bit_pos, len))
-            return -EINVAL;
+            return DAV1D_ERR(EINVAL);
         // The current bit position is a multiple of 8 (because we
         // just aligned it) and less than 8*pkt_bytelen because
         // otherwise the overrun check would have fired.
@@ -1362,7 +1362,7 @@
         switch (meta_type) {
         case OBU_META_HDR_CLL:
             ref = dav1d_ref_create(sizeof(Dav1dContentLightLevel));
-            if (!ref) return -ENOMEM;
+            if (!ref) return DAV1D_ERR(ENOMEM);
             content_light = ref->data;
             memset(content_light, 0, sizeof(*content_light));
 
@@ -1383,7 +1383,7 @@
             break;
         case OBU_META_HDR_MDCV: {
             ref = dav1d_ref_create(sizeof(Dav1dMasteringDisplay));
-            if (!ref) return -ENOMEM;
+            if (!ref) return DAV1D_ERR(ENOMEM);
             mastering_display = ref->data;
             memset(mastering_display, 0, sizeof(*mastering_display));
 
@@ -1428,12 +1428,12 @@
         break;
     default:
         dav1d_log(c, "Unknown OBU type %d of size %u\n", type, len);
-        return -EINVAL;
+        return DAV1D_ERR(EINVAL);
     }
 
     if (c->seq_hdr && c->frame_hdr) {
         if (c->frame_hdr->show_existing_frame) {
-            if (!c->refs[c->frame_hdr->existing_frame_idx].p.p.data[0]) return -EINVAL;
+            if (!c->refs[c->frame_hdr->existing_frame_idx].p.p.data[0]) return DAV1D_ERR(EINVAL);
             if (c->n_fc == 1) {
                 dav1d_picture_ref(&c->out,
                                   &c->refs[c->frame_hdr->existing_frame_idx].p.p);
@@ -1486,7 +1486,7 @@
             c->frame_hdr = NULL;
         } else if (c->n_tiles == c->frame_hdr->tiling.cols * c->frame_hdr->tiling.rows) {
             if (!c->n_tile_data)
-                return -EINVAL;
+                return DAV1D_ERR(EINVAL);
             if ((res = dav1d_submit_frame(c)) < 0)
                 return res;
             assert(!c->n_tile_data);
@@ -1499,5 +1499,5 @@
 
 error:
     dav1d_log(c, "Error parsing OBU data\n");
-    return -EINVAL;
+    return DAV1D_ERR(EINVAL);
 }
--- a/src/picture.c
+++ b/src/picture.c
@@ -62,7 +62,7 @@
     uint8_t *data = dav1d_alloc_aligned(pic_size + DAV1D_PICTURE_ALIGNMENT,
                                         DAV1D_PICTURE_ALIGNMENT);
     if (data == NULL) {
-        return -ENOMEM;
+        return DAV1D_ERR(ENOMEM);
     }
 
     p->data[0] = data;
@@ -116,7 +116,7 @@
 
     struct pic_ctx_context *pic_ctx = malloc(extra + sizeof(struct pic_ctx_context));
     if (pic_ctx == NULL) {
-        return -ENOMEM;
+        return DAV1D_ERR(ENOMEM);
     }
 
     p->p.w = w;
@@ -141,7 +141,7 @@
         p_allocator->release_picture_callback(p, p_allocator->cookie);
         free(pic_ctx);
         dav1d_log(c, "Failed to wrap picture: %s\n", strerror(errno));
-        return -ENOMEM;
+        return DAV1D_ERR(ENOMEM);
     }
 
     p->seq_hdr_ref = seq_hdr_ref;
--- a/src/ref_mvs.c
+++ b/src/ref_mvs.c
@@ -55,6 +55,8 @@
 #include <stdlib.h>
 #include <string.h>
 
+#include "dav1d/common.h"
+
 #include "common/intops.h"
 
 #define av1_zero(a) memset(a, 0, sizeof(a))
@@ -1986,7 +1988,7 @@
         const int align_h = (h8 + 15) & ~15;
         if (cm->tpl_mvs) free(cm->tpl_mvs);
         cm->tpl_mvs = malloc(sizeof(*cm->tpl_mvs) * (stride >> 1) * align_h);
-        if (!cm->tpl_mvs) return -ENOMEM;
+        if (!cm->tpl_mvs) return DAV1D_ERR(ENOMEM);
         for (int i = 0; i < 7; i++)
             cm->frame_refs[i].idx = i;
         cm->mi_cols = w8 << 1;
--- a/tests/libfuzzer/dav1d_fuzzer.c
+++ b/tests/libfuzzer/dav1d_fuzzer.c
@@ -61,7 +61,7 @@
 
 static int fuzz_picture_allocator(Dav1dPicture *pic, void *cookie) {
     if (pic->p.w > DAV1D_FUZZ_MAX_SIZE || pic->p.h > DAV1D_FUZZ_MAX_SIZE)
-        return -EINVAL;
+        return DAV1D_ERR(EINVAL);
 
     return default_picture_allocator(pic, cookie);
 }
@@ -149,7 +149,7 @@
 
         do {
             if ((err = dav1d_send_data(ctx, &buf)) < 0) {
-                if (err != -EAGAIN)
+                if (err != DAV1D_ERR(EAGAIN))
                     break;
             }
             memset(&pic, 0, sizeof(pic));
@@ -156,7 +156,7 @@
             err = dav1d_get_picture(ctx, &pic);
             if (err == 0) {
                 dav1d_picture_unref(&pic);
-            } else if (err != -EAGAIN) {
+            } else if (err != DAV1D_ERR(EAGAIN)) {
                 break;
             }
         } while (buf.sz > 0);
@@ -170,7 +170,7 @@
         err = dav1d_get_picture(ctx, &pic);
         if (err == 0)
             dav1d_picture_unref(&pic);
-    } while (err != -EAGAIN);
+    } while (err != DAV1D_ERR(EAGAIN));
 
 cleanup:
     dav1d_flush(ctx);
--- a/tools/dav1d.c
+++ b/tools/dav1d.c
@@ -129,7 +129,7 @@
     do {
         memset(&p, 0, sizeof(p));
         if ((res = dav1d_send_data(c, &data)) < 0) {
-            if (res != -EAGAIN) {
+            if (res != DAV1D_ERR(EAGAIN)) {
                 fprintf(stderr, "Error decoding frame: %s\n",
                         strerror(-res));
                 break;
@@ -137,7 +137,7 @@
         }
 
         if ((res = dav1d_get_picture(c, &p)) < 0) {
-            if (res != -EAGAIN) {
+            if (res != DAV1D_ERR(EAGAIN)) {
                 fprintf(stderr, "Error decoding frame: %s\n",
                         strerror(-res));
                 break;
@@ -168,7 +168,7 @@
     // flush
     if (res == 0) while (!cli_settings.limit || n_out < cli_settings.limit) {
         if ((res = dav1d_get_picture(c, &p)) < 0) {
-            if (res != -EAGAIN) {
+            if (res != DAV1D_ERR(EAGAIN)) {
                 fprintf(stderr, "Error decoding frame: %s\n",
                         strerror(-res));
             } else {
--- a/tools/input/input.c
+++ b/tools/input/input.c
@@ -90,7 +90,7 @@
         }
         if (i == num_demuxers) {
             fprintf(stderr, "Failed to find demuxer named \"%s\"\n", name);
-            return -ENOPROTOOPT;
+            return DAV1D_ERR(ENOPROTOOPT);
         }
     } else {
         const char *const ext = find_extension(filename);
@@ -109,13 +109,13 @@
             fprintf(stderr,
                     "Failed to find demuxer for file %s (\"%s\")\n",
                     filename, ext);
-            return -ENOPROTOOPT;
+            return DAV1D_ERR(ENOPROTOOPT);
         }
     }
 
     if (!(c = malloc(sizeof(DemuxerContext) + impl->priv_data_size))) {
         fprintf(stderr, "Failed to allocate memory\n");
-        return -ENOMEM;
+        return DAV1D_ERR(ENOMEM);
     }
     memset(c, 0, sizeof(DemuxerContext) + impl->priv_data_size);
     c->impl = impl;
--- a/tools/output/output.c
+++ b/tools/output/output.c
@@ -93,7 +93,7 @@
         }
         if (i == num_muxers) {
             fprintf(stderr, "Failed to find muxer named \"%s\"\n", name);
-            return -ENOPROTOOPT;
+            return DAV1D_ERR(ENOPROTOOPT);
         }
     } else {
         const char *ext = find_extension(filename);
@@ -109,13 +109,13 @@
         }
         if (i == num_muxers) {
             fprintf(stderr, "Failed to find muxer for extension \"%s\"\n", ext);
-            return -ENOPROTOOPT;
+            return DAV1D_ERR(ENOPROTOOPT);
         }
     }
 
     if (!(c = malloc(sizeof(MuxerContext) + impl->priv_data_size))) {
         fprintf(stderr, "Failed to allocate memory\n");
-        return -ENOMEM;
+        return DAV1D_ERR(ENOMEM);
     }
     c->impl = impl;
     c->data = (MuxerPriv *) &c[1];