/indra/newview/llcompilequeue.cpp

https://bitbucket.org/lindenlab/viewer-beta/ · C++ · 769 lines · 566 code · 96 blank · 107 comment · 77 complexity · d2b0d413754dde3001a8d7ed792b1748 MD5 · raw file

  1. /**
  2. * @file llcompilequeue.cpp
  3. * @brief LLCompileQueueData class implementation
  4. *
  5. * $LicenseInfo:firstyear=2002&license=viewerlgpl$
  6. * Second Life Viewer Source Code
  7. * Copyright (C) 2010, Linden Research, Inc.
  8. *
  9. * This library is free software; you can redistribute it and/or
  10. * modify it under the terms of the GNU Lesser General Public
  11. * License as published by the Free Software Foundation;
  12. * version 2.1 of the License only.
  13. *
  14. * This library is distributed in the hope that it will be useful,
  15. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  16. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  17. * Lesser General Public License for more details.
  18. *
  19. * You should have received a copy of the GNU Lesser General Public
  20. * License along with this library; if not, write to the Free Software
  21. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
  22. *
  23. * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
  24. * $/LicenseInfo$
  25. */
  26. /**
  27. *
  28. * Implementation of the script queue which keeps an array of object
  29. * UUIDs and manipulates all of the scripts on each of them.
  30. *
  31. */
  32. #include "llviewerprecompiledheaders.h"
  33. #include "llcompilequeue.h"
  34. #include "llagent.h"
  35. #include "llassetuploadqueue.h"
  36. #include "llassetuploadresponders.h"
  37. #include "llchat.h"
  38. #include "llfloaterreg.h"
  39. #include "llviewerwindow.h"
  40. #include "llviewerobject.h"
  41. #include "llviewerobjectlist.h"
  42. #include "llviewerregion.h"
  43. #include "lscript_rt_interface.h"
  44. #include "llviewercontrol.h"
  45. #include "llviewerobject.h"
  46. #include "llviewerregion.h"
  47. #include "llresmgr.h"
  48. #include "llbutton.h"
  49. #include "lldir.h"
  50. #include "llnotificationsutil.h"
  51. #include "llviewerstats.h"
  52. #include "llvfile.h"
  53. #include "lluictrlfactory.h"
  54. #include "lltrans.h"
  55. #include "llselectmgr.h"
  56. // *TODO: This should be separated into the script queue, and the floater views of that queue.
  57. // There should only be one floater class that can view any queue type
  58. ///----------------------------------------------------------------------------
  59. /// Local function declarations, constants, enums, and typedefs
  60. ///----------------------------------------------------------------------------
  61. struct LLScriptQueueData
  62. {
  63. LLUUID mQueueID;
  64. std::string mScriptName;
  65. LLUUID mTaskId;
  66. LLUUID mItemId;
  67. LLScriptQueueData(const LLUUID& q_id, const std::string& name, const LLUUID& task_id, const LLUUID& item_id) :
  68. mQueueID(q_id), mScriptName(name), mTaskId(task_id), mItemId(item_id) {}
  69. };
  70. ///----------------------------------------------------------------------------
  71. /// Class LLFloaterScriptQueue
  72. ///----------------------------------------------------------------------------
  73. // Default constructor
  74. LLFloaterScriptQueue::LLFloaterScriptQueue(const LLSD& key) :
  75. LLFloater(key),
  76. mDone(false),
  77. mMono(false)
  78. {
  79. }
  80. // Destroys the object
  81. LLFloaterScriptQueue::~LLFloaterScriptQueue()
  82. {
  83. }
  84. BOOL LLFloaterScriptQueue::postBuild()
  85. {
  86. childSetAction("close",onCloseBtn,this);
  87. getChildView("close")->setEnabled(FALSE);
  88. return TRUE;
  89. }
  90. // This is the callback method for the viewer object currently being
  91. // worked on.
  92. // NOT static, virtual!
  93. void LLFloaterScriptQueue::inventoryChanged(LLViewerObject* viewer_object,
  94. LLInventoryObject::object_list_t* inv,
  95. S32,
  96. void* q_id)
  97. {
  98. llinfos << "LLFloaterScriptQueue::inventoryChanged() for object "
  99. << viewer_object->getID() << llendl;
  100. //Remove this listener from the object since its
  101. //listener callback is now being executed.
  102. //We remove the listener here because the function
  103. //removeVOInventoryListener removes the listener from a ViewerObject
  104. //which it internally stores.
  105. //If we call this further down in the function, calls to handleInventory
  106. //and nextObject may update the interally stored viewer object causing
  107. //the removal of the incorrect listener from an incorrect object.
  108. //Fixes SL-6119:Recompile scripts fails to complete
  109. removeVOInventoryListener();
  110. if (viewer_object && inv && (viewer_object->getID() == mCurrentObjectID) )
  111. {
  112. handleInventory(viewer_object, inv);
  113. }
  114. else
  115. {
  116. // something went wrong...
  117. // note that we're not working on this one, and move onto the
  118. // next object in the list.
  119. llwarns << "No inventory for " << mCurrentObjectID
  120. << llendl;
  121. nextObject();
  122. }
  123. }
  124. // static
  125. void LLFloaterScriptQueue::onCloseBtn(void* user_data)
  126. {
  127. LLFloaterScriptQueue* self = (LLFloaterScriptQueue*)user_data;
  128. self->closeFloater();
  129. }
  130. void LLFloaterScriptQueue::addObject(const LLUUID& id)
  131. {
  132. mObjectIDs.put(id);
  133. }
  134. BOOL LLFloaterScriptQueue::start()
  135. {
  136. //llinfos << "LLFloaterCompileQueue::start()" << llendl;
  137. std::string buffer;
  138. LLSelectMgr *mgr = LLSelectMgr::getInstance();
  139. LLObjectSelectionHandle selectHandle = mgr->getSelection();
  140. U32 n_objects = 0;
  141. if (gSavedSettings.getBOOL("EditLinkedParts"))
  142. {
  143. n_objects = selectHandle->getObjectCount();
  144. }
  145. else
  146. {
  147. n_objects = selectHandle->getRootObjectCount();
  148. }
  149. LLStringUtil::format_map_t args;
  150. args["[START]"] = mStartString;
  151. args["[COUNT]"] = llformat ("%d", mObjectIDs.count());
  152. buffer = getString ("Starting", args);
  153. getChild<LLScrollListCtrl>("queue output")->setCommentText(buffer);
  154. return nextObject();
  155. }
  156. BOOL LLFloaterScriptQueue::isDone() const
  157. {
  158. return (mCurrentObjectID.isNull() && (mObjectIDs.count() == 0));
  159. }
  160. // go to the next object. If no objects left, it falls out silently
  161. // and waits to be killed by the window being closed.
  162. BOOL LLFloaterScriptQueue::nextObject()
  163. {
  164. S32 count;
  165. BOOL successful_start = FALSE;
  166. do
  167. {
  168. count = mObjectIDs.count();
  169. llinfos << "LLFloaterScriptQueue::nextObject() - " << count
  170. << " objects left to process." << llendl;
  171. mCurrentObjectID.setNull();
  172. if(count > 0)
  173. {
  174. successful_start = popNext();
  175. }
  176. llinfos << "LLFloaterScriptQueue::nextObject() "
  177. << (successful_start ? "successful" : "unsuccessful")
  178. << llendl;
  179. } while((mObjectIDs.count() > 0) && !successful_start);
  180. if(isDone() && !mDone)
  181. {
  182. mDone = true;
  183. getChild<LLScrollListCtrl>("queue output")->setCommentText(getString("Done"));
  184. getChildView("close")->setEnabled(TRUE);
  185. }
  186. return successful_start;
  187. }
  188. // returns true if the queue has started, otherwise false. This
  189. // method pops the top object off of the queue.
  190. BOOL LLFloaterScriptQueue::popNext()
  191. {
  192. // get the first element off of the container, and attempt to get
  193. // the inventory.
  194. BOOL rv = FALSE;
  195. S32 count = mObjectIDs.count();
  196. if(mCurrentObjectID.isNull() && (count > 0))
  197. {
  198. mCurrentObjectID = mObjectIDs.get(0);
  199. llinfos << "LLFloaterScriptQueue::popNext() - mCurrentID: "
  200. << mCurrentObjectID << llendl;
  201. mObjectIDs.remove(0);
  202. LLViewerObject* obj = gObjectList.findObject(mCurrentObjectID);
  203. if(obj)
  204. {
  205. llinfos << "LLFloaterScriptQueue::popNext() requesting inv for "
  206. << mCurrentObjectID << llendl;
  207. LLUUID* id = new LLUUID(getKey().asUUID());
  208. registerVOInventoryListener(obj,id);
  209. requestVOInventory();
  210. rv = TRUE;
  211. }
  212. }
  213. return rv;
  214. }
  215. ///----------------------------------------------------------------------------
  216. /// Class LLFloaterCompileQueue
  217. ///----------------------------------------------------------------------------
  218. class LLCompileFloaterUploadQueueSupplier : public LLAssetUploadQueueSupplier
  219. {
  220. public:
  221. LLCompileFloaterUploadQueueSupplier(const LLUUID& queue_id) :
  222. mQueueId(queue_id)
  223. {
  224. }
  225. virtual LLAssetUploadQueue* get() const
  226. {
  227. LLFloaterCompileQueue* queue = LLFloaterReg::findTypedInstance<LLFloaterCompileQueue>("compile_queue", LLSD(mQueueId));
  228. if(NULL == queue)
  229. {
  230. return NULL;
  231. }
  232. return queue->getUploadQueue();
  233. }
  234. virtual void log(std::string message) const
  235. {
  236. LLFloaterCompileQueue* queue = LLFloaterReg::findTypedInstance<LLFloaterCompileQueue>("compile_queue", LLSD(mQueueId));
  237. if(NULL == queue)
  238. {
  239. return;
  240. }
  241. queue->getChild<LLScrollListCtrl>("queue output")->setCommentText(message);
  242. }
  243. private:
  244. LLUUID mQueueId;
  245. };
  246. LLFloaterCompileQueue::LLFloaterCompileQueue(const LLSD& key)
  247. : LLFloaterScriptQueue(key)
  248. {
  249. setTitle(LLTrans::getString("CompileQueueTitle"));
  250. setStartString(LLTrans::getString("CompileQueueStart"));
  251. mUploadQueue = new LLAssetUploadQueue(new LLCompileFloaterUploadQueueSupplier(key.asUUID()));
  252. }
  253. LLFloaterCompileQueue::~LLFloaterCompileQueue()
  254. {
  255. }
  256. void LLFloaterCompileQueue::handleInventory(LLViewerObject *viewer_object,
  257. LLInventoryObject::object_list_t* inv)
  258. {
  259. // find all of the lsl, leaving off duplicates. We'll remove
  260. // all matching asset uuids on compilation success.
  261. typedef std::multimap<LLUUID, LLPointer<LLInventoryItem> > uuid_item_map;
  262. uuid_item_map asset_item_map;
  263. LLInventoryObject::object_list_t::const_iterator it = inv->begin();
  264. LLInventoryObject::object_list_t::const_iterator end = inv->end();
  265. for ( ; it != end; ++it)
  266. {
  267. if((*it)->getType() == LLAssetType::AT_LSL_TEXT)
  268. {
  269. LLInventoryItem* item = (LLInventoryItem*)((LLInventoryObject*)(*it));
  270. // Check permissions before allowing the user to retrieve data.
  271. if (item->getPermissions().allowModifyBy(gAgent.getID(), gAgent.getGroupID()) &&
  272. item->getPermissions().allowCopyBy(gAgent.getID(), gAgent.getGroupID()) )
  273. {
  274. LLPointer<LLViewerInventoryItem> script = new LLViewerInventoryItem(item);
  275. mCurrentScripts.put(script);
  276. asset_item_map.insert(std::make_pair(item->getAssetUUID(), item));
  277. }
  278. }
  279. }
  280. if (asset_item_map.empty())
  281. {
  282. // There are no scripts in this object. move on.
  283. nextObject();
  284. }
  285. else
  286. {
  287. // request all of the assets.
  288. uuid_item_map::iterator iter;
  289. for(iter = asset_item_map.begin(); iter != asset_item_map.end(); iter++)
  290. {
  291. LLInventoryItem *itemp = iter->second;
  292. LLScriptQueueData* datap = new LLScriptQueueData(getKey().asUUID(),
  293. itemp->getName(),
  294. viewer_object->getID(),
  295. itemp->getUUID());
  296. //llinfos << "ITEM NAME 2: " << names.get(i) << llendl;
  297. gAssetStorage->getInvItemAsset(viewer_object->getRegion()->getHost(),
  298. gAgent.getID(),
  299. gAgent.getSessionID(),
  300. itemp->getPermissions().getOwner(),
  301. viewer_object->getID(),
  302. itemp->getUUID(),
  303. itemp->getAssetUUID(),
  304. itemp->getType(),
  305. LLFloaterCompileQueue::scriptArrived,
  306. (void*)datap);
  307. }
  308. }
  309. }
  310. // This is the callback for when each script arrives
  311. // static
  312. void LLFloaterCompileQueue::scriptArrived(LLVFS *vfs, const LLUUID& asset_id,
  313. LLAssetType::EType type,
  314. void* user_data, S32 status, LLExtStat ext_status)
  315. {
  316. llinfos << "LLFloaterCompileQueue::scriptArrived()" << llendl;
  317. LLScriptQueueData* data = (LLScriptQueueData*)user_data;
  318. if(!data)
  319. {
  320. return;
  321. }
  322. LLFloaterCompileQueue* queue = LLFloaterReg::findTypedInstance<LLFloaterCompileQueue>("compile_queue", data->mQueueID);
  323. std::string buffer;
  324. if(queue && (0 == status))
  325. {
  326. //llinfos << "ITEM NAME 3: " << data->mScriptName << llendl;
  327. // Dump this into a file on the local disk so we can compile it.
  328. std::string filename;
  329. LLVFile file(vfs, asset_id, type);
  330. std::string uuid_str;
  331. asset_id.toString(uuid_str);
  332. filename = gDirUtilp->getExpandedFilename(LL_PATH_CACHE,uuid_str) + llformat(".%s",LLAssetType::lookup(type));
  333. const bool is_running = true;
  334. LLViewerObject* object = gObjectList.findObject(data->mTaskId);
  335. if (object)
  336. {
  337. std::string url = object->getRegion()->getCapability("UpdateScriptTask");
  338. if(!url.empty())
  339. {
  340. // Read script source in to buffer.
  341. U32 script_size = file.getSize();
  342. U8* script_data = new U8[script_size];
  343. file.read(script_data, script_size);
  344. queue->mUploadQueue->queue(filename, data->mTaskId,
  345. data->mItemId, is_running, queue->mMono, queue->getKey().asUUID(),
  346. script_data, script_size, data->mScriptName);
  347. }
  348. else
  349. {
  350. // It's now in the file, now compile it.
  351. buffer = LLTrans::getString("CompileQueueDownloadedCompiling") + (": ") + data->mScriptName;
  352. // Write script to local file for compilation.
  353. LLFILE *fp = LLFile::fopen(filename, "wb"); /*Flawfinder: ignore*/
  354. if (fp)
  355. {
  356. const S32 buf_size = 65536;
  357. U8 copy_buf[buf_size];
  358. while (file.read(copy_buf, buf_size)) /*Flawfinder: ignore*/
  359. {
  360. if (fwrite(copy_buf, file.getLastBytesRead(), 1, fp) < 1)
  361. {
  362. // return a bad file error if we can't write the whole thing
  363. status = LL_ERR_CANNOT_OPEN_FILE;
  364. }
  365. }
  366. fclose(fp);
  367. }
  368. else
  369. {
  370. llerrs << "Unable to find object to compile" << llendl;
  371. }
  372. // TODO: babbage: No compile if no cap.
  373. queue->compile(filename, data->mItemId);
  374. // Delete it after we're done compiling?
  375. LLFile::remove(filename);
  376. }
  377. }
  378. }
  379. else
  380. {
  381. LLViewerStats::getInstance()->incStat( LLViewerStats::ST_DOWNLOAD_FAILED );
  382. if( LL_ERR_ASSET_REQUEST_NOT_IN_DATABASE == status )
  383. {
  384. LLSD args;
  385. args["MESSAGE"] = LLTrans::getString("CompileQueueScriptNotFound");
  386. LLNotificationsUtil::add("SystemMessage", args);
  387. buffer = LLTrans::getString("CompileQueueProblemDownloading") + (": ") + data->mScriptName;
  388. }
  389. else if (LL_ERR_INSUFFICIENT_PERMISSIONS == status)
  390. {
  391. LLSD args;
  392. args["MESSAGE"] = LLTrans::getString("CompileQueueInsufficientPermDownload");
  393. LLNotificationsUtil::add("SystemMessage", args);
  394. buffer = LLTrans::getString("CompileQueueInsufficientPermFor") + (": ") + data->mScriptName;
  395. }
  396. else
  397. {
  398. buffer = LLTrans::getString("CompileQueueUnknownFailure") + (" ") + data->mScriptName;
  399. }
  400. llwarns << "Problem downloading script asset." << llendl;
  401. if(queue) queue->removeItemByItemID(data->mItemId);
  402. }
  403. if(queue && (buffer.size() > 0))
  404. {
  405. queue->getChild<LLScrollListCtrl>("queue output")->setCommentText(buffer);
  406. }
  407. delete data;
  408. }
  409. // static
  410. void LLFloaterCompileQueue::onSaveTextComplete(const LLUUID& asset_id, void* user_data, S32 status, LLExtStat ext_status) // StoreAssetData callback (fixed)
  411. {
  412. llinfos << "LLFloaterCompileQueue::onSaveTextComplete()" << llendl;
  413. if (status)
  414. {
  415. llwarns << "Unable to save text for script." << llendl;
  416. LLSD args;
  417. args["REASON"] = std::string(LLAssetStorage::getErrorString(status));
  418. LLNotificationsUtil::add("CompileQueueSaveText", args);
  419. }
  420. }
  421. // static
  422. void LLFloaterCompileQueue::onSaveBytecodeComplete(const LLUUID& asset_id, void* user_data, S32 status, LLExtStat ext_status) // StoreAssetData callback (fixed)
  423. {
  424. llinfos << "LLFloaterCompileQueue::onSaveBytecodeComplete()" << llendl;
  425. LLCompileQueueData* data = (LLCompileQueueData*)user_data;
  426. LLFloaterCompileQueue* queue = LLFloaterReg::findTypedInstance<LLFloaterCompileQueue>("compile_queue", data->mQueueID);
  427. if(queue && (0 == status) && data)
  428. {
  429. queue->saveItemByItemID(data->mItemId);
  430. queue->removeItemByItemID(data->mItemId);
  431. }
  432. else
  433. {
  434. llwarns << "Unable to save bytecode for script." << llendl;
  435. LLSD args;
  436. args["REASON"] = std::string(LLAssetStorage::getErrorString(status));
  437. LLNotificationsUtil::add("CompileQueueSaveBytecode", args);
  438. }
  439. delete data;
  440. data = NULL;
  441. }
  442. // compile the file given and save it out.
  443. void LLFloaterCompileQueue::compile(const std::string& filename,
  444. const LLUUID& item_id)
  445. {
  446. LLUUID new_asset_id;
  447. LLTransactionID tid;
  448. tid.generate();
  449. new_asset_id = tid.makeAssetID(gAgent.getSecureSessionID());
  450. std::string uuid_string;
  451. new_asset_id.toString(uuid_string);
  452. std::string dst_filename;
  453. dst_filename = gDirUtilp->getExpandedFilename(LL_PATH_CACHE,uuid_string) + ".lso";
  454. std::string err_filename;
  455. err_filename = gDirUtilp->getExpandedFilename(LL_PATH_CACHE,uuid_string) + ".out";
  456. gAssetStorage->storeAssetData(filename, tid,
  457. LLAssetType::AT_LSL_TEXT,
  458. &onSaveTextComplete, NULL, FALSE);
  459. const BOOL compile_to_mono = FALSE;
  460. if(!lscript_compile(filename.c_str(), dst_filename.c_str(),
  461. err_filename.c_str(), compile_to_mono,
  462. uuid_string.c_str(), gAgent.isGodlike()))
  463. {
  464. llwarns << "compile failed" << llendl;
  465. removeItemByItemID(item_id);
  466. }
  467. else
  468. {
  469. llinfos << "compile successful." << llendl;
  470. // Save LSL bytecode
  471. LLCompileQueueData* data = new LLCompileQueueData(getKey().asUUID(), item_id);
  472. gAssetStorage->storeAssetData(dst_filename, new_asset_id,
  473. LLAssetType::AT_LSL_BYTECODE,
  474. &LLFloaterCompileQueue::onSaveBytecodeComplete,
  475. (void*)data, FALSE);
  476. }
  477. }
  478. void LLFloaterCompileQueue::removeItemByItemID(const LLUUID& asset_id)
  479. {
  480. llinfos << "LLFloaterCompileQueue::removeItemByAssetID()" << llendl;
  481. for(S32 i = 0; i < mCurrentScripts.count(); )
  482. {
  483. if(asset_id == mCurrentScripts.get(i)->getUUID())
  484. {
  485. mCurrentScripts.remove(i);
  486. }
  487. else
  488. {
  489. ++i;
  490. }
  491. }
  492. if(mCurrentScripts.count() == 0)
  493. {
  494. nextObject();
  495. }
  496. }
  497. const LLInventoryItem* LLFloaterCompileQueue::findItemByItemID(const LLUUID& asset_id) const
  498. {
  499. LLInventoryItem* result = NULL;
  500. S32 count = mCurrentScripts.count();
  501. for(S32 i = 0; i < count; ++i)
  502. {
  503. if(asset_id == mCurrentScripts.get(i)->getUUID())
  504. {
  505. result = mCurrentScripts.get(i);
  506. }
  507. }
  508. return result;
  509. }
  510. void LLFloaterCompileQueue::saveItemByItemID(const LLUUID& asset_id)
  511. {
  512. llinfos << "LLFloaterCompileQueue::saveItemByAssetID()" << llendl;
  513. LLViewerObject* viewer_object = gObjectList.findObject(mCurrentObjectID);
  514. if(viewer_object)
  515. {
  516. S32 count = mCurrentScripts.count();
  517. for(S32 i = 0; i < count; ++i)
  518. {
  519. if(asset_id == mCurrentScripts.get(i)->getUUID())
  520. {
  521. // *FIX: this auto-resets active to TRUE. That might
  522. // be a bad idea.
  523. viewer_object->saveScript(mCurrentScripts.get(i), TRUE, false);
  524. }
  525. }
  526. }
  527. else
  528. {
  529. llwarns << "Unable to finish save!" << llendl;
  530. }
  531. }
  532. ///----------------------------------------------------------------------------
  533. /// Class LLFloaterResetQueue
  534. ///----------------------------------------------------------------------------
  535. LLFloaterResetQueue::LLFloaterResetQueue(const LLSD& key)
  536. : LLFloaterScriptQueue(key)
  537. {
  538. setTitle(LLTrans::getString("ResetQueueTitle"));
  539. setStartString(LLTrans::getString("ResetQueueStart"));
  540. }
  541. LLFloaterResetQueue::~LLFloaterResetQueue()
  542. {
  543. }
  544. void LLFloaterResetQueue::handleInventory(LLViewerObject* viewer_obj,
  545. LLInventoryObject::object_list_t* inv)
  546. {
  547. // find all of the lsl, leaving off duplicates. We'll remove
  548. // all matching asset uuids on compilation success.
  549. LLDynamicArray<const char*> names;
  550. LLInventoryObject::object_list_t::const_iterator it = inv->begin();
  551. LLInventoryObject::object_list_t::const_iterator end = inv->end();
  552. for ( ; it != end; ++it)
  553. {
  554. if((*it)->getType() == LLAssetType::AT_LSL_TEXT)
  555. {
  556. LLViewerObject* object = gObjectList.findObject(viewer_obj->getID());
  557. if (object)
  558. {
  559. LLInventoryItem* item = (LLInventoryItem*)((LLInventoryObject*)(*it));
  560. std::string buffer;
  561. buffer = getString("Resetting") + (": ") + item->getName();
  562. getChild<LLScrollListCtrl>("queue output")->setCommentText(buffer);
  563. LLMessageSystem* msg = gMessageSystem;
  564. msg->newMessageFast(_PREHASH_ScriptReset);
  565. msg->nextBlockFast(_PREHASH_AgentData);
  566. msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
  567. msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
  568. msg->nextBlockFast(_PREHASH_Script);
  569. msg->addUUIDFast(_PREHASH_ObjectID, viewer_obj->getID());
  570. msg->addUUIDFast(_PREHASH_ItemID, (*it)->getUUID());
  571. msg->sendReliable(object->getRegion()->getHost());
  572. }
  573. }
  574. }
  575. nextObject();
  576. }
  577. ///----------------------------------------------------------------------------
  578. /// Class LLFloaterRunQueue
  579. ///----------------------------------------------------------------------------
  580. LLFloaterRunQueue::LLFloaterRunQueue(const LLSD& key)
  581. : LLFloaterScriptQueue(key)
  582. {
  583. setTitle(LLTrans::getString("RunQueueTitle"));
  584. setStartString(LLTrans::getString("RunQueueStart"));
  585. }
  586. LLFloaterRunQueue::~LLFloaterRunQueue()
  587. {
  588. }
  589. void LLFloaterRunQueue::handleInventory(LLViewerObject* viewer_obj,
  590. LLInventoryObject::object_list_t* inv)
  591. {
  592. // find all of the lsl, leaving off duplicates. We'll remove
  593. // all matching asset uuids on compilation success.
  594. LLDynamicArray<const char*> names;
  595. LLInventoryObject::object_list_t::const_iterator it = inv->begin();
  596. LLInventoryObject::object_list_t::const_iterator end = inv->end();
  597. for ( ; it != end; ++it)
  598. {
  599. if((*it)->getType() == LLAssetType::AT_LSL_TEXT)
  600. {
  601. LLViewerObject* object = gObjectList.findObject(viewer_obj->getID());
  602. if (object)
  603. {
  604. LLInventoryItem* item = (LLInventoryItem*)((LLInventoryObject*)(*it));
  605. LLScrollListCtrl* list = getChild<LLScrollListCtrl>("queue output");
  606. std::string buffer;
  607. buffer = getString("Running") + (": ") + item->getName();
  608. list->setCommentText(buffer);
  609. LLMessageSystem* msg = gMessageSystem;
  610. msg->newMessageFast(_PREHASH_SetScriptRunning);
  611. msg->nextBlockFast(_PREHASH_AgentData);
  612. msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
  613. msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
  614. msg->nextBlockFast(_PREHASH_Script);
  615. msg->addUUIDFast(_PREHASH_ObjectID, viewer_obj->getID());
  616. msg->addUUIDFast(_PREHASH_ItemID, (*it)->getUUID());
  617. msg->addBOOLFast(_PREHASH_Running, TRUE);
  618. msg->sendReliable(object->getRegion()->getHost());
  619. }
  620. }
  621. }
  622. nextObject();
  623. }
  624. ///----------------------------------------------------------------------------
  625. /// Class LLFloaterNotRunQueue
  626. ///----------------------------------------------------------------------------
  627. LLFloaterNotRunQueue::LLFloaterNotRunQueue(const LLSD& key)
  628. : LLFloaterScriptQueue(key)
  629. {
  630. setTitle(LLTrans::getString("NotRunQueueTitle"));
  631. setStartString(LLTrans::getString("NotRunQueueStart"));
  632. }
  633. LLFloaterNotRunQueue::~LLFloaterNotRunQueue()
  634. {
  635. }
  636. void LLFloaterNotRunQueue::handleInventory(LLViewerObject* viewer_obj,
  637. LLInventoryObject::object_list_t* inv)
  638. {
  639. // find all of the lsl, leaving off duplicates. We'll remove
  640. // all matching asset uuids on compilation success.
  641. LLDynamicArray<const char*> names;
  642. LLInventoryObject::object_list_t::const_iterator it = inv->begin();
  643. LLInventoryObject::object_list_t::const_iterator end = inv->end();
  644. for ( ; it != end; ++it)
  645. {
  646. if((*it)->getType() == LLAssetType::AT_LSL_TEXT)
  647. {
  648. LLViewerObject* object = gObjectList.findObject(viewer_obj->getID());
  649. if (object)
  650. {
  651. LLInventoryItem* item = (LLInventoryItem*)((LLInventoryObject*)(*it));
  652. LLScrollListCtrl* list = getChild<LLScrollListCtrl>("queue output");
  653. std::string buffer;
  654. buffer = getString("NotRunning") + (": ") +item->getName();
  655. list->setCommentText(buffer);
  656. LLMessageSystem* msg = gMessageSystem;
  657. msg->newMessageFast(_PREHASH_SetScriptRunning);
  658. msg->nextBlockFast(_PREHASH_AgentData);
  659. msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID());
  660. msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
  661. msg->nextBlockFast(_PREHASH_Script);
  662. msg->addUUIDFast(_PREHASH_ObjectID, viewer_obj->getID());
  663. msg->addUUIDFast(_PREHASH_ItemID, (*it)->getUUID());
  664. msg->addBOOLFast(_PREHASH_Running, FALSE);
  665. msg->sendReliable(object->getRegion()->getHost());
  666. }
  667. }
  668. }
  669. nextObject();
  670. }
  671. ///----------------------------------------------------------------------------
  672. /// Local function definitions
  673. ///----------------------------------------------------------------------------