| #!/bin/sh |
| #--------------------------------------------- |
| # xdg-su |
| # |
| # Utility script to run a command as an alternate user, generally |
| # the root user, with a graphical prompt for the root |
| # password if needed |
| # |
| # Refer to the usage() function below for usage. |
| # |
| # Copyright 2006, Jeremy White <jwhite@codeweavers.com> |
| # Copyright 2006, Kevin Krammer <kevin.krammer@gmx.at> |
| # |
| # LICENSE: |
| # |
| # Permission is hereby granted, free of charge, to any person obtaining a |
| # copy of this software and associated documentation files (the "Software"), |
| # to deal in the Software without restriction, including without limitation |
| # the rights to use, copy, modify, merge, publish, distribute, sublicense, |
| # and/or sell copies of the Software, and to permit persons to whom the |
| # Software is furnished to do so, subject to the following conditions: |
| # |
| # The above copyright notice and this permission notice shall be included |
| # in all copies or substantial portions of the Software. |
| # |
| # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS |
| # OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, |
| # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL |
| # THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR |
| # OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, |
| # ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR |
| # OTHER DEALINGS IN THE SOFTWARE. |
| # |
| #--------------------------------------------- |
| |
| manualpage() |
| { |
| cat << _MANUALPAGE |
| Name |
| |
| xdg-su - run a GUI program as root after prompting for the root password |
| |
| Synopsis |
| |
| xdg-su [-u user] -c command |
| |
| xdg-su { --help | --manual | --version } |
| |
| Description |
| |
| xdg-su provides a graphical dialog that prompts the user for a password to run |
| command as user or as root if no user was specified. |
| |
| xdg-su is for use inside a desktop session only. |
| |
| xdg-su discards any stdout and stderr output from command. |
| |
| Options |
| |
| -u user |
| run command as user. The default is to run as root. |
| --help |
| Show command synopsis. |
| --manual |
| Show this manualpage. |
| --version |
| Show the xdg-utils version information. |
| |
| Exit Codes |
| |
| An exit code of 0 indicates success while a non-zero exit code indicates |
| failure. The following failure codes can be returned: |
| |
| 1 |
| Error in command line syntax. |
| 2 |
| One of the files passed on the command line did not exist. |
| 3 |
| A required tool could not be found. |
| 4 |
| The action failed. |
| |
| See Also |
| |
| su(1) |
| |
| Examples |
| |
| xdg-su -u root -c "/opt/shinythings/bin/install-GUI --install fast" |
| |
| Runs the /opt/shinythings/bin/install-GUI command with root permissions. |
| |
| _MANUALPAGE |
| } |
| |
| usage() |
| { |
| cat << _USAGE |
| xdg-su - run a GUI program as root after prompting for the root password |
| |
| Synopsis |
| |
| xdg-su [-u user] -c command |
| |
| xdg-su { --help | --manual | --version } |
| |
| _USAGE |
| } |
| |
| #@xdg-utils-common@ |
| |
| #---------------------------------------------------------------------------- |
| # Common utility functions included in all XDG wrapper scripts |
| #---------------------------------------------------------------------------- |
| |
| DEBUG() |
| { |
| [ ${XDG_UTILS_DEBUG_LEVEL-0} -lt $1 ] && return 0; |
| shift |
| echo "$@" >&2 |
| } |
| |
| #------------------------------------------------------------- |
| # Exit script on successfully completing the desired operation |
| |
| exit_success() |
| { |
| if [ $# -gt 0 ]; then |
| echo "$@" |
| echo |
| fi |
| |
| exit 0 |
| } |
| |
| |
| #----------------------------------------- |
| # Exit script on malformed arguments, not enough arguments |
| # or missing required option. |
| # prints usage information |
| |
| exit_failure_syntax() |
| { |
| if [ $# -gt 0 ]; then |
| echo "xdg-su: $@" >&2 |
| echo "Try 'xdg-su --help' for more information." >&2 |
| else |
| usage |
| echo "Use 'man xdg-su' or 'xdg-su --manual' for additional info." |
| fi |
| |
| exit 1 |
| } |
| |
| #------------------------------------------------------------- |
| # Exit script on missing file specified on command line |
| |
| exit_failure_file_missing() |
| { |
| if [ $# -gt 0 ]; then |
| echo "xdg-su: $@" >&2 |
| fi |
| |
| exit 2 |
| } |
| |
| #------------------------------------------------------------- |
| # Exit script on failure to locate necessary tool applications |
| |
| exit_failure_operation_impossible() |
| { |
| if [ $# -gt 0 ]; then |
| echo "xdg-su: $@" >&2 |
| fi |
| |
| exit 3 |
| } |
| |
| #------------------------------------------------------------- |
| # Exit script on failure returned by a tool application |
| |
| exit_failure_operation_failed() |
| { |
| if [ $# -gt 0 ]; then |
| echo "xdg-su: $@" >&2 |
| fi |
| |
| exit 4 |
| } |
| |
| #------------------------------------------------------------ |
| # Exit script on insufficient permission to read a specified file |
| |
| exit_failure_file_permission_read() |
| { |
| if [ $# -gt 0 ]; then |
| echo "xdg-su: $@" >&2 |
| fi |
| |
| exit 5 |
| } |
| |
| #------------------------------------------------------------ |
| # Exit script on insufficient permission to read a specified file |
| |
| exit_failure_file_permission_write() |
| { |
| if [ $# -gt 0 ]; then |
| echo "xdg-su: $@" >&2 |
| fi |
| |
| exit 6 |
| } |
| |
| check_input_file() |
| { |
| if [ ! -e "$1" ]; then |
| exit_failure_file_missing "file '$1' does not exist" |
| fi |
| if [ ! -r "$1" ]; then |
| exit_failure_file_permission_read "no permission to read file '$1'" |
| fi |
| } |
| |
| check_vendor_prefix() |
| { |
| file=`basename "$1"` |
| case "$file" in |
| [a-zA-Z]*-*) |
| return |
| ;; |
| esac |
| |
| echo "xdg-su: filename '$file' does not have a proper vendor prefix" >&2 |
| echo 'A vendor prefix consists of alpha characters ([a-zA-Z]) and is terminated' >&2 |
| echo 'with a dash ("-"). An example filename is '"'example-$file'" >&2 |
| echo "Use --novendor to override or 'xdg-su --manual' for additional info." >&2 |
| exit 1 |
| } |
| |
| check_output_file() |
| { |
| # if the file exists, check if it is writeable |
| # if it does not exists, check if we are allowed to write on the directory |
| if [ -e "$1" ]; then |
| if [ ! -w "$1" ]; then |
| exit_failure_file_permission_write "no permission to write to file '$1'" |
| fi |
| else |
| DIR=`dirname "$1"` |
| if [ ! -w "$DIR" -o ! -x "$DIR" ]; then |
| exit_failure_file_permission_write "no permission to create file '$1'" |
| fi |
| fi |
| } |
| |
| #---------------------------------------- |
| # Checks for shared commands, e.g. --help |
| |
| check_common_commands() |
| { |
| while [ $# -gt 0 ] ; do |
| parm="$1" |
| shift |
| |
| case "$parm" in |
| --help) |
| usage |
| echo "Use 'man xdg-su' or 'xdg-su --manual' for additional info." |
| exit_success |
| ;; |
| |
| --manual) |
| manualpage |
| exit_success |
| ;; |
| |
| --version) |
| echo "xdg-su 1.0beta2" |
| exit_success |
| ;; |
| esac |
| done |
| } |
| |
| check_common_commands "$@" |
| if [ ${XDG_UTILS_DEBUG_LEVEL-0} -lt 1 ]; then |
| # Be silent |
| xdg_redirect_output=" > /dev/null 2> /dev/null" |
| else |
| # All output to stderr |
| xdg_redirect_output=" >&2" |
| fi |
| |
| #-------------------------------------- |
| # Checks for known desktop environments |
| # set variable DE to the desktop environments name, lowercase |
| |
| detectDE() |
| { |
| if [ x"$KDE_FULL_SESSION" = x"true" ]; then DE=kde; |
| elif [ x"$GNOME_DESKTOP_SESSION_ID" != x"" ]; then DE=gnome; |
| elif xprop -root _DT_SAVE_MODE | grep ' = \"xfce4\"$' >/dev/null 2>&1; then DE=xfce; |
| fi |
| } |
| |
| #---------------------------------------------------------------------------- |
| |
| |
| |
| su_kde() |
| { |
| if [ x"$KDE_SESSION_VERSION" = x"4" ]; then |
| KDESU=`kde4-config --locate kdesu --path exe 2>/dev/null` |
| else |
| KDESU=`which kdesu 2>/dev/null` |
| fi |
| if [ $? -eq 0 ] ; then |
| if [ -z "$user" ] ; then |
| $KDESU -c "$cmd" |
| else |
| $KDESU -u "$user" -c "$cmd" |
| fi |
| |
| if [ $? -eq 0 ]; then |
| exit_success |
| else |
| exit_failure_operation_failed |
| fi |
| else |
| su_generic |
| fi |
| } |
| |
| su_gnome() |
| { |
| GSU=`which gnomesu 2>/dev/null` |
| if [ $? -ne 0 ] ; then |
| GSU=`which xsu 2>/dev/null` |
| fi |
| if [ $? -eq 0 ] ; then |
| if [ -z "$user" ] ; then |
| $GSU -c "$cmd" |
| else |
| $GSU -u "$user" -c "$cmd" |
| fi |
| |
| if [ $? -eq 0 ]; then |
| exit_success |
| else |
| exit_failure_operation_failed |
| fi |
| else |
| su_generic |
| fi |
| } |
| |
| su_generic() |
| { |
| if [ -z "$user" ] ; then |
| xterm -geom 60x5 -T "xdg-su: $cmd" -e su -c "$cmd" |
| else |
| xterm -geom 60x5 -T "xdg-su: $cmd" -e su -c "$cmd" "$user" |
| fi |
| |
| if [ $? -eq 0 ]; then |
| exit_success |
| else |
| exit_failure_operation_failed |
| fi |
| } |
| |
| [ x"$1" != x"" ] || exit_failure_syntax |
| |
| user= |
| cmd= |
| while [ $# -gt 0 ] ; do |
| parm="$1" |
| shift |
| |
| case "$parm" in |
| -u) |
| if [ -z "$1" ] ; then |
| exit_failure_syntax "user argument missing for -u" |
| fi |
| user="$1" |
| shift |
| ;; |
| |
| -c) |
| if [ -z "$1" ] ; then |
| exit_failure_syntax "command argument missing for -c" |
| fi |
| cmd="$1" |
| shift |
| ;; |
| |
| -*) |
| exit_failure_syntax "unexpected option '$parm'" |
| ;; |
| |
| *) |
| exit_failure_syntax "unexpected argument '$parm'" |
| ;; |
| esac |
| done |
| |
| if [ -z "${cmd}" ] ; then |
| exit_failure_syntax "command missing" |
| fi |
| |
| detectDE |
| |
| if [ x"$DE" = x"" ]; then |
| XSU=`which xsu 2>/dev/null` |
| if [ $? -eq 0 ] ; then |
| DE=generic |
| fi |
| fi |
| |
| case "$DE" in |
| kde) |
| su_kde |
| ;; |
| |
| gnome) |
| su_gnome |
| ;; |
| |
| generic) |
| su_generic |
| ;; |
| |
| *) |
| [ x"$user" = x"" ] && user=root |
| exit_failure_operation_impossible "no graphical method available for invoking '$cmd' as '$user'" |
| ;; |
| esac |