Forums

Skip to content

Advanced search
  • Quick links
    • Unanswered topics
    • Active topics
    • Search
  • FAQ
  • Login
  • Register
  • Board index Discussion & Documentation Documentation, Tips & Tricks
  • Search

HOWTO: Grsecurity quickstarting RBAC roles for Gentoo (x86)

Unofficial documentation for various parts of Gentoo Linux. Note: This is not a support forum.
Post Reply
Advanced search
3 posts • Page 1 of 1
Author
Message
schmeggahead
Guru
Guru
User avatar
Posts: 314
Joined: Tue Feb 25, 2003 3:28 am
Location: Columbus, Ohio

HOWTO: Grsecurity quickstarting RBAC roles for Gentoo (x86)

  • Quote

Post by schmeggahead » Sat Jan 30, 2010 10:01 pm

HOWTO: Grsecurity quickstarting RBAC roles for Gentoo (x86) Version 0.3

This guide is primarily addressing the Rule Based Access Control (RBAC) within grsecurity enhancements to the kernel.

The current guide is located here: http://www.gentoo.org/proj/en/hardened/grsecurity.xml
The current wiki book for the roles definition is here: http://en.wikibooks.org/wiki/Grsecurity/The_RBAC_System
Note: the wikibook is extensive but it is not obvious how to access various values in the RBAC policy statement. There are links to the value lists but they are not in the table of contents. Inside the "complete formal definition", click on these words to see valid values:
  • role mode
  • subject mode
  • object mode
  • capability name
  • resource name
  • pax flag
  • resource restrictions
I used this guide to bring up several systems and below is a sequence to start up that worked well for me compared to the dozen or so other more difficult routes to a successful grsecurity RBAC capable system with a minimal access policy.
  1. Prepare

    1. Requirements
    2. use the hardened stage and hardened-sources
    3. installed sys-apps/gradm package (version I used 2.1.13.200902232204-r1)
    4. bootable system
    5. kernel with grsecurity enabled (follow the guide section 3 RBAC) (Note: grsecurity is not enabled by default. However, in the hardened kernel configuration menus, many of the options are force selected once grsecurity is enabled. Reading the help on the few remaining choices is not that onerous)
    6. parts of the standard guide regarding learning roles and sysctl NOT completed

      So what you have now is a system that is booting with grsecurity enabled in the kernel but the RBAC system is off.
  2. Setup Passwords and Startup Learning
    1. Set your password for the RBAC system. Ensure this is a ridiculously hard password on a production system. On my dev system I make this easy because it is protected and not web accessible and wiped regularly.

      Code: Select all

      #/sbin/gradm -P
    2. set your admin password:

      Code: Select all

      #/sbin/gradm -P admin
      Note: I like to set an admin password and roles for admin that are more a decoy than the real admin role I use. I name my admin role something like omni and give it the rules admin normally receives. This means that even if the admin password is hacked, they cannot transition to another role and waste their time hacking that, hopefully leaving a trail in /var/log/kern.log such as:
      • Jan 30 10:55:32 localhost kernel: [75498.299128] grsec: From 192.168.0.3: (root:U:/sbin/gradm) special role admin failure for /sbin/gradm[gradm:9324] uid/euid:0/0 gid/egid:0/0, parent /bin/bash[bash:8846] uid/euid:0/0 gid/egid:0/0
    3. set the init script to start gradm at startup:

      Code: Select all

      #nano -w /etc/conf.d/local.start
      then insert the bottom two lines:

      Code: Select all

      # /etc/conf.d/local.start
      
      # This is a good place to load any misc programs
      # on startup (use &>/dev/null to hide output)
      /sbin/gradm -F -L /gradm.initial.learning.log
      #/sbin/gradm -E
      
      we'll come back to this setup down further

      Note: I did create an init script for init.d and conf.d companion but since this is not a daemon using start-stop-daemon is totally overkill and local.start & local.stop work better. (thanks Hopeless!) I filed a bug report to have local.start local.stop added to the initscript doc in the handbook.
    4. now add the shutdown to local.stop

      Code: Select all

      #nano -w /etc/conf.d/local.stop
      then insert the bottom line below:

      Code: Select all

      # /etc/conf.d/local.stop
      
      # This is a good place to unload any misc.
      # programs you started above.
      # For example, if you are using OSS and have
      # "/usr/local/bin/soundon" above, put
      # "/usr/local/bin/soundoff" here.
      
      /sbin/gradm -D
      
      [TODO: modify the script to check if RBAC is enabled. Better yet, I would prefer that the shutdown doesn't proceed because it makes a big mess if the RBAC system is enabled and requires resetting the system to restart. Adding all the rules for shutdown opens up a lot of access during normal operation, so I avoid it.]
  3. Create Initial Learned Roles and Manage Learning
    1. Now, ensure that all of the services required on the system are enabled at startup (Note: if you add them in the future, you can repeat this learning process) then reboot the system:

      Code: Select all

      shutdown -r now
      Note: upon reboot, if you use gpm, move the mouse on the terminal to ensure those accesses are logged otherwise there will be no rules for gpm. However, it is easy enough to generate those rules later. Also logging into each console that permits a user login will include those in the roles. Transition to su will also be a time saver. Since I limit root login to a single console, I perform that login as well. If you plan to connect and disconnect usb devices, do this also so the rules are added. I'm assuming no X at this point because I have been working with servers. [TODO: add X capability to the process.]

      This creates a learning log in /gradm.initial.learning.log file that can be used to generate roles (which is another term for a policy statement).
    2. To generate the intial policy statement:

      Code: Select all

      #/sbin/gradm -F -L /gradm.initial.learning.log -O /gradm.initial.learning.roles
    3. Now you have your first policy, so put it where it will be useful.

      Code: Select all

      #cat /gradm.initial.learning.roles >> /etc/grsec/policy
      and clean up

      Code: Select all

      #rm /gradm.initial.learning*
    4. Then set to autostart rather than autolearn:

      Code: Select all

      #nano -w /etc/conf.d/local.start
      then insert:

      Code: Select all

      # /etc/conf.d/local.start
      
      # This is a good place to load any misc programs
      # on startup (use &>/dev/null to hide output)
      #/sbin/gradm -F -L /gradm.initial.learning.log
      /sbin/gradm -E
      
    5. Now, test the workability of the system active:

      Code: Select all

      #/sbin/gradm -E
      and try the system in various ways.
    6. Examine the logs.
      If the system does not perform well, investigate the logs. Really, look at the logs anyway:

      Code: Select all

      #/sbin/gradm -a admin
      (enter password)
      #grep grsec /var/log/kern.log | less
      
      Now locate the activate line in the log, something like this:
      • Jan 29 13:59:45 localhost kernel: [ 151.460617] grsec: (root:U:/sbin/gram) grsecurity 2.1.13 RBAC system load by /sbin/gram[gram:4729] ui/eui:0/0 gi/egi:0/0, parent /sbin/runscript.sh[runscript.sh:4728] ui/eui:0/0 gi/egi:0/0
      and all the denied message following are your bogy to fix. Let's see how to fix those.

      The logging in grsecurity RBAC is pretty verbose and the role used for a specific denial is in the message. For example, take these two denial messages:
      • Jan 30 04:21:01 localhost kernel: [51827.619562] grsec: (root:U:/usr/sbin/cron) denied access to hidden file /etc/crontab by /usr/sbin/cron[cron:4671] uid/euid:0/0 gid/egid:0/0, parent /sbin/init[init:1] uid/euid:0/0 gid/egid:0/0

        Jan 30 04:21:48 localhost kernel: [51873.847865] grsec: (root:U:/) denied executable mmap of /bin/nano by /bin/nano[nano:7419] uid/euid:0/0 gid/egid:0/0, parent /bin/bash[bash:7413] uid/euid:0/0 gid/egid:0/0
      The first was using the root role but the subject "/usr/sbin/cron" while the second rule is using the root role but the subject "/".

      To fix the second, we have some choices. This particular error occured because I had not transitioned to the admin role, so access is not available until I do (i.e. the error is not with the policy but between the keyboard and the chair ;-) )

      To fix the first, we'll need to add a rule to the role root and the subject /usr/sbin/cron to allow read access to /etc/crontab:
      • role root uG

        ... additional subjects but no intervening role statements

        subject /usr/sbin/cron o {
        / h
        /etc/localtime r
        /etc/cron.d r
        /etc/crontab r
        /var/spool/cron/crontabs r
        -CAP_ALL
        bind disabled
        connect disabled
        }
      But also, looking at this list, we probably will fail hourly trying to run what is in /etc/cron.hourly, etc. So fixing that manually can be cumbersome. So lets try learning again, this time at the subject level by adding a lower case l to the subject:
      • role root uG

        ... additional subjects but no intervening role statements

        subject /usr/sbin/cron ol {
        / h
        /etc/localtime r
        /etc/cron.d r
        /etc/crontab r
        /var/spool/cron/crontabs r
        -CAP_ALL
        bind disabled
        connect disabled
        }
      Note: I left the current rules in place. We'll need to merge them later because we may not encounter all situations in the current roles.

      Then start the system for learning:

      Code: Select all

      # /sbin/gradm -L /gradm.cron.learning.log 
      
      Note: we omitted the -F because we are learning a specific item, not full system learning. If you do accidentally leave the -F in you get the cryptic message:
      • Duplicate role :::kernel::: on line 788 of /etc/grsec/policy.
        The RBAC system will not be allowed to be enabled until this error is fixed.
      Now generate the rules (it is a capital o not zero):

      Code: Select all

      # /sbin/gradm -L /gradm.cron.learning.log -O /gradm.cron.learning.roles
      
      Merging the learned subject rules I recommend extracting the subject section of the learned roles and from the original roles and using diff to work with the differences. Diff rarely gives usable output from comparing the existing roles to the learned roles. I have a script (see below) to parse the roles and subjects into a directory structure with sorting. I created the script originally to help me understand the roles, but I find now that it helps with this merge process and really seeing the changes. The diff output from the directory structure is much cleaner. [TODO: complete testing on parser and post.]

      Here are the generated roles:
      • ### THE BELOW SUBJECT(S) SHOULD BE ADDED TO THE USER ROLE "root" ###
        subject / o {
        / h
        -CAP_ALL
        bind disabled
        connect disabled
        }

        subject /usr/sbin/cron o {
        user_transition_allow root
        group_transition_allow root

        /
        /bin h
        /bin/bash x
        /etc r
        /etc/grsec h
        /etc/ssh h
        /etc/shadow- h
        /etc/gshadow h
        /etc/gshadow- h
        /etc/ppp/chap-secrets h
        /etc/ppp/pap-secrets h
        /etc/samba/smbpasswd h
        /lib rx
        /proc h
        /proc/sys/kernel/ngroups_max r
        /usr h
        /usr/sbin/cron rx
        /usr/sbin/ssmtp x
        /var h
        /var/run
        /var/spool/cron/crontabs r
        /dev/grsec h
        /dev/mem h
        /dev/kmem h
        /dev/port h
        /dev/log h
        /sys h
        /boot h
        -CAP_ALL
        +CAP_SETGID
        +CAP_SETUID
        bind disabled
        connect disabled
        }
      Then copy them to the appropriate place in the roles (where we did the learning in the first place) and remove the lower case l:
      • role root uG

        ... additional subjects but no intervening role statements

        subject /usr/sbin/cron o {
        user_transition_allow root
        group_transition_allow root

        /
        /boot h
        /bin h
        /bin/bash x
        /dev/grsec h
        /dev/mem h
        /dev/kmem h
        /dev/port h
        /dev/log h
        /etc r
        /etc/grsec h
        /etc/ssh h
        /etc/shadow- h
        /etc/gshadow h
        /etc/gshadow- h
        /etc/ppp/chap-secrets h
        /etc/ppp/pap-secrets h
        /etc/samba/smbpasswd h
        /lib rx
        /proc h
        /proc/sys/kernel/ngroups_max r
        /sys h
        /usr h
        /usr/sbin/cron rx
        /usr/sbin/ssmtp x
        /var h
        /var/run

        /var/spool/cron/crontabs r
        -CAP_ALL
        +CAP_SETGID
        +CAP_SETUID

        bind disabled
        connect disabled
        }
  4. Finalizing.

    Once you have rebooted and confirmed the security is where you want it, finalize it by adding to /etc/sysctl.conf:

    Code: Select all

    kernel.grsecurity.grsec_lock = 1
    kernel.grsecurity.disable_modules = 1
    
    Note: disabling module loading is not absolutely required. See the full grsecurity guide section 4 for other sysctl options to lock.

    Now, optionally and for the super paranoid, I edit the policy which will look something like this giving admin the same as default as my decoy and my real admin role (in this case omni) gets the admin capability and don't forget to allow root to transition to your new admin role:
    • role omni sA
      subject / rvka
      / rwcdmlxi

      role admin
      subject / {
      / h
      -CAP_ALL
      connect disabled
      bind disabled
      }

      role default
      subject / {
      / h
      -CAP_ALL
      connect disabled
      bind disabled
      }

      role root uG
      role_transitions admin omni
      role_allow_ip 0.0.0.0/32
      subject / {
      / h

      ... lots of rules deleted
      }

      subject /usr/sbin/gpm o {
      / h
      /dev
      /dev/gpmctl wd
      /dev/tty0 rw
      /dev/grsec h
      /dev/mem h
      /dev/kmem h
      /dev/port h
      /dev/log h
      /var/run
      /var/run/gpm.pid wd
      -CAP_ALL
      +CAP_SYS_ADMIN
      +CAP_SYS_TTY_CONFIG
      bind disabled
      connect disabled
      }
    for reference, here is the policy I started with to make the above changes:
    • role admin sA
      subject / rvka
      / rwcdmlxi

      role default
      subject / {
      / h
      -CAP_ALL
      connect disabled
      bind disabled
      }

      role root uG
      role_transitions admin
      role_allow_ip 0.0.0.0/32
      subject / {
      / h

      ... lots of rules deleted
      }

      subject /usr/sbin/gpm o {
      / h
      /dev
      /dev/gpmctl wd
      /dev/tty0 rw
      /dev/grsec h
      /dev/mem h
      /dev/kmem h
      /dev/port h
      /dev/log h
      /var/run
      /var/run/gpm.pid wd
      -CAP_ALL
      +CAP_SYS_ADMIN
      +CAP_SYS_TTY_CONFIG
      bind disabled
      connect disabled
      }
Here is my script to parse and compare rules.
It is rudimentary at this stage but by reviewing the results at the end, it is clear the differences between the policies.

In the current directory, save the existing policy as etc.grsec.policy and the new policy as etc.grsec.learned.policy.
The script creates a tree of existing rules in the existing/ directory and learned rules in the learned/ directory.
The "Only in" lines reflect full subject and role differences. The initial slash in paths of subjects are replaced by the word slash.
Rules are sorted to have better matching.

Here's the script:

Code: Select all

#!/bin/bash
echo " ensure in the directory to save policy tree"
echo " press ctrl+c to exit "
read
wd="`pwd`"
echo " working directory ${wd}"
# verify learned policy file provided
learned="${wd}/etc.grsec.learned.policy"
# verify existing policy updated
existing="${wd}/etc.grsec.policy"
mkdir existing
mkdir learned
cd existing
#  verify updated file date matches last update of /etc/grsec/policy
for policyfile in ${existing} ${learned}
do
#policyfile=${existing}
# regenerate existing policy tree
mode=0
exec 3< ${policyfile}
while read aline <&3
do
echo " ${mode} processing line ${aline} "
case ${mode} in 
	0) 
		# test for role start
		# if [ `expr match "${v}" "role "` -eq 5 ] ; then echo "mess1" ; else echo "mess2"; fi
		if [ `expr match "${aline}" "role "` -eq 5 ] ; then
			# if role start found
			# set role name in role variable from statement
			role="`echo "${aline}" | cut -d" " -f 2`"
			echo " found role ${role} "
			# create role directory
			mkdir ${role}
			cd ${role}
			# create role file with role statement
			echo "${aline}" > role
			# set to role mode
			mode=role
		#else
			# skip record
		fi
#	break
	;;
	role)
		# test for subject statements
		if [ `expr match "${aline}" "subject "` -eq 8 ] ; then
			# set subject to subject name
			subject="`echo "${aline}" | cut -d" " -f 2`"
			if [ "${subject}" == "/" ] ; then 
				subject="slash"
			else
				subject="`echo "slash${subject}" | tr "/" "."`"
			fi 
			echo " found subject ${subject} "
			# create subject file with subject statement
			echo "${aline}" > ${subject}
			# sort role file
			cat role | sort > role.sorted
			mv role.sorted role
			# set to subject mode
			mode=subject
		else
			if [ `expr match "${aline}" "role "` -eq 5 ] ; then
				# if role start found
				# move up dir
				cd ..
				# set role name in role variable from statement
				role="`echo "${aline}" | cut -d" " -f 2`"
				echo " found role ${role} "
				# create role directory
				mkdir ${role}
				cd ${role}
				# create role file with role statement
				echo "${aline}" >> role
				# set to role mode
				mode=role
			else
				# continue to write role statements
				echo "${aline}" >> role
			fi
		fi
#	break
	;;
	subject)
		if [ `expr match "${aline}" "subject "` -eq 8 ] ; then
			# set subject to subject name
			subject="`echo "${aline}" | cut -d" " -f 2`"
			if [ "${subject}" == "/" ] ; then 
				subject="slash"
			else
				subject="`echo "slash${subject}" | tr "/" "."`"
			fi 
			echo " found subject ${subject} "
			# create subject file with subject statement
			echo "${aline}" > ${subject}
			# sort role file
			cat role | sort > role.sorted
			mv role.sorted role
			# set to subject mode
			mode=subject
		else
		# write subject to file
		echo "${aline}" >> ${subject}
		# test for end of subject
		if [ `expr match "${aline}" ".*}.*"` -gt 0 ] ; then
			# end of subject } found
			echo " found end of subject ${subject}"
			# set mode to role
			mode=role
			# sort subject files
			cat ${subject} | sort > ${subject}.sorted
			mv ${subject}.sorted ${subject}
		else
			if [ `expr match "${aline}" "role "` -eq 5 ] ; then
				# if role start found
				# move up dir
				cd ..
				# set role name in role variable from statement
				role="`echo "${aline}" | cut -d" " -f 2`"
				echo " found role ${role} "
				# create role directory
				mkdir ${role}
				cd ${role}
				# create role file with role statement
				echo "${aline}" >> role
				# set to role mode
				mode=role
			fi
		fi
		fi
#	break
	;;
esac
done 
exec 3>&-
cd ${wd}/learned
# repeat for learned policy to verify changes
done
# show differences, omitting deletions from existing tree
cd ${wd}
echo "========begin showing differences============="
diff existing/ learned/ > result1
diff existing/ learned/ | grep Common | cut -d" " -f 3,5 | xargs -l diff -y -B >> result1
echo 'enter in less to review changes in context "/[<>\|]" '
echo '  then enter /Only to see the newly added sections '
read
less result1
Last edited by schmeggahead on Sat Feb 13, 2010 4:39 pm, edited 1 time in total.
Top
Sadako
Advocate
Advocate
User avatar
Posts: 3792
Joined: Thu Aug 05, 2004 5:50 pm
Location: sleeping in the bathtub
Contact:
Contact Sadako
Website

  • Quote

Post by Sadako » Sun Feb 07, 2010 6:28 pm

No response to this yet?

I finally got a decent new machine, so I can make use of kvm (which runs perfectly under a fully hardened kernel, sweet), so I'll be playing around with grsec's RBAC within a vm, I'll use this as a starting point and get back to you with any feedback or issues.

Thanks.

Oh, when emerging stuff, do you disable RBAC completely?
"You have to invite me in"
Top
schmeggahead
Guru
Guru
User avatar
Posts: 314
Joined: Tue Feb 25, 2003 3:28 am
Location: Columbus, Ohio

  • Quote

Post by schmeggahead » Sun Feb 07, 2010 8:15 pm

I just figured out how to do the start up and shutdown learning using local.start and local.stop

I'm changing the local.stop process to include /sbin/gradm -D < .file.with.your.password

once restarting the system, use /sbin/gradm -F -L /full.learning.log.name -O /full.policy.name

But I went to the grsecurity forum and posted a poll to see who uses auto start and how here: http://forums.grsecurity.net/viewtopic.php?f=5&t=2248

no luck on the hardened chat either.
Top
Post Reply

3 posts • Page 1 of 1

Return to “Documentation, Tips & Tricks”

Jump to
  • Assistance
  • ↳   News & Announcements
  • ↳   Frequently Asked Questions
  • ↳   Installing Gentoo
  • ↳   Multimedia
  • ↳   Desktop Environments
  • ↳   Networking & Security
  • ↳   Kernel & Hardware
  • ↳   Portage & Programming
  • ↳   Gamers & Players
  • ↳   Other Things Gentoo
  • ↳   Unsupported Software
  • Discussion & Documentation
  • ↳   Documentation, Tips & Tricks
  • ↳   Gentoo Chat
  • ↳   Gentoo Forums Feedback
  • ↳   Duplicate Threads
  • International Gentoo Users
  • ↳   中文 (Chinese)
  • ↳   Dutch
  • ↳   Finnish
  • ↳   French
  • ↳   Deutsches Forum (German)
  • ↳   Diskussionsforum
  • ↳   Deutsche Dokumentation
  • ↳   Greek
  • ↳   Forum italiano (Italian)
  • ↳   Forum di discussione italiano
  • ↳   Risorse italiane (documentazione e tools)
  • ↳   Polskie forum (Polish)
  • ↳   Instalacja i sprzęt
  • ↳   Polish OTW
  • ↳   Portuguese
  • ↳   Documentação, Ferramentas e Dicas
  • ↳   Russian
  • ↳   Scandinavian
  • ↳   Spanish
  • ↳   Other Languages
  • Architectures & Platforms
  • ↳   Gentoo on ARM
  • ↳   Gentoo on PPC
  • ↳   Gentoo on Sparc
  • ↳   Gentoo on Alternative Architectures
  • ↳   Gentoo on AMD64
  • ↳   Gentoo for Mac OS X (Portage for Mac OS X)
  • Board index
  • All times are UTC
  • Delete cookies

© 2001–2026 Gentoo Foundation, Inc.

Powered by phpBB® Forum Software © phpBB Limited

Privacy Policy

 

 

magic