view help2html/uintarray.c @ 21:1c9dac05d040

Add lint-style FALLTHROUGH annotations to fallthrough cases. (in the parse engine and thus the output code) Document this, because the old output causes warnings with gcc10.
author David A. Holland
date Mon, 13 Jun 2022 00:04:38 -0400
parents 60b08b68c750
children
line wrap: on
line source

#include <stdlib.h>
#include "must.h"
#include "uintarray.h"

////////////////////////////////////////////////////////////

void uintarray_init(struct uintarray *a) {
   a->v = NULL;
   a->num = a->max = 0;
}

struct uintarray *uintarray_create(void) {
   struct uintarray *a;
   a = must_malloc(sizeof(*a));
   uintarray_init(a);
   return a;
}

void uintarray_cleanup(struct uintarray *a) {
   free(a->v);
   a->v = NULL;
   a->num = a->max = 0;
}

void uintarray_destroy(struct uintarray *a) {
   uintarray_cleanup(a);
   free(a);
}

////////////////////////////////////////////////////////////

/*
 * I wish there were a way to check that these were the same as the
 * inline versions, but apparently allowing such things to diverge is
 * a feature of C99. Bleh.
 *
 * Update: it all broke anyway, so I've switched to static inline as
 * an expedient. Thus, at least for the time being, we don't need the
 * extra copies.
 */

#if 0
unsigned uintarray_num(const struct uintarray *a) {
   return a->num;
}

unsigned uintarray_get(const struct uintarray *a, unsigned ix) {
   assert(ix < a->num);
   return a->v[ix];
}

void uintarray_set(struct uintarray *a, unsigned ix, unsigned val) {
   assert(ix < a->num);
   a->v[ix] = val;
}
#endif

////////////////////////////////////////////////////////////

void uintarray_add(struct uintarray *a, unsigned val) {
   unsigned ix;

   ix = a->num;
   uintarray_setsize(a, a->num+1);
   a->v[ix] = val;
}

void uintarray_setsize(struct uintarray *a, unsigned newnum) {
   unsigned newmax;
   unsigned *newptr;

   if (newnum > a->max) {
      newmax = a->max;
      if (newmax == 0) {
	 newmax = 4;
      }
      while (newmax < newnum) {
	 newmax *= 2;
      }
      newptr = must_realloc(a->v, newmax*sizeof(unsigned));
      a->v = newptr;
      a->max = newmax;
   }

   a->num = newnum;

   /* Note: it's the user's responsibility to initialize the new space */
}

static int (*uintarray_usersort)(unsigned a, unsigned b);

static int uintarray_sortthunk(const void *av, const void *bv) {
   /* av and bv point to elements of the uintarray */
   unsigned a = *(const unsigned *)av;
   unsigned b = *(const unsigned *)bv;
   return uintarray_usersort(a, b);
}

void uintarray_sort(struct uintarray *a, int (*f)(unsigned a, unsigned b)) {
   uintarray_usersort = f;
   qsort(a->v, a->num, sizeof(unsigned), uintarray_sortthunk);
}