/etc/rc.d/init.d/functions 脚本详解【如何写出像红帽一样NB的启动脚本】

机器人动力学仿真软件:PyBullet_(10).案例分析:双足机器人行走仿真 在本节中,我们将详细探讨如何使用PyBullet进行双足机器人的行走仿真。双足机器人行走仿真是一个复杂的动力学问题,涉及多个关节的协调运动和环境交互。通过本节的学习,您将了解如何创建和控制双足机器人模型,设置仿真环境,以及实现基本的行走算法。首先,我们需要创建一个双足机器人模型。PyBullet支持多种模型格式,包括URDF(Unified Robot Description Format)和MJCF(MuJoCo XML Format)。URDF是一种广泛使用的机器人模型描述格式,我们将使用URDF来创建 阅读详情

以往写服务器启动脚本,关闭服务时,大多采用找PS-EF | GREP xxxx ,来 PID的方法,若运行成功,则echo .......... [ok],等等,总觉得不是很专业,,但凡看过REDHAT的启动脚本,他根本就没这些字眼,那么他是怎么实现的呢? 看完下面这篇文章,应该可以很深入的理解REDHAT是如何写的了。



脚本成功的关键:

    1、定义lock_file

    2、定义PIDfile,并将PID写入PIDfile


那么,如何得到当前程序PID值呢?可用如下方法(一般有两个文件,一个是程序,一个是启动脚本):

1、在要运行的程序中定义pid_file文件路径,

2、在主程序结束时的最后一行加一句

echo $! > $pid_file # 若$!值为空,表示程序已退出

3、在启动脚本中去读PID_FILE即可

4、如果无法控制写PID_FILE,可以用  pidof  -x  command_path 也是可直接返回PID值的。

******************************************************************************************

以下来自互联网


functions这个脚本是给/etc/init.d里边的文件使用的。提供了一些基础的功能,看看里边究竟有些什么。首先会设置umask,path,还有语言环境,然后会设置success,failure,warning,normal几种情况下的字体颜色。下面再看看提供的重要方法:
checkpid:检查是否已存在pid,如果有一个存在,返回0(通过查看/proc目录)
daemon:启动某个服务。/etc/init.d目录部分脚本的start使用到这个
killproc:杀死某个进程。/etc/init.d目录部分脚本的stop使用到这个
pidfileofproc:寻找某个进程的pid
pidofproc:类似上面的,只是还查找了pidof命令
status:返回一个服务的状态
echo_success,echo_failure,echo_passed,echo_warning分别输出各类信息
success,failure,passed,warning分别记录日志并调用相应的方法
action:打印某个信息并执行给定的命令,它会根据命令执行的结果来调用 success,failure方法
strstr:判断$1是否含有$2
confirm:显示 "Start service $1 (Y)es/(N)o/(C)ontinue? [Y]"的提示信息,并返回选择结果

 

详细分析:

# -*-Shell-script-*-
#
# functions This file contains functions to be used by most or all            # 注释 :该脚本几乎被 /etc/init.d/ 下的所有脚本所调用,因为它包含了大量的
#  shell scripts in the /etc/init.d directory.                                          
# 的基础函数。同时也被 /etc/rc.d/rc.sysinit ,例如 success、action、failure 等函数
#

 
TEXTDOMAIN=initscripts                # 设置 TEXTDOMAIN 变量
 
 
##########################################################################################################################################################
# Make sure umask is sane            # 确保 root 用户的 umask 是正确的 022 (也就是 rwxr-xr-x)
umask 022
 
# Set up a default search path.                                        # 设置默认的 PATH 变量
PATH="/sbin:/usr/sbin:/bin:/usr/bin:/usr/X11R6/bin"         # 默认为 /sbin:/usr/sbin:/bin:/usr/bin:/usr/X11R6/bin
export PATH                                                                  # 导出为环境变量
 
# Get a sane screen width                                                 # 设置正确的屏幕宽度
[ -z "${COLUMNS:-}" ] && COLUMNS=80                                # 如果 COLUMNS 变量的值为空,则设置为 80 (列)
 
[ -z "${CONSOLETYPE:-}" ] && CONSOLETYPE="`/sbin/consoletype`"            # 如果 CONSOLETYPE 为空则设置 CONSOLETYPE 为 /sbin/consoletype 命令返回的值
                                                                                                             # 一般是 vt 或者 pty 、serial
##########################################################################################################################################################
if [ -f /etc/sysconfig/i18n -a -z "${NOLOCALE:-}" ] ; then                             # 如果存在 /etc/sysconfig/i18n 且 NOLOCALE 变量的值为空,则
      . /etc/sysconfig/i18n                                                                                        # 执行 /etc/sysconfig/i18n 文件,取得 LANG 变量的值
      if [ "$CONSOLETYPE" != "pty" ]; then                                                                    
# 如果当前 console 类型不是 pty(远程登录),而是 vt 或者 serial ,则
          case "${LANG:-}" in                                                                                                    
# 根据 LANG 的值作出选择
              ja_JP*|ko_KR*|zh_CN*|zh_TW*|bn_*|bd_*|pa_*|hi_*|ta_*|gu_*)                                        
# 如果 LANG 是 日文、中文简体、中文繁体、韩文等,则
                   export LC_MESSAGES=en_US                                                                                                
# 把 LC_MESSAGES 设置为 en_US
                   export LANG                                                                                                                       # 同时导出为环境变量
                   ;;
              *)
                   export LANG                                                                                                               
 # 如果是其他类型的语言,则直接导出 LANG
               ;    ;
         esac
      else                                                                                                                    # 如果当前 consle 是 pty                                                    
       [ -n "$LC_MESSAGES" ] && export LC_MESSAGES                                                        # 且如果 LC_MESSAGES 不为空,则直接导出 LC_MESSAGES
       export LANG
  fi
fi
##########################################################################################################################################################
 
# 下面是设置 success、failure、passed、warning 4种情况下的字体颜色的
 
# Read in our configuration
if [ -z "${BOOTUP:-}" ]; then                                                
# 首先如果 BOOTUP 变量为空,则
  if [ -f /etc/sysconfig/init ]; then                                            
# 如果存在 /etc/sysconfig/init 文件,执行 /etc/sysconfig/init 文件
      . /etc/sysconfig/init
  else                                                                                    
# 否则我们就手工设置
    # This all seem confusing? Look in /etc/sysconfig/init,
    # or in /usr/doc/initscripts-*/sysconfig.txt
    BOOTUP=color                                                                       
 # 第一设置 BOOTUP 变量,默认就是 color
    RES_COL=60                                                                          
# 第二设置设置在屏幕的第几列输出后面的 "[ xxx ]" ,默认是第60列
    MOVE_TO_COL="echo -en
//033[${RES_COL}G "                           # MOVE_TO_COL 是用于打印 "OK" 或者 "FAILED" ,或者 "PASSED" ,或者 "WARNING" 之前的部分,不含 "["
    SETCOLOR_SUCCESS="echo -en
//033[1;32m "                              # SETCOLOR_SUCCESS 设置后面的字体都为绿色
    SETCOLOR_FAILURE="echo -en
//033[1;31m "                              # SETCOLOR_FAILURE 设置后面将要输出的字体都为红色
    SETCOLOR_WARNING="echo -en
//033[1;33m "                            # SETCOLOR_WARNING 设置后面将要输出的字体都为黄色
    SETCOLOR_NORMAL="echo -en
//033[0;39m "                               # SETCOLOR_NORMAL 设置后面输出的字体都为白色(默认)
    LOGLEVEL=1
  fi
  if [ "$CONSOLETYPE" = "serial" ]; then                                        # 如果是通过串口登录的,则全部取消彩色输出
      BOOTUP=serial
      MOVE_TO_COL=
      SETCOLOR_SUCCESS=
      SETCOLOR_FAILURE=
      SETCOLOR_WARNING=
      SETCOLOR_NORMAL=
  fi
fi
 
##########################################################################################################################################################
if [ "${BOOTUP:-}" != "verbose" ]; then                     # 如果 BOOTUP 变量的值不为 verbose ,则
   INITLOG_ARGS="-q"                                                    # 把 INITLOG_ARGS 的值设置为 -q (安静模式)
else                                                                    
# 否则
   INITLOG_ARGS=                                                         # 把 INITLOG_ARGS 的值请空 
fi
##########################################################################################################################################################
# Check if $pid (could be plural) are running             # 下面定义一个函数 checkpid (),目的是检查 /proc 下是否存在指定的目录(例如 /proc/1/)
checkpid() {                                                        
# 如果有任意一个存在,则返回0;
 local i
 
 for i in $* ; do
  [ -d "/proc/$i" ] && return 0
 done
 return 1                                                            
# 如果给出的参数全部不存在对应的目录,则返回1
}
 
##########################################################################################################################################################
# A function to start a program.                            # 下面定义最重要的一个函数,daemon 函数,它的作用是启动某项服务。/etc/init.d/ 下的脚本的 start 部分都会用到它
daemon() {
 # Test syntax.
 local gotbase= force=
 local base= user= nice= bg= pid=
 nicelevel=0
 while [ "$1" != "${1##[-+]}" ]; do                                        # daemon
函数本身可以指定多个选项,例如 --check <value> ,--check=<value> ,
   case $1 in
     '')    echo $"$0: Usage: daemon [+/-nicelevel] {program}"    # 也可以指定 nice 值
            return 1;;
     --check)
     base=$2
     gotbase="yes"
     shift 2
     ;;
     --check=?*)
         base=${1#--check=}
     gotbase="yes"
     shift
     ;;
     --user)                                                                        # 也可以指定要以什么用户身份运行(--user <usr> , --user=<usr>)
     user=$2
     shift 2
     ;;
     --user=?*)
            user=${1#--user=}
     shift
     ;;
     --force)
         force="force"                                                           
 # --force 表示强制运行
     shift
     ;;
     [-+][0-9]*)
         nice="nice -n $1"                                                        # 如果 daemon 的第一个参数是数字,则认为是 nice 值
            shift
     ;;
     *)     echo $"$0: Usage: daemon [+/-nicelevel] {program}"
            return 1;;
   esac
 done
 
        # Save basename.                                                        # basename 就是从服务器的二进制程序的 full path 中取出最后的部分
        [ -z "$gotbase" ] && base=${1##*/}                                        
 
        # See if it's already running. Look *only* at the pid file.     # 检查该服务是否已经在运行。不过 daemon 函数只查看 pid 文件而已
 if [ -f /var/run/${base}.pid ]; then                                         
# 如果 /var/run 下存在该服务的 pid 文件,则
  local line p
  read line < /var/run/${base}.pid                                               
# 从该 pid 文件每次读取一行,送给变量 line 。注意 pid 文件可能有多行,且不一定都是数字
  for p in $line ; do                                                                   
 # 对于 line 变量的每个 word 进行检查
   [ -z "${p//[0-9]/}" -a -d "/proc/$p" ] && pid="$pid $p"                    
 # 如果 p 全部是数字,且存在 /proc/$p/ 目录,则认为该数字是一个 pid ,把它加入到 pid 变量
  done                                                                                       # 到最后 pid 变量的值可能是有多个由空格分隔的数字组成
 fi
 
 [ -n "${pid:-}" -a -z "${force:-}" ] && return                                  # 如果 pid 变量最终为空,则 force 变量为空(不强制启动),则返回
 
 # make sure it doesn't core dump anywhere unless requested         # 下面对该服务使用的资源作一些设置
 ulimit -S -c ${DAEMON_COREFILE_LIMIT:-0} >/dev/null 2>&1          # ulimit 是控制由该 shell 启动的进程能够使用的资源,-S 是 soft control 的意思,-c 是指最大的 core   
                                                                                                # dump 文件大小,如果 DEAMON_COREFILE_LIMIT 为空,则默认为 0
 
 # if they set NICELEVEL in /etc/sysconfig/foo, honor it                # 如果存在 /etc/sysconfi/foo 文件,且其中有 NICELEVEL 变量则用它代替  daem
on 后面的那个 nice 值
 [ -n "$NICELEVEL" ] && nice="nice -n $NICELEVEL"                        # 注意,这里的 nice 赋值是用 nice -n <value> 的格式,因为 nice 本身可以启动命令,用这个格式较方便
 
 # Echo daemon                                                                         
# 如果 BOOTUP 的值为 verbose ,则打印一个服务名
        [ "${BOOTUP:-}" = "verbose" -a -z "$LSB" ] && echo -n " $base"
 
 # And start it up.                                                                                         # 下面是开始启动它了
 if [ -z "$user" ]; then                                                                                  
# 如果 user 变量为空,则默认使用 root 启动它
    $nice initlog $INITLOG_ARGS -c "$*"                                                                # 执行 nice -n <nice_value> initlog -q -c "$*" 
 else                                                                                                         
# 如果指定了用户,则
    $nice initlog $INITLOG_ARGS -c "runuser -s /bin/bash - $user -c /"$*/""                
# 执行 nice -n <nice_value> initlog -q -c "runuser -s /bin/bash - <user> -c "$*"
 fi
 [ "$?" -eq 0 ] && success $"$base startup" || failure $"$base startup"                # 如果上面的命令成功,则显示一个绿色的 [ OK ] ,否则显示 [ FAILURE ]
}
 
##########################################################################################################################################################
 
# A function to stop a program.                                # 下面定义另外一个很重要的函数 killproc ,/etc/init.d/ 下面的脚本的 stop 部分都会用到它
killproc() {
 RC=0                                                                    # RC 是最终返回的值,初始化为 0
 # Test syntax.
 if [ "$#" -eq 0 ]; then                                            
# killproc 函数的语法格式是 killproc <service> [<signal>] ,例如 killproc sm-client 9
  echo $"Usage: killproc {program} [signal]"              
  return 1
 fi
 
 notset=0                                                              # noset 是用于检查用户是否指定了 kill 要使用的信号
 # check for second arg to be kill level                  
 if [ -n "$2" ]; then                                                
# 如果 $2 不为空,则表示用户有设定信号,则
  killlevel=$2                                                            
# 把 $2 的值赋予 killlevel 变量
 else                                                                    
# 否则
  notset=1                                                                
# notset 变量的值为1,同时 killlevel 为 '-9' (KILL 信号)
  killlevel="-9"
 fi
 
# 补充 :注意,并不是说用户没有指定信号地停止某项服务时,就会立即用 kill -9 这样的方式强制杀死,而是先用 TERM 信号,然后再用 KILL
 
        # Save basename.
        base=${1##*/}                                                # basename 就是得出服务的名称
 
        # Find pid.
 pid=                                                                    
# 把 pid 变量的值清空。注意,不是指 pid 变量的值等于下面脚本的执行结果,要看清楚
 if [ -f /var/run/${base}.pid ]; then                        
# 下面和上面的 daemon 函数一样找出 pid 
    local line p
    read line < /var/run/${base}.pid
    for p in $line ; do
       [ -z "${p//[0-9]/}" -a -d "/proc/$p" ] && pid="$pid $p"
    done
 fi
 if [ -z "$pid" ]; then                                                
# 不过和 daemon 不同的是,一旦 pid 为空不会直接 return 而是尝试用 pid 命令再次查找
  pid=`pidof -o $$ -o $PPID -o %PPID -x $1 || /            
# -o 是用于忽略某个 pid ,-o $$ 是忽略当前 shell 的 pid、-o $PPID 是忽略 shell 的 pid
   pidof -o $$ -o $PPID -o %PPID -x $base`                   # -o %PPID 是忽略 pidof 命令的父进程,要查询的进程是 $1 (fullpath) 或者 $base 
 fi
 
 # Kill it.                                                            
  if [ -n "${pid:-}" ] ; then                                        # 如果 pid 的值最终不为空,则
    [ "$BOOTUP" = "verbose" -a -z "$LSB" ] && echo -n "$base "    
# 且 BOOTUP 的值为 verbose ,且 LSB 变量不为空,则打印一个服务名
    if [ "$notset" -eq "1" ] ; then                                         # 如果 notset 变量不为1,表示用户没有指定信号,则
         if checkpid $pid 2>&1; then                                        
# 调用 checkpid  $pid 检查是否在 /proc/ 下存在进程目录,如果有
              # TERM first, then KILL if not dead                            
# 先尝试用 TERM 信息,不行再用 KILL 信号
              kill -TERM $pid >/dev/null 2>&1                              
  # 执行 kill -TERM $pid
              usleep 100000                                                          # usleep 和 sleep 一样,不过单位是百万分之1秒。这里休眠1秒
              if checkpid $pid && sleep 1 &&                                
# 如果 checkpid $pid 还是查到有 /proc/<pid>/ 目录存在,则表示还没有杀死,继续等待1秒
                 checkpid $pid && sleep 3 &&                                
# 如果1秒后用 checkpid 检查还是有,则再等待3秒;
                 checkpid $pid ; then                                            # 如果还是没有杀死,则用 KILL 信号
                        kill -KILL $pid >/dev/null 2>&1                            
# 执行 kill -KILL 杀死它
                        usleep 100000                                                    
# 等待1秒种
              fi
    fi
    checkpid $pid                                                             # 再次检查 pid 目录       
    RC=$?                                                                         
# 并把结果返回给 RC ,这就算是 killproc 的最后状态了
    [ "$RC" -eq 0 ] && failure $"$base shutdown" || success $"$base shutdown"    
# 如果 RC 的值为0,则表示kill -9 没有杀死了进程,则调用 failure 函数,否则调用 success 
    RC=$((! $RC))
  
    # use specified level only                                            # 上面都是在没有指定信号的情况的,下面是用户指定了信号的。例如 restart)或者 reload)部分
    else    # 这个 else 是针对 if [ "$notset" -eq "1" ]  的
       if checkpid $pid; then                                             # 如果检查到进程存在,则
            kill $killlevel $pid >/dev/null 2>&1                            
# 执行kill命令,但使用指定的信号 $killlevel
            RC=$?                                                                    # 并把状态值返回给变量 RC
            [ "$RC" -eq 0 ] && success $"$base $killlevel" || failure $"$base $killlevel"    
# 如果 RC 为0则表示成功,调用 success;否则调用 failure 函数
       fi
  fi
 else      # 这个 else 是针对 if [ -n "${pid:-}" ]  的,也就是说没有 pid 文件,pidof 命令也没有找到 pid ,则
     failure $"$base shutdown"                # 调用 failure 函数,表示停止服务失败
     RC=1                                            
 # 同时 RC 的值为1
 fi
 
 # Remove pid file if any.                     # 根据具体情况可能需要删除 pid 文件
 if [ "$notset" = "1" ]; then                    
# 如果 notset 不为1 ,也就是用户没有指定信号的情况
            rm -f /var/run/$base.pid            
# 自动删除 /var/run 下的 pid 文件
 fi
 return $RC                                        
# 并把 RC 作为 exit status 返回
}
 
# 补充 :自所以删除 pid 文件只针对 notset 为1 的情况,是因为 -HUP 信号(重读配置),并不杀死进程,所以不能删除它的 pid 文件
 
# 例如下面 :
 
[root@mail init.d]# ps -ef |grep xinetd
root      2635     1  0 12:25 ?        00:00:00 xinetd -stayalive -pidfile /var/run/xinetd.pid
[root@mail init.d]# ./xinetd reload
Reloading configuration:                                   [  OK  ]
[root@mail init.d]# ps -ef |grep xinetd
root      2635     1  0 12:25 ?        00:00:00 xinetd -stayalive -pidfile /var/run/xinetd.pid
root      3927  3412  0 16:43 pts/0    00:00:00 grep xinetd
[root@mail init.d]#
 
可以看到 pid 在 reload 后并没有变
 
##########################################################################################################################################################
# A function to find the pid of a program. Looks *only* at the pidfile        # 下面的 pidfileofproc 函数和 checkpid 类似,但不执行 pidof 命令,只查询 pid 文件
pidfileofproc() {
 local base=${1##*/}
 
 # Test syntax.
 if [ "$#" = 0 ] ; then
  echo $"Usage: pidfileofproc {program}"
  return 1
 fi
 
 # First try "/var/run/*.pid" files
 if [ -f /var/run/$base.pid ] ; then
         local line p pid=
    read line < /var/run/$base.pid
    for p in $line ; do
         [ -z "${p//[0-9]/}" -a -d /proc/$p ] && pid="$pid $p"
    done
         if [ -n "$pid" ]; then
                 echo $pid
                 return 0
         fi
 fi
}
##########################################################################################################################################################
# A function to find the pid of a program.                        # 下面的 pidofproc 函数和上面的 pidfileofproc 函数类似,但多了一步 pidof 命令
pidofproc() {
 base=${1##*/}
 
 # Test syntax.
 if [ "$#" = 0 ]; then
  echo $"Usage: pidofproc {program}"
  return 1
 fi
 
 # First try "/var/run/*.pid" files
 if [ -f /var/run/$base.pid ]; then
         local line p pid=
  read line < /var/run/$base.pid
  for p in $line ; do
         [ -z "${p//[0-9]/}" -a -d /proc/$p ] && pid="$pid $p"
  done
         if [ -n "$pid" ]; then
                 echo $pid
                 return 0
         fi
 fi
 pidof -o $$ -o $PPID -o %PPID -x $1 || /
  pidof -o $$ -o $PPID -o %PPID -x $base
}
##########################################################################################################################################################
status() {                                                                   # 注释 :下面的 status 函数是判断服务的状态,总共有4种
 local base=${1##*/}
 local pid
 
 # Test syntax.
 if [ "$#" = 0 ] ; then
  echo $"Usage: status {program}"
  return 1
 fi
 
 # First try "pidof"                                                         # 同样是查找 pid 先。直接使用 pidof 命令
 pid=`pidof -o $$ -o $PPID -o %PPID -x $1 || /                
      pidof -o $$ -o $PPID -o %PPID -x ${base}`
 if [ -n "$pid" ]; then                                                    
# 如果 pid 变量的值不为空,则表示找到进程,
         echo $"${base} (pid $pid) is running..."                 
# 则打印 "xxx (pid nnn) is running " ,
         return 0                                                            
# 并返回 0
 fi
 
 # Next try "/var/run/*.pid" files                                     # 如果 pidof 命令没有找到,则尝试从 pid 文件找
 if [ -f /var/run/${base}.pid ] ; then
         read pid < /var/run/${base}.pid
         if [ -n "$pid" ]; then                                                
# 如果 pidof 命令找不到,但从 pid 文件找到了 pid ,则
                 echo $"${base} dead but pid file exists"                
# 打印 "xxx dead but pid file exists",
                 return 1                                                            
# 并返回 1
         fi
 fi
 # See if /var/lock/subsys/${base} exists                            
# 如果 pidof 命令和 pid 文件都没有找到 pid ,则
 if [ -f /var/lock/subsys/${base} ]; then                              
# 如果在 /var/lock/subsys 下存在对应的文件,则
  echo $"${base} dead but subsys locked"                               
 # 打印 “xxxx dead but subsys locked”,
  return 2                                                                            
# 并返回 2
 fi
 echo $"${base} is stopped"                                                # 如果 pidof 命令、pidf 文件都没有找到pid ,且没有别锁,则打印 “xxx is stopped”
 return 3                                                                          
 # 并返回3
}
##########################################################################################################################################################
 
# 注释 :下面的 echo_xxx 函数就是真正在屏幕上打印 [ ok ] 、[ PASSED ]、[ FAILURE ]、[ WARNING ] 的部分了
 
echo_success() {                                                                    # 下面是 echo_success 部分
  [ "$BOOTUP" = "color" ] && $MOVE_TO_COL                           
 # 首先是打印 “[” 之前的空格
  echo -n "[  "                                                                        
# 然后打印 "["
  [ "$BOOTUP" = "color" ] && $SETCOLOR_SUCCESS                    
# 设置字体为红色
  echo -n $"OK"                                                                      
# 打印 OK
  [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL                    
# 返回字体为白色
  echo -n "  ]"                                                                         # 打印 "]"    
  echo -ne "/r"                                                                        # 换行。
  return 0                                                                               # 返回 0,其他一律返回 1
 
 
echo_failure() {
  [ "$BOOTUP" = "color" ] && $MOVE_TO_COL
  echo -n "["
  [ "$BOOTUP" = "color" ] && $SETCOLOR_FAILURE
  echo -n $"FAILED"
  [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
  echo -n "]"
  echo -ne "/r"
  return 1
}
 
echo_passed() {
  [ "$BOOTUP" = "color" ] && $MOVE_TO_COL
  echo -n "["
  [ "$BOOTUP" = "color" ] && $SETCOLOR_WARNING
  echo -n $"PASSED"
  [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
  echo -n "]"
  echo -ne "/r"
  return 1
}
 
echo_warning() {
  [ "$BOOTUP" = "color" ] && $MOVE_TO_COL
  echo -n "["
  [ "$BOOTUP" = "color" ] && $SETCOLOR_WARNING
  echo -n $"WARNING"
  [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
  echo -n "]"
  echo -ne "/r"
  return 1
}
##########################################################################################################################################################
# Inform the graphical boot of our current state
update_boot_stage() {
  if [ "$GRAPHICAL" = "yes" -a -x /usr/bin/rhgb-client ]; then
    /usr/bin/rhgb-client --update="$1"
  fi
  return 0
}
##########################################################################################################################################################
# Log that something succeeded                                                
success() {                                                                                                
# success 函数除了打印 [ xxx ] 之外,还会使用 initlog 记录信息
  if [ -z "${IN_INITLOG:-}" ]; then
     initlog $INITLOG_ARGS -n $0 -s "$1" -e 1                                                 
  # -n 是 --name 的意思,-s 是 --string ,-e 是 --event ,1 表示完全成功
  else
     # silly hack to avoid EPIPE killing rc.sysinit
     trap "" SIGPIPE
     echo "$INITLOG_ARGS -n $0 -s /"$1/" -e 1" >&21
     trap - SIGPIPE
  fi
  [ "$BOOTUP" != "verbose" -a -z "$LSB" ] && echo_success
  return 0
}
 
# Log that something failed
failure() {
  rc=$?
  if [ -z "${IN_INITLOG:-}" ]; then
     initlog $INITLOG_ARGS -n $0 -s "$1" -e 2                                                    
# failure 的话 --event 是 2 是失败
  else
     trap "" SIGPIPE
     echo "$INITLOG_ARGS -n $0 -s /"$1/" -e 2" >&21
     trap - SIGPIPE
  fi
  [ "$BOOTUP" != "verbose" -a -z "$LSB" ] && echo_failure
  [ -x /usr/bin/rhgb-client ] && /usr/bin/rhgb-client --details=yes
  return $rc
}
 
# Log that something passed, but may have had errors. Useful for fsck
passed() {
  rc=$?
  if [ -z "${IN_INITLOG:-}" ]; then
     initlog $INITLOG_ARGS -n $0 -s "$1" -e 1                                                 # passed 的话 --event 还是1
  else
     trap "" SIGPIPE
     echo "$INITLOG_ARGS -n $0 -s /"$1/" -e 1" >&21
     trap - SIGPIPE
  fi
  [ "$BOOTUP" != "verbose" -a -z "$LSB" ] && echo_passed
  return $rc
} 
 
# Log a warning
warning() {
  rc=$?
  if [ -z "${IN_INITLOG:-}" ]; then
     initlog $INITLOG_ARGS -n $0 -s "$1" -e 1                                                
# warning 的话 --event 也是 1
  else
     trap "" SIGPIPE
     echo "$INITLOG_ARGS -n $0 -s /"$1/" -e 1" >&21
     trap - SIGPIPE
  fi
  [ "$BOOTUP" != "verbose" -a -z "$LSB" ] && echo_warning
  return $rc
} 
##########################################################################################################################################################
# Run some action. Log its output.                                                        # action 函数是另外一个最重要的函数,它的作用是打印某个提示信息并执行给定命令
tion() {
  STRING=$1
  echo -n "$STRING "
  if [ "${RHGB_STARTED}" != "" -a -w /etc/rhgb/temp/rhgb-console ]; then
      echo -n "$STRING " > /etc/rhgb/temp/rhgb-console
  fi
  shift
  initlog $INITLOG_ARGS -c "$*" && success $"$STRING" || failure $"$STRING"
  rc=$?
  echo
  if [ "${RHGB_STARTED}" != "" -a -w /etc/rhgb/temp/rhgb-console ]; then
      if [ "$rc" = "0" ]; then
       echo_success > /etc/rhgb/temp/rhgb-console
      else
        echo_failed > /etc/rhgb/temp/rhgb-console
 [ -x /usr/bin/rhgb-client ] && /usr/bin/rhgb-client --details=yes
      fi
      echo
  fi
  return $rc
}
##########################################################################################################################################################
# returns OK if $1 contains $2                        # strstr 函数是判断 $1 字符串是否含有 $2 字符串,是则返回0,否则返回1
() {
  [ "${1#*$2*}" = "$1" ] && return 1
  return 0
}
##########################################################################################################################################################
# Confirm whether we really want to run this service                                       # confirm 函数是用于交互式的启动服务
nfirm() {
  [ -x /usr/bin/rhgb-client ] && /usr/bin/rhgb-client --details=yes
  while : ; do 
    echo -n $"Start service $1 (Y)es/(N)o/(C)ontinue? [Y] "                                   
# 会打印一个提示信息
    read answer
    if strstr $"yY" "$answer" || [ "$answer" = "" ] ; then                                          
# 如果 answer 变量是 y 或者 Y 则
        return 0                                                                                                                
# 返回 0(但未真正启动)
    elif strstr $"cC" "$answer" ; then                                                                    
# 如果 answer 是 c 或者 C ,则
        rm -f /var/run/confirm                                                                                          # 删除 /var/run/confirm 文件                           
        [ -x /usr/bin/rhgb-client ] && /usr/bin/rhgb-client --details=no
        return 2                                                                                                                
# 返回2
   elif strstr $"nN" "$answer" ; then                                                                      
# 如果 answer 是 n 或者 N,则
  return 1                                                                                                                       
# 直接返回1
     fi
  done
}

基于信号完整性的PCB设计原则 基于信号完整性的PCB设计建议,以单网络的信号布线作为评估对象,给出了一些最基础的设计指导,如何灵活运用,取决于设计者根据实际场景如何做取舍和判断。 阅读详情

相关推荐

Anomalib实战:从零开始构建自定义数据集的异常检测模型

本文详细介绍了如何使用Anomalib 2.1.0从零开始构建自定义数据集的异常检测模型。通过实战演示,指导读者准备符合规范的数据集结构,快速上手训练Patchcore等先进算法,并完成模型推理与调优,为工业质检、医疗影像等场景提供高效的视觉异常检测解决方案。

weixin_29165465的博客 109

/etc/init.d/functions 说明

from:http://blog.csdn.net/adcxf/article/details/4013579 functions这个脚本是给/etc/init.d里边的文件使用的。提供了一些基础的功能,看看里边究竟有些什么。首先会设置umask,path,还有语言环境,然后会设置success,failure,warning,normal几种情况下的字体颜色。下面再看看提供的重要方法:...

renzhelife 628

双重机器学习 stata教程 手把手教学

双重机器学习(DDML)的stata教程

weixin_59030591的博客 1万+

/etc/rc.d/init.d/functions文件详细分析

/etc/rc.d/init.d/functions文件详细分析functions这个脚本是给/etc/init.d里边的文件使用的(可理解为全局文件)。提供了一些基础的功能,看看里边究竟有些什么。首先会设置umask,path,还有语言环境,然后会设置success,failure,warning,normal几种情况下的字体颜...

qianghong000的博客 747

第10篇:Agent + 爬虫 = 全自动数据采集专家

在企业级数据采集场景中,传统爬虫的痛点已经到了无法忽视的地步:而Agent + 爬虫的组合,就是这些痛点的终极解决方案。它的核心逻辑是:把爬虫从「人工写死的固定执行脚本」,升级为「能自主分析、自主决策、自主适配、自主修复的智能采集机器人」。我们在生产环境中做过对比测试:传统爬虫开发10个网站的采集脚本需要3人天,而Agent采集机器人只需要3分钟,页面改版后的修复成本从1人天降到了0,采集任务的成功率从62%提升到了95%以上。终端执行以下命令,安装基础依赖,与前9篇环境完全兼容: 二、核心能力拆解:Age

专注于Python爬虫开发,分享爬虫技巧、项目实战与反爬经验,使用Scrapy、BeautifulSoup等工具,解决数据抓取难题。 1577

YOLOv8改进:基于EfficientNetV2均衡缩放网络的特征提取层优化【YOLOv8】

YOLO(You Only Look Once)系列模型以其高效的实时目标检测能力而闻名。YOLOv8作为该系列的最新版本,通过引入改进的网络结构和算法优化,进一步提升了目标检测的性能。然而,YOLOv8在特征提取阶段的网络结构仍有改进的空间。EfficientNetV2是一种基于均衡缩放的卷积神经网络,它通过优化网络的宽度、深度和分辨率来实现高效的特征提取。与之前的EfficientNet版本相比,EfficientNetV2在速度和精度上都有显著提升,尤其在处理复杂目标检测任务时表现尤为突出。

博客 1582

/etc/init.d/functions详解

/etc/init.d/functions详解 functions这个脚本是给/etc/init.d里边的文件使用的。提供了一些基础的功能,看看里边究竟有些什么。首先会设置umask,path,还有语言环境,然后会设置success,failure,warning,normal几种情况下的字体颜色。下面再看看提供的重要方法: checkpid:检查是否已存在pid,如果有一个存在,返回0(通过查看/proc目录) daemon:启动某个服务。/etc/init.d目录部分脚本的start使用到这个 kil

Yonx 1768

Unity技术开发干货 - 总目录

总目录 欢迎大家来到 passion 的《Unity技术开发干货》开始前博主先列出学习的大纲,同时也供大家学习参考,如果有什么问题,欢迎留言。 一.Unity基础: Unity基础-脚本生命周期 Unity基础-向量 Unity基础-寻路系统 Unity基础-物理系统 Unity基础-Mecanim动画系统 Unity基础-UGUI Unity基础-灯光 Unity-UGUI之Event System Unity-2018-粒子系统 Unity-协程入门 Unity-2D物理引擎、铰链、效应器 Unity-

TxNet 4261

centos7容器运行报错/etc/rc.d/init.d/functions: No such file or directory

解决方案 yum -y install initscripts

想练武,就得下功夫 1323

34、婴儿监视器应用开发指南

本文详细介绍了基于 ESP32 和 Edge Impulse 开发婴儿监视器应用的全过程,涵盖音频处理、机器学习推理、ESP RainMaker 平台集成以及内存监控等功能。通过实现 AppAudio、AppRmaker 和 AppMem 三个核心类,完成了婴儿哭声的实时检测与远程通知,并通过合理的内存管理优化,有效节省了 ESP32 的内部 RAM 资源。文章还提供了完整的代码示例和配置说明,适用于物联网和嵌入式 AI 应用开发爱好者参考学习。

python9snake的博客 95

【unity实战】使用unity的Navigation+LineRenderer实现一个3D人物寻路提前指示预测移动轨迹的效果,并可以适配不同的地形

本文介绍了在Unity中使用Navigation导航系统和LineRenderer实现3D人物寻路轨迹预测效果的方法。通过NavMesh.CalculatePath计算路径点,结合Physics.Raycast进行地面点投射,将路径点赋予LineRenderer渲染出移动轨迹。关键点包括:1)利用NavMesh.CalculatePath计算两点间可行走路径;2)通过射线检测获取地面点提高路径适配性;3)使用协程定期更新路径绘制。文章还提供了完整代码实现,并说明需要将地面图层设置为Ground并进行导航网格

向宇的博客,专注php/web全栈 unity游戏开发,欢迎大家评论纠错 459

脚本中. /etc/rc.d/init.d/functions: No such file or directory 错误解决

rpm -qf /etc/init.d/functions 查找到 [xx@ ~]$ rpm -qf /etc/init.d/functions initscripts-9.03.40-2.el6.centos.4.x86_64 [xx@ ~]$ rpm -qf /sbin/service initscripts-9.03.40-2.el6.centos.4.x86_64 yum 安装即可: yum install initscripts ———————————————— 版权声明:本文为优快云博主「半路

花语无痕的博客 2419

YOLOv8与UNetV2融合:一种面向目标检测与图像分割的混合方法【附核心代码】

我们提出了一种基于YOLOv8和UNetV2相结合的混合架构。该架构利用YOLOv8作为主干进行目标检测,同时在YOLOv8的特征提取过程中,引入UNetV2来进行图像分割任务的增强。在该架构中,YOLOv8负责大范围目标检测和位置预测,而UNetV2则在检测网络的特征图基础上,通过其高效的上下文信息提取和细节恢复能力,进一步优化分割任务。在本文中,我们提出了一种改进YOLOv8的方法,通过引入图像分割网络UNetV2来提高图像分割检测性能。

一键难忘的博客 3526

/etc/init.d/functions

functions这个脚本是给/etc/init.d里边的文件使用的。提供了一些基础的功能,看看里边究竟有些什么。首先会设置umask,path,还有语言环境,然后会设置 success,failure,warning,normal几种情况下的字体颜色。下面再看看提供的重要方法: checkpid:检查是否已存在pid,如果有一个存在,返回0(通过查看/proc目录) daemon:启动某个服...

lilrq的专栏 609

Data-Structures-and-Algorithm-Analysis-in-Java.pdf

作者: Weiss, Mark A. 出版社: Addison Wesley Data Structures and Algorithm Analysis in Java is an “advanced algorithms” book that fits between traditional CS2 and Algorithms Analysis courses. In the old ACM Curriculum Guidelines, this course was known as CS7. This text is for readers who want to learn good programming and algorithm analysis skills simultaneously so that they can develop such programs with the maximum amo...

SAP B1中文培訓教材_SDK

公司内部培训资料,对开发工具 ,DIAPI, UIAPI,Add-ON有详细解说

Linux学习之/etc/init.d/functions详解

/etc/init.d/functions详解 functions这个脚本是给/etc/init.d里边的文件使用的,提供了一些基础的功能,看看里边究竟有些什么。首先会设置umask,path,还有语言环境,然后会设置success,failure,warning,normal几种情况下的字体颜色。下面再看看提供的重要方法: 1 checkpid:检查是否已存在pid,如果有一个存在,返回0(通过查看/proc目录) 2 daemon:启动某个服务。/etc/init.d目录部分脚本...

xyz的专栏 1154

IDEA的使用指南

IDEA基于java的使用手册,可以最快速的上手,在使用中不断的丰富自己的使用技巧.

Linux启动脚本分析之functions

# -*-Shell-script-*-## functionsThis file contains functions to be used by most or all# 注释 :该脚本几乎被 /etc/init.d/ 下的所有脚本所调用,因为它包含了大量的#shell scripts in the /etc/init.d direc...

weixin_34085658的博客 218

STM32F407中文手册

STM32f407中文手册 本参考手册面向应用开发人员,提供有关使用 STM32F405xx/07xx、STM32F415xx/17xx、 STM32F42xxx 和 STM32F43xxx 微控制器存储器与外设的完整信息。STM32F405xx/07xx、STM32F415xx/17xx、STM32F42xxx 和 STM32F43xxx 构成一个微 控制器系列,各产品具有不同的存储器大小、封装和外设。有关订购信息以及器件的机械与电气特性,请参见数据手册。有关 ARM Cortex™-M4F 内核的信息,请参见《Cortex™-M4F 技术参考手册》。

Linux /etc/rc.d/init.d/

在传统的 SysV init 系统中,服务启动脚本通常位于 /etc/rc.d/init.d/ 目录下。这些脚本可以直接执行以启动、停止或重启服务,并且可以接受参数如 start, stop, status 等。如果你想知道位于 /etc/rc.d/init.d/ 目录下的某个脚本文件实际上指向哪里,如果你想获取符号链接的目标而不关心其他信息,可以使用 readlink 命令。这对于脚本编写特别有用。

chengmin123456789的博客 350

/etc/rc.d/init.d目录说明与chkconfig命令详解

/etc/rc.d/init.d目录与chkconfig

weixin_47680367的博客 1903

Linux基础——Shell(二)

case菜单&函数

Xiaofa_123的博客 308

/etc/init.d/functions 详解

http://www.cnblogs.com/sunfie/p/5149678.html

挖坑埋你 2433

linux shell /etc/init.d/functions 加了个函数不起作用

1.在/etc/init.d/functions中加了个函数test(){echo "I am oldboy."} 然后.或source /etc/init.d/functions 调用函数 test提示没有test command 后来在test函数上面发现了return 0,将test函数移到return 0上面就可以了。...

qq_34412985的博客 855

/etc/init.d/functions运用实战配置system服务详解

/etc/init.d/functions详解

爱死亡机器人 1090

functions文件详细分析和说明

bash&amp;shell系列文章:http://www.cnblogs.com/f-ck-need-u/p/7048359.html /etc/rc.d/init.d/functions几乎被/etc/rc.d/init.d/下所有的Sysv服务启动脚本加载,也是学习shell脚本时一个非常不错的材料,在其中使用了不少技巧。 在该文件中提供了几个有用的函数: daemon:启动一...

weixin_33701564的博客 453

/etc/init.d/functions详解[转]

/etc/init.d/functions详解 functions 这个脚本是给/etc/init.d里边的文件使用的。提供了一些基础的功能,看看里边究竟有些什么。首先会设置umask,path,还有语言环境,然 后会设置success,failure,warning,normal几种情况下的字体颜色。下面再看看提供的重要方法:checkpid:检查是否已存在pid,如果有一个存在,返回0(通过...

weixin_34088598的博客 452

虚拟机 /etc/init.d/functions ;RTNETLINK answers: File exists的解决方法

1) centos7启动网卡服务报错“RTNETLINK answers: File exists”的解决方法 /etc/init.d/functions: 没有文件或目录 这个报错是由于最小化安装Centos 7引起的,yum install initscripts -y即可 2) 在 /etc/sysconfig/network-scripts/ifcfg-ens33文件配置...

plumjobc 1169
上一篇: tcpdump抓包
下一篇: ssh-copy-id 与端口
nerissa
博客等级 码龄22年 9粉丝 47原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符  | 博主筛选后可见
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值