Forcing Logout to kick off Filevault2

nortonpc
Contributor

Background:
I have a policy in the JSS that runs a script with a series of Jamf Helper huds. These walk a user through the instructions for enabling FV2. However I cannot figure out how to force a logout of the current user. I had this all working really well through self service but our users are being very naughty and not running it from self service. We need to move to something more "forceful". However in our environment we, do a lot of hand holding, as in we have to get as close to 100% of the process being automated or we just make tickets for ourselves.

‘tell application “System Events” to log out’

compiled into an applescript app works in 10.9 but not 10.8, or 10.7 - we are mostly 10.8 with some 10.7 and very few 10.9 machines.
Reboot does not kick off the deferral asking the user to enter password.
killing the login window is too dirty it also does not ask for the password.
local bash scripts don't work.
su -u $(currentUser) type stuff is also not working.

It seems that when something is running from policy, as root, that there is no way for it to influence the console user to log out gracefully. Has anyone else tried something like this?

1 ACCEPTED SOLUTION

mm2270
Legendary Contributor III

There's a way to do this, because I have an entire script/workflow I've developed to help enforce FV2 on our systems. While we're not actually using it just yet, its something I've been working on now for awhile.

Because its still a work in progress that we have yet to implement, I can't share the entire script here. But I can post the snippet I use to force the logout to happen that may help you get this working.

## Get the logged in user's name
loggedInUser=$( ls -l /dev/console | awk '{print $3}' )
## Get the PID of the logged in user
loggedInPID=$( ps -axj | awk "/^$loggedInUser/ && /Dock.app/ {print $2;exit}" )

## Use the above to run Applescript command to logout using keystroke commands
/bin/launchctl bsexec "${loggedInPID}" sudo -iu "${loggedInUser}" "/usr/bin/osascript -e 'tell application "System Events" to keystroke "q" using {command down, option down, shift down}'"

Keep in mind that prior to running this, I use a couple of lines to quit all visible running apps. What you see above is only a small part of the script where we will eventually be locking users out of their desktops with a full screen jamfHelper message, force quitting all running apps in the background, then killing jamfHelper and finally running the launchctl bsexec command above to log out of the account.
This will all be coupled with a Policybanner over the login screen explaining that FV2 is a company policy, etc etc. Once FV2 is enabled, the script removes the PolicyBanner.rtf file and cleans itself up so it won't run again. The whole thing is controlled by a LaunchDaemon.
Give the above a try and see if it works for you. YMMV. I found doing this under 10.9 to be much harder than getting it all to work in 10.8.x. (We don't use FV2 on 10.7 since we can't escrow the Recovery Keys to Casper)

All this said, this is one of those areas where I shake my fist in the air and rail at Apple. If they would just allow us to not have the stupid "Cancel" button in the dialog asking for the password, the whole thing would be moot. But because Apple refuses to allow us to enforce it, we need to script up all kinds of crazy workarounds.

View solution in original post

15 REPLIES 15

alexjdale
Valued Contributor III

I was never able to get this to work. It seems that any reboot/logout not initiated by the user through the GUI will not trigger the prompt for credentials. It makes sense to me because you don't want the system to hang indefinitely at that prompt if you have a scripted restart/logout.

It would be nice if the authentication stack could just grab those credentials at next login to start encrypting...

gachowski
Valued Contributor II

I was also not able to get this to work, I resorted to have a script on the desktop that tells the System Events.app to restart.

I would encourage you to open a ticket with Apple for a zero touch work follow. No matter what Apple thinks VF2 is an enterprise feature and we really require this and a way to prevent users from turning it off too.

C

nortonpc
Contributor

Chris, we tried a script in /Users/Shared. But when this is called via the policy running as root, I get this error:

Running command sudo open /Users/Shared/logout.app... Result of command:
LSOpenURLsWithRole() failed with error -10810 for the file /Users/Shared/logout.app.

Googling that error reveals it is a "session" issue. The root user is not able to access those process on the user logged in to the console. In the past to run things as the user i have used su -u but that only works from self service.

How are you triggering the local script?

rtrouton
Release Candidate Programs Tester

@gachowski,

Do your users have admin rights? If not, Apple built in a way to prevent users from turning off FileVault 2 encryption for Macs running 10.8.4 and later. I have a post on it here:

http://derflounder.wordpress.com/2013/06/07/standard-user-accounts-in-os-x-10-8-4-now-blocked-from-d...

mm2270
Legendary Contributor III

There's a way to do this, because I have an entire script/workflow I've developed to help enforce FV2 on our systems. While we're not actually using it just yet, its something I've been working on now for awhile.

Because its still a work in progress that we have yet to implement, I can't share the entire script here. But I can post the snippet I use to force the logout to happen that may help you get this working.

## Get the logged in user's name
loggedInUser=$( ls -l /dev/console | awk '{print $3}' )
## Get the PID of the logged in user
loggedInPID=$( ps -axj | awk "/^$loggedInUser/ && /Dock.app/ {print $2;exit}" )

## Use the above to run Applescript command to logout using keystroke commands
/bin/launchctl bsexec "${loggedInPID}" sudo -iu "${loggedInUser}" "/usr/bin/osascript -e 'tell application "System Events" to keystroke "q" using {command down, option down, shift down}'"

Keep in mind that prior to running this, I use a couple of lines to quit all visible running apps. What you see above is only a small part of the script where we will eventually be locking users out of their desktops with a full screen jamfHelper message, force quitting all running apps in the background, then killing jamfHelper and finally running the launchctl bsexec command above to log out of the account.
This will all be coupled with a Policybanner over the login screen explaining that FV2 is a company policy, etc etc. Once FV2 is enabled, the script removes the PolicyBanner.rtf file and cleans itself up so it won't run again. The whole thing is controlled by a LaunchDaemon.
Give the above a try and see if it works for you. YMMV. I found doing this under 10.9 to be much harder than getting it all to work in 10.8.x. (We don't use FV2 on 10.7 since we can't escrow the Recovery Keys to Casper)

All this said, this is one of those areas where I shake my fist in the air and rail at Apple. If they would just allow us to not have the stupid "Cancel" button in the dialog asking for the password, the whole thing would be moot. But because Apple refuses to allow us to enforce it, we need to script up all kinds of crazy workarounds.

nortonpc
Contributor

Well that certainly does work. I think this might do it for us. Thanks a lot for that code.

We just couldn't get it to run as the console user and it looks like found a way to make that happen. Thank you very much.

gachowski
Valued Contributor II

@ Rich our users are admin, I think there is a config profile in X.9 too that will prevent , but have read that it requires an AD account.

@ Patrick it's the one thing the techs have to do when the machine is set up it's a shell scrip save as .command file so they only have to single click. After reading Mike's post that is going to be the the way I go when I have the time to get to make the change… But now it's a timing issue we already have script/Launchd that runs on the users 1st log in so were do we trigger it and how do we trigger it : )

@ Mike, Very Nice!!!! Thanks, great idea and find!!!

Janowski
New Contributor II

wow, props Mike! Thats a great fix. Like Pat said, it solved our challenge for us.

Thanks for helping us. I'm totally going to keep the whole "tell launchd to use key commands" approach in my back pocket from here on out ;)

matt_jamison
Contributor

Would love to see what the final script looks like. Appreciate the snippet!

nortonpc
Contributor

I am not sure if oneloveamaru was looking for my script or Mike's but here is ours:

Script one, runs on an every15:

#!/bin/sh


###### User Parameters

currentUser=$(ls -l /dev/console | awk '{print $3}')

echo "Current Console User is: " $currentUser

if [ $currentUser = "root" ]; then

Echo "No User Logged in, Aborting"
echo "error: script failed"

exit 1

fi

#Window Title 
title="Associate Attention Required"

#Heading
heading="Help Company X Protect Your Data

"

#Window Message 
message="Company X is making efforts to protect important company and employee data by enabling Full Disk Encryption on all of the Company X-owned Macintosh Laptops.  This technology ensures that should a portable device be misplaced our employees, stockholders, and company have assurance that data is secure.  Mac Support requests a small amount of your time to help complete this process.


3XpmrsOpWfF3SSHYUgpg

message2="Encryption has started please click the logout button and log out of your mac.
1. Please save all your work and close all open programs.
2. Select log out and your computer will log out immediately.
3. Then enter your computer password on the following screen."

#Button Texts 
button1="Encrypt"
button2="Logout"
#To change icon edit the -icon path below


#command below makes the window and stores the value in $userdecision
if [ -d /Library/Application Support/JAMF/bin/jamfHelper.app ]; then
userDecision=`/Library/Application Support/JAMF/bin/jamfHelper.app/Contents/MacOS/jamfHelper -windowType hud -title "$title" -heading "$heading" -description "$message" -alignHeading center -button1 "$button1" -timeout "86400" -icon /System/Library/CoreServices/Installer.app/Contents/Resources/Installer.icns -iconSize 400 -lockHUD -countdown -startlaunchd`


else
echo "no jamf helper available"

fi


jamf policy -trigger CompanyXfdestart



if [ -d /Library/Application Support/JAMF/bin/jamfHelper.app ]; then
userDecision2=`/Library/Application Support/JAMF/bin/jamfHelper.app/Contents/MacOS/jamfHelper -windowType hud -title "$title" -heading "$heading" -description "$message2" -alignHeading center -button1 "$button2" -timeout "3600" -icon /System/Library/CoreServices/Installer.app/Contents/Resources/Installer.icns  -iconSize 400 -lockHUD -countdown -startlaunchd`
fi

## Get the logged in user's name
loggedInUser=$( ls -l /dev/console | awk '{print $3}' )
## Get the PID of the logged in user
loggedInPID=$( ps -axj | awk "/^$loggedInUser/ && /Dock.app/ {print $2;exit}" )

## Command Below from mm2270 JAMF nation to force log out of user session.
/bin/launchctl bsexec "${loggedInPID}" sudo -iu "${loggedInUser}" "/usr/bin/osascript -e 'tell application "System Events" to keystroke "q" using {command down, option down, shift down}'"


exit 0

This script calls a custom trigger on another policy to deploy the JAMF Disk encryption configuration. The reason for this was to be able to do both a self service version and a forced version.

The self service version is slightly different using an applescript command to ask the user to log out:

#!/bin/sh


###### User Parameters

currentUser=$(ls -l /dev/console | awk '{print $3}')

echo "Current Console User is: " $currentUser

if [ $currentUser = "root" ]; then

Echo "No User Logged in, Aborting"
echo "error: script failed"

exit 1

fi

#Window Title 
title="Associate Attention Required"

#Heading
heading="Help Company X Protect Your Data

"

#Window Message 
message="Company X is making efforts to protect important company and employee data by enabling Full Disk Encryption on all of the Company X-owned Macintosh Laptops.  This technology ensures that should a portable device be misplaced our employees, stockholders, and company have assurance that data is secure.  Mac Support requests a small amount of your time to help complete this process.


3XpmrsOpWfF3SSHYUgpg

message2="Encryption has started please click the logout button and log out of your mac.
1. Please save all your work and close all open programs.
2. Select log out and your computer will log out immediately.
3. Then enter your computer password on the following screen."

#Button Texts 
button1="Encrypt"
button2="Logout"
#To change icon edit the -icon path below


#command below makes the window and stores the value in $userdecision
if [ -d /Library/Application Support/JAMF/bin/jamfHelper.app ]; then
userDecision=`/Library/Application Support/JAMF/bin/jamfHelper.app/Contents/MacOS/jamfHelper -windowType hud -title "$title" -heading "$heading" -description "$message" -alignHeading center -button1 "$button1" -timeout "86400" -icon /System/Library/CoreServices/Installer.app/Contents/Resources/Installer.icns -iconSize 400 -lockHUD -countdown -startlaunchd`


else
echo "no jamf helper available"

fi


jamf policy -trigger CompanyXfdestart



if [ -d /Library/Application Support/JAMF/bin/jamfHelper.app ]; then
userDecision2=`/Library/Application Support/JAMF/bin/jamfHelper.app/Contents/MacOS/jamfHelper -windowType hud -title "$title" -heading "$heading" -description "$message2" -alignHeading center -button1 "$button2" -timeout "3600" -icon /System/Library/CoreServices/Installer.app/Contents/Resources/Installer.icns  -iconSize 400 -lockHUD -countdown -startlaunchd`
fi

## Applescript to log out.
osascript -e 'tell application "System Events" to log out'


exit 0

gachowski
Valued Contributor II

Thank you!!!! Patrick : ) I will definitely "steal" parts of it : )

C

Josh_Smith
Contributor III

I've been using @mm2270 's code posted above to logout a user, and it worked great with 10.10 (thanks Mike!). I'm just starting to test 10.11 and it seems to need a different subcommand (asuser). This is working for me in 10.10 and 10.11:

## Get the logged in user's username
loggedInUser=$( ls -l /dev/console | awk '{print $3}' )

## Get the logged in user's UID
loggedInUID=$(id -u $loggedInUser)

## Use the above to run Applescript command to logout using keystroke commands
/bin/launchctl asuser $loggedInUID sudo -iu "${loggedInUser}" "/usr/bin/osascript -e 'tell application "System Events" to keystroke "q" using {command down, option down, shift down}'"

mm2270
Legendary Contributor III

@Josh.Smith That's a fantastic find!! I knew the old launchctl bsexec stuff wasn't working under El Cap anymore, but I didn't really dig into the launchctl command to see if there was another way to do this. Thanks for posting! I'm going to give this a try. If it works in 10.11 that will solve one of the items we'd been looking at resolving for some of our 10.11 deployment stuff and scripts.

Just a note for anyone reading, it seems the "asuser" flag only exists as of 10.10 and up. I looked at the man page for launchctl on a Mavericks box and it doesn't exist, so its something new that Apple added in. Maybe the "official" way now of running items as the user.

Thanks again! :)

mm2270
Legendary Contributor III

Just posting back again to confirm what @Josh.Smith mentioned above about running commands as the logged in user under 10.11. His suggestion of using launchctl asuser is spot on. Thanks!

Here's a simple example of getting the list of running (visible) applications in the user space that works perfectly under 10.11.2.

loggedInUser=$(stat -f%Su /dev/console); userUID=$(id -u ${loggedInUser}); /bin/launchctl asuser "$userUID" sudo -iu "$loggedInUser" "/usr/bin/osascript -e 'tell application "System Events" to get name of (every process whose visible is true)'" | tr ',' '
' | sed 's/^ *//g;/^Finder$/d'

Its all lumped together in one string, but basically, get the logged in user name, then the user ID (UniqueID), then run an osascript command to get the list of visible processes (minus Finder since that's always there). It would produce a list like the following:

Microsoft Outlook
System Preferences
Terminal

That can then be used in another command to loop over these processes and do something if so desired. Here's another osascript one calling a simple dialog.

loggedInUser=$(stat -f%Su /dev/console); userUID=$(id -u ${loggedInUser}); /bin/launchctl asuser "$userUID" sudo -iu "$loggedInUser" "/usr/bin/osascript -e 'display dialog "Hello"'"

In testing, these work perfectly under El Capitan to display a dialog, or get data from the user session, etc. So seems like one issue solved, since that one was one of the ones I'd been working on how to resolve as we moved toward our El Capitan deployment.
Be sure to backslash escape any double quotes that are within the command to run, as shown in the examples above, or it won't work.

Big thanks to @Josh.Smith for pointing this one out!

bunnie84
New Contributor

We modified the above script to make some changes these are working as of 12/9/19

#!/bin/sh

set -x # log all the commands
set -e # bail out at any error

### SETUP

## Current User

CURRENT_USER=$(ls -l /dev/console | awk '{print $3}')
CURRENT_USER_UID=$(id -u $CURRENT_USER)

echo "Current user: ${CURRENT_USER} (${CURRENT_USER_UID})"

if [ $CURRENT_USER = "root" ]; then
    echo "ERROR: No User Logged in, aborting"
    exit 1
fi

## Check JAMF Helper Available
if [ ! -d /Library/Application Support/JAMF/bin/jamfHelper.app ]; then
    echo "ERROR: jamfHelper Unavailable, aborting..."
    exit 1
fi


### MESSAGING
TITLE="Crew Attention Required"
HEADING="Help keep Company X`s data safe

"


## Message 1 - What's going on
BUTTON="Continue"
TIMEOUT=172800  # 172800=24H
MESSAGE="Hi Crew, as a part of ongoing efforts by the IT and Security Teams to help protect CompanyX, we would like to enable full disk encryption on your laptop.

Why are we doing this?
In the event that your laptop is lost or stolen, Full Disk Encryption ensures that any data on your laptop is protected.

What do you need to do?
Everything is already configured however we do need you to logout and login to your laptop to complete the process.

When do you need to do this?
We understand that you might be in the middle of working on something, you have 48 hours before we will automatically log you out.

When you are ready to log out, please click "${BUTTON}".
"

/Library/Application Support/JAMF/bin/jamfHelper.app/Contents/MacOS/jamfHelper 
    -windowType hud 
    -title "$TITLE" 
    -heading "$HEADING" 
    -alignHeading center 
    -description "$MESSAGE" 
    -button1 "$BUTTON" 
    -icon /System/Library/CoreServices/Installer.app/Contents/Resources/Installer.icns 
    -iconSize 400 
    -lockHUD 
    -timeout "$TIMEOUT" 
    -countdown 
    -startlaunchd

## Message 2 - Lets continue
BUTTON="Logout Now"
TIMEOUT=3600  # 3600=1H
MESSAGE="Thanks for your help!


AKR3wRy9zWJNmOOdPK0N

We will automically log you out in 1 hour.
"

/Library/Application Support/JAMF/bin/jamfHelper.app/Contents/MacOS/jamfHelper 
    -windowType hud 
    -title "$TITLE" 
    -heading "$HEADING" 
    -alignHeading center 
    -description "$MESSAGE" 
    -button1 "$BUTTON" 
    -icon /System/Library/CoreServices/Installer.app/Contents/Resources/Installer.icns 
    -iconSize 400 
    -lockHUD 
    -timeout "$TIMEOUT" 
    -countdown 
    -startlaunchd



#exit 1 # short circuit



### LOGOUT
# References:
# - https://derflounder.wordpress.com/2016/03/25/running-processes-in-os-x-as-the-logged-in-user-from-outside-the-users-account/
# - https://apple.stackexchange.com/a/126762
launchctl asuser $CURRENT_USER_UID osascript -e 'tell app "System Events" to log out'

exit 0