Re: [PATCH v2] splice: sendfile() at once fails for big files

From: Jens Axboe
Date: Wed May 06 2015 - 10:48:56 EST


On 05/06/2015 08:38 AM, leroy christophe wrote:

Le 06/05/2015 16:23, Jens Axboe a Ãcrit :
On 05/05/2015 09:41 PM, Linus Torvalds wrote:
Jens, ping?

The test results should make this a no-brainer, but I hate how random
these flag ops.

Missed the original, apparently. I too am confused how this is a
correctness fix and not just an optimization.

+ if (read_len < len)
+ sd->flags |= SPLICE_F_MORE;
+ else if (!more)
+ sd->flags &= ~SPLICE_F_MORE;

Should that check be for 'more', not '!more'?


@@ -1204,6 +1204,7 @@ ssize_t splice_direct_to_actor(struct file *in,
struct splice_desc *sd,
* Don't block on output, we have to drain the direct pipe.
*/
sd->flags &= ~SPLICE_F_NONBLOCK;
+ more = sd->flags & SPLICE_F_MORE;

while (len) {
size_t read_len;
@@ -1216,6 +1217,10 @@ ssize_t splice_direct_to_actor(struct file *in,
struct splice_desc *sd,
read_len = ret;
sd->total_len = read_len;

+ if (read_len < len)
+ sd->flags |= SPLICE_F_MORE;
+ else if (!more)
+ sd->flags &= ~SPLICE_F_MORE;



'more' contains whether sendfile() has been called with SPLICE_F_MORE or
not.
Until all bytes are processed, we have to force SPLICE_F_MORE regardless
of how sendfile() was called.
Once all bytes have been read, we have to reset the flags according to
how sendfile() was called, so if 'more' is NOT set, we have to clear
SPLICE_F_MORE from sd->flags (which was unconditionaly set for
processing the first bytes)

Ah gotcha, that looks correct. Patch is fine with me then.

--
Jens Axboe

--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/