高级shell编程笔记(第二十七章 /dev 和 /proc)

第二十七章 /dev 和 /proc

27.1 /dev

在/dev目录内包含以或不以硬件形式出现的物理设备条目。包含被挂载的文件系统的硬设备分区在/dev目录下都有对应的条目,就像 df 命令所展示的。

[root@mail shell]# df
Filesystem              1K-blocks    Used Available Use% Mounted on
/dev/mapper/centos-root  17811456 4809860  13001596  28% /
devtmpfs                   929248       0    929248   0% /dev
tmpfs                      941176       0    941176   0% /dev/shm
tmpfs                      941176    8636    932540   1% /run
tmpfs                      941176       0    941176   0% /sys/fs/cgroup
/dev/vda1                 1038336  147840    890496  15% /boot
tmpfs                      188236       0    188236   0% /run/user/0

在其他方面,/dev目录也包含环回设备,例如/dev/loop0。环回设备是一个使普通文件能被像对待块设备一样来进行存取的机制。这使我们可以将一个大文件内的整个文件系统挂载到系统目录下。

/dev还有少量的伪设备用于特殊的用途,
例如:/dev/null,/dev/zero,/dev/urandom,/dev/sda1,/dev/udp,/dev/tcp

例如:为了挂载一个USB闪盘设备,将下面一行添加到/etc/fstab

/dev/sda1 /mnt/flashdrive auto noauto,user,noatime 0 0

当对/dev/tcp/$host/$port 伪设备文件执行一个命令时,Bash 会打开一个相关的 TCP 的 socket。

Example 27-1 利用/dev/tcp来检修故障(复制粘贴的)

#!/bin/bash
#
TCP_HOST=www.baidu.com
TCP_PORT=80

echo "HEAD / HTTP/1.0" >/dev/tcp/${TCP_HOST}/${TCP_PORT}
MYEXIT=$?

: << EXPLANATION
     If bash was compiled with --enable-net-redirections, it has the capability of
using a special character device for both TCP and UDP redirections. These
redirections are used identically as STDIN/STDOUT/STDERR. The device entries
are 30,36 for /dev/tcp:
          mknod /dev/tcp c 30 36
>From the bash reference:
          /dev/tcp/host/port
     If host is a valid hostname or Internet address, and port is an integer
port number or service name, Bash attempts to open a TCP connection to the
corresponding socket.
EXPLANATION

if [ "X$MYEXIT" = "X0" ]; then
  echo "Connection successful. Exit code: $MYEXIT"
else
  echo "Connection unsuccessful. Exit code: $MYEXIT"
fi
exit $MYEXIT

27.2 /proc

/proc目录实际上是一个伪文件系统。在/proc目录里的文件是当前运行系统和内核及它们的相关信息和统计

[root@zhhs-mail ~]# cat /proc/devices 
Character devices:
  1 mem
  4 /dev/vc/0
 ...
  5 /dev/console
  5 /dev/ptmx
 ...
253 device-mapper
254 mdp
[root@zhhs-mail ~]# cat /proc/interrupts 
           CPU0       
  0:         81   IO-APIC-edge      timer
  1:         10   IO-APIC-edge      i8042
  4:       1176   IO-APIC-edge      serial
 ...
NPI:          0   Nested posted-interrupt event
PIW:          0   Posted-interrupt wakeup event
[root@zhhs-mail ~]# cat /proc/partitions 
major minor  #blocks  name

 252        0   20971520 vda
 252        1    1048576 vda1
 252        2   19921920 vda2
  11        0    1048575 sr0
 253        0   17821696 dm-0
 253        1    2097152 dm-1
[root@zhhs-mail ~]# cat /proc/loadavg 
0.00 0.01 0.05 1/110 30207

Shell脚本可从/proc目录中的一些文件里提取数据

FS=iso
grep $FS /proc/filesystems
kernel_version=$(awk '{print $3}' /proc/version)
CPU=$(awk '/mode name/ {print $4}' < /proc/cpuinfo)

if [ $CPU = Pentium ];then
  run_some_commands
else
  run_different_commands
fi

devfile="/proc/bus/usb/devices"
USB1="Spd=12"
USB2="Spd=480"
bus_speed=$(grep Spd $devfile | awk '{print $9}')

if [ "$bus_speed" = "$USB1" ];then
  echo "USB 1.1 port found"
fi  

/proc 目录下有许多不相同的数字命名的子目录。这些子目录的数字名字都映射对应的当前正在运行的进程的进程号。这些子目录里面有许多文件用于保存对应进程的信息。文件 stat 和 status 保存着进程运行时的各项统计,the cmdline 文件保存该进程的被调用 时的命令行参数,而 and the exe 文件是该运行进程完整路径名的符号链接。还有其他一些文件,但从脚本的观点来看它们都非常的有意思。

Example 27-2 搜索一个与PID相关的进程

#!/bin/bash
#
ARGNO=1
E_WRONGARGS=65
E_BADPID=66
E_NOSUCHPROCESS=67
E_NOPERMISSION=68
PROCFILE=exe

if [ $# -ne $ARGNO ];then
  echo "Usage: `basename $0` PID-number" >&2
  exit $E_WRONGARGS
fi

pidno=$(ps ax | grep $1 | awk '{print $1}' | grep $1)

if [ -z "$pidno" ];then
  echo "No such process running."
  exit $E_NOSUCHPROCESS
fi

if [ ! -r "/proc/$1/$PROCFILE" ];then
  echo "Process $1 running, but..."
  echo "Can't get read permission on /proc/$1/$PROCFILE."
  exit $E_NOPERMISSION
fi

exe_file=$(ls -l /proc/$1 | grep "exe" | awk '{print $11}')

if [ -e "$exe_file" ];then
  echo "Process #$1 invoked by $exe_file."
else
  echo "No such process running."
fi
exit 0

Example 27-3 网络连接状态

#!/bin/bash
#
PROCNAME=postfix
PROCFILENAME=status
NOTCONNECTED=65
INTERVAL=2

pidno=$(ps ax | grep -v "ps ax" | grep -v grep | grep $PROCNAME |awk '{print $1}')

if [ -z "$pidno" ];then
  echo "Not connected."
  exit $NOTCONNECTED
else
  echo "Connected."; echo
fi

while [ true ]
do
  if [ ! -e "/proc/$pidno/$PROCFILENAME" ];then
    echo "Disconnected."
    exit $NOTCONNECTED
  fi
  netstat -s | grep "packets received"
  netstat -s | grep "packets delivered"
  
  sleep $INTERVAL
  echo;echo
done
exit 0

注意:一般来说,写/proc 目录里的文件是危险,因为这样会破坏这个文件系统或摧毁机器。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值