소스 검색

Add --bt-force-encryption option

This option requires BitTorrent message payload encryption with
arc4. This is a shorthand of --bt-requre-crypto
--bt-min-crypto-level=arc4.  If true is given, deny legacy BitTorrent
handshake and only use Obfuscation handshake and always encrypt
message payload. This option defaults to false.
Tatsuhiro Tsujikawa 10 년 전
부모
커밋
c653c72dc8
9개의 변경된 파일47개의 추가작업 그리고 6개의 파일을 삭제
  1. 10 0
      doc/manual-src/en/aria2c.rst
  2. 2 1
      src/DefaultBtAnnounce.cc
  3. 3 1
      src/InitiatorMSEHandshakeCommand.cc
  4. 6 3
      src/MSEHandshake.cc
  5. 12 0
      src/OptionHandlerFactory.cc
  6. 3 1
      src/ReceiverMSEHandshakeCommand.cc
  7. 1 0
      src/prefs.cc
  8. 2 0
      src/prefs.h
  9. 8 0
      src/usage_text.h

+ 10 - 0
doc/manual-src/en/aria2c.rst

@@ -625,6 +625,15 @@ BitTorrent Specific Options
   tracker. Although this function is named ``external``, it can accept
   any kind of IP addresses. IPADDRESS must be a numeric IP address.
 
+.. option:: --bt-force-encryption[=true|false]
+
+  Requires BitTorrent message payload encryption with arc4.  This is a
+  shorthand of :option:`--bt-requre-crypto`
+  :option:`--bt-min-crypto-level`\=arc4.  This option does not change
+  the option value of those options.  If ``true`` is given, deny
+  legacy BitTorrent handshake and only use Obfuscation handshake and
+  always encrypt message payload.  Default: ``false``
+
 .. option:: --bt-hash-check-seed[=true|false]
 
  If ``true`` is given, after hash check using :option:`--check-integrity <-V>` option and
@@ -1894,6 +1903,7 @@ of URIs. These optional lines must start with white space(s).
   * :option:`bt-enable-lpd <--bt-enable-lpd>`
   * :option:`bt-exclude-tracker <--bt-exclude-tracker>`
   * :option:`bt-external-ip <--bt-external-ip>`
+  * :option:`bt-force-encryption <--bt-force-encryption>`
   * :option:`bt-hash-check-seed <--bt-hash-check-seed>`
   * :option:`bt-max-peers <--bt-max-peers>`
   * :option:`bt-metadata-only <--bt-metadata-only>`

+ 2 - 1
src/DefaultBtAnnounce.cc

@@ -189,7 +189,8 @@ std::string DefaultBtAnnounce::getAnnounceUrl() {
     uri += "&trackerid=";
     uri += util::torrentPercentEncode(trackerId_);
   }
-  if(option_->getAsBool(PREF_BT_REQUIRE_CRYPTO)) {
+  if(option_->getAsBool(PREF_BT_FORCE_ENCRYPTION) ||
+     option_->getAsBool(PREF_BT_REQUIRE_CRYPTO)) {
     uri += "&requirecrypto=1";
   } else {
     uri += "&supportcrypto=1";

+ 3 - 1
src/InitiatorMSEHandshakeCommand.cc

@@ -216,7 +216,8 @@ bool InitiatorMSEHandshakeCommand::prepareForNextPeer(time_t wait)
     // established.
     tryNewPeer();
     return true;
-  } else if(getOption()->getAsBool(PREF_BT_REQUIRE_CRYPTO)) {
+  } else if(getOption()->getAsBool(PREF_BT_FORCE_ENCRYPTION) ||
+            getOption()->getAsBool(PREF_BT_REQUIRE_CRYPTO)) {
     A2_LOG_INFO(fmt("CUID#%" PRId64 " - Establishing connection using legacy"
                     " BitTorrent handshake is disabled by preference.",
                     getCuid()));
@@ -239,6 +240,7 @@ bool InitiatorMSEHandshakeCommand::prepareForNextPeer(time_t wait)
 void InitiatorMSEHandshakeCommand::onAbort()
 {
   if(sequence_ == INITIATOR_SEND_KEY ||
+     getOption()->getAsBool(PREF_BT_FORCE_ENCRYPTION) ||
      getOption()->getAsBool(PREF_BT_REQUIRE_CRYPTO)) {
     peerStorage_->returnPeer(getPeer());
   }

+ 6 - 3
src/MSEHandshake.cc

@@ -284,7 +284,8 @@ void MSEHandshake::sendInitiatorStep2()
   ptr += sizeof(VC);
   // crypto_provide
   memset(ptr, 0, CRYPTO_BITFIELD_LENGTH);
-  if(option_->get(PREF_BT_MIN_CRYPTO_LEVEL) == V_PLAIN) {
+  if(!option_->getAsBool(PREF_BT_FORCE_ENCRYPTION) &&
+     option_->get(PREF_BT_MIN_CRYPTO_LEVEL) == V_PLAIN) {
     ptr[3] = CRYPTO_PLAIN_TEXT;
   }
   ptr[3] |= CRYPTO_ARC4;
@@ -347,7 +348,8 @@ bool MSEHandshake::receiveInitiatorCryptoSelectAndPadDLength()
   //verifyCryptoSelect
   unsigned char* rbufptr = rbuf_;
   decryptor_->encrypt(CRYPTO_BITFIELD_LENGTH, rbufptr, rbufptr);
-  if(rbufptr[3]&CRYPTO_PLAIN_TEXT &&
+  if((rbufptr[3]&CRYPTO_PLAIN_TEXT) &&
+     !option_->getAsBool(PREF_BT_FORCE_ENCRYPTION) &&
      option_->get(PREF_BT_MIN_CRYPTO_LEVEL) == V_PLAIN) {
     A2_LOG_DEBUG(fmt("CUID#%" PRId64 " - peer prefers plaintext.",
                      cuid_));
@@ -447,7 +449,8 @@ bool MSEHandshake::receiveReceiverHashAndPadCLength
   decryptor_->encrypt(CRYPTO_BITFIELD_LENGTH, rbufptr, rbufptr);
   // TODO choose the crypto type based on the preference.
   // For now, choose ARC4.
-  if(rbufptr[3]&CRYPTO_PLAIN_TEXT &&
+  if((rbufptr[3]&CRYPTO_PLAIN_TEXT) &&
+     !option_->getAsBool(PREF_BT_FORCE_ENCRYPTION) &&
      option_->get(PREF_BT_MIN_CRYPTO_LEVEL) == V_PLAIN) {
     A2_LOG_DEBUG(fmt("CUID#%" PRId64 " - peer provides plaintext.",
                      cuid_));

+ 12 - 0
src/OptionHandlerFactory.cc

@@ -1757,6 +1757,18 @@ std::vector<OptionHandler*> OptionHandlerFactory::createOptionHandlers()
     op->setChangeOptionForReserved(true);
     handlers.push_back(op);
   }
+  {
+    OptionHandler* op(new BooleanOptionHandler
+                      (PREF_BT_FORCE_ENCRYPTION,
+                       TEXT_BT_FORCE_ENCRYPTION,
+                       A2_V_FALSE,
+                       OptionHandler::OPT_ARG));
+    op->addTag(TAG_BITTORRENT);
+    op->setInitialOption(true);
+    op->setChangeGlobalOption(true);
+    op->setChangeOptionForReserved(true);
+    handlers.push_back(op);
+  }
   {
     OptionHandler* op(new NumberOptionHandler
                       (PREF_BT_KEEP_ALIVE_INTERVAL,

+ 3 - 1
src/ReceiverMSEHandshakeCommand.cc

@@ -96,7 +96,9 @@ bool ReceiverMSEHandshakeCommand::executeInternal()
         sequence_ = RECEIVER_WAIT_KEY;
         break;
       case MSEHandshake::HANDSHAKE_LEGACY: {
-        if(getDownloadEngine()->getOption()->getAsBool(PREF_BT_REQUIRE_CRYPTO)){
+        const auto option = getDownloadEngine()->getOption();
+        if(option->getAsBool(PREF_BT_FORCE_ENCRYPTION) ||
+           option->getAsBool(PREF_BT_REQUIRE_CRYPTO)){
           throw DL_ABORT_EX
             ("The legacy BitTorrent handshake is not acceptable by the"
              " preference.");

+ 1 - 0
src/prefs.cc

@@ -549,6 +549,7 @@ PrefPtr PREF_BT_EXCLUDE_TRACKER = makePref("bt-exclude-tracker");
 PrefPtr PREF_BT_REMOVE_UNSELECTED_FILE =
   makePref("bt-remove-unselected-file");
 PrefPtr PREF_BT_DETACH_SEED_ONLY = makePref("bt-detach-seed-only");
+PrefPtr PREF_BT_FORCE_ENCRYPTION = makePref("bt-force-encryption");
 
 /**
  * Metalink related preferences

+ 2 - 0
src/prefs.h

@@ -486,6 +486,8 @@ extern PrefPtr PREF_BT_EXCLUDE_TRACKER;
 extern PrefPtr PREF_BT_REMOVE_UNSELECTED_FILE;
 // values: true |false
 extern PrefPtr PREF_BT_DETACH_SEED_ONLY;
+// values: true | false
+extern PrefPtr PREF_BT_FORCE_ENCRYPTION;
 
 /**
  * Metalink related preferences

+ 8 - 0
src/usage_text.h

@@ -1013,3 +1013,11 @@
   "                              recognized as active download in RPC method.")
 #define TEXT_MIN_TLS_VERSION                                            \
   _(" --min-tls-version=VERSION  Specify minimum SSL/TLS version to enable.")
+#define TEXT_BT_FORCE_ENCRYPTION                                        \
+  _(" --bt-force-encryption[=true|false]\n"                             \
+    "                              Requires BitTorrent message payload encryption\n" \
+    "                              with arc4. This is a shorthand of\n" \
+    "                              --bt-requre-crypto --bt-min-crypto-level=arc4.\n" \
+    "                              If true is given, deny legacy BitTorrent\n" \
+    "                              handshake and only use Obfuscation handshake and\n" \
+    "                              always encrypt message payload.")