On Fri, Jun 2, 2023 at 7:45 AM David Howells <dhowells@xxxxxxxxxx> wrote: > > Linus Torvalds <torvalds@xxxxxxxxxxxxxxxxxxxx> wrote: > > > Do what I already suggested: making SPLICE_F_MORE reflect reality. > > I'm trying to. I need MSG_MORE to behave sensibly for what I want. But you need to stop doing these random hacks to fs/splice.c The point is, you *CANNOT* make SPLICE_F_MORE reflect reality by hacking fs/splice.c. Really. The generic layer DOES NOT KNOW, AND FUNDAMENTALLY CANNOT KNOW if there is more data to be had. So any of these random patches that try to add heuristics to fs/splice.c will be rejected out of hand. They simply cannot be correct. And no, on the whole I do not believe you have to maintain some selftest. A selftest failure is worrisome in that it clearly shows that some behavior changed, but the situation here is (a) the current behavior is arguably bad and buggy (b) if we want to fix that bug, then the current behavior *will* change Now, the only question then is whether the self-test actually tests anything that user space actually depends on, or if it just tests some random corner case. So the self-test is certainly a ref flag, but not necessarily a very meaningful one. It shows that some user-visible change happened, which is always a big danger flag, but after all that was the whole *point* of the whole exercise. The fact that the self-test caught the change is good, because it means we had test coverage, but when the behavior is something we *want* to change, the test failure is not a problem in itself. So what I think you should do is to fix the bug right, with a clean patch, and no crazy hacks. That is something we can then apply and test. All the while knowing full well that "uhhuh, this is a visible change, we may have to revert it". If then some *real* load ends up showing a regression, we may just be screwed. Our current behavior may be buggy, but we have the rule that once user space depends on kernel bugs, they become features pretty much by definition, however much we might dislike it. At that point, we'll have to see what we can do - if anything. Basically, what I think the SPLICE_F_MORE rules *should* be (and hey, I may be missing something) is 1) if the user set that bit in the flags, then it's always true. The user basically told us "I will supply more data even after the splice has finished", so it doesn't matter if the kernel runs out of data in the middle. 2) if the splice read side sees "I was asked for N bytes, but I could only supply X bytes and I still have more to give", when we should set SPLICE_F_MORE internally ("temporarily") for the next splice call. This is basically the "kernel independently knows that there will be more data" case. 3) In the end, this is all "best effort" and to some degree inevitably a heuristic. We cannot see the future. We may hit that case #2 and set the "there will be more data" bit, but then get a signal and finish the splice system call before that more data actually happens. Now, presumably the user will then continue the partial splice after handling the signal, so (3) is still "right", but obviously we can't _know_ that. A corollary to (3) is that the reader side may not always know if there will be more data to be read. For a file source, it's fairly clear (modulo the obvious caveats - files can be truncated etc etc). For other splice sources, the "I still have more to give" may not be as unambiguous. It is what it is. Am I missing some important case? Considering that we clearly do *not* do a great job at SPLICE_F_MORE right now, I'd really want the situation to be either that we just make the code "ClearlyCorrect(tm)" and simple, or we just leave it alone as "that's our odd behavior, deal with it". None of this "let's change this all to be even more complex, and handle some particular special case the way I want" crap. Do it right, or don't do it at all. Linus