Commit ea995d69 authored by Poul-Henning Kamp's avatar Poul-Henning Kamp

Only emit the '-' line when the cluster is empty.

parent 9bf8ee9c
...@@ -106,6 +106,7 @@ struct vsmw_cluster { ...@@ -106,6 +106,7 @@ struct vsmw_cluster {
void *ptr; void *ptr;
size_t next; size_t next;
int refs; int refs;
int named;
}; };
struct vsmwseg { struct vsmwseg {
...@@ -221,7 +222,7 @@ vsmw_addseg(struct vsmw *vsmw, struct vsmwseg *seg) ...@@ -221,7 +222,7 @@ vsmw_addseg(struct vsmw *vsmw, struct vsmwseg *seg)
/*--------------------------------------------------------------------*/ /*--------------------------------------------------------------------*/
static void static void
vsmw_delseg(struct vsmw *vsmw, struct vsmwseg *seg, int fixidx) vsmw_delseg(struct vsmw *vsmw, struct vsmwseg *seg)
{ {
char *t = NULL; char *t = NULL;
int fd; int fd;
...@@ -234,11 +235,10 @@ vsmw_delseg(struct vsmw *vsmw, struct vsmwseg *seg, int fixidx) ...@@ -234,11 +235,10 @@ vsmw_delseg(struct vsmw *vsmw, struct vsmwseg *seg, int fixidx)
VTAILQ_REMOVE(&vsmw->segs, seg, list); VTAILQ_REMOVE(&vsmw->segs, seg, list);
vsmw->nsegs--; vsmw->nsegs--;
if (vsmw->nsubs * 2 < vsmw->nsegs || !fixidx) { if (vsmw->nsubs < 10 || vsmw->nsubs * 2 < vsmw->nsegs) {
vsmw_append_record(vsmw, seg, '-'); vsmw_append_record(vsmw, seg, '-');
vsmw->nsubs++; vsmw->nsubs++;
} else { } else {
vsmw->nsubs = 0;
vsmw_mkent(vsmw, vsmw->idx); vsmw_mkent(vsmw, vsmw->idx);
REPLACE(t, VSB_data(vsmw->vsb)); REPLACE(t, VSB_data(vsmw->vsb));
AN(t); AN(t);
...@@ -254,6 +254,7 @@ vsmw_delseg(struct vsmw *vsmw, struct vsmwseg *seg, int fixidx) ...@@ -254,6 +254,7 @@ vsmw_delseg(struct vsmw *vsmw, struct vsmwseg *seg, int fixidx)
closefd(&fd); closefd(&fd);
AZ(renameat(vsmw->vdirfd, t, vsmw->vdirfd, vsmw->idx)); AZ(renameat(vsmw->vdirfd, t, vsmw->vdirfd, vsmw->idx));
REPLACE(t, NULL); REPLACE(t, NULL);
vsmw->nsubs = 0;
} }
REPLACE(seg->class, NULL); REPLACE(seg->class, NULL);
REPLACE(seg->id, NULL); REPLACE(seg->id, NULL);
...@@ -315,6 +316,8 @@ VSMW_NewCluster(struct vsmw *vsmw, size_t len, const char *pfx) ...@@ -315,6 +316,8 @@ VSMW_NewCluster(struct vsmw *vsmw, size_t len, const char *pfx)
seg->cluster = vc; seg->cluster = vc;
REPLACE(seg->class, ""); REPLACE(seg->class, "");
REPLACE(seg->id, ""); REPLACE(seg->id, "");
vc->refs++;
vc->named = 1;
vsmw_addseg(vsmw, seg); vsmw_addseg(vsmw, seg);
vsmw_do_unlock(); vsmw_do_unlock();
...@@ -322,28 +325,19 @@ VSMW_NewCluster(struct vsmw *vsmw, size_t len, const char *pfx) ...@@ -322,28 +325,19 @@ VSMW_NewCluster(struct vsmw *vsmw, size_t len, const char *pfx)
} }
static void static void
vsmw_DestroyCluster_locked(struct vsmw *vsmw, struct vsmw_cluster **vsmcp) vsmw_DestroyCluster_locked(struct vsmw *vsmw, struct vsmw_cluster *vc)
{ {
struct vsmw_cluster *vc;
CHECK_OBJ_NOTNULL(vsmw, VSMW_MAGIC); CHECK_OBJ_NOTNULL(vsmw, VSMW_MAGIC);
TAKE_OBJ_NOTNULL(vc, vsmcp, VSMW_CLUSTER_MAGIC); CHECK_OBJ_NOTNULL(vc, VSMW_CLUSTER_MAGIC);
AZ(vc->refs);
if (vc->cseg != NULL) {
/*
* Backends go on the cool list, so the VGC cluster is
* destroyed before they are. Solve this by turning the
* cluster into an anonymous cluster which dies with the
* refcount on it.
*/
vsmw_delseg(vsmw, vc->cseg, 1);
vc->cseg = NULL;
if (vc->refs > 0)
return;
}
AZ(munmap(vc->ptr, vc->len)); AZ(munmap(vc->ptr, vc->len));
if (vc->named)
vsmw_delseg(vsmw, vc->cseg);
vc->cseg = 0;
AZ(vc->refs);
VTAILQ_REMOVE(&vsmw->clusters, vc, list); VTAILQ_REMOVE(&vsmw->clusters, vc, list);
if (unlinkat(vsmw->vdirfd, vc->fn, 0)) if (unlinkat(vsmw->vdirfd, vc->fn, 0))
assert (errno == ENOENT); assert (errno == ENOENT);
...@@ -354,9 +348,13 @@ vsmw_DestroyCluster_locked(struct vsmw *vsmw, struct vsmw_cluster **vsmcp) ...@@ -354,9 +348,13 @@ vsmw_DestroyCluster_locked(struct vsmw *vsmw, struct vsmw_cluster **vsmcp)
void void
VSMW_DestroyCluster(struct vsmw *vsmw, struct vsmw_cluster **vsmcp) VSMW_DestroyCluster(struct vsmw *vsmw, struct vsmw_cluster **vsmcp)
{ {
struct vsmw_cluster *vc;
TAKE_OBJ_NOTNULL(vc, vsmcp, VSMW_CLUSTER_MAGIC);
vsmw_do_lock(); vsmw_do_lock();
vsmw_DestroyCluster_locked(vsmw, vsmcp); if (--vc->refs == 0)
vsmw_DestroyCluster_locked(vsmw, vc);
vsmw_do_unlock(); vsmw_do_unlock();
} }
...@@ -371,7 +369,6 @@ VSMW_Allocv(struct vsmw *vsmw, struct vsmw_cluster *vc, ...@@ -371,7 +369,6 @@ VSMW_Allocv(struct vsmw *vsmw, struct vsmw_cluster *vc,
vsmw_do_lock(); vsmw_do_lock();
CHECK_OBJ_NOTNULL(vsmw, VSMW_MAGIC); CHECK_OBJ_NOTNULL(vsmw, VSMW_MAGIC);
(void)vc;
ALLOC_OBJ(seg, VSMWSEG_MAGIC); ALLOC_OBJ(seg, VSMWSEG_MAGIC);
AN(seg); AN(seg);
...@@ -431,11 +428,13 @@ VSMW_Free(struct vsmw *vsmw, void **pp) ...@@ -431,11 +428,13 @@ VSMW_Free(struct vsmw *vsmw, void **pp)
*pp = NULL; *pp = NULL;
cp = seg->cluster; cp = seg->cluster;
CHECK_OBJ_NOTNULL(cp, VSMW_CLUSTER_MAGIC);
assert(cp->refs > 0);
vsmw_delseg(vsmw, seg, 1); vsmw_delseg(vsmw, seg);
if (!--cp->refs && cp->cseg == NULL) if (!--cp->refs)
vsmw_DestroyCluster_locked(vsmw, &cp); vsmw_DestroyCluster_locked(vsmw, cp);
vsmw_do_unlock(); vsmw_do_unlock();
} }
...@@ -486,7 +485,7 @@ VSMW_Destroy(struct vsmw **pp) ...@@ -486,7 +485,7 @@ VSMW_Destroy(struct vsmw **pp)
vsmw_do_lock(); vsmw_do_lock();
TAKE_OBJ_NOTNULL(vsmw, pp, VSMW_MAGIC); TAKE_OBJ_NOTNULL(vsmw, pp, VSMW_MAGIC);
VTAILQ_FOREACH_SAFE(seg, &vsmw->segs, list, s2) VTAILQ_FOREACH_SAFE(seg, &vsmw->segs, list, s2)
vsmw_delseg(vsmw, seg, 0); vsmw_delseg(vsmw, seg);
if (unlinkat(vsmw->vdirfd, vsmw->idx, 0)) if (unlinkat(vsmw->vdirfd, vsmw->idx, 0))
assert (errno == ENOENT); assert (errno == ENOENT);
REPLACE(vsmw->idx, NULL); REPLACE(vsmw->idx, NULL);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment