前言

新项目打算采用运维搭建的发布系统发代码,发布后生效前需要做一些处理,因为发布系统登录目标机器使用的是非root账号,所以需要使用sudo来提升权限。当执行sudo cd /xxx/xx时会提示报错,提示未找到cd这个命令。一直以为cd是系统命令,bing了一下才知道,shell有内置的命令,cd就是其中之一。担心还会踩到其它坑,于是花时间了解了sudo这块的知识,发现没有自己想象的那么简单,以为只是一个简单的命令而已。

用途

以另外一个用户身份执行命令,一般用于提升用户权限

参数说明

-l 显示用户可以执行或者禁止的命令,如果未指定用户,默认显示的为当前登录的用户,如果是-ll格式化良好的显示
-U user 和-l参数一起使用,显示指定用户的可以执行的命令或者权限列表
-v 如果已超时,重新验证,并更新登录状态过期时间,默认超时时间是5分钟
-V 显示版本信息,如果是root账号,还会显示更加详细的配置信息
-- 指示命令停止处理命令行参数,可能后面的参数是传个被执行的命令的
-u user 指定命令执行的用户,未指定,默认为root
-s [command] 运行shell,优先选择SHELL环境变量指定的SHEEL,未指定的情况下,使用账号指定的shell。如果未指定需要执行的命令,会直接进入目标用户的shell交互环境,可以通过exit推出。这个权限很大,如果开通了执行shell权限,岂不是可以执行任意root命令?一般不能开通!
-S 密码通过stdin输入流中读取,默认是通过终端输入,例如echo 'password' | sudo -S
-p prompt 输入密码提示 例子:sudo -p '你在登陆%H:' command
扩展符说明
%H 完整主机名
%h 本地主机名
%p 需要输入密码的用户名,可能是当前登录用户或者执行命名的用户或者root用户的密码,这个要看sudoers配置文件里面的策略设置 rootpw, targetpw, and runaspw
%U 执行命名的用户
%u 调用sudo的用户
%% 输出%字面符号
-P The -P (preserve group vector) option causes sudo to preserve
the invoking user’s group vector unaltered. By default, the
sudoers policy will initialize the group vector to the list
of groups the target user is in. The real and effective
group IDs, however, are still set to match the target user.
-n 不显示密码输入,如果命令需要输入密码,会提示错误
-K The -K (sure kill) option is like -k except that it removes
the user’s cached credentials entirely and may not be used in
conjunction with a command or other option. This option does
not require a password. Not all security policies support
credential caching.

-k [command]
When used alone, the -k (kill) option to sudo invalidates the
user’s cached credentials. The next time sudo is run a pass-
word will be required. This option does not require a pass-
word and was added to allow a user to revoke sudo permissions
from a .logout file. Not all security policies support cre-
dential caching.

When used in conjunction with a command or an option that may
require a password, the -k option will cause sudo to ignore
the user’s cached credentials. As a result, sudo will prompt
for a password (if one is required by the security policy)
and will not update the user’s cached credentials.
看描述跟实际的行为不一致,使用这2个参数会发现一个问题,不管密码有没有错误,pam输入密码错误次数都会加1,当达到了pam最大限制密码错误次数时,即使密码正确也会一致提示你重试,不知道是不是sudo工具的bug?
-i [command] 模拟shell登陆初始化,执行成功会有一个shell交互,需要有指定执行shell的权限
-h 输出简短帮助信息
-H 设置环境变量HOME为执行命令所在用户的家目录
-g group 指定执行命令所在组
-e 不执行命令,使用指定的editor打开一个策略配置文件,需要执行sudoedit命令的权限,不清楚这个有什么用? 难道针对执行的命令单独设置安全策略?
-E 保留当前环境变量,如果没有当前环境变量的权限,会提示错误
-b 后台执行命令

执行流程

1.根据安全策略初始化命令执行环境
2.fork子进程调用execve系统call用于执行命令
3.sudo主进程等待直到命令执行结束,并把命令的的执行结果传递给安全策略指定的close方法,然后退出
4.如果配置了I/O logging插件,sudo会创建一个伪终端,用于转发信号

安全策略配置

1.由2种类型的entry组成,一种是定义别名(变量),一种是定义用户/用户组权限
2.支持文件和ldap配置形式,文件默认路径是/etc/sudoers,使用visudo这个命令启动文件编辑,这个命令保存时会检查语法,符合要求才会保存成功,安全策略使用的是ENBF语法来描述
3.别名类型
    a) 别名必须符合[A-Z]([A-Z][0-9]_)*
    b) 用户别名 User_Alias
        用于定义用户列表或者用户分类,多个使用英文半角逗号分隔,支持用户名和用户id
    c) 目标用户别名 Runas_Alias
        用于定义执行命令时允许的指定用户列表或者分类
    d) 主机别名 Host_Alias
        用于定义主机列表,支持主机名,支持ip,支持网络段
    e) 命令别名 Cmnd_Alias
        用于定义命令列表
4.别名定义通用形式
    a) 单个别名
        Alias_Type NAME = item1, item2, ...
    b) 多个别名
        Alias_Type NAME = item1, item2, item3 : NAME = item4, item5
5.标志位设置,详见man sudoers帮助文档
6.示例
    a) 定义主机别名
        Host_Alias HOST_WX_TEST = 192.168.148.161
    b) 定义命令别名
        Cmnd_Alias GIT = /usr/bin/git
7.用户权限配置
    a) 基本形式
        用户名/组名 允许的主机别名 = (指定可执行的用户或者用户别名) 修饰tag : 命令或者命令别名,...
    b) 说明:指定用户可选,修饰tag也是可选
    c) 常用的修饰tag
        NOPASSWD 不需要输入密码,默认是需要输入密码
    d) 示例1 允许phper用户组在 HOST_WX_TEST无密码执行git命令
        %phper HOST_WX_TEST = NOPASSWD: GIT

其它

1.查看计数器
pam_tally2 --user=username

2.重置错误计数器
pam_tally2 --user=username --reset

3.查看ssh登录日志
tail -f /var/log/secure

后记

1.安全策略未配置的用户不允许使用sudo执行命令
2.默认输入的密码是当前登录的用户,可以通过设置指定登录的密码类型
3.-k,-K这2个参数有bug,不管密码输入是否正确,登录错误次数都会累加
4.sudo只能执行系统命令,shell内置的指定不能执行
5.不可能开启shell权限,否则可以通过shell执行任何命令
6.使用visudo来编辑安全策略文件
7.sudo配置有点复杂,需要多花点时间了解下

参考资料

【1】 man sudo
【2】 man sudoers
【3】Redhat关于pam_tally2计数器在每次sudo时都增加的bug
http://blog.csdn.net/napolunyishi/article/details/23375927

N天学习一个Linux命令之sudo的更多相关文章

  1. N天学习一个Linux命令之帮助命令:man

    前言 工作中每天都在使用常用的命令和非常用的命令,忘记了用法或者参数,都会bing一下,然后如此循环.一直没有真正的系统的深入的去了解命令的用法,我决定打破它.以前看到有人,每天学习一个linux命令 ...

  2. N天学习一个Linux命令之free

    用途 查看系统内存(物理/虚拟/缓存/共享)使用情况 用法 free [-b | -k | -m | -g | -h] [-o] [-s delay ] [-c count ] [-a] [-t] [ ...

  3. N天学习一个linux命令之ping

    用途 检测主机是否可到达,也就是说,目标主机是否可以联网,还可以用于检测网速.通过发送ICMP ECHO_REQUEST数据包检测. 用法 ping [options] destination 常用选 ...

  4. N天学习一个linux命令之kill

    用途 用于终止进程 用法 kill [-s signal|-p] [--] pid... kill -l [signal] 说明 1.默认发送信号15(请求终止进程,程序可以捕获,操作系统会杀死没有对 ...

  5. N天学习一个linux命令之du

    用途 统计文件或者目录占用硬盘空间大小 用法 du [OPTION] [FILE]du [OPTION] --files0-from=F 常用参数 -a, --all统计所有文件,不仅仅是目录 -b, ...

  6. N天学习一个linux命令之scp

    用途 通过ssh通道,不同主机之间复制文件 用法 scp [options] [user@host:]file1 [user2@host2:]file2 常用参数 -1使用 ssh 1协议 -2使用s ...

  7. 每天学习一个Linux命令-目录

    在工作中总会零零散散使用到各种Linux命令,从今天开始详细的学习一下linux常用命令,坚持每天一个命令,学习的主要参考资料为: 1.竹子-博客(https://www.cnblogs.com/pe ...

  8. N天学习一个linux命令之umask

    前言 umask不是linux命令,而是shell内置的指令,俗称用户权限掩码,用于对用户创建的文件和目录设置默认权限.默认的权限掩码是0022,也就是说新创建的文件权限是0644,新创建的目录权限是 ...

  9. N天学习一个linux命令之ip

    用途 show / manipulate routing, devices, policy routing and tunnels 用法 通用格式 ip [ OPTIONS ] OBJECT { CO ...

随机推荐

  1. Python基础数据类型(四) tuple元祖

    元祖tuple(,) 元祖就是不可变的列表 元祖用()表示,元素与元素之间用逗号隔开,数据类型没有限制 tu = ('科比','詹姆斯','乔丹') tu = tuple('123') 小括号中 有一 ...

  2. RAP接口文档的安装

    本机环境 系统:CentOS 6.7 64 位 MySQL 5.6 JDK 1.8 Tomcat 8 Redis 3.0.7 Rap 0.14.1 Rap 说明 官网:https://github.c ...

  3. android UI 操作 不要在子线程中操作UI

    不管是android ,还是 ios ,请不要在子线程中操作UI,有时有些崩溃,从报错上看不出什么原因,就有可能是子线程操作了UI:切记,切记! 请放在主线程例: activity.runOnUiTh ...

  4. javascript:void(0);什么意思

    js里面void是一个操作符,该操作符计算表达式的值,但是不返回任何内容. <a href="javascript:void(0);"> 这里用到void(0)表示取消 ...

  5. vue-cli的创建、基本配置和遇到的问题总结

    vue-cli的创建及基本配置 1. 创建 vue-cli 项目 确保本地安装了最新版本的nodejs环境(会自带npm环境); 全局安装vue-cli,命令:npm i -g vue-cli 创建项 ...

  6. Unity3d dotween

    位置 1. 移动到指定位置 obj.transform.DOMove(, , ), 2f); a. 单方向可以用DOMoveX.DOMoveY.DOMoveZ b. 本地坐标系版本:DOLocalMo ...

  7. 【Java基础】多态

    首先先来个总结: 什么是多态 面向对象的三大特性:封装.继承.多态.从一定角度来看,封装和继承几乎都是为多态而准备的.这是我们最后一个概念,也是最重要的知识点. 多态的定义:指允许不同类的对象对同一消 ...

  8. <form> 标签

    <form method="传送方式" action="服务器文件"> action :浏览者输入的数据被传送到的地方,比如一个PHP页面(save ...

  9. 关于华为手机Log.d打印不出来log的问题

    http://blog.csdn.net/picasso_l/article/details/52489560     拨号,进入后台设置,进行操作.

  10. Android 在fragment中实现返回键单击提醒 双击退出

    尝试用mvp架构加dagger2来重写了一下,大致功能都实现了,还没有全部完成. 项目地址 接近完成的时候,想在天气信息页面实现一个很常见的功能,也就是点击屏幕下方的返回键的时候不是返回到上一个act ...