Esempio n. 1
0
int hash_insert(struct hash *hash, const char *key, void *mem, free_func *freer)
{
    unsigned i, h;
    struct hash_bucket *bucket = malloc(sizeof *bucket), *iter;
    if (!bucket)
        return -1;

    bucket->key = string_dup(key);
    if (!bucket->key) {
        free(bucket);
        return -1;
    }
    bucket->mem = mem;

    h = hashstr(key, hash->max_size);

    for (i = 0; i < hash->buckets[h].length; ++i) {
        darray_at(&hash->buckets[h], i, (void **)&iter);
        if (!strcmp(iter->key, bucket->key)) {
            if (freer)
                freer(hash->buckets[h].mem[i]);
            hash->buckets[h].mem[i] = bucket;
            return 0;
        }
    }

    darray_push_back(&hash->buckets[h], bucket);

    return 0;
}
Esempio n. 2
0
void darray_pop_back(struct darray *arr, free_func *freer)
{
    if (freer)
        freer(arr->mem[--arr->length]);
    else
        arr->length--;
}
Esempio n. 3
0
void pqueue_uninit(struct pqueue *pq, free_func *freer)
{
    unsigned i;
    if (freer)
        for (i = 1; i < pq->length + 1; ++i)
            freer(pq->mem[i]);
    free(pq->mem);
}
Esempio n. 4
0
void darray_remove(struct darray *arr, free_func *freer, int pos)
{
    if (freer)
        freer(arr->mem[pos]);

    arr->length--;
    memmove(&arr->mem[pos], &arr->mem[pos + 1], sizeof *arr->mem * (arr->length - pos));
}
Esempio n. 5
0
void stack_pop(struct stack *s, free_func *freer)
{
    struct stack_node *tofree = s->top;
    s->top = s->top->below;
    if (freer)
        freer(tofree->mem);
    free(tofree);
}
Esempio n. 6
0
void queue_dequeue(struct queue *q, free_func *freer)
{
    struct queue_node *tofree = q->bot;
    q->bot = q->bot->next;
    if (!q->bot)
        q->top = NULL;
    if (freer)
        freer(tofree->mem);
    free(tofree);
}
Esempio n. 7
0
void hash_uninit(struct hash *hash, free_func *freer)
{
    unsigned i, j;
    struct hash_bucket *iter;

    for (i = 0; i < hash->max_size; ++i) {
        for (j = 0; j < hash->buckets[i].length; ++j) {
            darray_at(&hash->buckets[i], j, (void **)&iter);
            free(iter->key);
            if (freer)
                freer(iter->mem);
        }
        darray_uninit(&hash->buckets[i], free);
    }

    free(hash->buckets);
}
Esempio n. 8
0
void
guestfs_set_private (guestfs_h *g, const char *key, void *data)
{
  if (g->pda == NULL) {
    g->pda = hash_initialize (16, NULL, hasher, comparator, freer);
    if (g->pda == NULL)
      g->abort_cb ();
  }

  struct pda_entry *new_entry = safe_malloc (g, sizeof *new_entry);
  new_entry->key = safe_strdup (g, key);
  new_entry->data = data;

  struct pda_entry *old_entry = hash_delete (g->pda, new_entry);
  freer (old_entry);

  struct pda_entry *entry = hash_insert (g->pda, new_entry);
  if (entry == NULL)
    g->abort_cb ();
  assert (entry == new_entry);
}
Esempio n. 9
0
void pqueue_pop_max(struct pqueue *pq, free_func *freer, comp_func *comp)
{
    unsigned i, child;
    void *tofree = pq->mem[1];
    void *last = pq->mem[pq->length--];
    if (freer)
        freer(tofree);

    for (i = 1; i * 2 <= pq->length; i = child) {
        child = i * 2;
        if (child != pq->length && comp(pq->mem[child], pq->mem[child + 1]) < 0)
            child++;

        if (comp(last, pq->mem[child]) < 0)
            pq->mem[i] = pq->mem[child];
        else
            break;
    }

    pq->mem[i] = last;
}
Esempio n. 10
0
static const struct stat *
lsc_lookup (guestfs_h *g, const char *pathname)
{
  const struct entry_common key = { .pathname = (char *) pathname };
  struct lsc_entry *entry;
  time_t now;

  time (&now);

  entry = hash_lookup (g->lsc_ht, &key);
  if (entry && entry->c.timeout >= now)
    return &entry->statbuf;
  else
    return NULL;
}

static const struct guestfs_xattr_list *
xac_lookup (guestfs_h *g, const char *pathname)
{
  const struct entry_common key = { .pathname = (char *) pathname };
  struct xac_entry *entry;
  time_t now;

  time (&now);

  entry = hash_lookup (g->xac_ht, &key);
  if (entry && entry->c.timeout >= now)
    return entry->xattrs;
  else
    return NULL;
}

static const char *
rlc_lookup (guestfs_h *g, const char *pathname)
{
  const struct entry_common key = { .pathname = (char *) pathname };
  struct rlc_entry *entry;
  time_t now;

  time (&now);

  entry = hash_lookup (g->rlc_ht, &key);
  if (entry && entry->c.timeout >= now)
    return entry->link;
  else
    return NULL;
}

static void
gen_remove (Hash_table *ht, const char *pathname, Hash_data_freer freer)
{
  const struct entry_common key = { .pathname = (char *) pathname };
  struct entry_common *entry;

  entry = hash_delete (ht, &key);

  freer (entry);
}

static void
dir_cache_invalidate (guestfs_h *g, const char *path)
{
  gen_remove (g->lsc_ht, path, lsc_free);
  gen_remove (g->xac_ht, path, xac_free);
  gen_remove (g->rlc_ht, path, rlc_free);
}

#else /* !HAVE_FUSE */

#define FUSE_NOT_SUPPORTED()                                            \
  NOT_SUPPORTED (g, -1, _("FUSE is not supported in this build of "     \
                          "libguestfs because libfuse was not found "   \
                          "when libguestfs was compiled"))

int
guestfs_impl_mount_local (guestfs_h *g, const char *localmountpoint,
			  const struct guestfs_mount_local_argv *optargs)
{
  FUSE_NOT_SUPPORTED ();
}

int
guestfs_impl_mount_local_run (guestfs_h *g)
{
  FUSE_NOT_SUPPORTED ();
}

int
guestfs_impl_umount_local (guestfs_h *g,
			   const struct guestfs_umount_local_argv *optargs)
{
  FUSE_NOT_SUPPORTED ();
}
Esempio n. 11
0
static const struct stat *
lsc_lookup (guestfs_h *g, const char *pathname)
{
  const struct lsc_entry key = { .pathname = (char *) pathname };
  struct lsc_entry *entry;
  time_t now;

  time (&now);

  entry = hash_lookup (g->lsc_ht, &key);
  if (entry && entry->timeout >= now)
    return &entry->statbuf;
  else
    return NULL;
}

static const struct guestfs_xattr_list *
xac_lookup (guestfs_h *g, const char *pathname)
{
  const struct xac_entry key = { .pathname = (char *) pathname };
  struct xac_entry *entry;
  time_t now;

  time (&now);

  entry = hash_lookup (g->xac_ht, &key);
  if (entry && entry->timeout >= now)
    return entry->xattrs;
  else
    return NULL;
}

static const char *
rlc_lookup (guestfs_h *g, const char *pathname)
{
  const struct rlc_entry key = { .pathname = (char *) pathname };
  struct rlc_entry *entry;
  time_t now;

  time (&now);

  entry = hash_lookup (g->rlc_ht, &key);
  if (entry && entry->timeout >= now)
    return entry->link;
  else
    return NULL;
}

static void
lsc_remove (Hash_table *ht, const char *pathname, Hash_data_freer freer)
{
  const struct lsc_entry key = { .pathname = (char *) pathname };
  struct lsc_entry *entry;

  entry = hash_delete (ht, &key);

  freer (entry);
}

static void
dir_cache_invalidate (guestfs_h *g, const char *path)
{
  lsc_remove (g->lsc_ht, path, lsc_free);
  lsc_remove (g->xac_ht, path, xac_free);
  lsc_remove (g->rlc_ht, path, rlc_free);
}

#else /* !HAVE_FUSE */

int
guestfs__mount_local (guestfs_h *g, const char *localmountpoint,
                      const struct guestfs_mount_local_argv *optargs)
{
  guestfs_error_errno (g, ENOTSUP, _("FUSE not supported"));
  return -1;
}

int
guestfs__mount_local_run (guestfs_h *g)
{
  guestfs_error_errno (g, ENOTSUP, _("FUSE not supported"));
  return -1;
}

int
guestfs__umount_local (guestfs_h *g,
                       const struct guestfs_umount_local_argv *optargs)
{
  guestfs_error_errno (g, ENOTSUP, _("FUSE not supported"));
  return -1;
}