Как использовать newgrp в скрипте, а затем оставаться в этой группе при выходе из скрипта?

StackOverflow https://stackoverflow.com/questions/299728

  •  08-07-2019
  •  | 
  •  

Вопрос

Я запускаю скрипт на коробке Solaris. в частности SunOS 5.7. Я не root. Я пытаюсь выполнить скрипт, подобный следующему:

  
    

newgrp thegroup < <     FOO
    источник .login_stuff
    эхо " привет мир "
    FOO

  

Сценарий запускается. Проблема в том, что он возвращается к вызывающему процессу, который помещает меня в старую группу с исходным кодом .login_stuff, который не был получен. Я понимаю это поведение. То, что я ищу, - это способ остаться в субоболочке. Теперь я знаю, что могу поставить xterm & Amp; (см. ниже) в сценарии, и это бы сделало это, но наличие нового xterm нежелательно.

  

Передача вашего текущего pid в качестве параметра.

     
    

newgrp thegroup < <     FOO
    источник .login_stuff
    & Xterm усилитель;
    эхо $ 1
    убить -9 $ 1
    FOO

  

У меня нет sg в наличии. Также необходим newgrp.

Это было полезно?

Решение

newgrp adm << ANYNAME
# You can do more lines than just this.
echo This is running as group \$(id -gn)
ANYNAME

.. выведет:

This is running as group adm

Будьте осторожны - убедитесь, что вы избежали '$' косой чертой. Взаимодействия немного странные, потому что они расширяют даже одинарные кавычки перед тем, как выполнить оболочку как другая группа. Итак, если ваша основная группа - «пользователи», а группа, которую вы пытаетесь использовать, - «adm», тогда:

newgrp adm << END
# You can do more lines than just this.
echo 'This is running as group $(id -gn)'
END

.. выведет:

This is running as group users

.. потому что 'id -gn' был запущен текущей оболочкой, а затем отправлен той, которая работает как adm. В любом случае, я знаю, что этот пост древний, но надеюсь, что он кому-нибудь пригодится.

Другие советы

Следующее работает хорошо; поместите следующий бит вверху скрипта (Bourne или Bash):

### first become another group
group=admin

if [ $(id -gn) != $group ]; then
  exec sg $group "$0 $*"
fi

### now continue with rest of the script

Это прекрасно работает на Linuxen. Одно предостережение: аргументы, содержащие пробелы, разбиты на части. Я предлагаю вам использовать env arg1 = 'value 1' arg2 = 'value 2' script.sh конструкция для их передачи (по какой-то причине я не смог заставить ее работать с $ @)

Команда newgrp может быть осмысленно использована только из интерактивной оболочки AFAICT. На самом деле, я отказался от этого из-за ... ну, скажем, достаточно давно, что написанная мною замена теперь имеет право голосовать как в Великобритании, так и в США.

Обратите внимание, что exec - это специальная команда, встроенная в оболочку. Строго говоря, это команда, которая является внешней по отношению к оболочке, но оболочка обладает встроенными знаниями о том, как ее обрабатывать. Оболочка фактически является программой, поэтому сразу после этого вы получаете новую оболочку. Это также корневая программа setuid. По крайней мере, в Solaris su также игнорирует переменную среды SHELL.

У меня есть множество программ, которые решают проблему, которую sudo должен был решить. Помните, что команда предшествует возможности пользователей принадлежать к нескольким группам одновременно (см. Unix версии 7 Руководства ). Поскольку newgid не предоставляет механизма для выполнения команд после его выполнения, в отличие от asroot или <=>, я написал программу <=>, которая, как и <=>, является корневой программой setuid и позволяет вам переключаться с одна группа в другую. Это довольно просто - просто main () плюс набор стандартных функций отчетов об ошибках. Свяжитесь со мной (первая точка последняя в gmail точка com) для источника. У меня также есть намного более опасная команда под названием <=>, которая позволяет мне (но только мне - при компиляции по умолчанию) настраивать списки пользователей и групп гораздо более тщательно.

asroot: Configured for use by jleffler only
Usage: asroot [-hnpxzV] [<uid controls>] [<gid controls>] [-m umask] [--] command [arguments]
    <uid controls> = [-u usr|-U uid] [-s euser|-S euid][-i user]
    <gid controls> = [-C] [-g grp|-G gid] [-a grp][-A gid] [-r egrp|-R egid]
Use -h for more help

Option summary:
 -a group  Add auxilliary group (by name)
 -A gid    Add auxilliary group (by number)
 -C        Cancel all auxilliary groups
 -g group  Run with specified real GID (by name)
 -G gid    Run with specified real GID (by number)
 -h        Print this message and exit
 -i        Initialize UID and GIDs as if for user (by name or number)
 -m umask  Set umask to given value
 -n        Do not run program

 -p        Print privileges to be set
 -r euser  Run with specified effective UID (by name)
 -R euid   Run with specified effective UID (by number)
 -s egroup Run with specified effective GID (by name)
 -S egid   Run with specified effective GID (by number)
 -u user   Run with specified real UID (by name)
 -U uid    Run with specified real UID (by number)
 -V        Print version and exit
 -x        Trace commands that are executed
 -z        Do not verify the UID/GID numbers
Mnemonic for effective UID/GID:
    s is second letter of user;
    r is second letter of group

(Эта программа выросла: если бы я ее переделывал с нуля, я бы принял идентификатор пользователя или имя пользователя, не требуя других букв опций; то же самое для идентификатора группы или имени группы.)

Получить разрешение на установку корневых программ setuid может быть сложно. В настоящее время доступны некоторые обходные пути из-за возможности использования нескольких групп. Один из методов, который может работать, - установить бит setgid в каталогах, в которых вы хотите создать файлы. Это означает, что независимо от того, кто создает файл, файл будет принадлежать группе, которой принадлежит каталог. Это часто дает нужный вам эффект - хотя я знаю мало людей, которые постоянно используют это.

Этот пример был расширен из ответа Плинджаада; он обрабатывает командную строку, которая содержит параметры в кавычках, содержащие пробелы.

#!/bin/bash
group=wg-sierra-admin
if [ $(id -gn) != $group ]
then
    # Construct an array which quotes all the command-line parameters.
    arr=("${@/#/\"}")
    arr=("${arr[*]/%/\"}")
    exec sg $group "$0 ${arr[@]}"
fi

### now continue with rest of the script
# This is a simple test to show that it works.
echo "group: $(id -gn)"
# Show all command line parameters.
for i in $(seq 1 $#)
do
    eval echo "$i:\${$i}"
done

Я использовал это, чтобы продемонстрировать, что это работает.

% ./sg.test  'a b' 'c d e' f 'g h' 'i j k' 'l m' 'n o' p q r s t 'u v' 'w x y z'
group: wg-sierra-admin
1:a b
2:c d e
3:f
4:g h
5:i j k
6:l m
7:n o
8:p
9:q
10:r
11:s
12:t
13:u v
14:w x y z

Возможно

exec $SHELL

сделал бы трюк?

Вы можете использовать sh & amp; (или любую другую оболочку, которую вы хотите использовать) вместо xterm & amp;

Или вы можете также использовать псевдоним (если ваша оболочка поддерживает это), чтобы вы оставались в контексте текущей оболочки.

В файле сценария, например, tst.ksh:

#! /bin/ksh
/bin/ksh -c "newgrp thegroup"

В командной строке:

>> groups fred
oldgroup
>> tst.ksh

>> groups fred
thegroup
sudo su - [user-name] -c exit;

Должен сделать свое дело:)

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top