struct au_dinfo *au_di_alloc(struct super_block *sb, unsigned int lsc) { struct au_dinfo *dinfo; int nbr, i; dinfo = au_cache_alloc_dinfo(); if (unlikely(!dinfo)) goto out; nbr = au_sbend(sb) + 1; if (nbr <= 0) nbr = 1; dinfo->di_hdentry = kcalloc(nbr, sizeof(*dinfo->di_hdentry), GFP_NOFS); if (dinfo->di_hdentry) { au_rw_write_lock_nested(&dinfo->di_rwsem, lsc); dinfo->di_bstart = -1; dinfo->di_bend = -1; dinfo->di_bwh = -1; dinfo->di_bdiropq = -1; dinfo->di_tmpfile = 0; for (i = 0; i < nbr; i++) dinfo->di_hdentry[i].hd_id = -1; goto out; } au_cache_free_dinfo(dinfo); dinfo = NULL; out: return dinfo; }
int au_alloc_dinfo(struct dentry *dentry) { struct au_dinfo *dinfo; struct super_block *sb; int nbr; dinfo = au_cache_alloc_dinfo(); if (unlikely(!dinfo)) goto out; sb = dentry->d_sb; nbr = au_sbend(sb) + 1; if (nbr <= 0) nbr = 1; dinfo->di_hdentry = kcalloc(nbr, sizeof(*dinfo->di_hdentry), GFP_NOFS); if (unlikely(!dinfo->di_hdentry)) goto out_dinfo; atomic_set(&dinfo->di_generation, au_sigen(sb)); /* smp_mb(); */ /* atomic_set */ au_rw_init_wlock_nested(&dinfo->di_rwsem, AuLsc_DI_CHILD); dinfo->di_bstart = -1; dinfo->di_bend = -1; dinfo->di_bwh = -1; dinfo->di_bdiropq = -1; dentry->d_fsdata = dinfo; dentry->d_op = &aufs_dop; return 0; /* success */ out_dinfo: au_cache_free_dinfo(dinfo); out: return -ENOMEM; }
static void aufs_d_release(struct dentry *dentry) { struct au_dinfo *dinfo; aufs_bindex_t bend, bindex; dinfo = dentry->d_fsdata; if (!dinfo) return; /* dentry may not be revalidated */ bindex = dinfo->di_bstart; if (bindex >= 0) { struct au_hdentry *p; bend = dinfo->di_bend; p = dinfo->di_hdentry + bindex; while (bindex++ <= bend) { if (p->hd_dentry) au_hdput(p); p++; } } kfree(dinfo->di_hdentry); AuRwDestroy(&dinfo->di_rwsem); au_cache_free_dinfo(dinfo); au_hin_di_reinit(dentry); }
void au_di_free(struct au_dinfo *dinfo) { struct au_hdentry *p; aufs_bindex_t bend, bindex; /* dentry may not be revalidated */ bindex = dinfo->di_bstart; if (bindex >= 0) { bend = dinfo->di_bend; p = dinfo->di_hdentry + bindex; while (bindex++ <= bend) au_hdput(p++); } kfree(dinfo->di_hdentry); au_cache_free_dinfo(dinfo); }
int au_alloc_dinfo(struct dentry *dentry) { struct au_dinfo *dinfo; struct super_block *sb; int nbr; LKTRTrace("%.*s\n", AuDLNPair(dentry)); AuDebugOn(dentry->d_fsdata); dinfo = au_cache_alloc_dinfo(); if (dinfo) { sb = dentry->d_sb; nbr = au_sbend(sb) + 1; if (nbr <= 0) nbr = 1; dinfo->di_hdentry = kcalloc(nbr, sizeof(*dinfo->di_hdentry), GFP_NOFS); if (dinfo->di_hdentry) { au_h_dentry_init_all(dinfo->di_hdentry, nbr); atomic_set(&dinfo->di_generation, au_sigen(sb)); /* smp_mb(); */ /* atomic_set */ au_rw_init_wlock_nested(&dinfo->di_rwsem, AuLsc_DI_CHILD); au_dbg_locked_di_reg(dentry, AuLock_DW, AuLsc_DI_CHILD); dinfo->di_bstart = -1; dinfo->di_bend = -1; dinfo->di_bwh = -1; dinfo->di_bdiropq = -1; dentry->d_fsdata = dinfo; dentry->d_op = &aufs_dop; return 0; /* success */ } au_cache_free_dinfo(dinfo); } AuTraceErr(-ENOMEM); return -ENOMEM; }