Chapter 2. Profile Components and Syntax

Contents

2.1. Breaking a Novell AppArmor Profile into Its Parts
2.2. #include Statements
2.3. Capability Entries (POSIX.1e)
2.4. Using the Local AppArmor Profile Repository

You are ready to build Novell AppArmor profiles after you select the programs to profile. To do so, it is important to understand the components and syntax of profiles. AppArmor profiles contain several building blocks that help build simple and reusable profile code: #include files, abstractions, program chunks, and capability entries. #include statements are used to pull in parts of other AppArmor profiles to simplify the structure of new profiles. Abstractions are #include statements grouped by common application tasks. Program chunks are chunks of profiles that are specific to program suites. Capability entries are profile entries for any of the POSIX.1e Linux capabilities.

For help determining the programs to profile, refer to Section 1.2, “Determining Programs to Immunize”. To start building AppArmor profiles with YaST, proceed to Chapter 3, Building and Managing Profiles with YaST. To build profiles using the AppArmor command line interface, proceed to Chapter 4, Building Profiles from the Command Line.

2.1. Breaking a Novell AppArmor Profile into Its Parts

Novell AppArmor profile components are called Novell AppArmor rules. Currently there are two main types of Novell AppArmor rules, path entries and capability entries. Path entries specify what the process can access in the file system and capability entries provide a more fine-grained control over what a confined process is allowed to do through other system calls that require privileges. Includes are a type of meta rule or directives that pull in path and capability entries from other files.

The easiest way of explaining what a profile consists of and how to create one is to show the details of a sample profile, in this case for a hypothetical application called /usr/bin/foo:

#include <tunables/global>1

# a comment naming the application to confine
/usr/bin/foo2
{3
   #include <abstractions/base>4

   capability setgid5,

   /bin/mount          ux,
   /dev/{,u}6random     r,
   /etc/ld.so.cache    r,
   /etc/foo.conf       r,
   /etc/foo/*          r,
   /lib/ld-*.so*       mr,
   /lib/lib*.so*       mr,
   /proc/[0-9]**       r,
   /usr/lib/**         mr,
   /tmp/7               r,
   /tmp/foo.pid        wr,
   /tmp/foo.*          lrw,
   /@{HOME}8/.foo_file  rw,
   /@{HOME}/.foo_lock  w,

  # a comment about foo's subprofile, bar.
   ^bar9 {
    /lib/ld-*.so*       mr,
    /usr/bin/bar        px,
    /var/spool/*        rwl,
   } 
}

1

This loads a file containing variable definitions.

2

The normalized path to the program that is confined.

3

The curly braces ({}) serve as a container for include statements, subprofiles, path entries, and capability entries.

4

This directive pulls in components of AppArmor profiles to simplify profiles.

5

Capability entry statements enable each of the 29 POSIX.1e draft capabilities.

6

The curly braces ({}) make this rule apply to the path both with and without the content enclosed by the braces.

7

A path entry specifying what areas of the file system the program can access. The first part of a path entry specifies the absolute path of a file (including regular expression globbing) and the second part indicates permissible access modes (r for read, w for write, and x for execute). A whitespace of any kind (spaces or tabs) can precede pathnames or separate the pathname from the access modes. Spaces between the access mode and the trailing comma is optional. Find a comprehensive overview of the available access modes in Section 4.8, “File Permission Access Modes”.

8

This variable expands to a value that can be changed without changing the entire profile.

9

This section references a subprofile of the application, also known as a hat. For more details on AppArmor's ChangeHat feature, refer to Chapter 5, Profiling Your Web Applications Using ChangeHat.

[Tip]Using Variables in Profiles

With the current AppArmor tools, variables as presented in the above example can only be used when manually editing and maintaining a profile.

A typical example when variables come in handy are network scenarios in which user home directories are not mounted in the standard location /home/username, but under a custom location. Find the variable definitions for this use case (@{HOME} and @{HOMEDIRS}) in the /etc/apparmor.d/tunables/home file.

When a profile is created for a program, the program can access only the files, modes, and POSIX capabilities specified in the profile. These restrictions are in addition to the native Linux access controls.

Example: .  To gain the capability CAP_CHOWN, the program must have both access to CAP_CHOWN under conventional Linux access controls (typically, be a root-owned process) and have the capability chown in its profile. Similarly, to be able to write to the file /foo/bar the program must have both the correct user ID and mode bits set in the files attributes (see the chmod and chown man pages) and have /foo/bar w in its profile.

Attempts to violate Novell AppArmor rules are recorded in /var/log/audit/audit.log if the audit package is installed or otherwise in /var/log/messages. In many cases, Novell AppArmor rules prevent an attack from working because necessary files are not accessible and, in all cases, Novell AppArmor confinement restricts the damage that the attacker can do to the set of files permitted by Novell AppArmor.

2.2. #include Statements

#include statements are directives that pull in components of other Novell AppArmor profiles to simplify profiles. Include files fetch access permissions for programs. By using an include, you can give the program access to directory paths or files that are also required by other programs. Using includes can reduce the size of a profile.

By default, AppArmor adds /etc/apparmor.d to the path in the #include statement. AppArmor expects the include files to be located in /etc/apparmor.d. Unlike other profile statements (but similar to C programs), #include lines do not end with a comma.

To assist you in profiling your applications, Novell AppArmor provides two classes of #includes: abstractions and program chunks.

2.2.1. Abstractions

Abstractions are #includes that are grouped by common application tasks. These tasks include access to authentication mechanisms, access to name service routines, common graphics requirements, and system accounting. Files listed in these abstractions are specific to the named task. Programs that require one of these files usually require some of the other files listed in the abstraction file (depending on the local configuration as well as the specific requirements of the program). Find abstractions in /etc/apparmor.d/abstractions.

2.2.2. Program Chunks

The program-chunks directory (/etc/apparmor.d/program-chunks) contains some chunks of profiles that are specific to program suites and not generally useful outside of the suite, thus are never suggested for use in profiles by the profile wizards (aa-logprof and aa-genprof). Currently program chunks are only available for the postfix program suite.

2.3. Capability Entries (POSIX.1e)

Capabilities statements are simply the word capability followed by the name of the POSIX.1e capability as defined in the capabilities(7) man page.

2.4. Using the Local AppArmor Profile Repository

AppArmor ships a set of profiles enabled by default and created by the AppArmor developers and kept under the /etc/apparmor.d. In addition to these profiles, SUSE Linux Enterprise ships profiles for individual applications together with the respective application. These profiles are not enabled by default and reside under another directory than the standard AppArmor profiles, /etc/apparmor/profiles/extras.

The AppArmor tools, both YaST and aa-genprof and aa-logprof, support the use of a local repository. Whenever you start to create a new profile from scratch and there already is one inactive profile in your local repository, you are asked whether you would like to use the existing inactive one from /etc/apparmor/profiles/extras and whether you want to base your efforts on it. If you decide to use this profile, it gets copied over to the directory of profiles enabled by default (/etc/apparmor.d) and loaded whenever AppArmor is started. Any further further adjustments will be done to the active profile under /etc/apparmor.d.