Rust for audio

Programming applications for making music on Linux.

Moderators: MattKingUSA, khz

User avatar
sadko4u
Established Member
Posts: 986
Joined: Mon Sep 28, 2015 9:03 pm
Has thanked: 2 times
Been thanked: 359 times

Re: Rust for audio

Post by sadko4u »

Basslint wrote: Sat Sep 26, 2020 10:06 am C++20
I'm still writing code in C++98 standard and don't have REASONABLE arguments to switch to recent C++ standards.
Moreover, I use C++ as "C with classes": I avoid STL, exceptions and other meta-programming if it is possible. Because it:
  • bloats the generated code;
  • extremely raises the compilation time;
  • yields to unpredictable memory allocations;
  • yields to unpredictable spinlocks when working with concurrency;
  • exceptions are unsafe if you're not working under RAII paradigm;
  • STL provides 'average' generalized solutions for data structures which are loosing to specific optimized solutions.
So for that case I've introduced leightweight Low-Level Template Library (LLTL) for C++ which allows to not to bloat the code when using some usual data structures:

https://github.com/sadko4u/lsp-lltl-lib
LSP (Linux Studio Plugins) Developer and Maintainer.
Basslint
Established Member
Posts: 1511
Joined: Sun Jan 27, 2019 2:25 pm
Location: Italy
Has thanked: 382 times
Been thanked: 298 times

Re: Rust for audio

Post by Basslint »

sadko4u wrote: Sat Sep 26, 2020 5:04 pm
Basslint wrote: Sat Sep 26, 2020 10:06 am C++20
I'm still writing code in C++98 standard and don't have REASONABLE arguments to switch to recent C++ standards.
Moreover, I use C++ as "C with classes": I avoid STL, exceptions and other meta-programming if it is possible. Because it:
  • bloats the generated code;
  • extremely raises the compilation time;
  • yields to unpredictable memory allocations;
  • yields to unpredictable spinlocks when working with concurrency;
  • exceptions are unsafe if you're not working under RAII paradigm;
  • STL provides 'average' generalized solutions for data structures which are loosing to specific optimized solutions.
So for that case I've introduced leightweight Low-Level Template Library (LLTL) for C++ which allows to not to bloat the code when using some usual data structures:

https://github.com/sadko4u/lsp-lltl-lib
Thanks for sharing! I like your approach a lot, I wish I were as good as you at programming :D
The community of believers was of one heart and mind, and no one claimed that any of his possessions was his own, but they had everything in common. [Acts 4:32]

Please donate time (even bug reports) or money to libre software 🎁

Jam on openSUSE + GeekosDAW!
PieterPenninckx
Established Member
Posts: 62
Joined: Sat Jul 04, 2020 1:01 pm
Has thanked: 17 times
Been thanked: 39 times

Re: Rust for audio

Post by PieterPenninckx »

Hi all, Rust developer here.

I'll give my Completely Unbiased and Authoritative opinion (ahem).

@Basslint, concerning the points you raise:
1) The Rust community is a bit like NodeJS' - they use their package manager a lot to provide basic functionalities in small libraries, to the point that a typical program might have dozens of dependencies
As somebody who happily adds another dependency to his Cargo.toml file, thinking "this is less code I have to write and maintain", I can confirm this. Rust's standard library is rather narrow compared to e.g. Java; this also explains why so many dependencies are added. Of course, as a developer, you choose which and how many dependencies you add.
2) Many Rust libraries use "unsafe" and this defeats part of the purpose of using Rust
I would sketch a more nuanced view on this. In Rust, you need unsafe for two things: a) for really low-level stuff like and interfacing with C libraries (obviously) and b) when the automated checks that the language imposes are too strict and you are 100% sure that you are right. For low-level stuff, unsafe is unavoidable (same goes for any language). For point b): you rarely need this. Some Rust developers use unsafe in situations where they shouldn't.
I would not go so far as to say that this defeats part of the purpose of using Rust. About 99% of my code is not unsafe and I've never ever had a memory issue in that code. (I think I've had just one segfault in five years, and that was obviously in unsafe code, so it was easy to find the problem.)
3) Rust has slow compile times (C++ has the same problem, as far as I can remember, also long error messages)
Slow compile times: true. Long error messages: yes, because it includes tips and pointers to the source code etc. Actually, I stopped using C++ after I got two-pages long error messages that pointed to file A because I had forgotten a semicolon in file B (at least, that's how I remember it). The Rust experience is much more pleasant in that regard.

There are some other aspects about Rust that I think are relevant.

Firstly: it's hard to learn as a language, at least in my opinion. Some will claim that it takes just a few weeks to learn it, but this has definitely not been the case for me. Rust is very unforgiving when it comes to making mistakes, refusing to compile your software if it thinks you're doing something wrong. The advantage is that you have fewer bugs, but the disadvantage is that you're now reasoning about code that didn't even compile, so it's all a very theoretical affair and you don't have a crash to make it very clear to you that you are indeed wrong and why. Instead, the compiler gives you an error in its own terminology ("lifetimes", "borrow", ...) and it's up to you as a developer to make sense of it and to figure out if there's a real fundamental issue with your code (90% of the times, that's the case for me), or if you need to "massage" the code a little to make the compiler happy (the remaining 10% of the times for me). It seems that some other developers don't experience it in the same way as I do, so I think it also depends on the type of code you write.

Secondly, when it comes to audio development, the ecosystem is rather immature. The current ecosystem supports some types of audio applications. E.g. a command-line Jack application is something you can easily write (depending on what audio transformations you need, of course), same goes for LV2, I think (I haven't tried it). If you want to go further, you will probably discover that some bits and pieces are missing and you will have to develop some infrastructural code yourself. I don't know how far this differs from e.g. C++ or D since I don't have any worth-mentioning audio development experience in those languages. I can tell however that there's no such thing as JUCE or Dplug for Rust.

Concerning garbage collectors: indeed, Rust does not require the use of a garbage collector. In fact, the only garbage collector that Rust supports is reference counting (if you ignore some experimental third-party garbage collectors). However, I understood that even heap allocation is a no-go in a real-time context (famous blog post: http://www.rossbencina.com/code/real-ti ... or-nothing ). This also means that even in Rust, in a real-time context, you have to pre-allocate heap memory. Hence in Rust, you're using the same techniques that you would use in say D to avoid needing the Garbage Collector. The big difference in my opinion is that it's easier to work on the stack in Rust. In most languages, objects (as in instance of classes) always live on the heap or there's no way to let the compiler know that this is supposed to only live on the stack (e.g. Go uses escape analysis to determine if objects can live on the stack as an optimization, but as far as I know, there's no way to enforce this). By contrast, in Rust, everything lives on the stack unless you tell it not to (e.g. by putting it in a vector). (Context: Rust is not an object oriented language.) The true power of Rust lies in the fact that the language allows you to hand out references to things on the stack without running into memory bugs.

All in all, I'm satisfied using Rust for audio development and I personally wouldn't look into using another language for it, except maybe for writing a GUI. The reasons I like Rust are pretty much those mentioned by @Basslint: the compiler prevents me from doing stupid things, there's a nice package manager etc. I would add excellent documentation of the standard library and of most libraries in general, absence of NULL and the presence of algebraic data types (which I now miss in almost any other language).

@Basslint, I very well understand your dilemma: it's indeed a bet on the future of Rust and neither of us can look into the future. There's some discussion about using Rust in the Linux kernel (https://lwn.net/Articles/829858/) and reading the comments it seems that many are scared of being the first to place a big bet on Rust. Whether Rust is going to gain foot in audio development is a question mark and it's also possible that Rust inspires a new, even better language that then takes over from Rust. However my bet is that Rust is going to stay, at least for programming multi-threaded systems that need to be reliable. In the meanwhile, I can tell that I'm enjoying it. I hope my comments above can help you to figure out in advance if you will enjoy it as well.

Anyway, I also want to mention there's a nice and friendly community around audio development in Rust: https://rust-audio.discourse.group/.
Basslint
Established Member
Posts: 1511
Joined: Sun Jan 27, 2019 2:25 pm
Location: Italy
Has thanked: 382 times
Been thanked: 298 times

Re: Rust for audio

Post by Basslint »

PieterPenninckx wrote: Sun Oct 11, 2020 8:31 am @Basslint, I very well understand your dilemma: it's indeed a bet on the future of Rust and neither of us can look into the future. There's some discussion about using Rust in the Linux kernel (https://lwn.net/Articles/829858/) and reading the comments it seems that many are scared of being the first to place a big bet on Rust. Whether Rust is going to gain foot in audio development is a question mark and it's also possible that Rust inspires a new, even better language that then takes over from Rust. However my bet is that Rust is going to stay, at least for programming multi-threaded systems that need to be reliable. In the meanwhile, I can tell that I'm enjoying it. I hope my comments above can help you to figure out in advance if you will enjoy it as well.

Anyway, I also want to mention there's a nice and friendly community around audio development in Rust: https://rust-audio.discourse.group/.
Thank you for your thoughtful post. You sold me on Rust a bit more, at the same time what you said about memory allocation pushed me toward D :lol:

I delved a bit more into C++20 since my OP and I really can't say I like it. The syntax is very hard to read sometimes and there are some language-specific concepts (pun intended) which I find hard adapting to, despite the fact that I know my way around C++11. It's true that I am not fully committing my time to it (and maybe I am just a bad coder as well) but I think that some of the criticism toward Rust (that it's too different from existing languages) can apply to C++20 as well, so it is not valid.

The option to write C++ like @sadko4u does I think is still a sustainable choice. The problem is that the language does not enforce that in any way - you have to use a lint tool I suppose to enforce a particular coding style. Which FLOSS program would you use for that, clang-format? Is it powerful enough to prevent complex constructs from being used?

Also, what about GUIs? Gtk-rs seems to be working and Azul seems interesting, is it suited for plugins?

(sorry for the questions after your great post but you seem a lot more knowledgeable than I am :D)
The community of believers was of one heart and mind, and no one claimed that any of his possessions was his own, but they had everything in common. [Acts 4:32]

Please donate time (even bug reports) or money to libre software 🎁

Jam on openSUSE + GeekosDAW!
PieterPenninckx
Established Member
Posts: 62
Joined: Sat Jul 04, 2020 1:01 pm
Has thanked: 17 times
Been thanked: 39 times

Re: Rust for audio

Post by PieterPenninckx »

(sorry for the questions after your great post but you seem a lot more knowledgeable than I am :D)
No problem at all, a forum is for asking and answering questions.

Concerning D: I'm one of those who left the ship in favour of Rust. I actually enjoyed programming in D quite a lot and I still have nice memories of using D. Unfortunately I discovered this issue: https://issues.dlang.org/show_bug.cgi?id=1164#c5. I assumed that if you avoid raw pointers etc. in D, then your program would be guaranteed to be memory safe, but that turned out not to be the case. I was disappointed and I moved to Rust. But when I discovered Dplug, I wondered if I should have stayed with D a little longer... D is easier to learn than Rust, so you won't lose that much when you just give it a try.
[D] is a lot more readable than both C++ and Rust
It didn't take me long to learn the concepts that I need to read Rust easily (macros-by-example aside). In my experience, the difficulty lies really in writing Rust.
Also, what about GUIs? Gtk-rs seems to be working and Azul seems interesting, is it suited for plugins?
I have no experience with either, I can only say what I've heard. Gtk-rs works perfectly fine and one developer even said its API is easier to use than the C API (sorry, I forgot who it was). It's a heavy library for the compiler however, so best try to compile a "hello world" to see if compile times are acceptable for you (best compile twice: one initial compile, then make a small change and compile again since the initial compilation is always slower because some set-up needs to be done).
It seems there's no recent development on Azul anymore. I don't think any Rust-native GUI system is going to be mature in the short or medium term.

When you talk about plugins, I assume you mean LV2 under Linux (otherwise it's even harder). This is very much in a prototyping stage: https://rust-audio.discourse.group/t/fi ... lv2-ui/256. This is one of the areas (if not the area) in which you will probably need to work on the infrastructure if you want to be able to use it any time soon. My strategy is to postpone GUIs for plugins as long as possible and wait until others have finished the foundations.
Basslint
Established Member
Posts: 1511
Joined: Sun Jan 27, 2019 2:25 pm
Location: Italy
Has thanked: 382 times
Been thanked: 298 times

Re: Rust for audio

Post by Basslint »

Well @PieterPenninckx, you sold me on Rust. It will be my next serious time investment. Glad to have met you :D I hope the D devs will focus more on their GC though, now that Rust is stable it makes no sense for D to go GC-less: if they adopted a better, pauseless GC however I can see myself using it even if Rust is around!
The community of believers was of one heart and mind, and no one claimed that any of his possessions was his own, but they had everything in common. [Acts 4:32]

Please donate time (even bug reports) or money to libre software 🎁

Jam on openSUSE + GeekosDAW!
PieterPenninckx
Established Member
Posts: 62
Joined: Sat Jul 04, 2020 1:01 pm
Has thanked: 17 times
Been thanked: 39 times

Re: Rust for audio

Post by PieterPenninckx »

You're welcome, @Basslint. If you have questions about Rust for audio, you can find me here or on the discourse instance dedicated to audio development in Rust.
Basslint
Established Member
Posts: 1511
Joined: Sun Jan 27, 2019 2:25 pm
Location: Italy
Has thanked: 382 times
Been thanked: 298 times

Re: Rust for audio

Post by Basslint »

Nim just got a new release and I feel like it maybe should be discussed as well.

It has many of the good features from languages like Rust, D and Go and it ships with a GC that is deemed suited for hard realtime. As I said before, I am not against GCs, and like in D you can just disable it anyways.

I personally prefer Rust's syntax a bit but I cannot help but feel that Nim is much easier to write and read than Rust. It also has a complete standard library, unlike Rust. I don't get why it isn't more popular, honestly!

Edit: added a link specific to Nim audio -> https://www.youtube.com/watch?v=ruT7sbs5O-Q
The community of believers was of one heart and mind, and no one claimed that any of his possessions was his own, but they had everything in common. [Acts 4:32]

Please donate time (even bug reports) or money to libre software 🎁

Jam on openSUSE + GeekosDAW!
User avatar
mike@overtonedsp
Established Member
Posts: 145
Joined: Mon Apr 24, 2017 5:26 pm
Location: Oxford, England
Been thanked: 55 times
Contact:

Re: Rust for audio

Post by mike@overtonedsp »

Also, what about GUIs? Gtk-rs seems to be working and Azul seems interesting, is it suited for plugins?
There are many good reasons why GTK is not a good fit for plug-in GUIs on Linux. The problems related to using <some kind of> UI toolkit (which may or may not be the native toolkit used by the host application) have been discussed at length in many other threads - quite often by me. At present the only reliable way to get plug-in UIs to work on Linux, is using X11. The bad news is you have to do a lot of the low level programming yourself, but that's ok because if you know enough about C / C++ to think its not the language you should be using to write plug-ins (despite that the SDKs are written in C / C++) then you must also know enough about it to just write a plugin using it :)
Basslint
Established Member
Posts: 1511
Joined: Sun Jan 27, 2019 2:25 pm
Location: Italy
Has thanked: 382 times
Been thanked: 298 times

Re: Rust for audio

Post by Basslint »

mike@overtonedsp wrote: Mon Oct 19, 2020 3:19 pm
Also, what about GUIs? Gtk-rs seems to be working and Azul seems interesting, is it suited for plugins?
There are many good reasons why GTK is not a good fit for plug-in GUIs on Linux. The problems related to using <some kind of> UI toolkit (which may or may not be the native toolkit used by the host application) have been discussed at length in many other threads - quite often by me. At present the only reliable way to get plug-in UIs to work on Linux, is using X11. The bad news is you have to do a lot of the low level programming yourself, but that's ok because if you know enough about C / C++ to think its not the language you should be using to write plug-ins (despite that the SDKs are written in C / C++) then you must also know enough about it to just write a plugin using it :)
I was asking about Azul, I know that GTK cannot be safely used for plugins, but thank you for the reminder :D
The community of believers was of one heart and mind, and no one claimed that any of his possessions was his own, but they had everything in common. [Acts 4:32]

Please donate time (even bug reports) or money to libre software 🎁

Jam on openSUSE + GeekosDAW!
sjaehn
Established Member
Posts: 138
Joined: Fri May 03, 2019 6:05 pm
Has thanked: 29 times
Been thanked: 61 times

Re: Rust for audio

Post by sjaehn »

sadko4u wrote: Sat Sep 26, 2020 5:04 pm I avoid STL, exceptions and other meta-programming if it is possible.
I fully agree - with the limitation to the DSP. I'm more tolerant for GUI programming.

For me, the only class from STL I accept in the DSP is the lightweight std::array.
sadko4u wrote: Sat Sep 26, 2020 5:04 pm So for that case I've introduced leightweight Low-Level Template Library (LLTL) for C++ which allows to not to bloat the code when using some usual data structures:

https://github.com/sadko4u/lsp-lltl-lib
Nice, I haven't seen it before :-).
User avatar
mike@overtonedsp
Established Member
Posts: 145
Joined: Mon Apr 24, 2017 5:26 pm
Location: Oxford, England
Been thanked: 55 times
Contact:

Re: Rust for audio

Post by mike@overtonedsp »

The rules are basically don't use dynamic memory allocation or locks in your DSP processing, and therefore by implication some STL structures should also be avoided (e.g. any kind of 'growable' arrays, which will (re)alloc memory as they grow). The danger with reinventing your own versions is that there are some pitfalls which could cause you problems whereas the STL versions will have been very well tested, and in some cases the STL versions will also be much better optimized than you could manage with your own versions.

Generally though, it makes sense to just keep everything as simple as possible (hence why discussions about using <insert other high level language, or worse, interpreted high level language, or why not a GUI using HTML and javascript and run in a separate process containing a web browser... here> make me twitch), and use as few dependencies as possible (especially if you are targetting Linux systems). I've seldom needed the STL for plug-ins - except where it has been required due to some aspect of a plug-in SDK - and that is normally confined to the UI.
Basslint
Established Member
Posts: 1511
Joined: Sun Jan 27, 2019 2:25 pm
Location: Italy
Has thanked: 382 times
Been thanked: 298 times

Re: Rust for audio

Post by Basslint »

OK, so a lot of study hours later and after having played a bit with Rust, I think I am going to pass on it even if I find it a great language, design-wise.

I tried to write a small program using only two third-party libraries, websocket and midir: "cargo run" installed 117 packages for a total of 211 MB!
I am a heavy Ruby user and in my ~/.gem directory there are 101 gems, less than what Rust required for writing this program! (duplicates notwithstanding).

This was the output of "cargo tree":

Code: Select all

├── midir v0.7.0
│   ├── alsa v0.4.3
│   │   ├── alsa-sys v0.3.0
│   │   │   └── libc v0.2.80
│   │   │   [build-dependencies]
│   │   │   └── pkg-config v0.3.19
│   │   ├── bitflags v1.2.1
│   │   ├── libc v0.2.80
│   │   └── nix v0.15.0
│   │       ├── bitflags v1.2.1
│   │       ├── cfg-if v0.1.10
│   │       ├── libc v0.2.80
│   │       └── void v1.0.2
│   ├── bitflags v1.2.1
│   ├── libc v0.2.80
│   ├── memalloc v0.1.0
│   └── nix v0.15.0 (*)
└── websocket v0.24.0
    ├── bytes v0.4.12
    │   ├── byteorder v1.3.4
    │   └── iovec v0.1.4
    │       └── libc v0.2.80
    ├── futures v0.1.30
    ├── hyper v0.10.16
    │   ├── base64 v0.9.3
    │   │   ├── byteorder v1.3.4
    │   │   └── safemem v0.3.3
    │   ├── httparse v1.3.4
    │   ├── language-tags v0.2.2
    │   ├── log v0.3.9
    │   │   └── log v0.4.11
    │   │       └── cfg-if v0.1.10
    │   ├── mime v0.2.6
    │   │   └── log v0.3.9 (*)
    │   ├── num_cpus v1.13.0
    │   │   └── libc v0.2.80
    │   ├── time v0.1.44
    │   │   └── libc v0.2.80
    │   ├── traitobject v0.1.0
    │   ├── typeable v0.1.2
    │   ├── unicase v1.4.2
    │   │   [build-dependencies]
    │   │   └── version_check v0.1.5
    │   └── url v1.7.2
    │       ├── idna v0.1.5
    │       │   ├── matches v0.1.8
    │       │   ├── unicode-bidi v0.3.4
    │       │   │   └── matches v0.1.8
    │       │   └── unicode-normalization v0.1.13
    │       │       └── tinyvec v0.3.4
    │       ├── matches v0.1.8
    │       └── percent-encoding v1.0.1
    ├── native-tls v0.2.6
    │   ├── log v0.4.11 (*)
    │   ├── openssl v0.10.30
    │   │   ├── bitflags v1.2.1
    │   │   ├── cfg-if v0.1.10
    │   │   ├── foreign-types v0.3.2
    │   │   │   └── foreign-types-shared v0.1.1
    │   │   ├── lazy_static v1.4.0
    │   │   ├── libc v0.2.80
    │   │   └── openssl-sys v0.9.58
    │   │       └── libc v0.2.80
    │   │       [build-dependencies]
    │   │       ├── autocfg v1.0.1
    │   │       ├── cc v1.0.62
    │   │       └── pkg-config v0.3.19
    │   ├── openssl-probe v0.1.2
    │   └── openssl-sys v0.9.58 (*)
    ├── rand v0.6.5
    │   ├── libc v0.2.80
    │   ├── rand_chacha v0.1.1
    │   │   └── rand_core v0.3.1
    │   │       └── rand_core v0.4.2
    │   │   [build-dependencies]
    │   │   └── autocfg v0.1.7
    │   ├── rand_core v0.4.2
    │   ├── rand_hc v0.1.0
    │   │   └── rand_core v0.3.1 (*)
    │   ├── rand_isaac v0.1.1
    │   │   └── rand_core v0.3.1 (*)
    │   ├── rand_jitter v0.1.4
    │   │   └── rand_core v0.4.2
    │   ├── rand_os v0.1.3
    │   │   ├── libc v0.2.80
    │   │   └── rand_core v0.4.2
    │   ├── rand_pcg v0.1.2
    │   │   └── rand_core v0.4.2
    │   │   [build-dependencies]
    │   │   └── autocfg v0.1.7
    │   └── rand_xorshift v0.1.1
    │       └── rand_core v0.3.1 (*)
    │   [build-dependencies]
    │   └── autocfg v0.1.7
    ├── tokio-codec v0.1.2
    │   ├── bytes v0.4.12 (*)
    │   ├── futures v0.1.30
    │   └── tokio-io v0.1.13
    │       ├── bytes v0.4.12 (*)
    │       ├── futures v0.1.30
    │       └── log v0.4.11 (*)
    ├── tokio-io v0.1.13 (*)
    ├── tokio-reactor v0.1.12
    │   ├── crossbeam-utils v0.7.2
    │   │   ├── cfg-if v0.1.10
    │   │   └── lazy_static v1.4.0
    │   │   [build-dependencies]
    │   │   └── autocfg v1.0.1
    │   ├── futures v0.1.30
    │   ├── lazy_static v1.4.0
    │   ├── log v0.4.11 (*)
    │   ├── mio v0.6.22
    │   │   ├── cfg-if v0.1.10
    │   │   ├── iovec v0.1.4 (*)
    │   │   ├── libc v0.2.80
    │   │   ├── log v0.4.11 (*)
    │   │   ├── net2 v0.2.35
    │   │   │   ├── cfg-if v0.1.10
    │   │   │   └── libc v0.2.80
    │   │   └── slab v0.4.2
    │   ├── num_cpus v1.13.0 (*)
    │   ├── parking_lot v0.9.0
    │   │   ├── lock_api v0.3.4
    │   │   │   └── scopeguard v1.1.0
    │   │   └── parking_lot_core v0.6.2
    │   │       ├── cfg-if v0.1.10
    │   │       ├── libc v0.2.80
    │   │       └── smallvec v0.6.13
    │   │           └── maybe-uninit v2.0.0
    │   │       [build-dependencies]
    │   │       └── rustc_version v0.2.3
    │   │           └── semver v0.9.0
    │   │               └── semver-parser v0.7.0
    │   │   [build-dependencies]
    │   │   └── rustc_version v0.2.3 (*)
    │   ├── slab v0.4.2
    │   ├── tokio-executor v0.1.10
    │   │   ├── crossbeam-utils v0.7.2 (*)
    │   │   └── futures v0.1.30
    │   ├── tokio-io v0.1.13 (*)
    │   └── tokio-sync v0.1.8
    │       ├── fnv v1.0.7
    │       └── futures v0.1.30
    ├── tokio-tcp v0.1.4
    │   ├── bytes v0.4.12 (*)
    │   ├── futures v0.1.30
    │   ├── iovec v0.1.4 (*)
    │   ├── mio v0.6.22 (*)
    │   ├── tokio-io v0.1.13 (*)
    │   └── tokio-reactor v0.1.12 (*)
    ├── tokio-tls v0.2.1
    │   ├── futures v0.1.30
    │   ├── native-tls v0.2.6 (*)
    │   └── tokio-io v0.1.13 (*)
    ├── unicase v1.4.2 (*)
    ├── url v1.7.2 (*)
    └── websocket-base v0.24.0
        ├── base64 v0.10.1
        │   └── byteorder v1.3.4
        ├── bitflags v1.2.1
        ├── byteorder v1.3.4
        ├── bytes v0.4.12 (*)
        ├── futures v0.1.30
        ├── native-tls v0.2.6 (*)
        ├── rand v0.6.5 (*)
        ├── sha1 v0.6.0
        ├── tokio-codec v0.1.2 (*)
        ├── tokio-io v0.1.13 (*)
        ├── tokio-tcp v0.1.4 (*)
        └── tokio-tls v0.2.1 (*)

I can understand why this can be desirable in some settings (e.g. only the binary is distributed) but pulling in so many dependencies is not a reasonable way to ensure a program is maintainable, no matter if the compiler is as pedantic as Rust's, especially if any package can actually have unsafe code in it (and in Rust, this is possible).

Now, I don't mean to stir a flame war - these are my raw comments as someone who tried hard to get into Rust because he likes it a lot and is continuing to study it despite this - my main concern is purely cultural: I suspect that being Rust an offspring of the web development community, its culture is similar to that of NodeJS, where even the most basic things are done via third-party libraries. Why use crates called "bytes", "url" or "rand", otherwise?

Despite all, I am willing to listen to people who say this is a good thing, I am without a doubt ignorant about many aspects of software development: perhaps the Rust way of doing dependencies is the way of the future, the right way...I would really like to switch to Rust, I believe the slowness of interpreted languages is hard to justify nowadays and that C++ has gotten so big and complex that you won't find two developers who write the same subset of it (unless they agree on written guidelines). Rust is a nice language with functional features and zero-cost abstractions but this and the slow compile times really discourage me from using it.

Edit: found a counterpoint to what I said: https://wiki.alopex.li/LetsBeRealAboutDependencies

I guess some good point are raised but I don't think the dependencies pulled by C programs (which often include libraries which are pretty much preinstalled on every distro) can be compared to those pulled by Rust. And of course, versions are often a problem which is put on the shoulders of maintainers (who often have to know coding as well to "backport" changes) and cargo seems to solve but I guess I am not fully convinced, also because of security issues.
Last edited by Basslint on Tue Nov 10, 2020 5:37 pm, edited 1 time in total.
The community of believers was of one heart and mind, and no one claimed that any of his possessions was his own, but they had everything in common. [Acts 4:32]

Please donate time (even bug reports) or money to libre software 🎁

Jam on openSUSE + GeekosDAW!
Basslint
Established Member
Posts: 1511
Joined: Sun Jan 27, 2019 2:25 pm
Location: Italy
Has thanked: 382 times
Been thanked: 298 times

Re: Rust for audio

Post by Basslint »

Now, I wanted to make a separate post for Nim, which is a language that has all the nice things and some more in a syntax as readable as Python's.

Nim is probably the best language I have ever had the pleasure of looking at (besides Ruby of course :wink:)! In the past (back when it was Nimrod) I snubbed it because it does a weird automatic translation from camelCase to snake_case (which can be safely ignored). I think the developer, Andreas Rumpf, keeps this feature intentionally to keep away design elitists, and I guess it worked, tragically: had I known Nim before, I would have picked it up immediately!

I did not need to speak about Rust's audio capabilities because they are self-evident, however for Nim there can be some skepticism due to the fact that it is a garbage collected language. Starting with the premise that the GC can be disabled and that Nim is pretty much an imperative language which does not generate a lot of garbage, I don't think it's impossible to write performant hard RT code: the DSL I already mentioned, omni, shows its potential in this field.

As far as the ecosystem goes, sadly the community is not that big but at the very least it has an official utility to automatically translate C code to Nim (c2nim) which facilitates bindings.

In short, Nim is pretty great: if you are familiar with C++, Python and a Lisp you will be able to pick it up really fast, in a week or so. As I said before, it has fast reference-counting GC which can be disabled. It'd be really great if it picked up some steam so I'm throwing the ball out there :D
The community of believers was of one heart and mind, and no one claimed that any of his possessions was his own, but they had everything in common. [Acts 4:32]

Please donate time (even bug reports) or money to libre software 🎁

Jam on openSUSE + GeekosDAW!
User avatar
sadko4u
Established Member
Posts: 986
Joined: Mon Sep 28, 2015 9:03 pm
Has thanked: 2 times
Been thanked: 359 times

Re: Rust for audio

Post by sadko4u »

Basslint wrote: Tue Nov 10, 2020 4:25 pm I tried to write a small program using only two third-party libraries, websocket and midir: "cargo run" installed 117 packages for a total of 211 MB!
I am a heavy Ruby user and in my ~/.gem directory there are 101 gems, less than what Rust required for writing this program! (duplicates notwithstanding).

This was the output of "cargo tree":
This is a common dependency hell which is already known in java world. When you take some library, for example, for:

Code: Select all

String a = "1";
String b = "2";
return StringUtils.equals(a, b);
it requires +N additional libraries. The implementation of StringUtils.equals is trivial and is used only by lazy programmers who 'Don't want to re-invent the wheel':

Code: Select all

boolean equals(String a, String b) {
    if (a == b) return true;
    return (a != null) && (a.equals(b));
}
But instead of implementing such function somewhere in their package they can just drag dependency on spring or apache package into project. And we get an avalanche effect of additional libraries brought into project just because the new dependency requires them.

Now let's look to the reason of such dependency hell.
And, obviously, the reason is... the bad decomposition of modules.
If you want a simple utilitary library, don't mix it with another one which does a lot of other stuff. But this yields to the case when 100 libraries will be decomposed into 1000 smaller ones. And adding the functions of a new library into the dependency list is not comfortable for average developer: you need to know which one library has this function/tool. Will the average developer do this? Obviously, no.

That's why the situation with dependencies is sooo sad.
LSP (Linux Studio Plugins) Developer and Maintainer.
Post Reply