mirror of
https://github.com/Rucknium/xmrpeers.git
synced 2024-11-16 18:37:36 +00:00
ping.peers() enable ipv6 and better error handling
This commit is contained in:
parent
a8c712d8f6
commit
b4bd6089e7
3 changed files with 56 additions and 11 deletions
|
@ -2,7 +2,7 @@ Package: xmrpeers
|
||||||
Type: Package
|
Type: Package
|
||||||
Title: Analysis of the Monero Cryptocurrency Peer-to-Peer Node Network
|
Title: Analysis of the Monero Cryptocurrency Peer-to-Peer Node Network
|
||||||
Version: 0.0.3
|
Version: 0.0.3
|
||||||
Date: 2024-04-14
|
Date: 2024-04-16
|
||||||
Authors@R:
|
Authors@R:
|
||||||
c(person(given = "Rucknium",
|
c(person(given = "Rucknium",
|
||||||
role = c("cre", "aut", "cph"),
|
role = c("cre", "aut", "cph"),
|
||||||
|
@ -18,6 +18,8 @@ Imports:
|
||||||
readr,
|
readr,
|
||||||
stringr,
|
stringr,
|
||||||
pingr,
|
pingr,
|
||||||
|
pingers,
|
||||||
|
IP,
|
||||||
parallelly,
|
parallelly,
|
||||||
future,
|
future,
|
||||||
future.apply
|
future.apply
|
||||||
|
|
|
@ -1,2 +1,3 @@
|
||||||
exportPattern("^[[:alpha:]]+")
|
exportPattern("^[[:alpha:]]+")
|
||||||
importFrom("utils", "read.csv")
|
importFrom("utils", "read.csv")
|
||||||
|
importFrom("stats", "complete.cases")
|
||||||
|
|
54
R/ping.R
54
R/ping.R
|
@ -89,16 +89,26 @@ ping.peers <- function(bitmonero.dir = "~/.bitmonero", output.file = "monero_pee
|
||||||
}
|
}
|
||||||
|
|
||||||
get.peer.ip.port.direction <- function(x) {
|
get.peer.ip.port.direction <- function(x) {
|
||||||
x <- stringr::str_extract(x, "\\[[0-9]{1,3}[.][0-9]{1,3}[.][0-9]{1,3}[.][0-9]{1,3}:[0-9]+\\s[INCOUT]{3}\\]")
|
x <- stringr::str_extract(x,
|
||||||
x <- stringr::str_extract(x, "[0-9]{1,3}[.][0-9]{1,3}[.][0-9]{1,3}[.][0-9]{1,3}:[0-9]+\\s[INCOUT]{3}")
|
"\t\\[+([^\\[\\]]+)\\]*:([0-9]+) ([INCOUT]{3})\\] Received NOTIFY_NEW_TRANSACTIONS",
|
||||||
x <- strsplit(x, "(:)|(\\s)")
|
group = c(1, 2, 3))
|
||||||
x <- as.data.frame(matrix(unlist(x), ncol = 3, byrow = TRUE), stringsAsFactors = FALSE)
|
if (!is.matrix(x)) {
|
||||||
|
x <- matrix(x, ncol = 3, byrow = TRUE)
|
||||||
|
# stringr::str_extract() creates an atomic vector instaed of a matrix
|
||||||
|
# if the x has only one element
|
||||||
|
}
|
||||||
|
x <- as.data.frame(x)
|
||||||
colnames(x) <- c("ip", "port", "direction")
|
colnames(x) <- c("ip", "port", "direction")
|
||||||
x
|
x
|
||||||
}
|
}
|
||||||
|
|
||||||
peers <- get.peer.ip.port.direction(tail.file[ip.lines])
|
peers <- get.peer.ip.port.direction(tail.file[ip.lines])
|
||||||
peers <- unique(peers)
|
peers <- unique(peers)
|
||||||
|
missed.parsing <- (! complete.cases(peers))
|
||||||
|
if (any(missed.parsing)) {
|
||||||
|
cat("Unable to parse ", sum(missed.parsing), " IPs of peers\n", sep = "")
|
||||||
|
}
|
||||||
|
peers <- peers[! missed.parsing, , drop = FALSE] # Drops any NAs in case the parsing doesn't work
|
||||||
peers <- peers[! paste0(peers$ip, ":", peers$port) %in% old.ip.ports, , drop = FALSE]
|
peers <- peers[! paste0(peers$ip, ":", peers$port) %in% old.ip.ports, , drop = FALSE]
|
||||||
|
|
||||||
if (nrow(peers) == 0) {
|
if (nrow(peers) == 0) {
|
||||||
|
@ -109,19 +119,51 @@ ping.peers <- function(bitmonero.dir = "~/.bitmonero", output.file = "monero_pee
|
||||||
|
|
||||||
get.ping.data <- function(x) {
|
get.ping.data <- function(x) {
|
||||||
ip <- x[[1]]
|
ip <- x[[1]]
|
||||||
|
ip.type <- IP::ip(ip)@.Data
|
||||||
|
|
||||||
|
if (is.na(ip.type) || (! ip.type %in% c(4, 6))) {
|
||||||
|
cat("Could not determine ipv4/ipv6 type of peer\n")
|
||||||
|
return(paste("UNPARSEABLE", "UNPARSEABLE", "UNPARSEABLE",
|
||||||
|
paste(rep(NA, ping.count), collapse = ","), sep = ","))
|
||||||
|
}
|
||||||
|
|
||||||
port <- x[[2]]
|
port <- x[[2]]
|
||||||
direction <- x[[3]]
|
direction <- x[[3]]
|
||||||
if (paste0(ip, ":", port) %in% old.ip.ports) {
|
if (paste0(ip, ":", port) %in% old.ip.ports) {
|
||||||
return("")
|
return("")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (ip.type == 4) {
|
||||||
pings <- pingr::ping_port(ip, port = port, count = ping.count)
|
pings <- pingr::ping_port(ip, port = port, count = ping.count)
|
||||||
if (all(is.na(pings))) {
|
if (all(is.na(pings))) {
|
||||||
# This may happen if it is an incoming connection and the peer's port is closed
|
# This may happen if it is an incoming connection and the peer's port is closed
|
||||||
pings <- pingr::ping(ip, count = ping.count)
|
pings <- pingr::ping(ip, count = ping.count)
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ip.type == 6) {
|
||||||
|
# pingr::ping() doesn't seem to work with ipv6, so switch to
|
||||||
|
# the pingers package
|
||||||
|
# pingers::ping_capture() output format makes it difficult to get the
|
||||||
|
# ping latency for each ping, so we will just loop ping.count times
|
||||||
|
ping.ipv6 <- function() {
|
||||||
|
y <- pingers::ping_capture(paste0(ip, ":", port), count = 1)$ping_min
|
||||||
|
if (is.na(y)) {
|
||||||
|
# This may happen if it is an incoming connection and the peer's port is closed
|
||||||
|
y <- pingers::ping_capture(ip, count = 1)$ping_min
|
||||||
|
}
|
||||||
|
y
|
||||||
|
}
|
||||||
|
pings <- replicate(ping.count, ping.ipv6())
|
||||||
|
}
|
||||||
|
|
||||||
paste(ip, port, direction, paste(pings, collapse = ","), sep = ",")
|
paste(ip, port, direction, paste(pings, collapse = ","), sep = ",")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
get.ping.data.errors.handled <- function(x) {
|
||||||
|
tryCatch(get.ping.data(x), error = function(e) {""})
|
||||||
|
}
|
||||||
|
|
||||||
if (nrow(peers) * ping.count > 5) {
|
if (nrow(peers) * ping.count > 5) {
|
||||||
|
|
||||||
if (is.null(threads)) {
|
if (is.null(threads)) {
|
||||||
|
@ -139,13 +181,13 @@ ping.peers <- function(bitmonero.dir = "~/.bitmonero", output.file = "monero_pee
|
||||||
# since the latter fails with" object 'n.workers' not found"
|
# since the latter fails with" object 'n.workers' not found"
|
||||||
# because of a strange scoping reason.
|
# because of a strange scoping reason.
|
||||||
|
|
||||||
ping.data <- future.apply::future_apply(peers, MARGIN = 1, get.ping.data, future.seed = TRUE)
|
ping.data <- future.apply::future_apply(peers, MARGIN = 1, get.ping.data.errors.handled, future.seed = TRUE)
|
||||||
|
|
||||||
future::plan(future::sequential)
|
future::plan(future::sequential)
|
||||||
# Shut down workers
|
# Shut down workers
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
ping.data <- apply(peers, MARGIN = 1, get.ping.data)
|
ping.data <- apply(peers, MARGIN = 1, get.ping.data.errors.handled)
|
||||||
}
|
}
|
||||||
|
|
||||||
ping.data <- unname(ping.data)
|
ping.data <- unname(ping.data)
|
||||||
|
|
Loading…
Reference in a new issue