coreutils test 源码分析

发布时间 2023-05-27 23:36:03作者: kun2023

Test的代码中主要解析如下语法,当然使用的时候也可以参考如下语法进行语句的编写

/* test(1) accepts the following grammar:
    oexpr   ::= aexpr | aexpr "-o" oexpr ;
    aexpr   ::= nexpr | nexpr "-a" aexpr ;
    nexpr   ::= primary | "!" primary
    primary ::= unary-operator operand
        | operand binary-operator operand
        | operand
        | "(" oexpr ")"
        ;
    unary-operator ::= "-r"|"-w"|"-x"|"-f"|"-d"|"-c"|"-b"|"-p"|
        "-u"|"-g"|"-k"|"-s"|"-t"|"-z"|"-n"|"-o"|"-O"|"-G"|"-L"|"-S";


    binary-operator ::= "="|"=="|"!="|"-eq"|"-ne"|"-ge"|"-gt"|"-le"|"-lt"|
            "-nt"|"-ot"|"-ef";
    operand ::= <any legal UNIX file name>
*/

如下是 test 支持的运算符

选项 类型 Token 操作数个数 类型
-r 只读 FILRD UNOP 文件相关
-w 只写 FILWR UNOP
-x 可执行 FILEX UNOP
-e 存在 FILEXIST UNOP
-f 路径名解析为常规文件的现有目录条目 FILREG UNOP
-d 文件夹 FILDIR UNOP
-c 字符设备 FILCDEV UNOP
-b 块设备 FILBDEV UNOP
-p fifo文件 FILFIFO UNOP
-u 设置了suid FILSUID UNOP
-g 设置了sgid FILSGID UNOP
-k 设置了黏着位 FILSTCK UNOP
-s 文件长度大于0 FILGZ UNOP
-t 文件描述符编号 file_descriptor 已打开并与终端相关联 FILTT UNOP
-h 路径名解析为符号链接的现有目录条目 FILSYM UNOP
-O UID与当前用户相同 FILUID UNOP
-G GID与当前用户相同 FILGID UNOP
-L 是否是符号链接文件 FILSYM UNOP
-S 路径名解析为套接字的现有目录条目 FILSOCK UNOP
-nt mtime大于 FILNT BINOP
-ot mtime小于 FILOT BINOP
-ef mtime等于 FILEQ BINOP
-z 字符串字符串的长度为零 STREZ UNOP 字符串相关
-n 字符串的长度不为零 STRNZ UNOP
= 字符串相等 STREQ BINOP
== 字符串相等 STREQ BINOP
!= 字符串不相等 STRNE BINOP
< 字符串小于 STRLT BINOP
> 字符串大于 STRGT BINOP
=~ 正则表达式 REGEX BINOP
-eq 整数相等 INTEQ BINOP 整数操作
-ne 整数不等 INTNE BINOP
-ge 整数大于等于 INTGE BINOP
-gt 整数大于 INTGT BINOP
-le 整数小于等于 INTLE BINOP
-lt 整数小于 INTLT BINOP
! 取反 UNOT BUNOP 组合符号
-a BAND BBINOP
-o BOR BBINOP
&& BAND BBINOP
|| BOR BBINOP
( 左括号 LPAREN PAREN
) 右括号 RPAREN PAREN

使用示例:

if test $# -gt 0 -o ! -d "$srctree"; then
    usage
fi
if ld --version 2>&1 | grep 'gold.* 2\.20' >/dev/null; then
    echo 'ERROR: Your system has gold 2.20 installed.'
    echo 'This version is shipped by Ubuntu even though'
    echo 'it is known not to work on Ubuntu.'
    echo 'Binaries built with this linker are likely to fail in mysterious ways.'
    echo
    echo 'Run sudo apt-get remove binutils-gold.'
    echo
    exit 1
fi
if ! test -t 0 && ! grep -q notrace; then
    echo "_mcount"
fi
if ! openssl version >& /dev/null; then
    echo "Failed to run openssl. Please ensure openssl is installed"
    exit 1
fi
if test -n "$before" && grep -Eq "$before_re" "$FN"; then
        sed -ri "/$before_re/a $new" "$FN"
elif grep -Eq "$name_re" "$FN"; then
        sed -ri "s:$name_re.*:$new:" "$FN"
else
        echo "$new" >>"$FN"
fi

参考文献

本文链接:https://www.cnblogs.com/zhaojiangkun/p/17437586.html