Index: sc/source/filter/inc/xicontent.hxx
===================================================================
RCS file: /cvs/sc/sc/source/filter/inc/xicontent.hxx,v
retrieving revision 1.14
diff -u -r1.14 xicontent.hxx
--- sc/source/filter/inc/xicontent.hxx	6 Jul 2007 12:38:28 -0000	1.14
+++ sc/source/filter/inc/xicontent.hxx	30 Aug 2007 04:23:19 -0000
@@ -110,6 +110,10 @@
 
     /** Inserts the URL into a range of cells. Does not modify value or formula cells. */
     static void         InsertUrl( const XclImpRoot& rRoot, const XclRange& rXclRange, const String& rUrl );
+
+    /** Convert the sheet name with invalid character(s) in URL when the URL is
+        to a location within the same document (e.g. #'Sheet&Name'.A1). */
+    static void         ConvertToValidTabName(String& rName);
 };
 
 // Label ranges ===============================================================
Index: sc/source/filter/excel/xicontent.cxx
===================================================================
RCS file: /cvs/sc/sc/source/filter/excel/xicontent.cxx,v
retrieving revision 1.28
diff -u -r1.28 xicontent.cxx
--- sc/source/filter/excel/xicontent.cxx	6 Jul 2007 12:37:07 -0000	1.28
+++ sc/source/filter/excel/xicontent.cxx	30 Aug 2007 04:23:25 -0000
@@ -407,8 +407,54 @@
     return String::EmptyString();
 }
 
+void XclImpHyperlink::ConvertToValidTabName(String& rUrl)
+{
+    xub_StrLen n = rUrl.Len();
+    if (n < 4)
+        // Needs at least 4 characters.
+        return;
+
+    sal_Unicode c = rUrl.GetChar(0);
+    if (c != sal_Unicode('#'))
+        // the 1st character must be '#'.
+        return;
+
+    String aNewUrl(sal_Unicode('#')), aTabName;
+
+    bool bInQuote = false;
+    for (xub_StrLen i = 1; i < n; ++i)
+    {
+        c = rUrl.GetChar(i);
+        if (c == sal_Unicode('\''))
+        {
+            bInQuote = !bInQuote;
+            if (!bInQuote && aTabName.Len() > 0)
+            {
+                // Sheet name exists.  Convert it to valid name the same way the
+                // sheet names are converted.
+                ScDocument::ConvertToValidTabName(aTabName, sal_Unicode('_'));
+                aNewUrl.Append(aTabName);
+            }
+        }
+        else if (bInQuote)
+            aTabName.Append(c);
+        else
+            aNewUrl.Append(c);
+    }
+
+    if (bInQuote)
+        // It should be outside the quotes!
+        return;
+
+    // All is good.  Pass the new URL.
+    rUrl = aNewUrl;
+}
+
 void XclImpHyperlink::InsertUrl( const XclImpRoot& rRoot, const XclRange& rXclRange, const String& rUrl )
 {
+    String aUrl(rUrl);
+    ConvertToValidTabName(aUrl);
+
     SCTAB nScTab = rRoot.GetCurrScTab();
     ScRange aScRange( ScAddress::UNINITIALIZED );
     if( rRoot.GetAddressConverter().ConvertRange( aScRange, rXclRange, nScTab, nScTab, true ) )
@@ -418,7 +464,7 @@
         aScRange.GetVars( nScCol1, nScRow1, nScTab, nScCol2, nScRow2, nScTab );
         for( SCCOL nScCol = nScCol1; nScCol <= nScCol2; ++nScCol )
             for( SCROW nScRow = nScRow1; nScRow <= nScRow2; ++nScRow )
-                lclInsertUrl( rRoot, rUrl, nScCol, nScRow, nScTab );
+                lclInsertUrl( rRoot, aUrl, nScCol, nScRow, nScTab );
     }
 }
 
