Skip to content

Commit

Permalink
Merge pull request #2147 from Vort/xp_fix2
Browse files Browse the repository at this point in the history
fix Windows XP build
  • Loading branch information
orignal authored Jan 7, 2025
2 parents 1293e12 + 0b788de commit c023051
Show file tree
Hide file tree
Showing 10 changed files with 135 additions and 104 deletions.
2 changes: 2 additions & 0 deletions .github/workflows/build-windows.yml
Original file line number Diff line number Diff line change
Expand Up @@ -133,6 +133,8 @@ jobs:
git clone https://github.com/msys2/MINGW-packages
cd MINGW-packages
git checkout 4cbb366edf2f268ac3146174b40ce38604646fc5 mingw-w64-boost
cd mingw-w64-boost
sed -i 's/boostorg.jfrog.io\/artifactory\/main/archives.boost.io/' PKGBUILD
# headers
- name: Get headers package version
Expand Down
14 changes: 13 additions & 1 deletion libi2pd/Config.cpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2013-2024, The PurpleI2P Project
* Copyright (c) 2013-2025, The PurpleI2P Project
*
* This file is part of Purple i2pd project and licensed under BSD3
*
Expand Down Expand Up @@ -154,6 +154,17 @@ namespace config {
("socksproxy.i2p.streaming.profile", value<std::string>()->default_value("1"), "SOCKS Proxy bandwidth usage profile. 1 - bulk(high), 2- interactive(low)")
;

options_description shareddest("Shared local destination options");
shareddest.add_options()
("shareddest.inbound.length", value<std::string>()->default_value("3"), "Shared local destination inbound tunnel length")
("shareddest.outbound.length", value<std::string>()->default_value("3"), "Shared local destination outbound tunnel length")
("shareddest.inbound.quantity", value<std::string>()->default_value("3"), "Shared local destination inbound tunnels quantity")
("shareddest.outbound.quantity", value<std::string>()->default_value("3"), "Shared local destination outbound tunnels quantity")
("shareddest.i2cp.leaseSetType", value<std::string>()->default_value("3"), "Shared local destination's LeaseSet type")
("shareddest.i2cp.leaseSetEncType", value<std::string>()->default_value("0,4"), "Shared local destination's LeaseSet encryption type")
("shareddest.i2p.streaming.profile", value<std::string>()->default_value("2"), "Shared local destination bandwidth usage profile. 1 - bulk(high), 2- interactive(low)")
;

options_description sam("SAM bridge options");
sam.add_options()
("sam.enabled", value<bool>()->default_value(true), "Enable or disable SAM Application bridge")
Expand Down Expand Up @@ -341,6 +352,7 @@ namespace config {
.add(httpserver)
.add(httpproxy)
.add(socksproxy)
.add(shareddest)
.add(sam)
.add(bob)
.add(i2cp)
Expand Down
17 changes: 9 additions & 8 deletions libi2pd/Destination.cpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2013-2024, The PurpleI2P Project
* Copyright (c) 2013-2025, The PurpleI2P Project
*
* This file is part of Purple i2pd project and licensed under BSD3
*
Expand Down Expand Up @@ -597,7 +597,8 @@ namespace client
m_ExcludedFloodfills.clear ();
m_PublishReplyToken = 0;
// schedule verification
m_PublishVerificationTimer.expires_from_now (boost::posix_time::seconds(PUBLISH_VERIFICATION_TIMEOUT));
m_PublishVerificationTimer.expires_from_now (boost::posix_time::seconds(PUBLISH_VERIFICATION_TIMEOUT +
(m_Pool ? m_Pool->GetRng ()() % PUBLISH_VERIFICATION_TIMEOUT_VARIANCE : 0)));
m_PublishVerificationTimer.async_wait (std::bind (&LeaseSetDestination::HandlePublishVerificationTimer,
shared_from_this (), std::placeholders::_1));
}
Expand Down Expand Up @@ -676,8 +677,8 @@ namespace client
m_ExcludedFloodfills.clear ();
m_PublishReplyToken = 1; // dummy non-zero value
// try again after a while
LogPrint (eLogInfo, "Destination: Can't publish LeasetSet because destination is not ready. Try publishing again after ", PUBLISH_CONFIRMATION_TIMEOUT, " seconds");
m_PublishConfirmationTimer.expires_from_now (boost::posix_time::seconds(PUBLISH_CONFIRMATION_TIMEOUT));
LogPrint (eLogInfo, "Destination: Can't publish LeasetSet because destination is not ready. Try publishing again after ", PUBLISH_CONFIRMATION_TIMEOUT, " milliseconds");
m_PublishConfirmationTimer.expires_from_now (boost::posix_time::milliseconds(PUBLISH_CONFIRMATION_TIMEOUT));
m_PublishConfirmationTimer.async_wait (std::bind (&LeaseSetDestination::HandlePublishConfirmationTimer,
shared_from_this (), std::placeholders::_1));
return;
Expand All @@ -696,7 +697,7 @@ namespace client
s->HandlePublishConfirmationTimer (boost::system::error_code());
});
};
m_PublishConfirmationTimer.expires_from_now (boost::posix_time::seconds(PUBLISH_CONFIRMATION_TIMEOUT));
m_PublishConfirmationTimer.expires_from_now (boost::posix_time::milliseconds(PUBLISH_CONFIRMATION_TIMEOUT));
m_PublishConfirmationTimer.async_wait (std::bind (&LeaseSetDestination::HandlePublishConfirmationTimer,
shared_from_this (), std::placeholders::_1));
outbound->SendTunnelDataMsgTo (floodfill->GetIdentHash (), 0, msg);
Expand All @@ -712,15 +713,15 @@ namespace client
m_PublishReplyToken = 0;
if (GetIdentity ()->GetCryptoKeyType () == i2p::data::CRYPTO_KEY_TYPE_ELGAMAL)
{
LogPrint (eLogWarning, "Destination: Publish confirmation was not received in ", PUBLISH_CONFIRMATION_TIMEOUT, " seconds or failed. will try again");
LogPrint (eLogWarning, "Destination: Publish confirmation was not received in ", PUBLISH_CONFIRMATION_TIMEOUT, " milliseconds or failed. will try again");
Publish ();
}
else
{
LogPrint (eLogWarning, "Destination: Publish confirmation was not received in ", PUBLISH_CONFIRMATION_TIMEOUT, " seconds from Java floodfill for crypto type ", (int)GetIdentity ()->GetCryptoKeyType ());
LogPrint (eLogWarning, "Destination: Publish confirmation was not received in ", PUBLISH_CONFIRMATION_TIMEOUT, " milliseconds from Java floodfill for crypto type ", (int)GetIdentity ()->GetCryptoKeyType ());
// Java floodfill never sends confirmation back for unknown crypto type
// assume it successive and try to verify
m_PublishVerificationTimer.expires_from_now (boost::posix_time::seconds(PUBLISH_VERIFICATION_TIMEOUT));
m_PublishVerificationTimer.expires_from_now (boost::posix_time::seconds(PUBLISH_VERIFICATION_TIMEOUT + PUBLISH_VERIFICATION_TIMEOUT_VARIANCE)); // always max
m_PublishVerificationTimer.async_wait (std::bind (&LeaseSetDestination::HandlePublishVerificationTimer,
shared_from_this (), std::placeholders::_1));

Expand Down
7 changes: 4 additions & 3 deletions libi2pd/Destination.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2013-2024, The PurpleI2P Project
* Copyright (c) 2013-2025, The PurpleI2P Project
*
* This file is part of Purple i2pd project and licensed under BSD3
*
Expand Down Expand Up @@ -36,8 +36,9 @@ namespace client
const uint8_t PROTOCOL_TYPE_STREAMING = 6;
const uint8_t PROTOCOL_TYPE_DATAGRAM = 17;
const uint8_t PROTOCOL_TYPE_RAW = 18;
const int PUBLISH_CONFIRMATION_TIMEOUT = 5; // in seconds
const int PUBLISH_VERIFICATION_TIMEOUT = 10; // in seconds after successful publish
const int PUBLISH_CONFIRMATION_TIMEOUT = 1800; // in milliseconds
const int PUBLISH_VERIFICATION_TIMEOUT = 5; // in seconds after successful publish
const int PUBLISH_VERIFICATION_TIMEOUT_VARIANCE = 3; // in seconds
const int PUBLISH_MIN_INTERVAL = 20; // in seconds
const int PUBLISH_REGULAR_VERIFICATION_INTERNAL = 100; // in seconds periodically
const int LEASESET_REQUEST_TIMEOUT = 1600; // in milliseconds
Expand Down
6 changes: 3 additions & 3 deletions libi2pd/RouterContext.cpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2013-2024, The PurpleI2P Project
* Copyright (c) 2013-2025, The PurpleI2P Project
*
* This file is part of Purple i2pd project and licensed under BSD3
*
Expand Down Expand Up @@ -1434,7 +1434,7 @@ namespace i2p
i2p::garlic::WrapECIESX25519MessageForRouter (msg, floodfill->GetIdentity ()->GetEncryptionPublicKey ()));
}
else
LogPrint (eLogInfo, "Router: Can't publish our RouterInfo. No tunnles. Try again in ", ROUTER_INFO_CONFIRMATION_TIMEOUT, " seconds");
LogPrint (eLogInfo, "Router: Can't publish our RouterInfo. No tunnels. Try again in ", ROUTER_INFO_CONFIRMATION_TIMEOUT, " milliseconds");
}
m_PublishExcluded.insert (floodfill->GetIdentHash ());
m_PublishReplyToken = replyToken;
Expand All @@ -1448,7 +1448,7 @@ namespace i2p
if (m_PublishTimer)
{
m_PublishTimer->cancel ();
m_PublishTimer->expires_from_now (boost::posix_time::seconds(ROUTER_INFO_CONFIRMATION_TIMEOUT));
m_PublishTimer->expires_from_now (boost::posix_time::milliseconds(ROUTER_INFO_CONFIRMATION_TIMEOUT));
m_PublishTimer->async_wait (std::bind (&RouterContext::HandlePublishResendTimer,
this, std::placeholders::_1));
}
Expand Down
4 changes: 2 additions & 2 deletions libi2pd/RouterContext.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2013-2024, The PurpleI2P Project
* Copyright (c) 2013-2025, The PurpleI2P Project
*
* This file is part of Purple i2pd project and licensed under BSD3
*
Expand Down Expand Up @@ -34,7 +34,7 @@ namespace garlic
const int ROUTER_INFO_PUBLISH_INTERVAL = 39*60; // in seconds
const int ROUTER_INFO_INITIAL_PUBLISH_INTERVAL = 10; // in seconds
const int ROUTER_INFO_PUBLISH_INTERVAL_VARIANCE = 105;// in seconds
const int ROUTER_INFO_CONFIRMATION_TIMEOUT = 5; // in seconds
const int ROUTER_INFO_CONFIRMATION_TIMEOUT = 1600; // in milliseconds
const int ROUTER_INFO_MAX_PUBLISH_EXCLUDED_FLOODFILLS = 15;
const int ROUTER_INFO_CONGESTION_UPDATE_INTERVAL = 12*60; // in seconds
const int ROUTER_INFO_CLEANUP_INTERVAL = 102; // in seconds
Expand Down
160 changes: 88 additions & 72 deletions libi2pd/SSU2Session.cpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2022-2024, The PurpleI2P Project
* Copyright (c) 2022-2025, The PurpleI2P Project
*
* This file is part of Purple i2pd project and licensed under BSD3
*
Expand Down Expand Up @@ -92,7 +92,7 @@ namespace transport
m_RTO (SSU2_INITIAL_RTO), m_RelayTag (0),m_ConnectTimer (server.GetService ()),
m_TerminationReason (eSSU2TerminationReasonNormalClose),
m_MaxPayloadSize (SSU2_MIN_PACKET_SIZE - IPV6_HEADER_SIZE - UDP_HEADER_SIZE - 32), // min size
m_LastResendTime (0), m_LastResendAttemptTime (0)
m_LastResendTime (0), m_LastResendAttemptTime (0), m_NumRanges (0)
{
if (noise)
m_NoiseState.reset (new i2p::crypto::NoiseSymmetricState);
Expand Down Expand Up @@ -1744,6 +1744,7 @@ namespace transport
HandleAckRange (firstPacketNum, ackThrough, i2p::util::GetMillisecondsSinceEpoch ()); // acnt
// ranges
len -= 5;
if (!len || m_SentPackets.empty ()) return; // don't handle ranges if nothing to acknowledge
const uint8_t * ranges = buf + 5;
while (len > 0 && firstPacketNum && ackThrough - firstPacketNum < SSU2_MAX_NUM_ACK_PACKETS)
{
Expand Down Expand Up @@ -2624,17 +2625,17 @@ namespace transport
size_t SSU2Session::CreateAckBlock (uint8_t * buf, size_t len)
{
if (len < 8) return 0;
int maxNumRanges = (len - 8) >> 1;
if (maxNumRanges > SSU2_MAX_NUM_ACK_RANGES) maxNumRanges = SSU2_MAX_NUM_ACK_RANGES;
buf[0] = eSSU2BlkAck;
uint32_t ackThrough = m_OutOfSequencePackets.empty () ? m_ReceivePacketNum : *m_OutOfSequencePackets.rbegin ();
htobe32buf (buf + 3, ackThrough); // Ack Through
uint16_t acnt = 0;
int numRanges = 0;
if (ackThrough)
{
if (m_OutOfSequencePackets.empty ())
{
acnt = std::min ((int)ackThrough, SSU2_MAX_NUM_ACNT); // no gaps
m_NumRanges = 0;
}
else
{
auto it = m_OutOfSequencePackets.rbegin (); it++; // prev packet num
Expand All @@ -2647,87 +2648,96 @@ namespace transport
it++;
}
// ranges
uint32_t lastNum = ackThrough - acnt;
if (acnt > SSU2_MAX_NUM_ACNT)
{
auto d = std::div (acnt - SSU2_MAX_NUM_ACNT, SSU2_MAX_NUM_ACNT);
acnt = SSU2_MAX_NUM_ACNT;
if (d.quot > maxNumRanges)
{
d.quot = maxNumRanges;
d.rem = 0;
}
// Acks only ranges for acnt
for (int i = 0; i < d.quot; i++)
{
buf[8 + numRanges*2] = 0; buf[8 + numRanges*2 + 1] = SSU2_MAX_NUM_ACNT; // NACKs 0, Acks 255
numRanges++;
}
if (d.rem > 0)
if (!m_NumRanges)
{
int maxNumRanges = (len - 8) >> 1;
if (maxNumRanges > SSU2_MAX_NUM_ACK_RANGES) maxNumRanges = SSU2_MAX_NUM_ACK_RANGES;
int numRanges = 0;
uint32_t lastNum = ackThrough - acnt;
if (acnt > SSU2_MAX_NUM_ACNT)
{
buf[8 + numRanges*2] = 0; buf[8 + numRanges*2 + 1] = d.rem;
numRanges++;
auto d = std::div (acnt - SSU2_MAX_NUM_ACNT, SSU2_MAX_NUM_ACNT);
acnt = SSU2_MAX_NUM_ACNT;
if (d.quot > maxNumRanges)
{
d.quot = maxNumRanges;
d.rem = 0;
}
// Acks only ranges for acnt
for (int i = 0; i < d.quot; i++)
{
m_Ranges[numRanges*2] = 0; m_Ranges[numRanges*2 + 1] = SSU2_MAX_NUM_ACNT; // NACKs 0, Acks 255
numRanges++;
}
if (d.rem > 0)
{
m_Ranges[numRanges*2] = 0; m_Ranges[numRanges*2 + 1] = d.rem;
numRanges++;
}
}
}
int numPackets = acnt + numRanges*SSU2_MAX_NUM_ACNT;
while (it != m_OutOfSequencePackets.rend () &&
numRanges < maxNumRanges && numPackets < SSU2_MAX_NUM_ACK_PACKETS)
{
if (lastNum - (*it) > SSU2_MAX_NUM_ACNT)
int numPackets = acnt + numRanges*SSU2_MAX_NUM_ACNT;
while (it != m_OutOfSequencePackets.rend () &&
numRanges < maxNumRanges && numPackets < SSU2_MAX_NUM_ACK_PACKETS)
{
// NACKs only ranges
if (lastNum > (*it) + SSU2_MAX_NUM_ACNT*(maxNumRanges - numRanges)) break; // too many NACKs
while (lastNum - (*it) > SSU2_MAX_NUM_ACNT)
if (lastNum - (*it) > SSU2_MAX_NUM_ACNT)
{
// NACKs only ranges
if (lastNum > (*it) + SSU2_MAX_NUM_ACNT*(maxNumRanges - numRanges)) break; // too many NACKs
while (lastNum - (*it) > SSU2_MAX_NUM_ACNT)
{
m_Ranges[numRanges*2] = SSU2_MAX_NUM_ACNT; m_Ranges[numRanges*2 + 1] = 0; // NACKs 255, Acks 0
lastNum -= SSU2_MAX_NUM_ACNT;
numRanges++;
numPackets += SSU2_MAX_NUM_ACNT;
}
}
// NACKs and Acks ranges
m_Ranges[numRanges*2] = lastNum - (*it) - 1; // NACKs
numPackets += m_Ranges[numRanges*2];
lastNum = *it; it++;
int numAcks = 1;
while (it != m_OutOfSequencePackets.rend () && lastNum > 0 && *it == lastNum - 1)
{
numAcks++; lastNum--;
it++;
}
while (numAcks > SSU2_MAX_NUM_ACNT)
{
buf[8 + numRanges*2] = SSU2_MAX_NUM_ACNT; buf[8 + numRanges*2 + 1] = 0; // NACKs 255, Acks 0
lastNum -= SSU2_MAX_NUM_ACNT;
// Acks only ranges
m_Ranges[numRanges*2 + 1] = SSU2_MAX_NUM_ACNT; // Acks 255
numAcks -= SSU2_MAX_NUM_ACNT;
numRanges++;
numPackets += SSU2_MAX_NUM_ACNT;
m_Ranges[numRanges*2] = 0; // NACKs 0
if (numRanges >= maxNumRanges || numPackets >= SSU2_MAX_NUM_ACK_PACKETS) break;
}
}
// NACKs and Acks ranges
buf[8 + numRanges*2] = lastNum - (*it) - 1; // NACKs
numPackets += buf[8 + numRanges*2];
lastNum = *it; it++;
int numAcks = 1;
while (it != m_OutOfSequencePackets.rend () && lastNum > 0 && *it == lastNum - 1)
{
numAcks++; lastNum--;
it++;
}
while (numAcks > SSU2_MAX_NUM_ACNT)
{
// Acks only ranges
buf[8 + numRanges*2 + 1] = SSU2_MAX_NUM_ACNT; // Acks 255
numAcks -= SSU2_MAX_NUM_ACNT;
if (numAcks > SSU2_MAX_NUM_ACNT) numAcks = SSU2_MAX_NUM_ACNT;
m_Ranges[numRanges*2 + 1] = (uint8_t)numAcks; // Acks
numPackets += numAcks;
numRanges++;
numPackets += SSU2_MAX_NUM_ACNT;
buf[8 + numRanges*2] = 0; // NACKs 0
if (numRanges >= maxNumRanges || numPackets >= SSU2_MAX_NUM_ACK_PACKETS) break;
}
if (numAcks > SSU2_MAX_NUM_ACNT) numAcks = SSU2_MAX_NUM_ACNT;
buf[8 + numRanges*2 + 1] = (uint8_t)numAcks; // Acks
numPackets += numAcks;
numRanges++;
}
if (it == m_OutOfSequencePackets.rend () &&
numRanges < maxNumRanges && numPackets < SSU2_MAX_NUM_ACK_PACKETS)
{
// add range between out-of-sequence and received
int nacks = *m_OutOfSequencePackets.begin () - m_ReceivePacketNum - 1;
if (nacks > 0)
if (it == m_OutOfSequencePackets.rend () &&
numRanges < maxNumRanges && numPackets < SSU2_MAX_NUM_ACK_PACKETS)
{
if (nacks > SSU2_MAX_NUM_ACNT) nacks = SSU2_MAX_NUM_ACNT;
buf[8 + numRanges*2] = nacks;
buf[8 + numRanges*2 + 1] = std::min ((int)m_ReceivePacketNum + 1, SSU2_MAX_NUM_ACNT);
numRanges++;
// add range between out-of-sequence and received
int nacks = *m_OutOfSequencePackets.begin () - m_ReceivePacketNum - 1;
if (nacks > 0)
{
if (nacks > SSU2_MAX_NUM_ACNT) nacks = SSU2_MAX_NUM_ACNT;
m_Ranges[numRanges*2] = nacks;
m_Ranges[numRanges*2 + 1] = std::min ((int)m_ReceivePacketNum + 1, SSU2_MAX_NUM_ACNT);
numRanges++;
}
}
}
m_NumRanges = numRanges;
}
if (m_NumRanges)
memcpy (buf + 8, m_Ranges, m_NumRanges*2);
}
}
buf[7] = (uint8_t)acnt; // acnt
htobe16buf (buf + 1, 5 + numRanges*2);
return 8 + numRanges*2;
htobe16buf (buf + 1, 5 + m_NumRanges*2);
return 8 + m_NumRanges*2;
}

size_t SSU2Session::CreatePaddingBlock (uint8_t * buf, size_t len, size_t minSize)
Expand Down Expand Up @@ -2961,11 +2971,17 @@ namespace transport
}
m_OutOfSequencePackets.erase (m_OutOfSequencePackets.begin (), it);
}
m_NumRanges = 0; // recalculate ranges when create next Ack
}
m_ReceivePacketNum = packetNum;
}
else
{
if (m_NumRanges && (m_OutOfSequencePackets.empty () ||
packetNum != (*m_OutOfSequencePackets.rbegin ()) + 1))
m_NumRanges = 0; // reset ranges if received packet is not next
m_OutOfSequencePackets.insert (packetNum);
}
return true;
}

Expand Down
Loading

0 comments on commit c023051

Please sign in to comment.