commit d4c7e5d3263b880b60002ec2ef5db33346f7ef1a
parent a2ed7dd5873d2ac5113b21735688737fab330191
Author: Pavel Renev <an2qzavok@gmail.com>
Date: Tue, 24 Aug 2021 03:14:31 +0000
hunt some bugs, remove newobject(), use new arrayinsert an objinsertbeforelast in place of ad-hoc object creation
Diffstat:
M | TODO | | | 9 | +++++---- |
M | array.c | | | 4 | +++- |
M | devfs.c | | | 29 | +++++++++-------------------- |
M | fs.c | | | 37 | +++++++++++++++++++++++++------------ |
M | richterm.c | | | 163 | +++++++++++++++++++++++++++++++++++-------------------------------------------- |
M | richterm.h | | | 9 | ++++++--- |
6 files changed, 121 insertions(+), 130 deletions(-)
diff --git a/TODO b/TODO
@@ -3,10 +3,6 @@
- object removal
- screen clearing.
-# find and fix memory locks
-
-there's one related to spawning many new objects
-
# images
draw them
@@ -14,3 +10,7 @@ draw them
# links
highlight them and add 3-button menu for interacting with them
+
+# catch ghost new file creation events
+
+probably related to new file being read by ls?
+\ No newline at end of file
diff --git a/array.c b/array.c
@@ -56,13 +56,15 @@ arraygrow(Array *ap, long n, void *v)
}
ve = arrayend(ap);
qlock(ap->l);
+
ap->count += n;
if (ap->count > ap->n) {
ap->n += ap->n;
if (ap->count > ap->n) ap->n = ap->count;
ap->p = realloc(ap->p, ap->size * ap->n);
}
- memset(ve, 0, ap->size * ap->n);
+
+ memset(ve, 0, n * ap->size);
if (v != nil) {
memcpy(ve, v, n * ap->size);
}
diff --git a/devfs.c b/devfs.c
@@ -36,33 +36,22 @@ void
devfs_write(Req *r)
{
File *f;
- Array *buf;
- Object *obj;
- buf = nil;
- obj = nil;
f = r->fid->file;
if (f == cons){
+ Object *obj;
r->ofcall.count = r->ifcall.count;
-
- if (rich.text->count - olast->offset > 0) {
- buf = arraycreate(sizeof(char),
- rich.text->count - olast->offset, nil);
- memcpy(buf->p, arrayget(rich.text, olast->offset),
- rich.text->count - olast->offset);
- }
+ obj = objectcreate();
+ mkobjectftree(obj, fsctl->tree->root);
+ objinsertbeforelast(obj);
- rich.objects->count--;
+//print("%ld -> ", olast->offset);
- obj = mkobjectftree(
- newobject(&rich, r->ifcall.data, r->ifcall.count),
- fsctl->tree->root);
+ arrayinsert(rich.text, olast->offset, r->ifcall.count, r->ifcall.data);
+ olast->offset += r->ifcall.count;
+
+//print("%ld\n", olast->offset);
- /* TODO: free olast */
- if (buf != nil) {
- olast = newobject(&rich, buf->p, buf->count);
- arrayfree(buf);
- } else olast = newobject(&rich, nil, 0);
nbsend(redrawc, &obj);
respond(r, nil);
diff --git a/fs.c b/fs.c
@@ -42,19 +42,20 @@ initfs(char *srvname)
char *
ctlcmd(char *buf)
{
- Object **op;
+ Object *obj;
int n, i, j;
char *args[256];
+ obj = nil;
n = tokenize(buf, args, 256);
if (n <= 0) return "expected a command";
qlock(rich.l);
if (strcmp(args[0], "remove") == 0) {
for (i = 1; i < n; i++) {
for (j = 0; j < rich.objects->count; j++) {
- op = arrayget(rich.objects, j);
- if (*op == olast) continue;
- if (strcmp((*op)->id, args[i]) == 0) {
- objectfree(*op);
+ arrayget(rich.objects, j, &obj);
+ if (obj == olast) continue;
+ if (strcmp(obj->id, args[i]) == 0) {
+ // objectfree(obj);
arraydel(rich.objects, j);
break;
}
@@ -64,9 +65,9 @@ ctlcmd(char *buf)
int k;
k = rich.objects->count;
for (i = 0; i < k; i++) {
- op = arrayget(rich.objects, 0);
- if (*op != olast) {
- objectfree(*op);
+ arrayget(rich.objects, 0, &obj);
+ if (obj != olast) {
+ // objectfree(obj);
arraydel(rich.objects, 0);
}
}
@@ -91,11 +92,23 @@ ftree_destroy(File *f)
void
fs_open(Req *r)
-{
+{
Fsctl *fsctl;
+
fsctl = new->aux;
- newobj = mkobjectftree(newobject(&rich, nil, 0), fsctl->tree->root);
+
+
+ newobj = objectcreate();
+ mkobjectftree(newobj, fsctl->tree->root);
+ objinsertbeforelast(newobj);
+
+ /*
+ * Because our newobj is created empty, there's no need
+ * to move text from olast around.
+ */
+
respond(r, nil);
+
}
void
@@ -174,7 +187,7 @@ textread(Req *r, void *)
if (oe == nil) n = rich.text->count;
else n = oe->offset;
- s = arrayget(rich.text, obj->offset);
+ s = arrayget(rich.text, obj->offset, nil);
qlock(rich.text->l);
@@ -206,7 +219,7 @@ textwrite(Req *r, void *)
m = r->ifcall.count + r->ifcall.offset;
dn = m - n;
- if (dn > 0) arraygrow(rich.text, dn);
+ if (dn > 0) arraygrow(rich.text, dn, nil);
else rich.text->count += dn;
qlock(rich.text->l);
diff --git a/richterm.c b/richterm.c
@@ -68,7 +68,6 @@ usage(void)
void
threadmain(int argc, char **argv)
{
- Font **fp;
int rv[2], mmode;
Mouse mv;
Rune kv;
@@ -106,15 +105,17 @@ threadmain(int argc, char **argv)
Itext = display->black;
fonts = arraycreate(sizeof(Font *), 2, nil);
- fp = arraygrow(fonts, 1);
- *fp = font;
+ arraygrow(fonts, 1, &font);
rich.l = mallocz(sizeof(QLock), 1);
qlock(rich.l);
- rich.objects = arraycreate(sizeof(Object *), 8, nil);
rich.text = arraycreate(sizeof(char), 4096, nil);
+ rich.objects = arraycreate(sizeof(Object *), 8, nil);
+
+ olast = objectcreate();
+ arraygrow(rich.objects, 1, &olast);
rich.page.scroll = ZP;
@@ -123,12 +124,12 @@ threadmain(int argc, char **argv)
qunlock(rich.l);
- olast = newobject(&rich, nil, 0);
-
redrawc = chancreate(sizeof(Object *), 8);
resize();
- nbsend(redrawc, nil);
+ draw(screen, screen->r, Inormbg, nil, ZP);
+ drawscrollbar();
+ flushimage(display, 1);
if(rfork(RFENVG) < 0)
sysfatal("rfork: %r");
@@ -139,7 +140,7 @@ threadmain(int argc, char **argv)
proccreate(runcmd, argv, 16 * 1024);
hostpid = recvul(pidchan);
- enum {MOUSE, RESIZE, REDRAW, KBD, DEVFSWRITE, NONE};
+ enum {MOUSE, RESIZE, REDRAW, KBD, NONE};
Alt alts[5] = {
{mctl->c, &mv, CHANRCV},
{mctl->resizec, rv, CHANRCV},
@@ -165,7 +166,7 @@ threadmain(int argc, char **argv)
draw(screen, screen->r, Inormbg, nil, ZP);
redraw(ov);
drawscrollbar();
- flushimage(display, 1);
+ flushimage(display, 1);
break;
case KBD:
if (kv == 0x7f) shutdown(); /* delete */
@@ -202,15 +203,13 @@ threadmain(int argc, char **argv)
if (rich.objects->count > 0) {
Object *obj;
int n;
- char *p;
obj = nil;
n = runelen(kv);
qlock(rich.l);
- p = arraygrow(rich.text, n);
- runetochar(p, &kv);
+ arraygrow(rich.text, n, &kv);
qunlock(rich.l);
@@ -221,19 +220,19 @@ threadmain(int argc, char **argv)
dv = arraycreate(sizeof(char),
rich.text->count - olast->offset, nil);
- arraygrow(dv, rich.text->count - olast->offset);
- memcpy(dv->p,
- arrayget(rich.text, olast->offset),
- rich.text->count - olast->offset);
+ arraygrow(dv, rich.text->count - olast->offset,
+ arrayget(rich.text, olast->offset, nil));
+
+ nbsend(dctl->rc, &dv);
/* dv is freed on recv end */
qunlock(rich.l);
- obj = mkobjectftree(olast, fsctl->tree->root);
- olast = newobject(&rich, nil, 0);
-
- nbsend(dctl->rc, &dv);
+ obj = objectcreate();
+ mkobjectftree(obj, fsctl->tree->root);
+ objinsertbeforelast(obj);
+ olast->offset = rich.text->count;
}
nbsend(redrawc, &obj);
}
@@ -338,17 +337,16 @@ Font *
getfont(Array *fonts, char *name)
{
int i;
- Font *newfont, **fp;
+ Font *newfont, *fnt;
for (i = 0; i < fonts->count; i++){
- fp = arrayget(fonts, i);
- if (strcmp((*fp)->name, name) == 0) return *fp;
+ arrayget(fonts, i, &fnt);
+ if (strcmp(fnt->name, name) == 0) return fnt;
}
if ((newfont = openfont(display, name)) == nil) {
fprint(2, "%r\n");
newfont = font;
} else {
- fp = arraygrow(fonts, 1);
- *fp = newfont;
+ arraygrow(fonts, 1, &newfont);
}
return newfont;
}
@@ -376,42 +374,33 @@ fauxalloc(Object *obj, Array *data, int type)
}
Object *
-newobject(Rich *rich, char *p, long n)
+objectcreate(void)
{
- Object *obj, **op, **old;
- qlock(rich->l);
-
- old = (rich->objects->count > 0) ?
- arrayget(rich->objects, rich->objects->count - 1) : nil;
-
- op = arraygrow(rich->objects, 1);
-
+ Object *obj;
obj = mallocz(sizeof(Object), 1);
- *op = obj;
-
- if ((old != nil) && (*old != nil)) {
- (*old)->next = obj;
- obj->prev = *old;
- }
-
- obj->offset = rich->text->count;
-
obj->font = font;
- obj->text = rich->text;
-
obj->dlink = arraycreate(sizeof(char), 4096, nil);
obj->dimage = arraycreate(sizeof(char), 4096, nil);
+ return obj;
+}
- if (p != nil) {
- char *pp;
+void
+objectfree(Object *obj)
+{
+ /* TODO: following should be in separate function rmobjectftree
- pp = arraygrow(rich->text, n);
- memcpy(pp, p, n);
- };
+ removefile(obj->ftext);
+ removefile(obj->ffont);
+ removefile(obj->flink);
+ removefile(obj->fimage);
+ removefile(obj->dir);
- qunlock(rich->l);
- return obj;
+ free(obj->id); */
+
+ /* TODO: why is this not working? */
+ arrayfree(obj->dlink);
+ arrayfree(obj->dimage);
}
Object *
@@ -442,6 +431,7 @@ mkobjectftree(Object *obj, File *root)
obj->fimage = createfile(obj->dir, "image", "richterm", 0666, auximage);
qunlock(rich.l);
+
return obj;
}
@@ -523,42 +513,18 @@ resize(void)
}
void
-objectfree(void *v)
-{
- Object *op;
- op = v;
-
- removefile(op->ftext);
- removefile(op->ffont);
- removefile(op->flink);
- removefile(op->fimage);
- removefile(op->dir);
-
- /* TODO: why is this not working? */
- free(op->id);
-
-// free(op->dtext->p);
-// free(op->dfont->p);
-// free(op->dlink->p);
-// free(op->dimage->p);
-
- free(op);
-}
-
-void
mpaste(Rich *)
{
int fd;
long n;
- char buf[4096], *p;
+ char buf[4096];
if ((fd = open("/dev/snarf", OREAD)) > 0) {
while((n = read(fd, buf, sizeof(buf))) > 0) {
- p = arraygrow(rich.text, n);
- memcpy(p, buf, n);
+ arraygrow(rich.text, n, buf);
}
if (n < 0) fprint(2, "mpaste: %r\n");
close(fd);
- nbsend(redrawc, &olast);;
+ nbsend(redrawc, &olast);
}
}
@@ -569,7 +535,7 @@ msnarf(Rich *)
long n;
if ((rich.selmin < rich.selmax) &&
((fd = open("/dev/snarf", OWRITE)) > 0)) {
- n = write(fd, arrayget(rich.text, rich.selmin),
+ n = write(fd, arrayget(rich.text, rich.selmin, nil),
rich.selmax - rich.selmin);
if (n < rich.selmax - rich.selmin) fprint(2, "msnarf: %r\n");
close(fd);
@@ -590,7 +556,7 @@ mplumb(Rich *)
"text",
nil,
rich.selmax - rich.selmin,
- arrayget(rich.text, rich.selmin)
+ arrayget(rich.text, rich.selmin, nil)
};
plumbsend(pd, &m);
close(pd);
@@ -623,7 +589,7 @@ drawchar(Object *obj, long *n, Point *cur)
bg = ((*n >= rich.selmin) && (*n < rich.selmax)) ?
Iselbg : Inormbg;
- p = arrayget(rich.text, *n);
+ p = arrayget(rich.text, *n, nil);
if (p == nil) return;
@@ -679,13 +645,16 @@ drawobject(Object *obj, Point *cur)
}
obj->startpt = *cur;
+
obj->nextlinept = Pt(0, cur->y + obj->font->height);
if ((obj->prev != nil) && (cur->x != 0)) {
if (obj->nextlinept.y < obj->prev->nextlinept.y)
obj->nextlinept.y = obj->prev->nextlinept.y;
}
+
if (obj->next == nil) n = rich.text->count;
else n = obj->next->offset;
+
for (i = obj->offset; i < n;) {
drawchar(obj, &i, cur);
}
@@ -696,20 +665,22 @@ void
redraw(Object *)
{
/* TODO: only redraw starting from arg-supplied *obj */
+ /* TODO: flush all messages in redrawc channel before proceeding */
Point cur;
- Object **op;
+ Object *obj;
long i;
+ obj = nil;
cur = ZP;
qlock(rich.l);
- qlock(rich.text->l);
+
for (i = 0; i < rich.objects->count; i++) {
- op = arrayget(rich.objects, i);
- drawobject(*op, &cur);
+ if (arrayget(rich.objects, i, &obj) == nil)
+ sysfatal("redraw: %r");
+ drawobject(obj, &cur);
}
rich.page.max = cur;
- qunlock(rich.text->l);
qunlock(rich.l);
}
@@ -717,12 +688,11 @@ Object *
getobj(Point xy)
{
long i;
- Object **op, *obj;
+ Object *obj;
Point prevlinept;
xy = subpt(xy, subpt(rich.page.r.min, rich.page.scroll));
for (i = 0; i < rich.objects->count; i++) {
- op = arrayget(rich.objects, i);
- obj = *op;
+ arrayget(rich.objects, i, &obj);
prevlinept = ( obj->prev == nil) ? ZP : obj->prev->nextlinept;
if (((obj->startpt.y == obj->endpt.y) &&
@@ -783,3 +753,16 @@ getsel(Point xy)
}
return li;
}
+
+void
+objinsertbeforelast(Object *obj)
+{
+ qlock(rich.l);
+ obj->offset = olast->offset;
+ arrayinsert(rich.objects, rich.objects->count - 1, 1, &obj);
+ obj->next = olast;
+ obj->prev = olast->prev;
+ if (olast->prev != nil) olast->prev->next = obj;
+ olast->prev = obj;
+ qunlock(rich.l);
+}
diff --git a/richterm.h b/richterm.h
@@ -11,15 +11,17 @@ struct Object {
File *flink;
File *fimage;
char *id;
+
Array *dlink;
Array *dimage;
Font *font;
Image *image;
- Array *text;
long offset;
+
Object *next;
Object *prev;
+
Point startpt;
Point endpt;
Point nextlinept;
@@ -29,9 +31,11 @@ extern Object *olast;
void redraw(Object *);
+Object * objectcreate(void);
Object * mkobjectftree(Object *, File *);
+void objinsertbeforelast(Object *);
void rmobjectftree(Object *);
-void objectfree(void *);
+void objectfree(Object *);
extern Array *fonts;
@@ -62,7 +66,6 @@ extern Rich rich;
void drawpage(Image *, Rich *);
void generatepage(Rich *, long);
-Object * newobject(Rich *, char *, long);
typedef struct Devfsctl Devfsctl;