6 ms·
Loom will be the next billion dollar mistake after nulls. Keep my words in mind for a decade or two...
by valenterry 4y ago
Loom will be the next billion dollar mistake after nulls. Keep my words in mind for a decade or two...
- geodel 4y agoOkay, are you going to give reason or is it more of a Thought leader style pronouncement?
- valenterry 4y agoHaha, I guess you are right. The reason why it is a mistake is because it is essentially trying to solve the rpc problem once again even though it has been tried many times without success. There just is a difference between making a synchronous call within your own OS thread vs. making such a call against anything else (the filesystem, the network, ...). Because you can assume that a synchronous call either succeeds and you can continue whatever you do. Or the whole thing crashes because e.g. the thread was killed due to some external effect or OOM error. But in that case, you have the guarantee that no more code on your thread is being run. With Loom, it is not clear anymore if more code will be run based on your call or not, since there isn't an immediate difference between the two types of calls anymore (when looking at the code). This missing distinction is exactly what makes it easier to use but it also makes it very easy to use the "wrong default".
- mietek 4y agoJoe Armstrong (the creator of Erlang) said the same thing back in 2008. > The fundamental problem with taking a remote operation and wrapping it up so that it looks like a local operation is that the failure modes of local and remote operations are completely different. > If that's not bad enough, the performance aspects are also completely different. A local operation that takes a few microseconds, when performed through an RPC, can suddenly take milliseconds. http://armstrongonsoftware.blogspot.com/2008/05/road-we-didnt-go-down.html http://armstrongonsoftware.blogspot.com/2008/05/road-we-didn...
- valenterry 4y agoThx, always feels good to be confirmed by what someone write ~15 years ago. I think he's right.
- mietek 4y agoA comment under Joe’s post points out that this has been understood at least since 1994. > We argue that objects that interact in a distributed system need to be dealt with in ways that are intrinsically different from objects that interact in a single address space. These differences are required because distributed systems require that the programmer be aware of latency, have a different model of memory access, and take into account issues of concurrency and partial failure. > We look at a number of distributed systems that have attempted to paper over the distinction between local and remote objects, and show that such systems fail to support basic requirements of robustness and reliability. https://web.archive.org/web/20030310070307/http://research.sun.com/techrep/1994/smli_tr-94-29.pdf https://web.archive.org/web/20030310070307/http://research.s...
- twic 4y agoWe can go further - the very first of Peter Deutsch's Fallacies of Distributed Computing, written in 1994, is [1]: > The network is reliable. [1] https://www.computing.dcu.ie/~ray/teaching/CA485/notes/fallacies.pdf https://www.computing.dcu.ie/~ray/teaching/CA485/notes/falla...
- mumblemumble 4y agoI think that I disagree. Not because I think Loom is a good design, but because I've seen the same design mistake committed a couple times before, and, despite initial hype, people tend learn to hate and avoid it long, long before it can become as intractable a problem as null is. The worst I anticipate coming from it is some hassles in production and a whole lot of time wasted futilely trying to explain why I don't like it to people who've had 1/10 as much time as me to become bitter and jaded from working in the profession.
- pestatije 4y ago> there isn't an immediate difference between the two types of calls anymore (when looking at the code) There is: sync calls don't change. Async calls use the Future::fork call, all within your parent thread block scope.
- valenterry 4y agoAre you saying that Thread.sleep() will still be blocking its OS-thread completely so that this thread executes no other code until the end of the sleep call? Because otherwise your claim "sync calls don't change" is wrong - since this is how it currently works.
- hota_mazi 4y agoThat's the very definition of what sleep() does, and the reason why, if you're calling it in an async context, you need to dispatch it in a special "blocking" dispatcher, as opposed to the other regular async calls.
- valenterry 4y agoThat doesn't answer my question to the OP. I know what sleep() does and how to use it, but that's not the point.
- pestatije 4y agoWe are talking virtual threads here(project loom), i think, no? https://openjdk.org/jeps/428 https://openjdk.org/jeps/428 Basically, you don't have a thread context anymore, or you don't have a use for it anymore
- valenterry 4y ago> We are talking virtual threads here(project loom), i think, no? No. Currently, when I have code (not using futures or anything) and in the middle there is a Thread.sleep() then I know that this thread will be blocked until the sleep is over (or interrupted) and _no other code is being executed on this thread_. So the question is: will this behaviour change? Because if it does, then Loom breaks existing code. And that's what it does. And it does it not by accident but on purpose, to retroactively improve performance of exactly those situations where OS threads are blocked.
- stickfigure 4y agoI'll take your bet. First of all, the difference between threads is not nearly as severe as the difference between (remote) machines. There is an analogy to be made, but that's all it is - an analogy. Most applications don't care about nitty gritty thread-management performance. Second, people said all that shit about network calls and yet... here we live in the age of distributed computing and it keeps getting more distributed. It's rapidly getting to the point where remote boundaries are something you consider as an optimization step. Most boring old business applications are "fast enough" even though the XyzService lives on another machine.
- valenterry 4y ago> First of all, the difference between threads is not nearly as severe as the difference between (remote) machines The whole reason for Loom is to improve performance of code that would otherwise be blocking. So what code is blocking? Exactly: code that waits for the OS (files, network, etc.). A call from one thread to the other isn't really a blocking call and that is not really what project Loom's main focus is about - at least as far as I can tell.
- ithrow 4y agoDoesn't the problem you mention for Loom applies equally to OS threads? What's the difference? Loom just lets you create more threads but with OS threads you are doing IO too.
- valenterry 4y agoThis is independent of OS threads or green threads. The problem is that with Loom the developer loses control whether they can execute something on one OS thread only or not. Whereas right now they conciously have to decide if they want to run something sync or async.
- seer-zig 4y agoNothing is stopping the developer from starting a single thread executor and using that to launch many virtual threads. Is that what you meant?
- valenterry 4y agoWell, that is something that is desired and also something we can already do in the JVM world. What I mean is that semantics of existing code changes (and becomes harder to understand for future code).
- lern_too_spel 4y agoLoom doesn't hide exceptions. Now you just write the exception handling the same way you would write synchronous exception handling.
- xani_ 4y agoIt does look awfully like the async/await mess languages with bad concurrency adopted as a crutch for not having good concurrency. Erlang/Golang model of superlight "threads" exchanging messages appears to be much better at both being actually concurrent and making most code look decent and easy to see what is actually happening.
- seer-zig 4y ago> model of superlight "threads" exchanging messages That's exactly what Loom is.
- protomolecule 4y agoWhy?
- lern_too_spel 4y agoGoroutines have been very successful.
- cube2222 4y agoAnd not just goroutines. The whole Go runtime is basically what Loom aspires to be. All functions async by default and preemptible. Writing code that looks like it's blocking but is in fact async. "Await" as the default action to do with an async function, and "go" being the optional action. So far the reception has been very good and it works very well in practice. To me it's a pain now to work with languages that don't work like that. I'd argue it's Go's biggest advantage, really. The Zig approach looks very good as well (If I understand it correctly, the underlying functions basically get compiled to whatever the caller wants them to be. Async or not. We'll see how that pans out in practice as the language gets more traction.).
- eweise 4y ago"All functions async by default and preemptible." Really? I thought functions were sync by default unless you add the 'go' keyword.
- cube2222 4y agoThe `go` keyword means you want to run this function concurrently to what you're doing right now. You can think of it this way, to use terms from other languages: in Go, every function really returns a Future. But every function call has an `await` implicitly. Using the `go` keyword signals that you don't want that `await`. The call-site action doesn't change whether or not the function itself is asynchronous or not (it is). However, if you use a mutex in Go, or wait on a channel, or try to write to a TCP connection, those calls won't block an OS thread. Additionally, if a goroutine goes on too long and others are waiting, it will be stopped and the OS thread will work on a different goroutine for a while.
- valzam 4y agoIs this really true? My impression was that the 'go' keyword means a green thread is spun up for the function to run in and this wrapper returns immediately (hence the need for channels or waitgroups etc to get the results back). I can't imagine that every synchronous function call creates a green thread, that seems massively wasteful.