From 98fd90ddd6595f2ee7e626c14117f51def621ec5 Mon Sep 17 00:00:00 2001
From: Josh Bell <josh@lindenlab.com>
Date: Thu, 14 Feb 2008 01:45:59 +0000
Subject: [PATCH] svn merge -r 79730:79944
 svn+ssh://svn.lindenlab.com/svn/linden/branches/parcel_media/sl-parcelmedia-6
 --> release

QAR-275 Parcel Media

Sam made me do it.
---
 etc/message.xml                               |   13 +-
 indra/llcommon/indra_constants.h              |    4 +
 indra/llcommon/llclickaction.h                |    2 +
 indra/llcommon/llpreprocessor.h               |   27 -
 indra/llinventory/llparcel.cpp                | 1402 +++++++++--------
 indra/llinventory/llparcel.h                  |   22 +
 indra/llmessage/llhttpclient.cpp              |   20 +-
 indra/llmessage/llhttpclient.h                |   11 +-
 indra/llmessage/llurlrequest.cpp              |    6 +-
 indra/llrender/llimagegl.cpp                  |    2 +-
 indra/llui/llcombobox.cpp                     |   31 +-
 indra/llui/llradiogroup.cpp                   |    4 +-
 indra/llui/llscrolllistctrl.cpp               |    9 +-
 indra/llui/lluictrl.cpp                       |   18 +-
 indra/llui/lluictrl.h                         |    2 +-
 indra/llui/lluifwd.h                          |   40 +
 indra/llwindow/llwindow.h                     |    3 +
 indra/llwindow/llwindowmacosx.cpp             |    9 +
 indra/llwindow/llwindowsdl.cpp                |   32 +-
 indra/llwindow/llwindowwin32.cpp              |    3 +
 indra/lscript/lscript_compile/indra.l         |   14 +
 .../lscript_library/lscript_library.cpp       |   12 +-
 indra/newview/app_settings/keywords.ini       |   12 +
 .../cursors_mac/UI_CURSOR_TOOLMEDIAOPEN.tif   |  Bin 0 -> 41228 bytes
 .../cursors_mac/UI_CURSOR_TOOLPAUSE.tif       |  Bin 0 -> 41224 bytes
 .../cursors_mac/UI_CURSOR_TOOLPLAY.tif        |  Bin 0 -> 41224 bytes
 indra/newview/llappviewer.cpp                 |   70 +-
 indra/newview/llfirstuse.cpp                  |   11 +
 indra/newview/llfirstuse.h                    |    3 +-
 indra/newview/llfloaterabout.cpp              |   24 +-
 indra/newview/llfloaterland.cpp               |  350 +---
 indra/newview/llfloaterland.h                 |   42 +-
 indra/newview/llfloaterpreference.cpp         |    8 -
 indra/newview/llfloatertos.cpp                |   17 -
 indra/newview/llfloaterurlentry.cpp           |  268 ++++
 indra/newview/llfloaterurlentry.h             |   44 +
 indra/newview/llglsandbox.cpp                 |    4 +-
 indra/newview/llmimetypes.cpp                 |  241 +++
 indra/newview/llmimetypes.h                   |   95 ++
 indra/newview/lloverlaybar.cpp                |   82 +-
 indra/newview/lloverlaybar.h                  |   11 +-
 indra/newview/llpanelavatar.cpp               |   20 -
 indra/newview/llpanelavatar.h                 |    4 -
 indra/newview/llpanelface.cpp                 |   50 +-
 indra/newview/llpanelland.cpp                 |    2 +-
 indra/newview/llpanellandmedia.cpp            |  378 +++++
 indra/newview/llpanellandmedia.h              |   58 +
 indra/newview/llpanellogin.cpp                |   22 +-
 indra/newview/llpanellogin.h                  |   12 +-
 indra/newview/llparcelselection.cpp           |   83 +
 indra/newview/llparcelselection.h             |   63 +
 indra/newview/llpreviewscript.cpp             |   14 +-
 indra/newview/llstartup.cpp                   |  186 +--
 indra/newview/llstartup.h                     |    4 +-
 indra/newview/llstatusbar.cpp                 |  117 +-
 indra/newview/llstatusbar.h                   |    4 +
 indra/newview/lltoolpie.cpp                   |  176 ++-
 indra/newview/llurldispatcher.cpp             |    3 +-
 indra/newview/llurlhistory.cpp                |  110 ++
 indra/newview/llurlhistory.h                  |   37 +
 indra/newview/llvieweraudio.cpp               |   13 +-
 indra/newview/llviewercontrol.cpp             |   11 +-
 indra/newview/llviewermedia.cpp               |  608 +++++++
 indra/newview/llviewermedia.h                 |   49 +
 indra/newview/llviewermenu.cpp                |    9 +-
 indra/newview/llviewermessage.cpp             |    2 +-
 indra/newview/llviewerobject.h                |    2 -
 indra/newview/llviewerparcelmedia.cpp         |  340 ++++
 indra/newview/llviewerparcelmedia.h           |   52 +
 indra/newview/llviewerparcelmediaautoplay.cpp |  129 ++
 indra/newview/llviewerparcelmediaautoplay.h   |   32 +
 indra/newview/llviewerparcelmgr.cpp           |  303 +---
 indra/newview/llviewerparcelmgr.h             |   54 +-
 indra/newview/llviewerregion.cpp              |    1 +
 indra/newview/llviewerwindow.cpp              |    1 -
 indra/newview/llweb.cpp                       |   13 +-
 indra/newview/pipeline.cpp                    |    2 +-
 indra/newview/res-sdl/toolmediaopen.BMP       |  Bin 0 -> 3128 bytes
 indra/newview/res-sdl/toolpause.BMP           |  Bin 0 -> 3128 bytes
 indra/newview/res-sdl/toolplay.BMP            |  Bin 0 -> 3128 bytes
 indra/newview/res/resource.h                  |    2 +
 indra/newview/res/toolmediaopen.cur           |  Bin 0 -> 2238 bytes
 indra/newview/res/toolpause.cur               |  Bin 0 -> 2238 bytes
 indra/newview/res/toolplay.cur                |  Bin 0 -> 2238 bytes
 indra/test/llhttpclient_tut.cpp               |   32 +-
 scripts/messages/message_template.msg         |    8 +
 86 files changed, 4185 insertions(+), 1789 deletions(-)
 create mode 100644 indra/llui/lluifwd.h
 create mode 100644 indra/newview/cursors_mac/UI_CURSOR_TOOLMEDIAOPEN.tif
 create mode 100644 indra/newview/cursors_mac/UI_CURSOR_TOOLPAUSE.tif
 create mode 100644 indra/newview/cursors_mac/UI_CURSOR_TOOLPLAY.tif
 create mode 100644 indra/newview/llfloaterurlentry.cpp
 create mode 100644 indra/newview/llfloaterurlentry.h
 create mode 100644 indra/newview/llmimetypes.cpp
 create mode 100644 indra/newview/llmimetypes.h
 create mode 100644 indra/newview/llpanellandmedia.cpp
 create mode 100644 indra/newview/llpanellandmedia.h
 create mode 100644 indra/newview/llparcelselection.cpp
 create mode 100644 indra/newview/llparcelselection.h
 create mode 100644 indra/newview/llurlhistory.cpp
 create mode 100644 indra/newview/llurlhistory.h
 create mode 100644 indra/newview/llviewermedia.cpp
 create mode 100644 indra/newview/llviewermedia.h
 create mode 100644 indra/newview/llviewerparcelmedia.cpp
 create mode 100644 indra/newview/llviewerparcelmedia.h
 create mode 100644 indra/newview/llviewerparcelmediaautoplay.cpp
 create mode 100644 indra/newview/llviewerparcelmediaautoplay.h
 create mode 100644 indra/newview/res-sdl/toolmediaopen.BMP
 create mode 100644 indra/newview/res-sdl/toolpause.BMP
 create mode 100644 indra/newview/res-sdl/toolplay.BMP
 create mode 100644 indra/newview/res/toolmediaopen.cur
 create mode 100644 indra/newview/res/toolpause.cur
 create mode 100644 indra/newview/res/toolplay.cur

diff --git a/etc/message.xml b/etc/message.xml
index ddbfa58ddbd..c9b9220ba21 100644
--- a/etc/message.xml
+++ b/etc/message.xml
@@ -357,6 +357,14 @@
 					<key>trusted-sender</key>
 					<boolean>true</boolean>
 				</map>
+				
+				<key>ParcelProperties</key>
+				<map>
+					<key>flavor</key>
+					<string>llsd</string>
+					<key>trusted-sender</key>
+					<boolean>true</boolean>
+				</map>
 
 				<key>avatarnotesrequest</key>
 				<map>
@@ -514,7 +522,10 @@
 
 			<key>SearchStatTracking</key>
 			<boolean>false</boolean>
-
+			
+			<key>ParcelPropertiesUpdate</key>
+			<boolean>false</boolean>
+		
 		</map>
 
 		<key>messageBans</key>
diff --git a/indra/llcommon/indra_constants.h b/indra/llcommon/indra_constants.h
index 0195893b160..46f46e24337 100644
--- a/indra/llcommon/indra_constants.h
+++ b/indra/llcommon/indra_constants.h
@@ -323,6 +323,10 @@ const U32 PARCEL_MEDIA_COMMAND_TIME = 6;
 const U32 PARCEL_MEDIA_COMMAND_AGENT = 7;
 const U32 PARCEL_MEDIA_COMMAND_UNLOAD = 8;
 const U32 PARCEL_MEDIA_COMMAND_AUTO_ALIGN = 9;
+const U32 PARCEL_MEDIA_COMMAND_TYPE = 10;
+const U32 PARCEL_MEDIA_COMMAND_SIZE = 11;
+const U32 PARCEL_MEDIA_COMMAND_DESC = 12;
+const U32 PARCEL_MEDIA_COMMAND_LOOP_SET = 13;
 
 // map item types
 const U32 MAP_ITEM_TELEHUB = 0x01;
diff --git a/indra/llcommon/llclickaction.h b/indra/llcommon/llclickaction.h
index be343c67853..e2ba02465d8 100644
--- a/indra/llcommon/llclickaction.h
+++ b/indra/llcommon/llclickaction.h
@@ -39,5 +39,7 @@ const U8 CLICK_ACTION_SIT = 1;
 const U8 CLICK_ACTION_BUY = 2;
 const U8 CLICK_ACTION_PAY = 3;
 const U8 CLICK_ACTION_OPEN = 4;
+const U8 CLICK_ACTION_PLAY = 5;
+const U8 CLICK_ACTION_OPEN_MEDIA = 6;
 
 #endif
diff --git a/indra/llcommon/llpreprocessor.h b/indra/llcommon/llpreprocessor.h
index 459d086cda6..ac06b431c1a 100644
--- a/indra/llcommon/llpreprocessor.h
+++ b/indra/llcommon/llpreprocessor.h
@@ -52,33 +52,6 @@
 #define LL_FORCE_INLINE __forceinline
 #endif
 
-// Per-OS feature switches.
-
-#if LL_DARWIN
-	#define LL_QUICKTIME_ENABLED	1
-	#define LL_LIBXUL_ENABLED		1
-#elif LL_WINDOWS
-	#define LL_QUICKTIME_ENABLED	1
-	#define LL_LIBXUL_ENABLED		1
-#elif LL_LINUX
-	#define LL_QUICKTIME_ENABLED	0
-        #ifndef LL_LIBXUL_ENABLED
-                #define LL_LIBXUL_ENABLED		1
-        #endif // def LL_LIBXUL_ENABLED
-#elif LL_SOLARIS
-	#define LL_QUICKTIME_ENABLED    0
-	#ifndef LL_LIBXUL_ENABLED
-		#define LL_LIBXUL_ENABLED               0
-	#endif // def LL_LIBXUL_ENABLED
-#endif
-
-#if LL_LIBXUL_ENABLED && !defined(MOZILLA_INTERNAL_API)
-	// Without this, nsTAString.h errors out with:
-	// "Cannot use internal string classes without MOZILLA_INTERNAL_API defined. Use the frozen header nsStringAPI.h instead."
-	// It might be worth our while to figure out if we can use the frozen apis at some point...
-	#define MOZILLA_INTERNAL_API 1
-#endif
-
 // Figure out differences between compilers
 #if defined(__GNUC__)
 	#define GCC_VERSION (__GNUC__ * 10000 \
diff --git a/indra/llinventory/llparcel.cpp b/indra/llinventory/llparcel.cpp
index b6a90b64e8d..792bb1be90f 100644
--- a/indra/llinventory/llparcel.cpp
+++ b/indra/llinventory/llparcel.cpp
@@ -42,6 +42,7 @@
 #include "llsdutil.h"
 #include "lltransactiontypes.h"
 #include "lltransactionflags.h"
+#include "llsdutil.h"
 #include "message.h"
 #include "u64.h"
 
@@ -170,73 +171,80 @@ void LLParcel::init(const LLUUID &owner_id,
                     S32 rent_price_per_meter, S32 area, S32 sim_object_limit, F32 parcel_object_bonus,
                     BOOL is_group_owned)
 {
-    mID.setNull();
-    mOwnerID		 = owner_id;
-    mGroupOwned		 = is_group_owned;
-    mClaimDate		 = claim_date;
-    mClaimPricePerMeter = claim_price_per_meter;
-    mRentPricePerMeter = rent_price_per_meter;
-    mArea			 = area;
-    mDiscountRate	 = 1.0f;
-    mDrawDistance	 = 512.f;
-    
-    mUserLookAt.setVec(0.0f, 0.f, 0.f);
-    // Default to using the parcel's landing point, if any.
-    mLandingType = L_LANDING_POINT;
-    
-    // *FIX: if owner_id != null, should be owned or sale pending,
-    // investigate init callers.
-    mStatus = OS_NONE;
-    mCategory = C_NONE;
-    mAuthBuyerID.setNull();
-    //mBuyerID.setNull();
-    //mJoinNeighbors = 0x0;
-    mSaleTimerExpires.setTimerExpirySec(0);
-    mSaleTimerExpires.stop();
-    mGraceExtension = 0;
-    //mExpireAction = STEA_REVERT;
-    mRecordTransaction = FALSE;
-    
-    mAuctionID = 0;
-    mInEscrow = false;
-    
-    mParcelFlags = PF_DEFAULT;
-    setParcelFlag(PF_CREATE_OBJECTS,	 modify);
-    setParcelFlag(PF_ALLOW_TERRAFORM, terraform);
-    setParcelFlag(PF_ALLOW_DAMAGE,			 damage);
-    
-    mSalePrice		 = 10000;
-    setName(NULL);
-    setDesc(NULL);
-    setMusicURL(NULL);
-    setMediaURL(NULL);
-    mMediaID.setNull();
-    mMediaAutoScale = 0;
-    
-    mGroupID.setNull();
-    
-    mPassPrice = PARCEL_PASS_PRICE_DEFAULT;
-    mPassHours = PARCEL_PASS_HOURS_DEFAULT;
-    
-    mAABBMin.setVec(SOME_BIG_NUMBER, SOME_BIG_NUMBER, SOME_BIG_NUMBER);
-    mAABBMax.setVec(SOME_BIG_NEG_NUMBER, SOME_BIG_NEG_NUMBER, SOME_BIG_NEG_NUMBER);
-    
-    mLocalID = 0;
-    
-    //mSimWidePrimCorrection = 0;
-    setMaxPrimCapacity((S32)(sim_object_limit * area / (F32)(REGION_WIDTH_METERS * REGION_WIDTH_METERS)));
-    setSimWideMaxPrimCapacity(0);
-    setSimWidePrimCount(0);
-    setOwnerPrimCount(0);
-    setGroupPrimCount(0);
-    setOtherPrimCount(0);
-    setSelectedPrimCount(0);
-    setTempPrimCount(0);
-    setCleanOtherTime(0);
-    setParcelPrimBonus(parcel_object_bonus);
-    
-    setPreviousOwnerID(LLUUID::null);
-    setPreviouslyGroupOwned(FALSE);
+	mID.setNull();
+	mOwnerID			= owner_id;
+	mGroupOwned			= is_group_owned;
+	mClaimDate			= claim_date;
+	mClaimPricePerMeter	= claim_price_per_meter;
+	mRentPricePerMeter	= rent_price_per_meter;
+	mArea				= area;
+	mDiscountRate		= 1.0f;
+	mDrawDistance		= 512.f;
+
+	mUserLookAt.setVec(0.0f, 0.f, 0.f);
+	// Default to using the parcel's landing point, if any.
+	mLandingType = L_LANDING_POINT;
+
+	// *FIX: if owner_id != null, should be owned or sale pending,
+	// investigate init callers.
+	mStatus = OS_NONE;
+	mCategory = C_NONE;
+	mAuthBuyerID.setNull();
+	//mBuyerID.setNull();
+	//mJoinNeighbors = 0x0;
+	mSaleTimerExpires.setTimerExpirySec(0);
+	mSaleTimerExpires.stop();
+	mGraceExtension = 0;
+	//mExpireAction = STEA_REVERT;
+	mRecordTransaction = FALSE;
+
+	mAuctionID = 0;
+	mInEscrow = false;
+
+	mParcelFlags = PF_DEFAULT;
+	setParcelFlag(PF_CREATE_OBJECTS,  modify);
+	setParcelFlag(PF_ALLOW_TERRAFORM, terraform);
+	setParcelFlag(PF_ALLOW_DAMAGE,    damage);
+
+	mSalePrice			= 10000;
+	setName(NULL);
+	setDesc(NULL);
+	setMusicURL(NULL);
+	setMediaURL(NULL);
+	setMediaDesc(NULL);
+	setMediaType(NULL);
+	mMediaID.setNull();
+	mMediaAutoScale = 0;
+	mMediaLoop = TRUE;
+	mObscureMedia = 0;
+	mObscureMusic = 0;
+	mMediaWidth = 0;
+	mMediaHeight = 0;
+
+	mGroupID.setNull();
+
+	mPassPrice = PARCEL_PASS_PRICE_DEFAULT;
+	mPassHours = PARCEL_PASS_HOURS_DEFAULT;
+
+	mAABBMin.setVec(SOME_BIG_NUMBER, SOME_BIG_NUMBER, SOME_BIG_NUMBER);
+	mAABBMax.setVec(SOME_BIG_NEG_NUMBER, SOME_BIG_NEG_NUMBER, SOME_BIG_NEG_NUMBER);
+
+	mLocalID = 0;
+
+	//mSimWidePrimCorrection = 0;
+	setMaxPrimCapacity((S32)(sim_object_limit * area / (F32)(REGION_WIDTH_METERS * REGION_WIDTH_METERS)));
+	setSimWideMaxPrimCapacity(0);
+	setSimWidePrimCount(0);
+	setOwnerPrimCount(0);
+	setGroupPrimCount(0);
+	setOtherPrimCount(0);
+	setSelectedPrimCount(0);
+	setTempPrimCount(0);
+	setCleanOtherTime(0);
+	setParcelPrimBonus(parcel_object_bonus);
+
+	setPreviousOwnerID(LLUUID::null);
+	setPreviouslyGroupOwned(FALSE);
 }
 
 void LLParcel::overrideOwner(const LLUUID& owner_id, BOOL is_group_owned)
@@ -260,7 +268,21 @@ void LLParcel::overrideParcelFlags(U32 flags)
 {
     mParcelFlags = flags;
 }
-
+void set_std_string(const char* src, std::string& dest)
+{
+	if(src)
+	{
+		dest.assign(src);
+	}
+	else
+	{
+#if (LL_LINUX && __GNUC__ < 3)
+		dest.assign(std::string(""));
+#else
+		dest.clear();
+#endif
+	}
+}
 void LLParcel::setName(const LLString& name)
 {
     // The escaping here must match the escaping in the database
@@ -297,6 +319,28 @@ void LLParcel::setMediaURL(const LLString& url)
     LLStringFn::replace_nonprintable(mMediaURL, LL_UNKNOWN_CHAR);
 }
 
+void LLParcel::setMediaDesc(const char* desc)
+{
+	// The escaping here must match the escaping in the database
+	// abstraction layer.
+	set_std_string(desc, mMediaDesc);
+	mMediaDesc = rawstr_to_utf8(mMediaDesc);
+}
+void LLParcel::setMediaType(const char* type)
+{
+	// The escaping here must match the escaping in the database
+	// abstraction layer.
+	set_std_string(type, mMediaType);
+	mMediaType = rawstr_to_utf8(mMediaType);
+}
+void LLParcel::setMediaWidth(S32 width)
+{
+	mMediaWidth = width;
+}
+void LLParcel::setMediaHeight(S32 height)
+{
+	mMediaHeight = height;
+}
 // virtual
 void LLParcel::setLocalID(S32 local_id)
 {
@@ -512,338 +556,367 @@ void LLParcel::setDiscountRate(F32 rate)
 // WARNING: Area will be wrong until you calculate it.
 BOOL LLParcel::importStream(std::istream& input_stream)
 {
-    U32 setting;
-    S32 secs_until_revert = 0;
-    
-    skip_to_end_of_next_keyword("{", input_stream);
-    if (!input_stream.good()) 
-    {
-        llwarns << "LLParcel::importStream() - bad input_stream" << llendl;
-        return FALSE;
-    }
-    
-    while (input_stream.good())
-    {
-        skip_comments_and_emptyspace(input_stream);
-        LLString line, keyword, value;
-        get_line(line, input_stream, MAX_STRING);
-        get_keyword_and_value(keyword, value, line);
-        
-        if ("}" == keyword)
-        {
-            break;
-        }
-        else if ("parcel_id" == keyword)
-        {
-            mID.set(value.c_str());
-        }
-        else if ("status" == keyword)
-        {
-            mStatus = ownership_string_to_status(value.c_str());
-        }
-        else if ("category" == keyword)
-        {
-            mCategory = category_string_to_category(value.c_str());
-        }
-        else if ("local_id" == keyword)
-        {
-            LLString::convertToS32(value, mLocalID);
-        }
-        else if ("name" == keyword)
-        {
-            setName( value );
-        }
-        else if ("desc" == keyword)
-        {
-            setDesc( value );
-        }
-        else if ("music_url" == keyword)
-        {
-            setMusicURL( value );
-        }
-        else if ("media_url" == keyword)
-        {
-            setMediaURL( value );
-        }
-        else if ("media_id" == keyword)
-        {
-            mMediaID.set( value.c_str() );
-        }
-        else if ("media_auto_scale" == keyword)
-        {
-            LLString::convertToU8(value, mMediaAutoScale);
-        }
-        else if ("owner_id" == keyword)
-        {
-            mOwnerID.set( value.c_str() );
-        }
-        else if ("group_owned" == keyword)
-        {
-            LLString::convertToBOOL(value, mGroupOwned);
-        }
-        else if ("clean_other_time" == keyword)
-        {
-            S32 time;
-            LLString::convertToS32(value, time);
-            setCleanOtherTime(time);
-        }
-        else if ("auth_buyer_id" == keyword)
-        {
-            mAuthBuyerID.set(value.c_str());
-        }
-        else if ("snapshot_id" == keyword)
-        {
-            mSnapshotID.set(value.c_str());
-        }
-        else if ("user_location" == keyword)
-        {
-            sscanf(value.c_str(), "%f %f %f",
-                   &mUserLocation.mV[VX],
-                   &mUserLocation.mV[VY],
-                   &mUserLocation.mV[VZ]);
-        }
-        else if ("user_look_at" == keyword)
-        {
-            sscanf(value.c_str(), "%f %f %f",
-                   &mUserLookAt.mV[VX],
-                   &mUserLookAt.mV[VY],
-                   &mUserLookAt.mV[VZ]);
-        }
-        else if ("landing_type" == keyword)
-        {
-            S32 landing_type = 0;
-            LLString::convertToS32(value, landing_type);
-            mLandingType = (ELandingType) landing_type;
-        }
-        else if ("join_neighbors" == keyword)
-        {
-            llinfos << "found deprecated keyword join_neighbors" << llendl;
-        }
-        else if ("revert_sale" == keyword)
-        {
-            LLString::convertToS32(value, secs_until_revert);
-            if (secs_until_revert > 0)
-            {
-                mSaleTimerExpires.start();
-                mSaleTimerExpires.setTimerExpirySec((F32)secs_until_revert);
-            }
-        }
-        else if("extended_grace" == keyword)
-        {
-            LLString::convertToS32(value, mGraceExtension);
-        }
-        else if ("user_list_type" == keyword)
-        {
-            // deprecated
-        }
-        else if("auction_id" == keyword)
-        {
-            LLString::convertToU32(value, mAuctionID);
-        }
-        else if ("allow_modify" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_CREATE_OBJECTS, setting);
-        }
-        else if ("allow_group_modify" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_CREATE_GROUP_OBJECTS, setting);
-        }
-        else if ("allow_all_object_entry" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_ALLOW_ALL_OBJECT_ENTRY, setting);
-        }
-        else if ("allow_group_object_entry" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_ALLOW_GROUP_OBJECT_ENTRY, setting);
-        }
-        else if ("allow_deed_to_group" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_ALLOW_DEED_TO_GROUP, setting);
-        }
-        else if("contribute_with_deed" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_CONTRIBUTE_WITH_DEED, setting);
-        }
-        else if ("allow_terraform" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_ALLOW_TERRAFORM, setting);
-        }
-        else if ("allow_damage" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_ALLOW_DAMAGE, setting);
-        }
-        else if ("allow_fly" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_ALLOW_FLY, setting);
-        }
-        else if ("allow_landmark" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_ALLOW_LANDMARK, setting);
-        }
-        else if ("sound_local" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_SOUND_LOCAL, setting);
-        }
-        else if ("allow_group_scripts" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_ALLOW_GROUP_SCRIPTS, setting);
-        }
-        else if ("allow_voice_chat" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_ALLOW_VOICE_CHAT, setting);
-        }
-        else if ("use_estate_voice_chan" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_USE_ESTATE_VOICE_CHAN, setting);
-        }
-        else if ("allow_scripts" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_ALLOW_OTHER_SCRIPTS, setting);
-        }
-        else if ("for_sale" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_FOR_SALE, setting);
-        }
-        else if ("sell_w_objects" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_SELL_PARCEL_OBJECTS, setting);
-        }
-        else if ("use_pass_list" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_USE_PASS_LIST, setting);
-        }
-        else if ("show_directory" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_SHOW_DIRECTORY, setting);
-        }
-        else if ("allow_publish" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_ALLOW_PUBLISH, setting);
-        }
-        else if ("mature_publish" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_MATURE_PUBLISH, setting);
-        }
-        else if ("claim_date" == keyword)
-        {
-            // BUG: This will fail when time rolls over in 2038.
-            S32 time;
-            LLString::convertToS32(value, time);
-            mClaimDate = time;
-        }
-        else if ("claim_price" == keyword)
-        {
-            LLString::convertToS32(value, mClaimPricePerMeter);
-        }
-        else if ("rent_price" == keyword)
-        {
-            LLString::convertToS32(value, mRentPricePerMeter);
-        }
-        else if ("discount_rate" == keyword)
-        {
-            LLString::convertToF32(value, mDiscountRate);
-        }
-        else if ("draw_distance" == keyword)
-        {
-            LLString::convertToF32(value, mDrawDistance);
-        }
-        else if ("sale_price" == keyword)
-        {
-            LLString::convertToS32(value, mSalePrice);
-        }
-        else if ("pass_price" == keyword)
-        {
-            LLString::convertToS32(value, mPassPrice);
-        }
-        else if ("pass_hours" == keyword)
-        {
-            LLString::convertToF32(value, mPassHours);
-        }
-        else if ("box" == keyword)
-        {
-            // deprecated
-        }
-        else if ("aabb_min" == keyword)
-        {
-            sscanf(value.c_str(), "%f %f %f", 
-                   &mAABBMin.mV[VX], &mAABBMin.mV[VY], &mAABBMin.mV[VZ]);
-        }
-        else if ("use_access_group" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_USE_ACCESS_GROUP, setting);
-        }
-        else if ("use_access_list" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_USE_ACCESS_LIST, setting);
-        }
-        else if ("use_ban_list" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_USE_BAN_LIST, setting);
-        }
-        else if ("group_name" == keyword)
-        {
-            llinfos << "found deprecated keyword group_name" << llendl;
-        }
-        else if ("group_id" == keyword)
-        {
-            mGroupID.set( value.c_str() );
-        }
-        // TODO: DEPRECATED FLAG
-        // Flag removed from simstate files in 1.11.1
-        // Keep if statement until we have guarenteed this flag
-        // no longer exists anywhere in simstate files.
-        else if ("require_identified" == keyword)
-        {
-// 			LLString::convertToU32(value, setting);
-// 			setParcelFlag(PF_DENY_ANONYMOUS, setting);
-        }
-        // TODO: DEPRECATED FLAG
-        // Flag removed from simstate files in 1.11.1
-        // Keep if statement until we have guarenteed this flag
-        // no longer exists anywhere in simstate files.
-        else if ("require_transacted" == keyword)
-        {
-// 			LLString::convertToU32(value, setting);
-// 			setParcelFlag(PF_DENY_ANONYMOUS, setting);
-// 			setParcelFlag(PF_DENY_IDENTIFIED, setting);
-        }
-        else if ("restrict_pushobject" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_RESTRICT_PUSHOBJECT, setting);
-        }
-        else if ("deny_anonymous" == keyword)
-        {
-            LLString::convertToU32(value, setting);
-            setParcelFlag(PF_DENY_ANONYMOUS, setting);
-        }
-        // TODO: DEPRECATED FLAG
-        // Keep if statement until we have guarenteed this flag
-        // no longer exists anywhere in simstate files.
+	U32 setting;
+	S32 secs_until_revert = 0;
+
+	skip_to_end_of_next_keyword("{", input_stream);
+	if (!input_stream.good()) 
+	{
+		llwarns << "LLParcel::importStream() - bad input_stream" << llendl;
+		return FALSE;
+	}
+
+	while (input_stream.good())
+	{
+		skip_comments_and_emptyspace(input_stream);
+		LLString line, keyword, value;
+		get_line(line, input_stream, MAX_STRING);
+		get_keyword_and_value(keyword, value, line);
+
+		if ("}" == keyword)
+		{
+			break;
+		}
+		else if ("parcel_id" == keyword)
+		{
+			mID.set(value.c_str());
+		}
+		else if ("status" == keyword)
+		{
+			mStatus = ownership_string_to_status(value.c_str());
+		}
+		else if ("category" == keyword)
+		{
+			mCategory = category_string_to_category(value.c_str());
+		}
+		else if ("local_id" == keyword)
+		{
+			LLString::convertToS32(value, mLocalID);
+		}
+		else if ("name" == keyword)
+		{
+			setName( value );
+		}
+		else if ("desc" == keyword)
+		{
+			setDesc( value );
+		}
+		else if ("music_url" == keyword)
+		{
+			setMusicURL( value );
+		}
+		else if ("media_url" == keyword)
+		{
+			setMediaURL( value );
+		}
+		else if ("media_desc" == keyword)
+		{
+			setMediaDesc( value.c_str() );
+		}
+		else if ("media_type" == keyword)
+		{
+			setMediaType( value.c_str() );
+		}
+		else if ("media_width" == keyword)
+		{
+			S32 width;
+			LLString::convertToS32(value, width);
+			setMediaWidth( width );
+		}
+		else if ("media_height" == keyword)
+		{
+			S32 height;
+			LLString::convertToS32(value, height);
+			setMediaHeight( height );
+		}
+		else if ("media_id" == keyword)
+		{
+			mMediaID.set( value.c_str() );
+		}
+		else if ("media_auto_scale" == keyword)
+		{
+			LLString::convertToU8(value, mMediaAutoScale);
+		}
+		else if ("media_loop" == keyword)
+		{
+			LLString::convertToU8(value, mMediaLoop);
+		}
+		else if ("obscure_media" == keyword)
+		{
+			LLString::convertToU8(value, mObscureMedia);
+		}		
+		else if ("obscure_music" == keyword)
+		{
+			LLString::convertToU8(value, mObscureMusic);
+		}		
+		else if ("owner_id" == keyword)
+		{
+			mOwnerID.set( value.c_str() );
+		}
+		else if ("group_owned" == keyword)
+		{
+			LLString::convertToBOOL(value, mGroupOwned);
+		}
+		else if ("clean_other_time" == keyword)
+		{
+			S32 time;
+			LLString::convertToS32(value, time);
+			setCleanOtherTime(time);
+		}
+		else if ("auth_buyer_id" == keyword)
+		{
+			mAuthBuyerID.set(value.c_str());
+		}
+		else if ("snapshot_id" == keyword)
+		{
+			mSnapshotID.set(value.c_str());
+		}
+		else if ("user_location" == keyword)
+		{
+			sscanf(value.c_str(), "%f %f %f",
+				&mUserLocation.mV[VX],
+				&mUserLocation.mV[VY],
+				&mUserLocation.mV[VZ]);
+		}
+		else if ("user_look_at" == keyword)
+		{
+			sscanf(value.c_str(), "%f %f %f",
+				&mUserLookAt.mV[VX],
+				&mUserLookAt.mV[VY],
+				&mUserLookAt.mV[VZ]);
+		}
+		else if ("landing_type" == keyword)
+		{
+			S32 landing_type = 0;
+			LLString::convertToS32(value, landing_type);
+			mLandingType = (ELandingType) landing_type;
+		}
+		else if ("join_neighbors" == keyword)
+		{
+			llinfos << "found deprecated keyword join_neighbors" << llendl;
+		}
+		else if ("revert_sale" == keyword)
+		{
+			LLString::convertToS32(value, secs_until_revert);
+			if (secs_until_revert > 0)
+			{
+				mSaleTimerExpires.start();
+				mSaleTimerExpires.setTimerExpirySec((F32)secs_until_revert);
+			}
+		}
+		else if("extended_grace" == keyword)
+		{
+			LLString::convertToS32(value, mGraceExtension);
+		}
+		else if ("user_list_type" == keyword)
+		{
+			// deprecated
+		}
+		else if("auction_id" == keyword)
+		{
+			LLString::convertToU32(value, mAuctionID);
+		}
+		else if ("allow_modify" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_CREATE_OBJECTS, setting);
+		}
+		else if ("allow_group_modify" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_CREATE_GROUP_OBJECTS, setting);
+		}
+		else if ("allow_all_object_entry" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_ALLOW_ALL_OBJECT_ENTRY, setting);
+		}
+		else if ("allow_group_object_entry" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_ALLOW_GROUP_OBJECT_ENTRY, setting);
+		}
+		else if ("allow_deed_to_group" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_ALLOW_DEED_TO_GROUP, setting);
+		}
+		else if("contribute_with_deed" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_CONTRIBUTE_WITH_DEED, setting);
+		}
+		else if ("allow_terraform" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_ALLOW_TERRAFORM, setting);
+		}
+		else if ("allow_damage" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_ALLOW_DAMAGE, setting);
+		}
+		else if ("allow_fly" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_ALLOW_FLY, setting);
+		}
+		else if ("allow_landmark" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_ALLOW_LANDMARK, setting);
+		}
+		else if ("sound_local" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_SOUND_LOCAL, setting);
+		}
+		else if ("allow_group_scripts" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_ALLOW_GROUP_SCRIPTS, setting);
+		}
+		else if ("allow_voice_chat" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_ALLOW_VOICE_CHAT, setting);
+		}
+		else if ("use_estate_voice_chan" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_USE_ESTATE_VOICE_CHAN, setting);
+		}
+		else if ("allow_scripts" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_ALLOW_OTHER_SCRIPTS, setting);
+		}
+		else if ("for_sale" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_FOR_SALE, setting);
+		}
+		else if ("sell_w_objects" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_SELL_PARCEL_OBJECTS, setting);
+		}
+		else if ("use_pass_list" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_USE_PASS_LIST, setting);
+		}
+		else if ("show_directory" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_SHOW_DIRECTORY, setting);
+		}
+		else if ("allow_publish" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_ALLOW_PUBLISH, setting);
+		}
+		else if ("mature_publish" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_MATURE_PUBLISH, setting);
+		}
+		else if ("claim_date" == keyword)
+		{
+			// BUG: This will fail when time rolls over in 2038.
+			S32 time;
+			LLString::convertToS32(value, time);
+			mClaimDate = time;
+		}
+		else if ("claim_price" == keyword)
+		{
+			LLString::convertToS32(value, mClaimPricePerMeter);
+		}
+		else if ("rent_price" == keyword)
+		{
+			LLString::convertToS32(value, mRentPricePerMeter);
+		}
+		else if ("discount_rate" == keyword)
+		{
+			LLString::convertToF32(value, mDiscountRate);
+		}
+		else if ("draw_distance" == keyword)
+		{
+			LLString::convertToF32(value, mDrawDistance);
+		}
+		else if ("sale_price" == keyword)
+		{
+			LLString::convertToS32(value, mSalePrice);
+		}
+		else if ("pass_price" == keyword)
+		{
+			LLString::convertToS32(value, mPassPrice);
+		}
+		else if ("pass_hours" == keyword)
+		{
+			LLString::convertToF32(value, mPassHours);
+		}
+		else if ("box" == keyword)
+		{
+			// deprecated
+		}
+		else if ("aabb_min" == keyword)
+		{
+			sscanf(value.c_str(), "%f %f %f", 
+				&mAABBMin.mV[VX], &mAABBMin.mV[VY], &mAABBMin.mV[VZ]);
+		}
+		else if ("use_access_group" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_USE_ACCESS_GROUP, setting);
+		}
+		else if ("use_access_list" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_USE_ACCESS_LIST, setting);
+		}
+		else if ("use_ban_list" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_USE_BAN_LIST, setting);
+		}
+		else if ("group_name" == keyword)
+		{
+			llinfos << "found deprecated keyword group_name" << llendl;
+		}
+		else if ("group_id" == keyword)
+		{
+			mGroupID.set( value.c_str() );
+		}
+		// TODO: DEPRECATED FLAG
+		// Flag removed from simstate files in 1.11.1
+		// Remove at some point where we have guarenteed this flag
+		// no longer exists anywhere in simstate files.
+		else if ("require_identified" == keyword)
+		{
+			// LLString::convertToU32(value, setting);
+			// setParcelFlag(PF_DENY_ANONYMOUS, setting);
+		}
+		// TODO: DEPRECATED FLAG
+		// Flag removed from simstate files in 1.11.1
+		// Remove at some point where we have guarenteed this flag
+		// no longer exists anywhere in simstate files.
+		else if ("require_transacted" == keyword)
+		{
+			// LLString::convertToU32(value, setting);
+			// setParcelFlag(PF_DENY_ANONYMOUS, setting);
+			// setParcelFlag(PF_DENY_IDENTIFIED, setting);
+		}
+		else if ("restrict_pushobject" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_RESTRICT_PUSHOBJECT, setting);
+		}
+		else if ("deny_anonymous" == keyword)
+		{
+			LLString::convertToU32(value, setting);
+			setParcelFlag(PF_DENY_ANONYMOUS, setting);
+		}
 		else if ("deny_identified" == keyword)
 		{
 // 			LLString::convertToU32(value, setting);
@@ -1018,211 +1091,223 @@ BOOL LLParcel::importAccessEntry(std::istream& input_stream, LLAccessEntry* entr
 
 BOOL LLParcel::exportStream(std::ostream& output_stream)
 {
-    S32 setting;
-    char id_string[MAX_STRING]; /* Flawfinder: ignore */
-    
-    std::ios::fmtflags old_flags = output_stream.flags();
-    output_stream.setf(std::ios::showpoint);
-    output_stream << "\t{\n";
-    
-    mID.toString(id_string);
-    output_stream << "\t\t parcel_id							 " << id_string << "\n";
-    output_stream << "\t\t status										 " << ownership_status_to_string(mStatus) << "\n";
-    output_stream << "\t\t category								 " << category_to_string(mCategory) << "\n";
-    
-    output_stream << "\t\t local_id								 " << mLocalID	 << "\n";
-    
-    const char* name = (mName.empty() ? "" : mName.c_str() );
-    output_stream << "\t\t name												 " << name << "\n";
-    
-    const char* desc = (mDesc.empty() ? "" : mDesc.c_str() );
-    output_stream << "\t\t desc												 " << desc << "\n";
-    
-    const char* music_url = (mMusicURL.empty() ? "" : mMusicURL.c_str() );
-    output_stream << "\t\t music_url							 " << music_url << "\n";
-    
-    const char* media_url = (mMediaURL.empty() ? "" : mMediaURL.c_str() );
-    output_stream << "\t\t media_url							 " << media_url << "\n";
-    
-    output_stream << "\t\t media_auto_scale " << (mMediaAutoScale ? 1 : 0)	 << "\n";
-    
-    mMediaID.toString(id_string);
-    output_stream << "\t\t media_id								 " << id_string	 << "\n";
-    
-    mOwnerID.toString(id_string);
-    output_stream << "\t\t owner_id								 " << id_string	 << "\n";
-    output_stream << "\t\t group_owned			 " << (mGroupOwned ? 1 : 0)	 << "\n";
-    output_stream << "\t\t clean_other_time " << getCleanOtherTime() << "\n";
-    
-    if(!mAuthBuyerID.isNull())
-    {
-        mAuthBuyerID.toString(id_string);
-        output_stream << "\t\t auth_buyer_id			 " << id_string << "\n";
-    }
-    if (!mSnapshotID.isNull())
-    {
-        mSnapshotID.toString(id_string);
-        output_stream << "\t\t snapshot_id					 " << id_string << "\n";
-    }
-    if (!mUserLocation.isExactlyZero())
-    {
-        output_stream << "\t\t user_location " 
-        << (F64)mUserLocation.mV[VX]
-        << " " << (F64)mUserLocation.mV[VY]
-        << " " << (F64)mUserLocation.mV[VZ] << "\n";
-        output_stream << "\t\t user_look_at " 
-            << (F64)mUserLookAt.mV[VX]
-            << " " << (F64)mUserLookAt.mV[VY]
-            << " " << (F64)mUserLookAt.mV[VZ] << "\n";
-    }
-    output_stream << "\t\t landing_type " << mLandingType << "\n";
-    //if(mJoinNeighbors)
-    //{
-    // output_stream << "\t\t join_neighbors " << mJoinNeighbors << "\n";
-    //}
-        if(mSaleTimerExpires.getStarted())
-        {
-            S32 dt_sec = (S32) mSaleTimerExpires.getRemainingTimeF32()+60; // Add a minute to prevent race conditions
-            output_stream << "\t\t revert_sale					 " << dt_sec << "\n";
-            //output_stream << "\t\t revert_action			 " << revert_action_to_string(mExpireAction) << "\n";
-            output_stream << "\t\t extended_grace		 " << mGraceExtension << "\n";
-        }
-        
-        if(0 != mAuctionID)
-        {
-            output_stream << "\t\t auction_id						 " << mAuctionID << "\n";
-        }
-        
-        output_stream << "\t\t allow_modify				 " << getAllowModify()	 << "\n";
-        output_stream << "\t\t allow_group_modify				 " << getAllowGroupModify()	 << "\n";
-        output_stream << "\t\t allow_all_object_entry				 " << getAllowAllObjectEntry()	 << "\n";
-        output_stream << "\t\t allow_group_object_entry				 " << getAllowGroupObjectEntry()	 << "\n";
-        output_stream << "\t\t allow_terraform	 " << getAllowTerraform()	 << "\n";
-        output_stream << "\t\t allow_deed_to_group " << getAllowDeedToGroup()	 << "\n";
-        output_stream << "\t\t contribute_with_deed " << getContributeWithDeed() << "\n";
-        output_stream << "\t\t allow_damage				 " << getAllowDamage()	 << "\n";
-        output_stream << "\t\t claim_date						 " << (S32)mClaimDate	 << "\n";
-        output_stream << "\t\t claim_price					 " << mClaimPricePerMeter	 << "\n";
-        output_stream << "\t\t rent_price						 " << mRentPricePerMeter	 << "\n";
-        output_stream << "\t\t discount_rate			 " << mDiscountRate	 << "\n";
-        output_stream << "\t\t allow_fly							 " << (getAllowFly()					 ? 1 : 0)	 << "\n";
-        output_stream << "\t\t allow_landmark		 " << (getAllowLandmark() ? 1 : 0)	 << "\n";
-        output_stream << "\t\t sound_local			 " << (getSoundLocal() ? 1 : 0)	 << "\n";
-        output_stream << "\t\t allow_scripts			 " << (getAllowOtherScripts()	 ? 1 : 0)	 << "\n";
-        output_stream << "\t\t allow_group_scripts			 " << (getAllowGroupScripts()	 ? 1 : 0)	 << "\n";
-        output_stream << "\t\t allow_voice_chat			 " << (getVoiceEnabled() ? 1 : 0) << "\n";
-        output_stream << "\t\t use_estate_voice_chan		 " << (getVoiceUseEstateChannel() ? 1 : 0) << "\n";
-        output_stream << "\t\t for_sale								 " << (getForSale()						 ? 1 : 0)	 << "\n";
-        output_stream << "\t\t sell_w_objects		 " << (getSellWithObjects() ? 1 : 0)	 << "\n";
-        output_stream << "\t\t draw_distance			 " << mDrawDistance	 << "\n";
-        output_stream << "\t\t sale_price						 " << mSalePrice	 << "\n";
-        
-        setting = (getParcelFlag(PF_USE_ACCESS_GROUP) ? 1 : 0);
-        output_stream << "\t\t use_access_group " << setting	 << "\n";
-        
-        setting = (getParcelFlag(PF_USE_ACCESS_LIST) ? 1 : 0);
-        output_stream << "\t\t use_access_list	 " << setting	 << "\n";
-        
-        setting = (getParcelFlag(PF_USE_BAN_LIST) ? 1 : 0);
-        output_stream << "\t\t use_ban_list				 " << setting	 << "\n";
-        
-        mGroupID.toString(id_string);
-        output_stream << "\t\t group_id	 " << id_string	 << "\n";
-        
-        //const char* group_name
-        // = (mGroupName.isEmpty() ? "" : mGroupName.c_str() );
-        //output_stream << "\t\t group_name " << group_name << "\n";
-        
-        setting = (getParcelFlag(PF_USE_PASS_LIST) ? 1 : 0);
-        output_stream << "\t\t use_pass_list			 " << setting	 << "\n";
-        
-        output_stream << "\t\t pass_price						 " << mPassPrice	 << "\n";
-        output_stream << "\t\t pass_hours						 " << mPassHours	 << "\n";
-        
-        setting = (getParcelFlag(PF_SHOW_DIRECTORY) ? 1 : 0);
-        output_stream << "\t\t show_directory		 " << setting	 << "\n";
-        
-        setting = (getParcelFlag(PF_ALLOW_PUBLISH) ? 1 : 0);
-        output_stream << "\t\t allow_publish				 " << setting	 << "\n";
-        
-        setting = (getParcelFlag(PF_MATURE_PUBLISH) ? 1 : 0);
-        output_stream << "\t\t mature_publish				 " << setting	 << "\n";
-        
-        setting = (getParcelFlag(PF_DENY_ANONYMOUS) ? 1 : 0);
-        output_stream << "\t\t deny_anonymous				 " << setting	 << "\n";
-        
-// 		setting = (getParcelFlag(PF_DENY_IDENTIFIED) ? 1 : 0);
-// 		output_stream << "\t\t deny_identified				 " << setting	 << "\n";
-		
-// 		setting = (getParcelFlag(PF_DENY_TRANSACTED) ? 1 : 0);
-// 		output_stream << "\t\t deny_transacted				 " << setting	 << "\n";
-        
-        setting = (getParcelFlag(PF_DENY_AGEUNVERIFIED) ? 1 : 0);
-        output_stream << "\t\t deny_age_unverified			 " << setting  << "\n";
-        
-        setting = (getParcelFlag(PF_RESTRICT_PUSHOBJECT) ? 1 : 0);
-        output_stream << "\t\t restrict_pushobject " << setting	 << "\n";
-        
-        output_stream << "\t\t aabb_min								 " 
-            << mAABBMin.mV[VX]
-            << " " << mAABBMin.mV[VY]
-            << " " << mAABBMin.mV[VZ] << "\n";
-        
-        if (!mAccessList.empty())
-        {
-            output_stream << "\t\t access_list " << mAccessList.size()	 << "\n";
-            access_map_const_iterator cit = mAccessList.begin();
-            access_map_const_iterator end = mAccessList.end();
-            
-            for ( ; cit != end; ++cit)
-            {
-                output_stream << "\t\t{\n";
-                const LLAccessEntry& entry = (*cit).second;
-                entry.mID.toString(id_string);
-                output_stream << "\t\t\tid " << id_string << "\n";
-                output_stream << "\t\t\ttime " << entry.mTime	 << "\n";
-                output_stream << "\t\t\tflags " << entry.mFlags	 << "\n";
-                output_stream << "\t\t}\n";
-            }
-        }
-        
-        if (!mBanList.empty())
-        {
-            output_stream << "\t\t ban_list " << mBanList.size()	 << "\n";
-            access_map_const_iterator cit = mBanList.begin();
-            access_map_const_iterator end = mBanList.end();
-            
-            for ( ; cit != end; ++cit)
-            {
-                output_stream << "\t\t{\n";
-                const LLAccessEntry& entry = (*cit).second;
-                entry.mID.toString(id_string);
-                output_stream << "\t\t\tid " << id_string << "\n";
-                output_stream << "\t\t\ttime " << entry.mTime	 << "\n";
-                output_stream << "\t\t\tflags " << entry.mFlags	 << "\n";
-                output_stream << "\t\t}\n";
-            }
-        }
-        
-        /*if (mRenterList.count() > 0)
-        {
-            output_stream << "\t\t renter_list " << mRenterList.count()	 << "\n";
-            for (i = 0; i < mRenterList.count(); i++)
-            {
-                output_stream << "\t\t{\n";
-                const LLAccessEntry& entry = mRenterList.get(i);
-                entry.mID.toString(id_string);
-                output_stream << "\t\t\tid " << id_string << "\n";
-                output_stream << "\t\t\ttime " << entry.mTime	 << "\n";
-                output_stream << "\t\t\tflags " << entry.mFlags	 << "\n";
-                output_stream << "\t\t}\n";
-            }
-        }*/
-        
-        output_stream << "\t}\n";
-        output_stream.flags(old_flags);
-        
-        return TRUE;
+	S32 setting;
+	char id_string[MAX_STRING];	/* Flawfinder: ignore */
+
+	std::ios::fmtflags old_flags = output_stream.flags();
+	output_stream.setf(std::ios::showpoint);
+	output_stream << "\t{\n";
+
+	mID.toString(id_string);
+	output_stream << "\t\t parcel_id        " << id_string << "\n";
+	output_stream << "\t\t status           " << ownership_status_to_string(mStatus) << "\n";
+	output_stream << "\t\t category         " << category_to_string(mCategory) << "\n";
+
+	output_stream << "\t\t local_id         " << mLocalID  << "\n";
+
+	const char* name = (mName.empty() ? "" : mName.c_str() );
+	output_stream << "\t\t name             " << name << "\n";
+
+	const char* desc = (mDesc.empty() ? "" : mDesc.c_str() );
+	output_stream << "\t\t desc             " << desc << "\n";
+
+	const char* music_url = (mMusicURL.empty() ? "" : mMusicURL.c_str() );
+	output_stream << "\t\t music_url        " << music_url << "\n";
+
+	const char* media_url = (mMediaURL.empty() ? "" : mMediaURL.c_str() );
+	output_stream << "\t\t media_url        " << media_url << "\n";
+
+	const char* media_type = (mMediaType.empty() ? "" : mMediaType.c_str() );
+	output_stream << "\t\t media_type             " << media_type << "\n";
+
+	const char* media_desc = (mMediaDesc.empty() ? "" : mMediaDesc.c_str() );
+	output_stream << "\t\t media_desc             " << media_desc << "\n";
+
+	output_stream << "\t\t media_auto_scale " << (mMediaAutoScale ? 1 : 0)  << "\n";
+	output_stream << "\t\t media_loop " << (mMediaLoop ? 1 : 0)  << "\n";
+	output_stream << "\t\t obscure_media " << (mObscureMedia ? 1 : 0)  << "\n";
+	output_stream << "\t\t obscure_music " << (mObscureMusic ? 1 : 0)  << "\n";
+
+	mMediaID.toString(id_string);
+	output_stream << "\t\t media_id         " << id_string  << "\n";
+
+	output_stream << "\t\t media_width     " << mMediaWidth  << "\n";
+	output_stream << "\t\t media_height     " << mMediaHeight  << "\n";
+
+	mOwnerID.toString(id_string);
+	output_stream << "\t\t owner_id         " << id_string  << "\n";
+	output_stream << "\t\t group_owned	   " << (mGroupOwned ? 1 : 0)  << "\n";
+	output_stream << "\t\t clean_other_time " << getCleanOtherTime() << "\n";
+
+	if(!mAuthBuyerID.isNull())
+	{
+		mAuthBuyerID.toString(id_string);
+		output_stream << "\t\t auth_buyer_id    " << id_string << "\n";
+	}
+	if (!mSnapshotID.isNull())
+	{
+		mSnapshotID.toString(id_string);
+		output_stream << "\t\t snapshot_id      " << id_string << "\n";
+	}
+	if (!mUserLocation.isExactlyZero())
+	{
+		output_stream << "\t\t user_location " 
+			<< (F64)mUserLocation.mV[VX]
+			<< " " << (F64)mUserLocation.mV[VY]
+			<< " " << (F64)mUserLocation.mV[VZ] << "\n";
+		output_stream << "\t\t user_look_at " 
+			<< (F64)mUserLookAt.mV[VX]
+			<< " " << (F64)mUserLookAt.mV[VY]
+			<< " " << (F64)mUserLookAt.mV[VZ] << "\n";
+	}
+	output_stream << "\t\t landing_type " << mLandingType << "\n";
+	//if(mJoinNeighbors)
+	//{
+	//	output_stream << "\t\t join_neighbors " << mJoinNeighbors << "\n";
+	//}
+	if(mSaleTimerExpires.getStarted())
+	{
+		S32 dt_sec = (S32) mSaleTimerExpires.getRemainingTimeF32()+60; // Add a minute to prevent race conditions
+		output_stream << "\t\t revert_sale      " << dt_sec << "\n";
+		//output_stream << "\t\t revert_action    " << revert_action_to_string(mExpireAction) << "\n";
+		output_stream << "\t\t extended_grace   " << mGraceExtension << "\n";
+	}
+
+	if(0 != mAuctionID)
+	{
+		output_stream << "\t\t auction_id       " << mAuctionID << "\n";
+	}
+
+	output_stream << "\t\t allow_modify     " << getAllowModify()  << "\n";
+	output_stream << "\t\t allow_group_modify     " << getAllowGroupModify()  << "\n";
+	output_stream << "\t\t allow_all_object_entry     " << getAllowAllObjectEntry()  << "\n";
+	output_stream << "\t\t allow_group_object_entry     " << getAllowGroupObjectEntry()  << "\n";
+	output_stream << "\t\t allow_terraform  " << getAllowTerraform()  << "\n";
+	output_stream << "\t\t allow_deed_to_group " << getAllowDeedToGroup()  << "\n";
+	output_stream << "\t\t contribute_with_deed " << getContributeWithDeed() << "\n";
+	output_stream << "\t\t allow_damage     " << getAllowDamage()  << "\n";
+	output_stream << "\t\t claim_date       " << (S32)mClaimDate  << "\n";
+	output_stream << "\t\t claim_price      " << mClaimPricePerMeter  << "\n";
+	output_stream << "\t\t rent_price       " << mRentPricePerMeter  << "\n";
+	output_stream << "\t\t discount_rate    " << mDiscountRate  << "\n";
+	output_stream << "\t\t allow_fly        " << (getAllowFly()      ? 1 : 0)  << "\n";
+	output_stream << "\t\t allow_landmark   " << (getAllowLandmark() ? 1 : 0)  << "\n";
+	output_stream << "\t\t sound_local	   " << (getSoundLocal() ? 1 : 0)  << "\n";
+	output_stream << "\t\t allow_scripts    " << (getAllowOtherScripts()  ? 1 : 0)  << "\n";
+	output_stream << "\t\t allow_group_scripts    " << (getAllowGroupScripts()  ? 1 : 0)  << "\n";
+	output_stream << "\t\t allow_voice_chat    " << (getVoiceEnabled() ? 1 : 0) << "\n";
+	output_stream << "\t\t use_estate_voice_chan   " << (getVoiceUseEstateChannel() ? 1 : 0) << "\n";
+	output_stream << "\t\t for_sale         " << (getForSale()       ? 1 : 0)  << "\n";
+	output_stream << "\t\t sell_w_objects   " << (getSellWithObjects()	? 1 : 0)  << "\n";
+	output_stream << "\t\t draw_distance    " << mDrawDistance  << "\n";
+	output_stream << "\t\t sale_price       " << mSalePrice  << "\n";
+
+	setting = (getParcelFlag(PF_USE_ACCESS_GROUP) ? 1 : 0);
+	output_stream << "\t\t use_access_group " << setting  << "\n";
+
+	setting = (getParcelFlag(PF_USE_ACCESS_LIST) ? 1 : 0);
+	output_stream << "\t\t use_access_list  " << setting  << "\n";
+
+	setting = (getParcelFlag(PF_USE_BAN_LIST) ? 1 : 0);
+	output_stream << "\t\t use_ban_list     " << setting  << "\n";
+
+	mGroupID.toString(id_string);
+	output_stream << "\t\t group_id  " << id_string  << "\n";
+
+	//const char* group_name
+	//	= (mGroupName.isEmpty() ? "" : mGroupName.c_str() );
+	//output_stream << "\t\t group_name " << group_name << "\n";
+
+	setting = (getParcelFlag(PF_USE_PASS_LIST) ? 1 : 0);
+	output_stream << "\t\t use_pass_list    " << setting  << "\n";
+
+	output_stream << "\t\t pass_price       " << mPassPrice  << "\n";
+	output_stream << "\t\t pass_hours       " << mPassHours  << "\n";
+
+	setting = (getParcelFlag(PF_SHOW_DIRECTORY) ? 1 : 0);
+	output_stream << "\t\t show_directory   " << setting  << "\n";
+
+	setting = (getParcelFlag(PF_ALLOW_PUBLISH) ? 1 : 0);
+	output_stream << "\t\t allow_publish     " << setting  << "\n";
+
+	setting = (getParcelFlag(PF_MATURE_PUBLISH) ? 1 : 0);
+	output_stream << "\t\t mature_publish     " << setting  << "\n";
+
+	setting = (getParcelFlag(PF_DENY_ANONYMOUS) ? 1 : 0);
+	output_stream << "\t\t deny_anonymous     " << setting  << "\n";
+
+//	setting = (getParcelFlag(PF_DENY_IDENTIFIED) ? 1 : 0);
+//	output_stream << "\t\t deny_identified     " << setting  << "\n";
+
+//	setting = (getParcelFlag(PF_DENY_TRANSACTED) ? 1 : 0);
+//	output_stream << "\t\t deny_transacted     " << setting  << "\n";
+
+	setting = (getParcelFlag(PF_DENY_AGEUNVERIFIED) ? 1 : 0);
+	output_stream << "\t\t deny_age_unverified			 " << setting  << "\n";
+
+	setting = (getParcelFlag(PF_RESTRICT_PUSHOBJECT) ? 1 : 0);
+	output_stream << "\t\t restrict_pushobject " << setting  << "\n";
+
+	output_stream << "\t\t aabb_min         " 
+		<< mAABBMin.mV[VX]
+		<< " " << mAABBMin.mV[VY]
+		<< " " << mAABBMin.mV[VZ] << "\n";
+
+	if (!mAccessList.empty())
+	{
+		output_stream << "\t\t access_list " << mAccessList.size()  << "\n";
+		access_map_const_iterator cit = mAccessList.begin();
+		access_map_const_iterator end = mAccessList.end();
+
+		for ( ; cit != end; ++cit)
+		{
+			output_stream << "\t\t{\n";
+			const LLAccessEntry& entry = (*cit).second;
+			entry.mID.toString(id_string);
+			output_stream << "\t\t\tid " << id_string << "\n";
+			output_stream << "\t\t\ttime " << entry.mTime  << "\n";
+			output_stream << "\t\t\tflags " << entry.mFlags  << "\n";
+			output_stream << "\t\t}\n";
+		}
+	}
+
+	if (!mBanList.empty())
+	{
+		output_stream << "\t\t ban_list " << mBanList.size()  << "\n";
+		access_map_const_iterator cit = mBanList.begin();
+		access_map_const_iterator end = mBanList.end();
+
+		for ( ; cit != end; ++cit)
+		{
+			output_stream << "\t\t{\n";
+			const LLAccessEntry& entry = (*cit).second;
+			entry.mID.toString(id_string);
+			output_stream << "\t\t\tid " << id_string << "\n";
+			output_stream << "\t\t\ttime " << entry.mTime  << "\n";
+			output_stream << "\t\t\tflags " << entry.mFlags  << "\n";
+			output_stream << "\t\t}\n";
+		}
+	}
+
+	/*if (mRenterList.count() > 0)
+	{
+		output_stream << "\t\t renter_list " << mRenterList.count()  << "\n";
+		for (i = 0; i < mRenterList.count(); i++)
+		{
+			output_stream << "\t\t{\n";
+			const LLAccessEntry& entry = mRenterList.get(i);
+			entry.mID.toString(id_string);
+			output_stream << "\t\t\tid " << id_string << "\n";
+			output_stream << "\t\t\ttime " << entry.mTime  << "\n";
+			output_stream << "\t\t\tflags " << entry.mFlags  << "\n";
+			output_stream << "\t\t}\n";
+		}
+	}*/
+
+	output_stream << "\t}\n";
+	output_stream.flags(old_flags);
+
+	return TRUE;
 }
 
 
@@ -1248,6 +1333,37 @@ void LLParcel::packMessage(LLMessageSystem* msg)
     msg->addU8Fast(	 _PREHASH_LandingType, (U8)mLandingType);
 }
 
+// Assumes we are in a block "ParcelData"
+void LLParcel::packMessage(LLSD& msg)
+{
+	msg["local_id"] = getLocalID();
+	msg["flags"] = ll_sd_from_U32(getParcelFlags());
+	msg["sale_price"] = getSalePrice();
+	msg["name"] = getName();
+	msg["description"] = getDesc();
+	msg["music_url"] = getMusicURL();
+	msg["media_url"] = getMediaURL();
+	msg["media_desc"] = getMediaDesc();
+	msg["media_type"] = getMediaType();
+	msg["media_width"] = getMediaWidth();
+	msg["media_height"] = getMediaHeight();
+	msg["auto_scale"] = getMediaAutoScale();
+	msg["media_loop"] = getMediaLoop();
+	msg["obscure_media"] = getObscureMedia();
+	msg["obscure_music"] = getObscureMusic();
+	msg["media_id"] = getMediaID();
+	msg["group_id"] = getGroupID();
+	msg["pass_price"] = mPassPrice;
+	msg["pass_hours"] = mPassHours;
+	msg["category"] = (U8)mCategory;
+	msg["auth_buyer_id"] = mAuthBuyerID;
+	msg["snapshot_id"] = mSnapshotID;
+	msg["snapshot_id"] = mSnapshotID;
+	msg["user_location"] = ll_sd_from_vector3(mUserLocation);
+	msg["user_look_at"] = ll_sd_from_vector3(mUserLookAt);
+	msg["landing_type"] = (U8)mLandingType;
+}
+
 
 void LLParcel::unpackMessage(LLMessageSystem* msg)
 {
@@ -1281,8 +1397,30 @@ void LLParcel::unpackMessage(LLMessageSystem* msg)
     U8 landing_type;
     msg->getU8Fast(	 _PREHASH_ParcelData,_PREHASH_LandingType, landing_type);
     mLandingType = (ELandingType)landing_type;
-}
 
+	// New Media Data
+	// Note: the message has been converted to TCP
+	if(msg->getNumberOfBlocks("MediaData") > 0)
+	{
+		msg->getString("MediaData", "MediaDesc", 256, buffer);
+		setMediaDesc(buffer);
+		msg->getString("MediaData", "MediaType", 256, buffer);
+		setMediaType(buffer);
+		msg->getS32("MediaData", "MediaWidth", mMediaWidth);
+		msg->getS32("MediaData", "MediaHeight", mMediaHeight);
+		msg->getU8 ( "MediaData", "MediaLoop", mMediaLoop );
+		msg->getU8 ( "MediaData", "ObscureMedia", mObscureMedia );
+		msg->getU8 ( "MediaData", "ObscureMusic", mObscureMusic );
+	}
+	else
+	{
+		setMediaType("video/vnd.secondlife.qt.legacy");
+		setMediaDesc("No Description available without Server Upgrade");
+		mMediaLoop = true;
+		mObscureMedia = true;
+		mObscureMusic = true;
+	}
+}
 
 void LLParcel::packAccessEntries(LLMessageSystem* msg,
 								 const std::map<LLUUID,LLAccessEntry>& list)
@@ -1702,27 +1840,34 @@ BOOL LLParcel::isBuyerAuthorized(const LLUUID& buyer_id) const
 
 void LLParcel::clearParcel()
 {
-    overrideParcelFlags(PF_DEFAULT);
-    setName(NULL);
-    setDesc(NULL);
-    setMusicURL(NULL);
-    setMediaURL(NULL);
-    setMediaID(LLUUID::null);
-    setMediaAutoScale(0);
-    setInEscrow(FALSE);
-    setAuthorizedBuyerID(LLUUID::null);
-    setCategory(C_NONE);
-    setSnapshotID(LLUUID::null);
-    setUserLocation(LLVector3::zero);
-    setUserLookAt(LLVector3::x_axis);
-    setLandingType(L_LANDING_POINT);
-    setAuctionID(0);
-    setGroupID(LLUUID::null);
-    setPassPrice(0);
-    setPassHours(0.f);
-    mAccessList.clear();
-    mBanList.clear();
-    //mRenterList.reset();
+	overrideParcelFlags(PF_DEFAULT);
+	setName(NULL);
+	setDesc(NULL);
+	setMediaURL(NULL);
+	setMediaType(NULL);
+	setMediaID(LLUUID::null);
+    setMediaDesc(NULL);
+	setMediaAutoScale(0);
+	setMediaLoop(TRUE);
+	mObscureMedia = 0;
+	mObscureMusic = 0;
+	mMediaWidth = 0;
+	mMediaHeight = 0;
+	setMusicURL(NULL);
+	setInEscrow(FALSE);
+	setAuthorizedBuyerID(LLUUID::null);
+	setCategory(C_NONE);
+	setSnapshotID(LLUUID::null);
+	setUserLocation(LLVector3::zero);
+	setUserLookAt(LLVector3::x_axis);
+	setLandingType(L_LANDING_POINT);
+	setAuctionID(0);
+	setGroupID(LLUUID::null);
+	setPassPrice(0);
+	setPassHours(0.f);
+	mAccessList.clear();
+	mBanList.clear();
+	//mRenterList.reset();
 }
 
 void LLParcel::dump()
@@ -1826,6 +1971,3 @@ LLParcel::ECategory category_ui_string_to_category(const char* s)
     // is a distinct option from "None" and "Other"
     return LLParcel::C_ANY;
 }
-
-
-
diff --git a/indra/llinventory/llparcel.h b/indra/llinventory/llparcel.h
index a8143f27dc4..ac5e1a1eae8 100644
--- a/indra/llinventory/llparcel.h
+++ b/indra/llinventory/llparcel.h
@@ -211,8 +211,15 @@ class LLParcel
 	void setDesc(const LLString& desc);
 	void setMusicURL(const LLString& url);
 	void setMediaURL(const LLString& url);
+	void setMediaType(const char* type);
+	void setMediaDesc(const char* desc);
 	void	setMediaID(const LLUUID& id) { mMediaID = id; }
 	void	setMediaAutoScale ( U8 flagIn ) { mMediaAutoScale = flagIn; }
+	void    setMediaLoop (U8 loop) { mMediaLoop = loop; }
+	void	setObscureMedia( U8 flagIn ) { mObscureMedia = flagIn; }
+	void	setObscureMusic( U8 flagIn ) { mObscureMusic = flagIn; }
+	void setMediaWidth(S32 width);
+	void setMediaHeight(S32 height);
 	virtual void	setLocalID(S32 local_id);
 
 	// blow away all the extra crap lurking in parcels, including urls, access lists, etc
@@ -268,6 +275,7 @@ class LLParcel
 	BOOL	exportStream(std::ostream& output_stream);
 
 	void	packMessage(LLMessageSystem* msg);
+	void	packMessage(LLSD& msg);
 	void	unpackMessage(LLMessageSystem* msg);
 
 	void	packAccessEntries(LLMessageSystem* msg,
@@ -299,8 +307,15 @@ class LLParcel
 	const LLString&	getDesc() const			{ return mDesc; }
 	const LLString&	getMusicURL() const		{ return mMusicURL; }
 	const LLString&	getMediaURL() const		{ return mMediaURL; }
+	const char*		getMediaDesc() const		{ return mMediaDesc.c_str(); }
+	const char*		getMediaType() const		{ return mMediaType.c_str(); }
 	const LLUUID&	getMediaID() const			{ return mMediaID; }
+	S32				getMediaWidth() const		{ return mMediaWidth; }
+	S32				getMediaHeight() const		{ return mMediaHeight; }
 	U8				getMediaAutoScale() const	{ return mMediaAutoScale; }
+	U8              getMediaLoop() const        { return mMediaLoop; }
+	U8				getObscureMedia() const		{ return mObscureMedia; }
+	U8				getObscureMusic() const		{ return mObscureMusic; }
 	S32				getLocalID() const			{ return mLocalID; }
 	const LLUUID&	getOwnerID() const			{ return mOwnerID; }
 	const LLUUID&	getGroupID() const			{ return mGroupID; }
@@ -576,7 +591,14 @@ class LLParcel
 	LLString 			mDesc;
 	LLString 			mMusicURL;
 	LLString 			mMediaURL;
+	std::string mMediaDesc;
+	std::string mMediaType;
+	S32					mMediaWidth;
+	S32					mMediaHeight;
 	U8					mMediaAutoScale;
+	U8                  mMediaLoop;
+	U8					mObscureMedia;
+	U8					mObscureMusic;
 	LLUUID				mMediaID;
 	S32					mPassPrice;
 	F32					mPassHours;
diff --git a/indra/llmessage/llhttpclient.cpp b/indra/llmessage/llhttpclient.cpp
index 9f6115a0e41..23295476ffd 100644
--- a/indra/llmessage/llhttpclient.cpp
+++ b/indra/llmessage/llhttpclient.cpp
@@ -38,6 +38,7 @@
 #include "llurlrequest.h"
 #include "llbufferstream.h"
 #include "llsdserialize.h"
+#include "llsdutil.h"
 #include "llvfile.h"
 #include "llvfs.h"
 #include "lluri.h"
@@ -112,7 +113,11 @@ void LLHTTPClient::Responder::completed(
 	}
 }
 
+// virtual
+void LLHTTPClient::Responder::completedHeader(U32 status, const std::string& reason, const LLSD& content)
+{
 
+}
 namespace
 {
 	class LLHTTPClientURLAdaptor : public LLURLRequestComplete
@@ -140,13 +145,19 @@ namespace
 			if (mResponder.get())
 			{
 				mResponder->completedRaw(mStatus, mReason, channels, buffer);
+				mResponder->completedHeader(mStatus, mReason, mHeaderOutput);
 			}
 		}
+		virtual void header(const std::string& header, const std::string& value)
+		{
+			mHeaderOutput[header] = value;
+		}
 
 	private:
 		LLHTTPClient::ResponderPtr mResponder;
 		U32 mStatus;
 		std::string mReason;
+		LLSD mHeaderOutput;
 	};
 	
 	class Injector : public LLIOPipe
@@ -340,11 +351,18 @@ void LLHTTPClient::get(const std::string& url, ResponderPtr responder, const LLS
 {
 	request(url, LLURLRequest::HTTP_GET, NULL, responder, headers, timeout);
 }
-
+void LLHTTPClient::getHeaderOnly(const std::string& url, ResponderPtr responder, const LLSD& headers, const F32 timeout)
+{
+	request(url, LLURLRequest::HTTP_HEAD, NULL, responder, headers, timeout);
+}
 void LLHTTPClient::get(const std::string& url, ResponderPtr responder, const F32 timeout)
 {
 	get(url, responder, LLSD(), timeout);
 }
+void LLHTTPClient::getHeaderOnly(const std::string& url, ResponderPtr responder, const F32 timeout)
+{
+	getHeaderOnly(url, responder, LLSD(), timeout);
+}
 
 void LLHTTPClient::get(const std::string& url, const LLSD& query, ResponderPtr responder, const LLSD& headers, const F32 timeout)
 {
diff --git a/indra/llmessage/llhttpclient.h b/indra/llmessage/llhttpclient.h
index 983ff46e034..1fbf0c36dc0 100644
--- a/indra/llmessage/llhttpclient.h
+++ b/indra/llmessage/llhttpclient.h
@@ -89,7 +89,11 @@ class LLHTTPClient
 				* result(), or
 				* error() 
 			*/
-			
+
+		// Override to handle parsing of the header only.  Note: this is the only place where the contents
+		// of the header can be parsed.  In the ::completed call above only the body is contained in the LLSD.
+		virtual void completedHeader(U32 status, const std::string& reason, const LLSD& content);
+
 	public: /* but not really -- don't touch this */
 		U32 mReferenceCount;
 	};
@@ -102,7 +106,10 @@ class LLHTTPClient
 	static void get(const std::string& url, const LLSD& query, ResponderPtr, const F32 timeout=HTTP_REQUEST_EXPIRY_SECS);
 	static void get(const std::string& url, const LLSD& query, ResponderPtr, const LLSD& headers, const F32 timeout=HTTP_REQUEST_EXPIRY_SECS);
 	static void put(const std::string& url, const LLSD& body, ResponderPtr, const F32 timeout=HTTP_REQUEST_EXPIRY_SECS);
-		///< non-blocking
+	static void getHeaderOnly(const std::string& url, ResponderPtr, const F32 timeout=HTTP_REQUEST_EXPIRY_SECS);
+	static void getHeaderOnly(const std::string& url, ResponderPtr, const LLSD& headers, const F32 timeout=HTTP_REQUEST_EXPIRY_SECS);
+
+	///< non-blocking
 	static void post(const std::string& url, const LLSD& body, ResponderPtr, const F32 timeout=HTTP_REQUEST_EXPIRY_SECS);
 	static void post(const std::string& url, const U8* data, S32 size, ResponderPtr responder, const F32 timeout=HTTP_REQUEST_EXPIRY_SECS);
 	static void postFile(const std::string& url, const std::string& filename, ResponderPtr, const F32 timeout=HTTP_REQUEST_EXPIRY_SECS);
diff --git a/indra/llmessage/llurlrequest.cpp b/indra/llmessage/llurlrequest.cpp
index 1cdaa1687df..631eea3e882 100644
--- a/indra/llmessage/llurlrequest.cpp
+++ b/indra/llmessage/llurlrequest.cpp
@@ -429,12 +429,10 @@ bool LLURLRequest::configure()
 	switch(mAction)
 	{
 	case HTTP_HEAD:
+		// These are in addition to the HTTP_GET options.
 		curl_easy_setopt(mDetail->mCurl, CURLOPT_HEADER, 1);
 		curl_easy_setopt(mDetail->mCurl, CURLOPT_NOBODY, 1);
-		curl_easy_setopt(mDetail->mCurl, CURLOPT_FOLLOWLOCATION, 1);
-		rv = true;
-		break;
-
+		
 	case HTTP_GET:
 		curl_easy_setopt(mDetail->mCurl, CURLOPT_HTTPGET, 1);
 		curl_easy_setopt(mDetail->mCurl, CURLOPT_FOLLOWLOCATION, 1);
diff --git a/indra/llrender/llimagegl.cpp b/indra/llrender/llimagegl.cpp
index 00f167c3236..748e405065d 100644
--- a/indra/llrender/llimagegl.cpp
+++ b/indra/llrender/llimagegl.cpp
@@ -686,7 +686,7 @@ BOOL LLImageGL::setSubImage(const U8* datap, S32 data_width, S32 data_height, S3
 		return FALSE;
 	}
 	
-	if (x_pos == 0 && y_pos == 0 && width == getWidth() && height == getHeight())
+	if (x_pos == 0 && y_pos == 0 && width == getWidth() && height == getHeight() && data_width == width && data_height == height)
 	{
 		setImage(datap, FALSE);
 	}
diff --git a/indra/llui/llcombobox.cpp b/indra/llui/llcombobox.cpp
index b4fdbfeb0e6..28237823dd6 100644
--- a/indra/llui/llcombobox.cpp
+++ b/indra/llui/llcombobox.cpp
@@ -640,12 +640,6 @@ void LLComboBox::showList()
 	// NB: this call will trigger the focuslost callback which will hide the list, so do it first
 	// before finally showing the list
 
-	if (!mList->getFirstSelected())
-	{
-		// if nothing is selected, select the first item
-		// so that the callback is not immediately triggered on setFocus()
-		mList->selectFirstItem();
-	}
 	mList->setFocus(TRUE);
 
 	// Show the list and push the button down
@@ -714,7 +708,7 @@ void LLComboBox::onButtonDown(void *userdata)
 	else
 	{
 		self->hideList();
-	}
+	} 
 
 }
 
@@ -737,30 +731,35 @@ void LLComboBox::onItemSelected(LLUICtrl* item, void *userdata)
 			self->mTextEntry->selectAll();
 		}
 	}
-	else
-	{
-		// invalid selection, just restore existing value
-		LLString orig_selection = self->mAllowTextEntry ? self->mTextEntry->getText() : self->mButton->getLabelSelected();
-
-		self->mList->selectItemByLabel(orig_selection);
-	}
-	self->onCommit();
 
+	// hiding the list reasserts the old value stored in the text editor/dropdown button
 	self->hideList();
+
+	// commit does the reverse, asserting the value in the list
+	self->onCommit();
 }
 
 BOOL LLComboBox::handleToolTip(S32 x, S32 y, LLString& msg, LLRect* sticky_rect_screen)
 {
     LLString tool_tip;
 
+	if(LLUICtrl::handleToolTip(x, y, msg, sticky_rect_screen))
+	{
+		return TRUE;
+	}
+	
 	if (LLUI::sShowXUINames)
 	{
 		tool_tip = getShowNamesToolTip();
 	}
-	else
+	else if (!mToolTipMsg.empty())
 	{
 		tool_tip = mToolTipMsg;
 	}
+	else
+	{
+		tool_tip = getValue().asString();
+	}
 
 	if( !tool_tip.empty() )
 	{
diff --git a/indra/llui/llradiogroup.cpp b/indra/llui/llradiogroup.cpp
index 53541f51286..6fba415d35f 100644
--- a/indra/llui/llradiogroup.cpp
+++ b/indra/llui/llradiogroup.cpp
@@ -245,7 +245,9 @@ void LLRadioGroup::draw()
 		radio->setValue( selected );
 		if (take_focus && selected && !gFocusMgr.childHasKeyboardFocus(radio))
 		{
-			radio->focusFirstItem();
+			// don't flash keyboard focus when navigating via keyboard
+			BOOL DONT_FLASH = FALSE;
+			radio->focusFirstItem(FALSE, DONT_FLASH);
 		}
 		current_button++;
 	}
diff --git a/indra/llui/llscrolllistctrl.cpp b/indra/llui/llscrolllistctrl.cpp
index c29789e0837..9d38bd0dab6 100644
--- a/indra/llui/llscrolllistctrl.cpp
+++ b/indra/llui/llscrolllistctrl.cpp
@@ -1381,6 +1381,8 @@ LLScrollListItem* LLScrollListCtrl::addSeparator(EAddPosition pos)
 // Returns false if item not found.
 BOOL LLScrollListCtrl::selectItemByLabel(const LLString& label, BOOL case_sensitive)
 {
+	// ensure that no stale items are selected, even if we don't find a match
+	deselectAllItems(TRUE);
 	//RN: assume no empty items
 	if (label.empty())
 	{
@@ -1762,10 +1764,9 @@ BOOL LLScrollListCtrl::handleToolTip(S32 x, S32 y, LLString& msg, LLRect* sticky
 	{
 		LLScrollListCell* hit_cell = hit_item->getColumn(column_index);
 		if (!hit_cell) return FALSE;
-		S32 cell_required_width = hit_cell->getContentWidth();
+		//S32 cell_required_width = hit_cell->getContentWidth();
 		if (hit_cell 
-			&& hit_cell->isText() 
-			&& cell_required_width > columnp->mWidth)
+			&& hit_cell->isText())
 		{
 
 			S32 rect_left = getColumnOffsetFromIndex(column_index) + mItemListRect.mLeft;
@@ -1781,8 +1782,8 @@ BOOL LLScrollListCtrl::handleToolTip(S32 x, S32 y, LLString& msg, LLRect* sticky
 				&(sticky_rect_screen->mRight), &(sticky_rect_screen->mTop) );
 
 			msg = hit_cell->getValue().asString();
-			handled = TRUE;
 		}
+		handled = TRUE;
 	}
 
 	// otherwise, look for a tooltip associated with this column
diff --git a/indra/llui/lluictrl.cpp b/indra/llui/lluictrl.cpp
index 241adb667ee..ee6176fff65 100644
--- a/indra/llui/lluictrl.cpp
+++ b/indra/llui/lluictrl.cpp
@@ -285,8 +285,6 @@ void LLUICtrl::setIsChrome(BOOL is_chrome)
 // virtual
 BOOL LLUICtrl::getIsChrome() const
 { 
-	// am I or any of my ancestors flagged as "chrome"?
-	if (mIsChrome) return TRUE;
 
 	LLView* parent_ctrl = getParent();
 	while(parent_ctrl)
@@ -300,11 +298,12 @@ BOOL LLUICtrl::getIsChrome() const
 	
 	if(parent_ctrl)
 	{
-		// recurse into parent_ctrl and ask if it is in a chrome subtree
-		return ((LLUICtrl*)parent_ctrl)->getIsChrome();
+		return mIsChrome || ((LLUICtrl*)parent_ctrl)->getIsChrome();
+	}
+	else
+	{
+		return mIsChrome ; 
 	}
-
-	return FALSE;
 }
 
 // this comparator uses the crazy disambiguating logic of LLCompareByTabOrder,
@@ -341,7 +340,7 @@ class DefaultTabGroupFirstSorter : public LLQuerySorter, public LLSingleton<Defa
 };
 
 
-BOOL LLUICtrl::focusFirstItem(BOOL prefer_text_fields)
+BOOL LLUICtrl::focusFirstItem(BOOL prefer_text_fields, BOOL focus_flash)
 {
 	// try to select default tab group child
 	LLCtrlQuery query = LLView::getTabOrderQuery();
@@ -355,7 +354,10 @@ BOOL LLUICtrl::focusFirstItem(BOOL prefer_text_fields)
 		{
 			ctrl->setFocus(TRUE);
 			ctrl->onTabInto();  
-			gFocusMgr.triggerFocusFlash();
+			if(focus_flash)
+			{
+				gFocusMgr.triggerFocusFlash();
+			}
 		}
 		return TRUE;
 	}	
diff --git a/indra/llui/lluictrl.h b/indra/llui/lluictrl.h
index ae360f401f4..e47ee318bef 100644
--- a/indra/llui/lluictrl.h
+++ b/indra/llui/lluictrl.h
@@ -155,7 +155,7 @@ class LLUICtrl
 	virtual void	setMinValue(LLSD min_value);
 	virtual void	setMaxValue(LLSD max_value);
 
-	/*virtual*/ BOOL focusFirstItem(BOOL prefer_text_fields = FALSE );
+	/*virtual*/ BOOL focusFirstItem(BOOL prefer_text_fields = FALSE, BOOL focus_flash = TRUE );
 
 	class LLTextInputFilter : public LLQueryFilter, public LLSingleton<LLTextInputFilter>
 	{
diff --git a/indra/llui/lluifwd.h b/indra/llui/lluifwd.h
new file mode 100644
index 00000000000..23f441ffead
--- /dev/null
+++ b/indra/llui/lluifwd.h
@@ -0,0 +1,40 @@
+/** 
+ * @file lluifwd.h
+ * @author James Cook
+ * @brief Forward declarations of common LLUI widget types.
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+#ifndef LLUIFWD_H
+#define LLUIFWD_H
+
+class LLButton;
+class LLCheckBoxCtrl;
+class LLComboBox;
+class LLDragHandle;
+class LLFloater;
+class LLIconCtrl;
+class LLLineEditor;
+class LLMenuGL;
+class LLPanel;
+class LLRadioGroup;
+class LLResizeBar;
+class LLResizeHandle;
+class LLScrollbar;
+class LLScrollContainer;
+class LLScrollingPanelList;
+class LLScrollListCtrl;
+class LLSlider;
+class LLSliderCtrl;
+class LLSpinCtrl;
+class LLTabContainer;
+class LLTabContainerVertical;
+class LLTextBox;
+class LLTextEditor;
+class LLTextureCtrl;
+class LLUICtrl;
+class LLView;
+class LLViewBorder;
+
+#endif
diff --git a/indra/llwindow/llwindow.h b/indra/llwindow/llwindow.h
index 8ef7066a314..0554d3a8db9 100644
--- a/indra/llwindow/llwindow.h
+++ b/indra/llwindow/llwindow.h
@@ -73,6 +73,9 @@ enum ECursorType {
 	UI_CURSOR_TOOLBUY,
 	UI_CURSOR_TOOLPAY,
 	UI_CURSOR_TOOLOPEN,
+	UI_CURSOR_TOOLPLAY,
+	UI_CURSOR_TOOLPAUSE,
+	UI_CURSOR_TOOLMEDIAOPEN,
 	UI_CURSOR_PIPETTE,
 	UI_CURSOR_COUNT			// Number of elements in this enum (NOT a cursor)
 };
diff --git a/indra/llwindow/llwindowmacosx.cpp b/indra/llwindow/llwindowmacosx.cpp
index 0a2f9cfb6c6..fe127b407ed 100644
--- a/indra/llwindow/llwindowmacosx.cpp
+++ b/indra/llwindow/llwindowmacosx.cpp
@@ -2738,6 +2738,9 @@ const char* cursorIDToName(int id)
 		case UI_CURSOR_TOOLBUY:			return "UI_CURSOR_TOOLBUY";
 		case UI_CURSOR_TOOLPAY:			return "UI_CURSOR_TOOLPAY";
 		case UI_CURSOR_TOOLOPEN:		return "UI_CURSOR_TOOLOPEN";
+		case UI_CURSOR_TOOLPLAY:		return "UI_CURSOR_TOOLPLAY";
+		case UI_CURSOR_TOOLPAUSE:		return "UI_CURSOR_TOOLPAUSE";
+		case UI_CURSOR_TOOLMEDIAOPEN:	return "UI_CURSOR_TOOLMEDIAOPEN";
 		case UI_CURSOR_PIPETTE:			return "UI_CURSOR_PIPETTE";		
 	}
 
@@ -2834,6 +2837,9 @@ void LLWindowMacOSX::setCursor(ECursorType cursor)
 	case UI_CURSOR_TOOLBUY:
 	case UI_CURSOR_TOOLPAY:
 	case UI_CURSOR_TOOLOPEN:
+	case UI_CURSOR_TOOLPLAY:
+	case UI_CURSOR_TOOLPAUSE:
+	case UI_CURSOR_TOOLMEDIAOPEN:
 		result = setImageCursor(gCursors[cursor]);
 		break;
 
@@ -2876,6 +2882,9 @@ void LLWindowMacOSX::initCursors()
 	initPixmapCursor(UI_CURSOR_TOOLBUY, 1, 1);
 	initPixmapCursor(UI_CURSOR_TOOLPAY, 1, 1);
 	initPixmapCursor(UI_CURSOR_TOOLOPEN, 1, 1);
+	initPixmapCursor(UI_CURSOR_TOOLPLAY, 1, 1);
+	initPixmapCursor(UI_CURSOR_TOOLPAUSE, 1, 1);
+	initPixmapCursor(UI_CURSOR_TOOLMEDIAOPEN, 1, 1);
 
 	initPixmapCursor(UI_CURSOR_SIZENWSE, 10, 10);
 	initPixmapCursor(UI_CURSOR_SIZENESW, 10, 10);
diff --git a/indra/llwindow/llwindowsdl.cpp b/indra/llwindow/llwindowsdl.cpp
index cbf4b7dc3ab..e7475d577db 100644
--- a/indra/llwindow/llwindowsdl.cpp
+++ b/indra/llwindow/llwindowsdl.cpp
@@ -116,7 +116,9 @@ BOOL ll_try_gtk_init(void)
 	if (!tried_gtk_init)
 	{
 		tried_gtk_init = TRUE;
+#if LL_GSTREAMER_ENABLED
 		if (!g_thread_supported ()) g_thread_init (NULL);
+#endif // LL_GSTREAMER_ENABLED
 		maybe_lock_display();
 		gtk_is_good = gtk_init_check(NULL, NULL);
 		maybe_unlock_display();
@@ -1985,7 +1987,7 @@ void LLWindowSDL::gatherInput()
     static Uint32 lastRightDown = 0;
     SDL_Event event;
 
-#if LL_GTK && LL_LIBXUL_ENABLED
+#if LL_GTK && LL_LLMOZLIB_ENABLED
     // Pump GTK events so embedded Gecko doesn't starve.
     if (ll_try_gtk_init())
     {
@@ -2004,7 +2006,7 @@ void LLWindowSDL::gatherInput()
 
 	    setlocale(LC_ALL, saved_locale.c_str() );
     }
-#endif // LL_GTK && LL_LIBXUL_ENABLED
+#endif // LL_GTK && LL_LLMOZLIB_ENABLED
 
     // Handle all outstanding SDL events
     while (SDL_PollEvent(&event))
@@ -2358,6 +2360,9 @@ void LLWindowSDL::initCursors()
 	mSDLCursors[UI_CURSOR_TOOLBUY] = makeSDLCursorFromBMP("toolbuy.BMP",0,0);
 	mSDLCursors[UI_CURSOR_TOOLPAY] = makeSDLCursorFromBMP("toolpay.BMP",0,0);
 	mSDLCursors[UI_CURSOR_TOOLOPEN] = makeSDLCursorFromBMP("toolopen.BMP",0,0);
+	mSDLCursors[UI_CURSOR_TOOLPLAY] = makeSDLCursorFromBMP("toolplay.BMP",0,0);
+	mSDLCursors[UI_CURSOR_TOOLPAUSE] = makeSDLCursorFromBMP("toolpause.BMP",0,0);
+	mSDLCursors[UI_CURSOR_TOOLMEDIAOPEN] = makeSDLCursorFromBMP("toolmediaopen.BMP",0,0);
 	mSDLCursors[UI_CURSOR_PIPETTE] = makeSDLCursorFromBMP("lltoolpipette.BMP",2,28);
 }
 
@@ -2744,20 +2749,27 @@ void spawn_web_browser(const char* escaped_url)
 
 void *LLWindowSDL::getPlatformWindow()
 {
-#if LL_GTK && LL_LIBXUL_ENABLED
+#if LL_GTK && LL_LLMOZLIB_ENABLED
 	if (ll_try_gtk_init())
 	{
 		maybe_lock_display();
-		GtkWidget *win = gtk_window_new(GTK_WINDOW_TOPLEVEL);
 
-		// show the hidden-widget while debugging (needs mozlib change)
-		//gtk_widget_show_all(GTK_WIDGET(win));
-
-		gtk_widget_realize(GTK_WIDGET(win));
+		GtkWidget *owin = gtk_window_new(GTK_WINDOW_POPUP);
+		// Why a layout widget?  A MozContainer would be ideal, but
+		// it involves exposing Mozilla headers to mozlib-using apps.
+		// A layout widget with a GtkWindow parent has the desired
+		// properties of being plain GTK, having a window, and being
+		// derived from a GtkContainer.
+		GtkWidget *rtnw = gtk_layout_new(NULL, NULL);
+		gtk_container_add(GTK_CONTAINER(owin), rtnw);
+		gtk_widget_realize(rtnw);
+		GTK_WIDGET_UNSET_FLAGS(GTK_WIDGET(rtnw), GTK_NO_WINDOW);
+		
 		maybe_unlock_display();
-		return win;
+		
+		return rtnw;
 	}
-#endif // LL_GTK && LL_LIBXUL_ENABLED
+#endif // LL_GTK && LL_LLMOZLIB_ENABLED
 	// Unixoid mozilla really needs GTK.
 	return NULL;
 }
diff --git a/indra/llwindow/llwindowwin32.cpp b/indra/llwindow/llwindowwin32.cpp
index 736ff9df97d..7e93d3ecf48 100644
--- a/indra/llwindow/llwindowwin32.cpp
+++ b/indra/llwindow/llwindowwin32.cpp
@@ -1907,6 +1907,9 @@ void LLWindowWin32::initCursors()
 	mCursor[UI_CURSOR_TOOLBUY] = loadColorCursor(TEXT("TOOLBUY"));
 	mCursor[UI_CURSOR_TOOLPAY] = loadColorCursor(TEXT("TOOLPAY"));
 	mCursor[UI_CURSOR_TOOLOPEN] = loadColorCursor(TEXT("TOOLOPEN"));
+	mCursor[UI_CURSOR_TOOLPLAY] = loadColorCursor(TEXT("TOOLPLAY"));
+	mCursor[UI_CURSOR_TOOLPAUSE] = loadColorCursor(TEXT("TOOLPAUSE"));
+	mCursor[UI_CURSOR_TOOLMEDIAOPEN] = loadColorCursor(TEXT("TOOLMEDIAOPEN"));
 
 	// Note: custom cursors that are not found make LoadCursor() return NULL.
 	for( S32 i = 0; i < UI_CURSOR_COUNT; i++ )
diff --git a/indra/lscript/lscript_compile/indra.l b/indra/lscript/lscript_compile/indra.l
index 57aef07e184..c8458a3ff04 100644
--- a/indra/lscript/lscript_compile/indra.l
+++ b/indra/lscript/lscript_compile/indra.l
@@ -36,6 +36,7 @@ FS			(f|F)
 #include "llparcelflags.h"
 #include "llregionflags.h"
 #include "lscript_http.h"
+#include "llclickaction.h"
 
 void count();
 void comment();
@@ -522,6 +523,10 @@ extern "C" { int yyerror(const char *fmt, ...); }
 "PARCEL_MEDIA_COMMAND_AGENT"	{ count(); yylval.ival = PARCEL_MEDIA_COMMAND_AGENT; return(INTEGER_CONSTANT); }
 "PARCEL_MEDIA_COMMAND_UNLOAD"	{ count(); yylval.ival = PARCEL_MEDIA_COMMAND_UNLOAD; return(INTEGER_CONSTANT); }
 "PARCEL_MEDIA_COMMAND_AUTO_ALIGN"	{ count(); yylval.ival = PARCEL_MEDIA_COMMAND_AUTO_ALIGN; return(INTEGER_CONSTANT); }
+"PARCEL_MEDIA_COMMAND_TYPE"     { count(); yylval.ival = PARCEL_MEDIA_COMMAND_TYPE; return(INTEGER_CONSTANT); }
+"PARCEL_MEDIA_COMMAND_SIZE"     { count(); yylval.ival = PARCEL_MEDIA_COMMAND_SIZE; return(INTEGER_CONSTANT); }
+"PARCEL_MEDIA_COMMAND_DESC"     { count(); yylval.ival = PARCEL_MEDIA_COMMAND_DESC; return(INTEGER_CONSTANT); }
+"PARCEL_MEDIA_COMMAND_LOOP_SET" { count(); yylval.ival = PARCEL_MEDIA_COMMAND_LOOP_SET; return(INTEGER_CONSTANT); }
 
 "LIST_STAT_MAX"			{ count(); yylval.ival = LIST_STAT_MAX; return(INTEGER_CONSTANT); }
 "LIST_STAT_MIN"			{ count(); yylval.ival = LIST_STAT_MIN; return(INTEGER_CONSTANT); }
@@ -587,6 +592,15 @@ extern "C" { int yyerror(const char *fmt, ...); }
 "STRING_TRIM_TAIL"	{ count(); yylval.ival = STRING_TRIM_TAIL; return(INTEGER_CONSTANT); }
 "STRING_TRIM"	{ count(); yylval.ival = STRING_TRIM; return(INTEGER_CONSTANT); }
 
+"CLICK_ACTION_NONE"       { count(); yylval.ival = CLICK_ACTION_NONE; return(INTEGER_CONSTANT); }
+"CLICK_ACTION_TOUCH"      { count(); yylval.ival = CLICK_ACTION_TOUCH; return(INTEGER_CONSTANT); }
+"CLICK_ACTION_SIT"        { count(); yylval.ival = CLICK_ACTION_SIT; return(INTEGER_CONSTANT); }
+"CLICK_ACTION_BUY"        { count(); yylval.ival = CLICK_ACTION_BUY; return(INTEGER_CONSTANT); }
+"CLICK_ACTION_PAY"        { count(); yylval.ival = CLICK_ACTION_PAY; return(INTEGER_CONSTANT); }
+"CLICK_ACTION_OPEN"       { count(); yylval.ival = CLICK_ACTION_OPEN; return(INTEGER_CONSTANT); }
+"CLICK_ACTION_PLAY"       { count(); yylval.ival = CLICK_ACTION_PLAY; return(INTEGER_CONSTANT); }
+"CLICK_ACTION_OPEN_MEDIA" { count(); yylval.ival = CLICK_ACTION_OPEN_MEDIA; return(INTEGER_CONSTANT); }
+
 {L}({L}|{N})*		{ count(); yylval.sval = new char[strlen(yytext) + 1]; strcpy(yylval.sval, yytext); return(IDENTIFIER); }
 
 {N}+{E}					{ count(); yylval.fval = (F32)atof(yytext); return(FP_CONSTANT); }
diff --git a/indra/lscript/lscript_library/lscript_library.cpp b/indra/lscript/lscript_library/lscript_library.cpp
index e0822203538..47ea62b8886 100644
--- a/indra/lscript/lscript_library/lscript_library.cpp
+++ b/indra/lscript/lscript_library/lscript_library.cpp
@@ -29,7 +29,15 @@
  * $/LicenseInfo$
  */
 
-// *WARNING*
+
+//  ##      ##    ###    ########  ##    ## #### ##    ##  ######   #### ####
+//  ##  ##  ##   ## ##   ##     ## ###   ##  ##  ###   ## ##    ##  #### ####
+//  ##  ##  ##  ##   ##  ##     ## ####  ##  ##  ####  ## ##        #### ####
+//  ##  ##  ## ##     ## ########  ## ## ##  ##  ## ## ## ##   ####  ##   ##
+//  ##  ##  ## ######### ##   ##   ##  ####  ##  ##  #### ##    ##
+//  ##  ##  ## ##     ## ##    ##  ##   ###  ##  ##   ### ##    ##  #### ####
+//   ###  ###  ##     ## ##     ## ##    ## #### ##    ##  ######   #### #### 
+//
 // When adding functions, they <b>MUST</b> be appended to the end of
 // the init() method. The init() associates the name with a number,
 // which is then serialized into the bytecode. Inserting a new
@@ -431,6 +439,8 @@ void LLScriptLibrary::init()
 
 	addFunction(new LLScriptLibraryFunction(10.f, 0.f, dummy_func, "llGetObjectDetails", "l", "kl", "list llGetObjectDetails(key id, list params)\nGets the object details specified in params for the object with key id.\nDetails are OBJECT_NAME, _DESC, _POS, _ROT, _VELOCITY, _OWNER, _GROUP, _CREATOR."));
 
+		addFunction(new LLScriptLibraryFunction(10.f, 0.f, dummy_func, "llSetClickAction", NULL, "i", "llSetClickAction(integer action)\nSets the action performed when a prim is clicked upon."));
+
 	// energy, sleep, dummy_func, name, return type, parameters, help text, gods-only
 
 	// IF YOU ADD NEW SCRIPT CALLS, YOU MUST PUT THEM AT THE END OF THIS LIST.
diff --git a/indra/newview/app_settings/keywords.ini b/indra/newview/app_settings/keywords.ini
index 5a68c5b1632..08006470681 100644
--- a/indra/newview/app_settings/keywords.ini
+++ b/indra/newview/app_settings/keywords.ini
@@ -422,7 +422,10 @@ PARCEL_MEDIA_COMMAND_PLAY  Play media stream
 PARCEL_MEDIA_COMMAND_LOOP  Loop media stream
 PARCEL_MEDIA_COMMAND_TEXTURE  Get or set the parcel's media texture
 PARCEL_MEDIA_COMMAND_URL  Get or set the parcel's media url
+PARCEL_MEDIA_COMMAND_TYPE Get or set the parcel's media mimetype
+PARCEL_MEDIA_COMMAND_DESC Get or set the parcel's media description
 PARCEL_MEDIA_COMMAND_TIME Set media stream to specific time
+PARCEL_MEDIA_COMMAND_SIZE Get or set the parcel's media pixel resolution
 PARCEL_MEDIA_COMMAND_AGENT Allows media stream commands to apply to only one agent
 PARCEL_MEDIA_COMMAND_UNLOAD Unloads the media stream
 PARCEL_MEDIA_COMMAND_AUTO_ALIGN Auto aligns the media stream to the texture size.  May cause a performance hit and loss of some visual quality.
@@ -492,6 +495,15 @@ STRING_TRIM_HEAD		Used with llStringTrim to trim leading spaces from a string.
 STRING_TRIM_TAIL		Used with llStringTrim to trim trailing spaces from a string.
 STRING_TRIM				Used with llStringTrim to trim both leading and trailing spaces from a string.
 
+CLICK_ACTION_NONE       Used with llSetClickAction to disable the click action
+CLICK_ACTION_TOUCH      Used with llSetClickAction to set touch as the default action when object is clicked
+CLICK_ACTION_SIT        Used with llSetClickAction to set sit as the default action when object is clicked
+CLICK_ACTION_BUY        Used with llSetClickAction to set buy as the default action when object is clicked
+CLICK_ACTION_PAY        Used with llSetClickAction to set pay as the default action when object is clicked
+CLICK_ACTION_OPEN       Used with llSetClickAction to set open as the default action when object is clicked
+CLICK_ACTION_PLAY       Used with llSetClickAction to set play as the default action when object is clicked
+CLICK_ACTION_OPEN_MEDIA Used with llSetClickAction to set open-media as the default action when object is clicked
+
 # string constants
 [word .1, .3, .5]
 NULL_KEY			Indicates an empty key
diff --git a/indra/newview/cursors_mac/UI_CURSOR_TOOLMEDIAOPEN.tif b/indra/newview/cursors_mac/UI_CURSOR_TOOLMEDIAOPEN.tif
new file mode 100644
index 0000000000000000000000000000000000000000..7c0bcfcbc5002fc613707ffd69ea8ed14e31a1c1
GIT binary patch
literal 41228
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
Y2ms|RskV(M$MY^8c0v6&lcv1?2SgZ2&Hw-a

literal 0
HcmV?d00001

diff --git a/indra/newview/cursors_mac/UI_CURSOR_TOOLPAUSE.tif b/indra/newview/cursors_mac/UI_CURSOR_TOOLPAUSE.tif
new file mode 100644
index 0000000000000000000000000000000000000000..3431887aff812a2194c31c925cee38ab8b205c06
GIT binary patch
literal 41224
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
BT{8dx

literal 0
HcmV?d00001

diff --git a/indra/newview/cursors_mac/UI_CURSOR_TOOLPLAY.tif b/indra/newview/cursors_mac/UI_CURSOR_TOOLPLAY.tif
new file mode 100644
index 0000000000000000000000000000000000000000..796bbb78e3c7a0682ade747d306f48668d5096c8
GIT binary patch
literal 41224
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

literal 0
HcmV?d00001

diff --git a/indra/newview/llappviewer.cpp b/indra/newview/llappviewer.cpp
index fe9b90ae600..075a7089de3 100644
--- a/indra/newview/llappviewer.cpp
+++ b/indra/newview/llappviewer.cpp
@@ -47,6 +47,7 @@
 #include "llpumpio.h"
 #include "llfloateractivespeakers.h"
 #include "llimpanel.h"
+#include "llmimetypes.h"
 #include "llstartup.h"
 #include "llfocusmgr.h"
 #include "llviewerjoystick.h"
@@ -59,6 +60,7 @@
 #include "llworldmap.h"
 #include "llmutelist.h"
 #include "llurldispatcher.h"
+#include "llurlhistory.h"
 
 #include "llweb.h"
 #include "llsecondlifeurls.h"
@@ -76,7 +78,6 @@
 
 
 #include "llnotify.h"
-#include "llmediaengine.h"
 #include "llviewerkeyboard.h"
 #include "lllfsthread.h"
 #include "llworkerthread.h"
@@ -97,7 +98,6 @@
 #include "llviewermenu.h"
 #include "llselectmgr.h"
 #include "lltracker.h"
-#include "llmozlib.h"
 #include "llviewerparcelmgr.h"
 #include "llworldmapview.h"
 
@@ -169,21 +169,6 @@ static char** gTempArgV;
 #if LL_WINDOWS && LL_LCD_COMPILE
 	#include "lllcd.h"
 #endif
-//
-#if LL_QUICKTIME_ENABLED
-	#if LL_DARWIN
-		#include <QuickTime/QuickTime.h>
-	#else
-		// quicktime specific includes
-		#include "MacTypes.h"
-		#include "QTML.h"
-		#include "Movies.h"
-		#include "FixMath.h"
-	#endif
-#endif
-//
-//////
-
 
 //----------------------------------------------------------------------------
 // viewer.cpp - these are only used in viewer, should be easily moved.
@@ -228,10 +213,6 @@ extern BOOL gbCapturing;
 extern BOOL gRandomizeFramerate;
 extern BOOL gPeriodicSlowFrame;
 
-#if LL_GSTREAMER_ENABLED
-void UnloadGStreamer();
-#endif
-
 ////////////////////////////////////////////////////////////
 // All from the last globals push...
 bool gVerifySSLCert = true;
@@ -257,6 +238,7 @@ BOOL				gShowObjectUpdates = FALSE;
 BOOL gLogMessages = FALSE;
 std::string gChannelName = LL_CHANNEL;
 BOOL gUseAudio = TRUE;
+BOOL gUseQuickTime = TRUE;
 LLString gCmdLineFirstName;
 LLString gCmdLineLastName;
 LLString gCmdLinePassword;
@@ -1174,6 +1156,9 @@ bool LLAppViewer::init()
 
 	LLAgent::parseTeleportMessages("teleport_strings.xml");
 
+	// load MIME type -> media impl mappings
+	LLMIMETypes::parseMIMETypes( "mime_types.xml" ); 
+
 	mCrashBehavior = gCrashSettings.getS32(CRASH_BEHAVIOR_SETTING);
 
 	LLVectorPerformanceOptions::initClass();
@@ -1574,32 +1559,6 @@ bool LLAppViewer::cleanup()
 	llwarns << "Hack, skipping audio engine cleanup" << llendflush;
 #endif
 
-
-	// moved to main application shutdown for now because it's non-trivial and only needs to be done once
-	// (even though it goes against the media framework design)
-
-	LLMediaEngine::cleanupClass();
-	
-#if LL_QUICKTIME_ENABLED
-	if (gQuickTimeInitialized)
-	{
-		// clean up media stuff
-		llinfos << "Cleaning up QuickTime" << llendl;
-		ExitMovies ();
-		#if LL_WINDOWS
-			// Only necessary/available on Windows.
-			TerminateQTML ();
-		#endif
-	}
-	llinfos << "Quicktime cleaned up" << llendflush;
-#endif
-
-#if LL_GSTREAMER_ENABLED
-	llinfos << "Cleaning up GStreamer" << llendl;
-	UnloadGStreamer();
-	llinfos << "GStreamer cleaned up" << llendflush;	
-#endif
-
 	llinfos << "Cleaning up feature manager" << llendflush;
 	delete gFeatureManagerp;
 	gFeatureManagerp = NULL;
@@ -1661,18 +1620,12 @@ bool LLAppViewer::cleanup()
 		
 	LLTracker::cleanupInstance();
 	
-#if LL_LIBXUL_ENABLED
-	// this must be done after floater cleanup (delete gViewerWindow) since 
-	// floaters  potentially need the manager to destroy their contents.
-	LLMozLib::getInstance()->reset();
-#endif
-
 	// *FIX: This is handled in LLAppViewerWin32::cleanup().
 	// I'm keeping the comment to remember its order in cleanup,
 	// in case of unforseen dependency.
-//#if LL_WINDOWS
-//	gDXHardware.cleanup();
-//#endif // LL_WINDOWS
+	//#if LL_WINDOWS
+	//	gDXHardware.cleanup();
+	//#endif // LL_WINDOWS
 
 #if LL_WINDOWS && LL_LCD_COMPILE
 	// shut down the LCD window on a logitech keyboard, if there is one
@@ -1729,6 +1682,9 @@ bool LLAppViewer::cleanup()
 	gColors.cleanup();
 	gCrashSettings.cleanup();
 
+	// Save URL history file
+	LLURLHistory::saveFile("url_history.xml");
+
 	if (gMuteListp)
 	{
 		// save mute list
@@ -2368,8 +2324,6 @@ bool LLAppViewer::initWindow()
 	LLAlertDialog::parseAlerts("alerts.xml");
 	LLNotifyBox::parseNotify("notify.xml");
 
-	LLMediaEngine::initClass();
-	
 	//
 	// Clean up the feature manager lookup table - settings were updated
 	// in the LLViewerWindow constructor
diff --git a/indra/newview/llfirstuse.cpp b/indra/newview/llfirstuse.cpp
index 2772a134166..97ebc02ba18 100644
--- a/indra/newview/llfirstuse.cpp
+++ b/indra/newview/llfirstuse.cpp
@@ -264,3 +264,14 @@ void LLFirstUse::useVoice()
 		LLFloaterVoiceWizard::showInstance();
 	}
 }
+
+// static 
+void LLFirstUse::useMedia()
+{
+	if (gSavedSettings.getWarning("FirstMedia"))
+	{
+		gSavedSettings.setWarning("FirstMedia", FALSE);
+
+		LLNotifyBox::showXml("FirstMedia");
+	}
+}
diff --git a/indra/newview/llfirstuse.h b/indra/newview/llfirstuse.h
index b5cf1482852..5510ce02b92 100644
--- a/indra/newview/llfirstuse.h
+++ b/indra/newview/llfirstuse.h
@@ -105,7 +105,8 @@ class LLFirstUse
 	static void useDebugMenus();
 	static void useSculptedPrim();
 	static void useVoice();
-
+	static void useMedia();
+	
 protected:
 	static std::set<LLString> sConfigVariables;
 };
diff --git a/indra/newview/llfloaterabout.cpp b/indra/newview/llfloaterabout.cpp
index 01e529078f7..7da2ac79b1a 100644
--- a/indra/newview/llfloaterabout.cpp
+++ b/indra/newview/llfloaterabout.cpp
@@ -48,12 +48,9 @@
 #include "llviewerbuild.h"
 #include "llvieweruictrlfactory.h"
 #include "llappviewer.h" 
-
-#if LL_LIBXUL_ENABLED
-#include "llmozlib.h"
-#endif // LL_LIBXUL_ENABLED
-
 #include "llglheaders.h"
+#include "llmediamanager.h"
+
 
 extern LLCPUInfo gSysCPU;
 extern LLMemoryInfo gSysMemory;
@@ -147,11 +144,18 @@ LLFloaterAbout::LLFloaterAbout()
 	support.append( (const char*) glGetString(GL_VERSION) );
 	support.append("\n");
 
-#if LL_LIBXUL_ENABLED
-	support.append("LLMozLib Version: ");
-	support.append( (const char*) LLMozLib::getInstance()->getVersion().c_str() );
-	support.append("\n");
-#endif // LL_LIBXUL_ENABLED
+	LLMediaManager *mgr = LLMediaManager::getInstance();
+	if (mgr)
+	{
+		LLMediaBase *media_source = mgr->createSourceFromMimeType("http", "text/html");
+		if (media_source)
+		{
+			support.append("LLMozLib Version: ");
+			support.append((const char*) media_source->getVersion().c_str());
+			support.append("\n");
+			mgr->destroySource(media_source);
+		}
+	}
 
 	if (gViewerStats
 		&& gPacketsIn > 0)
diff --git a/indra/newview/llfloaterland.cpp b/indra/newview/llfloaterland.cpp
index 6dd55c169ba..f340ff25697 100644
--- a/indra/newview/llfloaterland.cpp
+++ b/indra/newview/llfloaterland.cpp
@@ -31,8 +31,6 @@
 
 #include "llviewerprecompiledheaders.h"
 
-#include <sstream>
-
 #include "llfloaterland.h"
 
 #include "llcachename.h"
@@ -53,6 +51,7 @@
 #include "lllineeditor.h"
 #include "llnamelistctrl.h"
 #include "llnotify.h"
+#include "llpanellandmedia.h"
 #include "llradiogroup.h"
 #include "llscrolllistctrl.h"
 #include "llselectmgr.h"
@@ -68,10 +67,39 @@
 #include "llviewerstats.h"
 #include "llviewertexteditor.h"
 #include "llviewerwindow.h"
-#include "llmediaengine.h"
 #include "llviewercontrol.h"
 #include "roles_constants.h"
 
+#include <sstream>
+#include <time.h>
+
+static const S32 EDIT_HEIGHT = 16;
+static const S32 LEFT = HPAD;
+static const S32 BOTTOM = VPAD;
+static const S32 RULER0  = LEFT;
+static const S32 RULER05 = RULER0 + 24;
+static const S32 RULER1  = RULER05 + 16;
+static const S32 RULER15 = RULER1 + 20;
+static const S32 RULER2  = RULER1 + 32;
+static const S32 RULER205= RULER2 + 32;
+static const S32 RULER20 = RULER2 + 64;
+static const S32 RULER21 = RULER20 + 16;
+static const S32 RULER22 = RULER21 + 32;
+static const S32 RULER225 = RULER20 + 64;
+static const S32 RULER23 = RULER22 + 64;
+static const S32 RULER24 = RULER23 + 26;
+static const S32 RULER3  = RULER2 + 102;
+static const S32 RULER4  = RULER3 + 8;
+static const S32 RULER5  = RULER4 + 50;
+static const S32 RULER6  = RULER5 + 52;
+static const S32 RULER7  = RULER6 + 24;
+static const S32 RIGHT  = LEFT + 278;
+static const S32 FAR_RIGHT  = LEFT + 324 + 40;
+
+static const char PRICE[] = "Price:";
+static const char NO_PRICE[] = "";
+static const char AREA[] = "Area:";
+
 static const char OWNER_ONLINE[] 	= "0";
 static const char OWNER_OFFLINE[]	= "1";
 static const char OWNER_GROUP[] 	= "2";
@@ -80,16 +108,7 @@ static const char OWNER_GROUP[] 	= "2";
 static const BOOL BUY_GROUP_LAND = TRUE;
 static const BOOL BUY_PERSONAL_LAND = FALSE;
 
-// Values for the parcel voice settings radio group
-enum
-{
-	kRadioVoiceChatEstate = 0,
-	kRadioVoiceChatPrivate = 1,
-	kRadioVoiceChatDisable = 2
-};
-
 // Statics
-LLFloaterLand* LLFloaterLand::sInstance = NULL;
 LLParcelSelectionObserver* LLFloaterLand::sObserver = NULL;
 S32 LLFloaterLand::sLastTab = 0;
 
@@ -150,64 +169,42 @@ void send_parcel_select_objects(S32 parcel_local_id, S32 return_type,
 }
 
 
-// static
-void LLFloaterLand::show()
-{
-	if (!sInstance)
-	{
-		sInstance = new LLFloaterLand();
-
-		// Select tab from last view
-		sInstance->mTabLand->selectTab(sLastTab);
-
-		sObserver = new LLParcelSelectionObserver();
-		gParcelMgr->addObserver( sObserver );
-	}
-
-	sInstance->open();	/*Flawfinder: ignore*/
-
-	// Done automatically when the selected parcel's properties arrive
-	// (and hence we have the local id).
-	// gParcelMgr->sendParcelAccessListRequest(AL_ACCESS | AL_BAN | AL_RENTER);
-
-	sInstance->mParcel = gParcelMgr->getFloatingParcelSelection();
-	
-	// Refresh even if not over a region so we don't get an
-	// uninitialized dialog. The dialog is 0-region aware.
-	sInstance->refresh();
-}
-
 //static
 LLPanelLandObjects* LLFloaterLand::getCurrentPanelLandObjects()
 {
-	if (!sInstance)
-	{
-		return NULL;
-	}
-
-	return sInstance->mPanelObjects;
+	return LLFloaterLand::getInstance()->mPanelObjects;
 }
 
 //static
 LLPanelLandCovenant* LLFloaterLand::getCurrentPanelLandCovenant()
 {
-	if (!sInstance)
-	{
-		return NULL;
-	}
-
-	return sInstance->mPanelCovenant;
+	return LLFloaterLand::getInstance()->mPanelCovenant;
 }
 
 // static
 void LLFloaterLand::refreshAll()
 {
-	if (sInstance)
-	{
-		sInstance->refresh();
-	}
+	LLFloaterLand::getInstance()->refresh();
+}
+
+void LLFloaterLand::onOpen()
+{
+	// Select tab from last view
+	mTabLand->selectTab(sLastTab);
+
+
+	// Done automatically when the selected parcel's properties arrive
+	// (and hence we have the local id).
+	// gParcelMgr->sendParcelAccessListRequest(AL_ACCESS | AL_BAN | AL_RENTER);
+
+	mParcel = gParcelMgr->getFloatingParcelSelection();
+	
+	// Refresh even if not over a region so we don't get an
+	// uninitialized dialog. The dialog is 0-region aware.
+	refresh();
 }
 
+
 // virtual
 void LLFloaterLand::onClose(bool app_quitting)
 {
@@ -225,7 +222,7 @@ void LLFloaterLand::onClose(bool app_quitting)
 }
 
 
-LLFloaterLand::LLFloaterLand()
+LLFloaterLand::LLFloaterLand(const LLSD& seed)
 :	LLFloater("floaterland", "FloaterLandRect5", "About Land")
 {
 
@@ -242,7 +239,12 @@ LLFloaterLand::LLFloaterLand()
 
 	gUICtrlFactory->buildFloater(this, "floater_about_land.xml", &factory_map);
 
+	sObserver = new LLParcelSelectionObserver();
+	gParcelMgr->addObserver( sObserver );
+}
 
+BOOL LLFloaterLand::postBuild()
+{
 	LLTabContainerCommon* tab = LLUICtrlFactory::getTabContainerByName(this, "landtab");
 
 	mTabLand = (LLTabContainer*) tab;
@@ -252,16 +254,16 @@ LLFloaterLand::LLFloaterLand()
 	{
 		tab->selectTab(sLastTab);
 	}
+
+	return TRUE;
 }
 
 
 // virtual
 LLFloaterLand::~LLFloaterLand()
 {
-	sInstance = NULL;
 }
 
-
 // public
 void LLFloaterLand::refresh()
 {
@@ -2214,239 +2216,7 @@ void LLPanelLandOptions::onClickPublishHelp(void*)
 	}
 }
 
-//---------------------------------------------------------------------------
-// LLPanelLandMedia
-//---------------------------------------------------------------------------
-
-LLPanelLandMedia::LLPanelLandMedia(LLParcelSelectionHandle& parcel)
-:	LLPanel("land_media_panel"), mParcel(parcel)
-{
-}
-
-
-
 
-BOOL LLPanelLandMedia::postBuild()
-{
-		
-	mCheckSoundLocal = LLUICtrlFactory::getCheckBoxByName(this, "check sound local");
-	childSetCommitCallback("check sound local", onCommitAny, this);
-
-	mRadioVoiceChat = LLUICtrlFactory::getRadioGroupByName(this, "parcel_voice_channel");
-	childSetCommitCallback("parcel_voice_channel", onCommitAny, this);
-
-	mMusicURLEdit = LLUICtrlFactory::getLineEditorByName(this, "music_url");
-	childSetCommitCallback("music_url", onCommitAny, this);
-
-
-	mMediaTextureCtrl = LLUICtrlFactory::getTexturePickerByName(this, "media texture");
-	if (mMediaTextureCtrl)
-	{
-		mMediaTextureCtrl->setCommitCallback( onCommitAny );
-		mMediaTextureCtrl->setCallbackUserData( this );
-		mMediaTextureCtrl->setAllowNoTexture ( TRUE );
-		mMediaTextureCtrl->setImmediateFilterPermMask(PERM_COPY | PERM_TRANSFER);
-		mMediaTextureCtrl->setNonImmediateFilterPermMask(PERM_COPY | PERM_TRANSFER);
-	}
-	else
-	{
-		llwarns << "LLUICtrlFactory::getTexturePickerByName() returned NULL for 'media texure'" << llendl;
-	}
-		
-	mMediaAutoScaleCheck = LLUICtrlFactory::getCheckBoxByName(this, "media_auto_scale");
-	childSetCommitCallback("media_auto_scale", onCommitAny, this);
-
-	mMediaURLEdit = LLUICtrlFactory::getLineEditorByName(this, "media_url");
-	childSetCommitCallback("media_url", onCommitAny, this);
-	
-	return TRUE;
-}
-
-
-// virtual
-LLPanelLandMedia::~LLPanelLandMedia()
-{ }
-
-
-// public
-void LLPanelLandMedia::refresh()
-{
-	LLParcel *parcel = mParcel->getParcel();
-
-	if (!parcel)
-	{
-		mCheckSoundLocal->set(FALSE);
-		mCheckSoundLocal->setEnabled(FALSE);
-
-		mRadioVoiceChat->setSelectedIndex(kRadioVoiceChatEstate);
-		mRadioVoiceChat->setEnabled(FALSE);
-
-		mMusicURLEdit->setText(LLString::null);
-		mMusicURLEdit->setEnabled(FALSE);
-
-		mMediaURLEdit->setText(LLString::null);
-		mMediaURLEdit->setEnabled(FALSE);
-
-		mMediaAutoScaleCheck->set ( FALSE );
-		mMediaAutoScaleCheck->setEnabled(FALSE);
-
-		mMediaTextureCtrl->clear();
-		mMediaTextureCtrl->setEnabled(FALSE);
-
-		#if 0
-		mMediaStopButton->setEnabled ( FALSE );
-		mMediaStartButton->setEnabled ( FALSE );
-		#endif
-	}
-	else
-	{
-		// something selected, hooray!
-
-		// Display options
-		BOOL can_change_media = LLViewerParcelMgr::isParcelModifiableByAgent(parcel, GP_LAND_CHANGE_MEDIA);
-
-		mCheckSoundLocal->set( parcel->getSoundLocal() );
-		mCheckSoundLocal->setEnabled( can_change_media );
-
-		LLViewerRegion* selection_region = gParcelMgr->getSelectionRegion();
-		BOOL region_allows_voice = FALSE;
-		if (selection_region)
-		{
-			region_allows_voice = selection_region->isVoiceEnabled();
-		}
-
-		if(parcel->getVoiceEnabled())
-		{
-			if(parcel->getVoiceUseEstateChannel())
-				mRadioVoiceChat->setSelectedIndex(kRadioVoiceChatEstate);
-			else
-				mRadioVoiceChat->setSelectedIndex(kRadioVoiceChatPrivate);
-		}
-		else
-		{
-			mRadioVoiceChat->setSelectedIndex(kRadioVoiceChatDisable);
-		}
-
-		mRadioVoiceChat->setEnabled( can_change_media && region_allows_voice );
-
-		// don't display urls if you're not able to change it
-		// much requested change in forums so people can't 'steal' urls
-		// NOTE: bug#2009 means this is still vunerable - however, bug 
-		// should be closed since this bug opens up major security issues elsewhere.
-		if ( can_change_media )
-		{
-			mMusicURLEdit->setDrawAsterixes ( FALSE );
-			mMediaURLEdit->setDrawAsterixes ( FALSE );
-		}
-		else
-		{
-				mMusicURLEdit->setDrawAsterixes ( TRUE );
-				mMediaURLEdit->setDrawAsterixes ( TRUE );
-			}
-
-		mMusicURLEdit->setText(parcel->getMusicURL());
-		mMusicURLEdit->setEnabled( can_change_media );
-
-		mMediaURLEdit->setText(parcel->getMediaURL());
-		mMediaURLEdit->setEnabled( can_change_media );
-
-		mMediaAutoScaleCheck->set ( parcel->getMediaAutoScale () );
-		mMediaAutoScaleCheck->setEnabled ( can_change_media );
-
-		LLUUID tmp = parcel->getMediaID();
-		mMediaTextureCtrl->setImageAssetID ( parcel->getMediaID() );
-		mMediaTextureCtrl->setEnabled( can_change_media );
-
-		#if 0
-		// there is a media url and a media texture selected
-		if ( ( ! ( std::string ( parcel->getMediaURL() ).empty () ) ) && ( ! ( parcel->getMediaID ().isNull () ) ) )
-		{
-			// turn on transport controls if allowed for this parcel
-			mMediaStopButton->setEnabled ( editable );
-			mMediaStartButton->setEnabled ( editable );
-		}
-		else
-		{
-			// no media url or no media texture
-			mMediaStopButton->setEnabled ( FALSE );
-			mMediaStartButton->setEnabled ( FALSE );
-		};
-		#endif
-	}
-}
-
-// static
-void LLPanelLandMedia::onCommitAny(LLUICtrl *ctrl, void *userdata)
-{
-	LLPanelLandMedia *self = (LLPanelLandMedia *)userdata;
-
-	LLParcel* parcel = self->mParcel->getParcel();
-	if (!parcel)
-	{
-		return;
-	}
-
-	// Extract data from UI
-	BOOL sound_local		= self->mCheckSoundLocal->get();
-	int voice_setting		= self->mRadioVoiceChat->getSelectedIndex();
-	std::string music_url	= self->mMusicURLEdit->getText();
-	std::string media_url	= self->mMediaURLEdit->getText();
-	U8 media_auto_scale		= self->mMediaAutoScaleCheck->get();
-	LLUUID media_id			= self->mMediaTextureCtrl->getImageAssetID();
-
-	BOOL voice_enabled;
-	BOOL voice_estate_chan;
-	
-	switch(voice_setting)
-	{
-		default:
-		case kRadioVoiceChatEstate:
-			voice_enabled = TRUE;
-			voice_estate_chan = TRUE;
-		break;
-		case kRadioVoiceChatPrivate:
-			voice_enabled = TRUE;
-			voice_estate_chan = FALSE;
-		break;
-		case kRadioVoiceChatDisable:
-			voice_enabled = FALSE;
-			voice_estate_chan = FALSE;
-		break;
-	}
-	
-	// Remove leading/trailing whitespace (common when copying/pasting)
-	LLString::trim(music_url);
-	LLString::trim(media_url);
-
-	// Push data into current parcel
-	parcel->setParcelFlag(PF_ALLOW_VOICE_CHAT, voice_enabled);
-	parcel->setParcelFlag(PF_USE_ESTATE_VOICE_CHAN, voice_estate_chan);
-	parcel->setParcelFlag(PF_SOUND_LOCAL, sound_local);
-	parcel->setMusicURL(music_url.c_str());
-	parcel->setMediaURL(media_url.c_str());
-	parcel->setMediaID(media_id);
-	parcel->setMediaAutoScale ( media_auto_scale );
-
-	// Send current parcel data upstream to server
-	gParcelMgr->sendParcelPropertiesUpdate( parcel );
-
-	// Might have changed properties, so let's redraw!
-	self->refresh();
-}
-
-void LLPanelLandMedia::onClickStopMedia ( void* data )
-{
-	LLMediaEngine::getInstance ()->stop ();
-}
-
-void LLPanelLandMedia::onClickStartMedia ( void* data )
-{
-	// force a commit
-	gFocusMgr.setKeyboardFocus ( NULL );
-
-	// force a reload
-	LLMediaEngine::getInstance ()->convertImageAndLoadUrl ( true, false, std::string());
-}
 
 //---------------------------------------------------------------------------
 // LLPanelLandAccess
diff --git a/indra/newview/llfloaterland.h b/indra/newview/llfloaterland.h
index 8b77bb990a1..e504e27f21e 100644
--- a/indra/newview/llfloaterland.h
+++ b/indra/newview/llfloaterland.h
@@ -68,13 +68,9 @@ class LLPanelLandRenters;
 class LLPanelLandCovenant;
 
 class LLFloaterLand
-:	public LLFloater
+:	public LLFloater, public LLUISingleton<LLFloaterLand>
 {
 public:
-	// Call show() to open a land floater.
-	// Will query the viewer parcel manager to see what is selected.
-	static void show();
-	static BOOL floaterVisible() { return sInstance && sInstance->getVisible(); }
 	static void refreshAll();
 
 	static LLPanelLandObjects* getCurrentPanelLandObjects();
@@ -82,11 +78,15 @@ class LLFloaterLand
 
 	// Destroys itself on close.
 	virtual void onClose(bool app_quitting);
+	virtual void onOpen();
+	virtual BOOL postBuild();
 
 protected:
+	friend class LLUISingleton<LLFloaterLand>;
+
 	// Does its own instance management, so clients not allowed
 	// to allocate or destroy.
-	LLFloaterLand();
+	LLFloaterLand(const LLSD& seed);
 	virtual ~LLFloaterLand();
 
 	void refresh();
@@ -102,7 +102,6 @@ class LLFloaterLand
 
 
 protected:
-	static LLFloaterLand* sInstance;
 	static LLParcelSelectionObserver* sObserver;
 	static S32 sLastTab;
 
@@ -344,35 +343,6 @@ class LLPanelLandOptions
 };
 
 
-class LLPanelLandMedia
-:	public LLPanel
-{
-public:
-	LLPanelLandMedia(LLHandle<LLParcelSelection>& parcelp);
-	virtual ~LLPanelLandMedia();
-	void refresh();
-
-	static void onCommitAny(LLUICtrl* ctrl, void *userdata);
-	static void onClickStopMedia ( void* data );
-	static void onClickStartMedia ( void* data );
-
-	virtual BOOL postBuild();
-
-protected:
-	LLCheckBoxCtrl* mCheckSoundLocal;
-	LLRadioGroup*	mRadioVoiceChat;
-	LLLineEditor*	mMusicURLEdit;
-	LLLineEditor*	mMediaURLEdit;
-	LLTextureCtrl*	mMediaTextureCtrl;
-	LLCheckBoxCtrl*	mMediaAutoScaleCheck;
-	//LLButton*		mMediaStopButton;
-	//LLButton*		mMediaStartButton;
-
-	LLHandle<LLParcelSelection>&	mParcel;
-};
-
-
-
 class LLPanelLandAccess
 :	public LLPanel
 {
diff --git a/indra/newview/llfloaterpreference.cpp b/indra/newview/llfloaterpreference.cpp
index 8d77d79d83b..060952667b7 100644
--- a/indra/newview/llfloaterpreference.cpp
+++ b/indra/newview/llfloaterpreference.cpp
@@ -150,11 +150,9 @@ LLPreferenceCore::LLPreferenceCore(LLTabContainerCommon* tab_container, LLButton
 	mTabContainer->addTabPanel(mNetworkPanel, mNetworkPanel->getLabel(), FALSE, onTabChanged, mTabContainer);
 	mNetworkPanel->setDefaultBtn(default_btn);
 
-	#if LL_LIBXUL_ENABLED
 	mWebPanel = new LLPanelWeb();
 	mTabContainer->addTabPanel(mWebPanel, mWebPanel->getLabel(), FALSE, onTabChanged, mTabContainer);
 	mWebPanel->setDefaultBtn(default_btn);
-	#endif
 
 	mDisplayPanel = new LLPanelDisplay();
 	mTabContainer->addTabPanel(mDisplayPanel, mDisplayPanel->getLabel(), FALSE, onTabChanged, mTabContainer);
@@ -257,13 +255,11 @@ LLPreferenceCore::~LLPreferenceCore()
 		delete mMsgPanel;
 		mMsgPanel = NULL;
 	}
-	#if LL_LIBXUL_ENABLED
 	if (mWebPanel)
 	{
 		delete mWebPanel;
 		mWebPanel = NULL;
 	}
-	#endif
 }
 
 
@@ -279,9 +275,7 @@ void LLPreferenceCore::apply()
 	mPrefsVoice->apply();
 	mPrefsIM->apply();
 	mMsgPanel->apply();
-	#if LL_LIBXUL_ENABLED
 	mWebPanel->apply();
-	#endif
 #if LL_WINDOWS && LL_LCD_COMPILE
 	// only add this option if we actually have a logitech keyboard / speaker set
 	if (gLcdScreen->Enabled())
@@ -306,9 +300,7 @@ void LLPreferenceCore::cancel()
 	mPrefsVoice->cancel();
 	mPrefsIM->cancel();
 	mMsgPanel->cancel();
-	#if LL_LIBXUL_ENABLED
 	mWebPanel->cancel();
-	#endif
 #if LL_WINDOWS && LL_LCD_COMPILE
 	// only add this option if we actually have a logitech keyboard / speaker set
 	if (gLcdScreen->Enabled())
diff --git a/indra/newview/llfloatertos.cpp b/indra/newview/llfloatertos.cpp
index 20f9e1ecd40..bdf583126f9 100644
--- a/indra/newview/llfloatertos.cpp
+++ b/indra/newview/llfloatertos.cpp
@@ -145,7 +145,6 @@ BOOL LLFloaterTOS::postBuild()
 		return TRUE;
 	}
 
-#if LL_LIBXUL_ENABLED
 	// disable Agree to TOS radio button until the page has fully loaded
 	LLRadioGroup* tos_agreement = LLUICtrlFactory::getRadioGroupByName(this, "tos_agreement");
 	if ( tos_agreement )
@@ -172,18 +171,6 @@ BOOL LLFloaterTOS::postBuild()
 		gResponsePtr = LLIamHere::build( this );
 		LLHTTPClient::get( childGetValue( "real_url" ).asString(), gResponsePtr );
 	};
-#else
-	LLTextEditor *Editor = LLUICtrlFactory::getTextEditorByName(this, "tos_text");
-	if (Editor)
-	{
-		Editor->setHandleEditKeysDirectly( TRUE );
-		Editor->setEnabled( FALSE );
-		Editor->setReadOnlyFgColor(LLColor4::white);
-		Editor->setWordWrap(TRUE);
-		Editor->setFocus(TRUE);
-	}
-	childSetValue("tos_text", LLSD(mMessage));	
-#endif
 
 	return TRUE;
 }
@@ -193,7 +180,6 @@ void LLFloaterTOS::setSiteIsAlive( bool alive )
 	// only do this for TOS pages
 	if ( mType == TOS_TOS )
 	{
-#if LL_LIBXUL_ENABLED
 		LLWebBrowserCtrl* web_browser = LLUICtrlFactory::getWebBrowserCtrlByName(this, "tos_html");
 		// if the contents of the site was retrieved
 		if ( alive )
@@ -220,20 +206,17 @@ void LLFloaterTOS::setSiteIsAlive( bool alive )
 				web_browser->setVisible( FALSE );
 			};
 		};
-#endif // LL_LIBXUL_ENABLED
 	};
 }
 
 LLFloaterTOS::~LLFloaterTOS()
 {
-#if LL_LIBXUL_ENABLED
 	// stop obsaerving events
 	LLWebBrowserCtrl* web_browser = LLUICtrlFactory::getWebBrowserCtrlByName(this, "tos_html");
 	if ( web_browser )
 	{
 		web_browser->addObserver( this );		
 	};
-#endif // LL_LIBXUL_ENABLED
 
 	// tell the responder we're not here anymore
 	if ( gResponsePtr )
diff --git a/indra/newview/llfloaterurlentry.cpp b/indra/newview/llfloaterurlentry.cpp
new file mode 100644
index 00000000000..1ad9e0577c0
--- /dev/null
+++ b/indra/newview/llfloaterurlentry.cpp
@@ -0,0 +1,268 @@
+/** 
+ * @file llfloaterurlentry.cpp
+ * @brief LLFloaterURLEntry class implementation
+ *
+ * Copyright (c) 2002-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+
+#include "llviewerprecompiledheaders.h"
+
+#include "llfloaterurlentry.h"
+
+#include "llpanellandmedia.h"
+
+// project includes
+#include "llcombobox.h"
+#include "llurlhistory.h"
+#include "llvieweruictrlfactory.h"
+#include "llwindow.h"
+#include "llviewerwindow.h"
+
+static LLFloaterURLEntry* sInstance = NULL;
+
+// Move this to its own file.
+// helper class that tries to download a URL from a web site and calls a method 
+// on the Panel Land Media and to discover the MIME type
+class LLMediaTypeResponder : public LLHTTPClient::Responder
+{
+public:
+	LLMediaTypeResponder( LLViewHandle parent ) :
+	  mParent( parent )
+	  {}
+
+	  LLViewHandle mParent;
+
+
+	  virtual void completedHeader(U32 status, const std::string& reason, const LLSD& content)
+	  {
+		  std::string media_type = content["content-type"].asString();
+		  std::string::size_type idx1 = media_type.find_first_of(";");
+		  std::string mime_type = media_type.substr(0, idx1);
+		  completeAny(status, mime_type);
+	  }
+
+	  virtual void error( U32 status, const std::string& reason )
+	  {
+		  completeAny(status, "none/none");
+	  }
+
+	  void completeAny(U32 status, const std::string& mime_type)
+	  {
+		  LLFloaterURLEntry* floater_url_entry =
+			  (LLFloaterURLEntry*)LLFloater::getFloaterByHandle(mParent);
+		  if ( floater_url_entry )
+			  floater_url_entry->headerFetchComplete( status, mime_type );
+	  }
+};
+
+//-----------------------------------------------------------------------------
+// LLFloaterURLEntry()
+//-----------------------------------------------------------------------------
+LLFloaterURLEntry::LLFloaterURLEntry(LLViewHandle parent)
+	:
+	LLFloater(),
+	mPanelLandMediaHandle(parent)
+{
+	gUICtrlFactory->buildFloater(this, "floater_url_entry.xml");
+
+	mMediaURLEdit = LLUICtrlFactory::getComboBoxByName(this, "media_entry");
+
+	// Cancel button
+	childSetAction("cancel_btn", onBtnCancel, this);
+
+	// Cancel button
+	childSetAction("clear_btn", onBtnClear, this);
+
+	// clear media list button
+	LLSD parcel_history = LLURLHistory::getURLHistory("parcel");
+	bool enable_clear_button = parcel_history.size() > 0 ? true : false;
+	childSetEnabled( "clear_btn", enable_clear_button );
+
+	// OK button
+	childSetAction("ok_btn", onBtnOK, this);
+
+	setDefaultBtn("ok_btn");
+	buildURLHistory();
+
+	sInstance = this;
+}
+
+//-----------------------------------------------------------------------------
+// ~LLFloaterURLEntry()
+//-----------------------------------------------------------------------------
+LLFloaterURLEntry::~LLFloaterURLEntry()
+{
+	sInstance = NULL;
+}
+
+void LLFloaterURLEntry::buildURLHistory()
+{
+	LLCtrlListInterface* url_list = childGetListInterface("media_entry");
+	if (url_list)
+	{
+		url_list->operateOnAll(LLCtrlListInterface::OP_DELETE);
+	}
+
+	// Get all of the entries in the "parcel" collection
+	LLSD parcel_history = LLURLHistory::getURLHistory("parcel");
+
+	LLSD::array_iterator iter_history =
+		parcel_history.beginArray();
+	LLSD::array_iterator end_history =
+		parcel_history.endArray();
+	for(; iter_history != end_history; ++iter_history)
+	{
+		url_list->addSimpleElement((*iter_history).asString());
+	}
+}
+
+void LLFloaterURLEntry::headerFetchComplete(U32 status, const std::string& mime_type)
+{
+	LLPanelLandMedia* panel_media = (LLPanelLandMedia*)LLPanel::getPanelByHandle(mPanelLandMediaHandle);
+	if (panel_media)
+	{
+		// status is ignored for now -- error = "none/none"
+		panel_media->setMediaType(mime_type);
+		panel_media->setMediaURL(mMediaURLEdit->getValue().asString());
+	}
+	// Decrement the cursor
+	getWindow()->decBusyCount();
+	childSetVisible("loading_label", false);
+	close();
+}
+
+// static
+LLViewHandle LLFloaterURLEntry::show(LLViewHandle parent)
+{
+	if (sInstance)
+	{
+		sInstance->open();
+	}
+	else
+	{
+		sInstance = new LLFloaterURLEntry(parent);
+	}
+	sInstance->updateFromLandMediaPanel();
+	return sInstance->getHandle();
+}
+
+void LLFloaterURLEntry::updateFromLandMediaPanel()
+{
+	LLPanelLandMedia* panel_media = (LLPanelLandMedia*)LLPanel::getPanelByHandle(mPanelLandMediaHandle);
+	if (panel_media)
+	{
+		std::string media_url = panel_media->getMediaURL();
+		addURLToCombobox(media_url);
+	}
+}
+
+bool LLFloaterURLEntry::addURLToCombobox(const std::string& media_url)
+{
+	if(! mMediaURLEdit->setSimple( media_url ) && ! media_url.empty())
+	{
+		mMediaURLEdit->add( media_url );
+		mMediaURLEdit->setSimple( media_url );
+		return true;
+	}
+
+	// URL was not added for whatever reason (either it was empty or already existed)
+	return false;
+}
+
+// static 
+//-----------------------------------------------------------------------------
+// onBtnOK()
+//-----------------------------------------------------------------------------
+void LLFloaterURLEntry::onBtnOK( void* userdata )
+{
+	LLFloaterURLEntry *self =(LLFloaterURLEntry *)userdata;
+
+	std::string media_url	= self->mMediaURLEdit->getValue().asString();
+	self->mMediaURLEdit->remove(media_url);
+	LLURLHistory::removeURL("parcel", media_url);
+	if(self->addURLToCombobox(media_url))
+	{
+		// Add this url to the parcel collection
+		LLURLHistory::addURL("parcel", media_url);
+	}
+
+	// leading whitespace causes problems with the MIME-type detection so strip it
+	LLString::trim( media_url );
+
+	// First check the URL scheme
+	LLURI url(media_url);
+	std::string scheme = url.scheme();
+
+	// We assume that an empty scheme is an http url, as this is how we will treat it.
+	if(scheme == "")
+	{
+		scheme = "http";
+	}
+
+	// Discover the MIME type only for "http" scheme.
+	if(scheme == "http")
+	{
+		LLHTTPClient::getHeaderOnly( media_url,
+			new LLMediaTypeResponder(self->getHandle()));
+	}
+	else
+	{
+		self->headerFetchComplete(0, scheme);
+	}
+	
+	// Grey the buttons until we get the header response
+	self->childSetEnabled("ok_btn", false);
+	self->childSetEnabled("cancel_btn", false);
+	self->childSetEnabled("media_entry", false);
+
+	// show progress bar here?
+	getWindow()->incBusyCount();
+	self->childSetVisible("loading_label", true);
+}
+
+// static 
+//-----------------------------------------------------------------------------
+// onBtnCancel()
+//-----------------------------------------------------------------------------
+void LLFloaterURLEntry::onBtnCancel( void* userdata )
+{
+	LLFloaterURLEntry *self =(LLFloaterURLEntry *)userdata;
+	self->close();
+}
+
+// static 
+//-----------------------------------------------------------------------------
+// onBtnClear()
+//-----------------------------------------------------------------------------
+void LLFloaterURLEntry::onBtnClear( void* userdata )
+{
+	gViewerWindow->alertXml( "ConfirmClearMediaUrlList", callback_clear_url_list, userdata );
+}
+
+void LLFloaterURLEntry::callback_clear_url_list(S32 option, void* userdata)
+{
+	if ( option == 0 ) // YES
+	{
+		LLFloaterURLEntry *self =(LLFloaterURLEntry *)userdata;
+
+		if ( self )
+		{
+			// clear saved list
+			LLCtrlListInterface* url_list = self->childGetListInterface("media_entry");
+			if ( url_list )
+			{
+				url_list->operateOnAll( LLCtrlListInterface::OP_DELETE );
+			}
+
+			// clear current contents of combo box
+			self->mMediaURLEdit->clear();
+
+			// clear stored version of list
+			LLURLHistory::clear("parcel");
+
+			// cleared the list so disable Clear button
+			self->childSetEnabled( "clear_btn", false );
+		}
+	}
+}
diff --git a/indra/newview/llfloaterurlentry.h b/indra/newview/llfloaterurlentry.h
new file mode 100644
index 00000000000..022c1eddd70
--- /dev/null
+++ b/indra/newview/llfloaterurlentry.h
@@ -0,0 +1,44 @@
+/** 
+ * @file llfloaternamedesc.h
+ * @brief LLFloaterNameDesc class definition
+ *
+ * Copyright (c) 2002-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+
+#ifndef LL_LLFLOATERURLENTRY_H
+#define LL_LLFLOATERURLENTRY_H
+
+#include "llfloater.h"
+
+class LLLineEditor;
+
+class LLFloaterURLEntry : public LLFloater
+{
+public:
+	// Can only be shown by LLPanelLandMedia, and pushes data back into
+	// that panel via the handle.
+	static LLViewHandle show(LLViewHandle panel_land_media_handle);
+
+	void updateFromLandMediaPanel();
+
+	void headerFetchComplete(U32 status, const std::string& mime_type);
+	
+	bool addURLToCombobox(const std::string& media_url);
+
+private:
+	LLFloaterURLEntry(LLViewHandle parent);
+	/*virtual*/ ~LLFloaterURLEntry();
+	void buildURLHistory();
+
+private:
+	LLComboBox*		mMediaURLEdit;
+	LLViewHandle	mPanelLandMediaHandle;
+
+	static void		onBtnOK(void*);
+	static void		onBtnCancel(void*);
+	static void		onBtnClear(void*);
+	static void		callback_clear_url_list(S32 option, void* userdata);
+};
+
+#endif  // LL_LLFLOATERURLENTRY_H
diff --git a/indra/newview/llglsandbox.cpp b/indra/newview/llglsandbox.cpp
index ba56d70c0a7..29b739bca36 100644
--- a/indra/newview/llglsandbox.cpp
+++ b/indra/newview/llglsandbox.cpp
@@ -851,11 +851,11 @@ void LLViewerParcelMgr::renderCollisionSegments(U8* segments, BOOL use_pass, LLV
 	
 	if (use_pass && (mCollisionBanned == BA_NOT_ON_LIST))
 	{
-		LLViewerImage::bindTexture(mPassImage);
+		LLViewerImage::bindTexture( getPassImage() );
 	}
 	else
 	{
-		LLViewerImage::bindTexture(mBlockedImage);
+		LLViewerImage::bindTexture( getBlockedImage() );
 	}
 
 	glBegin(GL_QUADS);
diff --git a/indra/newview/llmimetypes.cpp b/indra/newview/llmimetypes.cpp
new file mode 100644
index 00000000000..3c4dab8e049
--- /dev/null
+++ b/indra/newview/llmimetypes.cpp
@@ -0,0 +1,241 @@
+/** 
+ * @file llmimetypes.cpp
+ * @author James Cook
+ * @brief Translates a MIME type like "video/quicktime" into a
+ * localizable user-friendly string like "QuickTime Movie"
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+#include "llviewerprecompiledheaders.h"
+
+#include "llmimetypes.h"
+
+#include "llvieweruictrlfactory.h"
+
+LLMIMETypes::mime_info_map_t LLMIMETypes::sMap;
+LLMIMETypes::mime_widget_set_map_t LLMIMETypes::sWidgetMap;
+
+LLString sDefaultLabel;
+	// Returned when we don't know what to do with the mime type
+LLString sDefaultWidgetType;
+	// Returned when we don't know what widget set to use
+LLString sDefaultImpl;
+	// Returned when we don't know what impl to use
+
+/////////////////////////////////////////////////////////////////////////////
+
+// static
+bool LLMIMETypes::parseMIMETypes(const LLString& xml_filename)
+{
+	LLXMLNodePtr root;
+	bool success = LLViewerUICtrlFactory::getLayeredXMLNode(xml_filename, root);
+	if (!success || !root || !root->hasName("mimetypes"))
+	{
+		llwarns << "Unable to read MIME type file: "
+			<< xml_filename << llendl;
+		return false;
+	}
+
+	for (LLXMLNode* node = root->getFirstChild();
+		 node != NULL;
+		 node = node->getNextSibling())
+	{
+		if (node->hasName("defaultlabel"))
+		{
+			sDefaultLabel = node->getTextContents();
+		}
+		else if (node->hasName("defaultwidget"))
+		{
+			sDefaultWidgetType = node->getTextContents();
+		}
+		else if (node->hasName("defaultimpl"))
+		{
+			sDefaultImpl = node->getTextContents();
+		}
+		else if (node->hasName("mimetype") || node->hasName("scheme"))
+		{
+			LLString mime_type;
+			node->getAttributeString("name", mime_type);
+			LLMIMEInfo info;
+			for (LLXMLNode* child = node->getFirstChild();
+				 child != NULL;
+				 child = child->getNextSibling())
+			{
+				if (child->hasName("label"))
+				{
+					info.mLabel = child->getTextContents();
+				}
+				else if (child->hasName("widgettype"))
+				{
+					info.mWidgetType = child->getTextContents();
+				}
+				else if (child->hasName("impl"))
+				{
+					info.mImpl = child->getTextContents();
+				}
+			}
+			sMap[mime_type] = info;
+		}
+		else if (node->hasName("widgetset"))
+		{
+			LLString set_name;
+			node->getAttributeString("name", set_name);
+			LLMIMEWidgetSet info;
+			for (LLXMLNode* child = node->getFirstChild();
+				child != NULL;
+				child = child->getNextSibling())
+			{
+				if (child->hasName("label"))
+				{
+					info.mLabel = child->getTextContents();
+				}
+				if (child->hasName("icon"))
+				{
+					info.mIcon = child->getTextContents();
+				}
+				if (child->hasName("default_type"))
+				{
+					info.mDefaultMimeType = child->getTextContents();
+				}
+				if (child->hasName("tooltip"))
+				{
+					info.mToolTip = child->getTextContents();
+				}
+				if (child->hasName("playtip"))
+				{
+					info.mPlayTip = child->getTextContents();
+				}
+				if (child->hasName("allow_resize"))
+				{
+					child->getBoolValue( 1, (BOOL*)&( info.mAllowResize ) );
+				}
+				if (child->hasName("allow_looping"))
+				{
+					child->getBoolValue( 1, (BOOL*)&( info.mAllowLooping ) );
+				}
+			}
+			sWidgetMap[set_name] = info;
+		}
+	}
+	return true;
+}
+
+// static
+LLString LLMIMETypes::translate(const LLString& mime_type)
+{
+	mime_info_map_t::const_iterator it = sMap.find(mime_type);
+	if (it != sMap.end())
+	{
+		return it->second.mLabel;
+	}
+	else
+	{
+		return sDefaultLabel;
+	}
+}
+
+// static
+LLString LLMIMETypes::widgetType(const LLString& mime_type)
+{
+	mime_info_map_t::const_iterator it = sMap.find(mime_type);
+	if (it != sMap.end())
+	{
+		return it->second.mWidgetType;
+	}
+	else
+	{
+		return sDefaultWidgetType;
+	}
+}
+
+// static
+LLString LLMIMETypes::implType(const LLString& mime_type)
+{
+	mime_info_map_t::const_iterator it = sMap.find(mime_type);
+	if (it != sMap.end())
+	{
+		return it->second.mImpl;
+	}
+	else
+	{
+		return sDefaultImpl;
+	}
+}
+
+// static
+LLString LLMIMETypes::findIcon(const LLString& mime_type)
+{
+	LLString icon = "";
+	LLString widget_type = LLMIMETypes::widgetType(mime_type);
+	mime_widget_set_map_t::iterator it = sWidgetMap.find(widget_type);
+	if(it != sWidgetMap.end())
+	{
+		icon = it->second.mIcon;
+	}
+	return icon;
+}
+
+// static
+LLString LLMIMETypes::findDefaultMimeType(const LLString& widget_type)
+{
+	LLString mime_type = "none/none";
+	mime_widget_set_map_t::iterator it = sWidgetMap.find(widget_type);
+	if(it != sWidgetMap.end())
+	{
+		mime_type = it->second.mDefaultMimeType;
+	}
+	return mime_type;
+}
+
+// static
+LLString LLMIMETypes::findToolTip(const LLString& mime_type)
+{
+	LLString tool_tip = "";
+	LLString widget_type = LLMIMETypes::widgetType(mime_type);
+	mime_widget_set_map_t::iterator it = sWidgetMap.find(widget_type);
+	if(it != sWidgetMap.end())
+	{
+		tool_tip = it->second.mToolTip;
+	}
+	return tool_tip;
+}
+
+// static
+LLString LLMIMETypes::findPlayTip(const LLString& mime_type)
+{
+	LLString play_tip = "";
+	LLString widget_type = LLMIMETypes::widgetType(mime_type);
+	mime_widget_set_map_t::iterator it = sWidgetMap.find(widget_type);
+	if(it != sWidgetMap.end())
+	{
+		play_tip = it->second.mPlayTip;
+	}
+	return play_tip;
+}
+
+// static
+bool LLMIMETypes::findAllowResize(const LLString& mime_type)
+{
+	bool allow_resize = false;
+	LLString widget_type = LLMIMETypes::widgetType(mime_type);
+	mime_widget_set_map_t::iterator it = sWidgetMap.find(widget_type);
+	if(it != sWidgetMap.end())
+	{
+		allow_resize = it->second.mAllowResize;
+	}
+	return allow_resize;
+}
+
+// static
+bool LLMIMETypes::findAllowLooping(const LLString& mime_type)
+{
+	bool allow_looping = false;
+	LLString widget_type = LLMIMETypes::widgetType(mime_type);
+	mime_widget_set_map_t::iterator it = sWidgetMap.find(widget_type);
+	if(it != sWidgetMap.end())
+	{
+		allow_looping = it->second.mAllowLooping;
+	}
+	return allow_looping;
+}
diff --git a/indra/newview/llmimetypes.h b/indra/newview/llmimetypes.h
new file mode 100644
index 00000000000..1c309477a21
--- /dev/null
+++ b/indra/newview/llmimetypes.h
@@ -0,0 +1,95 @@
+/** 
+ * @file llmimetypes.h
+ * @author James Cook
+ * @brief Translates a MIME type like "video/quicktime" into a
+ * localizable user-friendly string like "QuickTime Movie"
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+#ifndef LLMIMETYPES_H
+#define LLMIMETYPES_H
+
+#include "llstring.h"	// because XML parsing lib uses LLString, ugh
+#include <map>
+
+class LLMIMETypes
+{
+public:
+	static bool parseMIMETypes(const LLString& xml_file_path);
+		// Loads the MIME string definition XML file, usually
+		// from the application skins directory
+
+	static LLString translate(const LLString& mime_type);
+		// Returns "QuickTime Movie" from "video/quicktime"
+
+	static LLString widgetType(const LLString& mime_type);
+		// Type of control widgets for this MIME type
+		// Returns "movie" from "video/quicktime"
+
+	static LLString implType(const LLString& mime_type);
+		// Type of Impl to use for decoding media.
+
+	static LLString findIcon(const LLString& mime_type);
+		// Icon from control widget type for this MIME type
+
+	static LLString findToolTip(const LLString& mime_type);
+		// Tool tip from control widget type for this MIME type
+
+	static LLString findPlayTip(const LLString& mime_type);
+		// Play button tool tip from control widget type for this MIME type
+
+	static LLString findDefaultMimeType(const LLString& widget_type);
+		// Canonical mime type associated with this widget set
+
+	static bool findAllowResize(const LLString& mime_type);
+		// accessor for flag to enable/disable media size edit fields
+
+	static bool LLMIMETypes::findAllowLooping(const LLString& mime_type);
+		// accessor for flag to enable/disable media looping checkbox
+
+public:
+	struct LLMIMEInfo
+	{
+		LLString mLabel;
+			// friendly label like "QuickTime Movie"
+
+		LLString mWidgetType;
+			// "web" means use web media UI widgets
+
+		LLString mImpl;
+			// which impl to use with this mime type
+	};
+	struct LLMIMEWidgetSet
+	{
+		LLString mLabel;
+			// friendly label like "QuickTime Movie"
+
+		LLString mIcon;
+			// Name of icon asset to display in toolbar
+
+		LLString mDefaultMimeType;
+			// Mime type string to use in absence of a specific one
+
+		LLString mToolTip;
+			// custom tool tip for this mime type
+
+		LLString mPlayTip;
+			// custom tool tip to display for Play button
+
+		bool mAllowResize;
+			// enable/disable media size edit fields
+
+		bool mAllowLooping;
+			// enable/disable media looping checkbox
+	};
+	typedef std::map< LLString, LLMIMEInfo > mime_info_map_t;
+	typedef std::map< LLString, LLMIMEWidgetSet > mime_widget_set_map_t;
+
+	// Public so users can iterate over it
+	static mime_info_map_t sMap;
+	static mime_widget_set_map_t sWidgetMap;
+private:
+};
+
+#endif
diff --git a/indra/newview/lloverlaybar.cpp b/indra/newview/lloverlaybar.cpp
index 15195d8f02b..2c33cccf718 100644
--- a/indra/newview/lloverlaybar.cpp
+++ b/indra/newview/lloverlaybar.cpp
@@ -42,7 +42,6 @@
 #include "llchatbar.h"
 #include "llfocusmgr.h"
 #include "llimview.h"
-#include "llmediaengine.h"
 #include "llmediaremotectrl.h"
 #include "llpanelaudiovolume.h"
 #include "llparcel.h"
@@ -50,7 +49,10 @@
 #include "llui.h"
 #include "llviewercontrol.h"
 #include "llviewerimagelist.h"
+#include "llviewermedia.h"
 #include "llviewermenu.h"	// handle_reset_view()
+#include "llviewermedia.h"
+#include "llviewerparcelmedia.h"
 #include "llviewerparcelmgr.h"
 #include "llvieweruictrlfactory.h"
 #include "llviewerwindow.h"
@@ -97,7 +99,6 @@ LLOverlayBar::LLOverlayBar()
 	:	LLPanel(),
 		mMediaRemote(NULL),
 		mVoiceRemote(NULL),
-		mMediaState(STOPPED),
 		mMusicState(STOPPED)
 {
 	setMouseOpaque(FALSE);
@@ -220,7 +221,7 @@ void LLOverlayBar::refresh()
 
 	BOOL controls_grabbed = gAgent.anyControlGrabbed();
 	button = LLUICtrlFactory::getButtonByName(this, "Release Keys");
-	
+
 	if (button && button->getVisible() != controls_grabbed)
 	{
 		button->setVisible(controls_grabbed);
@@ -231,7 +232,7 @@ void LLOverlayBar::refresh()
 
 	BOOL mouselook_grabbed;
 	mouselook_grabbed = gAgent.isControlGrabbed(CONTROL_ML_LBUTTON_DOWN_INDEX)
-						|| gAgent.isControlGrabbed(CONTROL_ML_LBUTTON_UP_INDEX);
+		|| gAgent.isControlGrabbed(CONTROL_ML_LBUTTON_UP_INDEX);
 	button = LLUICtrlFactory::getButtonByName(this, "Mouselook");
 
 	if (button && button->getVisible() != mouselook_grabbed)
@@ -257,7 +258,6 @@ void LLOverlayBar::refresh()
 		buttons_changed = TRUE;
 	}
 
-	enableMediaButtons();
 
 	moveChildToBackOfTabGroup(mMediaRemote);
 	moveChildToBackOfTabGroup(mVoiceRemote);
@@ -340,24 +340,40 @@ void LLOverlayBar::mediaPlay(void*)
 		return;
 	}
 
-	if (gOverlayBar->mMediaState != PLAYING)
+	
+	if (LLViewerMedia::isMediaPaused())
+	{
+		LLViewerParcelMedia::start();
+	}
+	else if(LLViewerMedia::isMediaPlaying())
+	{
+		LLViewerParcelMedia::pause();
+	}
+	else
 	{
-		gOverlayBar->mMediaState = PLAYING; // desired state
 		LLParcel* parcel = gParcelMgr->getAgentParcel();
 		if (parcel)
 		{
-			LLString path("");
-			LLMediaEngine::getInstance()->convertImageAndLoadUrl( true, false, path );
+			LLViewerParcelMedia::play(parcel);
 		}
 	}
-	else
+}
+
+//static
+void LLOverlayBar::mediaPause(void*)
+{
+
+	LLViewerParcelMedia::pause();
+}
+
+//static
+void LLOverlayBar::mediaStop(void*)
+{
+	if (!gOverlayBar)
 	{
-		gOverlayBar->mMediaState = PAUSED; // desired state
-		LLMediaEngine::getInstance()->pause();
+		return;
 	}
-
-	//gOverlayBar->mMediaState = STOPPED; // desired state
-	//LLMediaEngine::getInstance()->stop();
+	LLViewerParcelMedia::stop();
 }
 
 //static
@@ -403,39 +419,3 @@ void LLOverlayBar::musicPlay(void*)
 	}
 }
 
-void LLOverlayBar::enableMediaButtons()
-{
-	if (mMediaRemote)
-	{
-		// Music
-		LLParcel* parcel = gParcelMgr->getAgentParcel();
-		if (parcel 
-			&& gAudiop
-			&& !parcel->getMusicURL().empty()
-			&& gSavedSettings.getBOOL("AudioStreamingMusic"))
-		{
-			mMediaRemote->childSetEnabled("music_play", TRUE);
-		}
-		else
-		{
-			mMediaRemote->childSetEnabled("music_play", FALSE);
-		}
-
-		// Media
-		// if there is a url and a texture and media is enabled and available and media streaming is on... (phew!)
-		if (LLMediaEngine::getInstance() 
-			&& LLMediaEngine::getInstance()->getUrl ().length () 
-			&& LLMediaEngine::getInstance()->getImageUUID ().notNull () 
-			&& LLMediaEngine::getInstance()->isEnabled () 
-			&& LLMediaEngine::getInstance()->isAvailable () 
-			&& gSavedSettings.getBOOL ( "AudioStreamingVideo" ) )
-		{
-			mMediaRemote->childSetEnabled("media_play", TRUE);
-		}
-		else
-		{
-			mMediaRemote->childSetEnabled("media_play", FALSE);	
-		}
-	}
-}
-
diff --git a/indra/newview/lloverlaybar.h b/indra/newview/lloverlaybar.h
index 90886e1c729..90ab8d057a6 100644
--- a/indra/newview/lloverlaybar.h
+++ b/indra/newview/lloverlaybar.h
@@ -67,7 +67,6 @@ class LLOverlayBar
 	void layoutButtons();
 
 	// helpers for returning desired state
-	BOOL mediaPlaying() { return mMediaState == PLAYING; }
 	BOOL musicPlaying() { return mMusicState == PLAYING; }
 	
 	static void onClickIMReceived(void* data);
@@ -79,7 +78,14 @@ class LLOverlayBar
 
 	//static media helper functions
 	static void mediaPlay(void*);
+	static void mediaPause(void*);
+	static void mediaStop(void*);
+
 	static void musicPlay(void*);
+	static void musicPause(void*);
+	static void musicStop(void*);
+
+	static void toggleAudioVolumeFloater(void*);
 
 protected:	
 	static void* createMediaRemote(void* userdata);
@@ -93,8 +99,7 @@ class LLOverlayBar
 	LLVoiceRemoteCtrl*	mVoiceRemote;
 	bool mBuilt;	// dialog constructed yet?
 	enum { STOPPED=0, PLAYING=1, PAUSED=2 };
-	BOOL mMediaState;
-	BOOL mMusicState;
+	S32 mMusicState;
 };
 
 extern LLOverlayBar* gOverlayBar;
diff --git a/indra/newview/llpanelavatar.cpp b/indra/newview/llpanelavatar.cpp
index 0146214c4bd..d9416bbf373 100644
--- a/indra/newview/llpanelavatar.cpp
+++ b/indra/newview/llpanelavatar.cpp
@@ -495,7 +495,6 @@ BOOL LLPanelAvatarWeb::postBuild(void)
 
 	childSetControlName("auto_load","AutoLoadWebProfiles");
 
-#if LL_LIBXUL_ENABLED
 	mWebBrowser = (LLWebBrowserCtrl*)getChildByName("profile_html");
 
 	// links open in internally 
@@ -503,7 +502,6 @@ BOOL LLPanelAvatarWeb::postBuild(void)
 
 	// observe browser events
 	mWebBrowser->addObserver( this );
-#endif // LL_LIBXUL_ENABLED
 
 	return TRUE;
 }
@@ -563,13 +561,11 @@ LLPanelAvatarWeb::LLPanelAvatarWeb(const std::string& name, const LLRect& rect,
 
 LLPanelAvatarWeb::~LLPanelAvatarWeb()
 {
-#if LL_LIBXUL_ENABLED
 	// stop observing browser events
 	if  ( mWebBrowser )
 	{
 		mWebBrowser->remObserver( this );
 	};
-#endif
 }
 
 void LLPanelAvatarWeb::enableControls(BOOL self)
@@ -606,12 +602,6 @@ void LLPanelAvatarWeb::setWebURL(std::string url)
 		childSetVisible("profile_html",false);
 	}
 	
-#if !LL_LIBXUL_ENABLED
-	childSetVisible("load",false);
-	childSetVisible("profile_html",false);
-	childSetVisible("status_text",false);
-#endif
-
 }
 
 // static
@@ -627,18 +617,13 @@ void LLPanelAvatarWeb::onCommitURL(LLUICtrl* ctrl, void* data)
 // static
 void LLPanelAvatarWeb::onClickWebProfileHelp(void *)
 {
-#if LL_LIBXUL_ENABLED
 	gViewerWindow->alertXml("ClickWebProfileHelpAvatar");
-#else
-	gViewerWindow->alertXml("ClickWebProfileNoWebHelpAvatar");
-#endif
 }
 
 void LLPanelAvatarWeb::load(std::string url)
 {
 	bool have_url = (!url.empty());
 
-#if LL_LIBXUL_ENABLED
 	if (have_url)
 	{
 		llinfos << "Loading " << url << llendl;
@@ -658,9 +643,6 @@ void LLPanelAvatarWeb::load(std::string url)
 	childSetEnabled("home",use_home);
 	childSetEnabled("open",have_url);
 	
-#else
-	childSetEnabled("open",have_url);
-#endif
 }
 
 void LLPanelAvatarWeb::load()
@@ -692,7 +674,6 @@ void LLPanelAvatarWeb::onClickOpen(void* data)
 	}
 }
 
-#if LL_LIBXUL_ENABLED
 void LLPanelAvatarWeb::onStatusTextChange( const EventType& eventIn )
 {
 	childSetText("status_text", eventIn.getStringValue() );
@@ -702,7 +683,6 @@ void LLPanelAvatarWeb::onLocationChange( const EventType& eventIn )
 {
 	childSetText("url_edit", eventIn.getStringValue() );
 }
-#endif
 
 
 //-----------------------------------------------------------------------------
diff --git a/indra/newview/llpanelavatar.h b/indra/newview/llpanelavatar.h
index 7d491c61436..d992c29304e 100644
--- a/indra/newview/llpanelavatar.h
+++ b/indra/newview/llpanelavatar.h
@@ -137,9 +137,7 @@ class LLPanelAvatarSecondLife
 // WARNING!  The order of the inheritance here matters!!  Do not change.  - KLW
 class LLPanelAvatarWeb : 
 	public LLPanelAvatarTab
-#if LL_LIBXUL_ENABLED
 	, public LLWebBrowserCtrlObserver
-#endif
 {
 public:
 	LLPanelAvatarWeb(const std::string& name, const LLRect& rect, LLPanelAvatar* panel_avatar);
@@ -157,11 +155,9 @@ class LLPanelAvatarWeb :
 	static void onCommitURL(LLUICtrl* ctrl, void* data);
 	static void onClickWebProfileHelp(void *);
 
-#if LL_LIBXUL_ENABLED
 	// browser observer impls
 	virtual void onStatusTextChange( const EventType& eventIn );
 	virtual void onLocationChange( const EventType& eventIn );
-#endif
 
 private:
 	std::string			mURL;
diff --git a/indra/newview/llpanelface.cpp b/indra/newview/llpanelface.cpp
index 8ce2ae5d9cd..83fc991ae04 100644
--- a/indra/newview/llpanelface.cpp
+++ b/indra/newview/llpanelface.cpp
@@ -57,10 +57,9 @@
 #include "lltooldraganddrop.h"
 #include "llui.h"
 #include "llviewercontrol.h"
+#include "llviewermedia.h"
 #include "llviewerobject.h"
 #include "llviewerstats.h"
-#include "llmediaengine.h"
-
 #include "llvieweruictrlfactory.h"
 
 //
@@ -374,14 +373,19 @@ void LLPanelFace::getState()
 		childSetEnabled("button align",FALSE);
 		//mBtnAutoFix->setEnabled ( FALSE );
 		
-		if ( LLMediaEngine::getInstance()->getMediaRenderer () )
-			if ( LLMediaEngine::getInstance()->getMediaRenderer ()->isLoaded () )
-			{	
-				childSetEnabled("textbox autofix",editable);
-				//mLabelTexAutoFix->setEnabled ( editable );
-				childSetEnabled("button align",editable);
-				//mBtnAutoFix->setEnabled ( editable );
-			}
+		if(LLViewerMedia::hasMedia())
+		{
+			childSetEnabled("textbox autofix",editable);
+			childSetEnabled("button align",editable);
+		}
+		//if ( LLMediaEngine::getInstance()->getMediaRenderer () )
+		//	if ( LLMediaEngine::getInstance()->getMediaRenderer ()->isLoaded () )
+		//	{	
+		//		
+		//		//mLabelTexAutoFix->setEnabled ( editable );
+		//		
+		//		//mBtnAutoFix->setEnabled ( editable );
+		//	}
 		childSetEnabled("button apply",editable);
 
 		bool identical;
@@ -884,27 +888,25 @@ struct LLPanelFaceSetMediaFunctor : public LLSelectedTEFunctor
 	virtual bool apply(LLViewerObject* object, S32 te)
 	{
 		// only do this if it's a media texture
-		if ( object->getTE ( te )->getID() ==  LLMediaEngine::getInstance()->getImageUUID () )
+		if ( object->getTE ( te )->getID() == LLViewerMedia::getMediaTextureID() )
 		{
-			// make sure we're valid
-			if ( LLMediaEngine::getInstance()->getMediaRenderer() )
+			S32 media_width, media_height;
+			S32 texture_width, texture_height;
+			if ( LLViewerMedia::getMediaSize( &media_width, &media_height )
+				&& LLViewerMedia::getTextureSize( &texture_width, &texture_height ) )
 			{
-				// calculate correct scaling based on media dimensions and next-power-of-2 texture dimensions
-				F32 scaleS = (F32)LLMediaEngine::getInstance()->getMediaRenderer()->getMediaWidth() / 
-								(F32)LLMediaEngine::getInstance()->getMediaRenderer()->getTextureWidth();
-
-				F32 scaleT = (F32)LLMediaEngine::getInstance()->getMediaRenderer()->getMediaHeight() /
-								(F32)LLMediaEngine::getInstance()->getMediaRenderer()->getTextureHeight();
+				F32 scale_s = (F32)media_width / (F32)texture_width;
+				F32 scale_t = (F32)media_height / (F32)texture_height;
 
 				// set scale and adjust offset
-				object->setTEScaleS( te, scaleS );
-				object->setTEScaleT( te, scaleT );	// don't need to flip Y anymore since QT does this for us now.
-				object->setTEOffsetS( te, -( 1.0f - scaleS ) / 2.0f );
-				object->setTEOffsetT( te, -( 1.0f - scaleT ) / 2.0f );
+				object->setTEScaleS( te, scale_s );
+				object->setTEScaleT( te, scale_t );	// don't need to flip Y anymore since QT does this for us now.
+				object->setTEOffsetS( te, -( 1.0f - scale_s ) / 2.0f );
+				object->setTEOffsetT( te, -( 1.0f - scale_t ) / 2.0f );
 			}
 		}
 		return true;
-	}
+	};
 };
 
 void LLPanelFace::onClickAutoFix(void* userdata)
diff --git a/indra/newview/llpanelland.cpp b/indra/newview/llpanelland.cpp
index d86f81d21d4..45e78f257f4 100644
--- a/indra/newview/llpanelland.cpp
+++ b/indra/newview/llpanelland.cpp
@@ -253,5 +253,5 @@ void LLPanelLandInfo::onClickAbout(void*)
 		gParcelMgr->selectParcelInRectangle();
 	}
 
-	LLFloaterLand::show();
+	LLFloaterLand::showInstance();
 }
diff --git a/indra/newview/llpanellandmedia.cpp b/indra/newview/llpanellandmedia.cpp
new file mode 100644
index 00000000000..1ac95c9a821
--- /dev/null
+++ b/indra/newview/llpanellandmedia.cpp
@@ -0,0 +1,378 @@
+/** 
+ * @file llpanellandmedia.cpp
+ * @author Callum Prentice, Sam Kolb, James Cook
+ * @brief Allows configuration of "media" for a land parcel,
+ *   for example movies, web pages, and audio.
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+#include "llviewerprecompiledheaders.h"
+
+#include "llpanellandmedia.h"
+
+// viewer includes
+#include "llmimetypes.h"
+#include "llviewerparcelmgr.h"
+#include "llvieweruictrlfactory.h"
+
+// library includes
+#include "llcheckboxctrl.h"
+#include "llcombobox.h"
+#include "llfloaterurlentry.h"
+#include "llfocusmgr.h"
+#include "lllineeditor.h"
+#include "llparcel.h"
+#include "lltextbox.h"
+#include "llradiogroup.h"
+#include "llspinctrl.h"
+#include "llsdutil.h"
+#include "lltexturectrl.h"
+#include "roles_constants.h"
+
+// Values for the parcel voice settings radio group
+enum
+{
+	kRadioVoiceChatEstate = 0,
+	kRadioVoiceChatPrivate = 1,
+	kRadioVoiceChatDisable = 2
+};
+
+//---------------------------------------------------------------------------
+// LLPanelLandMedia
+//---------------------------------------------------------------------------
+
+LLPanelLandMedia::LLPanelLandMedia(LLParcelSelectionHandle& parcel)
+:	LLPanel("land_media_panel"), mParcel(parcel)
+{
+}
+
+
+// virtual
+LLPanelLandMedia::~LLPanelLandMedia()
+{
+	// close LLFloaterURLEntry?
+}
+
+
+BOOL LLPanelLandMedia::postBuild()
+{
+	mCheckSoundLocal = LLUICtrlFactory::getCheckBoxByName(this, "check sound local");
+	childSetCommitCallback("check sound local", onCommitAny, this);
+
+	mRadioVoiceChat = LLUICtrlFactory::getRadioGroupByName(this, "parcel_voice_channel");
+	childSetCommitCallback("parcel_voice_channel", onCommitAny, this);
+
+	mMusicURLEdit = LLUICtrlFactory::getLineEditorByName(this, "music_url");
+	childSetCommitCallback("music_url", onCommitAny, this);
+
+	mMediaTextureCtrl = LLUICtrlFactory::getTexturePickerByName(this, "media texture");
+	if (mMediaTextureCtrl)
+	{
+		mMediaTextureCtrl->setCommitCallback( onCommitAny );
+		mMediaTextureCtrl->setCallbackUserData( this );
+		mMediaTextureCtrl->setAllowNoTexture ( TRUE );
+		mMediaTextureCtrl->setImmediateFilterPermMask(PERM_COPY | PERM_TRANSFER);
+		mMediaTextureCtrl->setNonImmediateFilterPermMask(PERM_COPY | PERM_TRANSFER);
+	}
+	else
+	{
+		llwarns << "LLUICtrlFactory::getTexturePickerByName() returned NULL for 'media texure'" << llendl;
+	}
+		
+	mMediaAutoScaleCheck = LLUICtrlFactory::getCheckBoxByName(this, "media_auto_scale");
+	childSetCommitCallback("media_auto_scale", onCommitAny, this);
+
+	mMediaLoopCheck = LLUICtrlFactory::getCheckBoxByName(this, "media_loop");
+	childSetCommitCallback("media_loop", onCommitAny, this);
+
+	mMediaUrlCheck = LLUICtrlFactory::getCheckBoxByName(this, "hide_media_url");
+	childSetCommitCallback("hide_media_url", onCommitAny, this);
+
+	mMusicUrlCheck = LLUICtrlFactory::getCheckBoxByName(this, "hide_music_url");
+	childSetCommitCallback("hide_music_url", onCommitAny, this);
+
+	mMediaURLEdit = LLUICtrlFactory::getLineEditorByName(this, "media_url");
+	childSetCommitCallback("media_url", onCommitAny, this);
+
+	mMediaDescEdit = LLUICtrlFactory::getLineEditorByName(this, "url_description");
+	childSetCommitCallback("url_description", onCommitAny, this);
+
+	mMediaTypeCombo = LLUICtrlFactory::getComboBoxByName(this, "media type");
+	childSetCommitCallback("media type", onCommitType, this);
+	populateMIMECombo();
+	mMediaTypeCombo->sortByName();
+
+	mMediaWidthCtrl = LLUICtrlFactory::getSpinnerByName(this, "media_size_width");
+	childSetCommitCallback("media_size_width", onCommitAny, this);
+	mMediaHeightCtrl = LLUICtrlFactory::getSpinnerByName(this, "media_size_height");
+	childSetCommitCallback("media_size_height", onCommitAny, this);
+	mMediaSizeCtrlLabel = LLUICtrlFactory::getTextBoxByName(this, "media_size");
+
+	mSetURLButton = LLUICtrlFactory::getButtonByName(this, "set_media_url");
+	childSetAction("set_media_url", onSetBtn, this);
+
+	return TRUE;
+}
+
+
+// public
+void LLPanelLandMedia::refresh()
+{
+	LLParcel *parcel = mParcel->getParcel();
+
+	if (!parcel)
+	{
+		clearCtrls();
+	}
+	else
+	{
+		// something selected, hooray!
+
+		// Display options
+		BOOL can_change_media = LLViewerParcelMgr::isParcelModifiableByAgent(parcel, GP_LAND_CHANGE_MEDIA);
+
+		mCheckSoundLocal->set( parcel->getSoundLocal() );
+		mCheckSoundLocal->setEnabled( can_change_media );
+
+		if(parcel->getVoiceEnabled())
+		{
+			if(parcel->getVoiceUseEstateChannel())
+				mRadioVoiceChat->setSelectedIndex(kRadioVoiceChatEstate);
+			else
+				mRadioVoiceChat->setSelectedIndex(kRadioVoiceChatPrivate);
+		}
+		else
+		{
+			mRadioVoiceChat->setSelectedIndex(kRadioVoiceChatDisable);
+		}
+
+		mRadioVoiceChat->setEnabled( can_change_media );
+
+		mMusicURLEdit->setText(parcel->getMusicURL());
+		mMusicURLEdit->setEnabled( can_change_media );
+
+		mMediaURLEdit->setText(parcel->getMediaURL());
+		mMediaURLEdit->setEnabled( FALSE );
+
+		mMediaDescEdit->setText(LLString(parcel->getMediaDesc()));
+		mMediaDescEdit->setEnabled( can_change_media );
+
+		std::string mime_type = parcel->getMediaType();
+		if (mime_type.empty())
+		{
+			mime_type = "none/none";
+		}
+		setMediaType(mime_type);
+		mMediaTypeCombo->setEnabled( can_change_media );
+		childSetText("mime_type", mime_type);
+
+		mMediaUrlCheck->set( parcel->getObscureMedia() );
+		mMediaUrlCheck->setEnabled( can_change_media );
+
+		mMusicUrlCheck->set( parcel->getObscureMusic() );
+		mMusicUrlCheck->setEnabled( can_change_media );
+
+		// don't display urls if you're not able to change it
+		// much requested change in forums so people can't 'steal' urls
+		// NOTE: bug#2009 means this is still vunerable - however, bug 
+		// should be closed since this bug opens up major security issues elsewhere.
+		bool obscure_media = ! can_change_media && parcel->getObscureMedia();
+		bool obscure_music = ! can_change_media && parcel->getObscureMusic();
+
+		// Special code to disable asterixes for html type
+		if(mime_type == "text/html")
+		{
+			obscure_media = false;
+			mMediaUrlCheck->set( 0 );
+			mMediaUrlCheck->setEnabled( false );
+		}
+
+		mMusicURLEdit->setDrawAsterixes( obscure_music );
+		mMediaURLEdit->setDrawAsterixes( obscure_media );
+
+		mMediaAutoScaleCheck->set( parcel->getMediaAutoScale () );
+		mMediaAutoScaleCheck->setEnabled ( can_change_media );
+
+		// Special code to disable looping checkbox for HTML MIME type
+		// (DEV-10042 -- Parcel Media: "Loop Media" should be disabled for static media types)
+		bool allow_looping = LLMIMETypes::findAllowLooping( mime_type );
+		if ( allow_looping )
+			mMediaLoopCheck->set( parcel->getMediaLoop () );
+		else
+			mMediaLoopCheck->set( false );
+		mMediaLoopCheck->setEnabled ( can_change_media && allow_looping );
+
+		// disallow media size change for mime types that don't allow it
+		bool allow_resize = LLMIMETypes::findAllowResize( mime_type );
+		if ( allow_resize )
+			mMediaWidthCtrl->setValue( parcel->getMediaWidth() );
+		else
+			mMediaWidthCtrl->setValue( 0 );
+		mMediaWidthCtrl->setEnabled ( can_change_media && allow_resize );
+
+		if ( allow_resize )
+			mMediaHeightCtrl->setValue( parcel->getMediaHeight() );
+		else
+			mMediaHeightCtrl->setValue( 0 );
+		mMediaHeightCtrl->setEnabled ( can_change_media && allow_resize );
+
+		// enable/disable for text label for completeness
+		mMediaSizeCtrlLabel->setEnabled( can_change_media && allow_resize );
+
+		LLUUID tmp = parcel->getMediaID();
+		mMediaTextureCtrl->setImageAssetID ( parcel->getMediaID() );
+		mMediaTextureCtrl->setEnabled( can_change_media );
+
+		mSetURLButton->setEnabled( can_change_media );
+
+		#if 0
+		// there is a media url and a media texture selected
+		if ( ( ! ( std::string ( parcel->getMediaURL() ).empty () ) ) && ( ! ( parcel->getMediaID ().isNull () ) ) )
+		{
+			// turn on transport controls if allowed for this parcel
+			mMediaStopButton->setEnabled ( editable );
+			mMediaStartButton->setEnabled ( editable );
+		}
+		else
+		{
+			// no media url or no media texture
+			mMediaStopButton->setEnabled ( FALSE );
+			mMediaStartButton->setEnabled ( FALSE );
+		};
+		#endif
+
+		LLFloaterURLEntry* floater_url_entry = (LLFloaterURLEntry*)LLFloater::getFloaterByHandle(mURLEntryFloater);
+		if (floater_url_entry)
+		{
+			floater_url_entry->updateFromLandMediaPanel();
+		}
+	}
+}
+
+void LLPanelLandMedia::populateMIMECombo()
+{
+	LLMIMETypes::mime_widget_set_map_t::const_iterator it;
+	for (it = LLMIMETypes::sWidgetMap.begin(); it != LLMIMETypes::sWidgetMap.end(); ++it)
+	{
+		const LLString& mime_type = it->first;
+		const LLMIMETypes::LLMIMEWidgetSet& info = it->second;
+		mMediaTypeCombo->add(info.mLabel, mime_type);
+	}
+}
+void LLPanelLandMedia::setMediaType(const LLString& mime_type)
+{
+	LLParcel *parcel = mParcel->getParcel();
+	if(parcel)
+		parcel->setMediaType(mime_type.c_str());
+
+	LLString media_key = LLMIMETypes::widgetType(mime_type);
+	mMediaTypeCombo->setValue(media_key);
+	childSetText("mime_type", mime_type);
+}
+
+void LLPanelLandMedia::setMediaURL(const LLString& media_url)
+{
+	mMediaURLEdit->setText(media_url);
+	mMediaURLEdit->onCommit();
+
+}
+
+// static
+void LLPanelLandMedia::onCommitType(LLUICtrl *ctrl, void *userdata)
+{
+	LLPanelLandMedia *self = (LLPanelLandMedia *)userdata;
+	std::string current_type = LLMIMETypes::widgetType(self->childGetText("mime_type"));
+	std::string new_type = self->mMediaTypeCombo->getValue();
+	if(current_type != new_type)
+	{
+		self->childSetText("mime_type", LLMIMETypes::findDefaultMimeType(new_type));
+	}
+	onCommitAny(ctrl, userdata);
+	
+}
+// static
+void LLPanelLandMedia::onCommitAny(LLUICtrl *ctrl, void *userdata)
+{
+	LLPanelLandMedia *self = (LLPanelLandMedia *)userdata;
+
+	LLParcel* parcel = self->mParcel->getParcel();
+	if (!parcel)
+	{
+		return;
+	}
+
+	// Extract data from UI
+	BOOL sound_local		= self->mCheckSoundLocal->get();
+	int voice_setting		= self->mRadioVoiceChat->getSelectedIndex();
+	std::string music_url	= self->mMusicURLEdit->getText();
+	std::string media_url	= self->mMediaURLEdit->getText();
+	std::string media_desc	= self->mMediaDescEdit->getText();
+	std::string mime_type	= self->childGetText("mime_type");
+	U8 media_auto_scale		= self->mMediaAutoScaleCheck->get();
+	U8 media_loop           = self->mMediaLoopCheck->get();
+	U8 obscure_media		= self->mMediaUrlCheck->get();
+	U8 obscure_music		= self->mMusicUrlCheck->get();
+	S32 media_width			= (S32)self->mMediaWidthCtrl->get();
+	S32 media_height		= (S32)self->mMediaHeightCtrl->get();
+	LLUUID media_id			= self->mMediaTextureCtrl->getImageAssetID();
+
+	self->childSetText("mime_type", mime_type);
+
+	BOOL voice_enabled;
+	BOOL voice_estate_chan;
+	
+	switch(voice_setting)
+	{
+		default:
+		case kRadioVoiceChatEstate:
+			voice_enabled = TRUE;
+			voice_estate_chan = TRUE;
+		break;
+		case kRadioVoiceChatPrivate:
+			voice_enabled = TRUE;
+			voice_estate_chan = FALSE;
+		break;
+		case kRadioVoiceChatDisable:
+			voice_enabled = FALSE;
+			voice_estate_chan = FALSE;
+		break;
+	}
+	
+	// Remove leading/trailing whitespace (common when copying/pasting)
+	LLString::trim(music_url);
+	LLString::trim(media_url);
+
+	// Push data into current parcel
+	parcel->setParcelFlag(PF_ALLOW_VOICE_CHAT, voice_enabled);
+	parcel->setParcelFlag(PF_USE_ESTATE_VOICE_CHAN, voice_estate_chan);
+	parcel->setParcelFlag(PF_SOUND_LOCAL, sound_local);
+	parcel->setMusicURL(music_url.c_str());
+	parcel->setMediaURL(media_url.c_str());
+	parcel->setMediaType(mime_type.c_str());
+	parcel->setMediaDesc(media_desc.c_str());
+	parcel->setMediaWidth(media_width);
+	parcel->setMediaHeight(media_height);
+	parcel->setMediaID(media_id);
+	parcel->setMediaAutoScale ( media_auto_scale );
+	parcel->setMediaLoop ( media_loop );
+	parcel->setObscureMedia( obscure_media );
+	parcel->setObscureMusic( obscure_music );
+
+	// Send current parcel data upstream to server 
+	gParcelMgr->sendParcelPropertiesUpdate( parcel );
+
+	// Might have changed properties, so let's redraw!
+	self->refresh();
+}
+// static
+void LLPanelLandMedia::onSetBtn(void *userdata)
+{
+	LLPanelLandMedia *self = (LLPanelLandMedia *)userdata;
+	self->mURLEntryFloater = LLFloaterURLEntry::show( self->getHandle() );
+	LLFloater* parent_floater = gFloaterView->getParentFloater(self); 
+	if (parent_floater)
+	{
+		parent_floater->addDependentFloater(LLFloater::getFloaterByHandle(self->mURLEntryFloater));
+	}
+}
diff --git a/indra/newview/llpanellandmedia.h b/indra/newview/llpanellandmedia.h
new file mode 100644
index 00000000000..aa84b245e24
--- /dev/null
+++ b/indra/newview/llpanellandmedia.h
@@ -0,0 +1,58 @@
+/** 
+ * @file llpanellandmedia.h
+ * @author Callum Prentice, Sam Kolb, James Cook
+ * @brief Allows configuration of "media" for a land parcel,
+ *   for example movies, web pages, and audio.
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+#ifndef LLPANELLANDMEDIA_H
+#define LLPANELLANDMEDIA_H
+
+#include "lllineeditor.h"
+#include "llmemory.h"	// LLHandle<>
+#include "llpanel.h"
+#include "llparcelselection.h"
+#include "lluifwd.h"	// widget pointer types
+
+class LLPanelLandMedia
+:	public LLPanel
+{
+public:
+	LLPanelLandMedia(LLHandle<LLParcelSelection>& parcelp);
+	/*virtual*/ ~LLPanelLandMedia();
+	/*virtual*/ BOOL postBuild();
+	void refresh();
+	void setMediaType(const LLString& media_type);
+	void setMediaURL(const LLString& media_type);
+	const LLString& getMediaURL() { return mMediaURLEdit->getText(); }
+
+private:
+	void populateMIMECombo();
+	static void onCommitAny(LLUICtrl* ctrl, void *userdata);
+	static void onCommitType(LLUICtrl* ctrl, void *userdata);
+	static void onSetBtn(void* userdata);
+
+private:
+	LLCheckBoxCtrl* mCheckSoundLocal;
+	LLRadioGroup*	mRadioVoiceChat;
+	LLLineEditor*	mMusicURLEdit;
+	LLLineEditor*	mMediaURLEdit;
+	LLLineEditor*	mMediaDescEdit;
+	LLComboBox*		mMediaTypeCombo;
+	LLButton*		mSetURLButton;
+	LLSpinCtrl*		mMediaHeightCtrl;
+	LLSpinCtrl*		mMediaWidthCtrl;
+	LLTextBox*		mMediaSizeCtrlLabel;
+	LLTextureCtrl*	mMediaTextureCtrl;
+	LLCheckBoxCtrl*	mMediaAutoScaleCheck;
+	LLCheckBoxCtrl*	mMediaLoopCheck;
+	LLCheckBoxCtrl* mMediaUrlCheck;
+	LLCheckBoxCtrl* mMusicUrlCheck;
+	LLViewHandle	mURLEntryFloater;
+
+	LLHandle<LLParcelSelection>&	mParcel;
+};
+
+#endif
diff --git a/indra/newview/llpanellogin.cpp b/indra/newview/llpanellogin.cpp
index bc6f6fedd82..a80765c8052 100644
--- a/indra/newview/llpanellogin.cpp
+++ b/indra/newview/llpanellogin.cpp
@@ -71,7 +71,8 @@
 #include "llwebbrowserctrl.h"
 
 #include "llfloaterhtml.h"
-//#include "llfloaterhtmlhelp.h"
+
+#include "llfloaterhtmlhelp.h"
 #include "llfloatertos.h"
 
 #include "llglheaders.h"
@@ -95,12 +96,10 @@ class LLLoginRefreshHandler : public LLCommandHandler
 	LLLoginRefreshHandler() : LLCommandHandler("login_refresh", false) { }
 	bool handle(const LLSD& tokens, const LLSD& queryMap)
 	{	
-#if LL_LIBXUL_ENABLED
 		if (LLStartUp::getStartupState() < STATE_LOGIN_CLEANUP)
 		{
 			LLPanelLogin::loadLoginPage();
 		}	
-#endif
 		return true;
 	}
 };
@@ -438,7 +437,6 @@ LLPanelLogin::LLPanelLogin(const LLRect &rect,
 #endif    
 	
 	// get the web browser control
-	#if LL_LIBXUL_ENABLED
 	LLWebBrowserCtrl* web_browser = LLUICtrlFactory::getWebBrowserCtrlByName(this, "login_html");
 	if ( web_browser )
 	{
@@ -475,9 +473,6 @@ LLPanelLogin::LLPanelLogin(const LLRect &rect,
  		}
  		LLHTTPClient::head( login_page, gResponsePtr );
 	};
-	#else
-		mHtmlAvailable = FALSE;
-	#endif
 
 #if !USE_VIEWER_AUTH
 	// Initialize visibility (and don't force visibility - use prefs)
@@ -487,7 +482,6 @@ LLPanelLogin::LLPanelLogin(const LLRect &rect,
 
 void LLPanelLogin::setSiteIsAlive( bool alive )
 {
-#if LL_LIBXUL_ENABLED
 	LLWebBrowserCtrl* web_browser = LLUICtrlFactory::getWebBrowserCtrlByName(this, "login_html");
 	// if the contents of the site was retrieved
 	if ( alive )
@@ -523,10 +517,6 @@ void LLPanelLogin::setSiteIsAlive( bool alive )
 		}
 #endif
 	}
-
-#else
-	mHtmlAvailable = FALSE;
-#endif
 }
 
 void LLPanelLogin::mungePassword(LLUICtrl* caller, void* user_data)
@@ -620,7 +610,6 @@ BOOL LLPanelLogin::handleKeyHere(KEY key, MASK mask, BOOL called_from_parent)
 			return TRUE;
 		}
 		
-#if LL_LIBXUL_ENABLED
 		if ( KEY_F1 == key )
 		{
 			llinfos << "Spawning HTML help window" << llendl;
@@ -636,7 +625,6 @@ BOOL LLPanelLogin::handleKeyHere(KEY key, MASK mask, BOOL called_from_parent)
 			tos_dialog->startModal();
 			return TRUE;
 		}
-# endif
 #endif
 
 		if (!called_from_parent)
@@ -917,14 +905,12 @@ void LLPanelLogin::setAlwaysRefresh(bool refresh)
 {
 	if (LLStartUp::getStartupState() >= STATE_LOGIN_CLEANUP) return;
 
-#if LL_LIBXUL_ENABLED
 	LLWebBrowserCtrl* web_browser = LLUICtrlFactory::getWebBrowserCtrlByName(sInstance, "login_html");
 
 	if (web_browser)
 	{
 		web_browser->setAlwaysRefresh(refresh);
 	}
-#endif
 }
 
 
@@ -1050,15 +1036,12 @@ void LLPanelLogin::loadLoginPage()
 #endif
 #endif
 	
-#if LL_LIBXUL_ENABLED
 	LLWebBrowserCtrl* web_browser = LLUICtrlFactory::getWebBrowserCtrlByName(sInstance, "login_html");
 	
 	// navigate to the "real" page 
 	web_browser->navigateTo( oStr.str() );
-#endif
 }
 
-#if LL_LIBXUL_ENABLED
 void LLPanelLogin::onNavigateComplete( const EventType& eventIn )
 {
 	LLWebBrowserCtrl* web_browser = LLUICtrlFactory::getWebBrowserCtrlByName(sInstance, "login_html");
@@ -1074,7 +1057,6 @@ void LLPanelLogin::onNavigateComplete( const EventType& eventIn )
 		//web_browser->handleKey(KEY_TAB, MASK_NONE, false);
 	}
 }
-#endif
 
 //---------------------------------------------------------------------------
 // Protected methods
diff --git a/indra/newview/llpanellogin.h b/indra/newview/llpanellogin.h
index 3deb6fee515..76a16528cb1 100644
--- a/indra/newview/llpanellogin.h
+++ b/indra/newview/llpanellogin.h
@@ -64,11 +64,9 @@ class LLLoginHandler : public LLCommandHandler
 
 extern LLLoginHandler gLoginHandler;
 
-class LLPanelLogin
-:	public LLPanel
-#if LL_LIBXUL_ENABLED
-	, public LLWebBrowserCtrlObserver
-#endif
+class LLPanelLogin:	
+	public LLPanel,
+	public LLWebBrowserCtrlObserver
 {
 public:
 	LLPanelLogin(const LLRect &rect, BOOL show_server, 
@@ -111,11 +109,7 @@ class LLPanelLogin
 	static void newAccountAlertCallback(S32 option, void*);
 	static void onClickQuit(void*);
 	static void onClickVersion(void*);
-
-#if LL_LIBXUL_ENABLED
-	// browser observer impls
 	virtual void onNavigateComplete( const EventType& eventIn );
-#endif
 	static void onClickForgotPassword(void*);
 	static void onPassKey(LLLineEditor* caller, void* user_data);
 	
diff --git a/indra/newview/llparcelselection.cpp b/indra/newview/llparcelselection.cpp
new file mode 100644
index 00000000000..5478a96b979
--- /dev/null
+++ b/indra/newview/llparcelselection.cpp
@@ -0,0 +1,83 @@
+/** 
+ * @file llparcelselection.cpp
+ * @brief Information about the currently selected parcel
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+
+#include "llviewerprecompiledheaders.h"
+
+#include "llparcelselection.h"
+
+#include "llparcel.h"
+
+
+// static
+LLPointer<LLParcelSelection> LLParcelSelection::sNullSelection;
+
+template<> 
+	const LLHandle<LLParcelSelection>::NullFunc 
+		LLHandle<LLParcelSelection>::sNullFunc =
+			LLParcelSelection::getNullParcelSelection;
+
+//
+// LLParcelSelection
+//
+LLParcelSelection::LLParcelSelection() : 
+	mParcel(NULL),
+	mSelectedMultipleOwners(FALSE),
+	mWholeParcelSelected(FALSE),
+	mSelectedSelfCount(0),
+	mSelectedOtherCount(0),
+	mSelectedPublicCount(0)
+{
+}
+
+LLParcelSelection::LLParcelSelection(LLParcel* parcel)  : 
+	mParcel(parcel),
+	mSelectedMultipleOwners(FALSE),
+	mWholeParcelSelected(FALSE),
+	mSelectedSelfCount(0),
+	mSelectedOtherCount(0),
+	mSelectedPublicCount(0)
+{
+}
+
+LLParcelSelection::~LLParcelSelection()
+{
+}
+
+BOOL LLParcelSelection::getMultipleOwners() const
+{
+	return mSelectedMultipleOwners;
+}
+
+
+BOOL LLParcelSelection::getWholeParcelSelected() const
+{
+	return mWholeParcelSelected;
+}
+
+
+S32 LLParcelSelection::getClaimableArea() const
+{
+	const S32 UNIT_AREA = S32( PARCEL_GRID_STEP_METERS * PARCEL_GRID_STEP_METERS );
+	return mSelectedPublicCount * UNIT_AREA;
+}
+
+bool LLParcelSelection::hasOthersSelected() const
+{
+	return mSelectedOtherCount != 0;
+}
+
+// static
+LLParcelSelection* LLParcelSelection::getNullParcelSelection()
+{
+	if (sNullSelection.isNull())
+	{
+		sNullSelection = new LLParcelSelection;
+	}
+	
+	return sNullSelection;
+}
diff --git a/indra/newview/llparcelselection.h b/indra/newview/llparcelselection.h
new file mode 100644
index 00000000000..579a0f2549f
--- /dev/null
+++ b/indra/newview/llparcelselection.h
@@ -0,0 +1,63 @@
+/** 
+ * @file llparcelselection.h
+ * @brief Information about the currently selected parcel
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+
+#ifndef LLPARCELSELECTION_H
+#define LLPARCELSELECTION_H
+
+#include "llmemory.h"
+
+class LLParcel;
+
+class LLParcelSelection : public LLRefCount
+{
+	friend class LLViewerParcelMgr;
+
+protected:
+	~LLParcelSelection();
+
+public:
+	LLParcelSelection(LLParcel* parcel);
+	LLParcelSelection();
+
+	// this can return NULL at any time, as parcel selection
+	// might have been invalidated.
+	LLParcel* getParcel() { return mParcel; }
+
+	// Return the number of grid units that are owned by you within
+	// the selection (computed by server).
+	S32 getSelfCount() const { return mSelectedSelfCount; }
+
+	// Returns area that will actually be claimed in meters squared.
+	S32		getClaimableArea() const;
+	bool	hasOthersSelected() const;
+
+	// Does the selection have multiple land owners in it?
+	BOOL	getMultipleOwners() const;
+
+	// Is the entire parcel selected, or just a part?
+	BOOL	getWholeParcelSelected() const;
+
+	static LLParcelSelection* getNullParcelSelection();
+
+private:
+	void setParcel(LLParcel* parcel) { mParcel = parcel; }
+
+private:
+	LLParcel*	mParcel;
+	BOOL		mSelectedMultipleOwners;
+	BOOL		mWholeParcelSelected;
+	S32			mSelectedSelfCount;
+	S32			mSelectedOtherCount;
+	S32			mSelectedPublicCount;
+
+	static LLPointer<LLParcelSelection> sNullSelection;
+};
+
+typedef LLHandle<LLParcelSelection> LLParcelSelectionHandle;
+
+#endif
diff --git a/indra/newview/llpreviewscript.cpp b/indra/newview/llpreviewscript.cpp
index c6d721faebd..d3afd65cbef 100644
--- a/indra/newview/llpreviewscript.cpp
+++ b/indra/newview/llpreviewscript.cpp
@@ -471,14 +471,12 @@ void LLScriptEdCore::updateDynamicHelp(BOOL immediate)
 	LLFloater* help_floater = LLFloater::getFloaterByHandle(mLiveHelpHandle);
 	if (!help_floater) return;
 
-#if LL_LIBXUL_ENABLED
 	// update back and forward buttons
 	LLButton* fwd_button = LLUICtrlFactory::getButtonByName(help_floater, "fwd_btn");
 	LLButton* back_button = LLUICtrlFactory::getButtonByName(help_floater, "back_btn");
 	LLWebBrowserCtrl* browser = LLUICtrlFactory::getWebBrowserCtrlByName(help_floater, "lsl_guide_html");
 	back_button->setEnabled(browser->canNavigateBack());
 	fwd_button->setEnabled(browser->canNavigateForward());
-#endif // LL_LIBXUL_ENABLED
 
 	if (!immediate && !gSavedSettings.getBOOL("ScriptHelpFollowsCursor"))
 	{
@@ -546,9 +544,9 @@ void LLScriptEdCore::setHelpPage(const LLString& help_string)
 	url_string.setArg("[LSL_STRING]", help_string);
 
 	addHelpItemToHistory(help_string);
-#if LL_LIBXUL_ENABLED
+
 	web_browser->navigateTo(url_string);
-#endif // LL_LIBXUL_ENABLED
+
 }
 
 void LLScriptEdCore::addHelpItemToHistory(const LLString& help_string)
@@ -680,10 +678,8 @@ void LLScriptEdCore::onBtnDynamicHelp(void* userdata)
 	live_help_floater->childSetAction("back_btn", onClickBack, userdata);
 	live_help_floater->childSetAction("fwd_btn", onClickForward, userdata);
 
-#if LL_LIBXUL_ENABLED
 	LLWebBrowserCtrl* browser = LLUICtrlFactory::getWebBrowserCtrlByName(live_help_floater, "lsl_guide_html");
 	browser->setAlwaysRefresh(TRUE);
-#endif // LL_LIBXUL_ENABLED
 
 	LLComboBox* help_combo = LLUICtrlFactory::getComboBoxByName(live_help_floater, "history_combo");
 	LLKeywordToken *token;
@@ -707,7 +703,6 @@ void LLScriptEdCore::onBtnDynamicHelp(void* userdata)
 //static 
 void LLScriptEdCore::onClickBack(void* userdata)
 {
-#if LL_LIBXUL_ENABLED
 	LLScriptEdCore* corep = (LLScriptEdCore*)userdata;
 	LLFloater* live_help_floater = LLFloater::getFloaterByHandle(corep->mLiveHelpHandle);
 	if (live_help_floater)
@@ -718,13 +713,11 @@ void LLScriptEdCore::onClickBack(void* userdata)
 			browserp->navigateBack();
 		}
 	}
-#endif // LL_LIBXUL_ENABLED
 }
 
 //static 
 void LLScriptEdCore::onClickForward(void* userdata)
 {
-#if LL_LIBXUL_ENABLED
 	LLScriptEdCore* corep = (LLScriptEdCore*)userdata;
 	LLFloater* live_help_floater = LLFloater::getFloaterByHandle(corep->mLiveHelpHandle);
 	if (live_help_floater)
@@ -735,7 +728,6 @@ void LLScriptEdCore::onClickForward(void* userdata)
 			browserp->navigateForward();
 		}
 	}
-#endif // LL_LIBXUL_ENABLED
 }
 
 // static
@@ -772,13 +764,11 @@ void LLScriptEdCore::onHelpComboCommit(LLUICtrl* ctrl, void* userdata)
 
 		corep->addHelpItemToHistory(help_string);
 
-#if LL_LIBXUL_ENABLED
 		LLWebBrowserCtrl* web_browser = gUICtrlFactory->getWebBrowserCtrlByName(live_help_floater, "lsl_guide_html");
 		LLUIString url_string = gSavedSettings.getString("LSLHelpURL");
 		url_string.setArg("[APP_DIRECTORY]", gDirUtilp->getWorkingDir());
 		url_string.setArg("[LSL_STRING]", help_string);
 		web_browser->navigateTo(url_string);
-#endif // LL_LIBXUL_ENABLED
 	}
 }
 
diff --git a/indra/newview/llstartup.cpp b/indra/newview/llstartup.cpp
index 8df34d39c66..423954800f0 100644
--- a/indra/newview/llstartup.cpp
+++ b/indra/newview/llstartup.cpp
@@ -134,6 +134,7 @@
 #include "llui.h"
 #include "llurldispatcher.h"
 #include "llurlsimstring.h"
+#include "llurlhistory.h"
 #include "llurlwhitelist.h"
 #include "lluserauth.h"
 #include "llvieweraudio.h"
@@ -143,10 +144,12 @@
 #include "llviewergenericmessage.h"
 #include "llviewergesture.h"
 #include "llviewerimagelist.h"
+#include "llviewermedia.h"
 #include "llviewermenu.h"
 #include "llviewermessage.h"
 #include "llviewernetwork.h"
 #include "llviewerobjectlist.h"
+#include "llviewerparcelmedia.h"
 #include "llviewerparcelmgr.h"
 #include "llviewerregion.h"
 #include "llviewerstats.h"
@@ -160,7 +163,6 @@
 #include "llxfermanager.h"
 #include "pipeline.h"
 #include "llappviewer.h"
-#include "llmediaengine.h"
 #include "llfasttimerview.h"
 #include "llfloatermap.h"
 #include "llweb.h"
@@ -169,27 +171,11 @@
 #include "llnamebox.h"
 #include "llnameeditor.h"
 
-#if LL_LIBXUL_ENABLED
-#include "llmozlib.h"
-#endif // LL_LIBXUL_ENABLED
-
 #if LL_WINDOWS
 #include "llwindebug.h"
 #include "lldxhardware.h"
 #endif
 
-#if LL_QUICKTIME_ENABLED
-#if LL_DARWIN
-#include <QuickTime/QuickTime.h>
-#else
-// quicktime specific includes
-#include "MacTypes.h"
-#include "QTML.h"
-#include "Movies.h"
-#include "FixMath.h"
-#endif
-#endif
-
 //
 // exported globals
 //
@@ -213,8 +199,6 @@ LLPointer<LLImageGL> gStartImageGL;
 static LLHost gAgentSimHost;
 static BOOL gSkipOptionalUpdate = FALSE;
 
-bool gUseQuickTime = true;
-bool gQuickTimeInitialized = false;
 static bool gGotUseCircuitCodeAck = false;
 LLString gInitialOutfit;
 LLString gInitialOutfitGender;	// "male" or "female"
@@ -545,59 +529,7 @@ BOOL idle_startup()
 		// initialize the economy
 		gGlobalEconomy = new LLGlobalEconomy();
 
-		//---------------------------------------------------------------------
-		// LibXUL (Mozilla) initialization
-		//---------------------------------------------------------------------
-		#if LL_LIBXUL_ENABLED
-		set_startup_status(0.58f, "Initializing embedded web browser...", gAgent.mMOTD.c_str());
-		display_startup();
-		llinfos << "Initializing embedded web browser..." << llendl;
-
-		#if LL_DARWIN
-			// For Mac OS, we store both the shared libraries and the runtime files (chrome/, plugins/, etc) in
-			// Second Life.app/Contents/MacOS/.  This matches the way Firefox is distributed on the Mac.
-			std::string componentDir(gDirUtilp->getExecutableDir());
-		#elif LL_WINDOWS
-			std::string componentDir( gDirUtilp->getExpandedFilename( LL_PATH_APP_SETTINGS, "" ) );
-			componentDir += gDirUtilp->getDirDelimiter();
-			#ifdef LL_DEBUG
-				componentDir += "mozilla_debug";
-			#else
-				componentDir += "mozilla";
-			#endif
-		#elif LL_LINUX
-			std::string componentDir( gDirUtilp->getExpandedFilename( LL_PATH_APP_SETTINGS, "" ) );
-			componentDir += gDirUtilp->getDirDelimiter();
-			componentDir += "mozilla-runtime-linux-i686";
-		#else
-			std::string componentDir( gDirUtilp->getExpandedFilename( LL_PATH_APP_SETTINGS, "" ) );
-			componentDir += gDirUtilp->getDirDelimiter();
-			componentDir += "mozilla";
-		#endif
 
-#if LL_LINUX
-		// Yuck, Mozilla init plays with the locale - push/pop
-		// the locale to protect it, as exotic/non-C locales
-		// causes our code lots of general critical weirdness
-		// and crashness. (SL-35450)
-		std::string saved_locale = setlocale(LC_ALL, NULL);
-#endif // LL_LINUX
-
-		// initialize Mozilla - pass in executable dir, location of extra dirs (chrome/, greprefs/, plugins/ etc.) and path to profile dir)
-		LLMozLib::getInstance()->init( gDirUtilp->getExecutableDir(), componentDir, gDirUtilp->getExpandedFilename( LL_PATH_MOZILLA_PROFILE, "" ) );
-
-#if LL_LINUX
-		setlocale(LC_ALL, saved_locale.c_str() );
-#endif // LL_LINUX
-
-		std::ostringstream codec;
-		codec << "[Second Life ";
-		codec << "(" << gChannelName << ")";
-		codec << " - " << LL_VERSION_MAJOR << "." << LL_VERSION_MINOR << "." << LL_VERSION_PATCH << "." << LL_VERSION_BUILD;
-		codec << "]";
-		LLMozLib::getInstance()->setBrowserAgentId( codec.str() );
-		LLMozLib::getInstance()->enableProxy( gSavedSettings.getBOOL("BrowserProxyEnabled"), gSavedSettings.getString("BrowserProxyAddress"), gSavedSettings.getS32("BrowserProxyPort") ); 
-		#endif
 
 		//-------------------------------------------------
 		// Init audio, which may be needed for prefs dialog
@@ -694,7 +626,29 @@ BOOL idle_startup()
 			show_connect_box = TRUE;
 		}
 
+
 		// Go to the next startup state
+		LLStartUp::setStartupState( STATE_MEDIA_INIT );
+		return do_normal_idle;
+	}
+
+	
+	//---------------------------------------------------------------------
+	// LLMediaEngine Init
+	//---------------------------------------------------------------------
+	if (STATE_MEDIA_INIT == LLStartUp::getStartupState())
+	{
+		llinfos << "Initializing Multimedia...." << llendl;
+		set_startup_status(0.03f, "Initializing Multimedia...", gAgent.mMOTD.c_str());
+		display_startup();
+		LLViewerMedia::initClass();
+		LLViewerParcelMedia::initClass();
+
+		if (gViewerWindow)
+		{
+			audio_update_volume(true);
+		}
+
 		LLStartUp::setStartupState( STATE_LOGIN_SHOW );
 		return do_normal_idle;
 	}
@@ -892,6 +846,9 @@ BOOL idle_startup()
 				&LLURLDispatcher::dispatchFromTextEditor,
 				&LLURLDispatcher::dispatchFromTextEditor   );
 
+		// Load URL History File
+		LLURLHistory::loadFile("url_history.xml");
+
 		//-------------------------------------------------
 		// Handle startup progress screen
 		//-------------------------------------------------
@@ -934,7 +891,7 @@ BOOL idle_startup()
 
 		// Poke the VFS, which could potentially block for a while if
 		// Windows XP is acting up
-		set_startup_status(0.05f, "Verifying cache files (can take 60-90 seconds)...", NULL);
+		set_startup_status(0.07f, "Verifying cache files (can take 60-90 seconds)...", NULL);
 		display_startup();
 
 		gVFS->pokeFiles();
@@ -1774,7 +1731,7 @@ BOOL idle_startup()
 			display_startup();
 			gImageList.decodeAllImages(1.f);
 		}
-		LLStartUp::setStartupState( STATE_QUICKTIME_INIT );
+		LLStartUp::setStartupState( STATE_WORLD_WAIT );
 
 		// JC - Do this as late as possible to increase likelihood Purify
 		// will run.
@@ -1808,79 +1765,8 @@ BOOL idle_startup()
 	}
 
 	//---------------------------------------------------------------------
-	// LLMediaEngine Init
-	//---------------------------------------------------------------------
-	if (STATE_QUICKTIME_INIT == LLStartUp::getStartupState())
-	{
-		if (gViewerWindow)
-		{
-			audio_update_volume(true);
-		}
-
-		#if LL_QUICKTIME_ENABLED	// windows only right now but will be ported to mac 
-		if (gUseQuickTime)
-		{
-			if(!gQuickTimeInitialized)
-			{
-				// initialize quicktime libraries (fails gracefully if quicktime not installed ($QUICKTIME)
-				llinfos << "Initializing QuickTime...." << llendl;
-				set_startup_status(0.57f, "Initializing QuickTime...", gAgent.mMOTD.c_str());
-				display_startup();
-				#if LL_WINDOWS
-					// Only necessary/available on Windows.
-					if ( InitializeQTML ( 0L ) != noErr )
-					{
-						// quicktime init failed - turn off media engine support
-						LLMediaEngine::getInstance ()->setAvailable ( FALSE );
-						llinfos << "...not found - unable to initialize." << llendl;
-						set_startup_status(0.57f, "QuickTime not found - unable to initialize.", gAgent.mMOTD.c_str());
-					}
-					else
-					{
-						llinfos << "QUICKTIME> QuickTime version (hex) is " << std::hex << LLMediaEngine::getInstance()->getQuickTimeVersion() << llendl;
-						llinfos << "QUICKTIME> QuickTime version is " << std::dec << LLMediaEngine::getInstance()->getQuickTimeVersion() << llendl;
-						if ( LLMediaEngine::getInstance()->getQuickTimeVersion() < LL_MIN_QUICKTIME_VERSION )
-						{
-							// turn off QuickTime if version is less than required
-							LLMediaEngine::getInstance ()->setAvailable ( FALSE );
-
-							// display a message here explaining why we disabled QuickTime
-							gViewerWindow->alertXml("QuickTimeOutOfDate");
-						}
-						else
-						{
-							llinfos << ".. initialized successfully." << llendl;
-							set_startup_status(0.57f, "QuickTime initialized successfully.", gAgent.mMOTD.c_str());
-						};
-					};
-				#elif LL_DARWIN
-					llinfos << "QUICKTIME> QuickTime version (hex) is " << std::hex << LLMediaEngine::getInstance()->getQuickTimeVersion() << llendl;
-					llinfos << "QUICKTIME> QuickTime version is " << std::dec << LLMediaEngine::getInstance()->getQuickTimeVersion() << llendl;
-					if ( LLMediaEngine::getInstance()->getQuickTimeVersion() < LL_MIN_QUICKTIME_VERSION )
-					{
-						// turn off QuickTime if version is less than required
-						LLMediaEngine::getInstance ()->setAvailable ( FALSE );
-
-						// display a message here explaining why we disabled QuickTime
-						gViewerWindow->alertXml("QuickTimeOutOfDate");
-					}
-				#endif
-
-				EnterMovies ();
-				gQuickTimeInitialized = true;
-			}
-		}
-		else
-		{
-			LLMediaEngine::getInstance()->setAvailable( FALSE );
-		}
-		#endif
 
-		LLStartUp::setStartupState( STATE_WORLD_WAIT );
-		return do_normal_idle;
-	}
 
-	//---------------------------------------------------------------------
 	// Agent Send
 	//---------------------------------------------------------------------
 	if(STATE_WORLD_WAIT == LLStartUp::getStartupState())
@@ -3126,18 +3012,6 @@ void register_viewer_callbacks(LLMessageSystem* msg)
 
 	msg->setHandlerFunc("ParcelObjectOwnersReply", LLPanelLandObjects::processParcelObjectOwnersReply);
 
-	// Reponse to the "Refresh" button on land objects floater.
-	if (gSavedSettings.getBOOL("AudioStreamingVideo"))
-	{
-		msg->setHandlerFunc("ParcelMediaCommandMessage", LLMediaEngine::process_parcel_media);
-		msg->setHandlerFunc ( "ParcelMediaUpdate", LLMediaEngine::process_parcel_media_update );
-	}
-	else
-	{
-		msg->setHandlerFunc("ParcelMediaCommandMessage", null_message_callback);
-		gMessageSystem->setHandlerFunc ( "ParcelMediaUpdate", null_message_callback );
-	}
-
 	msg->setHandlerFunc("InitiateDownload", process_initiate_download);
 	msg->setHandlerFunc("LandStatReply", LLFloaterTopObjects::handle_land_reply);
 	msg->setHandlerFunc("GenericMessage", process_generic_message);
diff --git a/indra/newview/llstartup.h b/indra/newview/llstartup.h
index 08f2f6002ce..351d4b1a214 100644
--- a/indra/newview/llstartup.h
+++ b/indra/newview/llstartup.h
@@ -46,6 +46,7 @@ extern const char* SCREEN_LAST_FILENAME;
 
 enum EStartupState{
 	STATE_FIRST,					// Initial startup
+	STATE_MEDIA_INIT,               // Initialzie media library
 	STATE_LOGIN_SHOW,				// Show login screen
 	STATE_LOGIN_WAIT,				// Wait for user input at login screen
 	STATE_LOGIN_CLEANUP,			// Get rid of login screen and start login
@@ -58,7 +59,6 @@ enum EStartupState{
 	STATE_WORLD_INIT,				// Start building the world
 	STATE_SEED_GRANTED_WAIT,		// Wait for seed cap grant
 	STATE_SEED_CAP_GRANTED,			// Have seed cap grant 
-	STATE_QUICKTIME_INIT,			// Initialzie QT
 	STATE_WORLD_WAIT,				// Waiting for simulator
 	STATE_AGENT_SEND,				// Connect to a region
 	STATE_AGENT_WAIT,				// Wait for region
@@ -72,8 +72,6 @@ enum EStartupState{
 
 // exported symbols
 extern BOOL gAgentMovementCompleted;
-extern bool gUseQuickTime;
-extern bool gQuickTimeInitialized;
 extern LLPointer<LLImageGL> gStartImageGL;
 
 class LLStartUp
diff --git a/indra/newview/llstatusbar.cpp b/indra/newview/llstatusbar.cpp
index 8c4fc833dbe..58039bf8781 100644
--- a/indra/newview/llstatusbar.cpp
+++ b/indra/newview/llstatusbar.cpp
@@ -49,6 +49,7 @@
 #include "llfloaterbuycurrency.h"
 #include "llfloaterchat.h"
 #include "llfloaterdirectory.h"		// to spawn search
+#include "llfloaterlagmeter.h"
 #include "llfloaterland.h"
 #include "llfloaterregioninfo.h"
 #include "llfloaterscriptdebug.h"
@@ -163,8 +164,49 @@ LLStatusBar::LLStatusBar(const std::string& name, const LLRect& rect)
 	childSetCommitCallback("search_editor", onCommitSearch, this);
 	childSetAction("search_btn", onClickSearch, this);
 
+	childSetVisible("search_editor", gSavedSettings.getBOOL("ShowSearchBar"));
+	childSetVisible("search_btn", gSavedSettings.getBOOL("ShowSearchBar"));
+
 	childSetActionTextbox("ParcelNameText", onClickParcelInfo );
 	childSetActionTextbox("BalanceText", onClickBalance );
+
+	// Adding Net Stat Graph
+	S32 x = mRect.getWidth() - 2;
+	S32 y = 0;
+	LLRect r;
+	r.set( x-SIM_STAT_WIDTH, y+MENU_BAR_HEIGHT-1, x, y+1);
+	mSGBandwidth = new LLStatGraph("BandwidthGraph", r);
+	mSGBandwidth->setFollows(FOLLOWS_BOTTOM | FOLLOWS_RIGHT);
+	mSGBandwidth->setStat(&gViewerStats->mKBitStat);
+	LLString text = childGetText("bandwidth_tooltip") + " ";
+	LLUIString bandwidth_tooltip = text;	// get the text from XML until this widget is XML driven
+	mSGBandwidth->setLabel(bandwidth_tooltip.getString().c_str());
+	mSGBandwidth->setUnits("Kbps");
+	mSGBandwidth->setPrecision(0);
+	mSGBandwidth->setMouseOpaque(FALSE);
+	addChild(mSGBandwidth);
+	x -= SIM_STAT_WIDTH + 2;
+
+	r.set( x-SIM_STAT_WIDTH, y+MENU_BAR_HEIGHT-1, x, y+1);
+	mSGPacketLoss = new LLStatGraph("PacketLossPercent", r);
+	mSGPacketLoss->setFollows(FOLLOWS_BOTTOM | FOLLOWS_RIGHT);
+	mSGPacketLoss->setStat(&gViewerStats->mPacketsLostPercentStat);
+	text = childGetText("packet_loss_tooltip") + " ";
+	LLUIString packet_loss_tooltip = text;	// get the text from XML until this widget is XML driven
+	mSGPacketLoss->setLabel(packet_loss_tooltip.getString().c_str());
+	mSGPacketLoss->setUnits("%");
+	mSGPacketLoss->setMin(0.f);
+	mSGPacketLoss->setMax(5.f);
+	mSGPacketLoss->setThreshold(0, 0.5f);
+	mSGPacketLoss->setThreshold(1, 1.f);
+	mSGPacketLoss->setThreshold(2, 3.f);
+	mSGPacketLoss->setPrecision(1);
+	mSGPacketLoss->setMouseOpaque(FALSE);
+	mSGPacketLoss->mPerSec = FALSE;
+	addChild(mSGPacketLoss);
+
+	childSetActionTextbox("stat_btn", onClickStatGraph);
+
 }
 
 LLStatusBar::~LLStatusBar()
@@ -212,6 +254,14 @@ void LLStatusBar::draw()
 // Per-frame updates of visibility
 void LLStatusBar::refresh()
 {
+	// Adding Net Stat Meter back in
+	F32 bwtotal = gViewerThrottle.getMaxBandwidth() / 1000.f;
+	mSGBandwidth->setMin(0.f);
+	mSGBandwidth->setMax(bwtotal*1.25f);
+	mSGBandwidth->setThreshold(0, bwtotal*0.75f);
+	mSGBandwidth->setThreshold(1, bwtotal);
+	mSGBandwidth->setThreshold(2, bwtotal);
+
 	// *TODO: Localize / translate time
 	
 	// Get current UTC time, adjusted for the user's clock
@@ -262,6 +312,8 @@ void LLStatusBar::refresh()
 	S32 x = MENU_RIGHT + MENU_PARCEL_SPACING;
 	S32 y = 0;
 	
+	bool search_visible = gSavedSettings.getBOOL("ShowSearchBar");
+
 	// reshape menu bar to its content's width
 	if (MENU_RIGHT != gMenuBarView->getRect().getWidth())
 	{
@@ -534,14 +586,69 @@ void LLStatusBar::refresh()
 		snprintf(mRegionDetails.mOwner, MAX_STRING, "Unknown");
 		mRegionDetails.mTraffic = 0.0f;
 	}
+
 	mTextParcelName->setText(location_name);
 
+
+
+	// x = right edge
+	// loop through: stat graphs, search btn, search text editor, money, buy money, clock
+	// adjust rect
+	// finally adjust parcel name rect
+
+	S32 new_right = getRect().getWidth();
+	if (search_visible)
+	{
+		childGetRect("search_btn", r);
+		r.translate( new_right - r.mRight, 0);
+		childSetRect("search_btn", r);
+		new_right -= r.getWidth();
+
+		childGetRect("search_editor", r);
+		r.translate( new_right - r.mRight, 0);
+		childSetRect("search_editor", r);
+		new_right -= r.getWidth() + 6;
+
+	}
+	else
+	{
+		childGetRect("stat_btn", r);
+		r.translate( new_right - r.mRight, 0);
+		childSetRect("stat_btn", r);
+		new_right -= r.getWidth() + 6;
+	}
+
+	// Set rects of money, buy money, time
+	childGetRect("BalanceText", r);
+	r.translate( new_right - r.mRight, 0);
+	childSetRect("BalanceText", r);
+	new_right -= r.getWidth() - 18;
+
+	childGetRect("buycurrency", r);
+	r.translate( new_right - r.mRight, 0);
+	childSetRect("buycurrency", r);
+	new_right -= r.getWidth() + 6;
+
+	childGetRect("TimeText", r);
+	// mTextTime->getTextPixelWidth();
+	r.translate( new_right - r.mRight, 0);
+	childSetRect("TimeText", r);
+	// new_right -= r.getWidth() + MENU_PARCEL_SPACING;
+
+
 	// Adjust region name and parcel name
 	x += 8;
 
 	const S32 PARCEL_RIGHT =  llmin(mTextTime->getRect().mLeft, mTextParcelName->getTextPixelWidth() + x + 5);
 	r.set(x+4, mRect.getHeight() - 2, PARCEL_RIGHT, 0);
 	mTextParcelName->setRect(r);
+
+	// Set search bar visibility
+	childSetVisible("search_editor", search_visible);
+	childSetVisible("search_btn", search_visible);
+	mSGBandwidth->setVisible(! search_visible);
+	mSGPacketLoss->setVisible(! search_visible);
+	childSetEnabled("stat_btn", ! search_visible);
 }
 
 void LLStatusBar::setVisibleForMouselook(bool visible)
@@ -551,6 +658,8 @@ void LLStatusBar::setVisibleForMouselook(bool visible)
 	childSetVisible("buycurrency", visible);
 	childSetVisible("search_editor", visible);
 	childSetVisible("search_btn", visible);
+	mSGBandwidth->setVisible(visible);
+	mSGPacketLoss->setVisible(visible);
 	setBackgroundVisible(visible);
 }
 
@@ -662,7 +771,7 @@ static void onClickParcelInfo(void* data)
 {
 	gParcelMgr->selectParcelAt(gAgent.getPositionGlobal());
 
-	LLFloaterLand::show();
+	LLFloaterLand::showInstance();
 }
 
 static void onClickBalance(void* data)
@@ -806,6 +915,12 @@ void LLStatusBar::onClickSearch(void* data)
 	LLFloaterDirectory::showFindAll(search_text);
 }
 
+// static
+void LLStatusBar::onClickStatGraph(void* data)
+{
+	LLFloaterLagMeter::show(data);
+}
+
 BOOL can_afford_transaction(S32 cost)
 {
 	return((cost <= 0)||((gStatusBar) && (gStatusBar->getBalance() >=cost)));
diff --git a/indra/newview/llstatusbar.h b/indra/newview/llstatusbar.h
index d0f3e66fa91..78f744c4b5a 100644
--- a/indra/newview/llstatusbar.h
+++ b/indra/newview/llstatusbar.h
@@ -120,6 +120,7 @@ class LLStatusBar
 
 	static void onCommitSearch(LLUICtrl*, void* data);
 	static void onClickSearch(void* data);
+	static void onClickStatGraph(void* data);
 
 private:
 	LLTextBox	*mTextBalance;
@@ -128,6 +129,9 @@ class LLStatusBar
 
 	LLTextBox*	mTextParcelName;
 
+	LLStatGraph *mSGBandwidth;
+	LLStatGraph *mSGPacketLoss;
+
 	LLButton	*mBtnBuyCurrency;
 
 	S32				mBalance;
diff --git a/indra/newview/lltoolpie.cpp b/indra/newview/lltoolpie.cpp
index fa8213d6621..0c88442fd28 100644
--- a/indra/newview/lltoolpie.cpp
+++ b/indra/newview/lltoolpie.cpp
@@ -35,6 +35,7 @@
 
 #include "indra_constants.h"
 #include "llclickaction.h"
+#include "llmediabase.h"	// for status codes
 #include "llparcel.h"
 
 #include "llagent.h"
@@ -54,14 +55,17 @@
 #include "lltoolmgr.h"
 #include "lltoolselect.h"
 #include "llviewercamera.h"
+#include "llviewerparcelmedia.h"
 #include "llviewermenu.h"
-#include "llviewerobject.h"
 #include "llviewerobjectlist.h"
+#include "llviewerobject.h"
 #include "llviewerparcelmgr.h"
 #include "llviewerwindow.h"
+#include "llviewermedia.h"
 #include "llvoavatar.h"
 #include "llworld.h"
 #include "llui.h"
+#include "llweb.h"
 
 LLToolPie *gToolPie = NULL;
 
@@ -73,6 +77,11 @@ extern void handle_buy(void*);
 
 extern BOOL gDebugClicks;
 
+static void handle_click_action_play();
+static void handle_click_action_open_media(LLPointer<LLViewerObject> objectp);
+static ECursorType cursor_from_parcel_media(U8 click_action);
+
+
 LLToolPie::LLToolPie()
 :	LLTool("Select"),
 	mPieMouseButtonDown( FALSE ),
@@ -87,6 +96,7 @@ BOOL LLToolPie::handleMouseDown(S32 x, S32 y, MASK mask)
 {
 	if (!gCamera) return FALSE;
 
+	gPickFaces = TRUE;
 	//left mouse down always picks transparent
 	gViewerWindow->hitObjectOrLandGlobalAsync(x, y, mask, leftMouseCallback, 
 											  TRUE, TRUE);
@@ -137,7 +147,7 @@ BOOL LLToolPie::pickAndShowMenu(S32 x, S32 y, MASK mask, BOOL always_show)
 			else
 			{
 				// not selling passes, get info
-				LLFloaterLand::show();
+				LLFloaterLand::showInstance();
 			}
 		}
 
@@ -211,6 +221,13 @@ BOOL LLToolPie::pickAndShowMenu(S32 x, S32 y, MASK mask, BOOL always_show)
 				sLeftClickSelection = LLToolSelect::handleObjectSelection(parent, MASK_NONE, FALSE, TRUE);
 			}
 			return TRUE;
+		case CLICK_ACTION_PLAY:
+			handle_click_action_play();
+			return TRUE;
+		case CLICK_ACTION_OPEN_MEDIA:
+			// sClickActionObject = object;
+			handle_click_action_open_media(object);
+			return TRUE;
 		}
 	}
 
@@ -411,6 +428,47 @@ U8 final_click_action(LLViewerObject* obj)
 	return click_action;
 }
 
+ECursorType cursor_from_object(LLViewerObject* object)
+{
+	LLViewerObject* parent = NULL;
+	if (object)
+	{
+		parent = object->getRootEdit();
+	}
+	U8 click_action = final_click_action(object);
+	ECursorType cursor = UI_CURSOR_ARROW;
+	switch(click_action)
+	{
+	case CLICK_ACTION_SIT:
+		cursor = UI_CURSOR_TOOLSIT;
+		break;
+	case CLICK_ACTION_BUY:
+		cursor = UI_CURSOR_TOOLBUY;
+		break;
+	case CLICK_ACTION_OPEN:
+		// Open always opens the parent.
+		if (parent && parent->allowOpen())
+		{
+			cursor = UI_CURSOR_TOOLOPEN;
+		}
+		break;
+	case CLICK_ACTION_PAY:	
+		if ((object && object->flagTakesMoney())
+			|| (parent && parent->flagTakesMoney()))
+		{
+			cursor = UI_CURSOR_TOOLPAY;
+		}
+		break;
+	case CLICK_ACTION_PLAY:
+	case CLICK_ACTION_OPEN_MEDIA: 
+		cursor = cursor_from_parcel_media(click_action);
+		break;
+	default:
+		break;
+	}
+	return cursor;
+}
+
 // When we get object properties after left-clicking on an object
 // with left-click = buy, if it's the same object, do the buy.
 // static
@@ -486,28 +544,7 @@ BOOL LLToolPie::handleHover(S32 x, S32 y, MASK mask)
 
 	if (object && useClickAction(FALSE, mask, object, parent))
 	{
-		U8 click_action = final_click_action(object);
-		ECursorType cursor = UI_CURSOR_ARROW;
-		switch(click_action)
-		{
-		default: break;
-		case CLICK_ACTION_SIT:	cursor = UI_CURSOR_TOOLSIT; break;
-		case CLICK_ACTION_BUY:	cursor = UI_CURSOR_TOOLBUY; break;
-		case CLICK_ACTION_OPEN:
-			// Open always opens the parent.
-			if (parent && parent->allowOpen())
-			{
-				cursor = UI_CURSOR_TOOLOPEN;
-			}
-			break;
-		case CLICK_ACTION_PAY:	
-			if ((object && object->flagTakesMoney())
-				|| (parent && parent->flagTakesMoney()))
-			{
-				cursor = UI_CURSOR_TOOLPAY;
-			}
-			break;
-		}
+		ECursorType cursor = cursor_from_object(object);
 		gViewerWindow->getWindow()->setCursor(cursor);
 		lldebugst(LLERR_USER_INPUT) << "hover handled by LLToolPie (inactive)" << llendl;
 	}
@@ -677,4 +714,95 @@ void LLToolPie::render()
 	return;
 }
 
+static void handle_click_action_play()
+{
+	LLParcel* parcel = gParcelMgr->getAgentParcel();
+	if (!parcel) return;
+
+	LLMediaBase::EStatus status = LLViewerParcelMedia::getStatus();
+	switch(status)
+	{
+		case LLMediaBase::STATUS_STARTED:
+			LLViewerParcelMedia::pause();
+			break;
+
+		case LLMediaBase::STATUS_PAUSED:
+			LLViewerParcelMedia::start();
+			break;
+
+		default:
+			LLViewerParcelMedia::play(parcel);
+			break;
+	}
+}
+
+static void handle_click_action_open_media(LLPointer<LLViewerObject> objectp)
+{
+	//FIXME: how do we handle object in different parcel than us?
+	LLParcel* parcel = gParcelMgr->getAgentParcel();
+	if (!parcel) return;
+
+	// did we hit an object?
+	if (objectp.isNull()) return;
+
+	// did we hit a valid face on the object?
+	if( gLastHitObjectFace < 0 || gLastHitObjectFace >= objectp->getNumTEs() ) return;
+		
+	// is media playing on this face?
+	if (!LLViewerMedia::isActiveMediaTexture(objectp->getTE(gLastHitObjectFace)->getID()))
+	{
+		handle_click_action_play();
+		return;
+	}
+
+	std::string media_url = std::string ( parcel->getMediaURL () );
+	std::string media_type = std::string ( parcel->getMediaType() );
+	LLString::trim(media_url);
+
+	// Get the scheme, see if that is handled as well.
+	LLURI uri(media_url);
+	std::string media_scheme = uri.scheme() != "" ? uri.scheme() : "http";
+
+	// HACK: This is directly referencing an impl name.  BAD!
+	// This can be removed when we have a truly generic media browser that only 
+	// builds an impl based on the type of url it is passed.
 
+	if(	LLMediaManager::getInstance()->supportsMediaType( "LLMediaImplLLMozLib", media_scheme, media_type ) )
+	{
+		LLWeb::loadURL(media_url);
+	}
+}
+
+static ECursorType cursor_from_parcel_media(U8 click_action)
+{
+	// HACK: This is directly referencing an impl name.  BAD!
+	// This can be removed when we have a truly generic media browser that only 
+	// builds an impl based on the type of url it is passed.
+	
+	//FIXME: how do we handle object in different parcel than us?
+	ECursorType open_cursor = UI_CURSOR_ARROW;
+	LLParcel* parcel = gParcelMgr->getAgentParcel();
+	if (!parcel) return open_cursor;
+
+	std::string media_url = std::string ( parcel->getMediaURL () );
+	std::string media_type = std::string ( parcel->getMediaType() );
+	LLString::trim(media_url);
+
+	// Get the scheme, see if that is handled as well.
+	LLURI uri(media_url);
+	std::string media_scheme = uri.scheme() != "" ? uri.scheme() : "http";
+
+	if(	LLMediaManager::getInstance()->supportsMediaType( "LLMediaImplLLMozLib", media_scheme, media_type ) )
+	{
+		open_cursor = UI_CURSOR_TOOLMEDIAOPEN;
+	}
+
+	LLMediaBase::EStatus status = LLViewerParcelMedia::getStatus();
+	switch(status)
+	{
+		case LLMediaBase::STATUS_STARTED:
+			return click_action == CLICK_ACTION_PLAY ? UI_CURSOR_TOOLPAUSE : open_cursor;
+		default:
+			return UI_CURSOR_TOOLPLAY;
+	}
+}
diff --git a/indra/newview/llurldispatcher.cpp b/indra/newview/llurldispatcher.cpp
index 82b2b597ca6..9e4f1966017 100644
--- a/indra/newview/llurldispatcher.cpp
+++ b/indra/newview/llurldispatcher.cpp
@@ -39,6 +39,7 @@
 #include "llfloaterdirectory.h"
 #include "llfloaterhtml.h"
 #include "llfloaterworldmap.h"
+#include "llfloaterhtmlhelp.h"
 #include "llpanellogin.h"
 #include "llstartup.h"			// gStartupState
 #include "llurlsimstring.h"
@@ -159,9 +160,7 @@ bool LLURLDispatcherImpl::dispatchHelp(const std::string& url, BOOL right_mouse)
 {
 	if (matchPrefix(url, SLURL_SL_HELP_PREFIX))
 	{
-#if LL_LIBXUL_ENABLED
 		gViewerHtmlHelp.show();
-#endif // LL_LIBXUL_ENABLED
 		return true;
 	}
 	return false;
diff --git a/indra/newview/llurlhistory.cpp b/indra/newview/llurlhistory.cpp
new file mode 100644
index 00000000000..86a12a73fae
--- /dev/null
+++ b/indra/newview/llurlhistory.cpp
@@ -0,0 +1,110 @@
+/** 
+ * @file llurlhistory.cpp
+ * @author Sam Kolb
+ * @brief Manages a list of recent URLs
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+#include "llviewerprecompiledheaders.h"
+
+#include "llurlhistory.h"
+
+#include "lldir.h"
+#include "llsdserialize.h"
+
+LLSD LLURLHistory::sHistorySD;
+
+const int MAX_URL_COUNT = 10;
+
+/////////////////////////////////////////////////////////////////////////////
+
+// static
+bool LLURLHistory::loadFile(const LLString& filename)
+{
+	LLSD data;
+	{
+		LLString temp_str = gDirUtilp->getLindenUserDir() + gDirUtilp->getDirDelimiter();
+
+		llifstream file((temp_str + filename).c_str());
+
+		if (file.is_open())
+		{
+			llinfos << "Loading history.xml file at " << filename << llendl;
+			LLSDSerialize::fromXML(data, file);
+		}
+
+		if (data.isUndefined())
+		{
+			llinfos << "file missing, ill-formed, "
+				"or simply undefined; not changing the"
+				" file" << llendl;
+			return false;
+		}
+	}
+	sHistorySD = data;
+	return true;
+}
+
+// static
+bool LLURLHistory::saveFile(const LLString& filename)
+{
+	LLString temp_str = gDirUtilp->getLindenUserDir() + gDirUtilp->getDirDelimiter();
+	llofstream out((temp_str + filename).c_str());
+	if (!out.good())
+	{
+		llwarns << "Unable to open " << filename << " for output." << llendl;
+		return false;
+	}
+
+	LLSDSerialize::toXML(sHistorySD, out);
+
+	out.close();
+	return true;
+}
+// static
+// This function returns a portion of the history llsd that contains the collected 
+// url history
+LLSD LLURLHistory::getURLHistory(const std::string& collection)
+{
+	if(sHistorySD.has(collection))
+	{
+		return sHistorySD[collection];
+	}
+	return LLSD();
+}
+
+// static
+void LLURLHistory::addURL(const std::string& collection, const std::string& url)
+{
+	sHistorySD[collection].insert(0, url);
+	LLURLHistory::limitSize(collection);
+}
+// static
+void LLURLHistory::removeURL(const std::string& collection, const std::string& url)
+{
+	LLSD::array_iterator iter = sHistorySD[collection].beginArray();
+	LLSD::array_iterator end = sHistorySD[collection].endArray();
+	for(int index = 0; index < sHistorySD[collection].size(); index++)
+	{
+		if(sHistorySD[collection].get(index).asString() == url)
+		{
+			sHistorySD[collection].erase(index);
+		}
+	}
+}
+
+// static
+void LLURLHistory::clear(const std::string& collection)
+{
+	sHistorySD[ collection ] = LLSD();
+}
+
+void LLURLHistory::limitSize(const std::string& collection)
+{
+	while(sHistorySD[collection].size() > MAX_URL_COUNT)
+	{
+		sHistorySD[collection].erase(MAX_URL_COUNT);
+	}
+}
+
diff --git a/indra/newview/llurlhistory.h b/indra/newview/llurlhistory.h
new file mode 100644
index 00000000000..210057f746e
--- /dev/null
+++ b/indra/newview/llurlhistory.h
@@ -0,0 +1,37 @@
+/** 
+ * @file llurlhistory.h
+ * @author Sam Kolb
+ * @brief Manages a list of recent URLs
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+#ifndef LLURLHISTORY_H
+#define LLURLHISTORY_H
+
+#include "llstring.h"	
+
+class LLSD;
+
+class LLURLHistory
+{
+public:
+	// Loads an xml file of URLs.  Currently only supports Parcel URL history
+	static bool loadFile(const LLString& filename);
+
+	// Saves the current history to XML
+	static bool saveFile(const LLString& filename);
+
+	static LLSD getURLHistory(const std::string& collection);
+
+	static void addURL(const std::string& collection, const std::string& url);
+	static void removeURL(const std::string& collection, const std::string& url);
+	static void clear(const std::string& collection);
+
+	static void limitSize(const std::string& collection);
+
+private:
+	static LLSD sHistorySD;
+};
+
+#endif // LLURLHISTORY_H
diff --git a/indra/newview/llvieweraudio.cpp b/indra/newview/llvieweraudio.cpp
index b8c8e62c4b6..affce91b79c 100644
--- a/indra/newview/llvieweraudio.cpp
+++ b/indra/newview/llvieweraudio.cpp
@@ -35,12 +35,12 @@
 #include "audiosettings.h"
 #include "llagent.h"
 #include "llappviewer.h"
-#include "llmediaengine.h"
 #include "llvieweraudio.h"
 #include "llviewercamera.h"
 #include "llviewercontrol.h"
 #include "llviewerwindow.h"
 #include "llvoiceclient.h"
+#include "llviewermedia.h"
 
 /////////////////////////////////////////////////////////
 
@@ -153,13 +153,10 @@ void audio_update_volume(bool force_update)
 	}
 
 	// Streaming Media
-	if(LLMediaEngine::getInstance())
-	{
-		F32 media_volume = gSavedSettings.getF32("AudioLevelMedia");
-		media_volume = mute_volume * master_volume * (media_volume*media_volume);
-		BOOL media_muted = gSavedSettings.getBOOL("MuteMedia");
-		LLMediaEngine::getInstance()->setVolume(media_muted ? 0.f : media_volume);
-	}
+	F32 media_volume = gSavedSettings.getF32("AudioLevelMedia");
+	BOOL media_muted = gSavedSettings.getBOOL("MuteMedia");
+	media_volume = mute_volume * master_volume * (media_volume*media_volume);
+	LLViewerMedia::setVolume( media_muted ? 0.0f : media_volume );
 
 	// Voice
 	if (gVoiceClient)
diff --git a/indra/newview/llviewercontrol.cpp b/indra/newview/llviewercontrol.cpp
index 250b250a7a6..7180683a860 100644
--- a/indra/newview/llviewercontrol.cpp
+++ b/indra/newview/llviewercontrol.cpp
@@ -261,7 +261,6 @@ void LLFloaterSettingsDebug::updateControl(LLControlBase* controlp)
 	spinner4->setVisible(FALSE);
 	color_swatch->setVisible(FALSE);
 	childSetVisible("val_text", FALSE);
-	childSetVisible("boolean_combo", FALSE);
 	mComment->setText(LLString::null);
 
 	if (controlp)
@@ -299,6 +298,7 @@ void LLFloaterSettingsDebug::updateControl(LLControlBase* controlp)
 		  case TYPE_U32:
 			spinner1->setVisible(TRUE);
 			spinner1->setLabel(LLString("value")); // Debug, don't translate
+			childSetVisible("boolean_combo", FALSE);
 			if (!spinner1->hasFocus())
 			{
 				spinner1->setValue(sd);
@@ -311,6 +311,7 @@ void LLFloaterSettingsDebug::updateControl(LLControlBase* controlp)
 		  case TYPE_S32:
 			spinner1->setVisible(TRUE);
 			spinner1->setLabel(LLString("value")); // Debug, don't translate
+			childSetVisible("boolean_combo", FALSE);
 			if (!spinner1->hasFocus())
 			{
 				spinner1->setValue(sd);
@@ -323,6 +324,7 @@ void LLFloaterSettingsDebug::updateControl(LLControlBase* controlp)
 		  case TYPE_F32:
 			spinner1->setVisible(TRUE);
 			spinner1->setLabel(LLString("value")); // Debug, don't translate
+			childSetVisible("boolean_combo", FALSE);
 			if (!spinner1->hasFocus())
 			{
 				spinner1->setPrecision(3);
@@ -346,6 +348,7 @@ void LLFloaterSettingsDebug::updateControl(LLControlBase* controlp)
 			break;
 		  case TYPE_STRING:
 			childSetVisible("val_text", TRUE);
+			childSetVisible("boolean_combo", FALSE);
 			if (!childHasFocus("val_text"))
 			{
 				childSetValue("val_text", sd);
@@ -353,6 +356,7 @@ void LLFloaterSettingsDebug::updateControl(LLControlBase* controlp)
 			break;
 		  case TYPE_VEC3:
 		  {
+			childSetVisible("boolean_combo", FALSE);
 			LLVector3 v;
 			v.setValue(sd);
 			spinner1->setVisible(TRUE);
@@ -380,6 +384,7 @@ void LLFloaterSettingsDebug::updateControl(LLControlBase* controlp)
 		  }
 		  case TYPE_VEC3D:
 		  {
+			childSetVisible("boolean_combo", FALSE);
 			LLVector3d v;
 			v.setValue(sd);
 			spinner1->setVisible(TRUE);
@@ -407,6 +412,7 @@ void LLFloaterSettingsDebug::updateControl(LLControlBase* controlp)
 		  }
 		  case TYPE_RECT:
 		  {
+			childSetVisible("boolean_combo", FALSE);
 			LLRect r;
 			r.setValue(sd);
 			spinner1->setVisible(TRUE);
@@ -457,6 +463,7 @@ void LLFloaterSettingsDebug::updateControl(LLControlBase* controlp)
 		  }
 		  case TYPE_COL4:
 		  {
+			childSetVisible("boolean_combo", FALSE);
 			LLColor4 clr;
 			clr.setValue(sd);
 			color_swatch->setVisible(TRUE);
@@ -478,6 +485,7 @@ void LLFloaterSettingsDebug::updateControl(LLControlBase* controlp)
 		  }
 		  case TYPE_COL3:
 		  {
+			childSetVisible("boolean_combo", FALSE);
 			LLColor3 clr;
 			clr.setValue(sd);
 			color_swatch->setVisible(TRUE);
@@ -486,6 +494,7 @@ void LLFloaterSettingsDebug::updateControl(LLControlBase* controlp)
 		  }
 		  case TYPE_COL4U:
 		  {
+			childSetVisible("boolean_combo", FALSE);
 			LLColor4U clr;
 			clr.setValue(sd);
 			color_swatch->setVisible(TRUE);
diff --git a/indra/newview/llviewermedia.cpp b/indra/newview/llviewermedia.cpp
new file mode 100644
index 00000000000..7a86b1d67c5
--- /dev/null
+++ b/indra/newview/llviewermedia.cpp
@@ -0,0 +1,608 @@
+/** 
+ * @file llviewermedia.cpp
+ * @author Callum Prentice & James Cook
+ * @brief Client interface to the media engine
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+#include "llviewerprecompiledheaders.h"
+
+#include "llviewermedia.h"
+
+#include "llmimetypes.h"
+#include "llviewercontrol.h"
+#include "llviewerimage.h"
+#include "llviewerwindow.h"
+#include "llversionviewer.h"
+#include "llviewerimagelist.h"
+
+#include "llevent.h"		// LLSimpleListener
+#include "llmediamanager.h"
+#include "lluuid.h"
+
+// don't want to include llappviewer.h
+extern std::string gChannelName;
+
+// Implementation functions not exported into header file
+class LLViewerMediaImpl
+	:	public LLMediaObserver
+{
+	public:
+		LLViewerMediaImpl()
+		:	mMediaSource( NULL ),
+			mMovieImageID(),
+			mMovieImageHasMips(false)
+		{ }
+
+		void initControlListeners();
+
+		void destroyMediaSource();
+
+	    void play(const std::string& media_url,
+				  const std::string& mime_type,
+				  const LLUUID& placeholder_texture_id,
+				  S32 media_width, S32 media_height, U8 media_auto_scale,
+				  U8 media_loop);
+	
+		void stop();
+		void pause();
+		void start();
+    	void seek(F32 time);
+    	void setVolume(F32 volume);
+		LLMediaBase::EStatus getStatus();
+
+		/*virtual*/ void onMediaSizeChange(const EventType& event_in);
+		/*virtual*/ void onMediaContentsChange(const EventType& event_in);
+
+		void updateMovieImage(const LLUUID& image_id, BOOL active);
+		void updateImagesMediaStreams();
+		LLUUID getMediaTextureID();
+
+	public:
+
+		// a single media url with some data and an impl.
+		LLMediaBase* mMediaSource;	
+		LLUUID mMovieImageID;
+		bool  mMovieImageHasMips;
+		std::string mMediaURL;		
+		std::string mMimeType;
+    private:
+	    void initializePlaceholderImage(LLViewerImage *placeholder_image, LLMediaBase *media_source);
+};
+
+static LLViewerMediaImpl sViewerMediaImpl;
+
+void LLViewerMediaImpl::destroyMediaSource()
+{
+	LLMediaManager* mgr = LLMediaManager::getInstance();
+	if ( mMediaSource )
+	{
+		bool was_playing = LLViewerMedia::isMediaPlaying();
+		mMediaSource->remObserver(this);
+		mgr->destroySource( mMediaSource );
+
+		// Restore the texture
+		updateMovieImage(LLUUID::null, was_playing);
+
+	}
+	mMediaSource = NULL;
+}
+
+void LLViewerMediaImpl::play(const std::string& media_url,
+							 const std::string& mime_type,
+							 const LLUUID& placeholder_texture_id,
+							 S32 media_width, S32 media_height, U8 media_auto_scale,
+							 U8 media_loop)
+{
+	// first stop any previously playing media
+	stop();
+	
+	// Save this first, as init/load below may fire events
+	mMovieImageID = placeholder_texture_id;
+
+	// If the mime_type passed in is different than the cached one, and 
+	// Auto-discovery is turned OFF, replace the cached mime_type with the new one.
+	if(mime_type != mMimeType && 
+		! gSavedSettings.getBOOL("AutoMimeDiscovery"))
+	{
+		mMimeType = mime_type;
+	}
+	LLURI url(media_url);
+	std::string scheme = url.scheme() != "" ? url.scheme() : "http";
+	
+	LLMediaManager* mgr = LLMediaManager::getInstance();
+	mMediaSource = mgr->createSourceFromMimeType(scheme, mMimeType );
+	if ( !mMediaSource )
+	{
+		llwarns << "media source create failed " << media_url
+			<< " type " << mMimeType
+			<< llendl;
+		return;
+	}
+	
+	if ((media_width != 0) && (media_height != 0))
+	{
+		mMediaSource->setRequestedMediaSize(media_width, media_height);
+	}
+	
+	mMediaSource->setLooping(media_loop);
+	mMediaSource->setAutoScaled(media_auto_scale);
+	mMediaSource->addObserver( this );
+	mMediaSource->navigateTo( media_url );
+	mMediaSource->addCommand(LLMediaBase::COMMAND_START);
+
+	// Store the URL and Mime Type
+	mMediaURL = media_url;
+
+}
+
+void LLViewerMediaImpl::stop()
+{
+	destroyMediaSource();
+}
+
+void LLViewerMediaImpl::pause()
+{
+	if(mMediaSource)
+	{
+		mMediaSource->addCommand(LLMediaBase::COMMAND_PAUSE);
+	}
+}
+
+void LLViewerMediaImpl::start()
+{
+	if(mMediaSource)
+	{
+		mMediaSource->addCommand(LLMediaBase::COMMAND_START);
+	}
+}
+
+void LLViewerMediaImpl::seek(F32 time)
+{
+	if(mMediaSource)
+	{
+		mMediaSource->seek(time);
+	}
+}
+
+void LLViewerMediaImpl::setVolume(F32 volume)
+{
+	if(mMediaSource)
+	{
+		mMediaSource->setVolume( volume);
+	}
+}
+
+LLMediaBase::EStatus LLViewerMediaImpl::getStatus()
+{
+	if (mMediaSource)
+	{
+		return mMediaSource->getStatus();
+	}
+	else
+	{
+		return LLMediaBase::STATUS_UNKNOWN;
+	}
+}
+
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+void LLViewerMediaImpl::updateMovieImage(const LLUUID& uuid, BOOL active)
+{
+	// IF the media image hasn't changed, do nothing
+	if (mMovieImageID == uuid)
+	{
+		return;
+	}
+	// If we have changed media uuid, restore the old one
+	if (!mMovieImageID.isNull())
+	{
+		LLViewerImage* oldImage = LLViewerImage::getImage( mMovieImageID );
+		if (oldImage)
+		{
+			oldImage->reinit(mMovieImageHasMips);
+			oldImage->mIsMediaTexture = FALSE;
+		}
+		mMovieImageID.setNull();
+	}
+	// If the movie is playing, set the new media image
+	if (active && !uuid.isNull())
+	{
+		LLViewerImage* viewerImage = LLViewerImage::getImage( uuid );
+		if( viewerImage )
+		{
+			mMovieImageID = uuid;
+			// Can't use mipmaps for movies because they don't update the full image
+			mMovieImageHasMips = viewerImage->getUseMipMaps();
+			viewerImage->reinit(FALSE);
+			viewerImage->mIsMediaTexture = TRUE;
+		}
+	}
+}
+
+
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+void LLViewerMediaImpl::updateImagesMediaStreams()
+{
+	LLMediaManager::updateClass();
+}
+
+void LLViewerMediaImpl::initializePlaceholderImage(LLViewerImage *placeholder_image, LLMediaBase *media_source)
+{
+	int media_width = media_source->getMediaWidth();
+	int media_height = media_source->getMediaHeight();
+	//int media_rowspan = media_source->getMediaRowSpan();
+
+	// if width & height are invalid, don't bother doing anything
+	if ( media_width < 1 || media_height < 1 ) 
+		return;
+
+	llinfos << "initializing media placeholder" << llendl;
+	llinfos << "movie image id " << mMovieImageID << llendl;
+
+	int texture_width = LLMediaManager::textureWidthFromMediaWidth( media_width );
+	int texture_height = LLMediaManager::textureHeightFromMediaHeight( media_height );
+	int texture_depth = media_source->getMediaDepth();
+
+	// MEDIAOPT: check to see if size actually changed before doing work
+	placeholder_image->destroyGLTexture();
+	// MEDIAOPT: apparently just calling setUseMipMaps(FALSE) doesn't work?
+	placeholder_image->reinit(FALSE);	// probably not needed
+
+	// MEDIAOPT: seems insane that we actually have to make an imageraw then
+	// immediately discard it
+	LLPointer<LLImageRaw> raw = new LLImageRaw(texture_width, texture_height, texture_depth);
+	raw->clear(0x0f, 0x0f, 0x0f, 0xff);	
+	int discard_level = 0;
+
+	// ask media source for correct GL image format constants
+	placeholder_image->setExplicitFormat(media_source->getTextureFormatInternal(), 
+										 media_source->getTextureFormatPrimary(), 
+										 media_source->getTextureFormatType());
+
+	placeholder_image->createGLTexture(discard_level, raw);
+
+	// placeholder_image->setExplicitFormat()
+	placeholder_image->setUseMipMaps(FALSE);
+
+	// MEDIAOPT: set this dynamically on play/stop
+	placeholder_image->mIsMediaTexture = true;
+}
+
+
+
+// virtual
+void LLViewerMediaImpl::onMediaContentsChange(const EventType& event_in)
+{
+	LLMediaBase* media_source = event_in.getSubject();
+	LLViewerImage* placeholder_image = gImageList.getImage( mMovieImageID );
+	if ((placeholder_image) && (placeholder_image->getHasGLTexture()))
+	{
+		if (placeholder_image->getUseMipMaps())
+		{
+			// bad image!  NO MIPMAPS!
+			initializePlaceholderImage(placeholder_image, media_source);
+		}
+
+		U8* data = media_source->getMediaData();
+		S32 x_pos = 0;
+		S32 y_pos = 0;
+		S32 width = media_source->getMediaWidth();
+		S32 height = media_source->getMediaHeight();
+		S32 data_width = media_source->getMediaDataWidth();
+		S32 data_height = media_source->getMediaDataHeight();
+		placeholder_image->setSubImage(data, data_width, data_height,
+			x_pos, y_pos, width, height);
+	}
+}
+
+
+// virtual
+void LLViewerMediaImpl::onMediaSizeChange(const EventType& event_in)
+{
+	LLMediaBase* media_source = event_in.getSubject();
+	LLViewerImage* placeholder_image = gImageList.getImage( mMovieImageID );
+	if (placeholder_image)
+	{
+		initializePlaceholderImage(placeholder_image, media_source);
+	}
+	else
+	{
+		llinfos << "no placeholder image" << llendl;
+	}
+}
+
+
+		// Get the image we're using
+
+	/*
+	// update media stream if required
+	LLMediaEngine* media_engine = LLMediaEngine::getInstance();
+	if (media_engine)
+	{
+		if ( media_engine->update() )
+		{
+			LLUUID media_uuid = media_engine->getImageUUID();
+			updateMovieImage(media_uuid, TRUE);
+			if (!media_uuid.isNull())
+			{
+				LLViewerImage* viewerImage = getImage( media_uuid );
+				if( viewerImage )
+				{
+					LLMediaBase* renderer = media_engine->getMediaRenderer();
+					if ((renderer->getTextureWidth() != viewerImage->getWidth()) ||
+						(renderer->getTextureHeight() != viewerImage->getHeight()) ||
+						(renderer->getTextureDepth() != viewerImage->getComponents()) ||
+						(viewerImage->getHasGLTexture() == FALSE))
+					{
+						// destroy existing GL image
+						viewerImage->destroyGLTexture();
+				
+						// set new size
+						viewerImage->setSize( renderer->getTextureWidth(),
+												renderer->getTextureHeight(),
+												renderer->getTextureDepth() );
+
+						LLPointer<LLImageRaw> raw = new LLImageRaw(renderer->getTextureWidth(),
+																	renderer->getTextureHeight(),
+																	renderer->getTextureDepth());
+						raw->clear(0x7f,0x7f,0x7f,0xff);
+						viewerImage->createGLTexture(0, raw);
+					}
+
+					// Set the explicit format the instance wants
+					viewerImage->setExplicitFormat(renderer->getTextureFormatInternal(), 
+													renderer->getTextureFormatPrimary(), 
+													renderer->getTextureFormatType(),
+													renderer->getTextureFormatSwapBytes());
+					// This should be redundant, but just in case:
+					viewerImage->setUseMipMaps(FALSE);
+
+					LLImageRaw* rawImage = media_engine->getImageRaw();
+					if ( rawImage )
+					{
+						viewerImage->setSubImage(rawImage, 0, 0,
+													renderer->getMediaWidth(),
+													renderer->getMediaHeight());
+					}
+				}
+				else
+				{
+					llwarns << "MediaEngine update unable to get viewer image for GL texture" << llendl;
+				}
+			}
+		}
+		else
+		{
+			LLUUID media_uuid = media_engine->getImageUUID();
+			updateMovieImage(media_uuid, FALSE);
+		}
+	}
+	*/
+
+
+//////////////////////////////////////////////////////////////////////////////////////////
+LLUUID LLViewerMediaImpl::getMediaTextureID()
+{
+	return mMovieImageID;
+}
+
+//////////////////////////////////////////////////////////////////////////////////////////
+// Wrapper class
+//////////////////////////////////////////////////////////////////////////////////////////
+
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+void LLViewerMedia::initClass()
+{
+	LLMediaManagerData* init_data = new LLMediaManagerData;
+
+//	std::string executable_dir = std::string( arg0 ).substr( 0, std::string( arg0 ).find_last_of("\\/") );
+//	std::string component_dir = std::string( executable_dir ).substr( 0, std::string( executable_dir ).find_last_of("\\/") );
+//	component_dir = std::string( component_dir ).substr( 0, std::string( component_dir ).find_last_of("\\/") );
+//	component_dir = std::string( component_dir ).substr( 0, std::string( component_dir ).find_last_of("\\/") );
+//	component_dir += "\\newview\\app_settings\\mozilla";
+
+
+#if LL_DARWIN
+	// For Mac OS, we store both the shared libraries and the runtime files (chrome/, plugins/, etc) in
+	// Second Life.app/Contents/MacOS/.  This matches the way Firefox is distributed on the Mac.
+	std::string component_dir(gDirUtilp->getExecutableDir());
+#elif LL_WINDOWS
+	std::string component_dir( gDirUtilp->getExpandedFilename( LL_PATH_APP_SETTINGS, "" ) );
+	component_dir += gDirUtilp->getDirDelimiter();
+  #ifdef LL_DEBUG
+	component_dir += "mozilla_debug";
+  #else // LL_DEBUG
+	component_dir += "mozilla";
+  #endif // LL_DEBUG
+#elif LL_LINUX
+	std::string component_dir( gDirUtilp->getExpandedFilename( LL_PATH_APP_SETTINGS, "" ) );
+	component_dir += gDirUtilp->getDirDelimiter();
+	component_dir += "mozilla-runtime-linux-i686";
+#else
+	std::string component_dir( gDirUtilp->getExpandedFilename( LL_PATH_APP_SETTINGS, "" ) );
+	component_dir += gDirUtilp->getDirDelimiter();
+	component_dir += "mozilla";
+#endif
+
+	// append our magic version number string to the browser user agent id
+	std::ostringstream codec;
+	codec << "[Second Life ";
+	codec << "(" << gChannelName << ")";
+	codec << " - " << LL_VERSION_MAJOR << "." << LL_VERSION_MINOR << "." << LL_VERSION_PATCH << "." << LL_VERSION_BUILD;
+	codec << "]";
+	init_data->setBrowserUserAgentId( codec.str() );
+
+	std::string application_dir = gDirUtilp->getExecutableDir();
+	
+	init_data->setBrowserApplicationDir( application_dir );
+	std::string profile_dir = gDirUtilp->getExpandedFilename( LL_PATH_MOZILLA_PROFILE, "" );
+	init_data->setBrowserProfileDir( profile_dir );
+	init_data->setBrowserComponentDir( component_dir );
+	std::string profile_name("Second Life");
+	init_data->setBrowserProfileName( profile_name );
+	init_data->setBrowserParentWindow( gViewerWindow->getPlatformWindow() );
+
+	LLMediaManager::initClass( init_data );
+
+	LLMediaManager* mm = LLMediaManager::getInstance();
+	LLMIMETypes::mime_info_map_t::const_iterator it;
+	for (it = LLMIMETypes::sMap.begin(); it != LLMIMETypes::sMap.end(); ++it)
+	{
+		const LLString& mime_type = it->first;
+		const LLMIMETypes::LLMIMEInfo& info = it->second;
+		mm->addMimeTypeImplNameMap( mime_type, info.mImpl );
+	}
+}
+
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+void LLViewerMedia::cleanupClass()
+{
+	LLMediaManager::cleanupClass();
+}
+
+// static
+void LLViewerMedia::play(const std::string& media_url,
+						 const std::string& mime_type,
+						 const LLUUID& placeholder_texture_id,
+						 S32 media_width, S32 media_height, U8 media_auto_scale,
+						 U8 media_loop)
+{
+	sViewerMediaImpl.play(media_url, mime_type, placeholder_texture_id,
+						  media_width, media_height, media_auto_scale, media_loop);
+}
+
+// static
+void LLViewerMedia::stop()
+{
+	sViewerMediaImpl.stop();
+}
+
+// static
+void LLViewerMedia::pause()
+{
+	sViewerMediaImpl.pause();
+}
+
+// static
+void LLViewerMedia::start()
+{
+	sViewerMediaImpl.start();
+}
+
+// static
+void LLViewerMedia::seek(F32 time)
+{
+	sViewerMediaImpl.seek(time);
+}
+
+// static
+void LLViewerMedia::setVolume(F32 volume)
+{
+	sViewerMediaImpl.setVolume(volume);
+}
+
+// static
+LLMediaBase::EStatus LLViewerMedia::getStatus()
+{
+	return sViewerMediaImpl.getStatus();
+}
+
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+LLUUID LLViewerMedia::getMediaTextureID()
+{
+	return sViewerMediaImpl.getMediaTextureID();
+}
+
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+bool LLViewerMedia::getMediaSize(S32 *media_width, S32 *media_height)
+{
+	// make sure we're valid
+
+	if ( sViewerMediaImpl.mMediaSource != NULL )
+	{
+		*media_width = sViewerMediaImpl.mMediaSource->getMediaWidth(); 
+		*media_height = sViewerMediaImpl.mMediaSource->getMediaHeight();
+		return true;
+	}
+	return false;
+}
+
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+bool LLViewerMedia::getTextureSize(S32 *texture_width, S32 *texture_height)
+{
+	if ( sViewerMediaImpl.mMediaSource != NULL )
+	{
+		S32 media_width = sViewerMediaImpl.mMediaSource->getMediaWidth(); 
+		S32 media_height = sViewerMediaImpl.mMediaSource->getMediaHeight();
+		*texture_width = LLMediaManager::textureWidthFromMediaWidth( media_width );
+		*texture_height = LLMediaManager::textureHeightFromMediaHeight( media_height );
+		return true;
+	}
+	return false;
+}
+
+
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+void LLViewerMedia::updateImagesMediaStreams()
+{
+	sViewerMediaImpl.updateImagesMediaStreams();
+}
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+bool LLViewerMedia::isMediaPlaying()
+{
+	LLMediaBase::EStatus status = sViewerMediaImpl.getStatus();
+	return (status == LLMediaBase::STATUS_STARTED ); 
+}
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+bool LLViewerMedia::isMediaPaused()
+{
+	LLMediaBase::EStatus status = sViewerMediaImpl.getStatus();
+	return (status == LLMediaBase::STATUS_PAUSED); 
+}
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+bool LLViewerMedia::hasMedia()
+{
+	return sViewerMediaImpl.mMediaSource != NULL;
+}
+
+//////////////////////////////////////////////////////////////////////////////////////////
+//static 
+bool LLViewerMedia::isActiveMediaTexture(const LLUUID& id)
+{
+	return (id.notNull()
+		&& id == getMediaTextureID()
+		&& isMediaPlaying());
+}
+
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+std::string LLViewerMedia::getMediaURL()
+{
+	return sViewerMediaImpl.mMediaURL;
+}
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+std::string LLViewerMedia::getMimeType()
+{
+	return sViewerMediaImpl.mMimeType;
+}
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+void LLViewerMedia::setMimeType(std::string mime_type)
+{
+	sViewerMediaImpl.mMimeType = mime_type;
+}
+
+
diff --git a/indra/newview/llviewermedia.h b/indra/newview/llviewermedia.h
new file mode 100644
index 00000000000..6ecaea54ce3
--- /dev/null
+++ b/indra/newview/llviewermedia.h
@@ -0,0 +1,49 @@
+/** 
+ * @file llviewermedia.h
+ * @author Callum Prentice & James Cook
+ * @brief Client interface to the media engine
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+#ifndef LLVIEWERMEDIA_H
+#define LLVIEWERMEDIA_H
+
+#include "llmediabase.h"	// for status codes
+
+class LLUUID;
+
+class LLViewerMedia
+{
+	public:
+		static void initClass();
+		static void cleanupClass();
+
+		static void play(const std::string& media_url,
+						 const std::string& mime_type,
+						 const LLUUID& placeholder_texture_id,
+						 S32 media_width, S32 media_height, U8 media_auto_scale,
+						 U8 media_loop);
+		static void stop();
+		static void pause();
+		static void start();
+		static void seek(F32 time);
+		static void setVolume(F32 volume);
+		static LLMediaBase::EStatus getStatus();
+
+		static LLUUID getMediaTextureID();
+		static bool getMediaSize(S32 *media_width, S32 *media_height);
+		static bool getTextureSize(S32 *texture_width, S32 *texture_height);
+		static bool isMediaPlaying();
+		static bool isMediaPaused();
+		static bool hasMedia();
+		static bool isActiveMediaTexture(const LLUUID& id);
+
+		static std::string getMediaURL();
+		static std::string getMimeType();
+		static void setMimeType(std::string mime_type);
+
+		static void updateImagesMediaStreams();
+};
+
+#endif	// LLVIEWERMEDIA_H
diff --git a/indra/newview/llviewermenu.cpp b/indra/newview/llviewermenu.cpp
index f732b0fda02..9c94306fb76 100644
--- a/indra/newview/llviewermenu.cpp
+++ b/indra/newview/llviewermenu.cpp
@@ -104,6 +104,7 @@
 #include "llfloatergroupinvite.h"
 #include "llfloatergroups.h"
 #include "llfloaterhtml.h"
+#include "llfloaterhtmlhelp.h"
 #include "llfloaterinspect.h"
 #include "llfloaterlagmeter.h"
 #include "llfloaterland.h"
@@ -5340,7 +5341,7 @@ class LLShowFloater : public view_listener_t
 				gParcelMgr->selectParcelAt(gAgent.getPositionGlobal());
 			}
 
-			LLFloaterLand::show();
+			LLFloaterLand::showInstance();
 		}
 		else if (floater_name == "buy land")
 		{
@@ -5365,25 +5366,19 @@ class LLShowFloater : public view_listener_t
 		}
 		else if (floater_name == "help f1")
 		{
-#if LL_LIBXUL_ENABLED
 			gViewerHtmlHelp.show( gSavedSettings.getString("HelpHomeURL") );
-#endif
 		}
 		else if (floater_name == "help in-world")
 		{
-#if LL_LIBXUL_ENABLED
 			const bool open_app_slurls = true;
 			LLFloaterHtml::getInstance()->show( 
 				"in-world_help", open_app_slurls );
-#endif
 		}
 		else if (floater_name == "help additional")
 		{
-#if LL_LIBXUL_ENABLED
 			const bool open_app_slurls = true;
 			LLFloaterHtml::getInstance()->show( 
 				"additional_help", open_app_slurls );
-#endif
 		}
 		else if (floater_name == "complaint reporter")
 		{
diff --git a/indra/newview/llviewermessage.cpp b/indra/newview/llviewermessage.cpp
index 6b18fb46bee..5e3ffb5e049 100644
--- a/indra/newview/llviewermessage.cpp
+++ b/indra/newview/llviewermessage.cpp
@@ -5039,7 +5039,7 @@ void callback_load_url(S32 option, void* data)
 
 	if (0 == option)
 	{
-		LLWeb::loadURL(infop->mUrl);  
+		LLWeb::loadURL(infop->mUrl);
 	}
 
 	delete infop;
diff --git a/indra/newview/llviewerobject.h b/indra/newview/llviewerobject.h
index f2ddc173a08..42124610eb9 100644
--- a/indra/newview/llviewerobject.h
+++ b/indra/newview/llviewerobject.h
@@ -156,8 +156,6 @@ class LLViewerObject : public LLPrimitive, public LLRefCount
 	// Return codes for processUpdateMessage
 	enum { MEDIA_URL_REMOVED = 0x1, MEDIA_URL_ADDED = 0x2, MEDIA_URL_UPDATED = 0x4 };
 
-	enum { CLICK_ACTION_TOUCH = 0, CLICK_ACTION_SIT = 1, CLICK_ACTION_BUY = 2 };
-
 	virtual U32		processUpdateMessage(LLMessageSystem *mesgsys,
 										void **user_data,
 										U32 block_num,
diff --git a/indra/newview/llviewerparcelmedia.cpp b/indra/newview/llviewerparcelmedia.cpp
new file mode 100644
index 00000000000..33c8ed919c0
--- /dev/null
+++ b/indra/newview/llviewerparcelmedia.cpp
@@ -0,0 +1,340 @@
+/** 
+ * @file llviewerparcelmedia.cpp
+ * @author Callum Prentice & James Cook
+ * @brief Handlers for multimedia on a per-parcel basis
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+#include "llviewerprecompiledheaders.h"
+#include "llviewerparcelmedia.h"
+
+#include "llagent.h"
+#include "llviewercontrol.h"
+#include "llviewermedia.h"
+#include "llviewerregion.h"
+#include "llparcel.h"
+#include "llviewerparcelmgr.h"
+#include "lluuid.h"
+#include "message.h"
+#include "llviewerparcelmediaautoplay.h"
+#include "llfirstuse.h"
+
+// Static Variables
+
+S32 LLViewerParcelMedia::sMediaParcelLocalID = 0;
+LLUUID LLViewerParcelMedia::sMediaRegionID;
+
+// Move this to its own file.
+// helper class that tries to download a URL from a web site and calls a method 
+// on the Panel Land Media and to discover the MIME type
+class LLMimeDiscoveryResponder : public LLHTTPClient::Responder
+{
+public:
+	LLMimeDiscoveryResponder( ) 
+	  {}
+
+
+
+	  virtual void completedHeader(U32 status, const std::string& reason, const LLSD& content)
+	  {
+		  std::string media_type = content["content-type"].asString();
+		  std::string::size_type idx1 = media_type.find_first_of(";");
+		  std::string mime_type = media_type.substr(0, idx1);
+		  completeAny(status, mime_type);
+	  }
+
+	  virtual void error( U32 status, const std::string& reason )
+	  {
+		  completeAny(status, "none/none");
+	  }
+
+	  void completeAny(U32 status, const std::string& mime_type)
+	  {
+		  LLViewerMedia::setMimeType(mime_type);
+	  }
+};
+
+// static
+void LLViewerParcelMedia::initClass()
+{
+	LLMessageSystem* msg = gMessageSystem;
+	msg->setHandlerFunc("ParcelMediaCommandMessage", processParcelMediaCommandMessage );
+	msg->setHandlerFunc("ParcelMediaUpdate", processParcelMediaUpdate );
+	LLViewerParcelMediaAutoPlay::initClass();
+}
+
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+void LLViewerParcelMedia::update(LLParcel* parcel)
+{
+	if (/*LLViewerMedia::hasMedia()*/ true)
+	{
+		// we have a player
+		if (parcel)
+		{
+			// we're in a parcel
+			bool new_parcel = false;
+			S32 parcelid = parcel->getLocalID();
+			LLUUID regionid = gAgent.getRegion()->getRegionID();
+			if (parcelid != sMediaParcelLocalID || regionid != sMediaRegionID)
+			{
+				sMediaParcelLocalID = parcelid;
+				sMediaRegionID = regionid;
+				new_parcel = true;
+			}
+
+			std::string mediaUrl = std::string ( parcel->getMediaURL () );
+			LLString::trim(mediaUrl);
+
+			// has something changed?
+			if (  ( LLViewerMedia::getMediaURL() != mediaUrl )
+				|| ( LLViewerMedia::getMediaTextureID() != parcel->getMediaID () ) )
+			{
+				bool video_was_playing = FALSE;
+				bool same_media_id = LLViewerMedia::getMediaTextureID() == parcel->getMediaID ();
+
+				if (LLViewerMedia::isMediaPlaying())
+				{
+					video_was_playing = TRUE;
+				}
+
+				if ( !mediaUrl.empty() && same_media_id && ! new_parcel)
+				{
+					// Someone has "changed the channel", changing the URL of a video
+					// you were already watching.  Automatically play provided the texture ID is the same
+					if (video_was_playing)
+					{
+						// Poke the mime type in before calling play.
+						// This is necessary because in this instance we are not waiting
+						// for the results of a header curl.  In order to change the channel
+						// a mime type MUST be provided.
+						LLViewerMedia::setMimeType(parcel->getMediaType());
+						play(parcel);
+					}
+				}
+				else
+				{
+					stop();
+				}
+
+				// Discover the MIME type
+				// Disabled for the time being.  Get the mime type from the parcel.
+				if(gSavedSettings.getBOOL("AutoMimeDiscovery"))
+				{
+					LLHTTPClient::getHeaderOnly( mediaUrl, new LLMimeDiscoveryResponder());
+				}
+				else
+				{
+					LLViewerMedia::setMimeType(parcel->getMediaType());
+				}
+
+			}
+		}
+		else
+		{
+			stop();
+		}
+	}
+	/*
+	else
+	{
+		// no audio player, do a first use dialog if their is media here
+		if (parcel)
+		{
+			std::string mediaUrl = std::string ( parcel->getMediaURL () );
+			if (!mediaUrl.empty ())
+			{
+				if (gSavedSettings.getWarning("QuickTimeInstalled"))
+				{
+					gSavedSettings.setWarning("QuickTimeInstalled", FALSE);
+
+					LLNotifyBox::showXml("NoQuickTime" );
+				};
+			}
+		}
+	}
+	*/
+}
+
+// static
+void LLViewerParcelMedia::play(LLParcel* parcel)
+{
+	llinfos << "play" << llendl;
+	
+	if (!parcel) return;
+
+	if (!gSavedSettings.getBOOL("AudioStreamingVideo"))
+		return;
+	
+	std::string media_url = parcel->getMediaURL();
+	std::string mime_type = parcel->getMediaType();
+	LLUUID placeholder_texture_id = parcel->getMediaID();
+	U8 media_auto_scale = parcel->getMediaAutoScale();
+	U8 media_loop = parcel->getMediaLoop();
+	S32 media_width = parcel->getMediaWidth();
+	S32 media_height = parcel->getMediaHeight();
+	LLViewerMedia::play(media_url, mime_type, placeholder_texture_id,
+						media_width, media_height, media_auto_scale,
+						media_loop);
+	LLFirstUse::useMedia();
+
+	LLViewerParcelMediaAutoPlay::playStarted();
+}
+
+// static
+void LLViewerParcelMedia::stop()
+{
+
+	LLViewerMedia::stop();
+}
+
+// static
+void LLViewerParcelMedia::pause()
+{
+	LLViewerMedia::pause();
+}
+
+// static
+void LLViewerParcelMedia::start()
+{
+	LLViewerMedia::start();
+	LLFirstUse::useMedia();
+
+	LLViewerParcelMediaAutoPlay::playStarted();
+}
+
+// static
+void LLViewerParcelMedia::seek(F32 time)
+{
+	LLViewerMedia::seek(time);
+}
+
+
+// static
+LLMediaBase::EStatus LLViewerParcelMedia::getStatus()
+{
+	return LLViewerMedia::getStatus();
+}
+
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+void LLViewerParcelMedia::processParcelMediaCommandMessage( LLMessageSystem *msg, void ** )
+{
+	// extract the agent id
+	//	LLUUID agent_id;
+	//	msg->getUUID( agent_id );
+
+	U32 flags;
+	U32 command;
+	F32 time;
+	msg->getU32( "CommandBlock", "Flags", flags );
+	msg->getU32( "CommandBlock", "Command", command);
+	msg->getF32( "CommandBlock", "Time", time );
+
+	if (flags &( (1<<PARCEL_MEDIA_COMMAND_STOP) 
+				| (1<<PARCEL_MEDIA_COMMAND_PAUSE) 
+				| (1<<PARCEL_MEDIA_COMMAND_PLAY) 
+				| (1<<PARCEL_MEDIA_COMMAND_LOOP) 
+				| (1<<PARCEL_MEDIA_COMMAND_UNLOAD) ))
+	{
+		// stop
+		if( command == PARCEL_MEDIA_COMMAND_STOP )
+		{
+			stop();
+		}
+		else
+		// pause
+		if( command == PARCEL_MEDIA_COMMAND_PAUSE )
+		{
+			pause();
+		}
+		else
+		// play
+		if( command == PARCEL_MEDIA_COMMAND_PLAY )
+		{
+			if (LLViewerMedia::isMediaPaused())
+			{
+				start();
+			}
+			else
+			{
+				LLParcel *parcel = gParcelMgr->getAgentParcel();
+				play(parcel);
+			}
+		}
+		else
+		// loop
+		if( command == PARCEL_MEDIA_COMMAND_LOOP )
+		{
+			//llinfos << ">>> LLMediaEngine::process_parcel_media with command = " <<( '0' + command ) << llendl;
+
+			// huh? what is play?
+			//convertImageAndLoadUrl( play );
+			//convertImageAndLoadUrl( true, false, std::string() );
+		}
+		else
+		// unload
+		if( command == PARCEL_MEDIA_COMMAND_UNLOAD )
+		{
+			stop();
+		}
+	}
+
+	if (flags & (1<<PARCEL_MEDIA_COMMAND_TIME))
+	{
+		if(! LLViewerMedia::hasMedia())
+		{
+			LLParcel *parcel = gParcelMgr->getAgentParcel();
+			play(parcel);
+		}
+		seek(time);
+	}
+}
+
+//////////////////////////////////////////////////////////////////////////////////////////
+// static
+void LLViewerParcelMedia::processParcelMediaUpdate( LLMessageSystem *msg, void ** )
+{
+	LLUUID media_id;
+	std::string media_url;
+	std::string media_type;
+	S32 media_width = 0;
+	S32 media_height = 0;
+	U8 media_auto_scale = FALSE;
+	U8 media_loop = FALSE;
+	
+	msg->getUUID( "DataBlock", "MediaID", media_id );
+	char media_url_buffer[257];
+	msg->getString( "DataBlock", "MediaURL", 255, media_url_buffer );
+	media_url = media_url_buffer;
+	msg->getU8("DataBlock", "MediaAutoScale", media_auto_scale);
+	
+	if (msg->getNumberOfBlocks("DataBlockExtended")) // do we have the extended data?
+	{
+		char media_type_buffer[257];
+		msg->getString("DataBlockExtended", "MediaType", 255, media_type_buffer);
+		media_type = media_type_buffer;
+		msg->getU8("DataBlockExtended", "MediaLoop", media_loop);
+		msg->getS32("DataBlockExtended", "MediaWidth", media_width);
+		msg->getS32("DataBlockExtended", "MediaHeight", media_height);
+	}
+
+	LLParcel *parcel = gParcelMgr->getAgentParcel();
+	BOOL same = FALSE;
+	if (parcel)
+	{
+		same = ((parcel->getMediaURL() == media_url) &&
+				(parcel->getMediaType() == media_type) &&
+				(parcel->getMediaID() == media_id) &&
+				(parcel->getMediaWidth() == media_width) &&
+				(parcel->getMediaHeight() == media_height) &&
+				(parcel->getMediaAutoScale() == media_auto_scale) &&
+				(parcel->getMediaLoop() == media_loop));
+	}
+
+	if (!same)
+		LLViewerMedia::play(media_url, media_type, media_id,
+							media_auto_scale, media_width, media_height,
+							media_loop);
+}
diff --git a/indra/newview/llviewerparcelmedia.h b/indra/newview/llviewerparcelmedia.h
new file mode 100644
index 00000000000..bf391a83cb8
--- /dev/null
+++ b/indra/newview/llviewerparcelmedia.h
@@ -0,0 +1,52 @@
+/** 
+ * @file llviewerparcelmedia.h
+ * @author Callum Prentice & James Cook
+ * @brief Handlers for multimedia on a per-parcel basis
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+#ifndef LLVIEWERPARCELMEDIA_H
+#define LLVIEWERPARCELMEDIA_H
+
+#include "llmediabase.h"
+
+class LLMessageSystem;
+class LLParcel;
+
+// This class understands land parcels, network traffic, LSL media
+// transport commands, and talks to the LLViewerMedia class to actually
+// do playback.  It allows us to remove code from LLViewerParcelMgr.
+class LLViewerParcelMedia
+{
+	public:
+		static void initClass();
+
+		static void update(LLParcel* parcel);
+			// called when the agent's parcel has a new URL, or the agent has
+			// walked on to a new parcel with media
+
+		static void play(LLParcel* parcel);
+			// user clicked play button in media transport controls
+
+		static void stop();
+			// user clicked stop button in media transport controls
+
+		static void pause();
+		static void start();
+			// restart after pause - no need for all the setup
+
+		static void seek(F32 time);
+		    // jump to timecode time
+
+		static LLMediaBase::EStatus getStatus();
+
+		static void processParcelMediaCommandMessage( LLMessageSystem *msg, void ** );
+		static void processParcelMediaUpdate( LLMessageSystem *msg, void ** );
+
+	public:
+		static S32 sMediaParcelLocalID;
+		static LLUUID sMediaRegionID;
+};
+
+#endif
diff --git a/indra/newview/llviewerparcelmediaautoplay.cpp b/indra/newview/llviewerparcelmediaautoplay.cpp
new file mode 100644
index 00000000000..112c6dfcea9
--- /dev/null
+++ b/indra/newview/llviewerparcelmediaautoplay.cpp
@@ -0,0 +1,129 @@
+/**
+ * @file llviewerparcelmediaautoplay.cpp
+ * @author Karl Stiefvater
+ * @brief timer to automatically play media in a parcel
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+
+#include "llviewerprecompiledheaders.h"
+#include "llviewerparcelmediaautoplay.h"
+#include "llviewerparcelmedia.h"
+#include "llviewercontrol.h"
+#include "llviewermedia.h"
+#include "llparcel.h"
+#include "llviewerparcelmgr.h"
+#include "lluuid.h"
+#include "message.h"
+#include "llviewerimagelist.h"         // for texture stats
+#include "llagent.h"
+
+const F32 AUTOPLAY_TIME  = 5;          // how many seconds before we autoplay
+const F32 AUTOPLAY_SIZE  = 24*24;      // how big the texture must be (pixel area) before we autoplay
+const F32 AUTOPLAY_SPEED = 0.1f;        // how slow should the agent be moving to autoplay
+
+LLViewerParcelMediaAutoPlay::LLViewerParcelMediaAutoPlay() :
+	LLEventTimer(1),
+	mPlayed(FALSE),
+	mTimeInParcel(0)
+{
+}
+
+static LLViewerParcelMediaAutoPlay *sAutoPlay = NULL;
+
+// static
+void LLViewerParcelMediaAutoPlay::initClass()
+{
+	if (!sAutoPlay)
+		sAutoPlay = new LLViewerParcelMediaAutoPlay;
+}
+
+// static
+void LLViewerParcelMediaAutoPlay::cleanupClass()
+{
+	if (sAutoPlay)
+		delete sAutoPlay;
+}
+
+// static
+void LLViewerParcelMediaAutoPlay::playStarted()
+{
+	if (sAutoPlay)
+	{
+		sAutoPlay->mPlayed = TRUE;
+	}
+}
+
+BOOL LLViewerParcelMediaAutoPlay::tick()
+{
+	LLParcel *this_parcel = NULL;
+	std::string this_media_url;
+	LLUUID this_media_texture_id;
+	S32 this_parcel_id = 0;
+	
+	if (gParcelMgr)
+	{
+		this_parcel = gParcelMgr->getAgentParcel();
+	}
+
+	if (this_parcel)
+	{
+		this_media_url = std::string(this_parcel->getMediaURL());
+
+		this_media_texture_id = this_parcel->getMediaID();
+
+		this_parcel_id = this_parcel->getLocalID();
+	}
+
+	if (this_parcel_id != mLastParcelID)
+	{
+		// we've entered a new parcel
+		mPlayed    = FALSE;                   // we haven't autoplayed yet
+		mTimeInParcel = 0;                    // reset our timer
+		mLastParcelID = this_parcel_id;
+	}
+
+	mTimeInParcel += mPeriod;                 // increase mTimeInParcel by the amount of time between ticks
+
+	if ((!mPlayed) &&                         // if we've never played
+		(mTimeInParcel > AUTOPLAY_TIME) &&    // and if we've been here for so many seconds
+		(this_media_url.size() != 0) &&       // and if the parcel has media
+		(!LLViewerMedia::isMediaPlaying()))   // and if the media is not already playing
+	{
+		if (this_media_texture_id.notNull())  // and if the media texture is good
+		{
+			LLViewerImage *image = gImageList.getImage(this_media_texture_id, FALSE);
+
+			F32 image_size = 0;
+			
+			if (image)
+			{
+				image_size = image->mMaxVirtualSize;
+			}
+
+			if (gAgent.getVelocity().magVec() < AUTOPLAY_SPEED) // and if the agent is stopped (slow enough)
+			{
+				if (image_size > AUTOPLAY_SIZE)    // and if the target texture is big enough on screen
+				{
+					if (this_parcel)
+					{
+						if (gSavedSettings.getBOOL("ParcelMediaAutoPlayEnable"))
+						{
+							// and last but not least, only play when autoplay is enabled
+							LLViewerParcelMedia::play(this_parcel);
+						}
+					}
+
+					mPlayed = TRUE;
+				}
+			}
+		}
+	}
+
+	
+	return FALSE; // continue ticking forever please.
+}
+		
+ 
+	
diff --git a/indra/newview/llviewerparcelmediaautoplay.h b/indra/newview/llviewerparcelmediaautoplay.h
new file mode 100644
index 00000000000..20b132c8279
--- /dev/null
+++ b/indra/newview/llviewerparcelmediaautoplay.h
@@ -0,0 +1,32 @@
+/**
+ * @file llviewerparcelmediaautoplay.h
+ * @author Karl Stiefvater
+ * @brief timer to automatically play media in a parcel
+ *
+ * Copyright (c) 2007-$CurrentYear$, Linden Research, Inc.
+ * $License$
+ */
+#ifndef LLVIEWERPARCELMEDIAAUTOPLAY_H
+#define LLVIEWERPARCELMEDIAAUTOPLAY_H
+
+#include "llmediabase.h"
+#include "lltimer.h"
+
+// timer to automatically play media
+class LLViewerParcelMediaAutoPlay : LLEventTimer
+{
+ public:
+	LLViewerParcelMediaAutoPlay();
+	virtual BOOL tick();
+	static void initClass();
+	static void cleanupClass();
+	static void playStarted();
+	
+ private:
+	S32 mLastParcelID;
+	BOOL mPlayed;
+	F32 mTimeInParcel;
+};
+
+
+#endif // LLVIEWERPARCELMEDIAAUTOPLAY_H
diff --git a/indra/newview/llviewerparcelmgr.cpp b/indra/newview/llviewerparcelmgr.cpp
index eaea0438faa..e027588eaa0 100644
--- a/indra/newview/llviewerparcelmgr.cpp
+++ b/indra/newview/llviewerparcelmgr.cpp
@@ -38,7 +38,6 @@
 #include "indra_constants.h"
 #include "llcachename.h"
 #include "llgl.h"
-#include "llmediaengine.h"
 #include "llparcel.h"
 #include "llsecondlifeurls.h"
 #include "message.h"
@@ -55,14 +54,16 @@
 #include "llfloatersellland.h"
 #include "llfloatertools.h"
 #include "llnotify.h"
+#include "llparcelselection.h"
 #include "llresmgr.h"
 #include "llstatusbar.h"
 #include "llui.h"
+#include "llviewerimage.h"
 #include "llviewerimagelist.h"
 #include "llviewermenu.h"
+#include "llviewerparcelmedia.h"
 #include "llviewerparceloverlay.h"
 #include "llviewerregion.h"
-//#include "llwebbrowserctrl.h"
 #include "llworld.h"
 #include "lloverlaybar.h"
 #include "roles_constants.h"
@@ -78,11 +79,8 @@ U8* LLViewerParcelMgr::sPackedOverlay = NULL;
 
 LLUUID gCurrentMovieID = LLUUID::null;
 
-static LLParcelSelection* get_null_parcel_selection();
-template<> 
-	const LLHandle<LLParcelSelection>::NullFunc 
-		LLHandle<LLParcelSelection>::sNullFunc = get_null_parcel_selection;
-
+LLPointer<LLViewerImage> sBlockedImage;
+LLPointer<LLViewerImage> sPassImage;
 
 // Local functions
 void optionally_start_music(const LLString& music_url);
@@ -141,10 +139,10 @@ LLViewerParcelMgr::LLViewerParcelMgr()
 	resetSegments(mCollisionSegments);
 
 	mBlockedImageID.set(gViewerArt.getString("noentrylines.tga"));
-	mBlockedImage = gImageList.getImage(mBlockedImageID, TRUE, TRUE);
+	sBlockedImage = gImageList.getImage(mBlockedImageID, TRUE, TRUE);
 
 	mPassImageID.set(gViewerArt.getString("noentrypasslines.tga"));
-	mPassImage = gImageList.getImage(mPassImageID, TRUE, TRUE);
+	sPassImage = gImageList.getImage(mPassImageID, TRUE, TRUE);
 
 	S32 overlay_size = mParcelsPerEdge * mParcelsPerEdge / PARCEL_OVERLAY_CHUNKS;
 	sPackedOverlay = new U8[overlay_size];
@@ -189,6 +187,9 @@ LLViewerParcelMgr::~LLViewerParcelMgr()
 
 	delete[] mAgentParcelOverlay;
 	mAgentParcelOverlay = NULL;
+
+	sBlockedImage = NULL;
+	sPassImage = NULL;
 }
 
 void LLViewerParcelMgr::dump()
@@ -1255,30 +1256,45 @@ const LLString& LLViewerParcelMgr::getAgentParcelName() const
 }
 
 
-void LLViewerParcelMgr::sendParcelPropertiesUpdate(LLParcel* parcel)
+void LLViewerParcelMgr::sendParcelPropertiesUpdate(LLParcel* parcel, bool use_agent_region)
 {
 	if (!parcel) return;
 	if(!gWorldp) return;
-	LLViewerRegion *region = gWorldp->getRegionFromPosGlobal( mWestSouth );
+	LLViewerRegion *region = use_agent_region ? gAgent.getRegion() : gWorldp->getRegionFromPosGlobal( mWestSouth );
 	if (!region) return;
 
-	LLMessageSystem *msg = gMessageSystem;
+	LLSD body;
+	std::string url = gAgent.getRegion()->getCapability("ParcelPropertiesUpdate");
+	if (!url.empty())
+	{
+		parcel->packMessage(body);
 
-	msg->newMessageFast(_PREHASH_ParcelPropertiesUpdate);
-	msg->nextBlockFast(_PREHASH_AgentData);
-	msg->addUUIDFast(_PREHASH_AgentID,	gAgent.getID() );
-	msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
-	msg->nextBlockFast(_PREHASH_ParcelData);
-	msg->addS32Fast(_PREHASH_LocalID, parcel->getLocalID() );
+		llinfos << "Sending parcel properties update via capability to:" << url << llendl;
 
-	U32 flags = 0x0;
-	// request new properties update from simulator
-	flags |= 0x01;
-	msg->addU32("Flags", flags);
+		LLHTTPClient::post(url, body, new LLHTTPClient::Responder());
+	}
+	else
+	{
+		LLMessageSystem *msg = gMessageSystem;
+
+		msg->newMessageFast(_PREHASH_ParcelPropertiesUpdate);
+		msg->nextBlockFast(_PREHASH_AgentData);
+		msg->addUUIDFast(_PREHASH_AgentID,	gAgent.getID() );
+		msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID());
+		msg->nextBlockFast(_PREHASH_ParcelData);
+		msg->addS32Fast(_PREHASH_LocalID, parcel->getLocalID() );
+
+		U32 flags = 0x0;
+		// request new properties update from simulator
+		flags |= 0x01;
+		msg->addU32("Flags", flags);
+
+		parcel->packMessage(msg);
+
+		msg->sendReliable( region->getHost() );
+	}
 
-	parcel->packMessage(msg);
 
-	msg->sendReliable( region->getHost() );
 }
 
 
@@ -1363,7 +1379,6 @@ void LLViewerParcelMgr::processParcelOverlay(LLMessageSystem *msg, void **user)
 	}
 }
 
-
 // static
 void LLViewerParcelMgr::processParcelProperties(LLMessageSystem *msg, void **user)
 {
@@ -1657,19 +1672,6 @@ void LLViewerParcelMgr::processParcelProperties(LLMessageSystem *msg, void **use
 	}
 	else
 	{
-		// It's the agent parcel
-		BOOL new_parcel = parcel ? FALSE : TRUE;
-		if (parcel)
-		{
-			S32 parcelid = parcel->getLocalID();
-			U64 regionid = gAgent.getRegion()->getHandle();
-			if (parcelid != gParcelMgr->mMediaParcelId || regionid != gParcelMgr->mMediaRegionId)
-			{
-				gParcelMgr->mMediaParcelId = parcelid;
-				gParcelMgr->mMediaRegionId = regionid;
-				new_parcel = TRUE;
-			}
-		}
 		// look for music.
 		if (gAudiop)
 		{
@@ -1714,75 +1716,7 @@ void LLViewerParcelMgr::processParcelProperties(LLMessageSystem *msg, void **use
 		}//if gAudiop
 
 		// now check for video
-		if (LLMediaEngine::getInstance ()->isAvailable ())
-		{
-			// we have a player
-			if (parcel)
-			{
-				// we're in a parcel
-				std::string mediaUrl = std::string ( parcel->getMediaURL () );
-				LLString::trim(mediaUrl);
-
-				// clean spaces and whatnot 
-				mediaUrl = LLWeb::escapeURL(mediaUrl);
-
-				
-				// something changed
-				LLMediaEngine* me = LLMediaEngine::getInstance();
-				if (  ( me->getUrl () != mediaUrl )
-					|| ( me->getImageUUID () != parcel->getMediaID () ) 
-					|| ( me->isAutoScaled () != parcel->getMediaAutoScale () ) )
-				{
-					BOOL video_was_playing = FALSE;
-					LLMediaBase* renderer = me->getMediaRenderer();
-					if (renderer && (renderer->isPlaying() || renderer->isLooping()))
-					{
-						video_was_playing = TRUE;
-					}
-
-					stop_video();
-
-					if ( !mediaUrl.empty () )
-					{
-						// Someone has "changed the channel", changing the URL of a video
-						// you were already watching.  Do we want to automatically start playing? JC
-						if (!new_parcel
-							&& gSavedSettings.getBOOL("AudioStreamingVideo")
-							&& video_was_playing)
-						{
-							start_video(parcel);
-						}
-						else
-						{
-							// "Prepare" the media engine, but don't auto-play. JC
-							optionally_prepare_video(parcel);
-						}
-					}
-				}
-			}
-			else
-			{
-				stop_video();
-			}
-		}
-		else
-		{
-			// no audio player, do a first use dialog if their is media here
-			if (parcel)
-			{
-				std::string mediaUrl = std::string ( parcel->getMediaURL () );
-				if (!mediaUrl.empty ())
-				{
-					if (gSavedSettings.getWarning("QuickTimeInstalled"))
-					{
-						gSavedSettings.setWarning("QuickTimeInstalled", FALSE);
-
-						LLNotifyBox::showXml("NoQuickTime" );
-					};
-				}
-			}
-		}
-
+		LLViewerParcelMedia::update( parcel );
 	};
 }
 
@@ -1832,94 +1766,6 @@ void callback_start_music(S32 option, void* data)
 	music_url = NULL;
 }
 
-void prepare_video(const LLParcel *parcel)
-{
-	std::string mediaUrl;
-	if (parcel->getParcelFlag(PF_URL_RAW_HTML))
-	{
-		mediaUrl = std::string("data:");
-		mediaUrl.append(parcel->getMediaURL());
-	}
-	else
-	{
-		mediaUrl = std::string ( parcel->getMediaURL () );
-	}
-
-	// clean spaces and whatnot 
-	mediaUrl = LLWeb::escapeURL(mediaUrl);
-	
-	LLMediaEngine::getInstance ()->setUrl ( mediaUrl );
-	LLMediaEngine::getInstance ()->setImageUUID ( parcel->getMediaID () );
-	LLMediaEngine::getInstance ()->setAutoScaled ( parcel->getMediaAutoScale () ? TRUE : FALSE );  // (U8 instead of BOOL for future expansion)
-}
-
-void start_video(const LLParcel *parcel)
-{
-	prepare_video(parcel);
-	std::string path( "" );
-	LLMediaEngine::getInstance ()->convertImageAndLoadUrl ( true, false, path);
-}
-
-void stop_video()
-{
-	// set up remote control so stop is selected
-	LLMediaEngine::getInstance ()->stop ();
-	if (gOverlayBar)
-	{
-		gOverlayBar->refresh ();
-	}
-
-	if (LLMediaEngine::getInstance ()->isLoaded())
-	{
-		LLMediaEngine::getInstance ()->unload ();
-
-		gImageList.updateMovieImage(LLUUID::null, FALSE);
-		gCurrentMovieID.setNull();
-	}
-
-	LLMediaEngine::getInstance ()->setUrl ( "" );
-	LLMediaEngine::getInstance ()->setImageUUID ( LLUUID::null );
-	
-}
-
-void optionally_prepare_video(const LLParcel *parcelp)
-{
-	if (gSavedSettings.getWarning("FirstStreamingVideo"))
-	{
-		gViewerWindow->alertXml("ParcelCanPlayMedia",
-			callback_prepare_video,
-			(void*)parcelp);
-	}
-	else
-	{
-		llinfos << "Entering parcel " << parcelp->getLocalID() << " with video " <<  parcelp->getMediaURL() << llendl;
-		prepare_video(parcelp);
-	}
-}
-
-
-void callback_prepare_video(S32 option, void* data)
-{
-	const LLParcel *parcelp = (const LLParcel *)data;
-
-	if (0 == option)
-	{
-		gSavedSettings.setBOOL("AudioStreamingVideo", TRUE);
-		llinfos << "Starting parcel video " <<  parcelp->getMediaURL() << " on parcel " << parcelp->getLocalID() << llendl;
-		gMessageSystem->setHandlerFunc("ParcelMediaCommandMessage", LLMediaEngine::process_parcel_media);
-		gMessageSystem->setHandlerFunc ( "ParcelMediaUpdate", LLMediaEngine::process_parcel_media_update );
-		prepare_video(parcelp);
-	}
-	else
-	{
-		gMessageSystem->setHandlerFunc("ParcelMediaCommandMessage", null_message_callback);
-		gMessageSystem->setHandlerFunc ( "ParcelMediaUpdate", null_message_callback );
-		gSavedSettings.setBOOL("AudioStreamingVideo", FALSE);
-	}
-
-	gSavedSettings.setWarning("FirstStreamingVideo", FALSE);
-}
-
 // static
 void LLViewerParcelMgr::processParcelAccessListReply(LLMessageSystem *msg, void **user)
 {
@@ -2548,71 +2394,20 @@ void sanitize_corners(const LLVector3d &corner1,
 	east_north_top.mdV[VZ] = llmax( corner1.mdV[VZ], corner2.mdV[VZ] );
 }
 
-//
-// LLParcelSelection
-//
-LLParcelSelection::LLParcelSelection() : 
-	mParcel(NULL),
-	mSelectedMultipleOwners(FALSE),
-	mWholeParcelSelected(FALSE),
-	mSelectedSelfCount(0),
-	mSelectedOtherCount(0),
-	mSelectedPublicCount(0)
-{
-}
-
-LLParcelSelection::LLParcelSelection(LLParcel* parcel)  : 
-	mParcel(parcel),
-	mSelectedMultipleOwners(FALSE),
-	mWholeParcelSelected(FALSE),
-	mSelectedSelfCount(0),
-	mSelectedOtherCount(0),
-	mSelectedPublicCount(0)
-{
-}
 
-LLParcelSelection::~LLParcelSelection()
-{
-}
-
-BOOL LLParcelSelection::getMultipleOwners() const
-{
-	return mSelectedMultipleOwners;
-}
-
-
-BOOL LLParcelSelection::getWholeParcelSelected() const
-{
-	return mWholeParcelSelected;
-}
-
-
-S32 LLParcelSelection::getClaimableArea() const
-{
-	const S32 UNIT_AREA = S32( PARCEL_GRID_STEP_METERS * PARCEL_GRID_STEP_METERS );
-	return mSelectedPublicCount * UNIT_AREA;
-}
-
-bool LLParcelSelection::hasOthersSelected() const
+void LLViewerParcelMgr::cleanupGlobals()
 {
-	return mSelectedOtherCount != 0;
+	delete gParcelMgr;
+	gParcelMgr = NULL;
+	LLParcelSelection::sNullSelection = NULL;
 }
 
-static LLPointer<LLParcelSelection> sNullSelection;
-
-LLParcelSelection* get_null_parcel_selection()
+LLViewerImage* LLViewerParcelMgr::getBlockedImage() const
 {
-	if (sNullSelection.isNull())
-	{
-		sNullSelection = new LLParcelSelection;
-	}
-	
-	return sNullSelection;
+	return sBlockedImage;
 }
 
-void LLViewerParcelMgr::cleanupGlobals()
+LLViewerImage* LLViewerParcelMgr::getPassImage() const
 {
-	delete gParcelMgr;
-	gParcelMgr = NULL;
-	sNullSelection = NULL;
+	return sPassImage;
 }
diff --git a/indra/newview/llviewerparcelmgr.h b/indra/newview/llviewerparcelmgr.h
index 640c8c5c57c..efea18158c7 100644
--- a/indra/newview/llviewerparcelmgr.h
+++ b/indra/newview/llviewerparcelmgr.h
@@ -36,11 +36,12 @@
 #include "lldarray.h"
 #include "llframetimer.h"
 #include "llmemory.h"
-#include "llviewerimage.h"
+#include "llparcelselection.h"
 
 class LLUUID;
 class LLMessageSystem;
 class LLParcel;
+class LLViewerImage;
 class LLViewerRegion;
 
 // Constants for sendLandOwner
@@ -72,49 +73,6 @@ class LLParcelObserver
 	virtual void changed() = 0;
 };
 
-class LLParcelSelection : public LLRefCount
-{
-	friend class LLViewerParcelMgr;
-
-protected:
-	~LLParcelSelection();
-
-public:
-	LLParcelSelection(LLParcel* parcel);
-	LLParcelSelection();
-
-	// this can return NULL at any time, as parcel selection
-	// might have been invalidated.
-	LLParcel* getParcel() { return mParcel; }
-
-	// Return the number of grid units that are owned by you within
-	// the selection (computed by server).
-	S32 getSelfCount() const { return mSelectedSelfCount; }
-
-	// Returns area that will actually be claimed in meters squared.
-	S32		getClaimableArea() const;
-	bool	hasOthersSelected() const;
-
-	// Does the selection have multiple land owners in it?
-	BOOL	getMultipleOwners() const;
-
-	// Is the entire parcel selected, or just a part?
-	BOOL	getWholeParcelSelected() const;
-
-protected:
-	void setParcel(LLParcel* parcel) { mParcel = parcel; }
-
-protected:
-
-	LLParcel*	mParcel;
-	BOOL		mSelectedMultipleOwners;
-	BOOL		mWholeParcelSelected;
-	S32			mSelectedSelfCount;
-	S32			mSelectedOtherCount;
-	S32			mSelectedPublicCount;
-};
-
-typedef LLHandle<LLParcelSelection> LLParcelSelectionHandle;
 
 class LLViewerParcelMgr
 {
@@ -231,7 +189,7 @@ class LLViewerParcelMgr
 	// containing the southwest corner of the selection.
 	// If want_reply_to_update, simulator will send back a ParcelProperties
 	// message.
-	void	sendParcelPropertiesUpdate(LLParcel* parcel);
+	void	sendParcelPropertiesUpdate(LLParcel* parcel, bool use_agent_region = false);
 
 	// Takes an Access List flag, like AL_ACCESS or AL_BAN
 	void	sendParcelAccessListUpdate(U32 which);
@@ -300,7 +258,7 @@ class LLViewerParcelMgr
 	static BOOL isParcelOwnedByAgent(const LLParcel* parcelp, U64 group_proxy_power);
 	static BOOL isParcelModifiableByAgent(const LLParcel* parcelp, U64 group_proxy_power);
 
-protected:
+private:
 	static void releaseAlertCB(S32 option, void *data);
 
 	// If the user is claiming land and the current selection 
@@ -322,6 +280,8 @@ class LLViewerParcelMgr
 	static void callbackJoinLand(S32 option, void* data);
 
 	//void	finishClaim(BOOL user_to_user_sale, U32 join);
+	LLViewerImage* getBlockedImage() const;
+	LLViewerImage* getPassImage() const;
 
 private:
 	BOOL						mSelected;
@@ -367,8 +327,6 @@ class LLViewerParcelMgr
 	LLFrameTimer				mCollisionTimer;
 	LLUUID						mBlockedImageID;
 	LLUUID						mPassImageID;
-	LLPointer<LLViewerImage> 	mBlockedImage;
-	LLPointer<LLViewerImage> 	mPassImage;
 
 	// Media
 	S32 						mMediaParcelId;
diff --git a/indra/newview/llviewerregion.cpp b/indra/newview/llviewerregion.cpp
index 2a7d2c13677..9f343abdaeb 100644
--- a/indra/newview/llviewerregion.cpp
+++ b/indra/newview/llviewerregion.cpp
@@ -1360,6 +1360,7 @@ void LLViewerRegion::setSeedCapability(const std::string& url)
 	capabilityNames.append("MapLayerGod");
 	capabilityNames.append("NewFileAgentInventory");
 	capabilityNames.append("ParcelGodReserveForNewbie");
+	capabilityNames.append("ParcelPropertiesUpdate");
 	capabilityNames.append("ParcelVoiceInfoRequest");
 	capabilityNames.append("ProvisionVoiceAccountRequest");
 	capabilityNames.append("RemoteParcelRequest");
diff --git a/indra/newview/llviewerwindow.cpp b/indra/newview/llviewerwindow.cpp
index 49d4d726475..95adf32ed51 100644
--- a/indra/newview/llviewerwindow.cpp
+++ b/indra/newview/llviewerwindow.cpp
@@ -60,7 +60,6 @@
 #include "linked_lists.h"
 #include "llassetstorage.h"
 #include "llfontgl.h"
-#include "llmediaengine.h"		// mute on minimize
 #include "llrect.h"
 #include "llsky.h"
 #include "llstring.h"
diff --git a/indra/newview/llweb.cpp b/indra/newview/llweb.cpp
index eac24cebf55..21be9369609 100644
--- a/indra/newview/llweb.cpp
+++ b/indra/newview/llweb.cpp
@@ -36,8 +36,8 @@
 
 #include "llwindow.h"
 
-//#include "llfloaterhtml.h"
 #include "llviewercontrol.h"
+#include "llfloaterhtmlhelp.h"
 
 // static
 void LLWeb::initClass()
@@ -48,7 +48,14 @@ void LLWeb::initClass()
 // static
 void LLWeb::loadURL(const std::string& url)
 {
-	loadURLExternal(url);
+	if (gSavedSettings.getBOOL("UseExternalBrowser"))
+	{
+		loadURLExternal(url);
+	}
+	else
+	{
+		LLFloaterMediaBrowser::showInstance(url);
+	}
 }
 
 
@@ -56,9 +63,7 @@ void LLWeb::loadURL(const std::string& url)
 void LLWeb::loadURLExternal(const std::string& url)
 {
 	std::string escaped_url = escapeURL(url);
-#if LL_LIBXUL_ENABLED
 	spawn_web_browser(escaped_url.c_str());
-#endif
 }
 
 
diff --git a/indra/newview/pipeline.cpp b/indra/newview/pipeline.cpp
index 0f17310840f..8c5ad393ab6 100644
--- a/indra/newview/pipeline.cpp
+++ b/indra/newview/pipeline.cpp
@@ -638,7 +638,7 @@ U32 LLPipeline::getPoolTypeFromTE(const LLTextureEntry* te, LLViewerImage* image
 	bool alpha = te->getColor().mV[3] < 0.999f;
 	if (imagep)
 	{
-		alpha = alpha || (imagep->getComponents() == 4) || (imagep->getComponents() == 2);
+		alpha = alpha || (imagep->getComponents() == 4 && ! imagep->mIsMediaTexture) || (imagep->getComponents() == 2);
 	}
 
 	if (alpha)
diff --git a/indra/newview/res-sdl/toolmediaopen.BMP b/indra/newview/res-sdl/toolmediaopen.BMP
new file mode 100644
index 0000000000000000000000000000000000000000..ac4b231994c1f3ccd69b04c35759fac271b1dbc4
GIT binary patch
literal 3128
zcmeH{y$-@K41^8o1``t_BTs;s*?Di?3Qj$+EH^SVI7mpfl+?}7ch2?aay@Tlj1&4J
z+Tqz&vPUMe#{6!>HV&Y>EwMQ8pANiU;mS4TK;YhMk@eO5l24C#n)Lb!SBVt!0Rd18
zwi4uX<QpyJL&fruQ=Lh(gyl~qsMrkG3N44Z?Hl;RFj%G|SU7Sw`}P)aK2s!au_FgH
z*o}@;N=fIdL{PjfX;w}qCHnE<Ne?(qs#w~t=3^W&%Zln^KrGqjUHK{Sz@O@28wRKT
mWL3^$96uNC{K3cD;6S`3_#wm_Kb)mM>9(jk$o=3@5qSVkjf<oJ

literal 0
HcmV?d00001

diff --git a/indra/newview/res-sdl/toolpause.BMP b/indra/newview/res-sdl/toolpause.BMP
new file mode 100644
index 0000000000000000000000000000000000000000..dd2c6857d28b9eb531819e1774e609e994e4bb37
GIT binary patch
literal 3128
zcmeH{Jrcqo5Jpkxw6e0a^aPHzy_e+_xs|@j5{i{DLY6K&1IhC9KJpQGy`N_{$AkJ#
zxutS&SKgdE(tkNgnH#94J$fBjEUZ0y*%Qzh<EI)7=-xplR@td@J0F6C5SJ{ellED}
z#5JIj+xf~6mG1s1LsYuapZY07tD8UQeh49m1OL>miw7=-@X|WBI9_qQ_vZX8VZM02
zNSGoqj*llJ;CcP(Cr3-7xMfX^a1=bJbTy%hgV*>ba1@JtD|nG_2><2V!WEyxON(uo
UUkGY>vcKlGWEIHc;HWtF1ys3!wEzGB

literal 0
HcmV?d00001

diff --git a/indra/newview/res-sdl/toolplay.BMP b/indra/newview/res-sdl/toolplay.BMP
new file mode 100644
index 0000000000000000000000000000000000000000..9c40d7dbecab270979b9a06fe4a7a0fe5ac1a56c
GIT binary patch
literal 3128
zcmds%F>As=6vxwoLuiK3DT6}=3H<<4x*4*GG?U;e_yK}zhKvpoH^Eh$0!ro#0SA{3
zet>+2Oo4m=`^Q%fNz<6vm!%KxIPSgs{V)H^o%!*uNSAm+|BCkV-5w+jBT0Hh{`ra8
zWdhyjzmCJ<(ChUUi$!x^2@fsHYPZ|7*$i^*Lg1gz=QxgS+g221JRS!@z^FoeNFdTQ
z^*pcB=@^EwUawhHuKA>b-uL}}zpv}M<2c9T@h?J!d=fgHPSfdBRn^I45{BV@DkXeU
zNs`2M-BznL7z{R>O<k4h{NZr8-EJBA!XLQA>(6etGfk8Ie6uWDE|=YI7ysvKwW@1H
zVLkaz_e+*#+^_w9Us!qHB>1DzNYgaD4^b4|2Ps*F_ia9(mlV`ZiA!2{VU>EoVF&_)
zD)l#Oa-1gkLV_KRuOlW&G{+~yFUGSuPe&v6OmGsyq==g*SY7~*Am;{1m9MRm{f*B8
j#|8@dT<}6ZBm5_y7oOv@!>{>Gzy-e{IPsf<gD**6!DY&`

literal 0
HcmV?d00001

diff --git a/indra/newview/res/resource.h b/indra/newview/res/resource.h
index 2a6a113cb99..4f2e88f7f20 100644
--- a/indra/newview/res/resource.h
+++ b/indra/newview/res/resource.h
@@ -50,6 +50,7 @@
 #define IDC_CURSOR4                     153
 #define IDC_CURSOR5                     154
 #define IDI_LCD_LL_ICON                 157
+#define IDC_CURSOR6                     158
 #define IDC_RADIO_56                    1000
 #define IDC_RADIO_128                   1001
 #define IDC_RADIO_256                   1002
@@ -182,6 +183,7 @@
 // 
 #ifdef APSTUDIO_INVOKED
 #ifndef APSTUDIO_READONLY_SYMBOLS
+#define _APS_NEXT_RESOURCE_VALUE        159
 #define _APS_NEXT_RESOURCE_VALUE        167
 #define _APS_NEXT_COMMAND_VALUE         40002
 #define _APS_NEXT_CONTROL_VALUE         1139
diff --git a/indra/newview/res/toolmediaopen.cur b/indra/newview/res/toolmediaopen.cur
new file mode 100644
index 0000000000000000000000000000000000000000..7609989ba7346729af3aaadb6a9412465ad6316a
GIT binary patch
literal 2238
zcmeHIF%H5o47|jZ!Uhv7Y%ubJ@*BRufK(>l!V?*g%sFk580_vSmab8KzDsgL3uGkh
z_uw<(xdOHTjs#mc6A5evB_im$4yqbVHL4}h5@-qhYXbZVTDjL7>5vCPy;(<kck4<-
zXRFRj1A%=GI8s@}o2dO1@Ei!_<njV9k=(RaIXefOc=v!a@5sOYUO=PXQ`ft@dz+`}
zlV{F;5N%aieo=Y3%o_gl{kr$6KN$FaAr3@QeH48UMPIj~SK>sc4Uq`+69%qRPq<R0
JYhp+A#0O5hX7T_4

literal 0
HcmV?d00001

diff --git a/indra/newview/res/toolpause.cur b/indra/newview/res/toolpause.cur
new file mode 100644
index 0000000000000000000000000000000000000000..7a6e85566b195ddd569688529257bb2accfc744b
GIT binary patch
literal 2238
zcmeHIyAHxI5OW?<*<fO&BO`xMK8vk<4s*Yb0qJl;N)#zM#K1&Oa?_sAPU@irEDXjG
zyc*m#z#hPnU<+r$fK8>GbMW3{Sr&+hGTEt~Ku@42@Ph;#zd)&6&3+}rTIbn~)W7mM
zp;|s_zP6^wJ?njIBKD2Kb3l=kvmbb`$%8hOwT%NNzInivZ^+;NIgIk|rEjU@yEpd^
zPC;)<%i>9iHqM3ov})zDYWTm;bshNkcVFRwLGH82g*ee^M;HQA!pt@G=q%hpw#0#$
Fh$r?fUF!e<

literal 0
HcmV?d00001

diff --git a/indra/newview/res/toolplay.cur b/indra/newview/res/toolplay.cur
new file mode 100644
index 0000000000000000000000000000000000000000..0776a17bbc4ca6103218276a2e6ff67ca8f6f1f8
GIT binary patch
literal 2238
zcmeHIJ8pwO6rBA8oERyo(uOi6H*hXQ@6Ndbw@A$uC^!Z8a1m)UyT%|S-m~nqJZbp6
zc{A)z!2%WrWeHvles;h+fKP%gd=Un0D&?Gm_a0f6(WgXJRjBJ4P1B%lTXbEAzV9&%
z140Oj(?)FxYzb@$JdnVym}>QJHL-kHvyc4K{xT);@Xu*L<bga6C_J)%@lN;mFY5Yk
z?JtRi^{M&VwH?nrTNKhn>KldUfFdVnZ}5dCkJ?z)3JV;0ae-G}kWc<|7|W-NUQ(yM
zi{Fk;QE!%(i#H|OG#B&JO3LM`;dwsSch1w@-GyJ|;d~0=NK|xsBMgDVh!gK)kIsQ#
L2(QEkaUlKxbhK{}

literal 0
HcmV?d00001

diff --git a/indra/test/llhttpclient_tut.cpp b/indra/test/llhttpclient_tut.cpp
index a4b2f451448..a177d5f2ea0 100644
--- a/indra/test/llhttpclient_tut.cpp
+++ b/indra/test/llhttpclient_tut.cpp
@@ -116,7 +116,7 @@ namespace tut
 			LLTimer timer;
 			timer.setTimerExpirySec(timeout);
 
-			while(!mSawCompleted && !timer.hasExpired())
+			while(!mSawCompleted && !mSawCompletedHeader && !timer.hasExpired())
 			{
 				if (mServerPump)
 				{
@@ -167,13 +167,19 @@ namespace tut
 		{
 			return mResult;
 		}
+		LLSD getHeader()
+		{
+			return mHeader;
+		}
 	
 	protected:
 		bool mSawError;
 		U32 mStatus;
 		std::string mReason;
 		bool mSawCompleted;
+		bool mSawCompletedHeader;
 		LLSD mResult;
+		LLSD mHeader;
 		bool mResultDeleted;
 
 		class Result : public LLHTTPClient::Responder
@@ -216,6 +222,14 @@ namespace tut
 				mClient.mSawCompleted = true;
 			}
 
+			virtual void completedHeader(
+				U32 status, const std::string& reason,
+				const LLSD& content)
+			{
+				mClient.mHeader = content;
+				mClient.mSawCompletedHeader = true;
+			}
+
 		private:
 			HTTPClientTestData& mClient;
 		};
@@ -228,7 +242,9 @@ namespace tut
 			mSawError = false;
 			mStatus = 0;
 			mSawCompleted = false;
+			mSawCompletedHeader = false;
 			mResult.clear();
+			mHeader.clear();
 			mResultDeleted = false;
 			
 			return Result::build(*this);
@@ -344,9 +360,19 @@ namespace tut
 		LLSD body = result["body"];
 		ensure_equals("echoed result matches", body.size(), expected.size());
 	}
-
 	template<> template<>
-	void HTTPClientTestObject::test<8>()
+		void HTTPClientTestObject::test<8>()
+	{
+		// This is testing for the presence of the Header in the returned results
+		// from an HTTP::get call.
+		LLHTTPClient::get("http://www.secondlife.com/", newResult());
+		runThePump();
+		ensureStatusOK();
+		LLSD header = getHeader();
+		ensure_equals("got a header", header.emptyMap().asBoolean(), FALSE);
+	}
+	template<> template<>
+	void HTTPClientTestObject::test<9>()
 	{
 		LLHTTPClient::head("http://www.secondlife.com/", newResult());
 		runThePump();
diff --git a/scripts/messages/message_template.msg b/scripts/messages/message_template.msg
index 5332b1263df..b9c694bbbf1 100644
--- a/scripts/messages/message_template.msg
+++ b/scripts/messages/message_template.msg
@@ -8714,6 +8714,14 @@ version 2.0
 		{	MediaID			LLUUID			}
 		{	MediaAutoScale	U8				}
 	}
+	{
+		DataBlockExtended Single
+		{   MediaType       Variable    1   }
+		{   MediaDesc       Variable    1   }
+		{   MediaWidth      S32             }
+		{   MediaHeight     S32             }
+		{   MediaLoop       U8              }
+	}
 }
 
 // LandStatRequest
-- 
GitLab