dresende / node-arping Goto Github PK
View Code? Open in Web Editor NEWNodeJS ARP ping using raw sockets
NodeJS ARP ping using raw sockets
@dresende
I have multiple interfaces defined on my server. One of them is used as prod interface and others might be used for internal communication. So how do I specify what device to be used in the library?
For instance, on terminal I use
# arping 192.168.122.3 -I prod
ARPING 192.168.122.3 from 192.168.122.2 prod
Unicast reply from 192.168.122.3 [52:54:00:6C:AE:66] 0.873ms
Unicast reply from 192.168.122.3 [52:54:00:6C:AE:66] 1.807ms
Unicast reply from 192.168.122.3 [52:54:00:6C:AE:66] 1.920ms
Unicast reply from 192.168.122.3 [52:54:00:6C:AE:66] 0.920ms
where in prod
is the name of the interface
let me know if anything needs clarification
edit: After reading the code, I figured out that I need to use library like
arp.ping("192.168.122.3", {spa: "192.168.122.2"}, (err, info) => console.log(err, info))
OR
arp.ping("192.168.122.3", {sha: "52:54:00:93:e4:27"}, (err, info) => console.log(err, info))
but I always get error:
at Timeout.setTimeout [as _onTimeout] (/opt/hive/services/hive-fabric/node_modules/arping/index.js:181:8)
at ontimeout (timers.js:436:11)
at tryOnTimeout (timers.js:300:5)
at listOnTimeout (timers.js:263:5)
at Timer.processTimers (timers.js:223:10) undefined
Occasionally ARP pings result in a Segmentation fault: 11
.
Consider this example script that sends an ARP ping to my router:
const arp = require("arping");
arp.ping("192.168.10.1", (err, info) => {
if (err) throw err;
console.log("%s responded in %s secs", info.tha, info.elapsed);
});
Generally this returns as expected.
totes:arp john$ node app.js
60:73:5c:98:72:f3 responded in 0.002274009 secs
But sometimes a native module appears to crash.
totes:arp john$ node app.js
60:73:5c:98:72:f3 responded in 0.001657804 secs
Segmentation fault: 11
I've used raw-socket
and pcap2
extensively in projects and I've never seen this issue. I suspected the problem is certainly occurring one of these native modules - but I was wondering if there was something we could do in node-arping
to avoid this issue.
I attempted to track this down using the debugger in Visual Studio Code, but try as I might, I cannot get the Segfault to occur under the debugger! So I'm thinking this may be related to a race condition that's not ocuring with the overhead of the debugger in the loop.
To help track this down, I'm used the Node.js segfault-handler
module. Then run this script:
const arp = require("arping");
const SegfaultHandler = require("segfault-handler");
SegfaultHandler.registerHandler("crash.log");
arp.ping("192.168.10.1", (err, info) => {
if (err) throw err;
console.log("%s responded in %s secs", info.tha, info.elapsed);
});
This is the same script as I ran earlier, just with segfault-handler
wired up. Here's the output:
totes:arp john$ node app.js
60:73:5c:98:72:f3 responded in 0.001684102 secs
PID 12154 received SIGSEGV for address: 0x0
0 segfault-handler.node 0x00000001027b2408 _ZL16segfault_handleriP9__siginfoPv + 312
1 libsystem_platform.dylib 0x00007fff65bc9f5a _sigtramp + 26
2 ??? 0x0000000000000002 0x0 + 2
3 pcap_binding.node 0x00000001027a8073 _ZN3Nan3impL23FunctionCallbackWrapperERKN2v820FunctionCallbackInfoINS1_5ValueEEE + 136
4 node 0x000000010018ada2 _ZN2v88internal25FunctionCallbackArguments4CallEPFvRKNS_20FunctionCallbackInfoINS_5ValueEEEE + 466
5 node 0x00000001001eb500 _ZN2v88internal12_GLOBAL__N_119HandleApiCallHelperILb0EEENS0_11MaybeHandleINS0_6ObjectEEEPNS0_7IsolateENS0_6HandleINS0_10HeapObjectEEESA_NS8_INS0_20FunctionTemplateInfoEEENS8_IS4_EENS0_16BuiltinArgumentsE + 816
6 node 0x00000001001eab40 _ZN2v88internalL26Builtin_Impl_HandleApiCallENS0_16BuiltinArgumentsEPNS0_7IsolateE + 288
7 ??? 0x000007f8328042fd 0x0 + 8762580550397
8 ??? 0x000007f8328bd1d6 0x0 + 8762581307862
Segmentation fault: 11
Multiple crashes result in very similar traces. So the best guess from here, is that the issue is occurring in pcap_binding.node
which is part of the pcap2
module.
The mangled name _ZN3Nan3impL23FunctionCallbackWrapperERKN2v820FunctionCallbackInfoINS1_5ValueEEE
corresponds to Nan::imp::FunctionCallbackWrapper
. Checking this out in Binary Ninja shows an issue with a dynamic call call r15
which the r15 register
holds an invalid value -- apparently 0x0
. r15
is set in the Nan::imp::FunctionCallbackWrapper
from the return value of v8::External::Value
-- in the depths of the V8 engine.
I'll add some links to screens shots soon and continue debugging this issue. My hope is that we may be able to avoid a clear problem in pcap2
by making a change in this module.
Nan::imp::FunctionCallbackWrapper
see insn @ 0x2070
https://imgur.com/a/pWLcqki
Hello @dresende, thanks for the very cool module!
I was just checking it out and noticed that the ping method returns packet.payload.payload.target_ha
which is the MAC of the system running the ARP ping, not the MAC of the responding system, which is packet.payload.payload.sender_ha
.
For example, no matter which IP I scan 192.168.10.1
, 192.168.10.20
, etc. this module will always return 8c:85:90:58:97:84 responded in X.XXX secs
. 8c:85:90:58:97:84
is the MAC address for my MacBook's network interface.
If I switch target_ha
to sender_ha
on the following line, everything works as expected.
Line 165 in 1035634
I submitted a PR for this.
This module works as expected when scanning IPs that are known to be listening on the network. When you scan an IP that is not on the network, the module crashes with a TypeError in pcap2 session.js:124 (in pcap2 v3.0.4).
Consider the following script
const arp = require("arping");
function arpPing(ip) {
arp.ping(ip, (err, info) => {
if (err) throw err;
console.log("%s - %s", ip, info.tha);
});
}
We can very quickly scan live hosts on the network in succession.
arpPing("192.168.10.1");
arpPing("192.168.10.20");
arpPing("192.168.10.21");
arpPing("192.168.10.254");
192.168.10.1 - 60:73:5c:98:72:f3
192.168.10.20 - 00:0f:ff:58:1e:39
192.168.10.21 - 00:0f:ff:17:29:7a
192.168.10.254 - 00:0a:dd:03:4f:5a
But if we try to scan just a single host that isn't listening this happens.
arpPing("192.168.10.2");
/Users/john/Desktop/scratch/arp/node_modules/pcap2/lib/session.js:124
return this.session.inject(data);
^
TypeError: First argument must be a buffer
at LiveSession.Session.inject (/Users/john/Desktop/scratch/arp/node_modules/pcap2/lib/session.js:124:25)
at try_ping (/Users/john/Desktop/scratch/arp/node_modules/arping/index.js:172:10)
at done (/Users/john/Desktop/scratch/arp/node_modules/arping/index.js:144:11)
at Timeout.setTimeout [as _onTimeout] (/Users/john/Desktop/scratch/arp/node_modules/arping/index.js:179:3)
at ontimeout (timers.js:466:11)
at tryOnTimeout (timers.js:304:5)
at Timer.listOnTimeout (timers.js:267:5)
I'm looking into this issue. I'll submit a PR for it once I track it down but I probably won't get to it until next week.
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.