github.com/kubiko/snapd@v0.0.0-20201013125620-d4f3094d9ddf/interfaces/builtin/ofono.go (about)

     1  // -*- Mode: Go; indent-tabs-mode: t -*-
     2  
     3  /*
     4   * Copyright (C) 2017 Canonical Ltd
     5   *
     6   * This program is free software: you can redistribute it and/or modify
     7   * it under the terms of the GNU General Public License version 3 as
     8   * published by the Free Software Foundation.
     9   *
    10   * This program is distributed in the hope that it will be useful,
    11   * but WITHOUT ANY WARRANTY; without even the implied warranty of
    12   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    13   * GNU General Public License for more details.
    14   *
    15   * You should have received a copy of the GNU General Public License
    16   * along with this program.  If not, see <http://www.gnu.org/licenses/>.
    17   *
    18   */
    19  
    20  package builtin
    21  
    22  import (
    23  	"strings"
    24  
    25  	"github.com/snapcore/snapd/interfaces"
    26  	"github.com/snapcore/snapd/interfaces/apparmor"
    27  	"github.com/snapcore/snapd/interfaces/dbus"
    28  	"github.com/snapcore/snapd/interfaces/seccomp"
    29  	"github.com/snapcore/snapd/interfaces/udev"
    30  	"github.com/snapcore/snapd/release"
    31  	"github.com/snapcore/snapd/snap"
    32  )
    33  
    34  const ofonoSummary = `allows operating as the ofono service`
    35  
    36  const ofonoBaseDeclarationSlots = `
    37    ofono:
    38      allow-installation:
    39        slot-snap-type:
    40          - app
    41          - core
    42      deny-auto-connection: true
    43      deny-connection:
    44        on-classic: false
    45  `
    46  
    47  const ofonoPermanentSlotAppArmor = `
    48  # Description: Allow operating as the ofono service. This gives privileged
    49  # access to the system.
    50  
    51  # to create ppp network interfaces
    52  capability net_admin,
    53  
    54  # To check present devices
    55  /run/udev/data/+usb:* r,
    56  /run/udev/data/+usb-serial:* r,
    57  /run/udev/data/+pci:* r,
    58  /run/udev/data/+platform:* r,
    59  /run/udev/data/+pnp:* r,
    60  /run/udev/data/c* r,
    61  /run/udev/data/n* r,
    62  /sys/bus/usb/devices/ r,
    63  # FIXME snapd should be querying udev and adding the /sys and /run/udev accesses
    64  # that are assigned to the snap, but we are not there yet.
    65  /sys/bus/usb/devices/** r,
    66  
    67  # To get current seat, used to know user preferences like default SIM in
    68  # multi-SIM devices.
    69  /run/systemd/seats/{,*} r,
    70  
    71  # Access to modem ports
    72  # FIXME snapd should be more dynamic to avoid conflicts between snaps trying to
    73  # access same ports.
    74  /dev/tty[^0-9]* rw,
    75  /dev/cdc-* rw,
    76  /dev/modem* rw,
    77  /dev/dsp rw,
    78  /dev/chnlat11 rw,
    79  /dev/socket/rild* rw,
    80  # ofono puts ppp on top of the tun device
    81  /dev/net/tun rw,
    82  
    83  network netlink raw,
    84  network netlink dgram,
    85  network bridge,
    86  network inet,
    87  network inet6,
    88  network packet,
    89  network bluetooth,
    90  
    91  include <abstractions/nameservice>
    92  /run/systemd/resolve/stub-resolv.conf r,
    93  
    94  # DBus accesses
    95  include <abstractions/dbus-strict>
    96  
    97  # systemd-resolved (not yet included in nameservice abstraction)
    98  #
    99  # Allow access to the safe members of the systemd-resolved D-Bus API:
   100  #
   101  #   https://www.freedesktop.org/wiki/Software/systemd/resolved/
   102  #
   103  # This API may be used directly over the D-Bus system bus or it may be used
   104  # indirectly via the nss-resolve plugin:
   105  #
   106  #   https://www.freedesktop.org/software/systemd/man/nss-resolve.html
   107  #
   108  dbus send
   109       bus=system
   110       path="/org/freedesktop/resolve1"
   111       interface="org.freedesktop.resolve1.Manager"
   112       member="Resolve{Address,Hostname,Record,Service}"
   113       peer=(name="org.freedesktop.resolve1"),
   114  
   115  dbus (send)
   116      bus=system
   117      path=/org/freedesktop/DBus
   118      interface=org.freedesktop.DBus
   119      member={Request,Release}Name
   120      peer=(name=org.freedesktop.DBus, label=unconfined),
   121  
   122  # Allow binding the service to the requested connection name
   123  dbus (bind)
   124      bus=system
   125      name="org.ofono",
   126  
   127  # Allow traffic to/from our path and interface with any method for unconfined
   128  # clients to talk to our ofono services.
   129  dbus (receive, send)
   130      bus=system
   131      path=/{,**}
   132      interface=org.ofono.*
   133      peer=(label=unconfined),
   134  `
   135  
   136  const ofonoConnectedSlotAppArmor = `
   137  # Allow service to interact with connected clients
   138  
   139  # Allow traffic to/from our interfaces. The path depends on the modem plugin,
   140  # and is arbitrary.
   141  dbus (receive, send)
   142      bus=system
   143      path=/{,**}
   144      interface=org.ofono.*
   145      peer=(label=###PLUG_SECURITY_TAGS###),
   146  `
   147  
   148  const ofonoConnectedPlugAppArmor = `
   149  # Description: Allow using Ofono service. This gives privileged access to the
   150  # Ofono service.
   151  
   152  #include <abstractions/dbus-strict>
   153  
   154  # Allow all access to ofono services
   155  dbus (receive, send)
   156      bus=system
   157      path=/{,**}
   158      interface=org.ofono.*
   159      peer=(label=###SLOT_SECURITY_TAGS###),
   160  
   161  # Allow clients to introspect the service on non-classic (due to the path,
   162  # allowing on classic would reveal too much for unconfined)
   163  dbus (send)
   164      bus=system
   165      path=/
   166      interface=org.freedesktop.DBus.Introspectable
   167      member=Introspect
   168      peer=(label=###SLOT_SECURITY_TAGS###),
   169  `
   170  
   171  const ofonoConnectedPlugAppArmorClassic = `
   172  # Allow access to the unconfined ofono services on classic.
   173  dbus (receive, send)
   174      bus=system
   175      path=/{,**}
   176      interface=org.ofono.*
   177      peer=(label=unconfined),
   178  
   179  # Don't allow introspection since it reveals too much (path is not service
   180  # specific for unconfined)
   181  #dbus (send)
   182  #    bus=system
   183  #    path=/
   184  #    interface=org.freedesktop.DBus.Introspectable
   185  #    member=Introspect
   186  #    peer=(label=unconfined),
   187  `
   188  
   189  const ofonoPermanentSlotSecComp = `
   190  # Description: Allow operating as the ofono service. This gives privileged
   191  # access to the system.
   192  
   193  # Communicate with DBus, netlink, rild
   194  accept
   195  accept4
   196  bind
   197  listen
   198  socket AF_NETLINK - NETLINK_ROUTE
   199  # libudev
   200  socket AF_NETLINK - NETLINK_KOBJECT_UEVENT
   201  `
   202  
   203  const ofonoPermanentSlotDBus = `
   204  <!-- Comes from src/ofono.conf in sources -->
   205  
   206  <policy user="root">
   207    <allow own="org.ofono"/>
   208    <allow send_destination="org.ofono"/>
   209    <allow send_interface="org.ofono.SimToolkitAgent"/>
   210    <allow send_interface="org.ofono.PushNotificationAgent"/>
   211    <allow send_interface="org.ofono.SmartMessagingAgent"/>
   212    <allow send_interface="org.ofono.PositioningRequestAgent"/>
   213    <allow send_interface="org.ofono.HandsfreeAudioAgent"/>
   214  </policy>
   215  
   216  <policy context="default">
   217    <deny send_destination="org.ofono"/>
   218    <!-- Additional restriction in next line (not in ofono.conf) -->
   219    <deny own="org.ofono"/>
   220  </policy>
   221  `
   222  
   223  const ofonoPermanentSlotUDev = `
   224  ## Concatenation of all ofono udev rules (plugins/*.rules in ofono sources)
   225  ## Note that ofono uses this for very few modems and that in most cases it finds
   226  ## modems by checking directly in code udev events, so changes here will be rare
   227  
   228  ## plugins/ofono.rules
   229  # do not edit this file, it will be overwritten on update
   230  
   231  ACTION!="add|change", GOTO="ofono_end"
   232  
   233  # ISI/Phonet drivers
   234  SUBSYSTEM!="net", GOTO="ofono_isi_end"
   235  ATTRS{type}!="820", GOTO="ofono_isi_end"
   236  KERNELS=="gadget", GOTO="ofono_isi_end"
   237  
   238  # Nokia N900 modem
   239  SUBSYSTEMS=="hsi", ENV{OFONO_DRIVER}="n900", ENV{OFONO_ISI_ADDRESS}="108"
   240  KERNEL=="phonet*", ENV{OFONO_DRIVER}="n900", ENV{OFONO_ISI_ADDRESS}="108"
   241  
   242  # STE u8500
   243  KERNEL=="shrm0", ENV{OFONO_DRIVER}="u8500"
   244  
   245  LABEL="ofono_isi_end"
   246  
   247  SUBSYSTEM!="usb", GOTO="ofono_end"
   248  ENV{DEVTYPE}!="usb_device", GOTO="ofono_end"
   249  
   250  # Ignore fake serial number
   251  ATTRS{serial}=="1234567890ABCDEF", ENV{ID_SERIAL_SHORT}=""
   252  
   253  # Nokia CDMA Device
   254  ATTRS{idVendor}=="0421", ATTRS{idProduct}=="023e", ENV{OFONO_DRIVER}="nokiacdma"
   255  ATTRS{idVendor}=="0421", ATTRS{idProduct}=="00b6", ENV{OFONO_DRIVER}="nokiacdma"
   256  
   257  # Lenovo H5321gw 0bdb:1926
   258  ATTRS{idVendor}=="0bdb", ATTRS{idProduct}=="1926", ENV{OFONO_DRIVER}="mbm"
   259  
   260  LABEL="ofono_end"
   261  
   262  ## plugins/ofono-speedup.rules
   263  # do not edit this file, it will be overwritten on update
   264  
   265  ACTION!="add|change", GOTO="ofono_speedup_end"
   266  
   267  SUBSYSTEM!="tty", GOTO="ofono_speedup_end"
   268  KERNEL!="ttyUSB[0-9]*", GOTO="ofono_speedup_end"
   269  
   270  # SpeedUp 7300
   271  ATTRS{idVendor}=="1c9e", ATTRS{idProduct}=="9e00", ENV{ID_USB_INTERFACE_NUM}=="00", ENV{OFONO_LABEL}="modem"
   272  ATTRS{idVendor}=="1c9e", ATTRS{idProduct}=="9e00", ENV{ID_USB_INTERFACE_NUM}=="03", ENV{OFONO_LABEL}="aux"
   273  
   274  # SpeedUp
   275  ATTRS{idVendor}=="2020", ATTRS{idProduct}=="1005", ENV{ID_USB_INTERFACE_NUM}=="03", ENV{OFONO_LABEL}="modem"
   276  ATTRS{idVendor}=="2020", ATTRS{idProduct}=="1005", ENV{ID_USB_INTERFACE_NUM}=="01", ENV{OFONO_LABEL}="aux"
   277  
   278  ATTRS{idVendor}=="2020", ATTRS{idProduct}=="1008", ENV{ID_USB_INTERFACE_NUM}=="03", ENV{OFONO_LABEL}="modem"
   279  ATTRS{idVendor}=="2020", ATTRS{idProduct}=="1008", ENV{ID_USB_INTERFACE_NUM}=="01", ENV{OFONO_LABEL}="aux"
   280  
   281  # SpeedUp 9800
   282  ATTRS{idVendor}=="1c9e", ATTRS{idProduct}=="9800", ENV{ID_USB_INTERFACE_NUM}=="01", ENV{OFONO_LABEL}="modem"
   283  ATTRS{idVendor}=="1c9e", ATTRS{idProduct}=="9800", ENV{ID_USB_INTERFACE_NUM}=="02", ENV{OFONO_LABEL}="aux"
   284  
   285  # SpeedUp U3501
   286  ATTRS{idVendor}=="1c9e", ATTRS{idProduct}=="9605", ENV{ID_USB_INTERFACE_NUM}=="03", ENV{OFONO_LABEL}="modem"
   287  ATTRS{idVendor}=="1c9e", ATTRS{idProduct}=="9605", ENV{ID_USB_INTERFACE_NUM}=="01", ENV{OFONO_LABEL}="aux"
   288  
   289  LABEL="ofono_speedup_end"
   290  `
   291  
   292  type ofonoInterface struct{}
   293  
   294  func (iface *ofonoInterface) Name() string {
   295  	return "ofono"
   296  }
   297  
   298  func (iface *ofonoInterface) StaticInfo() interfaces.StaticInfo {
   299  	return interfaces.StaticInfo{
   300  		Summary:              ofonoSummary,
   301  		ImplicitOnClassic:    true,
   302  		BaseDeclarationSlots: ofonoBaseDeclarationSlots,
   303  	}
   304  }
   305  
   306  func (iface *ofonoInterface) AppArmorConnectedPlug(spec *apparmor.Specification, plug *interfaces.ConnectedPlug, slot *interfaces.ConnectedSlot) error {
   307  	old := "###SLOT_SECURITY_TAGS###"
   308  	new := slotAppLabelExpr(slot)
   309  	spec.AddSnippet(strings.Replace(ofonoConnectedPlugAppArmor, old, new, -1))
   310  	if release.OnClassic {
   311  		// Let confined apps access unconfined ofono on classic
   312  		spec.AddSnippet(ofonoConnectedPlugAppArmorClassic)
   313  	}
   314  	return nil
   315  
   316  }
   317  
   318  func (iface *ofonoInterface) AppArmorPermanentSlot(spec *apparmor.Specification, slot *snap.SlotInfo) error {
   319  	spec.AddSnippet(ofonoPermanentSlotAppArmor)
   320  	return nil
   321  }
   322  
   323  func (iface *ofonoInterface) DBusPermanentSlot(spec *dbus.Specification, slot *snap.SlotInfo) error {
   324  	spec.AddSnippet(ofonoPermanentSlotDBus)
   325  	return nil
   326  }
   327  
   328  func (iface *ofonoInterface) UDevPermanentSlot(spec *udev.Specification, slot *snap.SlotInfo) error {
   329  	spec.AddSnippet(ofonoPermanentSlotUDev)
   330  	/*
   331  	   1.Linux modem drivers set up the modem device /dev/modem as a symbolic link
   332  	     to the actual device to /dev/ttyS*
   333  	   2./dev/socket/rild is just a socket, not device node created by rild daemon.
   334  	     Similar case for chnlat*.
   335  	   So we intetionally skipped modem, rild and chnlat.
   336  	*/
   337  	spec.TagDevice(`KERNEL=="tty[a-zA-Z]*[0-9]*|cdc-wdm[0-9]*"`)
   338  	spec.TagDevice(`KERNEL=="tun"`)
   339  	spec.TagDevice(`KERNEL=="dsp"`)
   340  	return nil
   341  }
   342  
   343  func (iface *ofonoInterface) AppArmorConnectedSlot(spec *apparmor.Specification, plug *interfaces.ConnectedPlug, slot *interfaces.ConnectedSlot) error {
   344  	old := "###PLUG_SECURITY_TAGS###"
   345  	new := plugAppLabelExpr(plug)
   346  	spec.AddSnippet(strings.Replace(ofonoConnectedSlotAppArmor, old, new, -1))
   347  	return nil
   348  }
   349  
   350  func (iface *ofonoInterface) SecCompPermanentSlot(spec *seccomp.Specification, slot *snap.SlotInfo) error {
   351  	spec.AddSnippet(ofonoPermanentSlotSecComp)
   352  	return nil
   353  }
   354  
   355  func (iface *ofonoInterface) AutoConnect(*snap.PlugInfo, *snap.SlotInfo) bool {
   356  	// allow what declarations allowed
   357  	return true
   358  }
   359  
   360  func init() {
   361  	registerIface(&ofonoInterface{})
   362  }