summaryrefslogtreecommitdiff
path: root/indra/llmessage
diff options
context:
space:
mode:
authorDon Kjer <don@lindenlab.com>2007-12-05 23:43:56 +0000
committerDon Kjer <don@lindenlab.com>2007-12-05 23:43:56 +0000
commitfacf67ae3226105910c983a8fa8760414bf703e9 (patch)
treeb5f7cd6b79a79f769080a65b6fe2cb6b97c8b6fb /indra/llmessage
parent45057e8881c3166c7c0ef545c02bc177922af6fb (diff)
EFFECTIVE MERGE: svn merge -r 71520:73420 svn+ssh://svn/svn/linden/branches/maintenance-3 into release
ACTUAL MERGE: svn merge -r 75074:75114 svn+ssh://svn/svn/linden/qa/maintenance-3-merge-75067 into release
Diffstat (limited to 'indra/llmessage')
-rw-r--r--indra/llmessage/lltransfermanager.cpp81
1 files changed, 48 insertions, 33 deletions
diff --git a/indra/llmessage/lltransfermanager.cpp b/indra/llmessage/lltransfermanager.cpp
index e80bc8cce8..ff4f8a2e66 100644
--- a/indra/llmessage/lltransfermanager.cpp
+++ b/indra/llmessage/lltransfermanager.cpp
@@ -106,10 +106,15 @@ void LLTransferManager::cleanup()
void LLTransferManager::updateTransfers()
{
- host_tc_map::iterator iter;
- for (iter = mTransferConnections.begin(); iter != mTransferConnections.end(); iter++)
+ host_tc_map::iterator iter,cur;
+
+ iter = mTransferConnections.begin();
+
+ while (iter !=mTransferConnections.end())
{
- iter->second->updateTransfers();
+ cur = iter;
+ iter++;
+ cur->second->updateTransfers();
}
}
@@ -571,7 +576,6 @@ void LLTransferManager::processTransferAbort(LLMessageSystem *msgp, void **)
msgp->getUUID("TransferInfo", "TransferID", transfer_id);
msgp->getS32("TransferInfo", "ChannelType", (S32 &)channel_type);
-
// See if it's a target that we're trying to abort
// Find the transfer associated with this packet.
LLTransferTargetChannel *ttcp = gTransferManager.getTargetChannel(msgp->getSender(), channel_type);
@@ -651,10 +655,14 @@ LLTransferConnection::~LLTransferConnection()
void LLTransferConnection::updateTransfers()
{
// Do stuff for source transfers (basically, send data out).
- tsc_iter iter;
- for (iter = mTransferSourceChannels.begin(); iter != mTransferSourceChannels.end(); iter++)
+ tsc_iter iter, cur;
+ iter = mTransferSourceChannels.begin();
+
+ while (iter !=mTransferSourceChannels.end())
{
- (*iter)->updateTransfers();
+ cur = iter;
+ iter++;
+ (*cur)->updateTransfers();
}
// Do stuff for target transfers
@@ -768,14 +776,16 @@ void LLTransferSourceChannel::updateTransfers()
return;
}
- LLPriQueueMap<LLTransferSource *>::pqm_iter iter;
-
+ LLPriQueueMap<LLTransferSource *>::pqm_iter iter, next;
BOOL done = FALSE;
for (iter = mTransferSources.mMap.begin(); (iter != mTransferSources.mMap.end()) && !done;)
{
//llinfos << "LLTransferSourceChannel::updateTransfers()" << llendl;
- // Do stuff.
+ // Do stuff.
+ next = iter;
+ next++;
+
LLTransferSource *tsp = iter->second;
U8 *datap = NULL;
S32 data_size = 0;
@@ -793,11 +803,12 @@ void LLTransferSourceChannel::updateTransfers()
// We don't have any data, but we're not done, just go on.
// This will presumably be used for streaming or async transfers that
// are stalled waiting for data from another source.
- iter++;
+ iter=next;
continue;
}
LLUUID *cb_uuid = new LLUUID(tsp->getID());
+ LLUUID transaction_id = tsp->getID();
// Send the data now, even if it's an error.
// The status code will tell the other end what to do.
@@ -822,7 +833,17 @@ void LLTransferSourceChannel::updateTransfers()
delete[] datap;
datap = NULL;
}
-
+
+ if (findTransferSource(transaction_id) == NULL)
+ {
+ //Warning! In the case of an aborted transfer, the sendReliable call above calls
+ //AbortTransfer which in turn calls deleteTransfer which means that somewhere way
+ //down the chain our current iter can get invalidated resulting in an infrequent
+ //sim crash. This check gets us to a valid transfer source in this event.
+ iter=next;
+ continue;
+ }
+
// Update the packet counter
tsp->setLastPacketID(packet_id);
@@ -839,7 +860,8 @@ void LLTransferSourceChannel::updateTransfers()
tsp->completionCallback(status);
delete tsp;
- mTransferSources.mMap.erase(iter++);
+ mTransferSources.mMap.erase(iter);
+ iter = next;
break;
default:
llerrs << "Unknown transfer error code!" << llendl;
@@ -876,23 +898,20 @@ LLTransferSource *LLTransferSourceChannel::findTransferSource(const LLUUID &tran
BOOL LLTransferSourceChannel::deleteTransfer(LLTransferSource *tsp)
{
+
LLPriQueueMap<LLTransferSource *>::pqm_iter iter;
for (iter = mTransferSources.mMap.begin(); iter != mTransferSources.mMap.end(); iter++)
{
if (iter->second == tsp)
{
- break;
+ delete tsp;
+ mTransferSources.mMap.erase(iter);
+ return TRUE;
}
}
- if (iter == mTransferSources.mMap.end())
- {
- llerrs << "Unable to find transfer source to delete!" << llendl;
- return FALSE;
- }
- mTransferSources.mMap.erase(iter);
- delete tsp;
- return TRUE;
+ llerrs << "Unable to find transfer source to delete!" << llendl;
+ return FALSE;
}
@@ -1000,18 +1019,14 @@ BOOL LLTransferTargetChannel::deleteTransfer(LLTransferTarget *ttp)
{
if (*iter == ttp)
{
- break;
+ delete ttp;
+ mTransferTargets.erase(iter);
+ return TRUE;
}
}
- if (iter == mTransferTargets.end())
- {
- llerrs << "Unable to find transfer target to delete!" << llendl;
- return FALSE;
- }
- mTransferTargets.erase(iter);
- delete ttp;
- return TRUE;
+ llerrs << "Unable to find transfer target to delete!" << llendl;
+ return FALSE;
}
@@ -1072,7 +1087,7 @@ void LLTransferSource::sendTransferStatus(LLTSCode status)
void LLTransferSource::abortTransfer()
{
// Send a message down, call the completion callback
- llinfos << "Aborting transfer " << getID() << " to " << mChannelp->getHost() << llendl;
+ llinfos << "LLTransferSource::Aborting transfer " << getID() << " to " << mChannelp->getHost() << llendl;
gMessageSystem->newMessage("TransferAbort");
gMessageSystem->nextBlock("TransferInfo");
gMessageSystem->addUUID("TransferID", getID());
@@ -1204,7 +1219,7 @@ LLTransferTarget::~LLTransferTarget()
void LLTransferTarget::abortTransfer()
{
// Send a message up, call the completion callback
- llinfos << "Aborting transfer " << getID() << " from " << mChannelp->getHost() << llendl;
+ llinfos << "LLTransferTarget::Aborting transfer " << getID() << " from " << mChannelp->getHost() << llendl;
gMessageSystem->newMessage("TransferAbort");
gMessageSystem->nextBlock("TransferInfo");
gMessageSystem->addUUID("TransferID", getID());