diff --git a/indra/newview/llagentwearables.cpp b/indra/newview/llagentwearables.cpp
index 6b2033fc6f93409211e230c1dab3104fd4e77656..e78ea88b94ff65f14d0a654d6e109fad15ca5621 100644
--- a/indra/newview/llagentwearables.cpp
+++ b/indra/newview/llagentwearables.cpp
@@ -2196,11 +2196,48 @@ void LLInitialWearablesFetch::processContents()
 	delete this;
 }
 
+class LLFetchAndLinkObserver: public LLInventoryFetchObserver
+{
+public:
+	LLFetchAndLinkObserver(LLInventoryFetchObserver::item_ref_t& ids):
+		m_ids(ids)
+	{
+		llwarns << "LLFetchAndLinkObserver" << llendl;
+	}
+	~LLFetchAndLinkObserver()
+	{
+		llwarns << "~LLFetchAndLinkObserver" << llendl;
+	}
+	virtual void done()
+	{
+		gInventory.removeObserver(this);
+		// Link to all fetched items in COF.
+		for (LLInventoryFetchObserver::item_ref_t::iterator it = m_ids.begin();
+			 it != m_ids.end();
+			 ++it)
+		{
+			LLUUID id = *it;
+			LLViewerInventoryItem *item = gInventory.getItem(*it);
+			if (!item)
+			{
+				llwarns << "LLFetchAndLinkObserver fetch failed!" << llendl;
+				continue;
+			}
+			link_inventory_item(gAgent.getID(), item->getLinkedUUID(), LLAppearanceManager::instance().getCOF(), item->getName(),
+								LLAssetType::AT_LINK, LLPointer<LLInventoryCallback>(NULL));
+		}
+
+	}
+private:
+	LLInventoryFetchObserver::item_ref_t m_ids;
+};
+
 void LLInitialWearablesFetch::processWearablesMessage()
 {
 	if (!mAgentInitialWearables.empty()) // We have an empty current outfit folder, use the message data instead.
 	{
-		const LLUUID current_outfit_id = gInventory.findCategoryUUIDForType(LLFolderType::FT_CURRENT_OUTFIT);
+		const LLUUID current_outfit_id = LLAppearanceManager::instance().getCOF();
+		LLInventoryFetchObserver::item_ref_t ids;
 		for (U8 i = 0; i < mAgentInitialWearables.size(); ++i)
 		{
 			// Populate the current outfit folder with links to the wearables passed in the message
@@ -2209,9 +2246,7 @@ void LLInitialWearablesFetch::processWearablesMessage()
 			if (wearable_data->mAssetID.notNull())
 			{
 #ifdef USE_CURRENT_OUTFIT_FOLDER
-				const std::string link_name = "WearableLink"; // Unimportant what this is named, it isn't exposed.
-				link_inventory_item(gAgent.getID(), wearable_data->mItemID, current_outfit_id, link_name,
-									LLAssetType::AT_LINK, LLPointer<LLInventoryCallback>(NULL));
+				ids.push_back(wearable_data->mItemID);
 #endif
 				// Fetch the wearables
 				LLWearableList::instance().getAsset(wearable_data->mAssetID,
@@ -2225,6 +2260,20 @@ void LLInitialWearablesFetch::processWearablesMessage()
 				<< wearable_data->mItemID << " assetID " << wearable_data->mAssetID << llendl;
 			}
 		}
+
+		// Need to fetch the inventory items for ids, then create links to them after they arrive.
+		LLFetchAndLinkObserver *fetcher = new LLFetchAndLinkObserver(ids);
+		fetcher->fetchItems(ids);
+		// If no items to be fetched, done will never be triggered.
+		// TODO: Change LLInventoryFetchObserver::fetchItems to trigger done() on this condition.
+		if (fetcher->isEverythingComplete())
+		{
+			fetcher->done();
+		}
+		else
+		{
+			gInventory.addObserver(fetcher);
+		}
 	}
 	else
 	{
diff --git a/indra/newview/llinventoryobserver.cpp b/indra/newview/llinventoryobserver.cpp
index 3ccf593d278a7fb10c7f5b8d62639aed9823e7e8..e904fb6c9210faafa299eb39b5d8e502c52b3f15 100644
--- a/indra/newview/llinventoryobserver.cpp
+++ b/indra/newview/llinventoryobserver.cpp
@@ -115,7 +115,8 @@ void LLInventoryFetchObserver::changed(U32 mask)
 				// BUG: This can cause done() to get called prematurely below.
 				// This happens with the LLGestureInventoryFetchObserver that
 				// loads gestures at startup. JC
-				it = mIncomplete.erase(it);
+				//it = mIncomplete.erase(it);
+				++it;
 				continue;
 			}
 			if(item->isComplete())