SecurityPermissions
Ubuntu has two systems for controlling whether users and apps can perform particular tasks.
Snap interfaces (the ends of which are called plugs and slots) give apps in snap packages access to particular resources, such as a connected camera, the device location, or part of the fileystem.
PolicyKit (Ubuntu package, Ubuntu bug reports) gives user accounts the ability to perform particular actions, such as installing or removing system-wide software.
Both systems involve authentication prompts.
Contents
Snap interfaces
If an app tries to access any of these interfaces, it should be subject to permission:
Interface |
Permission label |
Prompt text |
unity8-calendar |
Calendar |
wants to read/change your calendar |
|
Camera |
wants to take photos |
unity8-contacts |
Contacts |
wants to read/change your contacts |
|
In-app purchases |
wants to offer in-app purchases |
|
Location |
wants to track your location |
|
Microphone |
wants to use the microphone |
|
Video recording |
wants to record video |
online-accounts-service |
||
physical-memory-observe |
||
storage-framework-service |
“Video recording” should be separate from “Camera” so that:
- When you use a camera app, having prompted you for access to the camera on first launch, it then prompts you for access to “record video” rather than weirdly “the microphone” when you first access the video function.
When you use any app that records only video — such as Periscope or Ustream — it needs to prompt you only once, rather than separately for the camera and microphone.
Therefore, if an app has permission to record video, it should have access to the microphone when (and only when) it is recording video.
(In Ubuntu Touch, sometimes an app needed access only to a single stored item — for example, a single contact or a single photo. In this case, the app accessed it through the content picker, rather than asking for access to all items of that type.)
App labels
So that apps are identified consistently in permission prompts, lists, and elsewhere:
Normally, an app label should be the app’s name: in the case of a snap, its title. (“Installed apps:” also lists apps that are not snaps, since people can’t generally be expected to know and remember which are and which aren’t.)
If a .deb and a snap of the same app are installed, the app label should end with “ (.deb)” or “ (snap)”: for example, “JazzWriter (.deb)”. (If they have installed both, someone can be expected to understand the difference.)
If snaps have identical titles but the publisher is different, the app label should end with the publisher username in brackets: for example, “JazzWriter (Snapcrafters)”.
If snaps’ title and publisher are identical but the version number is different, the app label should end with the version number in brackets: for example, “MegaChess (1.0.1)”.
In the diabolical case where the title, publisher, and even version number are identical, the version number should be followed by “r” and the revision number: for example, “MegaChess (1.0.1 r67)”.
Permission prompts
All these prompts should take the form of a dialog that contains:
- the app icon
the app label, sanitized and ellipsized if necessary
- the app ID and publisher ID, in small print.
(The app icon, ellipsized label, app ID, and publisher ID are to protect against one app spoofing a different app.)
The layout of the prompts forms a sentence similar to structure “{app} wants to {do something}”. In some languages it may not be grammatically possible to construct a sentence this way. If so, in that language the prompt text should instead be a complete sentence of its own referring to the app above: “This app wants to {do something}.” Each prompt text string should have a translator note explaining this.
For all these prompts, because you are likely not expecting it, neither button should be default.
For all prompts that show a list of permissions:
- The list should be a fixed height, scrolling if necessary.
- To clarify that it does scroll (and so prevent scurrilous permissions hiding below innocuous ones), the height should be such that a line of text is half-clipped at the bottom.
Installing an app with required interfaces
If all the interfaces have installed implementations
This prompt should appear before the software begins to download.
If any of the interfaces do not have installed implementations
This prompt should appear before the software begins to download. In rare cases, this prompt will appear immediately after the previous one.
Launching an app with required interfaces, any without an installed implementation
This is the unusual case where you chose “Install Anyway” above, still didn’t install the needed software, and then tried to launch the app regardless. (Or you installed the app while having implementations of all necessary interfaces, and later removed one or more of the implementations.)
This dialog should be parentless, and therefore it should have “Ubuntu” as its title (the entity perceived to be responsible for launching apps).
App tries to use an optional interface at runtime
To prevent an app DoSing you into submission, if it tries to access an interface and you have previously denied it, it should silently be denied again. It’s then up to the app to either do without, or to plead with you to change it with a button for opening the relevant System Settings screen.
If you have not previously denied it, a prompt should open.
If the app does not currently have any windows open, the prompt should be parentless and therefore should have “Ubuntu” as its title. Otherwise, if the app has any windows open, then:
- if one of them is the focused window, that should be the dialog’s parent;
- if none of them have input focus, the frontmost window should be the dialog’s parent.
If the interface has an installed implementation
|
Ubuntu for PC |
Ubuntu Touch (retired) |
For the first two seconds |
||
Afterwards |
To avoid clickjacking an “Allow” click, the buttons should be disabled for the first two seconds that the prompt is open. For visual reassurance, a determinate spinner should fill over that two seconds.
If the interface does not have an installed implementation
As well as launching your snap client to the appropriate search, “Search Ubuntu Store…” should deny the app permission (to avoid blocking its UI for the whole time you are browsing). But the app should automatically be removed from the blacklist, so that it can prompt again, when either (a) 24 hours has passed or (b) you’ve installed any software that provides the interface.
Permission lists
When you make a choice, in any of those prompts, to allow or deny a permission, that app should be added to the relevant access list(s) in System Settings (if it wasn’t there already), with its toggle switch state corresponding to your response. If an app is uninstalled, the setting should be cleared, so that it doesn’t show up in the permission lists (bug 1389775) — and so that, for lower-knowledge users, reinstalling works as a way of correcting a mistaken decision.
“App Permissions”
“App Permissions” is the global list of installed interface permissions, and apps that have access to each.
This list alone could be a minimal implementation, since it at least provides access to each app×permission combination, though some will not be where people expect to find them.
“View by app”
Ubuntu for PC |
“View by app” should be the default selection, since for the most privacy- or security-concerning permissions, users are likely to look in the relevant tab (Location, Camera) or panel (Sound, Networking, or Printing) instead once app permissions are integrated there.
When “View by app” is selected:
“Installed apps:” should list all detected installed apps, each with its icon and label. If the list takes more than two seconds to load, it should load incrementally if possible, with a spinner above the top right corner. Alternatively, if the list can’t load incrementally, the listbox should be empty for up to two seconds, and then contain a centered spinner and text “Indexing… ({current number of apps})” until loading is complete.
- “Installed apps:” should always have exactly one app selected, so that the second pane is always “Permissions for {app label}:”. (If the app list is empty, the permissions pane should be both empty and unlabelled.)
“Permissions for {app label}:” should list all interfaces that the app has requested access to: first any that have a permission label (sorted alphabetically by label), then any that don’t (sorted alphabetically by interface name), with a separator between the groups if they are both present. Permissions that can be changed should have a switch representing the current state.
If the app is unconfined (whether classic, devmode, or .deb), the pane should instead contain centered text: “This app is unconfined. It can access all personal files and system resources.”
- The caption “Any apps not listed here are unconfined, with access to all personal files and system resources.” covers apps that are not detected because they were built from source, installed in your home folder, and so on.
“View by permission”
Ubuntu for PC |
Ubuntu Touch (retired) |
|
When “View by permission” is selected:
“Permissions:” should list all interfaces that have an installed implementation: first any that have a permission label (sorted alphabetically), then any that don’t (sorted alphabetically by interface name), with a separator between the groups if they are both present.
- The list item for each permission should have a grey summary value, of the form “{number of apps granted}/{number of apps requested}”, for example “7/9 or “0/1”. If no apps have requested access to that property yet, the summary value for the permission should simply be “0”.
- “Apps that requested this permission:” should list first any that required the permission on install (labelled “Required”), then any that requested the permission at runtime (labelled “Optional”), with a separator between the groups if they are both present. Permissions that can be changed should have a switch representing the current state.
The caption “Apps may also request access to Internet accounts.”, and button navigating to Internet Accounts settings, reflects that those are not snap interfaces but that they behave similarly and users likely think of them similarly.
Location permissions
TBD
Camera permissions
TBD
Audio permissions
TBD
Printing permissions
TBD
Why did we take this approach?
Older versions of Android ask you to grant access to every permission an app might need before you install it. This is poor design for two reasons.
First, of all the time you spend with an app, the moment you’re about to install it is the moment when you know the least about it. So it’s the moment when you’re least able to make informed decisions about granting those privileges. And if an app developer can assume that consent will be uninformed, they're more likely to abuse that consent, by asking for privileges they don’t really need.
Second, an app might need a privilege only for an uncommon function that you personally will never use. Asking for that permission before installation would give you the wrong idea about how invasive the app is.
Both these problems are addressed by apps asking for access privileges at the moment they need them. It is still possible that an app might ask for a privilege needlessly, or without enough explanation on launch. But if so, you would likely downrate and/or uninstall it.
PolicyKit
Authentication API
A request for authentication should have:
The action that you are trying to perform. This includes a plain-text description of why you are being asked to authenticate, and a group of user accounts that are allowed to perform the action. In PolicyKit, these are specified in .policy files.
An optional parent window. This is so that the authentication dialog can be modal to that window.
The prompt
The authentication prompt should vary in appearance depending on whether it has a parent window, who you are logged in as, who you need to authenticate as, which authentication methods are required, and whether you previously authenticated unsuccessfully.
Title and placement
If the request for authentication has a parent window, and that window is still open, then the alert should be modal to the parent window (fixing bug 420641 and bug 877265) and should have no title.
Otherwise, the alert should have the title “Authenticate”, and should not be modal to anything (see bug 797960), so it should be minimizable.
Icon
As long as full-screen programs and screenshots are both allowed, it is impossible to style an authentication prompt in a way that prevents spoofing by a program running on your computer. For example, a system-modal shell-integrated prompt could easily be spoofed by taking a screenshot, displaying it full-screen, applying the same visual effects the real prompt does, and embedding an imitation prompt. If a baddie’s unconfined program is running on your computer, you’ve already lost.
What we can do, however, is to reduce the feasibility of spoofing the prompt on a remote Web page. We do this by using something that you know but Web sites don’t: the icon of your Ubuntu user account.
Therefore, the icon for the prompt should be the standard keyring icon, overlaid in its bottom-right quarter with your Ubuntu user account icon.
(This is still subject to the Simon-says problem: you have to notice that the icon is missing to realize that it’s a spoof. But it’s better than nothing.)
After an authentication error, the icon should be the standard error icon, overlaid with your Ubuntu user account icon in the same way.
Primary text
The primary text of the alert should be the message for the action.
Secondary text
Normal prompt |
If only password authentication is required |
If other authentication is required |
If you are in the allowed group |
Ubuntu needs you to enter your login password. |
Ubuntu needs you to authenticate. |
If you aren’t in the allowed group, which is admin (fixing bug 920174) |
Ubuntu needs an administrator to authenticate. |
|
If you aren’t in the allowed group, which is anything else (fixing bug 961473) |
Ubuntu needs a member of the “{name of group}” group to authenticate. |
After incorrect authentication |
If only password authentication is required |
If other authentication is required |
If you are in the allowed group |
Your Ubuntu login password was incorrect. Please try again. |
Your authentication details were incorrect. Please try again. |
If you aren’t in the allowed group, which is admin |
Your administrator authentication details were incorrect. Please try again. |
|
If you aren’t in the allowed group, which is anything else |
Your “{name of group}” authentication details were incorrect. Please try again. |
Credential fields
If you are not in the allowed group, the first control should be “Login name:” (fixing bug 437508). This should be a combo box if you have permission to see the list of user accounts in the allowed group, or a text field if you don’t.
Next should be whichever credential fields are required for the user account, action, or group. “Password:” should be a standard password field. If a fingerprint or smart card can be used either for identification or authentication, “Fingerprint:” or “Smart card:” should be a slowly-animating scanner icon with the text “Scanning…”, replaced by a checkmark icon and the text “Scanned” once it is.
When the prompt opens, the first credential field should be focused, for example the “Password:” field if there is no “Login name:” field.
Details
“Details” should always be collapsed by default. Expanding it should reveal a two-column table in small font, of “Vendor:”, “Program:”, and “Action:”, aligned with the credential fields above. Only the “Vendor” value should be a hyperlink to the vendor’s Web site.
Commit buttons
“Cancel” should have Esc as its access key, “Continue” should have Enter. “Continue” should be insensitive whenever you have not provided the appropriate credentials, for example when the “Password:” field is empty.
When you choose “Continue”, all the controls in the prompt should become insensitive while the authentication takes place. If it succeeds, the prompt should close. If it fails, the icon and secondary text should change to their error states, and the controls should become sensitive again.
SecurityPermissions (last edited 2018-03-01 12:30:32 by mpt)