diff options
Diffstat (limited to 'linden/indra/llmessage/lltransfermanager.cpp')
-rw-r--r-- | linden/indra/llmessage/lltransfermanager.cpp | 85 |
1 files changed, 50 insertions, 35 deletions
diff --git a/linden/indra/llmessage/lltransfermanager.cpp b/linden/indra/llmessage/lltransfermanager.cpp index 78c8c50..6fbb4f9 100644 --- a/linden/indra/llmessage/lltransfermanager.cpp +++ b/linden/indra/llmessage/lltransfermanager.cpp | |||
@@ -13,12 +13,12 @@ | |||
13 | * ("GPL"), unless you have obtained a separate licensing agreement | 13 | * ("GPL"), unless you have obtained a separate licensing agreement |
14 | * ("Other License"), formally executed by you and Linden Lab. Terms of | 14 | * ("Other License"), formally executed by you and Linden Lab. Terms of |
15 | * the GPL can be found in doc/GPL-license.txt in this distribution, or | 15 | * the GPL can be found in doc/GPL-license.txt in this distribution, or |
16 | * online at http://secondlife.com/developers/opensource/gplv2 | 16 | * online at http://secondlifegrid.net/programs/open_source/licensing/gplv2 |
17 | * | 17 | * |
18 | * There are special exceptions to the terms and conditions of the GPL as | 18 | * There are special exceptions to the terms and conditions of the GPL as |
19 | * it is applied to this Source Code. View the full text of the exception | 19 | * it is applied to this Source Code. View the full text of the exception |
20 | * in the file doc/FLOSS-exception.txt in this software distribution, or | 20 | * in the file doc/FLOSS-exception.txt in this software distribution, or |
21 | * online at http://secondlife.com/developers/opensource/flossexception | 21 | * online at http://secondlifegrid.net/programs/open_source/licensing/flossexception |
22 | * | 22 | * |
23 | * By copying, modifying or distributing this software, you acknowledge | 23 | * By copying, modifying or distributing this software, you acknowledge |
24 | * that you have read and understood your obligations described above, | 24 | * that you have read and understood your obligations described above, |
@@ -106,10 +106,15 @@ void LLTransferManager::cleanup() | |||
106 | 106 | ||
107 | void LLTransferManager::updateTransfers() | 107 | void LLTransferManager::updateTransfers() |
108 | { | 108 | { |
109 | host_tc_map::iterator iter; | 109 | host_tc_map::iterator iter,cur; |
110 | for (iter = mTransferConnections.begin(); iter != mTransferConnections.end(); iter++) | 110 | |
111 | iter = mTransferConnections.begin(); | ||
112 | |||
113 | while (iter !=mTransferConnections.end()) | ||
111 | { | 114 | { |
112 | iter->second->updateTransfers(); | 115 | cur = iter; |
116 | iter++; | ||
117 | cur->second->updateTransfers(); | ||
113 | } | 118 | } |
114 | } | 119 | } |
115 | 120 | ||
@@ -571,7 +576,6 @@ void LLTransferManager::processTransferAbort(LLMessageSystem *msgp, void **) | |||
571 | msgp->getUUID("TransferInfo", "TransferID", transfer_id); | 576 | msgp->getUUID("TransferInfo", "TransferID", transfer_id); |
572 | msgp->getS32("TransferInfo", "ChannelType", (S32 &)channel_type); | 577 | msgp->getS32("TransferInfo", "ChannelType", (S32 &)channel_type); |
573 | 578 | ||
574 | |||
575 | // See if it's a target that we're trying to abort | 579 | // See if it's a target that we're trying to abort |
576 | // Find the transfer associated with this packet. | 580 | // Find the transfer associated with this packet. |
577 | LLTransferTargetChannel *ttcp = gTransferManager.getTargetChannel(msgp->getSender(), channel_type); | 581 | LLTransferTargetChannel *ttcp = gTransferManager.getTargetChannel(msgp->getSender(), channel_type); |
@@ -651,10 +655,14 @@ LLTransferConnection::~LLTransferConnection() | |||
651 | void LLTransferConnection::updateTransfers() | 655 | void LLTransferConnection::updateTransfers() |
652 | { | 656 | { |
653 | // Do stuff for source transfers (basically, send data out). | 657 | // Do stuff for source transfers (basically, send data out). |
654 | tsc_iter iter; | 658 | tsc_iter iter, cur; |
655 | for (iter = mTransferSourceChannels.begin(); iter != mTransferSourceChannels.end(); iter++) | 659 | iter = mTransferSourceChannels.begin(); |
660 | |||
661 | while (iter !=mTransferSourceChannels.end()) | ||
656 | { | 662 | { |
657 | (*iter)->updateTransfers(); | 663 | cur = iter; |
664 | iter++; | ||
665 | (*cur)->updateTransfers(); | ||
658 | } | 666 | } |
659 | 667 | ||
660 | // Do stuff for target transfers | 668 | // Do stuff for target transfers |
@@ -768,14 +776,16 @@ void LLTransferSourceChannel::updateTransfers() | |||
768 | return; | 776 | return; |
769 | } | 777 | } |
770 | 778 | ||
771 | LLPriQueueMap<LLTransferSource *>::pqm_iter iter; | 779 | LLPriQueueMap<LLTransferSource *>::pqm_iter iter, next; |
772 | |||
773 | 780 | ||
774 | BOOL done = FALSE; | 781 | BOOL done = FALSE; |
775 | for (iter = mTransferSources.mMap.begin(); (iter != mTransferSources.mMap.end()) && !done;) | 782 | for (iter = mTransferSources.mMap.begin(); (iter != mTransferSources.mMap.end()) && !done;) |
776 | { | 783 | { |
777 | //llinfos << "LLTransferSourceChannel::updateTransfers()" << llendl; | 784 | //llinfos << "LLTransferSourceChannel::updateTransfers()" << llendl; |
778 | // Do stuff. | 785 | // Do stuff. |
786 | next = iter; | ||
787 | next++; | ||
788 | |||
779 | LLTransferSource *tsp = iter->second; | 789 | LLTransferSource *tsp = iter->second; |
780 | U8 *datap = NULL; | 790 | U8 *datap = NULL; |
781 | S32 data_size = 0; | 791 | S32 data_size = 0; |
@@ -793,11 +803,12 @@ void LLTransferSourceChannel::updateTransfers() | |||
793 | // We don't have any data, but we're not done, just go on. | 803 | // We don't have any data, but we're not done, just go on. |
794 | // This will presumably be used for streaming or async transfers that | 804 | // This will presumably be used for streaming or async transfers that |
795 | // are stalled waiting for data from another source. | 805 | // are stalled waiting for data from another source. |
796 | iter++; | 806 | iter=next; |
797 | continue; | 807 | continue; |
798 | } | 808 | } |
799 | 809 | ||
800 | LLUUID *cb_uuid = new LLUUID(tsp->getID()); | 810 | LLUUID *cb_uuid = new LLUUID(tsp->getID()); |
811 | LLUUID transaction_id = tsp->getID(); | ||
801 | 812 | ||
802 | // Send the data now, even if it's an error. | 813 | // Send the data now, even if it's an error. |
803 | // The status code will tell the other end what to do. | 814 | // The status code will tell the other end what to do. |
@@ -822,7 +833,17 @@ void LLTransferSourceChannel::updateTransfers() | |||
822 | delete[] datap; | 833 | delete[] datap; |
823 | datap = NULL; | 834 | datap = NULL; |
824 | } | 835 | } |
825 | 836 | ||
837 | if (findTransferSource(transaction_id) == NULL) | ||
838 | { | ||
839 | //Warning! In the case of an aborted transfer, the sendReliable call above calls | ||
840 | //AbortTransfer which in turn calls deleteTransfer which means that somewhere way | ||
841 | //down the chain our current iter can get invalidated resulting in an infrequent | ||
842 | //sim crash. This check gets us to a valid transfer source in this event. | ||
843 | iter=next; | ||
844 | continue; | ||
845 | } | ||
846 | |||
826 | // Update the packet counter | 847 | // Update the packet counter |
827 | tsp->setLastPacketID(packet_id); | 848 | tsp->setLastPacketID(packet_id); |
828 | 849 | ||
@@ -839,7 +860,8 @@ void LLTransferSourceChannel::updateTransfers() | |||
839 | tsp->completionCallback(status); | 860 | tsp->completionCallback(status); |
840 | delete tsp; | 861 | delete tsp; |
841 | 862 | ||
842 | mTransferSources.mMap.erase(iter++); | 863 | mTransferSources.mMap.erase(iter); |
864 | iter = next; | ||
843 | break; | 865 | break; |
844 | default: | 866 | default: |
845 | llerrs << "Unknown transfer error code!" << llendl; | 867 | llerrs << "Unknown transfer error code!" << llendl; |
@@ -876,23 +898,20 @@ LLTransferSource *LLTransferSourceChannel::findTransferSource(const LLUUID &tran | |||
876 | 898 | ||
877 | BOOL LLTransferSourceChannel::deleteTransfer(LLTransferSource *tsp) | 899 | BOOL LLTransferSourceChannel::deleteTransfer(LLTransferSource *tsp) |
878 | { | 900 | { |
901 | |||
879 | LLPriQueueMap<LLTransferSource *>::pqm_iter iter; | 902 | LLPriQueueMap<LLTransferSource *>::pqm_iter iter; |
880 | for (iter = mTransferSources.mMap.begin(); iter != mTransferSources.mMap.end(); iter++) | 903 | for (iter = mTransferSources.mMap.begin(); iter != mTransferSources.mMap.end(); iter++) |
881 | { | 904 | { |
882 | if (iter->second == tsp) | 905 | if (iter->second == tsp) |
883 | { | 906 | { |
884 | break; | 907 | delete tsp; |
908 | mTransferSources.mMap.erase(iter); | ||
909 | return TRUE; | ||
885 | } | 910 | } |
886 | } | 911 | } |
887 | 912 | ||
888 | if (iter == mTransferSources.mMap.end()) | 913 | llerrs << "Unable to find transfer source to delete!" << llendl; |
889 | { | 914 | return FALSE; |
890 | llerrs << "Unable to find transfer source to delete!" << llendl; | ||
891 | return FALSE; | ||
892 | } | ||
893 | mTransferSources.mMap.erase(iter); | ||
894 | delete tsp; | ||
895 | return TRUE; | ||
896 | } | 915 | } |
897 | 916 | ||
898 | 917 | ||
@@ -1000,18 +1019,14 @@ BOOL LLTransferTargetChannel::deleteTransfer(LLTransferTarget *ttp) | |||
1000 | { | 1019 | { |
1001 | if (*iter == ttp) | 1020 | if (*iter == ttp) |
1002 | { | 1021 | { |
1003 | break; | 1022 | delete ttp; |
1023 | mTransferTargets.erase(iter); | ||
1024 | return TRUE; | ||
1004 | } | 1025 | } |
1005 | } | 1026 | } |
1006 | 1027 | ||
1007 | if (iter == mTransferTargets.end()) | 1028 | llerrs << "Unable to find transfer target to delete!" << llendl; |
1008 | { | 1029 | return FALSE; |
1009 | llerrs << "Unable to find transfer target to delete!" << llendl; | ||
1010 | return FALSE; | ||
1011 | } | ||
1012 | mTransferTargets.erase(iter); | ||
1013 | delete ttp; | ||
1014 | return TRUE; | ||
1015 | } | 1030 | } |
1016 | 1031 | ||
1017 | 1032 | ||
@@ -1072,7 +1087,7 @@ void LLTransferSource::sendTransferStatus(LLTSCode status) | |||
1072 | void LLTransferSource::abortTransfer() | 1087 | void LLTransferSource::abortTransfer() |
1073 | { | 1088 | { |
1074 | // Send a message down, call the completion callback | 1089 | // Send a message down, call the completion callback |
1075 | llinfos << "Aborting transfer " << getID() << " to " << mChannelp->getHost() << llendl; | 1090 | llinfos << "LLTransferSource::Aborting transfer " << getID() << " to " << mChannelp->getHost() << llendl; |
1076 | gMessageSystem->newMessage("TransferAbort"); | 1091 | gMessageSystem->newMessage("TransferAbort"); |
1077 | gMessageSystem->nextBlock("TransferInfo"); | 1092 | gMessageSystem->nextBlock("TransferInfo"); |
1078 | gMessageSystem->addUUID("TransferID", getID()); | 1093 | gMessageSystem->addUUID("TransferID", getID()); |
@@ -1204,7 +1219,7 @@ LLTransferTarget::~LLTransferTarget() | |||
1204 | void LLTransferTarget::abortTransfer() | 1219 | void LLTransferTarget::abortTransfer() |
1205 | { | 1220 | { |
1206 | // Send a message up, call the completion callback | 1221 | // Send a message up, call the completion callback |
1207 | llinfos << "Aborting transfer " << getID() << " from " << mChannelp->getHost() << llendl; | 1222 | llinfos << "LLTransferTarget::Aborting transfer " << getID() << " from " << mChannelp->getHost() << llendl; |
1208 | gMessageSystem->newMessage("TransferAbort"); | 1223 | gMessageSystem->newMessage("TransferAbort"); |
1209 | gMessageSystem->nextBlock("TransferInfo"); | 1224 | gMessageSystem->nextBlock("TransferInfo"); |
1210 | gMessageSystem->addUUID("TransferID", getID()); | 1225 | gMessageSystem->addUUID("TransferID", getID()); |