Unable to get Roon to Start on Nix Linux

Hey @support,

I’m working on getting RoonServer working on NixOS as that’s what my NAS runs. While I’m well aware it’s a fairly uncommon distribution, I’ve managed to get all the dependencies that Roon (& mono) need to run in place, but when I try to start RoonServer I get:

Started
Error
Initializing
Started
Error
Initializing
Started
Error
Initializing
Started
Error
Initializing
Started
Error
Initializing
Started
Error
Initializing
Started

endless until I end the program with Ctrl-c.

I’ve run the ./check.sh script and I’m getting a clean bill of health (other than mount.cifs, which I don’t need at the moment)

Using strace I see the last call it makes before those messages is to wait4, which doesn’t tell me much other than it’s launching a subprocess.

Anything I can do to get more details on what’s causing the error?

Thanks

HI @Michael_Francis,

I’ve shifted this into the Linux category as I suspect Support may not be as familiar with NixOS as some of the old Linux hands in this section of the Forum. In particular let’s drop a flag for @crieke and see if he can assist.

I will check back in this thread to see if you are getting some attention and if not then we can try Support again.

Is it creating log files?

If you didn’t set environment vars, these will be in ~/.RoonServer/Logs
If you did, it will be in $ROON_DATAROOT/RoonServer/Logs

If it is, post the contents of one.

Unfortunately, it doesn’t seem to be creating logs. I tried exporting the
ROON_DATAROOT environment variable before running it but no luck.

Does the mono binary inside of our package start up if you run it by itself?

RoonServer $ ./Mono/bin/mono-sgen
...

Yep, works fine

[nix-shell:~/code/roon-nix/RoonServer]$ ./Mono/bin/mono-sgen
Usage is: mono [options] program [program-options]

Development:
    --aot[=<options>]      Compiles the assembly to native code
    --debug[=<options>]    Enable debugging support, use --help-debug for details
    --debugger-agent=options Enable the debugger agent
    --profile[=profiler]   Runs in profiling mode with the specified profiler module
    --trace[=EXPR]         Enable tracing, use --help-trace for details
    --jitmap               Output a jit method map to /tmp/perf-PID.map
    --help-devel           Shows more options available to developers

Runtime:
    --config FILE          Loads FILE as the Mono config
    --verbose, -v          Increases the verbosity level
    --help, -h             Show usage information
    --version, -V          Show version information
    --runtime=VERSION      Use the VERSION runtime, instead of autodetecting
    --optimize=OPT         Turns on or off a specific optimization
                           Use --list-opt to get a list of optimizations
    --security[=mode]      Turns on the unsupported security manager (off by default)
                           mode is one of cas, core-clr, verifiable or validil
    --attach=OPTIONS       Pass OPTIONS to the attach agent in the runtime.
                           Currently the only supported option is 'disable'.
    --llvm, --nollvm       Controls whenever the runtime uses LLVM to compile code.
    --gc=[sgen,boehm]      Select SGen or Boehm GC (runs mono or mono-sgen)

It’s very strange that it’s not creating log files. Maybe a permissions issue with the data directory? That would blow things up quickly without producing logs too.

Try this:

$ cd RoonAppliance
$ ROON_DATAROOT=/whatever/you/have_it_set_to ./RoonAppliance -logtoconsole

Maybe there will be an error there that gives a clue

Hi @brian, will try that shortly. By the way, if you or anyone else is interested in trying this yourself I’ve put together some reproduction steps over here https://gist.github.com/edude03/1d30f505b2e28cfc50a812ba1fcad52b - all the NixOS stuff is automated so if you have the inclinations it should be pretty straightforward to test :slight_smile:

Woops, missed a step in those instructions, updating now (need to patch bash in the RoonServer script as well

OK All fixed up :slight_smile: Have at 'er

That RoonServer script gets replaced with each update…patching it might not be a great move.

@brian, so, for Roon to work on NixOS automatic update would have to be disabled. This is because NixOS keeps binaries in a read only, hash addressed volume called a “store.” This allows users to guaranty that their system is identical to another system by comparing the hashes of the dependencies.

When finished, the script would likely have to remove/patch the auto update functionality, then allow users to update the normal way using nix-env update roon or whatever.

That said, making progress on getting it started, turns out there are unpatched bash scripts in Appliance as well, with those fixed, I now get

[nix-shell:~/code/roon-nix/RoonServer/Server]$ sudo ./RoonServer
Initializing
Started

Unhandled Exception:
System.DllNotFoundException: raatmanager
  at (wrapper managed-to-native) Sooloos.RC:RC__suppress_crash_dialogs ()
  at Sooloos.RAATServerApp.ev_go () [0x0000b] in /home/roon/roon/Client/RAATServer/raatserver_app.cs:168
  at System.Threading.ThreadHelper.ThreadStart_Context (System.Object state) [0x00017] in <a8460a77e67a430a8486a9751162e5f4>:0
  at System.Threading.ExecutionContext.RunInternal (System.Threading.ExecutionContext executionContext, System.Threading.ContextCallback callback, System.Object state, System.Boolean preserveSyncCtx) [0x0008d] in <a8460a77e67a430a8486a9751162e5f4>:0
  at System.Threading.ExecutionContext.Run (System.Threading.ExecutionContext executionContext, System.Threading.ContextCallback callback, System.Object state, System.Boolean preserveSyncCtx) [0x00000] in <a8460a77e67a430a8486a9751162e5f4>:0
  at System.Threading.ExecutionContext.Run (System.Threading.ExecutionContext executionContext, System.Threading.ContextCallback callback, System.Object state) [0x00031] in <a8460a77e67a430a8486a9751162e5f4>:0
  at System.Threading.ThreadHelper.ThreadStart () [0x0000b] in <a8460a77e67a430a8486a9751162e5f4>:0
[ERROR] FATAL UNHANDLED EXCEPTION: System.DllNotFoundException: raatmanager
  at (wrapper managed-to-native) Sooloos.RC:RC__suppress_crash_dialogs ()
  at Sooloos.RAATServerApp.ev_go () [0x0000b] in /home/roon/roon/Client/RAATServer/raatserver_app.cs:168
  at System.Threading.ThreadHelper.ThreadStart_Context (System.Object state) [0x00017] in <a8460a77e67a430a8486a9751162e5f4>:0
  at System.Threading.ExecutionContext.RunInternal (System.Threading.ExecutionContext executionContext, System.Threading.ContextCallback callback, System.Object state, System.Boolean preserveSyncCtx) [0x0008d] in <a8460a77e67a430a8486a9751162e5f4>:0
  at System.Threading.ExecutionContext.Run (System.Threading.ExecutionContext executionContext, System.Threading.ContextCallback callback, System.Object state, System.Boolean preserveSyncCtx) [0x00000] in <a8460a77e67a430a8486a9751162e5f4>:0
  at System.Threading.ExecutionContext.Run (System.Threading.ExecutionContext executionContext, System.Threading.ContextCallback callback, System.Object state) [0x00031] in <a8460a77e67a430a8486a9751162e5f4>:0
  at System.Threading.ThreadHelper.ThreadStart () [0x0000b] in <a8460a77e67a430a8486a9751162e5f4>:0
Running

Repeated in a loop

We don’t support arrangements like this. You’re free to tinker, of course, but it will be in “you are on your own” territory.

For example, we don’t let hardware partners who ship Roon Server do this, and the externally-developed NAS packages that we condone are required to work with “off the shelf” packages that self-update.

Roon Server updates sometimes need to be synchronized with remote updates or updates of other components. Being mis-matched by a small amount is usually OK, but over time things get weird–newer remotes will have user interface support for things missing in the older core software, and eventually an incompatibility will be introduced. Sometimes we declare versions incompatible (1.2 vs 1.3, for example), and a truly synchronous update is required. So it’s really important that people be able to get all of the updates at once without waiting for some else to “catch up”.

I think it would be better if you treated our code more like data–let it update itself, and manage your scripts within the NixOS system (sort of like what @crieke did for QNAP and Synology).

As for that error–I bet there’s something wrong with a dependency or library path resolution. You could try running ldd on the .so's to see what might be unresolved. I think the scripts may use LD_LIBRARY_PATH–maybe something is amiss there?

Oh, wow. I got it working! Seems like it was a really minor issue after all. I threw an export in the Appliance script to see what variables are set when the application starts looking for anything that could mess with the library path and I saw

declare -x LD_LIBRARY_PATH="/home/edude03/code/roon-nix/RoonServer/Mono/lib:"

Notice the trailing : which is invalid path. This is because LD_LIBRARY_PATH isn’t normally in a closure since the binaries should have the paths hardcoded. I fixed that join in the script and it starts up :smiley:

Will report back with any other finding

Thanks @brian, yep, looks like we discovered the problem at roughly the same time haha.

While I completely understand where you’re coming from and to be honest I expected that you’d say that, I’m not sure what the exact solution would be here. While treating the code as data would make sense, it will only work for Nix if there is a way to separate the launch script from the startup script. For example, mounting anything that Roon can auto replace in a “RoonBinaries” volume or something like that, which gets mounted when the service is started up.

As you mentioned though, the problem with that is future updates will likely break the way things are patched at the moment. It’s possible to run the patch on every start or something for sure but it definitely opens up the possibility that someone will wake up to a broken server haha,

On that note - I realize that for this to work the way I have it built I’d need to vendor the current binary; I noticed that the install link doesn’t have a “version” or “hash” in the URL but nix is expecting that the defined version of Roon will always have that sha256.

So there are definitely some hurdles to overcome.

I’ll continue to tinker and report back what I find out.

1 Like