diff --git a/accessible/src/atk/nsHTMLLinkAccessibleWrap.cpp b/accessible/src/atk/nsHTMLLinkAccessibleWrap.cpp
index c4ff646291c9..0a94cc7c4807 100644
--- a/accessible/src/atk/nsHTMLLinkAccessibleWrap.cpp
+++ b/accessible/src/atk/nsHTMLLinkAccessibleWrap.cpp
@@ -89,10 +89,7 @@ NS_IMETHODIMP nsHTMLLinkAccessibleWrap::GetURI(PRInt32 i, nsIURI **aURI)
nsCOMPtr link(do_QueryInterface(mLinkContent));
if (link) {
- nsXPIDLCString hrefValue;
- if (NS_SUCCEEDED(link->GetHrefUTF8(getter_Copies(hrefValue)))) {
- return NS_NewURI(aURI, hrefValue, nsnull, nsnull);
- }
+ return link->GetHrefURI(aURI);
}
return NS_ERROR_FAILURE;
diff --git a/content/base/src/nsGenericElement.cpp b/content/base/src/nsGenericElement.cpp
index 76c40b6e958e..7f0f88582f05 100644
--- a/content/base/src/nsGenericElement.cpp
+++ b/content/base/src/nsGenericElement.cpp
@@ -3115,29 +3115,16 @@ nsGenericElement::LeaveLink(nsIPresContext* aPresContext)
nsresult
nsGenericElement::TriggerLink(nsIPresContext* aPresContext,
nsLinkVerb aVerb,
- nsIURI* aBaseURL,
- const nsAString& aURLSpec,
+ nsIURI* aOriginURI,
+ nsIURI* aLinkURI,
const nsAFlatString& aTargetSpec,
PRBool aClick)
{
+ NS_PRECONDITION(aLinkURI, "No link URI");
nsCOMPtr handler;
nsresult rv = aPresContext->GetLinkHandler(getter_AddRefs(handler));
if (NS_FAILED(rv) || !handler) return rv;
- // Resolve url to an absolute url
- nsCOMPtr targetURI;
- nsCAutoString docCharset;
- if (mDocument &&
- NS_SUCCEEDED(mDocument->GetDocumentCharacterSet(docCharset))) {
- rv = NS_NewURI(getter_AddRefs(targetURI), aURLSpec,
- docCharset.get(), aBaseURL);
- } else {
- rv = NS_NewURI(getter_AddRefs(targetURI), aURLSpec, nsnull, aBaseURL);
- }
-
- NS_ENSURE_SUCCESS(rv, rv);
-
- // Now pass on absolute url to the click handler
if (aClick) {
nsresult proceed = NS_OK;
// Check that this page is allowed to load this URI.
@@ -3145,17 +3132,15 @@ nsGenericElement::TriggerLink(nsIPresContext* aPresContext,
do_GetService(NS_SCRIPTSECURITYMANAGER_CONTRACTID, &rv);
if (NS_SUCCEEDED(rv))
proceed =
- securityManager->CheckLoadURI(aBaseURL, targetURI,
+ securityManager->CheckLoadURI(aOriginURI, aLinkURI,
nsIScriptSecurityManager::STANDARD);
// Only pass off the click event if the script security manager
// says it's ok.
if (NS_SUCCEEDED(proceed))
- handler->OnLinkClick(this, aVerb, targetURI,
- aTargetSpec.get());
+ handler->OnLinkClick(this, aVerb, aLinkURI, aTargetSpec.get());
} else {
- handler->OnOverLink(this, targetURI,
- aTargetSpec.get());
+ handler->OnOverLink(this, aLinkURI, aTargetSpec.get());
}
return rv;
}
diff --git a/content/base/src/nsGenericElement.h b/content/base/src/nsGenericElement.h
index b81d1f8bb55b..5c417c1bbab8 100644
--- a/content/base/src/nsGenericElement.h
+++ b/content/base/src/nsGenericElement.h
@@ -535,19 +535,22 @@ public:
const nsAString& aValue);
/**
- * Load a link, putting together the proper URL from the pieces given.
+ * Trigger a link with uri aLinkURI. If aClick is false, this triggers a
+ * mouseover on the link, otherwise it triggers a load, after doing a
+ * security check.
* @param aPresContext the pres context.
* @param aVerb how the link will be loaded (replace page, new window, etc.)
- * @param aBaseURL the base URL to start with (content.baseURL, may be null)
- * @param aURLSpec the URL of the link (may be relative)
- * @param aTargetSpec the target (like target=, may be null)
+ * @param aOriginURI the URI the request originates from. Used as the origin
+ * uri for a CheckLoadURI call.
+ * @param aLinkURI the URI of the link
+ * @param aTargetSpec the target (like target=, may be empty)
* @param aClick whether this was a click or not (if false, it assumes you
* just hovered over the link)
*/
nsresult TriggerLink(nsIPresContext* aPresContext,
nsLinkVerb aVerb,
- nsIURI* aBaseURL,
- const nsAString& aURLSpec,
+ nsIURI* aOriginURI,
+ nsIURI* aLinkURI,
const nsAFlatString& aTargetSpec,
PRBool aClick);
/**
diff --git a/content/base/src/nsStyleLinkElement.cpp b/content/base/src/nsStyleLinkElement.cpp
index f2b88b308842..4026fc1c7ca5 100644
--- a/content/base/src/nsStyleLinkElement.cpp
+++ b/content/base/src/nsStyleLinkElement.cpp
@@ -207,19 +207,20 @@ nsStyleLinkElement::UpdateStyleSheet(nsIDocument *aOldDocument,
return NS_OK;
}
- nsAutoString url;
+ nsCOMPtr uri;
PRBool isInline;
+ GetStyleSheetURL(&isInline, getter_AddRefs(uri));
- GetStyleSheetURL(&isInline, url);
+ if (mStyleSheet && !isInline && uri) {
+ nsCOMPtr oldURI;
- nsCOMPtr styleSheet(do_QueryInterface(mStyleSheet));
-
- if (styleSheet && !isInline) {
- nsAutoString oldHref;
-
- styleSheet->GetHref(oldHref);
- if (oldHref.Equals(url)) {
- return NS_OK; // We already loaded this stylesheet
+ mStyleSheet->GetURL(*getter_AddRefs(oldURI));
+ if (oldURI) {
+ PRBool equal;
+ nsresult rv = oldURI->Equals(uri, &equal);
+ if (NS_SUCCEEDED(rv) && equal) {
+ return NS_OK; // We already loaded this stylesheet
+ }
}
}
@@ -228,7 +229,7 @@ nsStyleLinkElement::UpdateStyleSheet(nsIDocument *aOldDocument,
mStyleSheet = nsnull;
}
- if (url.IsEmpty() && !isInline) {
+ if (!uri && !isInline) {
return NS_OK; // If href is empty and this is not inline style then just bail
}
@@ -241,17 +242,6 @@ nsStyleLinkElement::UpdateStyleSheet(nsIDocument *aOldDocument,
return NS_OK;
}
- nsCOMPtr uri;
- nsresult rv = NS_OK;
-
- if (!isInline) {
- rv = NS_NewURI(getter_AddRefs(uri), url);
-
- if (NS_FAILED(rv)) {
- return NS_OK; // The URL is bad, move along, don't propagate the error (for now)
- }
- }
-
nsCOMPtr htmlContainer(do_QueryInterface(doc));
nsCOMPtr loader;
@@ -286,6 +276,7 @@ nsStyleLinkElement::UpdateStyleSheet(nsIDocument *aOldDocument,
}
PRBool doneLoading;
+ nsresult rv = NS_OK;
if (isInline) {
PRInt32 count;
thisContent->ChildCount(count);
diff --git a/content/base/src/nsStyleLinkElement.h b/content/base/src/nsStyleLinkElement.h
index b22addc9a25c..325c9ca8dfd3 100644
--- a/content/base/src/nsStyleLinkElement.h
+++ b/content/base/src/nsStyleLinkElement.h
@@ -57,7 +57,7 @@ public:
protected:
virtual void GetStyleSheetURL(PRBool* aIsInline,
- nsAString& aUrl) = 0;
+ nsIURI** aURI) = 0;
virtual void GetStyleSheetInfo(nsAString& aTitle,
nsAString& aType,
nsAString& aMedia,
diff --git a/content/html/content/public/nsILink.h b/content/html/content/public/nsILink.h
index eaebb9ac45d8..de6b0e527b51 100644
--- a/content/html/content/public/nsILink.h
+++ b/content/html/content/public/nsILink.h
@@ -42,6 +42,8 @@
#include "nsISupports.h"
#include "nsILinkHandler.h" // definition of nsLinkState
+class nsIURI;
+
// IID for the nsILink interface
#define NS_ILINK_IID \
{ 0xa904ac22, 0x28fa, 0x4812, \
@@ -76,18 +78,14 @@ public:
NS_IMETHOD SetLinkState(nsLinkState aState) = 0;
/**
- * Get a pointer to the UTF-8 encoded canonical URL (i.e., fully
- * resolved to the base URL) that this link element points to. The
- * buffer returned has been allocated for and should be deleted by
- * the caller.
+ * Get a pointer to the fully href URI (fully resolved and canonicalized,
+ * since it's an nsIURI object).
*
- * @param aBuf [out] A pointer to be filled in with a pointer to a
- * null-terminated string containing the canonical URL.
- * If the element has no HREF attribute, it is set to
- * nsnull.
- * @return NS_OK if the out pointer is filled in
+ * @param aURI [out] A pointer to be filled in with a pointer to the URI
+ * If the element has no HREF attribute, it is set to nsnull.
+ * @return NS_OK if the out pointer is filled in (possibly with nsnull)
*/
- NS_IMETHOD GetHrefUTF8(char** aBuf) = 0;
+ NS_IMETHOD GetHrefURI(nsIURI** aURI) = 0;
};
diff --git a/content/html/content/src/nsGenericHTMLElement.cpp b/content/html/content/src/nsGenericHTMLElement.cpp
index 54ada59bbf88..25e0a4f031a3 100644
--- a/content/html/content/src/nsGenericHTMLElement.cpp
+++ b/content/html/content/src/nsGenericHTMLElement.cpp
@@ -1467,17 +1467,12 @@ nsGenericHTMLElement::HandleDOMEventForAnchors(nsIPresContext* aPresContext,
// nsILink interface to get a canonified URL that has been
// correctly escaped and URL-encoded for the document's charset.
- nsXPIDLCString hrefCStr;
- GetHrefUTF8ForAnchors(getter_Copies(hrefCStr));
+ nsCOMPtr hrefURI;
+ GetHrefURIForAnchors(getter_AddRefs(hrefURI));
// Only bother to handle the mouse event if there was an href
// specified.
- if (hrefCStr) {
- NS_ConvertUTF8toUCS2 href(hrefCStr);
- // Strip off any unneeded CF/LF (for Bug 52119)
- // It can't be done in the parser because of Bug 15204
- href.StripChars("\r\n");
-
+ if (hrefURI) {
switch (aEvent->message) {
case NS_MOUSE_LEFT_BUTTON_DOWN:
{
@@ -1527,7 +1522,7 @@ nsGenericHTMLElement::HandleDOMEventForAnchors(nsIPresContext* aPresContext,
break; // let the click go through so we can handle it in JS/XUL
}
- ret = TriggerLink(aPresContext, eLinkVerb_Replace, baseURL, href,
+ ret = TriggerLink(aPresContext, eLinkVerb_Replace, baseURL, hrefURI,
target, PR_TRUE);
*aEventStatus = nsEventStatus_eConsumeDoDefault;
@@ -1577,8 +1572,8 @@ nsGenericHTMLElement::HandleDOMEventForAnchors(nsIPresContext* aPresContext,
if (target.IsEmpty()) {
GetBaseTarget(target);
}
- ret = TriggerLink(aPresContext, eLinkVerb_Replace,
- baseURL, href, target, PR_FALSE);
+ ret = TriggerLink(aPresContext, eLinkVerb_Replace, baseURL,
+ hrefURI, target, PR_FALSE);
}
break;
@@ -1598,7 +1593,7 @@ nsGenericHTMLElement::HandleDOMEventForAnchors(nsIPresContext* aPresContext,
}
nsresult
-nsGenericHTMLElement::GetHrefUTF8ForAnchors(char** aHref)
+nsGenericHTMLElement::GetHrefURIForAnchors(nsIURI** aURI)
{
// This is used by the three nsILink implementations and
// nsHTMLStyleElement.
@@ -1608,29 +1603,21 @@ nsGenericHTMLElement::GetHrefUTF8ForAnchors(char** aHref)
if (NS_CONTENT_ATTR_HAS_VALUE ==
GetAttr(kNameSpaceID_None, nsHTMLAtoms::href, relURLSpec)) {
- // Clean up any leading or trailing whitespace
- relURLSpec.Trim(" \t\n\r");
-
// Get base URL.
nsCOMPtr baseURL;
GetBaseURL(getter_AddRefs(baseURL));
- if (baseURL) {
- // Get absolute URL.
- nsCAutoString buf;
- NS_MakeAbsoluteURIWithCharset(buf, relURLSpec, mDocument, baseURL,
- nsHTMLUtils::IOService,
- nsHTMLUtils::CharsetMgr);
- *aHref = ToNewCString(buf);
- }
- else {
- // Absolute URL is same as relative URL.
- *aHref = ToNewUTF8String(relURLSpec);
+ // Get absolute URL.
+ nsCAutoString buf;
+ nsresult rv = NS_NewURIWithDocumentCharset(aURI, relURLSpec, mDocument,
+ baseURL);
+ if (NS_FAILED(rv)) {
+ *aURI = nsnull;
}
}
else {
// Absolute URL is null to say we have no HREF.
- *aHref = nsnull;
+ *aURI = nsnull;
}
return NS_OK;
diff --git a/content/html/content/src/nsGenericHTMLElement.h b/content/html/content/src/nsGenericHTMLElement.h
index cb63d011787a..d44403616e72 100644
--- a/content/html/content/src/nsGenericHTMLElement.h
+++ b/content/html/content/src/nsGenericHTMLElement.h
@@ -217,7 +217,7 @@ public:
// Used by A, AREA, LINK, and STYLE.
// Callers must hold a reference to nsHTMLUtils's global reference count.
- nsresult GetHrefUTF8ForAnchors(char** aHref);
+ nsresult GetHrefURIForAnchors(nsIURI** aURI);
// Implementation for nsIHTMLContent
NS_IMETHOD SetHTMLAttribute(nsIAtom* aAttribute, const nsHTMLValue& aValue,
diff --git a/content/html/content/src/nsHTMLAnchorElement.cpp b/content/html/content/src/nsHTMLAnchorElement.cpp
index ce213285f815..187df3944dc3 100644
--- a/content/html/content/src/nsHTMLAnchorElement.cpp
+++ b/content/html/content/src/nsHTMLAnchorElement.cpp
@@ -106,7 +106,7 @@ public:
// nsILink
NS_IMETHOD GetLinkState(nsLinkState &aState);
NS_IMETHOD SetLinkState(nsLinkState aState);
- NS_IMETHOD GetHrefUTF8(char** aBuf);
+ NS_IMETHOD GetHrefURI(nsIURI** aURI);
NS_IMETHOD SetDocument(nsIDocument* aDocument, PRBool aDeep,
PRBool aCompileEventHandlers);
@@ -164,12 +164,12 @@ NS_NewHTMLAnchorElement(nsIHTMLContent** aInstancePtrResult,
nsHTMLAnchorElement::nsHTMLAnchorElement() : mLinkState(eLinkState_Unknown)
{
- nsHTMLUtils::AddRef(); // for GetHrefUTF8
+ nsHTMLUtils::AddRef(); // for GetHrefURI
}
nsHTMLAnchorElement::~nsHTMLAnchorElement()
{
- nsHTMLUtils::Release(); // for GetHrefUTF8
+ nsHTMLUtils::Release(); // for GetHrefURI
}
@@ -357,13 +357,17 @@ nsHTMLAnchorElement::HandleDOMEvent(nsIPresContext* aPresContext,
NS_IMETHODIMP
nsHTMLAnchorElement::GetHref(nsAString& aValue)
{
- nsXPIDLCString buf;
- nsresult rv = GetHrefUTF8(getter_Copies(buf));
- if (NS_FAILED(rv)) return rv;
+ nsCOMPtr uri;
+ nsresult rv = GetHrefURI(getter_AddRefs(uri));
+ if (NS_FAILED(rv))
+ return rv;
- CopyUTF8toUTF16(buf, aValue);
+ nsCAutoString spec;
+ if (uri) {
+ uri->GetSpec(spec);
+ }
+ CopyUTF8toUTF16(spec, aValue);
- // NS_IMPL_STRING_ATTR does nothing where we have (buf == null)
return NS_OK;
}
@@ -660,9 +664,9 @@ nsHTMLAnchorElement::SetLinkState(nsLinkState aState)
}
NS_IMETHODIMP
-nsHTMLAnchorElement::GetHrefUTF8(char** aBuf)
+nsHTMLAnchorElement::GetHrefURI(nsIURI** aURI)
{
- return GetHrefUTF8ForAnchors(aBuf);
+ return GetHrefURIForAnchors(aURI);
}
NS_IMETHODIMP
diff --git a/content/html/content/src/nsHTMLAreaElement.cpp b/content/html/content/src/nsHTMLAreaElement.cpp
index fd3dfd812147..8e6de3e8a333 100644
--- a/content/html/content/src/nsHTMLAreaElement.cpp
+++ b/content/html/content/src/nsHTMLAreaElement.cpp
@@ -83,7 +83,7 @@ public:
// nsILink
NS_IMETHOD GetLinkState(nsLinkState &aState);
NS_IMETHOD SetLinkState(nsLinkState aState);
- NS_IMETHOD GetHrefUTF8(char** aBuf);
+ NS_IMETHOD GetHrefURI(nsIURI** aURI);
NS_IMETHOD StringToAttribute(nsIAtom* aAttribute,
const nsAString& aValue,
@@ -140,12 +140,12 @@ NS_NewHTMLAreaElement(nsIHTMLContent** aInstancePtrResult,
nsHTMLAreaElement::nsHTMLAreaElement()
: mLinkState(eLinkState_Unknown)
{
- nsHTMLUtils::AddRef(); // for GetHrefUTF8
+ nsHTMLUtils::AddRef(); // for GetHrefURI
}
nsHTMLAreaElement::~nsHTMLAreaElement()
{
- nsHTMLUtils::Release(); // for GetHrefUTF8
+ nsHTMLUtils::Release(); // for GetHrefURI
}
NS_IMPL_ADDREF_INHERITED(nsHTMLAreaElement, nsGenericElement)
@@ -273,14 +273,14 @@ nsHTMLAreaElement::RemoveFocus(nsIPresContext* aPresContext)
NS_IMETHODIMP
nsHTMLAreaElement::GetHref(nsAString& aValue)
{
- char *buf;
- nsresult rv = GetHrefUTF8(&buf);
+ nsCOMPtr uri;
+ nsresult rv = GetHrefURI(getter_AddRefs(uri));
if (NS_FAILED(rv)) return rv;
- if (buf) {
- aValue.Assign(NS_ConvertASCIItoUCS2(buf));
- nsCRT::free(buf);
+ if (uri) {
+ nsCAutoString spec;
+ uri->GetSpec(spec);
+ CopyUTF8toUTF16(spec, aValue);
}
- // NS_IMPL_STRING_ATTR does nothing where we have (buf == null)
return NS_OK;
}
@@ -571,7 +571,7 @@ nsHTMLAreaElement::SetLinkState(nsLinkState aState)
}
NS_IMETHODIMP
-nsHTMLAreaElement::GetHrefUTF8(char** aBuf)
+nsHTMLAreaElement::GetHrefURI(nsIURI** aURI)
{
- return GetHrefUTF8ForAnchors(aBuf);
+ return GetHrefURIForAnchors(aURI);
}
diff --git a/content/html/content/src/nsHTMLLinkElement.cpp b/content/html/content/src/nsHTMLLinkElement.cpp
index 4730df7f76e0..961428ec3ed7 100644
--- a/content/html/content/src/nsHTMLLinkElement.cpp
+++ b/content/html/content/src/nsHTMLLinkElement.cpp
@@ -86,7 +86,7 @@ public:
// nsILink
NS_IMETHOD GetLinkState(nsLinkState &aState);
NS_IMETHOD SetLinkState(nsLinkState aState);
- NS_IMETHOD GetHrefUTF8(char** aBuf);
+ NS_IMETHOD GetHrefURI(nsIURI** aURI);
NS_IMETHOD SetDocument(nsIDocument* aDocument, PRBool aDeep,
PRBool aCompileEventHandlers) {
@@ -186,7 +186,7 @@ public:
protected:
virtual void GetStyleSheetURL(PRBool* aIsInline,
- nsAString& aUrl);
+ nsIURI** aURI);
virtual void GetStyleSheetInfo(nsAString& aTitle,
nsAString& aType,
nsAString& aMedia,
@@ -226,12 +226,12 @@ NS_NewHTMLLinkElement(nsIHTMLContent** aInstancePtrResult,
nsHTMLLinkElement::nsHTMLLinkElement()
: mLinkState(eLinkState_Unknown)
{
- nsHTMLUtils::AddRef(); // for GetHrefUTF8
+ nsHTMLUtils::AddRef(); // for GetHrefURI
}
nsHTMLLinkElement::~nsHTMLLinkElement()
{
- nsHTMLUtils::Release(); // for GetHrefUTF8
+ nsHTMLUtils::Release(); // for GetHrefURI
}
@@ -320,16 +320,15 @@ NS_IMPL_STRING_ATTR(nsHTMLLinkElement, Type, type)
NS_IMETHODIMP
nsHTMLLinkElement::GetHref(nsAString& aValue)
{
- char *buf;
- nsresult rv = GetHrefUTF8(&buf);
+ nsCOMPtr uri;
+ nsresult rv = GetHrefURI(getter_AddRefs(uri));
if (NS_FAILED(rv)) return rv;
- if (buf) {
- aValue.Assign(NS_ConvertUTF8toUCS2(buf));
- nsCRT::free(buf);
+ if (uri) {
+ nsCAutoString spec;
+ uri->GetSpec(spec);
+ CopyUTF8toUTF16(spec, aValue);
}
- // NS_IMPL_STRING_ATTR does nothing where we have (buf == null)
-
return NS_OK;
}
@@ -375,17 +374,17 @@ nsHTMLLinkElement::SetLinkState(nsLinkState aState)
}
NS_IMETHODIMP
-nsHTMLLinkElement::GetHrefUTF8(char** aBuf)
+nsHTMLLinkElement::GetHrefURI(nsIURI** aURI)
{
- return GetHrefUTF8ForAnchors(aBuf);
+ return GetHrefURIForAnchors(aURI);
}
void
nsHTMLLinkElement::GetStyleSheetURL(PRBool* aIsInline,
- nsAString& aUrl)
+ nsIURI** aURI)
{
*aIsInline = PR_FALSE;
- GetHref(aUrl);
+ GetHrefURIForAnchors(aURI);
return;
}
diff --git a/content/html/content/src/nsHTMLStyleElement.cpp b/content/html/content/src/nsHTMLStyleElement.cpp
index f00368dbcf54..2c3e183d8800 100644
--- a/content/html/content/src/nsHTMLStyleElement.cpp
+++ b/content/html/content/src/nsHTMLStyleElement.cpp
@@ -168,7 +168,7 @@ public:
protected:
void GetStyleSheetURL(PRBool* aIsInline,
- nsAString& aUrl);
+ nsIURI** aURI);
void GetStyleSheetInfo(nsAString& aTitle,
nsAString& aType,
nsAString& aMedia,
@@ -204,12 +204,12 @@ NS_NewHTMLStyleElement(nsIHTMLContent** aInstancePtrResult,
nsHTMLStyleElement::nsHTMLStyleElement()
{
- nsHTMLUtils::AddRef(); // for GetHrefUTF8ForAnchors
+ nsHTMLUtils::AddRef(); // for GetHrefURIForAnchors
}
nsHTMLStyleElement::~nsHTMLStyleElement()
{
- nsHTMLUtils::Release(); // for GetHrefUTF8ForAnchors
+ nsHTMLUtils::Release(); // for GetHrefURIForAnchors
}
@@ -314,9 +314,9 @@ nsHTMLStyleElement::SetInnerHTML(const nsAString& aInnerHTML)
void
nsHTMLStyleElement::GetStyleSheetURL(PRBool* aIsInline,
- nsAString& aUrl)
+ nsIURI** aURI)
{
- aUrl.Truncate();
+ *aURI = nsnull;
*aIsInline = !HasAttr(kNameSpaceID_None, nsHTMLAtoms::src);
if (*aIsInline) {
return;
@@ -328,12 +328,7 @@ nsHTMLStyleElement::GetStyleSheetURL(PRBool* aIsInline,
return;
}
- char *buf;
- GetHrefUTF8ForAnchors(&buf);
- if (buf) {
- aUrl.Assign(NS_ConvertUTF8toUCS2(buf));
- nsCRT::free(buf);
- }
+ GetHrefURIForAnchors(aURI);
return;
}
diff --git a/content/html/style/src/nsStyleUtil.cpp b/content/html/style/src/nsStyleUtil.cpp
index 903db3e8750b..7def156cbfc4 100644
--- a/content/html/style/src/nsStyleUtil.cpp
+++ b/content/html/style/src/nsStyleUtil.cpp
@@ -595,15 +595,14 @@ PRBool nsStyleUtil::IsHTMLLink(nsIContent *aContent, nsIAtom *aTag, nsIPresConte
// if there is no link, then this anchor is not really a linkpseudo.
// bug=23209
- nsXPIDLCString href;
- link->GetHrefUTF8(getter_Copies(href));
+ nsCOMPtr hrefURI;
+ link->GetHrefURI(getter_AddRefs(hrefURI));
- if (href) {
- nsILinkHandler *linkHandler = nsnull;
- aPresContext->GetLinkHandler(&linkHandler);
+ if (hrefURI) {
+ nsCOMPtr linkHandler;
+ aPresContext->GetLinkHandler(getter_AddRefs(linkHandler));
if (linkHandler) {
- linkHandler->GetLinkState(href, linkState);
- NS_RELEASE(linkHandler);
+ linkHandler->GetLinkState(hrefURI, linkState);
}
else {
// no link handler? then all links are unvisited
@@ -665,16 +664,14 @@ PRBool nsStyleUtil::IsSimpleXlink(nsIContent *aContent, nsIPresContext *aPresCon
}
}
- // convert here, rather than twice in NS_MakeAbsoluteURI and
- // back again
- nsCAutoString absHREF;
- (void) NS_MakeAbsoluteURI(absHREF, NS_ConvertUCS2toUTF8(val), baseURI);
+ nsCOMPtr absURI;
+ // XXX should we make sure to get the right charset off the document?
+ (void) NS_NewURI(getter_AddRefs(absURI), val, nsnull, baseURI);
- nsILinkHandler *linkHandler = nsnull;
- aPresContext->GetLinkHandler(&linkHandler);
+ nsCOMPtr linkHandler;
+ aPresContext->GetLinkHandler(getter_AddRefs(linkHandler));
if (linkHandler) {
- linkHandler->GetLinkState(absHREF, *aState);
- NS_RELEASE(linkHandler);
+ linkHandler->GetLinkState(absURI, *aState);
}
else {
// no link handler? then all links are unvisited
diff --git a/content/shared/public/nsHTMLUtils.h b/content/shared/public/nsHTMLUtils.h
index 301a63c0bf62..74896de048b1 100644
--- a/content/shared/public/nsHTMLUtils.h
+++ b/content/shared/public/nsHTMLUtils.h
@@ -53,19 +53,14 @@ class nsString;
class nsACString;
/**
- * A version of NS_MakeAbsoluteURI that's savvy to document character
- * set encodings, and will recode a relative spec in the specified
- * charset and URL-escape it before resolving.
- *
- * XXXdarin this should really return a nsIURI
+ * A version of NS_NewURI that's savvy to document character
+ * set encodings
*/
nsresult
-NS_MakeAbsoluteURIWithCharset(nsACString &aResult,
- const nsString& aSpec,
- nsIDocument* aDocument,
- nsIURI* aBaseURI = nsnull,
- nsIIOService* aIOService = nsnull,
- nsICharsetConverterManager* aConvMgr = nsnull);
+NS_NewURIWithDocumentCharset(nsIURI** aResult,
+ const nsString& aSpec,
+ nsIDocument* aDocument,
+ nsIURI* aBaseURI);
class nsHTMLUtils {
diff --git a/content/shared/src/nsHTMLUtils.cpp b/content/shared/src/nsHTMLUtils.cpp
index 1227f56a801a..f2fb02de5329 100644
--- a/content/shared/src/nsHTMLUtils.cpp
+++ b/content/shared/src/nsHTMLUtils.cpp
@@ -58,49 +58,21 @@
static NS_DEFINE_CID(kIOServiceCID, NS_IOSERVICE_CID);
nsresult
-NS_MakeAbsoluteURIWithCharset(nsACString &aResult,
- const nsString& aSpec,
- nsIDocument* aDocument,
- nsIURI* aBaseURI,
- nsIIOService* aIOService,
- nsICharsetConverterManager* aConvMgr)
+NS_NewURIWithDocumentCharset(nsIURI** aResult,
+ const nsString& aSpec,
+ nsIDocument* aDocument,
+ nsIURI* aBaseURI)
{
- // Initialize aResult in case of tragedy
- aResult.Truncate();
-
- // Sanity
- NS_PRECONDITION(aBaseURI != nsnull, "no base URI");
- if (! aBaseURI)
- return NS_ERROR_FAILURE;
-
- // This gets the relative spec after gyrating it through all the
- // necessary encodings and escaping.
-
- if (IsASCII(aSpec)) {
- // If it's ASCII, then just copy the characters
- return aBaseURI->Resolve(NS_LossyConvertUCS2toASCII(aSpec), aResult);
- }
-
- nsCOMPtr absURI;
- nsresult rv;
-
- nsCAutoString originCharset; // XXX why store charset as UCS2?
+ NS_PRECONDITION(aResult, "Null out param");
+ NS_PRECONDITION(aBaseURI, "Must have a base URI");
+
+ nsCAutoString originCharset;
if (aDocument && NS_FAILED(aDocument->GetDocumentCharacterSet(originCharset)))
originCharset.Truncate();
- // URI can't be encoded in UTF-16, UTF-16BE, UTF-16LE, UTF-32, UTF-32-LE,
- // UTF-32LE, UTF-32BE (yet?). Truncate it and leave it to default (UTF-8)
- if (originCharset[0] == 'U' &&
- originCharset[1] == 'T' &&
- originCharset[2] == 'F')
- originCharset.Truncate();
-
- rv = nsHTMLUtils::IOService->NewURI(NS_ConvertUCS2toUTF8(aSpec),
- originCharset.get(),
- aBaseURI, getter_AddRefs(absURI));
- if (NS_FAILED(rv)) return rv;
-
- return absURI->GetSpec(aResult);
+ return nsHTMLUtils::IOService->NewURI(NS_ConvertUCS2toUTF8(aSpec),
+ originCharset.get(),
+ aBaseURI, aResult);
}
diff --git a/content/xml/content/src/nsXMLElement.cpp b/content/xml/content/src/nsXMLElement.cpp
index 6e039d63d663..c970b8c31a64 100644
--- a/content/xml/content/src/nsXMLElement.cpp
+++ b/content/xml/content/src/nsXMLElement.cpp
@@ -40,8 +40,10 @@
#include "nsXMLElement.h"
#include "nsHTMLAtoms.h"
#include "nsLayoutAtoms.h"
+#include "nsHTMLUtils.h"
#include "nsIDocument.h"
#include "nsIAtom.h"
+#include "nsNetUtil.h"
#include "nsIEventListenerManager.h"
#include "nsIDocShell.h"
#include "nsIEventStateManager.h"
@@ -97,10 +99,12 @@ NS_NewXMLElement(nsIContent** aInstancePtrResult, nsINodeInfo *aNodeInfo)
nsXMLElement::nsXMLElement() : mIsLink(PR_FALSE)
{
+ nsHTMLUtils::AddRef(); // for NS_NewURIWithDocumentCharset
}
nsXMLElement::~nsXMLElement()
{
+ nsHTMLUtils::Release(); // for NS_NewURIWithDocumentCharset
}
@@ -143,17 +147,6 @@ NS_IMPL_ADDREF_INHERITED(nsXMLElement, nsGenericElement)
NS_IMPL_RELEASE_INHERITED(nsXMLElement, nsGenericElement)
-static inline nsresult MakeURI(const nsACString &aSpec, nsIURI *aBase, nsIURI **aURI)
-{
- nsresult rv;
- static NS_DEFINE_CID(ioServCID,NS_IOSERVICE_CID);
- nsCOMPtr service(do_GetService(ioServCID, &rv));
- if (NS_FAILED(rv))
- return rv;
-
- return service->NewURI(aSpec,nsnull,aBase,aURI);
-}
-
NS_IMETHODIMP
nsXMLElement::GetXMLBaseURI(nsIURI **aURI)
{
@@ -176,14 +169,12 @@ nsXMLElement::GetXMLBaseURI(nsIURI **aURI)
// The complex looking if above is to make sure that we do not erroneously
// think a value of "./this:that" would have a scheme of "./that"
- NS_ConvertUCS2toUTF8 str(value);
-
- rv = MakeURI(str, nsnull, aURI);
+ rv = NS_NewURIWithDocumentCharset(aURI, value, mDocument, nsnull);
if (NS_FAILED(rv))
break;
if (!base.IsEmpty()) { // XXXdarin base is always empty
- CopyUTF16toUTF8(base, str);
+ NS_ConvertUTF16toUTF8 str(base);
nsCAutoString resolvedStr;
rv = (*aURI)->Resolve(str, resolvedStr);
if (NS_FAILED(rv)) break;
@@ -224,7 +215,7 @@ nsXMLElement::GetXMLBaseURI(nsIURI **aURI)
*aURI = docBase.get();
NS_IF_ADDREF(*aURI); // nsCOMPtr releases this once
} else {
- rv = MakeURI(NS_ConvertUCS2toUTF8(base), docBase, aURI);
+ rv = NS_NewURIWithDocumentCharset(aURI, base, mDocument, docBase);
}
}
@@ -319,15 +310,13 @@ static nsresult DocShellToPresContext(nsIDocShell *aShell,
}
-static nsresult CheckLoadURI(nsIURI *aBaseURI, const nsAString& aURI,
- nsIURI **aAbsURI)
+static nsresult CheckLoadURI(const nsString& aSpec, nsIURI *aBaseURI,
+ nsIDocument* aDocument, nsIURI **aAbsURI)
{
- NS_ConvertUCS2toUTF8 str(aURI);
-
*aAbsURI = nsnull;
nsresult rv;
- rv = MakeURI(str, aBaseURI, aAbsURI);
+ rv = NS_NewURIWithDocumentCharset(aAbsURI, aSpec, aDocument, aBaseURI);
if (NS_SUCCEEDED(rv)) {
nsCOMPtr securityManager =
do_GetService(NS_SCRIPTSECURITYMANAGER_CONTRACTID, &rv);
@@ -449,12 +438,12 @@ nsXMLElement::MaybeTriggerAutoLink(nsIDocShell *aShell)
value);
if (rv == NS_CONTENT_ATTR_HAS_VALUE && !value.IsEmpty()) {
nsCOMPtr uri;
- rv = CheckLoadURI(base,value,getter_AddRefs(uri));
+ rv = CheckLoadURI(value, base, mDocument, getter_AddRefs(uri));
if (NS_SUCCEEDED(rv)) {
nsCOMPtr pc;
- rv = DocShellToPresContext(aShell,getter_AddRefs(pc));
+ rv = DocShellToPresContext(aShell, getter_AddRefs(pc));
if (NS_SUCCEEDED(rv)) {
- rv = TriggerLink(pc, verb, base, value,
+ rv = TriggerLink(pc, verb, base, uri,
NS_LITERAL_STRING(""), PR_TRUE);
return SpecialAutoLoadReturn(rv,verb);
@@ -506,7 +495,6 @@ nsXMLElement::HandleDOMEvent(nsIPresContext* aPresContext,
break; // let the click go through so we can handle it in JS/XUL
}
nsAutoString show, href, target;
- nsIURI* baseURL = nsnull;
nsLinkVerb verb = eLinkVerb_Undefined; // basically means same as replace
nsGenericContainerElement::GetAttr(kNameSpaceID_XLink,
nsHTMLAtoms::href,
@@ -539,12 +527,16 @@ nsXMLElement::HandleDOMEvent(nsIPresContext* aPresContext,
verb = eLinkVerb_Embed;
}
- GetXMLBaseURI(&baseURL);
+ nsCOMPtr baseURL;
+ GetXMLBaseURI(getter_AddRefs(baseURL));
+ nsCOMPtr uri;
+ ret = NS_NewURIWithDocumentCharset(getter_AddRefs(uri), href,
+ mDocument, baseURL);
+ if (NS_SUCCEEDED(ret)) {
+ ret = TriggerLink(aPresContext, verb, baseURL, uri, target,
+ PR_TRUE);
+ }
- ret = TriggerLink(aPresContext, verb, baseURL, href, target,
- PR_TRUE);
-
- NS_IF_RELEASE(baseURL);
*aEventStatus = nsEventStatus_eConsumeDoDefault;
}
}
@@ -586,7 +578,6 @@ nsXMLElement::HandleDOMEvent(nsIPresContext* aPresContext,
case NS_MOUSE_ENTER_SYNTH:
{
nsAutoString href, target;
- nsIURI* baseURL = nsnull;
nsGenericContainerElement::GetAttr(kNameSpaceID_XLink,
nsHTMLAtoms::href,
href);
@@ -595,12 +586,17 @@ nsXMLElement::HandleDOMEvent(nsIPresContext* aPresContext,
break;
}
- GetXMLBaseURI(&baseURL);
+ nsCOMPtr baseURL;
+ GetXMLBaseURI(getter_AddRefs(baseURL));
- ret = TriggerLink(aPresContext, eLinkVerb_Replace, baseURL, href,
- target, PR_FALSE);
+ nsCOMPtr uri;
+ ret = NS_NewURIWithDocumentCharset(getter_AddRefs(uri), href,
+ mDocument, baseURL);
+ if (NS_SUCCEEDED(ret)) {
+ ret = TriggerLink(aPresContext, eLinkVerb_Replace, baseURL, uri,
+ target, PR_FALSE);
+ }
- NS_IF_RELEASE(baseURL);
*aEventStatus = nsEventStatus_eConsumeDoDefault;
}
break;
diff --git a/content/xml/content/src/nsXMLStylesheetPI.cpp b/content/xml/content/src/nsXMLStylesheetPI.cpp
index fbda72d10b3a..54948131c60f 100644
--- a/content/xml/content/src/nsXMLStylesheetPI.cpp
+++ b/content/xml/content/src/nsXMLStylesheetPI.cpp
@@ -71,7 +71,7 @@ public:
protected:
void GetStyleSheetURL(PRBool* aIsInline,
- nsAString& aUrl);
+ nsIURI** aURI);
void GetStyleSheetInfo(nsAString& aTitle,
nsAString& aType,
nsAString& aMedia,
@@ -157,10 +157,10 @@ nsXMLStylesheetPI::GetCharset(nsAString& aCharset)
void
nsXMLStylesheetPI::GetStyleSheetURL(PRBool* aIsInline,
- nsAString& aUrl)
+ nsIURI** aURI)
{
*aIsInline = PR_FALSE;
- aUrl.Truncate();
+ *aURI = nsnull;
nsAutoString href;
GetAttrValue(NS_LITERAL_STRING("href"), href);
@@ -169,10 +169,12 @@ nsXMLStylesheetPI::GetStyleSheetURL(PRBool* aIsInline,
}
nsCOMPtr url, baseURL;
+ nsCAutoString charset;
if (mDocument) {
mDocument->GetBaseURL(getter_AddRefs(baseURL));
+ mDocument->GetDocumentCharacterSet(charset);
}
- NS_MakeAbsoluteURI(aUrl, href, baseURL);
+ NS_NewURI(aURI, href, charset.get(), baseURL);
}
void
diff --git a/docshell/base/nsWebShell.cpp b/docshell/base/nsWebShell.cpp
index 43ff63e6863e..b17755b34747 100644
--- a/docshell/base/nsWebShell.cpp
+++ b/docshell/base/nsWebShell.cpp
@@ -757,86 +757,26 @@ nsWebShell::OnLeaveLink()
return rv;
}
-nsresult
-nsWebShell::NormalizeURI(nsACString& aURLSpec)
-{
- nsIURI *uri = nsnull;
- nsCAutoString scheme;
- nsresult rv = mIOService->ExtractScheme(aURLSpec, scheme);
- if (NS_FAILED(rv)) return rv;
-
- // keep tempUri up here to keep it in scope
- nsCOMPtr tempUri;
-
- // used to avoid extra work later
- PRBool clearUri(PR_TRUE);
-
- if (scheme.Equals(NS_LITERAL_CSTRING("http"))) {
- if (mCachedHttpUrl)
- rv = mCachedHttpUrl->SetSpec(aURLSpec);
- else
- rv = NS_NewURI(getter_AddRefs(mCachedHttpUrl), aURLSpec);
-
- uri = mCachedHttpUrl;
- }
-
- else if (scheme.Equals(NS_LITERAL_CSTRING("https"))) {
- if (mCachedHttpsUrl)
- rv = mCachedHttpsUrl->SetSpec(aURLSpec);
- else
- rv = NS_NewURI(getter_AddRefs(mCachedHttpsUrl), aURLSpec);
-
- uri = mCachedHttpsUrl;
- }
-
- else if (scheme.Equals(NS_LITERAL_CSTRING("ftp"))) {
- if (mCachedFtpUrl)
- rv = mCachedFtpUrl->SetSpec(aURLSpec);
- else
- rv = NS_NewURI(getter_AddRefs(mCachedFtpUrl), aURLSpec);
-
- uri = mCachedFtpUrl;
- } else {
- rv = NS_NewURI(getter_AddRefs(tempUri), aURLSpec);
- uri = tempUri;
- clearUri = PR_FALSE;
- }
-
- // covers all above failures
- if (NS_FAILED(rv)) return rv;
-
- rv = uri->GetSpec(aURLSpec);
-
- // clear out the old spec, for security reasons - old data should
- // not be floating around in cached URIs!
- // (but avoid doing extra work if we're just destroying the uri)
- if (clearUri)
- uri->SetSpec(NS_LITERAL_CSTRING(""));
-
- return rv;
-}
-
NS_IMETHODIMP
-nsWebShell::GetLinkState(const nsACString& aLinkURI, nsLinkState& aState)
+nsWebShell::GetLinkState(nsIURI* aLinkURI, nsLinkState& aState)
{
+ if (!aLinkURI) {
+ // No uri means not a link
+ aState = eLinkState_NotLink;
+ return NS_OK;
+ }
+
aState = eLinkState_Unvisited;
// no history, leave state unchanged
if (!mGlobalHistory)
return NS_OK;
-
- // default to the given URI
- nsCAutoString resolvedPath(aLinkURI);
- nsresult rv;
- // get the cached IO service
- if (!mIOService)
- mIOService = do_GetService(NS_IOSERVICE_CONTRACTID, &rv);
-
- NormalizeURI(resolvedPath);
+ nsCAutoString spec;
+ aLinkURI->GetSpec(spec);
PRBool isVisited;
- NS_ENSURE_SUCCESS(mGlobalHistory->IsVisited(resolvedPath.get(), &isVisited),
+ NS_ENSURE_SUCCESS(mGlobalHistory->IsVisited(spec.get(), &isVisited),
NS_ERROR_FAILURE);
if (isVisited)
aState = eLinkState_Visited;
diff --git a/docshell/base/nsWebShell.h b/docshell/base/nsWebShell.h
index 66b18d5285de..731902fa9e96 100644
--- a/docshell/base/nsWebShell.h
+++ b/docshell/base/nsWebShell.h
@@ -87,7 +87,7 @@ public:
nsIURI* aURI,
const PRUnichar* aTargetSpec);
NS_IMETHOD OnLeaveLink();
- NS_IMETHOD GetLinkState(const nsACString& aLinkURI, nsLinkState& aState);
+ NS_IMETHOD GetLinkState(nsIURI* aLinkURI, nsLinkState& aState);
NS_IMETHOD Create();
NS_IMETHOD Destroy();
@@ -117,8 +117,6 @@ protected:
nsIChannel* channel,
nsresult aStatus);
- nsresult NormalizeURI(nsACString& aURLSpec);
-
PRThread *mThread;
nsIWebShellContainer* mContainer;
@@ -134,17 +132,6 @@ protected:
nsIStreamListener** aResult);
nsCOMPtr mCommandManager;
-
- // cached io service for NS_NewURI
- nsCOMPtr mIOService;
-
- // these are specifically cached for these
- // protocols, because we're optimizing for link coloring -
- // most links are http, https, or ftp
- nsCOMPtr mCachedHttpUrl;
- nsCOMPtr mCachedHttpsUrl;
- nsCOMPtr mCachedFtpUrl;
-
#ifdef DEBUG
private:
diff --git a/layout/style/nsStyleUtil.cpp b/layout/style/nsStyleUtil.cpp
index 903db3e8750b..7def156cbfc4 100644
--- a/layout/style/nsStyleUtil.cpp
+++ b/layout/style/nsStyleUtil.cpp
@@ -595,15 +595,14 @@ PRBool nsStyleUtil::IsHTMLLink(nsIContent *aContent, nsIAtom *aTag, nsIPresConte
// if there is no link, then this anchor is not really a linkpseudo.
// bug=23209
- nsXPIDLCString href;
- link->GetHrefUTF8(getter_Copies(href));
+ nsCOMPtr hrefURI;
+ link->GetHrefURI(getter_AddRefs(hrefURI));
- if (href) {
- nsILinkHandler *linkHandler = nsnull;
- aPresContext->GetLinkHandler(&linkHandler);
+ if (hrefURI) {
+ nsCOMPtr linkHandler;
+ aPresContext->GetLinkHandler(getter_AddRefs(linkHandler));
if (linkHandler) {
- linkHandler->GetLinkState(href, linkState);
- NS_RELEASE(linkHandler);
+ linkHandler->GetLinkState(hrefURI, linkState);
}
else {
// no link handler? then all links are unvisited
@@ -665,16 +664,14 @@ PRBool nsStyleUtil::IsSimpleXlink(nsIContent *aContent, nsIPresContext *aPresCon
}
}
- // convert here, rather than twice in NS_MakeAbsoluteURI and
- // back again
- nsCAutoString absHREF;
- (void) NS_MakeAbsoluteURI(absHREF, NS_ConvertUCS2toUTF8(val), baseURI);
+ nsCOMPtr absURI;
+ // XXX should we make sure to get the right charset off the document?
+ (void) NS_NewURI(getter_AddRefs(absURI), val, nsnull, baseURI);
- nsILinkHandler *linkHandler = nsnull;
- aPresContext->GetLinkHandler(&linkHandler);
+ nsCOMPtr linkHandler;
+ aPresContext->GetLinkHandler(getter_AddRefs(linkHandler));
if (linkHandler) {
- linkHandler->GetLinkState(absHREF, *aState);
- NS_RELEASE(linkHandler);
+ linkHandler->GetLinkState(absURI, *aState);
}
else {
// no link handler? then all links are unvisited
diff --git a/netwerk/base/src/nsStandardURL.cpp b/netwerk/base/src/nsStandardURL.cpp
index be763e2ec3c9..eed77249c0c9 100644
--- a/netwerk/base/src/nsStandardURL.cpp
+++ b/netwerk/base/src/nsStandardURL.cpp
@@ -2264,8 +2264,14 @@ nsStandardURL::Init(PRUint32 urlType,
else
mOriginCharset = charset;
- // an empty charset implies UTF-8
- if (mOriginCharset.EqualsIgnoreCase("UTF-8"))
+ // URI can't be encoded in UTF-16, UTF-16BE, UTF-16LE, UTF-32, UTF-32-LE,
+ // UTF-32LE, UTF-32BE (yet?). Truncate mOriginCharset if it starts with
+ // "utf" (since an empty mOriginCharset implies UTF-8, this is safe even if
+ // mOriginCharset is UTF-8).
+ if (mOriginCharset.Length() >= 3 &&
+ (mOriginCharset[0] == 'U' || mOriginCharset[0] == 'u') &&
+ (mOriginCharset[1] == 'T' || mOriginCharset[1] == 't') &&
+ (mOriginCharset[2] == 'F' || mOriginCharset[2] == 'f'))
mOriginCharset.Truncate();
if (baseURI) {
diff --git a/webshell/public/nsILinkHandler.h b/webshell/public/nsILinkHandler.h
index 74524877fb4f..db9de1cf7f1d 100644
--- a/webshell/public/nsILinkHandler.h
+++ b/webshell/public/nsILinkHandler.h
@@ -138,7 +138,7 @@ public:
/**
* Get the state of a link to a given absolute URL
*/
- NS_IMETHOD GetLinkState(const nsACString& aLinkURI, nsLinkState& aState) = 0;
+ NS_IMETHOD GetLinkState(nsIURI* aLinkURI, nsLinkState& aState) = 0;
};
#endif /* nsILinkHandler_h___ */