Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Browse files

Merge pull request #28 from darrenw/initial

Tweak to the IPv6 address zero-compression function
  • Loading branch information...
commit f0c04a59ea4e5e2d34fe2b70df065014f033e845 2 parents 8221090 + 62eb9cd
@mranney authored
Showing with 67 additions and 33 deletions.
  1. +29 −8 pcap.js
  2. +38 −25 pcap_binding.cc
View
37 pcap.js
@@ -171,16 +171,37 @@ var unpack = {
].join('.');
},
ipv6_addr: function (raw_packet, offset) {
- var ret = '';
- for (var i=offset; i<offset+16; i+=2) {
- if (i > offset) {
- ret += ':';
+ var ret = '';
+ var octets = [];
+ for (var i=offset; i<offset+16; i+=2) {
+ octets.push(unpack.uint16(raw_packet,i).toString(16));
+ }
+ var curr_start, curr_len = undefined;
+ var max_start, max_len = undefined;
+ for(var i = 0; i < 8; i++){
+ if(octets[i] == "0"){
+ if(curr_start === undefined){
+ curr_len = 1;
+ curr_start = i;
+ }else{
+ curr_len++;
+ if(!max_start || curr_len > max_len){
+ max_start = curr_start;
+ max_len = curr_len;
}
- ret += unpack.uint16(raw_packet, i).toString(16);
+ }
+ }else{
+ curr_start = undefined;
}
- // TODO: do a better job to compress out largest run of zeros.
- return ret.replace(/(0:)+/, ':');
- return ret;
+ }
+
+ if(max_start !== undefined){
+ var tosplice = max_start == 0 || (max_start + max_len > 7) ? ":" : "";
+ octets.splice(max_start, max_len,tosplice);
+ if(max_len == 8){octets.push("");}
+ }
+ ret = octets.join(":");
+ return ret;
}
};
exports.unpack = unpack;
View
63 pcap_binding.cc
@@ -200,13 +200,15 @@ Open(bool live, const Arguments& args)
return ThrowException(Exception::Error(String::New(errbuf)));
}
- // TODO - if filter is empty, don't bother with compile or set
- if (pcap_compile(pcap_handle, &fp, (char *) *filter, 1, net) == -1) {
+ if(filter.length() != 0){
+ if (pcap_compile(pcap_handle, &fp, (char *) *filter, 1, net) == -1) {
return ThrowException(Exception::Error(String::New(pcap_geterr(pcap_handle))));
- }
-
- if (pcap_setfilter(pcap_handle, &fp) == -1) {
+ }
+
+ if (pcap_setfilter(pcap_handle, &fp) == -1) {
return ThrowException(Exception::Error(String::New(pcap_geterr(pcap_handle))));
+ }
+ pcap_freecode(&fp);
}
// Work around buffering bug in BPF on OSX 10.6 as of May 19, 2010
@@ -256,6 +258,27 @@ OpenOffline(const Arguments& args)
return Open(false, args);
}
+// Helper method, convert a sockaddr* (AF_INET or AF_INET6) to a string, and set it as the property
+// named 'key' in the Address object you pass in.
+void SetAddrStringHelper(const char* key, sockaddr *addr, Local<Object> Address){
+ if(key && addr){
+ char dst_addr[INET6_ADDRSTRLEN + 1] = {0};
+ char* src = 0;
+ socklen_t size = 0;
+ if(addr->sa_family == AF_INET){
+ struct sockaddr_in* saddr = (struct sockaddr_in*) addr;
+ src = (char*) &(saddr->sin_addr);
+ size = INET_ADDRSTRLEN;
+ }else{
+ struct sockaddr_in6* saddr6 = (struct sockaddr_in6*) addr;
+ src = (char*) &(saddr6->sin6_addr);
+ size = INET6_ADDRSTRLEN;
+ }
+ const char* address = inet_ntop(addr->sa_family, src, dst_addr, size);
+ Address->Set(String::New(key), String::New(address));
+ }
+}
+
Handle<Value>
FindAllDevs(const Arguments& args)
{
@@ -280,27 +303,17 @@ FindAllDevs(const Arguments& args)
Local<Array> AddrArray = Array::New();
int j = 0;
for (pcap_addr_t *cur_addr = cur_dev->addresses ; cur_addr != NULL ; cur_addr = cur_addr->next, j++) {
- if (cur_addr->addr && cur_addr->addr->sa_family == AF_INET) {
- Local<Object> Address = Object::New();
-
- struct sockaddr_in *sin = (struct sockaddr_in *) cur_addr->addr;
- Address->Set(String::New("addr"), String::New(inet_ntoa(sin->sin_addr)));
-
- if (cur_addr->netmask != NULL) {
- sin = (struct sockaddr_in *) cur_addr->netmask;
- Address->Set(String::New("netmask"), String::New(inet_ntoa(sin->sin_addr)));
- }
- if (cur_addr->broadaddr != NULL) {
- sin = (struct sockaddr_in *) cur_addr->broadaddr;
- Address->Set(String::New("broadaddr"), String::New(inet_ntoa(sin->sin_addr)));
- }
- if (cur_addr->dstaddr != NULL) {
- sin = (struct sockaddr_in *) cur_addr->dstaddr;
- Address->Set(String::New("dstaddr"), String::New(inet_ntoa(sin->sin_addr)));
- }
- AddrArray->Set(Integer::New(j), Address);
+ if (cur_addr->addr){
+ int af = cur_addr->addr->sa_family;
+ if(af == AF_INET || af == AF_INET6){
+ Local<Object> Address = Object::New();
+ SetAddrStringHelper("addr", cur_addr->addr, Address);
+ SetAddrStringHelper("netmask", cur_addr->netmask, Address);
+ SetAddrStringHelper("broadaddr", cur_addr->broadaddr, Address);
+ SetAddrStringHelper("dstaddr", cur_addr->dstaddr, Address);
+ AddrArray->Set(Integer::New(j), Address);
+ }
}
- // TODO - support AF_INET6
}
Dev->Set(String::New("addresses"), AddrArray);
Please sign in to comment.
Something went wrong with that request. Please try again.