MFV r272803:
Illumos issue: 5175 implement dmu_read_uio_dbuf() to improve cached read performance MFC after: 2 weeks
This commit is contained in:
parent
02099c7034
commit
85c930be77
@ -1021,8 +1021,8 @@ xuio_stat_wbuf_nocopy()
|
||||
}
|
||||
|
||||
#ifdef _KERNEL
|
||||
int
|
||||
dmu_read_uio(objset_t *os, uint64_t object, uio_t *uio, uint64_t size)
|
||||
static int
|
||||
dmu_read_uio_dnode(dnode_t *dn, uio_t *uio, uint64_t size)
|
||||
{
|
||||
dmu_buf_t **dbp;
|
||||
int numbufs, i, err;
|
||||
@ -1032,8 +1032,8 @@ dmu_read_uio(objset_t *os, uint64_t object, uio_t *uio, uint64_t size)
|
||||
* NB: we could do this block-at-a-time, but it's nice
|
||||
* to be reading in parallel.
|
||||
*/
|
||||
err = dmu_buf_hold_array(os, object, uio->uio_loffset, size, TRUE, FTAG,
|
||||
&numbufs, &dbp);
|
||||
err = dmu_buf_hold_array_by_dnode(dn, uio->uio_loffset, size,
|
||||
TRUE, FTAG, &numbufs, &dbp, 0);
|
||||
if (err)
|
||||
return (err);
|
||||
|
||||
@ -1080,6 +1080,58 @@ dmu_read_uio(objset_t *os, uint64_t object, uio_t *uio, uint64_t size)
|
||||
return (err);
|
||||
}
|
||||
|
||||
/*
|
||||
* Read 'size' bytes into the uio buffer.
|
||||
* From object zdb->db_object.
|
||||
* Starting at offset uio->uio_loffset.
|
||||
*
|
||||
* If the caller already has a dbuf in the target object
|
||||
* (e.g. its bonus buffer), this routine is faster than dmu_read_uio(),
|
||||
* because we don't have to find the dnode_t for the object.
|
||||
*/
|
||||
int
|
||||
dmu_read_uio_dbuf(dmu_buf_t *zdb, uio_t *uio, uint64_t size)
|
||||
{
|
||||
dmu_buf_impl_t *db = (dmu_buf_impl_t *)zdb;
|
||||
dnode_t *dn;
|
||||
int err;
|
||||
|
||||
if (size == 0)
|
||||
return (0);
|
||||
|
||||
DB_DNODE_ENTER(db);
|
||||
dn = DB_DNODE(db);
|
||||
err = dmu_read_uio_dnode(dn, uio, size);
|
||||
DB_DNODE_EXIT(db);
|
||||
|
||||
return (err);
|
||||
}
|
||||
|
||||
/*
|
||||
* Read 'size' bytes into the uio buffer.
|
||||
* From the specified object
|
||||
* Starting at offset uio->uio_loffset.
|
||||
*/
|
||||
int
|
||||
dmu_read_uio(objset_t *os, uint64_t object, uio_t *uio, uint64_t size)
|
||||
{
|
||||
dnode_t *dn;
|
||||
int err;
|
||||
|
||||
if (size == 0)
|
||||
return (0);
|
||||
|
||||
err = dnode_hold(os, object, FTAG, &dn);
|
||||
if (err)
|
||||
return (err);
|
||||
|
||||
err = dmu_read_uio_dnode(dn, uio, size);
|
||||
|
||||
dnode_rele(dn, FTAG);
|
||||
|
||||
return (err);
|
||||
}
|
||||
|
||||
static int
|
||||
dmu_write_uio_dnode(dnode_t *dn, uio_t *uio, uint64_t size, dmu_tx_t *tx)
|
||||
{
|
||||
@ -1132,6 +1184,15 @@ dmu_write_uio_dnode(dnode_t *dn, uio_t *uio, uint64_t size, dmu_tx_t *tx)
|
||||
return (err);
|
||||
}
|
||||
|
||||
/*
|
||||
* Write 'size' bytes from the uio buffer.
|
||||
* To object zdb->db_object.
|
||||
* Starting at offset uio->uio_loffset.
|
||||
*
|
||||
* If the caller already has a dbuf in the target object
|
||||
* (e.g. its bonus buffer), this routine is faster than dmu_write_uio(),
|
||||
* because we don't have to find the dnode_t for the object.
|
||||
*/
|
||||
int
|
||||
dmu_write_uio_dbuf(dmu_buf_t *zdb, uio_t *uio, uint64_t size,
|
||||
dmu_tx_t *tx)
|
||||
@ -1151,6 +1212,11 @@ dmu_write_uio_dbuf(dmu_buf_t *zdb, uio_t *uio, uint64_t size,
|
||||
return (err);
|
||||
}
|
||||
|
||||
/*
|
||||
* Write 'size' bytes from the uio buffer.
|
||||
* To the specified object.
|
||||
* Starting at offset uio->uio_loffset.
|
||||
*/
|
||||
int
|
||||
dmu_write_uio(objset_t *os, uint64_t object, uio_t *uio, uint64_t size,
|
||||
dmu_tx_t *tx)
|
||||
|
@ -616,6 +616,7 @@ void dmu_write(objset_t *os, uint64_t object, uint64_t offset, uint64_t size,
|
||||
void dmu_prealloc(objset_t *os, uint64_t object, uint64_t offset, uint64_t size,
|
||||
dmu_tx_t *tx);
|
||||
int dmu_read_uio(objset_t *os, uint64_t object, struct uio *uio, uint64_t size);
|
||||
int dmu_read_uio_dbuf(dmu_buf_t *zdb, struct uio *uio, uint64_t size);
|
||||
int dmu_write_uio(objset_t *os, uint64_t object, struct uio *uio, uint64_t size,
|
||||
dmu_tx_t *tx);
|
||||
int dmu_write_uio_dbuf(dmu_buf_t *zdb, struct uio *uio, uint64_t size,
|
||||
|
@ -582,7 +582,6 @@ static int
|
||||
mappedread(vnode_t *vp, int nbytes, uio_t *uio)
|
||||
{
|
||||
znode_t *zp = VTOZ(vp);
|
||||
objset_t *os = zp->z_zfsvfs->z_os;
|
||||
vm_object_t obj;
|
||||
int64_t start;
|
||||
caddr_t va;
|
||||
@ -613,7 +612,8 @@ mappedread(vnode_t *vp, int nbytes, uio_t *uio)
|
||||
page_unhold(pp);
|
||||
} else {
|
||||
zfs_vmobject_wunlock(obj);
|
||||
error = dmu_read_uio(os, zp->z_id, uio, bytes);
|
||||
error = dmu_read_uio_dbuf(sa_get_db(zp->z_sa_hdl),
|
||||
uio, bytes);
|
||||
zfs_vmobject_wlock(obj);
|
||||
}
|
||||
len -= bytes;
|
||||
@ -650,7 +650,6 @@ zfs_read(vnode_t *vp, uio_t *uio, int ioflag, cred_t *cr, caller_context_t *ct)
|
||||
{
|
||||
znode_t *zp = VTOZ(vp);
|
||||
zfsvfs_t *zfsvfs = zp->z_zfsvfs;
|
||||
objset_t *os;
|
||||
ssize_t n, nbytes;
|
||||
int error = 0;
|
||||
rl_t *rl;
|
||||
@ -658,7 +657,6 @@ zfs_read(vnode_t *vp, uio_t *uio, int ioflag, cred_t *cr, caller_context_t *ct)
|
||||
|
||||
ZFS_ENTER(zfsvfs);
|
||||
ZFS_VERIFY_ZP(zp);
|
||||
os = zfsvfs->z_os;
|
||||
|
||||
if (zp->z_pflags & ZFS_AV_QUARANTINED) {
|
||||
ZFS_EXIT(zfsvfs);
|
||||
@ -756,10 +754,12 @@ zfs_read(vnode_t *vp, uio_t *uio, int ioflag, cred_t *cr, caller_context_t *ct)
|
||||
error = mappedread_sf(vp, nbytes, uio);
|
||||
else
|
||||
#endif /* __FreeBSD__ */
|
||||
if (vn_has_cached_data(vp))
|
||||
if (vn_has_cached_data(vp)) {
|
||||
error = mappedread(vp, nbytes, uio);
|
||||
else
|
||||
error = dmu_read_uio(os, zp->z_id, uio, nbytes);
|
||||
} else {
|
||||
error = dmu_read_uio_dbuf(sa_get_db(zp->z_sa_hdl),
|
||||
uio, nbytes);
|
||||
}
|
||||
if (error) {
|
||||
/* convert checksum errors into IO errors */
|
||||
if (error == ECKSUM)
|
||||
|
Loading…
Reference in New Issue
Block a user