Merge branch 'master' of ssh://opensimulator.org/var/git/opensim
commit
7d2cd0d935
|
@ -57,39 +57,36 @@ namespace OpenSim.Region.CoreModules.Agent.AssetTransaction
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Return a xfer uploader if one does not already exist.
|
/// Return the xfer uploader for the given transaction.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// If an uploader does not already exist for this transaction then it is created, otherwise the existing
|
||||||
|
/// uploader is returned.
|
||||||
|
/// </remarks>
|
||||||
/// <param name="transactionID"></param>
|
/// <param name="transactionID"></param>
|
||||||
/// <param name="assetID">
|
/// <returns>The asset xfer uploader</returns>
|
||||||
/// We must transfer the new asset ID into the uploader on creation, otherwise
|
public AssetXferUploader RequestXferUploader(UUID transactionID)
|
||||||
/// we can see race conditions with other threads which can retrieve an item before it is updated with the new
|
|
||||||
/// asset id.
|
|
||||||
/// </param>
|
|
||||||
/// <returns>
|
|
||||||
/// The xfer uploader requested. Null if one is already in existence.
|
|
||||||
/// FIXME: This is a bizarre thing to do, and is probably meant to signal an error condition if multiple
|
|
||||||
/// transfers are made. Needs to be corrected.
|
|
||||||
/// </returns>
|
|
||||||
public AssetXferUploader RequestXferUploader(UUID transactionID, UUID assetID)
|
|
||||||
{
|
{
|
||||||
|
AssetXferUploader uploader;
|
||||||
|
|
||||||
lock (XferUploaders)
|
lock (XferUploaders)
|
||||||
{
|
{
|
||||||
if (!XferUploaders.ContainsKey(transactionID))
|
if (!XferUploaders.ContainsKey(transactionID))
|
||||||
{
|
{
|
||||||
AssetXferUploader uploader = new AssetXferUploader(this, m_Scene, assetID, m_dumpAssetsToFile);
|
uploader = new AssetXferUploader(this, m_Scene, transactionID, m_dumpAssetsToFile);
|
||||||
|
|
||||||
// m_log.DebugFormat(
|
// m_log.DebugFormat(
|
||||||
// "[AGENT ASSETS TRANSACTIONS]: Adding asset xfer uploader {0} since it didn't previously exist", transactionID);
|
// "[AGENT ASSETS TRANSACTIONS]: Adding asset xfer uploader {0} since it didn't previously exist", transactionID);
|
||||||
|
|
||||||
XferUploaders.Add(transactionID, uploader);
|
XferUploaders.Add(transactionID, uploader);
|
||||||
|
}
|
||||||
return uploader;
|
else
|
||||||
|
{
|
||||||
|
uploader = XferUploaders[transactionID];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
m_log.WarnFormat("[AGENT ASSETS TRANSACTIONS]: Ignoring request for asset xfer uploader {0} since it already exists", transactionID);
|
return uploader;
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public void HandleXfer(ulong xferID, uint packetID, byte[] data)
|
public void HandleXfer(ulong xferID, uint packetID, byte[] data)
|
||||||
|
@ -151,115 +148,28 @@ namespace OpenSim.Region.CoreModules.Agent.AssetTransaction
|
||||||
string description, string name, sbyte invType,
|
string description, string name, sbyte invType,
|
||||||
sbyte type, byte wearableType, uint nextOwnerMask)
|
sbyte type, byte wearableType, uint nextOwnerMask)
|
||||||
{
|
{
|
||||||
AssetXferUploader uploader = null;
|
AssetXferUploader uploader = RequestXferUploader(transactionID);
|
||||||
|
|
||||||
lock (XferUploaders)
|
uploader.RequestCreateInventoryItem(
|
||||||
{
|
remoteClient, folderID, callbackID,
|
||||||
if (XferUploaders.ContainsKey(transactionID))
|
description, name, invType, type, wearableType, nextOwnerMask);
|
||||||
uploader = XferUploaders[transactionID];
|
|
||||||
}
|
|
||||||
|
|
||||||
if (uploader != null)
|
|
||||||
uploader.RequestCreateInventoryItem(
|
|
||||||
remoteClient, transactionID, folderID,
|
|
||||||
callbackID, description, name, invType, type,
|
|
||||||
wearableType, nextOwnerMask);
|
|
||||||
else
|
|
||||||
m_log.ErrorFormat(
|
|
||||||
"[AGENT ASSET TRANSACTIONS]: Could not find uploader with transaction ID {0} when handling request to create inventory item {1} from {2}",
|
|
||||||
transactionID, name, remoteClient.Name);
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Get an uploaded asset. If the data is successfully retrieved,
|
|
||||||
/// the transaction will be removed.
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="transactionID"></param>
|
|
||||||
/// <returns>The asset if the upload has completed, null if it has not.</returns>
|
|
||||||
private AssetBase GetTransactionAsset(UUID transactionID)
|
|
||||||
{
|
|
||||||
lock (XferUploaders)
|
|
||||||
{
|
|
||||||
if (XferUploaders.ContainsKey(transactionID))
|
|
||||||
{
|
|
||||||
AssetXferUploader uploader = XferUploaders[transactionID];
|
|
||||||
AssetBase asset = uploader.GetAssetData();
|
|
||||||
RemoveXferUploader(transactionID);
|
|
||||||
|
|
||||||
return asset;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public void RequestUpdateTaskInventoryItem(IClientAPI remoteClient,
|
public void RequestUpdateTaskInventoryItem(IClientAPI remoteClient,
|
||||||
SceneObjectPart part, UUID transactionID,
|
SceneObjectPart part, UUID transactionID,
|
||||||
TaskInventoryItem item)
|
TaskInventoryItem item)
|
||||||
{
|
{
|
||||||
AssetXferUploader uploader = null;
|
AssetXferUploader uploader = RequestXferUploader(transactionID);
|
||||||
|
|
||||||
lock (XferUploaders)
|
uploader.RequestUpdateTaskInventoryItem(remoteClient, item);
|
||||||
{
|
|
||||||
if (XferUploaders.ContainsKey(transactionID))
|
|
||||||
uploader = XferUploaders[transactionID];
|
|
||||||
}
|
|
||||||
|
|
||||||
if (uploader != null)
|
|
||||||
{
|
|
||||||
AssetBase asset = GetTransactionAsset(transactionID);
|
|
||||||
|
|
||||||
// Only legacy viewers use this, and they prefer CAPS, which
|
|
||||||
// we have, so this really never runs.
|
|
||||||
// Allow it, but only for "safe" types.
|
|
||||||
if ((InventoryType)item.InvType != InventoryType.Notecard &&
|
|
||||||
(InventoryType)item.InvType != InventoryType.LSL)
|
|
||||||
return;
|
|
||||||
|
|
||||||
if (asset != null)
|
|
||||||
{
|
|
||||||
// m_log.DebugFormat(
|
|
||||||
// "[AGENT ASSETS TRANSACTIONS]: Updating item {0} in {1} for transaction {2}",
|
|
||||||
// item.Name, part.Name, transactionID);
|
|
||||||
|
|
||||||
asset.FullID = UUID.Random();
|
|
||||||
asset.Name = item.Name;
|
|
||||||
asset.Description = item.Description;
|
|
||||||
asset.Type = (sbyte)item.Type;
|
|
||||||
item.AssetID = asset.FullID;
|
|
||||||
|
|
||||||
m_Scene.AssetService.Store(asset);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
m_log.ErrorFormat(
|
|
||||||
"[AGENT ASSET TRANSACTIONS]: Could not find uploader with transaction ID {0} when handling request to update task inventory item {1} in {2}",
|
|
||||||
transactionID, item.Name, part.Name);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public void RequestUpdateInventoryItem(IClientAPI remoteClient,
|
public void RequestUpdateInventoryItem(IClientAPI remoteClient,
|
||||||
UUID transactionID, InventoryItemBase item)
|
UUID transactionID, InventoryItemBase item)
|
||||||
{
|
{
|
||||||
AssetXferUploader uploader = null;
|
AssetXferUploader uploader = RequestXferUploader(transactionID);
|
||||||
|
|
||||||
lock (XferUploaders)
|
uploader.RequestUpdateInventoryItem(remoteClient, item);
|
||||||
{
|
|
||||||
if (XferUploaders.ContainsKey(transactionID))
|
|
||||||
uploader = XferUploaders[transactionID];
|
|
||||||
}
|
|
||||||
|
|
||||||
if (uploader != null)
|
|
||||||
{
|
|
||||||
uploader.RequestUpdateInventoryItem(remoteClient, transactionID, item);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
m_log.ErrorFormat(
|
|
||||||
"[AGENT ASSET TRANSACTIONS]: Could not find uploader with transaction ID {0} when handling request to update inventory item {1} for {2}",
|
|
||||||
transactionID, item.Name, remoteClient.Name);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -215,7 +215,7 @@ namespace OpenSim.Region.CoreModules.Agent.AssetTransaction
|
||||||
IClientAPI remoteClient, SceneObjectPart part, UUID transactionID, TaskInventoryItem item)
|
IClientAPI remoteClient, SceneObjectPart part, UUID transactionID, TaskInventoryItem item)
|
||||||
{
|
{
|
||||||
m_log.DebugFormat(
|
m_log.DebugFormat(
|
||||||
"[TRANSACTIONS MANAGER] Called HandleTaskItemUpdateFromTransaction with item {0} in {1} for {2} in {3}",
|
"[ASSET TRANSACTION MODULE] Called HandleTaskItemUpdateFromTransaction with item {0} in {1} for {2} in {3}",
|
||||||
item.Name, part.Name, remoteClient.Name, m_Scene.RegionInfo.RegionName);
|
item.Name, part.Name, remoteClient.Name, m_Scene.RegionInfo.RegionName);
|
||||||
|
|
||||||
AgentAssetTransactions transactions =
|
AgentAssetTransactions transactions =
|
||||||
|
@ -274,13 +274,8 @@ namespace OpenSim.Region.CoreModules.Agent.AssetTransaction
|
||||||
}
|
}
|
||||||
|
|
||||||
AgentAssetTransactions transactions = GetUserTransactions(remoteClient.AgentId);
|
AgentAssetTransactions transactions = GetUserTransactions(remoteClient.AgentId);
|
||||||
AssetXferUploader uploader = transactions.RequestXferUploader(transaction, assetID);
|
AssetXferUploader uploader = transactions.RequestXferUploader(transaction);
|
||||||
|
uploader.StartUpload(remoteClient, assetID, transaction, type, data, storeLocal, tempFile);
|
||||||
if (uploader != null)
|
|
||||||
{
|
|
||||||
uploader.Initialise(remoteClient, assetID, transaction, type,
|
|
||||||
data, storeLocal, tempFile);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|
|
@ -40,39 +40,75 @@ namespace OpenSim.Region.CoreModules.Agent.AssetTransaction
|
||||||
{
|
{
|
||||||
private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
|
private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Upload state.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// New -> Uploading -> Complete
|
||||||
|
/// </remarks>
|
||||||
|
private enum UploadState
|
||||||
|
{
|
||||||
|
New,
|
||||||
|
Uploading,
|
||||||
|
Complete
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Reference to the object that holds this uploader. Used to remove ourselves from it's list if we
|
/// Reference to the object that holds this uploader. Used to remove ourselves from it's list if we
|
||||||
/// are performing a delayed update.
|
/// are performing a delayed update.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
AgentAssetTransactions m_transactions;
|
AgentAssetTransactions m_transactions;
|
||||||
|
|
||||||
|
private UploadState m_uploadState = UploadState.New;
|
||||||
|
|
||||||
private AssetBase m_asset;
|
private AssetBase m_asset;
|
||||||
private UUID InventFolder = UUID.Zero;
|
private UUID InventFolder = UUID.Zero;
|
||||||
private sbyte invType = 0;
|
private sbyte invType = 0;
|
||||||
|
|
||||||
private bool m_createItem = false;
|
private bool m_createItem;
|
||||||
private uint m_createItemCallback = 0;
|
private uint m_createItemCallback;
|
||||||
private bool m_updateItem = false;
|
|
||||||
|
private bool m_updateItem;
|
||||||
private InventoryItemBase m_updateItemData;
|
private InventoryItemBase m_updateItemData;
|
||||||
|
|
||||||
|
private bool m_updateTaskItem;
|
||||||
|
private TaskInventoryItem m_updateTaskItemData;
|
||||||
|
|
||||||
private string m_description = String.Empty;
|
private string m_description = String.Empty;
|
||||||
private bool m_dumpAssetToFile;
|
private bool m_dumpAssetToFile;
|
||||||
private bool m_finished = false;
|
|
||||||
private string m_name = String.Empty;
|
private string m_name = String.Empty;
|
||||||
private bool m_storeLocal;
|
// private bool m_storeLocal;
|
||||||
private uint nextPerm = 0;
|
private uint nextPerm = 0;
|
||||||
private IClientAPI ourClient;
|
private IClientAPI ourClient;
|
||||||
private UUID TransactionID = UUID.Zero;
|
|
||||||
|
private UUID m_transactionID;
|
||||||
|
|
||||||
private sbyte type = 0;
|
private sbyte type = 0;
|
||||||
private byte wearableType = 0;
|
private byte wearableType = 0;
|
||||||
public ulong XferID;
|
public ulong XferID;
|
||||||
private Scene m_Scene;
|
private Scene m_Scene;
|
||||||
|
|
||||||
public AssetXferUploader(AgentAssetTransactions transactions, Scene scene, UUID assetID, bool dumpAssetToFile)
|
/// <summary>
|
||||||
|
/// AssetXferUploader constructor
|
||||||
|
/// </summary>
|
||||||
|
/// <param name='transactions'>/param>
|
||||||
|
/// <param name='scene'></param>
|
||||||
|
/// <param name='transactionID'></param>
|
||||||
|
/// <param name='dumpAssetToFile'>
|
||||||
|
/// If true then when the asset is uploaded it is dumped to a file with the format
|
||||||
|
/// String.Format("{6}_{7}_{0:d2}{1:d2}{2:d2}_{3:d2}{4:d2}{5:d2}.dat",
|
||||||
|
/// now.Year, now.Month, now.Day, now.Hour, now.Minute,
|
||||||
|
/// now.Second, m_asset.Name, m_asset.Type);
|
||||||
|
/// for debugging purposes.
|
||||||
|
/// </param>
|
||||||
|
public AssetXferUploader(
|
||||||
|
AgentAssetTransactions transactions, Scene scene, UUID transactionID, bool dumpAssetToFile)
|
||||||
{
|
{
|
||||||
|
m_asset = new AssetBase();
|
||||||
|
|
||||||
m_transactions = transactions;
|
m_transactions = transactions;
|
||||||
|
m_transactionID = transactionID;
|
||||||
m_Scene = scene;
|
m_Scene = scene;
|
||||||
m_asset = new AssetBase() { FullID = assetID };
|
|
||||||
m_dumpAssetToFile = dumpAssetToFile;
|
m_dumpAssetToFile = dumpAssetToFile;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -118,30 +154,50 @@ namespace OpenSim.Region.CoreModules.Agent.AssetTransaction
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Initialise asset transfer from the client
|
/// Start asset transfer from the client
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="xferID"></param>
|
/// <param name="remoteClient"></param>
|
||||||
/// <param name="packetID"></param>
|
/// <param name="assetID"></param>
|
||||||
/// <param name="data"></param>
|
/// <param name="transaction"></param>
|
||||||
public void Initialise(IClientAPI remoteClient, UUID assetID,
|
/// <param name="type"></param>
|
||||||
UUID transaction, sbyte type, byte[] data, bool storeLocal,
|
/// <param name="data">
|
||||||
bool tempFile)
|
/// Optional data. If present then the asset is created immediately with this data
|
||||||
|
/// rather than requesting an upload from the client. The data must be longer than 2 bytes.
|
||||||
|
/// </param>
|
||||||
|
/// <param name="storeLocal"></param>
|
||||||
|
/// <param name="tempFile"></param>
|
||||||
|
public void StartUpload(
|
||||||
|
IClientAPI remoteClient, UUID assetID, UUID transaction, sbyte type, byte[] data, bool storeLocal,
|
||||||
|
bool tempFile)
|
||||||
{
|
{
|
||||||
// m_log.DebugFormat(
|
// m_log.DebugFormat(
|
||||||
// "[ASSET XFER UPLOADER]: Initialised xfer from {0}, asset {1}, transaction {2}, type {3}, storeLocal {4}, tempFile {5}, already received data length {6}",
|
// "[ASSET XFER UPLOADER]: Initialised xfer from {0}, asset {1}, transaction {2}, type {3}, storeLocal {4}, tempFile {5}, already received data length {6}",
|
||||||
// remoteClient.Name, assetID, transaction, type, storeLocal, tempFile, data.Length);
|
// remoteClient.Name, assetID, transaction, type, storeLocal, tempFile, data.Length);
|
||||||
|
|
||||||
|
lock (this)
|
||||||
|
{
|
||||||
|
if (m_uploadState != UploadState.New)
|
||||||
|
{
|
||||||
|
m_log.WarnFormat(
|
||||||
|
"[ASSET XFER UPLOADER]: Tried to start upload of asset {0}, transaction {1} for {2} but this is already in state {3}. Aborting.",
|
||||||
|
assetID, transaction, remoteClient.Name, m_uploadState);
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
m_uploadState = UploadState.Uploading;
|
||||||
|
}
|
||||||
|
|
||||||
ourClient = remoteClient;
|
ourClient = remoteClient;
|
||||||
m_asset.Name = "blank";
|
|
||||||
m_asset.Description = "empty";
|
m_asset.FullID = assetID;
|
||||||
m_asset.Type = type;
|
m_asset.Type = type;
|
||||||
m_asset.CreatorID = remoteClient.AgentId.ToString();
|
m_asset.CreatorID = remoteClient.AgentId.ToString();
|
||||||
m_asset.Data = data;
|
m_asset.Data = data;
|
||||||
m_asset.Local = storeLocal;
|
m_asset.Local = storeLocal;
|
||||||
m_asset.Temporary = tempFile;
|
m_asset.Temporary = tempFile;
|
||||||
|
|
||||||
TransactionID = transaction;
|
// m_storeLocal = storeLocal;
|
||||||
m_storeLocal = storeLocal;
|
|
||||||
|
|
||||||
if (m_asset.Data.Length > 2)
|
if (m_asset.Data.Length > 2)
|
||||||
{
|
{
|
||||||
|
@ -166,36 +222,35 @@ namespace OpenSim.Region.CoreModules.Agent.AssetTransaction
|
||||||
|
|
||||||
protected void SendCompleteMessage()
|
protected void SendCompleteMessage()
|
||||||
{
|
{
|
||||||
ourClient.SendAssetUploadCompleteMessage(m_asset.Type, true,
|
|
||||||
m_asset.FullID);
|
|
||||||
|
|
||||||
// We must lock in order to avoid a race with a separate thread dealing with an inventory item or create
|
// We must lock in order to avoid a race with a separate thread dealing with an inventory item or create
|
||||||
// message from other client UDP.
|
// message from other client UDP.
|
||||||
lock (this)
|
lock (this)
|
||||||
{
|
{
|
||||||
m_finished = true;
|
m_uploadState = UploadState.Complete;
|
||||||
|
|
||||||
|
ourClient.SendAssetUploadCompleteMessage(m_asset.Type, true, m_asset.FullID);
|
||||||
|
|
||||||
if (m_createItem)
|
if (m_createItem)
|
||||||
{
|
{
|
||||||
DoCreateItem(m_createItemCallback);
|
CompleteCreateItem(m_createItemCallback);
|
||||||
}
|
}
|
||||||
else if (m_updateItem)
|
else if (m_updateItem)
|
||||||
{
|
{
|
||||||
StoreAssetForItemUpdate(m_updateItemData);
|
CompleteItemUpdate(m_updateItemData);
|
||||||
|
|
||||||
// Remove ourselves from the list of transactions if completion was delayed until the transaction
|
|
||||||
// was complete.
|
|
||||||
// TODO: Should probably do the same for create item.
|
|
||||||
m_transactions.RemoveXferUploader(TransactionID);
|
|
||||||
}
|
}
|
||||||
else if (m_storeLocal)
|
else if (m_updateTaskItem)
|
||||||
{
|
{
|
||||||
m_Scene.AssetService.Store(m_asset);
|
CompleteTaskItemUpdate(m_updateTaskItemData);
|
||||||
}
|
}
|
||||||
|
// else if (m_storeLocal)
|
||||||
|
// {
|
||||||
|
// m_Scene.AssetService.Store(m_asset);
|
||||||
|
// }
|
||||||
}
|
}
|
||||||
|
|
||||||
m_log.DebugFormat(
|
m_log.DebugFormat(
|
||||||
"[ASSET XFER UPLOADER]: Uploaded asset {0} for transaction {1}",
|
"[ASSET XFER UPLOADER]: Uploaded asset {0} for transaction {1}",
|
||||||
m_asset.FullID, TransactionID);
|
m_asset.FullID, m_transactionID);
|
||||||
|
|
||||||
if (m_dumpAssetToFile)
|
if (m_dumpAssetToFile)
|
||||||
{
|
{
|
||||||
|
@ -223,40 +278,37 @@ namespace OpenSim.Region.CoreModules.Agent.AssetTransaction
|
||||||
}
|
}
|
||||||
|
|
||||||
public void RequestCreateInventoryItem(IClientAPI remoteClient,
|
public void RequestCreateInventoryItem(IClientAPI remoteClient,
|
||||||
UUID transactionID, UUID folderID, uint callbackID,
|
UUID folderID, uint callbackID,
|
||||||
string description, string name, sbyte invType,
|
string description, string name, sbyte invType,
|
||||||
sbyte type, byte wearableType, uint nextOwnerMask)
|
sbyte type, byte wearableType, uint nextOwnerMask)
|
||||||
{
|
{
|
||||||
if (TransactionID == transactionID)
|
InventFolder = folderID;
|
||||||
{
|
m_name = name;
|
||||||
InventFolder = folderID;
|
m_description = description;
|
||||||
m_name = name;
|
this.type = type;
|
||||||
m_description = description;
|
this.invType = invType;
|
||||||
this.type = type;
|
this.wearableType = wearableType;
|
||||||
this.invType = invType;
|
nextPerm = nextOwnerMask;
|
||||||
this.wearableType = wearableType;
|
m_asset.Name = name;
|
||||||
nextPerm = nextOwnerMask;
|
m_asset.Description = description;
|
||||||
m_asset.Name = name;
|
m_asset.Type = type;
|
||||||
m_asset.Description = description;
|
|
||||||
m_asset.Type = type;
|
|
||||||
|
|
||||||
// We must lock to avoid a race with a separate thread uploading the asset.
|
// We must lock to avoid a race with a separate thread uploading the asset.
|
||||||
lock (this)
|
lock (this)
|
||||||
|
{
|
||||||
|
if (m_uploadState == UploadState.Complete)
|
||||||
{
|
{
|
||||||
if (m_finished)
|
CompleteCreateItem(callbackID);
|
||||||
{
|
}
|
||||||
DoCreateItem(callbackID);
|
else
|
||||||
}
|
{
|
||||||
else
|
m_createItem = true; //set flag so the inventory item is created when upload is complete
|
||||||
{
|
m_createItemCallback = callbackID;
|
||||||
m_createItem = true; //set flag so the inventory item is created when upload is complete
|
|
||||||
m_createItemCallback = callbackID;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void RequestUpdateInventoryItem(IClientAPI remoteClient, UUID transactionID, InventoryItemBase item)
|
public void RequestUpdateInventoryItem(IClientAPI remoteClient, InventoryItemBase item)
|
||||||
{
|
{
|
||||||
// We must lock to avoid a race with a separate thread uploading the asset.
|
// We must lock to avoid a race with a separate thread uploading the asset.
|
||||||
lock (this)
|
lock (this)
|
||||||
|
@ -271,9 +323,9 @@ namespace OpenSim.Region.CoreModules.Agent.AssetTransaction
|
||||||
item.AssetID = m_asset.FullID;
|
item.AssetID = m_asset.FullID;
|
||||||
m_Scene.InventoryService.UpdateItem(item);
|
m_Scene.InventoryService.UpdateItem(item);
|
||||||
|
|
||||||
if (m_finished)
|
if (m_uploadState == UploadState.Complete)
|
||||||
{
|
{
|
||||||
StoreAssetForItemUpdate(item);
|
CompleteItemUpdate(item);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -287,20 +339,59 @@ namespace OpenSim.Region.CoreModules.Agent.AssetTransaction
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void RequestUpdateTaskInventoryItem(IClientAPI remoteClient, TaskInventoryItem taskItem)
|
||||||
|
{
|
||||||
|
// We must lock to avoid a race with a separate thread uploading the asset.
|
||||||
|
lock (this)
|
||||||
|
{
|
||||||
|
m_asset.Name = taskItem.Name;
|
||||||
|
m_asset.Description = taskItem.Description;
|
||||||
|
m_asset.Type = (sbyte)taskItem.Type;
|
||||||
|
taskItem.AssetID = m_asset.FullID;
|
||||||
|
|
||||||
|
if (m_uploadState == UploadState.Complete)
|
||||||
|
{
|
||||||
|
CompleteTaskItemUpdate(taskItem);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
m_updateTaskItem = true;
|
||||||
|
m_updateTaskItemData = taskItem;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Store the asset for the given item.
|
/// Store the asset for the given item when it has been uploaded.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="item"></param>
|
/// <param name="item"></param>
|
||||||
private void StoreAssetForItemUpdate(InventoryItemBase item)
|
private void CompleteItemUpdate(InventoryItemBase item)
|
||||||
{
|
{
|
||||||
// m_log.DebugFormat(
|
// m_log.DebugFormat(
|
||||||
// "[ASSET XFER UPLOADER]: Storing asset {0} for earlier item update for {1} for {2}",
|
// "[ASSET XFER UPLOADER]: Storing asset {0} for earlier item update for {1} for {2}",
|
||||||
// m_asset.FullID, item.Name, ourClient.Name);
|
// m_asset.FullID, item.Name, ourClient.Name);
|
||||||
|
|
||||||
m_Scene.AssetService.Store(m_asset);
|
m_Scene.AssetService.Store(m_asset);
|
||||||
|
|
||||||
|
m_transactions.RemoveXferUploader(m_transactionID);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void DoCreateItem(uint callbackID)
|
/// <summary>
|
||||||
|
/// Store the asset for the given task item when it has been uploaded.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="taskItem"></param>
|
||||||
|
private void CompleteTaskItemUpdate(TaskInventoryItem taskItem)
|
||||||
|
{
|
||||||
|
// m_log.DebugFormat(
|
||||||
|
// "[ASSET XFER UPLOADER]: Storing asset {0} for earlier task item update for {1} for {2}",
|
||||||
|
// m_asset.FullID, taskItem.Name, ourClient.Name);
|
||||||
|
|
||||||
|
m_Scene.AssetService.Store(m_asset);
|
||||||
|
|
||||||
|
m_transactions.RemoveXferUploader(m_transactionID);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void CompleteCreateItem(uint callbackID)
|
||||||
{
|
{
|
||||||
m_Scene.AssetService.Store(m_asset);
|
m_Scene.AssetService.Store(m_asset);
|
||||||
|
|
||||||
|
@ -326,20 +417,8 @@ namespace OpenSim.Region.CoreModules.Agent.AssetTransaction
|
||||||
ourClient.SendInventoryItemCreateUpdate(item, callbackID);
|
ourClient.SendInventoryItemCreateUpdate(item, callbackID);
|
||||||
else
|
else
|
||||||
ourClient.SendAlertMessage("Unable to create inventory item");
|
ourClient.SendAlertMessage("Unable to create inventory item");
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
m_transactions.RemoveXferUploader(m_transactionID);
|
||||||
/// Get the asset data uploaded in this transfer.
|
|
||||||
/// </summary>
|
|
||||||
/// <returns>null if the asset has not finished uploading</returns>
|
|
||||||
public AssetBase GetAssetData()
|
|
||||||
{
|
|
||||||
if (m_finished)
|
|
||||||
{
|
|
||||||
return m_asset;
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -1,19 +1,23 @@
|
||||||
;; This is the main configuration file for OpenSimulator. If it's named OpenSim.ini
|
;; This is the main configuration file for OpenSimulator.
|
||||||
;; then it will be loaded by OpenSimulator. If it's named OpenSim.ini.example then
|
;; If it's named OpenSim.ini then it will be loaded by OpenSimulator.
|
||||||
;; you will need to copy it to OpenSim.ini first (if that file does not already exist)
|
;; If it's named OpenSim.ini.example then you will need to copy it to
|
||||||
|
;; OpenSim.ini first (if that file does not already exist)
|
||||||
;;
|
;;
|
||||||
;; If you are copying, then once you have copied OpenSim.ini.example to OpenSim.ini you will
|
;; If you are copying, then once you have copied OpenSim.ini.example to
|
||||||
;; need to pick an architecture in the [Architecture] section at the end of this file.
|
;; OpenSim.ini you will need to pick an architecture in the [Architecture]
|
||||||
|
;; section at the end of this file.
|
||||||
;;
|
;;
|
||||||
;; The settings in this file are in the form "<key> = <value>". For example, save_crashes = false
|
;; The settings in this file are in the form "<key> = <value>". For example,
|
||||||
;; in the [Startup] section below.
|
;; save_crashes = false in the [Startup] section below.
|
||||||
;;
|
;;
|
||||||
;; All settings are initially commented out and the default value used, as found in
|
;; All settings are initially commented out and the default value used, as
|
||||||
;; OpenSimDefaults.ini. To change a setting, first uncomment it by deleting the initial semicolon (;)
|
;; found in OpenSimDefaults.ini. To change a setting, first uncomment it by
|
||||||
;; and then change the value. This will override the value in OpenSimDefaults.ini
|
;; deleting the initial semicolon (;) and then change the value. This will
|
||||||
|
;; override the value in OpenSimDefaults.ini
|
||||||
;;
|
;;
|
||||||
;; If you want to find out what configuration OpenSimulator has finished with once all the configuration
|
;; If you want to find out what configuration OpenSimulator has finished with
|
||||||
;; files are loaded then type "config show" on the region console command line.
|
;; once all the configuration files are loaded then type "config show" on the
|
||||||
|
;; region console command line.
|
||||||
;;
|
;;
|
||||||
;;
|
;;
|
||||||
;; NOTES FOR DEVELOPERS REGARDING THE FORMAT OF THIS FILE
|
;; NOTES FOR DEVELOPERS REGARDING THE FORMAT OF THIS FILE
|
||||||
|
@ -26,13 +30,16 @@
|
||||||
;; formatted as:
|
;; formatted as:
|
||||||
;; {option} {depends on} {question to ask} {choices} default value
|
;; {option} {depends on} {question to ask} {choices} default value
|
||||||
;; Any text comments following the declaration, up to the next blank line.
|
;; Any text comments following the declaration, up to the next blank line.
|
||||||
;; will be copied to the generated file (NOTE: generation is not yet implemented)
|
;; will be copied to the generated file (NOTE: generation is not yet
|
||||||
|
;; implemented)
|
||||||
|
;;
|
||||||
;; A * in the choices list will allow an empty entry.
|
;; A * in the choices list will allow an empty entry.
|
||||||
;; An empty question will set the default if the dependencies are
|
;; An empty question will set the default if the dependencies are
|
||||||
;; satisfied.
|
;; satisfied.
|
||||||
;;
|
;;
|
||||||
;; ; denotes a commented out option.
|
;; ; denotes a commented out option.
|
||||||
;; Any options added to OpenSim.ini.example should be initially commented out.
|
;; Any options added to OpenSim.ini.example should be initially commented
|
||||||
|
;; out.
|
||||||
|
|
||||||
|
|
||||||
[Startup]
|
[Startup]
|
||||||
|
@ -47,9 +54,12 @@
|
||||||
;# {save_crashes} {} {Save crashes to disk?} {true false} false
|
;# {save_crashes} {} {Save crashes to disk?} {true false} false
|
||||||
;; Set this to true if you want to log crashes to disk
|
;; Set this to true if you want to log crashes to disk
|
||||||
;; this can be useful when submitting bug reports.
|
;; this can be useful when submitting bug reports.
|
||||||
;; However, this will only log crashes within OpenSimulator that cause the entire program to exit
|
;; However, this will only log crashes within OpenSimulator that cause the
|
||||||
;; It will not log crashes caused by virtual machine failures, which includes mono and ODE failures.
|
;; entire program to exit
|
||||||
;; You will need to capture these native stack traces by recording the session log itself.
|
;; It will not log crashes caused by virtual machine failures, which
|
||||||
|
;; includes mono and ODE failures.
|
||||||
|
;; You will need to capture these native stack traces by recording the
|
||||||
|
;; session log itself.
|
||||||
; save_crashes = false
|
; save_crashes = false
|
||||||
|
|
||||||
;# {crash_dir} {save_crashes:true} {Directory to save crashes to?} {} crashes
|
;# {crash_dir} {save_crashes:true} {Directory to save crashes to?} {} crashes
|
||||||
|
@ -88,35 +98,46 @@
|
||||||
; allow_regionless = false
|
; allow_regionless = false
|
||||||
|
|
||||||
;# {NonPhysicalPrimMin} {} {Minimum size of nonphysical prims?} {} 0.001
|
;# {NonPhysicalPrimMin} {} {Minimum size of nonphysical prims?} {} 0.001
|
||||||
;; Minimum size for non-physical prims. Affects resizing of existing prims. This can be overriden in the region config file (as NonPhysicalPrimMin!).
|
;; Minimum size for non-physical prims. Affects resizing of existing
|
||||||
|
;; prims. This can be overriden in the region config file (as
|
||||||
|
;; NonPhysicalPrimMin!).
|
||||||
; NonPhysicalPrimMin = 0.001
|
; NonPhysicalPrimMin = 0.001
|
||||||
|
|
||||||
;# {NonPhysicalPrimMax} {} {Maximum size of nonphysical prims?} {} 256
|
;# {NonPhysicalPrimMax} {} {Maximum size of nonphysical prims?} {} 256
|
||||||
;; Maximum size for non-physical prims. Affects resizing of existing prims. This can be overriden in the region config file (as NonPhysicalPrimMax!).
|
;; Maximum size for non-physical prims. Affects resizing of existing
|
||||||
|
;; prims. This can be overriden in the region config file (as
|
||||||
|
;; NonPhysicalPrimMax!).
|
||||||
; NonPhysicalPrimMax = 256
|
; NonPhysicalPrimMax = 256
|
||||||
|
|
||||||
;# {PhysicalPrimMin} {} {Minimum size of physical prims?} {} 10
|
;# {PhysicalPrimMin} {} {Minimum size of physical prims?} {} 10
|
||||||
;; Maximum size where a prim can be physical. Affects resizing of existing prims. This can be overriden in the region config file.
|
;; Maximum size where a prim can be physical. Affects resizing of
|
||||||
|
;; existing prims. This can be overriden in the region config file.
|
||||||
; PhysicalPrimMin = 0.01
|
; PhysicalPrimMin = 0.01
|
||||||
|
|
||||||
;# {PhysicalPrimMax} {} {Maximum size of physical prims?} {} 10
|
;# {PhysicalPrimMax} {} {Maximum size of physical prims?} {} 10
|
||||||
;; Maximum size where a prim can be physical. Affects resizing of existing prims. This can be overriden in the region config file.
|
;; Maximum size where a prim can be physical. Affects resizing of
|
||||||
|
;; existing prims. This can be overriden in the region config file.
|
||||||
; PhysicalPrimMax = 10
|
; PhysicalPrimMax = 10
|
||||||
|
|
||||||
;# {ClampPrimSize} {} {Clamp viewer rezzed prims to max sizes?} {true false} false
|
;# {ClampPrimSize} {} {Clamp viewer rezzed prims to max sizes?} {true false} false
|
||||||
;; If a viewer attempts to rez a prim larger than the non-physical or physical prim max, clamp the dimensions to the appropriate maximum
|
;; If a viewer attempts to rez a prim larger than the non-physical or
|
||||||
|
;; physical prim max, clamp the dimensions to the appropriate maximum
|
||||||
;; This can be overriden in the region config file.
|
;; This can be overriden in the region config file.
|
||||||
; ClampPrimSize = false
|
; ClampPrimSize = false
|
||||||
|
|
||||||
;# {LinksetPrims} {} {Max prims an object will hold?} {} 0
|
;# {LinksetPrims} {} {Max prims an object will hold?} {} 0
|
||||||
;; Maximum number of prims allowable in a linkset. Affects creating new linksets. Ignored if less than or equal to zero.
|
;; Maximum number of prims allowable in a linkset. Affects creating new
|
||||||
|
;; linksets. Ignored if less than or equal to zero.
|
||||||
;; This can be overriden in the region config file.
|
;; This can be overriden in the region config file.
|
||||||
; LinksetPrims = 0
|
; LinksetPrims = 0
|
||||||
|
|
||||||
;# {AllowScriptCrossing} {} {Allow scripts to cross into this region} {true false} true
|
;# {AllowScriptCrossing} {} {Allow scripts to cross into this region} {true false} true
|
||||||
;; Allow scripts to keep running when they cross region boundaries, rather than being restarted. State is reloaded on the destination region.
|
;; Allow scripts to keep running when they cross region boundaries, rather
|
||||||
;; This only applies when crossing to a region running in a different simulator.
|
;; than being restarted. State is reloaded on the destination region.
|
||||||
;; For crossings where the regions are on the same simulator the script is always kept running.
|
;; This only applies when crossing to a region running in a different
|
||||||
|
;; simulator.
|
||||||
|
;; For crossings where the regions are on the same simulator the script is
|
||||||
|
;; always kept running.
|
||||||
; AllowScriptCrossing = true
|
; AllowScriptCrossing = true
|
||||||
|
|
||||||
;# {TrustBinaries} {AllowScriptCrossing:true} {Accept compiled binary script code? (DANGEROUS!)} {true false} false
|
;# {TrustBinaries} {AllowScriptCrossing:true} {Accept compiled binary script code? (DANGEROUS!)} {true false} false
|
||||||
|
@ -186,7 +207,8 @@
|
||||||
;# {physics} {} {Select physics engine} {OpenDynamicsEngine BulletSim basicphysics POS} OpenDynamicsEngine
|
;# {physics} {} {Select physics engine} {OpenDynamicsEngine BulletSim basicphysics POS} OpenDynamicsEngine
|
||||||
;; OpenDynamicsEngine is by some distance the most developed physics engine
|
;; OpenDynamicsEngine is by some distance the most developed physics engine
|
||||||
;; BulletSim is incomplete and experimental but in active development
|
;; BulletSim is incomplete and experimental but in active development
|
||||||
;; basicphysics effectively does not model physics at all, making all objects phantom
|
;; basicphysics effectively does not model physics at all, making all
|
||||||
|
;; objects phantom
|
||||||
;; Default is OpenDynamicsEngine
|
;; Default is OpenDynamicsEngine
|
||||||
; physics = OpenDynamicsEngine
|
; physics = OpenDynamicsEngine
|
||||||
; physics = BulletSim
|
; physics = BulletSim
|
||||||
|
@ -229,8 +251,9 @@
|
||||||
;# {simple_build_permissions} {} {Allow building in parcel by access list (no groups)} {true false} false
|
;# {simple_build_permissions} {} {Allow building in parcel by access list (no groups)} {true false} false
|
||||||
;; More control over permissions
|
;; More control over permissions
|
||||||
;; This is definitely not SL!
|
;; This is definitely not SL!
|
||||||
;; Provides a simple control for land owners to give build rights to specific avatars
|
;; Provides a simple control for land owners to give build rights to
|
||||||
;; in publicly accessible parcels that disallow object creation in general.
|
;; specific avatars in publicly accessible parcels that disallow object
|
||||||
|
;; creation in general.
|
||||||
;; Owners specific avatars by adding them to the Access List of the parcel
|
;; Owners specific avatars by adding them to the Access List of the parcel
|
||||||
;; without having to use the Groups feature
|
;; without having to use the Groups feature
|
||||||
; simple_build_permissions = false
|
; simple_build_permissions = false
|
||||||
|
@ -266,11 +289,14 @@
|
||||||
; DrawPrimOnMapTile = true
|
; DrawPrimOnMapTile = true
|
||||||
|
|
||||||
;# {HttpProxy} {} {Proxy URL for llHTTPRequest and dynamic texture loading} {} http://proxy.com:8080
|
;# {HttpProxy} {} {Proxy URL for llHTTPRequest and dynamic texture loading} {} http://proxy.com:8080
|
||||||
;; Http proxy setting for llHTTPRequest and dynamic texture loading, if required
|
;; Http proxy setting for llHTTPRequest and dynamic texture loading, if
|
||||||
|
;; required
|
||||||
; HttpProxy = "http://proxy.com:8080"
|
; HttpProxy = "http://proxy.com:8080"
|
||||||
|
|
||||||
;# {HttpProxyExceptions} {HttpProxy} {Set of regular expressions defining URL that should not be proxied} {}
|
;# {HttpProxyExceptions} {HttpProxy} {Set of regular expressions defining URL that should not be proxied} {}
|
||||||
;; If you're using HttpProxy, then you can set HttpProxyExceptions to a list of regular expressions for URLs that you don't want to go through the proxy
|
;; If you're using HttpProxy, then you can set HttpProxyExceptions to a
|
||||||
|
;; list of regular expressions for URLs that you don't want to go through
|
||||||
|
;; the proxy.
|
||||||
;; For example, servers inside your firewall.
|
;; For example, servers inside your firewall.
|
||||||
;; Separate patterns with a ';'
|
;; Separate patterns with a ';'
|
||||||
; HttpProxyExceptions = ".mydomain.com;localhost"
|
; HttpProxyExceptions = ".mydomain.com;localhost"
|
||||||
|
@ -289,13 +315,15 @@
|
||||||
; SpawnPointRouting = closest
|
; SpawnPointRouting = closest
|
||||||
|
|
||||||
;# {TelehubAllowLandmark} {} {Allow users with landmarks to override telehub routing} {true false} false
|
;# {TelehubAllowLandmark} {} {Allow users with landmarks to override telehub routing} {true false} false
|
||||||
;; TelehubAllowLandmark allows users with landmarks to override telehub routing and land at the landmark coordinates when set to true
|
;; TelehubAllowLandmark allows users with landmarks to override telehub
|
||||||
|
;; routing and land at the landmark coordinates when set to true
|
||||||
;; default is false
|
;; default is false
|
||||||
; TelehubAllowLandmark = false
|
; TelehubAllowLandmark = false
|
||||||
|
|
||||||
;# {AllowedClients} {} {Bar (|) separated list of allowed clients} {}
|
;# {AllowedClients} {} {Bar (|) separated list of allowed clients} {}
|
||||||
;; Bar (|) separated list of viewers which may gain access to the regions.
|
;; Bar (|) separated list of viewers which may gain access to the regions.
|
||||||
;; One can use a substring of the viewer name to enable only certain versions
|
;; One can use a substring of the viewer name to enable only certain
|
||||||
|
;; versions
|
||||||
;; Example: Agent uses the viewer "Imprudence 1.3.2.0"
|
;; Example: Agent uses the viewer "Imprudence 1.3.2.0"
|
||||||
;; - "Imprudence" has access
|
;; - "Imprudence" has access
|
||||||
;; - "Imprudence 1.3" has access
|
;; - "Imprudence 1.3" has access
|
||||||
|
@ -304,7 +332,8 @@
|
||||||
|
|
||||||
;# {BannedClients} {} {Bar (|) separated list of banned clients} {}
|
;# {BannedClients} {} {Bar (|) separated list of banned clients} {}
|
||||||
;# Bar (|) separated list of viewers which may not gain access to the regions.
|
;# Bar (|) separated list of viewers which may not gain access to the regions.
|
||||||
;; One can use a Substring of the viewer name to disable only certain versions
|
;; One can use a Substring of the viewer name to disable only certain
|
||||||
|
;; versions
|
||||||
;; Example: Agent uses the viewer "Imprudence 1.3.2.0"
|
;; Example: Agent uses the viewer "Imprudence 1.3.2.0"
|
||||||
;; - "Imprudence" has no access
|
;; - "Imprudence" has no access
|
||||||
;; - "Imprudence 1.3" has no access
|
;; - "Imprudence 1.3" has no access
|
||||||
|
@ -450,7 +479,8 @@
|
||||||
[SimulatorFeatures]
|
[SimulatorFeatures]
|
||||||
|
|
||||||
;# {MapImageServerURI} {} {URL for the map server} {}
|
;# {MapImageServerURI} {} {URL for the map server} {}
|
||||||
; Experimental new information sent in SimulatorFeatures cap for Kokua viewers
|
; Experimental new information sent in SimulatorFeatures cap for Kokua
|
||||||
|
; viewers
|
||||||
; meant to override the MapImage and search server url given at login, and varying
|
; meant to override the MapImage and search server url given at login, and varying
|
||||||
; on a sim-basis.
|
; on a sim-basis.
|
||||||
; Viewers that don't understand it, will ignore it
|
; Viewers that don't understand it, will ignore it
|
||||||
|
|
Loading…
Reference in New Issue