Accessing LIRC socket from a strictly confined snap?

LIRC opens a socket at /run/lirc/lircd and applications are expected to read this socket for infrared input. Is there an interface that provides access to it? Note, we currently connect to the socket in read-write mode, but we probably only need read access:

= AppArmor =
Time: Oct 29 11:21:19
Log: apparmor="DENIED" operation="connect" profile="snap.plex-htpc.plex-htpc" name="/run/lirc/lircd" pid=11062 comm="Plex" requested_mask="wr" denied_mask="wr" fsuid=1000 ouid=0
File: /run/lirc/lircd (write)
Suggestions:
* adjust program to use $SNAP_DATA
* adjust program to use /run/shm/snap.$SNAP_NAME.*
* adjust program to use /run/snap.$SNAP_NAME.*
* adjust snap to use snap layouts (https://forum.snapcraft.io/t/snap-layouts/7207)

(read access also doesn’t work if we do cat /run/lirc/lircd inside the snap). I don’t think any of the snappy-debug suggestions would allow IR input to work.

1 Like

This probably justifies a new interface in snapd to enable lircd, if you run your snap in devmode (snap install --devmode <foo.snap>`), do you get more denials? It’s unclear to me if lircd needs more than just this single file to operate.

1 Like

What about a socket interface, which would operate similarly to the content and to the (under development) shared-memory interface? That is, the lirc snap (or the base system) could be the slot providing the socket, like

slots:
  lirc:
    interface: socket
    socket: lirc
    write:
      - /run/lirc/lircd

and clients would then declare a plug like

plugs:
  lirc:
    interface: socket
    socket: lirc

It would be nice also (and I’m not sure if it’s possible to do at the moment) if the decision on whether the interface would autoconnect would be up to the slot: that’s because the slot provider knows how privacy-sensitive or secure the slot is – in the case of lirc, it would make sense to allow autoconnection.

1 Like

I’ll get back to you on this, but most likely nothing else is needed (we are straight up reading the socket from application code because the protocol is very simple).

It appears there are no other violations related to the LIRC socket in devmode (and the application correctly receives infrared input). We do have a small issue though, because it appears Qt won’t open the socket in readonly mode even if we explicitly request that. We technically only need read access. There is use for writing to LIRC for sending infrared signals (which is not something that we do, but other applications might). So if you are adding a new interface, this might be something to consider.

For context, the code accessing largely based on our open-source PMP code: https://github.com/plexinc/plex-media-player/blob/master/src/input/InputLIRC.cpp (it’s not 100% the same, but close).

Can you clarify in this case where lircd is being run inside the snap and needs to share data with non-snap applications or whether lircd is being run on the host as a non-snap and you are trying to interact with it from inside a strictly confined snap?

lircd is running on the host and we want to read its socket from inside a strictly confined snap. I’m not opposed to running lircd in the snap (though I have a feeling that it might be more difficult to securely allow, since that would be more low-level).

So in this case probably it makes sense to have a bare lirc interface, which the plug side allows access to this socket, but the slot side allows access to the socket and some day could be expanded to be able to run lircd fully confined as a strict snap on i.e. Ubuntu Core

1 Like