简体   繁体   中英

Java. Getting URL from package

I'm making an application that captures the network trafic. I need to get the URL that the browser displays to the users and I thought I could use InetAddress to get the domain from the IP I had captured but It's not the same. For example, the domain I get from facebook.com is xx-fbcdn-shv-01-dft4.fbcdn.net and this is not always the same. Is there any other way to do it? Is it even possible?

I'm using JNetPCap library and the example code of it's page just to learn how to implement it in my proyect.

import java.net.InetAddress;
import java.net.UnknownHostException;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.jnetpcap.*;
import org.jnetpcap.packet.PcapPacket;
import org.jnetpcap.packet.PcapPacketHandler;
import org.jnetpcap.protocol.network.Ip4;

/**
 *
 * @author User
 */
public class Sniffer {

static private String device;

public static void main(String[] args) {

    List<PcapIf> alldevs = new ArrayList<>(); // Will be filled with NICs  
    StringBuilder errbuf = new StringBuilder(); // For any error msgs  

    /**
     * *************************************************************************
     * First get a list of devices on this system 
     *************************************************************************
     */
    int r = Pcap.findAllDevs(alldevs, errbuf);
    if (r == Pcap.NOT_OK || alldevs.isEmpty()) {
        System.err.printf("Can't read list of devices, error is %s", errbuf
                .toString());
        return;
    }

    System.out.println("Network devices found:");

    int i = 0;
    for (PcapIf device : alldevs) {
        String description
                = (device.getDescription() != null) ? device.getDescription()
                        : "No description available";
        System.out.printf("#%d: %s [%s]\n", i++, device.getName(), description);

        System.out.println(device.toString());
    }

    PcapIf device = alldevs.get(2);
    /*************************************************************************** 
     * Second we open up the selected device 
     **************************************************************************/
    int snaplen = 64 * 1024;           // Capture all packets, no trucation  
    int flags = Pcap.MODE_PROMISCUOUS; // capture all packets  
    int timeout = 10 * 1000;           // 10 seconds in millis  
    Pcap pcap
            = Pcap.openLive(device.getName(), snaplen, flags, timeout, errbuf);

    if (pcap == null) {
        System.err.printf("Error while opening device for capture: "
                + errbuf.toString());
        return;
    }
    ///*--------------------------------------------------------------------    ------------------------------
    PcapBpfProgram program = new PcapBpfProgram();
    String expression = "port 80";
    int optimize = 0;         // false
    int netmask = 0xFFFFFF00; // 255.255.255.0  

    if (pcap.compile(program, expression, optimize, netmask) != Pcap.OK) {
        System.err.println(pcap.getErr());
        return;
    }

    if (pcap.setFilter(program) != Pcap.OK) {
        System.err.println(pcap.getErr());
        return;
    }
    ///*

    /**
     * *************************************************************************
     * Third we create a packet handler which will receive packets from the
     * libpcap loop. 
     *************************************************************************
     */
    PcapPacketHandler<String> jpacketHandler = (PcapPacket packet, String user) -> {
        System.out.printf("Received packet at %s caplen=%-4d len=%-4d %s\n",
                new Date(packet.getCaptureHeader().timestampInMillis()),
                packet.getCaptureHeader().caplen(), // Length actually captured
                packet.getCaptureHeader().wirelen(), // Original length
                user // User supplied object

        );
Ip4 ip = new Ip4();
//Tcp tcp= new Tcp();

byte[] sIP;

if (packet.hasHeader(ip)) {

try {
    sIP = packet.getHeader(ip).source();
    String sourceIP = org.jnetpcap.packet.format.FormatUtils.ip(sIP);
    String myIp = InetAddress.getLocalHost().getHostAddress();

    if (!myIp.equals(sourceIP)) {
        System.out.println("source= "+sourceIP);

        String domain;
        domain = InetAddress.getByName(sourceIP).getHostName();

        System.out.println("--------------------------"+domain);

    }
    } catch (UnknownHostException ex) {
    Logger.getLogger(Sniffer.class.getName()).log(Level.SEVERE, null, ex);
    }
}    
    };

    /**
     * *************************************************************************
     * Fourth we enter the loop and tell it to capture 10 packets. The loop
     * method does a mapping of pcap.datalink() DLT value to JProtocol ID,
     * which is needed by JScanner. The scanner scans the packet buffer and
     * decodes the headers. The mapping is done automatically, although a
     * variation on the loop method exists that allows the programmer to
     * sepecify exactly which protocol ID to use as the data link type for
     * this pcap interface. 
     *************************************************************************
     */
    pcap.loop(-1, jpacketHandler, "jNetPcap rocks!");

    /**
     * *************************************************************************
     * Last thing to do is close the pcap handle 
     *************************************************************************
     */
    pcap.close();
    }
}

You can't. Big sites got several addresses, so Facebook.com resolves to many addresses but reverse lookup of those addresses does not resolve to Facebook.com. If you can capture the conversation you can read http headers, there you can find the url you are interested in.

I found a way to do it reading the tcp packets and using it's destination port. Thanks you for your help minus, I wouldn't find the solution without your help. This is the handler method.

static String dominios[] = {"com", "org", "net", "info", "biz", "edu", "gob"};

PcapPacketHandler<String> jpacketHandler = (PcapPacket packet, String user) -> {
    Tcp tcp= new Tcp();
    Http http= new Http();
    if (packet.hasHeader(tcp)) {

            if (tcp.destination() == 443) {
                int payloadstart = tcp.getOffset() + tcp.size();
                JBuffer buffer = new JBuffer(64 * 1024);
                buffer.peer(packet, payloadstart, packet.size() - payloadstart);
                String payload = buffer.toHexdump(packet.size(), false, true, true);

               for (String b : dominios) {
                    if (payload.contains(b)) {
                        procesarTcp(payload, b);
                    }
                }
            }
            else if(packet.hasHeader(http)){    
                System.out.println(http.fieldValue(Http.Request.Host));
            }
        }
    };
    public static void procesarTcp(String payload, String dominio) {

    payload= payload.substring(0,payload.indexOf(dominio)+dominio.length());
    StringTokenizer token= new StringTokenizer(payload,"\n");
    String pagina;
    String aux;
    payload="";
    while(token.hasMoreTokens()){
        aux=token.nextToken();
        payload+=aux.substring(aux.indexOf("    ")+4, aux.length());
    }
    pagina= payload.substring(payload.lastIndexOf("..")+2,payload.length());
System.err.println(pagina);
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM