Search in sources :

Example 6 with RouterInfo

use of net.i2p.data.router.RouterInfo in project i2p.i2p by i2p.

the class SybilRenderer method renderIPGroups16.

private void renderIPGroups16(Writer out, StringBuilder buf, List<RouterInfo> ris, Map<Hash, Points> points) throws IOException {
    buf.append("<h3 id=\"same16\" class=\"sybils\">Floodfills in the Same /16 (4 minimum)</h3>");
    ObjectCounter<Integer> oc = new ObjectCounter<Integer>();
    for (RouterInfo info : ris) {
        byte[] ip = getIP(info);
        if (ip == null)
            continue;
        Integer x = Integer.valueOf((int) DataHelper.fromLong(ip, 0, 2));
        oc.increment(x);
    }
    List<Integer> foo = new ArrayList<Integer>();
    for (Integer ii : oc.objects()) {
        int count = oc.count(ii);
        if (count >= 4)
            foo.add(ii);
    }
    Collections.sort(foo, new FooComparator(oc));
    boolean found = false;
    for (Integer ii : foo) {
        int count = oc.count(ii);
        int i = ii.intValue();
        int i0 = i >> 8;
        int i1 = i & 0xff;
        String sip = i0 + "." + i1 + ".0/16";
        buf.append("<p class=\"sybil_info\"><b>").append(count).append(" floodfills with IP <a href=\"/netdb?ip=").append(sip).append("&amp;sybil\">").append(sip).append("</a></b></p>");
        for (RouterInfo info : ris) {
            byte[] ip = getIP(info);
            if (ip == null)
                continue;
            if ((ip[0] & 0xff) != i0)
                continue;
            if ((ip[1] & 0xff) != i1)
                continue;
            found = true;
            // limit display
            // renderRouterInfo(buf, info, null, false, false);
            double point = POINTS16 * (count - 1);
            addPoints(points, info.getHash(), point, "Same /16 IP with " + (count - 1) + " other" + ((count > 2) ? "s" : ""));
        }
    }
    if (!found)
        buf.append("<p class=\"notfound\">None</p>");
    out.write(buf.toString());
    out.flush();
    buf.setLength(0);
}
Also used : BigInteger(java.math.BigInteger) ObjectCounter(net.i2p.util.ObjectCounter) RouterInfo(net.i2p.data.router.RouterInfo) ArrayList(java.util.ArrayList)

Example 7 with RouterInfo

use of net.i2p.data.router.RouterInfo in project i2p.i2p by i2p.

the class SybilRenderer method renderPairDistance.

private void renderPairDistance(Writer out, StringBuilder buf, List<RouterInfo> ris, Map<Hash, Points> points) throws IOException {
    int sz = ris.size();
    List<Pair> pairs = new ArrayList<Pair>(PAIRMAX);
    double total = 0;
    for (int i = 0; i < sz; i++) {
        RouterInfo info1 = ris.get(i);
        for (int j = i + 1; j < sz; j++) {
            RouterInfo info2 = ris.get(j);
            BigInteger dist = HashDistance.getDistance(info1.getHash(), info2.getHash());
            if (pairs.isEmpty()) {
                pairs.add(new Pair(info1, info2, dist));
            } else if (pairs.size() < PAIRMAX) {
                pairs.add(new Pair(info1, info2, dist));
                Collections.sort(pairs);
            } else if (dist.compareTo(pairs.get(PAIRMAX - 1).dist) < 0) {
                pairs.set(PAIRMAX - 1, new Pair(info1, info2, dist));
                Collections.sort(pairs);
            }
            total += biLog2(dist);
        }
    }
    double avg = total / (sz * sz / 2d);
    buf.append("<h3 class=\"sybils\">Average Floodfill Distance is ").append(fmt.format(avg)).append("</h3>");
    buf.append("<h3 id=\"pairs\" class=\"sybils\">Closest Floodfill Pairs by Hash</h3>");
    for (Pair p : pairs) {
        double distance = biLog2(p.dist);
        double point = MIN_CLOSE - distance;
        if (point < 0)
            // sorted;
            break;
        if (point >= 2) {
            // limit display
            buf.append("<p class=\"hashdist\"><b>Hash Distance: ").append(fmt.format(distance)).append(": </b>");
            buf.append("</p>");
            renderRouterInfo(buf, p.r1, null, false, false);
            renderRouterInfo(buf, p.r2, null, false, false);
        }
        point *= PAIR_DISTANCE_FACTOR;
        String b2 = p.r2.getHash().toBase64();
        addPoints(points, p.r1.getHash(), point, "Very close (" + fmt.format(distance) + ") to other floodfill <a href=\"netdb?r=" + b2 + "\">" + b2 + "</a>");
        String b1 = p.r1.getHash().toBase64();
        addPoints(points, p.r2.getHash(), point, "Very close (" + fmt.format(distance) + ") to other floodfill <a href=\"netdb?r=" + b1 + "\">" + b1 + "</a>");
    }
    out.write(buf.toString());
    out.flush();
    buf.setLength(0);
}
Also used : RouterInfo(net.i2p.data.router.RouterInfo) ArrayList(java.util.ArrayList) BigInteger(java.math.BigInteger)

Example 8 with RouterInfo

use of net.i2p.data.router.RouterInfo in project i2p.i2p by i2p.

the class SybilRenderer method renderIPGroups32.

private void renderIPGroups32(Writer out, StringBuilder buf, List<RouterInfo> ris, Map<Hash, Points> points) throws IOException {
    buf.append("<h3 id=\"sameIP\" class=\"sybils\">Floodfills with the Same IP</h3>");
    ObjectCounter<Integer> oc = new ObjectCounter<Integer>();
    for (RouterInfo info : ris) {
        byte[] ip = getIP(info);
        if (ip == null)
            continue;
        Integer x = Integer.valueOf((int) DataHelper.fromLong(ip, 0, 4));
        oc.increment(x);
    }
    List<Integer> foo = new ArrayList<Integer>();
    for (Integer ii : oc.objects()) {
        int count = oc.count(ii);
        if (count >= 2)
            foo.add(ii);
    }
    Collections.sort(foo, new FooComparator(oc));
    boolean found = false;
    for (Integer ii : foo) {
        int count = oc.count(ii);
        int i = ii.intValue();
        int i0 = (i >> 24) & 0xff;
        int i1 = (i >> 16) & 0xff;
        int i2 = (i >> 8) & 0xff;
        int i3 = i & 0xff;
        String sip = i0 + "." + i1 + '.' + i2 + '.' + i3;
        buf.append("<p class=\"sybil_info\"><b>").append(count).append(" floodfills with IP <a href=\"/netdb?ip=").append(sip).append("&amp;sybil\">").append(sip).append("</a>:</b></p>");
        for (RouterInfo info : ris) {
            byte[] ip = getIP(info);
            if (ip == null)
                continue;
            if ((ip[0] & 0xff) != i0)
                continue;
            if ((ip[1] & 0xff) != i1)
                continue;
            if ((ip[2] & 0xff) != i2)
                continue;
            if ((ip[3] & 0xff) != i3)
                continue;
            found = true;
            renderRouterInfo(buf, info, null, false, false);
            double point = POINTS32 * (count - 1);
            addPoints(points, info.getHash(), point, "Same IP with " + (count - 1) + " other" + ((count > 2) ? "s" : ""));
        }
    }
    if (!found)
        buf.append("<p class=\"notfound\">None</p>");
    out.write(buf.toString());
    out.flush();
    buf.setLength(0);
}
Also used : BigInteger(java.math.BigInteger) ObjectCounter(net.i2p.util.ObjectCounter) RouterInfo(net.i2p.data.router.RouterInfo) ArrayList(java.util.ArrayList)

Example 9 with RouterInfo

use of net.i2p.data.router.RouterInfo in project i2p.i2p by i2p.

the class SybilRenderer method renderRouterInfoHTML.

/**
 *  The whole thing
 *
 *  @param routerPrefix ignored
 */
private void renderRouterInfoHTML(Writer out, String routerPrefix) throws IOException {
    Set<Hash> ffs = _context.peerManager().getPeersByCapability('f');
    List<RouterInfo> ris = new ArrayList<RouterInfo>(ffs.size());
    Hash us = _context.routerHash();
    Hash ourRKey = _context.router().getRouterInfo().getRoutingKey();
    for (Hash ff : ffs) {
        if (ff.equals(us))
            continue;
        RouterInfo ri = _context.netDb().lookupRouterInfoLocally(ff);
        if (ri != null)
            ris.add(ri);
    }
    if (ris.isEmpty()) {
        out.write("<h3 class=\"sybils\">No known floodfills</h3>");
        return;
    }
    StringBuilder buf = new StringBuilder(4 * 1024);
    buf.append("<p id=\"sybilinfo\"><b>This is an experimental network database tool for debugging and analysis. Do not panic even if you see warnings below. " + "Possible \"threats\" are summarized at the bottom, however these are unlikely to be real threats. " + "If you see anything you would like to discuss with the devs, contact us on IRC #i2p-dev.</b></p>" + "<div id=\"sybilnav\"><ul><li><a href=\"#known\">FF Summary</a>" + "</li><li><a href=\"#family\">Same Family</a>" + "</li><li><a href=\"#ourIP\">IP close to us</a>" + "</li><li><a href=\"#sameIP\">Same IP</a>" + "</li><li><a href=\"#same24\">Same /24</a>" + "</li><li><a href=\"#same16\">Same /16</a>" + "</li><li><a href=\"#pairs\">Pair distance</a>" + "</li><li><a href=\"#ritoday\">Close to us</a>" + "</li><li><a href=\"#ritmrw\">Close to us tomorrow</a>" + "</li><li><a href=\"#dht\">DHT neighbors</a>" + "</li><li><a href=\"#dest\">Close to our destinations</a>" + "</li><li><a href=\"#threats\">Highest threats</a>" + "</li></ul></div>");
    renderRouterInfo(buf, _context.router().getRouterInfo(), null, true, false);
    buf.append("<h3 id=\"known\" class=\"sybils\">Known Floodfills: ").append(ris.size()).append("</h3>");
    double tot = 0;
    int count = 200;
    byte[] b = new byte[32];
    for (int i = 0; i < count; i++) {
        _context.random().nextBytes(b);
        Hash h = new Hash(b);
        double d = closestDistance(h, ris);
        tot += d;
    }
    double avgMinDist = tot / count;
    buf.append("<div id=\"sybils_summary\">\n");
    buf.append("<b>Average closest floodfill distance:</b> ").append(fmt.format(avgMinDist)).append("<br>\n");
    buf.append("<b>Routing Data:</b> \"").append(DataHelper.getUTF8(_context.routerKeyGenerator().getModData())).append("\" <b>Last Changed:</b> ").append(new Date(_context.routerKeyGenerator().getLastChanged())).append("<br>\n");
    buf.append("<b>Next Routing Data:</b> \"").append(DataHelper.getUTF8(_context.routerKeyGenerator().getNextModData())).append("\" <b>Rotates in:</b> ").append(DataHelper.formatDuration(_context.routerKeyGenerator().getTimeTillMidnight())).append("\n");
    buf.append("</div>\n");
    Map<Hash, Points> points = new HashMap<Hash, Points>(64);
    // IP analysis
    renderIPGroupsFamily(out, buf, ris, points);
    renderIPGroupsUs(out, buf, ris, points);
    renderIPGroups32(out, buf, ris, points);
    renderIPGroups24(out, buf, ris, points);
    renderIPGroups16(out, buf, ris, points);
    // Pairwise distance analysis
    renderPairDistance(out, buf, ris, points);
    // Distance to our router analysis
    buf.append("<h3 id=\"ritoday\" class=\"sybils\">Closest Floodfills to Our Routing Key (Where we Store our RI)</h3>");
    buf.append("<p class=\"sybil_info\"><a href=\"/netdb?caps=f&amp;sybil\">See all</a></p>");
    renderRouterInfoHTML(out, buf, ourRKey, avgMinDist, ris, points);
    RouterKeyGenerator rkgen = _context.routerKeyGenerator();
    Hash nkey = rkgen.getNextRoutingKey(us);
    buf.append("<h3 id=\"ritmrw\" class=\"sybils\">Closest Floodfills to Tomorrow's Routing Key (Where we will Store our RI)</h3>");
    buf.append("<p class=\"sybil_info\"><a href=\"/netdb?caps=f&amp;sybil\">See all</a></p>");
    renderRouterInfoHTML(out, buf, nkey, avgMinDist, ris, points);
    buf.append("<h3 id=\"dht\" class=\"sybils\">Closest Floodfills to Our Router Hash (DHT Neighbors if we are Floodfill)</h3>");
    renderRouterInfoHTML(out, buf, us, avgMinDist, ris, points);
    // Distance to our published destinations analysis
    buf.append("<h3 id=\"dest\" class=\"sybils\">Floodfills Close to Our Destinations</h3>");
    Map<Hash, TunnelPool> clientInboundPools = _context.tunnelManager().getInboundClientPools();
    List<Hash> destinations = new ArrayList<Hash>(clientInboundPools.keySet());
    // boolean debug = _context.getBooleanProperty(HelperBase.PROP_ADVANCED);
    for (Hash client : destinations) {
        boolean isLocal = _context.clientManager().isLocal(client);
        if (!isLocal)
            continue;
        if (!_context.clientManager().shouldPublishLeaseSet(client))
            continue;
        LeaseSet ls = _context.netDb().lookupLeaseSetLocally(client);
        if (ls == null)
            continue;
        Hash rkey = ls.getRoutingKey();
        TunnelPool in = clientInboundPools.get(client);
        String name = (in != null) ? in.getSettings().getDestinationNickname() : client.toBase64().substring(0, 4);
        buf.append("<h3 class=\"sybils\">Closest floodfills to the Routing Key for " + DataHelper.escapeHTML(name) + " (where we store our LS)</h3>");
        buf.append("<p class=\"sybil_info\"><a href=\"/netdb?caps=f&amp;sybil=" + ls.getHash().toBase64() + "\">See all</a></p>");
        renderRouterInfoHTML(out, buf, rkey, avgMinDist, ris, points);
        nkey = rkgen.getNextRoutingKey(ls.getHash());
        buf.append("<h3 class=\"sybils\">Closest floodfills to Tomorrow's Routing Key for " + DataHelper.escapeHTML(name) + " (where we will store our LS)</h3>");
        buf.append("<p class=\"sybil_info\"><a href=\"/netdb?caps=f&amp;sybil=" + ls.getHash().toBase64() + "\">See all</a></p>");
        renderRouterInfoHTML(out, buf, nkey, avgMinDist, ris, points);
    }
    // Profile analysis
    addProfilePoints(ris, points);
    addVersionPoints(ris, points);
    if (!points.isEmpty()) {
        List<Hash> warns = new ArrayList<Hash>(points.keySet());
        Collections.sort(warns, new PointsComparator(points));
        buf.append("<h3 id=\"threats\" class=\"sybils\">Routers with Most Threat Points</h3>");
        for (Hash h : warns) {
            RouterInfo ri = _context.netDb().lookupRouterInfoLocally(h);
            if (ri == null)
                continue;
            Points pp = points.get(h);
            double p = pp.points;
            if (p < MIN_DISPLAY_POINTS)
                // sorted
                break;
            buf.append("<p class=\"threatpoints\"><b>Threat Points: " + fmt.format(p) + "</b></p><ul>");
            for (String s : pp.reasons) {
                buf.append("<li>").append(s).append("</li>");
            }
            buf.append("</ul>");
            renderRouterInfo(buf, ri, null, false, false);
        }
    }
    out.write(buf.toString());
    out.flush();
    buf.setLength(0);
}
Also used : TunnelPool(net.i2p.router.tunnel.pool.TunnelPool) HashMap(java.util.HashMap) RouterInfo(net.i2p.data.router.RouterInfo) RouterKeyGenerator(net.i2p.data.router.RouterKeyGenerator) ArrayList(java.util.ArrayList) Hash(net.i2p.data.Hash) ConvertToHash(net.i2p.util.ConvertToHash) Date(java.util.Date) LeaseSet(net.i2p.data.LeaseSet)

Example 10 with RouterInfo

use of net.i2p.data.router.RouterInfo in project i2p.i2p by i2p.

the class DatabaseStoreMessage method readMessage.

public void readMessage(byte[] data, int offset, int dataSize, int type) throws I2NPMessageException {
    if (type != MESSAGE_TYPE)
        throw new I2NPMessageException("Message type is incorrect for this message");
    int curIndex = offset;
    _key = Hash.create(data, curIndex);
    // Fast-fail here to save resources.
    if (_key.equals(Hash.FAKE_HASH)) {
        // createRateStat in KNDF
        _context.statManager().addRateData("netDb.DSMAllZeros", 1);
        throw new I2NPMessageException("DSM all zeros");
    }
    curIndex += Hash.HASH_LENGTH;
    // as of 0.9.18, ignore other 7 bits of the type byte, in preparation for future options
    int dbType = data[curIndex] & 0x01;
    curIndex++;
    _replyToken = DataHelper.fromLong(data, curIndex, 4);
    curIndex += 4;
    if (_replyToken > 0) {
        long tunnel = DataHelper.fromLong(data, curIndex, 4);
        if (tunnel > 0)
            _replyTunnel = new TunnelId(tunnel);
        curIndex += 4;
        _replyGateway = Hash.create(data, curIndex);
        curIndex += Hash.HASH_LENGTH;
    } else {
        _replyTunnel = null;
        _replyGateway = null;
    }
    if (dbType == DatabaseEntry.KEY_TYPE_LEASESET) {
        _dbEntry = new LeaseSet();
        try {
            _dbEntry.readBytes(new ByteArrayInputStream(data, curIndex, data.length - curIndex));
        } catch (DataFormatException dfe) {
            throw new I2NPMessageException("Error reading the leaseSet", dfe);
        } catch (IOException ioe) {
            throw new I2NPMessageException("Error reading the leaseSet", ioe);
        }
    } else {
        // dbType == DatabaseEntry.KEY_TYPE_ROUTERINFO
        _dbEntry = new RouterInfo();
        int compressedSize = (int) DataHelper.fromLong(data, curIndex, 2);
        curIndex += 2;
        if (compressedSize <= 0 || curIndex + compressedSize > data.length || curIndex + compressedSize > dataSize + offset)
            throw new I2NPMessageException("Compressed RI length: " + compressedSize + " but remaining bytes: " + Math.min(data.length - curIndex, dataSize + offset - curIndex));
        try {
            // TODO we could delay decompression, just copy to a new byte array and store in _byteCache
            // May not be necessary since the IBGW now uses UnknownI2NPMessage.
            // DSMs at the OBEP are generally garlic wrapped, so the OBEP won't see it.
            // If we do delay it, getEntry() will have to check if _dbEntry is null and _byteCache
            // is non-null, and then decompress.
            byte[] decompressed = DataHelper.decompress(data, curIndex, compressedSize);
            _dbEntry.readBytes(new ByteArrayInputStream(decompressed));
        } catch (DataFormatException dfe) {
            throw new I2NPMessageException("Error reading the routerInfo", dfe);
        } catch (IOException ioe) {
            throw new I2NPMessageException("Corrupt compressed routerInfo size = " + compressedSize, ioe);
        }
    }
// if (!key.equals(_dbEntry.getHash()))
// throw new I2NPMessageException("Hash mismatch in DSM");
}
Also used : LeaseSet(net.i2p.data.LeaseSet) DataFormatException(net.i2p.data.DataFormatException) ByteArrayInputStream(java.io.ByteArrayInputStream) RouterInfo(net.i2p.data.router.RouterInfo) IOException(java.io.IOException) TunnelId(net.i2p.data.TunnelId)

Aggregations

RouterInfo (net.i2p.data.router.RouterInfo)95 Hash (net.i2p.data.Hash)45 ArrayList (java.util.ArrayList)18 RouterAddress (net.i2p.data.router.RouterAddress)17 DataFormatException (net.i2p.data.DataFormatException)11 IOException (java.io.IOException)10 RouterIdentity (net.i2p.data.router.RouterIdentity)10 DatabaseEntry (net.i2p.data.DatabaseEntry)9 OutNetMessage (net.i2p.router.OutNetMessage)9 File (java.io.File)8 DatabaseStoreMessage (net.i2p.data.i2np.DatabaseStoreMessage)8 Properties (java.util.Properties)7 LeaseSet (net.i2p.data.LeaseSet)6 BigInteger (java.math.BigInteger)5 Date (java.util.Date)5 SigType (net.i2p.crypto.SigType)5 TunnelId (net.i2p.data.TunnelId)5 TunnelInfo (net.i2p.router.TunnelInfo)5 FileOutputStream (java.io.FileOutputStream)4 HashMap (java.util.HashMap)4