diff --git a/mozilla/content/base/src/nsHTMLValue.cpp b/mozilla/content/base/src/nsHTMLValue.cpp
index a52ad27af79..1071667d728 100644
--- a/mozilla/content/base/src/nsHTMLValue.cpp
+++ b/mozilla/content/base/src/nsHTMLValue.cpp
@@ -42,12 +42,13 @@
#include "nsReadableUtils.h"
#include "nsUnicharUtils.h"
#include "nsCRT.h"
+#include "nsMemory.h"
nsHTMLValue::nsHTMLValue(nsHTMLUnit aUnit)
: mUnit(aUnit)
{
- NS_ASSERTION((aUnit <= eHTMLUnit_Empty), "not a valueless unit");
- if (aUnit > eHTMLUnit_Empty) {
+ NS_ASSERTION(GetUnitClass() == HTMLUNIT_NOSTORE, "not a valueless unit");
+ if (GetUnitClass() != HTMLUNIT_NOSTORE) {
mUnit = eHTMLUnit_Null;
}
mValue.mString = nsnull;
@@ -56,19 +57,14 @@ nsHTMLValue::nsHTMLValue(nsHTMLUnit aUnit)
nsHTMLValue::nsHTMLValue(PRInt32 aValue, nsHTMLUnit aUnit)
: mUnit(aUnit)
{
- NS_ASSERTION((eHTMLUnit_Integer == aUnit) ||
- (eHTMLUnit_Enumerated == aUnit) ||
- (eHTMLUnit_Proportional == aUnit) ||
- (eHTMLUnit_Pixel == aUnit), "not an integer value");
- if ((eHTMLUnit_Integer == aUnit) ||
- (eHTMLUnit_Enumerated == aUnit) ||
- (eHTMLUnit_Proportional == aUnit) ||
- (eHTMLUnit_Pixel == aUnit)) {
+ NS_ASSERTION(GetUnitClass() == HTMLUNIT_INTEGER ||
+ GetUnitClass() == HTMLUNIT_PIXEL, "unit not an integer unit");
+ if (GetUnitClass() == HTMLUNIT_INTEGER ||
+ GetUnitClass() == HTMLUNIT_PIXEL) {
mValue.mInt = aValue;
- }
- else {
+ } else {
mUnit = eHTMLUnit_Null;
- mValue.mInt = 0;
+ mValue.mString = nsnull;
}
}
@@ -81,16 +77,7 @@ nsHTMLValue::nsHTMLValue(float aValue)
nsHTMLValue::nsHTMLValue(const nsAString& aValue, nsHTMLUnit aUnit)
: mUnit(aUnit)
{
- NS_ASSERTION((eHTMLUnit_String == aUnit) ||
- (eHTMLUnit_ColorName == aUnit), "not a string value");
- if ((eHTMLUnit_String == aUnit) ||
- (eHTMLUnit_ColorName == aUnit)) {
- mValue.mString = ToNewUnicode(aValue);
- }
- else {
- mUnit = eHTMLUnit_Null;
- mValue.mInt = 0;
- }
+ SetStringValueInternal(aValue, aUnit);
}
nsHTMLValue::nsHTMLValue(nsISupports* aValue)
@@ -107,29 +94,8 @@ nsHTMLValue::nsHTMLValue(nscolor aValue)
}
nsHTMLValue::nsHTMLValue(const nsHTMLValue& aCopy)
- : mUnit(aCopy.mUnit)
{
- if ((eHTMLUnit_String == mUnit) || (eHTMLUnit_ColorName == mUnit)) {
- if (nsnull != aCopy.mValue.mString) {
- mValue.mString = nsCRT::strdup(aCopy.mValue.mString);
- }
- else {
- mValue.mString = nsnull;
- }
- }
- else if (eHTMLUnit_ISupports == mUnit) {
- mValue.mISupports = aCopy.mValue.mISupports;
- NS_IF_ADDREF(mValue.mISupports);
- }
- else if (eHTMLUnit_Color == mUnit){
- mValue.mColor = aCopy.mValue.mColor;
- }
- else if (eHTMLUnit_Percent == mUnit) {
- mValue.mFloat = aCopy.mValue.mFloat;
- }
- else {
- mValue.mInt = aCopy.mValue.mInt;
- }
+ InitializeFrom(aCopy);
}
nsHTMLValue::~nsHTMLValue(void)
@@ -140,76 +106,69 @@ nsHTMLValue::~nsHTMLValue(void)
nsHTMLValue& nsHTMLValue::operator=(const nsHTMLValue& aCopy)
{
Reset();
- mUnit = aCopy.mUnit;
- if ((eHTMLUnit_String == mUnit) || (eHTMLUnit_ColorName == mUnit)) {
- if (nsnull != aCopy.mValue.mString) {
- mValue.mString = nsCRT::strdup(aCopy.mValue.mString);
- }
- }
- else if (eHTMLUnit_ISupports == mUnit) {
- mValue.mISupports = aCopy.mValue.mISupports;
- NS_IF_ADDREF(mValue.mISupports);
- }
- else if (eHTMLUnit_Color == mUnit){
- mValue.mColor = aCopy.mValue.mColor;
- }
- else if (eHTMLUnit_Percent == mUnit) {
- mValue.mFloat = aCopy.mValue.mFloat;
- }
- else {
- mValue.mInt = aCopy.mValue.mInt;
- }
+ InitializeFrom(aCopy);
return *this;
}
PRBool nsHTMLValue::operator==(const nsHTMLValue& aOther) const
{
- if (mUnit == aOther.mUnit) {
- if ((eHTMLUnit_String == mUnit) || (eHTMLUnit_ColorName == mUnit)) {
- if (nsnull == mValue.mString) {
- if (nsnull == aOther.mValue.mString) {
- return PR_TRUE;
- }
- }
- else if (nsnull != aOther.mValue.mString) {
- return nsDependentString(mValue.mString).Equals(nsDependentString(aOther.mValue.mString),
- nsCaseInsensitiveStringComparator());
- }
- }
- else if (eHTMLUnit_ISupports == mUnit) {
- return PRBool(mValue.mISupports == aOther.mValue.mISupports);
- }
- else if (eHTMLUnit_Color == mUnit){
- return PRBool(mValue.mColor == aOther.mValue.mColor);
- }
- else if (eHTMLUnit_Percent == mUnit) {
- return PRBool(mValue.mFloat == aOther.mValue.mFloat);
- }
- else {
- return PRBool(mValue.mInt == aOther.mValue.mInt);
- }
+ if (mUnit != aOther.mUnit) {
+ return PR_FALSE;
+ }
+ // Call GetUnitClass() so that we turn StringWithLength into String
+ PRUint32 unitClass = GetUnitClass();
+ switch (unitClass) {
+ case HTMLUNIT_NOSTORE:
+ return PR_TRUE;
+
+ case HTMLUNIT_STRING:
+ if (mValue.mString && aOther.mValue.mString) {
+ return GetDependentString().Equals(aOther.GetDependentString(),
+ nsCaseInsensitiveStringComparator());
+ }
+ // One of them is null. An == check will see if they are both null.
+ return mValue.mString == aOther.mValue.mString;
+
+ case HTMLUNIT_INTEGER:
+ case HTMLUNIT_PIXEL:
+ return mValue.mInt == aOther.mValue.mInt;
+
+ case HTMLUNIT_COLOR:
+ return mValue.mColor == aOther.mValue.mColor;
+
+ case HTMLUNIT_ISUPPORTS:
+ return mValue.mISupports == aOther.mValue.mISupports;
+
+ case HTMLUNIT_PERCENT:
+ return mValue.mFloat == aOther.mValue.mFloat;
+
+ default:
+ NS_WARNING("Unknown unit");
+ return PR_TRUE;
}
- return PR_FALSE;
}
PRUint32 nsHTMLValue::HashValue(void) const
{
- return PRUint32(mUnit) ^
- ((((eHTMLUnit_String == mUnit) || (eHTMLUnit_ColorName == mUnit)) &&
- (nsnull != mValue.mString)) ?
- nsCRT::HashCode(mValue.mString) :
- mValue.mInt);
+ PRUint32 retval;
+ if (GetUnitClass() == HTMLUNIT_STRING) {
+ retval = mValue.mString ? nsCheapStringBufferUtils::HashCode(mValue.mString)
+ : 0;
+ } else {
+ retval = mValue.mInt;
+ }
+ return retval ^ PRUint32(mUnit);
}
void nsHTMLValue::Reset(void)
{
- if ((eHTMLUnit_String == mUnit) || (eHTMLUnit_ColorName == mUnit)) {
- if (nsnull != mValue.mString) {
- nsCRT::free(mValue.mString);
+ if (GetUnitClass() == HTMLUNIT_STRING) {
+ if (mValue.mString) {
+ nsCheapStringBufferUtils::Free(mValue.mString);
}
}
- else if (eHTMLUnit_ISupports == mUnit) {
+ else if (mUnit == eHTMLUnit_ISupports) {
NS_IF_RELEASE(mValue.mISupports);
}
mUnit = eHTMLUnit_Null;
@@ -220,14 +179,12 @@ void nsHTMLValue::Reset(void)
void nsHTMLValue::SetIntValue(PRInt32 aValue, nsHTMLUnit aUnit)
{
Reset();
- NS_ASSERTION((eHTMLUnit_Integer == aUnit) ||
- (eHTMLUnit_Enumerated == aUnit) ||
- (eHTMLUnit_Proportional == aUnit), "not an int value");
- if ((eHTMLUnit_Integer == aUnit) ||
- (eHTMLUnit_Enumerated == aUnit) ||
- (eHTMLUnit_Proportional == aUnit)) {
- mUnit = aUnit;
+ mUnit = aUnit;
+ NS_ASSERTION(GetUnitClass() == HTMLUNIT_INTEGER, "not an int value");
+ if (GetUnitClass() == HTMLUNIT_INTEGER) {
mValue.mInt = aValue;
+ } else {
+ mUnit = eHTMLUnit_Null;
}
}
@@ -245,14 +202,29 @@ void nsHTMLValue::SetPercentValue(float aValue)
mValue.mFloat = aValue;
}
+void nsHTMLValue::SetStringValueInternal(const nsAString& aValue,
+ nsHTMLUnit aUnit)
+{
+ NS_ASSERTION(GetUnitClass() == HTMLUNIT_STRING, "unit not a string unit!");
+ if (GetUnitClass() == HTMLUNIT_STRING) {
+ // Remember the length of the string if necessary
+ if (aValue.IsEmpty()) {
+ mValue.mString = nsnull;
+ } else {
+ nsCheapStringBufferUtils::CopyToBuffer(mValue.mString, aValue);
+ }
+ } else {
+ mUnit = eHTMLUnit_Null;
+ mValue.mString = nsnull;
+ }
+}
+
void nsHTMLValue::SetStringValue(const nsAString& aValue,
nsHTMLUnit aUnit)
{
Reset();
- if ((eHTMLUnit_String == aUnit) || (eHTMLUnit_ColorName == aUnit)) {
- mUnit = aUnit;
- mValue.mString = ToNewUnicode(aValue);
- }
+ mUnit = aUnit;
+ SetStringValueInternal(aValue, aUnit);
}
void nsHTMLValue::SetISupportsValue(nsISupports* aValue)
@@ -279,70 +251,130 @@ void nsHTMLValue::SetEmptyValue(void)
#ifdef DEBUG
void nsHTMLValue::AppendToString(nsAString& aBuffer) const
{
- if (eHTMLUnit_Null == mUnit) {
- return;
- }
-
- if (eHTMLUnit_Empty == mUnit) {
- }
- else if ((eHTMLUnit_String == mUnit) || (eHTMLUnit_ColorName == mUnit)) {
- if (nsnull != mValue.mString) {
+ switch (GetUnitClass()) {
+ case HTMLUNIT_NOSTORE:
+ break;
+ case HTMLUNIT_STRING:
aBuffer.Append(PRUnichar('"'));
- aBuffer.Append(mValue.mString);
+ aBuffer.Append(GetDependentString());
aBuffer.Append(PRUnichar('"'));
- }
- else {
- aBuffer.Append(NS_LITERAL_STRING("null str"));
- }
- }
- else if (eHTMLUnit_ISupports == mUnit) {
- aBuffer.Append(NS_LITERAL_STRING("0x"));
- nsAutoString intStr;
- intStr.AppendInt(NS_PTR_TO_INT32(mValue.mISupports), 16);
- aBuffer.Append(intStr);
- }
- else if (eHTMLUnit_Color == mUnit){
- nsAutoString intStr;
- intStr.Append(NS_LITERAL_STRING("(0x"));
- intStr.AppendInt(NS_GET_R(mValue.mColor), 16);
- intStr.Append(NS_LITERAL_STRING(" 0x"));
- intStr.AppendInt(NS_GET_G(mValue.mColor), 16);
- intStr.Append(NS_LITERAL_STRING(" 0x"));
- intStr.AppendInt(NS_GET_B(mValue.mColor), 16);
- intStr.Append(NS_LITERAL_STRING(" 0x"));
- intStr.AppendInt(NS_GET_A(mValue.mColor), 16);
- intStr.Append(PRUnichar(')'));
+ break;
+ case HTMLUNIT_INTEGER:
+ case HTMLUNIT_PIXEL:
+ {
+ nsAutoString intStr;
+ intStr.AppendInt(mValue.mInt, 10);
+ intStr.Append(NS_LITERAL_STRING("[0x"));
+ intStr.AppendInt(mValue.mInt, 16);
+ intStr.Append(PRUnichar(']'));
- aBuffer.Append(intStr);
- }
- else if (eHTMLUnit_Percent == mUnit) {
- nsAutoString floatStr;
- floatStr.AppendFloat(mValue.mFloat * 100.0f);
- aBuffer.Append(floatStr);
- }
- else {
- nsAutoString intStr;
- intStr.AppendInt(mValue.mInt, 10);
- intStr.Append(NS_LITERAL_STRING("[0x"));
- intStr.AppendInt(mValue.mInt, 16);
- intStr.Append(PRUnichar(']'));
+ aBuffer.Append(intStr);
+ }
+ break;
+ case HTMLUNIT_COLOR:
+ {
+ nsAutoString intStr;
+ intStr.Append(NS_LITERAL_STRING("(0x"));
+ intStr.AppendInt(NS_GET_R(mValue.mColor), 16);
+ intStr.Append(NS_LITERAL_STRING(" 0x"));
+ intStr.AppendInt(NS_GET_G(mValue.mColor), 16);
+ intStr.Append(NS_LITERAL_STRING(" 0x"));
+ intStr.AppendInt(NS_GET_B(mValue.mColor), 16);
+ intStr.Append(NS_LITERAL_STRING(" 0x"));
+ intStr.AppendInt(NS_GET_A(mValue.mColor), 16);
+ intStr.Append(PRUnichar(')'));
- aBuffer.Append(intStr);
+ aBuffer.Append(intStr);
+ }
+ break;
+ case HTMLUNIT_ISUPPORTS:
+ {
+ aBuffer.Append(NS_LITERAL_STRING("0x"));
+ nsAutoString intStr;
+ intStr.AppendInt(NS_PTR_TO_INT32(mValue.mISupports), 16);
+ aBuffer.Append(intStr);
+ }
+ break;
+ case HTMLUNIT_PERCENT:
+ {
+ nsAutoString floatStr;
+ floatStr.AppendFloat(mValue.mFloat * 100.0f);
+ aBuffer.Append(floatStr);
+ }
+ break;
+ default:
+ NS_ERROR("Unknown HTMLValue type!");
}
+ //
+ // Append the type name for types that are ambiguous
+ //
switch (mUnit) {
- case eHTMLUnit_Null: break;
- case eHTMLUnit_Empty: break;
- case eHTMLUnit_String: break;
- case eHTMLUnit_ColorName: break;
- case eHTMLUnit_ISupports: aBuffer.Append(NS_LITERAL_STRING("ptr")); break;
- case eHTMLUnit_Integer: break;
- case eHTMLUnit_Enumerated: aBuffer.Append(NS_LITERAL_STRING("enum")); break;
- case eHTMLUnit_Proportional: aBuffer.Append(NS_LITERAL_STRING("*")); break;
- case eHTMLUnit_Color: aBuffer.Append(NS_LITERAL_STRING("rbga")); break;
- case eHTMLUnit_Percent: aBuffer.Append(NS_LITERAL_STRING("%")); break;
- case eHTMLUnit_Pixel: aBuffer.Append(NS_LITERAL_STRING("px")); break;
+ case eHTMLUnit_Null:
+ aBuffer.Append(NS_LITERAL_STRING("null"));
+ break;
+ case eHTMLUnit_Empty:
+ aBuffer.Append(NS_LITERAL_STRING("empty"));
+ break;
+ case eHTMLUnit_ISupports:
+ aBuffer.Append(NS_LITERAL_STRING("ptr"));
+ break;
+ case eHTMLUnit_Enumerated:
+ aBuffer.Append(NS_LITERAL_STRING("enum"));
+ break;
+ case eHTMLUnit_Proportional:
+ aBuffer.Append(NS_LITERAL_STRING("*"));
+ break;
+ case eHTMLUnit_Color:
+ aBuffer.Append(NS_LITERAL_STRING("rbga"));
+ break;
+ case eHTMLUnit_Percent:
+ aBuffer.Append(NS_LITERAL_STRING("%"));
+ break;
+ case eHTMLUnit_Pixel:
+ aBuffer.Append(NS_LITERAL_STRING("px"));
+ break;
}
aBuffer.Append(PRUnichar(' '));
}
#endif // DEBUG
+
+void
+nsHTMLValue::InitializeFrom(const nsHTMLValue& aCopy)
+{
+ mUnit = aCopy.mUnit;
+ switch (GetUnitClass()) {
+ case HTMLUNIT_NOSTORE:
+ mValue.mString = nsnull;
+ break;
+
+ case HTMLUNIT_STRING:
+ if (aCopy.mValue.mString) {
+ nsCheapStringBufferUtils::Clone(mValue.mString, aCopy.mValue.mString);
+ } else {
+ mValue.mString = nsnull;
+ }
+ break;
+
+ case HTMLUNIT_INTEGER:
+ case HTMLUNIT_PIXEL:
+ mValue.mInt = aCopy.mValue.mInt;
+ break;
+
+ case HTMLUNIT_COLOR:
+ mValue.mColor = aCopy.mValue.mColor;
+ break;
+
+ case HTMLUNIT_ISUPPORTS:
+ mValue.mISupports = aCopy.mValue.mISupports;
+ NS_IF_ADDREF(mValue.mISupports);
+ break;
+
+ case HTMLUNIT_PERCENT:
+ mValue.mFloat = aCopy.mValue.mFloat;
+ break;
+
+ default:
+ NS_ERROR("Unknown HTMLValue type!");
+ }
+}
diff --git a/mozilla/content/base/src/nsHTMLValue.h b/mozilla/content/base/src/nsHTMLValue.h
index 08554bf426b..749b2d7f346 100644
--- a/mozilla/content/base/src/nsHTMLValue.h
+++ b/mozilla/content/base/src/nsHTMLValue.h
@@ -43,20 +43,129 @@
#include "nsString.h"
#include "nsISupports.h"
-enum nsHTMLUnit {
- eHTMLUnit_Null = 0, // (n/a) null unit, value is not specified
- eHTMLUnit_Empty = 1, // (n/a) empty unit, value is not specified
- eHTMLUnit_String = 10, // (nsString) a string value
- eHTMLUnit_ISupports = 20, // (nsISupports*) a ref counted interface
- eHTMLUnit_Integer = 50, // (int) simple value
- eHTMLUnit_Enumerated = 51, // (int) value has enumerated meaning
- eHTMLUnit_Proportional = 52, // (int) value is a relative proportion of some whole
- eHTMLUnit_Color = 80, // (color) an RGBA value
- eHTMLUnit_ColorName = 81, // (nsString/color) a color name value
- eHTMLUnit_Percent = 90, // (float) 1.0 == 100%) value is percentage of something
+#include "nsReadableUtils.h"
+#include "nsCRT.h"
- // Screen relative measure
- eHTMLUnit_Pixel = 600 // (int) screen pixels
+class nsCheapStringBufferUtils {
+public:
+ /**
+ * Get the string pointer
+ * @param aBuf the buffer
+ * @return a pointer to the string
+ */
+ static const PRUnichar* StrPtr(const PRUnichar* aBuf) {
+ NS_ASSERTION(aBuf, "Cannot work on null buffer!");
+ return (const PRUnichar*)( ((const char*)aBuf) + sizeof(PRUint32) );
+ }
+ static PRUnichar* StrPtr(PRUnichar* aBuf) {
+ NS_ASSERTION(aBuf, "Cannot work on null buffer!");
+ return (PRUnichar*)( ((char*)aBuf) + sizeof(PRUint32) );
+ }
+ /**
+ * Get the string length
+ * @param aBuf the buffer
+ * @return the string length
+ */
+ static PRUint32 Length(const PRUnichar* aBuf) {
+ NS_ASSERTION(aBuf, "Cannot work on null buffer!");
+ return *((PRUint32*)aBuf);
+ }
+ /**
+ * Get a DependentString from a buffer
+ *
+ * @param aBuf the buffer to get string from
+ * @return a DependentString representing this string
+ */
+ static nsDependentSingleFragmentSubstring GetDependentString(const PRUnichar* aBuf) {
+ NS_ASSERTION(aBuf, "Cannot work on null buffer!");
+ const PRUnichar* buf = StrPtr(aBuf);
+ return Substring(buf, buf + Length(aBuf));
+ }
+ /**
+ * Construct from an AString
+ * @param aBuf the buffer to copy to
+ * @param aStr the string to construct from
+ */
+ static void CopyToBuffer(PRUnichar*& aBuf, const nsAString& aStr) {
+ PRUint32 len = aStr.Length();
+ aBuf = (PRUnichar*)nsMemory::Alloc(sizeof(PRUint32) +
+ len * sizeof(PRUnichar));
+ *((PRUint32*)aBuf) = len;
+ CopyUnicodeTo(aStr, 0, StrPtr(aBuf), len);
+ }
+ /**
+ * Construct from another nsCheapStringBuffer
+ * @param aBuf the buffer to put into
+ * @param aSrc the buffer to construct from
+ */
+ static void Clone(PRUnichar*& aBuf, const PRUnichar* aSrc) {
+ NS_ASSERTION(aSrc, "Cannot work on null buffer!");
+ aBuf = (PRUnichar*)nsMemory::Clone(aSrc, sizeof(PRUint32) +
+ Length(aSrc) * sizeof(PRUnichar));
+ }
+ /**
+ * Free the memory for the buf
+ * @param aBuf the buffer to free
+ */
+ static void Free(PRUnichar* aBuf) {
+ NS_ASSERTION(aBuf, "Cannot work on null buffer!");
+ nsMemory::Free(aBuf);
+ }
+ /**
+ * Get a hashcode for the buffer
+ * @param aBuf the buffer
+ * @return the hashcode
+ */
+ static PRUint32 HashCode(const PRUnichar* aBuf) {
+ NS_ASSERTION(aBuf, "Cannot work on null buffer!");
+ return nsCRT::BufferHashCode((char*)StrPtr(aBuf),
+ Length(aBuf)*sizeof(PRUnichar));
+ }
+};
+
+//
+// nsHTMLUnit is two bytes: the class of type, and a specifier to distinguish
+// between different things stored as the same type. Doing
+// mUnit & HTMLUNIT_CLASS_MASK should give you the class of type.
+//
+#define HTMLUNIT_NOSTORE 0x0000
+#define HTMLUNIT_STRING 0x0100
+#define HTMLUNIT_INTEGER 0x0200
+#define HTMLUNIT_PIXEL 0x0400
+#define HTMLUNIT_COLOR 0x0800
+#define HTMLUNIT_ISUPPORTS 0x1000
+#define HTMLUNIT_PERCENT 0x2000
+#define HTMLUNIT_CLASS_MASK 0xff00
+
+enum nsHTMLUnit {
+ // null, value is not specified: 0x0000
+ eHTMLUnit_Null = HTMLUNIT_NOSTORE,
+ // empty, value is not specified: 0x0001
+ eHTMLUnit_Empty = HTMLUNIT_NOSTORE | 1,
+
+ // a string value
+ eHTMLUnit_String = HTMLUNIT_STRING,
+ // a color name value
+ eHTMLUnit_ColorName = HTMLUNIT_STRING | 1,
+
+ // a simple int value
+ eHTMLUnit_Integer = HTMLUNIT_INTEGER,
+ // value has enumerated meaning
+ eHTMLUnit_Enumerated = HTMLUNIT_INTEGER | 1,
+ // value is a relative proportion of some whole
+ eHTMLUnit_Proportional = HTMLUNIT_INTEGER | 2,
+
+ // screen pixels (screen relative measure)
+ eHTMLUnit_Pixel = HTMLUNIT_PIXEL,
+
+ // an RGBA value
+ eHTMLUnit_Color = HTMLUNIT_COLOR,
+
+ // (nsISupports*) a ref counted interface
+ eHTMLUnit_ISupports = HTMLUNIT_ISUPPORTS,
+
+ // (1.0 == 100%) value is percentage of something
+ eHTMLUnit_Percent = HTMLUNIT_PERCENT
};
/**
@@ -81,14 +190,22 @@ public:
PRBool operator!=(const nsHTMLValue& aOther) const;
PRUint32 HashValue(void) const;
- nsHTMLUnit GetUnit(void) const { return mUnit; }
- PRInt32 GetIntValue(void) const;
- PRInt32 GetPixelValue(void) const;
- float GetPercentValue(void) const;
- nsAString& GetStringValue(nsAString& aBuffer) const;
- nsISupports* GetISupportsValue(void) const;
- nscolor GetColorValue(void) const;
+ /**
+ * Get the unit of this HTMLValue
+ * @return the unit of this HTMLValue
+ */
+ nsHTMLUnit GetUnit(void) const { return (nsHTMLUnit)mUnit; }
+ PRInt32 GetIntValue(void) const;
+ PRInt32 GetPixelValue(void) const;
+ float GetPercentValue(void) const;
+ nsAString& GetStringValue(nsAString& aBuffer) const;
+ nsISupports* GetISupportsValue(void) const;
+ nscolor GetColorValue(void) const;
+
+ /**
+ * Reset the string to null type, freeing things in the process if necessary.
+ */
void Reset(void);
void SetIntValue(PRInt32 aValue, nsHTMLUnit aUnit);
void SetPixelValue(PRInt32 aValue);
@@ -103,34 +220,85 @@ public:
#endif
protected:
- nsHTMLUnit mUnit;
+ /**
+ * The unit of the value
+ * @see nsHTMLUnit
+ */
+ PRUint32 mUnit;
+ /**
+ * The actual value. Please to not be adding more-than-4-byte things to this
+ * union.
+ */
union {
+ /** Int. */
PRInt32 mInt;
+ /** Float. */
float mFloat;
+ /** String. First 4 bytes are the length, non-null-terminated. */
PRUnichar* mString;
+ /** ISupports. Strong reference. */
nsISupports* mISupports;
+ /** Color. */
nscolor mColor;
- } mValue;
+ } mValue;
+private:
+ /**
+ * Copy into this HTMLValue from aCopy. Please be aware that if this is an
+ * existing HTMLValue and you do not call Reset(), this will leak.
+ * @param aCopy the value to copy
+ */
+ void InitializeFrom(const nsHTMLValue& aCopy);
+ /**
+ * Helper to set string value (checks for embedded nulls or length); verifies
+ * that aUnit is a string type as well.
+ * @param aValue the value to set
+ * @param aUnit the unit to set
+ */
+ void SetStringValueInternal(const nsAString& aValue, nsHTMLUnit aUnit);
+ /**
+ * Get a DependentString from mValue.mString (if the string is stored with
+ * length, passes that information to the DependentString). Do not call this
+ * if mValue.mString is null.
+ *
+ * @return a DependentString representing this string
+ */
+ nsDependentSingleFragmentSubstring GetDependentString() const;
+ /**
+ * Get the unit class (HTMLUNIT_*)
+ * @return the unit class
+ */
+ PRUint32 GetUnitClass() const { return mUnit & HTMLUNIT_CLASS_MASK; }
};
+inline nsDependentSingleFragmentSubstring nsHTMLValue::GetDependentString() const
+{
+ NS_ASSERTION(GetUnitClass() == HTMLUNIT_STRING,
+ "Some dork called GetDependentString() on a non-string!");
+ static const PRUnichar blankStr[] = { '\0' };
+ return mValue.mString
+ ? nsCheapStringBufferUtils::GetDependentString(mValue.mString)
+ : Substring(blankStr, blankStr);
+}
+
inline PRInt32 nsHTMLValue::GetIntValue(void) const
{
- NS_ASSERTION((mUnit == eHTMLUnit_String) ||
- (mUnit == eHTMLUnit_Integer) ||
- (mUnit == eHTMLUnit_Enumerated) ||
- (mUnit == eHTMLUnit_Proportional), "not an int value");
- if ((mUnit == eHTMLUnit_Integer) ||
- (mUnit == eHTMLUnit_Enumerated) ||
- (mUnit == eHTMLUnit_Proportional)) {
+ NS_ASSERTION(GetUnitClass() == HTMLUNIT_STRING ||
+ GetUnitClass() == HTMLUNIT_INTEGER,
+ "not an int value");
+ PRUint32 unitClass = GetUnitClass();
+ if (unitClass == HTMLUNIT_INTEGER) {
return mValue.mInt;
}
- else if (mUnit == eHTMLUnit_String) {
+
+ if (unitClass == HTMLUNIT_STRING) {
if (mValue.mString) {
PRInt32 err=0;
- nsAutoString str(mValue.mString); // XXX copy. new string APIs will make this better, right?
+ // XXX this copies. new string APIs will make this better, right?
+ nsAutoString str(GetDependentString());
return str.ToInteger(&err);
}
}
+
return 0;
}
@@ -154,12 +322,12 @@ inline float nsHTMLValue::GetPercentValue(void) const
inline nsAString& nsHTMLValue::GetStringValue(nsAString& aBuffer) const
{
- NS_ASSERTION((mUnit == eHTMLUnit_String) || (mUnit == eHTMLUnit_ColorName) ||
- (mUnit == eHTMLUnit_Null), "not a string value");
- aBuffer.SetLength(0);
- if (((mUnit == eHTMLUnit_String) || (mUnit == eHTMLUnit_ColorName)) &&
- (nsnull != mValue.mString)) {
- aBuffer.Append(mValue.mString);
+ NS_ASSERTION(GetUnitClass() == HTMLUNIT_STRING || mUnit == eHTMLUnit_Null,
+ "not a string value");
+ if (GetUnitClass() == HTMLUNIT_STRING && mValue.mString) {
+ aBuffer = GetDependentString();
+ } else {
+ aBuffer.Truncate();
}
return aBuffer;
}
@@ -182,9 +350,9 @@ inline nscolor nsHTMLValue::GetColorValue(void) const
if (mUnit == eHTMLUnit_Color) {
return mValue.mColor;
}
- if ((mUnit == eHTMLUnit_ColorName) && (mValue.mString)) {
+ if (mUnit == eHTMLUnit_ColorName) {
nscolor color;
- if (NS_ColorNameToRGB(nsAutoString(mValue.mString), &color)) {
+ if (NS_ColorNameToRGB(GetDependentString(), &color)) {
return color;
}
}
diff --git a/mozilla/content/shared/public/nsHTMLValue.h b/mozilla/content/shared/public/nsHTMLValue.h
index 08554bf426b..749b2d7f346 100644
--- a/mozilla/content/shared/public/nsHTMLValue.h
+++ b/mozilla/content/shared/public/nsHTMLValue.h
@@ -43,20 +43,129 @@
#include "nsString.h"
#include "nsISupports.h"
-enum nsHTMLUnit {
- eHTMLUnit_Null = 0, // (n/a) null unit, value is not specified
- eHTMLUnit_Empty = 1, // (n/a) empty unit, value is not specified
- eHTMLUnit_String = 10, // (nsString) a string value
- eHTMLUnit_ISupports = 20, // (nsISupports*) a ref counted interface
- eHTMLUnit_Integer = 50, // (int) simple value
- eHTMLUnit_Enumerated = 51, // (int) value has enumerated meaning
- eHTMLUnit_Proportional = 52, // (int) value is a relative proportion of some whole
- eHTMLUnit_Color = 80, // (color) an RGBA value
- eHTMLUnit_ColorName = 81, // (nsString/color) a color name value
- eHTMLUnit_Percent = 90, // (float) 1.0 == 100%) value is percentage of something
+#include "nsReadableUtils.h"
+#include "nsCRT.h"
- // Screen relative measure
- eHTMLUnit_Pixel = 600 // (int) screen pixels
+class nsCheapStringBufferUtils {
+public:
+ /**
+ * Get the string pointer
+ * @param aBuf the buffer
+ * @return a pointer to the string
+ */
+ static const PRUnichar* StrPtr(const PRUnichar* aBuf) {
+ NS_ASSERTION(aBuf, "Cannot work on null buffer!");
+ return (const PRUnichar*)( ((const char*)aBuf) + sizeof(PRUint32) );
+ }
+ static PRUnichar* StrPtr(PRUnichar* aBuf) {
+ NS_ASSERTION(aBuf, "Cannot work on null buffer!");
+ return (PRUnichar*)( ((char*)aBuf) + sizeof(PRUint32) );
+ }
+ /**
+ * Get the string length
+ * @param aBuf the buffer
+ * @return the string length
+ */
+ static PRUint32 Length(const PRUnichar* aBuf) {
+ NS_ASSERTION(aBuf, "Cannot work on null buffer!");
+ return *((PRUint32*)aBuf);
+ }
+ /**
+ * Get a DependentString from a buffer
+ *
+ * @param aBuf the buffer to get string from
+ * @return a DependentString representing this string
+ */
+ static nsDependentSingleFragmentSubstring GetDependentString(const PRUnichar* aBuf) {
+ NS_ASSERTION(aBuf, "Cannot work on null buffer!");
+ const PRUnichar* buf = StrPtr(aBuf);
+ return Substring(buf, buf + Length(aBuf));
+ }
+ /**
+ * Construct from an AString
+ * @param aBuf the buffer to copy to
+ * @param aStr the string to construct from
+ */
+ static void CopyToBuffer(PRUnichar*& aBuf, const nsAString& aStr) {
+ PRUint32 len = aStr.Length();
+ aBuf = (PRUnichar*)nsMemory::Alloc(sizeof(PRUint32) +
+ len * sizeof(PRUnichar));
+ *((PRUint32*)aBuf) = len;
+ CopyUnicodeTo(aStr, 0, StrPtr(aBuf), len);
+ }
+ /**
+ * Construct from another nsCheapStringBuffer
+ * @param aBuf the buffer to put into
+ * @param aSrc the buffer to construct from
+ */
+ static void Clone(PRUnichar*& aBuf, const PRUnichar* aSrc) {
+ NS_ASSERTION(aSrc, "Cannot work on null buffer!");
+ aBuf = (PRUnichar*)nsMemory::Clone(aSrc, sizeof(PRUint32) +
+ Length(aSrc) * sizeof(PRUnichar));
+ }
+ /**
+ * Free the memory for the buf
+ * @param aBuf the buffer to free
+ */
+ static void Free(PRUnichar* aBuf) {
+ NS_ASSERTION(aBuf, "Cannot work on null buffer!");
+ nsMemory::Free(aBuf);
+ }
+ /**
+ * Get a hashcode for the buffer
+ * @param aBuf the buffer
+ * @return the hashcode
+ */
+ static PRUint32 HashCode(const PRUnichar* aBuf) {
+ NS_ASSERTION(aBuf, "Cannot work on null buffer!");
+ return nsCRT::BufferHashCode((char*)StrPtr(aBuf),
+ Length(aBuf)*sizeof(PRUnichar));
+ }
+};
+
+//
+// nsHTMLUnit is two bytes: the class of type, and a specifier to distinguish
+// between different things stored as the same type. Doing
+// mUnit & HTMLUNIT_CLASS_MASK should give you the class of type.
+//
+#define HTMLUNIT_NOSTORE 0x0000
+#define HTMLUNIT_STRING 0x0100
+#define HTMLUNIT_INTEGER 0x0200
+#define HTMLUNIT_PIXEL 0x0400
+#define HTMLUNIT_COLOR 0x0800
+#define HTMLUNIT_ISUPPORTS 0x1000
+#define HTMLUNIT_PERCENT 0x2000
+#define HTMLUNIT_CLASS_MASK 0xff00
+
+enum nsHTMLUnit {
+ // null, value is not specified: 0x0000
+ eHTMLUnit_Null = HTMLUNIT_NOSTORE,
+ // empty, value is not specified: 0x0001
+ eHTMLUnit_Empty = HTMLUNIT_NOSTORE | 1,
+
+ // a string value
+ eHTMLUnit_String = HTMLUNIT_STRING,
+ // a color name value
+ eHTMLUnit_ColorName = HTMLUNIT_STRING | 1,
+
+ // a simple int value
+ eHTMLUnit_Integer = HTMLUNIT_INTEGER,
+ // value has enumerated meaning
+ eHTMLUnit_Enumerated = HTMLUNIT_INTEGER | 1,
+ // value is a relative proportion of some whole
+ eHTMLUnit_Proportional = HTMLUNIT_INTEGER | 2,
+
+ // screen pixels (screen relative measure)
+ eHTMLUnit_Pixel = HTMLUNIT_PIXEL,
+
+ // an RGBA value
+ eHTMLUnit_Color = HTMLUNIT_COLOR,
+
+ // (nsISupports*) a ref counted interface
+ eHTMLUnit_ISupports = HTMLUNIT_ISUPPORTS,
+
+ // (1.0 == 100%) value is percentage of something
+ eHTMLUnit_Percent = HTMLUNIT_PERCENT
};
/**
@@ -81,14 +190,22 @@ public:
PRBool operator!=(const nsHTMLValue& aOther) const;
PRUint32 HashValue(void) const;
- nsHTMLUnit GetUnit(void) const { return mUnit; }
- PRInt32 GetIntValue(void) const;
- PRInt32 GetPixelValue(void) const;
- float GetPercentValue(void) const;
- nsAString& GetStringValue(nsAString& aBuffer) const;
- nsISupports* GetISupportsValue(void) const;
- nscolor GetColorValue(void) const;
+ /**
+ * Get the unit of this HTMLValue
+ * @return the unit of this HTMLValue
+ */
+ nsHTMLUnit GetUnit(void) const { return (nsHTMLUnit)mUnit; }
+ PRInt32 GetIntValue(void) const;
+ PRInt32 GetPixelValue(void) const;
+ float GetPercentValue(void) const;
+ nsAString& GetStringValue(nsAString& aBuffer) const;
+ nsISupports* GetISupportsValue(void) const;
+ nscolor GetColorValue(void) const;
+
+ /**
+ * Reset the string to null type, freeing things in the process if necessary.
+ */
void Reset(void);
void SetIntValue(PRInt32 aValue, nsHTMLUnit aUnit);
void SetPixelValue(PRInt32 aValue);
@@ -103,34 +220,85 @@ public:
#endif
protected:
- nsHTMLUnit mUnit;
+ /**
+ * The unit of the value
+ * @see nsHTMLUnit
+ */
+ PRUint32 mUnit;
+ /**
+ * The actual value. Please to not be adding more-than-4-byte things to this
+ * union.
+ */
union {
+ /** Int. */
PRInt32 mInt;
+ /** Float. */
float mFloat;
+ /** String. First 4 bytes are the length, non-null-terminated. */
PRUnichar* mString;
+ /** ISupports. Strong reference. */
nsISupports* mISupports;
+ /** Color. */
nscolor mColor;
- } mValue;
+ } mValue;
+private:
+ /**
+ * Copy into this HTMLValue from aCopy. Please be aware that if this is an
+ * existing HTMLValue and you do not call Reset(), this will leak.
+ * @param aCopy the value to copy
+ */
+ void InitializeFrom(const nsHTMLValue& aCopy);
+ /**
+ * Helper to set string value (checks for embedded nulls or length); verifies
+ * that aUnit is a string type as well.
+ * @param aValue the value to set
+ * @param aUnit the unit to set
+ */
+ void SetStringValueInternal(const nsAString& aValue, nsHTMLUnit aUnit);
+ /**
+ * Get a DependentString from mValue.mString (if the string is stored with
+ * length, passes that information to the DependentString). Do not call this
+ * if mValue.mString is null.
+ *
+ * @return a DependentString representing this string
+ */
+ nsDependentSingleFragmentSubstring GetDependentString() const;
+ /**
+ * Get the unit class (HTMLUNIT_*)
+ * @return the unit class
+ */
+ PRUint32 GetUnitClass() const { return mUnit & HTMLUNIT_CLASS_MASK; }
};
+inline nsDependentSingleFragmentSubstring nsHTMLValue::GetDependentString() const
+{
+ NS_ASSERTION(GetUnitClass() == HTMLUNIT_STRING,
+ "Some dork called GetDependentString() on a non-string!");
+ static const PRUnichar blankStr[] = { '\0' };
+ return mValue.mString
+ ? nsCheapStringBufferUtils::GetDependentString(mValue.mString)
+ : Substring(blankStr, blankStr);
+}
+
inline PRInt32 nsHTMLValue::GetIntValue(void) const
{
- NS_ASSERTION((mUnit == eHTMLUnit_String) ||
- (mUnit == eHTMLUnit_Integer) ||
- (mUnit == eHTMLUnit_Enumerated) ||
- (mUnit == eHTMLUnit_Proportional), "not an int value");
- if ((mUnit == eHTMLUnit_Integer) ||
- (mUnit == eHTMLUnit_Enumerated) ||
- (mUnit == eHTMLUnit_Proportional)) {
+ NS_ASSERTION(GetUnitClass() == HTMLUNIT_STRING ||
+ GetUnitClass() == HTMLUNIT_INTEGER,
+ "not an int value");
+ PRUint32 unitClass = GetUnitClass();
+ if (unitClass == HTMLUNIT_INTEGER) {
return mValue.mInt;
}
- else if (mUnit == eHTMLUnit_String) {
+
+ if (unitClass == HTMLUNIT_STRING) {
if (mValue.mString) {
PRInt32 err=0;
- nsAutoString str(mValue.mString); // XXX copy. new string APIs will make this better, right?
+ // XXX this copies. new string APIs will make this better, right?
+ nsAutoString str(GetDependentString());
return str.ToInteger(&err);
}
}
+
return 0;
}
@@ -154,12 +322,12 @@ inline float nsHTMLValue::GetPercentValue(void) const
inline nsAString& nsHTMLValue::GetStringValue(nsAString& aBuffer) const
{
- NS_ASSERTION((mUnit == eHTMLUnit_String) || (mUnit == eHTMLUnit_ColorName) ||
- (mUnit == eHTMLUnit_Null), "not a string value");
- aBuffer.SetLength(0);
- if (((mUnit == eHTMLUnit_String) || (mUnit == eHTMLUnit_ColorName)) &&
- (nsnull != mValue.mString)) {
- aBuffer.Append(mValue.mString);
+ NS_ASSERTION(GetUnitClass() == HTMLUNIT_STRING || mUnit == eHTMLUnit_Null,
+ "not a string value");
+ if (GetUnitClass() == HTMLUNIT_STRING && mValue.mString) {
+ aBuffer = GetDependentString();
+ } else {
+ aBuffer.Truncate();
}
return aBuffer;
}
@@ -182,9 +350,9 @@ inline nscolor nsHTMLValue::GetColorValue(void) const
if (mUnit == eHTMLUnit_Color) {
return mValue.mColor;
}
- if ((mUnit == eHTMLUnit_ColorName) && (mValue.mString)) {
+ if (mUnit == eHTMLUnit_ColorName) {
nscolor color;
- if (NS_ColorNameToRGB(nsAutoString(mValue.mString), &color)) {
+ if (NS_ColorNameToRGB(GetDependentString(), &color)) {
return color;
}
}
diff --git a/mozilla/content/shared/src/nsHTMLValue.cpp b/mozilla/content/shared/src/nsHTMLValue.cpp
index a52ad27af79..1071667d728 100644
--- a/mozilla/content/shared/src/nsHTMLValue.cpp
+++ b/mozilla/content/shared/src/nsHTMLValue.cpp
@@ -42,12 +42,13 @@
#include "nsReadableUtils.h"
#include "nsUnicharUtils.h"
#include "nsCRT.h"
+#include "nsMemory.h"
nsHTMLValue::nsHTMLValue(nsHTMLUnit aUnit)
: mUnit(aUnit)
{
- NS_ASSERTION((aUnit <= eHTMLUnit_Empty), "not a valueless unit");
- if (aUnit > eHTMLUnit_Empty) {
+ NS_ASSERTION(GetUnitClass() == HTMLUNIT_NOSTORE, "not a valueless unit");
+ if (GetUnitClass() != HTMLUNIT_NOSTORE) {
mUnit = eHTMLUnit_Null;
}
mValue.mString = nsnull;
@@ -56,19 +57,14 @@ nsHTMLValue::nsHTMLValue(nsHTMLUnit aUnit)
nsHTMLValue::nsHTMLValue(PRInt32 aValue, nsHTMLUnit aUnit)
: mUnit(aUnit)
{
- NS_ASSERTION((eHTMLUnit_Integer == aUnit) ||
- (eHTMLUnit_Enumerated == aUnit) ||
- (eHTMLUnit_Proportional == aUnit) ||
- (eHTMLUnit_Pixel == aUnit), "not an integer value");
- if ((eHTMLUnit_Integer == aUnit) ||
- (eHTMLUnit_Enumerated == aUnit) ||
- (eHTMLUnit_Proportional == aUnit) ||
- (eHTMLUnit_Pixel == aUnit)) {
+ NS_ASSERTION(GetUnitClass() == HTMLUNIT_INTEGER ||
+ GetUnitClass() == HTMLUNIT_PIXEL, "unit not an integer unit");
+ if (GetUnitClass() == HTMLUNIT_INTEGER ||
+ GetUnitClass() == HTMLUNIT_PIXEL) {
mValue.mInt = aValue;
- }
- else {
+ } else {
mUnit = eHTMLUnit_Null;
- mValue.mInt = 0;
+ mValue.mString = nsnull;
}
}
@@ -81,16 +77,7 @@ nsHTMLValue::nsHTMLValue(float aValue)
nsHTMLValue::nsHTMLValue(const nsAString& aValue, nsHTMLUnit aUnit)
: mUnit(aUnit)
{
- NS_ASSERTION((eHTMLUnit_String == aUnit) ||
- (eHTMLUnit_ColorName == aUnit), "not a string value");
- if ((eHTMLUnit_String == aUnit) ||
- (eHTMLUnit_ColorName == aUnit)) {
- mValue.mString = ToNewUnicode(aValue);
- }
- else {
- mUnit = eHTMLUnit_Null;
- mValue.mInt = 0;
- }
+ SetStringValueInternal(aValue, aUnit);
}
nsHTMLValue::nsHTMLValue(nsISupports* aValue)
@@ -107,29 +94,8 @@ nsHTMLValue::nsHTMLValue(nscolor aValue)
}
nsHTMLValue::nsHTMLValue(const nsHTMLValue& aCopy)
- : mUnit(aCopy.mUnit)
{
- if ((eHTMLUnit_String == mUnit) || (eHTMLUnit_ColorName == mUnit)) {
- if (nsnull != aCopy.mValue.mString) {
- mValue.mString = nsCRT::strdup(aCopy.mValue.mString);
- }
- else {
- mValue.mString = nsnull;
- }
- }
- else if (eHTMLUnit_ISupports == mUnit) {
- mValue.mISupports = aCopy.mValue.mISupports;
- NS_IF_ADDREF(mValue.mISupports);
- }
- else if (eHTMLUnit_Color == mUnit){
- mValue.mColor = aCopy.mValue.mColor;
- }
- else if (eHTMLUnit_Percent == mUnit) {
- mValue.mFloat = aCopy.mValue.mFloat;
- }
- else {
- mValue.mInt = aCopy.mValue.mInt;
- }
+ InitializeFrom(aCopy);
}
nsHTMLValue::~nsHTMLValue(void)
@@ -140,76 +106,69 @@ nsHTMLValue::~nsHTMLValue(void)
nsHTMLValue& nsHTMLValue::operator=(const nsHTMLValue& aCopy)
{
Reset();
- mUnit = aCopy.mUnit;
- if ((eHTMLUnit_String == mUnit) || (eHTMLUnit_ColorName == mUnit)) {
- if (nsnull != aCopy.mValue.mString) {
- mValue.mString = nsCRT::strdup(aCopy.mValue.mString);
- }
- }
- else if (eHTMLUnit_ISupports == mUnit) {
- mValue.mISupports = aCopy.mValue.mISupports;
- NS_IF_ADDREF(mValue.mISupports);
- }
- else if (eHTMLUnit_Color == mUnit){
- mValue.mColor = aCopy.mValue.mColor;
- }
- else if (eHTMLUnit_Percent == mUnit) {
- mValue.mFloat = aCopy.mValue.mFloat;
- }
- else {
- mValue.mInt = aCopy.mValue.mInt;
- }
+ InitializeFrom(aCopy);
return *this;
}
PRBool nsHTMLValue::operator==(const nsHTMLValue& aOther) const
{
- if (mUnit == aOther.mUnit) {
- if ((eHTMLUnit_String == mUnit) || (eHTMLUnit_ColorName == mUnit)) {
- if (nsnull == mValue.mString) {
- if (nsnull == aOther.mValue.mString) {
- return PR_TRUE;
- }
- }
- else if (nsnull != aOther.mValue.mString) {
- return nsDependentString(mValue.mString).Equals(nsDependentString(aOther.mValue.mString),
- nsCaseInsensitiveStringComparator());
- }
- }
- else if (eHTMLUnit_ISupports == mUnit) {
- return PRBool(mValue.mISupports == aOther.mValue.mISupports);
- }
- else if (eHTMLUnit_Color == mUnit){
- return PRBool(mValue.mColor == aOther.mValue.mColor);
- }
- else if (eHTMLUnit_Percent == mUnit) {
- return PRBool(mValue.mFloat == aOther.mValue.mFloat);
- }
- else {
- return PRBool(mValue.mInt == aOther.mValue.mInt);
- }
+ if (mUnit != aOther.mUnit) {
+ return PR_FALSE;
+ }
+ // Call GetUnitClass() so that we turn StringWithLength into String
+ PRUint32 unitClass = GetUnitClass();
+ switch (unitClass) {
+ case HTMLUNIT_NOSTORE:
+ return PR_TRUE;
+
+ case HTMLUNIT_STRING:
+ if (mValue.mString && aOther.mValue.mString) {
+ return GetDependentString().Equals(aOther.GetDependentString(),
+ nsCaseInsensitiveStringComparator());
+ }
+ // One of them is null. An == check will see if they are both null.
+ return mValue.mString == aOther.mValue.mString;
+
+ case HTMLUNIT_INTEGER:
+ case HTMLUNIT_PIXEL:
+ return mValue.mInt == aOther.mValue.mInt;
+
+ case HTMLUNIT_COLOR:
+ return mValue.mColor == aOther.mValue.mColor;
+
+ case HTMLUNIT_ISUPPORTS:
+ return mValue.mISupports == aOther.mValue.mISupports;
+
+ case HTMLUNIT_PERCENT:
+ return mValue.mFloat == aOther.mValue.mFloat;
+
+ default:
+ NS_WARNING("Unknown unit");
+ return PR_TRUE;
}
- return PR_FALSE;
}
PRUint32 nsHTMLValue::HashValue(void) const
{
- return PRUint32(mUnit) ^
- ((((eHTMLUnit_String == mUnit) || (eHTMLUnit_ColorName == mUnit)) &&
- (nsnull != mValue.mString)) ?
- nsCRT::HashCode(mValue.mString) :
- mValue.mInt);
+ PRUint32 retval;
+ if (GetUnitClass() == HTMLUNIT_STRING) {
+ retval = mValue.mString ? nsCheapStringBufferUtils::HashCode(mValue.mString)
+ : 0;
+ } else {
+ retval = mValue.mInt;
+ }
+ return retval ^ PRUint32(mUnit);
}
void nsHTMLValue::Reset(void)
{
- if ((eHTMLUnit_String == mUnit) || (eHTMLUnit_ColorName == mUnit)) {
- if (nsnull != mValue.mString) {
- nsCRT::free(mValue.mString);
+ if (GetUnitClass() == HTMLUNIT_STRING) {
+ if (mValue.mString) {
+ nsCheapStringBufferUtils::Free(mValue.mString);
}
}
- else if (eHTMLUnit_ISupports == mUnit) {
+ else if (mUnit == eHTMLUnit_ISupports) {
NS_IF_RELEASE(mValue.mISupports);
}
mUnit = eHTMLUnit_Null;
@@ -220,14 +179,12 @@ void nsHTMLValue::Reset(void)
void nsHTMLValue::SetIntValue(PRInt32 aValue, nsHTMLUnit aUnit)
{
Reset();
- NS_ASSERTION((eHTMLUnit_Integer == aUnit) ||
- (eHTMLUnit_Enumerated == aUnit) ||
- (eHTMLUnit_Proportional == aUnit), "not an int value");
- if ((eHTMLUnit_Integer == aUnit) ||
- (eHTMLUnit_Enumerated == aUnit) ||
- (eHTMLUnit_Proportional == aUnit)) {
- mUnit = aUnit;
+ mUnit = aUnit;
+ NS_ASSERTION(GetUnitClass() == HTMLUNIT_INTEGER, "not an int value");
+ if (GetUnitClass() == HTMLUNIT_INTEGER) {
mValue.mInt = aValue;
+ } else {
+ mUnit = eHTMLUnit_Null;
}
}
@@ -245,14 +202,29 @@ void nsHTMLValue::SetPercentValue(float aValue)
mValue.mFloat = aValue;
}
+void nsHTMLValue::SetStringValueInternal(const nsAString& aValue,
+ nsHTMLUnit aUnit)
+{
+ NS_ASSERTION(GetUnitClass() == HTMLUNIT_STRING, "unit not a string unit!");
+ if (GetUnitClass() == HTMLUNIT_STRING) {
+ // Remember the length of the string if necessary
+ if (aValue.IsEmpty()) {
+ mValue.mString = nsnull;
+ } else {
+ nsCheapStringBufferUtils::CopyToBuffer(mValue.mString, aValue);
+ }
+ } else {
+ mUnit = eHTMLUnit_Null;
+ mValue.mString = nsnull;
+ }
+}
+
void nsHTMLValue::SetStringValue(const nsAString& aValue,
nsHTMLUnit aUnit)
{
Reset();
- if ((eHTMLUnit_String == aUnit) || (eHTMLUnit_ColorName == aUnit)) {
- mUnit = aUnit;
- mValue.mString = ToNewUnicode(aValue);
- }
+ mUnit = aUnit;
+ SetStringValueInternal(aValue, aUnit);
}
void nsHTMLValue::SetISupportsValue(nsISupports* aValue)
@@ -279,70 +251,130 @@ void nsHTMLValue::SetEmptyValue(void)
#ifdef DEBUG
void nsHTMLValue::AppendToString(nsAString& aBuffer) const
{
- if (eHTMLUnit_Null == mUnit) {
- return;
- }
-
- if (eHTMLUnit_Empty == mUnit) {
- }
- else if ((eHTMLUnit_String == mUnit) || (eHTMLUnit_ColorName == mUnit)) {
- if (nsnull != mValue.mString) {
+ switch (GetUnitClass()) {
+ case HTMLUNIT_NOSTORE:
+ break;
+ case HTMLUNIT_STRING:
aBuffer.Append(PRUnichar('"'));
- aBuffer.Append(mValue.mString);
+ aBuffer.Append(GetDependentString());
aBuffer.Append(PRUnichar('"'));
- }
- else {
- aBuffer.Append(NS_LITERAL_STRING("null str"));
- }
- }
- else if (eHTMLUnit_ISupports == mUnit) {
- aBuffer.Append(NS_LITERAL_STRING("0x"));
- nsAutoString intStr;
- intStr.AppendInt(NS_PTR_TO_INT32(mValue.mISupports), 16);
- aBuffer.Append(intStr);
- }
- else if (eHTMLUnit_Color == mUnit){
- nsAutoString intStr;
- intStr.Append(NS_LITERAL_STRING("(0x"));
- intStr.AppendInt(NS_GET_R(mValue.mColor), 16);
- intStr.Append(NS_LITERAL_STRING(" 0x"));
- intStr.AppendInt(NS_GET_G(mValue.mColor), 16);
- intStr.Append(NS_LITERAL_STRING(" 0x"));
- intStr.AppendInt(NS_GET_B(mValue.mColor), 16);
- intStr.Append(NS_LITERAL_STRING(" 0x"));
- intStr.AppendInt(NS_GET_A(mValue.mColor), 16);
- intStr.Append(PRUnichar(')'));
+ break;
+ case HTMLUNIT_INTEGER:
+ case HTMLUNIT_PIXEL:
+ {
+ nsAutoString intStr;
+ intStr.AppendInt(mValue.mInt, 10);
+ intStr.Append(NS_LITERAL_STRING("[0x"));
+ intStr.AppendInt(mValue.mInt, 16);
+ intStr.Append(PRUnichar(']'));
- aBuffer.Append(intStr);
- }
- else if (eHTMLUnit_Percent == mUnit) {
- nsAutoString floatStr;
- floatStr.AppendFloat(mValue.mFloat * 100.0f);
- aBuffer.Append(floatStr);
- }
- else {
- nsAutoString intStr;
- intStr.AppendInt(mValue.mInt, 10);
- intStr.Append(NS_LITERAL_STRING("[0x"));
- intStr.AppendInt(mValue.mInt, 16);
- intStr.Append(PRUnichar(']'));
+ aBuffer.Append(intStr);
+ }
+ break;
+ case HTMLUNIT_COLOR:
+ {
+ nsAutoString intStr;
+ intStr.Append(NS_LITERAL_STRING("(0x"));
+ intStr.AppendInt(NS_GET_R(mValue.mColor), 16);
+ intStr.Append(NS_LITERAL_STRING(" 0x"));
+ intStr.AppendInt(NS_GET_G(mValue.mColor), 16);
+ intStr.Append(NS_LITERAL_STRING(" 0x"));
+ intStr.AppendInt(NS_GET_B(mValue.mColor), 16);
+ intStr.Append(NS_LITERAL_STRING(" 0x"));
+ intStr.AppendInt(NS_GET_A(mValue.mColor), 16);
+ intStr.Append(PRUnichar(')'));
- aBuffer.Append(intStr);
+ aBuffer.Append(intStr);
+ }
+ break;
+ case HTMLUNIT_ISUPPORTS:
+ {
+ aBuffer.Append(NS_LITERAL_STRING("0x"));
+ nsAutoString intStr;
+ intStr.AppendInt(NS_PTR_TO_INT32(mValue.mISupports), 16);
+ aBuffer.Append(intStr);
+ }
+ break;
+ case HTMLUNIT_PERCENT:
+ {
+ nsAutoString floatStr;
+ floatStr.AppendFloat(mValue.mFloat * 100.0f);
+ aBuffer.Append(floatStr);
+ }
+ break;
+ default:
+ NS_ERROR("Unknown HTMLValue type!");
}
+ //
+ // Append the type name for types that are ambiguous
+ //
switch (mUnit) {
- case eHTMLUnit_Null: break;
- case eHTMLUnit_Empty: break;
- case eHTMLUnit_String: break;
- case eHTMLUnit_ColorName: break;
- case eHTMLUnit_ISupports: aBuffer.Append(NS_LITERAL_STRING("ptr")); break;
- case eHTMLUnit_Integer: break;
- case eHTMLUnit_Enumerated: aBuffer.Append(NS_LITERAL_STRING("enum")); break;
- case eHTMLUnit_Proportional: aBuffer.Append(NS_LITERAL_STRING("*")); break;
- case eHTMLUnit_Color: aBuffer.Append(NS_LITERAL_STRING("rbga")); break;
- case eHTMLUnit_Percent: aBuffer.Append(NS_LITERAL_STRING("%")); break;
- case eHTMLUnit_Pixel: aBuffer.Append(NS_LITERAL_STRING("px")); break;
+ case eHTMLUnit_Null:
+ aBuffer.Append(NS_LITERAL_STRING("null"));
+ break;
+ case eHTMLUnit_Empty:
+ aBuffer.Append(NS_LITERAL_STRING("empty"));
+ break;
+ case eHTMLUnit_ISupports:
+ aBuffer.Append(NS_LITERAL_STRING("ptr"));
+ break;
+ case eHTMLUnit_Enumerated:
+ aBuffer.Append(NS_LITERAL_STRING("enum"));
+ break;
+ case eHTMLUnit_Proportional:
+ aBuffer.Append(NS_LITERAL_STRING("*"));
+ break;
+ case eHTMLUnit_Color:
+ aBuffer.Append(NS_LITERAL_STRING("rbga"));
+ break;
+ case eHTMLUnit_Percent:
+ aBuffer.Append(NS_LITERAL_STRING("%"));
+ break;
+ case eHTMLUnit_Pixel:
+ aBuffer.Append(NS_LITERAL_STRING("px"));
+ break;
}
aBuffer.Append(PRUnichar(' '));
}
#endif // DEBUG
+
+void
+nsHTMLValue::InitializeFrom(const nsHTMLValue& aCopy)
+{
+ mUnit = aCopy.mUnit;
+ switch (GetUnitClass()) {
+ case HTMLUNIT_NOSTORE:
+ mValue.mString = nsnull;
+ break;
+
+ case HTMLUNIT_STRING:
+ if (aCopy.mValue.mString) {
+ nsCheapStringBufferUtils::Clone(mValue.mString, aCopy.mValue.mString);
+ } else {
+ mValue.mString = nsnull;
+ }
+ break;
+
+ case HTMLUNIT_INTEGER:
+ case HTMLUNIT_PIXEL:
+ mValue.mInt = aCopy.mValue.mInt;
+ break;
+
+ case HTMLUNIT_COLOR:
+ mValue.mColor = aCopy.mValue.mColor;
+ break;
+
+ case HTMLUNIT_ISUPPORTS:
+ mValue.mISupports = aCopy.mValue.mISupports;
+ NS_IF_ADDREF(mValue.mISupports);
+ break;
+
+ case HTMLUNIT_PERCENT:
+ mValue.mFloat = aCopy.mValue.mFloat;
+ break;
+
+ default:
+ NS_ERROR("Unknown HTMLValue type!");
+ }
+}
diff --git a/mozilla/layout/base/nsCSSFrameConstructor.cpp b/mozilla/layout/base/nsCSSFrameConstructor.cpp
index d6d19a01ef5..daf722903ca 100644
--- a/mozilla/layout/base/nsCSSFrameConstructor.cpp
+++ b/mozilla/layout/base/nsCSSFrameConstructor.cpp
@@ -1649,39 +1649,47 @@ nsCSSFrameConstructor::CreateInputFrame(nsIPresShell *aPresShell,
nsIFrame *&aFrame,
nsIStyleContext *aStyleContext)
{
- // Figure out which type of input frame to create
- nsAutoString val;
- if (NS_OK == aContent->GetAttr(kNameSpaceID_None, nsHTMLAtoms::type, val)) {
- if (val.EqualsIgnoreCase("submit") ||
- val.EqualsIgnoreCase("reset") ||
- val.EqualsIgnoreCase("button")) {
+ nsCOMPtr control = do_QueryInterface(aContent);
+ NS_ASSERTION(control, "input is not an nsIFormControl!");
+
+ PRInt32 type;
+ control->GetType(&type);
+ switch (type) {
+ case NS_FORM_INPUT_SUBMIT:
+ case NS_FORM_INPUT_RESET:
+ case NS_FORM_INPUT_BUTTON:
if (UseXBLForms())
return NS_OK;
return ConstructButtonControlFrame(aPresShell, aPresContext, aFrame);
- }
- else if (val.EqualsIgnoreCase("checkbox")) {
+
+ case NS_FORM_INPUT_CHECKBOX:
if (UseXBLForms())
return NS_OK;
return ConstructCheckboxControlFrame(aPresShell, aPresContext, aFrame, aContent, aStyleContext);
- }
- else if (val.EqualsIgnoreCase("file")) {
- return NS_NewFileControlFrame(aPresShell, &aFrame);
- }
- else if (val.EqualsIgnoreCase("hidden")) {
- return NS_OK;
- }
- else if (val.EqualsIgnoreCase("image")) {
- return NS_NewImageControlFrame(aPresShell, &aFrame);
- }
- else if (val.EqualsIgnoreCase("radio")) {
+
+ case NS_FORM_INPUT_RADIO:
if (UseXBLForms())
return NS_OK;
return ConstructRadioControlFrame(aPresShell, aPresContext, aFrame, aContent, aStyleContext);
- }
- }
- // "password", "text", and all others
- return ConstructTextControlFrame(aPresShell, aPresContext, aFrame, aContent);
+ case NS_FORM_INPUT_FILE:
+ return NS_NewFileControlFrame(aPresShell, &aFrame);
+
+ case NS_FORM_INPUT_HIDDEN:
+ return NS_OK;
+
+ case NS_FORM_INPUT_IMAGE:
+ return NS_NewImageControlFrame(aPresShell, &aFrame);
+
+ case NS_FORM_INPUT_TEXT:
+ case NS_FORM_INPUT_PASSWORD:
+ return ConstructTextControlFrame(aPresShell, aPresContext,
+ aFrame, aContent);
+
+ default:
+ NS_ASSERTION(0, "Unknown input type!");
+ return NS_ERROR_INVALID_ARG;
+ }
}
static PRBool
diff --git a/mozilla/layout/html/style/src/nsCSSFrameConstructor.cpp b/mozilla/layout/html/style/src/nsCSSFrameConstructor.cpp
index d6d19a01ef5..daf722903ca 100644
--- a/mozilla/layout/html/style/src/nsCSSFrameConstructor.cpp
+++ b/mozilla/layout/html/style/src/nsCSSFrameConstructor.cpp
@@ -1649,39 +1649,47 @@ nsCSSFrameConstructor::CreateInputFrame(nsIPresShell *aPresShell,
nsIFrame *&aFrame,
nsIStyleContext *aStyleContext)
{
- // Figure out which type of input frame to create
- nsAutoString val;
- if (NS_OK == aContent->GetAttr(kNameSpaceID_None, nsHTMLAtoms::type, val)) {
- if (val.EqualsIgnoreCase("submit") ||
- val.EqualsIgnoreCase("reset") ||
- val.EqualsIgnoreCase("button")) {
+ nsCOMPtr control = do_QueryInterface(aContent);
+ NS_ASSERTION(control, "input is not an nsIFormControl!");
+
+ PRInt32 type;
+ control->GetType(&type);
+ switch (type) {
+ case NS_FORM_INPUT_SUBMIT:
+ case NS_FORM_INPUT_RESET:
+ case NS_FORM_INPUT_BUTTON:
if (UseXBLForms())
return NS_OK;
return ConstructButtonControlFrame(aPresShell, aPresContext, aFrame);
- }
- else if (val.EqualsIgnoreCase("checkbox")) {
+
+ case NS_FORM_INPUT_CHECKBOX:
if (UseXBLForms())
return NS_OK;
return ConstructCheckboxControlFrame(aPresShell, aPresContext, aFrame, aContent, aStyleContext);
- }
- else if (val.EqualsIgnoreCase("file")) {
- return NS_NewFileControlFrame(aPresShell, &aFrame);
- }
- else if (val.EqualsIgnoreCase("hidden")) {
- return NS_OK;
- }
- else if (val.EqualsIgnoreCase("image")) {
- return NS_NewImageControlFrame(aPresShell, &aFrame);
- }
- else if (val.EqualsIgnoreCase("radio")) {
+
+ case NS_FORM_INPUT_RADIO:
if (UseXBLForms())
return NS_OK;
return ConstructRadioControlFrame(aPresShell, aPresContext, aFrame, aContent, aStyleContext);
- }
- }
- // "password", "text", and all others
- return ConstructTextControlFrame(aPresShell, aPresContext, aFrame, aContent);
+ case NS_FORM_INPUT_FILE:
+ return NS_NewFileControlFrame(aPresShell, &aFrame);
+
+ case NS_FORM_INPUT_HIDDEN:
+ return NS_OK;
+
+ case NS_FORM_INPUT_IMAGE:
+ return NS_NewImageControlFrame(aPresShell, &aFrame);
+
+ case NS_FORM_INPUT_TEXT:
+ case NS_FORM_INPUT_PASSWORD:
+ return ConstructTextControlFrame(aPresShell, aPresContext,
+ aFrame, aContent);
+
+ default:
+ NS_ASSERTION(0, "Unknown input type!");
+ return NS_ERROR_INVALID_ARG;
+ }
}
static PRBool
diff --git a/mozilla/xpcom/ds/nsCRT.cpp b/mozilla/xpcom/ds/nsCRT.cpp
index d5acef0d532..bb1c400bb97 100644
--- a/mozilla/xpcom/ds/nsCRT.cpp
+++ b/mozilla/xpcom/ds/nsCRT.cpp
@@ -399,6 +399,17 @@ PRUint32 nsCRT::BufferHashCode(const char* s, PRUint32 len)
return h;
}
+PRUint32 nsCRT::BufferHashCode(const PRUnichar* s, PRUint32 len)
+{
+ PRUint32 h = 0;
+ const PRUnichar* done = s + len;
+
+ while ( s < done )
+ h = (h>>28) ^ (h<<4) ^ PRUint16(*s++); // cast to unsigned to prevent possible sign extension
+
+ return h;
+}
+
// This should use NSPR but NSPR isn't exporting its PR_strtoll function
// Until then...
PRInt64 nsCRT::atoll(const char *str)
diff --git a/mozilla/xpcom/ds/nsCRT.h b/mozilla/xpcom/ds/nsCRT.h
index bcd8d6ae497..ce9d69da54b 100644
--- a/mozilla/xpcom/ds/nsCRT.h
+++ b/mozilla/xpcom/ds/nsCRT.h
@@ -238,6 +238,9 @@ public:
// Computes the hashcode for a buffer with a specified length.
static PRUint32 BufferHashCode(const char* str, PRUint32 strLen);
+ // Computes the hashcode for a buffer with a specified length.
+ static PRUint32 BufferHashCode(const PRUnichar* str, PRUint32 strLen);
+
// String to longlong
static PRInt64 atoll(const char *str);