SUJ doesn't work with GELI?
Kostik Belousov
kostikbel at gmail.com
Thu Dec 30 09:05:21 UTC 2010
On Wed, Dec 29, 2010 at 09:54:21PM -0500, Boris Kochergin wrote:
> On 12/29/10 21:44, Lucius Windschuh wrote:
> >2010/12/29 Boris Kochergin<spawk at acm.poly.edu>:
> >>Ahoy. I'm having trouble enabling SUJ on a UFS filesystem that lives on
> >>top
> >>of a GELI device. The system is an i386 -CURRENT build from December
> >>24th. I
> >>first noticed the problem when it happened with an actual disk, but here
> >>is
> >>an example with a memory disk for ease of reproduction:
> >Hi Boris.
> >The problem is, as you may have already noticed, the "non-standard"
> >block size of 4k of the GELI device.
> >If you specify the tradiditional block size of 512 bytes when
> >initializing the GELI provider, it should work.
> >
> >I sent an email to Jeff, the answer on April 27 was:
> >>Thanks for the repro. This is an interesting case. I'll have to
> >>slightly rewrite the directory handling code in tunefs but it should not
> >>take long.
> >But I forgot to remind Jeff about this issue, as it seems. So I'll try
> >again with this mail...
> >
> >Regards,
> >
> >Lucius
>
> Aha. I hadn't thought of that. Thanks for the insight.
I had the following patch lurking around for some time. This is only
for the kernel, I did not have time to go through the usermode tools.
diff --git a/sys/ufs/ffs/ffs_softdep.c b/sys/ufs/ffs/ffs_softdep.c
index 002911c..4f4e020 100644
--- a/sys/ufs/ffs/ffs_softdep.c
+++ b/sys/ufs/ffs/ffs_softdep.c
@@ -747,7 +747,7 @@ static void handle_written_jnewblk(struct jnewblk *);
static void handle_written_jfreeblk(struct jfreeblk *);
static void handle_written_jfreefrag(struct jfreefrag *);
static void complete_jseg(struct jseg *);
-static void jseg_write(struct fs *, struct jblocks *, struct jseg *,
+static void jseg_write(struct ufsmount *ump, struct jblocks *, struct jseg *,
uint8_t *);
static void jaddref_write(struct jaddref *, struct jseg *, uint8_t *);
static void jremref_write(struct jremref *, struct jseg *, uint8_t *);
@@ -886,7 +886,8 @@ static void handle_jwork(struct workhead *);
static struct mkdir *setup_newdir(struct diradd *, ino_t, ino_t, struct buf *,
struct mkdir **);
static struct jblocks *jblocks_create(void);
-static ufs2_daddr_t jblocks_alloc(struct jblocks *, int, int *);
+static ufs2_daddr_t jblocks_alloc(struct ufsmount *, struct jblocks *, int,
+ int *);
static void jblocks_free(struct jblocks *, struct mount *, int);
static void jblocks_destroy(struct jblocks *);
static void jblocks_add(struct jblocks *, ufs2_daddr_t, int);
@@ -2135,7 +2136,8 @@ jblocks_create(void)
}
static ufs2_daddr_t
-jblocks_alloc(jblocks, bytes, actual)
+jblocks_alloc(ump, jblocks, bytes, actual)
+ struct ufsmount *ump;
struct jblocks *jblocks;
int bytes;
int *actual;
@@ -2145,7 +2147,7 @@ jblocks_alloc(jblocks, bytes, actual)
int freecnt;
int blocks;
- blocks = bytes / DEV_BSIZE;
+ blocks = bytes / ump->um_devvp->v_bufobj.bo_bsize;
jext = &jblocks->jb_extent[jblocks->jb_head];
freecnt = jext->je_blocks - jblocks->jb_off;
if (freecnt == 0) {
@@ -2157,7 +2159,7 @@ jblocks_alloc(jblocks, bytes, actual)
}
if (freecnt > blocks)
freecnt = blocks;
- *actual = freecnt * DEV_BSIZE;
+ *actual = freecnt * ump->um_devvp->v_bufobj.bo_bsize;
daddr = jext->je_daddr + jblocks->jb_off;
jblocks->jb_off += freecnt;
jblocks->jb_free -= freecnt;
@@ -2172,7 +2174,7 @@ jblocks_free(jblocks, mp, bytes)
int bytes;
{
- jblocks->jb_free += bytes / DEV_BSIZE;
+ jblocks->jb_free += bytes / VFSTOUFS(mp)->um_devvp->v_bufobj.bo_bsize;
if (jblocks->jb_suspended)
worklist_speedup();
wakeup(jblocks);
@@ -2422,7 +2424,8 @@ journal_space(ump, thresh)
thresh = jblocks->jb_min;
else
thresh = jblocks->jb_low;
- avail = (ump->softdep_on_journal * JREC_SIZE) / DEV_BSIZE;
+ avail = (ump->softdep_on_journal * JREC_SIZE) /
+ ump->um_devvp->v_bufobj.bo_bsize;
avail = jblocks->jb_free - avail;
return (avail > thresh);
@@ -2555,8 +2558,8 @@ softdep_prelink(dvp, vp)
}
static void
-jseg_write(fs, jblocks, jseg, data)
- struct fs *fs;
+jseg_write(ump, jblocks, jseg, data)
+ struct ufsmount *ump;
struct jblocks *jblocks;
struct jseg *jseg;
uint8_t *data;
@@ -2567,9 +2570,9 @@ jseg_write(fs, jblocks, jseg, data)
rec->jsr_seq = jseg->js_seq;
rec->jsr_oldest = jblocks->jb_oldestseq;
rec->jsr_cnt = jseg->js_cnt;
- rec->jsr_blocks = jseg->js_size / DEV_BSIZE;
+ rec->jsr_blocks = jseg->js_size / ump->um_devvp->v_bufobj.bo_bsize;
rec->jsr_crc = 0;
- rec->jsr_time = fs->fs_mtime;
+ rec->jsr_time = ump->um_fs->fs_mtime;
}
static inline void
@@ -2719,19 +2722,21 @@ softdep_process_journal(mp, flags)
int size;
int cnt;
int off;
+ int devbsize;
if ((mp->mnt_kern_flag & MNTK_SUJ) == 0)
return;
ump = VFSTOUFS(mp);
fs = ump->um_fs;
jblocks = ump->softdep_jblocks;
+ devbsize = ump->um_devvp->v_bufobj.bo_bsize;
/*
* We write anywhere between a disk block and fs block. The upper
* bound is picked to prevent buffer cache fragmentation and limit
* processing time per I/O.
*/
- jrecmin = (DEV_BSIZE / JREC_SIZE) - 1; /* -1 for seg header */
- jrecmax = (fs->fs_bsize / DEV_BSIZE) * jrecmin;
+ jrecmin = (devbsize / JREC_SIZE) - 1; /* -1 for seg header */
+ jrecmax = (fs->fs_bsize / devbsize) * jrecmin;
segwritten = 0;
while ((cnt = ump->softdep_on_journal) != 0) {
/*
@@ -2786,7 +2791,7 @@ softdep_process_journal(mp, flags)
*/
cnt = ump->softdep_on_journal;
if (cnt < jrecmax)
- size = howmany(cnt, jrecmin) * DEV_BSIZE;
+ size = howmany(cnt, jrecmin) * devbsize;
else
size = fs->fs_bsize;
/*
@@ -2794,9 +2799,10 @@ softdep_process_journal(mp, flags)
* for truncation of the requested size if enough contiguous
* space was not available.
*/
- bp->b_blkno = jblocks_alloc(jblocks, size, &size);
+ bp->b_blkno = jblocks_alloc(ump, jblocks, size, &size) *
+ btodb(devbsize);
bp->b_lblkno = bp->b_blkno;
- bp->b_offset = bp->b_blkno * DEV_BSIZE;
+ bp->b_offset = bp->b_blkno * devbsize;
bp->b_bcount = size;
bp->b_bufobj = &ump->um_devvp->v_bufobj;
bp->b_flags &= ~B_INVAL;
@@ -2806,7 +2812,7 @@ softdep_process_journal(mp, flags)
* sequence number to it and link it in-order.
*/
cnt = MIN(ump->softdep_on_journal,
- (size / DEV_BSIZE) * jrecmin);
+ (size / devbsize) * jrecmin);
jseg->js_buf = bp;
jseg->js_cnt = cnt;
jseg->js_refs = cnt + 1; /* Self ref. */
@@ -2825,8 +2831,8 @@ softdep_process_journal(mp, flags)
while ((wk = LIST_FIRST(&ump->softdep_journal_pending))
!= NULL) {
/* Place a segment header on every device block. */
- if ((off % DEV_BSIZE) == 0) {
- jseg_write(fs, jblocks, jseg, data);
+ if ((off % devbsize) == 0) {
+ jseg_write(ump, jblocks, jseg, data);
off += JREC_SIZE;
data = bp->b_data + off;
}
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 196 bytes
Desc: not available
Url : http://lists.freebsd.org/pipermail/freebsd-fs/attachments/20101230/8b036c60/attachment.pgp
More information about the freebsd-fs
mailing list