diff --git a/apps/i2psnark/java/src/org/klomp/snark/Peer.java b/apps/i2psnark/java/src/org/klomp/snark/Peer.java index 3958aed46146f7b09ef6fc1a3e796a2218728290..0dbd23bbb6cf0fb10c0f6c86ef09f8563e5a3108 100644 --- a/apps/i2psnark/java/src/org/klomp/snark/Peer.java +++ b/apps/i2psnark/java/src/org/klomp/snark/Peer.java @@ -104,7 +104,10 @@ public class Peer implements Comparable */ public String toString() { - return peerID.toString() + _id; + if (peerID != null) + return peerID.toString() + _id; + else + return "[unknown id]" + _id; } /** @@ -163,13 +166,16 @@ public class Peer implements Comparable if (din == null) { sock = I2PSnarkUtil.instance().connect(peerID); + _log.debug("Connected to " + peerID + ": " + sock); if ((sock == null) || (sock.isClosed())) { throw new IOException("Unable to reach " + peerID); } - InputStream in = new BufferedInputStream(sock.getInputStream()); + InputStream in = sock.getInputStream(); OutputStream out = sock.getOutputStream(); //new BufferedOutputStream(sock.getOutputStream()); - if (true) + if (true) { out = new BufferedOutputStream(out); + in = new BufferedInputStream(sock.getInputStream()); + } //BufferedInputStream bis // = new BufferedInputStream(sock.getInputStream()); //BufferedOutputStream bos @@ -181,6 +187,9 @@ public class Peer implements Comparable + PeerID.idencode(id) + "' expected '" + PeerID.idencode(expected_id) + "'"); + _log.debug("Handshake got matching IDs with " + toString()); + } else { + _log.debug("Already have din [" + sock + "] with " + toString()); } PeerConnectionIn in = new PeerConnectionIn(this, din); @@ -195,8 +204,10 @@ public class Peer implements Comparable state = s; listener.connected(this); + _log.debug("Start running the reader with " + toString()); // Use this thread for running the incomming connection. - // The outgoing connection has created its own Thread. + // The outgoing connection creates its own Thread. + out.startup(); s.in.run(); } catch(IOException eofe) @@ -241,6 +252,8 @@ public class Peer implements Comparable dout.write(my_id); dout.flush(); + _log.debug("Wrote my shared hash and ID to " + toString()); + // Handshake read - header byte b = din.readByte(); if (b != 19) @@ -266,6 +279,7 @@ public class Peer implements Comparable // Handshake read - peer id din.readFully(bs); + _log.debug("Read the remote side's hash and peerID fully from " + toString()); return bs; } diff --git a/apps/i2psnark/java/src/org/klomp/snark/PeerAcceptor.java b/apps/i2psnark/java/src/org/klomp/snark/PeerAcceptor.java index 9e12db6ce260151895a93b31bce70f0cc3571c9b..e54d91b9ccf334c3f555b7cf7df81fbcf58e2a20 100644 --- a/apps/i2psnark/java/src/org/klomp/snark/PeerAcceptor.java +++ b/apps/i2psnark/java/src/org/klomp/snark/PeerAcceptor.java @@ -63,15 +63,22 @@ public class PeerAcceptor // ahead the first $LOOKAHEAD_SIZE bytes to figure out which infohash they want to // talk about, and we can just look for that in our list of active torrents. byte peerInfoHash[] = null; - try { - peerInfoHash = readHash(in); - _log.info("infohash read from " + socket.getPeerDestination().calculateHash().toBase64() - + ": " + Base64.encode(peerInfoHash)); - } catch (IOException ioe) { - _log.info("Unable to read the infohash from " + socket.getPeerDestination().calculateHash().toBase64()); - throw ioe; + if (in instanceof BufferedInputStream) { + in.mark(LOOKAHEAD_SIZE); + peerInfoHash = readHash(in); + in.reset(); + } else { + // is this working right? + try { + peerInfoHash = readHash(in); + _log.info("infohash read from " + socket.getPeerDestination().calculateHash().toBase64() + + ": " + Base64.encode(peerInfoHash)); + } catch (IOException ioe) { + _log.info("Unable to read the infohash from " + socket.getPeerDestination().calculateHash().toBase64()); + throw ioe; + } + in = new SequenceInputStream(new ByteArrayInputStream(peerInfoHash), in); } - in = new SequenceInputStream(new ByteArrayInputStream(peerInfoHash), in); if (coordinator != null) { // single torrent capability MetaInfo meta = coordinator.getMetaInfo(); diff --git a/apps/i2psnark/java/src/org/klomp/snark/PeerConnectionOut.java b/apps/i2psnark/java/src/org/klomp/snark/PeerConnectionOut.java index 8bbeb71723467bcbebb15441c2231cc73a8fc453..7494daa31f21281dad54e011f78d71d2d170e42b 100644 --- a/apps/i2psnark/java/src/org/klomp/snark/PeerConnectionOut.java +++ b/apps/i2psnark/java/src/org/klomp/snark/PeerConnectionOut.java @@ -53,6 +53,9 @@ class PeerConnectionOut implements Runnable lastSent = System.currentTimeMillis(); quit = false; + } + + public void startup() { thread = new I2PThread(this, "Snark sender " + _id); thread.start(); } @@ -63,6 +66,7 @@ class PeerConnectionOut implements Runnable */ public void run() { + try { Thread.sleep(1000); } catch (InterruptedException ie) {} try { while (!quit && peer.isConnected()) diff --git a/apps/i2psnark/java/src/org/klomp/snark/Storage.java b/apps/i2psnark/java/src/org/klomp/snark/Storage.java index 5a6690574d2d1cebab0fd2a1dbe6d1388d1c498b..b9eb7914b99c0090e89822d2eb5e68b78db06de7 100644 --- a/apps/i2psnark/java/src/org/klomp/snark/Storage.java +++ b/apps/i2psnark/java/src/org/klomp/snark/Storage.java @@ -129,7 +129,7 @@ public class Storage } // Creates piece hases for a new storage. - private void create() throws IOException + public void create() throws IOException { if (true) { fast_digestCreate(); diff --git a/apps/i2psnark/java/src/org/klomp/snark/TrackerClient.java b/apps/i2psnark/java/src/org/klomp/snark/TrackerClient.java index c29d2015e641dcb2e336f6daa3ee907dabb845a8..57b34d04ad69df65d4c9dba38b52bf188d76694e 100644 --- a/apps/i2psnark/java/src/org/klomp/snark/TrackerClient.java +++ b/apps/i2psnark/java/src/org/klomp/snark/TrackerClient.java @@ -209,7 +209,9 @@ public class TrackerClient extends I2PThread if ( (left > 0) && (!completed) ) { // we only want to talk to new people if we need things // from them (duh) - Iterator it = peers.iterator(); + List ordered = new ArrayList(peers); + Collections.shuffle(ordered); + Iterator it = ordered.iterator(); while (it.hasNext()) { Peer cur = (Peer)it.next(); coordinator.addPeer(cur); diff --git a/apps/i2psnark/java/src/org/klomp/snark/web/I2PSnarkServlet.java b/apps/i2psnark/java/src/org/klomp/snark/web/I2PSnarkServlet.java index 4df41ff30fa80a426e0e64032efb8f2bb33fc768..a9a685296596ffb21f906ab450cab454322cb388 100644 --- a/apps/i2psnark/java/src/org/klomp/snark/web/I2PSnarkServlet.java +++ b/apps/i2psnark/java/src/org/klomp/snark/web/I2PSnarkServlet.java @@ -80,6 +80,8 @@ public class I2PSnarkServlet extends HttpServlet { out.write(TABLE_FOOTER); writeAddForm(out, req); + if (false) // seeding needs to register the torrent first (boo, hiss) + writeSeedForm(out, req); writeConfigForm(out, req); out.write(FOOTER); } @@ -227,6 +229,36 @@ public class I2PSnarkServlet extends HttpServlet { String i2cpPort = req.getParameter("i2cpPort"); String i2cpOpts = req.getParameter("i2cpOpts"); _manager.updateConfig(dataDir, autoStart, seedPct, eepHost, eepPort, i2cpHost, i2cpPort, i2cpOpts); + } else if ("Create torrent".equals(action)) { + String baseData = req.getParameter("baseFile"); + if (baseData != null) { + File baseFile = new File(_manager.getDataDir(), baseData); + String announceURL = req.getParameter("announceURL"); + String announceURLOther = req.getParameter("announceURLOther"); + if ( (announceURLOther != null) && (announceURLOther.trim().length() > "http://.i2p/announce".length()) ) + announceURL = announceURLOther; + + if (baseFile.exists()) { + try { + Storage s = new Storage(baseFile, announceURL, null); + s.create(); + MetaInfo info = s.getMetaInfo(); + File torrentFile = new File(baseFile.getParent(), baseFile.getName() + ".torrent"); + if (torrentFile.exists()) + throw new IOException("Cannot overwrite an existing .torrent file: " + torrentFile.getPath()); + FileOutputStream out = new FileOutputStream(torrentFile); + out.write(info.getTorrentData()); + out.close(); + _manager.addMessage("Torrent created for " + baseFile.getName() + ": " + torrentFile.getAbsolutePath()); + // now fire it up and seed away! + _manager.addTorrent(torrentFile.getCanonicalPath()); + } catch (IOException ioe) { + _manager.addMessage("Error creating a torrent for " + baseFile.getAbsolutePath() + ": " + ioe.getMessage()); + } + } else { + _manager.addMessage("Cannot create a torrent for the nonexistant data: " + baseFile.getAbsolutePath()); + } + } } } @@ -399,7 +431,36 @@ public class I2PSnarkServlet extends HttpServlet { out.write("<input type=\"submit\" value=\"Add torrent\" name=\"action\" /><br />\n"); out.write("<span class=\"snarkAddInfo\">Alternately, you can copy .torrent files to " + _manager.getDataDir().getAbsolutePath() + "<br />\n"); out.write("Removing that .torrent file will cause the torrent to stop.<br /></span>\n"); - out.write("</form>\n</span>\n"); + out.write("</form>\n</span>\n"); + } + + private static final String DEFAULT_TRACKERS[] = { + "Postman's tracker", "http://YRgrgTLGnbTq2aZOZDJQ~o6Uk5k6TK-OZtx0St9pb0G-5EGYURZioxqYG8AQt~LgyyI~NCj6aYWpPO-150RcEvsfgXLR~CxkkZcVpgt6pns8SRc3Bi-QSAkXpJtloapRGcQfzTtwllokbdC-aMGpeDOjYLd8b5V9Im8wdCHYy7LRFxhEtGb~RL55DA8aYOgEXcTpr6RPPywbV~Qf3q5UK55el6Kex-6VCxreUnPEe4hmTAbqZNR7Fm0hpCiHKGoToRcygafpFqDw5frLXToYiqs9d4liyVB-BcOb0ihORbo0nS3CLmAwZGvdAP8BZ7cIYE3Z9IU9D1G8JCMxWarfKX1pix~6pIA-sp1gKlL1HhYhPMxwyxvuSqx34o3BqU7vdTYwWiLpGM~zU1~j9rHL7x60pVuYaXcFQDR4-QVy26b6Pt6BlAZoFmHhPcAuWfu-SFhjyZYsqzmEmHeYdAwa~HojSbofg0TMUgESRXMw6YThK1KXWeeJVeztGTz25sL8AAAA.i2p/announce.php", + "Orion's tracker", "http://gKik1lMlRmuroXVGTZ~7v4Vez3L3ZSpddrGZBrxVriosCQf7iHu6CIk8t15BKsj~P0JJpxrofeuxtm7SCUAJEr0AIYSYw8XOmp35UfcRPQWyb1LsxUkMT4WqxAT3s1ClIICWlBu5An~q-Mm0VFlrYLIPBWlUFnfPR7jZ9uP5ZMSzTKSMYUWao3ejiykr~mtEmyls6g-ZbgKZawa9II4zjOy-hdxHgP-eXMDseFsrym4Gpxvy~3Fv9TuiSqhpgm~UeTo5YBfxn6~TahKtE~~sdCiSydqmKBhxAQ7uT9lda7xt96SS09OYMsIWxLeQUWhns-C~FjJPp1D~IuTrUpAFcVEGVL-BRMmdWbfOJEcWPZ~CBCQSO~VkuN1ebvIOr9JBerFMZSxZtFl8JwcrjCIBxeKPBmfh~xYh16BJm1BBBmN1fp2DKmZ2jBNkAmnUbjQOqWvUcehrykWk5lZbE7bjJMDFH48v3SXwRuDBiHZmSbsTY6zhGY~GkMQHNGxPMMSIAAAA.i2p/bt", + "The freak's tracker", "http://mHKva9x24E5Ygfey2llR1KyQHv5f8hhMpDMwJDg1U-hABpJ2NrQJd6azirdfaR0OKt4jDlmP2o4Qx0H598~AteyD~RJU~xcWYdcOE0dmJ2e9Y8-HY51ie0B1yD9FtIV72ZI-V3TzFDcs6nkdX9b81DwrAwwFzx0EfNvK1GLVWl59Ow85muoRTBA1q8SsZImxdyZ-TApTVlMYIQbdI4iQRwU9OmmtefrCe~ZOf4UBS9-KvNIqUL0XeBSqm0OU1jq-D10Ykg6KfqvuPnBYT1BYHFDQJXW5DdPKwcaQE4MtAdSGmj1epDoaEBUa9btQlFsM2l9Cyn1hzxqNWXELmx8dRlomQLlV4b586dRzW~fLlOPIGC13ntPXogvYvHVyEyptXkv890jC7DZNHyxZd5cyrKC36r9huKvhQAmNABT2Y~pOGwVrb~RpPwT0tBuPZ3lHYhBFYmD8y~AOhhNHKMLzea1rfwTvovBMByDdFps54gMN1mX4MbCGT4w70vIopS9yAAAA.i2p/bytemonsoon/announce.php" + }; + private void writeSeedForm(PrintWriter out, HttpServletRequest req) throws IOException { + String uri = req.getRequestURI(); + String baseFile = req.getParameter("baseFile"); + if (baseFile == null) + baseFile = ""; + + out.write("<span class=\"snarkNewTorrent\">\n"); + // *not* enctype="multipart/form-data", so that the input type=file sends the filename, not the file + out.write("<form action=\"" + uri + "\" method=\"POST\">\n"); + out.write("<input type=\"hidden\" name=\"nonce\" value=\"" + _nonce + "\" />\n"); + //out.write("From file: <input type=\"file\" name=\"newFile\" size=\"50\" value=\"" + newFile + "\" /><br />\n"); + out.write("Data to seed: <input type=\"text\" name=\"baseFile\" size=\"50\" value=\"" + baseFile + + "\" title=\"File within " + _manager.getDataDir().getAbsolutePath() + " to seed\" /><br />\n"); + out.write("Tracker: <select name=\"announceURL\"><option value=\"\">Select a tracker</option>\n"); + for (int i = 0; i + 1 < DEFAULT_TRACKERS.length; i += 2) + out.write("\t<option value=\"" + DEFAULT_TRACKERS[i+1] + "\">" + DEFAULT_TRACKERS[i] + "</option>\n"); + out.write("</select><br />\n"); + out.write(" or: "); + out.write("<input type=\"text\" name=\"announceURLOther\" size=\"50\" value=\"http://\" " + + "title=\"Custom tracker URL\" /><br />\n"); + out.write("<input type=\"submit\" value=\"Create torrent\" name=\"action\" />\n"); + out.write("</form>\n</span>\n"); } private void writeConfigForm(PrintWriter out, HttpServletRequest req) throws IOException { diff --git a/apps/syndie/java/src/net/i2p/syndie/User.java b/apps/syndie/java/src/net/i2p/syndie/User.java index 3892cccc043fdc0a0e5efff2c07d8c404b1d044f..5d1f50ead744e28152e4683f7e8da70edfb5def4 100644 --- a/apps/syndie/java/src/net/i2p/syndie/User.java +++ b/apps/syndie/java/src/net/i2p/syndie/User.java @@ -49,7 +49,8 @@ public class User { private static final String DEFAULT_FAVORITE_TAGS[] = { "syndie", "syndie.tech", "syndie.intro", "syndie.bugs", "syndie.featurerequest", "syndie.announce", - "i2p", "i2p.tech", "i2p.bugs", "i2p.i2phex", "i2p.susimail", "i2p.irc", + "i2p", "i2p.tech", "i2p.bugs", "i2p.i2phex", "i2p.susimail", "i2p.irc", + "bt.i2psnark", "bt.i2prufus", "bt.i2p-bt", "bt.azureus", "bt.misc", "security.misc", "chat", "test" diff --git a/apps/syndie/java/src/net/i2p/syndie/web/BaseServlet.java b/apps/syndie/java/src/net/i2p/syndie/web/BaseServlet.java index 0458a6a0adfc35b1fb8446266ef78e1ac3db8423..d74b2a97f96e187b6f12dab1dfc75aeb9fdf996a 100644 --- a/apps/syndie/java/src/net/i2p/syndie/web/BaseServlet.java +++ b/apps/syndie/java/src/net/i2p/syndie/web/BaseServlet.java @@ -330,7 +330,8 @@ public abstract class BaseServlet extends HttpServlet { (AddressesServlet.ACTION_DELETE_OTHER.equals(action)) || (AddressesServlet.ACTION_DELETE_TAG.equals(action)) || (AddressesServlet.ACTION_DELETE_PEER.equals(action)) ) { - PetName pn = user.getPetNameDB().getByName(req.getParameter(AddressesServlet.PARAM_NAME)); + String name = req.getParameter(AddressesServlet.PARAM_NAME); + PetName pn = user.getPetNameDB().getByName(name); if (pn != null) { user.getPetNameDB().remove(pn); BlogManager.instance().saveUser(user); @@ -580,7 +581,7 @@ public abstract class BaseServlet extends HttpServlet { //out.write("<tr class=\"topNav\"><td class=\"topNav_user\" colspan=\"2\" nowrap=\"true\">\n"); out.write("<tr class=\"topNav\"><td colspan=\"3\" nowrap=\"true\"><span class=\"topNav_user\">\n"); out.write("<!-- nav bar begin -->\n"); - out.write("<a href=\"threads.jsp\" title=\"Syndie home\">Home</a> <a href=\"blogs.jsp\" title=\"Blog summary\">Blogs</a> "); + out.write("<a href=\"threads.jsp\" title=\"Syndie home\">Threads</a> <a href=\"blogs.jsp\" title=\"Blog summary\">Blogs</a> "); if (user.getAuthenticated() && (user.getBlog() != null) ) { out.write("Logged in as <a href=\"" + getProfileLink(req, user.getBlog()) + "\" title=\"Edit your profile\">"); out.write(user.getUsername()); diff --git a/apps/syndie/java/src/net/i2p/syndie/web/ViewBlogsServlet.java b/apps/syndie/java/src/net/i2p/syndie/web/ViewBlogsServlet.java index 7b62a1a3f7e06c6e8e3948eb6aca039763393847..6f09e4153dfee523bd243ac2d5fad166ba176a19 100644 --- a/apps/syndie/java/src/net/i2p/syndie/web/ViewBlogsServlet.java +++ b/apps/syndie/java/src/net/i2p/syndie/web/ViewBlogsServlet.java @@ -26,8 +26,8 @@ public class ViewBlogsServlet extends BaseServlet { private String getViewBlogLink(Hash blog, long lastPost) { long dayBegin = BlogManager.instance().getDayBegin(); int daysAgo = 2; - if ( (lastPost > 0) && (dayBegin - 3*24*60*6081000 > lastPost) ) // last post was old 3 days ago - daysAgo = (int)((dayBegin - lastPost + 24*60*60*1000-1)/(24*60*60*1000)); + if ( (lastPost > 0) && (dayBegin - 3*24*60*60*1000l >= lastPost) ) // last post was old 3 days ago + daysAgo = (int)((dayBegin - lastPost + 24*60*60*1000l-1)/(24*60*60*1000l)); daysAgo++; return getControlTarget() + "?" + ThreadedHTMLRenderer.PARAM_AUTHOR + '=' + blog.toBase64() + '&' + ThreadedHTMLRenderer.PARAM_THREAD_AUTHOR + "=true&daysBack=" + daysAgo; @@ -65,7 +65,7 @@ public class ViewBlogsServlet extends BaseServlet { out.write("<tr><td colspan=\"3\" valign=\"top\" align=\"left\"><span class=\"syndieBlogFavorites\">"); if ( (user != null) && (user.getAuthenticated()) ) { - out.write("<b>Favorite blogs:</b><br />\n"); + out.write("<b>Favorite blogs:</b> <a href=\"" + getControlTarget() + "?author=favorites&daysBack=3\" title=\"View all posts by your favorite authors in the last 3 days\">view all</a><br />\n"); out.write("<a href=\"" + getViewBlogLink(user.getBlog(), user.getLastMetaEntry()) + "\" title=\"View your blog\">Your blog</a><br />\n"); diff --git a/core/java/src/net/i2p/client/naming/PetNameDB.java b/core/java/src/net/i2p/client/naming/PetNameDB.java index ee5741e22e2abb92aeea7104f2336a182a77deb8..c335a934194744abbbb49816ab2022bca74e7b5b 100644 --- a/core/java/src/net/i2p/client/naming/PetNameDB.java +++ b/core/java/src/net/i2p/client/naming/PetNameDB.java @@ -33,7 +33,7 @@ public class PetNameDB { public boolean isEmpty() { return _names.isEmpty(); } public Iterator iterator() { return new ArrayList(_names.values()).iterator(); } public void remove(PetName pn) { - if (pn != null) _names.remove(pn.getName()); + if (pn != null) _names.remove(pn.getName().toLowerCase()); } public void removeName(String name) { if (name != null) _names.remove(name.toLowerCase()); diff --git a/history.txt b/history.txt index 340377796bddd9c7fdc9206c16218f48b11672c2..18c268ba0070bd34a02bc3f252d45c8604116df7 100644 --- a/history.txt +++ b/history.txt @@ -1,4 +1,9 @@ -$Id: history.txt,v 1.363 2005/12/18 00:39:54 jrandom Exp $ +$Id: history.txt,v 1.364 2005/12/19 08:34:56 jrandom Exp $ + +2005-12-19 jrandom + * Fix for old Syndie blog bookmarks (thanks Complication!) + * Fix for I2PSnark to accept incoming connections again (oops) + * Randomize the order that peers from the tracker are contacted 2005-12-19 jrandom * I2PSnark logging, disconnect old inactive peers rather than new ones, diff --git a/router/java/src/net/i2p/router/RouterVersion.java b/router/java/src/net/i2p/router/RouterVersion.java index be418c92e92334aec0d9a9b6ca728d825322886c..15e0a044c466784d59a21751379c8a6fa6665c4c 100644 --- a/router/java/src/net/i2p/router/RouterVersion.java +++ b/router/java/src/net/i2p/router/RouterVersion.java @@ -15,9 +15,9 @@ import net.i2p.CoreVersion; * */ public class RouterVersion { - public final static String ID = "$Revision: 1.312 $ $Date: 2005/12/16 22:47:03 $"; + public final static String ID = "$Revision: 1.313 $ $Date: 2005/12/19 08:34:55 $"; public final static String VERSION = "0.6.1.7"; - public final static long BUILD = 6; + public final static long BUILD = 7; public static void main(String args[]) { System.out.println("I2P Router version: " + VERSION + "-" + BUILD); System.out.println("Router ID: " + RouterVersion.ID);