2006-12-24 Tatsuhiro Tsujikawa <tujikawa at rednoah dot com>

Rewritten a portion of bittorrent implementation:
	
	* src/BtMessageValidator.h: New class.
	* src/BtBitfieldMessageValidator.h: New class.
	* src/BtHandshakeMessageValidator.h: New class.
	* src/BtRequestMessageValidator.h: New class.
	* src/BtSuggestPieceMessageValidator.h: New class.
	* src/BtAllowedFastMessageValidator.h: New class.
	* src/BtRejectMessageValidator.h: New class.
	* src/BtCancelMessageValidator.h: New class.
	* src/BtPieceMessageValidator.h: New class.
	* src/BtHaveMessageValidator.h: New class.
	* src/BtEventListener.h: New class.
	* src/AbstractBtEventListener.h: New class.
	* src/BtEvent.h: New class.
	* src/BtChokingEvent.h: New class.
	* src/BtChokedEvent.h: New class.
	* src/BtCancelSendingPieceEvent.h: New class.
	* src/BtAbortOutstandingRequestEvent.h: New class.
	* src/Randomizer.h: New class.
	* src/SimpleRandomizer.h: New class.
	* src/BtMessage.h: New class.
	* src/AbstractBtMessage.h: New class.
	* src/SimpleBtMessage.h: New class.
	* src/BtHaveMessage.h: New class.
	* src/BtInterestedMessage.h: New class.
	* src/BtAllowedFastMessage.h: New class.
	* src/BtUnchokeMessage.h: New class.
	* src/BtCancelMessage.h: New class.
	* src/BtNotInterestedMessage.h: New class.
	* src/BtChokeMessage.h: New class.
	* src/BtHaveNoneMessage.h: New class.
	* src/BtHandshakeMessage.h: New class.
	* src/BtSuggestPieceMessage.h: New class.
	* src/BtHaveMessage.h: New class.
	* src/BtPieceMessage.h: New class.
	* src/BtHaveAllMessage.h: New class.
	* src/BtKeepAliveMessage.h: New class.
	* src/BtPortMessage.h: New class.
	* src/BtRejectMessage.h: New class.
	* src/BtBitfieldMessage.h: New class.
	* src/BtRequestMessage.h: New class.
	* src/DefaultBtRequestFactory.h: New class.
	* src/DefaultBtMessageReceiver.h: New class.
	* src/BtInteractive.h: New class.
	* src/BtMessageDispatcher.h: New class.
	* src/DefaultBtMessageDispatcher.h: New class.
	* src/DefaultBtInteractive.h: New class.
	* src/BitfieldManFactory.h: New class.
	* src/HandleRegistry.h: New class.
	* src/BtMessageFactory.h: New class.
	* src/BtMessageReceiver.h: New class.
	* src/DefaultBtMessageFactory.h: New class.
	* src/PeerObject.h: New class.
	* src/BtRequestFactory.h: New class.
pull/1/head
Tatsuhiro Tsujikawa 2006-12-24 06:25:21 +00:00
parent 458cc27462
commit 9c3e8fbd9c
162 changed files with 11207 additions and 663 deletions

View File

@ -1,3 +1,61 @@
2006-12-24 Tatsuhiro Tsujikawa <tujikawa at rednoah dot com>
Rewritten a portion of bittorrent implementation:
* src/BtMessageValidator.h: New class.
* src/BtBitfieldMessageValidator.h: New class.
* src/BtHandshakeMessageValidator.h: New class.
* src/BtRequestMessageValidator.h: New class.
* src/BtSuggestPieceMessageValidator.h: New class.
* src/BtAllowedFastMessageValidator.h: New class.
* src/BtRejectMessageValidator.h: New class.
* src/BtCancelMessageValidator.h: New class.
* src/BtPieceMessageValidator.h: New class.
* src/BtHaveMessageValidator.h: New class.
* src/BtEventListener.h: New class.
* src/AbstractBtEventListener.h: New class.
* src/BtEvent.h: New class.
* src/BtChokingEvent.h: New class.
* src/BtChokedEvent.h: New class.
* src/BtCancelSendingPieceEvent.h: New class.
* src/BtAbortOutstandingRequestEvent.h: New class.
* src/Randomizer.h: New class.
* src/SimpleRandomizer.h: New class.
* src/BtMessage.h: New class.
* src/AbstractBtMessage.h: New class.
* src/SimpleBtMessage.h: New class.
* src/BtHaveMessage.h: New class.
* src/BtInterestedMessage.h: New class.
* src/BtAllowedFastMessage.h: New class.
* src/BtUnchokeMessage.h: New class.
* src/BtCancelMessage.h: New class.
* src/BtNotInterestedMessage.h: New class.
* src/BtChokeMessage.h: New class.
* src/BtHaveNoneMessage.h: New class.
* src/BtHandshakeMessage.h: New class.
* src/BtSuggestPieceMessage.h: New class.
* src/BtHaveMessage.h: New class.
* src/BtPieceMessage.h: New class.
* src/BtHaveAllMessage.h: New class.
* src/BtKeepAliveMessage.h: New class.
* src/BtPortMessage.h: New class.
* src/BtRejectMessage.h: New class.
* src/BtBitfieldMessage.h: New class.
* src/BtRequestMessage.h: New class.
* src/DefaultBtRequestFactory.h: New class.
* src/DefaultBtMessageReceiver.h: New class.
* src/BtInteractive.h: New class.
* src/BtMessageDispatcher.h: New class.
* src/DefaultBtMessageDispatcher.h: New class.
* src/DefaultBtInteractive.h: New class.
* src/BitfieldManFactory.h: New class.
* src/HandleRegistry.h: New class.
* src/BtMessageFactory.h: New class.
* src/BtMessageReceiver.h: New class.
* src/DefaultBtMessageFactory.h: New class.
* src/PeerObject.h: New class.
* src/BtRequestFactory.h: New class.
2006-12-01 Tatsuhiro Tsujikawa <tujikawa at rednoah dot com>
To know root cause of exception:

11
TODO
View File

@ -20,4 +20,13 @@
* Add Turkish translation.
* Add the message like "you can resume the transfer by invoking aria2 again" when the download stops.
* Add --bt-timeout command line option.
* Fix DefaultBtProgressInfoFile.cc: save(), load()
* Fix DefaultBtProgressInfoFile.cc: save(), load()
* Add a feature that if any existing file is detected, then
do not start downloading and print some useful message to the user.
* Fix Segfaults in BitfieldMan.cc:71
https://sourceforge.net/tracker/index.php?func=detail&aid=1606060&group_id=159897&atid=813673
* Prevent the file to be fragmented. Use PreAllocationDiskWriter
https://sourceforge.net/tracker/index.php?func=detail&aid=1611886&group_id=159897&atid=813673
* Add #include <libgen.h> to DefaultBtContext.h
* int32_t
* remove blockIndex

View File

@ -0,0 +1,55 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_ABSTRACT_BT_EVENT_LISTENER_H_
#define _D_ABSTRACT_BT_EVENT_LISTENER_H_
#include "BtEventListener.h"
class AbstractBtEventListener : public BtEventListener {
public:
virtual ~AbstractBtEventListener() {}
virtual bool canHandle(const BtEventHandle& event) = 0;
virtual void handleEventInternal(const BtEventHandle& event) = 0;
virtual void handleEvent(const BtEventHandle& event) {
if(canHandle(event)) {
handleEventInternal(event);
}
}
};
#endif // _D_ABSTRACT_BT_EVENT_LISTENER_H_

167
src/AbstractBtMessage.h Normal file
View File

@ -0,0 +1,167 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_ABSTRACT_BT_MESSAGE_H_
#define _D_ABSTRACT_BT_MESSAGE_H_
#include "BtMessage.h"
#include "Peer.h"
#include "Piece.h"
#include "LogFactory.h"
#include "Logger.h"
#include "BtEvent.h"
#include "BtEventListener.h"
#include "BtContext.h"
#include "BtRegistry.h"
class AbstractBtMessage : public BtMessage {
protected:
bool sendingInProgress;
bool invalidate;
bool uploading;
int32_t id;
int32_t cuid;
BtContextHandle btContext;
PieceStorageHandle pieceStorage;
PeerHandle peer;
BtMessageValidatorHandle validator;
BtEventListeners listeners;
const Logger* logger;
public:
AbstractBtMessage():sendingInProgress(false),
invalidate(false),
uploading(false),
id(0),
cuid(0),
btContext(0),
pieceStorage(0),
peer(0),
validator(0),
logger(LogFactory::getInstance())
{}
virtual bool isSendingInProgress() {
return sendingInProgress;
}
void setSendingInProgress(bool sendingInProgress) {
this->sendingInProgress = sendingInProgress;
}
virtual bool isInvalidate() {
return invalidate;
}
void setInvalidate(bool invalidate) {
this->invalidate = invalidate;
}
virtual bool isUploading() {
return uploading;
}
void setUploading(bool uploading) {
this->uploading = uploading;
}
virtual int32_t getId() {
return id;
}
int32_t getCuid() const {
return cuid;
}
void setCuid(int32_t cuid) {
this->cuid = cuid;
}
PeerHandle getPeer() const {
return peer;
}
void setPeer(const PeerHandle& peer) {
this->peer = peer;
}
virtual void doReceivedAction() {}
virtual bool validate(Errors& errors) {
if(validator.get()) {
return validator->validate(errors);
} else {
return true;
}
}
virtual void onQueued() {}
virtual void handleEvent(const BtEventHandle& event) {
for(BtEventListeners::iterator itr = listeners.begin();
itr != listeners.end(); ++itr) {
(*itr)->handleEvent(event);
}
}
void addEventListener(const BtEventListenerHandle& listener) {
listeners.push_back(listener);
}
void setBtMessageValidator(const BtMessageValidatorHandle& validator) {
this->validator = validator;
}
BtMessageValidatorHandle getBtMessageValidator() const {
return validator;
}
void setBtContext(const BtContextHandle& btContext) {
this->btContext = btContext;
this->pieceStorage = PIECE_STORAGE(btContext);
}
BtContextHandle getBtContext() const {
return btContext;
}
};
typedef SharedHandle<AbstractBtMessage> AbstractBtMessageHandle;
#endif // _D_ABSTRACT_BT_MESSAGE_H_

View File

@ -38,7 +38,7 @@
BitfieldMan::BitfieldMan(int blockLength, long long int totalLength)
:blockLength(blockLength), totalLength(totalLength), filterBitfield(0),
filterEnabled(false) {
filterEnabled(false), randomizer(0) {
if(blockLength > 0 && totalLength > 0) {
blocks = totalLength/blockLength+(totalLength%blockLength ? 1 : 0);
bitfieldLength = blocks/8+(blocks%8 ? 1 : 0);
@ -49,7 +49,7 @@ BitfieldMan::BitfieldMan(int blockLength, long long int totalLength)
}
}
BitfieldMan::BitfieldMan(const BitfieldMan& bitfieldMan) {
BitfieldMan::BitfieldMan(const BitfieldMan& bitfieldMan):randomizer(0) {
blockLength = bitfieldMan.blockLength;
totalLength = bitfieldMan.totalLength;
blocks = bitfieldMan.blocks;
@ -65,6 +65,7 @@ BitfieldMan::BitfieldMan(const BitfieldMan& bitfieldMan) {
} else {
filterBitfield = 0;
}
this->randomizer = bitfieldMan.randomizer;
}
BitfieldMan::~BitfieldMan() {
@ -106,7 +107,9 @@ int
BitfieldMan::getMissingIndexRandomly(const unsigned char* bitfield,
int bitfieldLength) const
{
int byte = (int)(((double)bitfieldLength)*random()/(RAND_MAX+1.0));
int byte = (int)(((double)bitfieldLength)*
randomizer->getRandomNumber()/
(randomizer->getMaxRandomNumber()+1.0));
unsigned char lastMask = 0;
int lastByteLength = totalLength%(blockLength*8);

View File

@ -36,6 +36,7 @@
#define _D_BITFIELD_MAN_H_
#include "common.h"
#include "Randomizer.h"
#include <deque>
typedef deque<int> BlockIndexes;
@ -50,6 +51,8 @@ private:
int bitfieldLength;
int blocks;
bool filterEnabled;
RandomizerHandle randomizer;
int countSetBit(const unsigned char* bitfield, int len) const;
int getNthBitIndex(const unsigned char bit, int nth) const;
int getMissingIndexRandomly(const unsigned char* bitfield, int len) const;
@ -176,6 +179,8 @@ public:
*/
int countBlock() const;
int getMaxIndex() const { return blocks-1; }
void setBitfield(const unsigned char* bitfield, int bitfieldLength);
void clearAllBit();
@ -202,6 +207,14 @@ public:
* affected by filter
*/
long long int getFilteredCompletedLength() const;
void setRandomizer(const RandomizerHandle& randomizer) {
this->randomizer = randomizer;
}
RandomizerHandle getRandomizer() const {
return randomizer;
}
};
#endif // _D_BITFIELD_MAN_H_

40
src/BitfieldManFactory.cc Normal file
View File

@ -0,0 +1,40 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BitfieldManFactory.h"
#include "SimpleRandomizer.h"
RandomizerHandle BitfieldManFactory::defaultRandomizer = SimpleRandomizer::getInstance();
BitfieldManFactory::BitfieldManFactory():randomizer(defaultRandomizer) {}

85
src/BitfieldManFactory.h Normal file
View File

@ -0,0 +1,85 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BITFIELD_MAN_FACTORY_H_
#define _D_BITFIELD_MAN_FACTORY_H_
#include "common.h"
#include "Randomizer.h"
#include "BitfieldMan.h"
class BitfieldManFactory;
typedef SharedHandle<BitfieldManFactory> BitfieldManFactoryHandle;
class BitfieldManFactory {
private:
static RandomizerHandle defaultRandomizer;
RandomizerHandle randomizer;
BitfieldManFactory();
public:
~BitfieldManFactory() {}
static BitfieldManFactoryHandle getNewFactory() {
BitfieldManFactoryHandle factory =
BitfieldManFactoryHandle(new BitfieldManFactory());
factory->setRandomizer(defaultRandomizer);
return factory;
}
BitfieldMan* createBitfieldMan(int blockLength, long long int totalLength) {
BitfieldMan* bitfieldMan = new BitfieldMan(blockLength, totalLength);
bitfieldMan->setRandomizer(randomizer);
return bitfieldMan;
}
static void setDefaultRandomizer(const RandomizerHandle& randomizer) {
defaultRandomizer = randomizer;
}
static RandomizerHandle getDefaultRandomizer() {
return defaultRandomizer;
}
void setRandomizer(const RandomizerHandle& randomizer) {
this->randomizer = randomizer;
}
RandomizerHandle getRandomizer() const {
return randomizer;
}
};
#endif // _D_BITFIELD_MAN_FACTORY_H_

View File

@ -0,0 +1,57 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_ABORT_OUTSTANDING_REQUEST_EVENT_H_
#define _D_BT_ABORT_OUTSTANDING_REQUEST_EVENT_H_
#include "BtEvent.h"
class BtAbortOutstandingRequestEvent : public BtEvent {
private:
PieceHandle piece;
public:
BtAbortOutstandingRequestEvent(const PieceHandle& piece):piece(piece) {}
PieceHandle getPiece() const {
return piece;
}
void setPiece(const PieceHandle& piece) {
this->piece = piece;
}
};
typedef SharedHandle<BtAbortOutstandingRequestEvent> BtAbortOutstandingRequestEventHandle;
#endif // _D_BT_ABORT_OUTSTANDING_REQUEST_EVENT_H_

View File

@ -0,0 +1,89 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtAllowedFastMessage.h"
#include "PeerMessageUtil.h"
#include "Util.h"
#include "DlAbortEx.h"
BtAllowedFastMessageHandle BtAllowedFastMessage::create(const unsigned char* data, uint32_t dataLength) {
if(dataLength != 5) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be %d", "allowed fast", dataLength, 5);
}
uint32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "allowed fast", ID);
}
BtAllowedFastMessageHandle message = new BtAllowedFastMessage();
message->setIndex(PeerMessageUtil::getIntParam(data, 1));
return message;
}
void BtAllowedFastMessage::doReceivedAction() {
if(!peer->isFastExtensionEnabled()) {
throw new DlAbortEx("%s received while fast extension is disabled",
toString().c_str());
}
peer->addPeerAllowedIndex(index);
}
uint32_t BtAllowedFastMessage::MESSAGE_LENGTH = 9;
const char* BtAllowedFastMessage::getMessage() {
if(!msg) {
/**
* len --- 5, 4bytes
* id --- 17, 1byte
* piece index --- index, 4bytes
* total: 9bytes
*/
msg = new char[MESSAGE_LENGTH];
PeerMessageUtil::createPeerMessageString(msg, MESSAGE_LENGTH, 5, ID);
PeerMessageUtil::setIntParam(&msg[5], index);
}
return msg;
}
uint32_t BtAllowedFastMessage::getMessageLength() {
return MESSAGE_LENGTH;
}
void BtAllowedFastMessage::onSendComplete() {
peer->addAmAllowedIndex(index);
}
string BtAllowedFastMessage::toString() const {
return "allowed fast index="+Util::uitos(index);
}

View File

@ -0,0 +1,85 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_ALLOWED_FAST_MESSAGE_H_
#define _D_BT_ALLOWED_FAST_MESSAGE_H_
#include "SimpleBtMessage.h"
class BtAllowedFastMessage;
typedef SharedHandle<BtAllowedFastMessage> BtAllowedFastMessageHandle;
class BtAllowedFastMessage : public SimpleBtMessage {
private:
uint32_t index;
char* msg;
static uint32_t MESSAGE_LENGTH;
public:
BtAllowedFastMessage(uint32_t index = 0)
:SimpleBtMessage(),
index(index),
msg(0) {}
virtual ~BtAllowedFastMessage() {
delete [] msg;
}
enum ID_t {
ID = 17
};
void setIndex(uint32_t index) {
this->index = index;
}
uint32_t getIndex() const { return index; }
static BtAllowedFastMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction();
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual string toString() const;
virtual void onSendComplete();
};
#endif // _D_BT_ALLOWED_FAST_MESSAGE_H_

View File

@ -0,0 +1,60 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_ALLOWED_FAST_MESSAGE_VALIDATOR_H_
#define _D_BT_ALLOWED_FAST_MESSAGE_VALIDATOR_H_
#include "BtMessageValidator.h"
#include "BtAllowedFastMessage.h"
class BtAllowedFastMessageValidator : public BtMessageValidator {
private:
const BtAllowedFastMessage* message;
uint32_t numPiece;
public:
BtAllowedFastMessageValidator(const BtAllowedFastMessage* message,
uint32_t numPiece):
message(message),
numPiece(numPiece) {}
virtual bool validate(Errors& error) {
// TODO
PeerMessageUtil::checkIndex(message->getIndex(), numPiece);
return true;
}
};
typedef SharedHandle<BtAllowedFastMessageValidator> BtAllowedFastMessageValidatorHandle;
#endif // _D_BT_ALLOWED_FAST_MESSAGE_VALIDATOR_H_

View File

@ -99,11 +99,6 @@ public:
* Shuffles the URLs in each announce tier.
*/
virtual void shuffleAnnounce() = 0;
/**
* Returns the peer id of the client.
*/
virtual string getPeerId() = 0;
};
typedef SharedHandle<BtAnnounce> BtAnnounceHandle;

95
src/BtBitfieldMessage.cc Normal file
View File

@ -0,0 +1,95 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtBitfieldMessage.h"
#include "PeerMessageUtil.h"
#include "Util.h"
#include "DlAbortEx.h"
void BtBitfieldMessage::setBitfield(const unsigned char* bitfield, uint32_t bitfieldLength) {
if(this->bitfield == bitfield) {
return;
}
delete [] this->bitfield;
this->bitfieldLength = bitfieldLength;
this->bitfield = new unsigned char[this->bitfieldLength];
memcpy(this->bitfield, bitfield, this->bitfieldLength);
}
BtBitfieldMessageHandle
BtBitfieldMessage::create(const unsigned char* data, uint32_t dataLength)
{
if(dataLength <= 1) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be greater than %d", "bitfield", dataLength, 1);
}
int32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "bitfield", ID);
}
BtBitfieldMessageHandle message = new BtBitfieldMessage();
message->setBitfield((unsigned char*)data+1, dataLength-1);
return message;
}
void BtBitfieldMessage::doReceivedAction() {
peer->setBitfield(bitfield, bitfieldLength);
}
const char* BtBitfieldMessage::getMessage() {
if(!msg) {
/**
* len --- 1+bitfieldLength, 4bytes
* id --- 5, 1byte
* bitfield --- bitfield, len bytes
* total: 5+len bytes
*/
msgLength = 5+bitfieldLength;
msg = new char[msgLength];
PeerMessageUtil::createPeerMessageString(msg, msgLength,
1+bitfieldLength, ID);
memcpy(msg+5, bitfield, bitfieldLength);
}
return msg;
}
uint32_t BtBitfieldMessage::getMessageLength() {
getMessage();
return msgLength;
}
string BtBitfieldMessage::toString() const {
return "bitfield "+Util::toHex(bitfield, bitfieldLength);
}

98
src/BtBitfieldMessage.h Normal file
View File

@ -0,0 +1,98 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_BITFIELD_MESSAGE_H_
#define _D_BT_BITFIELD_MESSAGE_H_
#include "SimpleBtMessage.h"
class BtBitfieldMessage;
typedef SharedHandle<BtBitfieldMessage> BtBitfieldMessageHandle;
class BtBitfieldMessage : public SimpleBtMessage {
private:
unsigned char* bitfield;
uint32_t bitfieldLength;
char* msg;
int msgLength;
void init() {
bitfield = 0;
bitfieldLength = 0;
msg = 0;
msgLength = 0;
}
public:
BtBitfieldMessage():SimpleBtMessage()
{
init();
}
BtBitfieldMessage(const unsigned char* bitfield,
uint32_t bitfieldLength):SimpleBtMessage()
{
init();
setBitfield(bitfield, bitfieldLength);
}
virtual ~BtBitfieldMessage() {
delete [] bitfield;
delete [] msg;
}
enum ID_t {
ID = 5
};
void setBitfield(const unsigned char* bitfield, uint32_t bitfieldLength);
const unsigned char* getBitfield() const { return bitfield; }
uint32_t getBitfieldLength() const { return bitfieldLength; }
static BtBitfieldMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction();
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual string toString() const;
};
#endif // _D_BT_BITFIELD_MESSAGE_H_

View File

@ -0,0 +1,61 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_BITFIELD_MESSAGE_VALIDATOR_H_
#define _D_BT_BITFIELD_MESSAGE_VALIDATOR_H_
#include "BtMessageValidator.h"
#include "BtBitfieldMessage.h"
class BtBitfieldMessageValidator : public BtMessageValidator {
private:
const BtBitfieldMessage* message;
int numPiece;
public:
BtBitfieldMessageValidator(const BtBitfieldMessage* message,
int numPiece):
message(message),
numPiece(numPiece) {}
virtual bool validate(Errors& error) {
// TODO
PeerMessageUtil::checkBitfield(message->getBitfield(),
message->getBitfieldLength(),
numPiece);
return true;
}
};
typedef SharedHandle<BtBitfieldMessageValidator> BtBitfieldMessageValidatorHandle;
#endif // _D_BT_BITFIELD_MESSAGE_VALIDATOR_H_

88
src/BtCancelMessage.cc Normal file
View File

@ -0,0 +1,88 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtCancelMessage.h"
#include "PeerMessageUtil.h"
#include "Util.h"
#include "DlAbortEx.h"
BtCancelMessageHandle BtCancelMessage::create(const unsigned char* data, uint32_t dataLength) {
if(dataLength != 13) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be %d", "cancel", dataLength, 13);
}
int32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "cancel", ID);
}
BtCancelMessageHandle message = new BtCancelMessage();
message->setIndex(PeerMessageUtil::getIntParam(data, 1));
message->setBegin(PeerMessageUtil::getIntParam(data, 5));
message->setLength(PeerMessageUtil::getIntParam(data, 9));
return message;
}
void BtCancelMessage::doReceivedAction() {
BT_MESSAGE_DISPATCHER(btContext, peer)->doCancelSendingPieceAction(index, begin, length);
}
uint32_t BtCancelMessage::MESSAGE_LENGTH = 17;
const char* BtCancelMessage::getMessage() {
if(!msg) {
/**
* len --- 13, 4bytes
* id --- 8, 1byte
* index --- index, 4bytes
* begin --- begin, 4bytes
* length -- length, 4bytes
* total: 17bytes
*/
msg = new char[MESSAGE_LENGTH];
PeerMessageUtil::createPeerMessageString(msg, MESSAGE_LENGTH, 13, ID);
PeerMessageUtil::setIntParam(&msg[5], index);
PeerMessageUtil::setIntParam(&msg[9], begin);
PeerMessageUtil::setIntParam(&msg[13], length);
}
return msg;
}
uint32_t BtCancelMessage::getMessageLength() {
return MESSAGE_LENGTH;
}
string BtCancelMessage::toString() const {
return "cancel index="+Util::uitos(index)+", begin="+Util::uitos(begin)+
", length="+Util::uitos(length);
}

93
src/BtCancelMessage.h Normal file
View File

@ -0,0 +1,93 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_CANCEL_MESSAGE_H_
#define _D_BT_CANCEL_MESSAGE_H_
#include "SimpleBtMessage.h"
class BtCancelMessage;
typedef SharedHandle<BtCancelMessage> BtCancelMessageHandle;
class BtCancelMessage : public SimpleBtMessage {
private:
uint32_t index;
uint32_t begin;
uint32_t length;
char* msg;
static uint32_t MESSAGE_LENGTH;
public:
BtCancelMessage(uint32_t index = 0, uint32_t begin = 0, uint32_t length = 0)
:SimpleBtMessage(),
index(index),
begin(begin),
length(length),
msg(0) {}
virtual ~BtCancelMessage() {
delete [] msg;
}
enum ID_t {
ID = 8
};
uint32_t getIndex() const { return index; }
void setIndex(uint32_t index) { this->index = index; }
uint32_t getBegin() const { return begin; }
void setBegin(uint32_t begin) { this->begin = begin; }
uint32_t getLength() const { return length; }
void setLength(uint32_t length) { this->length = length; }
static BtCancelMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction();
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual string toString() const;
};
#endif // _D_BT_CANCEL_MESSAGE_H_

View File

@ -0,0 +1,67 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_CANCEL_MESSAGE_VALIDATOR_H_
#define _D_BT_CANCEL_MESSAGE_VALIDATOR_H_
#include "BtMessageValidator.h"
#include "BtCancelMessage.h"
class BtCancelMessageValidator : public BtMessageValidator {
private:
const BtCancelMessage* message;
uint32_t numPiece;
uint32_t pieceLength;
public:
BtCancelMessageValidator(const BtCancelMessage* message,
uint32_t numPiece,
uint32_t pieceLength):
message(message),
numPiece(numPiece),
pieceLength(pieceLength) {}
virtual bool validate(Errors& error) {
// TODO
PeerMessageUtil::checkIndex(message->getIndex(), numPiece);
PeerMessageUtil::checkBegin(message->getBegin(), pieceLength);
PeerMessageUtil::checkLength(message->getLength());
PeerMessageUtil::checkRange(message->getBegin(), message->getLength(),
pieceLength);
return true;
}
};
typedef SharedHandle<BtCancelMessageValidator> BtCancelMessageValidatorHandle;
#endif // _D_BT_CANCEL_MESSAGE_VALIDATOR_H_

View File

@ -0,0 +1,78 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_CANCEL_SENDING_PIECE_EVENT_H_
#define _D_BT_CANCEL_SENDING_PIECE_EVENT_H_
#include "BtEvent.h"
class BtCancelSendingPieceEvent : public BtEvent {
private:
uint32_t index;
uint32_t begin;
uint32_t length;
public:
BtCancelSendingPieceEvent(uint32_t index, uint32_t begin, uint32_t length):
index(index), begin(begin), length(length) {}
virtual ~BtCancelSendingPieceEvent() {}
void setIndex(uint32_t index) {
this->index = index;
}
uint32_t getIndex() const {
return index;
}
void setBegin(uint32_t begin) {
this->begin = begin;
}
uint32_t getBegin() const {
return begin;
}
void setLength(uint32_t length) {
this->length = length;
}
uint32_t getLength() const {
return length;
}
};
typedef SharedHandle<BtCancelSendingPieceEvent> BtCancelSendingPieceEventHandle;
#endif // _D_BT_CANCEL_SENDING_PIECE_EVENT_H_

87
src/BtChokeMessage.cc Normal file
View File

@ -0,0 +1,87 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtChokeMessage.h"
#include "PeerMessageUtil.h"
#include "DlAbortEx.h"
BtChokeMessageHandle BtChokeMessage::create(const unsigned char* data, uint32_t dataLength) {
if(dataLength != 1) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be %d", "choke", dataLength, 1);
}
int32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "choke", ID);
}
BtChokeMessageHandle chokeMessage = new BtChokeMessage();
return chokeMessage;
}
void BtChokeMessage::doReceivedAction() {
peer->peerChoking = true;
BT_MESSAGE_DISPATCHER(btContext, peer)->doChokedAction();
}
bool BtChokeMessage::sendPredicate() const {
return !peer->amChoking;
}
uint32_t BtChokeMessage::MESSAGE_LENGTH = 5;
const char* BtChokeMessage::getMessage() {
if(!msg) {
/**
* len --- 1, 4bytes
* id --- 0, 1byte
* total: 5bytes
*/
msg = new char[MESSAGE_LENGTH];
PeerMessageUtil::createPeerMessageString(msg, MESSAGE_LENGTH, 1, ID);
}
return msg;
}
uint32_t BtChokeMessage::getMessageLength() {
return MESSAGE_LENGTH;
}
void BtChokeMessage::onSendComplete() {
peer->amChoking = true;
BT_MESSAGE_DISPATCHER(btContext, peer)->doChokingAction();
}
string BtChokeMessage::toString() const {
return "choke";
}

77
src/BtChokeMessage.h Normal file
View File

@ -0,0 +1,77 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_CHOKE_MESSAGE_H_
#define _D_BT_CHOKE_MESSAGE_H_
#include "SimpleBtMessage.h"
class BtChokeMessage;
typedef SharedHandle<BtChokeMessage> BtChokeMessageHandle;
class BtChokeMessage : public SimpleBtMessage {
private:
char* msg;
static uint32_t MESSAGE_LENGTH;
public:
BtChokeMessage():SimpleBtMessage(), msg(0) {}
virtual ~BtChokeMessage() {
delete [] msg;
}
enum ID_t {
ID = 0
};
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction();
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual string toString() const;
static BtChokeMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual bool sendPredicate() const;
virtual void onSendComplete();
};
#endif // _D_CHOKE_MESSAGE_H_

45
src/BtChokedEvent.h Normal file
View File

@ -0,0 +1,45 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_CHOKED_EVENT_H_
#define _D_BT_CHOKED_EVENT_H_
#include "BtEvent.h"
class BtChokedEvent : public BtEvent {
};
typedef SharedHandle<BtChokedEvent> BtChokedEventHandle;
#endif // _D_BT_CHOKED_EVENT_H_

45
src/BtChokingEvent.h Normal file
View File

@ -0,0 +1,45 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_CHOKING_EVENT_H_
#define _D_BT_CHOKING_EVENT_H_
#include "BtEvent.h"
class BtChokingEvent : public BtEvent {
};
typedef SharedHandle<BtChokingEvent> BtChokingEventHandle;
#endif // _D_BT_CHOKING_EVENT_H_

View File

@ -77,6 +77,11 @@ public:
virtual int getPieceLength() const = 0;
virtual int getNumPieces() const = 0;
/**
* Returns the peer id of localhost, 20 byte length
*/
virtual const unsigned char* getPeerId() = 0;
};
typedef SharedHandle<BtContext> BtContextHandle;

47
src/BtEvent.h Normal file
View File

@ -0,0 +1,47 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_EVENT_H_
#define _D_BT_EVENT_H_
#include "common.h"
class BtEvent {
public:
virtual ~BtEvent() {}
};
typedef SharedHandle<BtEvent> BtEventHandle;
#endif // _D_BT_EVENT_H_

51
src/BtEventListener.h Normal file
View File

@ -0,0 +1,51 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_EVENT_LISTENER_H_
#define _D_BT_EVENT_LISTENER_H_
#include "common.h"
#include "BtEvent.h"
class BtEventListener {
public:
virtual ~BtEventListener() {}
virtual void handleEvent(const BtEventHandle& event) = 0;
};
typedef SharedHandle<BtEventListener> BtEventListenerHandle;
typedef deque<BtEventListenerHandle> BtEventListeners;
#endif // _D_BT_EVENT_LISTENER_H_

100
src/BtHandshakeMessage.cc Normal file
View File

@ -0,0 +1,100 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtHandshakeMessage.h"
#include "PeerMessageUtil.h"
#include "Util.h"
const unsigned char* BtHandshakeMessage::BT_PSTR = (const unsigned char*)"BitTorrent protocol";
BtHandshakeMessage::BtHandshakeMessage() {
init();
}
BtHandshakeMessage::BtHandshakeMessage(const unsigned char* infoHash,
const unsigned char* peerId)
{
init();
memcpy(this->infoHash, infoHash, INFO_HASH_LENGTH);
memcpy(this->peerId, peerId, PEER_ID_LENGTH);
}
void BtHandshakeMessage::init() {
msg = 0;
this->pstrlen = 19;
pstr = new unsigned char[PSTR_LENGTH];
reserved = new unsigned char[RESERVED_LENGTH];
infoHash = new unsigned char[INFO_HASH_LENGTH];
peerId = new unsigned char[PEER_ID_LENGTH];
memcpy(this->pstr, PSTR, PSTR_LENGTH);
memset(this->reserved, 0, RESERVED_LENGTH);
// fast extension
this->reserved[7] |= 0x04;
}
BtHandshakeMessageHandle BtHandshakeMessage::create(const unsigned char* data, uint32_t dataLength) {
BtHandshakeMessageHandle message = new BtHandshakeMessage();
message->pstrlen = data[0];
memcpy(message->pstr, &data[1], PSTR_LENGTH);
memcpy(message->reserved, &data[20], RESERVED_LENGTH);
memcpy(message->infoHash, &data[28], INFO_HASH_LENGTH);
memcpy(message->peerId, &data[48], PEER_ID_LENGTH);
return message;
}
const char* BtHandshakeMessage::getMessage() {
if(!msg) {
msg = new char[MESSAGE_LENGTH];
msg[0] = pstrlen;
memcpy(msg+1, pstr, PSTR_LENGTH);
memcpy(msg+20, reserved, RESERVED_LENGTH);
memcpy(msg+28, infoHash, INFO_HASH_LENGTH);
memcpy(msg+48, peerId, PEER_ID_LENGTH);
}
return msg;
}
uint32_t BtHandshakeMessage::getMessageLength() {
return MESSAGE_LENGTH;
}
string BtHandshakeMessage::toString() const {
return "handshake peerId="+
Util::urlencode(peerId, PEER_ID_LENGTH)+
", reserved="+Util::toHex(reserved, RESERVED_LENGTH);
}
bool BtHandshakeMessage::isFastExtensionSupported() const {
return reserved[7]&0x04;
}

117
src/BtHandshakeMessage.h Normal file
View File

@ -0,0 +1,117 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_HANDSHAKE_MESSAGE_H_
#define _D_BT_HANDSHAKE_MESSAGE_H_
#include "SimpleBtMessage.h"
class BtHandshakeMessage;
typedef SharedHandle<BtHandshakeMessage> BtHandshakeMessageHandle;
class BtHandshakeMessage : public SimpleBtMessage {
public:
static const uint32_t PSTR_LENGTH = 19;
static const unsigned char* BT_PSTR;
static const uint32_t RESERVED_LENGTH = 8;
static const uint32_t MESSAGE_LENGTH = 68;
private:
uint8_t pstrlen;
unsigned char* pstr;
unsigned char* reserved;
unsigned char* infoHash;
unsigned char* peerId;
char* msg;
void init();
public:
BtHandshakeMessage();
/**
* infoHash must be 20 byte length.
* peerId must be 20 byte length.
*/
BtHandshakeMessage(const unsigned char* infoHash, const unsigned char* peerId);
static BtHandshakeMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual ~BtHandshakeMessage() {
delete [] msg;
delete [] pstr;
delete [] reserved;
delete [] infoHash;
delete [] peerId;
}
virtual int32_t getId() const { return INT32_MAX; }
virtual void doReceivedAction() {};
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual string toString() const;
bool isFastExtensionSupported() const;
uint8_t getPstrlen() const {
return pstrlen;
}
const unsigned char* getPstr() const {
return pstr;
}
const unsigned char* getReserved() const {
return reserved;
}
const unsigned char* getInfoHash() const {
return infoHash;
}
void setInfoHash(const unsigned char* infoHash) {
memcpy(this->infoHash, infoHash, INFO_HASH_LENGTH);
}
const unsigned char* getPeerId() const {
return peerId;
}
void setPeerId(const unsigned char* peerId) {
memcpy(this->peerId, peerId, PEER_ID_LENGTH);
}
};
#endif // _D_HANDSHAKE_MESSAGE_H_

View File

@ -0,0 +1,75 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_HANDSHAKE_MESSAGE_VALIDATOR_H_
#define _D_BT_HANDSHAKE_MESSAGE_VALIDATOR_H_
#include "BtMessageValidator.h"
#include "BtHandshakeMessage.h"
#include "Util.h"
class BtHandshakeMessageValidator : public BtMessageValidator {
private:
const BtHandshakeMessage* message;
unsigned char infoHash[20];
public:
BtHandshakeMessageValidator(const BtHandshakeMessage* message,
const unsigned char* infoHash):
message(message)
{
memcpy(this->infoHash, infoHash, sizeof(this->infoHash));
}
virtual bool validate(Errors& error) {
// TODO
if(message->getPstrlen() != 19) {
throw new DlAbortEx("invalid handshake pstrlen=%u",
message->getPstrlen());
}
if(memcmp(BtHandshakeMessage::BT_PSTR, message->getPstr(), 19) != 0) {
throw new DlAbortEx("invalid handshake pstr=%s",
Util::urlencode(message->getPstr(), 19).c_str());
}
if(memcmp(infoHash, message->getInfoHash(), 20) != 0) {
throw new DlAbortEx("invalid handshake info hash: expected:%s, actual:%s",
Util::toHex(infoHash, 20).c_str(),
Util::toHex(message->getInfoHash(), 20).c_str());
}
return true;
}
};
typedef SharedHandle<BtHandshakeMessageValidator> BtHandshakeMessageValidatorHandle;
#endif // _D_BT_HANDSHAKE_MESSAGE_VALIDATOR_H_

81
src/BtHaveAllMessage.cc Normal file
View File

@ -0,0 +1,81 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtHaveAllMessage.h"
#include "DlAbortEx.h"
#include "PeerMessageUtil.h"
BtHaveAllMessageHandle BtHaveAllMessage::create(const unsigned char* data, uint32_t dataLength) {
if(dataLength != 1) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be %d", "have all", dataLength, 1);
}
int32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "have all", ID);
}
BtHaveAllMessageHandle message = new BtHaveAllMessage();
return message;
}
void BtHaveAllMessage::doReceivedAction() {
if(!peer->isFastExtensionEnabled()) {
throw new DlAbortEx("%s received while fast extension is disabled",
toString().c_str());
}
peer->setAllBitfield();
}
uint32_t BtHaveAllMessage::MESSAGE_LENGTH = 5;
const char* BtHaveAllMessage::getMessage() {
if(!msg) {
/**
* len --- 1, 4bytes
* id --- 14, 1byte
* total: 5bytes
*/
msg = new char[MESSAGE_LENGTH];
PeerMessageUtil::createPeerMessageString(msg, MESSAGE_LENGTH, 1, ID);
}
return msg;
}
uint32_t BtHaveAllMessage::getMessageLength() {
return MESSAGE_LENGTH;
}
string BtHaveAllMessage::toString() const {
return "have all";
}

73
src/BtHaveAllMessage.h Normal file
View File

@ -0,0 +1,73 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_HAVE_ALL_MESSAGE_H_
#define _D_BT_HAVE_ALL_MESSAGE_H_
#include "SimpleBtMessage.h"
class BtHaveAllMessage;
typedef SharedHandle<BtHaveAllMessage> BtHaveAllMessageHandle;
class BtHaveAllMessage : public SimpleBtMessage {
private:
char* msg;
static uint32_t MESSAGE_LENGTH;
public:
BtHaveAllMessage():msg(0) {}
virtual ~BtHaveAllMessage() {
delete [] msg;
}
enum ID_t {
ID = 14
};
static BtHaveAllMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction();
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual string toString() const;
};
#endif // _D_BT_HAVE_ALL_MESSAGE_H_

85
src/BtHaveMessage.cc Normal file
View File

@ -0,0 +1,85 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtHaveMessage.h"
#include "PeerMessageUtil.h"
#include "Util.h"
#include "DlAbortEx.h"
BtHaveMessageHandle BtHaveMessage::create(const unsigned char* data, uint32_t dataLength) {
if(dataLength != 5) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be %d", "have", dataLength, 5);
}
int32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "have", ID);
}
BtHaveMessageHandle message = new BtHaveMessage();
message->setIndex(PeerMessageUtil::getIntParam(data, 1));
return message;
}
void BtHaveMessage::doReceivedAction() {
peer->updateBitfield(index, 1);
}
bool BtHaveMessage::sendPredicate() const {
return !peer->hasPiece(index);
}
uint32_t BtHaveMessage::MESSAGE_LENGTH = 9;
const char* BtHaveMessage::getMessage() {
if(!msg) {
/**
* len --- 5, 4bytes
* id --- 4, 1byte
* piece index --- index, 4bytes
* total: 9bytes
*/
msg = new char[MESSAGE_LENGTH];
PeerMessageUtil::createPeerMessageString(msg, MESSAGE_LENGTH, 5, ID);
PeerMessageUtil::setIntParam(&msg[5], index);
}
return msg;
}
uint32_t BtHaveMessage::getMessageLength() {
return MESSAGE_LENGTH;
}
string BtHaveMessage::toString() const {
return "have index="+Util::uitos(index);
}

81
src/BtHaveMessage.h Normal file
View File

@ -0,0 +1,81 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_HAVE_MESSAGE_H_
#define _D_BT_HAVE_MESSAGE_H_
#include "SimpleBtMessage.h"
class BtHaveMessage;
typedef SharedHandle<BtHaveMessage> BtHaveMessageHandle;
class BtHaveMessage : public SimpleBtMessage {
private:
uint32_t index;
char* msg;
static uint32_t MESSAGE_LENGTH;
public:
BtHaveMessage(uint32_t index = 0):index(index), msg(0) {}
virtual ~BtHaveMessage() {
delete [] msg;
}
enum ID_t {
ID = 4
};
void setIndex(uint32_t index) {
this->index = index;
}
uint32_t getIndex() const { return index; }
static BtHaveMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction();
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual bool sendPredicate() const;
virtual string toString() const;
};
#endif // _D_BT_HAVE_MESSAGE_H_

View File

@ -0,0 +1,60 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_HAVE_MESSAGE_VALIDATOR_H_
#define _D_BT_HAVE_MESSAGE_VALIDATOR_H_
#include "BtMessageValidator.h"
#include "BtHaveMessage.h"
#include "PeerMessageUtil.h"
class BtHaveMessageValidator : public BtMessageValidator {
private:
const BtHaveMessage* message;
int numPiece;
public:
BtHaveMessageValidator(const BtHaveMessage* message,
int numPiece):
message(message),
numPiece(numPiece) {}
virtual bool validate(Errors& errors) {
// TODO
PeerMessageUtil::checkIndex(message->getIndex(), numPiece);
return true;
}
};
#endif // _D_BT_HAVE_MESSAGE_VALIDATOR_H_

80
src/BtHaveNoneMessage.cc Normal file
View File

@ -0,0 +1,80 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtHaveNoneMessage.h"
#include "DlAbortEx.h"
#include "PeerMessageUtil.h"
BtHaveNoneMessageHandle BtHaveNoneMessage::create(const unsigned char* data, uint32_t dataLength) {
if(dataLength != 1) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be %d", "have none", dataLength, 1);
}
int32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "have none", ID);
}
BtHaveNoneMessageHandle message = new BtHaveNoneMessage();
return message;
}
void BtHaveNoneMessage::doReceivedAction() {
if(!peer->isFastExtensionEnabled()) {
throw new DlAbortEx("%s received while fast extension is disabled",
toString().c_str());
}
}
uint32_t BtHaveNoneMessage::MESSAGE_LENGTH = 5;
const char* BtHaveNoneMessage::getMessage() {
if(!msg) {
/**
* len --- 1, 4bytes
* id --- 15, 1byte
* total: 5bytes
*/
msg = new char[MESSAGE_LENGTH];
PeerMessageUtil::createPeerMessageString(msg, MESSAGE_LENGTH, 1, ID);
}
return msg;
}
uint32_t BtHaveNoneMessage::getMessageLength() {
return MESSAGE_LENGTH;
}
string BtHaveNoneMessage::toString() const {
return "have none";
}

73
src/BtHaveNoneMessage.h Normal file
View File

@ -0,0 +1,73 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_HAVE_NONE_MESSAGE_H_
#define _D_BT_HAVE_NONE_MESSAGE_H_
#include "SimpleBtMessage.h"
class BtHaveNoneMessage;
typedef SharedHandle<BtHaveNoneMessage> BtHaveNoneMessageHandle;
class BtHaveNoneMessage : public SimpleBtMessage {
private:
char* msg;
static uint32_t MESSAGE_LENGTH;
public:
BtHaveNoneMessage():msg(0) {}
virtual ~BtHaveNoneMessage() {
delete [] msg;
}
enum ID_t {
ID = 15
};
static BtHaveNoneMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction();
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual string toString() const;
};
#endif // _D_BT_HAVE_NONE_MESSAGE_H_

66
src/BtInteractive.h Normal file
View File

@ -0,0 +1,66 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_INTERACTIVE_H_
#define _D_BT_INTERACTIVE_H_
#include "common.h"
#include "BtMessage.h"
class BtInteractive {
public:
virtual ~BtInteractive() {}
virtual void initiateHandshake() = 0;
virtual BtMessageHandle receiveHandshake(bool quickReply = false) = 0;
virtual BtMessageHandle receiveAndSendHandshake() = 0;
virtual void doPostHandshakeProcessing() = 0;
virtual void doInteractionProcessing() = 0;
virtual void cancelAllPiece() = 0;
virtual void sendPendingMessage() = 0;
virtual uint32_t countPendingMessage() = 0;
virtual bool isSendingMessageInProgress() = 0;
};
typedef SharedHandle<BtInteractive> BtInteractiveHandle;
#endif // _D_BT_INTERACTIVE_H_

View File

@ -0,0 +1,85 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtInterestedMessage.h"
#include "PeerMessageUtil.h"
#include "DlAbortEx.h"
BtInterestedMessageHandle BtInterestedMessage::create(const unsigned char* data, uint32_t dataLength) {
if(dataLength != 1) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be %d", "interested", dataLength, 1);
}
int32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "interested", ID);
}
BtInterestedMessageHandle message = new BtInterestedMessage();
return message;
}
void BtInterestedMessage::doReceivedAction() {
peer->peerInterested = true;
}
bool BtInterestedMessage::sendPredicate() const {
return !peer->amInterested;
}
uint32_t BtInterestedMessage::MESSAGE_LENGTH = 5;
const char* BtInterestedMessage::getMessage() {
if(!msg) {
/**
* len --- 1, 4bytes
* id --- 2, 1byte
* total: 5bytes
*/
msg = new char[MESSAGE_LENGTH];
PeerMessageUtil::createPeerMessageString(msg, MESSAGE_LENGTH, 1, ID);
}
return msg;
}
uint32_t BtInterestedMessage::getMessageLength() {
return MESSAGE_LENGTH;
}
void BtInterestedMessage::onSendComplete() {
peer->amInterested = true;
}
string BtInterestedMessage::toString() const {
return "interested";
}

77
src/BtInterestedMessage.h Normal file
View File

@ -0,0 +1,77 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_INTERESTED_MESSAGE_H_
#define _D_BT_INTERESTED_MESSAGE_H_
#include "SimpleBtMessage.h"
class BtInterestedMessage;
typedef SharedHandle<BtInterestedMessage> BtInterestedMessageHandle;
class BtInterestedMessage : public SimpleBtMessage {
private:
char* msg;
static uint32_t MESSAGE_LENGTH;
public:
BtInterestedMessage():msg(0) {}
virtual ~BtInterestedMessage() {
delete [] msg;
}
enum ID_t {
ID = 2
};
static BtInterestedMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction();
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual string toString() const;
virtual bool sendPredicate() const;
virtual void onSendComplete();
};
#endif // _D_BT_INTERESTED_MESSAGE_H_

53
src/BtKeepAliveMessage.cc Normal file
View File

@ -0,0 +1,53 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtKeepAliveMessage.h"
uint32_t BtKeepAliveMessage::MESSAGE_LENGTH = 4;
const char* BtKeepAliveMessage::getMessage() {
if(!msg) {
/**
* len --- 0, 4bytes
* total: 4bytes
*/
msg = new char[MESSAGE_LENGTH];
memset(msg, 0, MESSAGE_LENGTH);
}
return msg;
}
uint32_t BtKeepAliveMessage::getMessageLength() {
return MESSAGE_LENGTH;
}

73
src/BtKeepAliveMessage.h Normal file
View File

@ -0,0 +1,73 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_KEEP_ALIVE_MESSAGE_H_
#define _D_BT_KEEP_ALIVE_MESSAGE_H_
#include "SimpleBtMessage.h"
class BtKeepAliveMessage;
typedef SharedHandle<BtKeepAliveMessage> BtKeepAliveMessageHandle;
class BtKeepAliveMessage : public SimpleBtMessage {
private:
char* msg;
static uint32_t MESSAGE_LENGTH;
public:
BtKeepAliveMessage():msg(0) {}
virtual ~BtKeepAliveMessage() {
delete [] msg;
}
enum ID_t {
ID = 99
};
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction() {}
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual string toString() const {
return "keep alive";
}
};
#endif // _D_BT_KEEP_ALIVE_MESSAGE_H_

72
src/BtMessage.h Normal file
View File

@ -0,0 +1,72 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_MESSAGE_H_
#define _D_BT_MESSAGE_H_
#include "common.h"
#include "Piece.h"
#include "BtMessageValidator.h"
#include "BtEvent.h"
class BtMessage {
public:
virtual ~BtMessage() {}
virtual bool isSendingInProgress() = 0;
virtual bool isInvalidate() = 0;
virtual bool isUploading() = 0;
virtual int32_t getId() = 0;
virtual void doReceivedAction() = 0;
virtual void send() = 0;
virtual bool validate(Errors& errors) = 0;
virtual void handleEvent(const BtEventHandle& event) = 0;
virtual void onQueued() = 0;
virtual string toString() const = 0;
};
typedef SharedHandle<BtMessage> BtMessageHandle;
typedef deque<BtMessageHandle> BtMessages;
#endif // _D_BT_MESSAGE_H_

82
src/BtMessageDispatcher.h Normal file
View File

@ -0,0 +1,82 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_MESSAGE_DISPATCHER_H_
#define _D_BT_MESSAGE_DISPATCHER_H_
#include "common.h"
#include "Piece.h"
#include "BtMessage.h"
#include "RequestSlot.h"
class BtMessageDispatcher {
public:
virtual ~BtMessageDispatcher() {}
virtual void addMessageToQueue(const BtMessageHandle& btMessage) = 0;
virtual void addMessageToQueue(const BtMessages& btMessages) = 0;
virtual void sendMessages() = 0;
virtual void doCancelSendingPieceAction(uint32_t index, uint32_t begin, uint32_t blockLength) = 0;
virtual void doCancelSendingPieceAction(const PieceHandle& piece) = 0;
virtual void doAbortOutstandingRequestAction(const PieceHandle& piece) = 0;
virtual void doChokedAction() = 0;
virtual void doChokingAction() = 0;
virtual void checkRequestSlotAndDoNecessaryThing() = 0;
virtual bool isSendingInProgress() = 0;
virtual uint32_t countMessageInQueue() = 0;
virtual uint32_t countOutstandingRequest() = 0;
virtual bool isOutstandingRequest(uint32_t index, uint32_t blockIndex) = 0;
virtual RequestSlot getOutstandingRequest(uint32_t index, uint32_t begin, uint32_t blockLength) = 0;
virtual void removeOutstandingRequest(const RequestSlot& slot) = 0;
virtual void addOutstandingRequest(const RequestSlot& slot) = 0;
};
typedef SharedHandle<BtMessageDispatcher> BtMessageDispatcherHandle;
#endif // _D_BT_MESSAGE_DISPATCHER_H_

53
src/BtMessageFactory.cc Normal file
View File

@ -0,0 +1,53 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtMessageFactory.h"
#include "DefaultBtMessageFactory.h"
void BtMessageFactory::registerFactory(const string& key,
const BtMessageFactoryPrerequisiteHandle& prereq) {
prerequisiteMap.erase(key);
BtMessageFactoryPrerequisiteMap::value_type p(key, prereq);
prerequisiteMap.insert(p);
}
static BtMessageFactory::BtMessageFactoryHandle getNewFactory(const string& key) {
DefaultBtMessageFactoryHandle factory = new DefaultBtMessageFactory();
BtMessageFactoryPrerequisiteMap::iterator itr = prerequisiteMap.find(key);
if(prerequisiteMap.end() != itr) {
// TODO set prerequisite objects to factory here
}
return factory;
}

91
src/BtMessageFactory.h Normal file
View File

@ -0,0 +1,91 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_MESSAGE_FACTORY_H_
#define _D_BT_MESSAGE_FACTORY_H_
#include "common.h"
#include "BtMessage.h"
#include "Piece.h"
class BtMessageFactory {
public:
virtual ~BtMessageFactory() {}
virtual BtMessageHandle
createBtMessage(const unsigned char* msg, uint32_t msgLength) = 0;
virtual BtMessageHandle
createHandshakeMessage(const unsigned char* msg, uint32_t msgLength) = 0;
virtual BtMessageHandle
createHandshakeMessage(const unsigned char* infoHash,
const unsigned char* peerId) = 0;
virtual BtMessageHandle
createRequestMessage(const PieceHandle& piece, uint32_t blockIndex) = 0;
virtual BtMessageHandle
createCancelMessage(uint32_t index, uint32_t begin, uint32_t length) = 0;
virtual BtMessageHandle
createPieceMessage(uint32_t index, uint32_t begin, uint32_t length) = 0;
virtual BtMessageHandle createHaveMessage(uint32_t index) = 0;
virtual BtMessageHandle createChokeMessage() = 0;
virtual BtMessageHandle createUnchokeMessage() = 0;
virtual BtMessageHandle createInterestedMessage() = 0;
virtual BtMessageHandle createNotInterestedMessage() = 0;
virtual BtMessageHandle createBitfieldMessage() = 0;
virtual BtMessageHandle createKeepAliveMessage() = 0;
virtual BtMessageHandle createHaveAllMessage() = 0;
virtual BtMessageHandle createHaveNoneMessage() = 0;
virtual BtMessageHandle
createRejectMessage(uint32_t index, uint32_t begin, uint32_t length) = 0;
virtual BtMessageHandle createAllowedFastMessage(uint32_t index) = 0;
};
typedef SharedHandle<BtMessageFactory> BtMessageFactoryHandle;
#endif // _D_BT_MESSAGE_FACTORY_H_

54
src/BtMessageReceiver.h Normal file
View File

@ -0,0 +1,54 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_MESSAGE_RECEIVER_H_
#define _D_BT_MESSAGE_RECEIVER_H_
#include "common.h"
#include "BtMessage.h"
class BtMessageReceiver {
public:
virtual ~BtMessageReceiver() {}
virtual BtMessageHandle receiveHandshake(bool quickReply = false) = 0;
virtual BtMessageHandle receiveAndSendHandshake() = 0;
virtual BtMessageHandle receiveMessage() = 0;
};
typedef SharedHandle<BtMessageReceiver> BtMessageReceiverHandle;
#endif // _D_BT_MESSAGE_RECEIVER_H_

52
src/BtMessageValidator.h Normal file
View File

@ -0,0 +1,52 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_MESSAGE_VALIDATOR_H_
#define _D_BT_MESSAGE_VALIDATOR_H_
#include "common.h"
#include "BtMessage.h"
typedef Strings Errors;
class BtMessageValidator {
public:
virtual ~BtMessageValidator() {}
virtual bool validate(Errors& errors) = 0;
};
typedef SharedHandle<BtMessageValidator> BtMessageValidatorHandle;
#endif // _D_BT_MESSAGE_VALIDATOR_H_

View File

@ -0,0 +1,85 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtNotInterestedMessage.h"
#include "PeerMessageUtil.h"
#include "DlAbortEx.h"
BtNotInterestedMessageHandle BtNotInterestedMessage::create(const unsigned char* data, uint32_t dataLength) {
if(dataLength != 1) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be %d", "not interested", dataLength, 1);
}
int32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "not interested", ID);
}
BtNotInterestedMessageHandle message = new BtNotInterestedMessage();
return message;
}
void BtNotInterestedMessage::doReceivedAction() {
peer->peerInterested = false;
}
bool BtNotInterestedMessage::sendPredicate() const {
return peer->amInterested;
}
uint32_t BtNotInterestedMessage::MESSAGE_LENGTH = 5;
const char* BtNotInterestedMessage::getMessage() {
if(!msg) {
/**
* len --- 1, 4bytes
* id --- 3, 1byte
* total: 5bytes
*/
msg = new char[MESSAGE_LENGTH];
PeerMessageUtil::createPeerMessageString(msg, MESSAGE_LENGTH, 1, ID);
}
return msg;
}
uint32_t BtNotInterestedMessage::getMessageLength() {
return MESSAGE_LENGTH;
}
void BtNotInterestedMessage::onSendComplete() {
peer->amInterested = false;
}
string BtNotInterestedMessage::toString() const {
return "not interested";
}

View File

@ -0,0 +1,77 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_NOT_INTERESTED_MESSAGE_H_
#define _D_BT_NOT_INTERESTED_MESSAGE_H_
#include "SimpleBtMessage.h"
class BtNotInterestedMessage;
typedef SharedHandle<BtNotInterestedMessage> BtNotInterestedMessageHandle;
class BtNotInterestedMessage : public SimpleBtMessage {
private:
char* msg;
static uint32_t MESSAGE_LENGTH;
public:
BtNotInterestedMessage():msg(0) {}
virtual ~BtNotInterestedMessage() {
delete [] msg;
}
enum ID_t {
ID = 3
};
static BtNotInterestedMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction();
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual string toString() const;
virtual bool sendPredicate() const;
virtual void onSendComplete();
};
#endif // _D_BT_NOT_INTERESTED_MESSAGE_H_

283
src/BtPieceMessage.cc Normal file
View File

@ -0,0 +1,283 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtPieceMessage.h"
#include "PeerMessageUtil.h"
#include "Util.h"
#include "message.h"
#include "DlAbortEx.h"
#include "BtChokingEvent.h"
#include "BtCancelSendingPieceEvent.h"
void BtPieceMessage::setBlock(const unsigned char* block, uint32_t blockLength) {
delete [] this->block;
this->blockLength = blockLength;
this->block = new char[this->blockLength];
memcpy(this->block, block, this->blockLength);
}
BtPieceMessageHandle BtPieceMessage::create(const unsigned char* data, uint32_t dataLength) {
if(dataLength <= 9) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be greater than %d", "piece", dataLength, 9);
}
int32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "piece", ID);
}
BtPieceMessageHandle message = new BtPieceMessage();
message->setIndex(PeerMessageUtil::getIntParam(data, 1));
message->setBegin(PeerMessageUtil::getIntParam(data, 5));
message->setBlock(data+9, dataLength-9);
return message;
}
void BtPieceMessage::doReceivedAction() {
RequestSlot slot =
BT_MESSAGE_DISPATCHER(btContext, peer)->getOutstandingRequest(index,
begin,
blockLength);
peer->updateDownloadLength(blockLength);
if(!RequestSlot::isNull(slot)) {
peer->snubbing = false;
peer->updateLatency(slot.getLatencyInMillis());
PieceHandle piece = pieceStorage->getPiece(index);
uint64_t offset =
((uint64_t)index)*btContext->getPieceLength()+begin;
logger->debug("CUID#%d - Piece received. index=%u, begin=%u, length=%u, offset=%llu, blockIndex=%u",
cuid, index, begin, blockLength, offset, slot.getBlockIndex());
pieceStorage->getDiskAdaptor()->writeData(block,
blockLength,
offset);
piece->completeBlock(slot.getBlockIndex());
BT_MESSAGE_DISPATCHER(btContext, peer)->removeOutstandingRequest(slot);
if(piece->pieceComplete()) {
if(checkPieceHash(piece)) {
onNewPiece(piece);
} else {
onWrongPiece(piece);
}
}
}
}
uint32_t BtPieceMessage::MESSAGE_HEADER_LENGTH = 13;
const char* BtPieceMessage::getMessageHeader() {
if(!msgHeader) {
/**
* len --- 9+blockLength, 4bytes
* id --- 7, 1byte
* index --- index, 4bytes
* begin --- begin, 4bytes
* total: 13bytes
*/
msgHeader = new char[MESSAGE_HEADER_LENGTH];
PeerMessageUtil::createPeerMessageString(msgHeader, MESSAGE_HEADER_LENGTH,
9+blockLength, ID);
PeerMessageUtil::setIntParam(&msgHeader[5], index);
PeerMessageUtil::setIntParam(&msgHeader[9], begin);
}
return msgHeader;
}
uint32_t BtPieceMessage::getMessageHeaderLength() {
return MESSAGE_HEADER_LENGTH;
}
void BtPieceMessage::send() {
if(invalidate) {
return;
}
if(!headerSent) {
if(!sendingInProgress) {
logger->info(MSG_SEND_PEER_MESSAGE,
cuid, peer->ipaddr.c_str(), peer->port,
toString().c_str());
getMessageHeader();
leftDataLength = getMessageHeaderLength();
sendingInProgress = true;
}
uint32_t writtenLength
= PEER_CONNECTION(btContext, peer)->sendMessage(msgHeader+getMessageHeaderLength()-leftDataLength,
leftDataLength);
if(writtenLength == leftDataLength) {
headerSent = true;
leftDataLength = blockLength;
} else {
leftDataLength -= writtenLength;
}
}
if(headerSent) {
sendingInProgress = false;
uint64_t pieceDataOffset =
((uint64_t)index)*btContext->getPieceLength()+begin+blockLength-leftDataLength;
uint32_t writtenLength =
sendPieceData(pieceDataOffset, leftDataLength);
peer->updateUploadLength(writtenLength);
if(writtenLength < leftDataLength) {
sendingInProgress = true;
}
leftDataLength -= writtenLength;
}
}
uint32_t BtPieceMessage::sendPieceData(uint64_t offset, uint32_t length) const {
uint32_t BUF_SIZE = 256;
char buf[BUF_SIZE];
int32_t iteration = length/BUF_SIZE;
uint32_t writtenLength = 0;
for(int32_t i = 0; i < iteration; i++) {
if(pieceStorage->getDiskAdaptor()->readData(buf, BUF_SIZE, offset+i*BUF_SIZE) < BUF_SIZE) {
throw new DlAbortEx("Failed to read data from disk.");
}
uint32_t ws = PEER_CONNECTION(btContext, peer)->sendMessage(buf, BUF_SIZE);
writtenLength += ws;
if(ws != BUF_SIZE) {
return writtenLength;
}
}
int32_t rem = length%BUF_SIZE;
if(rem > 0) {
if(pieceStorage->getDiskAdaptor()->readData(buf, rem, offset+iteration*BUF_SIZE) < rem) {
throw new DlAbortEx("Failed to read data from disk.");
}
uint32_t ws = PEER_CONNECTION(btContext, peer)->sendMessage(buf, rem);
writtenLength += ws;
}
return writtenLength;
}
string BtPieceMessage::toString() const {
return "piece index="+Util::uitos(index)+", begin="+Util::uitos(begin)+
", length="+Util::uitos(blockLength);
}
bool BtPieceMessage::checkPieceHash(const PieceHandle& piece) {
uint64_t offset =
((uint64_t)piece->getIndex())*btContext->getPieceLength();
return pieceStorage->getDiskAdaptor()->sha1Sum(offset, piece->getLength()) ==
btContext->getPieceHash(piece->getIndex());
}
void BtPieceMessage::onNewPiece(const PieceHandle& piece) {
logger->info(MSG_GOT_NEW_PIECE, cuid, piece->getIndex());
pieceStorage->completePiece(piece);
pieceStorage->advertisePiece(cuid, piece->getIndex());
}
void BtPieceMessage::onWrongPiece(const PieceHandle& piece) {
logger->error(MSG_GOT_WRONG_PIECE, cuid, piece->getIndex());
erasePieceOnDisk(piece);
piece->clearAllBlock();
BT_REQUEST_FACTORY(btContext, peer)->removeTargetPiece(piece);
}
void BtPieceMessage::erasePieceOnDisk(const PieceHandle& piece) {
int32_t BUFSIZE = 4096;
char buf[BUFSIZE];
memset(buf, 0, BUFSIZE);
uint64_t offset =
((uint64_t)piece->getIndex())*btContext->getPieceLength();
for(int32_t i = 0; i < piece->getLength()/BUFSIZE; i++) {
pieceStorage->getDiskAdaptor()->writeData(buf, BUFSIZE, offset);
offset += BUFSIZE;
}
int32_t r = piece->getLength()%BUFSIZE;
if(r > 0) {
pieceStorage->getDiskAdaptor()->writeData(buf, r, offset);
}
}
bool BtPieceMessage::BtChokingEventListener::canHandle(const BtEventHandle& event) {
BtChokingEvent* intEvent = dynamic_cast<BtChokingEvent*>(event.get());
return intEvent != 0;
}
void BtPieceMessage::BtChokingEventListener::handleEventInternal(const BtEventHandle& event) {
message->handleChokingEvent(event);
}
void BtPieceMessage::handleChokingEvent(const BtEventHandle& event) {
if(!invalidate &&
!sendingInProgress &&
!peer->isInAmAllowedIndexSet(index)) {
logger->debug("CUID#%d - Reject piece message in queue because"
" the peer has been choked. index=%d, begin=%d, length=%d",
cuid,
index,
begin,
blockLength);
if(peer->isFastExtensionEnabled()) {
BtMessageHandle rej =
BT_MESSAGE_FACTORY(btContext, peer)->createRejectMessage(index,
begin,
blockLength);
BT_MESSAGE_DISPATCHER(btContext, peer)->addMessageToQueue(rej);
}
invalidate = true;
}
}
bool BtPieceMessage::BtCancelSendingPieceEventListener::canHandle(const BtEventHandle& event) {
BtCancelSendingPieceEvent* intEvent = dynamic_cast<BtCancelSendingPieceEvent*>(event.get());
return intEvent != 0;
}
void BtPieceMessage::BtCancelSendingPieceEventListener::handleEventInternal(const BtEventHandle& event) {
message->handleCancelSendingPieceEvent(event);
}
void BtPieceMessage::handleCancelSendingPieceEvent(const BtEventHandle& event) {
BtCancelSendingPieceEvent* intEvent = (BtCancelSendingPieceEvent*)(event.get());
if(!invalidate &&
!sendingInProgress &&
index == intEvent->getIndex() &&
begin == intEvent->getBegin() &&
blockLength == intEvent->getLength()) {
logger->debug("CUID#%d - Reject piece message in queue because cancel"
" message received. index=%d, begin=%d, length=%d",
cuid, index, begin, blockLength);
if(peer->isFastExtensionEnabled()) {
BtMessageHandle rej =
BT_MESSAGE_FACTORY(btContext, peer)->createRejectMessage(index,
begin,
blockLength);
BT_MESSAGE_DISPATCHER(btContext, peer)->addMessageToQueue(rej);
}
invalidate = true;
}
}

154
src/BtPieceMessage.h Normal file
View File

@ -0,0 +1,154 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_PIECE_MESSAGE_H_
#define _D_BT_PIECE_MESSAGE_H_
#include "AbstractBtMessage.h"
#include "BtContext.h"
#include "PieceStorage.h"
#include "BtEvent.h"
#include "AbstractBtEventListener.h"
class BtPieceMessage;
typedef SharedHandle<BtPieceMessage> BtPieceMessageHandle;
class BtPieceMessage : public AbstractBtMessage {
private:
uint32_t index;
uint32_t begin;
uint32_t blockLength;
char* block;
uint32_t leftDataLength;
bool headerSent;
char* msgHeader;
static uint32_t MESSAGE_HEADER_LENGTH;
bool checkPieceHash(const PieceHandle& piece);
void onNewPiece(const PieceHandle& piece);
void onWrongPiece(const PieceHandle& piece);
void erasePieceOnDisk(const PieceHandle& piece);
uint32_t sendPieceData(uint64_t offset, uint32_t length) const;
class BtChokingEventListener : public AbstractBtEventListener {
private:
BtPieceMessage* message;
public:
BtChokingEventListener(BtPieceMessage* message):message(message) {}
virtual bool canHandle(const BtEventHandle& btEvent);
virtual void handleEventInternal(const BtEventHandle& btEvent);
};
typedef SharedHandle<BtChokingEventListener> BtChokingEventListenerHandle;
class BtCancelSendingPieceEventListener : public AbstractBtEventListener {
private:
BtPieceMessage* message;
public:
BtCancelSendingPieceEventListener(BtPieceMessage* message):message(message) {}
virtual bool canHandle(const BtEventHandle& btEvent);
virtual void handleEventInternal(const BtEventHandle& btEvent);
};
typedef SharedHandle<BtCancelSendingPieceEventListener> BtCancelSendingPieceEventListenerHandle;
public:
BtPieceMessage(uint32_t index = 0, uint32_t begin = 0, uint32_t blockLength = 0)
:index(index),
begin(begin),
blockLength(blockLength),
block(0),
leftDataLength(0),
headerSent(false),
msgHeader(0)
{
uploading = true;
addEventListener(new BtChokingEventListener(this));
addEventListener(new BtCancelSendingPieceEventListener(this));
}
virtual ~BtPieceMessage() {
delete [] msgHeader;
delete [] block;
}
enum ID_t {
ID = 7
};
uint32_t getIndex() const { return index; }
void setIndex(uint32_t index) { this->index = index; }
uint32_t getBegin() const { return begin; }
void setBegin(uint32_t begin) { this->begin = begin; }
const char* getBlock() const { return block; }
void setBlock(const unsigned char* block, uint32_t blockLength);
uint32_t getBlockLength() const { return blockLength; }
void setBlockLength(uint32_t blockLength) { this->blockLength = blockLength; }
static BtPieceMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction();
const char* getMessageHeader();
uint32_t getMessageHeaderLength();
virtual void send();
virtual string toString() const;
void handleChokingEvent(const BtEventHandle& event);
void handleCancelSendingPieceEvent(const BtEventHandle& event);
};
#endif // _D_BT_PIECE_MESSAGE_H_

View File

@ -0,0 +1,64 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_PIECE_MESSAGE_VALIDATOR_H_
#define _D_BT_PIECE_MESSAGE_VALIDATOR_H_
#include "BtMessageValidator.h"
#include "BtPieceMessage.h"
class BtPieceMessageValidator : public BtMessageValidator {
private:
const BtPieceMessage* message;
uint32_t numPiece;
uint32_t pieceLength;
public:
BtPieceMessageValidator(const BtPieceMessage* message,
uint32_t numPiece,
uint32_t pieceLength):
message(message),
numPiece(numPiece),
pieceLength(pieceLength) {}
virtual bool validate(Errors& error) {
// TODO
PeerMessageUtil::checkIndex(message->getIndex(), numPiece);
PeerMessageUtil::checkBegin(message->getBegin(), pieceLength);
return true;
}
};
typedef SharedHandle<BtPieceMessageValidator> BtPieceMessageValidatorHandle;
#endif // _D_BT_PIECE_MESSAGE_VALIDATOR_H_

56
src/BtPortMessage.cc Normal file
View File

@ -0,0 +1,56 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtPortMessage.h"
#include "PeerMessageUtil.h"
#include "DlAbortEx.h"
#include "Util.h"
BtPortMessageHandle BtPortMessage::create(const unsigned char* data, uint32_t dataLength) {
if(dataLength != 3) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be %d", "port", dataLength, 3);
}
int32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "piece", ID);
}
BtPortMessageHandle message = new BtPortMessage();
message->setPort(PeerMessageUtil::getShortIntParam(data, 1));
return message;
}
string BtPortMessage::toString() const {
return "port port="+Util::uitos(port);
}

72
src/BtPortMessage.h Normal file
View File

@ -0,0 +1,72 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_PORT_MESSAGE_H_
#define _D_BT_PORT_MESSAGE_H_
#include "AbstractBtMessage.h"
class BtPortMessage;
typedef SharedHandle<BtPortMessage> BtPortMessageHandle;
class BtPortMessage : public AbstractBtMessage {
private:
uint16_t port;
public:
BtPortMessage(uint16_t port = 0):port(port) {}
virtual ~BtPortMessage() {}
enum ID_t {
ID = 9
};
uint16_t getPort() const { return port; }
void setPort(uint16_t port) { this->port = port; }
virtual int32_t getId() const { return ID; }
static BtPortMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual void doReceivedAction() {
logger->info("DHT is not supported yet.");
}
virtual void send() {}
virtual string toString() const;
};
#endif // _D_BT_PORT_MESSAGE_H_

View File

@ -40,6 +40,7 @@ PieceStorageMap BtRegistry::pieceStorageMap;
BtAnnounceMap BtRegistry::btAnnounceMap;
BtRuntimeMap BtRegistry::btRuntimeMap;
BtProgressInfoFileMap BtRegistry::btProgressInfoFileMap;
PeerObjectClusterRegistry BtRegistry::peerObjectClusterRegistry;
PeerStorageHandle BtRegistry::getPeerStorage(const string& key) {
PeerStorageMap::iterator itr = peerStorageMap.find(key);
@ -70,6 +71,7 @@ BtRegistry::getPieceStorage(const string& key) {
bool
BtRegistry::registerPieceStorage(const string& key,
const PieceStorageHandle& pieceStorage) {
pieceStorageMap.erase(key);
PieceStorageMap::value_type p(key, pieceStorage);
pair<PieceStorageMap::iterator, bool> retval = pieceStorageMap.insert(p);
return retval.second;
@ -128,3 +130,31 @@ BtRegistry::registerBtProgressInfoFile(const string& key,
btProgressInfoFileMap.insert(p);
return retval.second;
}
PeerObjectClusterHandle
BtRegistry::getPeerObjectCluster(const string& key)
{
return peerObjectClusterRegistry.getHandle(key);
}
void
BtRegistry::registerPeerObjectCluster(const string& key,
const PeerObjectClusterHandle& cluster)
{
peerObjectClusterRegistry.registerHandle(key, cluster);
}
void
BtRegistry::unregisterPeerObjectCluster(const string& key)
{
peerObjectClusterRegistry.unregisterHandle(key);
}
void BtRegistry::clear() {
peerStorageMap.clear();
pieceStorageMap.clear();
btAnnounceMap.clear();
btRuntimeMap.clear();
btProgressInfoFileMap.clear();
peerObjectClusterRegistry.clear();
}

View File

@ -41,6 +41,8 @@
#include "BtAnnounce.h"
#include "BtRuntime.h"
#include "BtProgressInfoFile.h"
#include "PeerObject.h"
#include "HandleRegistry.h"
#include <map>
typedef map<string, PeerStorageHandle> PeerStorageMap;
@ -49,6 +51,11 @@ typedef map<string, BtAnnounceHandle> BtAnnounceMap;
typedef map<string, BtRuntimeHandle> BtRuntimeMap;
typedef map<string, BtProgressInfoFileHandle> BtProgressInfoFileMap;
// for BtMessageFactory
typedef HandleRegistry<string, PeerObject> PeerObjectCluster;
typedef SharedHandle<PeerObjectCluster> PeerObjectClusterHandle;
typedef HandleRegistry<string, PeerObjectCluster> PeerObjectClusterRegistry;
class BtRegistry {
private:
BtRegistry() {}
@ -58,6 +65,7 @@ private:
static BtAnnounceMap btAnnounceMap;
static BtRuntimeMap btRuntimeMap;
static BtProgressInfoFileMap btProgressInfoFileMap;
static PeerObjectClusterRegistry peerObjectClusterRegistry;
public:
static PeerStorageHandle getPeerStorage(const string& key);
static bool registerPeerStorage(const string& key,
@ -78,6 +86,19 @@ public:
static BtProgressInfoFileHandle getBtProgressInfoFile(const string& key);
static bool registerBtProgressInfoFile(const string& key,
const BtProgressInfoFileHandle& btProgressInfoFile);
// for PeerObject
static PeerObjectClusterHandle
getPeerObjectCluster(const string& key);
static void
registerPeerObjectCluster(const string& key,
const PeerObjectClusterHandle& cluster);
static void
unregisterPeerObjectCluster(const string& key);
static void clear();
};
#define PEER_STORAGE(btContext) \
@ -95,4 +116,22 @@ BtRegistry::getBtRuntime(btContext->getInfoHashAsString())
#define BT_PROGRESS_INFO_FILE(btContext) \
BtRegistry::getBtProgressInfoFile(btContext->getInfoHashAsString())
#define PEER_OBJECT_CLUSTER(btContext) \
BtRegistry::getPeerObjectCluster(btContext->getInfoHashAsString())
#define PEER_OBJECT(btContext, peer) \
PEER_OBJECT_CLUSTER(btContext)->getHandle(peer->getId())
#define BT_MESSAGE_DISPATCHER(btContext, peer) \
PEER_OBJECT(btContext, peer)->btMessageDispatcher
#define BT_MESSAGE_FACTORY(btContext, peer) \
PEER_OBJECT(btContext, peer)->btMessageFactory
#define BT_REQUEST_FACTORY(btContext, peer) \
PEER_OBJECT(btContext, peer)->btRequestFactory
#define PEER_CONNECTION(btContext, peer) \
PEER_OBJECT(btContext, peer)->peerConnection
#endif // _D_BT_REGISTRY_H_

101
src/BtRejectMessage.cc Normal file
View File

@ -0,0 +1,101 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtRejectMessage.h"
#include "PeerMessageUtil.h"
#include "Util.h"
#include "DlAbortEx.h"
BtRejectMessageHandle BtRejectMessage::create(const unsigned char* data, uint32_t dataLength) {
if(dataLength != 13) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be %d", "reject", dataLength, 13);
}
int32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "reject", ID);
}
BtRejectMessageHandle message = new BtRejectMessage();
message->setIndex(PeerMessageUtil::getIntParam(data, 1));
message->setBegin(PeerMessageUtil::getIntParam(data, 5));
message->setLength(PeerMessageUtil::getIntParam(data, 9));
return message;
}
void BtRejectMessage::doReceivedAction() {
if(!peer->isFastExtensionEnabled()) {
throw new DlAbortEx("%s received while fast extension is disabled.",
toString().c_str());
}
// TODO Current implementation does not close a connection even if
// a request for this reject message has never sent.
RequestSlot slot =
BT_MESSAGE_DISPATCHER(btContext, peer)->getOutstandingRequest(index, begin, length);
if(RequestSlot::isNull(slot)) {
//throw new DlAbortEx("reject recieved, but it is not in the request slots.");
} else {
BT_MESSAGE_DISPATCHER(btContext, peer)->removeOutstandingRequest(slot);
}
}
uint32_t BtRejectMessage::MESSAGE_LENGTH = 17;
const char* BtRejectMessage::getMessage() {
if(!msg) {
/**
* len --- 13, 4bytes
* id --- 16, 1byte
* index --- index, 4bytes
* begin --- begin, 4bytes
* length -- length, 4bytes
* total: 17bytes
*/
msg = new char[MESSAGE_LENGTH];
PeerMessageUtil::createPeerMessageString(msg, MESSAGE_LENGTH, 13, ID);
PeerMessageUtil::setIntParam(&msg[5], index);
PeerMessageUtil::setIntParam(&msg[9], begin);
PeerMessageUtil::setIntParam(&msg[13], length);
}
return msg;
}
uint32_t BtRejectMessage::getMessageLength() {
return MESSAGE_LENGTH;
}
string BtRejectMessage::toString() const {
return "reject index="+Util::uitos(index)+", begin="+Util::uitos(begin)+
", length="+Util::uitos(length);
}

88
src/BtRejectMessage.h Normal file
View File

@ -0,0 +1,88 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_REJECT_MESSAGE_H_
#define _D_BT_REJECT_MESSAGE_H_
#include "SimpleBtMessage.h"
class BtRejectMessage;
typedef SharedHandle<BtRejectMessage> BtRejectMessageHandle;
class BtRejectMessage : public SimpleBtMessage {
private:
uint32_t index;
uint32_t begin;
uint32_t length;
char* msg;
static uint32_t MESSAGE_LENGTH;
public:
BtRejectMessage(uint32_t index = 0, uint32_t begin = 0, uint32_t length = 0)
:index(index),
begin(begin),
length(length),
msg(0) {}
virtual ~BtRejectMessage() {
delete [] msg;
}
enum ID_t {
ID = 16
};
uint32_t getIndex() const { return index; }
void setIndex(uint32_t index) { this->index = index; }
uint32_t getBegin() const { return begin; }
void setBegin(uint32_t begin) { this->begin = begin; }
uint32_t getLength() const { return length; }
void setLength(uint32_t length) { this->length = length; }
static BtRejectMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction();
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual string toString() const;
};
#endif // _D_BT_REJECT_MESSAGE_H_

View File

@ -0,0 +1,68 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_REJECT_MESSAGE_VALIDATOR_H_
#define _D_BT_REJECT_MESSAGE_VALIDATOR_H_
#include "BtMessageValidator.h"
#include "BtRejectMessage.h"
class BtRejectMessageValidator : public BtMessageValidator {
private:
const BtRejectMessage* message;
uint32_t numPiece;
uint32_t pieceLength;
public:
BtRejectMessageValidator(const BtRejectMessage* message,
uint32_t numPiece,
uint32_t pieceLength):
message(message),
numPiece(numPiece),
pieceLength(pieceLength) {}
virtual bool validate(Errors& error) {
// TODO
PeerMessageUtil::checkIndex(message->getIndex(), numPiece);
PeerMessageUtil::checkBegin(message->getBegin(), pieceLength);
PeerMessageUtil::checkLength(message->getLength());
PeerMessageUtil::checkRange(message->getBegin(),
message->getLength(),
pieceLength);
return true;
}
};
typedef SharedHandle<BtRejectMessageValidator> BtRejectMessageValidatorHandle;
#endif // _D_BT_REJECT_MESSAGE_VALIDATOR_H_

72
src/BtRequestFactory.h Normal file
View File

@ -0,0 +1,72 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_REQUEST_FACTORY_H_
#define _D_BT_REQUEST_FACTORY_H_
#include "common.h"
#include "BtMessage.h"
#include "Piece.h"
class BtRequestFactory {
public:
virtual ~BtRequestFactory() {}
virtual void addTargetPiece(const PieceHandle& piece) = 0;
virtual void removeTargetPiece(const PieceHandle& piece) = 0;
virtual void removeAllTargetPiece() = 0;
virtual int countTargetPiece() = 0;
virtual void removeCompletedPiece() = 0;
/**
* Creates RequestMessage objects associated to the pieces added by
* addTargetPiece() and returns them.
* The number of objects returned is capped by max.
*/
virtual BtMessages createRequestMessages(int max) = 0;
/**
* Use this method in end game mode.
*
*/
virtual BtMessages createRequestMessagesOnEndGame(int max) = 0;
};
typedef SharedHandle<BtRequestFactory> BtRequestFactoryHandle;
#endif // _D_BT_REQUEST_FACTORY_H_

129
src/BtRequestMessage.cc Normal file
View File

@ -0,0 +1,129 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtRequestMessage.h"
#include "PeerInteraction.h"
#include "PeerMessageUtil.h"
#include "Util.h"
#include "DlAbortEx.h"
#include "BtAbortOutstandingRequestEvent.h"
BtRequestMessageHandle BtRequestMessage::create(const unsigned char* data, uint32_t dataLength) {
if(dataLength != 13) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be %d", "request", dataLength, 13);
}
int32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "request", ID);
}
BtRequestMessageHandle message = new BtRequestMessage();
message->setIndex(PeerMessageUtil::getIntParam(data, 1));
message->setBegin(PeerMessageUtil::getIntParam(data, 5));
message->setLength(PeerMessageUtil::getIntParam(data, 9));
return message;
}
void BtRequestMessage::doReceivedAction() {
if(pieceStorage->hasPiece(index) &&
(!peer->amChoking ||
peer->amChoking && peer->isInAmAllowedIndexSet(index))) {
BtMessageHandle msg =
BT_MESSAGE_FACTORY(btContext, peer)->createPieceMessage(index,
begin,
length);
BT_MESSAGE_DISPATCHER(btContext, peer)->addMessageToQueue(msg);
} else {
if(peer->isFastExtensionEnabled()) {
BtMessageHandle msg =
BT_MESSAGE_FACTORY(btContext, peer)->createRejectMessage(index,
begin,
length);
BT_MESSAGE_DISPATCHER(btContext, peer)->addMessageToQueue(msg);
}
}
}
uint32_t BtRequestMessage::MESSAGE_LENGTH = 17;
const char* BtRequestMessage::getMessage() {
if(!msg) {
/**
* len --- 13, 4bytes
* id --- 6, 1byte
* index --- index, 4bytes
* begin --- begin, 4bytes
* length --- length, 4bytes
* total: 17bytes
*/
msg = new char[MESSAGE_LENGTH];
PeerMessageUtil::createPeerMessageString(msg, MESSAGE_LENGTH, 13, ID);
PeerMessageUtil::setIntParam(&msg[5], index);
PeerMessageUtil::setIntParam(&msg[9], begin);
PeerMessageUtil::setIntParam(&msg[13], length);
}
return msg;
}
uint32_t BtRequestMessage::getMessageLength() {
return MESSAGE_LENGTH;
}
string BtRequestMessage::toString() const {
return "request index="+Util::uitos(index)+", begin="+Util::uitos(begin)+
", length="+Util::uitos(length);
}
void BtRequestMessage::onQueued() {
RequestSlot requestSlot(index, begin, length, blockIndex);
BT_MESSAGE_DISPATCHER(btContext, peer)->addOutstandingRequest(requestSlot);
}
bool BtRequestMessage::BtAbortOutstandingRequestEventListener::canHandle(const BtEventHandle& event) {
BtAbortOutstandingRequestEvent* intEvent = dynamic_cast<BtAbortOutstandingRequestEvent*>(event.get());
return intEvent != 0;
}
void BtRequestMessage::BtAbortOutstandingRequestEventListener::handleEventInternal(const BtEventHandle& event) {
message->handleAbortOutstandingRequestEvent(event);
}
void BtRequestMessage::handleAbortOutstandingRequestEvent(const BtEventHandle& event) {
BtAbortOutstandingRequestEvent* intEvent = (BtAbortOutstandingRequestEvent*)event.get();
if(index == intEvent->getPiece()->getIndex() &&
!invalidate &&
!sendingInProgress) {
invalidate = true;
}
}

117
src/BtRequestMessage.h Normal file
View File

@ -0,0 +1,117 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_REQUEST_MESSAGE_H_
#define _D_BT_REQUEST_MESSAGE_H_
#include "SimpleBtMessage.h"
#include "BtContext.h"
#include "PieceStorage.h"
#include "AbstractBtEventListener.h"
class BtRequestMessage;
typedef SharedHandle<BtRequestMessage> BtRequestMessageHandle;
class BtRequestMessage : public SimpleBtMessage {
private:
uint32_t index;
uint32_t begin;
uint32_t length;
uint32_t blockIndex;
char* msg;
static uint32_t MESSAGE_LENGTH;
class BtAbortOutstandingRequestEventListener : public AbstractBtEventListener {
private:
BtRequestMessage* message;
public:
BtAbortOutstandingRequestEventListener(BtRequestMessage* message):message(message) {}
virtual bool canHandle(const BtEventHandle& event);
virtual void handleEventInternal(const BtEventHandle& event);
};
typedef SharedHandle<BtAbortOutstandingRequestEventListener> BtAbortOutstandingRequestEventListenerHandle;
public:
BtRequestMessage(uint32_t index = 0,
uint32_t begin = 0,
uint32_t length = 0,
uint32_t blockIndex = 0)
:index(index),
begin(begin),
length(length),
blockIndex(blockIndex),
msg(0)
{
addEventListener(new BtAbortOutstandingRequestEventListener(this));
}
virtual ~BtRequestMessage() {
delete [] msg;
}
enum ID_t {
ID = 6
};
uint32_t getIndex() const { return index; }
void setIndex(uint32_t index) { this->index = index; }
uint32_t getBegin() const { return begin; }
void setBegin(uint32_t begin) { this->begin = begin; }
uint32_t getLength() const { return length; }
void setLength(uint32_t length) { this->length = length; }
uint32_t getBlockIndex() const { return blockIndex; }
void setBlockIndex(uint32_t blockIndex) { this->blockIndex = blockIndex; }
static BtRequestMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction();
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual string toString() const;
virtual void onQueued();
virtual void handleAbortOutstandingRequestEvent(const BtEventHandle& event);
};
#endif // _D_BT_REQUEST_MESSAGE_H_

View File

@ -0,0 +1,68 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_REQUEST_MESSAGE_VALIDATOR_H_
#define _D_BT_REQUEST_MESSAGE_VALIDATOR_H_
#include "BtMessageValidator.h"
#include "BtRequestMessage.h"
class BtRequestMessageValidator : public BtMessageValidator {
private:
const BtRequestMessage* message;
uint32_t numPiece;
uint32_t pieceLength;
public:
BtRequestMessageValidator(const BtRequestMessage* message,
uint32_t numPiece,
uint32_t pieceLength):
message(message),
numPiece(numPiece),
pieceLength(pieceLength) {}
virtual bool validate(Errors& error) {
// TODO
PeerMessageUtil::checkIndex(message->getIndex(), numPiece);
PeerMessageUtil::checkBegin(message->getBegin(), pieceLength);
PeerMessageUtil::checkLength(message->getLength());
PeerMessageUtil::checkRange(message->getBegin(),
message->getLength(),
pieceLength);
return true;
}
};
typedef SharedHandle<BtRequestMessageValidator> BtRequestMessageValidatorHandle;
#endif // _D_BT_REQUEST_MESSAGE_VALIDATOR_H_

View File

@ -0,0 +1,78 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtSuggestPieceMessage.h"
#include "PeerInteraction.h"
#include "PeerMessageUtil.h"
#include "Util.h"
#include "DlAbortEx.h"
BtSuggestPieceMessageHandle BtSuggestPieceMessage::create(const unsigned char* data, uint32_t dataLength) {
if(dataLength != 5) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be %d", "suggest piece", dataLength, 5);
}
int32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "suggest piece", ID);
}
BtSuggestPieceMessageHandle message = new BtSuggestPieceMessage();
message->setIndex(PeerMessageUtil::getIntParam(data, 1));
return message;
}
uint32_t BtSuggestPieceMessage::MESSAGE_LENGTH = 9;
const char* BtSuggestPieceMessage::getMessage() {
if(!msg) {
/**
* len --- 5, 4bytes
* id --- 13, 1byte
* piece index --- index, 4bytes
* total: 9bytes
*/
msg = new char[MESSAGE_LENGTH];
PeerMessageUtil::createPeerMessageString(msg, MESSAGE_LENGTH, 5, ID);
PeerMessageUtil::setIntParam(&msg[5], index);
}
return msg;
}
uint32_t BtSuggestPieceMessage::getMessageLength() {
return MESSAGE_LENGTH;
}
string BtSuggestPieceMessage::toString() const {
return "suggest piece index="+Util::uitos(index);
}

View File

@ -0,0 +1,81 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_SUGGEST_PIECE_MESSAGE_H_
#define _D_BT_SUGGEST_PIECE_MESSAGE_H_
#include "SimpleBtMessage.h"
class BtSuggestPieceMessage;
typedef SharedHandle<BtSuggestPieceMessage> BtSuggestPieceMessageHandle;
class BtSuggestPieceMessage : public SimpleBtMessage {
private:
uint32_t index;
char* msg;
static uint32_t MESSAGE_LENGTH;
public:
BtSuggestPieceMessage():index(0), msg(0) {}
virtual ~BtSuggestPieceMessage() {
delete [] msg;
}
enum ID_t {
ID = 13
};
void setIndex(uint32_t index) {
this->index = index;
}
uint32_t getIndex() const { return index; }
static BtSuggestPieceMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction() {
// TODO Current implementation ignores this message.
}
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual string toString() const;
};
#endif // _D_BT_SUGGEST_PIECE_MESSAGE_H_

View File

@ -0,0 +1,60 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_SUGGEST_PIECE_MESSAGE_VALIDATOR_H_
#define _D_BT_SUGGEST_PIECE_MESSAGE_VALIDATOR_H_
#include "BtMessageValidator.h"
#include "BtSuggestPieceMessage.h"
class BtSuggestPieceMessageValidator : public BtMessageValidator {
private:
const BtSuggestPieceMessage* message;
int numPiece;
public:
BtSuggestPieceMessageValidator(const BtSuggestPieceMessage* message,
int numPiece):
message(message),
numPiece(numPiece) {}
virtual bool validate(Errors& errors) {
// TODO
PeerMessageUtil::checkIndex(message->getIndex(), numPiece);
return true;
}
};
typedef SharedHandle<BtSuggestPieceMessageValidator> BtSuggestPieceMessageValidatorHandle;
#endif // _D_BT_SUGGEST_PIECE_MESSAGE_VALIDATOR_H_

85
src/BtUnchokeMessage.cc Normal file
View File

@ -0,0 +1,85 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "BtUnchokeMessage.h"
#include "PeerMessageUtil.h"
#include "DlAbortEx.h"
BtUnchokeMessageHandle BtUnchokeMessage::create(const unsigned char* data, uint32_t dataLength) {
if(dataLength != 1) {
throw new DlAbortEx("invalid payload size for %s, size = %d. It should be %d", "unchoke", dataLength, 1);
}
int32_t id = PeerMessageUtil::getId(data);
if(id != ID) {
throw new DlAbortEx("invalid ID=%d for %s. It should be %d.",
id, "unchoke", ID);
}
BtUnchokeMessageHandle message = new BtUnchokeMessage();
return message;
}
void BtUnchokeMessage::doReceivedAction() {
peer->peerChoking = false;
}
bool BtUnchokeMessage::sendPredicate() const {
return peer->amChoking;
}
uint32_t BtUnchokeMessage::MESSAGE_LENGTH = 5;
const char* BtUnchokeMessage::getMessage() {
if(!msg) {
/**
* len --- 1, 4bytes
* id --- 1, 1byte
* total: 5bytes
*/
msg = new char[MESSAGE_LENGTH];
PeerMessageUtil::createPeerMessageString(msg, MESSAGE_LENGTH, 1, ID);
}
return msg;
}
uint32_t BtUnchokeMessage::getMessageLength() {
return MESSAGE_LENGTH;
}
void BtUnchokeMessage::onSendComplete() {
peer->amChoking = false;
}
string BtUnchokeMessage::toString() const {
return "unchoke";
}

76
src/BtUnchokeMessage.h Normal file
View File

@ -0,0 +1,76 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_BT_UNCHOKE_MESSAGE_H_
#define _D_BT_UNCHOKE_MESSAGE_H_
#include "SimpleBtMessage.h"
class BtUnchokeMessage;
typedef SharedHandle<BtUnchokeMessage> BtUnchokeMessageHandle;
class BtUnchokeMessage : public SimpleBtMessage {
private:
char* msg;
static uint32_t MESSAGE_LENGTH;
public:
BtUnchokeMessage():msg(0) {}
virtual ~BtUnchokeMessage() {
delete [] msg;
}
enum ID_t {
ID = 1
};
static BtUnchokeMessageHandle create(const unsigned char* data, uint32_t dataLength);
virtual int32_t getId() const { return ID; }
virtual void doReceivedAction();
virtual const char* getMessage();
virtual uint32_t getMessageLength();
virtual string toString() const;
virtual bool sendPredicate() const;
virtual void onSendComplete();
};
#endif // _D_BT_UNCHOKE_MESSAGE_H_

View File

@ -62,7 +62,6 @@ DefaultBtAnnounce::DefaultBtAnnounce(BtContextHandle btContext,
{
prevAnnounceTime.setTimeInSec(0);
key = generateKey();
peerId = generatePeerId();
logger = LogFactory::getInstance();
}
@ -73,12 +72,6 @@ string DefaultBtAnnounce::generateKey() const {
return Util::randomAlpha(8);
}
string DefaultBtAnnounce::generatePeerId() const {
string peerId = "-aria2-";
peerId += Util::randomAlpha(20-peerId.size());
return peerId;
}
bool DefaultBtAnnounce::isDefaultAnnounceReady() {
return (trackers == 0 && prevAnnounceTime.elapsed(minInterval));
}
@ -131,7 +124,7 @@ string DefaultBtAnnounce::getAnnounceUrl() {
string url = announceList.getAnnounce()+"?"+
"info_hash="+Util::torrentUrlencode(btContext->getInfoHash(),
btContext->getInfoHashLength())+"&"+
"peer_id="+peerId+"&"+
"peer_id="+Util::torrentUrlencode(btContext->getPeerId(), 20)+"&"+
"port="+Util::itos(btRuntime->getListenPort())+"&"+
"uploaded="+Util::llitos(stat.getSessionUploadLength())+"&"+
"downloaded="+Util::llitos(stat.getSessionDownloadLength())+"&"+

View File

@ -60,7 +60,6 @@ private:
string trackerId;
string key;
int trackerNumTry;
string peerId;
const Option* option;
Logger* logger;
BtRuntimeHandle btRuntime;
@ -112,11 +111,7 @@ public:
virtual void shuffleAnnounce();
string generateKey() const;
string generatePeerId() const;
virtual string getPeerId() { return peerId; }
string generateKey() const;
};
#endif // _D_DEFAULT_BT_ANNOUNCE_H_

View File

@ -45,6 +45,12 @@ DefaultBtContext::DefaultBtContext() {}
DefaultBtContext::~DefaultBtContext() {}
string DefaultBtContext::generatePeerId() const {
string peerId = "-aria2-";
peerId += Util::randomAlpha(20-peerId.size());
return peerId;
}
const unsigned char* DefaultBtContext::getInfoHash() const {
return infoHash;
}

View File

@ -55,6 +55,7 @@ private:
int pieceLength;
string name;
int numPieces;
string peerId;
AnnounceTiers announceTiers;
void clear();
@ -92,6 +93,15 @@ private:
virtual int getPieceLength() const;
virtual int getNumPieces() const;
virtual const unsigned char* getPeerId() {
if(peerId == "") {
peerId = generatePeerId();
}
return (const unsigned char*)peerId.c_str();
}
string generatePeerId() const;
};
#endif // _D_DEFAULT_BT_CONTEXT_H_

307
src/DefaultBtInteractive.cc Normal file
View File

@ -0,0 +1,307 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "DefaultBtInteractive.h"
#include "prefs.h"
#include "message.h"
#include "BtHandshakeMessage.h"
#include "Util.h"
#include "BtKeepAliveMessage.h"
#include "BtChokeMessage.h"
#include "BtUnchokeMessage.h"
#include "DlAbortEx.h"
void DefaultBtInteractive::initiateHandshake() {
BtMessageHandle message =
BT_MESSAGE_FACTORY(btContext, peer)->
createHandshakeMessage(btContext->getInfoHash(),
btContext->getPeerId());
dispatcher->addMessageToQueue(message);
dispatcher->sendMessages();
}
BtMessageHandle DefaultBtInteractive::receiveHandshake(bool quickReply) {
BtHandshakeMessageHandle message =
btMessageReceiver->receiveHandshake(quickReply);
if(message.isNull()) {
return 0;
}
peer->setPeerId(message->getPeerId());
logger->info(MSG_RECEIVE_PEER_MESSAGE, cuid,
peer->ipaddr.c_str(), peer->port,
message->toString().c_str());
return message;
}
BtMessageHandle DefaultBtInteractive::receiveAndSendHandshake() {
return receiveHandshake(true);
}
void DefaultBtInteractive::doPostHandshakeProcessing() {
// TODO where is the valid place to rest haveCheckTime?
haveCheckPoint.reset();
keepAliveCheckPoint.reset();
floodingCheckPoint.reset();
addBitfieldMessageToQueue();
addAllowedFastMessageToQueue();
}
void DefaultBtInteractive::addBitfieldMessageToQueue() {
BtMessageFactoryHandle factory = BT_MESSAGE_FACTORY(btContext, peer);
if(peer->isFastExtensionEnabled()) {
if(pieceStorage->downloadFinished()) {
dispatcher->addMessageToQueue(factory->createHaveAllMessage());
} else if(pieceStorage->getCompletedLength() > 0) {
dispatcher->addMessageToQueue(factory->createBitfieldMessage());
} else {
dispatcher->addMessageToQueue(factory->createHaveNoneMessage());
}
} else {
if(pieceStorage->getCompletedLength() > 0) {
dispatcher->addMessageToQueue(factory->createBitfieldMessage());
}
}
}
void DefaultBtInteractive::addAllowedFastMessageToQueue() {
if(peer->isFastExtensionEnabled()) {
Integers fastSet = Util::computeFastSet(peer->ipaddr,
btContext->getInfoHash(),
btContext->getNumPieces(),
allowedFastSetSize);
for(Integers::const_iterator itr = fastSet.begin();
itr != fastSet.end(); itr++) {
dispatcher->addMessageToQueue(BT_MESSAGE_FACTORY(btContext, peer)->
createAllowedFastMessage(*itr));
}
}
}
void DefaultBtInteractive::decideChoking() {
if(peer->shouldBeChoking()) {
if(!peer->amChoking) {
dispatcher->addMessageToQueue(BT_MESSAGE_FACTORY(btContext, peer)->
createChokeMessage());
}
} else {
if(peer->amChoking) {
dispatcher->addMessageToQueue(BT_MESSAGE_FACTORY(btContext, peer)->
createUnchokeMessage());
}
}
}
void DefaultBtInteractive::checkHave() {
BtMessageFactoryHandle factory = BT_MESSAGE_FACTORY(btContext, peer);
Integers indexes =
pieceStorage->getAdvertisedPieceIndexes(cuid, haveCheckPoint);
haveCheckPoint.reset();
if(indexes.size() >= 20) {
if(peer->isFastExtensionEnabled() && pieceStorage->downloadFinished()) {
dispatcher->addMessageToQueue(factory->createHaveAllMessage());
} else {
dispatcher->addMessageToQueue(factory->createBitfieldMessage());
}
} else {
for(Integers::iterator itr = indexes.begin(); itr != indexes.end(); itr++) {
dispatcher->addMessageToQueue(factory->createHaveMessage(*itr));
}
}
}
void DefaultBtInteractive::sendKeepAlive() {
if(keepAliveCheckPoint.elapsed(option->getAsInt(PREF_BT_KEEP_ALIVE_INTERVAL))) {
if(dispatcher->countMessageInQueue() == 0) {
dispatcher->addMessageToQueue(BT_MESSAGE_FACTORY(btContext, peer)->createKeepAliveMessage());
dispatcher->sendMessages();
}
keepAliveCheckPoint.reset();
}
}
void DefaultBtInteractive::receiveMessages() {
for(int i = 0; i < 50; i++) {
int maxSpeedLimit = option->getAsInt(PREF_MAX_DOWNLOAD_LIMIT);
if(maxSpeedLimit > 0) {
TransferStat stat = peerStorage->calculateStat();
if(maxSpeedLimit < stat.downloadSpeed) {
break;
}
}
BtMessageHandle message = btMessageReceiver->receiveMessage();
if(message.isNull()) {
break;
}
logger->info(MSG_RECEIVE_PEER_MESSAGE, cuid,
peer->ipaddr.c_str(), peer->port,
message->toString().c_str());
message->doReceivedAction();
switch(message->getId()) {
case BtKeepAliveMessage::ID:
floodingStat.incKeepAliveCount();
break;
case BtChokeMessage::ID:
if(!peer->peerChoking) {
floodingStat.incChokeUnchokeCount();
}
break;
case BtUnchokeMessage::ID:
if(peer->peerChoking) {
floodingStat.incChokeUnchokeCount();
}
break;
}
}
}
void DefaultBtInteractive::decideInterest() {
if(!pieceStorage->hasMissingPiece(peer)) {
if(peer->amInterested) {
logger->debug("CUID#%d - Not interested in the peer", cuid);
dispatcher->
addMessageToQueue(BT_MESSAGE_FACTORY(btContext, peer)->
createNotInterestedMessage());
}
} else {
if(!peer->amInterested) {
logger->debug("CUID#%d - Interested in the peer", cuid);
dispatcher->
addMessageToQueue(BT_MESSAGE_FACTORY(btContext, peer)->
createInterestedMessage());
}
}
}
void DefaultBtInteractive::fillPiece(int maxPieceNum) {
if(pieceStorage->hasMissingPiece(peer)) {
if(peer->peerChoking) {
dispatcher->doChokedAction();
if(peer->isFastExtensionEnabled()) {
while(btRequestFactory->countTargetPiece() < maxPieceNum) {
PieceHandle piece = pieceStorage->getMissingFastPiece(peer);
if(piece.isNull()) {
break;
} else {
btRequestFactory->addTargetPiece(piece);
}
}
}
} else {
while(btRequestFactory->countTargetPiece() < maxPieceNum) {
PieceHandle piece = pieceStorage->getMissingPiece(peer);
if(piece.isNull()) {
break;
} else {
btRequestFactory->addTargetPiece(piece);
}
}
}
}
}
void DefaultBtInteractive::addRequests() {
uint32_t MAX_PENDING_REQUEST;
if(peer->getLatency() < 500) {
MAX_PENDING_REQUEST = 24;
} else if(peer->getLatency() < 1500) {
MAX_PENDING_REQUEST = 12;
} else {
MAX_PENDING_REQUEST = 6;
}
uint32_t pieceNum;
if(pieceStorage->isEndGame()) {
pieceNum = 1;
} else {
uint32_t blocks = DIV_FLOOR(btContext->getPieceLength(), BLOCK_LENGTH);
pieceNum = DIV_FLOOR(MAX_PENDING_REQUEST, blocks);
}
fillPiece(pieceNum);
uint32_t reqNumToCreate =
MAX_PENDING_REQUEST <= dispatcher->countOutstandingRequest() ?
0 : MAX_PENDING_REQUEST-dispatcher->countOutstandingRequest();
if(reqNumToCreate > 0) {
//logger->debug("CUID#%d - %u requets to go.", cuid, reqNumToCreate);
BtMessages requests;
if(pieceStorage->isEndGame()) {
requests = btRequestFactory->createRequestMessagesOnEndGame(reqNumToCreate);
} else {
requests = btRequestFactory->createRequestMessages(reqNumToCreate);
}
dispatcher->addMessageToQueue(requests);
}
}
void DefaultBtInteractive::cancelAllPiece() {
btRequestFactory->removeAllTargetPiece();
}
void DefaultBtInteractive::sendPendingMessage() {
dispatcher->sendMessages();
}
void DefaultBtInteractive::detectMessageFlooding() {
if(floodingCheckPoint.elapsed(FLOODING_CHECK_INTERVAL)) {
if(floodingStat.getChokeUnchokeCount() >= 2 ||
floodingStat.getKeepAliveCount() >= 2) {
throw new DlAbortEx("Flooding detected.");
} else {
floodingStat.reset();
}
floodingCheckPoint.reset();
}
}
void DefaultBtInteractive::doInteractionProcessing() {
decideChoking();
detectMessageFlooding();
dispatcher->checkRequestSlotAndDoNecessaryThing();
checkHave();
sendKeepAlive();
receiveMessages();
btRequestFactory->removeCompletedPiece();
decideInterest();
if(!pieceStorage->downloadFinished()) {
addRequests();
}
sendPendingMessage();
}

195
src/DefaultBtInteractive.h Normal file
View File

@ -0,0 +1,195 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_DEFAULT_BT_INTERACTIVE_H_
#define _D_DEFAULT_BT_INTERACTIVE_H_
#include "BtInteractive.h"
#include "Peer.h"
#include "BtContext.h"
#include "PieceStorage.h"
#include "PeerStorage.h"
#include "BtMessageReceiver.h"
#include "BtMessageDispatcher.h"
#include "BtRequestFactory.h"
#include "PeerConnection.h"
#include "BtRegistry.h"
#include "Logger.h"
#include "LogFactory.h"
#include "TimeA2.h"
class FloodingStat {
private:
uint32_t chokeUnchokeCount;
uint32_t keepAliveCount;
public:
FloodingStat():chokeUnchokeCount(0), keepAliveCount(0) {}
void incChokeUnchokeCount() {
if(chokeUnchokeCount < UINT32_MAX) {
chokeUnchokeCount++;
}
}
void incKeepAliveCount() {
if(keepAliveCount < UINT32_MAX) {
keepAliveCount++;
}
}
uint32_t getChokeUnchokeCount() const {
return chokeUnchokeCount;
}
uint32_t getKeepAliveCount() const {
return keepAliveCount;
}
void reset() {
chokeUnchokeCount = 0;
keepAliveCount = 0;
}
};
class DefaultBtInteractive : public BtInteractive {
private:
int32_t cuid;
PeerHandle peer;
BtContextHandle btContext;
PeerStorageHandle peerStorage;
PieceStorageHandle pieceStorage;
BtMessageReceiverHandle btMessageReceiver;
BtMessageDispatcherHandle dispatcher;
BtRequestFactoryHandle btRequestFactory;
PeerConnectionHandle peerConnection;
const Logger* logger;
uint32_t allowedFastSetSize;
Time haveCheckPoint;
Time keepAliveCheckPoint;
Time floodingCheckPoint;
FloodingStat floodingStat;
const Option* option;
static const uint32_t FLOODING_CHECK_INTERVAL = 5;
void addBitfieldMessageToQueue();
void addAllowedFastMessageToQueue();
void decideChoking();
void checkHave();
void sendKeepAlive();
void decideInterest();
void fillPiece(int maxPieceNum);
void addRequests();
void detectMessageFlooding();
public:
DefaultBtInteractive():peer(0),
btContext(0),
peerStorage(0),
pieceStorage(0),
btMessageReceiver(0),
dispatcher(0),
btRequestFactory(0),
peerConnection(0),
logger(LogFactory::getInstance()),
allowedFastSetSize(10)
{
logger->debug("DefaultBtInteractive instantiated.");
}
virtual ~DefaultBtInteractive() {
logger->debug("DefaultBtInteractive deleted.");
}
virtual void initiateHandshake();
virtual BtMessageHandle receiveHandshake(bool quickReply = false);
virtual BtMessageHandle receiveAndSendHandshake();
virtual void doPostHandshakeProcessing();
virtual void doInteractionProcessing();
virtual void cancelAllPiece();
virtual void sendPendingMessage();
void receiveMessages();
virtual uint32_t countPendingMessage() {
return dispatcher->countMessageInQueue();
}
virtual bool isSendingMessageInProgress() {
return dispatcher->isSendingInProgress();
}
void setCuid(int32_t cuid) {
this->cuid = cuid;
}
void setPeer(const PeerHandle& peer) {
this->peer = peer;
}
void setBtContext(const BtContextHandle& btContext) {
this->btContext = btContext;
this->peerStorage = PEER_STORAGE(btContext);
this->pieceStorage = PIECE_STORAGE(btContext);
}
void setBtMessageReceiver(const BtMessageReceiverHandle& receiver) {
this->btMessageReceiver = receiver;
}
void setDispatcher(const BtMessageDispatcherHandle& dispatcher) {
this->dispatcher = dispatcher;
}
void setBtRequestFactory(const BtRequestFactoryHandle& factory) {
this->btRequestFactory = factory;
}
void setPeerConnection(const PeerConnectionHandle& peerConnection) {
this->peerConnection = peerConnection;
}
void setOption(const Option* option) {
this->option = option;
}
};
typedef SharedHandle<DefaultBtInteractive> DefaultBtInteractiveHandle;
#endif // _D_DEFAULT_BT_INTERACTIVE_H_

View File

@ -0,0 +1,214 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "DefaultBtMessageDispatcher.h"
#include "BtRegistry.h"
#include "prefs.h"
#include "BtAbortOutstandingRequestEvent.h"
#include "BtCancelSendingPieceEvent.h"
#include "BtChokedEvent.h"
#include "BtChokingEvent.h"
#include "BtRegistry.h"
#include "BtMessageFactory.h"
void DefaultBtMessageDispatcher::addMessageToQueue(const BtMessageHandle& btMessage)
{
btMessage->onQueued();
messageQueue.push_back(btMessage);
}
void DefaultBtMessageDispatcher::addMessageToQueue(const BtMessages& btMessages)
{
for(BtMessages::const_iterator itr = btMessages.begin(); itr != btMessages.end(); itr++) {
addMessageToQueue(*itr);
}
}
void DefaultBtMessageDispatcher::sendMessages() {
BtMessages tempQueue;
int32_t uploadLimit = option->getAsInt(PREF_MAX_UPLOAD_LIMIT);
while(messageQueue.size() > 0) {
BtMessageHandle msg = messageQueue.front();
messageQueue.pop_front();
if(uploadLimit > 0) {
TransferStat stat = peerStorage->calculateStat();
if(uploadLimit < stat.getUploadSpeed() &&
msg->isUploading() && !msg->isSendingInProgress()) {
tempQueue.push_back(msg);
continue;
}
}
msg->send();
if(msg->isSendingInProgress()) {
messageQueue.push_front(msg);
break;
}
}
copy(tempQueue.begin(), tempQueue.end(), back_inserter(messageQueue));
}
// Cancel sending piece message to peer.
void DefaultBtMessageDispatcher::doCancelSendingPieceAction(uint32_t index, uint32_t begin, uint32_t blockLength)
{
BtCancelSendingPieceEventHandle event =
new BtCancelSendingPieceEvent(index, begin, blockLength);
BtMessages tempQueue = messageQueue;
for(BtMessages::iterator itr = tempQueue.begin(); itr != tempQueue.end(); itr++) {
(*itr)->handleEvent(event);
}
}
// Cancel sending piece message to peer.
// TODO Is this method really necessary?
void DefaultBtMessageDispatcher::doCancelSendingPieceAction(const PieceHandle& piece)
{
}
// localhost cancels outstanding download requests to the peer.
void DefaultBtMessageDispatcher::doAbortOutstandingRequestAction(const PieceHandle& piece) {
for(RequestSlots::iterator itr = requestSlots.begin();
itr != requestSlots.end();) {
RequestSlot& slot = *itr;
if(slot.getIndex() == piece->getIndex()) {
logger->debug("CUID#%d - Deleting request slot index=%d, blockIndex=%d",
cuid,
slot.getIndex(),
slot.getBlockIndex());
piece->cancelBlock(slot.getBlockIndex());
itr = requestSlots.erase(itr);
} else {
itr++;
}
}
BtAbortOutstandingRequestEventHandle event =
new BtAbortOutstandingRequestEvent(piece);
BtMessages tempQueue = messageQueue;
for(BtMessages::iterator itr = tempQueue.begin(); itr != tempQueue.end(); ++itr) {
(*itr)->handleEvent(event);
}
}
// localhost received choke message from the peer.
void DefaultBtMessageDispatcher::doChokedAction()
{
for(RequestSlots::iterator itr = requestSlots.begin();
itr != requestSlots.end();) {
RequestSlot& slot = *itr;
logger->debug("CUID#%d - Deleting request slot index=%d, blockIndex=%d"
" because localhost got choked.",
cuid,
slot.getIndex(),
slot.getBlockIndex());
PieceHandle piece = pieceStorage->getPiece(slot.getIndex());
piece->cancelBlock(slot.getBlockIndex());
itr = requestSlots.erase(itr);
}
BtChokedEventHandle event = new BtChokedEvent();
BtMessages tempQueue = messageQueue;
for(BtMessages::iterator itr = tempQueue.begin(); itr != tempQueue.end(); ++itr) {
(*itr)->handleEvent(event);
}
}
// localhost dispatched choke message to the peer.
void DefaultBtMessageDispatcher::doChokingAction()
{
BtChokingEventHandle event = new BtChokingEvent();
BtMessages tempQueue = messageQueue;
for(BtMessages::iterator itr = tempQueue.begin(); itr != tempQueue.end(); ++itr) {
(*itr)->handleEvent(event);
}
}
void DefaultBtMessageDispatcher::checkRequestSlotAndDoNecessaryThing()
{
for(RequestSlots::iterator itr = requestSlots.begin();
itr != requestSlots.end();) {
RequestSlot& slot = *itr;
PieceHandle piece = pieceStorage->getPiece(slot.getIndex());
if(slot.isTimeout(option->getAsInt(PREF_BT_REQUEST_TIMEOUT))) {
logger->debug("CUID#%d - Deleting request slot blockIndex=%d"
" because of time out",
cuid,
slot.getBlockIndex());
piece->cancelBlock(slot.getBlockIndex());
peer->snubbing = true;
itr = requestSlots.erase(itr);
} else if(piece->hasBlock(slot.getBlockIndex())) {
logger->debug("CUID#%d - Deleting request slot blockIndex=%d because"
" the block has been acquired.",
cuid,
slot.getBlockIndex());
addMessageToQueue(BT_MESSAGE_FACTORY(btContext, peer)->
createCancelMessage(slot.getIndex(),
slot.getBegin(),
slot.getLength()));
itr = requestSlots.erase(itr);
} else {
itr++;
}
}
}
bool DefaultBtMessageDispatcher::isSendingInProgress()
{
if(messageQueue.size() > 0) {
return messageQueue.front()->isSendingInProgress();
} else {
return false;
}
}
uint32_t DefaultBtMessageDispatcher::countOutstandingRequest()
{
return requestSlots.size();
}
bool DefaultBtMessageDispatcher::isOutstandingRequest(uint32_t index, uint32_t blockIndex) {
for(RequestSlots::const_iterator itr = requestSlots.begin();
itr != requestSlots.end(); itr++) {
const RequestSlot& slot = *itr;
if(slot.getIndex() == index && slot.getBlockIndex() == blockIndex) {
return true;
}
}
return false;
}

View File

@ -0,0 +1,163 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_DEFAULT_BT_MESSAGE_DISPATCHER_H_
#define _D_DEFAULT_BT_MESSAGE_DISPATCHER_H_
#include "BtMessageDispatcher.h"
#include "BtContext.h"
#include "PeerStorage.h"
#include "PieceStorage.h"
#include "RequestSlot.h"
#include "BtMessage.h"
#include "Peer.h"
#include "Option.h"
#include "LogFactory.h"
#include "Logger.h"
#include "BtRegistry.h"
class DefaultBtMessageDispatcher : public BtMessageDispatcher {
private:
int32_t cuid;
BtMessages messageQueue;
RequestSlots requestSlots;
BtContextHandle btContext;
PeerStorageHandle peerStorage;
PieceStorageHandle pieceStorage;
PeerHandle peer;
const Option* option;
const Logger* logger;
public:
DefaultBtMessageDispatcher():
cuid(0),
btContext(0),
peerStorage(0),
pieceStorage(0),
peer(0),
option(0),
logger(LogFactory::getInstance())
{
logger->debug("DefaultBtMessageDispatcher::instantiated");
}
virtual ~DefaultBtMessageDispatcher()
{
logger->debug("DefaultBtMessageDispatcher::deleted");
}
virtual void addMessageToQueue(const BtMessageHandle& btMessage);
virtual void addMessageToQueue(const BtMessages& btMessages);
virtual void sendMessages();
virtual void doCancelSendingPieceAction(uint32_t index, uint32_t begin, uint32_t blockLength);
virtual void doCancelSendingPieceAction(const PieceHandle& piece);
virtual void doAbortOutstandingRequestAction(const PieceHandle& piece);
virtual void doChokedAction();
virtual void doChokingAction();
virtual void checkRequestSlotAndDoNecessaryThing();
virtual bool isSendingInProgress();
virtual uint32_t countMessageInQueue() {
return messageQueue.size();
}
virtual uint32_t countOutstandingRequest();
virtual bool isOutstandingRequest(uint32_t index, uint32_t blockIndex);
virtual RequestSlot getOutstandingRequest(uint32_t index, uint32_t begin, uint32_t blockLength) {
for(RequestSlots::iterator itr = requestSlots.begin();
itr != requestSlots.end(); itr++) {
if(itr->getIndex() == index &&
itr->getBegin() == begin &&
itr->getLength() == blockLength) {
return *itr;
}
}
return RequestSlot::nullSlot;
}
virtual void removeOutstandingRequest(const RequestSlot& slot) {
RequestSlots temp;
remove_copy(requestSlots.begin(), requestSlots.end(), back_inserter(temp), slot);
requestSlots = temp;
}
virtual void addOutstandingRequest(const RequestSlot& requestSlot) {
if(!isOutstandingRequest(requestSlot.getIndex(), requestSlot.getBlockIndex())) {
requestSlots.push_back(requestSlot);
}
}
BtMessages& getMessageQueue() {
return messageQueue;
}
void setOption(const Option* option) {
this->option = option;
}
const Option* getOption() const {
return option;
}
RequestSlots& getRequestSlots() {
return requestSlots;
}
void setPeer(const PeerHandle& peer) {
this->peer = peer;
}
void setBtContext(const BtContextHandle& btContext) {
this->btContext = btContext;
this->pieceStorage = PIECE_STORAGE(btContext);
this->peerStorage = PEER_STORAGE(btContext);
}
void setCuid(int32_t cuid) {
this->cuid = cuid;
}
};
typedef SharedHandle<DefaultBtMessageDispatcher> DefaultBtMessageDispatcherHandle;
#endif // _D_DEFAULT_BT_MESSAGE_DISPATCHER_H_

View File

@ -0,0 +1,347 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "DefaultBtMessageFactory.h"
#include "DlAbortEx.h"
#include "PeerMessageUtil.h"
#include "BtKeepAliveMessage.h"
#include "BtChokeMessage.h"
#include "BtUnchokeMessage.h"
#include "BtInterestedMessage.h"
#include "BtNotInterestedMessage.h"
#include "BtHaveMessage.h"
#include "BtHaveMessageValidator.h"
#include "BtBitfieldMessage.h"
#include "BtBitfieldMessageValidator.h"
#include "BtRequestMessage.h"
#include "BtRequestMessageValidator.h"
#include "BtCancelMessage.h"
#include "BtCancelMessageValidator.h"
#include "BtPieceMessage.h"
#include "BtPieceMessageValidator.h"
#include "BtPortMessage.h"
#include "BtHaveAllMessage.h"
#include "BtHaveNoneMessage.h"
#include "BtRejectMessage.h"
#include "BtRejectMessageValidator.h"
#include "BtSuggestPieceMessage.h"
#include "BtSuggestPieceMessageValidator.h"
#include "BtAllowedFastMessage.h"
#include "BtAllowedFastMessageValidator.h"
#include "BtHandshakeMessage.h"
#include "BtHandshakeMessageValidator.h"
BtMessageHandle
DefaultBtMessageFactory::createBtMessage(const unsigned char* data, uint32_t dataLength)
{
AbstractBtMessageHandle msg(0);
if(dataLength == 0) {
// keep-alive
msg = new BtKeepAliveMessage();
} else {
int32_t id = PeerMessageUtil::getId(data);
switch(id) {
case BtChokeMessage::ID:
msg = BtChokeMessage::create(data, dataLength);
break;
case BtUnchokeMessage::ID:
msg = BtUnchokeMessage::create(data, dataLength);
break;
case BtInterestedMessage::ID:
msg = BtInterestedMessage::create(data, dataLength);
break;
case BtNotInterestedMessage::ID:
msg = BtNotInterestedMessage::create(data, dataLength);
break;
case BtHaveMessage::ID:
msg = BtHaveMessage::create(data, dataLength);
msg->setBtMessageValidator(new BtHaveMessageValidator((BtHaveMessage*)msg.get(),
btContext->getNumPieces()));
break;
case BtBitfieldMessage::ID:
msg = BtBitfieldMessage::create(data, dataLength);
msg->setBtMessageValidator(new BtBitfieldMessageValidator((BtBitfieldMessage*)msg.get(),
btContext->getNumPieces()));
break;
case BtRequestMessage::ID: {
BtRequestMessageHandle temp = BtRequestMessage::create(data, dataLength);
BtMessageValidatorHandle validator =
new BtRequestMessageValidator(temp.get(),
btContext->getNumPieces(),
pieceStorage->getPieceLength(temp->getIndex()));
temp->setBtMessageValidator(validator);
msg = temp;
break;
}
case BtCancelMessage::ID: {
BtCancelMessageHandle temp = BtCancelMessage::create(data, dataLength);
BtMessageValidatorHandle validator =
new BtCancelMessageValidator(temp.get(),
btContext->getNumPieces(),
pieceStorage->getPieceLength(temp->getIndex()));
temp->setBtMessageValidator(validator);
msg = temp;
break;
}
case BtPieceMessage::ID: {
BtPieceMessageHandle temp = BtPieceMessage::create(data, dataLength);
BtMessageValidatorHandle validator =
new BtPieceMessageValidator(temp.get(),
btContext->getNumPieces(),
pieceStorage->getPieceLength(temp->getIndex()));
temp->setBtMessageValidator(validator);
msg = temp;
break;
}
case BtPortMessage::ID:
msg = BtPortMessage::create(data, dataLength);
break;
case BtHaveAllMessage::ID:
msg = BtHaveAllMessage::create(data, dataLength);
break;
case BtHaveNoneMessage::ID:
msg = BtHaveNoneMessage::create(data, dataLength);
break;
case BtRejectMessage::ID: {
BtRejectMessageHandle temp = BtRejectMessage::create(data, dataLength);
BtMessageValidatorHandle validator =
new BtRejectMessageValidator(temp.get(),
btContext->getNumPieces(),
pieceStorage->getPieceLength(temp->getIndex()));
temp->setBtMessageValidator(validator);
msg = temp;
break;
}
case BtSuggestPieceMessage::ID: {
BtSuggestPieceMessageHandle temp = BtSuggestPieceMessage::create(data, dataLength);
BtMessageValidatorHandle validator =
new BtSuggestPieceMessageValidator(temp.get(),
btContext->getNumPieces());
temp->setBtMessageValidator(validator);
msg = temp;
break;
}
case BtAllowedFastMessage::ID: {
BtAllowedFastMessageHandle temp = BtAllowedFastMessage::create(data, dataLength);
BtMessageValidatorHandle validator =
new BtAllowedFastMessageValidator(temp.get(),
btContext->getNumPieces());
temp->setBtMessageValidator(validator);
msg = temp;
break;
}
default:
throw new DlAbortEx("Invalid message id. id = %d", id);
}
}
setCommonProperty(msg);
return msg;
}
void DefaultBtMessageFactory::setCommonProperty(const AbstractBtMessageHandle& msg) {
msg->setCuid(cuid);
msg->setPeer(peer);
msg->setBtContext(btContext);
}
BtMessageHandle
DefaultBtMessageFactory::createHandshakeMessage(const unsigned char* data, uint32_t dataLength)
{
BtHandshakeMessageHandle msg = BtHandshakeMessage::create(data, dataLength);
BtMessageValidatorHandle validator =
new BtHandshakeMessageValidator(msg.get(),
btContext->getInfoHash());
msg->setBtMessageValidator(validator);
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createHandshakeMessage(const unsigned char* infoHash,
const unsigned char* peerId)
{
BtHandshakeMessageHandle msg = new BtHandshakeMessage(infoHash, peerId);
BtMessageValidatorHandle validator =
new BtHandshakeMessageValidator(msg.get(),
btContext->getInfoHash());
msg->setBtMessageValidator(validator);
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createRequestMessage(const PieceHandle& piece, uint32_t blockIndex)
{
BtRequestMessageHandle msg =
new BtRequestMessage(piece->getIndex(),
blockIndex*piece->getBlockLength(),
piece->getBlockLength(blockIndex),
blockIndex);
BtMessageValidatorHandle validator =
new BtRequestMessageValidator(msg.get(),
btContext->getNumPieces(),
pieceStorage->getPieceLength(msg->getIndex()));
msg->setBtMessageValidator(validator);
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createCancelMessage(uint32_t index, uint32_t begin, uint32_t length)
{
BtCancelMessageHandle msg = new BtCancelMessage(index, begin, length);
BtMessageValidatorHandle validator =
new BtCancelMessageValidator(msg.get(),
btContext->getNumPieces(),
pieceStorage->getPieceLength(index));
msg->setBtMessageValidator(validator);
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createPieceMessage(uint32_t index, uint32_t begin, uint32_t length)
{
BtPieceMessageHandle msg = new BtPieceMessage(index, begin, length);
BtMessageValidatorHandle validator =
new BtPieceMessageValidator(msg.get(),
btContext->getNumPieces(),
pieceStorage->getPieceLength(index));
msg->setBtMessageValidator(validator);
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createHaveMessage(uint32_t index)
{
BtHaveMessageHandle msg = new BtHaveMessage(index);
msg->setBtMessageValidator(new BtHaveMessageValidator(msg.get(),
btContext->getNumPieces()));
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createChokeMessage()
{
BtChokeMessageHandle msg = new BtChokeMessage();
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createUnchokeMessage()
{
BtUnchokeMessageHandle msg = new BtUnchokeMessage();
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createInterestedMessage()
{
BtInterestedMessageHandle msg = new BtInterestedMessage();
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createNotInterestedMessage()
{
BtNotInterestedMessageHandle msg = new BtNotInterestedMessage();
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createBitfieldMessage()
{
BtBitfieldMessageHandle msg =
new BtBitfieldMessage(pieceStorage->getBitfield(),
pieceStorage->getBitfieldLength());
msg->setBtMessageValidator(new BtBitfieldMessageValidator(msg.get(),
btContext->getNumPieces()));
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createKeepAliveMessage()
{
BtKeepAliveMessageHandle msg = new BtKeepAliveMessage();
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createHaveAllMessage()
{
BtHaveAllMessageHandle msg = new BtHaveAllMessage();
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createHaveNoneMessage()
{
BtHaveNoneMessageHandle msg = new BtHaveNoneMessage();
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createRejectMessage(uint32_t index, uint32_t begin, uint32_t length)
{
BtRejectMessageHandle msg = new BtRejectMessage(index, begin, length);
BtMessageValidatorHandle validator =
new BtRejectMessageValidator(msg.get(),
btContext->getNumPieces(),
pieceStorage->getPieceLength(index));
msg->setBtMessageValidator(validator);
setCommonProperty(msg);
return msg;
}
BtMessageHandle
DefaultBtMessageFactory::createAllowedFastMessage(uint32_t index)
{
BtAllowedFastMessageHandle msg = new BtAllowedFastMessage(index);
BtMessageValidatorHandle validator =
new BtAllowedFastMessageValidator(msg.get(),
btContext->getNumPieces());
msg->setBtMessageValidator(validator);
setCommonProperty(msg);
return msg;
}

View File

@ -0,0 +1,131 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_DEFAULT_BT_MESSAGE_FACTORY_H_
#define _D_DEFAULT_BT_MESSAGE_FACTORY_H_
#include "BtMessageFactory.h"
#include "Peer.h"
#include "AbstractBtMessage.h"
#include "BtRegistry.h"
class DefaultBtMessageFactory : public BtMessageFactory {
private:
int32_t cuid;
BtContextHandle btContext;
PieceStorageHandle pieceStorage;
PeerHandle peer;
void setCommonProperty(const AbstractBtMessageHandle& msg);
public:
DefaultBtMessageFactory():cuid(0),
btContext(0),
pieceStorage(0),
peer(0)
{
LogFactory::getInstance()->debug("DefaultBtMessageFactory::instantiated");
}
virtual ~DefaultBtMessageFactory()
{
LogFactory::getInstance()->debug("DefaultBtMessageFactory::deleted");
}
virtual BtMessageHandle
createBtMessage(const unsigned char* msg, uint32_t msgLength);
virtual BtMessageHandle
createHandshakeMessage(const unsigned char* msg, uint32_t msgLength);
virtual BtMessageHandle
createHandshakeMessage(const unsigned char* infoHash,
const unsigned char* peerId);
virtual BtMessageHandle
createRequestMessage(const PieceHandle& piece, uint32_t blockIndex);
virtual BtMessageHandle
createCancelMessage(uint32_t index, uint32_t begin, uint32_t length);
virtual BtMessageHandle
createPieceMessage(uint32_t index, uint32_t begin, uint32_t length);
virtual BtMessageHandle createHaveMessage(uint32_t index);
virtual BtMessageHandle createChokeMessage();
virtual BtMessageHandle createUnchokeMessage();
virtual BtMessageHandle createInterestedMessage();
virtual BtMessageHandle createNotInterestedMessage();
virtual BtMessageHandle createBitfieldMessage();
virtual BtMessageHandle createKeepAliveMessage();
virtual BtMessageHandle createHaveAllMessage();
virtual BtMessageHandle createHaveNoneMessage();
virtual BtMessageHandle
createRejectMessage(uint32_t index, uint32_t begin, uint32_t length);
virtual BtMessageHandle createAllowedFastMessage(uint32_t index);
void setPeer(const PeerHandle& peer) {
this->peer = peer;
}
PeerHandle getPeer() const {
return peer;
}
void setBtContext(const BtContextHandle& btContext) {
this->btContext = btContext;
this->pieceStorage = PIECE_STORAGE(btContext);
}
BtContextHandle getBtContext() const {
return btContext;
}
void setCuid(int32_t cuid) {
this->cuid = cuid;
}
};
typedef SharedHandle<DefaultBtMessageFactory> DefaultBtMessageFactoryHandle;
#endif // _D_DEFAULT_BT_MESSAGE_FACTORY_H_

View File

@ -0,0 +1,95 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "DefaultBtMessageReceiver.h"
#include "BtHandshakeMessage.h"
BtMessageHandle DefaultBtMessageReceiver::receiveHandshake(bool quickReply) {
unsigned char data[BtHandshakeMessage::MESSAGE_LENGTH];
uint32_t dataLength = sizeof(data);
bool retval = peerConnection->receiveHandshake(data, dataLength);
// To handle tracker's NAT-checking feature
if(!handshakeSent && quickReply && dataLength >= 48) {
handshakeSent = true;
// check info_hash
if(memcmp(btContext->getInfoHash(), &data[28], INFO_HASH_LENGTH) == 0) {
sendHandshake();
}
}
if(!retval) {
return 0;
}
BtHandshakeMessageHandle msg =
BT_MESSAGE_FACTORY(btContext, peer)->createHandshakeMessage(data, dataLength);
Errors errors;
if(msg->validate(errors)) {
if(msg->isFastExtensionSupported()) {
peer->setFastExtensionEnabled(true);
logger->info("CUID#%d - Fast extension enabled.", cuid);
}
} else {
// TODO throw exception here based on errors
}
return msg;
}
BtMessageHandle DefaultBtMessageReceiver::receiveAndSendHandshake() {
return receiveHandshake(true);
}
void DefaultBtMessageReceiver::sendHandshake() {
BtHandshakeMessageHandle msg =
BT_MESSAGE_FACTORY(btContext, peer)->createHandshakeMessage(btContext->getInfoHash(),
btContext->getPeerId());
dispatcher->addMessageToQueue(msg);
dispatcher->sendMessages();
}
BtMessageHandle DefaultBtMessageReceiver::receiveMessage() {
unsigned char data[MAX_PAYLOAD_LEN];
uint32_t dataLength = 0;
if(!peerConnection->receiveMessage(data, dataLength)) {
return 0;
}
BtMessageHandle msg =
BT_MESSAGE_FACTORY(btContext, peer)->createBtMessage(data, dataLength);
Errors errors;
if(msg->validate(errors)) {
return msg;
} else {
// TODO throw exception here based on errors;
return 0;
}
}

View File

@ -0,0 +1,120 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_DEFAULT_BT_MESSAGE_RECEIVER_H_
#define _D_DEFAULT_BT_MESSAGE_RECEIVER_H_
#include "BtMessageReceiver.h"
#include "BtContext.h"
#include "BtRegistry.h"
#include "Peer.h"
#include "PeerConnection.h"
#include "BtMessageDispatcher.h"
#include "Logger.h"
#include "LogFactory.h"
class DefaultBtMessageReceiver : public BtMessageReceiver {
private:
int32_t cuid;
bool handshakeSent;
BtContextHandle btContext;
PeerHandle peer;
PeerConnectionHandle peerConnection;
BtMessageDispatcherHandle dispatcher;
const Logger* logger;
void sendHandshake();
public:
DefaultBtMessageReceiver():cuid(0),
handshakeSent(false),
btContext(0),
peer(0),
peerConnection(0),
dispatcher(0),
logger(LogFactory::getInstance())
{
logger->debug("DefaultBtMessageReceiver::instantiated");
}
virtual ~DefaultBtMessageReceiver()
{
logger->debug("DefaultBtMessageReceiver::deleted");
}
virtual BtMessageHandle receiveHandshake(bool quickReply = false);
virtual BtMessageHandle receiveAndSendHandshake();
virtual BtMessageHandle receiveMessage();
void setCuid(int32_t cuid) {
this->cuid = cuid;
}
int32_t getCuid() const {
return cuid;
}
void setPeerConnection(const PeerConnectionHandle& peerConnection) {
this->peerConnection = peerConnection;
}
PeerConnectionHandle getPeerConnection() const {
return peerConnection;
}
void setBtContext(const BtContextHandle& btContext) {
this->btContext = btContext;
}
BtContextHandle getBtContext() const {
return btContext;
}
void setPeer(const PeerHandle& peer) {
this->peer = peer;
}
PeerHandle getPeer() const {
return peer;
}
void setDispatcher(const BtMessageDispatcherHandle& dispatcher) {
this->dispatcher = dispatcher;
}
};
typedef SharedHandle<DefaultBtMessageReceiver> DefaultBtMessageReceiverHandle;
#endif // _D_DEFAULT_BT_MESSAGE_RECEIVER_H_

View File

@ -0,0 +1,99 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#include "DefaultBtRequestFactory.h"
void DefaultBtRequestFactory::removeCompletedPiece() {
for(Pieces::iterator itr = pieces.begin(); itr != pieces.end();) {
PieceHandle& piece = *itr;
if(piece->pieceComplete()) {
dispatcher->doAbortOutstandingRequestAction(piece);
itr = pieces.erase(itr);
} else {
itr++;
}
}
}
void DefaultBtRequestFactory::removeTargetPiece(const PieceHandle& piece) {
Pieces temp;
remove_copy(pieces.begin(), pieces.end(), back_inserter(temp), piece);
pieces = temp;
dispatcher->doAbortOutstandingRequestAction(piece);
pieceStorage->cancelPiece(piece);
}
void DefaultBtRequestFactory::removeAllTargetPiece() {
for(Pieces::iterator itr = pieces.begin(); itr != pieces.end(); itr++) {
dispatcher->doAbortOutstandingRequestAction(*itr);
pieceStorage->cancelPiece(*itr);
}
pieces.clear();
}
BtMessages DefaultBtRequestFactory::createRequestMessages(int max) {
BtMessages requests;
for(Pieces::iterator itr = pieces.begin();
itr != pieces.end() && requests.size() < (size_t)max; itr++) {
PieceHandle& piece = *itr;
int blockIndex;
while(requests.size() < (size_t)max &&
(blockIndex = piece->getMissingUnusedBlockIndex()) != -1) {
requests.push_back(BT_MESSAGE_FACTORY(btContext, peer)->
createRequestMessage(piece, blockIndex));
}
}
return requests;
}
BtMessages DefaultBtRequestFactory::createRequestMessagesOnEndGame(int max) {
BtMessages requests;
for(Pieces::iterator itr = pieces.begin();
itr != pieces.end() && requests.size() < (size_t)max; itr++) {
PieceHandle& piece = *itr;
BlockIndexes missingBlockIndexes = piece->getAllMissingBlockIndexes();
random_shuffle(missingBlockIndexes.begin(), missingBlockIndexes.end());
for(BlockIndexes::const_iterator bitr = missingBlockIndexes.begin();
bitr != missingBlockIndexes.end() && requests.size() < (size_t)max;
bitr++) {
int blockIndex = *bitr;
if(!dispatcher->isOutstandingRequest(piece->getIndex(),
blockIndex)) {
requests.push_back(BT_MESSAGE_FACTORY(btContext, peer)->
createRequestMessage(piece, blockIndex));
}
}
}
return requests;
}

View File

@ -0,0 +1,125 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_DEFAULT_BT_REQUEST_FACTORY_H_
#define _D_DEFAULT_BT_REQUEST_FACTORY_H_
#include "BtRequestFactory.h"
#include "BtContext.h"
#include "PieceStorage.h"
#include "Piece.h"
#include "Peer.h"
#include "BtMessageDispatcher.h"
#include "BtRegistry.h"
#include "LogFactory.h"
class DefaultBtRequestFactory : public BtRequestFactory {
private:
int cuid;
BtContextHandle btContext;
PieceStorageHandle pieceStorage;
PeerHandle peer;
BtMessageDispatcherHandle dispatcher;
Pieces pieces;
public:
DefaultBtRequestFactory():
cuid(0),
btContext(0),
pieceStorage(0),
peer(0),
dispatcher(0)
{
LogFactory::getInstance()->debug("DefaultBtRequestFactory::instantiated");
}
virtual ~DefaultBtRequestFactory()
{
LogFactory::getInstance()->debug("DefaultBtRequestFactory::deleted");
}
virtual void addTargetPiece(const PieceHandle& piece) {
pieces.push_back(piece);
}
virtual void removeTargetPiece(const PieceHandle& piece);
virtual void removeAllTargetPiece();
virtual int countTargetPiece() {
return pieces.size();
}
virtual void removeCompletedPiece();
virtual BtMessages createRequestMessages(int max);
virtual BtMessages createRequestMessagesOnEndGame(int max);
Pieces& getTargetPieces() {
return pieces;
}
void setCuid(int32_t cuid) {
this->cuid = cuid;
}
int32_t getCuid() const {
return cuid;
}
void setBtContext(const BtContextHandle& btContext) {
this->btContext = btContext;
this->pieceStorage = PIECE_STORAGE(btContext);
}
BtContextHandle getBtContext() const {
return btContext;
}
PeerHandle getPeer() const {
return peer;
}
void setPeer(const PeerHandle& peer) {
this->peer = peer;
}
void setBtMessageDispatcher(const BtMessageDispatcherHandle& dispatcher) {
this->dispatcher = dispatcher;
}
};
typedef SharedHandle<DefaultBtRequestFactory> DefaultBtRequestFactoryHandle;
#endif // _D_DEFAULT_BT_REQUEST_FACTORY_H_

View File

@ -36,14 +36,11 @@
#include "LogFactory.h"
#include "BtRegistry.h"
extern PeerHandle nullPeer;
DefaultPeerStorage::DefaultPeerStorage(BtContextHandle btContext,
const Option* option):
btContext(btContext),
option(option),
maxPeerListSize(MAX_PEER_LIST_SIZE),
peerEntryIdCounter(0),
btRuntime(BT_RUNTIME(btContext)),
removedPeerSessionDownloadLength(0),
removedPeerSessionUploadLength(0)
@ -59,8 +56,6 @@ bool DefaultPeerStorage::addPeer(const PeerHandle& peer) {
if(peers.size() >= (size_t)maxPeerListSize) {
deleteUnusedPeer(peers.size()-maxPeerListSize+1);
}
++peerEntryIdCounter;
peer->entryId = peerEntryIdCounter;
peers.push_back(peer);
return true;
} else {
@ -100,7 +95,7 @@ PeerHandle DefaultPeerStorage::getUnusedPeer() {
Peers::const_iterator itr = find_if(peers.begin(), peers.end(),
FindFinePeer());
if(itr == peers.end()) {
return nullPeer;
return 0;
} else {
return *itr;
}
@ -123,7 +118,7 @@ PeerHandle DefaultPeerStorage::getPeer(const string& ipaddr,
Peers::const_iterator itr = find_if(peers.begin(), peers.end(),
FindPeer(ipaddr, port));
if(itr == peers.end()) {
return nullPeer;
return 0;
} else {
return *itr;
}
@ -134,7 +129,7 @@ int DefaultPeerStorage::countPeer() const {
}
bool DefaultPeerStorage::isPeerAvailable() {
return getUnusedPeer() != nullPeer;
return !getUnusedPeer().isNull();
}
Peers DefaultPeerStorage::getActivePeers() {

View File

@ -50,7 +50,6 @@ private:
const Option* option;
Peers peers;
int maxPeerListSize;
int peerEntryIdCounter;
Logger* logger;
BtRuntimeHandle btRuntime;
long long int removedPeerSessionDownloadLength;

View File

@ -42,6 +42,7 @@
#include "MultiDiskWriter.h"
#include "PreAllocationDiskWriter.h"
#include "DlAbortEx.h"
#include "BitfieldManFactory.h"
DefaultPieceStorage::DefaultPieceStorage(BtContextHandle btContext, const Option* option):
btContext(btContext),
@ -49,13 +50,16 @@ DefaultPieceStorage::DefaultPieceStorage(BtContextHandle btContext, const Option
endGamePieceNum(END_GAME_PIECE_NUM),
option(option)
{
bitfieldMan = new BitfieldMan(btContext->getPieceLength(),
btContext->getTotalLength());
bitfieldMan =
BitfieldManFactory::getNewFactory()->
createBitfieldMan(btContext->getPieceLength(),
btContext->getTotalLength());
logger = LogFactory::getInstance();
}
DefaultPieceStorage::~DefaultPieceStorage() {
delete bitfieldMan;
delete diskAdaptor;
}
bool DefaultPieceStorage::hasMissingPiece(const PeerHandle& peer) {
@ -79,15 +83,15 @@ int DefaultPieceStorage::getMissingPieceIndex(const PeerHandle& peer) {
return index;
}
Piece DefaultPieceStorage::checkOutPiece(int index) {
PieceHandle DefaultPieceStorage::checkOutPiece(int index) {
if(index == -1) {
return Piece::nullPiece;
return 0;
}
bitfieldMan->setUseBit(index);
Piece piece = findUsedPiece(index);
if(Piece::isNull(piece)) {
Piece piece(index, bitfieldMan->getBlockLength(index));
PieceHandle piece = findUsedPiece(index);
if(piece.isNull()) {
piece = new Piece(index, bitfieldMan->getBlockLength(index));
addUsedPiece(piece);
return piece;
} else {
@ -95,8 +99,26 @@ Piece DefaultPieceStorage::checkOutPiece(int index) {
}
}
void DefaultPieceStorage::addUsedPiece(const Piece& piece) {
// TODO ? if nullPiece
/**
* Newly instantiated piece is not added to usedPieces.
* Because it is waste of memory and there is no chance to use them later.
*/
PieceHandle DefaultPieceStorage::getPiece(int index) {
if(0 <= index && index <= bitfieldMan->getMaxIndex()) {
PieceHandle piece = findUsedPiece(index);
if(piece.isNull()) {
piece = new Piece(index, bitfieldMan->getBlockLength(index));
if(hasPiece(index)) {
piece->setAllBlock();
}
}
return piece;
} else {
return 0;
}
}
void DefaultPieceStorage::addUsedPiece(const PieceHandle& piece) {
usedPieces.push_back(piece);
}
@ -106,23 +128,23 @@ private:
public:
FindPiece(int index):index(index) {}
bool operator()(const Piece& piece) {
return piece.getIndex() == index;
bool operator()(const PieceHandle& piece) {
return piece->getIndex() == index;
}
};
Piece DefaultPieceStorage::findUsedPiece(int index) const {
PieceHandle DefaultPieceStorage::findUsedPiece(int index) const {
Pieces::const_iterator itr = find_if(usedPieces.begin(),
usedPieces.end(),
FindPiece(index));
if(itr == usedPieces.end()) {
return Piece::nullPiece;
return 0;
} else {
return *itr;
}
}
Piece DefaultPieceStorage::getMissingPiece(const PeerHandle& peer) {
PieceHandle DefaultPieceStorage::getMissingPiece(const PeerHandle& peer) {
int index = getMissingPieceIndex(peer);
return checkOutPiece(index);
}
@ -149,13 +171,13 @@ int DefaultPieceStorage::getMissingFastPieceIndex(const PeerHandle& peer) {
return index;
}
Piece DefaultPieceStorage::getMissingFastPiece(const PeerHandle& peer) {
PieceHandle DefaultPieceStorage::getMissingFastPiece(const PeerHandle& peer) {
int index = getMissingFastPieceIndex(peer);
return checkOutPiece(index);
}
void DefaultPieceStorage::deleteUsedPiece(const Piece& piece) {
if(Piece::isNull(piece)) {
void DefaultPieceStorage::deleteUsedPiece(const PieceHandle& piece) {
if(piece.isNull()) {
return;
}
Pieces::iterator itr = find(usedPieces.begin(), usedPieces.end(), piece);
@ -185,12 +207,12 @@ int DefaultPieceStorage::deleteUsedPiecesByFillRate(int fillRate,
int deleted = 0;
for(Pieces::iterator itr = usedPieces.begin();
itr != usedPieces.end() && deleted < toDelete;) {
Piece& piece = *itr;
if(!bitfieldMan->isUseBitSet(piece.getIndex()) &&
piece.countCompleteBlock() <= piece.countBlock()*(fillRate/100.0)) {
PieceHandle& piece = *itr;
if(!bitfieldMan->isUseBitSet(piece->getIndex()) &&
piece->countCompleteBlock() <= piece->countBlock()*(fillRate/100.0)) {
logger->debug("Deleting used piece index=%d, fillRate(%%)=%d<=%d",
piece.getIndex(),
(piece.countCompleteBlock()*100)/piece.countBlock(),
piece->getIndex(),
(piece->countCompleteBlock()*100)/piece->countBlock(),
fillRate);
itr = usedPieces.erase(itr);
deleted++;
@ -201,8 +223,8 @@ int DefaultPieceStorage::deleteUsedPiecesByFillRate(int fillRate,
return deleted;
}
void DefaultPieceStorage::completePiece(const Piece& piece) {
if(Piece::isNull(piece)) {
void DefaultPieceStorage::completePiece(const PieceHandle& piece) {
if(piece.isNull()) {
return;
}
deleteUsedPiece(piece);
@ -212,8 +234,8 @@ void DefaultPieceStorage::completePiece(const Piece& piece) {
if(downloadFinished()) {
return;
}
bitfieldMan->setBit(piece.getIndex());
bitfieldMan->unsetUseBit(piece.getIndex());
bitfieldMan->setBit(piece->getIndex());
bitfieldMan->unsetUseBit(piece->getIndex());
if(downloadFinished()) {
diskAdaptor->onDownloadComplete();
if(isSelectiveDownloadingMode()) {
@ -235,50 +257,18 @@ void DefaultPieceStorage::finishSelectiveDownloadingMode() {
}
// not unittested
void DefaultPieceStorage::cancelPiece(const Piece& piece) {
if(Piece::isNull(piece)) {
void DefaultPieceStorage::cancelPiece(const PieceHandle& piece) {
if(piece.isNull()) {
return;
}
updatePiece(piece);
bitfieldMan->unsetUseBit(piece.getIndex());
bitfieldMan->unsetUseBit(piece->getIndex());
if(!isEndGame()) {
if(piece.countCompleteBlock() == 0) {
if(piece->countCompleteBlock() == 0) {
deleteUsedPiece(piece);
}
}
}
// not unittested
void DefaultPieceStorage::updatePiece(const Piece& piece) {
if(Piece::isNull(piece)) {
return;
}
Pieces::iterator itr = find(usedPieces.begin(), usedPieces.end(),
piece);
if(itr != usedPieces.end()) {
*itr = piece;
}
}
// not unittested
void DefaultPieceStorage::syncPiece(Piece& piece) {
if(Piece::isNull(piece)) {
return;
}
Pieces::iterator itr = find(usedPieces.begin(), usedPieces.end(),
piece);
if(itr != usedPieces.end()) {
piece = *itr;
return;
} else {
// hasPiece(piece.getIndex()) is true, then set all bit of
// piece.bitfield to 1
if(hasPiece(piece.getIndex())) {
piece.setAllBlock();
}
}
}
bool DefaultPieceStorage::hasPiece(int index) {
return bitfieldMan->isBitSet(index);
}

View File

@ -77,29 +77,26 @@ private:
int getMissingPieceIndex(const PeerHandle& peer);
int getMissingFastPieceIndex(const PeerHandle& peer);
Piece checkOutPiece(int index);
void addUsedPiece(const Piece& piece);
Piece findUsedPiece(int index) const;
PieceHandle checkOutPiece(int index);
int deleteUsedPiecesByFillRate(int fillRate, int toDelete);
void reduceUsedPieces(int delMax);
void deleteUsedPiece(const Piece& piece);
void deleteUsedPiece(const PieceHandle& piece);
PieceHandle findUsedPiece(int index) const;
public:
DefaultPieceStorage(BtContextHandle btContext, const Option* option);
virtual ~DefaultPieceStorage();
virtual bool hasMissingPiece(const PeerHandle& peer);
virtual Piece getMissingPiece(const PeerHandle& peer);
virtual PieceHandle getMissingPiece(const PeerHandle& peer);
virtual Piece getMissingFastPiece(const PeerHandle& peer);
virtual PieceHandle getMissingFastPiece(const PeerHandle& peer);
virtual void completePiece(const Piece& piece);
virtual PieceHandle getPiece(int index);
virtual void cancelPiece(const Piece& piece);
virtual void completePiece(const PieceHandle& piece);
virtual void updatePiece(const Piece& piece);
virtual void syncPiece(Piece& piece);
virtual void cancelPiece(const PieceHandle& piece);
virtual bool hasPiece(int index);
@ -153,6 +150,10 @@ public:
virtual void removeAdvertisedPiece(int elapsed);
/**
* This method is made private for test purpose only.
*/
void addUsedPiece(const PieceHandle& piece);
};
#endif // _D_DEFAULT_PIECE_STORAGE_H_

View File

@ -107,6 +107,24 @@ DownloadEngineFactory::newTorrentConsoleEngine(const BtContextHandle& btContext,
BtRegistry::registerBtProgressInfoFile(btContext->getInfoHashAsString(),
btProgressInfoFile);
BtRegistry::registerPeerObjectCluster(btContext->getInfoHashAsString(),
new PeerObjectCluster());
/*
DefaultBtMessageFactoryAdaptorHandle factoryAdaptor =
new DefaultBtMessageFactoryAdaptor();
BtRegistry::registerBtMessageFactoryAdaptor(btContext->getInfoHashAsString(),
factoryAdaptor);
BtMessageFactoryClusterHandle factoryCluster = new BtMessageFactoryCluster();
BtRegistry::registerBtMessageFactoryCluster(btContext->getInfoHashAsString(),
factoryCluster);
BtMessageDispatcherClusterHandle dispatcherCluster =
new BtMessageDispatcherCluster();
BtRegistry::registerBtMessageDispatcherCluster(btContext->getInfoHashAsString(),
dispatcherCluster);
*/
te->setBtContext(btContext);
// initialize file storage
pieceStorage->initStorage();

73
src/HandleRegistry.h Normal file
View File

@ -0,0 +1,73 @@
/* <!-- copyright */
/*
* aria2 - The high speed download utility
*
* Copyright (C) 2006 Tatsuhiro Tsujikawa
*
* 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* In addition, as a special exception, the copyright holders give
* permission to link the code of portions of this program with the
* OpenSSL library under certain conditions as described in each
* individual source file, and distribute linked combinations
* including the two.
* You must obey the GNU General Public License in all respects
* for all of the code used other than OpenSSL. If you modify
* file(s) with this exception, you may extend this exception to your
* version of the file(s), but you are not obligated to do so. If you
* do not wish to do so, delete this exception statement from your
* version. If you delete this exception statement from all source
* files in the program, then also delete it here.
*/
/* copyright --> */
#ifndef _D_HANDLE_REGISTRY_H_
#define _D_HANDLE_REGISTRY_H_
#include "SharedHandle.h"
#include <map>
using namespace std;
template<typename K, typename T>
class HandleRegistry {
typedef map<K, SharedHandle<T> > HandleMap;
private:
HandleMap handleMap;
public:
void registerHandle(const K& key, const SharedHandle<T>& obj) {
unregisterHandle(key);
typename HandleMap::value_type p(key, obj);
handleMap.insert(p);
}
void unregisterHandle(const K& key) {
handleMap.erase(key);
}
SharedHandle<T> getHandle(const K& key) {
typename HandleMap::const_iterator itr = handleMap.find(key);
if(itr == handleMap.end()) {
return 0;
} else {
return itr->second;
}
}
void clear() {
handleMap.clear();
}
};
#endif // _D_HANDLE_REGISTRY_H_

View File

@ -49,13 +49,18 @@ SRCS = Socket.h\
NullLogger.h\
TimeA2.cc TimeA2.h\
SharedHandle.h\
HandleRegistry.h\
FeatureConfig.cc FeatureConfig.h\
DownloadEngineFactory.cc DownloadEngineFactory.h\
RequestInfo.h\
UrlRequestInfo.cc UrlRequestInfo.h\
SpeedCalc.cc SpeedCalc.h\
PeerStat.h\
BitfieldMan.cc BitfieldMan.h
BitfieldMan.cc BitfieldMan.h\
BitfieldManFactory.cc BitfieldManFactory.h\
Randomizer.h\
SimpleRandomizer.cc SimpleRandomizer.h
# debug_new.cpp
if ENABLE_ASYNC_DNS
SRCS += NameResolver.cc NameResolver.h
@ -138,7 +143,54 @@ SRCS += MetaEntry.h\
BtRuntime.h\
BtProgressInfoFile.h\
DefaultBtProgressInfoFile.cc DefaultBtProgressInfoFile.h\
BtContextAwareCommand.cc BtContextAwareCommand.h
BtContextAwareCommand.cc BtContextAwareCommand.h\
BtMessage.h\
AbstractBtMessage.h\
SimpleBtMessage.cc SimpleBtMessage.h\
BtAllowedFastMessage.cc BtAllowedFastMessage.h\
BtBitfieldMessage.cc BtBitfieldMessage.h\
BtCancelMessage.cc BtCancelMessage.h\
BtChokeMessage.cc BtChokeMessage.h\
BtHaveAllMessage.cc BtHaveAllMessage.h\
BtHaveMessage.cc BtHaveMessage.h\
BtHaveNoneMessage.cc BtHaveNoneMessage.h\
BtInterestedMessage.cc BtInterestedMessage.h\
BtKeepAliveMessage.cc BtKeepAliveMessage.h\
BtNotInterestedMessage.cc BtNotInterestedMessage.h\
BtPieceMessage.cc BtPieceMessage.h\
BtPortMessage.cc BtPortMessage.h\
BtRejectMessage.cc BtRejectMessage.h\
BtRequestMessage.cc BtRequestMessage.h\
BtSuggestPieceMessage.cc BtSuggestPieceMessage.h\
BtUnchokeMessage.cc BtUnchokeMessage.h\
BtHandshakeMessage.cc BtHandshakeMessage.h\
BtMessageValidator.h\
BtAllowedFastMessageValidator.h\
BtBitfieldMessageValidator.h\
BtCancelMessageValidator.h\
BtHaveMessageValidator.h\
BtPieceMessageValidator.h\
BtRejectMessageValidator.h\
BtRequestMessageValidator.h\
BtSuggestPieceMessageValidator.h\
BtHandshakeMessageValidator.h\
BtMessageFactory.h\
DefaultBtMessageFactory.cc DefaultBtMessageFactory.h\
BtMessageDispatcher.h\
DefaultBtMessageDispatcher.cc DefaultBtMessageDispatcher.h\
BtMessageReceiver.h\
DefaultBtMessageReceiver.cc DefaultBtMessageReceiver.h\
BtRequestFactory.h\
DefaultBtRequestFactory.cc DefaultBtRequestFactory.h\
BtEvent.h\
BtEventListener.h\
BtCancelSendingPieceEvent.h\
BtAbortOutstandingRequestEvent.h\
BtChokedEvent.h\
BtChokingEvent.h\
BtInteractive.h\
DefaultBtInteractive.cc DefaultBtInteractive.h\
PeerObject.h
endif # ENABLE_BITTORRENT
if ENABLE_METALINK

View File

@ -115,7 +115,54 @@ bin_PROGRAMS = aria2c$(EXEEXT)
@ENABLE_BITTORRENT_TRUE@ BtRuntime.h\
@ENABLE_BITTORRENT_TRUE@ BtProgressInfoFile.h\
@ENABLE_BITTORRENT_TRUE@ DefaultBtProgressInfoFile.cc DefaultBtProgressInfoFile.h\
@ENABLE_BITTORRENT_TRUE@ BtContextAwareCommand.cc BtContextAwareCommand.h
@ENABLE_BITTORRENT_TRUE@ BtContextAwareCommand.cc BtContextAwareCommand.h\
@ENABLE_BITTORRENT_TRUE@ BtMessage.h\
@ENABLE_BITTORRENT_TRUE@ AbstractBtMessage.h\
@ENABLE_BITTORRENT_TRUE@ SimpleBtMessage.cc SimpleBtMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtAllowedFastMessage.cc BtAllowedFastMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtBitfieldMessage.cc BtBitfieldMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtCancelMessage.cc BtCancelMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtChokeMessage.cc BtChokeMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtHaveAllMessage.cc BtHaveAllMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtHaveMessage.cc BtHaveMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtHaveNoneMessage.cc BtHaveNoneMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtInterestedMessage.cc BtInterestedMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtKeepAliveMessage.cc BtKeepAliveMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtNotInterestedMessage.cc BtNotInterestedMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtPieceMessage.cc BtPieceMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtPortMessage.cc BtPortMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtRejectMessage.cc BtRejectMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtRequestMessage.cc BtRequestMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtSuggestPieceMessage.cc BtSuggestPieceMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtUnchokeMessage.cc BtUnchokeMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtHandshakeMessage.cc BtHandshakeMessage.h\
@ENABLE_BITTORRENT_TRUE@ BtMessageValidator.h\
@ENABLE_BITTORRENT_TRUE@ BtAllowedFastMessageValidator.h\
@ENABLE_BITTORRENT_TRUE@ BtBitfieldMessageValidator.h\
@ENABLE_BITTORRENT_TRUE@ BtCancelMessageValidator.h\
@ENABLE_BITTORRENT_TRUE@ BtHaveMessageValidator.h\
@ENABLE_BITTORRENT_TRUE@ BtPieceMessageValidator.h\
@ENABLE_BITTORRENT_TRUE@ BtRejectMessageValidator.h\
@ENABLE_BITTORRENT_TRUE@ BtRequestMessageValidator.h\
@ENABLE_BITTORRENT_TRUE@ BtSuggestPieceMessageValidator.h\
@ENABLE_BITTORRENT_TRUE@ BtHandshakeMessageValidator.h\
@ENABLE_BITTORRENT_TRUE@ BtMessageFactory.h\
@ENABLE_BITTORRENT_TRUE@ DefaultBtMessageFactory.cc DefaultBtMessageFactory.h\
@ENABLE_BITTORRENT_TRUE@ BtMessageDispatcher.h\
@ENABLE_BITTORRENT_TRUE@ DefaultBtMessageDispatcher.cc DefaultBtMessageDispatcher.h\
@ENABLE_BITTORRENT_TRUE@ BtMessageReceiver.h\
@ENABLE_BITTORRENT_TRUE@ DefaultBtMessageReceiver.cc DefaultBtMessageReceiver.h\
@ENABLE_BITTORRENT_TRUE@ BtRequestFactory.h\
@ENABLE_BITTORRENT_TRUE@ DefaultBtRequestFactory.cc DefaultBtRequestFactory.h\
@ENABLE_BITTORRENT_TRUE@ BtEvent.h\
@ENABLE_BITTORRENT_TRUE@ BtEventListener.h\
@ENABLE_BITTORRENT_TRUE@ BtCancelSendingPieceEvent.h\
@ENABLE_BITTORRENT_TRUE@ BtAbortOutstandingRequestEvent.h\
@ENABLE_BITTORRENT_TRUE@ BtChokedEvent.h\
@ENABLE_BITTORRENT_TRUE@ BtChokingEvent.h\
@ENABLE_BITTORRENT_TRUE@ BtInteractive.h\
@ENABLE_BITTORRENT_TRUE@ DefaultBtInteractive.cc DefaultBtInteractive.h\
@ENABLE_BITTORRENT_TRUE@ PeerObject.h
@ENABLE_METALINK_TRUE@am__append_3 = Metalinker.cc Metalinker.h\
@ENABLE_METALINK_TRUE@ MetalinkEntry.cc MetalinkEntry.h\
@ -178,16 +225,19 @@ am__libaria2c_a_SOURCES_DIST = Socket.h SocketCore.cc SocketCore.h \
AbstractDiskWriter.cc AbstractDiskWriter.h File.cc File.h \
Option.cc Option.h Base64.cc Base64.h CookieBox.cc CookieBox.h \
messageDigest.h LogFactory.cc LogFactory.h NullLogger.h \
TimeA2.cc TimeA2.h SharedHandle.h FeatureConfig.cc \
FeatureConfig.h DownloadEngineFactory.cc \
TimeA2.cc TimeA2.h SharedHandle.h HandleRegistry.h \
FeatureConfig.cc FeatureConfig.h DownloadEngineFactory.cc \
DownloadEngineFactory.h RequestInfo.h UrlRequestInfo.cc \
UrlRequestInfo.h SpeedCalc.cc SpeedCalc.h PeerStat.h \
BitfieldMan.cc BitfieldMan.h NameResolver.cc NameResolver.h \
MetaEntry.h Data.cc Data.h Dictionary.cc Dictionary.h List.cc \
List.h MetaFileUtil.cc MetaFileUtil.h MetaEntryVisitor.h \
ShaVisitor.cc ShaVisitor.h PeerConnection.cc PeerConnection.h \
PeerMessageUtil.cc PeerMessageUtil.h PeerAbstractCommand.cc \
PeerAbstractCommand.h PeerInitiateConnectionCommand.cc \
BitfieldMan.cc BitfieldMan.h BitfieldManFactory.cc \
BitfieldManFactory.h Randomizer.h SimpleRandomizer.cc \
SimpleRandomizer.h debug_new.cpp NameResolver.cc \
NameResolver.h MetaEntry.h Data.cc Data.h Dictionary.cc \
Dictionary.h List.cc List.h MetaFileUtil.cc MetaFileUtil.h \
MetaEntryVisitor.h ShaVisitor.cc ShaVisitor.h \
PeerConnection.cc PeerConnection.h PeerMessageUtil.cc \
PeerMessageUtil.h PeerAbstractCommand.cc PeerAbstractCommand.h \
PeerInitiateConnectionCommand.cc \
PeerInitiateConnectionCommand.h PeerInteractionCommand.cc \
PeerInteractionCommand.h Peer.cc Peer.h \
TorrentDownloadEngine.cc TorrentDownloadEngine.h \
@ -231,9 +281,38 @@ am__libaria2c_a_SOURCES_DIST = Socket.h SocketCore.cc SocketCore.h \
DefaultBtAnnounce.h BtRegistry.cc BtRegistry.h BtRuntime.h \
BtProgressInfoFile.h DefaultBtProgressInfoFile.cc \
DefaultBtProgressInfoFile.h BtContextAwareCommand.cc \
BtContextAwareCommand.h Metalinker.cc Metalinker.h \
MetalinkEntry.cc MetalinkEntry.h MetalinkResource.cc \
MetalinkResource.h MetalinkProcessor.h \
BtContextAwareCommand.h BtMessage.h AbstractBtMessage.h \
SimpleBtMessage.cc SimpleBtMessage.h BtAllowedFastMessage.cc \
BtAllowedFastMessage.h BtBitfieldMessage.cc \
BtBitfieldMessage.h BtCancelMessage.cc BtCancelMessage.h \
BtChokeMessage.cc BtChokeMessage.h BtHaveAllMessage.cc \
BtHaveAllMessage.h BtHaveMessage.cc BtHaveMessage.h \
BtHaveNoneMessage.cc BtHaveNoneMessage.h \
BtInterestedMessage.cc BtInterestedMessage.h \
BtKeepAliveMessage.cc BtKeepAliveMessage.h \
BtNotInterestedMessage.cc BtNotInterestedMessage.h \
BtPieceMessage.cc BtPieceMessage.h BtPortMessage.cc \
BtPortMessage.h BtRejectMessage.cc BtRejectMessage.h \
BtRequestMessage.cc BtRequestMessage.h \
BtSuggestPieceMessage.cc BtSuggestPieceMessage.h \
BtUnchokeMessage.cc BtUnchokeMessage.h BtHandshakeMessage.cc \
BtHandshakeMessage.h BtMessageValidator.h \
BtAllowedFastMessageValidator.h BtBitfieldMessageValidator.h \
BtCancelMessageValidator.h BtHaveMessageValidator.h \
BtPieceMessageValidator.h BtRejectMessageValidator.h \
BtRequestMessageValidator.h BtSuggestPieceMessageValidator.h \
BtHandshakeMessageValidator.h BtMessageFactory.h \
DefaultBtMessageFactory.cc DefaultBtMessageFactory.h \
BtMessageDispatcher.h DefaultBtMessageDispatcher.cc \
DefaultBtMessageDispatcher.h BtMessageReceiver.h \
DefaultBtMessageReceiver.cc DefaultBtMessageReceiver.h \
BtRequestFactory.h DefaultBtRequestFactory.cc \
DefaultBtRequestFactory.h BtEvent.h BtEventListener.h \
BtCancelSendingPieceEvent.h BtAbortOutstandingRequestEvent.h \
BtChokedEvent.h BtChokingEvent.h BtInteractive.h \
DefaultBtInteractive.cc DefaultBtInteractive.h PeerObject.h \
Metalinker.cc Metalinker.h MetalinkEntry.cc MetalinkEntry.h \
MetalinkResource.cc MetalinkResource.h MetalinkProcessor.h \
Xml2MetalinkProcessor.cc Xml2MetalinkProcessor.h \
MetalinkRequestInfo.cc MetalinkRequestInfo.h
@ENABLE_ASYNC_DNS_TRUE@am__objects_1 = NameResolver.$(OBJEXT)
@ -297,7 +376,30 @@ am__libaria2c_a_SOURCES_DIST = Socket.h SocketCore.cc SocketCore.h \
@ENABLE_BITTORRENT_TRUE@ DefaultBtAnnounce.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtRegistry.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ DefaultBtProgressInfoFile.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtContextAwareCommand.$(OBJEXT)
@ENABLE_BITTORRENT_TRUE@ BtContextAwareCommand.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ SimpleBtMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtAllowedFastMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtBitfieldMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtCancelMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtChokeMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtHaveAllMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtHaveMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtHaveNoneMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtInterestedMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtKeepAliveMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtNotInterestedMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtPieceMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtPortMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtRejectMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtRequestMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtSuggestPieceMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtUnchokeMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ BtHandshakeMessage.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ DefaultBtMessageFactory.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ DefaultBtMessageDispatcher.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ DefaultBtMessageReceiver.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ DefaultBtRequestFactory.$(OBJEXT) \
@ENABLE_BITTORRENT_TRUE@ DefaultBtInteractive.$(OBJEXT)
@ENABLE_METALINK_TRUE@am__objects_3 = Metalinker.$(OBJEXT) \
@ENABLE_METALINK_TRUE@ MetalinkEntry.$(OBJEXT) \
@ENABLE_METALINK_TRUE@ MetalinkResource.$(OBJEXT) \
@ -326,8 +428,9 @@ am__objects_4 = SocketCore.$(OBJEXT) Command.$(OBJEXT) \
CookieBox.$(OBJEXT) LogFactory.$(OBJEXT) TimeA2.$(OBJEXT) \
FeatureConfig.$(OBJEXT) DownloadEngineFactory.$(OBJEXT) \
UrlRequestInfo.$(OBJEXT) SpeedCalc.$(OBJEXT) \
BitfieldMan.$(OBJEXT) $(am__objects_1) $(am__objects_2) \
$(am__objects_3)
BitfieldMan.$(OBJEXT) BitfieldManFactory.$(OBJEXT) \
SimpleRandomizer.$(OBJEXT) debug_new.$(OBJEXT) \
$(am__objects_1) $(am__objects_2) $(am__objects_3)
am_libaria2c_a_OBJECTS = $(am__objects_4)
libaria2c_a_OBJECTS = $(am_libaria2c_a_OBJECTS)
am__installdirs = "$(DESTDIR)$(bindir)"
@ -525,12 +628,14 @@ SRCS = Socket.h SocketCore.cc SocketCore.h Command.cc Command.h \
AbstractDiskWriter.cc AbstractDiskWriter.h File.cc File.h \
Option.cc Option.h Base64.cc Base64.h CookieBox.cc CookieBox.h \
messageDigest.h LogFactory.cc LogFactory.h NullLogger.h \
TimeA2.cc TimeA2.h SharedHandle.h FeatureConfig.cc \
FeatureConfig.h DownloadEngineFactory.cc \
TimeA2.cc TimeA2.h SharedHandle.h HandleRegistry.h \
FeatureConfig.cc FeatureConfig.h DownloadEngineFactory.cc \
DownloadEngineFactory.h RequestInfo.h UrlRequestInfo.cc \
UrlRequestInfo.h SpeedCalc.cc SpeedCalc.h PeerStat.h \
BitfieldMan.cc BitfieldMan.h $(am__append_1) $(am__append_2) \
$(am__append_3)
BitfieldMan.cc BitfieldMan.h BitfieldManFactory.cc \
BitfieldManFactory.h Randomizer.h SimpleRandomizer.cc \
SimpleRandomizer.h debug_new.cpp $(am__append_1) \
$(am__append_2) $(am__append_3)
noinst_LIBRARIES = libaria2c.a
libaria2c_a_SOURCES = $(SRCS)
aria2c_LDADD = libaria2c.a @LIBINTL@ @ALLOCA@ @LIBGNUTLS_LIBS@\
@ -547,7 +652,7 @@ AM_CPPFLAGS = -Wall\
all: all-am
.SUFFIXES:
.SUFFIXES: .cc .o .obj
.SUFFIXES: .cc .cpp .o .obj
$(srcdir)/Makefile.in: $(srcdir)/Makefile.am $(am__configure_deps)
@for dep in $?; do \
case '$(am__configure_deps)' in \
@ -624,9 +729,27 @@ distclean-compile:
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/AnnounceList.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/Base64.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BitfieldMan.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BitfieldManFactory.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BitfieldMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtAllowedFastMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtBitfieldMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtCancelMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtChokeMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtContextAwareCommand.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtHandshakeMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtHaveAllMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtHaveMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtHaveNoneMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtInterestedMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtKeepAliveMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtNotInterestedMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtPieceMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtPortMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtRegistry.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtRejectMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtRequestMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtSuggestPieceMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/BtUnchokeMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/ByteArrayDiskWriter.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/CancelMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/ChokeMessage.Po@am__quote@
@ -639,7 +762,12 @@ distclean-compile:
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/Data.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/DefaultBtAnnounce.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/DefaultBtContext.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/DefaultBtInteractive.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/DefaultBtMessageDispatcher.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/DefaultBtMessageFactory.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/DefaultBtMessageReceiver.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/DefaultBtProgressInfoFile.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/DefaultBtRequestFactory.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/DefaultDiskWriter.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/DefaultPeerListProcessor.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/DefaultPeerStorage.Po@am__quote@
@ -712,8 +840,10 @@ distclean-compile:
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/Segment.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/SegmentMan.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/ShaVisitor.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/SimpleBtMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/SimpleLogger.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/SimplePeerMessage.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/SimpleRandomizer.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/SleepCommand.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/SocketCore.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/SpeedCalc.Po@am__quote@
@ -729,6 +859,7 @@ distclean-compile:
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/UrlRequestInfo.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/Util.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/Xml2MetalinkProcessor.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/debug_new.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/main.Po@am__quote@
.cc.o:
@ -744,6 +875,20 @@ distclean-compile:
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
@am__fastdepCXX_FALSE@ $(CXXCOMPILE) -c -o $@ `$(CYGPATH_W) '$<'`
.cpp.o:
@am__fastdepCXX_TRUE@ if $(CXXCOMPILE) -MT $@ -MD -MP -MF "$(DEPDIR)/$*.Tpo" -c -o $@ $<; \
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/$*.Tpo" "$(DEPDIR)/$*.Po"; else rm -f "$(DEPDIR)/$*.Tpo"; exit 1; fi
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
@am__fastdepCXX_FALSE@ $(CXXCOMPILE) -c -o $@ $<
.cpp.obj:
@am__fastdepCXX_TRUE@ if $(CXXCOMPILE) -MT $@ -MD -MP -MF "$(DEPDIR)/$*.Tpo" -c -o $@ `$(CYGPATH_W) '$<'`; \
@am__fastdepCXX_TRUE@ then mv -f "$(DEPDIR)/$*.Tpo" "$(DEPDIR)/$*.Po"; else rm -f "$(DEPDIR)/$*.Tpo"; exit 1; fi
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
@am__fastdepCXX_FALSE@ $(CXXCOMPILE) -c -o $@ `$(CYGPATH_W) '$<'`
uninstall-info-am:
ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES)

View File

@ -33,8 +33,33 @@
*/
/* copyright --> */
#include "Peer.h"
#include "BitfieldManFactory.h"
#include "Util.h"
PeerHandle nullPeer = PeerHandle(new Peer("", 0, 0, 0));
Peer::Peer(string ipaddr, int port, int pieceLength, long long int totalLength):
ipaddr(ipaddr),
port(port),
error(0),
sessionUploadLength(0),
sessionDownloadLength(0),
pieceLength(pieceLength),
active(false)
{
resetStatus();
this->bitfield = BitfieldManFactory::getNewFactory()->
createBitfieldMan(pieceLength, totalLength);
string idSeed = ipaddr+":"+Util::itos(port);
id = Util::simpleMessageDigest(idSeed);
}
/*
Peer::Peer():entryId(0), ipaddr(""), port(0), bitfield(0),
sessionUploadLength(0), sessionDownloadLength(0),
pieceLength(0)
{
resetStatus();
}
*/
void Peer::updateBitfield(int index, int operation) {
if(operation == 1) {
@ -74,6 +99,8 @@ void Peer::resetStatus() {
fastExtensionEnabled = false;
latency = DEFAULT_LATENCY;
fastSet.clear();
peerAllowedIndexSet.clear();
amAllowedIndexSet.clear();
peerStat.reset();
}
@ -87,6 +114,28 @@ void Peer::addFastSetIndex(int index) {
}
}
bool Peer::isInPeerAllowedIndexSet(int index) const {
return find(peerAllowedIndexSet.begin(), peerAllowedIndexSet.end(),
index) != peerAllowedIndexSet.end();
}
void Peer::addPeerAllowedIndex(int index) {
if(!isInPeerAllowedIndexSet(index)) {
peerAllowedIndexSet.push_back(index);
}
}
bool Peer::isInAmAllowedIndexSet(int index) const {
return find(amAllowedIndexSet.begin(), amAllowedIndexSet.end(),
index) != amAllowedIndexSet.end();
}
void Peer::addAmAllowedIndex(int index) {
if(!isInAmAllowedIndexSet(index)) {
amAllowedIndexSet.push_back(index);
}
}
void Peer::setAllBitfield() {
bitfield->setAllBit();
}

View File

@ -51,7 +51,6 @@ class Peer {
friend bool operator==(const Peer& p1, const Peer& p2);
friend bool operator!=(const Peer& p1, const Peer& p2);
public:
int entryId;
string ipaddr;
int port;
bool amChoking;
@ -65,42 +64,32 @@ public:
bool optUnchoking;
bool snubbing;
private:
char peerId[PEER_ID_LENGTH];
unsigned char peerId[PEER_ID_LENGTH];
BitfieldMan* bitfield;
bool fastExtensionEnabled;
// allowed fast indexes that peer has sent by Allowed Fast message
Integers fastSet;
// fast index set which a peer has sent to localhost.
Integers peerAllowedIndexSet;
// fast index set which localhost has sent to a peer.
Integers amAllowedIndexSet;
PeerStat peerStat;
long long int sessionUploadLength;
long long int sessionDownloadLength;
int pieceLength;
int latency;
bool active;
string id;
public:
Peer(string ipaddr, int port, int pieceLength, long long int totalLength):
entryId(0), ipaddr(ipaddr), port(port), error(0),
sessionUploadLength(0), sessionDownloadLength(0),
pieceLength(pieceLength), active(false)
{
resetStatus();
this->bitfield = new BitfieldMan(pieceLength, totalLength);
}
Peer():entryId(0), ipaddr(""), port(0), bitfield(0),
sessionUploadLength(0), sessionDownloadLength(0),
pieceLength(0)
{
resetStatus();
}
Peer(string ipaddr, int port, int pieceLength, long long int totalLength);
~Peer() {
if(bitfield != NULL) {
delete bitfield;
}
delete bitfield;
}
bool operator==(const Peer& p) {
return ipaddr == p.ipaddr && port == p.port;
//return ipaddr == p.ipaddr && port == p.port;
return id == p.id;
}
bool operator!=(const Peer& p) {
@ -161,10 +150,10 @@ public:
return active;
}
void setPeerId(const char* peerId) {
void setPeerId(const unsigned char* peerId) {
memcpy(this->peerId, peerId, PEER_ID_LENGTH);
}
const char* getPeerId() const { return this->peerId; }
const unsigned char* getPeerId() const { return this->peerId; }
void setBitfield(const unsigned char* bitfield, int bitfieldLength) {
this->bitfield->setBitfield(bitfield, bitfieldLength);
@ -189,6 +178,12 @@ public:
bool isInFastSet(int index) const;
int countFastSet() const { return fastSet.size(); }
void addPeerAllowedIndex(int index);
bool isInPeerAllowedIndexSet(int index) const;
void addAmAllowedIndex(int index);
bool isInAmAllowedIndexSet(int index) const;
bool shouldBeChoking() const;
bool hasPiece(int index) const;
@ -197,6 +192,10 @@ public:
void updateLatency(int latency);
int getLatency() const { return latency; }
const string& getId() const {
return id;
}
};
typedef SharedHandle<Peer> PeerHandle;

View File

@ -38,9 +38,10 @@
#include "PeerMessageUtil.h"
#include "Util.h"
#include "LogFactory.h"
#include "BtHandshakeMessage.h"
#include <netinet/in.h>
PeerConnection::PeerConnection(int cuid,
PeerConnection::PeerConnection(int32_t cuid,
const SocketHandle& socket,
const Option* op)
:cuid(cuid),
@ -55,24 +56,26 @@ PeerConnection::PeerConnection(int cuid,
PeerConnection::~PeerConnection() {}
int PeerConnection::sendMessage(const char* msg, int length) {
int writtenLength = 0;
uint32_t PeerConnection::sendMessage(const unsigned char* data, uint32_t dataLength) {
uint32_t writtenLength = 0;
if(socket->isWritable(0)) {
socket->writeData(msg, length);
writtenLength += length;
// TODO fix this
socket->writeData((const char*)data, dataLength);
writtenLength += dataLength;
}
return writtenLength;
}
bool PeerConnection::receiveMessage(char* msg, int& length) {
bool PeerConnection::receiveMessage(unsigned char* data, uint32_t& dataLength) {
if(!socket->isReadable(0)) {
return false;
}
if(resbufLength == 0 && lenbufLength != 4) {
// read payload size, 4-byte integer
int remain = 4-lenbufLength;
int temp = remain;
socket->readData(lenbuf+lenbufLength, temp);
uint32_t remain = 4-lenbufLength;
uint32_t temp = remain;
// TODO fix this
socket->readData((char*)lenbuf+lenbufLength, (int&)temp);
if(temp == 0) {
// we got EOF
throw new DlAbortEx(EX_EOF_FROM_PEER);
@ -83,7 +86,7 @@ bool PeerConnection::receiveMessage(char* msg, int& length) {
return false;
}
//payloadLen = ntohl(nPayloadLen);
int payloadLength = ntohl(*((int*)lenbuf));
uint32_t payloadLength = ntohl(*((uint32_t*)lenbuf));
if(payloadLength > MAX_PAYLOAD_LEN || payloadLength < 0) {
throw new DlAbortEx("max payload length exceeded or invalid. length = %d",
payloadLength);
@ -91,9 +94,9 @@ bool PeerConnection::receiveMessage(char* msg, int& length) {
currentPayloadLength = payloadLength;
}
// we have currentPayloadLen-resbufLen bytes to read
int remaining = currentPayloadLength-resbufLength;
uint32_t remaining = currentPayloadLength-resbufLength;
if(remaining > 0) {
socket->readData(resbuf+resbufLength, remaining);
socket->readData((char*)resbuf+resbufLength, (int&)remaining);
if(remaining == 0) {
// we got EOF
throw new DlAbortEx(EX_EOF_FROM_PEER);
@ -107,19 +110,19 @@ bool PeerConnection::receiveMessage(char* msg, int& length) {
resbufLength = 0;
lenbufLength = 0;
memcpy(msg, resbuf, currentPayloadLength);
length = currentPayloadLength;
memcpy(data, resbuf, currentPayloadLength);
dataLength = currentPayloadLength;
return true;
}
bool PeerConnection::receiveHandshake(char* msg, int& length) {
bool PeerConnection::receiveHandshake(unsigned char* data, uint32_t& dataLength) {
if(!socket->isReadable(0)) {
length = 0;
dataLength = 0;
return false;
}
int remain = HANDSHAKE_MESSAGE_LENGTH-resbufLength;
int temp = remain;
socket->readData(resbuf+resbufLength, temp);
uint32_t remain = BtHandshakeMessage::MESSAGE_LENGTH-resbufLength;
uint32_t temp = remain;
socket->readData((char*)resbuf+resbufLength, (int&)temp);
if(temp == 0) {
// we got EOF
throw new DlAbortEx(EX_EOF_FROM_PEER);
@ -132,9 +135,9 @@ bool PeerConnection::receiveHandshake(char* msg, int& length) {
}
resbufLength += temp;
// we got whole handshake payload
int writeLength = resbufLength > length ? length : resbufLength;
memcpy(msg, resbuf, writeLength);
length = writeLength;
uint32_t writeLength = resbufLength > dataLength ? dataLength : resbufLength;
memcpy(data, resbuf, writeLength);
dataLength = writeLength;
if(retval) {
resbufLength = 0;
}

View File

@ -38,7 +38,6 @@
#include "Option.h"
#include "Socket.h"
#include "Logger.h"
#include "PeerMessage.h"
#include "common.h"
// we assume maximum length of incoming message is "piece" message with 16KB
@ -47,32 +46,44 @@
class PeerConnection {
private:
int cuid;
int32_t cuid;
SocketHandle socket;
const Option* option;
const Logger* logger;
char resbuf[MAX_PAYLOAD_LEN];
int resbufLength;
int currentPayloadLength;
char lenbuf[4];
int lenbufLength;
uint32_t resbufLength;
uint32_t currentPayloadLength;
unsigned char lenbuf[4];
uint32_t lenbufLength;
public:
PeerConnection(int cuid, const SocketHandle& socket, const Option* op);
PeerConnection(int32_t cuid, const SocketHandle& socket, const Option* op);
~PeerConnection();
// Returns the number of bytes written
int sendMessage(const char* msg, int length);
uint32_t sendMessage(const unsigned char* data, uint32_t dataLength);
uint32_t sendMessage(const char* msg, int length) {
return sendMessage((const unsigned char*)msg, (uint32_t)length);
}
bool receiveMessage(unsigned char* data, uint32_t& dataLength);
bool receiveMessage(char* msg, int& length) {
return receiveMessage((unsigned char*)msg, (uint32_t&)length);
}
bool receiveMessage(char* msg, int& length);
/**
* Returns true if a handshake message is fully received, otherwise returns
* false.
* In both cases, 'msg' is filled with received bytes and the filled length
* is assigned to 'length'.
*/
bool receiveHandshake(char* msg, int& length);
bool receiveHandshake(unsigned char* data, uint32_t& dataLength);
bool receiveHandshake(char* msg, int& length) {
return receiveHandshake((unsigned char*)msg, (uint32_t&)length);
}
};
typedef SharedHandle<PeerConnection> PeerConnectionHandle;
#endif // _D_PEER_CONNECTION_H_

View File

@ -123,8 +123,8 @@ void PeerInteraction::rejectPieceMessageInQueue(int index, int begin, int length
void PeerInteraction::onChoked() {
for(Pieces::iterator itr = pieces.begin(); itr != pieces.end();) {
Piece& piece = *itr;
if(!peer->isInFastSet(piece.getIndex())) {
PieceHandle& piece = *itr;
if(!peer->isInFastSet(piece->getIndex())) {
abortPiece(piece);
itr = pieces.erase(itr);
} else {
@ -140,20 +140,20 @@ void PeerInteraction::abortAllPieces() {
}
}
void PeerInteraction::abortPiece(Piece& piece) {
if(!Piece::isNull(piece)) {
void PeerInteraction::abortPiece(const PieceHandle& piece) {
if(!piece.isNull()) {
int size = messageQueue.size();
for(int i = 0; i < size; i++) {
messageQueue.at(i)->onAbortPiece(piece);
}
for(RequestSlots::iterator itr = requestSlots.begin();
itr != requestSlots.end();) {
if(itr->getIndex() == piece.getIndex()) {
if(itr->getIndex() == piece->getIndex()) {
logger->debug("CUID#%d - Deleting request slot blockIndex=%d"
" because piece was canceled",
cuid,
itr->getBlockIndex());
piece.cancelBlock(itr->getBlockIndex());
piece->cancelBlock(itr->getBlockIndex());
itr = requestSlots.erase(itr);
} else {
itr++;
@ -181,14 +181,14 @@ void PeerInteraction::checkRequestSlot() {
" because of time out",
cuid,
slot.getBlockIndex());
Piece& piece = getDownloadPiece(slot.getIndex());
piece.cancelBlock(slot.getBlockIndex());
PieceHandle piece = getDownloadPiece(slot.getIndex());
piece->cancelBlock(slot.getBlockIndex());
itr = requestSlots.erase(itr);
peer->snubbing = true;
} else {
Piece piece = getDownloadPiece(slot.getIndex());
if(piece.hasBlock(slot.getBlockIndex()) ||
pieceStorage->hasPiece(piece.getIndex())) {
PieceHandle piece = getDownloadPiece(slot.getIndex());
if(piece->hasBlock(slot.getBlockIndex()) ||
pieceStorage->hasPiece(piece->getIndex())) {
logger->debug("CUID#%d - Deleting request slot blockIndex=%d because"
" the block has been acquired.", cuid,
slot.getBlockIndex());
@ -275,15 +275,19 @@ PeerMessageHandle PeerInteraction::receiveMessage() {
}
void PeerInteraction::syncPiece() {
/*
for(Pieces::iterator itr = pieces.begin(); itr != pieces.end(); itr++) {
pieceStorage->syncPiece(*itr);
}
*/
}
void PeerInteraction::updatePiece() {
/*
for(Pieces::iterator itr = pieces.begin(); itr != pieces.end(); itr++) {
pieceStorage->updatePiece(*itr);
}
*/
}
void PeerInteraction::getNewPieceAndSendInterest(int pieceNum) {
@ -297,8 +301,8 @@ void PeerInteraction::getNewPieceAndSendInterest(int pieceNum) {
onChoked();
if(peer->isFastExtensionEnabled()) {
while((int)pieces.size() < pieceNum) {
Piece piece = pieceStorage->getMissingFastPiece(peer);
if(Piece::isNull(piece)) {
PieceHandle piece = pieceStorage->getMissingFastPiece(peer);
if(piece.isNull()) {
break;
} else {
pieces.push_back(piece);
@ -307,8 +311,8 @@ void PeerInteraction::getNewPieceAndSendInterest(int pieceNum) {
}
} else {
while((int)pieces.size() < pieceNum) {
Piece piece = pieceStorage->getMissingPiece(peer);
if(Piece::isNull(piece)) {
PieceHandle piece = pieceStorage->getMissingPiece(peer);
if(piece.isNull()) {
break;
} else {
pieces.push_back(piece);
@ -325,8 +329,8 @@ void PeerInteraction::getNewPieceAndSendInterest(int pieceNum) {
void PeerInteraction::addRequests() {
// Abort downloading of completed piece.
for(Pieces::iterator itr = pieces.begin(); itr != pieces.end();) {
Piece& piece = *itr;
if(piece.pieceComplete()) {
PieceHandle& piece = *itr;
if(piece->pieceComplete()) {
abortPiece(piece);
itr = pieces.erase(itr);
} else {
@ -350,16 +354,16 @@ void PeerInteraction::addRequests() {
}
getNewPieceAndSendInterest(pieceNum);
for(Pieces::iterator itr = pieces.begin(); itr != pieces.end(); itr++) {
Piece& piece = *itr;
PieceHandle& piece = *itr;
if(pieceStorage->isEndGame()) {
BlockIndexes missingBlockIndexes = piece.getAllMissingBlockIndexes();
BlockIndexes missingBlockIndexes = piece->getAllMissingBlockIndexes();
random_shuffle(missingBlockIndexes.begin(), missingBlockIndexes.end());
int count = countRequestSlot();
for(BlockIndexes::const_iterator bitr = missingBlockIndexes.begin();
bitr != missingBlockIndexes.end() && count < MAX_PENDING_REQUEST;
bitr++) {
int blockIndex = *bitr;
if(!isInRequestSlot(piece.getIndex(), blockIndex)) {
if(!isInRequestSlot(piece->getIndex(), blockIndex)) {
addMessage(peerMessageFactory->createRequestMessage(piece,
blockIndex));
count++;
@ -367,7 +371,7 @@ void PeerInteraction::addRequests() {
}
} else {
while(countRequestSlot() < MAX_PENDING_REQUEST) {
int blockIndex = piece.getMissingUnusedBlockIndex();
int blockIndex = piece->getMissingUnusedBlockIndex();
if(blockIndex == -1) {
break;
}
@ -385,7 +389,7 @@ void PeerInteraction::addRequests() {
void PeerInteraction::sendHandshake() {
PeerMessageHandle handle =
peerMessageFactory->createHandshakeMessage(btContext->getInfoHash(),
btAnnounce->getPeerId().c_str());
(const char*)btContext->getPeerId());
addMessage(handle);
sendMessages();
}
@ -420,9 +424,9 @@ void PeerInteraction::sendAllowedFast() {
}
}
Piece& PeerInteraction::getDownloadPiece(int index) {
PieceHandle PeerInteraction::getDownloadPiece(int index) {
for(Pieces::iterator itr = pieces.begin(); itr != pieces.end(); itr++) {
if(itr->getIndex() == index) {
if((*itr)->getIndex() == index) {
return *itr;
}
}
@ -431,7 +435,7 @@ Piece& PeerInteraction::getDownloadPiece(int index) {
bool PeerInteraction::hasDownloadPiece(int index) const {
for(Pieces::const_iterator itr = pieces.begin(); itr != pieces.end(); itr++) {
if(itr->getIndex() == index) {
if((*itr)->getIndex() == index) {
return true;
}
}

View File

@ -48,7 +48,6 @@
#define REQUEST_TIME_OUT 60
#define ALLOWED_FAST_SET_SIZE 10
typedef deque<RequestSlot> RequestSlots;
typedef deque<PeerMessageHandle> MessageQueue;
class PeerInteraction {
@ -85,7 +84,7 @@ public:
void rejectPieceMessageInQueue(int index, int begin, int length);
void rejectAllPieceMessageInQueue();
void onChoked();
void abortPiece(Piece& piece);
void abortPiece(const PieceHandle& piece);
void abortAllPieces();
bool isSendingMessageInProgress() const;
@ -104,7 +103,7 @@ public:
// If the piece which this object has is nullPiece, then throws an exception.
// So before calling this function, call hasDownloadPiece and make sure
// this has valid piece, not nullPiece.
Piece& getDownloadPiece(int index);
PieceHandle getDownloadPiece(int index);
bool isInFastSet(int index) const;

View File

@ -35,15 +35,17 @@
#include "PeerInteractionCommand.h"
#include "PeerInitiateConnectionCommand.h"
#include "PeerMessageUtil.h"
#include "HandshakeMessage.h"
#include "KeepAliveMessage.h"
#include "ChokeMessage.h"
#include "UnchokeMessage.h"
#include "HaveMessage.h"
#include "DefaultBtInteractive.h"
#include "DlAbortEx.h"
#include "Util.h"
#include "message.h"
#include "prefs.h"
#include "DefaultBtMessageDispatcher.h"
#include "DefaultBtMessageReceiver.h"
#include "DefaultBtRequestFactory.h"
#include "DefaultBtMessageFactory.h"
#include "DefaultBtInteractive.h"
#include "PeerConnection.h"
#include <algorithm>
PeerInteractionCommand::PeerInteractionCommand(int cuid,
@ -52,198 +54,135 @@ PeerInteractionCommand::PeerInteractionCommand(int cuid,
const BtContextHandle& btContext,
const SocketHandle& s,
int sequence)
:PeerAbstractCommand(cuid, p, e, btContext, s), sequence(sequence) {
:PeerAbstractCommand(cuid, p, e, btContext, s),
sequence(sequence),
btInteractive(0)
{
// TODO move following bunch of processing to separate method, like init()
if(sequence == INITIATOR_SEND_HANDSHAKE) {
disableReadCheckSocket();
setWriteCheckSocket(socket);
setTimeout(e->option->getAsInt(PREF_PEER_CONNECTION_TIMEOUT));
}
peerInteraction = new PeerInteraction(cuid, peer, socket, e->option,
btContext);
PeerConnectionHandle peerConnection =
new PeerConnection(cuid, socket, e->option);
DefaultBtMessageDispatcherHandle dispatcher = new DefaultBtMessageDispatcher();
dispatcher->setCuid(cuid);
dispatcher->setPeer(peer);
dispatcher->setBtContext(btContext);
dispatcher->setOption(e->option);
DefaultBtMessageReceiverHandle receiver = new DefaultBtMessageReceiver();
receiver->setCuid(cuid);
receiver->setPeer(peer);
receiver->setBtContext(btContext);
receiver->setPeerConnection(peerConnection);
receiver->setDispatcher(dispatcher);
DefaultBtRequestFactoryHandle reqFactory = new DefaultBtRequestFactory();
reqFactory->setCuid(cuid);
reqFactory->setPeer(peer);
reqFactory->setBtContext(btContext);
reqFactory->setBtMessageDispatcher(dispatcher);
DefaultBtInteractiveHandle btInteractive = new DefaultBtInteractive();
btInteractive->setCuid(cuid);
btInteractive->setPeer(peer);
btInteractive->setBtContext(btContext);
btInteractive->setBtMessageReceiver(receiver);
btInteractive->setDispatcher(dispatcher);
btInteractive->setBtRequestFactory(reqFactory);
btInteractive->setPeerConnection(peerConnection);
btInteractive->setOption(e->option);
this->btInteractive = btInteractive;
DefaultBtMessageFactoryHandle factory = new DefaultBtMessageFactory();
factory->setCuid(cuid);
factory->setBtContext(btContext);
factory->setPeer(peer);
PeerObjectHandle peerObject = new PeerObject();
peerObject->btMessageDispatcher = dispatcher;
peerObject->btMessageFactory = factory;
peerObject->btRequestFactory = reqFactory;
peerObject->peerConnection = peerConnection;
PEER_OBJECT_CLUSTER(btContext)->registerHandle(peer->getId(), peerObject);
setUploadLimit(e->option->getAsInt(PREF_MAX_UPLOAD_LIMIT));
chokeUnchokeCount = 0;
haveCount = 0;
keepAliveCount = 0;
peer->activate();
}
PeerInteractionCommand::~PeerInteractionCommand() {
delete peerInteraction;
peer->deactivate();
PEER_OBJECT_CLUSTER(btContext)->unregisterHandle(peer->getId());
logger->debug("CUID#%d - unregistered message factory using ID:%s",
cuid, peer->getId().c_str());
}
bool PeerInteractionCommand::executeInternal() {
setReadCheckSocket(socket);
disableWriteCheckSocket();
setUploadLimitCheck(false);
setNoCheck(false);
switch(sequence) {
case INITIATOR_SEND_HANDSHAKE:
if(!socket->isWritable(0)) {
disableReadCheckSocket();
setWriteCheckSocket(socket);
break;
}
socket->setBlockingMode();
setReadCheckSocket(socket);
setTimeout(e->option->getAsInt(PREF_TIMEOUT));
peerInteraction->sendHandshake();
setTimeout(e->option->getAsInt(PREF_BT_TIMEOUT));
btInteractive->initiateHandshake();
sequence = INITIATOR_WAIT_HANDSHAKE;
break;
case INITIATOR_WAIT_HANDSHAKE: {
if(peerInteraction->countMessageInQueue() > 0) {
peerInteraction->sendMessages();
if(peerInteraction->countMessageInQueue() > 0) {
if(btInteractive->countPendingMessage() > 0) {
btInteractive->sendPendingMessage();
if(btInteractive->countPendingMessage() > 0) {
break;
}
}
PeerMessageHandle handshakeMessage =
peerInteraction->receiveHandshake();
if(handshakeMessage.get() == 0) {
BtMessageHandle handshakeMessage = btInteractive->receiveHandshake();
if(handshakeMessage.isNull()) {
break;
}
peer->setPeerId(((HandshakeMessage*)handshakeMessage.get())->peerId);
logger->info(MSG_RECEIVE_PEER_MESSAGE, cuid,
peer->ipaddr.c_str(), peer->port,
handshakeMessage->toString().c_str());
haveCheckTime.reset();
peerInteraction->sendBitfield();
peerInteraction->sendAllowedFast();
btInteractive->doPostHandshakeProcessing();
sequence = WIRED;
break;
}
case RECEIVER_WAIT_HANDSHAKE: {
PeerMessageHandle handshakeMessage =
peerInteraction->receiveHandshake(true);
if(handshakeMessage.get() == 0) {
BtMessageHandle handshakeMessage = btInteractive->receiveAndSendHandshake();
if(handshakeMessage.isNull()) {
break;
}
peer->setPeerId(((HandshakeMessage*)handshakeMessage.get())->peerId);
logger->info(MSG_RECEIVE_PEER_MESSAGE, cuid,
peer->ipaddr.c_str(), peer->port,
handshakeMessage->toString().c_str());
haveCheckTime.reset();
peerInteraction->sendBitfield();
peerInteraction->sendAllowedFast();
btInteractive->doPostHandshakeProcessing();
sequence = WIRED;
break;
}
case WIRED:
peerInteraction->syncPiece();
decideChoking();
btInteractive->doInteractionProcessing();
if(periodicExecPoint.elapsedInMillis(500)) {
periodicExecPoint.reset();
detectMessageFlooding();
peerInteraction->checkRequestSlot();
checkHave();
sendKeepAlive();
}
receiveMessages();
peerInteraction->addRequests();
peerInteraction->sendMessages();
break;
}
if(peerInteraction->countMessageInQueue() > 0) {
if(peerInteraction->isSendingMessageInProgress()) {
setUploadLimitCheck(true);
}
if(btInteractive->countPendingMessage() > 0) {
setNoCheck(true);
}
int maxSpeedLimit = e->option->getAsInt(PREF_MAX_DOWNLOAD_LIMIT);
if(maxSpeedLimit > 0) {
TransferStat stat = peerStorage->calculateStat();
if(maxSpeedLimit < stat.downloadSpeed) {
disableReadCheckSocket();
setNoCheck(true);
}
}
e->commands.push_back(this);
return false;
}
#define FLOODING_CHECK_INTERVAL 5
void PeerInteractionCommand::detectMessageFlooding() {
if(freqCheckPoint.elapsed(FLOODING_CHECK_INTERVAL)) {
if(chokeUnchokeCount*1.0/FLOODING_CHECK_INTERVAL >= 0.4
//|| haveCount*1.0/elapsed >= 20.0
|| keepAliveCount*1.0/FLOODING_CHECK_INTERVAL >= 1.0) {
throw new DlAbortEx("Flooding detected.");
} else {
chokeUnchokeCount = 0;
haveCount = 0;
keepAliveCount = 0;
freqCheckPoint.reset();
}
}
}
/*
void PeerInteractionCommand::checkLongTimePeerChoking() {
if(pieceStorage->downloadFinished()) {
return;
}
if(peer->amInterested && peer->peerChoking) {
if(chokeCheckPoint.elapsed(MAX_PEER_CHOKING_INTERVAL)) {
logger->info("CUID#%d - The peer is choking too long.", cuid);
peer->snubbing = true;
}
} else {
chokeCheckPoint.reset();
}
}
*/
void PeerInteractionCommand::decideChoking() {
if(peer->shouldBeChoking()) {
if(!peer->amChoking) {
peerInteraction->addMessage(peerInteraction->getPeerMessageFactory()->
createChokeMessage());
}
} else {
if(peer->amChoking) {
peerInteraction->addMessage(peerInteraction->getPeerMessageFactory()->
createUnchokeMessage());
}
}
}
void PeerInteractionCommand::receiveMessages() {
for(int i = 0; i < 50; i++) {
int maxSpeedLimit = e->option->getAsInt(PREF_MAX_DOWNLOAD_LIMIT);
if(maxSpeedLimit > 0) {
TransferStat stat = peerStorage->calculateStat();
if(maxSpeedLimit < stat.downloadSpeed) {
disableReadCheckSocket();
setNoCheck(true);
break;
}
}
PeerMessageHandle message = peerInteraction->receiveMessage();
if(message.get() == NULL) {
return;
}
logger->info(MSG_RECEIVE_PEER_MESSAGE, cuid,
peer->ipaddr.c_str(), peer->port,
message->toString().c_str());
// to detect flooding
switch(message->getId()) {
case KeepAliveMessage::ID:
keepAliveCount++;
break;
case ChokeMessage::ID:
if(!peer->peerChoking) {
chokeUnchokeCount++;
}
break;
case UnchokeMessage::ID:
if(peer->peerChoking) {
chokeUnchokeCount++;
}
break;
case HaveMessage::ID:
haveCount++;
break;
}
message->receivedAction();
}
}
// TODO this method removed when PeerBalancerCommand is implemented
bool PeerInteractionCommand::prepareForNextPeer(int wait) {
if(peerStorage->isPeerAvailable() && btRuntime->lessThanEqMinPeer()) {
@ -266,42 +205,6 @@ bool PeerInteractionCommand::prepareForRetry(int wait) {
}
void PeerInteractionCommand::onAbort(Exception* ex) {
peerInteraction->abortAllPieces();
btInteractive->cancelAllPiece();
PeerAbstractCommand::onAbort(ex);
}
void PeerInteractionCommand::sendKeepAlive() {
if(keepAliveCheckPoint.elapsed(KEEP_ALIVE_INTERVAL)) {
if(peerInteraction->countMessageInQueue() == 0) {
peerInteraction->addMessage(peerInteraction->getPeerMessageFactory()->
createKeepAliveMessage());
peerInteraction->sendMessages();
}
keepAliveCheckPoint.reset();
}
}
void PeerInteractionCommand::checkHave() {
Integers indexes =
pieceStorage->getAdvertisedPieceIndexes(cuid, haveCheckTime);
haveCheckTime.reset();
if(indexes.size() >= 20) {
if(peer->isFastExtensionEnabled()) {
if(pieceStorage->downloadFinished()) {
peerInteraction->addMessage(peerInteraction->getPeerMessageFactory()->
createHaveAllMessage());
} else {
peerInteraction->addMessage(peerInteraction->getPeerMessageFactory()->
createBitfieldMessage());
}
} else {
peerInteraction->addMessage(peerInteraction->getPeerMessageFactory()->
createBitfieldMessage());
}
} else {
for(Integers::iterator itr = indexes.begin(); itr != indexes.end(); itr++) {
peerInteraction->addMessage(peerInteraction->getPeerMessageFactory()->
createHaveMessage(*itr));
}
}
}

View File

@ -36,45 +36,24 @@
#define _D_PEER_INTERACTION_COMMAND_H_
#include "PeerAbstractCommand.h"
#include "PeerConnection.h"
#include "PeerInteraction.h"
#include "TimeA2.h"
using namespace std;
#define MAX_PEER_CHOKING_INTERVAL (1*60)
#define KEEP_ALIVE_INTERVAL 120
#include "BtInteractive.h"
class PeerInteractionCommand : public PeerAbstractCommand {
private:
int sequence;
PeerInteraction* peerInteraction;
Time keepAliveCheckPoint;
//Time chokeCheckPoint;
Time freqCheckPoint;
Time haveCheckTime;
Time periodicExecPoint;
int chokeUnchokeCount;
int haveCount;
int keepAliveCount;
void receiveMessages();
void detectMessageFlooding();
void checkLongTimePeerChoking();
void detectTimeoutAndDuplicateBlock();
void decideChoking();
void sendKeepAlive();
void checkHave();
BtInteractiveHandle btInteractive;
protected:
bool executeInternal();
bool prepareForRetry(int wait);
bool prepareForNextPeer(int wait);
void onAbort(Exception* ex);
public:
PeerInteractionCommand(int cuid, const PeerHandle& peer,
PeerInteractionCommand(int cuid,
const PeerHandle& peer,
TorrentDownloadEngine* e,
const BtContextHandle& btContext,
const SocketHandle& s, int sequence);
const SocketHandle& s,
int sequence);
~PeerInteractionCommand();

View File

@ -39,6 +39,7 @@ PeerMessage::PeerMessage()
:inProgress(false),
invalidate(false),
uploading(false),
peer(0),
btContext(0),
peerStorage(0),
pieceStorage(0)

Some files were not shown because too many files have changed in this diff Show More