R - 将IPv6转换为IPv4(十进制)

时间:2018-04-20 20:03:15

标签: r ip

我搜索谷歌和这个网站,并找到了几个非R替代方案来做到这一点..不幸的是,iptools软件包也无法做到这一点。我需要这样做才能将两个数据集合并在一起。有什么想法吗?

有些想法,但对于批量IP:https://isc.sans.edu/tools/ipv6.html#form

没有可重现的示例,因为您可以使用任何IP地址来演示此内容。

1 个答案:

答案 0 :(得分:0)

You haven't provided sample data.

You haven't told us whether you really know you have the "right kind" of IPv6 addresses to translate to IPv4.

But, we can use base R to implement the basic algorithms:

ipv4_to_ipv6 <- function(x) {
  sapply(x, function(res) {
    res <- strsplit(res, ".", fixed=TRUE)[[1]]
    res <- as.numeric(res)
    res <- sprintf("%02x", res)
    res <- toupper(sprintf("%s%s:%s%s", res[1], res[2], res[3], res[4]))
    sprintf("2002:%s::%s", res, res)
  }, USE.NAMES = FALSE)
}

ipv6_to_ipv4 <- function(x) {
  sapply(x, function(res) {
    res <- iptools::expand_ipv6(res) # NOTE: github version
    res <- strsplit(res, ":", fixed=TRUE)[[1]]
    res <- tail(res, 2)
    res <- c( substr(res[1], 1, 2), substr(res[1], 3, 4), substr(res[2], 1, 2), substr(res[2], 3, 4))
    res <- as.integer(as.raw(sprintf("0x%s", res)))
    res <- paste0(res, collapse=".")
  }, USE.NAMES = FALSE)
}

Now I'll cheat and use a method from dplyr to make the example/test code a bit less cumbersome:

set.seed(0)

dplyr::data_frame(
  rip4_in = iptools::ip_random(10),
  rip6 = ipv4_to_ipv6(rip4_in),
  rip4_out = ipv6_to_ipv4(rip6)
)
## # A tibble: 10 x 3
##    rip4_in         rip6                      rip4_out       
##    <chr>           <chr>                     <chr>          
##  1 113.251.221.104 2002:71FB:DD68::71FB:DD68 113.251.221.104
##  2 34.116.63.87    2002:2274:3F57::2274:3F57 34.116.63.87   
##  3 47.227.58.127   2002:2FE3:3A7F::2FE3:3A7F 47.227.58.127  
##  4 73.45.245.68    2002:492D:F544::492D:F544 73.45.245.68   
##  5 115.111.38.132  2002:736F:2684::736F:2684 115.111.38.132 
##  6 26.105.115.206  2002:1A69:73CE::1A69:73CE 26.105.115.206 
##  7 114.50.117.41   2002:7232:7529::7232:7529 114.50.117.41  
##  8 120.7.114.8     2002:7807:7208::7807:7208 120.7.114.8    
##  9 84.66.177.142   2002:5442:B18E::5442:B18E 84.66.177.142  
## 10 80.68.179.220   2002:5044:B3DC::5044:B3DC 80.68.179.220

NOTE: The above is missing tons of validation checks for proper input.

ALSO: They've been added to the inet package.

Read — https://tools.ietf.org/html/rfc3056#section-2 — to brush up on some of this.

If you have real, "internet" IPv4 and IPv6 addresses and are trying to match up hosts that host the same service on the same system to both IPv4 and IPv6 clients the above will not work. The only way to accomplish that is to try to get to the FQDN in front of the A or AAAA you have and then lookup either the A or AAAA you don't have.

That operation is going to take alot of time for a large list of addresses so I highly suggest you make a local cache (SQLite is likely fine depending on the volume) so you can then wrap that lookup dance with a cache check.

相关问题