Bash 中 SHLVL 变量为空的时候

SHLVL 环境变量代表 Shell 嵌套执行的深度。


$ echo $SHLVL

1

$ bash

$ echo $SHLVL

2

$ bash

$ echo $SHLVL

3

在 Bash 里,这个值的范围是 [1, 1000],在 1001 的时候会重置到 1。


$ SHLVL=1000

$ bash

bash: warning: shell level (1001) too high, resetting to 1

$ echo $SHLVL

1

我也本以为就是这样了,然而却发现个特例:


$ SHLVL=999

$ bash

$ echo $SHLVL

在嵌套 1000 层的时候,SHEVL 会是个空字符串,也就是说 SHEVL 实际的值会在 [1, 999] 以及空这 1000 个值里轮询,不会真正到达 1000。

看了下 Bash 源码:

void
adjust_shell_level (change)
     int change;
{
  char new_level[5], *old_SHLVL;
  intmax_t old_level;
  SHELL_VAR *temp_var;

  old_SHLVL = get_string_value ("SHLVL");
  if (old_SHLVL == 0 || *old_SHLVL == ‘\0‘ || legal_number (old_SHLVL, &old_level) == 0)
    old_level = 0;

  shell_level = old_level + change;
  if (shell_level < 0)
    shell_level = 0;
  else if (shell_level > 1000)
    {
      internal_warning (_("shell level (%d) too high, resetting to 1"), shell_level);
      shell_level = 1;
    }

  /* We don‘t need the full generality of itos here. */
  if (shell_level < 10)
    {
      new_level[0] = shell_level + ‘0‘;
      new_level[1] = ‘\0‘;
    }
  else if (shell_level < 100)
    {
      new_level[0] = (shell_level / 10) + ‘0‘;
      new_level[1] = (shell_level % 10) + ‘0‘;
      new_level[2] = ‘\0‘;
    }
  else if (shell_level < 1000)
    {
      new_level[0] = (shell_level / 100) + ‘0‘;
      old_level = shell_level % 100;
      new_level[1] = (old_level / 10) + ‘0‘;
      new_level[2] = (old_level % 10) + ‘0‘;
      new_level[3] = ‘\0‘;
    }

  temp_var = bind_variable ("SHLVL", new_level, 0);
  set_auto_export (temp_var);
}

static void
initialize_shell_level ()
{
  adjust_shell_level (1);
}

它把数字转字符串的逻辑只写到 shell_level < 1000 的地方,看上去像是少了最后一个 else 的样子,不管是否是作者有意的,这个表现都应该都不会改动了,反正这也算是 edge case 了,顺便说一句,ksh 和 zsh 都没有这个 1000 限制。

时间: 2024-11-05 15:09:07

Bash 中 SHLVL 变量为空的时候的相关文章

bash中的变量

1.bash中的变量: #命令set:显示所有变量. (1).本地变量:只对当前shell进程有效,对其子shell以及其它shell都无效. 定义本地变量:[set]变量名="Value",例animal=dog 引用本地变量:${变量名},其中{}通常省略,例echo $animal 撤销本地变量:unset 变量名,例unset animal (2).局部变量:只对局部代码有效 定义局部变量:local 变量名=变量值 (3).环境变量:当前shell进程以及其子shell都有效

Linux学习日记--基础命令(7)--bash中的变量,配置文件

变量的定义和使用 变量类型 强类型:定义变量时必须指定类型.参与运算必须符合类型要求:调用未声明变量会产生错误: 弱类型:无须指定类型,默认均为字符型:参与运算会自动进行隐式类型转换:变量无须事先定义可直接调用: 变量命名法则:                1.不能使程序中的保留字:例如if, for;                 2.只能使用数字.字母及下划线,且不能以数字开头:                3.见名知义,         bash中的变量的种类:          

***PHP中判断变量为空的几种方法

总结PHP中,"NULL" 和 "空" 是2个概念. isset  主要用来判断变量是否被初始化过empty  可以将值为 "假"."空"."0"."NULL"."未初始化" 的变量都判断为TRUEis_null  仅把值为 "NULL" 的变量判断为TRUEvar == null  把值为 "假"."空".

bash中的变量以及类型

一.本机变量:支队当前shell进程有效,对其子shell以及其它shell均无效. 定义变量:[set] var_name=value:其中value支持强引用.弱引用.命令引用. 引用变量:${var_name} 撤销变量:unset var_name $set:显示当前系统的所有变量(包括所有本地变量.局部变量和环境变量). 二.局部变量:仅对局部代码有效. local var_name=value,value支持强引用.弱引用.命令引用. 三.环境变量:对当前shell进程以及子shel

Linux bash中的变量分类

1.本地变量 VAR=XYZ 2.局部变量 local VAR=XYZ 3.环境变量 在子shell中可以起作用 export VAR=XYZ 4.位置变量 $0 脚本名本身 $1 第一个参数 $2 第二个参数 ... ${10} 第十个参数 ${11} 第十一个参数 shift 依次向后移动参数 比如:分别显示第一.二.三个参数 !#/bin/bash echo $1 shift echo $1 shift echo $1 5.特殊变量 $? 脚本执行状态(0--正确,1-255错误,1/2/

bash 中的变量

Linux command line 笔记 变量无需声明,自动创建 var=abc #变量a赋值为字符串abc var="hello world" #字符串里有空格赋值要加引号 var="hello world $var" #任何可以扩展成字符串的都可以赋给变量 var=$(ls -l *.md) # 输出结果为字符串的命令 var=$(5*5) #运算符 var="hello\nworld" #转义字符串序列,例子中的\n 最后一个转义字符赋值

在Linux系详解Linux bash中的变量

(大讲台:国内首个it在线教育混合式自适应学习) 统中进行日常运维或者是编写脚本时,变量是再熟悉不过的了,但这些变量都有哪些类型,具体的用法又有哪些差异呢?本文整理分享给大家: 一.bash变量类型: 本地变量 局部变量 环境变量 位置变量 特殊变量(内置) 二.本地变量: varname=value:作用域为整个bash进程可以使用: 变量命名规范: 1. 只能含字母.数字和下划线,并且以字母和下划线开头 2. 最好不要跟系统已有的环境变量重名 3. 见名知意 三.局部变量: local va

Bash中的变量类型

变量的类型: 本地变量:只对当前shell进程有效,对其子shell以及其它shell都无效: 定义变量: [set]Var_Name="Value" 引用变量: ${Var_Name} 撤销变量: unset Var_Name 局部变量:仅对局部代码生效 local Var_Name="Value" 环境变量:对当shell进程及其子shell有效: export Var_Name="Value" 先赋值Var_Name="Value

PHP中判断变量为空的几种方法小结

isset  主要用来判断变量是否被初始化过empty  可以将值为 "假"."空"."0"."NULL"."未初始化" 的变量都判断为TRUEis_null  仅把值为 "NULL" 的变量判断为TRUEvar == null  把值为 "假"."空"."0"."NULL" 的变量都判断为TRUEvar =