/* * Dijjer - A Peer to Peer HTTP Cache * Copyright (C) 2004,2005 Change.Tv, Inc * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ package freenet.io.comm; import freenet.crypt.DSAPublicKey; import freenet.keys.Key; import freenet.keys.NodeCHK; import freenet.keys.NodeSSK; import freenet.node.NodeStats.PeerLoadStats; import freenet.node.probe.Error; import freenet.node.probe.Type; import freenet.support.BitArray; import freenet.support.Buffer; import freenet.support.Fields; import freenet.support.ShortBuffer; /** * @author ian * * To change the template for this generated type comment go to * Window - Preferences - Java - Code Generation - Code and Comments */ public class DMT { public static final String UID = "uid"; public static final String SEND_TIME = "sendTime"; public static final String EXTERNAL_ADDRESS = "externalAddress"; public static final String BUILD = "build"; public static final String FIRST_GOOD_BUILD = "firstGoodBuild"; public static final String JOINER = "joiner"; public static final String REASON = "reason"; public static final String DESCRIPTION = "description"; public static final String TTL = "ttl"; public static final String PEERS = "peers"; public static final String URL = "url"; public static final String FORWARDERS = "forwarders"; public static final String FILE_LENGTH = "fileLength"; public static final String LAST_MODIFIED = "lastModified"; public static final String CHUNK_NO = "chunkNo"; public static final String DATA_SOURCE = "dataSource"; public static final String CACHED = "cached"; public static final String PACKET_NO = "packetNo"; public static final String DATA = "data"; public static final String IS_HASH = "isHash"; public static final String HASH = "hash"; public static final String SENT = "sent"; public static final String MISSING = "missing"; public static final String KEY = "key"; public static final String CHK_HEADER = "chkHeader"; public static final String FREENET_URI = "freenetURI"; public static final String FREENET_ROUTING_KEY = "freenetRoutingKey"; public static final String TEST_CHK_HEADERS = "testCHKHeaders"; public static final String HTL = "hopsToLive"; public static final String SUCCESS = "success"; public static final String FNP_SOURCE_PEERNODE = "sourcePeerNode"; public static final String PING_SEQNO = "pingSequenceNumber"; public static final String LOCATION = "location"; public static final String NEAREST_LOCATION = "nearestLocation"; public static final String BEST_LOCATION = "bestLocation"; public static final String TARGET_LOCATION = "targetLocation"; public static final String TYPE = "type"; public static final String PAYLOAD = "payload"; public static final String COUNTER = "counter"; public static final String UNIQUE_COUNTER = "uniqueCounter"; public static final String LINEAR_COUNTER = "linearCounter"; public static final String RETURN_LOCATION = "returnLocation"; public static final String BLOCK_HEADERS = "blockHeaders"; public static final String DATA_INSERT_REJECTED_REASON = "dataInsertRejectedReason"; public static final String STREAM_SEQNO = "streamSequenceNumber"; public static final String IS_LOCAL = "isLocal"; public static final String ANY_TIMED_OUT = "anyTimedOut"; public static final String PUBKEY_HASH = "pubkeyHash"; public static final String NEED_PUB_KEY = "needPubKey"; public static final String PUBKEY_AS_BYTES = "pubkeyAsBytes"; public static final String SOURCE_NODENAME = "sourceNodename"; public static final String TARGET_NODENAME = "targetNodename"; public static final String NODE_TO_NODE_MESSAGE_TYPE = "nodeToNodeMessageType"; public static final String NODE_TO_NODE_MESSAGE_TEXT = "nodeToNodeMessageText"; public static final String NODE_TO_NODE_MESSAGE_DATA = "nodeToNodeMessageData"; public static final String NODE_UIDS = "nodeUIDs"; public static final String MY_UID = "myUID"; public static final String PEER_LOCATIONS = "peerLocations"; public static final String PEER_UIDS = "peerUIDs"; public static final String BEST_LOCATIONS_NOT_VISITED = "bestLocationsNotVisited"; public static final String MAIN_JAR_KEY = "mainJarKey"; public static final String EXTRA_JAR_KEY = "extraJarKey"; public static final String REVOCATION_KEY = "revocationKey"; public static final String HAVE_REVOCATION_KEY = "haveRevocationKey"; public static final String MAIN_JAR_VERSION = "mainJarVersion"; public static final String EXTRA_JAR_VERSION = "extJarVersion"; public static final String REVOCATION_KEY_TIME_LAST_TRIED = "revocationKeyTimeLastTried"; public static final String REVOCATION_KEY_DNF_COUNT = "revocationKeyDNFCount"; public static final String REVOCATION_KEY_FILE_LENGTH = "revocationKeyFileLength"; public static final String MAIN_JAR_FILE_LENGTH = "mainJarFileLength"; public static final String EXTRA_JAR_FILE_LENGTH = "extraJarFileLength"; public static final String PING_TIME = "pingTime"; public static final String BWLIMIT_DELAY_TIME = "bwlimitDelayTime"; public static final String TIME = "time"; public static final String FORK_COUNT = "forkCount"; public static final String TIME_LEFT = "timeLeft"; public static final String PREV_UID = "prevUID"; public static final String OPENNET_NODEREF = "opennetNoderef"; public static final String REMOVE = "remove"; public static final String PURGE = "purge"; public static final String TRANSFER_UID = "transferUID"; public static final String NODEREF_LENGTH = "noderefLength"; public static final String PADDED_LENGTH = "paddedLength"; public static final String TIME_DELTAS = "timeDeltas"; public static final String HASHES = "hashes"; public static final String REJECT_CODE = "rejectCode"; public static final String ROUTING_ENABLED = "routingEnabled"; public static final String OFFER_AUTHENTICATOR = "offerAuthenticator"; public static final String DAWN_HTL = "dawnHtl"; public static final String SECRET = "secret"; public static final String NODE_IDENTITY = "nodeIdentity"; public static final String UPTIME_PERCENT_48H = "uptimePercent48H"; public static final String FRIEND_VISIBILITY = "friendVisibility"; public static final String ENABLE_INSERT_FORK_WHEN_CACHEABLE = "enableInsertForkWhenCacheable"; public static final String PREFER_INSERT = "preferInsert"; public static final String IGNORE_LOW_BACKOFF = "ignoreLowBackoff"; public static final String LIST_OF_UIDS = "listOfUIDs"; public static final String UID_STILL_RUNNING_FLAGS = "UIDStillRunningFlags"; public static final String PROBE_IDENTIFIER = "probeIdentifier"; public static final String STORE_SIZE = "storeSize"; public static final String LINK_LENGTHS = "linkLengths"; public static final String UPTIME_PERCENT = "uptimePercent"; public static final String EXPECTED_HASH = "expectedHash"; public static final String REJECT_STATS = "rejectStats"; public static final String OUTPUT_BANDWIDTH_CLASS = "outputBandwidthClass"; public static final String CAPACITY_USAGE = "capacityUsage"; /** Very urgent */ public static final short PRIORITY_NOW=0; /** Short timeout, or urgent for other reasons - Accepted, RejectedLoop etc. */ public static final short PRIORITY_HIGH=1; // /** Stuff that completes a request, and miscellaneous stuff. */ public static final short PRIORITY_UNSPECIFIED=2; /** Stuff that starts a request. */ public static final short PRIORITY_LOW=3; // long timeout, or moderately urgent /** Bulk data transfer for realtime requests. Not strictly inferior to * PRIORITY_BULK_DATA: we will not allow PRIORITY_REALTIME_DATA to starve * PRIORITY_BULK_DATA. */ public static final short PRIORITY_REALTIME_DATA=4; /** * Bulk data transfer, bottom of the heap, high level limiting must ensure there is time to send it by * not accepting an infeasible number of requests; starvation will cause bwlimitDelayTime to go high and * requests to be rejected. That's the ultimate limiter if even output bandwidth liability fails. */ public static final short PRIORITY_BULK_DATA=5; public static final short NUM_PRIORITIES = 6; // Assimilation // New data transmission messages public static final MessageType packetTransmit = new MessageType("packetTransmit", PRIORITY_BULK_DATA) {{ addField(UID, Long.class); addField(PACKET_NO, Integer.class); addField(SENT, BitArray.class); addField(DATA, Buffer.class); }}; public static Message createPacketTransmit(long uid, int packetNo, BitArray sent, Buffer data, boolean realTime) { Message msg = new Message(packetTransmit); msg.set(UID, uid); msg.set(PACKET_NO, packetNo); msg.set(SENT, sent); msg.set(DATA, data); if(realTime) msg.boostPriority(); return msg; } public static int packetTransmitSize(int size, int _packets) { return size + 8 /* uid */ + 4 /* packet# */ + BitArray.serializedLength(_packets) + 4 /* Message header */; } public static int bulkPacketTransmitSize(int size) { return size + 8 /* uid */ + 4 /* packet# */ + 4 /* Message header */; } //This is of priority BULK_DATA to cut down on suprious resend requests, it will be queued after the packets it represents public static final MessageType allSent = new MessageType("allSent", PRIORITY_BULK_DATA) {{ addField(UID, Long.class); }}; public static Message createAllSent(long uid, boolean realTime) { Message msg = new Message(allSent); msg.set(UID, uid); return msg; } public static final MessageType allReceived = new MessageType("allReceived", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); }}; public static Message createAllReceived(long uid) { Message msg = new Message(allReceived); msg.set(UID, uid); return msg; } public static final MessageType sendAborted = new MessageType("sendAborted", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); addField(DESCRIPTION, String.class); addField(REASON, Integer.class); }}; public static Message createSendAborted(long uid, int reason, String description) { Message msg = new Message(sendAborted); msg.set(UID, uid); msg.set(REASON, reason); msg.set(DESCRIPTION, description); return msg; } public static final MessageType FNPBulkPacketSend = new MessageType("FNPBulkPacketSend", PRIORITY_BULK_DATA) {{ addField(UID, Long.class); addField(PACKET_NO, Integer.class); addField(DATA, ShortBuffer.class); }}; public static Message createFNPBulkPacketSend(long uid, int packetNo, ShortBuffer data, boolean realTime) { Message msg = new Message(FNPBulkPacketSend); msg.set(UID, uid); msg.set(PACKET_NO, packetNo); msg.set(DATA, data); return msg; } public static Message createFNPBulkPacketSend(long uid, int packetNo, byte[] data, boolean realTime) { return createFNPBulkPacketSend(uid, packetNo, new ShortBuffer(data), realTime); } public static final MessageType FNPBulkSendAborted = new MessageType("FNPBulkSendAborted", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); }}; public static Message createFNPBulkSendAborted(long uid) { Message msg = new Message(FNPBulkSendAborted); msg.set(UID, uid); return msg; } public static final MessageType FNPBulkReceiveAborted = new MessageType("FNPBulkReceiveAborted", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); }}; public static Message createFNPBulkReceiveAborted(long uid) { Message msg = new Message(FNPBulkReceiveAborted); msg.set(UID, uid); return msg; } public static final MessageType FNPBulkReceivedAll = new MessageType("FNPBulkReceivedAll", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); }}; public static Message createFNPBulkReceivedAll(long uid) { Message msg = new Message(FNPBulkReceivedAll); msg.set(UID, uid); return msg; } public static final MessageType testTransferSend = new MessageType("testTransferSend", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); }}; public static Message createTestTransferSend(long uid) { Message msg = new Message(testTransferSend); msg.set(UID, uid); return msg; } public static final MessageType testTransferSendAck = new MessageType("testTransferSendAck", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); }}; public static Message createTestTransferSendAck(long uid) { Message msg = new Message(testTransferSendAck); msg.set(UID, uid); return msg; } public static final MessageType testSendCHK = new MessageType("testSendCHK", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); addField(FREENET_URI, String.class); addField(CHK_HEADER, Buffer.class); }}; public static Message createTestSendCHK(long uid, String uri, Buffer header) { Message msg = new Message(testSendCHK); msg.set(UID, uid); msg.set(FREENET_URI, uri); msg.set(CHK_HEADER, header); return msg; } public static final MessageType testRequest = new MessageType("testRequest", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); addField(FREENET_ROUTING_KEY, Key.class); addField(HTL, Integer.class); }}; public static Message createTestRequest(Key Key, long id, int htl) { Message msg = new Message(testRequest); msg.set(UID, id); msg.set(FREENET_ROUTING_KEY, Key); msg.set(HTL, htl); return msg; } public static final MessageType testDataNotFound = new MessageType("testDataNotFound", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); }}; public static Message createTestDataNotFound(long uid) { Message msg = new Message(testDataNotFound); msg.set(UID, uid); return msg; } public static final MessageType testDataReply = new MessageType("testDataReply", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); addField(TEST_CHK_HEADERS, Buffer.class); }}; public static Message createTestDataReply(long uid, byte[] headers) { Message msg = new Message(testDataReply); msg.set(UID, uid); msg.set(TEST_CHK_HEADERS, new Buffer(headers)); return msg; } public static final MessageType testSendCHKAck = new MessageType("testSendCHKAck", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); addField(FREENET_URI, String.class); }}; public static Message createTestSendCHKAck(long uid, String key) { Message msg = new Message(testSendCHKAck); msg.set(UID, uid); msg.set(FREENET_URI, key); return msg; } public static final MessageType testDataReplyAck = new MessageType("testDataReplyAck", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); }}; public static Message createTestDataReplyAck(long id) { Message msg = new Message(testDataReplyAck); msg.set(UID, id); return msg; } public static final MessageType testDataNotFoundAck = new MessageType("testDataNotFoundAck", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); }}; public static Message createTestDataNotFoundAck(long id) { Message msg = new Message(testDataNotFoundAck); msg.set(UID, id); return msg; } // Internal only messages public static final MessageType testReceiveCompleted = new MessageType("testReceiveCompleted", PRIORITY_UNSPECIFIED, true, false) {{ addField(UID, Long.class); addField(SUCCESS, Boolean.class); addField(REASON, String.class); }}; public static Message createTestReceiveCompleted(long id, boolean success, String reason) { Message msg = new Message(testReceiveCompleted); msg.set(UID, id); msg.set(SUCCESS, success); msg.set(REASON, reason); return msg; } public static final MessageType testSendCompleted = new MessageType("testSendCompleted", PRIORITY_UNSPECIFIED, true, false) {{ addField(UID, Long.class); addField(SUCCESS, Boolean.class); addField(REASON, String.class); }}; public static Message createTestSendCompleted(long id, boolean success, String reason) { Message msg = new Message(testSendCompleted); msg.set(UID, id); msg.set(SUCCESS, success); msg.set(REASON, reason); return msg; } // Node-To-Node Message (generic) public static final MessageType nodeToNodeMessage = new MessageType("nodeToNodeMessage", PRIORITY_LOW, false, false) {{ addField(NODE_TO_NODE_MESSAGE_TYPE, Integer.class); addField(NODE_TO_NODE_MESSAGE_DATA, ShortBuffer.class); }}; public static Message createNodeToNodeMessage(int type, byte[] data) { Message msg = new Message(nodeToNodeMessage); msg.set(NODE_TO_NODE_MESSAGE_TYPE, type); msg.set(NODE_TO_NODE_MESSAGE_DATA, new ShortBuffer(data)); return msg; } // FNP messages public static final MessageType FNPCHKDataRequest = new MessageType("FNPCHKDataRequest", PRIORITY_LOW) {{ addField(UID, Long.class); addField(HTL, Short.class); addField(NEAREST_LOCATION, Double.class); addField(FREENET_ROUTING_KEY, NodeCHK.class); }}; public static Message createFNPCHKDataRequest(long id, short htl, NodeCHK key) { Message msg = new Message(FNPCHKDataRequest); msg.set(UID, id); msg.set(HTL, htl); msg.set(FREENET_ROUTING_KEY, key); msg.set(NEAREST_LOCATION, 0.0); return msg; } public static final MessageType FNPSSKDataRequest = new MessageType("FNPSSKDataRequest", PRIORITY_LOW) {{ addField(UID, Long.class); addField(HTL, Short.class); addField(NEAREST_LOCATION, Double.class); addField(FREENET_ROUTING_KEY, NodeSSK.class); addField(NEED_PUB_KEY, Boolean.class); }}; public static Message createFNPSSKDataRequest(long id, short htl, NodeSSK key, boolean needPubKey) { Message msg = new Message(FNPSSKDataRequest); msg.set(UID, id); msg.set(HTL, htl); msg.set(FREENET_ROUTING_KEY, key); msg.set(NEAREST_LOCATION, 0.0); msg.set(NEED_PUB_KEY, needPubKey); return msg; } // Hit our tail, try a different node. public static final MessageType FNPRejectedLoop = new MessageType("FNPRejectLoop", PRIORITY_HIGH) {{ addField(UID, Long.class); }}; public static Message createFNPRejectedLoop(long id) { Message msg = new Message(FNPRejectedLoop); msg.set(UID, id); return msg; } // Too many requests for present capacity. Fail, propagate back // to source, and reduce send rate. public static final MessageType FNPRejectedOverload = new MessageType("FNPRejectOverload", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(IS_LOCAL, Boolean.class); }}; public static Message createFNPRejectedOverload(long id, boolean isLocal, boolean needsLoad, boolean realTimeFlag) { Message msg = new Message(FNPRejectedOverload); msg.set(UID, id); msg.set(IS_LOCAL, isLocal); if(needsLoad) { if(realTimeFlag) msg.setNeedsLoadRT(); else msg.setNeedsLoadBulk(); } return msg; } public static final MessageType FNPAccepted = new MessageType("FNPAccepted", PRIORITY_HIGH) {{ addField(UID, Long.class); }}; public static Message createFNPAccepted(long id) { Message msg = new Message(FNPAccepted); msg.set(UID, id); return msg; } public static final MessageType FNPDataNotFound = new MessageType("FNPDataNotFound", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); }}; public static Message createFNPDataNotFound(long id) { Message msg = new Message(FNPDataNotFound); msg.set(UID, id); return msg; } public static final MessageType FNPRecentlyFailed = new MessageType("FNPRecentlyFailed", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(TIME_LEFT, Integer.class); }}; public static Message createFNPRecentlyFailed(long id, int timeLeft) { Message msg = new Message(FNPRecentlyFailed); msg.set(UID, id); msg.set(TIME_LEFT, timeLeft); return msg; } public static final MessageType FNPCHKDataFound = new MessageType("FNPCHKDataFound", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); addField(BLOCK_HEADERS, ShortBuffer.class); }}; public static Message createFNPCHKDataFound(long id, byte[] buf) { Message msg = new Message(FNPCHKDataFound); msg.set(UID, id); msg.set(BLOCK_HEADERS, new ShortBuffer(buf)); return msg; } public static final MessageType FNPRouteNotFound = new MessageType("FNPRouteNotFound", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); addField(HTL, Short.class); }}; public static Message createFNPRouteNotFound(long id, short htl) { Message msg = new Message(FNPRouteNotFound); msg.set(UID, id); msg.set(HTL, htl); return msg; } public static final MessageType FNPInsertRequest = new MessageType("FNPInsertRequest", PRIORITY_LOW) {{ addField(UID, Long.class); addField(HTL, Short.class); addField(NEAREST_LOCATION, Double.class); addField(FREENET_ROUTING_KEY, Key.class); }}; public static Message createFNPInsertRequest(long id, short htl, Key key) { Message msg = new Message(FNPInsertRequest); msg.set(UID, id); msg.set(HTL, htl); msg.set(FREENET_ROUTING_KEY, key); msg.set(NEAREST_LOCATION, 0.0); return msg; } public static final MessageType FNPInsertReply = new MessageType("FNPInsertReply", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); }}; public static Message createFNPInsertReply(long id) { Message msg = new Message(FNPInsertReply); msg.set(UID, id); return msg; } public static final MessageType FNPDataInsert = new MessageType("FNPDataInsert", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(BLOCK_HEADERS, ShortBuffer.class); }}; public static Message createFNPDataInsert(long uid, byte[] headers) { Message msg = new Message(FNPDataInsert); msg.set(UID, uid); msg.set(BLOCK_HEADERS, new ShortBuffer(headers)); return msg; } public static final MessageType FNPInsertTransfersCompleted = new MessageType("FNPInsertTransfersCompleted", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); addField(ANY_TIMED_OUT, Boolean.class); }}; public static Message createFNPInsertTransfersCompleted(long uid, boolean anyTimedOut) { Message msg = new Message(FNPInsertTransfersCompleted); msg.set(UID, uid); msg.set(ANY_TIMED_OUT, anyTimedOut); return msg; } // This is used by CHK inserts when the DataInsert isn't received. // SSK inserts just use DataInsertRejected with a timeout reason. // FIXME we probably should just use one message for both. One complication is that // CHKs have a single DataInsert (followed by a transfer), whereas SSKs have 2-3 messages, // any of which can timeout independantly. Arguably that's bad design and we should // just send one message now that we have new packet format, see the discussion on // FNPSSKInsertRequestNew vs the old version. public static final MessageType FNPRejectedTimeout = new MessageType("FNPTooSlow", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); }}; public static Message createFNPRejectedTimeout(long uid) { Message msg = new Message(FNPRejectedTimeout); msg.set(UID, uid); return msg; } public static final MessageType FNPDataInsertRejected = new MessageType("FNPDataInsertRejected", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); addField(DATA_INSERT_REJECTED_REASON, Short.class); }}; public static Message createFNPDataInsertRejected(long uid, short reason) { Message msg = new Message(FNPDataInsertRejected); msg.set(UID, uid); msg.set(DATA_INSERT_REJECTED_REASON, reason); return msg; } public static final short DATA_INSERT_REJECTED_VERIFY_FAILED = 1; public static final short DATA_INSERT_REJECTED_RECEIVE_FAILED = 2; public static final short DATA_INSERT_REJECTED_SSK_ERROR = 3; public static final short DATA_INSERT_REJECTED_TIMEOUT_WAITING_FOR_ACCEPTED = 4; public static String getDataInsertRejectedReason(short reason) { if(reason == DATA_INSERT_REJECTED_VERIFY_FAILED) return "Verify failed"; else if(reason == DATA_INSERT_REJECTED_RECEIVE_FAILED) return "Receive failed"; else if(reason == DATA_INSERT_REJECTED_SSK_ERROR) return "SSK error"; else if(reason == DATA_INSERT_REJECTED_TIMEOUT_WAITING_FOR_ACCEPTED) return "Timeout waiting for Accepted (moved on)"; return "Unknown reason code: "+reason; } // FIXME consider using this again now we have new packet format which can handle big messages on any connection. // FIXME be careful if we do - make sure boost priority if realtime, and note timeout issues associated with sending a request at BULK. public static final MessageType FNPSSKInsertRequest = new MessageType("FNPSSKInsertRequest", PRIORITY_BULK_DATA) {{ addField(UID, Long.class); addField(HTL, Short.class); addField(FREENET_ROUTING_KEY, NodeSSK.class); addField(NEAREST_LOCATION, Double.class); addField(BLOCK_HEADERS, ShortBuffer.class); addField(PUBKEY_HASH, ShortBuffer.class); addField(DATA, ShortBuffer.class); }}; public static Message createFNPSSKInsertRequest(long uid, short htl, NodeSSK myKey, byte[] headers, byte[] data, byte[] pubKeyHash, boolean realTime) { Message msg = new Message(FNPSSKInsertRequest); msg.set(UID, uid); msg.set(HTL, htl); msg.set(FREENET_ROUTING_KEY, myKey); msg.set(NEAREST_LOCATION, 0.0); msg.set(BLOCK_HEADERS, new ShortBuffer(headers)); msg.set(PUBKEY_HASH, new ShortBuffer(pubKeyHash)); msg.set(DATA, new ShortBuffer(data)); if(realTime) msg.boostPriority(); return msg; } public static final MessageType FNPSSKInsertRequestNew = new MessageType("FNPSSKInsertRequestNew", PRIORITY_LOW) {{ addField(UID, Long.class); addField(HTL, Short.class); addField(FREENET_ROUTING_KEY, NodeSSK.class); }}; public static Message createFNPSSKInsertRequestNew(long uid, short htl, NodeSSK myKey) { Message msg = new Message(FNPSSKInsertRequestNew); msg.set(UID, uid); msg.set(HTL, htl); msg.set(FREENET_ROUTING_KEY, myKey); return msg; } // SSK inserts data and headers. These are BULK_DATA or REALTIME. public static final MessageType FNPSSKInsertRequestHeaders = new MessageType("FNPSSKInsertRequestHeaders", PRIORITY_BULK_DATA) {{ addField(UID, Long.class); addField(BLOCK_HEADERS, ShortBuffer.class); }}; public static Message createFNPSSKInsertRequestHeaders(long uid, byte[] headers, boolean realTime) { Message msg = new Message(FNPSSKInsertRequestHeaders); msg.set(UID, uid); msg.set(BLOCK_HEADERS, new ShortBuffer(headers)); if(realTime) msg.boostPriority(); return msg; } public static final MessageType FNPSSKInsertRequestData = new MessageType("FNPSSKInsertRequestData", PRIORITY_BULK_DATA) {{ addField(UID, Long.class); addField(DATA, ShortBuffer.class); }}; public static Message createFNPSSKInsertRequestData(long uid, byte[] data, boolean realTime) { Message msg = new Message(FNPSSKInsertRequestData); msg.set(UID, uid); msg.set(DATA, new ShortBuffer(data)); if(realTime) msg.boostPriority(); return msg; } // SSK pubkeys, data and headers are all BULK_DATA or REALTIME. // Requests wait for them all equally, so there is no reason for them to be different, // plus everything is throttled now. public static final MessageType FNPSSKDataFoundHeaders = new MessageType("FNPSSKDataFoundHeaders", PRIORITY_BULK_DATA) {{ addField(UID, Long.class); addField(BLOCK_HEADERS, ShortBuffer.class); }}; public static Message createFNPSSKDataFoundHeaders(long uid, byte[] headers, boolean realTime) { Message msg = new Message(FNPSSKDataFoundHeaders); msg.set(UID, uid); msg.set(BLOCK_HEADERS, new ShortBuffer(headers)); if(realTime) msg.boostPriority(); return msg; } public static final MessageType FNPSSKDataFoundData = new MessageType("FNPSSKDataFoundData", PRIORITY_BULK_DATA) {{ addField(UID, Long.class); addField(DATA, ShortBuffer.class); }}; public static Message createFNPSSKDataFoundData(long uid, byte[] data, boolean realTime) { Message msg = new Message(FNPSSKDataFoundData); msg.set(UID, uid); msg.set(DATA, new ShortBuffer(data)); if(realTime) msg.boostPriority(); return msg; } public final static MessageType FNPSSKAccepted = new MessageType("FNPSSKAccepted", PRIORITY_HIGH) { { addField(UID, Long.class); addField(NEED_PUB_KEY, Boolean.class); }}; public static Message createFNPSSKAccepted(long uid, boolean needPubKey) { Message msg = new Message(FNPSSKAccepted); msg.set(UID, uid); msg.set(NEED_PUB_KEY, needPubKey); return msg; } public final static MessageType FNPSSKPubKey = new MessageType("FNPSSKPubKey", PRIORITY_BULK_DATA) { { addField(UID, Long.class); addField(PUBKEY_AS_BYTES, ShortBuffer.class); }}; public static Message createFNPSSKPubKey(long uid, DSAPublicKey pubkey, boolean realTime) { Message msg = new Message(FNPSSKPubKey); msg.set(UID, uid); msg.set(PUBKEY_AS_BYTES, new ShortBuffer(pubkey.asPaddedBytes())); if(realTime) msg.boostPriority(); return msg; } public final static MessageType FNPSSKPubKeyAccepted = new MessageType("FNPSSKPubKeyAccepted", PRIORITY_HIGH) { { addField(UID, Long.class); }}; public static Message createFNPSSKPubKeyAccepted(long uid) { Message msg = new Message(FNPSSKPubKeyAccepted); msg.set(UID, uid); return msg; } // Opennet completions (not sent to darknet nodes) /** Sent when a request to an opennet node is completed, but the data source does not want to * path fold. Sent even on pure darknet. A better name might be FNPRequestCompletedAck. */ public final static MessageType FNPOpennetCompletedAck = new MessageType("FNPOpennetCompletedAck", PRIORITY_HIGH) { { addField(UID, Long.class); }}; public static Message createFNPOpennetCompletedAck(long uid) { Message msg = new Message(FNPOpennetCompletedAck); msg.set(UID, uid); return msg; } /** Sent when we wait for an FNP transfer or a completion from upstream and it never comes. */ public final static MessageType FNPOpennetCompletedTimeout = new MessageType("FNPOpennetCompletedTimeout", PRIORITY_HIGH) {{ addField(UID, Long.class); }}; public static Message createFNPOpennetCompletedTimeout(long uid) { Message msg = new Message(FNPOpennetCompletedTimeout); msg.set(UID, uid); return msg; } /** Sent when a request completes and the data source wants to path fold. Starts a bulk data * transfer including the (padded) noderef. */ public final static MessageType FNPOpennetConnectDestinationNew = new MessageType("FNPConnectDestinationNew", PRIORITY_UNSPECIFIED) { { addField(UID, Long.class); // UID of original message chain addField(TRANSFER_UID, Long.class); // UID of data transfer addField(NODEREF_LENGTH, Integer.class); // Size of noderef addField(PADDED_LENGTH, Integer.class); // Size of actual transfer i.e. padded length }}; public static Message createFNPOpennetConnectDestinationNew(long uid, long transferUID, int noderefLength, int paddedLength) { Message msg = new Message(FNPOpennetConnectDestinationNew); msg.set(UID, uid); msg.set(TRANSFER_UID, transferUID); msg.set(NODEREF_LENGTH, noderefLength); msg.set(PADDED_LENGTH, paddedLength); return msg; } /** Path folding response. Sent when the requestor wants to path fold and has received a noderef * from the data source. Starts a bulk data transfer including the (padded) noderef. */ public final static MessageType FNPOpennetConnectReplyNew = new MessageType("FNPConnectReplyNew", PRIORITY_UNSPECIFIED) { { addField(UID, Long.class); // UID of original message chain addField(TRANSFER_UID, Long.class); // UID of data transfer addField(NODEREF_LENGTH, Integer.class); // Size of noderef addField(PADDED_LENGTH, Integer.class); // Size of actual transfer i.e. padded length }}; public static Message createFNPOpennetConnectReplyNew(long uid, long transferUID, int noderefLength, int paddedLength) { Message msg = new Message(FNPOpennetConnectReplyNew); msg.set(UID, uid); msg.set(TRANSFER_UID, transferUID); msg.set(NODEREF_LENGTH, noderefLength); msg.set(PADDED_LENGTH, paddedLength); return msg; } // Opennet announcement /** * Announcement request. Noderef is attached, will be transferred before anything else is done. */ public final static MessageType FNPOpennetAnnounceRequest = new MessageType("FNPOpennetAnnounceRequest", PRIORITY_HIGH) { { addField(UID, Long.class); addField(TRANSFER_UID, Long.class); addField(NODEREF_LENGTH, Integer.class); addField(PADDED_LENGTH, Integer.class); addField(HTL, Short.class); addField(NEAREST_LOCATION, Double.class); addField(TARGET_LOCATION, Double.class); }}; public static Message createFNPOpennetAnnounceRequest(long uid, long transferUID, int noderefLength, int paddedLength, double target, short htl) { Message msg = new Message(FNPOpennetAnnounceRequest); msg.set(UID, uid); msg.set(TRANSFER_UID, transferUID); msg.set(NODEREF_LENGTH, noderefLength); msg.set(PADDED_LENGTH, paddedLength); msg.set(HTL, htl); msg.set(NEAREST_LOCATION, 0.0); msg.set(TARGET_LOCATION, target); return msg; } /** * Announcement reply. Noderef is attached, will be transferred, both nodes add the other. A single * request will result in many reply's. When the announcement is done, we return a DataNotFound; if * we run into a dead-end, we return a RejectedLoop; if we can't accept it, RejectedOverload. */ public final static MessageType FNPOpennetAnnounceReply = new MessageType("FNPOpennetAnnounceReply", PRIORITY_UNSPECIFIED) { { addField(UID, Long.class); addField(TRANSFER_UID, Long.class); addField(NODEREF_LENGTH, Integer.class); addField(PADDED_LENGTH, Integer.class); }}; public static Message createFNPOpennetAnnounceReply(long uid, long transferUID, int noderefLength, int paddedLength) { Message msg = new Message(FNPOpennetAnnounceReply); msg.set(UID, uid); msg.set(TRANSFER_UID, transferUID); msg.set(NODEREF_LENGTH, noderefLength); msg.set(PADDED_LENGTH, paddedLength); return msg; } public final static MessageType FNPOpennetAnnounceCompleted = new MessageType("FNPOpennetAnnounceCompleted", PRIORITY_UNSPECIFIED) { { addField(UID, Long.class); }}; public static Message createFNPOpennetAnnounceCompleted(long uid) { Message msg = new Message(FNPOpennetAnnounceCompleted); msg.set(UID, uid); return msg; } public final static MessageType FNPOpennetDisabled = new MessageType("FNPOpennetDisabled", PRIORITY_HIGH) { { addField(UID, Long.class); }}; public static Message createFNPOpennetDisabled(long uid) { Message msg = new Message(FNPOpennetDisabled); msg.set(UID, uid); return msg; } public final static MessageType FNPOpennetNoderefRejected = new MessageType("FNPOpennetNoderefRejected", PRIORITY_HIGH) { { addField(UID, Long.class); addField(REJECT_CODE, Integer.class); }}; public static Message createFNPOpennetNoderefRejected(long uid, int rejectCode) { Message msg = new Message(FNPOpennetNoderefRejected); msg.set(UID, uid); msg.set(REJECT_CODE, rejectCode); return msg; } 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; // FIXME get rid??? public final static MessageType FNPOpennetAnnounceNodeNotWanted = new MessageType( "FNPOpennetAnnounceNodeNotWanted", PRIORITY_LOW) { { addField(UID, Long.class); }}; public static Message createFNPOpennetAnnounceNodeNotWanted(long uid) { Message msg = new Message(FNPOpennetAnnounceNodeNotWanted); msg.set(UID, uid); return msg; } // Key offers (ULPRs) public final static MessageType FNPOfferKey = new MessageType("FNPOfferKey", PRIORITY_LOW) { { addField(KEY, Key.class); addField(OFFER_AUTHENTICATOR, ShortBuffer.class); }}; public static Message createFNPOfferKey(Key key, byte[] authenticator) { Message msg = new Message(FNPOfferKey); msg.set(KEY, key); msg.set(OFFER_AUTHENTICATOR, new ShortBuffer(authenticator)); return msg; } // Short timeout so PRIORITY_HIGH public final static MessageType FNPGetOfferedKey = new MessageType("FNPGetOfferedKey", PRIORITY_LOW) { { addField(KEY, Key.class); addField(OFFER_AUTHENTICATOR, ShortBuffer.class); addField(NEED_PUB_KEY, Boolean.class); addField(UID, Long.class); }}; public static Message createFNPGetOfferedKey(Key key, byte[] authenticator, boolean needPubkey, long uid) { Message msg = new Message(FNPGetOfferedKey); msg.set(KEY, key); msg.set(OFFER_AUTHENTICATOR, new ShortBuffer(authenticator)); msg.set(NEED_PUB_KEY, needPubkey); msg.set(UID, uid); return msg; } // Permanently rejected. RejectedOverload means temporarily rejected. public final static MessageType FNPGetOfferedKeyInvalid = new MessageType("FNPGetOfferedKeyInvalid", PRIORITY_HIGH) { { // short timeout addField(UID, Long.class); addField(REASON, Short.class); }}; public static Message createFNPGetOfferedKeyInvalid(long uid, short reason) { Message msg = new Message(FNPGetOfferedKeyInvalid); msg.set(UID, uid); msg.set(REASON, reason); return msg; } public final static short GET_OFFERED_KEY_REJECTED_BAD_AUTHENTICATOR = 1; public final static short GET_OFFERED_KEY_REJECTED_NO_KEY = 2; public static final MessageType FNPPing = new MessageType("FNPPing", PRIORITY_HIGH) {{ addField(PING_SEQNO, Integer.class); }}; public static Message createFNPPing(int seqNo) { Message msg = new Message(FNPPing); msg.set(PING_SEQNO, seqNo); return msg; } public static final MessageType FNPPong = new MessageType("FNPPong", PRIORITY_HIGH) {{ addField(PING_SEQNO, Integer.class); }}; public static Message createFNPPong(int seqNo) { Message msg = new Message(FNPPong); msg.set(PING_SEQNO, seqNo); return msg; } public static final MessageType FNPRHProbeReply = new MessageType("FNPRHProbeReply", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); addField(NEAREST_LOCATION, Double.class); addField(BEST_LOCATION, Double.class); addField(COUNTER, Short.class); addField(UNIQUE_COUNTER, Short.class); addField(LINEAR_COUNTER, Short.class); }}; public static Message createFNPRHProbeReply(long uid, double nearest, double best, short counter, short uniqueCounter, short linearCounter) { Message msg = new Message(FNPRHProbeReply); msg.set(UID, uid); msg.set(NEAREST_LOCATION, nearest); msg.set(BEST_LOCATION, best); msg.set(COUNTER, counter); msg.set(UNIQUE_COUNTER, uniqueCounter); msg.set(LINEAR_COUNTER, linearCounter); return msg; } public static final MessageType ProbeRequest = new MessageType("ProbeRequest", PRIORITY_HIGH) {{ addField(HTL, Byte.class); addField(UID, Long.class); addField(TYPE, Byte.class); }}; /** * Constructs a a probe request. * @param htl hopsToLive: hops until result is requested. * @param uid Probe identifier: should be unique. * @return Message with requested attributes. */ public static Message createProbeRequest(byte htl, long uid, Type type) { Message msg = new Message(ProbeRequest); msg.set(HTL, htl); msg.set(UID, uid); msg.set(TYPE, type.code); return msg; } public static final MessageType ProbeError = new MessageType("ProbeError", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(TYPE, Byte.class); }}; /** * Creates a probe response which indicates there was an error. * @param uid Probe identifier. * @param error The type of error that occurred. Can be one of Probe.ProbeError. * @return Message with the requested attributes. */ public static Message createProbeError(long uid, Error error) { Message msg = new Message(ProbeError); msg.set(UID, uid); msg.set(TYPE, error.code); return msg; } public static final MessageType ProbeRefused = new MessageType("ProbeRefused", PRIORITY_HIGH) {{ addField(DMT.UID, Long.class); }}; /** * Creates a probe response which indicates that the endpoint opted not to respond with the requested result. * @param uid Probe identifier. * @return Message with the requested attribute. */ public static Message createProbeRefused(long uid) { Message msg = new Message(ProbeRefused); msg.set(UID, uid); return msg; } public static final MessageType ProbeBandwidth = new MessageType("ProbeBandwidth", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(OUTPUT_BANDWIDTH_UPPER_LIMIT, Float.class); }}; /** * Creates a probe response to a query for bandwidth limits. * @param uid Probe identifier. * @param limit Endpoint output bandwidth limit in KiB per second. * @return Message with requested attributes. */ public static Message createProbeBandwidth(long uid, float limit) { Message msg = new Message(ProbeBandwidth); msg.set(UID, uid); msg.set(OUTPUT_BANDWIDTH_UPPER_LIMIT, limit); return msg; } public static final MessageType ProbeBuild = new MessageType("ProbeBuild", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(BUILD, Integer.class); }}; /** * Creates a probe response to a query for build. * @param uid Probe identifier. * @param build Endpoint build of Freenet. * @return Message with requested attributes. */ public static Message createProbeBuild(long uid, int build) { Message msg = new Message(ProbeBuild); msg.set(UID, uid); msg.set(BUILD, build); return msg; } public static final MessageType ProbeIdentifier = new MessageType("ProbeIdentifier", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(PROBE_IDENTIFIER, Long.class); addField(UPTIME_PERCENT, Byte.class); }}; /** * Creates a probe response to a query for identifier. * @param uid Probe UID. * @param probeIdentifier Endpoint identifier. * @param uptimePercentage 7-day uptime percentage. * @return Message with requested attributes. */ public static Message createProbeIdentifier(long uid, long probeIdentifier, byte uptimePercentage) { Message msg = new Message(ProbeIdentifier); msg.set(UID, uid); msg.set(PROBE_IDENTIFIER, probeIdentifier); msg.set(UPTIME_PERCENT, uptimePercentage); return msg; } public static final MessageType ProbeLinkLengths = new MessageType("ProbeLinkLengths", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(LINK_LENGTHS, float[].class); }}; /** * Creates a probe response to a query for link lengths. * @param uid Probe identifier. * @param linkLengths Endpoint link lengths. * @return Message with requested attributes. */ public static Message createProbeLinkLengths(long uid, float[] linkLengths) { Message msg = new Message(ProbeLinkLengths); msg.set(UID, uid); msg.set(LINK_LENGTHS, linkLengths); return msg; } public static final MessageType ProbeLocation = new MessageType("ProbeLocation", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(LOCATION, Float.class); }}; /** * Creates a probe response to a query for location. * @param uid Probe identifier. * @param location Endpoint location. * @return Message with the requested attributes. */ public static Message createProbeLocation(long uid, float location) { Message msg = new Message(ProbeLocation); msg.set(UID, uid); msg.set(LOCATION, location); return msg; } public static final MessageType ProbeStoreSize = new MessageType("ProbeStoreSize", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(STORE_SIZE, Float.class); }}; /** * Creates a probe response to a query for store size. * @param uid Probe identifier. * @param storeSize Endpoint store size in GiB multiplied by Gaussian noise. * @return Message with requested attributes. */ public static Message createProbeStoreSize(long uid, float storeSize) { Message msg = new Message(ProbeStoreSize); msg.set(UID, uid); msg.set(STORE_SIZE, storeSize); return msg; } public static final MessageType ProbeUptime = new MessageType("ProbeUptime", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(UPTIME_PERCENT, Float.class); }}; /** * Creates a probe response to a query for uptime. * @param uid Probe identifier. * @param uptimePercent Percent of the requested period (48 hours or 7 days) which the endpoint was online. * @return Message with requested attributes. */ public static Message createProbeUptime(long uid, float uptimePercent) { Message msg = new Message(ProbeUptime); msg.set(UID, uid); msg.set(UPTIME_PERCENT, uptimePercent); return msg; } public static final MessageType ProbeRejectStats = new MessageType("ProbeRejectStats", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(REJECT_STATS, ShortBuffer.class); }}; public static Message createProbeRejectStats(long uid, byte[] rejectStats) { Message msg = new Message(ProbeRejectStats); msg.set(UID, uid); msg.set(REJECT_STATS, new ShortBuffer(rejectStats)); return msg; } /** Divide output bandwidth limit by this to get bandwidth class. */ static final int CAPACITY_USAGE_MULTIPLIER = 10*1024; /** Maximum value of bandwidth class */ static final byte CAPACITY_USAGE_MAX = 10; /** Minimum value of bandwidth class */ static final byte CAPACITY_USAGE_MIN = 1; public static final MessageType ProbeOverallBulkOutputCapacityUsage = new MessageType("ProbeOverallBulkOutputCapacityUsage", PRIORITY_HIGH) {{ addField(UID, Long.class); // UID for the probe addField(OUTPUT_BANDWIDTH_CLASS, Byte.class); // Approximate bandwidth, severely truncated. addField(CAPACITY_USAGE, Float.class); // Noisy capacity usage. }}; public static final byte bandwidthClassForCapacityUsage(int bandwidthLimit) { bandwidthLimit /= CAPACITY_USAGE_MULTIPLIER; bandwidthLimit = Math.min(bandwidthLimit, CAPACITY_USAGE_MAX); return (byte) Math.max(bandwidthLimit, CAPACITY_USAGE_MIN); } public static final Message createProbeOverallBulkOutputCapacityUsage(long uid, byte outputBandwidthClass, float capacityUsage) { Message msg = new Message(ProbeOverallBulkOutputCapacityUsage); msg.set(UID, uid); msg.set(OUTPUT_BANDWIDTH_CLASS, outputBandwidthClass); msg.set(CAPACITY_USAGE, capacityUsage); return msg; } public static final MessageType FNPSwapRequest = new MessageType("FNPSwapRequest", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(HASH, ShortBuffer.class); addField(HTL, Integer.class); }}; public static Message createFNPSwapRequest(long uid, byte[] buf, int htl) { Message msg = new Message(FNPSwapRequest); msg.set(UID, uid); msg.set(HASH, new ShortBuffer(buf)); msg.set(HTL, htl); return msg; } public static final MessageType FNPSwapRejected = new MessageType("FNPSwapRejected", PRIORITY_HIGH) {{ addField(UID, Long.class); }}; public static Message createFNPSwapRejected(long uid) { Message msg = new Message(FNPSwapRejected); msg.set(UID, uid); return msg; } public static final MessageType FNPSwapReply = new MessageType("FNPSwapReply", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(HASH, ShortBuffer.class); }}; public static Message createFNPSwapReply(long uid, byte[] buf) { Message msg = new Message(FNPSwapReply); msg.set(UID, uid); msg.set(HASH, new ShortBuffer(buf)); return msg; } public static final MessageType FNPSwapCommit = new MessageType("FNPSwapCommit", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(DATA, ShortBuffer.class); }}; public static Message createFNPSwapCommit(long uid, byte[] buf) { Message msg = new Message(FNPSwapCommit); msg.set(UID, uid); msg.set(DATA, new ShortBuffer(buf)); return msg; } public static final MessageType FNPSwapComplete = new MessageType("FNPSwapComplete", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(DATA, ShortBuffer.class); }}; public static Message createFNPSwapComplete(long uid, byte[] buf) { Message msg = new Message(FNPSwapComplete); msg.set(UID, uid); msg.set(DATA, new ShortBuffer(buf)); return msg; } public static final MessageType FNPLocChangeNotificationNew = new MessageType("FNPLocationChangeNotification2", PRIORITY_LOW) {{ addField(LOCATION, Double.class); addField(PEER_LOCATIONS, ShortBuffer.class); }}; public static Message createFNPLocChangeNotificationNew(double myLocation, double[] locations) { Message msg = new Message(FNPLocChangeNotificationNew); ShortBuffer dst = new ShortBuffer(Fields.doublesToBytes(locations)); msg.set(LOCATION, myLocation); msg.set(PEER_LOCATIONS, dst); return msg; } public static final MessageType FNPRoutedPing = new MessageType("FNPRoutedPing", PRIORITY_LOW) {{ addRoutedToNodeMessageFields(); addField(COUNTER, Integer.class); }}; public static Message createFNPRoutedPing(long uid, double targetLocation, short htl, int counter, byte[] nodeIdentity) { Message msg = new Message(FNPRoutedPing); msg.setRoutedToNodeFields(uid, targetLocation, htl, nodeIdentity); msg.set(COUNTER, counter); return msg; } public static final MessageType FNPRoutedPong = new MessageType("FNPRoutedPong", PRIORITY_LOW) {{ addField(UID, Long.class); addField(COUNTER, Integer.class); }}; public static Message createFNPRoutedPong(long uid, int counter) { Message msg = new Message(FNPRoutedPong); msg.set(UID, uid); msg.set(COUNTER, counter); return msg; } public static final MessageType FNPRoutedRejected = new MessageType("FNPRoutedRejected", PRIORITY_UNSPECIFIED) {{ addField(UID, Long.class); addField(HTL, Short.class); }}; public static Message createFNPRoutedRejected(long uid, short htl) { Message msg = new Message(FNPRoutedRejected); msg.set(UID, uid); msg.set(HTL, htl); return msg; } public static final MessageType FNPDetectedIPAddress = new MessageType("FNPDetectedIPAddress", PRIORITY_HIGH) {{ addField(EXTERNAL_ADDRESS, Peer.class); }}; public static Message createFNPDetectedIPAddress(Peer peer) { Message msg = new Message(FNPDetectedIPAddress); msg.set(EXTERNAL_ADDRESS, peer); return msg; } public static final MessageType FNPTime = new MessageType("FNPTime", PRIORITY_HIGH) {{ addField(TIME, Long.class); }}; public static Message createFNPTime(long time) { Message msg = new Message(FNPTime); msg.set(TIME, time); return msg; } public static final MessageType FNPUptime = new MessageType("FNPUptime", PRIORITY_LOW) {{ addField(UPTIME_PERCENT_48H, Byte.class); }}; public static Message createFNPUptime(byte uptimePercent) { Message msg = new Message(FNPUptime); msg.set(UPTIME_PERCENT_48H, uptimePercent); return msg; } public static final MessageType FNPVisibility = new MessageType("FNPVisibility", PRIORITY_HIGH) {{ addField(FRIEND_VISIBILITY, Short.class); }}; public static Message createFNPVisibility(short visibility) { Message msg = new Message(FNPVisibility); msg.set(FRIEND_VISIBILITY, visibility); return msg; } // FIXME remove this message. public static final MessageType FNPSentPackets = new MessageType("FNPSentPackets", PRIORITY_HIGH) {{ addField(TIME_DELTAS, ShortBuffer.class); addField(HASHES, ShortBuffer.class); addField(TIME, Long.class); }}; public static final MessageType FNPVoid = new MessageType("FNPVoid", PRIORITY_LOW, false, true) {{ }}; public static Message createFNPVoid() { Message msg = new Message(FNPVoid); return msg; } public static final MessageType FNPDisconnect = new MessageType("FNPDisconnect", PRIORITY_HIGH) {{ // If true, remove from active routing table, likely to be down for a while. // Otherwise just dump all current connection state and keep trying to connect. addField(REMOVE, Boolean.class); // If true, purge all references to this node. Otherwise, we can keep the node // around in secondary tables etc in order to more easily reconnect later. // (Mostly used on opennet) addField(PURGE, Boolean.class); // Parting message, may be empty. A SimpleFieldSet in exactly the same format // as an N2NTM. addField(NODE_TO_NODE_MESSAGE_TYPE, Integer.class); addField(NODE_TO_NODE_MESSAGE_DATA, ShortBuffer.class); }}; public static Message createFNPDisconnect(boolean remove, boolean purge, int messageType, ShortBuffer messageData) { Message msg = new Message(FNPDisconnect); msg.set(REMOVE, remove); msg.set(PURGE, purge); msg.set(NODE_TO_NODE_MESSAGE_TYPE, messageType); msg.set(NODE_TO_NODE_MESSAGE_DATA, messageData); return msg; } // Update over mandatory. Not strictly part of FNP. Only goes between nodes at the link // level, and will be sent, and parsed, even if the node is out of date. Should be stable // long-term. public static final MessageType UOMAnnouncement = new MessageType("UOMAnnouncement", PRIORITY_LOW) {{ addField(MAIN_JAR_KEY, String.class); addField(REVOCATION_KEY, String.class); addField(HAVE_REVOCATION_KEY, Boolean.class); addField(MAIN_JAR_VERSION, Long.class); // Last time (ms ago) we had 3 DNFs in a row on the revocation checker. addField(REVOCATION_KEY_TIME_LAST_TRIED, Long.class); // Number of DNFs so far this time. addField(REVOCATION_KEY_DNF_COUNT, Integer.class); // For convenience, may change addField(REVOCATION_KEY_FILE_LENGTH, Long.class); addField(MAIN_JAR_FILE_LENGTH, Long.class); addField(PING_TIME, Integer.class); addField(BWLIMIT_DELAY_TIME, Integer.class); }}; public static Message createUOMAnnouncement(String mainKey, String revocationKey, boolean haveRevocation, long mainJarVersion, long timeLastTriedRevocationFetch, int revocationDNFCount, long revocationKeyLength, long mainJarLength, int pingTime, int bwlimitDelayTime) { Message msg = new Message(UOMAnnouncement); msg.set(MAIN_JAR_KEY, mainKey); msg.set(REVOCATION_KEY, revocationKey); msg.set(HAVE_REVOCATION_KEY, haveRevocation); msg.set(MAIN_JAR_VERSION, mainJarVersion); msg.set(REVOCATION_KEY_TIME_LAST_TRIED, timeLastTriedRevocationFetch); msg.set(REVOCATION_KEY_DNF_COUNT, revocationDNFCount); msg.set(REVOCATION_KEY_FILE_LENGTH, revocationKeyLength); msg.set(MAIN_JAR_FILE_LENGTH, mainJarLength); msg.set(PING_TIME, pingTime); msg.set(BWLIMIT_DELAY_TIME, bwlimitDelayTime); return msg; } public static final MessageType UOMRequestRevocation = new MessageType("UOMRequestRevocation", PRIORITY_HIGH) {{ addField(UID, Long.class); }}; public static Message createUOMRequestRevocation(long uid) { Message msg = new Message(UOMRequestRevocation); msg.set(UID, uid); return msg; } // Used by new UOM. public static final MessageType UOMRequestMainJar = new MessageType("UOMRequestMainJar", PRIORITY_LOW) {{ addField(UID, Long.class); }}; public static Message createUOMRequestMainJar(long uid) { Message msg = new Message(UOMRequestMainJar); msg.set(UID, uid); return msg; } public static final MessageType UOMSendingRevocation = new MessageType("UOMSendingRevocation", PRIORITY_HIGH) {{ addField(UID, Long.class); // Probably excessive, but lengths are always long's, and wasting a few bytes here // doesn't matter in the least, as it's very rarely called. addField(FILE_LENGTH, Long.class); addField(REVOCATION_KEY, String.class); }}; public static Message createUOMSendingRevocation(long uid, long length, String key) { Message msg = new Message(UOMSendingRevocation); msg.set(UID, uid); msg.set(FILE_LENGTH, length); msg.set(REVOCATION_KEY, key); return msg; } // Used by new UOM. We need to distinguish them in NodeDispatcher. public static final MessageType UOMSendingMainJar = new MessageType("UOMSendingMainJar", PRIORITY_LOW) {{ addField(UID, Long.class); addField(FILE_LENGTH, Long.class); addField(MAIN_JAR_KEY, String.class); addField(MAIN_JAR_VERSION, Integer.class); }}; public static Message createUOMSendingMainJar(long uid, long length, String key, int version) { Message msg = new Message(UOMSendingMainJar); msg.set(UID, uid); msg.set(FILE_LENGTH, length); msg.set(MAIN_JAR_KEY, key); msg.set(MAIN_JAR_VERSION, version); return msg; } /** Used to fetch a file required for deploying an update. The client * knows both the size and hash of the file. If we don't want to send * the data we should send an FNPBulkReceiveAborted, otherwise we just * send the data as a BulkTransmitter transfer. */ public static final MessageType UOMFetchDependency = new MessageType("UOMFetchDependency", PRIORITY_LOW) {{ addField(UID, Long.class); // This will be used for the transfer. addField(EXPECTED_HASH, ShortBuffer.class); // Fetch by hash addField(FILE_LENGTH, Long.class); // Length is known by both sides. }}; public static Message createUOMFetchDependency(long uid, byte[] hash, long length) { Message msg = new Message(UOMFetchDependency); msg.set(UID, uid); msg.set(EXPECTED_HASH, new ShortBuffer(hash)); msg.set(FILE_LENGTH, length); return msg; } // Secondary messages (debug messages attached to primary messages) public static final MessageType FNPSwapNodeUIDs = new MessageType("FNPSwapNodeUIDs", PRIORITY_UNSPECIFIED) {{ addField(NODE_UIDS, ShortBuffer.class); }}; public static Message createFNPSwapLocations(long[] uids) { Message msg = new Message(FNPSwapNodeUIDs); msg.set(NODE_UIDS, new ShortBuffer(Fields.longsToBytes(uids))); return msg; } // More permanent secondary messages (should perhaps be replaced by new main messages when stable) public static final MessageType FNPBestRoutesNotTaken = new MessageType("FNPBestRoutesNotTaken", PRIORITY_UNSPECIFIED) {{ // Maybe this should be some sort of typed array? // It's just a bunch of double's anyway. addField(BEST_LOCATIONS_NOT_VISITED, ShortBuffer.class); }}; public static Message createFNPBestRoutesNotTaken(byte[] locs) { Message msg = new Message(FNPBestRoutesNotTaken); msg.set(BEST_LOCATIONS_NOT_VISITED, new ShortBuffer(locs)); return msg; } public static Message createFNPBestRoutesNotTaken(double[] locs) { return createFNPBestRoutesNotTaken(Fields.doublesToBytes(locs)); } public static Message createFNPBestRoutesNotTaken(Double[] doubles) { double[] locs = new double[doubles.length]; for(int i=0;i<locs.length;i++) locs[i] = doubles[i].doubleValue(); return createFNPBestRoutesNotTaken(locs); } public static final MessageType FNPRoutingStatus = new MessageType("FNPRoutingStatus", PRIORITY_HIGH) {{ addField(ROUTING_ENABLED, Boolean.class); }}; public static Message createRoutingStatus(boolean routeRequests) { Message msg = new Message(FNPRoutingStatus); msg.set(ROUTING_ENABLED, routeRequests); return msg; } public static final MessageType FNPSubInsertForkControl = new MessageType("FNPSubInsertForkControl", PRIORITY_HIGH) {{ addField(ENABLE_INSERT_FORK_WHEN_CACHEABLE, Boolean.class); }}; public static Message createFNPSubInsertForkControl(boolean enableInsertForkWhenCacheable) { Message msg = new Message(FNPSubInsertForkControl); msg.set(ENABLE_INSERT_FORK_WHEN_CACHEABLE, enableInsertForkWhenCacheable); return msg; } public static final MessageType FNPSubInsertPreferInsert = new MessageType("FNPSubInsertPreferInsert", PRIORITY_HIGH) {{ addField(PREFER_INSERT, Boolean.class); }}; public static Message createFNPSubInsertPreferInsert(boolean preferInsert) { Message msg = new Message(FNPSubInsertPreferInsert); msg.set(PREFER_INSERT, preferInsert); return msg; } public static final MessageType FNPSubInsertIgnoreLowBackoff = new MessageType("FNPSubInsertIgnoreLowBackoff", PRIORITY_HIGH) {{ addField(IGNORE_LOW_BACKOFF, Boolean.class); }}; public static Message createFNPSubInsertIgnoreLowBackoff(boolean ignoreLowBackoff) { Message msg = new Message(FNPSubInsertIgnoreLowBackoff); msg.set(IGNORE_LOW_BACKOFF, ignoreLowBackoff); return msg; } public static final MessageType FNPRejectIsSoft = new MessageType("FNPRejectIsSoft", PRIORITY_HIGH) {{ // No fields??? }}; public static Message createFNPRejectIsSoft() { return new Message(FNPRejectIsSoft); } // New load management public static final MessageType FNPPeerLoadStatusByte = new MessageType("FNPPeerLoadStatusByte", PRIORITY_HIGH, false, true) {{ addField(OTHER_TRANSFERS_OUT_CHK, Byte.class); addField(OTHER_TRANSFERS_IN_CHK, Byte.class); addField(OTHER_TRANSFERS_OUT_SSK, Byte.class); addField(OTHER_TRANSFERS_IN_SSK, Byte.class); addField(AVERAGE_TRANSFERS_OUT_PER_INSERT, Byte.class); addField(OUTPUT_BANDWIDTH_LOWER_LIMIT, Integer.class); addField(OUTPUT_BANDWIDTH_UPPER_LIMIT, Integer.class); addField(OUTPUT_BANDWIDTH_PEER_LIMIT, Integer.class); addField(INPUT_BANDWIDTH_LOWER_LIMIT, Integer.class); addField(INPUT_BANDWIDTH_UPPER_LIMIT, Integer.class); addField(INPUT_BANDWIDTH_PEER_LIMIT, Integer.class); addField(MAX_TRANSFERS_OUT, Byte.class); addField(MAX_TRANSFERS_OUT_PEER_LIMIT, Byte.class); addField(MAX_TRANSFERS_OUT_LOWER_LIMIT, Byte.class); addField(MAX_TRANSFERS_OUT_UPPER_LIMIT, Byte.class); addField(REAL_TIME_FLAG, Boolean.class); }}; public static final MessageType FNPPeerLoadStatusShort = new MessageType("FNPPeerLoadStatusShort", PRIORITY_HIGH, false, true) {{ addField(OTHER_TRANSFERS_OUT_CHK, Short.class); addField(OTHER_TRANSFERS_IN_CHK, Short.class); addField(OTHER_TRANSFERS_OUT_SSK, Short.class); addField(OTHER_TRANSFERS_IN_SSK, Short.class); addField(AVERAGE_TRANSFERS_OUT_PER_INSERT, Short.class); addField(OUTPUT_BANDWIDTH_LOWER_LIMIT, Integer.class); addField(OUTPUT_BANDWIDTH_UPPER_LIMIT, Integer.class); addField(OUTPUT_BANDWIDTH_PEER_LIMIT, Integer.class); addField(INPUT_BANDWIDTH_LOWER_LIMIT, Integer.class); addField(INPUT_BANDWIDTH_UPPER_LIMIT, Integer.class); addField(INPUT_BANDWIDTH_PEER_LIMIT, Integer.class); addField(MAX_TRANSFERS_OUT, Short.class); addField(MAX_TRANSFERS_OUT_PEER_LIMIT, Short.class); addField(MAX_TRANSFERS_OUT_LOWER_LIMIT, Short.class); addField(MAX_TRANSFERS_OUT_UPPER_LIMIT, Short.class); addField(REAL_TIME_FLAG, Boolean.class); }}; public static final MessageType FNPPeerLoadStatusInt = new MessageType("FNPPeerLoadStatusInt", PRIORITY_HIGH, false, true) {{ addField(OTHER_TRANSFERS_OUT_CHK, Integer.class); addField(OTHER_TRANSFERS_IN_CHK, Integer.class); addField(OTHER_TRANSFERS_OUT_SSK, Integer.class); addField(OTHER_TRANSFERS_IN_SSK, Integer.class); addField(AVERAGE_TRANSFERS_OUT_PER_INSERT, Integer.class); addField(OUTPUT_BANDWIDTH_LOWER_LIMIT, Integer.class); addField(OUTPUT_BANDWIDTH_UPPER_LIMIT, Integer.class); addField(OUTPUT_BANDWIDTH_PEER_LIMIT, Integer.class); addField(INPUT_BANDWIDTH_LOWER_LIMIT, Integer.class); addField(INPUT_BANDWIDTH_UPPER_LIMIT, Integer.class); addField(INPUT_BANDWIDTH_PEER_LIMIT, Integer.class); addField(MAX_TRANSFERS_OUT, Integer.class); addField(MAX_TRANSFERS_OUT_PEER_LIMIT, Integer.class); addField(MAX_TRANSFERS_OUT_LOWER_LIMIT, Integer.class); addField(MAX_TRANSFERS_OUT_UPPER_LIMIT, Integer.class); addField(REAL_TIME_FLAG, Boolean.class); }}; public static Message createFNPPeerLoadStatus(PeerLoadStats stats) { Message msg; if(stats.expectedTransfersInCHK < 256 && stats.expectedTransfersInSSK < 256 && stats.expectedTransfersOutCHK < 256 && stats.expectedTransfersOutSSK < 256 && stats.averageTransfersOutPerInsert < 256 && stats.maxTransfersOut < 256 && stats.maxTransfersOutLowerLimit < 256 && stats.maxTransfersOutPeerLimit < 256 && stats.maxTransfersOutUpperLimit < 256) { msg = new Message(FNPPeerLoadStatusByte); msg.set(OTHER_TRANSFERS_OUT_CHK, (byte)stats.expectedTransfersOutCHK); msg.set(OTHER_TRANSFERS_IN_CHK, (byte)stats.expectedTransfersInCHK); msg.set(OTHER_TRANSFERS_OUT_SSK, (byte)stats.expectedTransfersOutSSK); msg.set(OTHER_TRANSFERS_IN_SSK, (byte)stats.expectedTransfersInSSK); msg.set(AVERAGE_TRANSFERS_OUT_PER_INSERT, (byte)stats.averageTransfersOutPerInsert); msg.set(MAX_TRANSFERS_OUT, (byte)stats.maxTransfersOut); msg.set(MAX_TRANSFERS_OUT_PEER_LIMIT, (byte)stats.maxTransfersOutPeerLimit); msg.set(MAX_TRANSFERS_OUT_LOWER_LIMIT, (byte)stats.maxTransfersOutLowerLimit); msg.set(MAX_TRANSFERS_OUT_UPPER_LIMIT, (byte)stats.maxTransfersOutUpperLimit); } else if(stats.expectedTransfersInCHK < 65536 && stats.expectedTransfersInSSK < 65536 && stats.expectedTransfersOutCHK < 65536 && stats.expectedTransfersOutSSK < 65536 && stats.averageTransfersOutPerInsert < 65536 && stats.maxTransfersOut < 65536 && stats.maxTransfersOutLowerLimit < 65536 && stats.maxTransfersOutPeerLimit < 65536 && stats.maxTransfersOutUpperLimit < 65536) { msg = new Message(FNPPeerLoadStatusShort); msg.set(OTHER_TRANSFERS_OUT_CHK, (short)stats.expectedTransfersOutCHK); msg.set(OTHER_TRANSFERS_IN_CHK, (short)stats.expectedTransfersInCHK); msg.set(OTHER_TRANSFERS_OUT_SSK, (short)stats.expectedTransfersOutSSK); msg.set(OTHER_TRANSFERS_IN_SSK, (short)stats.expectedTransfersInSSK); msg.set(AVERAGE_TRANSFERS_OUT_PER_INSERT, (short)stats.averageTransfersOutPerInsert); msg.set(MAX_TRANSFERS_OUT, (short)stats.maxTransfersOut); msg.set(MAX_TRANSFERS_OUT_PEER_LIMIT, (short)stats.maxTransfersOutPeerLimit); msg.set(MAX_TRANSFERS_OUT_LOWER_LIMIT, (short)stats.maxTransfersOutLowerLimit); msg.set(MAX_TRANSFERS_OUT_UPPER_LIMIT, (short)stats.maxTransfersOutUpperLimit); } else { msg = new Message(FNPPeerLoadStatusInt); msg.set(OTHER_TRANSFERS_OUT_CHK, stats.expectedTransfersOutCHK); msg.set(OTHER_TRANSFERS_IN_CHK, stats.expectedTransfersInCHK); msg.set(OTHER_TRANSFERS_OUT_SSK, stats.expectedTransfersOutSSK); msg.set(OTHER_TRANSFERS_IN_SSK, stats.expectedTransfersInSSK); msg.set(AVERAGE_TRANSFERS_OUT_PER_INSERT, stats.averageTransfersOutPerInsert); msg.set(MAX_TRANSFERS_OUT, stats.maxTransfersOut); msg.set(MAX_TRANSFERS_OUT_PEER_LIMIT, stats.maxTransfersOutPeerLimit); msg.set(MAX_TRANSFERS_OUT_LOWER_LIMIT, stats.maxTransfersOutLowerLimit); msg.set(MAX_TRANSFERS_OUT_UPPER_LIMIT, stats.maxTransfersOutUpperLimit); } msg.set(OUTPUT_BANDWIDTH_LOWER_LIMIT, (int)stats.outputBandwidthLowerLimit); msg.set(OUTPUT_BANDWIDTH_UPPER_LIMIT, (int)stats.outputBandwidthUpperLimit); msg.set(OUTPUT_BANDWIDTH_PEER_LIMIT, (int)stats.outputBandwidthPeerLimit); msg.set(INPUT_BANDWIDTH_LOWER_LIMIT, (int)stats.inputBandwidthLowerLimit); msg.set(INPUT_BANDWIDTH_UPPER_LIMIT, (int)stats.inputBandwidthUpperLimit); msg.set(INPUT_BANDWIDTH_PEER_LIMIT, (int)stats.inputBandwidthPeerLimit); msg.set(REAL_TIME_FLAG, stats.realTime); return msg; } public static final String AVERAGE_TRANSFERS_OUT_PER_INSERT = "averageTransfersOutPerInsert"; public static final String OTHER_TRANSFERS_OUT_CHK = "otherTransfersOutCHK"; public static final String OTHER_TRANSFERS_IN_CHK = "otherTransfersInCHK"; public static final String OTHER_TRANSFERS_OUT_SSK = "otherTransfersOutSSK"; public static final String OTHER_TRANSFERS_IN_SSK = "otherTransfersInSSK"; /** Maximum transfers out, hard limit based on congestion control; we will be rejected if our usage * is over this. */ public static final String MAX_TRANSFERS_OUT = "maxTransfersOut"; /** Maximum transfers out, peer limit. If total is over the lower limit and our usage is over the * peer limit, we will be rejected. */ public static final String MAX_TRANSFERS_OUT_PEER_LIMIT = "maxTransfersOutPeerLimit"; /** Maximum transfers out, lower limit. If total is over the lower limit and our usage is over the * peer limit, we will be rejected. */ public static final String MAX_TRANSFERS_OUT_LOWER_LIMIT = "maxTransfersOutLowerLimit"; /** Maximum transfers out, upper limit. If total is over the upper limit, everything is rejected. */ public static final String MAX_TRANSFERS_OUT_UPPER_LIMIT = "maxTransfersOutUpperLimit"; public static final String OUTPUT_BANDWIDTH_LOWER_LIMIT = "outputBandwidthLowerLimit"; public static final String OUTPUT_BANDWIDTH_UPPER_LIMIT = "outputBandwidthUpperLimit"; public static final String OUTPUT_BANDWIDTH_PEER_LIMIT = "outputBandwidthPeerLimit"; public static final String INPUT_BANDWIDTH_LOWER_LIMIT = "inputBandwidthLowerLimit"; public static final String INPUT_BANDWIDTH_UPPER_LIMIT = "inputBandwidthUpperLimit"; public static final String INPUT_BANDWIDTH_PEER_LIMIT = "inputBandwidthPeerLimit"; public static final String REAL_TIME_FLAG = "realTimeFlag"; public static final MessageType FNPRealTimeFlag = new MessageType("FNPRealTimeFlag", PRIORITY_HIGH) {{ addField(REAL_TIME_FLAG, Boolean.class); }}; public static Message createFNPRealTimeFlag(boolean isBulk) { Message msg = new Message(FNPRealTimeFlag); msg.set(REAL_TIME_FLAG, isBulk); return msg; } public static boolean getRealTimeFlag(Message m) { Message bulk = m.getSubMessage(FNPRealTimeFlag); if(bulk == null) return false; return bulk.getBoolean(REAL_TIME_FLAG); } public static boolean isPeerLoadStatusMessage(Message m) { MessageType spec = m.getSpec(); return (spec == FNPPeerLoadStatusByte || spec == FNPPeerLoadStatusShort || spec == FNPPeerLoadStatusInt); } public static boolean isLoadLimitedRequest(Message m) { MessageType spec = m.getSpec(); return (spec == FNPCHKDataRequest || spec == FNPSSKDataRequest || spec == FNPSSKInsertRequest || spec == FNPInsertRequest || spec == FNPSSKInsertRequestNew || spec == FNPGetOfferedKey); } // Extended fatal timeout handling. public static final MessageType FNPCheckStillRunning = new MessageType("FNPCheckStillRunning", PRIORITY_HIGH) {{ addField(UID, Long.class); // UID for this message, used to identify reply addField(LIST_OF_UIDS, ShortBuffer.class); }}; public static final MessageType FNPIsStillRunning = new MessageType("FNPIsStillRunning", PRIORITY_HIGH) {{ addField(UID, Long.class); addField(UID_STILL_RUNNING_FLAGS, BitArray.class); }}; // Friend-of-a-friend (FOAF) related messages public static final MessageType FNPGetYourFullNoderef = new MessageType("FNPGetYourFullNoderef", PRIORITY_LOW) {{ }}; public static Message createFNPGetYourFullNoderef() { return new Message(FNPGetYourFullNoderef); } public static final MessageType FNPMyFullNoderef = new MessageType("FNPMyFullNoderef", PRIORITY_LOW) {{ addField(UID, Long.class); // Not necessary to pad it since it's not propagated across the network. // It might be relayed one hop, but there's enough padding elsewhere, don't worry about it. // As opposed to opennet refs, which are relayed long distances, down request paths which they might reveal, so do need to be padded. addField(NODEREF_LENGTH, Integer.class); }}; public static Message createFNPMyFullNoderef(long uid, int length) { Message m = new Message(FNPMyFullNoderef); m.set(UID, uid); m.set(NODEREF_LENGTH, length); return m; } }