[HN Gopher] Show HN: Io_uring for Ruby
___________________________________________________________________
Show HN: Io_uring for Ruby
Author : ciconia
Score : 89 points
Date : 2024-09-09 11:59 UTC (11 hours ago)
(HTM) web link (github.com)
(TXT) w3m dump (github.com)
| slashdev wrote:
| The whole point of IO uring is to be fast by reducing the number
| of system calls per request.
|
| If you then process your requests in the slowest programming
| language, you add back at least 100x the overhead.
|
| It doesn't make sense to me.
| carbotaniuman wrote:
| One way you can think of this is speeding up the "slowest
| programming language". And removing/reducing blocking calls has
| benefits for languages like Ruby too.
| faizshah wrote:
| I found the easiest way to explain it is Ruby/Python/Lua are
| scripting languages for optimized C code.
| slashdev wrote:
| A syscall is so fast compared to Ruby code. It really doesn't
| make much sense to me.
| sliken wrote:
| The slower the language the bigger the upside.
| slashdev wrote:
| That's false.
|
| If the difference between IO uring and epoll is 2x, but that
| was only 5% of the total runtime, the rest being slow Ruby
| code, then at best you get a 2.5% speed up. Not worth it.
| jcmfernandes wrote:
| I expected this comment, just not so early in the life of this
| thread. Moving on... cool stuff!
| adamrezich wrote:
| It shouldn't have been flagged though--what's up with that?
| Why would someone, let alone multiple people, flag OP's
| comment? It's inoffensive, doesn't violate guidelines
| whatsoever, and in fact asks a question that I'm sure many
| people (myself included) feel is quite worthy of asking, so
| we can read peoples' responses to it.
|
| Using flags to shut down entirely reasonable discussion is
| very lame.
| dgfitz wrote:
| This whole forum is becoming quite lame. I just haven't
| found a better one yet.
| FridgeSeal wrote:
| Probably because it's a fairly tired argument that gets
| rolled out almost automatically in response to any async-IO
| or high speed IO work. It's like there's a group that likes
| to argue that only the cream of the crop spills get to use
| nice new things, and the rest of us spills be pleased with
| what we have already. At this point, it's a bit "ok thank
| you", it don't add much.
| ckolkey wrote:
| Oh, that meme is old, sorry to say. Here's a nice blog post
| about ruby outperforming C with the new JIT compiler. Fun times
| :)
|
| https://railsatscale.com/2023-08-29-ruby-outperforms-c/
| neonsunset wrote:
| Ruby YJIT is slower by multiple orders of magnitude if we
| look at more than a single constructed example.
|
| In addition, the blog post measures the cost of avoiding
| doing the interop, which allows wins as the compiler improves
| in the case of short-lived calls implemented in a native
| component.
|
| This, however, is not exclusive to Ruby and statically typed
| JIT or AOT compiled languages benefit from this to a much
| higher extent.
|
| https://benchmarksgame-
| team.pages.debian.net/benchmarksgame/...
| slashdev wrote:
| In very specific, very limited cases.
|
| I remember when these claims were made for Java twenty years
| ago. It's still slower than C, most of the time.
|
| Some things don't change.
| yxhuvud wrote:
| Io uring have several use cases. You describe one, but it also
| enables things like no blocking file IO, which nothing else
| provides in a useful manner. Ruby can be slow in certain
| scenarios, but not slow enough that things like that doesxnt
| matter.
| slashdev wrote:
| Well that's true. To do async file IO without that is really
| just using a thread pool.
|
| Of course, I don't see why that won't perform fine for Ruby.
|
| It's just so slow that optimizing the async IO at the OS
| level doesn't matter
| ciconia wrote:
| Just this morning I was benchmarking the example HTTP server I
| wrote using IOU [0]. The usual caveats notwithstanding, I would
| say 100K sustained requests per second serving 1024 concurrent
| connections (on a more-or-less average laptop) is anything but
| slow...
|
| In fact, the whole idea for this library is to provide a low-
| level, fast, flexible, asynchronous I/O layer for building Ruby
| apps and letting Ruby+YJIT optimize the app code, which it
| actually is getting pretty good at.
|
| If you're open to learning more about where the Ruby runtime is
| performance-wise, there was a very interesting recent talk [1]
| about this very subject.
|
| [0] https://github.com/digital-
| fabric/iou/blob/main/examples/htt... [1]
| https://www.youtube.com/watch?v=qf5V02QNMnA
| jhyaaasdfw wrote:
| Would Ruby benefit if we put epoll(7) or io_uring(7) on IO
| boundaries and then do something like Go or BEAM where we preempt
| at a certain number of function calls or time? One challenge I
| see with this approach is calling into C libraries although I
| don't know how common that is in Ruby ecosystem.
| davexunit wrote:
| It's pretty common to call into C libraries in Ruby. Many
| widely used Ruby gems have what are called "native extensions".
| The approach that I know of to deal with this problem is that
| captured continuations with C stack frames are marked as non-
| resumable. Trying to resume such a continuation throws an
| exception. As the programmer, you'd write your async code in a
| way that avoids calls to C that call back into Ruby to prevent
| capturing non-resumable continuations.
| xerxes901 wrote:
| This is in fact exactly what Ruby's Fibers and the async fiber-
| scheduler gem do
| blacklite wrote:
| Is Ruby commonly used in high-performance applications?
| yxhuvud wrote:
| Dunno, but being able to do nonblocking file io could still be
| useful, I suppose.
| Asmod4n wrote:
| its definitely better than just having select in the base
| installation.
| Tuna-Fish wrote:
| Ruby is used plenty in the kind of situations where the
| performance of the program itself is less important that the
| overhead of IO. This should help quite a lot on such loads.
| yxhuvud wrote:
| It is interesting to compare the effort required to interact with
| C libs in Ruby and in Crystal. I wrote
| https://github.com/yxhuvud/ior a couple of years ago and it is
| roughly on the same level of abstraction as this lib if I read it
| correctly. So it also allows a nice comparison between how the
| API is exposed.
|
| Ior doesn't contain the multishot stuff because it didn't exist
| when I still added stuff to it, but apart from that it do include
| a whole lot of ops.
| Lammy wrote:
| Very cool. Would love to see it be Ractor-safe too, which C
| extensions are not by default.
|
| https://docs.ruby-lang.org/en/master/extension_rdoc.html#lab...
| sez:
|
| "Ractor safety around C extensions has the following properties:
|
| -- By default, all C extensions are recognized as Ractor-unsafe.
|
| -- Ractor-unsafe C-methods may only be called from the main
| Ractor. If invoked by a non-main Ractor, then a
| Ractor::UnsafeError is raised.
|
| -- If an extension desires to be marked as Ractor-safe the
| extension should call rb_ext_ractor_safe(true) at the Init_
| function for the extension, and all defined methods will be
| marked as Ractor-safe."
|
| I don't know enough about io_uring to know if there would be any
| thread-safety issues to just declaring it, but here's an example
| pull request from a few years ago enabling Ractor support on a C
| extension that had no sharing issues:
| https://github.com/dearblue/ruby-extattr/pull/1/
| ciconia wrote:
| Thanks, that should be possible. I'll put it on the project's
| TODO list :-).
___________________________________________________________________
(page generated 2024-09-09 23:00 UTC)