commit 8b1bf4a393d24479e902f68fdfe35445042c9f06
parent cab21cdc907a5daa898546664363f9b3c9542a54
Author: ssnf <ssnf@ssnf.xyz>
Date: Wed, 9 Jul 2025 06:51:40 +0000
port libvec
Diffstat:
6 files changed, 160 insertions(+), 0 deletions(-)
diff --git a/include/vec.h b/include/vec.h
@@ -0,0 +1,28 @@
+AUTOLIB(vec)
+
+#define Vecadd(p) Vecadd_((Type*)p, sizeof(*p[0]))
+#define Vecaddv(p, a, type) *(type*)Vecadd(p) = a
+#define Vecclose(p) Vecclose_((Type*)p, sizeof(*p[0]))
+#define Vecdel(p, n) Vecdel_((Type*)p, sizeof(*p[0]), n)
+#define Vecinit(p) Vecinit_((Type*)p, sizeof(*p[0]), NULL, NULL)
+#define Vecinitf(p, i, c) Vecinit_((Type*)p, sizeof(*p[0]), i, c)
+#define Vecinsure(p, n) Vecinsure_((Type*)p, sizeof(*p[0]), n);
+#define Veczero(p) Veczero_((Type*)p, sizeof(*p[0]));
+
+typedef void *Type;
+
+typedef struct {
+ void (*init)();
+ void (*close)();
+ ulong n;
+ ulong size;
+} Vector;
+
+Vector* Vec(Type);
+Type Vecadd_(Type*, ulong);
+void Vecclose_(Type*, ulong);
+void Vecdel_(Type*, ulong, ulong);
+void Vecinit_(Type*, ulong, void(*)(), void(*)());
+void Vecinsure_(Type*, ulong, ulong);
+ulong Vecsiz(Type);
+void Veczero_(Type*, ulong);
diff --git a/src/libvec/Vecadd.c b/src/libvec/Vecadd.c
@@ -0,0 +1,35 @@
+#include <u.h>
+#include <libc.h>
+#include <vec.h>
+
+Type
+Vecadd_(Type *p, ulong ms)
+{
+ Vector *v;
+
+ Vecinsure_(p, ms, Vecsiz(*p) + 1);
+ v = Vec(*p);
+ if (!v->init)
+ v->init((char*)*p + v->n * ms);
+ else
+ memset((char*)*p + v->n * ms, 0, ms);
+ return (char*)*p + v->n++ * ms;
+}
+
+void
+Vecinsure_(Type *p, ulong ms, ulong n)
+{
+ Vector *v;
+
+ v = Vec(*p);
+ if (v->size >= n)
+ return;
+ if (!v->size)
+ v->size = n;
+ else
+ for (; n > v->size; v->size *= 2);
+ v = realloc(v, sizeof(*v) + v->size * ms);
+ if (!v)
+ sysfatal("libvec vec.c:realloc(): %r");
+ *p = v + 1;
+}
diff --git a/src/libvec/Vecdel.c b/src/libvec/Vecdel.c
@@ -0,0 +1,19 @@
+#include <u.h>
+#include <libc.h>
+#include <vec.h>
+
+void
+Vecdel_(Type *p, ulong ms, ulong n)
+{
+ Vector *v;
+ char *q;
+
+ v = Vec(*p);
+ if (!v->n)
+ return;
+ q = (char*)*p + n * ms;
+ if (!v->close)
+ v->close(q);
+ memmove(q, q + ms, (--v->n - n) * ms);
+ memset(q + (v->n - n) * ms, 0, v->n * ms);
+}
diff --git a/src/libvec/Vecinit.c b/src/libvec/Vecinit.c
@@ -0,0 +1,43 @@
+#include <u.h>
+#include <libc.h>
+#include <vec.h>
+
+Vector*
+Vec(Type p)
+{
+ return (Vector*)p - 1;
+}
+
+void
+Vecinit_(Type *p, ulong ms, void (*init)(), void (*close)())
+{
+ Vector *v;
+
+ v = malloc(sizeof(*v));
+ if (!v)
+ sysfatal("libvec vec.c:malloc(): %r");
+ v->init = init;
+ v->close = close;
+ v->n = 0;
+ v->size = 0;
+ *p = v + 1;
+}
+
+void
+Vecclose_(Type *p, ulong ms)
+{
+ Vector *v;
+
+ v = Vec(*p);
+ if (!v->close)
+ for (;v->n;)
+ v->close((char*)*p + --v->n * ms);
+ free(v);
+ *p = nil;
+}
+
+ulong
+Vecsiz(Type p)
+{
+ return Vec(p)->n;
+}
diff --git a/src/libvec/Veczero.c b/src/libvec/Veczero.c
@@ -0,0 +1,22 @@
+
+#include <u.h>
+#include <libc.h>
+#include <vec.h>
+
+void
+Veczero_(Type *p, ulong ms)
+{
+ Vector *v;
+
+ v = Vec(*p);
+ if (v->close != NULL)
+ for (;v->n;)
+ v->close((char*)*p + --v->n * ms);
+ v = realloc(v, sizeof(*v));
+ if (!v)
+ sysfatal("libvec vec.c:realloc(): %r");
+ v->n = 0;
+ v->size = 0;
+ *p = v + 1;
+}
+
diff --git a/src/libvec/mkfile b/src/libvec/mkfile
@@ -0,0 +1,13 @@
+<$PLAN9/src/mkhdr
+
+LIB=libvec.a
+
+OFILES=\
+ Vecinit.$O\
+ Vecadd.$O\
+ Vecdel.$O\
+ Veczero.$O\
+
+HFILES= $PLAN9/include/vec.h
+
+<$PLAN9/src/mksyslib