IPv6地址的正则表达式

我有一个IPv6地址的正则表达式,如下所示

IPV4ADDRESS [ \t]*(([[:digit:]]{1,3}"."){3}([[:digit:]]{1,3}))[ \t]* x4 ([[:xdigit:]]{1,4}) xseq ({x4}(:{x4}){0,7}) xpart ({xseq}|({xseq}::({xseq}?))|::{xseq}) IPV6ADDRESS [ \t]*({xpart}(":"{IPV4ADDRESS})?)[ \t]* 

它是正确的所有格式的IPv6地址,包括

 1) non-compressed IPv6 addresses 2) compressed IPv6 addresses 3) IPv6 addresses in legacy formats.(supporting IPv4) 

传统格式的IPv6地址的理想示例是

 2001:1234::3210:5.6.7.8 OR 2001:1234:1234:5432:4578:5678:5.6.7.8 As you can see above there are 10 groups separated by either `":" or ".".` 

与普通IPv6地址中的8组相反。这是因为最后4组由“”组成。 应该压缩成IPv6地址的最低32位。因此我们需要10组来满足128位。

但是,如果我使用以下地址格式

  2001:1234:4563:3210:5.6.7.8 

这里用“:”分隔的每个组代表16位。最后四个组用“。”分隔。 代表8位。总位数是64 + 32 = 96位。缺少32位

正则表达式接受它作为有效的IPv6地址格式。我无法弄清楚如何修复正则表达式以丢弃这些值。任何帮助都非常感谢。

这是RFC 3986中给出的IPv6地址语法,随后在RFC 5954中得到了肯定:

  IPv6address = 6( h16 ":" ) ls32 / "::" 5( h16 ":" ) ls32 / [ h16 ] "::" 4( h16 ":" ) ls32 / [ *1( h16 ":" ) h16 ] "::" 3( h16 ":" ) ls32 / [ *2( h16 ":" ) h16 ] "::" 2( h16 ":" ) ls32 / [ *3( h16 ":" ) h16 ] "::" h16 ":" ls32 / [ *4( h16 ":" ) h16 ] "::" ls32 / [ *5( h16 ":" ) h16 ] "::" h16 / [ *6( h16 ":" ) h16 ] "::" h16 = 1*4HEXDIG ls32 = ( h16 ":" h16 ) / IPv4address IPv4address = dec-octet "." dec-octet "." dec-octet "." dec-octet dec-octet = DIGIT ; 0-9 / %x31-39 DIGIT ; 10-99 / "1" 2DIGIT ; 100-199 / "2" %x30-34 DIGIT ; 200-249 / "25" %x30-35 ; 250-255 

使用它,我们可以为IPv6地址构建符合标准的正则表达式。

 dec_octet ([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5]) ipv4address ({dec_octet}"."){3}{dec_octet} h16 ([[:xdigit:]]{1,4}) ls32 ({h16}:{h16}|{ipv4address}) ipv6address (({h16}:){6}{ls32}|::({h16}:){5}{ls32}|({h16})?::({h16}:){4}{ls32}|(({h16}:){0,1}{h16})?::({h16}:){3}{ls32}|(({h16}:){0,2}{h16})?::({h16}:){2}{ls32}|(({h16}:){0,3}{h16})?::{h16}:{ls32}|(({h16}:){0,4}{h16})?::{ls32}|(({h16}:){0,5}{h16})?::{h16}|(({h16}:){0,6}{h16})?::) 

免责声明:未经测试。