Signed-off-by: Alexey Kuznetsov <kuz...@acronis.com> --- fs/fuse/kio/pcs/pcs_cs.c | 22 ++++++++-------------- fs/fuse/kio/pcs/pcs_cs_accel.c | 30 +++++++++++++++++++++++++++++- 2 files changed, 37 insertions(+), 15 deletions(-)
diff --git a/fs/fuse/kio/pcs/pcs_cs.c b/fs/fuse/kio/pcs/pcs_cs.c index d298be9..20840f8 100644 --- a/fs/fuse/kio/pcs/pcs_cs.c +++ b/fs/fuse/kio/pcs/pcs_cs.c @@ -829,18 +829,14 @@ void pcs_cs_submit(struct pcs_cs *cs, struct pcs_int_request *ireq) if (pcs_csa_cs_submit(cs, ireq)) return; } else if (ireq->iochunk.cmd == PCS_REQ_T_WRITE) { - /* Synchronous writes in accel mode are still not supported */ - if (!(ireq->dentry->fileinfo.attr.attrib & PCS_FATTR_IMMEDIATE_WRITE) && - !ireq->dentry->no_write_delay) { - struct pcs_int_request * sreq; - - sreq = pcs_csa_csl_write_submit(ireq); - if (!sreq) - return; - if (sreq != ireq) { - ireq = sreq; - cs = ireq->iochunk.csl->cs[ireq->iochunk.cs_index].cslink.cs; - } + struct pcs_int_request * sreq; + + sreq = pcs_csa_csl_write_submit(ireq); + if (!sreq) + return; + if (sreq != ireq) { + ireq = sreq; + cs = ireq->iochunk.csl->cs[ireq->iochunk.cs_index].cslink.cs; } } } @@ -879,8 +875,6 @@ void pcs_cs_submit(struct pcs_cs *cs, struct pcs_int_request *ireq) * chain. */ if (idx == ireq->iochunk.cs_index || - (ireq->dentry->fileinfo.attr.attrib & PCS_FATTR_IMMEDIATE_WRITE) || - ireq->dentry->no_write_delay || ((ireq->iochunk.size|ireq->iochunk.offset) & 511) || (ireq->flags & IREQ_F_NO_ACCEL) || !pcs_csa_csl_write_submit_single(sreq, idx)) diff --git a/fs/fuse/kio/pcs/pcs_cs_accel.c b/fs/fuse/kio/pcs/pcs_cs_accel.c index 5d44862..8a7e7f9 100644 --- a/fs/fuse/kio/pcs/pcs_cs_accel.c +++ b/fs/fuse/kio/pcs/pcs_cs_accel.c @@ -827,6 +827,25 @@ static void __pcs_csa_write_final_completion(struct pcs_accel_write_req *areq) csa_complete_acr(ireq); } +static void csa_sync_work(struct work_struct *w) +{ + struct pcs_accel_write_req * areq = container_of(w, struct pcs_accel_write_req, work); + struct pcs_int_request * ireq = container_of(areq-areq->index, struct pcs_int_request, iochunk.acr.awr[0]); + int res; + + res = vfs_fsync(areq->iocb.ki_filp, 1); + + if (res) { + ireq->error.remote = 1; + ireq->error.offender = ireq->iochunk.csl->cs[ireq->iochunk.cs_index].info.id; + ireq->error.value = PCS_ERR_IO; + ireq->flags |= IREQ_F_ACCELERROR; + } + + if (atomic_dec_and_test(&areq->iocount)) + __pcs_csa_write_final_completion(areq); +} + static void csa_write_complete_work(struct work_struct *w) { struct pcs_accel_write_req * areq = container_of(w, struct pcs_accel_write_req, work); @@ -851,6 +870,15 @@ static void csa_write_complete(struct kiocb *iocb, long ret) } } + if (!ireq->error.value) { + if ((ireq->dentry->fileinfo.attr.attrib & PCS_FATTR_IMMEDIATE_WRITE) || + ireq->dentry->no_write_delay) { + INIT_WORK(&areq->work, csa_sync_work); + queue_work(ireq->cc->wq, &areq->work); + return; + } + } + if (atomic_dec_and_test(&areq->iocount)) { INIT_WORK(&areq->work, csa_write_complete_work); queue_work(ireq->cc->wq, &areq->work); @@ -1027,7 +1055,7 @@ static inline int csa_submit_write(struct file * file, struct pcs_int_request * return ret >= 0 ? -EIO : ret; } - /* IO already finished. Drop AIO refcnt and proceed to crc */ + /* IO already finished. Drop AIO refcnt yet. */ FUSE_KTRACE(ireq->cc->fc, "No good, AIO executed synchronously, ireq:%p : %llu:%u+%u", ireq, (unsigned long long)ireq->iochunk.chunk, (unsigned)ireq->iochunk.offset, -- 1.8.3.1 _______________________________________________ Devel mailing list Devel@openvz.org https://lists.openvz.org/mailman/listinfo/devel