From nextgens at freenetproject.org Sat Dec 1 00:02:26 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 00:02:26 +0000 (UTC) Subject: [freenet-cvs] r16171 - trunk/freenet/src/freenet/node/fcp Message-ID: <20071201000226.0A0EA479612@freenetproject.org> Author: nextgens Date: 2007-12-01 00:02:24 +0000 (Sat, 01 Dec 2007) New Revision: 16171 Modified: trunk/freenet/src/freenet/node/fcp/ClientGet.java trunk/freenet/src/freenet/node/fcp/PersistentGet.java Log: Resolve #1889: PersistentGet fields missing Modified: trunk/freenet/src/freenet/node/fcp/ClientGet.java =================================================================== --- trunk/freenet/src/freenet/node/fcp/ClientGet.java 2007-11-30 23:59:55 UTC (rev 16170) +++ trunk/freenet/src/freenet/node/fcp/ClientGet.java 2007-12-01 00:02:24 UTC (rev 16171) @@ -494,7 +494,7 @@ } protected FCPMessage persistentTagMessage() { - return new PersistentGet(identifier, uri, verbosity, priorityClass, returnType, persistenceType, targetFile, tempFile, clientToken, client.isGlobalQueue, started, fctx.maxNonSplitfileRetries); + return new PersistentGet(identifier, uri, verbosity, priorityClass, returnType, persistenceType, targetFile, tempFile, clientToken, client.isGlobalQueue, started, fctx.maxNonSplitfileRetries, binaryBlob, fctx.maxOutputLength); } public void onFailure(FetchException e, ClientGetter state) { Modified: trunk/freenet/src/freenet/node/fcp/PersistentGet.java =================================================================== --- trunk/freenet/src/freenet/node/fcp/PersistentGet.java 2007-11-30 23:59:55 UTC (rev 16170) +++ trunk/freenet/src/freenet/node/fcp/PersistentGet.java 2007-12-01 00:02:24 UTC (rev 16171) @@ -30,10 +30,12 @@ final boolean global; final boolean started; final int maxRetries; + final boolean binaryBlob; + final long maxSize; public PersistentGet(String identifier, FreenetURI uri, int verbosity, short priorityClass, short returnType, short persistenceType, - File targetFile, File tempFile, String clientToken, boolean global, boolean started, int maxRetries) { + File targetFile, File tempFile, String clientToken, boolean global, boolean started, int maxRetries, boolean binaryBlob, long maxSize) { this.identifier = identifier; this.uri = uri; this.verbosity = verbosity; @@ -46,6 +48,8 @@ this.global = global; this.started = started; this.maxRetries = maxRetries; + this.binaryBlob = binaryBlob; + this.maxSize = maxSize; } public SimpleFieldSet getFieldSet() { @@ -65,6 +69,8 @@ fs.put("Global", global); fs.put("Started", started); fs.put("MaxRetries", maxRetries); + fs.put("BinaryBlob", binaryBlob); + fs.put("MaxSize", maxSize); return fs; } From nextgens at freenetproject.org Sat Dec 1 00:15:26 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 00:15:26 +0000 (UTC) Subject: [freenet-cvs] r16172 - trunk/freenet/src/freenet/l10n Message-ID: <20071201001526.A0FE8479EF5@freenetproject.org> Author: nextgens Date: 2007-12-01 00:15:26 +0000 (Sat, 01 Dec 2007) New Revision: 16172 Modified: trunk/freenet/src/freenet/l10n/freenet.l10n.de.properties Log: l10n: more more german strings from Thomas Modified: trunk/freenet/src/freenet/l10n/freenet.l10n.de.properties =================================================================== --- trunk/freenet/src/freenet/l10n/freenet.l10n.de.properties 2007-12-01 00:02:24 UTC (rev 16171) +++ trunk/freenet/src/freenet/l10n/freenet.l10n.de.properties 2007-12-01 00:15:26 UTC (rev 16172) @@ -1,5 +1,6 @@ BookmarkEditorToadlet.addBookmark=Lesezeichen hinzuf?gen BookmarkEditorToadlet.addCategory=Kategorie hinzuf?gen +BookmarkEditorToadlet.addDefaultBookmarks=F?ge die Standard-Lesezeichen erneut hinzu BookmarkEditorToadlet.addNewBookmark=Ein neues Lesezeichen hinzuf?gen BookmarkEditorToadlet.addNewCategory=Eine neue Kategorie hinzuf?gen BookmarkEditorToadlet.addedNewBookmark=Das neue Lesezeichen wurde erfolgreich hinzugef?gt. @@ -22,7 +23,7 @@ BookmarkEditorToadlet.editBookmarkTitle=Lesezeichen bearbeiten BookmarkEditorToadlet.editCategoryTitle=Kategorie bearbeiten BookmarkEditorToadlet.error=Fehler -BookmarkEditorToadlet.hasAnActivelinkLabel=Hat die Freesite einen Aktivlink? +BookmarkEditorToadlet.hasAnActivelinkLabel=Hat die Freesite einen Aktivlink (kleines Bild)? BookmarkEditorToadlet.invalidKey=Der Freenet-Schl?ssel ist ung?ltig. BookmarkEditorToadlet.invalidKeyTitle=Ung?ltiger Schl?ssel BookmarkEditorToadlet.invalidKeyWithReason=Ung?ltiger Freenet-Schl?ssel. @@ -64,7 +65,7 @@ ConfigToadlet.console=Konsole ConfigToadlet.contributeTranslation=Zur ?bersetzung beitragen ConfigToadlet.defaultIs=Der Standard-Wert f?r diese Einstellung ist: "${default}". -ConfigToadlet.false=falsch +ConfigToadlet.false=nein ConfigToadlet.fcp=FCP ConfigToadlet.fproxy=FProxy ConfigToadlet.fullTitle=Freenet-Knoten-Konfiguration von ${name} @@ -78,7 +79,7 @@ ConfigToadlet.shortTitle=Konfiguration ConfigToadlet.title=Freenet-Knoten-Konfiguration ConfigToadlet.toadletsymlinker=ToadletSymlinker -ConfigToadlet.true=wahr +ConfigToadlet.true=ja ConfigToadlet.node.load=Knoten.Last ConfigToadlet.node.opennet=Knoten.Opennet ConfigToadlet.node.scheduler=Knoten.Planer @@ -104,9 +105,16 @@ ConnectivityToadlet.addressTitle=Addresse ConnectivityToadlet.byIPTitle=Pakete f?r ${ip} nach IP-Adresse sortiert - ${status} (Zeit, f?r die der Router/die Firewall einen UDP-Tunnel mindestens offen h?lt: ${tunnelLength}) ConnectivityToadlet.byPortTitle=Pakete f?r ${port} nach Port sortiert - ${status} (Zeit, f?r die der Router/die Firewall einen UDP-Tunnel mindestens offen h?lt:${tunnelLength}) +ConnectivityToadlet.connectivity=Erreichbarkeit aus dem Internet +ConnectivityToadlet.connectivityTitle=Erreichbarkeit +ConnectivityToadlet.firstReceiveLeadTime=Online bis zum ersten empfangenen Paket ConnectivityToadlet.firstSendLeadTime=Vom Start bis zum ersten gesendeten Paket +ConnectivityToadlet.local=LOKAL +ConnectivityToadlet.localRemoteTitle=Lokal/Remote ConnectivityToadlet.noreply=KEINE ANTWORT ConnectivityToadlet.sentReceivedTitle=Gesendete/empfangene Pakete +ConnectivityToadlet.summaryTitle=Erreichbarkeit aus dem Internet (?berpr?fung, ob Dark-/Opennet-Port weitergeleitet werden oder nicht) +ConnectivityToadlet.title=?berpr?fung der Erreichbarkeit aus dem Internet f?r ${nodeName} ContentDataFilter.unknownCharset=Die Seite, die Sie ansehen wollen, hat einen unbekannten Zeichensatz. Das hei?t, dass wir nicht die M?glichkeit haben, die Seite zu filtern und es kann sein, dass dies Ihre Anonymit?t gef?hrdet. ContentDataFilter.unknownCharsetTitle=Unbekannter Zeichensatz! ContentDataFilter.warningUnknownCharsetTitle=Warnung: Unbekannter Zeichensatz (${charset}) @@ -722,8 +730,8 @@ PproxyToadlet.internalIDTitle=Interne ID PproxyToadlet.loadOfficialPlugin=Ein offizielles Plugin hinzuf?gen PproxyToadlet.loadOfficialPluginLabel=Offizielles Plugin laden -PproxyToadlet.loadOfficialPluginText=Diese Plugins liegen auf den Servern des Freenetprojekts. Wir glauben, dass diese Plugins keine pers?nlichen Informationen ungefragt herausgeben, auch wenn wir es nicht garantieren. -PproxyToadlet.loadOfficialPluginWarning=WARNUNG: Das Laden eines offiziellen Plugins beinhaltet das Herunterladen aus dem Internet (nicht ?ber Freenet). Ein Angreifer k?nnte diesen Download sehen und ihn m?glicherweise beeinflussen. Lade keine Plugins herunter, wenn dies ein Problem ist. +PproxyToadlet.loadOfficialPluginText=Diese Plugins liegen auf den Servern des Freenet-Projekts. Wir glauben, dass diese Plugins keine pers?nlichen Informationen ungefragt herausgeben, auch wenn wir es nicht garantieren. +PproxyToadlet.loadOfficialPluginWarning=WARNUNG: Das Laden eines offiziellen Plugins beinhaltet das Herunterladen des Plugins aus dem Internet (nicht aus dem Freenet). Ein Angreifer k?nnte das Herunterladen bemerken und vielleicht manipulieren. Laden Sie hier keine Plugins herunter wenn dies ein Problem darstellt. PproxyToadlet.loadOtherPlugin=Ein inoffizielles Plugin hinzuf?gen PproxyToadlet.loadOtherPluginText=Hier k?nnen Sie die URL eines Plugins eingeben, das geladen werden soll. Andere Plugins als die oben aufgelisteten, werden von uns noch nicht einmal im Entferntesten unterst?tzt oder darauf gepr?ft, ob sie pers?nliche Informationen herausgeben. Wenn Sie also hier ein inoffizielles Plugin laden, sind Sie auf sich allein gestellt. PproxyToadlet.loadOtherURLLabel=Plugin-URL @@ -811,7 +819,7 @@ QueueToadlet.legend=Legende QueueToadlet.mimeType=MIME-Typ QueueToadlet.noTaskOnGlobalQueue=Im Moment ist keine Aufgabe in der globalen Warteschlange. -QueueToadlet.none=keine/r +QueueToadlet.none=nicht vorhanden QueueToadlet.panicButton=Alarm-Knopf QueueToadlet.panicButtonConfirmation=Alle Anfragen ohne Best?tigung entfernen! QueueToadlet.persistence=Persistenz (Speicher-Dauer) @@ -944,6 +952,7 @@ Toadlet.unauthorizedTitle=Nicht erlaubt Toadlet.yes=Ja ToadletContextImpl.cannotParseContentLength=Fehler beim Erkennen der Inhalts-L?nge: ${error} +ToadletContextImpl.cannotParseContentLengthWithError=Kann die Gr??e des Inhalts nicht verarbeiten, Fehlermeldung: ${error} ToadletContextImpl.headersLineTooLong=Zeile zu lang, beim Analysieren der Header (Dateik?pfe) ToadletContextImpl.methodNotAllowed=HTTP-Methode (Funktion) nicht erlaubt ToadletContextImpl.noContentLengthInPOST=Keine Inhalts-L?nge im POST From bombe at freenetproject.org Sat Dec 1 12:14:40 2007 From: bombe at freenetproject.org (bombe at freenetproject.org) Date: Sat, 1 Dec 2007 12:14:40 +0000 (UTC) Subject: [freenet-cvs] r16173 - trunk/apps/jSite/src/de/todesbaum/jsite/gui Message-ID: <20071201121440.42BF9479708@freenetproject.org> Author: bombe Date: 2007-12-01 12:14:39 +0000 (Sat, 01 Dec 2007) New Revision: 16173 Modified: trunk/apps/jSite/src/de/todesbaum/jsite/gui/ProjectPage.java Log: start new projects with edition 1 add a scrollpane around the project list Modified: trunk/apps/jSite/src/de/todesbaum/jsite/gui/ProjectPage.java =================================================================== --- trunk/apps/jSite/src/de/todesbaum/jsite/gui/ProjectPage.java 2007-12-01 00:15:26 UTC (rev 16172) +++ trunk/apps/jSite/src/de/todesbaum/jsite/gui/ProjectPage.java 2007-12-01 12:14:39 UTC (rev 16173) @@ -47,6 +47,7 @@ import javax.swing.JScrollPane; import javax.swing.JTextField; import javax.swing.ListSelectionModel; +import javax.swing.ScrollPaneConstants; import javax.swing.border.EmptyBorder; import javax.swing.event.DocumentEvent; import javax.swing.event.DocumentListener; @@ -81,6 +82,7 @@ private JFileChooser pathChooser; private SortedListModel projectListModel; + private JScrollPane projectScrollPane; private JList projectList; private JTextField projectNameTextField; private JTextField projectDescriptionTextField; @@ -115,7 +117,7 @@ projectList.addListSelectionListener(this); projectList.setPreferredSize(new Dimension(150, projectList.getPreferredSize().height)); - add(new JScrollPane(projectList), BorderLayout.LINE_START); + add(projectScrollPane = new JScrollPane(projectList), BorderLayout.LINE_START); add(createInformationPanel(), BorderLayout.CENTER); } @@ -397,8 +399,10 @@ newProject.setName(I18n.getMessage("jsite.project.new-project.name")); newProject.setInsertURI(keyPair[0]); newProject.setRequestURI(keyPair[1]); - newProject.setEdition(1); + newProject.setEdition(0); projectListModel.add(newProject); + projectScrollPane.revalidate(); + projectScrollPane.repaint(); projectList.setSelectedIndex(projectListModel.size() - 1); } From bombe at freenetproject.org Sat Dec 1 12:17:34 2007 From: bombe at freenetproject.org (bombe at freenetproject.org) Date: Sat, 1 Dec 2007 12:17:34 +0000 (UTC) Subject: [freenet-cvs] r16174 - trunk/apps/jSite/src/de/todesbaum/jsite/application Message-ID: <20071201121734.6F1F2390A91@freenetproject.org> Author: bombe Date: 2007-12-01 12:17:34 +0000 (Sat, 01 Dec 2007) New Revision: 16174 Modified: trunk/apps/jSite/src/de/todesbaum/jsite/application/Project.java Log: don't create superfluous map Modified: trunk/apps/jSite/src/de/todesbaum/jsite/application/Project.java =================================================================== --- trunk/apps/jSite/src/de/todesbaum/jsite/application/Project.java 2007-12-01 12:14:39 UTC (rev 16173) +++ trunk/apps/jSite/src/de/todesbaum/jsite/application/Project.java 2007-12-01 12:17:34 UTC (rev 16174) @@ -241,7 +241,7 @@ * @return Returns the fileOptions. */ public Map getFileOptions() { - return Collections.unmodifiableMap(new HashMap(fileOptions)); + return Collections.unmodifiableMap(fileOptions); } /** From bombe at freenetproject.org Sat Dec 1 12:18:10 2007 From: bombe at freenetproject.org (bombe at freenetproject.org) Date: Sat, 1 Dec 2007 12:18:10 +0000 (UTC) Subject: [freenet-cvs] r16175 - trunk/apps/jSite/src/de/todesbaum/jsite/gui Message-ID: <20071201121810.345F6390A91@freenetproject.org> Author: bombe Date: 2007-12-01 12:18:09 +0000 (Sat, 01 Dec 2007) New Revision: 16175 Modified: trunk/apps/jSite/src/de/todesbaum/jsite/gui/ProjectFilesPage.java Log: fix exception when files is removed (should fix #1755) Modified: trunk/apps/jSite/src/de/todesbaum/jsite/gui/ProjectFilesPage.java =================================================================== --- trunk/apps/jSite/src/de/todesbaum/jsite/gui/ProjectFilesPage.java 2007-12-01 12:17:34 UTC (rev 16174) +++ trunk/apps/jSite/src/de/todesbaum/jsite/gui/ProjectFilesPage.java 2007-12-01 12:18:09 UTC (rev 16175) @@ -31,8 +31,11 @@ import java.text.MessageFormat; import java.util.ArrayList; import java.util.Collections; +import java.util.HashSet; import java.util.Iterator; import java.util.List; +import java.util.Set; +import java.util.Map.Entry; import javax.swing.AbstractAction; import javax.swing.Action; @@ -400,13 +403,17 @@ rebuildContainerComboBox(); } }); + Set entriesToRemove = new HashSet(); Iterator filenames = project.getFileOptions().keySet().iterator(); while (filenames.hasNext()) { String filename = filenames.next(); if (!files.contains(filename)) { - project.setFileOption(filename, null); + entriesToRemove.add(filename); } } + for (String filename: entriesToRemove) { + project.setFileOption(filename, null); + } } else { JOptionPane.showMessageDialog(wizard, I18n.getMessage("jsite.project-files.scan-error"), null, JOptionPane.ERROR_MESSAGE); } From bombe at freenetproject.org Sat Dec 1 12:23:33 2007 From: bombe at freenetproject.org (bombe at freenetproject.org) Date: Sat, 1 Dec 2007 12:23:33 +0000 (UTC) Subject: [freenet-cvs] r16176 - trunk/apps/jSite/src/de/todesbaum/jsite/main Message-ID: <20071201122333.704E0390A91@freenetproject.org> Author: bombe Date: 2007-12-01 12:23:33 +0000 (Sat, 01 Dec 2007) New Revision: 16176 Modified: trunk/apps/jSite/src/de/todesbaum/jsite/main/Version.java Log: increase version number Modified: trunk/apps/jSite/src/de/todesbaum/jsite/main/Version.java =================================================================== --- trunk/apps/jSite/src/de/todesbaum/jsite/main/Version.java 2007-12-01 12:18:09 UTC (rev 16175) +++ trunk/apps/jSite/src/de/todesbaum/jsite/main/Version.java 2007-12-01 12:23:33 UTC (rev 16176) @@ -25,7 +25,7 @@ */ public class Version { - private static final String VERSION = "0.4.9.3"; + private static final String VERSION = "0.4.9.4"; public static final String getVersion() { return VERSION; From nextgens at freenetproject.org Sat Dec 1 13:43:35 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 13:43:35 +0000 (UTC) Subject: [freenet-cvs] r16177 - trunk/freenet/src/freenet/node Message-ID: <20071201134335.91A634796F8@freenetproject.org> Author: nextgens Date: 2007-12-01 13:43:35 +0000 (Sat, 01 Dec 2007) New Revision: 16177 Modified: trunk/freenet/src/freenet/node/PacketSender.java Log: Fix a potential rekeying bug: we were "loosing" some packets here Modified: trunk/freenet/src/freenet/node/PacketSender.java =================================================================== --- trunk/freenet/src/freenet/node/PacketSender.java 2007-12-01 12:23:33 UTC (rev 16176) +++ trunk/freenet/src/freenet/node/PacketSender.java 2007-12-01 13:43:35 UTC (rev 16177) @@ -202,7 +202,7 @@ lastReceivedPacketFromAnyNode = Math.max(pn.lastReceivedPacketTime(), lastReceivedPacketFromAnyNode); pn.maybeOnConnect(); - if(pn.isConnected() && !pn.isRekeying()) { + if(pn.isConnected()) { // Is the node dead? if(now - pn.lastReceivedPacketTime() > pn.maxTimeBetweenReceivedPackets()) { Logger.normal(this, "Disconnecting from "+pn+" - haven't received packets recently"); @@ -309,21 +309,22 @@ pn.getOutgoingMangler().processOutgoingOrRequeue(new MessageItem[] { new MessageItem(m, null, 0, null) }, pn, true, true); } } else { - // Not connected + // Not connected + if(pn.noContactDetails()) + pn.startARKFetcher(); + } + if(pn.shouldSendHandshake()) { // Send handshake if necessary long beforeHandshakeTime = System.currentTimeMillis(); - if(pn.shouldSendHandshake()) - pn.getOutgoingMangler().sendHandshake(pn); - if(pn.noContactDetails()) - pn.startARKFetcher(); + pn.getOutgoingMangler().sendHandshake(pn); long afterHandshakeTime = System.currentTimeMillis(); if((afterHandshakeTime - beforeHandshakeTime) > (2*1000)) Logger.error(this, "afterHandshakeTime is more than 2 seconds past beforeHandshakeTime ("+(afterHandshakeTime - beforeHandshakeTime)+") in PacketSender working with "+pn.userToString()); - } + } long tempNow = System.currentTimeMillis(); - if((tempNow - oldTempNow) > (5*1000)) - Logger.error(this, "tempNow is more than 5 seconds past oldTempNow ("+(tempNow - oldTempNow)+") in PacketSender working with "+pn.userToString()); - oldTempNow = tempNow; + if((tempNow - oldTempNow) > (5 * 1000)) + Logger.error(this, "tempNow is more than 5 seconds past oldTempNow (" + (tempNow - oldTempNow) + ") in PacketSender working with " + pn.userToString()); + oldTempNow = tempNow; } // Consider sending connect requests to our opennet old-peers. From nextgens at freenetproject.org Sat Dec 1 13:45:01 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 13:45:01 +0000 (UTC) Subject: [freenet-cvs] r16178 - trunk/freenet/src/freenet/node Message-ID: <20071201134501.7E9C94797B8@freenetproject.org> Author: nextgens Date: 2007-12-01 13:45:01 +0000 (Sat, 01 Dec 2007) New Revision: 16178 Modified: trunk/freenet/src/freenet/node/PacketSender.java Log: indent Modified: trunk/freenet/src/freenet/node/PacketSender.java =================================================================== --- trunk/freenet/src/freenet/node/PacketSender.java 2007-12-01 13:43:35 UTC (rev 16177) +++ trunk/freenet/src/freenet/node/PacketSender.java 2007-12-01 13:45:01 UTC (rev 16178) @@ -29,446 +29,447 @@ private static boolean logMINOR; private static boolean logDEBUG; - /** Maximum time we will queue a message for in millseconds */ static final int MAX_COALESCING_DELAY = 100; - /** If opennet is enabled, and there are fewer than this many connections, * we MAY attempt to contact old opennet peers (opennet peers we have * dropped from the routing table but kept around in case we can't connect). */ static final int MIN_CONNECTIONS_TRY_OLD_OPENNET_PEERS = 5; - /** We send connect attempts to old-opennet-peers no more than once every * this many milliseconds. */ - static final int MIN_OLD_OPENNET_CONNECT_DELAY_NO_CONNS = 10*1000; - + static final int MIN_OLD_OPENNET_CONNECT_DELAY_NO_CONNS = 10 * 1000; /** We send connect attempts to old-opennet-peers no more than once every * this many milliseconds. */ - static final int MIN_OLD_OPENNET_CONNECT_DELAY = 60*1000; - - final LinkedList resendPackets; - /** ~= Ticker :) */ - private final TreeMap timedJobsByTime; - final Thread myThread; - final Node node; - NodeStats stats; - long lastClearedOldSwapChains; - long lastReportedNoPackets; - long lastReceivedPacketFromAnyNode; - /** For watchdog. 32-bit to avoid locking. */ - volatile int lastTimeInSeconds; - private long timeLastSentOldOpennetConnectAttempt; - - private Vector rpiTemp; - private int[] rpiIntTemp; - - PacketSender(Node node) { - resendPackets = new LinkedList(); - timedJobsByTime = new TreeMap(); - this.node = node; - myThread = new Thread(this, "PacketSender thread for "+node.getDarknetPortNumber()); - myThread.setDaemon(true); - myThread.setPriority(Thread.MAX_PRIORITY); - logMINOR = Logger.shouldLog(Logger.MINOR, this); - logDEBUG = Logger.shouldLog(Logger.DEBUG, this); - rpiTemp = new Vector(); - rpiIntTemp = new int[64]; - } + static final int MIN_OLD_OPENNET_CONNECT_DELAY = 60 * 1000; + final LinkedList resendPackets; + /** ~= Ticker :) */ + private final TreeMap timedJobsByTime; + final Thread myThread; + final Node node; + NodeStats stats; + long lastClearedOldSwapChains; + long lastReportedNoPackets; + long lastReceivedPacketFromAnyNode; + /** For watchdog. 32-bit to avoid locking. */ + volatile int lastTimeInSeconds; + private long timeLastSentOldOpennetConnectAttempt; + private Vector rpiTemp; + private int[] rpiIntTemp; - - /** - * The main purpose of this thread is to detect the lost-lock deadlocks that happen occasionally - * on Sun VMs with NPTL enabled, and restart the node. - * - * Consequently it MUST NOT LOCK ANYTHING. That further means it must not use the Logger, and even - * System.err/System.out if they have been redirected. - * @author root - * - */ - private class Watchdog implements Runnable { - - public void run() { - freenet.support.Logger.OSThread.logPID(this); - // Do not lock anything, or we may be caught up with a lost-lock deadlock. - while(true) { - try { + PacketSender(Node node) { + resendPackets = new LinkedList(); + timedJobsByTime = new TreeMap(); + this.node = node; + myThread = new Thread(this, "PacketSender thread for " + node.getDarknetPortNumber()); + myThread.setDaemon(true); + myThread.setPriority(Thread.MAX_PRIORITY); + logMINOR = Logger.shouldLog(Logger.MINOR, this); + logDEBUG = Logger.shouldLog(Logger.DEBUG, this); + rpiTemp = new Vector(); + rpiIntTemp = new int[64]; + } + + /** + * The main purpose of this thread is to detect the lost-lock deadlocks that happen occasionally + * on Sun VMs with NPTL enabled, and restart the node. + * + * Consequently it MUST NOT LOCK ANYTHING. That further means it must not use the Logger, and even + * System.err/System.out if they have been redirected. + * @author root + * + */ + private class Watchdog implements Runnable { + + public void run() { + freenet.support.Logger.OSThread.logPID(this); + // Do not lock anything, or we may be caught up with a lost-lock deadlock. + while(true) { + try { Thread.sleep(5000); - } catch (InterruptedException e) { - // Ignore + } catch(InterruptedException e) { + // Ignore } long now = System.currentTimeMillis(); - long recordedTime = ((long)lastTimeInSeconds) * 1000; + long recordedTime = ((long) lastTimeInSeconds) * 1000; long diff = now - recordedTime; - if((diff > 3*60*1000) && node.isHasStarted()) { + if((diff > 3 * 60 * 1000) && node.isHasStarted()) { FileLoggerHook flh = Node.logConfigHandler.getFileLoggerHook(); boolean redirected = flh != null && !flh.hasRedirectedStdOutErrNoLock(); if(!redirected) - System.err.println("Restarting node: PacketSender froze for 3 minutes! ("+diff+ ')'); - + System.err.println("Restarting node: PacketSender froze for 3 minutes! (" + diff + ')'); + try { - if(node.isUsingWrapper()){ + if(node.isUsingWrapper()) { WrapperManager.requestThreadDump(); WrapperManager.restart(); - }else{ + } else { if(!redirected) System.err.println("Exiting on deadlock, but not running in the wrapper! Please restart the node manually."); - + // No wrapper : we don't want to let it harm the network! node.exit("PacketSender deadlock"); } - } catch (Throwable t) { + } catch(Throwable t) { if(!Node.logConfigHandler.getFileLoggerHook().hasRedirectedStdOutErrNoLock()) { System.err.println("Error : can't restart the node : consider installing the wrapper. PLEASE REPORT THAT ERROR TO devl at freenetproject.org"); t.printStackTrace(); } node.exit("PacketSender deadlock and error"); } - + } - - } - } - } - - void start(NodeStats stats) { - this.stats = stats; - Logger.normal(this, "Starting PacketSender"); - System.out.println("Starting PacketSender"); - long now = System.currentTimeMillis(); - long transition = Version.transitionTime; - if(now < transition) { - queueTimedJob(new Runnable() { - public void run() { - freenet.support.Logger.OSThread.logPID(this); - PeerNode[] nodes = node.peers.myPeers; - for(int i=0;i pn.maxTimeBetweenReceivedPackets()) { - Logger.normal(this, "Disconnecting from "+pn+" - haven't received packets recently"); - pn.disconnected(); - continue; - } else if(pn.isRoutable() && pn.noLongerRoutable()) { - // we don't disconnect but we mark it incompatible - pn.invalidate(); - pn.setPeerNodeStatus(now); - Logger.normal(this, "shouldDisconnectNow has returned true : marking the peer as incompatible"); - continue; - } - - boolean mustSend = false; - - // Any urgent notifications to send? - long urgentTime = pn.getNextUrgentTime(); - // Should spam the logs, unless there is a deadlock - if(urgentTime < Long.MAX_VALUE && logMINOR) - Logger.minor(this, "Next urgent time: "+urgentTime+" for "+pn.getPeer()); - if(urgentTime <= now) { - mustSend = true; - } else { - nextActionTime = Math.min(nextActionTime, urgentTime); - } - - // Any packets to resend? - for(int j=0;j<2;j++) { - KeyTracker kt; - if(j == 0) kt = pn.getCurrentKeyTracker(); - else if(j == 1) kt = pn.getPreviousKeyTracker(); - else break; // impossible - if(kt == null) continue; - int[] tmp = kt.grabResendPackets(rpiTemp, rpiIntTemp); - if(tmp == null) continue; - rpiIntTemp = tmp; - for(int k=0;k pn.maxTimeBetweenReceivedPackets()) { + Logger.normal(this, "Disconnecting from " + pn + " - haven't received packets recently"); + pn.disconnected(); + continue; + } else if(pn.isRoutable() && pn.noLongerRoutable()) { + // we don't disconnect but we mark it incompatible + pn.invalidate(); + pn.setPeerNodeStatus(now); + Logger.normal(this, "shouldDisconnectNow has returned true : marking the peer as incompatible"); + continue; + } + + boolean mustSend = false; + + // Any urgent notifications to send? + long urgentTime = pn.getNextUrgentTime(); + // Should spam the logs, unless there is a deadlock + if(urgentTime < Long.MAX_VALUE && logMINOR) + Logger.minor(this, "Next urgent time: " + urgentTime + " for " + pn.getPeer()); + if(urgentTime <= now) + mustSend = true; + else + nextActionTime = Math.min(nextActionTime, urgentTime); + + // Any packets to resend? + for(int j = 0; j < 2; j++) { + KeyTracker kt; + if(j == 0) + kt = pn.getCurrentKeyTracker(); + else if(j == 1) + kt = pn.getPreviousKeyTracker(); + else + break; // impossible + if(kt == null) + continue; + int[] tmp = kt.grabResendPackets(rpiTemp, rpiIntTemp); + if(tmp == null) + continue; + rpiIntTemp = tmp; + for(int k = 0; k < rpiTemp.size(); k++) { + ResendPacketItem item = (ResendPacketItem) rpiTemp.get(k); + if(item == null) + continue; + try { + if(logMINOR) + Logger.minor(this, "Resending " + item.packetNumber + " to " + item.kt); + pn.getOutgoingMangler().resend(item); + mustSend = false; + } catch(KeyChangedException e) { + Logger.error(this, "Caught " + e + " resending packets to " + kt); + pn.requeueResendItems(rpiTemp); + break; + } catch(NotConnectedException e) { + Logger.normal(this, "Caught " + e + " resending packets to " + kt); + pn.requeueResendItems(rpiTemp); + break; + } catch(PacketSequenceException e) { + Logger.error(this, "Caught " + e + " - disconnecting", e); + pn.forceDisconnect(); + } catch(WouldBlockException e) { + Logger.error(this, "Impossible: " + e, e); } - } - - } + } - // Any messages to send? - MessageItem[] messages = null; - messages = pn.grabQueuedMessageItems(); - if((messages != null) && (messages.length > 0)) { - long l = Long.MAX_VALUE; - int sz = pn.getOutgoingMangler().fullHeadersLengthOneMessage(); // includes UDP headers - for(int j=0;j messages[j].submitted) l = messages[j].submitted; - sz += 2 + /* FIXME only 2? */ messages[j].getData(pn).length; - } - if((l + MAX_COALESCING_DELAY > now) && - (sz < ((PacketSocketHandler) pn.getSocketHandler()).getPacketSendThreshold())) { - // Don't send immediately - if(nextActionTime > (l+MAX_COALESCING_DELAY)) - nextActionTime = l+MAX_COALESCING_DELAY; - pn.requeueMessageItems(messages, 0, messages.length, true, "TrafficCoalescing"); - } else { - for(int j=0;j 0)) { + long l = Long.MAX_VALUE; + int sz = pn.getOutgoingMangler().fullHeadersLengthOneMessage(); // includes UDP headers + for(int j = 0; j < messages.length; j++) { + if(l > messages[j].submitted) + l = messages[j].submitted; + sz += 2 + /* FIXME only 2? */ messages[j].getData(pn).length; + } + if((l + MAX_COALESCING_DELAY > now) && + (sz < ((PacketSocketHandler) pn.getSocketHandler()).getPacketSendThreshold())) { + // Don't send immediately + if(nextActionTime > (l + MAX_COALESCING_DELAY)) + nextActionTime = l + MAX_COALESCING_DELAY; + pn.requeueMessageItems(messages, 0, messages.length, true, "TrafficCoalescing"); + } else { + for(int j = 0; j < messages.length; j++) + if(logMINOR) + Logger.minor(this, "PS Sending: " + (messages[j].msg == null ? "(not a Message)" : messages[j].msg.getSpec().getName())); + // Send packets, right now, blocking, including any active notifications + pn.getOutgoingMangler().processOutgoingOrRequeue(messages, pn, true, false); + continue; + } + } + + if(mustSend) + // Send them + + try { pn.sendAnyUrgentNotifications(); - } catch (PacketSequenceException e) { - Logger.error(this, "Caught "+e+" - while sending urgent notifications : disconnecting", e); - pn.forceDisconnect(); + } catch(PacketSequenceException e) { + Logger.error(this, "Caught " + e + " - while sending urgent notifications : disconnecting", e); + pn.forceDisconnect(); } - } - - // Need to send a keepalive packet? - if(now - pn.lastSentPacketTime() > Node.KEEPALIVE_INTERVAL) { - if(logMINOR) Logger.minor(this, "Sending keepalive"); - // Force packet to have a sequence number. - Message m = DMT.createFNPVoid(); - pn.addToLocalNodeSentMessagesToStatistic(m); - pn.getOutgoingMangler().processOutgoingOrRequeue(new MessageItem[] { new MessageItem(m, null, 0, null) }, pn, true, true); - } - } else { - // Not connected - if(pn.noContactDetails()) - pn.startARKFetcher(); - } - if(pn.shouldSendHandshake()) { - // Send handshake if necessary - long beforeHandshakeTime = System.currentTimeMillis(); - pn.getOutgoingMangler().sendHandshake(pn); - long afterHandshakeTime = System.currentTimeMillis(); - if((afterHandshakeTime - beforeHandshakeTime) > (2*1000)) - Logger.error(this, "afterHandshakeTime is more than 2 seconds past beforeHandshakeTime ("+(afterHandshakeTime - beforeHandshakeTime)+") in PacketSender working with "+pn.userToString()); - } - long tempNow = System.currentTimeMillis(); - if((tempNow - oldTempNow) > (5 * 1000)) - Logger.error(this, "tempNow is more than 5 seconds past oldTempNow (" + (tempNow - oldTempNow) + ") in PacketSender working with " + pn.userToString()); - oldTempNow = tempNow; - } - - // Consider sending connect requests to our opennet old-peers. - // No point if they are NATed, of course... but we don't know whether they are. - OpennetManager om = node.getOpennet(); - if(om != null) { - int connCount = node.peers.quickCountConnectedPeers(); - int minDelay = connCount == 0 ? MIN_OLD_OPENNET_CONNECT_DELAY_NO_CONNS : MIN_OLD_OPENNET_CONNECT_DELAY; - if(logDEBUG) - Logger.debug(this, "Conns "+connCount+" minDelay "+minDelay+" old opennet peers "+om.countOldOpennetPeers()+" last sent "+(now - timeLastSentOldOpennetConnectAttempt)+" startup "+(now - node.startupTime)); - if(now - timeLastSentOldOpennetConnectAttempt > minDelay && - connCount <= MIN_CONNECTIONS_TRY_OLD_OPENNET_PEERS && - om.countOldOpennetPeers() > 0 && - now - node.startupTime > OpennetManager.DROP_STARTUP_DELAY) { - PeerNode pn = om.randomOldOpennetNode(); - if(pn != null) { - if(logMINOR) - Logger.minor(this, "Sending old-opennet connect attempt to "+pn); - pn.getOutgoingMangler().sendHandshake(pn); - timeLastSentOldOpennetConnectAttempt = now; - if(pn.noContactDetails() && node.getPeerNodes().length > 0 && connCount > 0 && node.random.nextBoolean()) - pn.startARKFetcher(); - } - } - } - - if(now - lastClearedOldSwapChains > 10000) { - node.lm.clearOldSwapChains(); - lastClearedOldSwapChains = now; - } - - long oldNow = System.currentTimeMillis(); - // Send may have taken some time - now = System.currentTimeMillis(); - lastTimeInSeconds = (int) (now / 1000); - - if((now - oldNow) > (10*1000)) - Logger.error(this, "now is more than 10 seconds past oldNow ("+(now - oldNow)+") in PacketSender"); - - Vector jobsToRun = null; - - synchronized(timedJobsByTime) { - while(!timedJobsByTime.isEmpty()) { - Long tRun = (Long) timedJobsByTime.firstKey(); - if(tRun.longValue() <= now) { - if(jobsToRun == null) jobsToRun = new Vector(); - Object o = timedJobsByTime.remove(tRun); - if(o instanceof Runnable[]) { - Runnable[] r = (Runnable[]) o; - for(int i=0;i Node.KEEPALIVE_INTERVAL) { + if(logMINOR) + Logger.minor(this, "Sending keepalive"); + // Force packet to have a sequence number. + Message m = DMT.createFNPVoid(); + pn.addToLocalNodeSentMessagesToStatistic(m); + pn.getOutgoingMangler().processOutgoingOrRequeue(new MessageItem[]{new MessageItem(m, null, 0, null)}, pn, true, true); + } + } else + // Not connected + + if(pn.noContactDetails()) + pn.startARKFetcher(); + if(pn.shouldSendHandshake()) { + // Send handshake if necessary + long beforeHandshakeTime = System.currentTimeMillis(); + pn.getOutgoingMangler().sendHandshake(pn); + long afterHandshakeTime = System.currentTimeMillis(); + if((afterHandshakeTime - beforeHandshakeTime) > (2 * 1000)) + Logger.error(this, "afterHandshakeTime is more than 2 seconds past beforeHandshakeTime (" + (afterHandshakeTime - beforeHandshakeTime) + ") in PacketSender working with " + pn.userToString()); + } + long tempNow = System.currentTimeMillis(); + if((tempNow - oldTempNow) > (5 * 1000)) + Logger.error(this, "tempNow is more than 5 seconds past oldTempNow (" + (tempNow - oldTempNow) + ") in PacketSender working with " + pn.userToString()); + oldTempNow = tempNow; + } + + // Consider sending connect requests to our opennet old-peers. + // No point if they are NATed, of course... but we don't know whether they are. + OpennetManager om = node.getOpennet(); + if(om != null) { + int connCount = node.peers.quickCountConnectedPeers(); + int minDelay = connCount == 0 ? MIN_OLD_OPENNET_CONNECT_DELAY_NO_CONNS : MIN_OLD_OPENNET_CONNECT_DELAY; + if(logDEBUG) + Logger.debug(this, "Conns " + connCount + " minDelay " + minDelay + " old opennet peers " + om.countOldOpennetPeers() + " last sent " + (now - timeLastSentOldOpennetConnectAttempt) + " startup " + (now - node.startupTime)); + if(now - timeLastSentOldOpennetConnectAttempt > minDelay && + connCount <= MIN_CONNECTIONS_TRY_OLD_OPENNET_PEERS && + om.countOldOpennetPeers() > 0 && + now - node.startupTime > OpennetManager.DROP_STARTUP_DELAY) { + PeerNode pn = om.randomOldOpennetNode(); + if(pn != null) { + if(logMINOR) + Logger.minor(this, "Sending old-opennet connect attempt to " + pn); + pn.getOutgoingMangler().sendHandshake(pn); + timeLastSentOldOpennetConnectAttempt = now; + if(pn.noContactDetails() && node.getPeerNodes().length > 0 && connCount > 0 && node.random.nextBoolean()) + pn.startARKFetcher(); + } + } + } + + if(now - lastClearedOldSwapChains > 10000) { + node.lm.clearOldSwapChains(); + lastClearedOldSwapChains = now; + } + + long oldNow = System.currentTimeMillis(); + + // Send may have taken some time + now = System.currentTimeMillis(); + lastTimeInSeconds = (int) (now / 1000); + + if((now - oldNow) > (10 * 1000)) + Logger.error(this, "now is more than 10 seconds past oldNow (" + (now - oldNow) + ") in PacketSender"); + + Vector jobsToRun = null; + + synchronized(timedJobsByTime) { + while(!timedJobsByTime.isEmpty()) { + Long tRun = (Long) timedJobsByTime.firstKey(); + if(tRun.longValue() <= now) { + if(jobsToRun == null) + jobsToRun = new Vector(); + Object o = timedJobsByTime.remove(tRun); + if(o instanceof Runnable[]) { + Runnable[] r = (Runnable[]) o; + for(int i = 0; i < r.length; i++) + jobsToRun.add(r[i]); + } else { + Runnable r = (Runnable) o; + jobsToRun.add(r); + } + } else + // FIXME how accurately do we want ticker jobs to be scheduled? // FIXME can they wait the odd 200ms? - break; - } - } - } - if(jobsToRun != null) { - for(int i=0;i 60*1000*5) { - if(now - lastReceivedPacketFromAnyNode > Node.ALARM_TIME) { - Logger.error(this, "Have not received any packets from any node in last "+Node.ALARM_TIME/1000+" seconds"); - lastReportedNoPackets = now; - } - } - - if(sleepTime > 0) { - // Update logging only when have time to do so - logMINOR = Logger.shouldLog(Logger.MINOR, this); - logDEBUG = Logger.shouldLog(Logger.DEBUG, this); - try { - synchronized(this) { - if(logMINOR) Logger.minor(this, "Sleeping for "+sleepTime); - wait(sleepTime); - } - } catch (InterruptedException e) { - // Ignore, just wake up. Probably we got interrupt()ed - // because a new packet came in. - } - } + } + + long sleepTime = nextActionTime - now; + // MAX_COALESCING_DELAYms maximum sleep time - same as the maximum coalescing delay + sleepTime = Math.min(sleepTime, MAX_COALESCING_DELAY); + + if(now - node.startupTime > 60 * 1000 * 5) + if(now - lastReceivedPacketFromAnyNode > Node.ALARM_TIME) { + Logger.error(this, "Have not received any packets from any node in last " + Node.ALARM_TIME / 1000 + " seconds"); + lastReportedNoPackets = now; + } + + if(sleepTime > 0) { + // Update logging only when have time to do so + logMINOR = Logger.shouldLog(Logger.MINOR, this); + logDEBUG = Logger.shouldLog(Logger.DEBUG, this); + try { + synchronized(this) { + if(logMINOR) + Logger.minor(this, "Sleeping for " + sleepTime); + wait(sleepTime); + } + } catch(InterruptedException e) { + // Ignore, just wake up. Probably we got interrupt()ed + // because a new packet came in. + } + } } - /** Wake up, and send any queued packets. */ + /** Wake up, and send any queued packets. */ void wakeUp() { - // Wake up if needed - synchronized(this) { - notifyAll(); - } - } + // Wake up if needed + synchronized(this) { + notifyAll(); + } + } public void queueTimedJob(Runnable job, long offset) { if(offset <= 0) { - node.executor.execute(job, "Scheduled job: "+job); + node.executor.execute(job, "Scheduled job: " + job); return; } long now = System.currentTimeMillis(); Long l = new Long(offset + now); synchronized(timedJobsByTime) { Object o = timedJobsByTime.get(l); - if(o == null) { + if(o == null) timedJobsByTime.put(l, job); - } else if(o instanceof Runnable) { - timedJobsByTime.put(l, new Runnable[] { (Runnable)o, job }); - } else if(o instanceof Runnable[]) { + else if(o instanceof Runnable) + timedJobsByTime.put(l, new Runnable[]{(Runnable) o, job}); + else if(o instanceof Runnable[]) { Runnable[] r = (Runnable[]) o; - Runnable[] jobs = new Runnable[r.length+1]; + Runnable[] jobs = new Runnable[r.length + 1]; System.arraycopy(r, 0, jobs, 0, r.length); - jobs[jobs.length-1] = job; + jobs[jobs.length - 1] = job; timedJobsByTime.put(l, jobs); } } From nextgens at freenetproject.org Sat Dec 1 13:55:50 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 13:55:50 +0000 (UTC) Subject: [freenet-cvs] r16179 - trunk/freenet/src/freenet/node Message-ID: <20071201135550.9277047B33B@freenetproject.org> Author: nextgens Date: 2007-12-01 13:55:50 +0000 (Sat, 01 Dec 2007) New Revision: 16179 Modified: trunk/freenet/src/freenet/node/FNPPacketMangler.java trunk/freenet/src/freenet/node/PeerNode.java Log: JFK: don't display such a worrying message if there is no need to Modified: trunk/freenet/src/freenet/node/FNPPacketMangler.java =================================================================== --- trunk/freenet/src/freenet/node/FNPPacketMangler.java 2007-12-01 13:45:01 UTC (rev 16178) +++ trunk/freenet/src/freenet/node/FNPPacketMangler.java 2007-12-01 13:55:50 UTC (rev 16179) @@ -812,7 +812,9 @@ DiffieHellmanLightContext ctx = findContextByExponential(_ourExponential); if(ctx == null) { - Logger.error(this, "WTF? the HMAC verified but we don't know about that exponential! SHOULDN'T HAPPEN!"); + // It ca be null if we have just rekeyed and we have more than one handshake/jfk run + if(!pn.isConnected()) + Logger.error(this, "WTF? the HMAC verified but we don't know about that exponential! SHOULDN'T HAPPEN!"); return; } BigInteger computedExponential = ctx.getHMACKey(_hisExponential, Global.DHgroupA); Modified: trunk/freenet/src/freenet/node/PeerNode.java =================================================================== --- trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 13:45:01 UTC (rev 16178) +++ trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 13:55:50 UTC (rev 16179) @@ -926,10 +926,6 @@ Logger.normal(this, "We are asking for the key to be renewed (" + this.detectedPeer + ')'); } - protected synchronized boolean isRekeying() { - return isRekeying; - } - /** * @return The time this PeerNode was added to the node (persistent across restarts). */ From nextgens at freenetproject.org Sat Dec 1 14:49:29 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 14:49:29 +0000 (UTC) Subject: [freenet-cvs] r16180 - in trunk/freenet/src/freenet: crypt node Message-ID: <20071201144929.F0D83391D94@freenetproject.org> Author: nextgens Date: 2007-12-01 14:49:29 +0000 (Sat, 01 Dec 2007) New Revision: 16180 Modified: trunk/freenet/src/freenet/crypt/DiffieHellmanContext.java trunk/freenet/src/freenet/crypt/DiffieHellmanLightContext.java trunk/freenet/src/freenet/crypt/KeyAgreementSchemeContext.java trunk/freenet/src/freenet/node/FNPPacketMangler.java trunk/freenet/src/freenet/node/PeerNode.java Log: JFK: make DiffieHellmanLightContext extend a refactored KeyAgreementSchemeContext The purpose is to fix PeerNode.hasliveHandshake(long) Modified: trunk/freenet/src/freenet/crypt/DiffieHellmanContext.java =================================================================== --- trunk/freenet/src/freenet/crypt/DiffieHellmanContext.java 2007-12-01 13:55:50 UTC (rev 16179) +++ trunk/freenet/src/freenet/crypt/DiffieHellmanContext.java 2007-12-01 14:49:29 UTC (rev 16180) @@ -4,6 +4,7 @@ package freenet.crypt; +import freenet.crypt.ciphers.Rijndael; import net.i2p.util.NativeBigInteger; import freenet.support.HexUtil; import freenet.support.Logger; @@ -18,6 +19,9 @@ /** The group we both share */ final DHGroup group; + BlockCipher cipher; + byte[] key; + // Generated or set later NativeBigInteger peerExponential; @@ -86,4 +90,17 @@ public NativeBigInteger getHisExponential() { return peerExponential; } + + public synchronized BlockCipher getCipher() { + lastUsedTime = System.currentTimeMillis(); + if(cipher != null) return cipher; + getKey(); + try { + cipher = new Rijndael(256, 256); + } catch (UnsupportedCipherException e1) { + throw new Error(e1); + } + cipher.initialize(key); + return cipher; + } } Modified: trunk/freenet/src/freenet/crypt/DiffieHellmanLightContext.java =================================================================== --- trunk/freenet/src/freenet/crypt/DiffieHellmanLightContext.java 2007-12-01 13:55:50 UTC (rev 16179) +++ trunk/freenet/src/freenet/crypt/DiffieHellmanLightContext.java 2007-12-01 14:49:29 UTC (rev 16180) @@ -7,7 +7,7 @@ import net.i2p.util.NativeBigInteger; -public class DiffieHellmanLightContext { +public class DiffieHellmanLightContext extends KeyAgreementSchemeContext { /** My exponent.*/ public final NativeBigInteger myExponent; @@ -17,8 +17,6 @@ public DSASignature signature = null; /** A timestamp: when was the context created ? */ public final long lifetime = System.currentTimeMillis(); - - private final boolean logMINOR; public String toString() { StringBuffer sb = new StringBuffer(); @@ -34,7 +32,8 @@ public DiffieHellmanLightContext(NativeBigInteger myExponent, NativeBigInteger myExponential) { this.myExponent = myExponent; this.myExponential = myExponential; - logMINOR = Logger.shouldLog(Logger.MINOR, this); + this.lastUsedTime = System.currentTimeMillis(); + this.logMINOR = Logger.shouldLog(Logger.MINOR, this); } public void setSignature(DSASignature sig) { @@ -45,6 +44,7 @@ * Calling the following is costy; avoid */ public NativeBigInteger getHMACKey(NativeBigInteger peerExponential, DHGroup group) { + lastUsedTime = System.currentTimeMillis(); BigInteger P = group.getP(); NativeBigInteger sharedSecret = (NativeBigInteger) peerExponential.modPow(myExponent, P); Modified: trunk/freenet/src/freenet/crypt/KeyAgreementSchemeContext.java =================================================================== --- trunk/freenet/src/freenet/crypt/KeyAgreementSchemeContext.java 2007-12-01 13:55:50 UTC (rev 16179) +++ trunk/freenet/src/freenet/crypt/KeyAgreementSchemeContext.java 2007-12-01 14:49:29 UTC (rev 16180) @@ -3,35 +3,15 @@ * http://www.gnu.org/ for further details of the GPL. */ package freenet.crypt; -import freenet.crypt.ciphers.Rijndael; - public abstract class KeyAgreementSchemeContext { - BlockCipher cipher; - byte[] key; - - protected long lastUsedTime; - protected boolean logMINOR; - - /** - * @return The time at which this object was last used. - */ - public synchronized long lastUsedTime() { - return lastUsedTime; - } - - public abstract byte[] getKey(); - public abstract boolean canGetCipher(); - - public synchronized BlockCipher getCipher() { - lastUsedTime = System.currentTimeMillis(); - if(cipher != null) return cipher; - getKey(); - try { - cipher = new Rijndael(256, 256); - } catch (UnsupportedCipherException e1) { - throw new Error(e1); - } - cipher.initialize(key); - return cipher; - } -} + + protected long lastUsedTime; + protected boolean logMINOR; + + /** + * @return The time at which this object was last used. + */ + public synchronized long lastUsedTime() { + return lastUsedTime; + } +} \ No newline at end of file Modified: trunk/freenet/src/freenet/node/FNPPacketMangler.java =================================================================== --- trunk/freenet/src/freenet/node/FNPPacketMangler.java 2007-12-01 13:55:50 UTC (rev 16179) +++ trunk/freenet/src/freenet/node/FNPPacketMangler.java 2007-12-01 14:49:29 UTC (rev 16180) @@ -535,12 +535,13 @@ private void sendJFKMessage1(PeerNode pn, Peer replyTo) { if(logMINOR) Logger.minor(this, "Sending a JFK(1) message to "+pn); final long now = System.currentTimeMillis(); - if((pn.jfkContext == null) || ((pn.jfkContextLifetime + 15*60*1000) < now)) { - pn.jfkContext = getLightDiffieHellmanContext(); + DiffieHellmanLightContext ctx = (DiffieHellmanLightContext) pn.getKeyAgreementSchemeContext(); + if((ctx == null) || ((pn.jfkContextLifetime + 15*60*1000) < now)) { pn.jfkContextLifetime = now; + pn.setKeyAgreementSchemeContext(ctx = getLightDiffieHellmanContext()); } int offset = 0; - byte[] myExponential = stripBigIntegerToNetworkFormat(pn.jfkContext.myExponential); + byte[] myExponential = stripBigIntegerToNetworkFormat(ctx.myExponential); byte[] nonce = new byte[NONCE_SIZE]; node.random.nextBytes(nonce); @@ -1026,7 +1027,7 @@ pn.jfkKs = null; // We want to clear it here so that new handshake requests // will be sent with a different DH pair - pn.jfkContext = null; + pn.setKeyAgreementSchemeContext(null); synchronized (pn) { // FIXME TRUE MULTI-HOMING: winner-takes-all, kill all other connection attempts since we can't deal with multiple active connections // Also avoids leaking @@ -1052,7 +1053,9 @@ if(logMINOR) Logger.minor(this, "Sending a JFK(3) message to "+pn); BlockCipher c = null; try { c = new Rijndael(256, 256); } catch (UnsupportedCipherException e) {} - byte[] ourExponential = stripBigIntegerToNetworkFormat(pn.jfkContext.myExponential); + DiffieHellmanLightContext ctx = (DiffieHellmanLightContext) pn.getKeyAgreementSchemeContext(); + if(ctx == null) return; + byte[] ourExponential = stripBigIntegerToNetworkFormat(ctx.myExponential); pn.jfkMyRef = crypto.myCompressedSetupRef(); byte[] data = new byte[8 + pn.jfkMyRef.length]; System.arraycopy(Fields.longToBytes(node.bootID), 0, data, 0, 8); @@ -1094,7 +1097,7 @@ byte[] r = localSignature.getRBytes(Node.SIGNATURE_PARAMETER_LENGTH); byte[] s = localSignature.getSBytes(Node.SIGNATURE_PARAMETER_LENGTH); - BigInteger computedExponential = pn.jfkContext.getHMACKey(_hisExponential, Global.DHgroupA); + BigInteger computedExponential = ctx.getHMACKey(_hisExponential, Global.DHgroupA); pn.jfkKs = computeJFKSharedKey(computedExponential, nonceInitiator, nonceResponder, "0"); pn.jfkKe = computeJFKSharedKey(computedExponential, nonceInitiator, nonceResponder, "1"); pn.jfkKa = computeJFKSharedKey(computedExponential, nonceInitiator, nonceResponder, "2"); @@ -2430,9 +2433,6 @@ if((DHTime2 - DHTime1) > 1000) Logger.error(this, "DHTime2 is more than a second after DHTime1 ("+(DHTime2 - DHTime1)+") working on "+pn.userToString()); pn.setKeyAgreementSchemeContext(ctx); - long DHTime3 = System.currentTimeMillis(); - if((DHTime3 - DHTime2) > 1000) - Logger.error(this, "DHTime3 is more than a second after DHTime2 ("+(DHTime3 - DHTime2)+") working on "+pn.userToString()); } int sentCount = 0; long loopTime1 = System.currentTimeMillis(); Modified: trunk/freenet/src/freenet/node/PeerNode.java =================================================================== --- trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 13:55:50 UTC (rev 16179) +++ trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 14:49:29 UTC (rev 16180) @@ -29,7 +29,6 @@ import freenet.crypt.DSAGroup; import freenet.crypt.DSAPublicKey; import freenet.crypt.DSASignature; -import freenet.crypt.DiffieHellmanLightContext; import freenet.crypt.KeyAgreementSchemeContext; import freenet.crypt.SHA256; import freenet.crypt.UnsupportedCipherException; @@ -102,7 +101,6 @@ // The following is used only if we are the initiator protected long jfkContextLifetime = 0; - protected DiffieHellmanLightContext jfkContext = null; /** My low-level address for SocketManager purposes */ private Peer detectedPeer; /** My OutgoingPacketMangler i.e. the object which encrypts packets sent to this node */ @@ -914,6 +912,7 @@ hasRekeyed = true; isRekeying = true; sendHandshakeTime = now; // Immediately + ctx = null; } } @@ -1509,7 +1508,6 @@ if(previousTracker == null) previousTracker = unverifiedTracker; unverifiedTracker = newTracker; - ctx = null; } else { prev = currentTracker; previousTracker = prev; @@ -1517,8 +1515,8 @@ unverifiedTracker = null; neverConnected = false; peerAddedTime = 0; // don't store anymore - ctx = null; } + ctx = null; isRekeying = false; timeLastRekeyed = now; totalBytesExchangedWithCurrentTracker = 0; From nextgens at freenetproject.org Sat Dec 1 14:50:20 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 14:50:20 +0000 (UTC) Subject: [freenet-cvs] r16181 - trunk/freenet/src/freenet/node Message-ID: <20071201145020.8EB95391D96@freenetproject.org> Author: nextgens Date: 2007-12-01 14:50:20 +0000 (Sat, 01 Dec 2007) New Revision: 16181 Modified: trunk/freenet/src/freenet/node/FNPPacketMangler.java Log: JFK: set negType to 2 only (StS beeing deprecated) Modified: trunk/freenet/src/freenet/node/FNPPacketMangler.java =================================================================== --- trunk/freenet/src/freenet/node/FNPPacketMangler.java 2007-12-01 14:49:29 UTC (rev 16180) +++ trunk/freenet/src/freenet/node/FNPPacketMangler.java 2007-12-01 14:50:20 UTC (rev 16181) @@ -2481,7 +2481,7 @@ } public int[] supportedNegTypes() { - return new int[] { 1, 2 }; + return new int[] { 2 }; } public int fullHeadersLengthOneMessage() { From nextgens at freenetproject.org Sat Dec 1 15:14:36 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 15:14:36 +0000 (UTC) Subject: [freenet-cvs] r16182 - trunk/freenet/src/freenet/node Message-ID: <20071201151436.632FC47AE7D@freenetproject.org> Author: nextgens Date: 2007-12-01 15:14:36 +0000 (Sat, 01 Dec 2007) New Revision: 16182 Modified: trunk/freenet/src/freenet/node/PeerNode.java Log: JFK: simplify|fix the logic of rekeying Modified: trunk/freenet/src/freenet/node/PeerNode.java =================================================================== --- trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 14:50:20 UTC (rev 16181) +++ trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 15:14:36 UTC (rev 16182) @@ -899,30 +899,33 @@ protected void maybeRekey() { long now = System.currentTimeMillis(); - boolean hasRekeyed = false; - if(hasLiveHandshake(now)) - return; - + boolean shouldDisconnect = false; + boolean shouldReturn = false; + boolean shouldRekey = false; long timeWhenRekeyingShouldOccur = 0; - synchronized(this) { - if(isRekeying || !isConnected) - return; + + synchronized (this) { timeWhenRekeyingShouldOccur = timeLastRekeyed + FNPPacketMangler.SESSION_KEY_REKEYING_INTERVAL; - if((timeWhenRekeyingShouldOccur < now) || (totalBytesExchangedWithCurrentTracker > FNPPacketMangler.AMOUNT_OF_BYTES_ALLOWED_BEFORE_WE_REKEY)) { - hasRekeyed = true; + shouldDisconnect = (timeWhenRekeyingShouldOccur + FNPPacketMangler.MAX_SESSION_KEY_REKEYING_DELAY < now) && isRekeying; + shouldReturn = isRekeying || !isConnected; + shouldRekey = (timeWhenRekeyingShouldOccur < now) || (totalBytesExchangedWithCurrentTracker > FNPPacketMangler.AMOUNT_OF_BYTES_ALLOWED_BEFORE_WE_REKEY); + } + + if(shouldDisconnect) { + String time = TimeUtil.formatTime(FNPPacketMangler.MAX_SESSION_KEY_REKEYING_DELAY); + System.err.println("The peer (" + this + ") has been asked to rekey " + time + " ago... force disconnect."); + Logger.error(this, "The peer (" + this + ") has been asked to rekey " + time + " ago... force disconnect."); + forceDisconnect(); + } else if (shouldReturn || hasLiveHandshake(now)) { + return; + } else if(shouldRekey) { + synchronized(this) { isRekeying = true; sendHandshakeTime = now; // Immediately ctx = null; } + Logger.normal(this, "We are asking for the key to be renewed (" + this.detectedPeer + ')'); } - - if(timeWhenRekeyingShouldOccur + FNPPacketMangler.MAX_SESSION_KEY_REKEYING_DELAY < now) { - Logger.error(this, "The peer (" + this + ") has been asked to rekey " + TimeUtil.formatTime(FNPPacketMangler.MAX_SESSION_KEY_REKEYING_DELAY) + " ago... force disconnect."); - forceDisconnect(); - } - - if(hasRekeyed) - Logger.normal(this, "We are asking for the key to be renewed (" + this.detectedPeer + ')'); } /** From nextgens at freenetproject.org Sat Dec 1 15:25:47 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 15:25:47 +0000 (UTC) Subject: [freenet-cvs] r16183 - trunk/freenet/src/freenet/node Message-ID: <20071201152547.371B8391D9C@freenetproject.org> Author: nextgens Date: 2007-12-01 15:25:47 +0000 (Sat, 01 Dec 2007) New Revision: 16183 Modified: trunk/freenet/src/freenet/node/PeerNode.java Log: JFK: more rekeying related fixes Modified: trunk/freenet/src/freenet/node/PeerNode.java =================================================================== --- trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 15:14:36 UTC (rev 16182) +++ trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 15:25:47 UTC (rev 16183) @@ -1479,6 +1479,7 @@ KeyTracker newTracker = new KeyTracker(this, encCipher, encKey); changedIP(replyTo); boolean bootIDChanged = false; + boolean wasARekey = false; KeyTracker oldPrev = null; KeyTracker oldCur = null; KeyTracker prev = null; @@ -1489,7 +1490,8 @@ if(!isConnected) { connectedTime = now; sentInitialMessages = false; - } + } else + wasARekey = true; isConnected = true; isRoutable = routable; verifiedIncompatibleNewerVersion = newer; @@ -1543,7 +1545,7 @@ if(newer || older || !isConnected()) node.peers.disconnected(this); - else { + else if(!wasARekey) { node.peers.addConnectedPeer(this); onConnect(); } From nextgens at freenetproject.org Sat Dec 1 15:55:19 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 15:55:19 +0000 (UTC) Subject: [freenet-cvs] r16184 - in trunk/freenet/src/freenet: crypt node Message-ID: <20071201155519.D7E0A391DC7@freenetproject.org> Author: nextgens Date: 2007-12-01 15:55:19 +0000 (Sat, 01 Dec 2007) New Revision: 16184 Removed: trunk/freenet/src/freenet/crypt/DiffieHellmanContext.java Modified: trunk/freenet/src/freenet/crypt/DiffieHellman.java trunk/freenet/src/freenet/node/FNPPacketMangler.java Log: deprecate StS : remove all the related code Modified: trunk/freenet/src/freenet/crypt/DiffieHellman.java =================================================================== --- trunk/freenet/src/freenet/crypt/DiffieHellman.java 2007-12-01 15:25:47 UTC (rev 16183) +++ trunk/freenet/src/freenet/crypt/DiffieHellman.java 2007-12-01 15:55:19 UTC (rev 16184) @@ -103,18 +103,6 @@ } /** - * Create a DiffieHellmanContext. This will include this side's DH params. - */ - public static DiffieHellmanContext generateContext() { - long time1 = System.currentTimeMillis(); - NativeBigInteger[] params = getParams(); - long time2 = System.currentTimeMillis(); - if((time2 - time1) > 300) { - Logger.error(null, "DiffieHellman.generateContext(): time2 is more than 300ms after time1 ("+(time2 - time1)+ ')'); - } - return new DiffieHellmanContext(params[0], params[1], group); - } - /** * Create a DiffieHellmanLightContext. */ public static DiffieHellmanLightContext generateLightContext() { Deleted: trunk/freenet/src/freenet/crypt/DiffieHellmanContext.java =================================================================== --- trunk/freenet/src/freenet/crypt/DiffieHellmanContext.java 2007-12-01 15:25:47 UTC (rev 16183) +++ trunk/freenet/src/freenet/crypt/DiffieHellmanContext.java 2007-12-01 15:55:19 UTC (rev 16184) @@ -1,106 +0,0 @@ -/* This code is part of Freenet. It is distributed under the GNU General - * Public License, version 2 (or at your option any later version). See - * http://www.gnu.org/ for further details of the GPL. */ - -package freenet.crypt; - -import freenet.crypt.ciphers.Rijndael; -import net.i2p.util.NativeBigInteger; -import freenet.support.HexUtil; -import freenet.support.Logger; - -public class DiffieHellmanContext extends KeyAgreementSchemeContext { - - // Set on startup - /** My exponent. We keep this and then raise our peer's exponential to this power. */ - final NativeBigInteger myExponent; - /** My exponential. This is group.g ^ myExponent mod group.p */ - final NativeBigInteger myExponential; - /** The group we both share */ - final DHGroup group; - - BlockCipher cipher; - byte[] key; - - // Generated or set later - NativeBigInteger peerExponential; - - public String toString() { - StringBuffer sb = new StringBuffer(); - sb.append(super.toString()); - sb.append(": myExponent="); - sb.append(myExponent.toHexString()); - sb.append(", myExponential="); - sb.append(myExponential.toHexString()); - if(peerExponential != null) { - sb.append(", peerExponential="); - sb.append(peerExponential.toHexString()); - } - return sb.toString(); - } - - public DiffieHellmanContext(NativeBigInteger myExponent, NativeBigInteger myExponential, DHGroup group) { - this.myExponent = myExponent; - this.myExponential = myExponential; - this.group = group; - lastUsedTime = System.currentTimeMillis(); - logMINOR = Logger.shouldLog(Logger.MINOR, this); - } - - public synchronized NativeBigInteger getOurExponential() { - lastUsedTime = System.currentTimeMillis(); - return myExponential; - } - - public synchronized byte[] getKey() { - lastUsedTime = System.currentTimeMillis(); - if(key != null) return key; - - // Calculate key - if(logMINOR) - Logger.minor(this, "My exponent: "+myExponent.toHexString()+", my exponential: "+myExponential.toHexString()+", peer's exponential: "+peerExponential.toHexString()); - NativeBigInteger sharedSecret = - (NativeBigInteger) peerExponential.modPow(myExponent, group.getP()); - - key = SHA256.digest(sharedSecret.toByteArray()); - if(logMINOR) - Logger.minor(this, "Key="+HexUtil.bytesToHex(key)); - return key; - } - - public synchronized void setOtherSideExponential(NativeBigInteger a) { - lastUsedTime = System.currentTimeMillis(); - if(peerExponential != null) { - if(!peerExponential.equals(a)) - throw new IllegalStateException("Assigned other side exponential twice"); - else return; - } - if(a == null) throw new NullPointerException(); - peerExponential = a; - } - - /** - * @return True if getCipher() will work. If this returns false, getCipher() will - * probably NPE. - */ - public boolean canGetCipher() { - return peerExponential != null; - } - - public NativeBigInteger getHisExponential() { - return peerExponential; - } - - public synchronized BlockCipher getCipher() { - lastUsedTime = System.currentTimeMillis(); - if(cipher != null) return cipher; - getKey(); - try { - cipher = new Rijndael(256, 256); - } catch (UnsupportedCipherException e1) { - throw new Error(e1); - } - cipher.initialize(key); - return cipher; - } -} Modified: trunk/freenet/src/freenet/node/FNPPacketMangler.java =================================================================== --- trunk/freenet/src/freenet/node/FNPPacketMangler.java 2007-12-01 15:25:47 UTC (rev 16183) +++ trunk/freenet/src/freenet/node/FNPPacketMangler.java 2007-12-01 15:55:19 UTC (rev 16184) @@ -17,7 +17,6 @@ import freenet.crypt.DSAGroup; import freenet.crypt.DSASignature; import freenet.crypt.DiffieHellman; -import freenet.crypt.DiffieHellmanContext; import freenet.crypt.DiffieHellmanLightContext; import freenet.crypt.EntropySource; import freenet.crypt.Global; @@ -362,66 +361,11 @@ if(negType == 0) { Logger.error(this, "Old ephemeral Diffie-Hellman (negType 0) not supported."); return; - }else if (negType == 1) { - // Four stage Diffie-Hellman. 0 = ephemeral, 1 = payload stages are signed (not quite STS) - // FIXME reduce to 3 stages and implement STS properly (we have a separate validation mechanism in PeerNode) - // AFAICS this (with negType=1) is equivalent in security to STS; it expands the second phase into a second and a fourth phase. - // A -> B g^x - // B -> A g^y - // A -> B E^k ( ... ) - // B -> A E^k ( ... ) - - if((packetType < 0) || (packetType > 3)) { - Logger.error(this, "Decrypted auth packet but unknown packet type "+packetType+" from "+replyTo+" possibly from "+pn); - return; - } - - // We keep one DiffieHellmanContext per node ONLY + } else if (negType == 1) { + Logger.error(this, "Old StationToStation (negType 1) not supported."); + return; + } else if (negType==2){ /* - * Now, to the real meat - * Alice, Bob share a base, g, and a modulus, p - * Alice generates a random number r, and: 1: Alice -> Bob: a=g^r - * Bob receives this and generates his own random number, s, and: 2: Bob -> Alice: b=g^s - * Alice receives this, calculates K = b^r, and: 3: Alice -> Bob: E_K ( H(data) data ) - * where data = [ Alice's startup number ] - * Bob does exactly the same as Alice for packet 4. - * - * At this point we are done. - */ - if(packetType == 0) { - // We are Bob - // We need to: - // - Record Alice's a - // - Generate our own s and b - // - Send a type 1 packet back to Alice containing this - - DiffieHellmanContext ctx = - processDHZeroOrOne(0, payload, pn); - if(ctx == null) return; - // Send reply - sendFirstHalfDHPacket(1, negType, ctx.getOurExponential(), pn, replyTo); - // Send a type 1, they will reply with a type 2 - } else if(packetType == 1) { - // We are Alice - DiffieHellmanContext ctx = - processDHZeroOrOne(1, payload, pn); - if(ctx == null) return; - sendSignedDHCompletion(2, ctx.getCipher(), pn, replyTo, ctx); - // Send a type 2 - } else if(packetType == 2) { - // We are Bob - // Receiving a completion packet - // Verify the packet, then complete - // Format: IV E_K ( H(data) data ) - // Where data = [ long: bob's startup number ] - processSignedDHTwoOrThree(2, payload, pn, replyTo, true, oldOpennetPeer); - } else if(packetType == 3) { - // We are Alice - processSignedDHTwoOrThree(3, payload, pn, replyTo, false, oldOpennetPeer); - } - } - else if (negType==2){ - /* * We implement Just Fast Keying key management protocol with active identity protection * for the initiator and no identity protection for the responder * M1: @@ -478,8 +422,7 @@ */ processJFKMessage4(payload, pn, replyTo, oldOpennetPeer); } - } - else { + } else { Logger.error(this, "Decrypted auth packet but unknown negotiation type "+negType+" from "+replyTo+" possibly from "+pn); return; } @@ -1225,89 +1168,6 @@ } /** - * Send a signed DH completion message. - * Format: - * IV - * Signature on { My exponential, his exponential, data } - * Data - * @param phase The packet phase number. Either 2 or 3. - * @param cipher The negotiated cipher. - * @param pn The PeerNode which we are talking to. - * @param replyTo The Peer to which to send the packet (not necessarily the same - * as the one on pn as the IP may have changed). - */ - private void sendSignedDHCompletion(int phase, BlockCipher cipher, PeerNode pn, Peer replyTo, DiffieHellmanContext ctx) { - PCFBMode pcfb = PCFBMode.create(cipher); - byte[] iv = new byte[pcfb.lengthIV()]; - - byte[] myRef = crypto.myCompressedSetupRef(); - byte[] data = new byte[myRef.length + 8]; - System.arraycopy(Fields.longToBytes(node.bootID), 0, data, 0, 8); - System.arraycopy(myRef, 0, data, 8, myRef.length); - byte[] myExp = ctx.getOurExponential().toByteArray(); - byte[] hisExp = ctx.getHisExponential().toByteArray(); - - MessageDigest md = SHA256.getMessageDigest(); - md.update(myExp); - md.update(hisExp); - md.update(data); - byte[] hash = md.digest(); - - DSASignature sig = crypto.sign(hash); - - byte[] r = sig.getRBytes(Node.SIGNATURE_PARAMETER_LENGTH); - byte[] s = sig.getSBytes(Node.SIGNATURE_PARAMETER_LENGTH); - - Logger.minor(this, "Sending DH completion: "+pn+" hash "+HexUtil.bytesToHex(hash)+" r="+HexUtil.bytesToHex(sig.getR().toByteArray())+" s="+HexUtil.bytesToHex(sig.getS().toByteArray())); - - int outputLength = iv.length + data.length + r.length + s.length + 2; - - byte[] output = new byte[outputLength]; - - System.arraycopy(iv, 0, output, 0, iv.length); - int count = iv.length; - if(r.length > 255 || s.length > 255) - throw new IllegalStateException("R or S is too long: r.length="+r.length+" s.length="+s.length); - output[count++] = (byte) r.length; - System.arraycopy(r, 0, output, count, r.length); - count += r.length; - output[count++] = (byte) s.length; - System.arraycopy(s, 0, output, count, s.length); - count += s.length; - System.arraycopy(data, 0, output, count, data.length); - - pcfb.blockEncipher(output, 0, output.length); - - sendAuthPacket(1, 1, phase, output, pn, replyTo); - } - - /** - * Send a first-half (phase 0 or 1) DH negotiation packet to the node. - * @param phase The phase of the message to be sent (0 or 1). - * @param negType The negotiation type. - * @param integer Our exponential - * @param replyTo The peer to reply to - */ - private void sendFirstHalfDHPacket(int phase, int negType, NativeBigInteger integer, PeerNode pn, Peer replyTo) { - long time1 = System.currentTimeMillis(); - if(logMINOR) Logger.minor(this, "Sending ("+phase+") "+integer.toHexString()+" to "+pn.getPeer()); - byte[] data = stripBigIntegerToNetworkFormat(integer); - if(logMINOR) Logger.minor(this, "Processed: "+HexUtil.bytesToHex(data)); - long time2 = System.currentTimeMillis(); - if((time2 - time1) > 200) { - Logger.error(this, "sendFirstHalfDHPacket: time2 is more than 200ms after time1 ("+(time2 - time1)+") working on "+replyTo+" of "+pn.userToString()); - } - sendAuthPacket(1, negType, phase, data, pn, replyTo); - long time3 = System.currentTimeMillis(); - if((time3 - time2) > 500) { - Logger.error(this, "sendFirstHalfDHPacket:sendAuthPacket() time3 is more than half a second after time2 ("+(time3 - time2)+") working on "+replyTo+" of "+pn.userToString()); - } - if((time3 - time1) > 500) { - Logger.error(this, "sendFirstHalfDHPacket: time3 is more than half a second after time1 ("+(time3 - time1)+") working on "+replyTo+" of "+pn.userToString()); - } - } - - /** * Send an auth packet. */ private void sendAuthPacket(int version, int negType, int phase, byte[] data, PeerNode pn, Peer replyTo) { @@ -1369,126 +1229,6 @@ } /** - * Process a stage 2 or stage 3 auth packet. - * Send a signed DH completion message. - * Format: - * IV - * Signature on { My exponential, his exponential, data } - * Data - * - * May decrypt in place. - * @param oldOpennetPeer If true, the peer we are negotiating with is not in - * the primary routing table, it needs to be promoted from the list of old opennet - * nodes. - */ - private DiffieHellmanContext processSignedDHTwoOrThree(int phase, byte[] payload, PeerNode pn, Peer replyTo, boolean sendCompletion, boolean oldOpennetPeer) { - if(logMINOR) Logger.minor(this, "Handling signed stage "+phase+" auth packet"); - // Get context, cipher, IV - DiffieHellmanContext ctx = (DiffieHellmanContext) pn.getKeyAgreementSchemeContext(); - if((ctx == null) || !ctx.canGetCipher()) { - if(shouldLogErrorInHandshake()) { - Logger.error(this, "Cannot get cipher"); - } - return null; - } - byte[] encKey = ctx.getKey(); - BlockCipher cipher = ctx.getCipher(); - PCFBMode pcfb = PCFBMode.create(cipher); - int ivLength = pcfb.lengthIV(); - if(payload.length-3 < HASH_LENGTH + ivLength + 8) { - Logger.error(this, "Too short phase "+phase+" packet from "+replyTo+" probably from "+pn); - return null; - } - pcfb.reset(payload, 3); // IV - - // Decrypt the rest - pcfb.blockDecipher(payload, 3, payload.length - 3); - - int count = 3 + ivLength; - - // R - int rLen = payload[count++] & 0xFF; - if(rLen > pn.getSigParamsByteLength()) { - String msg = "R too long - changed key? Can happen on startup"; - if(node.getUptime() < 15*60*1000) - Logger.minor(this, msg); - else Logger.error(this, msg); - return null; - } - byte[] rBytes = new byte[rLen]; - System.arraycopy(payload, count, rBytes, 0, rLen); - count += rLen; - NativeBigInteger r = new NativeBigInteger(1, rBytes); - - // S - int sLen = payload[count++] & 0xFF; - if(rLen > pn.getSigParamsByteLength()) { - String msg = "S too long - changed key? Can happen on startup"; - if(node.getUptime() < 15*60*1000) - Logger.minor(this, msg); - else Logger.error(this, msg); - return null; - } - byte[] sBytes = new byte[sLen]; - System.arraycopy(payload, count, sBytes, 0, sLen); - count += sLen; - NativeBigInteger s = new NativeBigInteger(1, sBytes); - - DSASignature sig = new DSASignature(r, s); - - // Data - byte[] data = new byte[payload.length - count]; - System.arraycopy(payload, count, data, 0, payload.length - count); - - // Now verify - MessageDigest md = SHA256.getMessageDigest(); - md.update(ctx.getHisExponential().toByteArray()); - md.update(ctx.getOurExponential().toByteArray()); - md.update(data); - byte[] hash = md.digest(); - if(!pn.verify(hash, sig)) { - Logger.error(this, "Signature verification failed for "+pn+" hash "+HexUtil.bytesToHex(hash)+" r="+HexUtil.bytesToHex(sig.getR().toByteArray())+" s="+HexUtil.bytesToHex(sig.getS().toByteArray())); - return null; - } - - // Success! - long bootID = Fields.bytesToLong(data); - - // Promote if necessary - boolean dontWant = false; - if(oldOpennetPeer) { - OpennetManager opennet = node.getOpennet(); - if(opennet == null) { - Logger.normal(this, "Dumping incoming old-opennet peer as opennet just turned off: "+pn+"."); - return null; - } - if(!opennet.wantPeer(pn, true)) { - Logger.normal(this, "No longer want peer "+pn+" - dumping it after connecting"); - dontWant = true; - } - // wantPeer will call node.peers.addPeer(), we don't have to. - } - - // Send the completion before parsing the data, because this is easiest - // Doesn't really matter - if it fails, we get loads of errors anyway... - // Only downside is that the other side might still think we are connected for a while. - // But this should be extremely rare. - // REDFLAG? - // We need to send the completion before the PN sends any packets, that's all... - if(pn.completedHandshake(bootID, data, 8, data.length-8, cipher, encKey, replyTo, phase == 2)) { - if(sendCompletion) - sendSignedDHCompletion(3, ctx.getCipher(), pn, replyTo, ctx); - if(dontWant) - node.peers.disconnect(pn, true, false); - else - pn.maybeSendInitialMessages(); - } else { - Logger.error(this, "Handshake not completed"); - } - return ctx; - } - - /** * Should we log an error for an event that could easily be * caused by a handshake across a restart boundary? */ @@ -1500,50 +1240,6 @@ } /** - * Process a phase-0 or phase-1 Diffie-Hellman packet. - * @return a DiffieHellmanContext if we succeeded, otherwise null. - */ - private DiffieHellmanContext processDHZeroOrOne(int phase, byte[] payload, PeerNode pn) { - - if((phase == 0) && pn.hasLiveHandshake(System.currentTimeMillis())) { - if(logMINOR) Logger.minor(this, "Rejecting phase "+phase+" handshake on "+pn+" - already running one"); - return null; - } - - // First, get the BigInteger - int length = DiffieHellman.modulusLengthInBytes(); - if(payload.length < length + 3) { - Logger.error(this, "Packet too short: "+payload.length+" after decryption in DH("+phase+"), should be "+(length + 3)); - return null; - } - byte[] aAsBytes = new byte[length]; - System.arraycopy(payload, 3, aAsBytes, 0, length); - NativeBigInteger a = new NativeBigInteger(1, aAsBytes); - if(!DiffieHellman.checkDHExponentialValidity(this.getClass(), a)) { - Logger.error(this, "We can't accept the exponential the other end sent us!!"); - return null; - } - DiffieHellmanContext ctx; - if(phase == 1) { - ctx = (DiffieHellmanContext) pn.getKeyAgreementSchemeContext(); - if(ctx == null) { - if(shouldLogErrorInHandshake()) - Logger.error(this, "Could not get context for phase 1 handshake from "+pn); - return null; - } - } else { - ctx = DiffieHellman.generateContext(); - // Don't calculate the key until we need it - pn.setKeyAgreementSchemeContext(ctx); - } - ctx.setOtherSideExponential(a); - if(logMINOR) Logger.minor(this, "His exponential: "+a.toHexString()); - // REDFLAG: This is of course easily DoS'ed if you know the node. - // We will fix this by means of JFKi. - return ctx; - } - - /** * Try to process an incoming packet with a given PeerNode. * We need to know where the packet has come from in order to * decrypt and authenticate it. @@ -2409,7 +2105,6 @@ Logger.normal(this, "Cannot send handshake to "+pn+" because no common negTypes, choosing random negType of "+negType); } if(logMINOR) Logger.minor(this, "Possibly sending handshake to "+pn+" negotiation type "+negType); - DiffieHellmanContext ctx = null; Peer[] handshakeIPs; if(!pn.shouldSendHandshake()) { if(logMINOR) Logger.minor(this, "Not sending handshake to "+pn.getPeer()+" because pn.shouldSendHandshake() returned false"); @@ -2426,13 +2121,6 @@ if((thirdTime - secondTime) > 1000) Logger.error(this, "couldNotSendHandshake() (after getHandshakeIPs()) took more than a second to execute ("+(thirdTime - secondTime)+") working on "+pn.userToString()); return; - } else if(negType < 2){ - long DHTime1 = System.currentTimeMillis(); - ctx = DiffieHellman.generateContext(); - long DHTime2 = System.currentTimeMillis(); - if((DHTime2 - DHTime1) > 1000) - Logger.error(this, "DHTime2 is more than a second after DHTime1 ("+(DHTime2 - DHTime1)+") working on "+pn.userToString()); - pn.setKeyAgreementSchemeContext(ctx); } int sentCount = 0; long loopTime1 = System.currentTimeMillis(); @@ -2451,10 +2139,7 @@ if(logMINOR) Logger.minor(this, "Not sending handshake to "+handshakeIPs[i]+" for "+pn.getPeer()+" because it's not a real Internet address and metadata.allowLocalAddresses is not true"); continue; } - if(negType == 1) - sendFirstHalfDHPacket(0, negType, ctx.getOurExponential(), pn, peer); - else - sendJFKMessage1(pn, peer); + sendJFKMessage1(pn, peer); if(logMINOR) Logger.minor(this, "Sending handshake to "+peer+" for "+pn+" ("+i+" of "+handshakeIPs.length); pn.sentHandshake(); From nextgens at freenetproject.org Sat Dec 1 16:47:41 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 16:47:41 +0000 (UTC) Subject: [freenet-cvs] r16185 - trunk/freenet/src/freenet/node Message-ID: <20071201164741.207344797CD@freenetproject.org> Author: nextgens Date: 2007-12-01 16:47:40 +0000 (Sat, 01 Dec 2007) New Revision: 16185 Modified: trunk/freenet/src/freenet/node/PeerNode.java Log: logging Modified: trunk/freenet/src/freenet/node/PeerNode.java =================================================================== --- trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 15:55:19 UTC (rev 16184) +++ trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 16:47:40 UTC (rev 16185) @@ -2559,7 +2559,7 @@ Logger.minor(this, "Connected, primary tracker deprecated, unverified is valid, " + unverifiedTracker + " for " + this, new Exception("debug")); else { // !!!!!!! - Logger.error(this, "Connected but primary tracker and unverified tracker are null on " + this, new Exception("debug")); + Logger.error(this, "Connected but primary tracker is deprecated and unverified tracker is null on " + this, new Exception("debug")); isConnected = false; } } From toad at freenetproject.org Sat Dec 1 16:56:30 2007 From: toad at freenetproject.org (toad at freenetproject.org) Date: Sat, 1 Dec 2007 16:56:30 +0000 (UTC) Subject: [freenet-cvs] r16186 - trunk/freenet/src/freenet/io/comm Message-ID: <20071201165630.1D31A47AE7D@freenetproject.org> Author: toad Date: 2007-12-01 16:56:29 +0000 (Sat, 01 Dec 2007) New Revision: 16186 Modified: trunk/freenet/src/freenet/io/comm/DMT.java Log: Make comments final, include a code-to-string method Modified: trunk/freenet/src/freenet/io/comm/DMT.java =================================================================== --- trunk/freenet/src/freenet/io/comm/DMT.java 2007-12-01 16:47:40 UTC (rev 16185) +++ trunk/freenet/src/freenet/io/comm/DMT.java 2007-12-01 16:56:29 UTC (rev 16186) @@ -857,11 +857,26 @@ return msg; } - public static int NODEREF_REJECTED_TOO_BIG = 1; - public static int NODEREF_REJECTED_REAL_BIGGER_THAN_PADDED = 2; - public static int NODEREF_REJECTED_TRANSFER_FAILED = 3; - public static int NODEREF_REJECTED_INVALID = 4; + public static String getOpennetRejectedCode(int x) { + switch(x) { + case NODEREF_REJECTED_TOO_BIG: + return "Too big"; + case NODEREF_REJECTED_REAL_BIGGER_THAN_PADDED: + return "Real length bigger than padded length"; + case NODEREF_REJECTED_TRANSFER_FAILED: + return "Transfer failed"; + case NODEREF_REJECTED_INVALID: + return "Invalid noderef"; + default: + return "Unknown rejection code "+x; + } + } + public static final int NODEREF_REJECTED_TOO_BIG = 1; + public static final int NODEREF_REJECTED_REAL_BIGGER_THAN_PADDED = 2; + public static final int NODEREF_REJECTED_TRANSFER_FAILED = 3; + public static final int NODEREF_REJECTED_INVALID = 4; + // Key offers (ULPRs) public static MessageType FNPOfferKey = new MessageType("FNPOfferKey") {{ From toad at freenetproject.org Sat Dec 1 16:57:29 2007 From: toad at freenetproject.org (toad at freenetproject.org) Date: Sat, 1 Dec 2007 16:57:29 +0000 (UTC) Subject: [freenet-cvs] r16187 - trunk/freenet/src/freenet/node Message-ID: <20071201165729.CF2A2479818@freenetproject.org> Author: toad Date: 2007-12-01 16:57:29 +0000 (Sat, 01 Dec 2007) New Revision: 16187 Modified: trunk/freenet/src/freenet/node/OpennetManager.java Log: Refactor the actual sending into another method Modified: trunk/freenet/src/freenet/node/OpennetManager.java =================================================================== --- trunk/freenet/src/freenet/node/OpennetManager.java 2007-12-01 16:56:29 UTC (rev 16186) +++ trunk/freenet/src/freenet/node/OpennetManager.java 2007-12-01 16:57:29 UTC (rev 16187) @@ -478,6 +478,18 @@ Message msg2 = isReply ? DMT.createFNPOpennetConnectReplyNew(uid, xferUID, noderef.length, padded.length) : DMT.createFNPOpennetConnectDestinationNew(uid, xferUID, noderef.length, padded.length); peer.sendAsync(msg2, null, 0, ctr); + innerSendOpennetRef(xferUID, padded, peer); + } + + /** + * Just the actual transfer. + * @param xferUID The transfer UID + * @param padded The length of the data to transfer. + * @param peer The peer to send it to. + * @throws NotConnectedException If the peer is not connected, or we lose the connection to the peer, + * or it restarts. + */ + private void innerSendOpennetRef(long xferUID, byte[] padded, PeerNode peer) throws NotConnectedException { ByteArrayRandomAccessThing raf = new ByteArrayRandomAccessThing(padded); raf.setReadOnly(); PartiallyReceivedBulk prb = From toad at freenetproject.org Sat Dec 1 17:00:15 2007 From: toad at freenetproject.org (toad at freenetproject.org) Date: Sat, 1 Dec 2007 17:00:15 +0000 (UTC) Subject: [freenet-cvs] r16188 - trunk/freenet/src/freenet/node Message-ID: <20071201170015.B55D847AE7D@freenetproject.org> Author: toad Date: 2007-12-01 17:00:15 +0000 (Sat, 01 Dec 2007) New Revision: 16188 Modified: trunk/freenet/src/freenet/node/OpennetManager.java Log: Add sendAnnouncementRequest() method Modified: trunk/freenet/src/freenet/node/OpennetManager.java =================================================================== --- trunk/freenet/src/freenet/node/OpennetManager.java 2007-12-01 16:57:29 UTC (rev 16187) +++ trunk/freenet/src/freenet/node/OpennetManager.java 2007-12-01 17:00:15 UTC (rev 16188) @@ -503,6 +503,21 @@ } } + public void sendAnnouncementRequest(long uid, PeerNode peer, byte[] noderef, ByteCounter ctr, + double target, short htl, double nearestLocSoFar) throws NotConnectedException { + byte[] padded = new byte[PADDED_NODEREF_SIZE]; + if(noderef.length > padded.length) { + Logger.error(this, "Noderef too big: "+noderef.length+" bytes"); + return; + } + System.arraycopy(noderef, 0, padded, 0, noderef.length); + long xferUID = node.random.nextLong(); + Message msg = DMT.createFNPOpennetAnnounceRequest(uid, xferUID, noderef.length, + padded.length, target, htl, nearestLocSoFar); + peer.sendAsync(msg, null, 0, ctr); + innerSendOpennetRef(xferUID, padded, peer); + } + /** * Wait for an opennet noderef. * @param isReply If true, wait for an FNPOpennetConnectReply[New], if false wait for an FNPOpennetConnectDestination[New]. From nextgens at freenetproject.org Sat Dec 1 17:00:49 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 17:00:49 +0000 (UTC) Subject: [freenet-cvs] r16189 - trunk/freenet/src/freenet/node Message-ID: <20071201170049.DF34747B2D8@freenetproject.org> Author: nextgens Date: 2007-12-01 17:00:49 +0000 (Sat, 01 Dec 2007) New Revision: 16189 Modified: trunk/freenet/src/freenet/node/FNPPacketMangler.java Log: JFK: block message3 processing if we are already connected with a fresh handshake Modified: trunk/freenet/src/freenet/node/FNPPacketMangler.java =================================================================== --- trunk/freenet/src/freenet/node/FNPPacketMangler.java 2007-12-01 17:00:15 UTC (rev 16188) +++ trunk/freenet/src/freenet/node/FNPPacketMangler.java 2007-12-01 17:00:49 UTC (rev 16189) @@ -733,7 +733,9 @@ if(!mac.verify(getTransientKey(), assembleJFKAuthenticator(responderExponential, initiatorExponential, nonceResponder, nonceInitiator, replyTo.getAddress().getAddress()) , authenticator)) { Logger.error(this, "The HMAC doesn't match; let's discard the packet (either we rekeyed or we are victim of forgery)"); return; - } + } else if(pn.isConnected() && !pn.firstHandshake) + return; + // Check try to find the authenticator in the cache. // If authenticator is already present, indicates duplicate/replayed message3 // Now simply transmit the corresponding message4 From toad at freenetproject.org Sat Dec 1 17:14:09 2007 From: toad at freenetproject.org (toad at freenetproject.org) Date: Sat, 1 Dec 2007 17:14:09 +0000 (UTC) Subject: [freenet-cvs] r16190 - trunk/freenet/src/freenet/node Message-ID: <20071201171409.87D4D391E29@freenetproject.org> Author: toad Date: 2007-12-01 17:14:09 +0000 (Sat, 01 Dec 2007) New Revision: 16190 Added: trunk/freenet/src/freenet/node/AnnounceSender.java Modified: trunk/freenet/src/freenet/node/Node.java trunk/freenet/src/freenet/node/NodeDispatcher.java trunk/freenet/src/freenet/node/OpennetManager.java trunk/freenet/src/freenet/node/PeerNode.java Log: Opennet announcement. Untested. Added: trunk/freenet/src/freenet/node/AnnounceSender.java =================================================================== --- trunk/freenet/src/freenet/node/AnnounceSender.java (rev 0) +++ trunk/freenet/src/freenet/node/AnnounceSender.java 2007-12-01 17:14:09 UTC (rev 16190) @@ -0,0 +1,392 @@ +package freenet.node; + +import java.util.HashSet; + +import freenet.io.comm.ByteCounter; +import freenet.io.comm.DMT; +import freenet.io.comm.DisconnectedException; +import freenet.io.comm.Message; +import freenet.io.comm.MessageFilter; +import freenet.io.comm.NotConnectedException; +import freenet.io.comm.PeerParseException; +import freenet.io.comm.ReferenceSignatureVerificationException; +import freenet.support.Logger; +import freenet.support.SimpleFieldSet; + +public class AnnounceSender implements Runnable, ByteCounter { + + // Constants + static final int ACCEPTED_TIMEOUT = 5000; + static final int ANNOUNCE_TIMEOUT = 240000; // longer than a regular request as have to transfer noderefs hop by hop etc + + private final PeerNode source; + private final long uid; + private final OpennetManager om; + private final Node node; + private Message msg; + private byte[] noderefBuf; + private int noderefLength; + private short htl; + private double nearestLoc; + private double target; + private static boolean logMINOR; + + public AnnounceSender(Message m, long uid, PeerNode source, OpennetManager om, Node node) { + this.source = source; + this.uid = uid; + this.msg = m; + this.om = om; + this.node = node; + htl = m.getShort(DMT.HTL); + target = m.getDouble(DMT.TARGET_LOCATION); // FIXME validate + logMINOR = Logger.shouldLog(Logger.MINOR, this); + } + + public void run() { + try { + realRun(); + } catch (Throwable t) { + Logger.error(this, "Caught "+t+" announcing "+uid+" from "+source, t); + } finally { + source.completedAnnounce(uid); + source.node.completed(uid); + } + } + + private void realRun() { + boolean hasForwarded = false; + try { + source.sendAsync(DMT.createFNPAccepted(uid), null, 0, null); + } catch (NotConnectedException e) { + return; + } + if(source != null) { + if(!transferNoderef()) return; + } + + double myLoc = node.lm.getLocation(); + if(Location.distance(target, myLoc) < Location.distance(target, nearestLoc)) { + nearestLoc = myLoc; + htl = node.maxHTL(); + } else { + if(source != null) + htl = node.decrementHTL(source, htl); + } + + // Now route it. + + HashSet nodesRoutedTo = new HashSet(); + HashSet nodesNotIgnored = new HashSet(); + while(true) { + if(logMINOR) Logger.minor(this, "htl="+htl); + if(htl == 0) { + // No more nodes. + complete(); + return; + } + + // Route it + PeerNode next; + next = node.peers.closerPeer(source, nodesRoutedTo, nodesNotIgnored, target, true, node.isAdvancedModeEnabled(), -1, null); + + if(next == null) { + // Backtrack + rnf(); + return; + } + if(logMINOR) Logger.minor(this, "Routing request to "+next); + nodesRoutedTo.add(next); + + if(hasForwarded) + htl = node.decrementHTL(source, htl); + + if(!sendTo(next)) continue; + + hasForwarded = true; + + Message msg = null; + + while(true) { + + /** + * What are we waiting for? + * FNPAccepted - continue + * FNPRejectedLoop - go to another node + * FNPRejectedOverload - go to another node + */ + + MessageFilter mfAccepted = MessageFilter.create().setSource(next).setField(DMT.UID, uid).setTimeout(ACCEPTED_TIMEOUT).setType(DMT.FNPAccepted); + MessageFilter mfRejectedLoop = MessageFilter.create().setSource(next).setField(DMT.UID, uid).setTimeout(ACCEPTED_TIMEOUT).setType(DMT.FNPRejectedLoop); + MessageFilter mfRejectedOverload = MessageFilter.create().setSource(next).setField(DMT.UID, uid).setTimeout(ACCEPTED_TIMEOUT).setType(DMT.FNPRejectedOverload); + MessageFilter mfOpennetDisabled = MessageFilter.create().setSource(next).setField(DMT.UID, uid).setTimeout(ACCEPTED_TIMEOUT).setType(DMT.FNPOpennetDisabled); + MessageFilter mfOpennetNoderefRejected = MessageFilter.create().setSource(next).setField(DMT.UID, uid).setTimeout(ACCEPTED_TIMEOUT).setType(DMT.FNPOpennetNoderefRejected); + + // mfRejectedOverload must be the last thing in the or + // So its or pointer remains null + // Otherwise we need to recreate it below + MessageFilter mf = mfAccepted.or(mfRejectedLoop.or(mfRejectedOverload.or(mfOpennetDisabled.or(mfOpennetNoderefRejected)))); + + try { + msg = node.usm.waitFor(mf, this); + if(logMINOR) Logger.minor(this, "first part got "+msg); + } catch (DisconnectedException e) { + Logger.normal(this, "Disconnected from "+next+" while waiting for Accepted on "+uid); + break; + } + + if(msg == null) { + if(logMINOR) Logger.minor(this, "Timeout waiting for Accepted"); + // Try next node + msg = null; + break; + } + + if(msg.getSpec() == DMT.FNPRejectedLoop) { + if(logMINOR) Logger.minor(this, "Rejected loop"); + // Find another node to route to + msg = null; + break; + } + + if(msg.getSpec() == DMT.FNPRejectedOverload) { + if(logMINOR) Logger.minor(this, "Rejected: overload"); + // Give up on this one, try another + msg = null; + break; + } + + if(msg.getSpec() == DMT.FNPOpennetDisabled) { + source.setOpennetDisabled(); + msg = null; + break; + } + + if(msg.getSpec() == DMT.FNPOpennetNoderefRejected) { + int reason = msg.getInt(DMT.REJECT_CODE); + Logger.normal(this, "Announce rejected by "+source+" : "+DMT.getOpennetRejectedCode(reason)); + msg = null; + break; + } + + if(msg.getSpec() != DMT.FNPAccepted) { + Logger.error(this, "Unrecognized message: "+msg); + continue; + } + + break; + } + + if((msg == null) || (msg.getSpec() != DMT.FNPAccepted)) { + // Try another node + continue; + } + + if(logMINOR) Logger.minor(this, "Got Accepted"); + + // Otherwise, must be Accepted + + // So wait... + + while(true) { + + MessageFilter mfAnnounceCompleted = MessageFilter.create().setSource(next).setField(DMT.UID, uid).setTimeout(ANNOUNCE_TIMEOUT).setType(DMT.FNPOpennetAnnounceCompleted); + MessageFilter mfRouteNotFound = MessageFilter.create().setSource(next).setField(DMT.UID, uid).setTimeout(ANNOUNCE_TIMEOUT).setType(DMT.FNPRouteNotFound); + MessageFilter mfRejectedOverload = MessageFilter.create().setSource(next).setField(DMT.UID, uid).setTimeout(ANNOUNCE_TIMEOUT).setType(DMT.FNPRejectedOverload); + MessageFilter mfAnnounceReply = MessageFilter.create().setSource(next).setField(DMT.UID, uid).setTimeout(ANNOUNCE_TIMEOUT).setType(DMT.FNPOpennetAnnounceReply); + MessageFilter mfOpennetDisabled = MessageFilter.create().setSource(next).setField(DMT.UID, uid).setTimeout(ANNOUNCE_TIMEOUT).setType(DMT.FNPOpennetDisabled); + MessageFilter mf = mfAnnounceCompleted.or(mfRouteNotFound.or(mfRejectedOverload.or(mfAnnounceReply.or(mfOpennetDisabled)))); + + try { + msg = node.usm.waitFor(mf, this); + } catch (DisconnectedException e) { + Logger.normal(this, "Disconnected from "+next+" while waiting for announcement"); + break; + } + + if(logMINOR) Logger.minor(this, "second part got "+msg); + + if(msg == null) { + // Fatal timeout + timedOut(); + return; + } + + if(msg.getSpec() == DMT.FNPOpennetAnnounceCompleted) { + complete(); + return; + } + + if(msg.getSpec() == DMT.FNPRouteNotFound) { + // Backtrack within available hops + short newHtl = msg.getShort(DMT.HTL); + if(newHtl < htl) htl = newHtl; + break; + } + + if(msg.getSpec() == DMT.FNPRejectedOverload) { + // Give up on this one, try another + break; + } + + if(msg.getSpec() == DMT.FNPOpennetDisabled) { + source.setOpennetDisabled(); + msg = null; + break; + } + + if(msg.getSpec() == DMT.FNPOpennetAnnounceReply) { + validateForwardReply(msg, next); + continue; // There may be more + } + + Logger.error(this, "Unexpected message: "+msg); + } + } + } + + /** + * Validate a reply, and relay it back to the source. + * @param msg2 The AnnouncementReply message. + * @return True unless we lost the connection to our request source. + */ + private boolean validateForwardReply(Message msg, PeerNode source) { + long xferUID = msg.getLong(DMT.TRANSFER_UID); + int noderefLength = msg.getInt(DMT.NODEREF_LENGTH); + int paddedLength = msg.getInt(DMT.PADDED_LENGTH); + byte[] noderefBuf = om.innerWaitForOpennetNoderef(xferUID, paddedLength, noderefLength, source, false, uid, true, this); + if(noderefBuf == null) { + return true; // Don't relay + } + SimpleFieldSet fs = om.validateNoderef(noderefBuf, 0, noderefLength, source); + if(fs == null) { + om.rejectRef(uid, source, DMT.NODEREF_REJECTED_INVALID, this); + return true; // Don't relay + } + // Now relay it + try { + om.sendAnnouncementReply(uid, source, noderefBuf, this); + } catch (NotConnectedException e) { + // Hmmm...! + return false; + } + return true; + } + + /** + * Send an AnnouncementRequest. + * @param next The node to send the announcement to. + * @return True if the announcement was successfully sent. + */ + private boolean sendTo(PeerNode next) { + try { + om.sendAnnouncementRequest(uid, next, noderefBuf, this, target, htl, nearestLoc); + } catch (NotConnectedException e) { + if(logMINOR) Logger.minor(this, "Disconnected"); + return false; + } + return true; + } + + private void timedOut() { + Message msg = DMT.createFNPRejectedOverload(uid, false); + try { + source.sendAsync(msg, null, 0, this); + } catch (NotConnectedException e) { + // Ok + } + } + + private void rnf() { + Message msg = DMT.createFNPRouteNotFound(uid, htl); + try { + source.sendAsync(msg, null, 0, this); + } catch (NotConnectedException e) { + // Ok + } + } + + private void complete() { + Message msg = DMT.createFNPOpennetAnnounceCompleted(uid); + try { + source.sendAsync(msg, null, 0, this); + } catch (NotConnectedException e) { + // Oh well. + } + } + + /** + * @return True unless the noderef is bogus. + */ + private boolean transferNoderef() { + long xferUID = msg.getLong(DMT.TRANSFER_UID); + noderefLength = msg.getInt(DMT.NODEREF_LENGTH); + int paddedLength = msg.getInt(DMT.PADDED_LENGTH); + noderefBuf = om.innerWaitForOpennetNoderef(xferUID, paddedLength, noderefLength, source, false, uid, true, this); + if(noderefBuf == null) { + return false; + } + SimpleFieldSet fs = om.validateNoderef(noderefBuf, 0, noderefLength, source); + if(fs == null) { + om.rejectRef(uid, source, DMT.NODEREF_REJECTED_INVALID, this); + return false; + } + // If we want it, add it and send it. + try { + if(om.addNewOpennetNode(fs)) { + sendOurRef(); + } else { + // Okay, just route it. + } + } catch (FSParseException e) { + om.rejectRef(uid, source, DMT.NODEREF_REJECTED_INVALID, this); + return false; + } catch (PeerParseException e) { + om.rejectRef(uid, source, DMT.NODEREF_REJECTED_INVALID, this); + return false; + } catch (ReferenceSignatureVerificationException e) { + om.rejectRef(uid, source, DMT.NODEREF_REJECTED_INVALID, this); + return false; + } + return true; + } + + private void sendOurRef() { + // FIXME transmit our noderef back to the node + // TODO Auto-generated method stub + + } + + private volatile Object totalBytesSync = new Object(); + private int totalBytesSent; + + public void sentBytes(int x) { + synchronized(totalBytesSync) { + totalBytesSent += x; + } + } + + public int getTotalSentBytes() { + synchronized(totalBytesSync) { + return totalBytesSent; + } + } + + private int totalBytesReceived; + + public void receivedBytes(int x) { + synchronized(totalBytesSync) { + totalBytesReceived += x; + } + } + + public int getTotalReceivedBytes() { + synchronized(totalBytesSync) { + return totalBytesReceived; + } + } + + public void sentPayload(int x) { + // Doesn't count. + } + +} Modified: trunk/freenet/src/freenet/node/Node.java =================================================================== --- trunk/freenet/src/freenet/node/Node.java 2007-12-01 17:00:49 UTC (rev 16189) +++ trunk/freenet/src/freenet/node/Node.java 2007-12-01 17:14:09 UTC (rev 16190) @@ -2224,7 +2224,7 @@ /** * A request completed (regardless of success). */ - private synchronized void completed(long id) { + synchronized void completed(long id) { recentlyCompletedIDs.push(new Long(id)); while(recentlyCompletedIDs.size() > MAX_RECENTLY_COMPLETED_IDS) recentlyCompletedIDs.pop(); Modified: trunk/freenet/src/freenet/node/NodeDispatcher.java =================================================================== --- trunk/freenet/src/freenet/node/NodeDispatcher.java 2007-12-01 17:00:49 UTC (rev 16189) +++ trunk/freenet/src/freenet/node/NodeDispatcher.java 2007-12-01 17:14:09 UTC (rev 16190) @@ -97,6 +97,8 @@ return node.nodeUpdater.uom.handleRequestMain(m, source); } else if(spec == DMT.UOMSendingMain) { return node.nodeUpdater.uom.handleSendingMain(m, source); + } else if(spec == DMT.FNPOpennetAnnounceRequest) { + return handleAnnounceRequest(m, source); } if(!source.isRoutable()) return false; @@ -141,7 +143,7 @@ // return handleProbeRejected(m, source); // } else if(spec == DMT.FNPProbeTrace) { // return handleProbeTrace(m, source); - } + } return false; } @@ -265,6 +267,49 @@ return true; } + private boolean handleAnnounceRequest(Message m, PeerNode source) { + long uid = m.getLong(DMT.UID); + OpennetManager om = node.getOpennet(); + if(om == null) { + Message msg = DMT.createFNPOpennetDisabled(uid); + try { + source.sendAsync(msg, null, 0, null); + } catch (NotConnectedException e) { + // Ok + } + return true; + } + if(node.recentlyCompleted(uid)) { + Message msg = DMT.createFNPRejectedLoop(uid); + try { + source.sendAsync(msg, null, 0, null); + } catch (NotConnectedException e) { + // Ok + } + return true; + } + boolean success = false; + try { + if(!source.shouldAcceptAnnounce(uid)) { + node.completed(uid); + Message msg = DMT.createFNPRejectedOverload(uid, true); + try { + source.sendAsync(msg, null, 0, null); + } catch (NotConnectedException e) { + // Ok + } + return true; + } + AnnounceSender sender = new AnnounceSender(m, uid, source, om, node); + node.executor.execute(sender, "Announcement sender for "+uid); + success = true; + return true; + } finally { + if(!success) + source.completedAnnounce(uid); + } + } + final Hashtable routedContexts = new Hashtable(); static class RoutedContext { Modified: trunk/freenet/src/freenet/node/OpennetManager.java =================================================================== --- trunk/freenet/src/freenet/node/OpennetManager.java 2007-12-01 17:00:49 UTC (rev 16189) +++ trunk/freenet/src/freenet/node/OpennetManager.java 2007-12-01 17:14:09 UTC (rev 16190) @@ -518,6 +518,21 @@ innerSendOpennetRef(xferUID, padded, peer); } + public void sendAnnouncementReply(long uid, PeerNode peer, byte[] noderef, ByteCounter ctr) + throws NotConnectedException { + byte[] padded = new byte[PADDED_NODEREF_SIZE]; + if(noderef.length > padded.length) { + Logger.error(this, "Noderef too big: "+noderef.length+" bytes"); + return; + } + System.arraycopy(noderef, 0, padded, 0, noderef.length); + long xferUID = node.random.nextLong(); + Message msg = DMT.createFNPOpennetAnnounceReply(uid, xferUID, noderef.length, + padded.length); + peer.sendAsync(msg, null, 0, ctr); + innerSendOpennetRef(xferUID, padded, peer); + } + /** * Wait for an opennet noderef. * @param isReply If true, wait for an FNPOpennetConnectReply[New], if false wait for an FNPOpennetConnectDestination[New]. Modified: trunk/freenet/src/freenet/node/PeerNode.java =================================================================== --- trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 17:00:49 UTC (rev 16189) +++ trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 17:14:09 UTC (rev 16190) @@ -266,6 +266,7 @@ final WeakReference myRef; /** The node is being disconnected, but it may take a while. */ private boolean disconnecting; + /** * For FNP link setup: * The initiator has to ensure that nonces send back by the @@ -3038,4 +3039,47 @@ synchronized boolean manyPacketsClaimedSentNotReceived() { return manyPacketsClaimedSentNotReceived; } + + static final int MAX_SIMULTANEOUS_ANNOUNCEMENTS = 1; + static final int MAX_ANNOUNCE_DELAY = 1000; + private long timeLastAcceptedAnnouncement; + private long[] runningAnnounceUIDs = new long[0]; + + public synchronized boolean shouldAcceptAnnounce(long uid) { + long now = System.currentTimeMillis(); + if(runningAnnounceUIDs.length < MAX_SIMULTANEOUS_ANNOUNCEMENTS && + now - timeLastAcceptedAnnouncement > MAX_ANNOUNCE_DELAY) { + long[] newList = new long[runningAnnounceUIDs.length + 1]; + if(runningAnnounceUIDs.length > 0) + System.arraycopy(runningAnnounceUIDs, 0, newList, 0, runningAnnounceUIDs.length); + newList[runningAnnounceUIDs.length] = uid; + timeLastAcceptedAnnouncement = now; + return true; + } else { + return false; + } + } + + public synchronized boolean completedAnnounce(long uid) { + if(runningAnnounceUIDs.length == 0) return false; + long[] newList = new long[runningAnnounceUIDs.length - 1]; + int x = 0; + for(int i=0;i Author: nextgens Date: 2007-12-01 17:21:06 +0000 (Sat, 01 Dec 2007) New Revision: 16191 Modified: trunk/freenet/src/freenet/node/FNPPacketMangler.java Log: JFK: block message4 too... it doesn't help though :/ Modified: trunk/freenet/src/freenet/node/FNPPacketMangler.java =================================================================== --- trunk/freenet/src/freenet/node/FNPPacketMangler.java 2007-12-01 17:14:09 UTC (rev 16190) +++ trunk/freenet/src/freenet/node/FNPPacketMangler.java 2007-12-01 17:21:06 UTC (rev 16191) @@ -898,7 +898,8 @@ if(!mac.verify(pn.jfkKa, decypheredPayload, hmac)) { Logger.error(this, "The digest-HMAC doesn't match; let's discard the packet"); return; - } + }else if(pn.isConnected() && !pn.firstHandshake) + return; // Get the IV pk.reset(decypheredPayload, decypheredPayloadOffset); From nextgens at freenetproject.org Sat Dec 1 17:29:52 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 17:29:52 +0000 (UTC) Subject: [freenet-cvs] r16192 - trunk/freenet/src/freenet/node Message-ID: <20071201172952.B3BE2391E4E@freenetproject.org> Author: nextgens Date: 2007-12-01 17:29:52 +0000 (Sat, 01 Dec 2007) New Revision: 16192 Modified: trunk/freenet/src/freenet/node/FNPPacketMangler.java Log: JFK: revert r16191 and r16189 : they are a few cases I can think of where we want to accept incoming handshakes even if we didn't send any out Modified: trunk/freenet/src/freenet/node/FNPPacketMangler.java =================================================================== --- trunk/freenet/src/freenet/node/FNPPacketMangler.java 2007-12-01 17:21:06 UTC (rev 16191) +++ trunk/freenet/src/freenet/node/FNPPacketMangler.java 2007-12-01 17:29:52 UTC (rev 16192) @@ -733,9 +733,7 @@ if(!mac.verify(getTransientKey(), assembleJFKAuthenticator(responderExponential, initiatorExponential, nonceResponder, nonceInitiator, replyTo.getAddress().getAddress()) , authenticator)) { Logger.error(this, "The HMAC doesn't match; let's discard the packet (either we rekeyed or we are victim of forgery)"); return; - } else if(pn.isConnected() && !pn.firstHandshake) - return; - + } // Check try to find the authenticator in the cache. // If authenticator is already present, indicates duplicate/replayed message3 // Now simply transmit the corresponding message4 @@ -898,9 +896,7 @@ if(!mac.verify(pn.jfkKa, decypheredPayload, hmac)) { Logger.error(this, "The digest-HMAC doesn't match; let's discard the packet"); return; - }else if(pn.isConnected() && !pn.firstHandshake) - return; - + } // Get the IV pk.reset(decypheredPayload, decypheredPayloadOffset); decypheredPayloadOffset += ivLength; From toad at freenetproject.org Sat Dec 1 18:45:27 2007 From: toad at freenetproject.org (toad at freenetproject.org) Date: Sat, 1 Dec 2007 18:45:27 +0000 (UTC) Subject: [freenet-cvs] r16194 - trunk/freenet/src/freenet/node Message-ID: <20071201184527.760124797B8@freenetproject.org> Author: toad Date: 2007-12-01 18:45:27 +0000 (Sat, 01 Dec 2007) New Revision: 16194 Modified: trunk/freenet/src/freenet/node/PeerNode.java Log: Fix rekey logic: disconnect after the timeout after a rekey due to transferred bytes, as well as after a scheduled rekey Modified: trunk/freenet/src/freenet/node/PeerNode.java =================================================================== --- trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 18:41:30 UTC (rev 16193) +++ trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 18:45:27 UTC (rev 16194) @@ -909,7 +909,11 @@ timeWhenRekeyingShouldOccur = timeLastRekeyed + FNPPacketMangler.SESSION_KEY_REKEYING_INTERVAL; shouldDisconnect = (timeWhenRekeyingShouldOccur + FNPPacketMangler.MAX_SESSION_KEY_REKEYING_DELAY < now) && isRekeying; shouldReturn = isRekeying || !isConnected; - shouldRekey = (timeWhenRekeyingShouldOccur < now) || (totalBytesExchangedWithCurrentTracker > FNPPacketMangler.AMOUNT_OF_BYTES_ALLOWED_BEFORE_WE_REKEY); + shouldRekey = (timeWhenRekeyingShouldOccur < now); + if((!shouldRekey) && totalBytesExchangedWithCurrentTracker > FNPPacketMangler.AMOUNT_OF_BYTES_ALLOWED_BEFORE_WE_REKEY) { + shouldRekey = true; + timeWhenRekeyingShouldOccur = now; + } } if(shouldDisconnect) { From toad at freenetproject.org Sat Dec 1 19:12:21 2007 From: toad at freenetproject.org (toad at freenetproject.org) Date: Sat, 1 Dec 2007 19:12:21 +0000 (UTC) Subject: [freenet-cvs] r16196 - trunk/freenet/src/freenet/node Message-ID: <20071201191221.DDFA64790AE@freenetproject.org> Author: toad Date: 2007-12-01 19:12:21 +0000 (Sat, 01 Dec 2007) New Revision: 16196 Modified: trunk/freenet/src/freenet/node/PeerNode.java Log: Maybe fix connected but both primary and unverified null message Modified: trunk/freenet/src/freenet/node/PeerNode.java =================================================================== --- trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 18:48:12 UTC (rev 16195) +++ trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 19:12:21 UTC (rev 16196) @@ -1518,6 +1518,8 @@ if(previousTracker == null) previousTracker = unverifiedTracker; unverifiedTracker = newTracker; + if(currentTracker == null || currentTracker.isDeprecated()) + isConnected = false; } else { prev = currentTracker; previousTracker = prev; From nextgens at freenetproject.org Sat Dec 1 22:02:03 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 22:02:03 +0000 (UTC) Subject: [freenet-cvs] r16197 - trunk/freenet/src/freenet/clients/http/bookmark Message-ID: <20071201220203.1B17147B740@freenetproject.org> Author: nextgens Date: 2007-12-01 22:02:02 +0000 (Sat, 01 Dec 2007) New Revision: 16197 Modified: trunk/freenet/src/freenet/clients/http/bookmark/Bookmark.java Log: indent Modified: trunk/freenet/src/freenet/clients/http/bookmark/Bookmark.java =================================================================== --- trunk/freenet/src/freenet/clients/http/bookmark/Bookmark.java 2007-12-01 19:12:21 UTC (rev 16196) +++ trunk/freenet/src/freenet/clients/http/bookmark/Bookmark.java 2007-12-01 22:02:02 UTC (rev 16197) @@ -16,7 +16,7 @@ public boolean equals(Object o) { if (o == this) { - return true; + return true; } if (o instanceof Bookmark) { Bookmark b = (Bookmark) o; From svn-build at freenetproject.org Sat Dec 1 22:05:25 2007 From: svn-build at freenetproject.org (svn-build at freenetproject.org) Date: Sat, 1 Dec 2007 22:05:25 +0000 (UTC) Subject: [freenet-cvs] Verification of r16197 on emu Message-ID: <20071201220525.8292047B76C@freenetproject.org> The commit 16197 has been declared to be an 'indent only' commit. That's TRUE. freenet/clients/http/bookmark/Bookmark.class : 863b0c5efdb9cab16117054e744e70e0276b5b8e From nextgens at freenetproject.org Sat Dec 1 22:06:20 2007 From: nextgens at freenetproject.org (nextgens at freenetproject.org) Date: Sat, 1 Dec 2007 22:06:20 +0000 (UTC) Subject: [freenet-cvs] r16198 - trunk/freenet/src/freenet/clients/http/bookmark Message-ID: <20071201220620.74C9E47B775@freenetproject.org> Author: nextgens Date: 2007-12-01 22:06:20 +0000 (Sat, 01 Dec 2007) New Revision: 16198 Modified: trunk/freenet/src/freenet/clients/http/bookmark/Bookmark.java Log: indent Modified: trunk/freenet/src/freenet/clients/http/bookmark/Bookmark.java =================================================================== --- trunk/freenet/src/freenet/clients/http/bookmark/Bookmark.java 2007-12-01 22:02:02 UTC (rev 16197) +++ trunk/freenet/src/freenet/clients/http/bookmark/Bookmark.java 2007-12-01 22:06:20 UTC (rev 16198) @@ -15,9 +15,8 @@ } public boolean equals(Object o) { - if (o == this) { + if (o == this) return true; - } if (o instanceof Bookmark) { Bookmark b = (Bookmark) o; if (!b.name.equals(name)) { From svn-build at freenetproject.org Sat Dec 1 22:08:19 2007 From: svn-build at freenetproject.org (svn-build at freenetproject.org) Date: Sat, 1 Dec 2007 22:08:19 +0000 (UTC) Subject: [freenet-cvs] Verification of r16198 on emu Message-ID: <20071201220819.74F083A0558@freenetproject.org> The commit 16198 has been declared to be an 'indent only' commit. That's FALSE. freenet/clients/http/bookmark/Bookmark.class : 7764669f81580ae93cc9497470bc08aa7d12759b should be 863b0c5efdb9cab16117054e744e70e0276b5b8e From svn-build at freenetproject.org Sat Dec 1 22:08:20 2007 From: svn-build at freenetproject.org (svn-build at freenetproject.org) Date: Sat, 1 Dec 2007 22:08:20 +0000 (UTC) Subject: [freenet-cvs] Verification of r16198 on emu Message-ID: <20071201220820.09A1547B772@freenetproject.org> The commit 16198 has been declared to be an 'indent only' commit. That's FALSE. freenet/clients/http/bookmark/Bookmark.class : 7764669f81580ae93cc9497470bc08aa7d12759b should be 863b0c5efdb9cab16117054e744e70e0276b5b8e From toad at freenetproject.org Sat Dec 1 22:41:17 2007 From: toad at freenetproject.org (toad at freenetproject.org) Date: Sat, 1 Dec 2007 22:41:17 +0000 (UTC) Subject: [freenet-cvs] r16199 - trunk/freenet/src/freenet/node Message-ID: <20071201224117.17B9A479620@freenetproject.org> Author: toad Date: 2007-12-01 22:41:16 +0000 (Sat, 01 Dec 2007) New Revision: 16199 Modified: trunk/freenet/src/freenet/node/PeerNode.java Log: paranoia Modified: trunk/freenet/src/freenet/node/PeerNode.java =================================================================== --- trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 22:06:20 UTC (rev 16198) +++ trunk/freenet/src/freenet/node/PeerNode.java 2007-12-01 22:41:16 UTC (rev 16199) @@ -1673,7 +1673,7 @@ long now = System.currentTimeMillis(); KeyTracker completelyDeprecatedTracker; synchronized(this) { - if(tracker == unverifiedTracker) { + if(tracker == unverifiedTracker && !tracker.isDeprecated()) { if(logMINOR) Logger.minor(this, "Promoting unverified tracker " + tracker + " for " + getPeer()); completelyDeprecatedTracker = previousTracker; From svn-build at freenetproject.org Sat Dec 1 22:42:18 2007 From: svn-build at freenetproject.org (svn-build at freenetproject.org) Date: Sat, 1 Dec 2007 22:42:18 +0000 (UTC) Subject: [freenet-cvs] Verification of r16199 on emu Message-ID: <20071201224218.7DE7C479818@freenetproject.org> From toad at freenetproject.org Sat Dec 1 22:58:27 2007 From: toad at freenetproject.org (toad at freenetproject.org) Date: Sat, 1 Dec 2007 22:58:27 +0000 (UTC) Subject: [freenet-cvs] r16200 - trunk/freenet/src/freenet/node Message-ID: <20071201225827.12D1E47AE60@freenetproject.org> Author: toad Date: 2007-12-01 22:58:26 +0000 (Sat, 01 Dec 2007) New Revision: 16200 Modified: trunk/freenet/src/freenet/node/Version.java Log: 1084: Link level connectivity: - Rekeying bug: we weren't