ref: 56f73b3e05d5a3866377f1c20dbf2ad35804772d
parent: 9b14a2f3b443a8bd615551cb2320829d134650bd
author: kvik <kvik@a-b.xyz>
date: Sun May 30 11:13:03 EDT 2021
Use Strings for paths This reduces the amount of obnoxious allocations and copying.
--- a/qmap.c
+++ b/qmap.c
@@ -51,8 +51,8 @@
#include <u.h>
#include <libc.h>
-#include <thread.h>
-#include "unionfs.h"
+
+void *emalloc(ulong);
#define mask(v) ((1ull << v) - 1)
--- a/unionfs.c
+++ b/unionfs.c
@@ -1,5 +1,6 @@
#include <u.h>
#include <libc.h>
+#include <String.h>
#include <fcall.h>
#include <thread.h>
#include <9p.h>
@@ -57,8 +58,8 @@
if(f->uid) free(f->uid);
if(f->gid) free(f->gid);
if(f->muid) free(f->muid);
- if(f->path) free(f->path);
- if(f->realpath) free(f->realpath);
+ if(f->path) s_free(f->path);
+ if(f->realpath) s_free(f->realpath);
if(f->fd != -1) close(f->fd);
if(f->dirs) free(f->dirs);
if(f->mtpt) mtptfree(f->mtpt);
@@ -74,9 +75,17 @@
a->mode = b->mode;
a->mtime = b->mtime;
a->atime = b->atime;
+ if(a->name)
+ free(a->name);
a->name = estrdup(b->name);
+ if(a->uid)
+ free(a->uid);
a->uid = estrdup(b->uid);
+ if(a->gid)
+ free(a->gid);
a->gid = estrdup(b->gid);
+ if(a->muid)
+ free(a->muid);
a->muid = estrdup(b->muid);
}
@@ -98,8 +107,8 @@
f->dev = 0xFFFFFFFFFFFFFFFF;
f->qid = (Qid){0, 0, QTDIR};
f->qid = qencode(f);
- f->path = estrdup(f->name);
- f->realpath = estrdup(f->name);
+ f->path = s_copy(f->name);
+ f->realpath = s_copy(f->name);
r->fid->aux = f;
r->fid->qid = f->qid;
@@ -107,22 +116,14 @@
respond(r, nil);
}
-char*
-mkpath(char *a0, ...)
+String*
+walk(String *s, char *n0, char *n1)
{
- va_list args;
- int i;
- char *a;
- char *ap[] = {a0, "", ""};
-
- va_start(args, a0);
- for(i = 1; (a = va_arg(args, char*)) != nil && i < 3; i++)
- ap[i] = a;
- va_end(args);
- if((a = smprint("%s/%s/%s", ap[0], ap[1], ap[2])) == nil)
- sysfatal("smprint: %r");
-
- return cleanname(a);
+ s_putc(s, '/'); s_append(s, n0);
+ s_putc(s, '/'); s_append(s, n1);
+ cleanname(s->base);
+ s->ptr = s->base + strlen(s->base);
+ return s;
}
char*
@@ -133,45 +134,30 @@
f = filenew();
dircopy(f, parent);
- f->qid = parent->qid;
- f->path = estrdup(parent->path);
- f->realpath = estrdup(parent->realpath);
+ f->path = s_clone(parent->path);
+ f->realpath = s_clone(parent->realpath);
newfid->aux = f;
return nil;
}
char*
-walkto(Fid *fid, char *name, void *aux)
+walkto(Fid *fid, char *name, void *)
{
- Req *r;
Dir *d;
FILE *f;
- char *path, *realpath;
- int i, *nwalk;
+ int i;
- r = aux;
f = fid->aux;
- nwalk = r->aux;
- path = mkpath(f->path, name, nil);
+ walk(f->path, name, nil);
for(i = 0; i < nbranch; i++){
- realpath = mkpath(branch[i].root, path, nil);
- if((d = dirstat(realpath)) == nil)
+ s_reset(f->realpath);
+ walk(f->realpath, branch[i].root, s_to_c(f->path));
+ if((d = dirstat(s_to_c(f->realpath))) == nil)
continue;
- if(*nwalk == r->ifcall.nwname){
- filefree(f);
- f = filenew();
- dircopy(f, d);
- }else{
- free(f->path);
- free(f->realpath);
- }
+ dircopy(f, d);
f->qid = qencode(d);
free(d);
- f->path = path;
- f->realpath = realpath;
- fid->aux = f;
fid->qid = f->qid;
- *nwalk = *nwalk + 1;
return nil;
}
return "not found";
@@ -180,10 +166,6 @@
void
fswalk(Req *r)
{
- int nwalk;
-
- nwalk = 1;
- r->aux = &nwalk;
walkandclone(r, walkto, clone, r);
}
@@ -201,7 +183,7 @@
Fcall *T, *R;
FILE *f;
usize i;
- char *path;
+ String *path;
Dir *d;
T = &r->ifcall;
@@ -211,22 +193,24 @@
srvrelease(&thefs);
if(f->mode & DMDIR){
f->mtpt = mtptgrab();
+ path = s_new();
for(i = 0; i < nbranch; i++){
- path = mkpath(branch[i].root, f->path, nil);
- if((d = dirstat(path)) != nil){
+ s_reset(path);
+ walk(path, branch[i].root, s_to_c(f->path));
+ if((d = dirstat(s_to_c(path))) != nil){
if(d->mode & DMDIR)
- if(bind(path, f->mtpt->path, MAFTER) == -1)
+ if(bind(s_to_c(path), f->mtpt->path, MAFTER) == -1)
sysfatal("bind: %r");
free(d);
}
- free(path);
}
+ s_free(path);
if((f->fd = open(f->mtpt->path, T->mode)) < 0){
responderror(r);
goto done;
}
}else{
- if((f->fd = open(f->realpath, T->mode)) < 0){
+ if((f->fd = open(s_to_c(f->realpath), T->mode)) < 0){
responderror(r);
goto done;
}
@@ -244,7 +228,7 @@
f = r->fid->aux;
srvrelease(&thefs);
- if(remove(f->path) < 0){
+ if(remove(s_to_c(f->path)) < 0){
responderror(r);
goto done;
}
@@ -357,7 +341,7 @@
void
fscreate(Req *r)
{
- char *path, *realpath;
+ String *realpath;
usize i;
Dir *d;
Fcall *T, *R;
@@ -372,40 +356,35 @@
for(i = 0; i < nbranch; i++)
if(branch[i].create == 1)
break;
- path = mkpath(branch[i].root, parent->path, nil);
- if(mkdirp(path) < 0){
+ realpath = s_new();
+ walk(realpath, branch[i].root, s_to_c(parent->path));
+ if(mkdirp(s_to_c(realpath)) < 0){
+error:
+ s_free(realpath);
responderror(r);
- goto done;
+ srvacquire(&thefs);
+ return;
}
- realpath = mkpath(path, T->name, nil);
- free(path);
- if((fd = create(realpath, T->mode, T->perm)) < 0){
- free(realpath);
- responderror(r);
- goto done;
- }
- if((d = dirfstat(fd)) == nil){
- free(realpath);
- responderror(r);
- goto done;
- }
+ walk(realpath, T->name, nil);
+ if((fd = create(s_to_c(realpath), T->mode, T->perm)) < 0)
+ goto error;
+ if((d = dirfstat(fd)) == nil)
+ goto error;
f = filenew();
dircopy(f, d);
f->fd = fd;
f->qid = qencode(d);
- f->path = mkpath(parent->path, T->name, nil);
- f->realpath = realpath;
free(d);
+ f->path = walk(s_clone(parent->path), T->name, nil);
+ f->realpath = realpath;
filefree(parent);
r->fid->aux = f;
R->qid = f->qid;
respond(r, nil);
-done:
srvacquire(&thefs);
}
-
void
fsstat(Req *r)
{
@@ -421,7 +400,7 @@
FILE *f = r->fid->aux;
srvrelease(&thefs);
- if(dirwstat(f->realpath, &r->d) < 0){
+ if(dirwstat(s_to_c(f->realpath), &r->d) < 0){
responderror(r);
goto done;
}
@@ -447,7 +426,7 @@
main(int argc, char *argv[])
{
int c, i, mflag, stdio;
- char *mountat, *srvname, *path, *p;
+ char *mountat, *srvname, *path;
Dir *d;
Branch *b;
@@ -497,18 +476,14 @@
continue;
}
- path = mkpath(argv[i], nil);
+ path = cleanname(argv[i]);
if((d = dirstat(path)) == nil){
fprint(2, "%s: %s does not exist, skipping\n", argv0, path);
- free(path);
continue;
}
free(d);
- if(mountat && strcmp(path, mountat) == 0){
- p = pivot(path);
- free(path);
- path = p;
- }
+ if(mountat && strcmp(path, mountat) == 0)
+ path = pivot(path);
b->root = path;
b->create = c == 1 ? c : 0;
b++;
--- a/unionfs.h
+++ b/unionfs.h
@@ -9,8 +9,8 @@
struct FILE {
Dir;
- char *realpath;
- char *path;
+ String *realpath;
+ String *path;
int fd;
Mtpt *mtpt;
--- a/util.c
+++ b/util.c
@@ -1,7 +1,5 @@
#include <u.h>
#include <libc.h>
-#include <thread.h>
-#include "unionfs.h"
void
usage(void)