5 ms·
Learn Wayland by writing a GUI from scratch
- diath 3y agoThe use of assert instead of runtime conditions for bounds checking doesn't seem like a good idea.
- arghwhat 3y agoThat's a very normal use if asserts - no point in a running but broken program if important programmer assumptions failed, and a coredump is more useful for debugging than an error message.
- ahoka 3y agoBut C assert.h checks can be disabled by setting NDEBUG and sometimes are for production builds. It’s not meant for bounds checking or anything that required for correctness, but for asserting invariants, hence the name.
- sph 3y agoIt's a blog post to teach about Wayland, not a production app. If one creates an app by copy-pasting this code, blame them, not the author.
- arghwhat 3y agoYes you can actively disable it. You can also pass "-gcflags=-B" to Go to disable bounds checking, and Rust disables runtime overflow checks in release mode by default. Doesn't make the use any less valid.
- LoganDark 3y agoIn-bounds accesses should be an invariant. A program that is capable of even attempting an out-of-bounds access is probably incorrect. With that said, I would not be confident enough to allow bounds checks to be disabled. (Rust is my favorite.)
- diath 3y agoConsider this - you may not be able to hit your assumption with all possible inputs in debug/during development, or your function may accept user-provided input, you then release your software, and then somebody gets your code executed with a set of inputs that don't pass the assumption, now since it's an assert that's been effectively turned into a no-op in release, you're reading past the end of the buffer.
- arghwhat 3y agoasserts are not disabled in release builds unless you explicitly go out of your way to do so.
- josefx 3y agoVarious build tool chains disable them implicitly for release builds. You should probably assert #ifdef NDEBUG #error #endif In your source code if your code assumes that assertions will never be disabled.
- deleted 3y ago[deleted]
- runeks 3y agoHonest question : what's the difference between the two? I assume assert also checks conditions at runtime?
- lionkor 3y agoNot in release builds
- tonyedgecombe 3y agoWhich can catch the unwary out, for instance if you do something like this it won't decrement index in your release build: assert(--index >= 0);
- asicsp 3y agoSee also: Learn x86-64 assembly by writing a GUI from scratch https://gaultier.github.io/blog/x11_x64.html https://gaultier.github.io/blog/x11_x64.html Discussion: https://news.ycombinator.com/item?id=36153237 https://news.ycombinator.com/item?id=36153237 (638 points | 4 months ago | 146 comments)
- cassepipe 3y agoI am learning x86-64 asm with it. It's great !
- criddell 3y agoThanks for posting this! I missed it when it was originally posted and I’ve been looking for something like this. From that link I also learned about lobste.rs which is also new (and interesting!) to me. Now I need to figure out a way to get an invite…
- criddell 3y agoTo the kind soul who sent me an invite: thank you!
- charcircuit 3y agoWAYLAND_DISPLAY lets you do a buffer overflow
- sph 3y agoThe C code in the article is not great, but I don't think the author was trying to write a robust, production-ready Wayland client either. A couple examples of fragile code, so my comment is a little constructive: - I truly dislike the cstring_len macro, which sounds like strlen yet its semantics are completely different. - The wayland_display_connect function returns EINVAL or an fd. Both are positive integers. It should instead return -EINVAL. - The functions benefit from more comments, because they do a lot and are not factored to smaller, more composable units. - wayland_handle_message should be refactored so it's a simple switch that operates on constants, and ideally delegates to other functions. - Probably outside of the scope of a simple article, but all the buffer boilerplate should be simplified by using a buffer structure that holds pointer, cursor and capacity, to make the code much more readable.
- ahoka 3y agoAnd EINVAL is a perfectly valid fd.
- mananaysiempre 3y ago> wayland_handle_message should be refactored so it's a simple switch that operates on constants, and ideally delegates to other functions. Is that actually possible? Opcodes by themselves are not unique, and the object IDs are right now assigned at runtime (I can’t tell if that’s actually necessary).
- unwind 3y agoAgree. Not sure about roundup_4() either.
- smcameron 3y ago> The wayland_display_connect function returns EINVAL or an fd. Both are positive integers. It should instead return -EINVAL. Or maybe return -1 and set errno? I haven't seen many C programs that return negative errnos (excepting the linux kernel which uses negative errnos internally).
- _dain_ 3y agoNever programmed with Wayland (or X) before but this doesn't look so terrible. Let's say I want to do something only slightly more complicated than this article, e.g. have a few static rectangles on the screen showing images and text, without any window decorations, like for a status bar or a clock or something. If I don't want to roll my own protocol-handling code as in this article, what libraries are good? In say Rust or Go or something? Every time I've looked into Gtk or Qt they seemed way too complicated, doing far more than I want and introducing too many abstractions and dependencies. Conceptually all I want to do is: window = make_stupid_simple_undecorated_window(x, y, w, h); paint_window(window, some_image_buffer); block_forever();
- vially 3y agoI've toyed around with Smithay Client Toolkit [1] for Rust and I think it offers just the right abstraction for writing simple Wayland clients. [1] - https://github.com/Smithay/client-toolkit https://github.com/Smithay/client-toolkit
- deleted 3y ago[deleted]
- narag 3y agoUnless your "application" is the only thing in the screen, you need some protocol. At a minimum, repainting after your windows has been obscured by others, reacting to commands like closing the window or the session, shutting down, etc. The main difference from CLI is that GUI works reacting to messages, even for (re)painting. Once you get that, the rest falls into place. This is usually implemented with object-oriented libraries, because it's the kind of application where OOP shines. But it's not mandatory. Oh, and your app should also respond to move, change workspace, minimize... messages.
- samsquire 3y agoThere's so many ideas and separate things/topics in this: a protocol between the Wayland server and your client, an RPC mechanism, a protocol format serialisation, synchronization (lock), an async mechanism, an object registry, shared memory, domain sockets, event loop. Now I haven't written any non-CLI GUI Linux applications in C. I once played with the Qt IDE. I feel it is pretty difficult stuff! I think dbus is also really interesting too. This causes me to think of the success of Nodejs and how it abstracts async and makes it approachable to anyone. Rather than pointers in C you have JavaScript object literals. The most complicated GUIs I created were with Swing in Java and JavaScript. Can someone more knowledgeable tell me what is GPU accelerated with Wayland? Is there a bitblit operation uses by compositor? And how would you write a high performance GUI that is maintainable. I'm aware Blink/Chromium uses Skia which I presume is accelerated. In my JavaScript visualisation experiments with canvases - the page has started to slow down because I'm doing stuff on the main thread. See this example - scroll down and you'll see a process visualiser and scroll down further and there's a graph. I'm doing parsing on the main thread https://replit.com/@Chronological/Processes3#index.html https://replit.com/@Chronological/Processes3#index.html I feel this would be so much harder to build in C. I am kind of following the trends in GUI rendering tech - I am curious how you support rendering lists of hundreds of thousands of items without expensive update costs. The perennial react performance problem. I'm following the approaches taken by Tauri and Rust desktop app designs. Looking for a silver bullet.
- dathinab 3y agoWayland is not a GUI toolkit It's protocols which handle the communication between GUI toolkits your desktop manager (e.g. make new windows, resize windows, scaling, etc.) and how to connect to the GPU driver. I.e. wayland isn't GUI technology it's a level below it. So on systems using Wayland every GUI toolkit, including Skia, uses Wayland internally. Also Wayland is _only_ protocols, so questions like "is window composition GPU accelerated" are implementation details of the specific compositor (through yes in general they are). This is also on of the differences with X. Another one is X had a bunch of features sprinkled in which belong to the space of GUI toolkits (most of which had been abandoned by most software long before Wayland become relevant). Wayland is more cleanly designed wrt. to this aspects.
- arun-mani-j 3y agohttps://wayland-book.com/ https://wayland-book.com/ This book is nice if you want to: - Understand Wayland itself - Write applications without being dependent on GUI frameworks - Write a compositor yourself It's author is Drew DeVault.
- rc00 3y agoThe only PDF version of the book appears to be at https://github.com/rcalixte/wayland-book https://github.com/rcalixte/wayland-book for now. Are there plans to do the same on the original site? The print button didn't work for me.
- arun-mani-j 3y agoNo idea about that :)
- st3fan 3y agoThis was fun to read but also .. I'm so happy I don't have to touch C anymore.
- JoeyBananas 3y agoThere's an increasingly small list of reasons to build a GUI outside of the browser. Personally, I don't think I ever will have this need again.
- axilmar 3y agoWay too many chances for buffer overflows. It is a nice approach to learn how things work, but not a recommended approach for building anything useful.