Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/csharp-4.0/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Shell 在破折号中验证ip(不是bash)_Shell_Sh_Dash Shell - Fatal编程技术网

Shell 在破折号中验证ip(不是bash)

Shell 在破折号中验证ip(不是bash),shell,sh,dash-shell,Shell,Sh,Dash Shell,我正在尝试验证dash脚本中的ip地址。我已经找到了许多方法来实现与bash相同的功能,例如 基本上,is使用以下方法进行比较: if [[ $ip =~ '^[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}$' ]]; then do something fi dash有没有办法做到这一点 更新:这是完成我需要的最后一个脚本: #In case RANGE is a network range (cidr notation) it's spli

我正在尝试验证dash脚本中的ip地址。我已经找到了许多方法来实现与bash相同的功能,例如

基本上,is使用以下方法进行比较:

if [[ $ip =~ '^[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}$' ]]; then
  do something
fi
dash有没有办法做到这一点

更新:这是完成我需要的最后一个脚本:

#In case RANGE is a network range (cidr notation) it's splitted to every ip from 
# that range, otherwise we just keep the ip
if echo $RANGE | grep -E -q '^[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\/[0-9]{1,2}$'; then
    IPS=`prips $RANGE -e ...0,255`
    if [ "$?" != "0" ] ; then
        echo "ERROR: Not a valid network range!"
        exit 1
    fi
elif echo $RANGE | grep -E -q '^[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}$'; then
    IPS="$RANGE"
else
    echo "$RANGE no is not a valid IP address or network range"
    exit 1
fi

假设您对验证字符串满意:

$ s='[0-9]\{1,3\}' $ echo $ip | grep > /dev/null "^$s\.$s\.$s\.$s$" && echo $ip is valid 注意,它接受无效的ip地址,如876.3.4.5

要验证ip,使用正则表达式确实不方便。一件相对容易的事情是:

IFS=. read a b c d << EOF $ip EOF if ( for i in a b c d; do eval test \$$i -gt 0 && eval test \$$i -le 255 || exit 1 done 2> /dev/null ) then echo $ip is valid fi 您可以构建case语句,尽管它比正则表达式更详细。另一方面,您可以避免产生任何外部进程,并且它可能更易于读取和维护以引导

if case $ip in
    # Invalid if it contains any character other than number or dot
    # Invalid if it contains more than three dots
    # Invalid if it contains two adjacent dots
    # Invalid if it begins with a non-number
    # Invalid if it ends with a non-number
    *[!.0-9]* | *.*.*.*.* | *..* | [!0-9]* | *[!0-9] ) false ;;
    # Invalid if it contains a number bigger than 255:
    #  256-259 or 260-299 or 300-999 or four adjacent digits
    *25[6-9]* | *2[6-9][0-9]* | *[3-9][0-9][0-9]* | *[0-9][0-9][0-9][0-9]* ) false;;
    # Verify that it contains three dots
    *.*.*.* ) true ;;
    # Failing that, invalid after all (too few dots)
    *) false ;;
esac; then
    echo "$ip" is valid
fi
请注意,在if语句中,case语句作为条件返回true或false,这种用法很奇怪

这比正则表达式稍微严格一些,因为它要求每个八位字节小于256。

这里有一个小的破折号shell函数,它不使用任何外部命令,并检查IPv4地址是否有效。如果地址格式正确,则返回true,否则返回false

我试着在我的评论中解释这一魔力

valid_ip() {
    local IP="$1" IFS="." PART           # make vars local, get arg, set $IFS
    set -- $IP                           # split on $IFS, set $1, $2 etc.
    [ "$#" != 4 ] && return 1            # BAD: if not 4 parts
    for PART; do                         # loop over $1, $2 etc.
        case "$PART" in
            *[!0-9]*) return 1           #   BAD: if $PART contains non-digit
        esac
        [ "$PART" -gt 255 ] && return 1  #   BAD: if $PART > 255
    done
    return 0                             # GOOD: nothing bad found
}
使用此功能,您可以测试您的IP地址,例如,如果IP地址无效,则中止脚本:

if valid_ip "$IP"; then
    echo "ERROR: IP address '$IP' is invalid" >&2
    exit 4
fi

很好,唯一的问题是我需要-E标志来计算正则表达式或使用egrep,所以只有在使用s='[0-9]{1,3}'时才需要使用多个正则表达式。如果不使用括号,基本正则表达式应该可以工作。啊,你在我编辑之前发表了评论……而且,重定向的事情有点奇怪。只需使用egrep-q regex即可。@ghoti出于可移植性的原因,我一直避免使用-q,但我刚刚发现它是在开放组规范中指定的,这可能已经足够可移植了@ghoti在另一方面,grep-q可以被认为是膨胀的:IP地址只是一个32位的数字。您要求的是虚线四元表示法,但请记住,十进制和十六进制表示法同样有效。0x1020304和16909060与1.2.3.4相同。我只需要验证人为错误,除了我和我的同事之外,没有人会使用此脚本,因此我可以选择一个符号并坚持使用它。关于您的最终regexp,您也可以将其表示为略短一点的内容:^[0-9]{1,3}.{3}[0-9]{1,3}\/[0-9]{1,2}$您正在使用一系列不同的外部命令,而仅使用dash内置命令就可以很好、干净地完成这项工作。如果您对如何调试感到好奇,请参阅下面我的回答。我不想调试这样的函数…:/