Back to index

lightning-sunbird  0.9+nobinonly
nsDOMClassInfo.cpp
Go to the documentation of this file.
00001 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
00002 /* vim: set ts=2 sw=2 et tw=78: */
00003 /* ***** BEGIN LICENSE BLOCK *****
00004  * Version: MPL 1.1/GPL 2.0/LGPL 2.1
00005  *
00006  * The contents of this file are subject to the Mozilla Public License Version
00007  * 1.1 (the "License"); you may not use this file except in compliance with
00008  * the License. You may obtain a copy of the License at
00009  * http://www.mozilla.org/MPL/
00010  *
00011  * Software distributed under the License is distributed on an "AS IS" basis,
00012  * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
00013  * for the specific language governing rights and limitations under the
00014  * License.
00015  *
00016  * The Original Code is mozilla.org code.
00017  *
00018  * The Initial Developer of the Original Code is
00019  * Netscape Communications Corporation.
00020  * Portions created by the Initial Developer are Copyright (C) 2000
00021  * the Initial Developer. All Rights Reserved.
00022  *
00023  * Contributor(s):
00024  *   Johnny Stenback <jst@netscape.com> (original author)
00025  *
00026  * Alternatively, the contents of this file may be used under the terms of
00027  * either of the GNU General Public License Version 2 or later (the "GPL"),
00028  * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
00029  * in which case the provisions of the GPL or the LGPL are applicable instead
00030  * of those above. If you wish to allow use of your version of this file only
00031  * under the terms of either the GPL or the LGPL, and not to allow others to
00032  * use your version of this file under the terms of the MPL, indicate your
00033  * decision by deleting the provisions above and replace them with the notice
00034  * and other provisions required by the GPL or the LGPL. If you do not delete
00035  * the provisions above, a recipient may use your version of this file under
00036  * the terms of any one of the MPL, the GPL or the LGPL.
00037  *
00038  * ***** END LICENSE BLOCK ***** */
00039 
00040 #include "nscore.h"
00041 #include "nsDOMClassInfo.h"
00042 #include "nsCRT.h"
00043 #include "nsIServiceManager.h"
00044 #include "nsICategoryManager.h"
00045 #include "nsIComponentRegistrar.h"
00046 #include "nsXPCOM.h"
00047 #include "nsISupportsPrimitives.h"
00048 #include "nsIXPConnect.h"
00049 #include "nsIJSContextStack.h"
00050 #include "nsIXPCSecurityManager.h"
00051 #include "nsIStringBundle.h"
00052 #include "nsIConsoleService.h"
00053 #include "nsIScriptError.h"
00054 #include "nsXPIDLString.h"
00055 #include "nsReadableUtils.h"
00056 #include "nsUnicharUtils.h"
00057 #include "xptcall.h"
00058 #include "prprf.h"
00059 #include "nsTArray.h"
00060 
00061 // JavaScript includes
00062 #include "jsapi.h"
00063 #include "jsnum.h"
00064 #include "jsdbgapi.h"
00065 #include "jscntxt.h"
00066 
00067 // General helper includes
00068 #include "nsGlobalWindow.h"
00069 #include "nsIContent.h"
00070 #include "nsIDocument.h"
00071 #include "nsIDOMDocument.h"
00072 #include "nsIDOM3Document.h"
00073 #include "nsIDOMXMLDocument.h"
00074 #include "nsIDOMNSDocument.h"
00075 #include "nsIDOMEvent.h"
00076 #include "nsIDOMNSEvent.h"
00077 #include "nsIDOMKeyEvent.h"
00078 #include "nsIDOMEventListener.h"
00079 #include "nsINodeInfo.h"
00080 #include "nsContentUtils.h"
00081 
00082 // Window scriptable helper includes
00083 #include "nsIDocShell.h"
00084 #include "nsIDocShellTreeItem.h"
00085 #include "nsIDocShellTreeNode.h"
00086 #include "nsIScriptExternalNameSet.h"
00087 #include "nsJSUtils.h"
00088 #include "nsIInterfaceRequestor.h"
00089 #include "nsIInterfaceRequestorUtils.h"
00090 #include "nsScriptNameSpaceManager.h"
00091 #include "nsIScriptObjectOwner.h"
00092 #include "nsIJSNativeInitializer.h"
00093 
00094 // DOM base includes
00095 #include "nsIDOMPluginArray.h"
00096 #include "nsIDOMPlugin.h"
00097 #include "nsIDOMMimeTypeArray.h"
00098 #include "nsIDOMMimeType.h"
00099 #include "nsIDOMNSLocation.h"
00100 #include "nsIDOMLocation.h"
00101 #include "nsIDOMWindowInternal.h"
00102 #include "nsPIDOMWindow.h"
00103 #include "nsIDOMJSWindow.h"
00104 #include "nsIDOMWindowCollection.h"
00105 #include "nsIDOMHistory.h"
00106 #include "nsIDOMNSHistory.h"
00107 #include "nsIDOMMediaList.h"
00108 #include "nsIDOMChromeWindow.h"
00109 #include "nsIDOMConstructor.h"
00110 
00111 // DOM core includes
00112 #include "nsDOMError.h"
00113 #include "nsIDOMDOMException.h"
00114 #include "nsIDOMNode.h"
00115 #include "nsIDOM3Node.h"
00116 #include "nsIDOMNodeList.h"
00117 #include "nsIDOMNamedNodeMap.h"
00118 #include "nsIDOMDOMStringList.h"
00119 #include "nsIDOMNameList.h"
00120 
00121 // HTMLFormElement helper includes
00122 #include "nsIForm.h"
00123 #include "nsIFormControl.h"
00124 #include "nsIDOMHTMLFormElement.h"
00125 #include "nsIDOMNSHTMLFormControlList.h"
00126 #include "nsIDOMHTMLCollection.h"
00127 #include "nsIHTMLDocument.h"
00128 
00129 // HTMLSelectElement helper includes
00130 #include "nsIDOMHTMLSelectElement.h"
00131 #include "nsIDOMNSXBLFormControl.h"
00132 
00133 // HTMLEmbed/ObjectElement helper includes
00134 #include "nsIPluginInstance.h"
00135 #include "nsIPluginInstanceInternal.h"
00136 #include "nsIObjectFrame.h"
00137 #include "nsIScriptablePlugin.h"
00138 #include "nsIPluginHost.h"
00139 #include "nsPIPluginHost.h"
00140 
00141 #ifdef OJI
00142 // HTMLAppletElement helper includes
00143 #include "nsIJVMManager.h"
00144 
00145 // Oh, did I mention that I hate Microsoft for doing this to me?
00146 #ifndef WINCE
00147 #undef GetClassName
00148 #endif
00149 
00150 #include "nsILiveConnectManager.h"
00151 #include "nsIJVMPluginInstance.h"
00152 #endif
00153 
00154 // HTMLOptionsCollection includes
00155 #include "nsIDOMHTMLOptionElement.h"
00156 #include "nsIDOMNSHTMLOptionElement.h"
00157 #include "nsIDOMHTMLOptionsCollection.h"
00158 #include "nsIDOMNSHTMLOptionCollectn.h"
00159 #include "nsIDOMHTMLOptionsCollection.h"
00160 
00161 // ContentList includes
00162 #include "nsContentList.h"
00163 
00164 // Event related includes
00165 #include "nsIEventListenerManager.h"
00166 #include "nsIDOMEventReceiver.h"
00167 #include "nsIDOMNSEventTarget.h"
00168 
00169 // CSS related includes
00170 #include "nsIDOMStyleSheet.h"
00171 #include "nsIDOMStyleSheetList.h"
00172 #include "nsIDOMCSSStyleDeclaration.h"
00173 #include "nsIDOMCSSRule.h"
00174 #include "nsIDOMCSSRuleList.h"
00175 #include "nsIDOMRect.h"
00176 #include "nsIDOMRGBColor.h"
00177 
00178 // XBL related includes.
00179 #include "nsIXBLService.h"
00180 #include "nsXBLBinding.h"
00181 #include "nsIBindingManager.h"
00182 #include "nsIFrame.h"
00183 #include "nsIPresShell.h"
00184 #include "nsIDOMViewCSS.h"
00185 #include "nsIDOMElement.h"
00186 #include "nsIDOMCSSStyleDeclaration.h"
00187 #include "nsIScriptGlobalObject.h"
00188 #include "nsStyleSet.h"
00189 #include "nsStyleContext.h"
00190 #include "nsAutoPtr.h"
00191 
00192 #include "nsIDOMLSProgressEvent.h"
00193 #include "nsIDOMParser.h"
00194 #include "nsIDOMSerializer.h"
00195 #include "nsIXMLHttpRequest.h"
00196 
00197 // includes needed for the prototype chain interfaces
00198 #include "nsIDOMNavigator.h"
00199 #include "nsIDOMBarProp.h"
00200 #include "nsIDOMScreen.h"
00201 #include "nsIDOMDocumentType.h"
00202 #include "nsIDOMDOMImplementation.h"
00203 #include "nsIDOMDocumentFragment.h"
00204 #include "nsIDOMDocumentEvent.h"
00205 #include "nsIDOMAttr.h"
00206 #include "nsIDOMText.h"
00207 #include "nsIDOMComment.h"
00208 #include "nsIDOMCDATASection.h"
00209 #include "nsIDOMProcessingInstruction.h"
00210 #include "nsIDOMEntity.h"
00211 #include "nsIDOMEntityReference.h"
00212 #include "nsIDOMNotation.h"
00213 #include "nsIDOMNSEvent.h"
00214 #include "nsIDOMKeyEvent.h"
00215 #include "nsIDOMMouseEvent.h"
00216 #include "nsIDOMPopupBlockedEvent.h"
00217 #include "nsIDOMBeforeUnloadEvent.h"
00218 #include "nsIDOMMutationEvent.h"
00219 #include "nsIDOMSmartCardEvent.h"
00220 #include "nsIDOMXULCommandEvent.h"
00221 #include "nsIDOMPageTransitionEvent.h"
00222 #include "nsIDOMNSDocumentStyle.h"
00223 #include "nsIDOMDocumentRange.h"
00224 #include "nsIDOMDocumentTraversal.h"
00225 #include "nsIDOMDocumentXBL.h"
00226 #include "nsIDOMDocumentView.h"
00227 #include "nsIDOMElementCSSInlineStyle.h"
00228 #include "nsIDOMLinkStyle.h"
00229 #include "nsIDOMHTMLDocument.h"
00230 #include "nsIDOMNSHTMLDocument.h"
00231 #include "nsIDOMNSHTMLElement.h"
00232 #include "nsIDOMHTMLAnchorElement.h"
00233 #include "nsIDOMNSHTMLAnchorElement.h"
00234 #include "nsIDOMHTMLAppletElement.h"
00235 #include "nsIDOMHTMLAreaElement.h"
00236 #include "nsIDOMNSHTMLAreaElement.h"
00237 #include "nsIDOMHTMLBRElement.h"
00238 #include "nsIDOMHTMLBaseElement.h"
00239 #include "nsIDOMHTMLBaseFontElement.h"
00240 #include "nsIDOMHTMLBodyElement.h"
00241 #include "nsIDOMHTMLButtonElement.h"
00242 #include "nsIDOMNSHTMLButtonElement.h"
00243 #include "nsIDOMHTMLCanvasElement.h"
00244 #include "nsIDOMHTMLDListElement.h"
00245 #include "nsIDOMHTMLDirectoryElement.h"
00246 #include "nsIDOMHTMLDivElement.h"
00247 #include "nsIDOMHTMLEmbedElement.h"
00248 #include "nsIDOMHTMLFieldSetElement.h"
00249 #include "nsIDOMHTMLFontElement.h"
00250 #include "nsIDOMNSHTMLFormElement.h"
00251 #include "nsIDOMHTMLFrameElement.h"
00252 #include "nsIDOMHTMLFrameSetElement.h"
00253 #include "nsIDOMNSHTMLFrameElement.h"
00254 #include "nsIDOMHTMLHRElement.h"
00255 #include "nsIDOMNSHTMLHRElement.h"
00256 #include "nsIDOMHTMLHeadElement.h"
00257 #include "nsIDOMHTMLHeadingElement.h"
00258 #include "nsIDOMHTMLHtmlElement.h"
00259 #include "nsIDOMHTMLIFrameElement.h"
00260 #include "nsIDOMHTMLImageElement.h"
00261 #include "nsIDOMNSHTMLImageElement.h"
00262 #include "nsIDOMHTMLInputElement.h"
00263 #include "nsIDOMNSHTMLInputElement.h"
00264 #include "nsIDOMHTMLIsIndexElement.h"
00265 #include "nsIDOMHTMLLIElement.h"
00266 #include "nsIDOMHTMLLabelElement.h"
00267 #include "nsIDOMHTMLLegendElement.h"
00268 #include "nsIDOMHTMLLinkElement.h"
00269 #include "nsIDOMHTMLMapElement.h"
00270 #include "nsIDOMHTMLMenuElement.h"
00271 #include "nsIDOMHTMLMetaElement.h"
00272 #include "nsIDOMHTMLModElement.h"
00273 #include "nsIDOMHTMLOListElement.h"
00274 #include "nsIDOMHTMLObjectElement.h"
00275 #include "nsIDOMHTMLOptGroupElement.h"
00276 #include "nsIDOMHTMLParagraphElement.h"
00277 #include "nsIDOMHTMLParamElement.h"
00278 #include "nsIDOMHTMLPreElement.h"
00279 #include "nsIDOMHTMLQuoteElement.h"
00280 #include "nsIDOMHTMLScriptElement.h"
00281 #include "nsIDOMNSHTMLSelectElement.h"
00282 #include "nsIDOMHTMLStyleElement.h"
00283 #include "nsIDOMHTMLTableCaptionElem.h"
00284 #include "nsIDOMHTMLTableCellElement.h"
00285 #include "nsIDOMHTMLTableColElement.h"
00286 #include "nsIDOMHTMLTableElement.h"
00287 #include "nsIDOMHTMLTableRowElement.h"
00288 #include "nsIDOMHTMLTableSectionElem.h"
00289 #include "nsIDOMHTMLTextAreaElement.h"
00290 #include "nsIDOMNSHTMLTextAreaElement.h"
00291 #include "nsIDOMHTMLTitleElement.h"
00292 #include "nsIDOMHTMLUListElement.h"
00293 #include "nsIDOMNSUIEvent.h"
00294 #include "nsIDOMCSS2Properties.h"
00295 #include "nsIDOMCSSCharsetRule.h"
00296 #include "nsIDOMCSSImportRule.h"
00297 #include "nsIDOMCSSMediaRule.h"
00298 #include "nsIDOMCSSMozDocumentRule.h"
00299 #include "nsIDOMCSSPrimitiveValue.h"
00300 #include "nsIDOMCSSStyleRule.h"
00301 #include "nsIDOMCSSStyleSheet.h"
00302 #include "nsIDOMCSSValueList.h"
00303 #include "nsIDOMRange.h"
00304 #include "nsIDOMNSRange.h"
00305 #include "nsIDOMRangeException.h"
00306 #include "nsIDOMTreeWalker.h"
00307 #include "nsIDOMXULDocument.h"
00308 #include "nsIDOMXULElement.h"
00309 #include "nsIDOMXULCommandDispatcher.h"
00310 #include "nsIDOMCrypto.h"
00311 #include "nsIDOMCRMFObject.h"
00312 #include "nsIDOMPkcs11.h"
00313 #include "nsIControllers.h"
00314 #include "nsISelection.h"
00315 #include "nsIBoxObject.h"
00316 #ifdef MOZ_XUL
00317 #include "nsITreeSelection.h"
00318 #include "nsITreeContentView.h"
00319 #include "nsITreeView.h"
00320 #include "nsIXULTemplateBuilder.h"
00321 #include "nsITreeColumns.h"
00322 #endif
00323 #include "nsIDOMXPathEvaluator.h"
00324 
00325 #ifdef MOZ_SVG
00326 #include "nsIDOMGetSVGDocument.h"
00327 #include "nsIDOMSVGAngle.h"
00328 #include "nsIDOMSVGAnimatedAngle.h"
00329 #include "nsIDOMSVGAnimatedEnum.h"
00330 #include "nsIDOMSVGAnimatedLength.h"
00331 #include "nsIDOMSVGAnimatedLengthList.h"
00332 #include "nsIDOMSVGAnimatedNumber.h"
00333 #include "nsIDOMSVGAnimatedNumberList.h"
00334 #include "nsIDOMSVGAnimatedPathData.h"
00335 #include "nsIDOMSVGAnimatedPoints.h"
00336 #include "nsIDOMSVGAnimPresAspRatio.h"
00337 #include "nsIDOMSVGAnimatedRect.h"
00338 #include "nsIDOMSVGAnimatedString.h"
00339 #include "nsIDOMSVGAnimTransformList.h"
00340 #include "nsIDOMSVGCircleElement.h"
00341 #include "nsIDOMSVGClipPathElement.h"
00342 #include "nsIDOMSVGDefsElement.h"
00343 #include "nsIDOMSVGDescElement.h"
00344 #include "nsIDOMSVGDocument.h"
00345 #include "nsIDOMSVGElement.h"
00346 #include "nsIDOMSVGEllipseElement.h"
00347 #include "nsIDOMSVGEvent.h"
00348 #include "nsIDOMSVGException.h"
00349 #include "nsIDOMSVGFitToViewBox.h"
00350 #ifdef MOZ_SVG_FOREIGNOBJECT
00351 #include "nsIDOMSVGForeignObjectElem.h"
00352 #endif
00353 #include "nsIDOMSVGGElement.h"
00354 #include "nsIDOMSVGGradientElement.h"
00355 #include "nsIDOMSVGImageElement.h"
00356 #include "nsIDOMSVGLength.h"
00357 #include "nsIDOMSVGLengthList.h"
00358 #include "nsIDOMSVGLineElement.h"
00359 #include "nsIDOMSVGLocatable.h"
00360 #include "nsIDOMSVGMarkerElement.h"
00361 #include "nsIDOMSVGMatrix.h"
00362 #include "nsIDOMSVGMetadataElement.h"
00363 #include "nsIDOMSVGNumber.h"
00364 #include "nsIDOMSVGNumberList.h"
00365 #include "nsIDOMSVGPathElement.h"
00366 #include "nsIDOMSVGPathSeg.h"
00367 #include "nsIDOMSVGPathSegList.h"
00368 #include "nsIDOMSVGPoint.h"
00369 #include "nsIDOMSVGPointList.h"
00370 #include "nsIDOMSVGPolygonElement.h"
00371 #include "nsIDOMSVGPolylineElement.h"
00372 #include "nsIDOMSVGPresAspectRatio.h"
00373 #include "nsIDOMSVGRect.h"
00374 #include "nsIDOMSVGRectElement.h"
00375 #include "nsIDOMSVGScriptElement.h"
00376 #include "nsIDOMSVGStopElement.h"
00377 #include "nsIDOMSVGStylable.h"
00378 #include "nsIDOMSVGStyleElement.h"
00379 #include "nsIDOMSVGSVGElement.h"
00380 #include "nsIDOMSVGSymbolElement.h"
00381 #include "nsIDOMSVGTextElement.h"
00382 #include "nsIDOMSVGTextPathElement.h"
00383 #include "nsIDOMSVGTitleElement.h"
00384 #include "nsIDOMSVGTransform.h"
00385 #include "nsIDOMSVGTransformable.h"
00386 #include "nsIDOMSVGTransformList.h"
00387 #include "nsIDOMSVGTSpanElement.h"
00388 #include "nsIDOMSVGURIReference.h"
00389 #include "nsIDOMSVGUseElement.h"
00390 #include "nsIDOMSVGZoomAndPan.h"
00391 #include "nsIDOMSVGZoomEvent.h"
00392 #endif // MOZ_SVG
00393 
00394 #ifdef MOZ_ENABLE_CANVAS
00395 #include "nsIDOMCanvasRenderingContext2D.h"
00396 #endif
00397 
00398 #include "nsIImageDocument.h"
00399 
00400 // Storage includes
00401 #include "nsIDOMStorage.h"
00402 #include "nsPIDOMStorage.h"
00403 #include "nsIDOMStorageList.h"
00404 #include "nsIDOMStorageItem.h"
00405 #include "nsIDOMStorageEvent.h"
00406 #include "nsIDOMToString.h"
00407 
00408 static NS_DEFINE_CID(kCPluginManagerCID, NS_PLUGINMANAGER_CID);
00409 static NS_DEFINE_CID(kDOMSOF_CID, NS_DOM_SCRIPT_OBJECT_FACTORY_CID);
00410 
00411 static const char kDOMStringBundleURL[] =
00412   "chrome://global/locale/dom/dom.properties";
00413 
00414 // NOTE: DEFAULT_SCRIPTABLE_FLAGS and DOM_DEFAULT_SCRIPTABLE_FLAGS
00415 //       are defined in nsIDOMClassInfo.h.
00416 
00417 #define GCPARTICIPANT_SCRIPTABLE_FLAGS                                        \
00418  (DOM_DEFAULT_SCRIPTABLE_FLAGS |                                              \
00419   nsIXPCScriptable::WANT_FINALIZE |                                           \
00420   nsIXPCScriptable::WANT_MARK)
00421 
00422 #define WINDOW_SCRIPTABLE_FLAGS                                               \
00423  (nsIXPCScriptable::WANT_GETPROPERTY |                                        \
00424   nsIXPCScriptable::WANT_SETPROPERTY |                                        \
00425   nsIXPCScriptable::WANT_PRECREATE |                                          \
00426   nsIXPCScriptable::WANT_FINALIZE |                                           \
00427   nsIXPCScriptable::WANT_ADDPROPERTY |                                        \
00428   nsIXPCScriptable::WANT_DELPROPERTY |                                        \
00429   nsIXPCScriptable::WANT_NEWENUMERATE |                                       \
00430   nsIXPCScriptable::WANT_MARK |                                               \
00431   nsIXPCScriptable::WANT_EQUALITY |                                           \
00432   nsIXPCScriptable::WANT_OUTER_OBJECT |                                       \
00433   nsIXPCScriptable::WANT_INNER_OBJECT |                                       \
00434   nsIXPCScriptable::DONT_ENUM_QUERY_INTERFACE)
00435 
00436 #define NODE_SCRIPTABLE_FLAGS                                                 \
00437  ((GCPARTICIPANT_SCRIPTABLE_FLAGS |                                           \
00438    nsIXPCScriptable::WANT_PRECREATE |                                         \
00439    nsIXPCScriptable::WANT_ADDPROPERTY |                                       \
00440    nsIXPCScriptable::WANT_SETPROPERTY) &                                      \
00441   ~nsIXPCScriptable::USE_JSSTUB_FOR_ADDPROPERTY)
00442 
00443 // We need to let JavaScript QI elements to interfaces that are not in
00444 // the classinfo since XBL can be used to dynamically implement new
00445 // unknown interfaces on elements, accessibility relies on this being
00446 // possible.
00447 
00448 #define ELEMENT_SCRIPTABLE_FLAGS                                              \
00449   (NODE_SCRIPTABLE_FLAGS & ~nsIXPCScriptable::CLASSINFO_INTERFACES_ONLY)
00450 
00451 #define FRAME_ELEMENT_SCRIPTABLE_FLAGS                                        \
00452   (ELEMENT_SCRIPTABLE_FLAGS |                                                 \
00453    nsIXPCScriptable::WANT_DELPROPERTY)
00454 
00455 #define EXTERNAL_OBJ_SCRIPTABLE_FLAGS                                         \
00456   (ELEMENT_SCRIPTABLE_FLAGS & ~nsIXPCScriptable::USE_JSSTUB_FOR_SETPROPERTY | \
00457    nsIXPCScriptable::WANT_GETPROPERTY |                                       \
00458    nsIXPCScriptable::WANT_SETPROPERTY |                                       \
00459    nsIXPCScriptable::WANT_CALL)
00460 
00461 #define DOCUMENT_SCRIPTABLE_FLAGS                                             \
00462   (NODE_SCRIPTABLE_FLAGS |                                                    \
00463    nsIXPCScriptable::WANT_ADDPROPERTY |                                       \
00464    nsIXPCScriptable::WANT_DELPROPERTY |                                       \
00465    nsIXPCScriptable::WANT_GETPROPERTY |                                       \
00466    nsIXPCScriptable::WANT_POSTCREATE)
00467 
00468 #define ARRAY_SCRIPTABLE_FLAGS                                                \
00469   (DOM_DEFAULT_SCRIPTABLE_FLAGS       |                                       \
00470    nsIXPCScriptable::WANT_GETPROPERTY |                                       \
00471    nsIXPCScriptable::WANT_ENUMERATE)
00472 
00473 #define DOMCLASSINFO_STANDARD_FLAGS                                           \
00474   (nsIClassInfo::MAIN_THREAD_ONLY | nsIClassInfo::DOM_OBJECT)
00475 
00476 
00477 #ifdef NS_DEBUG
00478 #define NS_DEFINE_CLASSINFO_DATA_DEBUG(_class)                                \
00479     eDOMClassInfo_##_class##_id,
00480 #else
00481 #define NS_DEFINE_CLASSINFO_DATA_DEBUG(_class)                                \
00482   // nothing
00483 #endif
00484 
00485 
00486 #define NS_DEFINE_CLASSINFO_DATA_WITH_NAME(_class, _name, _helper,            \
00487                                            _flags)                            \
00488   { #_name,                                                                   \
00489     { _helper::doCreate },                                                    \
00490     nsnull,                                                                   \
00491     nsnull,                                                                   \
00492     nsnull,                                                                   \
00493     _flags,                                                                   \
00494     PR_TRUE,                                                                  \
00495     NS_DEFINE_CLASSINFO_DATA_DEBUG(_class)                                    \
00496   },
00497 
00498 #define NS_DEFINE_CLASSINFO_DATA(_class, _helper, _flags)                     \
00499   NS_DEFINE_CLASSINFO_DATA_WITH_NAME(_class, _class, _helper, _flags)
00500 
00501 
00502 // This list of NS_DEFINE_CLASSINFO_DATA macros is what gives the DOM
00503 // classes their correct behavior when used through XPConnect. The
00504 // arguments that are passed to NS_DEFINE_CLASSINFO_DATA are
00505 //
00506 // 1. Class name as it should appear in JavaScript, this name is also
00507 //    used to find the id of the class in nsDOMClassInfo
00508 //    (i.e. e<classname>_id)
00509 // 2. Scriptable helper class
00510 // 3. nsIClassInfo/nsIXPCScriptable flags (i.e. for GetScriptableFlags)
00511 
00512 static nsDOMClassInfoData sClassInfoData[] = {
00513   // Base classes
00514 
00515   // The Window class lets you QI into interfaces that are not in the
00516   // flattened set (i.e. nsIXPCScriptable::CLASSINFO_INTERFACES_ONLY
00517   // is not set), because of this make sure all scriptable interfaces
00518   // that are implemented by nsGlobalWindow can securely be exposed
00519   // to JS.
00520 
00521 
00522   NS_DEFINE_CLASSINFO_DATA(Window, nsWindowSH,
00523                            DEFAULT_SCRIPTABLE_FLAGS |
00524                            WINDOW_SCRIPTABLE_FLAGS)
00525 
00526   // Don't allow modifications to Location.prototype
00527   NS_DEFINE_CLASSINFO_DATA(Location, nsLocationSH,
00528                            (DOM_DEFAULT_SCRIPTABLE_FLAGS |
00529                             nsIXPCScriptable::WANT_PRECREATE) &
00530                            ~nsIXPCScriptable::ALLOW_PROP_MODS_TO_PROTOTYPE)
00531 
00532   NS_DEFINE_CLASSINFO_DATA(Navigator, nsNavigatorSH,
00533                            DOM_DEFAULT_SCRIPTABLE_FLAGS |
00534                            nsIXPCScriptable::WANT_PRECREATE)
00535   NS_DEFINE_CLASSINFO_DATA(Plugin, nsPluginSH,
00536                            ARRAY_SCRIPTABLE_FLAGS)
00537   NS_DEFINE_CLASSINFO_DATA(PluginArray, nsPluginArraySH,
00538                            ARRAY_SCRIPTABLE_FLAGS)
00539   NS_DEFINE_CLASSINFO_DATA(MimeType, nsDOMGenericSH,
00540                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00541   NS_DEFINE_CLASSINFO_DATA(MimeTypeArray, nsMimeTypeArraySH,
00542                            ARRAY_SCRIPTABLE_FLAGS)
00543   NS_DEFINE_CLASSINFO_DATA(BarProp, nsDOMGenericSH,
00544                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00545   NS_DEFINE_CLASSINFO_DATA(History, nsHistorySH,
00546                            ARRAY_SCRIPTABLE_FLAGS)
00547   NS_DEFINE_CLASSINFO_DATA(Screen, nsDOMGenericSH,
00548                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00549 
00550   // Core classes
00551   NS_DEFINE_CLASSINFO_DATA(XMLDocument, nsDocumentSH,
00552                            DOCUMENT_SCRIPTABLE_FLAGS |
00553                            nsIXPCScriptable::WANT_ENUMERATE)
00554   NS_DEFINE_CLASSINFO_DATA(DocumentType, nsNodeSH,
00555                            NODE_SCRIPTABLE_FLAGS)
00556   NS_DEFINE_CLASSINFO_DATA(DOMImplementation, nsDOMGenericSH,
00557                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00558   NS_DEFINE_CLASSINFO_DATA(DOMException, nsDOMGenericSH,
00559                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00560   NS_DEFINE_CLASSINFO_DATA(DocumentFragment, nsDOMGenericSH,
00561                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00562   NS_DEFINE_CLASSINFO_DATA(Element, nsElementSH,
00563                            ELEMENT_SCRIPTABLE_FLAGS)
00564   NS_DEFINE_CLASSINFO_DATA(Attr, nsDOMGenericSH,
00565                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00566   NS_DEFINE_CLASSINFO_DATA(Text, nsNodeSH,
00567                            NODE_SCRIPTABLE_FLAGS)
00568   NS_DEFINE_CLASSINFO_DATA(Comment, nsNodeSH,
00569                            NODE_SCRIPTABLE_FLAGS)
00570   NS_DEFINE_CLASSINFO_DATA(CDATASection, nsNodeSH, NODE_SCRIPTABLE_FLAGS)
00571   NS_DEFINE_CLASSINFO_DATA(ProcessingInstruction, nsNodeSH,
00572                            NODE_SCRIPTABLE_FLAGS)
00573   NS_DEFINE_CLASSINFO_DATA(Entity, nsNodeSH, NODE_SCRIPTABLE_FLAGS)
00574   NS_DEFINE_CLASSINFO_DATA(EntityReference, nsNodeSH, NODE_SCRIPTABLE_FLAGS)
00575   NS_DEFINE_CLASSINFO_DATA(Notation, nsNodeSH, NODE_SCRIPTABLE_FLAGS)
00576   NS_DEFINE_CLASSINFO_DATA(NodeList, nsArraySH, ARRAY_SCRIPTABLE_FLAGS)
00577   NS_DEFINE_CLASSINFO_DATA(NamedNodeMap, nsNamedNodeMapSH,
00578                            ARRAY_SCRIPTABLE_FLAGS)
00579 
00580   // Misc Core related classes
00581 
00582   // StyleSheet classes
00583   NS_DEFINE_CLASSINFO_DATA_WITH_NAME(DocumentStyleSheetList, StyleSheetList,
00584                                      nsStyleSheetListSH,
00585                                      ARRAY_SCRIPTABLE_FLAGS)
00586 
00587   // Event
00588   NS_DEFINE_CLASSINFO_DATA(Event, nsDOMGenericSH,
00589                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00590   NS_DEFINE_CLASSINFO_DATA(MutationEvent, nsDOMGenericSH,
00591                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00592   NS_DEFINE_CLASSINFO_DATA(UIEvent, nsDOMGenericSH,
00593                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00594   NS_DEFINE_CLASSINFO_DATA(MouseEvent, nsDOMGenericSH,
00595                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00596   NS_DEFINE_CLASSINFO_DATA(KeyboardEvent, nsDOMGenericSH,
00597                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00598   NS_DEFINE_CLASSINFO_DATA(PopupBlockedEvent, nsDOMGenericSH,
00599                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00600 
00601   // Misc HTML classes
00602   NS_DEFINE_CLASSINFO_DATA(HTMLDocument, nsHTMLDocumentSH,
00603                            DOCUMENT_SCRIPTABLE_FLAGS |
00604                            nsIXPCScriptable::WANT_ENUMERATE)
00605   NS_DEFINE_CLASSINFO_DATA(HTMLCollection, nsHTMLCollectionSH,
00606                            ARRAY_SCRIPTABLE_FLAGS)
00607   NS_DEFINE_CLASSINFO_DATA(HTMLOptionsCollection,
00608                            nsHTMLOptionsCollectionSH,
00609                            ARRAY_SCRIPTABLE_FLAGS |
00610                            nsIXPCScriptable::WANT_SETPROPERTY)
00611   NS_DEFINE_CLASSINFO_DATA_WITH_NAME(HTMLFormControlCollection, HTMLCollection,
00612                                      nsFormControlListSH,
00613                                      ARRAY_SCRIPTABLE_FLAGS)
00614   NS_DEFINE_CLASSINFO_DATA_WITH_NAME(HTMLGenericCollection, HTMLCollection,
00615                                      nsHTMLCollectionSH,
00616                                      ARRAY_SCRIPTABLE_FLAGS)
00617 
00618   // HTML element classes
00619   NS_DEFINE_CLASSINFO_DATA(HTMLAnchorElement, nsHTMLElementSH,
00620                            ELEMENT_SCRIPTABLE_FLAGS)
00621   NS_DEFINE_CLASSINFO_DATA(HTMLAppletElement, nsHTMLAppletElementSH,
00622                            EXTERNAL_OBJ_SCRIPTABLE_FLAGS)
00623   NS_DEFINE_CLASSINFO_DATA(HTMLAreaElement, nsHTMLElementSH,
00624                            ELEMENT_SCRIPTABLE_FLAGS)
00625   NS_DEFINE_CLASSINFO_DATA(HTMLBRElement, nsHTMLElementSH,
00626                            ELEMENT_SCRIPTABLE_FLAGS)
00627   NS_DEFINE_CLASSINFO_DATA(HTMLBaseElement, nsHTMLElementSH,
00628                            ELEMENT_SCRIPTABLE_FLAGS)
00629   NS_DEFINE_CLASSINFO_DATA(HTMLBaseFontElement, nsHTMLElementSH,
00630                            ELEMENT_SCRIPTABLE_FLAGS)
00631   NS_DEFINE_CLASSINFO_DATA(HTMLBodyElement, nsHTMLElementSH,
00632                            ELEMENT_SCRIPTABLE_FLAGS)
00633   NS_DEFINE_CLASSINFO_DATA(HTMLButtonElement, nsHTMLElementSH,
00634                            ELEMENT_SCRIPTABLE_FLAGS)
00635   NS_DEFINE_CLASSINFO_DATA(HTMLDListElement, nsHTMLElementSH,
00636                            ELEMENT_SCRIPTABLE_FLAGS)
00637   NS_DEFINE_CLASSINFO_DATA(HTMLDelElement, nsHTMLElementSH,
00638                            ELEMENT_SCRIPTABLE_FLAGS)
00639   NS_DEFINE_CLASSINFO_DATA(HTMLDirectoryElement, nsHTMLElementSH,
00640                            ELEMENT_SCRIPTABLE_FLAGS)
00641   NS_DEFINE_CLASSINFO_DATA(HTMLDivElement, nsHTMLElementSH,
00642                            ELEMENT_SCRIPTABLE_FLAGS)
00643   NS_DEFINE_CLASSINFO_DATA(HTMLEmbedElement, nsHTMLPluginObjElementSH,
00644                            EXTERNAL_OBJ_SCRIPTABLE_FLAGS)
00645   NS_DEFINE_CLASSINFO_DATA(HTMLFieldSetElement, nsHTMLElementSH,
00646                            ELEMENT_SCRIPTABLE_FLAGS)
00647   NS_DEFINE_CLASSINFO_DATA(HTMLFontElement, nsHTMLElementSH,
00648                            ELEMENT_SCRIPTABLE_FLAGS)
00649   NS_DEFINE_CLASSINFO_DATA(HTMLFormElement, nsHTMLFormElementSH,
00650                            ELEMENT_SCRIPTABLE_FLAGS |
00651                            nsIXPCScriptable::WANT_GETPROPERTY |
00652                            nsIXPCScriptable::WANT_NEWENUMERATE)
00653   NS_DEFINE_CLASSINFO_DATA(HTMLFrameElement, nsHTMLFrameElementSH,
00654                            FRAME_ELEMENT_SCRIPTABLE_FLAGS)
00655   NS_DEFINE_CLASSINFO_DATA(HTMLFrameSetElement, nsHTMLElementSH,
00656                            ELEMENT_SCRIPTABLE_FLAGS)
00657   NS_DEFINE_CLASSINFO_DATA(HTMLHRElement, nsHTMLElementSH,
00658                            ELEMENT_SCRIPTABLE_FLAGS)
00659   NS_DEFINE_CLASSINFO_DATA(HTMLHeadElement, nsHTMLElementSH,
00660                            ELEMENT_SCRIPTABLE_FLAGS)
00661   NS_DEFINE_CLASSINFO_DATA(HTMLHeadingElement, nsHTMLElementSH,
00662                            ELEMENT_SCRIPTABLE_FLAGS)
00663   NS_DEFINE_CLASSINFO_DATA(HTMLHtmlElement, nsHTMLElementSH,
00664                            ELEMENT_SCRIPTABLE_FLAGS)
00665   NS_DEFINE_CLASSINFO_DATA(HTMLIFrameElement, nsHTMLFrameElementSH,
00666                            FRAME_ELEMENT_SCRIPTABLE_FLAGS)
00667   NS_DEFINE_CLASSINFO_DATA(HTMLImageElement, nsHTMLElementSH,
00668                            ELEMENT_SCRIPTABLE_FLAGS)
00669   NS_DEFINE_CLASSINFO_DATA(HTMLInputElement, nsHTMLElementSH,
00670                            ELEMENT_SCRIPTABLE_FLAGS)
00671   NS_DEFINE_CLASSINFO_DATA(HTMLInsElement, nsHTMLElementSH,
00672                            ELEMENT_SCRIPTABLE_FLAGS)
00673   NS_DEFINE_CLASSINFO_DATA(HTMLIsIndexElement, nsHTMLElementSH,
00674                            ELEMENT_SCRIPTABLE_FLAGS)
00675   NS_DEFINE_CLASSINFO_DATA(HTMLLIElement, nsHTMLElementSH,
00676                            ELEMENT_SCRIPTABLE_FLAGS)
00677   NS_DEFINE_CLASSINFO_DATA(HTMLLabelElement, nsHTMLElementSH,
00678                            ELEMENT_SCRIPTABLE_FLAGS)
00679   NS_DEFINE_CLASSINFO_DATA(HTMLLegendElement, nsHTMLElementSH,
00680                            ELEMENT_SCRIPTABLE_FLAGS)
00681   NS_DEFINE_CLASSINFO_DATA(HTMLLinkElement, nsHTMLElementSH,
00682                            ELEMENT_SCRIPTABLE_FLAGS)
00683   NS_DEFINE_CLASSINFO_DATA(HTMLMapElement, nsHTMLElementSH,
00684                            ELEMENT_SCRIPTABLE_FLAGS)
00685   NS_DEFINE_CLASSINFO_DATA(HTMLMenuElement, nsHTMLElementSH,
00686                            ELEMENT_SCRIPTABLE_FLAGS)
00687   NS_DEFINE_CLASSINFO_DATA(HTMLMetaElement, nsHTMLElementSH,
00688                            ELEMENT_SCRIPTABLE_FLAGS)
00689   NS_DEFINE_CLASSINFO_DATA(HTMLModElement, nsHTMLElementSH,
00690                            ELEMENT_SCRIPTABLE_FLAGS)
00691   NS_DEFINE_CLASSINFO_DATA(HTMLOListElement, nsHTMLElementSH,
00692                            ELEMENT_SCRIPTABLE_FLAGS)
00693   NS_DEFINE_CLASSINFO_DATA(HTMLObjectElement, nsHTMLPluginObjElementSH,
00694                            EXTERNAL_OBJ_SCRIPTABLE_FLAGS)
00695   NS_DEFINE_CLASSINFO_DATA(HTMLOptGroupElement, nsHTMLElementSH,
00696                            ELEMENT_SCRIPTABLE_FLAGS)
00697   NS_DEFINE_CLASSINFO_DATA(HTMLOptionElement, nsHTMLElementSH,
00698                            ELEMENT_SCRIPTABLE_FLAGS)
00699   NS_DEFINE_CLASSINFO_DATA(HTMLParagraphElement, nsHTMLElementSH,
00700                            ELEMENT_SCRIPTABLE_FLAGS)
00701   NS_DEFINE_CLASSINFO_DATA(HTMLParamElement, nsHTMLElementSH,
00702                            ELEMENT_SCRIPTABLE_FLAGS)
00703   NS_DEFINE_CLASSINFO_DATA(HTMLPreElement, nsHTMLElementSH,
00704                            ELEMENT_SCRIPTABLE_FLAGS)
00705   NS_DEFINE_CLASSINFO_DATA(HTMLQuoteElement, nsHTMLElementSH,
00706                            ELEMENT_SCRIPTABLE_FLAGS)
00707   NS_DEFINE_CLASSINFO_DATA(HTMLScriptElement, nsHTMLElementSH,
00708                            ELEMENT_SCRIPTABLE_FLAGS)
00709   NS_DEFINE_CLASSINFO_DATA(HTMLSelectElement, nsHTMLSelectElementSH,
00710                            ELEMENT_SCRIPTABLE_FLAGS |
00711                            nsIXPCScriptable::WANT_GETPROPERTY)
00712   NS_DEFINE_CLASSINFO_DATA(HTMLSpacerElement, nsHTMLElementSH,
00713                            ELEMENT_SCRIPTABLE_FLAGS)
00714   NS_DEFINE_CLASSINFO_DATA(HTMLSpanElement, nsHTMLElementSH,
00715                            ELEMENT_SCRIPTABLE_FLAGS)
00716   NS_DEFINE_CLASSINFO_DATA(HTMLStyleElement, nsHTMLElementSH,
00717                            ELEMENT_SCRIPTABLE_FLAGS)
00718   NS_DEFINE_CLASSINFO_DATA(HTMLTableCaptionElement, nsHTMLElementSH,
00719                            ELEMENT_SCRIPTABLE_FLAGS)
00720   NS_DEFINE_CLASSINFO_DATA(HTMLTableCellElement, nsHTMLElementSH,
00721                            ELEMENT_SCRIPTABLE_FLAGS)
00722   NS_DEFINE_CLASSINFO_DATA(HTMLTableColElement, nsHTMLElementSH,
00723                            ELEMENT_SCRIPTABLE_FLAGS)
00724   NS_DEFINE_CLASSINFO_DATA(HTMLTableColGroupElement, nsHTMLElementSH,
00725                            ELEMENT_SCRIPTABLE_FLAGS)
00726   NS_DEFINE_CLASSINFO_DATA(HTMLTableElement, nsHTMLElementSH,
00727                            ELEMENT_SCRIPTABLE_FLAGS)
00728   NS_DEFINE_CLASSINFO_DATA(HTMLTableRowElement, nsHTMLElementSH,
00729                            ELEMENT_SCRIPTABLE_FLAGS)
00730   NS_DEFINE_CLASSINFO_DATA(HTMLTableSectionElement, nsHTMLElementSH,
00731                            ELEMENT_SCRIPTABLE_FLAGS)
00732   NS_DEFINE_CLASSINFO_DATA(HTMLTextAreaElement, nsHTMLElementSH,
00733                            ELEMENT_SCRIPTABLE_FLAGS)
00734   NS_DEFINE_CLASSINFO_DATA(HTMLTitleElement, nsHTMLElementSH,
00735                            ELEMENT_SCRIPTABLE_FLAGS)
00736   NS_DEFINE_CLASSINFO_DATA(HTMLUListElement, nsHTMLElementSH,
00737                            ELEMENT_SCRIPTABLE_FLAGS)
00738   NS_DEFINE_CLASSINFO_DATA(HTMLUnknownElement, nsHTMLElementSH,
00739                            ELEMENT_SCRIPTABLE_FLAGS)
00740   NS_DEFINE_CLASSINFO_DATA(HTMLWBRElement, nsHTMLElementSH,
00741                            ELEMENT_SCRIPTABLE_FLAGS)
00742 
00743   // CSS classes
00744   NS_DEFINE_CLASSINFO_DATA(CSSStyleRule, nsDOMGenericSH,
00745                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00746   NS_DEFINE_CLASSINFO_DATA(CSSCharsetRule, nsDOMGenericSH,
00747                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00748   NS_DEFINE_CLASSINFO_DATA(CSSImportRule, nsDOMGenericSH,
00749                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00750   NS_DEFINE_CLASSINFO_DATA(CSSMediaRule, nsDOMGenericSH,
00751                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00752   NS_DEFINE_CLASSINFO_DATA(CSSNameSpaceRule, nsDOMGenericSH,
00753                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00754   NS_DEFINE_CLASSINFO_DATA(CSSRuleList, nsCSSRuleListSH,
00755                            ARRAY_SCRIPTABLE_FLAGS)
00756   NS_DEFINE_CLASSINFO_DATA(CSSGroupRuleRuleList, nsCSSRuleListSH,
00757                            ARRAY_SCRIPTABLE_FLAGS)
00758   NS_DEFINE_CLASSINFO_DATA(MediaList, nsMediaListSH,
00759                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00760   NS_DEFINE_CLASSINFO_DATA(StyleSheetList, nsDOMGenericSH,
00761                            ARRAY_SCRIPTABLE_FLAGS)
00762   NS_DEFINE_CLASSINFO_DATA(CSSStyleSheet, nsDOMGenericSH,
00763                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00764   NS_DEFINE_CLASSINFO_DATA(CSSStyleDeclaration, nsCSSStyleDeclSH,
00765                            ARRAY_SCRIPTABLE_FLAGS)
00766   NS_DEFINE_CLASSINFO_DATA(ComputedCSSStyleDeclaration, nsCSSStyleDeclSH,
00767                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00768   NS_DEFINE_CLASSINFO_DATA(ROCSSPrimitiveValue, nsDOMGenericSH,
00769                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00770 
00771   // Range classes
00772   NS_DEFINE_CLASSINFO_DATA(Range, nsDOMGenericSH,
00773                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00774   NS_DEFINE_CLASSINFO_DATA(Selection, nsDOMGenericSH,
00775                            DEFAULT_SCRIPTABLE_FLAGS)
00776 
00777   // XUL classes
00778 #ifdef MOZ_XUL
00779   NS_DEFINE_CLASSINFO_DATA(XULDocument, nsDocumentSH,
00780                            DOCUMENT_SCRIPTABLE_FLAGS |
00781                            nsIXPCScriptable::WANT_ENUMERATE)
00782   NS_DEFINE_CLASSINFO_DATA(XULElement, nsElementSH,
00783                            ELEMENT_SCRIPTABLE_FLAGS)
00784   NS_DEFINE_CLASSINFO_DATA(XULCommandDispatcher, nsDOMGenericSH,
00785                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00786   NS_DEFINE_CLASSINFO_DATA_WITH_NAME(XULNodeList, NodeList, nsArraySH,
00787                                      ARRAY_SCRIPTABLE_FLAGS)
00788   NS_DEFINE_CLASSINFO_DATA_WITH_NAME(XULNamedNodeMap, NamedNodeMap,
00789                                      nsNamedNodeMapSH, ARRAY_SCRIPTABLE_FLAGS)
00790   NS_DEFINE_CLASSINFO_DATA_WITH_NAME(XULAttr, Attr, nsDOMGenericSH,
00791                                      DOM_DEFAULT_SCRIPTABLE_FLAGS)
00792 #endif
00793   NS_DEFINE_CLASSINFO_DATA(XULControllers, nsNonDOMObjectSH,
00794                            DEFAULT_SCRIPTABLE_FLAGS)
00795 #ifdef MOZ_XUL
00796   NS_DEFINE_CLASSINFO_DATA(BoxObject, nsDOMGenericSH,
00797                            DEFAULT_SCRIPTABLE_FLAGS)
00798   NS_DEFINE_CLASSINFO_DATA(TreeSelection, nsDOMGenericSH,
00799                            DEFAULT_SCRIPTABLE_FLAGS)
00800   NS_DEFINE_CLASSINFO_DATA(TreeContentView, nsDOMGenericSH,
00801                            DEFAULT_SCRIPTABLE_FLAGS)
00802 #endif
00803 
00804   // Crypto classes
00805   NS_DEFINE_CLASSINFO_DATA(Crypto, nsDOMGenericSH,
00806                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00807   NS_DEFINE_CLASSINFO_DATA(CRMFObject, nsDOMGenericSH,
00808                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00809   NS_DEFINE_CLASSINFO_DATA(Pkcs11, nsDOMGenericSH,
00810                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00811 
00812   // DOM Traversal classes
00813   NS_DEFINE_CLASSINFO_DATA(TreeWalker, nsDOMGCParticipantSH,
00814                            GCPARTICIPANT_SCRIPTABLE_FLAGS)
00815 
00816   // We are now trying to preserve binary compat in classinfo.  No
00817   // more putting things in those categories up there.  New entries
00818   // are to be added to the end of the list
00819   NS_DEFINE_CLASSINFO_DATA(CSSRect, nsDOMGenericSH,
00820                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00821 
00822   // DOM Chrome Window class.
00823   NS_DEFINE_CLASSINFO_DATA(ChromeWindow, nsWindowSH,
00824                            DEFAULT_SCRIPTABLE_FLAGS |
00825                            WINDOW_SCRIPTABLE_FLAGS)
00826 
00827   NS_DEFINE_CLASSINFO_DATA(CSSRGBColor, nsDOMGenericSH,
00828                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00829 
00830   NS_DEFINE_CLASSINFO_DATA(RangeException, nsDOMGenericSH,
00831                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00832 
00833   NS_DEFINE_CLASSINFO_DATA(CSSValueList, nsCSSValueListSH,
00834                            ARRAY_SCRIPTABLE_FLAGS)
00835 
00836   NS_DEFINE_CLASSINFO_DATA_WITH_NAME(ContentList, HTMLCollection,
00837                                      nsContentListSH,
00838                                      ARRAY_SCRIPTABLE_FLAGS |
00839                                      nsIXPCScriptable::WANT_PRECREATE)
00840 
00841   NS_DEFINE_CLASSINFO_DATA(XMLStylesheetProcessingInstruction, nsNodeSH,
00842                            NODE_SCRIPTABLE_FLAGS)
00843 
00844   NS_DEFINE_CLASSINFO_DATA(ImageDocument, nsHTMLDocumentSH,
00845                            DOCUMENT_SCRIPTABLE_FLAGS |
00846                            nsIXPCScriptable::WANT_ENUMERATE)
00847 
00848 #ifdef MOZ_XUL
00849   NS_DEFINE_CLASSINFO_DATA(XULTemplateBuilder, nsDOMGenericSH,
00850                            DEFAULT_SCRIPTABLE_FLAGS)
00851 
00852   NS_DEFINE_CLASSINFO_DATA(XULTreeBuilder, nsDOMGenericSH,
00853                            DEFAULT_SCRIPTABLE_FLAGS)
00854 #endif
00855 
00856   NS_DEFINE_CLASSINFO_DATA(DOMStringList, nsStringListSH,
00857                            ARRAY_SCRIPTABLE_FLAGS)
00858 
00859   NS_DEFINE_CLASSINFO_DATA(NameList, nsDOMGenericSH,
00860                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00861 
00862 #ifdef MOZ_XUL
00863   NS_DEFINE_CLASSINFO_DATA(TreeColumn, nsDOMGenericSH,
00864                            DEFAULT_SCRIPTABLE_FLAGS)
00865 
00866   NS_DEFINE_CLASSINFO_DATA(TreeColumns, nsTreeColumnsSH,
00867                            ARRAY_SCRIPTABLE_FLAGS)
00868 #endif
00869 
00870   NS_DEFINE_CLASSINFO_DATA(CSSMozDocumentRule, nsDOMGenericSH,
00871                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00872 
00873   NS_DEFINE_CLASSINFO_DATA(BeforeUnloadEvent, nsDOMGenericSH,
00874                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00875 
00876 #ifdef MOZ_SVG
00877   // SVG document
00878   NS_DEFINE_CLASSINFO_DATA(SVGDocument, nsDocumentSH,
00879                            DOCUMENT_SCRIPTABLE_FLAGS)
00880 
00881   // SVG element classes
00882   NS_DEFINE_CLASSINFO_DATA(SVGCircleElement, nsElementSH,
00883                            ELEMENT_SCRIPTABLE_FLAGS)
00884   NS_DEFINE_CLASSINFO_DATA(SVGClipPathElement, nsElementSH,
00885                            ELEMENT_SCRIPTABLE_FLAGS)
00886   NS_DEFINE_CLASSINFO_DATA(SVGDefsElement, nsElementSH,
00887                            ELEMENT_SCRIPTABLE_FLAGS)
00888   NS_DEFINE_CLASSINFO_DATA(SVGDescElement, nsElementSH,
00889                            ELEMENT_SCRIPTABLE_FLAGS)
00890   NS_DEFINE_CLASSINFO_DATA(SVGEllipseElement, nsElementSH,
00891                            ELEMENT_SCRIPTABLE_FLAGS)
00892   NS_DEFINE_CLASSINFO_DATA(SVGGElement, nsElementSH,
00893                            ELEMENT_SCRIPTABLE_FLAGS)
00894   NS_DEFINE_CLASSINFO_DATA(SVGGradientElement, nsElementSH,
00895                            ELEMENT_SCRIPTABLE_FLAGS)
00896   NS_DEFINE_CLASSINFO_DATA(SVGImageElement, nsElementSH,
00897                            ELEMENT_SCRIPTABLE_FLAGS)
00898   NS_DEFINE_CLASSINFO_DATA(SVGLinearGradientElement, nsElementSH,
00899                            ELEMENT_SCRIPTABLE_FLAGS)
00900   NS_DEFINE_CLASSINFO_DATA(SVGLineElement, nsElementSH,
00901                            ELEMENT_SCRIPTABLE_FLAGS)
00902   NS_DEFINE_CLASSINFO_DATA(SVGMarkerElement, nsElementSH,
00903                            ELEMENT_SCRIPTABLE_FLAGS)
00904   NS_DEFINE_CLASSINFO_DATA(SVGMetadataElement, nsElementSH,
00905                            ELEMENT_SCRIPTABLE_FLAGS)
00906   NS_DEFINE_CLASSINFO_DATA(SVGPathElement, nsElementSH,
00907                            ELEMENT_SCRIPTABLE_FLAGS)
00908   NS_DEFINE_CLASSINFO_DATA(SVGPolygonElement, nsElementSH,
00909                            ELEMENT_SCRIPTABLE_FLAGS)
00910   NS_DEFINE_CLASSINFO_DATA(SVGPolylineElement, nsElementSH,
00911                            ELEMENT_SCRIPTABLE_FLAGS)
00912   NS_DEFINE_CLASSINFO_DATA(SVGRadialGradientElement, nsElementSH,
00913                            ELEMENT_SCRIPTABLE_FLAGS)
00914   NS_DEFINE_CLASSINFO_DATA(SVGRectElement, nsElementSH,
00915                            ELEMENT_SCRIPTABLE_FLAGS)
00916   NS_DEFINE_CLASSINFO_DATA(SVGScriptElement, nsElementSH,
00917                            ELEMENT_SCRIPTABLE_FLAGS)
00918   NS_DEFINE_CLASSINFO_DATA(SVGStopElement, nsElementSH,
00919                            ELEMENT_SCRIPTABLE_FLAGS)
00920   NS_DEFINE_CLASSINFO_DATA(SVGStyleElement, nsElementSH,
00921                            ELEMENT_SCRIPTABLE_FLAGS)
00922   NS_DEFINE_CLASSINFO_DATA(SVGSVGElement, nsElementSH,
00923                            ELEMENT_SCRIPTABLE_FLAGS)
00924   NS_DEFINE_CLASSINFO_DATA(SVGSymbolElement, nsElementSH,
00925                            ELEMENT_SCRIPTABLE_FLAGS)
00926   NS_DEFINE_CLASSINFO_DATA(SVGTextElement, nsElementSH,
00927                            ELEMENT_SCRIPTABLE_FLAGS)
00928   NS_DEFINE_CLASSINFO_DATA(SVGTitleElement, nsElementSH,
00929                            ELEMENT_SCRIPTABLE_FLAGS)
00930   NS_DEFINE_CLASSINFO_DATA(SVGTSpanElement, nsElementSH,
00931                            ELEMENT_SCRIPTABLE_FLAGS)
00932   NS_DEFINE_CLASSINFO_DATA(SVGUseElement, nsElementSH,
00933                            ELEMENT_SCRIPTABLE_FLAGS)
00934 
00935   // other SVG classes
00936   NS_DEFINE_CLASSINFO_DATA(SVGAngle, nsDOMGenericSH,
00937                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00938   NS_DEFINE_CLASSINFO_DATA(SVGAnimatedAngle, nsDOMGenericSH,
00939                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00940   NS_DEFINE_CLASSINFO_DATA(SVGAnimatedEnumeration, nsDOMGenericSH,
00941                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00942   NS_DEFINE_CLASSINFO_DATA(SVGAnimatedLength, nsDOMGenericSH,
00943                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00944   NS_DEFINE_CLASSINFO_DATA(SVGAnimatedLengthList, nsDOMGenericSH,
00945                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00946   NS_DEFINE_CLASSINFO_DATA(SVGAnimatedNumber, nsDOMGenericSH,
00947                            DOM_DEFAULT_SCRIPTABLE_FLAGS)    
00948   NS_DEFINE_CLASSINFO_DATA(SVGAnimatedNumberList, nsDOMGenericSH,
00949                            DOM_DEFAULT_SCRIPTABLE_FLAGS)    
00950   NS_DEFINE_CLASSINFO_DATA(SVGAnimatedPoints, nsDOMGenericSH,
00951                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00952   NS_DEFINE_CLASSINFO_DATA(SVGAnimatedPreserveAspectRatio, nsDOMGenericSH,
00953                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00954   NS_DEFINE_CLASSINFO_DATA(SVGAnimatedRect, nsDOMGenericSH,
00955                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00956   NS_DEFINE_CLASSINFO_DATA(SVGAnimatedString, nsDOMGenericSH,
00957                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00958   NS_DEFINE_CLASSINFO_DATA(SVGAnimatedTransformList, nsDOMGenericSH,
00959                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00960   NS_DEFINE_CLASSINFO_DATA(SVGEvent, nsDOMGenericSH,
00961                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00962   NS_DEFINE_CLASSINFO_DATA(SVGException, nsDOMGenericSH,
00963                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00964   NS_DEFINE_CLASSINFO_DATA(SVGLength, nsDOMGenericSH,
00965                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00966   NS_DEFINE_CLASSINFO_DATA(SVGLengthList, nsDOMGenericSH,
00967                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00968   NS_DEFINE_CLASSINFO_DATA(SVGMatrix, nsDOMGenericSH,
00969                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00970   NS_DEFINE_CLASSINFO_DATA(SVGNumber, nsDOMGenericSH,
00971                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00972   NS_DEFINE_CLASSINFO_DATA(SVGNumberList, nsDOMGenericSH,
00973                            DOM_DEFAULT_SCRIPTABLE_FLAGS)    
00974   NS_DEFINE_CLASSINFO_DATA(SVGPathSegArcAbs, nsDOMGenericSH,
00975                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00976   NS_DEFINE_CLASSINFO_DATA(SVGPathSegArcRel, nsDOMGenericSH,
00977                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00978   NS_DEFINE_CLASSINFO_DATA(SVGPathSegClosePath, nsDOMGenericSH,
00979                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00980   NS_DEFINE_CLASSINFO_DATA(SVGPathSegCurvetoCubicAbs, nsDOMGenericSH,
00981                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00982   NS_DEFINE_CLASSINFO_DATA(SVGPathSegCurvetoCubicRel, nsDOMGenericSH,
00983                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00984   NS_DEFINE_CLASSINFO_DATA(SVGPathSegCurvetoCubicSmoothAbs, nsDOMGenericSH,
00985                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00986   NS_DEFINE_CLASSINFO_DATA(SVGPathSegCurvetoCubicSmoothRel, nsDOMGenericSH,
00987                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00988   NS_DEFINE_CLASSINFO_DATA(SVGPathSegCurvetoQuadraticAbs, nsDOMGenericSH,
00989                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00990   NS_DEFINE_CLASSINFO_DATA(SVGPathSegCurvetoQuadraticRel, nsDOMGenericSH,
00991                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00992   NS_DEFINE_CLASSINFO_DATA(SVGPathSegCurvetoQuadraticSmoothAbs, nsDOMGenericSH,
00993                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00994   NS_DEFINE_CLASSINFO_DATA(SVGPathSegCurvetoQuadraticSmoothRel, nsDOMGenericSH,
00995                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00996   NS_DEFINE_CLASSINFO_DATA(SVGPathSegLinetoAbs, nsDOMGenericSH,
00997                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
00998   NS_DEFINE_CLASSINFO_DATA(SVGPathSegLinetoHorizontalAbs, nsDOMGenericSH,
00999                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01000   NS_DEFINE_CLASSINFO_DATA(SVGPathSegLinetoHorizontalRel, nsDOMGenericSH,
01001                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01002   NS_DEFINE_CLASSINFO_DATA(SVGPathSegLinetoRel, nsDOMGenericSH,
01003                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01004   NS_DEFINE_CLASSINFO_DATA(SVGPathSegLinetoVerticalAbs, nsDOMGenericSH,
01005                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01006   NS_DEFINE_CLASSINFO_DATA(SVGPathSegLinetoVerticalRel, nsDOMGenericSH,
01007                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01008   NS_DEFINE_CLASSINFO_DATA(SVGPathSegList, nsDOMGenericSH,
01009                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01010   NS_DEFINE_CLASSINFO_DATA(SVGPathSegMovetoAbs, nsDOMGenericSH,
01011                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01012   NS_DEFINE_CLASSINFO_DATA(SVGPathSegMovetoRel, nsDOMGenericSH,
01013                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01014   NS_DEFINE_CLASSINFO_DATA(SVGPoint, nsDOMGenericSH,
01015                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01016   NS_DEFINE_CLASSINFO_DATA(SVGPointList, nsDOMGenericSH,
01017                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01018   NS_DEFINE_CLASSINFO_DATA(SVGPreserveAspectRatio, nsDOMGenericSH,
01019                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01020   NS_DEFINE_CLASSINFO_DATA(SVGRect, nsDOMGenericSH,
01021                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01022   NS_DEFINE_CLASSINFO_DATA(SVGTransform, nsDOMGenericSH,
01023                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01024   NS_DEFINE_CLASSINFO_DATA(SVGTransformList, nsDOMGenericSH,
01025                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01026   NS_DEFINE_CLASSINFO_DATA(SVGZoomEvent, nsDOMGenericSH,
01027                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01028 #endif // MOZ_SVG
01029 
01030   NS_DEFINE_CLASSINFO_DATA(HTMLCanvasElement, nsHTMLElementSH,
01031                            ELEMENT_SCRIPTABLE_FLAGS)
01032 #ifdef MOZ_ENABLE_CANVAS
01033   NS_DEFINE_CLASSINFO_DATA(CanvasRenderingContext2D, nsDOMGenericSH,
01034                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01035   NS_DEFINE_CLASSINFO_DATA(CanvasGradient, nsDOMGenericSH,
01036                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01037   NS_DEFINE_CLASSINFO_DATA(CanvasPattern, nsDOMGenericSH,
01038                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01039 #endif // MOZ_ENABLE_CANVAS
01040 
01041  NS_DEFINE_CLASSINFO_DATA(SmartCardEvent, nsDOMGenericSH,
01042                           DOM_DEFAULT_SCRIPTABLE_FLAGS)
01043  NS_DEFINE_CLASSINFO_DATA(PageTransitionEvent, nsDOMGenericSH,
01044                           DOM_DEFAULT_SCRIPTABLE_FLAGS)
01045 
01046    // WhatWG Storage
01047  
01048    // mrbkap says we don't need WANT_ADDPROPERTY on Storage objects
01049    // since a call to addProperty() is always followed by a call to
01050    // setProperty(), except in the case when a getter or setter is set
01051    // for a property. But we don't care about getters or setters here.
01052    NS_DEFINE_CLASSINFO_DATA(Storage, nsStorageSH,
01053                             DOM_DEFAULT_SCRIPTABLE_FLAGS |
01054                             nsIXPCScriptable::WANT_NEWRESOLVE |
01055                             nsIXPCScriptable::WANT_GETPROPERTY |
01056                             nsIXPCScriptable::WANT_SETPROPERTY |
01057                             nsIXPCScriptable::WANT_DELPROPERTY |
01058                             nsIXPCScriptable::DONT_ENUM_STATIC_PROPS |
01059                             nsIXPCScriptable::WANT_NEWENUMERATE)
01060    NS_DEFINE_CLASSINFO_DATA(StorageList, nsStorageListSH,
01061                             ARRAY_SCRIPTABLE_FLAGS)
01062    NS_DEFINE_CLASSINFO_DATA(StorageItem, nsDOMGenericSH,
01063                             DOM_DEFAULT_SCRIPTABLE_FLAGS)
01064    NS_DEFINE_CLASSINFO_DATA(StorageEvent, nsDOMGenericSH,
01065                             DOM_DEFAULT_SCRIPTABLE_FLAGS)
01066  
01067 
01068   NS_DEFINE_CLASSINFO_DATA(Constructor, nsDOMConstructorSH,
01069                            (DEFAULT_SCRIPTABLE_FLAGS |
01070                             nsIXPCScriptable::WANT_CONSTRUCT |
01071                             nsIXPCScriptable::WANT_HASINSTANCE) &
01072                            ~(nsIXPCScriptable::WANT_PRECREATE |
01073                              nsIXPCScriptable::WANT_POSTCREATE |
01074                              nsIXPCScriptable::WANT_CHECKACCESS |
01075                              nsIXPCScriptable::WANT_NEWRESOLVE))
01076 
01077 #if defined(MOZ_SVG)
01078   NS_DEFINE_CLASSINFO_DATA(SVGTextPathElement, nsElementSH,
01079                            ELEMENT_SCRIPTABLE_FLAGS)
01080 #endif
01081 
01082   // We just want this to have classinfo so it gets mark callbacks for marking
01083   // event listeners.
01084   // We really don't want any of the default flags!
01085   NS_DEFINE_CLASSINFO_DATA(WindowRoot, nsEventReceiverSH,
01086                            nsIXPCScriptable::WANT_MARK)
01087 
01088   NS_DEFINE_CLASSINFO_DATA(DOMParser, nsDOMGenericSH,
01089                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01090   NS_DEFINE_CLASSINFO_DATA(XMLSerializer, nsDOMGenericSH,
01091                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01092 
01093   NS_DEFINE_CLASSINFO_DATA(XMLHttpProgressEvent, nsDOMGenericSH,
01094                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01095   NS_DEFINE_CLASSINFO_DATA(XMLHttpRequest, nsDOMGCParticipantSH,
01096                            GCPARTICIPANT_SCRIPTABLE_FLAGS)
01097 
01098   // Define MOZ_SVG_FOREIGNOBJECT here so that when it gets switched on,
01099   // we preserve binary compatibility. New classes should be added
01100   // at the end.
01101 #if defined(MOZ_SVG) && defined(MOZ_SVG_FOREIGNOBJECT)
01102   NS_DEFINE_CLASSINFO_DATA(SVGForeignObjectElement, nsElementSH,
01103                            ELEMENT_SCRIPTABLE_FLAGS)
01104 #endif
01105 
01106   NS_DEFINE_CLASSINFO_DATA(XULCommandEvent, nsDOMGenericSH,
01107                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
01108 };
01109 
01110 // Objects that shuld be constructable through |new Name();|
01111 struct nsContractIDMapData
01112 {
01113   PRInt32 mDOMClassInfoID;
01114   const char *mContractID;
01115 };
01116 
01117 #define NS_DEFINE_CONSTRUCTOR_DATA(_class, _contract_id)                      \
01118   { eDOMClassInfo_##_class##_id, _contract_id },
01119 
01120 static const nsContractIDMapData kConstructorMap[] =
01121 {
01122   NS_DEFINE_CONSTRUCTOR_DATA(DOMParser, NS_DOMPARSER_CONTRACTID)
01123   NS_DEFINE_CONSTRUCTOR_DATA(XMLSerializer, NS_XMLSERIALIZER_CONTRACTID)
01124   NS_DEFINE_CONSTRUCTOR_DATA(XMLHttpRequest, NS_XMLHTTPREQUEST_CONTRACTID)
01125 };
01126 
01127 nsIXPConnect *nsDOMClassInfo::sXPConnect = nsnull;
01128 nsIScriptSecurityManager *nsDOMClassInfo::sSecMan = nsnull;
01129 PRBool nsDOMClassInfo::sIsInitialized = PR_FALSE;
01130 PRBool nsDOMClassInfo::sDisableDocumentAllSupport = PR_FALSE;
01131 PRBool nsDOMClassInfo::sDisableGlobalScopePollutionSupport = PR_FALSE;
01132 
01133 
01134 jsval nsDOMClassInfo::sTop_id             = JSVAL_VOID;
01135 jsval nsDOMClassInfo::sParent_id          = JSVAL_VOID;
01136 jsval nsDOMClassInfo::sScrollbars_id      = JSVAL_VOID;
01137 jsval nsDOMClassInfo::sLocation_id        = JSVAL_VOID;
01138 jsval nsDOMClassInfo::sComponents_id      = JSVAL_VOID;
01139 jsval nsDOMClassInfo::sConstructor_id     = JSVAL_VOID;
01140 jsval nsDOMClassInfo::s_content_id        = JSVAL_VOID;
01141 jsval nsDOMClassInfo::sContent_id         = JSVAL_VOID;
01142 jsval nsDOMClassInfo::sMenubar_id         = JSVAL_VOID;
01143 jsval nsDOMClassInfo::sToolbar_id         = JSVAL_VOID;
01144 jsval nsDOMClassInfo::sLocationbar_id     = JSVAL_VOID;
01145 jsval nsDOMClassInfo::sPersonalbar_id     = JSVAL_VOID;
01146 jsval nsDOMClassInfo::sStatusbar_id       = JSVAL_VOID;
01147 jsval nsDOMClassInfo::sDirectories_id     = JSVAL_VOID;
01148 jsval nsDOMClassInfo::sControllers_id     = JSVAL_VOID;
01149 jsval nsDOMClassInfo::sLength_id          = JSVAL_VOID;
01150 jsval nsDOMClassInfo::sInnerHeight_id     = JSVAL_VOID;
01151 jsval nsDOMClassInfo::sInnerWidth_id      = JSVAL_VOID;
01152 jsval nsDOMClassInfo::sOuterHeight_id     = JSVAL_VOID;
01153 jsval nsDOMClassInfo::sOuterWidth_id      = JSVAL_VOID;
01154 jsval nsDOMClassInfo::sScreenX_id         = JSVAL_VOID;
01155 jsval nsDOMClassInfo::sScreenY_id         = JSVAL_VOID;
01156 jsval nsDOMClassInfo::sStatus_id          = JSVAL_VOID;
01157 jsval nsDOMClassInfo::sName_id            = JSVAL_VOID;
01158 jsval nsDOMClassInfo::sOnmousedown_id     = JSVAL_VOID;
01159 jsval nsDOMClassInfo::sOnmouseup_id       = JSVAL_VOID;
01160 jsval nsDOMClassInfo::sOnclick_id         = JSVAL_VOID;
01161 jsval nsDOMClassInfo::sOndblclick_id      = JSVAL_VOID;
01162 jsval nsDOMClassInfo::sOncontextmenu_id   = JSVAL_VOID;
01163 jsval nsDOMClassInfo::sOnmouseover_id     = JSVAL_VOID;
01164 jsval nsDOMClassInfo::sOnmouseout_id      = JSVAL_VOID;
01165 jsval nsDOMClassInfo::sOnkeydown_id       = JSVAL_VOID;
01166 jsval nsDOMClassInfo::sOnkeyup_id         = JSVAL_VOID;
01167 jsval nsDOMClassInfo::sOnkeypress_id      = JSVAL_VOID;
01168 jsval nsDOMClassInfo::sOnmousemove_id     = JSVAL_VOID;
01169 jsval nsDOMClassInfo::sOnfocus_id         = JSVAL_VOID;
01170 jsval nsDOMClassInfo::sOnblur_id          = JSVAL_VOID;
01171 jsval nsDOMClassInfo::sOnsubmit_id        = JSVAL_VOID;
01172 jsval nsDOMClassInfo::sOnreset_id         = JSVAL_VOID;
01173 jsval nsDOMClassInfo::sOnchange_id        = JSVAL_VOID;
01174 jsval nsDOMClassInfo::sOnselect_id        = JSVAL_VOID;
01175 jsval nsDOMClassInfo::sOnload_id          = JSVAL_VOID;
01176 jsval nsDOMClassInfo::sOnbeforeunload_id  = JSVAL_VOID;
01177 jsval nsDOMClassInfo::sOnunload_id        = JSVAL_VOID;
01178 jsval nsDOMClassInfo::sOnpageshow_id      = JSVAL_VOID;
01179 jsval nsDOMClassInfo::sOnpagehide_id      = JSVAL_VOID;
01180 jsval nsDOMClassInfo::sOnabort_id         = JSVAL_VOID;
01181 jsval nsDOMClassInfo::sOnerror_id         = JSVAL_VOID;
01182 jsval nsDOMClassInfo::sOnpaint_id         = JSVAL_VOID;
01183 jsval nsDOMClassInfo::sOnresize_id        = JSVAL_VOID;
01184 jsval nsDOMClassInfo::sOnscroll_id        = JSVAL_VOID;
01185 jsval nsDOMClassInfo::sScrollIntoView_id  = JSVAL_VOID;
01186 jsval nsDOMClassInfo::sScrollX_id         = JSVAL_VOID;
01187 jsval nsDOMClassInfo::sScrollY_id         = JSVAL_VOID;
01188 jsval nsDOMClassInfo::sScrollMaxX_id      = JSVAL_VOID;
01189 jsval nsDOMClassInfo::sScrollMaxY_id      = JSVAL_VOID;
01190 jsval nsDOMClassInfo::sOpen_id            = JSVAL_VOID;
01191 jsval nsDOMClassInfo::sItem_id            = JSVAL_VOID;
01192 jsval nsDOMClassInfo::sNamedItem_id       = JSVAL_VOID;
01193 jsval nsDOMClassInfo::sEnumerate_id       = JSVAL_VOID;
01194 jsval nsDOMClassInfo::sNavigator_id       = JSVAL_VOID;
01195 jsval nsDOMClassInfo::sDocument_id        = JSVAL_VOID;
01196 jsval nsDOMClassInfo::sWindow_id          = JSVAL_VOID;
01197 jsval nsDOMClassInfo::sFrames_id          = JSVAL_VOID;
01198 jsval nsDOMClassInfo::sSelf_id            = JSVAL_VOID;
01199 jsval nsDOMClassInfo::sOpener_id          = JSVAL_VOID;
01200 jsval nsDOMClassInfo::sAdd_id             = JSVAL_VOID;
01201 jsval nsDOMClassInfo::sAll_id             = JSVAL_VOID;
01202 jsval nsDOMClassInfo::sTags_id            = JSVAL_VOID;
01203 jsval nsDOMClassInfo::sAddEventListener_id= JSVAL_VOID;
01204 
01205 const JSClass *nsDOMClassInfo::sObjectClass = nsnull;
01206 const JSClass *nsDOMClassInfo::sXPCNativeWrapperClass = nsnull;
01207 
01208 PRBool nsDOMClassInfo::sDoSecurityCheckInAddProperty = PR_TRUE;
01209 
01210 const JSClass*
01211 NS_DOMClassInfo_GetXPCNativeWrapperClass()
01212 {
01213   return nsDOMClassInfo::GetXPCNativeWrapperClass();
01214 }
01215 
01216 void
01217 NS_DOMClassInfo_SetXPCNativeWrapperClass(JSClass* aClass)
01218 {
01219   nsDOMClassInfo::SetXPCNativeWrapperClass(aClass);
01220 }
01221 
01222 static void
01223 PrintWarningOnConsole(JSContext *cx, const char *stringBundleProperty)
01224 {
01225   nsCOMPtr<nsIStringBundleService>
01226     stringService(do_GetService(NS_STRINGBUNDLE_CONTRACTID));
01227   if (!stringService) {
01228     return;
01229   }
01230 
01231   nsCOMPtr<nsIStringBundle> bundle;
01232   stringService->CreateBundle(kDOMStringBundleURL, getter_AddRefs(bundle));
01233   if (!bundle) {
01234     return;
01235   }
01236 
01237   nsXPIDLString msg;
01238   bundle->GetStringFromName(NS_ConvertASCIItoUTF16(stringBundleProperty).get(),
01239                             getter_Copies(msg));
01240 
01241   if (msg.IsEmpty()) {
01242     NS_ERROR("Failed to get strings from dom.properties!");
01243     return;
01244   }
01245 
01246   nsCOMPtr<nsIConsoleService> consoleService
01247     (do_GetService("@mozilla.org/consoleservice;1"));
01248   if (!consoleService) {
01249     return;
01250   }
01251 
01252   nsCOMPtr<nsIScriptError> scriptError =
01253     do_CreateInstance(NS_SCRIPTERROR_CONTRACTID);
01254   if (!scriptError) {
01255     return;
01256   }
01257 
01258   JSStackFrame *fp, *iterator = nsnull;
01259   fp = ::JS_FrameIterator(cx, &iterator);
01260   PRUint32 lineno = 0;
01261   nsAutoString sourcefile;
01262   if (fp) {
01263     JSScript* script = ::JS_GetFrameScript(cx, fp);
01264     if (script) {
01265       const char* filename = ::JS_GetScriptFilename(cx, script);
01266       if (filename) {
01267         CopyUTF8toUTF16(nsDependentCString(filename), sourcefile);
01268       }
01269       jsbytecode* pc = ::JS_GetFramePC(cx, fp);
01270       if (pc) {
01271         lineno = ::JS_PCToLineNumber(cx, script, pc);
01272       }
01273     }
01274   }
01275   nsresult rv = scriptError->Init(msg.get(),
01276                                   sourcefile.get(),
01277                                   EmptyString().get(),
01278                                   lineno,
01279                                   0, // column for error is not available
01280                                   nsIScriptError::warningFlag,
01281                                   "DOM:HTML");
01282   if (NS_SUCCEEDED(rv)){
01283     consoleService->LogMessage(scriptError);
01284   }
01285 }
01286 
01287 static inline JSObject *
01288 GetGlobalJSObject(JSContext *cx, JSObject *obj)
01289 {
01290   JSObject *tmp;
01291 
01292   while ((tmp = ::JS_GetParent(cx, obj))) {
01293     obj = tmp;
01294   }
01295 
01296   return obj;
01297 }
01298 
01299 static jsval
01300 GetInternedJSVal(JSContext *cx, const char *str)
01301 {
01302   JSString *s = ::JS_InternString(cx, str);
01303 
01304   if (!s) {
01305     return JSVAL_VOID;
01306   }
01307 
01308   return STRING_TO_JSVAL(s);
01309 }
01310 
01311 // static
01312 nsresult
01313 nsDOMClassInfo::DefineStaticJSVals(JSContext *cx)
01314 {
01315 #define SET_JSVAL_TO_STRING(_val, _cx, _str)                                  \
01316   _val = GetInternedJSVal(_cx, _str);                                         \
01317   if (!JSVAL_IS_STRING(_val)) {                                               \
01318     return NS_ERROR_OUT_OF_MEMORY;                                            \
01319   }
01320 
01321   SET_JSVAL_TO_STRING(sTop_id,             cx, "top");
01322   SET_JSVAL_TO_STRING(sParent_id,          cx, "parent");
01323   SET_JSVAL_TO_STRING(sScrollbars_id,      cx, "scrollbars");
01324   SET_JSVAL_TO_STRING(sLocation_id,        cx, "location");
01325   SET_JSVAL_TO_STRING(sComponents_id,      cx, "Components");
01326   SET_JSVAL_TO_STRING(sConstructor_id,     cx, "constructor");
01327   SET_JSVAL_TO_STRING(s_content_id,        cx, "_content");
01328   SET_JSVAL_TO_STRING(sContent_id,         cx, "content");
01329   SET_JSVAL_TO_STRING(sMenubar_id,         cx, "menubar");
01330   SET_JSVAL_TO_STRING(sToolbar_id,         cx, "toolbar");
01331   SET_JSVAL_TO_STRING(sLocationbar_id,     cx, "locationbar");
01332   SET_JSVAL_TO_STRING(sPersonalbar_id,     cx, "personalbar");
01333   SET_JSVAL_TO_STRING(sStatusbar_id,       cx, "statusbar");
01334   SET_JSVAL_TO_STRING(sDirectories_id,     cx, "directories");
01335   SET_JSVAL_TO_STRING(sControllers_id,     cx, "controllers");
01336   SET_JSVAL_TO_STRING(sLength_id,          cx, "length");
01337   SET_JSVAL_TO_STRING(sInnerHeight_id,     cx, "innerHeight");
01338   SET_JSVAL_TO_STRING(sInnerWidth_id,      cx, "innerWidth");
01339   SET_JSVAL_TO_STRING(sOuterHeight_id,     cx, "outerHeight");
01340   SET_JSVAL_TO_STRING(sOuterWidth_id,      cx, "outerWidth");
01341   SET_JSVAL_TO_STRING(sScreenX_id,         cx, "screenX");
01342   SET_JSVAL_TO_STRING(sScreenY_id,         cx, "screenY");
01343   SET_JSVAL_TO_STRING(sStatus_id,          cx, "status");
01344   SET_JSVAL_TO_STRING(sName_id,            cx, "name");
01345   SET_JSVAL_TO_STRING(sOnmousedown_id,     cx, "onmousedown");
01346   SET_JSVAL_TO_STRING(sOnmouseup_id,       cx, "onmouseup");
01347   SET_JSVAL_TO_STRING(sOnclick_id,         cx, "onclick");
01348   SET_JSVAL_TO_STRING(sOndblclick_id,      cx, "ondblclick");
01349   SET_JSVAL_TO_STRING(sOncontextmenu_id,   cx, "oncontextmenu");
01350   SET_JSVAL_TO_STRING(sOnmouseover_id,     cx, "onmouseover");
01351   SET_JSVAL_TO_STRING(sOnmouseout_id,      cx, "onmouseout");
01352   SET_JSVAL_TO_STRING(sOnkeydown_id,       cx, "onkeydown");
01353   SET_JSVAL_TO_STRING(sOnkeyup_id,         cx, "onkeyup");
01354   SET_JSVAL_TO_STRING(sOnkeypress_id,      cx, "onkeypress");
01355   SET_JSVAL_TO_STRING(sOnmousemove_id,     cx, "onmousemove");
01356   SET_JSVAL_TO_STRING(sOnfocus_id,         cx, "onfocus");
01357   SET_JSVAL_TO_STRING(sOnblur_id,          cx, "onblur");
01358   SET_JSVAL_TO_STRING(sOnsubmit_id,        cx, "onsubmit");
01359   SET_JSVAL_TO_STRING(sOnreset_id,         cx, "onreset");
01360   SET_JSVAL_TO_STRING(sOnchange_id,        cx, "onchange");
01361   SET_JSVAL_TO_STRING(sOnselect_id,        cx, "onselect");
01362   SET_JSVAL_TO_STRING(sOnload_id,          cx, "onload");
01363   SET_JSVAL_TO_STRING(sOnbeforeunload_id,  cx, "onbeforeunload");
01364   SET_JSVAL_TO_STRING(sOnunload_id,        cx, "onunload");
01365   SET_JSVAL_TO_STRING(sOnpageshow_id,      cx, "onpageshow");
01366   SET_JSVAL_TO_STRING(sOnpagehide_id,      cx, "onpagehide");
01367   SET_JSVAL_TO_STRING(sOnabort_id,         cx, "onabort");
01368   SET_JSVAL_TO_STRING(sOnerror_id,         cx, "onerror");
01369   SET_JSVAL_TO_STRING(sOnpaint_id,         cx, "onpaint");
01370   SET_JSVAL_TO_STRING(sOnresize_id,        cx, "onresize");
01371   SET_JSVAL_TO_STRING(sOnscroll_id,        cx, "onscroll");
01372   SET_JSVAL_TO_STRING(sScrollIntoView_id,  cx, "scrollIntoView");
01373   SET_JSVAL_TO_STRING(sScrollX_id,         cx, "scrollX");
01374   SET_JSVAL_TO_STRING(sScrollY_id,         cx, "scrollY");
01375   SET_JSVAL_TO_STRING(sScrollMaxX_id,      cx, "scrollMaxX");
01376   SET_JSVAL_TO_STRING(sScrollMaxY_id,      cx, "scrollMaxY");
01377   SET_JSVAL_TO_STRING(sOpen_id,            cx, "open");
01378   SET_JSVAL_TO_STRING(sItem_id,            cx, "item");
01379   SET_JSVAL_TO_STRING(sNamedItem_id,       cx, "namedItem");
01380   SET_JSVAL_TO_STRING(sEnumerate_id,       cx, "enumerateProperties");
01381   SET_JSVAL_TO_STRING(sNavigator_id,       cx, "navigator");
01382   SET_JSVAL_TO_STRING(sDocument_id,        cx, "document");
01383   SET_JSVAL_TO_STRING(sWindow_id,          cx, "window");
01384   SET_JSVAL_TO_STRING(sFrames_id,          cx, "frames");
01385   SET_JSVAL_TO_STRING(sSelf_id,            cx, "self");
01386   SET_JSVAL_TO_STRING(sOpener_id,          cx, "opener");
01387   SET_JSVAL_TO_STRING(sAdd_id,             cx, "add");
01388   SET_JSVAL_TO_STRING(sAll_id,             cx, "all");
01389   SET_JSVAL_TO_STRING(sTags_id,            cx, "tags");
01390   SET_JSVAL_TO_STRING(sAddEventListener_id,cx, "addEventListener");
01391 
01392   return NS_OK;
01393 }
01394 
01395 // static
01396 nsresult
01397 nsDOMClassInfo::WrapNative(JSContext *cx, JSObject *scope, nsISupports *native,
01398                            const nsIID& aIID, jsval *vp,
01399                            nsIXPConnectJSObjectHolder **aHolder)
01400 {
01401   *aHolder = nsnull;
01402   
01403   if (!native) {
01404     *vp = JSVAL_NULL;
01405 
01406     return NS_OK;
01407   }
01408 
01409   NS_ENSURE_TRUE(sXPConnect, NS_ERROR_UNEXPECTED);
01410 
01411   nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
01412   nsresult rv = sXPConnect->WrapNative(cx, GetGlobalJSObject(cx, scope),
01413                                        native, aIID, getter_AddRefs(holder));
01414   NS_ENSURE_SUCCESS(rv, rv);
01415 
01416   JSObject* obj = nsnull;
01417   rv = holder->GetJSObject(&obj);
01418   NS_ENSURE_SUCCESS(rv, rv);
01419 
01420   *vp = OBJECT_TO_JSVAL(obj);
01421   holder.swap(*aHolder);
01422 
01423   return rv;
01424 }
01425 
01426 // static
01427 nsresult
01428 nsDOMClassInfo::ThrowJSException(JSContext *cx, nsresult aResult)
01429 {
01430   do {
01431     nsCOMPtr<nsIExceptionService> xs =
01432       do_GetService(NS_EXCEPTIONSERVICE_CONTRACTID);
01433     if (!xs) {
01434       break;
01435     }
01436 
01437     nsCOMPtr<nsIExceptionManager> xm;
01438     nsresult rv = xs->GetCurrentExceptionManager(getter_AddRefs(xm));
01439     if (NS_FAILED(rv)) {
01440       break;
01441     }
01442 
01443     nsCOMPtr<nsIException> exception;
01444     rv = xm->GetExceptionFromProvider(aResult, 0, getter_AddRefs(exception));
01445     if (NS_FAILED(rv) || !exception) {
01446       break;
01447     }
01448 
01449     jsval jv;
01450     nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
01451     rv = WrapNative(cx, ::JS_GetGlobalObject(cx), exception,
01452                     NS_GET_IID(nsIException), &jv, getter_AddRefs(holder));
01453     if (NS_FAILED(rv) || JSVAL_IS_NULL(jv)) {
01454       break;
01455     }
01456     JS_SetPendingException(cx, jv);
01457 
01458     return NS_OK;
01459   } while (0);
01460 
01461   // XXX This probably wants to be localized, but that can fail in ways that
01462   // are hard to report correctly.
01463   JSString *str =
01464     JS_NewStringCopyZ(cx, "An error occured throwing an exception");
01465   if (!str) {
01466     // JS_NewStringCopyZ reported the error for us.
01467     return NS_OK; 
01468   }
01469   JS_SetPendingException(cx, STRING_TO_JSVAL(str));
01470   return NS_OK;
01471 }
01472 
01473 nsDOMClassInfo::nsDOMClassInfo(nsDOMClassInfoData* aData) : mData(aData)
01474 {
01475 }
01476 
01477 nsDOMClassInfo::~nsDOMClassInfo()
01478 {
01479   if (IS_EXTERNAL(mData->mCachedClassInfo)) {
01480     // Some compilers don't like delete'ing a const nsDOMClassInfo*
01481     nsDOMClassInfoData* data = NS_CONST_CAST(nsDOMClassInfoData*, mData);
01482     delete NS_STATIC_CAST(nsExternalDOMClassInfoData*, data);
01483   }
01484 }
01485 
01486 NS_IMPL_ADDREF(nsDOMClassInfo)
01487 NS_IMPL_RELEASE(nsDOMClassInfo)
01488 
01489 NS_INTERFACE_MAP_BEGIN(nsDOMClassInfo)
01490   NS_INTERFACE_MAP_ENTRY(nsIXPCScriptable)
01491   NS_INTERFACE_MAP_ENTRY(nsIClassInfo)
01492   NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, nsIXPCScriptable)
01493 NS_INTERFACE_MAP_END
01494 
01495 
01496 JSClass nsDOMClassInfo::sDOMConstructorProtoClass = {
01497   "DOM Constructor.prototype", 0,
01498   JS_PropertyStub, JS_PropertyStub, JS_PropertyStub, JS_PropertyStub,
01499   JS_EnumerateStub, JS_ResolveStub, JS_ConvertStub, JS_FinalizeStub
01500 };
01501 
01502 
01503 static const char *
01504 CutPrefix(const char *aName) {
01505   static const char prefix_nsIDOM[] = "nsIDOM";
01506   static const char prefix_nsI[]    = "nsI";
01507 
01508   if (strncmp(aName, prefix_nsIDOM, sizeof(prefix_nsIDOM) - 1) == 0) {
01509     return aName + sizeof(prefix_nsIDOM) - 1;
01510   }
01511 
01512   if (strncmp(aName, prefix_nsI, sizeof(prefix_nsI) - 1) == 0) {
01513     return aName + sizeof(prefix_nsI) - 1;
01514   }
01515 
01516   return aName;
01517 }
01518 
01519 // static
01520 nsresult
01521 nsDOMClassInfo::RegisterClassName(PRInt32 aClassInfoID)
01522 {
01523   extern nsScriptNameSpaceManager *gNameSpaceManager;
01524   NS_ENSURE_TRUE(gNameSpaceManager, NS_ERROR_NOT_INITIALIZED);
01525 
01526   gNameSpaceManager->RegisterClassName(sClassInfoData[aClassInfoID].mName,
01527                                        aClassInfoID);
01528 
01529   return NS_OK;
01530 }
01531 
01532 // static
01533 nsresult
01534 nsDOMClassInfo::RegisterClassProtos(PRInt32 aClassInfoID)
01535 {
01536   extern nsScriptNameSpaceManager *gNameSpaceManager;
01537   NS_ENSURE_TRUE(gNameSpaceManager, NS_ERROR_NOT_INITIALIZED);
01538   PRBool found_old;
01539 
01540   const nsIID *primary_iid = sClassInfoData[aClassInfoID].mProtoChainInterface;
01541 
01542   if (!primary_iid || primary_iid == &NS_GET_IID(nsISupports)) {
01543     return NS_OK;
01544   }
01545 
01546   nsCOMPtr<nsIInterfaceInfoManager> iim =
01547     dont_AddRef(XPTI_GetInterfaceInfoManager());
01548   NS_ENSURE_TRUE(iim, NS_ERROR_NOT_AVAILABLE);
01549 
01550   nsCOMPtr<nsIInterfaceInfo> if_info;
01551   PRBool first = PR_TRUE;
01552 
01553   iim->GetInfoForIID(primary_iid, getter_AddRefs(if_info));
01554 
01555   while (if_info) {
01556     nsIID *iid = nsnull;
01557 
01558     if_info->GetInterfaceIID(&iid);
01559     NS_ENSURE_TRUE(iid, NS_ERROR_UNEXPECTED);
01560 
01561     if (iid->Equals(NS_GET_IID(nsISupports))) {
01562       nsMemory::Free(iid);
01563 
01564       break;
01565     }
01566 
01567     nsXPIDLCString name;
01568     if_info->GetName(getter_Copies(name));
01569 
01570     gNameSpaceManager->RegisterClassProto(CutPrefix(name), iid, &found_old);
01571 
01572     nsMemory::Free(iid);
01573 
01574     if (first) {
01575       first = PR_FALSE;
01576     } else if (found_old) {
01577       break;
01578     }
01579 
01580     nsCOMPtr<nsIInterfaceInfo> tmp(if_info);
01581     tmp->GetParent(getter_AddRefs(if_info));
01582   }
01583 
01584   return NS_OK;
01585 }
01586 
01587 // static
01588 nsresult
01589 nsDOMClassInfo::RegisterExternalClasses()
01590 {
01591   extern nsScriptNameSpaceManager *gNameSpaceManager;
01592   NS_ENSURE_TRUE(gNameSpaceManager, NS_ERROR_NOT_INITIALIZED);
01593 
01594   nsresult rv;
01595   nsCOMPtr<nsIComponentRegistrar> registrar;
01596   rv = NS_GetComponentRegistrar(getter_AddRefs(registrar));
01597   NS_ENSURE_SUCCESS(rv, rv);
01598 
01599   nsCOMPtr<nsICategoryManager> cm =
01600     do_GetService(NS_CATEGORYMANAGER_CONTRACTID, &rv);
01601   NS_ENSURE_SUCCESS(rv, rv);
01602 
01603   nsCOMPtr<nsISimpleEnumerator> e;
01604   rv = cm->EnumerateCategory(JAVASCRIPT_DOM_CLASS, getter_AddRefs(e));
01605   NS_ENSURE_SUCCESS(rv, rv);
01606 
01607   nsXPIDLCString contractId;
01608   nsCAutoString categoryEntry;
01609   nsCOMPtr<nsISupports> entry;
01610 
01611   while (NS_SUCCEEDED(e->GetNext(getter_AddRefs(entry)))) {
01612     nsCOMPtr<nsISupportsCString> category(do_QueryInterface(entry));
01613 
01614     if (!category) {
01615       NS_WARNING("Category entry not an nsISupportsCString!");
01616       continue;
01617     }
01618 
01619     rv = category->GetData(categoryEntry);
01620 
01621     cm->GetCategoryEntry(JAVASCRIPT_DOM_CLASS, categoryEntry.get(),
01622                          getter_Copies(contractId));
01623     NS_ENSURE_SUCCESS(rv, rv);
01624 
01625     nsCID *cid;
01626     rv = registrar->ContractIDToCID(contractId, &cid);
01627     if (NS_FAILED(rv)) {
01628       NS_WARNING("Bad contract id registered with the script namespace manager");
01629       continue;
01630     }
01631 
01632     rv = gNameSpaceManager->RegisterExternalClassName(categoryEntry.get(), *cid);
01633     nsMemory::Free(cid);
01634     NS_ENSURE_SUCCESS(rv, rv);
01635   }
01636 
01637   return gNameSpaceManager->RegisterExternalInterfaces(PR_TRUE);
01638 }
01639 
01640 #define _DOM_CLASSINFO_MAP_BEGIN(_class, _ifptr, _has_class_if)               \
01641   {                                                                           \
01642     nsDOMClassInfoData &d = sClassInfoData[eDOMClassInfo_##_class##_id];      \
01643     d.mProtoChainInterface = _ifptr;                                          \
01644     d.mHasClassInterface = _has_class_if;                                     \
01645     static const nsIID *interface_list[] = {
01646 
01647 #define DOM_CLASSINFO_MAP_BEGIN(_class, _interface)                           \
01648   _DOM_CLASSINFO_MAP_BEGIN(_class, &NS_GET_IID(_interface), PR_TRUE)
01649 
01650 #define DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(_class, _interface)               \
01651   _DOM_CLASSINFO_MAP_BEGIN(_class, &NS_GET_IID(_interface), PR_FALSE)
01652 
01653 #define DOM_CLASSINFO_MAP_ENTRY(_if)                                          \
01654       &NS_GET_IID(_if),
01655 
01656 #define DOM_CLASSINFO_MAP_END                                                 \
01657       nsnull                                                                  \
01658     };                                                                        \
01659                                                                               \
01660     d.mInterfaces = interface_list;                                           \
01661   }
01662 
01663 #define DOM_CLASSINFO_DOCUMENT_MAP_ENTRIES                                    \
01664     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSDocument)                                 \
01665     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDocumentEvent)                              \
01666     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDocumentStyle)                              \
01667     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSDocumentStyle)                            \
01668     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDocumentView)                               \
01669     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDocumentRange)                              \
01670     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDocumentTraversal)                          \
01671     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDocumentXBL)                                \
01672     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)                                \
01673     DOM_CLASSINFO_MAP_ENTRY(nsIDOM3Document)                                  \
01674     DOM_CLASSINFO_MAP_ENTRY(nsIDOM3Node)
01675 
01676 #define DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES                                \
01677     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLElement_MOZILLA_1_8_BRANCH)           \
01678     DOM_CLASSINFO_MAP_ENTRY(nsIDOMElementCSSInlineStyle)                      \
01679     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)                                \
01680     DOM_CLASSINFO_MAP_ENTRY(nsIDOM3Node)
01681 
01682 #define DOM_CLASSINFO_EVENT_MAP_ENTRIES                                       \
01683     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEvent)                                      \
01684     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSEvent)                                    \
01685 
01686 #define DOM_CLASSINFO_UI_EVENT_MAP_ENTRIES                                    \
01687     DOM_CLASSINFO_MAP_ENTRY(nsIDOMUIEvent)                                    \
01688     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSUIEvent)                                  \
01689     DOM_CLASSINFO_EVENT_MAP_ENTRIES
01690 
01691 #define DOM_CLASSINFO_MAP_END_WITH_XPATH                                      \
01692     xpathEvaluatorIID,                                                        \
01693   DOM_CLASSINFO_MAP_END
01694 
01695 nsresult
01696 nsDOMClassInfo::Init()
01697 {
01698   /* Errors that can trigger early returns are done first,
01699      otherwise nsDOMClassInfo is left in a half inited state. */
01700   NS_ASSERTION(sizeof(PtrBits) == sizeof(void*),
01701                "BAD! You'll need to adjust the size of PtrBits to the size "
01702                "of a pointer on your platform.");
01703 
01704   NS_ENSURE_TRUE(!sIsInitialized, NS_ERROR_ALREADY_INITIALIZED);
01705 
01706   extern nsScriptNameSpaceManager *gNameSpaceManager;
01707   NS_ENSURE_TRUE(gNameSpaceManager, NS_ERROR_NOT_INITIALIZED);
01708 
01709   nsresult rv = CallGetService(nsIXPConnect::GetCID(), &sXPConnect);
01710   NS_ENSURE_SUCCESS(rv, rv);
01711 
01712   nsCOMPtr<nsIXPCFunctionThisTranslator> old;
01713 
01714   nsCOMPtr<nsIXPCFunctionThisTranslator> elt = new nsEventListenerThisTranslator();
01715   NS_ENSURE_TRUE(elt, NS_ERROR_OUT_OF_MEMORY);
01716 
01717   sXPConnect->SetFunctionThisTranslator(NS_GET_IID(nsIDOMEventListener),
01718                                         elt, getter_AddRefs(old));
01719 
01720   nsCOMPtr<nsIScriptSecurityManager> sm =
01721     do_GetService("@mozilla.org/scriptsecuritymanager;1", &rv);
01722   NS_ENSURE_SUCCESS(rv, rv);
01723 
01724   sSecMan = sm;
01725   NS_ADDREF(sSecMan);
01726 
01727   nsCOMPtr<nsIThreadJSContextStack> stack =
01728     do_GetService("@mozilla.org/js/xpc/ContextStack;1", &rv);
01729   NS_ENSURE_SUCCESS(rv, rv);
01730 
01731   JSContext *cx = nsnull;
01732 
01733   rv = stack->GetSafeJSContext(&cx);
01734   NS_ENSURE_SUCCESS(rv, rv);
01735 
01736   nsCOMPtr<nsIComponentRegistrar> cr;
01737   NS_GetComponentRegistrar(getter_AddRefs(cr));
01738 
01739   const nsIID* xpathEvaluatorIID = nsnull;
01740   if (cr) {
01741     PRBool haveXPathDOM;
01742     cr->IsContractIDRegistered(NS_XPATH_EVALUATOR_CONTRACTID,
01743                                &haveXPathDOM);
01744     if (haveXPathDOM) {
01745       xpathEvaluatorIID = &NS_GET_IID(nsIDOMXPathEvaluator);
01746     }
01747   }
01748 
01749   DOM_CLASSINFO_MAP_BEGIN(Window, nsIDOMWindow)
01750     DOM_CLASSINFO_MAP_ENTRY(nsIDOMWindow)
01751     DOM_CLASSINFO_MAP_ENTRY(nsIDOMJSWindow)
01752     DOM_CLASSINFO_MAP_ENTRY(nsIDOMWindowInternal)
01753     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
01754     DOM_CLASSINFO_MAP_ENTRY(nsIDOMViewCSS)
01755     DOM_CLASSINFO_MAP_ENTRY(nsIDOMAbstractView)
01756     DOM_CLASSINFO_MAP_ENTRY(nsIDOMStorageWindow)
01757   DOM_CLASSINFO_MAP_END
01758 
01759   DOM_CLASSINFO_MAP_BEGIN(Location, nsIDOMLocation)
01760     DOM_CLASSINFO_MAP_ENTRY(nsIDOMLocation)
01761     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSLocation)
01762   DOM_CLASSINFO_MAP_END
01763 
01764   DOM_CLASSINFO_MAP_BEGIN(Navigator, nsIDOMNavigator)
01765     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNavigator)
01766     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNavigator_MOZILLA_1_8_BRANCH)
01767     DOM_CLASSINFO_MAP_ENTRY(nsIDOMJSNavigator)
01768     DOM_CLASSINFO_MAP_ENTRY(nsIDOMClientInformation)
01769   DOM_CLASSINFO_MAP_END
01770 
01771   DOM_CLASSINFO_MAP_BEGIN(Plugin, nsIDOMPlugin)
01772     DOM_CLASSINFO_MAP_ENTRY(nsIDOMPlugin)
01773   DOM_CLASSINFO_MAP_END
01774 
01775   DOM_CLASSINFO_MAP_BEGIN(PluginArray, nsIDOMPluginArray)
01776     DOM_CLASSINFO_MAP_ENTRY(nsIDOMPluginArray)
01777     DOM_CLASSINFO_MAP_ENTRY(nsIDOMJSPluginArray)
01778   DOM_CLASSINFO_MAP_END
01779 
01780   DOM_CLASSINFO_MAP_BEGIN(MimeType, nsIDOMMimeType)
01781     DOM_CLASSINFO_MAP_ENTRY(nsIDOMMimeType)
01782   DOM_CLASSINFO_MAP_END
01783 
01784   DOM_CLASSINFO_MAP_BEGIN(MimeTypeArray, nsIDOMMimeTypeArray)
01785     DOM_CLASSINFO_MAP_ENTRY(nsIDOMMimeTypeArray)
01786   DOM_CLASSINFO_MAP_END
01787 
01788   DOM_CLASSINFO_MAP_BEGIN(BarProp, nsIDOMBarProp)
01789     DOM_CLASSINFO_MAP_ENTRY(nsIDOMBarProp)
01790   DOM_CLASSINFO_MAP_END
01791 
01792   DOM_CLASSINFO_MAP_BEGIN(History, nsIDOMHistory)
01793     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHistory)
01794     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHistory)
01795   DOM_CLASSINFO_MAP_END
01796 
01797   DOM_CLASSINFO_MAP_BEGIN(Screen, nsIDOMScreen)
01798     DOM_CLASSINFO_MAP_ENTRY(nsIDOMScreen)
01799   DOM_CLASSINFO_MAP_END
01800 
01801   DOM_CLASSINFO_MAP_BEGIN(Constructor, nsIDOMConstructor)
01802     DOM_CLASSINFO_MAP_ENTRY(nsIDOMConstructor)
01803   DOM_CLASSINFO_MAP_END
01804 
01805   DOM_CLASSINFO_MAP_BEGIN(XMLDocument, nsIDOMXMLDocument)
01806     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDocument)
01807     DOM_CLASSINFO_MAP_ENTRY(nsIDOMXMLDocument)
01808     DOM_CLASSINFO_DOCUMENT_MAP_ENTRIES
01809   DOM_CLASSINFO_MAP_END_WITH_XPATH
01810 
01811   DOM_CLASSINFO_MAP_BEGIN(DocumentType, nsIDOMDocumentType)
01812     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDocumentType)
01813     DOM_CLASSINFO_MAP_ENTRY(nsIDOM3Node)
01814   DOM_CLASSINFO_MAP_END
01815 
01816   DOM_CLASSINFO_MAP_BEGIN(DOMImplementation, nsIDOMDOMImplementation)
01817     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDOMImplementation)
01818   DOM_CLASSINFO_MAP_END
01819 
01820   DOM_CLASSINFO_MAP_BEGIN(DOMException, nsIDOMDOMException)
01821     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDOMException)
01822     DOM_CLASSINFO_MAP_ENTRY(nsIException)
01823   DOM_CLASSINFO_MAP_END
01824 
01825   DOM_CLASSINFO_MAP_BEGIN(DocumentFragment, nsIDOMDocumentFragment)
01826     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDocumentFragment)
01827     DOM_CLASSINFO_MAP_ENTRY(nsIDOM3Node)
01828   DOM_CLASSINFO_MAP_END
01829 
01830   DOM_CLASSINFO_MAP_BEGIN(Element, nsIDOMElement)
01831     DOM_CLASSINFO_MAP_ENTRY(nsIDOMElement)
01832     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
01833     DOM_CLASSINFO_MAP_ENTRY(nsIDOM3Node)
01834   DOM_CLASSINFO_MAP_END
01835 
01836   DOM_CLASSINFO_MAP_BEGIN(Attr, nsIDOMAttr)
01837     DOM_CLASSINFO_MAP_ENTRY(nsIDOMAttr)
01838     DOM_CLASSINFO_MAP_ENTRY(nsIDOM3Node)
01839   DOM_CLASSINFO_MAP_END
01840 
01841   DOM_CLASSINFO_MAP_BEGIN(Text, nsIDOMText)
01842     DOM_CLASSINFO_MAP_ENTRY(nsIDOMText)
01843     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
01844     DOM_CLASSINFO_MAP_ENTRY(nsIDOM3Node)
01845   DOM_CLASSINFO_MAP_END
01846 
01847   DOM_CLASSINFO_MAP_BEGIN(Comment, nsIDOMComment)
01848     DOM_CLASSINFO_MAP_ENTRY(nsIDOMComment)
01849     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
01850     DOM_CLASSINFO_MAP_ENTRY(nsIDOM3Node)
01851   DOM_CLASSINFO_MAP_END
01852 
01853   DOM_CLASSINFO_MAP_BEGIN(CDATASection, nsIDOMCDATASection)
01854     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCDATASection)
01855     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
01856     DOM_CLASSINFO_MAP_ENTRY(nsIDOM3Node)
01857   DOM_CLASSINFO_MAP_END
01858 
01859   DOM_CLASSINFO_MAP_BEGIN(ProcessingInstruction, nsIDOMProcessingInstruction)
01860     DOM_CLASSINFO_MAP_ENTRY(nsIDOMProcessingInstruction)
01861     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
01862     DOM_CLASSINFO_MAP_ENTRY(nsIDOM3Node)
01863   DOM_CLASSINFO_MAP_END
01864 
01865   DOM_CLASSINFO_MAP_BEGIN(Entity, nsIDOMEntity)
01866     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEntity)
01867   DOM_CLASSINFO_MAP_END
01868 
01869   DOM_CLASSINFO_MAP_BEGIN(EntityReference, nsIDOMEntityReference)
01870     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEntityReference)
01871   DOM_CLASSINFO_MAP_END
01872 
01873   DOM_CLASSINFO_MAP_BEGIN(Notation, nsIDOMNotation)
01874     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNotation)
01875   DOM_CLASSINFO_MAP_END
01876 
01877   DOM_CLASSINFO_MAP_BEGIN(NodeList, nsIDOMNodeList)
01878     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNodeList)
01879   DOM_CLASSINFO_MAP_END
01880 
01881   DOM_CLASSINFO_MAP_BEGIN(NamedNodeMap, nsIDOMNamedNodeMap)
01882     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNamedNodeMap)
01883   DOM_CLASSINFO_MAP_END
01884 
01885   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(DocumentStyleSheetList,
01886                                       nsIDOMStyleSheetList)
01887     DOM_CLASSINFO_MAP_ENTRY(nsIDOMStyleSheetList)
01888   DOM_CLASSINFO_MAP_END
01889   
01890   DOM_CLASSINFO_MAP_BEGIN(Event, nsIDOMEvent)
01891     DOM_CLASSINFO_EVENT_MAP_ENTRIES
01892   DOM_CLASSINFO_MAP_END
01893 
01894   DOM_CLASSINFO_MAP_BEGIN(PopupBlockedEvent, nsIDOMPopupBlockedEvent)
01895     DOM_CLASSINFO_MAP_ENTRY(nsIDOMPopupBlockedEvent)
01896     DOM_CLASSINFO_MAP_ENTRY(nsIDOMPopupBlockedEvent_MOZILLA_1_8_BRANCH)
01897     DOM_CLASSINFO_EVENT_MAP_ENTRIES
01898   DOM_CLASSINFO_MAP_END
01899 
01900   DOM_CLASSINFO_MAP_BEGIN(SmartCardEvent, nsIDOMSmartCardEvent)
01901     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSmartCardEvent)
01902   DOM_CLASSINFO_MAP_END
01903 
01904   DOM_CLASSINFO_MAP_BEGIN(PageTransitionEvent, nsIDOMPageTransitionEvent)
01905     DOM_CLASSINFO_MAP_ENTRY(nsIDOMPageTransitionEvent)
01906     DOM_CLASSINFO_EVENT_MAP_ENTRIES
01907   DOM_CLASSINFO_MAP_END
01908 
01909   DOM_CLASSINFO_MAP_BEGIN(MutationEvent, nsIDOMMutationEvent)
01910     DOM_CLASSINFO_MAP_ENTRY(nsIDOMMutationEvent)
01911     DOM_CLASSINFO_EVENT_MAP_ENTRIES
01912   DOM_CLASSINFO_MAP_END
01913 
01914   DOM_CLASSINFO_MAP_BEGIN(UIEvent, nsIDOMUIEvent)
01915     DOM_CLASSINFO_UI_EVENT_MAP_ENTRIES
01916   DOM_CLASSINFO_MAP_END
01917   
01918   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(KeyboardEvent, nsIDOMKeyEvent)
01919     DOM_CLASSINFO_MAP_ENTRY(nsIDOMKeyEvent)
01920     DOM_CLASSINFO_UI_EVENT_MAP_ENTRIES
01921   DOM_CLASSINFO_MAP_END
01922 
01923   DOM_CLASSINFO_MAP_BEGIN(MouseEvent, nsIDOMMouseEvent)
01924     DOM_CLASSINFO_MAP_ENTRY(nsIDOMMouseEvent)
01925     DOM_CLASSINFO_UI_EVENT_MAP_ENTRIES
01926   DOM_CLASSINFO_MAP_END
01927 
01928   DOM_CLASSINFO_MAP_BEGIN(HTMLDocument, nsIDOMHTMLDocument)
01929     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLDocument)
01930     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLDocument)
01931     DOM_CLASSINFO_DOCUMENT_MAP_ENTRIES
01932   DOM_CLASSINFO_MAP_END_WITH_XPATH
01933 
01934   DOM_CLASSINFO_MAP_BEGIN(HTMLCollection, nsIDOMHTMLCollection)
01935     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNodeList)
01936     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLCollection)
01937   DOM_CLASSINFO_MAP_END
01938 
01939   DOM_CLASSINFO_MAP_BEGIN(HTMLOptionsCollection, nsIDOMHTMLOptionsCollection)
01940     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLOptionsCollection)
01941     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLOptionCollection)
01942     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLCollection)
01943   DOM_CLASSINFO_MAP_END
01944 
01945   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(HTMLFormControlCollection,
01946                                       nsIDOMHTMLCollection)
01947     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLCollection)
01948     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLFormControlList)
01949   DOM_CLASSINFO_MAP_END
01950 
01951   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(HTMLGenericCollection,
01952                                       nsIDOMHTMLCollection)
01953     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLCollection)
01954   DOM_CLASSINFO_MAP_END
01955 
01956   DOM_CLASSINFO_MAP_BEGIN(HTMLAnchorElement, nsIDOMHTMLAnchorElement)
01957     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLAnchorElement)
01958     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLAnchorElement)
01959     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
01960   DOM_CLASSINFO_MAP_END
01961 
01962   DOM_CLASSINFO_MAP_BEGIN(HTMLAppletElement, nsIDOMHTMLAppletElement)
01963     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLAppletElement)
01964     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
01965   DOM_CLASSINFO_MAP_END
01966 
01967   DOM_CLASSINFO_MAP_BEGIN(HTMLAreaElement, nsIDOMHTMLAreaElement)
01968     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLAreaElement)
01969     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLAreaElement)
01970     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
01971   DOM_CLASSINFO_MAP_END
01972 
01973   DOM_CLASSINFO_MAP_BEGIN(HTMLBRElement, nsIDOMHTMLBRElement)
01974     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLBRElement)
01975     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
01976   DOM_CLASSINFO_MAP_END
01977 
01978   DOM_CLASSINFO_MAP_BEGIN(HTMLBaseElement, nsIDOMHTMLBaseElement)
01979     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLBaseElement)
01980     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
01981   DOM_CLASSINFO_MAP_END
01982 
01983   DOM_CLASSINFO_MAP_BEGIN(HTMLBaseFontElement, nsIDOMHTMLBaseFontElement)
01984     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLBaseFontElement)
01985     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
01986   DOM_CLASSINFO_MAP_END
01987 
01988   DOM_CLASSINFO_MAP_BEGIN(HTMLBodyElement, nsIDOMHTMLBodyElement)
01989     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLBodyElement)
01990     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
01991   DOM_CLASSINFO_MAP_END
01992 
01993   DOM_CLASSINFO_MAP_BEGIN(HTMLButtonElement, nsIDOMHTMLButtonElement)
01994     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLButtonElement)
01995     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLButtonElement)
01996     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
01997   DOM_CLASSINFO_MAP_END
01998 
01999   DOM_CLASSINFO_MAP_BEGIN(HTMLDListElement, nsIDOMHTMLDListElement)
02000     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLDListElement)
02001     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02002   DOM_CLASSINFO_MAP_END
02003 
02004   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(HTMLDelElement, nsIDOMHTMLElement)
02005     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLModElement)
02006     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02007   DOM_CLASSINFO_MAP_END
02008 
02009   DOM_CLASSINFO_MAP_BEGIN(HTMLDirectoryElement, nsIDOMHTMLDirectoryElement)
02010     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLDirectoryElement)
02011     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02012   DOM_CLASSINFO_MAP_END
02013 
02014   DOM_CLASSINFO_MAP_BEGIN(HTMLDivElement, nsIDOMHTMLDivElement)
02015     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLDivElement)
02016     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02017   DOM_CLASSINFO_MAP_END
02018 
02019   DOM_CLASSINFO_MAP_BEGIN(HTMLEmbedElement, nsIDOMHTMLEmbedElement)
02020     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLEmbedElement)
02021 #ifdef MOZ_SVG
02022     DOM_CLASSINFO_MAP_ENTRY(nsIDOMGetSVGDocument)
02023 #endif
02024     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02025   DOM_CLASSINFO_MAP_END
02026 
02027   DOM_CLASSINFO_MAP_BEGIN(HTMLFieldSetElement, nsIDOMHTMLFieldSetElement)
02028     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLFieldSetElement)
02029     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02030   DOM_CLASSINFO_MAP_END
02031 
02032   DOM_CLASSINFO_MAP_BEGIN(HTMLFontElement, nsIDOMHTMLFontElement)
02033     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLFontElement)
02034     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02035   DOM_CLASSINFO_MAP_END
02036 
02037   DOM_CLASSINFO_MAP_BEGIN(HTMLFormElement, nsIDOMHTMLFormElement)
02038     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLFormElement)
02039     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLFormElement)
02040     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02041   DOM_CLASSINFO_MAP_END
02042 
02043   DOM_CLASSINFO_MAP_BEGIN(HTMLFrameElement, nsIDOMHTMLFrameElement)
02044     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLFrameElement)
02045     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLFrameElement)
02046     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02047   DOM_CLASSINFO_MAP_END
02048 
02049   DOM_CLASSINFO_MAP_BEGIN(HTMLFrameSetElement, nsIDOMHTMLFrameSetElement)
02050     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLFrameSetElement)
02051     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02052   DOM_CLASSINFO_MAP_END
02053 
02054   DOM_CLASSINFO_MAP_BEGIN(HTMLHRElement, nsIDOMHTMLHRElement)
02055     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLHRElement)
02056     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLHRElement)
02057     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02058   DOM_CLASSINFO_MAP_END
02059 
02060   DOM_CLASSINFO_MAP_BEGIN(HTMLHeadElement, nsIDOMHTMLHeadElement)
02061     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLHeadElement)
02062     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02063   DOM_CLASSINFO_MAP_END
02064 
02065   DOM_CLASSINFO_MAP_BEGIN(HTMLHeadingElement, nsIDOMHTMLHeadingElement)
02066     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLHeadingElement)
02067     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02068   DOM_CLASSINFO_MAP_END
02069 
02070   DOM_CLASSINFO_MAP_BEGIN(HTMLHtmlElement, nsIDOMHTMLHtmlElement)
02071     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLHtmlElement)
02072     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02073   DOM_CLASSINFO_MAP_END
02074 
02075   DOM_CLASSINFO_MAP_BEGIN(HTMLIFrameElement, nsIDOMHTMLIFrameElement)
02076     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLIFrameElement)
02077     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLFrameElement)
02078     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02079   DOM_CLASSINFO_MAP_END
02080 
02081   DOM_CLASSINFO_MAP_BEGIN(HTMLImageElement, nsIDOMHTMLImageElement)
02082     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLImageElement)
02083     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLImageElement)
02084     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02085   DOM_CLASSINFO_MAP_END
02086 
02087   DOM_CLASSINFO_MAP_BEGIN(HTMLInputElement, nsIDOMHTMLInputElement)
02088     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLInputElement)
02089     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLInputElement)
02090     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02091   DOM_CLASSINFO_MAP_END
02092 
02093   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(HTMLInsElement, nsIDOMHTMLElement)
02094     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLModElement)
02095     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02096   DOM_CLASSINFO_MAP_END
02097 
02098   DOM_CLASSINFO_MAP_BEGIN(HTMLIsIndexElement, nsIDOMHTMLIsIndexElement)
02099     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLIsIndexElement)
02100     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02101   DOM_CLASSINFO_MAP_END
02102 
02103   DOM_CLASSINFO_MAP_BEGIN(HTMLLIElement, nsIDOMHTMLLIElement)
02104     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLLIElement)
02105     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02106   DOM_CLASSINFO_MAP_END
02107 
02108   DOM_CLASSINFO_MAP_BEGIN(HTMLLabelElement, nsIDOMHTMLLabelElement)
02109     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLLabelElement)
02110     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02111   DOM_CLASSINFO_MAP_END
02112 
02113   DOM_CLASSINFO_MAP_BEGIN(HTMLLegendElement, nsIDOMHTMLLegendElement)
02114     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLLegendElement)
02115     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02116   DOM_CLASSINFO_MAP_END
02117 
02118   DOM_CLASSINFO_MAP_BEGIN(HTMLLinkElement, nsIDOMHTMLLinkElement)
02119     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLLinkElement)
02120     DOM_CLASSINFO_MAP_ENTRY(nsIDOMLinkStyle)
02121     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02122   DOM_CLASSINFO_MAP_END
02123 
02124   DOM_CLASSINFO_MAP_BEGIN(HTMLMapElement, nsIDOMHTMLMapElement)
02125     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLMapElement)
02126     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02127   DOM_CLASSINFO_MAP_END
02128 
02129   DOM_CLASSINFO_MAP_BEGIN(HTMLMenuElement, nsIDOMHTMLMenuElement)
02130     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLMenuElement)
02131     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02132   DOM_CLASSINFO_MAP_END
02133 
02134   DOM_CLASSINFO_MAP_BEGIN(HTMLMetaElement, nsIDOMHTMLMetaElement)
02135     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLMetaElement)
02136     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02137   DOM_CLASSINFO_MAP_END
02138 
02139   DOM_CLASSINFO_MAP_BEGIN(HTMLModElement, nsIDOMHTMLModElement)
02140     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLModElement)
02141     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02142   DOM_CLASSINFO_MAP_END
02143 
02144   DOM_CLASSINFO_MAP_BEGIN(HTMLOListElement, nsIDOMHTMLOListElement)
02145     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLOListElement)
02146     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02147   DOM_CLASSINFO_MAP_END
02148 
02149   DOM_CLASSINFO_MAP_BEGIN(HTMLObjectElement, nsIDOMHTMLObjectElement)
02150     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLObjectElement)
02151     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02152   DOM_CLASSINFO_MAP_END
02153 
02154   DOM_CLASSINFO_MAP_BEGIN(HTMLOptGroupElement, nsIDOMHTMLOptGroupElement)
02155     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLOptGroupElement)
02156     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02157   DOM_CLASSINFO_MAP_END
02158 
02159   DOM_CLASSINFO_MAP_BEGIN(HTMLOptionElement, nsIDOMHTMLOptionElement)
02160     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLOptionElement)
02161     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLOptionElement)
02162     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02163   DOM_CLASSINFO_MAP_END
02164 
02165   DOM_CLASSINFO_MAP_BEGIN(HTMLParagraphElement, nsIDOMHTMLParagraphElement)
02166     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLParagraphElement)
02167     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02168   DOM_CLASSINFO_MAP_END
02169 
02170   DOM_CLASSINFO_MAP_BEGIN(HTMLParamElement, nsIDOMHTMLParamElement)
02171     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLParamElement)
02172     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02173   DOM_CLASSINFO_MAP_END
02174 
02175   DOM_CLASSINFO_MAP_BEGIN(HTMLPreElement, nsIDOMHTMLPreElement)
02176     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLPreElement)
02177     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02178   DOM_CLASSINFO_MAP_END
02179 
02180   DOM_CLASSINFO_MAP_BEGIN(HTMLQuoteElement, nsIDOMHTMLQuoteElement)
02181     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLQuoteElement)
02182     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02183   DOM_CLASSINFO_MAP_END
02184 
02185   DOM_CLASSINFO_MAP_BEGIN(HTMLScriptElement, nsIDOMHTMLScriptElement)
02186     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLScriptElement)
02187     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02188   DOM_CLASSINFO_MAP_END
02189 
02190   DOM_CLASSINFO_MAP_BEGIN(HTMLSelectElement, nsIDOMHTMLSelectElement)
02191     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLSelectElement)
02192     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLSelectElement)
02193     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSXBLFormControl)
02194     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02195   DOM_CLASSINFO_MAP_END
02196 
02197   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(HTMLSpacerElement, nsIDOMHTMLElement)
02198     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLElement)
02199     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02200   DOM_CLASSINFO_MAP_END
02201 
02202   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(HTMLSpanElement, nsIDOMHTMLElement)
02203     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLElement)
02204     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02205   DOM_CLASSINFO_MAP_END
02206 
02207   DOM_CLASSINFO_MAP_BEGIN(HTMLStyleElement, nsIDOMHTMLStyleElement)
02208     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLStyleElement)
02209     DOM_CLASSINFO_MAP_ENTRY(nsIDOMLinkStyle)
02210     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02211   DOM_CLASSINFO_MAP_END
02212 
02213   DOM_CLASSINFO_MAP_BEGIN(HTMLTableCaptionElement,
02214                           nsIDOMHTMLTableCaptionElement)
02215     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLTableCaptionElement)
02216     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02217   DOM_CLASSINFO_MAP_END
02218 
02219   DOM_CLASSINFO_MAP_BEGIN(HTMLTableCellElement, nsIDOMHTMLTableCellElement)
02220     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLTableCellElement)
02221     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02222   DOM_CLASSINFO_MAP_END
02223 
02224   DOM_CLASSINFO_MAP_BEGIN(HTMLTableColElement, nsIDOMHTMLTableColElement)
02225     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLTableColElement)
02226     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02227   DOM_CLASSINFO_MAP_END
02228 
02229 
02230   // This should be removed, there are no users of this class any more.
02231 
02232   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(HTMLTableColGroupElement,
02233                                       nsIDOMHTMLTableColElement)
02234     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLTableColElement)
02235     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02236   DOM_CLASSINFO_MAP_END
02237 
02238   DOM_CLASSINFO_MAP_BEGIN(HTMLTableElement, nsIDOMHTMLTableElement)
02239     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLTableElement)
02240     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02241   DOM_CLASSINFO_MAP_END
02242 
02243   DOM_CLASSINFO_MAP_BEGIN(HTMLTableRowElement, nsIDOMHTMLTableRowElement)
02244     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLTableRowElement)
02245     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02246   DOM_CLASSINFO_MAP_END
02247 
02248   DOM_CLASSINFO_MAP_BEGIN(HTMLTableSectionElement,
02249                           nsIDOMHTMLTableSectionElement)
02250     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLTableSectionElement)
02251     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02252   DOM_CLASSINFO_MAP_END
02253 
02254   DOM_CLASSINFO_MAP_BEGIN(HTMLTextAreaElement, nsIDOMHTMLTextAreaElement)
02255     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLTextAreaElement)
02256     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLTextAreaElement)
02257     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02258   DOM_CLASSINFO_MAP_END
02259 
02260   DOM_CLASSINFO_MAP_BEGIN(HTMLTitleElement, nsIDOMHTMLTitleElement)
02261     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLTitleElement)
02262     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02263   DOM_CLASSINFO_MAP_END
02264 
02265   DOM_CLASSINFO_MAP_BEGIN(HTMLUListElement, nsIDOMHTMLUListElement)
02266     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLUListElement)
02267     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02268   DOM_CLASSINFO_MAP_END
02269 
02270   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(HTMLUnknownElement, nsIDOMHTMLElement)
02271     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLElement)
02272     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02273   DOM_CLASSINFO_MAP_END
02274 
02275   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(HTMLWBRElement, nsIDOMHTMLElement)
02276     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLElement)
02277     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02278   DOM_CLASSINFO_MAP_END
02279 
02280   DOM_CLASSINFO_MAP_BEGIN(CSSStyleRule, nsIDOMCSSStyleRule)
02281     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSSStyleRule)
02282   DOM_CLASSINFO_MAP_END
02283 
02284   DOM_CLASSINFO_MAP_BEGIN(CSSCharsetRule, nsIDOMCSSCharsetRule)
02285     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSSCharsetRule)
02286   DOM_CLASSINFO_MAP_END
02287 
02288   DOM_CLASSINFO_MAP_BEGIN(CSSImportRule, nsIDOMCSSImportRule)
02289     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSSImportRule)
02290   DOM_CLASSINFO_MAP_END
02291 
02292   DOM_CLASSINFO_MAP_BEGIN(CSSMediaRule, nsIDOMCSSMediaRule)
02293     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSSMediaRule)
02294   DOM_CLASSINFO_MAP_END
02295 
02296   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(CSSNameSpaceRule, nsIDOMCSSRule)
02297     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSSRule)
02298   DOM_CLASSINFO_MAP_END
02299 
02300   DOM_CLASSINFO_MAP_BEGIN(CSSRuleList, nsIDOMCSSRuleList)
02301     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSSRuleList)
02302   DOM_CLASSINFO_MAP_END
02303 
02304   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(CSSGroupRuleRuleList, nsIDOMCSSRuleList)
02305     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSSRuleList)
02306   DOM_CLASSINFO_MAP_END
02307 
02308   DOM_CLASSINFO_MAP_BEGIN(MediaList, nsIDOMMediaList)
02309     DOM_CLASSINFO_MAP_ENTRY(nsIDOMMediaList)
02310   DOM_CLASSINFO_MAP_END
02311 
02312   DOM_CLASSINFO_MAP_BEGIN(StyleSheetList, nsIDOMStyleSheetList)
02313     DOM_CLASSINFO_MAP_ENTRY(nsIDOMStyleSheetList)
02314   DOM_CLASSINFO_MAP_END
02315 
02316   DOM_CLASSINFO_MAP_BEGIN(CSSStyleSheet, nsIDOMCSSStyleSheet)
02317     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSSStyleSheet)
02318   DOM_CLASSINFO_MAP_END
02319 
02320   DOM_CLASSINFO_MAP_BEGIN(CSSStyleDeclaration, nsIDOMCSSStyleDeclaration)
02321     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSSStyleDeclaration)
02322     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSS2Properties)
02323     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSCSS2Properties)
02324   DOM_CLASSINFO_MAP_END
02325 
02326   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(ComputedCSSStyleDeclaration,
02327                                       nsIDOMCSSStyleDeclaration)
02328     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSSStyleDeclaration)
02329     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSS2Properties)
02330     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSCSS2Properties)
02331   DOM_CLASSINFO_MAP_END
02332 
02333   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(ROCSSPrimitiveValue,
02334                                       nsIDOMCSSPrimitiveValue)
02335     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSSPrimitiveValue)
02336   DOM_CLASSINFO_MAP_END
02337 
02338   DOM_CLASSINFO_MAP_BEGIN(CSSValueList, nsIDOMCSSValueList)
02339     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSSValueList)
02340   DOM_CLASSINFO_MAP_END
02341 
02342   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(CSSRect, nsIDOMRect)
02343     DOM_CLASSINFO_MAP_ENTRY(nsIDOMRect)
02344   DOM_CLASSINFO_MAP_END
02345 
02346   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(CSSRGBColor, nsIDOMRGBColor)
02347     DOM_CLASSINFO_MAP_ENTRY(nsIDOMRGBColor)
02348   DOM_CLASSINFO_MAP_END
02349 
02350   DOM_CLASSINFO_MAP_BEGIN(Range, nsIDOMRange)
02351     DOM_CLASSINFO_MAP_ENTRY(nsIDOMRange)
02352     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSRange)
02353   DOM_CLASSINFO_MAP_END
02354 
02355   DOM_CLASSINFO_MAP_BEGIN(TreeWalker, nsIDOMTreeWalker)
02356     DOM_CLASSINFO_MAP_ENTRY(nsIDOMTreeWalker)
02357   DOM_CLASSINFO_MAP_END
02358 
02359   DOM_CLASSINFO_MAP_BEGIN(Selection, nsISelection)
02360     DOM_CLASSINFO_MAP_ENTRY(nsISelection)
02361   DOM_CLASSINFO_MAP_END
02362 
02363 #ifdef MOZ_XUL
02364   DOM_CLASSINFO_MAP_BEGIN(XULDocument, nsIDOMXULDocument)
02365     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDocument)
02366     DOM_CLASSINFO_MAP_ENTRY(nsIDOMXULDocument)
02367     DOM_CLASSINFO_MAP_ENTRY(nsIDOMXULDocument_MOZILLA_1_8_BRANCH)
02368     DOM_CLASSINFO_DOCUMENT_MAP_ENTRIES
02369   DOM_CLASSINFO_MAP_END_WITH_XPATH
02370 
02371   DOM_CLASSINFO_MAP_BEGIN(XULElement, nsIDOMXULElement)
02372     DOM_CLASSINFO_MAP_ENTRY(nsIDOMXULElement)
02373     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
02374     DOM_CLASSINFO_MAP_ENTRY(nsIDOM3Node)
02375   DOM_CLASSINFO_MAP_END
02376 
02377   DOM_CLASSINFO_MAP_BEGIN(XULCommandDispatcher, nsIDOMXULCommandDispatcher)
02378     DOM_CLASSINFO_MAP_ENTRY(nsIDOMXULCommandDispatcher)
02379   DOM_CLASSINFO_MAP_END
02380 
02381   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(XULNodeList, nsIDOMNodeList)
02382     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNodeList)
02383   DOM_CLASSINFO_MAP_END
02384 
02385   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(XULNamedNodeMap, nsIDOMNamedNodeMap)
02386     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNamedNodeMap)
02387   DOM_CLASSINFO_MAP_END
02388 
02389   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(XULAttr, nsIDOMAttr)
02390     DOM_CLASSINFO_MAP_ENTRY(nsIDOMAttr)
02391   DOM_CLASSINFO_MAP_END
02392 #endif
02393 
02394   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(XULControllers, nsIControllers)
02395     DOM_CLASSINFO_MAP_ENTRY(nsIControllers)
02396   DOM_CLASSINFO_MAP_END
02397 
02398 #ifdef MOZ_XUL
02399   DOM_CLASSINFO_MAP_BEGIN(BoxObject, nsIBoxObject)
02400     DOM_CLASSINFO_MAP_ENTRY(nsIBoxObject)
02401   DOM_CLASSINFO_MAP_END
02402 
02403   DOM_CLASSINFO_MAP_BEGIN(TreeSelection, nsITreeSelection)
02404     DOM_CLASSINFO_MAP_ENTRY(nsITreeSelection)
02405   DOM_CLASSINFO_MAP_END
02406 
02407   DOM_CLASSINFO_MAP_BEGIN(TreeContentView, nsITreeContentView)
02408     DOM_CLASSINFO_MAP_ENTRY(nsITreeContentView)
02409     DOM_CLASSINFO_MAP_ENTRY(nsITreeView)
02410   DOM_CLASSINFO_MAP_END
02411 #endif
02412 
02413   DOM_CLASSINFO_MAP_BEGIN(Crypto, nsIDOMCrypto)
02414     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCrypto)
02415   DOM_CLASSINFO_MAP_END
02416 
02417   DOM_CLASSINFO_MAP_BEGIN(CRMFObject, nsIDOMCRMFObject)
02418     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCRMFObject)
02419   DOM_CLASSINFO_MAP_END
02420 
02421   DOM_CLASSINFO_MAP_BEGIN(Pkcs11, nsIDOMPkcs11)
02422     DOM_CLASSINFO_MAP_ENTRY(nsIDOMPkcs11)
02423   DOM_CLASSINFO_MAP_END
02424 
02425   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(XMLStylesheetProcessingInstruction, nsIDOMProcessingInstruction)
02426     DOM_CLASSINFO_MAP_ENTRY(nsIDOMProcessingInstruction)
02427     DOM_CLASSINFO_MAP_ENTRY(nsIDOMLinkStyle)
02428     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
02429     DOM_CLASSINFO_MAP_ENTRY(nsIDOM3Node)
02430   DOM_CLASSINFO_MAP_END
02431 
02432   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(ChromeWindow, nsIDOMWindow)
02433     DOM_CLASSINFO_MAP_ENTRY(nsIDOMWindow)
02434     DOM_CLASSINFO_MAP_ENTRY(nsIDOMJSWindow)
02435     DOM_CLASSINFO_MAP_ENTRY(nsIDOMWindowInternal)
02436     DOM_CLASSINFO_MAP_ENTRY(nsIDOMChromeWindow)
02437     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
02438     // XXXjst: Do we want this on chrome windows?
02439     // DOM_CLASSINFO_MAP_ENTRY(nsIDOMStorageWindow)
02440     DOM_CLASSINFO_MAP_ENTRY(nsIDOMViewCSS)
02441     DOM_CLASSINFO_MAP_ENTRY(nsIDOMAbstractView)
02442   DOM_CLASSINFO_MAP_END
02443 
02444   DOM_CLASSINFO_MAP_BEGIN(RangeException, nsIDOMRangeException)
02445     DOM_CLASSINFO_MAP_ENTRY(nsIDOMRangeException)
02446     DOM_CLASSINFO_MAP_ENTRY(nsIException)
02447   DOM_CLASSINFO_MAP_END
02448 
02449   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(ContentList, nsIDOMHTMLCollection)
02450     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNodeList)
02451     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLCollection)
02452   DOM_CLASSINFO_MAP_END
02453 
02454   DOM_CLASSINFO_MAP_BEGIN(ImageDocument, nsIImageDocument)
02455     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLDocument)
02456     DOM_CLASSINFO_MAP_ENTRY(nsIImageDocument)
02457     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSHTMLDocument)
02458     DOM_CLASSINFO_DOCUMENT_MAP_ENTRIES
02459   DOM_CLASSINFO_MAP_END_WITH_XPATH
02460 
02461 #ifdef MOZ_XUL
02462   DOM_CLASSINFO_MAP_BEGIN(XULTemplateBuilder, nsIXULTemplateBuilder)
02463     DOM_CLASSINFO_MAP_ENTRY(nsIXULTemplateBuilder)
02464   DOM_CLASSINFO_MAP_END
02465 
02466   DOM_CLASSINFO_MAP_BEGIN(XULTreeBuilder, nsIXULTreeBuilder)
02467     DOM_CLASSINFO_MAP_ENTRY(nsIXULTreeBuilder)
02468     DOM_CLASSINFO_MAP_ENTRY(nsITreeView)
02469   DOM_CLASSINFO_MAP_END
02470 #endif
02471 
02472   DOM_CLASSINFO_MAP_BEGIN(DOMStringList, nsIDOMDOMStringList)
02473     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDOMStringList)
02474   DOM_CLASSINFO_MAP_END
02475 
02476   DOM_CLASSINFO_MAP_BEGIN(NameList, nsIDOMNameList)
02477     DOM_CLASSINFO_MAP_ENTRY(nsIDOMNameList)
02478   DOM_CLASSINFO_MAP_END
02479 
02480 #ifdef MOZ_XUL
02481   DOM_CLASSINFO_MAP_BEGIN(TreeColumn, nsITreeColumn)
02482     DOM_CLASSINFO_MAP_ENTRY(nsITreeColumn)
02483   DOM_CLASSINFO_MAP_END
02484 
02485   DOM_CLASSINFO_MAP_BEGIN(TreeColumns, nsITreeColumns)
02486     DOM_CLASSINFO_MAP_ENTRY(nsITreeColumns)
02487   DOM_CLASSINFO_MAP_END
02488 #endif
02489 
02490   DOM_CLASSINFO_MAP_BEGIN(CSSMozDocumentRule, nsIDOMCSSMozDocumentRule)
02491     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCSSMozDocumentRule)
02492   DOM_CLASSINFO_MAP_END
02493 
02494   DOM_CLASSINFO_MAP_BEGIN(BeforeUnloadEvent, nsIDOMBeforeUnloadEvent)
02495     DOM_CLASSINFO_MAP_ENTRY(nsIDOMBeforeUnloadEvent)
02496     DOM_CLASSINFO_EVENT_MAP_ENTRIES
02497   DOM_CLASSINFO_MAP_END
02498 
02499 #ifdef MOZ_SVG
02500 #define DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES \
02501     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGElement) \
02502     DOM_CLASSINFO_MAP_ENTRY(nsIDOM3Node)
02503 
02504 #define DOM_CLASSINFO_SVG_GRAPHIC_ELEMENT_MAP_ENTRIES \
02505     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)        \
02506     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGLocatable)       \
02507     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGTransformable)   \
02508     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStylable)        \
02509     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02510 
02511   // XXX - the proto chain stuff is sort of hackish, because of the MI in
02512   // the SVG interfaces. I doubt that extending the proto on one interface
02513   // works properly on an element which inherits off multiple interfaces.
02514   // Tough luck. - bbaetz
02515 
02516   // The SVG document
02517 
02518   DOM_CLASSINFO_MAP_BEGIN(SVGDocument, nsIDOMSVGDocument)
02519     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGDocument)
02520     DOM_CLASSINFO_MAP_ENTRY(nsIDOMDocument)
02521     DOM_CLASSINFO_DOCUMENT_MAP_ENTRIES
02522   DOM_CLASSINFO_MAP_END_WITH_XPATH
02523 
02524   // SVG element classes
02525 
02526   DOM_CLASSINFO_MAP_BEGIN(SVGCircleElement, nsIDOMSVGCircleElement)
02527     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGCircleElement)
02528     DOM_CLASSINFO_SVG_GRAPHIC_ELEMENT_MAP_ENTRIES
02529   DOM_CLASSINFO_MAP_END
02530 
02531   DOM_CLASSINFO_MAP_BEGIN(SVGClipPathElement, nsIDOMSVGClipPathElement)
02532     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGClipPathElement)
02533     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGLocatable)
02534     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGTransformable)
02535     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStylable)
02536     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02537   DOM_CLASSINFO_MAP_END
02538 
02539   DOM_CLASSINFO_MAP_BEGIN(SVGDefsElement, nsIDOMSVGDefsElement)
02540     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGDefsElement)
02541     DOM_CLASSINFO_SVG_GRAPHIC_ELEMENT_MAP_ENTRIES
02542   DOM_CLASSINFO_MAP_END
02543 
02544   DOM_CLASSINFO_MAP_BEGIN(SVGDescElement, nsIDOMSVGDescElement)
02545     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGDescElement)
02546     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStylable)
02547     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02548   DOM_CLASSINFO_MAP_END
02549 
02550   DOM_CLASSINFO_MAP_BEGIN(SVGEllipseElement, nsIDOMSVGEllipseElement)
02551     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGEllipseElement)
02552     DOM_CLASSINFO_SVG_GRAPHIC_ELEMENT_MAP_ENTRIES
02553   DOM_CLASSINFO_MAP_END
02554 
02555   DOM_CLASSINFO_MAP_BEGIN(SVGGElement, nsIDOMSVGGElement)
02556     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGGElement)
02557     DOM_CLASSINFO_SVG_GRAPHIC_ELEMENT_MAP_ENTRIES
02558   DOM_CLASSINFO_MAP_END
02559 
02560   DOM_CLASSINFO_MAP_BEGIN(SVGGradientElement, nsIDOMSVGGradientElement)
02561     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGGradientElement)
02562     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGURIReference)
02563     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStylable)
02564     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02565   DOM_CLASSINFO_MAP_END
02566 
02567   DOM_CLASSINFO_MAP_BEGIN(SVGImageElement, nsIDOMSVGImageElement)
02568     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGImageElement)
02569     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGURIReference)
02570     DOM_CLASSINFO_SVG_GRAPHIC_ELEMENT_MAP_ENTRIES
02571   DOM_CLASSINFO_MAP_END
02572 
02573   DOM_CLASSINFO_MAP_BEGIN(SVGLinearGradientElement, nsIDOMSVGLinearGradientElement)
02574     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGGradientElement)
02575     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGLinearGradientElement)
02576     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGURIReference)
02577     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStylable)
02578     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02579   DOM_CLASSINFO_MAP_END
02580 
02581   DOM_CLASSINFO_MAP_BEGIN(SVGLineElement, nsIDOMSVGLineElement)
02582     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGLineElement)
02583     DOM_CLASSINFO_SVG_GRAPHIC_ELEMENT_MAP_ENTRIES
02584   DOM_CLASSINFO_MAP_END
02585 
02586   DOM_CLASSINFO_MAP_BEGIN(SVGMarkerElement, nsIDOMSVGMarkerElement)
02587     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGMarkerElement)
02588     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStylable)
02589     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGFitToViewBox)
02590     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02591   DOM_CLASSINFO_MAP_END
02592 
02593   DOM_CLASSINFO_MAP_BEGIN(SVGMetadataElement, nsIDOMSVGMetadataElement)
02594     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGMetadataElement)
02595     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02596   DOM_CLASSINFO_MAP_END
02597 
02598   DOM_CLASSINFO_MAP_BEGIN(SVGPathElement, nsIDOMSVGPathElement)
02599     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathElement)
02600     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAnimatedPathData)
02601     DOM_CLASSINFO_SVG_GRAPHIC_ELEMENT_MAP_ENTRIES
02602   DOM_CLASSINFO_MAP_END
02603 
02604   DOM_CLASSINFO_MAP_BEGIN(SVGPolygonElement, nsIDOMSVGPolygonElement)
02605     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPolygonElement)
02606     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAnimatedPoints)
02607     DOM_CLASSINFO_SVG_GRAPHIC_ELEMENT_MAP_ENTRIES
02608   DOM_CLASSINFO_MAP_END
02609 
02610   DOM_CLASSINFO_MAP_BEGIN(SVGPolylineElement, nsIDOMSVGPolylineElement)
02611     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPolylineElement)
02612     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAnimatedPoints)
02613     DOM_CLASSINFO_SVG_GRAPHIC_ELEMENT_MAP_ENTRIES
02614   DOM_CLASSINFO_MAP_END
02615 
02616   DOM_CLASSINFO_MAP_BEGIN(SVGRadialGradientElement, nsIDOMSVGRadialGradientElement)
02617     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGGradientElement)
02618     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGRadialGradientElement)
02619     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGURIReference)
02620     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStylable)
02621     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02622   DOM_CLASSINFO_MAP_END
02623 
02624   DOM_CLASSINFO_MAP_BEGIN(SVGRectElement, nsIDOMSVGRectElement)
02625     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGRectElement)
02626     DOM_CLASSINFO_SVG_GRAPHIC_ELEMENT_MAP_ENTRIES
02627   DOM_CLASSINFO_MAP_END
02628 
02629   DOM_CLASSINFO_MAP_BEGIN(SVGScriptElement, nsIDOMSVGScriptElement)
02630     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGScriptElement)
02631     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGURIReference)
02632     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02633   DOM_CLASSINFO_MAP_END
02634 
02635   DOM_CLASSINFO_MAP_BEGIN(SVGStopElement, nsIDOMSVGStopElement)
02636     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStopElement)
02637     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStylable)
02638     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02639   DOM_CLASSINFO_MAP_END
02640   
02641   DOM_CLASSINFO_MAP_BEGIN(SVGStyleElement, nsIDOMSVGStyleElement)
02642     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStyleElement)
02643     DOM_CLASSINFO_MAP_ENTRY(nsIDOMLinkStyle)
02644     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02645   DOM_CLASSINFO_MAP_END
02646 
02647   DOM_CLASSINFO_MAP_BEGIN(SVGSVGElement, nsIDOMSVGSVGElement)
02648     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
02649     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGSVGElement)
02650     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGFitToViewBox)
02651     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGLocatable)
02652     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStylable)
02653     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGZoomAndPan)
02654     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02655   DOM_CLASSINFO_MAP_END
02656 
02657   DOM_CLASSINFO_MAP_BEGIN(SVGSymbolElement, nsIDOMSVGSymbolElement)
02658     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
02659     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGSymbolElement)
02660     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGFitToViewBox)
02661     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStylable)
02662     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02663   DOM_CLASSINFO_MAP_END
02664 
02665   DOM_CLASSINFO_MAP_BEGIN(SVGTextElement, nsIDOMSVGTextElement)
02666     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGTextPositioningElement)
02667     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGTextContentElement)
02668     DOM_CLASSINFO_SVG_GRAPHIC_ELEMENT_MAP_ENTRIES
02669   DOM_CLASSINFO_MAP_END
02670 
02671   DOM_CLASSINFO_MAP_BEGIN(SVGTitleElement, nsIDOMSVGTitleElement)
02672     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGTitleElement)
02673     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStylable)
02674     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02675   DOM_CLASSINFO_MAP_END
02676 
02677   DOM_CLASSINFO_MAP_BEGIN(SVGTSpanElement, nsIDOMSVGTSpanElement)
02678     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGTextPositioningElement)
02679     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGTextContentElement)
02680     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
02681     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStylable)
02682     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02683   DOM_CLASSINFO_MAP_END
02684 
02685   DOM_CLASSINFO_MAP_BEGIN(SVGUseElement, nsIDOMSVGUseElement)
02686     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGUseElement)
02687     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGURIReference)
02688     DOM_CLASSINFO_SVG_GRAPHIC_ELEMENT_MAP_ENTRIES
02689   DOM_CLASSINFO_MAP_END
02690 
02691   // other SVG classes
02692 
02693   DOM_CLASSINFO_MAP_BEGIN(SVGAngle, nsIDOMSVGAngle)
02694     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAngle)
02695   DOM_CLASSINFO_MAP_END
02696 
02697   DOM_CLASSINFO_MAP_BEGIN(SVGAnimatedAngle, nsIDOMSVGAnimatedAngle)
02698     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAnimatedAngle)
02699   DOM_CLASSINFO_MAP_END
02700 
02701   DOM_CLASSINFO_MAP_BEGIN(SVGAnimatedEnumeration, nsIDOMSVGAnimatedEnumeration)
02702     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAnimatedEnumeration)
02703   DOM_CLASSINFO_MAP_END
02704 
02705   DOM_CLASSINFO_MAP_BEGIN(SVGAnimatedLength, nsIDOMSVGAnimatedLength)
02706     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAnimatedLength)
02707   DOM_CLASSINFO_MAP_END
02708 
02709   DOM_CLASSINFO_MAP_BEGIN(SVGAnimatedLengthList, nsIDOMSVGAnimatedLengthList)
02710     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAnimatedLengthList)
02711   DOM_CLASSINFO_MAP_END
02712 
02713   DOM_CLASSINFO_MAP_BEGIN(SVGAnimatedNumber, nsIDOMSVGAnimatedNumber)
02714     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAnimatedNumber)
02715   DOM_CLASSINFO_MAP_END
02716 
02717   DOM_CLASSINFO_MAP_BEGIN(SVGAnimatedNumberList, nsIDOMSVGAnimatedNumberList)
02718     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAnimatedNumberList)
02719   DOM_CLASSINFO_MAP_END
02720 
02721   DOM_CLASSINFO_MAP_BEGIN(SVGAnimatedPoints, nsIDOMSVGAnimatedPoints)
02722     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAnimatedPoints)
02723   DOM_CLASSINFO_MAP_END
02724 
02725   DOM_CLASSINFO_MAP_BEGIN(SVGAnimatedPreserveAspectRatio, nsIDOMSVGAnimatedPreserveAspectRatio)
02726     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAnimatedPreserveAspectRatio)
02727   DOM_CLASSINFO_MAP_END
02728 
02729   DOM_CLASSINFO_MAP_BEGIN(SVGAnimatedRect, nsIDOMSVGAnimatedRect)
02730     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAnimatedRect)
02731   DOM_CLASSINFO_MAP_END
02732 
02733   DOM_CLASSINFO_MAP_BEGIN(SVGAnimatedString, nsIDOMSVGAnimatedString)
02734     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAnimatedString)
02735   DOM_CLASSINFO_MAP_END
02736 
02737   DOM_CLASSINFO_MAP_BEGIN(SVGAnimatedTransformList, nsIDOMSVGAnimatedTransformList)
02738     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGAnimatedTransformList)
02739   DOM_CLASSINFO_MAP_END
02740 
02741   DOM_CLASSINFO_MAP_BEGIN(SVGEvent, nsIDOMSVGEvent)
02742     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGEvent)
02743     DOM_CLASSINFO_EVENT_MAP_ENTRIES
02744   DOM_CLASSINFO_MAP_END
02745 
02746   DOM_CLASSINFO_MAP_BEGIN(SVGException, nsIDOMSVGException)
02747     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGException)
02748     DOM_CLASSINFO_MAP_ENTRY(nsIException)
02749   DOM_CLASSINFO_MAP_END
02750 
02751   DOM_CLASSINFO_MAP_BEGIN(SVGLength, nsIDOMSVGLength)
02752     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGLength)
02753   DOM_CLASSINFO_MAP_END
02754 
02755   DOM_CLASSINFO_MAP_BEGIN(SVGLengthList, nsIDOMSVGLengthList)
02756     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGLengthList)
02757   DOM_CLASSINFO_MAP_END
02758 
02759   DOM_CLASSINFO_MAP_BEGIN(SVGMatrix, nsIDOMSVGMatrix)
02760     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGMatrix)
02761   DOM_CLASSINFO_MAP_END
02762 
02763   DOM_CLASSINFO_MAP_BEGIN(SVGNumber, nsIDOMSVGNumber)
02764     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGNumber)
02765   DOM_CLASSINFO_MAP_END
02766 
02767   DOM_CLASSINFO_MAP_BEGIN(SVGNumberList, nsIDOMSVGNumberList)
02768     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGNumberList)
02769   DOM_CLASSINFO_MAP_END
02770 
02771   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegArcAbs, nsIDOMSVGPathSegArcAbs)
02772     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegArcAbs)
02773   DOM_CLASSINFO_MAP_END
02774 
02775   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegArcRel, nsIDOMSVGPathSegArcRel)
02776     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegArcRel)
02777   DOM_CLASSINFO_MAP_END
02778 
02779   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegClosePath, nsIDOMSVGPathSegClosePath)
02780     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegClosePath)
02781   DOM_CLASSINFO_MAP_END
02782 
02783   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegCurvetoCubicAbs, nsIDOMSVGPathSegCurvetoCubicAbs)
02784     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegCurvetoCubicAbs)
02785   DOM_CLASSINFO_MAP_END
02786 
02787   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegCurvetoCubicRel, nsIDOMSVGPathSegCurvetoCubicRel)
02788     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegCurvetoCubicRel)
02789   DOM_CLASSINFO_MAP_END
02790 
02791   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegCurvetoCubicSmoothAbs, nsIDOMSVGPathSegCurvetoCubicSmoothAbs)
02792     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegCurvetoCubicSmoothAbs)
02793   DOM_CLASSINFO_MAP_END
02794 
02795   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegCurvetoCubicSmoothRel, nsIDOMSVGPathSegCurvetoCubicSmoothRel)
02796     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegCurvetoCubicSmoothRel)
02797   DOM_CLASSINFO_MAP_END
02798 
02799   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegCurvetoQuadraticAbs, nsIDOMSVGPathSegCurvetoQuadraticAbs)
02800     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegCurvetoQuadraticAbs)
02801   DOM_CLASSINFO_MAP_END
02802 
02803   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegCurvetoQuadraticRel, nsIDOMSVGPathSegCurvetoQuadraticRel)
02804     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegCurvetoQuadraticRel)
02805   DOM_CLASSINFO_MAP_END
02806 
02807   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegCurvetoQuadraticSmoothAbs, nsIDOMSVGPathSegCurvetoQuadraticSmoothAbs)
02808     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegCurvetoQuadraticSmoothAbs)
02809   DOM_CLASSINFO_MAP_END
02810 
02811   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegCurvetoQuadraticSmoothRel, nsIDOMSVGPathSegCurvetoQuadraticSmoothRel)
02812     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegCurvetoQuadraticSmoothRel)
02813   DOM_CLASSINFO_MAP_END
02814 
02815   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegLinetoAbs, nsIDOMSVGPathSegLinetoAbs)
02816     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegLinetoAbs)
02817   DOM_CLASSINFO_MAP_END
02818 
02819   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegLinetoHorizontalAbs, nsIDOMSVGPathSegLinetoHorizontalAbs)
02820     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegLinetoHorizontalAbs)
02821   DOM_CLASSINFO_MAP_END
02822 
02823   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegLinetoHorizontalRel, nsIDOMSVGPathSegLinetoHorizontalRel)
02824     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegLinetoHorizontalRel)
02825   DOM_CLASSINFO_MAP_END
02826 
02827   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegLinetoRel, nsIDOMSVGPathSegLinetoRel)
02828     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegLinetoRel)
02829   DOM_CLASSINFO_MAP_END
02830 
02831   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegLinetoVerticalAbs, nsIDOMSVGPathSegLinetoVerticalAbs)
02832     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegLinetoVerticalAbs)
02833   DOM_CLASSINFO_MAP_END
02834 
02835   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegLinetoVerticalRel, nsIDOMSVGPathSegLinetoVerticalRel)
02836     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegLinetoVerticalRel)
02837   DOM_CLASSINFO_MAP_END
02838 
02839   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegList, nsIDOMSVGPathSegList)
02840     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegList)
02841   DOM_CLASSINFO_MAP_END
02842 
02843   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegMovetoAbs, nsIDOMSVGPathSegMovetoAbs)
02844     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegMovetoAbs)
02845   DOM_CLASSINFO_MAP_END
02846 
02847   DOM_CLASSINFO_MAP_BEGIN(SVGPathSegMovetoRel, nsIDOMSVGPathSegMovetoRel)
02848     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPathSegMovetoRel)
02849   DOM_CLASSINFO_MAP_END
02850 
02851   DOM_CLASSINFO_MAP_BEGIN(SVGPoint, nsIDOMSVGPoint)
02852     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPoint)
02853   DOM_CLASSINFO_MAP_END
02854 
02855   DOM_CLASSINFO_MAP_BEGIN(SVGPointList, nsIDOMSVGPointList)
02856     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPointList)
02857   DOM_CLASSINFO_MAP_END
02858 
02859   DOM_CLASSINFO_MAP_BEGIN(SVGPreserveAspectRatio, nsIDOMSVGPreserveAspectRatio)
02860     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGPreserveAspectRatio)
02861   DOM_CLASSINFO_MAP_END
02862 
02863   DOM_CLASSINFO_MAP_BEGIN(SVGRect, nsIDOMSVGRect)
02864     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGRect)
02865   DOM_CLASSINFO_MAP_END
02866 
02867   DOM_CLASSINFO_MAP_BEGIN(SVGTransform, nsIDOMSVGTransform)
02868     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGTransform)
02869   DOM_CLASSINFO_MAP_END
02870 
02871   DOM_CLASSINFO_MAP_BEGIN(SVGTransformList, nsIDOMSVGTransformList)
02872     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGTransformList)
02873   DOM_CLASSINFO_MAP_END
02874 
02875   DOM_CLASSINFO_MAP_BEGIN(SVGZoomEvent, nsIDOMSVGZoomEvent)
02876     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGZoomEvent)
02877     DOM_CLASSINFO_EVENT_MAP_ENTRIES
02878   DOM_CLASSINFO_MAP_END
02879 #endif // MOZ_SVG
02880 
02881   DOM_CLASSINFO_MAP_BEGIN(HTMLCanvasElement, nsIDOMHTMLCanvasElement)
02882     DOM_CLASSINFO_MAP_ENTRY(nsIDOMHTMLCanvasElement)
02883     DOM_CLASSINFO_GENERIC_HTML_MAP_ENTRIES
02884   DOM_CLASSINFO_MAP_END
02885 
02886 #ifdef MOZ_ENABLE_CANVAS
02887   DOM_CLASSINFO_MAP_BEGIN(CanvasRenderingContext2D, nsIDOMCanvasRenderingContext2D)
02888     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCanvasRenderingContext2D)
02889   DOM_CLASSINFO_MAP_END
02890 
02891   DOM_CLASSINFO_MAP_BEGIN(CanvasGradient, nsIDOMCanvasGradient)
02892     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCanvasGradient)
02893   DOM_CLASSINFO_MAP_END
02894 
02895   DOM_CLASSINFO_MAP_BEGIN(CanvasPattern, nsIDOMCanvasPattern)
02896     DOM_CLASSINFO_MAP_ENTRY(nsIDOMCanvasPattern)
02897   DOM_CLASSINFO_MAP_END
02898 #endif // MOZ_ENABLE_CANVAS
02899 
02900 #if defined(MOZ_SVG)
02901   DOM_CLASSINFO_MAP_BEGIN(SVGTextPathElement, nsIDOMSVGTextPathElement)
02902     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGTextContentElement)
02903     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGURIReference)
02904     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
02905     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGStylable)
02906     DOM_CLASSINFO_SVG_ELEMENT_MAP_ENTRIES
02907   DOM_CLASSINFO_MAP_END
02908 #endif
02909 
02910   // We just want this to have classinfo so it gets mark callbacks for marking
02911   // event listeners.
02912   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(WindowRoot, nsISupports)
02913   DOM_CLASSINFO_MAP_END
02914 
02915   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(DOMParser, nsIDOMParser)
02916     DOM_CLASSINFO_MAP_ENTRY(nsIDOMParser)
02917   DOM_CLASSINFO_MAP_END
02918 
02919   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(XMLSerializer, nsIDOMSerializer)
02920     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSerializer)
02921   DOM_CLASSINFO_MAP_END
02922 
02923   DOM_CLASSINFO_MAP_BEGIN(XMLHttpRequest, nsIXMLHttpRequest)
02924     DOM_CLASSINFO_MAP_ENTRY(nsIXMLHttpRequest)
02925     DOM_CLASSINFO_MAP_ENTRY(nsIJSXMLHttpRequest)
02926     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
02927     DOM_CLASSINFO_MAP_ENTRY(nsIInterfaceRequestor)
02928   DOM_CLASSINFO_MAP_END
02929 
02930   DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(XMLHttpProgressEvent, nsIDOMEvent)
02931     DOM_CLASSINFO_MAP_ENTRY(nsIDOMEvent)
02932     DOM_CLASSINFO_MAP_ENTRY(nsIDOMLSProgressEvent)
02933   DOM_CLASSINFO_MAP_END
02934 
02935 #if defined(MOZ_SVG) && defined(MOZ_SVG_FOREIGNOBJECT)
02936   DOM_CLASSINFO_MAP_BEGIN(SVGForeignObjectElement, nsIDOMSVGForeignObjectElement)
02937     DOM_CLASSINFO_MAP_ENTRY(nsIDOMSVGForeignObjectElement)
02938     DOM_CLASSINFO_SVG_GRAPHIC_ELEMENT_MAP_ENTRIES
02939   DOM_CLASSINFO_MAP_END
02940 #endif
02941 
02942    DOM_CLASSINFO_MAP_BEGIN(Storage, nsIDOMStorage)
02943      DOM_CLASSINFO_MAP_ENTRY(nsIDOMStorage)
02944    DOM_CLASSINFO_MAP_END
02945  
02946    DOM_CLASSINFO_MAP_BEGIN(StorageList, nsIDOMStorageList)
02947      DOM_CLASSINFO_MAP_ENTRY(nsIDOMStorageList)
02948    DOM_CLASSINFO_MAP_END
02949  
02950    DOM_CLASSINFO_MAP_BEGIN(StorageItem, nsIDOMStorageItem)
02951      DOM_CLASSINFO_MAP_ENTRY(nsIDOMStorageItem)
02952      DOM_CLASSINFO_MAP_ENTRY(nsIDOMToString)
02953    DOM_CLASSINFO_MAP_END
02954  
02955    DOM_CLASSINFO_MAP_BEGIN(StorageEvent, nsIDOMStorageEvent)
02956      DOM_CLASSINFO_MAP_ENTRY(nsIDOMStorageEvent)
02957    DOM_CLASSINFO_MAP_END
02958  
02959    DOM_CLASSINFO_MAP_BEGIN(XULCommandEvent, nsIDOMXULCommandEvent)
02960      DOM_CLASSINFO_MAP_ENTRY(nsIDOMXULCommandEvent)
02961      DOM_CLASSINFO_UI_EVENT_MAP_ENTRIES
02962    DOM_CLASSINFO_MAP_END
02963 
02964 #ifdef NS_DEBUG
02965   {
02966     PRUint32 i = sizeof(sClassInfoData) / sizeof(sClassInfoData[0]);
02967 
02968     if (i != eDOMClassInfoIDCount) {
02969       NS_ERROR("The number of items in sClassInfoData doesn't match the "
02970                "number of nsIDOMClassInfo ID's, this is bad! Fix it!");
02971 
02972       return NS_ERROR_NOT_INITIALIZED;
02973     }
02974 
02975     for (i = 0; i < eDOMClassInfoIDCount; i++) {
02976       if (!sClassInfoData[i].u.mConstructorFptr ||
02977           sClassInfoData[i].mDebugID != i) {
02978         NS_ERROR("Class info data out of sync, you forgot to update "
02979                  "nsDOMClassInfo.h and nsDOMClassInfo.cpp! Fix this, "
02980                  "mozilla will not work without this fixed!");
02981 
02982         return NS_ERROR_NOT_INITIALIZED;
02983       }
02984     }
02985 
02986     for (i = 0; i < eDOMClassInfoIDCount; i++) {
02987       if (!sClassInfoData[i].mInterfaces) {
02988         NS_ERROR("Class info data without an interface list! Fix this, "
02989                  "mozilla will not work without this fixed!");
02990 
02991         return NS_ERROR_NOT_INITIALIZED;
02992       }
02993     }
02994   }
02995 #endif
02996 
02997   // Initialize static JSString's
02998   DefineStaticJSVals(cx);
02999 
03000   PRInt32 i;
03001 
03002   for (i = 0; i < eDOMClassInfoIDCount; ++i) {
03003     RegisterClassName(i);
03004   }
03005 
03006   for (i = 0; i < eDOMClassInfoIDCount; ++i) {
03007     RegisterClassProtos(i);
03008   }
03009 
03010   PRBool doSecurityCheckInAddProperty = sDoSecurityCheckInAddProperty;
03011   sDoSecurityCheckInAddProperty = PR_FALSE;
03012   RegisterExternalClasses();
03013   sDoSecurityCheckInAddProperty = doSecurityCheckInAddProperty;
03014 
03015   sDisableDocumentAllSupport =
03016     nsContentUtils::GetBoolPref("browser.dom.document.all.disabled");
03017 
03018   sDisableGlobalScopePollutionSupport =
03019     nsContentUtils::GetBoolPref("browser.dom.global_scope_pollution.disabled");
03020 
03021   sIsInitialized = PR_TRUE;
03022 
03023   return NS_OK;
03024 }
03025 
03026 // static
03027 PRInt32
03028 nsDOMClassInfo::GetArrayIndexFromId(JSContext *cx, jsval id, PRBool *aIsNumber)
03029 {
03030   jsdouble array_index;
03031 
03032   if (aIsNumber) {
03033     *aIsNumber = PR_FALSE;
03034   }
03035 
03036   if (!::JS_ValueToNumber(cx, id, &array_index)) {
03037     return -1;
03038   }
03039 
03040   jsint i = -1;
03041 
03042   if (!JSDOUBLE_IS_INT(array_index, i)) {
03043     return -1;
03044   }
03045 
03046   if (aIsNumber) {
03047     *aIsNumber = PR_TRUE;
03048   }
03049 
03050   return i;
03051 }
03052 
03053 NS_IMETHODIMP
03054 nsDOMClassInfo::GetInterfaces(PRUint32 *aCount, nsIID ***aArray)
03055 {
03056   PRUint32 count = 0;
03057 
03058   while (mData->mInterfaces[count]) {
03059     count++;
03060   }
03061 
03062   *aCount = count;
03063 
03064   if (!count) {
03065     *aArray = nsnull;
03066 
03067     return NS_OK;
03068   }
03069 
03070   *aArray = NS_STATIC_CAST(nsIID **, nsMemory::Alloc(count * sizeof(nsIID *)));
03071   NS_ENSURE_TRUE(*aArray, NS_ERROR_OUT_OF_MEMORY);
03072 
03073   PRUint32 i;
03074   for (i = 0; i < count; i++) {
03075     nsIID *iid = NS_STATIC_CAST(nsIID *, nsMemory::Clone(mData->mInterfaces[i],
03076                                                          sizeof(nsIID)));
03077 
03078     if (!iid) {
03079       NS_FREE_XPCOM_ALLOCATED_POINTER_ARRAY(i, *aArray);
03080 
03081       return NS_ERROR_OUT_OF_MEMORY;
03082     }
03083 
03084     *((*aArray) + i) = iid;
03085   }
03086 
03087   return NS_OK;
03088 }
03089 
03090 NS_IMETHODIMP
03091 nsDOMClassInfo::GetHelperForLanguage(PRUint32 language, nsISupports **_retval)
03092 {
03093   if (language == nsIProgrammingLanguage::JAVASCRIPT) {
03094     *_retval = NS_STATIC_CAST(nsIXPCScriptable *, this);
03095 
03096     NS_ADDREF(*_retval);
03097   } else {
03098     *_retval = nsnull;
03099   }
03100 
03101   return NS_OK;
03102 }
03103 
03104 NS_IMETHODIMP
03105 nsDOMClassInfo::GetContractID(char **aContractID)
03106 {
03107   *aContractID = nsnull;
03108 
03109   return NS_OK;
03110 }
03111 
03112 NS_IMETHODIMP
03113 nsDOMClassInfo::GetClassDescription(char **aClassDescription)
03114 {
03115   return GetClassName(aClassDescription);
03116 }
03117 
03118 NS_IMETHODIMP
03119 nsDOMClassInfo::GetClassID(nsCID **aClassID)
03120 {
03121   *aClassID = nsnull;
03122   return NS_OK;
03123 }
03124 
03125 NS_IMETHODIMP
03126 nsDOMClassInfo::GetClassIDNoAlloc(nsCID *aClassID)
03127 {
03128   return NS_ERROR_NOT_AVAILABLE;
03129 }
03130 
03131 NS_IMETHODIMP
03132 nsDOMClassInfo::GetImplementationLanguage(PRUint32 *aImplLanguage)
03133 {
03134   *aImplLanguage = nsIProgrammingLanguage::CPLUSPLUS;
03135 
03136   return NS_OK;
03137 }
03138 
03139 NS_IMETHODIMP
03140 nsDOMClassInfo::GetFlags(PRUint32 *aFlags)
03141 {
03142   *aFlags = DOMCLASSINFO_STANDARD_FLAGS;
03143 
03144   return NS_OK;
03145 }
03146 
03147 // nsIXPCScriptable
03148 
03149 NS_IMETHODIMP
03150 nsDOMClassInfo::GetClassName(char **aClassName)
03151 {
03152   *aClassName = nsCRT::strdup(mData->mName);
03153 
03154   return NS_OK;
03155 }
03156 
03157 NS_IMETHODIMP
03158 nsDOMClassInfo::GetScriptableFlags(PRUint32 *aFlags)
03159 {
03160   *aFlags = mData->mScriptableFlags;
03161 
03162   return NS_OK;
03163 }
03164 
03165 NS_IMETHODIMP
03166 nsDOMClassInfo::PreCreate(nsISupports *nativeObj, JSContext *cx,
03167                           JSObject *globalObj, JSObject **parentObj)
03168 {
03169   *parentObj = globalObj;
03170 
03171   nsCOMPtr<nsIXPConnectWrappedNative> wrapper;
03172   nsresult rv =
03173     sXPConnect->GetWrappedNativeOfJSObject(cx, globalObj,
03174                                            getter_AddRefs(wrapper));
03175   if (NS_FAILED(rv)) {
03176     return NS_OK;
03177   }
03178 
03179   nsCOMPtr<nsPIDOMWindow> piwin = do_QueryWrappedNative(wrapper);
03180 
03181   if (!piwin) {
03182     return NS_OK;
03183   }
03184 
03185   if (piwin->IsOuterWindow()) {
03186     *parentObj = ((nsGlobalWindow *)piwin.get())->
03187       GetCurrentInnerWindowInternal()->GetGlobalJSObject();
03188   }
03189 
03190   return NS_OK;
03191 }
03192 
03193 NS_IMETHODIMP
03194 nsDOMClassInfo::Create(nsIXPConnectWrappedNative *wrapper,
03195                        JSContext *cx, JSObject *obj)
03196 {
03197   NS_ERROR("Don't call me!");
03198 
03199   return NS_ERROR_UNEXPECTED;
03200 }
03201 
03202 NS_IMETHODIMP
03203 nsDOMClassInfo::PostCreate(nsIXPConnectWrappedNative *wrapper,
03204                            JSContext *cx, JSObject *obj)
03205 {
03206   static const nsIID *sSupportsIID = &NS_GET_IID(nsISupports);
03207 
03208   // This is safe because...
03209   if (mData->mProtoChainInterface == sSupportsIID ||
03210       !mData->mProtoChainInterface) {
03211     return NS_OK;
03212   }
03213 
03214 #ifdef DEBUG
03215   {
03216     nsCOMPtr<nsIScriptGlobalObject> sgo(do_QueryWrappedNative(wrapper));
03217 
03218     NS_ASSERTION(!sgo || sgo->GetGlobalJSObject() == nsnull,
03219                  "Multiple wrappers created for global object!");
03220   }
03221 #endif
03222 
03223   JSObject *proto = nsnull;
03224 
03225   wrapper->GetJSObjectPrototype(&proto);
03226 
03227   JSObject *proto_proto = ::JS_GetPrototype(cx, proto);
03228 
03229   JSClass *proto_proto_class = JS_GET_CLASS(cx, proto_proto);
03230 
03231   if (proto_proto_class != sObjectClass) {
03232     // We've just wrapped an object of a type that has been wrapped on
03233     // this scope already so the prototype of the xpcwrapped native's
03234     // prototype is already set up.
03235 
03236     return NS_OK;
03237   }
03238 
03239 #ifdef DEBUG
03240   if (mData->mHasClassInterface) {
03241     nsCOMPtr<nsIInterfaceInfoManager> iim =
03242       dont_AddRef(XPTI_GetInterfaceInfoManager());
03243 
03244     if (iim) {
03245       nsCOMPtr<nsIInterfaceInfo> if_info;
03246       iim->GetInfoForIID(mData->mProtoChainInterface,
03247                          getter_AddRefs(if_info));
03248 
03249       if (if_info) {
03250         nsXPIDLCString name;
03251         if_info->GetName(getter_Copies(name));
03252         NS_ASSERTION(nsCRT::strcmp(CutPrefix(name), mData->mName) == 0,
03253                      "Class name and proto chain interface name mismatch!");
03254       }
03255     }
03256   }
03257 #endif
03258 
03259   // Look up the name of our constructor in the current global scope. We do
03260   // this because triggering this lookup can cause us to call
03261   // nsWindowSH::NewResolve, which will end up in nsWindowSH::GlobalResolve.
03262   // GlobalResolve does some prototype magic (which satisfies the if condition
03263   // above) in order to make sure that prototype delegation works correctly.
03264   // Consider if a site sets HTMLElement.prototype.foopy = function () { ... }
03265   // Now, calling document.body.foopy() needs to ensure that looking up foopy
03266   // on document.body's prototype will find the right function. This
03267   // LookupProperty accomplishes that.
03268   // XXX This shouldn't need to go through the JS engine. Instead, we should
03269   // be calling nsWindowSH::GlobalResolve directly.
03270   JSObject *global = GetGlobalJSObject(cx, obj);
03271   jsval val;
03272   if (!::JS_LookupProperty(cx, global, mData->mName, &val)) {
03273     return NS_ERROR_UNEXPECTED;
03274   }
03275 
03276   return NS_OK;
03277 }
03278 
03279 NS_IMETHODIMP
03280 nsDOMClassInfo::AddProperty(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
03281                             JSObject *obj, jsval id, jsval *vp,
03282                             PRBool *_retval)
03283 {
03284   NS_ERROR("Don't call me!");
03285 
03286   return NS_ERROR_UNEXPECTED;
03287 }
03288 
03289 NS_IMETHODIMP
03290 nsDOMClassInfo::DelProperty(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
03291                             JSObject *obj, jsval id, jsval *vp,
03292                             PRBool *_retval)
03293 {
03294   NS_ERROR("Don't call me!");
03295 
03296   return NS_ERROR_UNEXPECTED;
03297 }
03298 
03299 NS_IMETHODIMP
03300 nsDOMClassInfo::GetProperty(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
03301                             JSObject *obj, jsval id, jsval *vp,
03302                             PRBool *_retval)
03303 {
03304   NS_ERROR("Don't call me!");
03305 
03306   return NS_OK;
03307 }
03308 
03309 NS_IMETHODIMP
03310 nsDOMClassInfo::SetProperty(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
03311                             JSObject *obj, jsval id, jsval *vp,
03312                             PRBool *_retval)
03313 {
03314   NS_ERROR("Don't call me!");
03315 
03316   return NS_ERROR_UNEXPECTED;
03317 }
03318 
03319 NS_IMETHODIMP
03320 nsDOMClassInfo::Enumerate(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
03321                           JSObject *obj, PRBool *_retval)
03322 {
03323   if (!sSecMan)
03324     return NS_OK;
03325 
03326   // Ask the security manager if it's OK to enumerate
03327   nsresult rv =
03328     sSecMan->CheckPropertyAccess(cx, obj, mData->mName, sEnumerate_id,
03329                                  nsIXPCSecurityManager::ACCESS_GET_PROPERTY);
03330 
03331   if (NS_FAILED(rv)) {
03332     // Let XPConnect know that the access was not granted.
03333     *_retval = PR_FALSE;
03334   }
03335 
03336   return NS_OK;
03337 }
03338 
03339 NS_IMETHODIMP
03340 nsDOMClassInfo::NewEnumerate(nsIXPConnectWrappedNative *wrapper,
03341                              JSContext *cx, JSObject *obj, PRUint32 enum_op,
03342                              jsval *statep, jsid *idp, PRBool *_retval)
03343 {
03344   NS_ERROR("Don't call me!");
03345 
03346   return NS_ERROR_UNEXPECTED;
03347 }
03348 
03349 nsresult
03350 nsDOMClassInfo::ResolveConstructor(JSContext *cx, JSObject *obj,
03351                                    JSObject **objp)
03352 {
03353   JSObject *global = GetGlobalJSObject(cx, obj);
03354 
03355   jsval val;
03356   if (!::JS_GetProperty(cx, global, mData->mName, &val)) {
03357     return NS_ERROR_UNEXPECTED;
03358   }
03359 
03360   if (!JSVAL_IS_PRIMITIVE(val)) {
03361     // If val is not an (non-null) object there either is no
03362     // constructor for this class, or someone messed with
03363     // window.classname, just fall through and let the JS engine
03364     // return the Object constructor.
03365 
03366     JSString *str = JSVAL_TO_STRING(sConstructor_id);
03367     if (!::JS_DefineUCProperty(cx, obj, ::JS_GetStringChars(str),
03368                                ::JS_GetStringLength(str), val, nsnull, nsnull,
03369                                JSPROP_ENUMERATE)) {
03370       return NS_ERROR_UNEXPECTED;
03371     }
03372 
03373     *objp = obj;
03374   }
03375 
03376   return NS_OK;
03377 }
03378 
03379 NS_IMETHODIMP
03380 nsDOMClassInfo::NewResolve(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
03381                            JSObject *obj, jsval id, PRUint32 flags,
03382                            JSObject **objp, PRBool *_retval)
03383 {
03384   if (id == sConstructor_id && !(flags & JSRESOLVE_ASSIGNING)) {
03385     return ResolveConstructor(cx, obj, objp);
03386   }
03387 
03388   return NS_OK;
03389 }
03390 
03391 NS_IMETHODIMP
03392 nsDOMClassInfo::Convert(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
03393                         JSObject *obj, PRUint32 type, jsval *vp,
03394                         PRBool *_retval)
03395 {
03396   NS_ERROR("Don't call me!");
03397 
03398   return NS_ERROR_UNEXPECTED;
03399 }
03400 
03401 NS_IMETHODIMP
03402 nsDOMClassInfo::Finalize(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
03403                          JSObject *obj)
03404 {
03405   NS_ERROR("Don't call me!");
03406 
03407   return NS_ERROR_UNEXPECTED;
03408 }
03409 
03410 NS_IMETHODIMP
03411 nsDOMClassInfo::CheckAccess(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
03412                             JSObject *obj, jsval id, PRUint32 mode,
03413                             jsval *vp, PRBool *_retval)
03414 {
03415   PRUint32 mode_type = mode & JSACC_TYPEMASK;
03416 
03417   if ((mode_type == JSACC_WATCH ||
03418        mode_type == JSACC_PROTO ||
03419        mode_type == JSACC_PARENT) &&
03420       sSecMan) {
03421 
03422     JSObject *real_obj = nsnull;
03423     nsresult rv = wrapper->GetJSObject(&real_obj);
03424     NS_ENSURE_SUCCESS(rv, rv);
03425 
03426     rv =
03427       sSecMan->CheckPropertyAccess(cx, real_obj, mData->mName, id,
03428                                    nsIXPCSecurityManager::ACCESS_GET_PROPERTY);
03429 
03430     if (NS_FAILED(rv)) {
03431       // Let XPConnect know that the access was not granted.
03432       *_retval = PR_FALSE;
03433     }
03434   }
03435 
03436   return NS_OK;
03437 }
03438 
03439 NS_IMETHODIMP
03440 nsDOMClassInfo::Call(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
03441                      JSObject *obj, PRUint32 argc, jsval *argv, jsval *vp,
03442                      PRBool *_retval)
03443 {
03444   NS_ERROR("Don't call me!");
03445 
03446   return NS_ERROR_UNEXPECTED;
03447 }
03448 
03449 NS_IMETHODIMP
03450 nsDOMClassInfo::Construct(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
03451                           JSObject *obj, PRUint32 argc, jsval *argv,
03452                           jsval *vp, PRBool *_retval)
03453 {
03454   NS_ERROR("Don't call me!");
03455 
03456   return NS_ERROR_UNEXPECTED;
03457 }
03458 
03459 NS_IMETHODIMP
03460 nsDOMClassInfo::HasInstance(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
03461                             JSObject *obj, jsval val, PRBool *bp,
03462                             PRBool *_retval)
03463 {
03464   NS_ERROR("Don't call me!");
03465 
03466   return NS_ERROR_UNEXPECTED;
03467 }
03468 
03469 NS_IMETHODIMP
03470 nsDOMClassInfo::Mark(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
03471                      JSObject *obj, void *arg, PRUint32 *_retval)
03472 {
03473   NS_ERROR("Don't call me!");
03474 
03475   return NS_ERROR_UNEXPECTED;
03476 }
03477 
03478 NS_IMETHODIMP
03479 nsDOMClassInfo::Equality(nsIXPConnectWrappedNative *wrapper, JSContext * cx,
03480                          JSObject * obj, jsval val, PRBool *bp)
03481 {
03482   NS_ERROR("Don't call me!");
03483 
03484   return NS_ERROR_UNEXPECTED;
03485 }
03486 
03487 NS_IMETHODIMP
03488 nsDOMClassInfo::OuterObject(nsIXPConnectWrappedNative *wrapper, JSContext * cx,
03489                             JSObject * obj, JSObject * *_retval)
03490 {
03491   NS_ERROR("Don't call me!");
03492 
03493   return NS_ERROR_UNEXPECTED;
03494 }
03495 
03496 NS_IMETHODIMP
03497 nsDOMClassInfo::InnerObject(nsIXPConnectWrappedNative *wrapper, JSContext * cx,
03498                             JSObject * obj, JSObject * *_retval)
03499 {
03500   NS_ERROR("nsDOMClassInfo::InnerObject Don't call me!");
03501 
03502   return NS_ERROR_UNEXPECTED;
03503 }
03504 
03505 // These are declared here so we can assert that they're empty in ShutDown.
03515 static PLDHashTable sPreservedWrapperTable;
03516 
03517 // See ExternallyReferencedEntry.
03518 static PLDHashTable sExternallyReferencedTable;
03519 
03520 // See RootWhenExternallyReferencedEntry
03521 static PLDHashTable sRootWhenExternallyReferencedTable;
03522 
03523 // static
03524 nsIClassInfo *
03525 nsDOMClassInfo::GetClassInfoInstance(nsDOMClassInfoID aID)
03526 {
03527   if (aID >= eDOMClassInfoIDCount) {
03528     NS_ERROR("Bad ID!");
03529 
03530     return nsnull;
03531   }
03532 
03533   if (!sIsInitialized) {
03534     nsresult rv = Init();
03535 
03536     NS_ENSURE_SUCCESS(rv, nsnull);
03537   }
03538 
03539   if (!sClassInfoData[aID].mCachedClassInfo) {
03540     nsDOMClassInfoData& data = sClassInfoData[aID];
03541 
03542     data.mCachedClassInfo = data.u.mConstructorFptr(&data);
03543     NS_ENSURE_TRUE(data.mCachedClassInfo, nsnull);
03544 
03545     NS_ADDREF(data.mCachedClassInfo);
03546   }
03547 
03548   NS_ASSERTION(!IS_EXTERNAL(sClassInfoData[aID].mCachedClassInfo),
03549                "This is bad, internal class marked as external!");
03550 
03551   return sClassInfoData[aID].mCachedClassInfo;
03552 }
03553 
03554 // static
03555 nsIClassInfo *
03556 nsDOMClassInfo::GetClassInfoInstance(nsDOMClassInfoData* aData)
03557 {
03558   NS_ASSERTION(IS_EXTERNAL(aData->mCachedClassInfo)
03559                || !aData->mCachedClassInfo,
03560                "This is bad, external class marked as internal!");
03561 
03562   if (!aData->mCachedClassInfo) {
03563     if (aData->u.mExternalConstructorFptr) {
03564       aData->mCachedClassInfo =
03565         aData->u.mExternalConstructorFptr(aData->mName);
03566     } else {
03567       aData->mCachedClassInfo = nsDOMGenericSH::doCreate(aData);
03568     }
03569     NS_ENSURE_TRUE(aData->mCachedClassInfo, nsnull);
03570 
03571     NS_ADDREF(aData->mCachedClassInfo);
03572     aData->mCachedClassInfo = MARK_EXTERNAL(aData->mCachedClassInfo);
03573   }
03574 
03575   return GET_CLEAN_CI_PTR(aData->mCachedClassInfo);
03576 }
03577 
03578 // static
03579 void
03580 nsDOMClassInfo::ShutDown()
03581 {
03582   NS_ASSERTION(sPreservedWrapperTable.ops == 0,
03583                "preserved wrapper table not empty at shutdown");
03584   NS_ASSERTION(sExternallyReferencedTable.ops == 0 ||
03585                sExternallyReferencedTable.entryCount == 0,
03586                "rooted participant table not empty at shutdown");
03587   NS_ASSERTION(sRootWhenExternallyReferencedTable.ops == 0,
03588                "root when externally referenced table not empty at shutdown");
03589 
03590   if (sExternallyReferencedTable.ops &&
03591       sExternallyReferencedTable.entryCount == 0) {
03592     PL_DHashTableFinish(&sExternallyReferencedTable);
03593     sExternallyReferencedTable.ops = nsnull;
03594   }
03595 
03596   if (sClassInfoData[0].u.mConstructorFptr) {
03597     PRUint32 i;
03598 
03599     for (i = 0; i < eDOMClassInfoIDCount; i++) {
03600       NS_IF_RELEASE(sClassInfoData[i].mCachedClassInfo);
03601     }
03602   }
03603 
03604   sTop_id             = JSVAL_VOID;
03605   sParent_id          = JSVAL_VOID;
03606   sScrollbars_id      = JSVAL_VOID;
03607   sLocation_id        = JSVAL_VOID;
03608   sComponents_id      = JSVAL_VOID;
03609   sConstructor_id     = JSVAL_VOID;
03610   s_content_id        = JSVAL_VOID;
03611   sContent_id         = JSVAL_VOID;
03612   sMenubar_id         = JSVAL_VOID;
03613   sToolbar_id         = JSVAL_VOID;
03614   sLocationbar_id     = JSVAL_VOID;
03615   sPersonalbar_id     = JSVAL_VOID;
03616   sStatusbar_id       = JSVAL_VOID;
03617   sDirectories_id     = JSVAL_VOID;
03618   sControllers_id     = JSVAL_VOID;
03619   sLength_id          = JSVAL_VOID;
03620   sInnerHeight_id     = JSVAL_VOID;
03621   sInnerWidth_id      = JSVAL_VOID;
03622   sOuterHeight_id     = JSVAL_VOID;
03623   sOuterWidth_id      = JSVAL_VOID;
03624   sScreenX_id         = JSVAL_VOID;
03625   sScreenY_id         = JSVAL_VOID;
03626   sStatus_id          = JSVAL_VOID;
03627   sName_id            = JSVAL_VOID;
03628   sOnmousedown_id     = JSVAL_VOID;
03629   sOnmouseup_id       = JSVAL_VOID;
03630   sOnclick_id         = JSVAL_VOID;
03631   sOndblclick_id      = JSVAL_VOID;
03632   sOncontextmenu_id   = JSVAL_VOID;
03633   sOnmouseover_id     = JSVAL_VOID;
03634   sOnmouseout_id      = JSVAL_VOID;
03635   sOnkeydown_id       = JSVAL_VOID;
03636   sOnkeyup_id         = JSVAL_VOID;
03637   sOnkeypress_id      = JSVAL_VOID;
03638   sOnmousemove_id     = JSVAL_VOID;
03639   sOnfocus_id         = JSVAL_VOID;
03640   sOnblur_id          = JSVAL_VOID;
03641   sOnsubmit_id        = JSVAL_VOID;
03642   sOnreset_id         = JSVAL_VOID;
03643   sOnchange_id        = JSVAL_VOID;
03644   sOnselect_id        = JSVAL_VOID;
03645   sOnload_id          = JSVAL_VOID;
03646   sOnbeforeunload_id  = JSVAL_VOID;
03647   sOnunload_id        = JSVAL_VOID;
03648   sOnpageshow_id      = JSVAL_VOID;
03649   sOnpagehide_id      = JSVAL_VOID;
03650   sOnabort_id         = JSVAL_VOID;
03651   sOnerror_id         = JSVAL_VOID;
03652   sOnpaint_id         = JSVAL_VOID;
03653   sOnresize_id        = JSVAL_VOID;
03654   sOnscroll_id        = JSVAL_VOID;
03655   sScrollIntoView_id  = JSVAL_VOID;
03656   sScrollX_id         = JSVAL_VOID;
03657   sScrollY_id         = JSVAL_VOID;
03658   sScrollMaxX_id      = JSVAL_VOID;
03659   sScrollMaxY_id      = JSVAL_VOID;
03660   sOpen_id            = JSVAL_VOID;
03661   sItem_id            = JSVAL_VOID;
03662   sEnumerate_id       = JSVAL_VOID;
03663   sNavigator_id       = JSVAL_VOID;
03664   sDocument_id        = JSVAL_VOID;
03665   sWindow_id          = JSVAL_VOID;
03666   sFrames_id          = JSVAL_VOID;
03667   sSelf_id            = JSVAL_VOID;
03668   sOpener_id          = JSVAL_VOID;
03669 
03670   NS_IF_RELEASE(sXPConnect);
03671   NS_IF_RELEASE(sSecMan);
03672   sIsInitialized = PR_FALSE;
03673 }
03674 
03675 
03676 static const nsIXPConnectWrappedNative *cached_win_wrapper;
03677 static const JSContext *cached_win_cx;
03678 static PRBool cached_win_needs_check = PR_TRUE;
03679 static const nsIXPConnectWrappedNative *cached_doc_wrapper;
03680 static const JSContext *cached_doc_cx;
03681 static PRBool cached_doc_needs_check = PR_TRUE;
03682 
03683 
03684 void InvalidateContextAndWrapperCache()
03685 {
03686   cached_win_wrapper = nsnull;
03687   cached_doc_wrapper = nsnull;
03688   cached_win_cx = nsnull;
03689   cached_doc_cx = nsnull;
03690   cached_win_needs_check = PR_TRUE;
03691   cached_doc_needs_check = PR_TRUE;
03692 }
03693 
03694 // static helper that determines if a security manager check is needed
03695 // by checking if the callee's context is the same as the caller's
03696 // context
03697 // Note: See documentNeedsSecurityCheck for information about the control
03698 // flow in this function.
03699 
03700 static inline PRBool
03701 needsSecurityCheck(JSContext *cx, nsIXPConnectWrappedNative *wrapper)
03702 {
03703   // We cache a pointer to a wrapper and a context that we've last vetted
03704   // and cache what the verdict was.
03705 
03706   // First, compare the context and wrapper with the cached ones
03707   if (cx == cached_win_cx && wrapper == cached_win_wrapper) {
03708     return cached_win_needs_check;
03709   }
03710 
03711   cached_win_cx = cx;
03712   cached_win_wrapper = wrapper;
03713   cached_win_needs_check = PR_TRUE;
03714   
03715   nsCOMPtr<nsIScriptGlobalObject> sgo(do_QueryWrappedNative(wrapper));
03716 
03717   if (!sgo) {
03718     NS_ERROR("Huh, global not a nsIScriptGlobalObject?");
03719 
03720     return PR_TRUE;
03721   }
03722 
03723   nsIScriptContext *otherScriptContext = sgo->GetContext();
03724 
03725   if (!otherScriptContext) {
03726     return PR_TRUE;
03727   }
03728 
03729   if (cx != (JSContext *)otherScriptContext->GetNativeContext()) {
03730     return PR_TRUE;
03731   }
03732 
03733   // Compare the current context and function object
03734   // to the ones in the next JS frame
03735   JSStackFrame *fp = nsnull;
03736   JSObject *fp_obj = nsnull;
03737 
03738   cached_win_needs_check = PR_FALSE;
03739 
03740   do {
03741     fp = ::JS_FrameIterator(cx, &fp);
03742 
03743     if (!fp) {
03744       cached_win_cx = nsnull;
03745       return cached_win_needs_check;
03746     }
03747 
03748     fp_obj = ::JS_GetFrameFunctionObject(cx, fp);
03749     cached_win_needs_check = PR_TRUE;
03750   } while (!fp_obj);
03751 
03752   JSObject *global = GetGlobalJSObject(cx, fp_obj);
03753 
03754   JSObject *wrapper_obj = nsnull;
03755   wrapper->GetJSObject(&wrapper_obj);
03756 
03757   if (global != wrapper_obj) {
03758     return PR_TRUE;
03759   }
03760 
03761   cached_win_needs_check = PR_FALSE;
03762   return PR_FALSE;
03763 }
03764 
03765 
03766 // Window helper
03767 
03768 nsresult
03769 nsDOMClassInfo::doCheckPropertyAccess(JSContext *cx, JSObject *obj, jsval id,
03770                                       nsIXPConnectWrappedNative *wrapper,
03771                                       PRUint32 accessMode, PRBool isWindow)
03772 {
03773   if (!sSecMan) {
03774     return NS_OK;
03775   }
03776 
03777   // Don't check when getting the Components property, since we check
03778   // its properties anyway. This will help performance.
03779   if (id == sComponents_id &&
03780       accessMode == nsIXPCSecurityManager::ACCESS_GET_PROPERTY && isWindow) {
03781     return NS_OK;
03782   }
03783 
03784   nsISupports *native = wrapper->Native();
03785   nsCOMPtr<nsIScriptGlobalObject> sgo;
03786 
03787   if (isWindow) {
03788     sgo = do_QueryInterface(native);
03789     NS_ENSURE_TRUE(sgo, NS_ERROR_UNEXPECTED);
03790   } else {
03791     nsCOMPtr<nsIDocument> doc(do_QueryInterface(native));
03792     NS_ENSURE_TRUE(doc, NS_ERROR_UNEXPECTED);
03793 
03794     sgo = doc->GetScriptGlobalObject();
03795 
03796     if (!sgo) {
03797       // There's no script global in the document. This means that
03798       // this document is a result from using XMLHttpRequest or it's a
03799       // document created through a DOMImplementation. In that case
03800       // there's nothing we can do since the context on which the
03801       // document was created is not accessable and we can't do a
03802       // security check, but the document must remain
03803       // scriptable. Documents loaded through these methods have
03804       // already been vetted by the security manager before they were
03805       // loaded, so allowing access here w/o doing a security check
03806       // here is probably safe anyway.
03807 
03808       return NS_OK;
03809     }
03810   }
03811 
03812   nsIScriptContext *scx = sgo->GetContext();
03813   JSObject *global;
03814 
03815   if (!scx || !scx->IsContextInitialized() ||
03816       !(global = sgo->GetGlobalJSObject())) {
03817     return NS_OK;
03818   }
03819 
03820   return sSecMan->CheckPropertyAccess(cx, global, mData->mName, id,
03821                                       accessMode);
03822 }
03823 
03824 NS_IMETHODIMP
03825 nsWindowSH::PreCreate(nsISupports *nativeObj, JSContext *cx,
03826                       JSObject *globalObj, JSObject **parentObj)
03827 {
03828   // Since this is one of the first calls we'll get from XPConnect,
03829   // grab the pointer to the Object class so we'll have it later on.
03830 
03831   if (!sObjectClass) {
03832     JSObject *obj, *proto = globalObj;
03833 
03834     do {
03835       obj = proto;
03836       proto = ::JS_GetPrototype(cx, obj);
03837     } while (proto);
03838 
03839     sObjectClass = JS_GET_CLASS(cx, obj);
03840   }
03841 
03842   // Normally ::PreCreate() is used to give XPConnect the parent
03843   // object for the object that's being wrapped, this parent object is
03844   // set as the parent of the wrapper and it's also used to find the
03845   // right scope for the object being wrapped. Now, in the case of the
03846   // global object the wrapper shouldn't have a parent but we supply
03847   // one here anyway (the global object itself) and this will be used
03848   // by XPConnect only to find the right scope, once the scope is
03849   // found XPConnect will find the existing wrapper (which always
03850   // exists since it's created on window construction), since an
03851   // existing wrapper is found the parent we supply here is ignored
03852   // after the wrapper is found.
03853 
03854   nsCOMPtr<nsIScriptGlobalObject> sgo(do_QueryInterface(nativeObj));
03855   NS_WARN_IF_FALSE(sgo, "nativeObj not a global object!");
03856 
03857   if (sgo) {
03858     *parentObj = sgo->GetGlobalJSObject();
03859 
03860     if (*parentObj) {
03861       return NS_OK;
03862     }
03863   }
03864 
03865   // We're most likely being called when the global object is
03866   // created, at that point we won't get a nsIScriptContext but we
03867   // know we're called on the correct context so we return globalObj
03868 
03869   *parentObj = globalObj;
03870 
03871   return NS_OK;
03872 }
03873 
03874 
03875 // This JS class piggybacks on nsHTMLDocumentSH::ReleaseDocument()...
03876 
03877 static JSClass sGlobalScopePolluterClass = {
03878   "Global Scope Polluter",
03879   JSCLASS_HAS_PRIVATE | JSCLASS_PRIVATE_IS_NSISUPPORTS | JSCLASS_NEW_RESOLVE,
03880   nsWindowSH::SecurityCheckOnSetProp, nsWindowSH::SecurityCheckOnSetProp,
03881   nsWindowSH::GlobalScopePolluterGetProperty,
03882   nsWindowSH::SecurityCheckOnSetProp, JS_EnumerateStub,
03883   (JSResolveOp)nsWindowSH::GlobalScopePolluterNewResolve, JS_ConvertStub,
03884   nsHTMLDocumentSH::ReleaseDocument
03885 };
03886 
03887 
03888 // static
03889 JSBool JS_DLL_CALLBACK
03890 nsWindowSH::GlobalScopePolluterGetProperty(JSContext *cx, JSObject *obj,
03891                                            jsval id, jsval *vp)
03892 {
03893   // Someone is accessing a element by referencing its name/id in the
03894   // global scope, do a security check to make sure that's ok.
03895 
03896   nsresult rv =
03897     sSecMan->CheckPropertyAccess(cx, GetGlobalJSObject(cx, obj), "Window", id,
03898                                  nsIXPCSecurityManager::ACCESS_GET_PROPERTY);
03899 
03900   if (NS_FAILED(rv)) {
03901     // The security check failed. The security manager set a JS
03902     // exception for us.
03903 
03904     return JS_FALSE;
03905   }
03906 
03907   // Print a warning on the console so developers have a chance to
03908   // catch and fix these mistakes.
03909   PrintWarningOnConsole(cx, "GlobalScopeElementReference");
03910 
03911   return JS_TRUE;
03912 }
03913 
03914 // static
03915 JSBool JS_DLL_CALLBACK
03916 nsWindowSH::SecurityCheckOnSetProp(JSContext *cx, JSObject *obj, jsval id,
03917                                    jsval *vp)
03918 {
03919   // Someone is accessing a element by referencing its name/id in the
03920   // global scope, do a security check to make sure that's ok.
03921 
03922   nsresult rv =
03923     sSecMan->CheckPropertyAccess(cx, GetGlobalJSObject(cx, obj), "Window", id,
03924                                  nsIXPCSecurityManager::ACCESS_SET_PROPERTY);
03925 
03926   // If !NS_SUCCEEDED(rv) the security check failed. The security
03927   // manager set a JS exception for us.
03928   return NS_SUCCEEDED(rv);
03929 }
03930 
03931 // static
03932 JSBool JS_DLL_CALLBACK
03933 nsWindowSH::GlobalScopePolluterNewResolve(JSContext *cx, JSObject *obj,
03934                                           jsval id, uintN flags,
03935                                           JSObject **objp)
03936 {
03937   if (flags & (JSRESOLVE_ASSIGNING | JSRESOLVE_DECLARING |
03938                JSRESOLVE_CLASSNAME | JSRESOLVE_QUALIFIED) ||
03939       !JSVAL_IS_STRING(id)) {
03940     // Nothing to do here if we're either assigning or declaring,
03941     // resolving a class name, doing a qualified resolve, or
03942     // resolving a number.
03943 
03944     return JS_TRUE;
03945   }
03946 
03947   nsIHTMLDocument *doc = (nsIHTMLDocument *)::JS_GetPrivate(cx, obj);
03948 
03949   if (!doc || doc->GetCompatibilityMode() != eCompatibility_NavQuirks) {
03950     // If we don't have a document, or if the document is not in
03951     // quirks mode, return early.
03952 
03953     return JS_TRUE;
03954   }
03955 
03956   JSObject *proto = ::JS_GetPrototype(cx, obj);
03957   JSString *jsstr = JSVAL_TO_STRING(id);
03958   JSBool hasProp;
03959 
03960   if (!proto || !::JS_HasUCProperty(cx, proto, ::JS_GetStringChars(jsstr),
03961                                     ::JS_GetStringLength(jsstr), &hasProp) ||
03962       hasProp) {
03963     // No prototype, or the property exists on the prototype. Do
03964     // nothing.
03965 
03966     return JS_TRUE;
03967   }
03968 
03969   nsDependentJSString str(jsstr);
03970   nsCOMPtr<nsISupports> result;
03971 
03972   {
03973     nsCOMPtr<nsIDOMDocument> dom_doc(do_QueryInterface(doc));
03974     nsCOMPtr<nsIDOMElement> element;
03975 
03976     dom_doc->GetElementById(str, getter_AddRefs(element));
03977 
03978     result = element;
03979   }
03980 
03981   if (!result) {
03982     doc->ResolveName(str, nsnull, getter_AddRefs(result));
03983   }
03984 
03985   if (result) {
03986     jsval v;
03987     nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
03988     nsresult rv = WrapNative(cx, obj, result, NS_GET_IID(nsISupports), &v,
03989                              getter_AddRefs(holder));
03990     NS_ENSURE_SUCCESS(rv, rv);
03991 
03992     if (!::JS_DefineUCProperty(cx, obj, ::JS_GetStringChars(jsstr),
03993                                ::JS_GetStringLength(jsstr), v, nsnull, nsnull,
03994                                0)) {
03995       nsDOMClassInfo::ThrowJSException(cx, NS_ERROR_UNEXPECTED);
03996 
03997       return JS_FALSE;
03998     }
03999 
04000     *objp = obj;
04001   }
04002 
04003   return JS_TRUE;
04004 }
04005 
04006 // static
04007 void
04008 nsWindowSH::InvalidateGlobalScopePolluter(JSContext *cx, JSObject *obj)
04009 {
04010   JSObject *proto;
04011 
04012   while ((proto = ::JS_GetPrototype(cx, obj))) {
04013     if (JS_GET_CLASS(cx, proto) == &sGlobalScopePolluterClass) {
04014       nsIHTMLDocument *doc = (nsIHTMLDocument *)::JS_GetPrivate(cx, proto);
04015 
04016       NS_IF_RELEASE(doc);
04017 
04018       ::JS_SetPrivate(cx, proto, nsnull);
04019 
04020       // Pull the global scope polluter out of the prototype chain so
04021       // that it can be freed.
04022       ::JS_SetPrototype(cx, obj, ::JS_GetPrototype(cx, proto));
04023 
04024       break;
04025     }
04026 
04027     obj = proto;
04028   }
04029 }
04030 
04031 // static
04032 nsresult
04033 nsWindowSH::InstallGlobalScopePolluter(JSContext *cx, JSObject *obj,
04034                                        nsIHTMLDocument *doc)
04035 {
04036   // If global scope pollution is disabled, or if our document is not
04037   // a HTML document, do nothing
04038   if (sDisableGlobalScopePollutionSupport || !doc) {
04039     return NS_OK;
04040   }
04041 
04042   JSObject *gsp = ::JS_NewObject(cx, &sGlobalScopePolluterClass, nsnull, obj);
04043   if (!gsp) {
04044     return NS_ERROR_OUT_OF_MEMORY;
04045   }
04046 
04047   JSObject *o = obj, *proto;
04048 
04049   // Find the place in the prototype chain where we want this global
04050   // scope polluter (right before Object.prototype).
04051 
04052   while ((proto = ::JS_GetPrototype(cx, o))) {
04053     if (JS_GET_CLASS(cx, proto) == sObjectClass) {
04054       // Set the global scope polluters prototype to Object.prototype
04055       if (!::JS_SetPrototype(cx, gsp, proto)) {
04056         return NS_ERROR_UNEXPECTED;
04057       }
04058 
04059       break;
04060     }
04061 
04062     o = proto;
04063   }
04064 
04065   // And then set the prototype of the object whose prototype was
04066   // Object.prototype to be the global scope polluter.
04067   if (!::JS_SetPrototype(cx, o, gsp)) {
04068     return NS_ERROR_UNEXPECTED;
04069   }
04070 
04071   if (!::JS_SetPrivate(cx, gsp, doc)) {
04072     return NS_ERROR_UNEXPECTED;
04073   }
04074 
04075   // The global scope polluter will release doc on destruction (or
04076   // invalidation).
04077   NS_ADDREF(doc);
04078 
04079   return NS_OK;
04080 }
04081 
04082 static
04083 already_AddRefed<nsIDOMWindow>
04084 GetChildFrame(nsGlobalWindow *win, jsval id)
04085 {
04086   nsCOMPtr<nsIDOMWindowCollection> frames;
04087   win->GetFrames(getter_AddRefs(frames));
04088 
04089   nsIDOMWindow *frame = nsnull;
04090 
04091   if (frames) {
04092     frames->Item(JSVAL_TO_INT(id), &frame);
04093   }
04094 
04095   return frame;
04096 }
04097 
04098 NS_IMETHODIMP
04099 nsWindowSH::GetProperty(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
04100                         JSObject *obj, jsval id, jsval *vp, PRBool *_retval)
04101 {
04102   nsGlobalWindow *win = nsGlobalWindow::FromWrapper(wrapper);
04103 
04104 #ifdef DEBUG_SH_FORWARDING
04105   {
04106     nsDependentJSString str(::JS_ValueToString(cx, id));
04107 
04108     if (win->IsInnerWindow()) {
04109 #ifdef DEBUG_PRINT_INNER
04110       printf("Property '%s' get on inner window %p\n",
04111              NS_ConvertUTF16toUTF8(str).get(), (void *)win);
04112 #endif
04113     } else {
04114       printf("Property '%s' get on outer window %p\n",
04115              NS_ConvertUTF16toUTF8(str).get(), (void *)win);
04116     }
04117   }
04118 #endif
04119 
04120   if (win->IsOuterWindow() && !ObjectIsNativeWrapper(cx, obj)) {
04121     // XXXjst: Do security checks here when we remove the security
04122     // checks on the inner window.
04123 
04124     nsGlobalWindow *innerWin = win->GetCurrentInnerWindowInternal();
04125 
04126     JSObject *innerObj;
04127     if (innerWin && (innerObj = innerWin->GetGlobalJSObject())) {
04128 #ifdef DEBUG_SH_FORWARDING
04129       printf(" --- Forwarding get to inner window %p\n", (void *)innerWin);
04130 #endif
04131 
04132       // Forward the get to the inner object
04133       if (JSVAL_IS_STRING(id)) {
04134         JSString *str = JSVAL_TO_STRING(id);
04135 
04136         *_retval = ::JS_GetUCProperty(cx, innerObj, ::JS_GetStringChars(str),
04137                                       ::JS_GetStringLength(str), vp);
04138       } else if (JSVAL_IS_INT(id)) {
04139         *_retval = ::JS_GetElement(cx, innerObj, JSVAL_TO_INT(id), vp);
04140       } else {
04141         NS_ERROR("Write me!");
04142 
04143         return NS_ERROR_NOT_IMPLEMENTED;
04144       }
04145 
04146       return NS_OK;
04147     }
04148   }
04149 
04150   // The order in which things are done in this method are a bit
04151   // whacky, that's because this method is *extremely* performace
04152   // critical. Don't touch this unless you know what you're doing.
04153 
04154   if (JSVAL_IS_INT(id)) {
04155     // If we're accessing a numeric property we'll treat that as if
04156     // window.frames[n] is accessed (since window.frames === window),
04157     // if window.frames[n] is a child frame, wrap the frame and return
04158     // it without doing a security check.
04159 
04160     nsCOMPtr<nsIDOMWindow> frame = GetChildFrame(win, id);
04161     nsresult rv = NS_OK;
04162 
04163     if (frame) {
04164       // A numeric property accessed and the numeric property is a
04165       // child frame, wrap the child frame without doing a security
04166       // check and return.
04167 
04168       nsGlobalWindow *frameWin = (nsGlobalWindow *)frame.get();
04169 
04170       nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
04171       rv = WrapNative(cx, frameWin->GetGlobalJSObject(), frame,
04172                       NS_GET_IID(nsIDOMWindow), vp,
04173                       getter_AddRefs(holder));
04174     }
04175 
04176     return NS_FAILED(rv) ? rv : NS_SUCCESS_I_DID_SOMETHING;
04177   }
04178 
04179   if (needsSecurityCheck(cx, wrapper)) {
04180     // Even if we'd need to do a security check for access to "normal"
04181     // properties on a window, we won't do a security check if we're
04182     // accessing a child frame.
04183 
04184     if (JSVAL_IS_STRING(id) && !JSVAL_IS_PRIMITIVE(*vp) &&
04185         ::JS_TypeOfValue(cx, *vp) != JSTYPE_FUNCTION) {
04186       // A named property accessed which could have been resolved to a
04187       // child frame in nsWindowSH::NewResolve() (*vp will tell us if
04188       // that's the case). If *vp is a window object (i.e. a child
04189       // frame), return without doing a security check.
04190 
04191       nsCOMPtr<nsIXPConnectWrappedNative> vpwrapper;
04192       sXPConnect->GetWrappedNativeOfJSObject(cx, JSVAL_TO_OBJECT(*vp),
04193                                              getter_AddRefs(vpwrapper));
04194 
04195       if (vpwrapper) {
04196         nsCOMPtr<nsIDOMWindow> window(do_QueryWrappedNative(vpwrapper));
04197 
04198         if (window) {
04199           // Yup, *vp is a window object, return early (*vp is already
04200           // the window, so no need to wrap it again).
04201 
04202           return NS_SUCCESS_I_DID_SOMETHING;
04203         }
04204       }
04205     }
04206 
04207     nsresult rv =
04208       doCheckPropertyAccess(cx, obj, id, wrapper,
04209                             nsIXPCSecurityManager::ACCESS_GET_PROPERTY,
04210                             PR_TRUE);
04211 
04212     if (NS_FAILED(rv)) {
04213       // Security check failed. The security manager set a JS
04214       // exception, we must make sure that exception is propagated.
04215 
04216       *_retval = PR_FALSE;
04217 
04218       *vp = JSVAL_NULL;
04219     }
04220   }
04221 
04222   return NS_OK;
04223 }
04224 
04225 NS_IMETHODIMP
04226 nsWindowSH::SetProperty(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
04227                         JSObject *obj, jsval id, jsval *vp, PRBool *_retval)
04228 {
04229   nsGlobalWindow *win = nsGlobalWindow::FromWrapper(wrapper);
04230 
04231 #ifdef DEBUG_SH_FORWARDING
04232   {
04233     nsDependentJSString str(::JS_ValueToString(cx, id));
04234 
04235     if (win->IsInnerWindow()) {
04236 #ifdef DEBUG_PRINT_INNER
04237       printf("Property '%s' set on inner window %p\n",
04238              NS_ConvertUTF16toUTF8(str).get(), (void *)win);
04239 #endif
04240     } else {
04241       printf("Property '%s' set on outer window %p\n",
04242              NS_ConvertUTF16toUTF8(str).get(), (void *)win);
04243     }
04244   }
04245 #endif
04246 
04247   if (win->IsOuterWindow() && !ObjectIsNativeWrapper(cx, obj)) {
04248     // XXXjst: Do security checks here when we remove the security
04249     // checks on the inner window.
04250 
04251     nsGlobalWindow *innerWin = win->GetCurrentInnerWindowInternal();
04252 
04253     JSObject *innerObj;
04254     if (innerWin && (innerObj = innerWin->GetGlobalJSObject())) {
04255 #ifdef DEBUG_SH_FORWARDING
04256       printf(" --- Forwarding set to inner window %p\n", (void *)innerWin);
04257 #endif
04258 
04259       // Forward the set to the inner object
04260       if (JSVAL_IS_STRING(id)) {
04261         JSString *str = JSVAL_TO_STRING(id);
04262 
04263         *_retval = ::JS_SetUCProperty(cx, innerObj, ::JS_GetStringChars(str),
04264                                       ::JS_GetStringLength(str), vp);
04265       } else if (JSVAL_IS_INT(id)) {
04266         *_retval = ::JS_SetElement(cx, innerObj, JSVAL_TO_INT(id), vp);
04267       } else {
04268         NS_ERROR("Write me!");
04269 
04270         return NS_ERROR_NOT_IMPLEMENTED;
04271       }
04272 
04273       return NS_OK;
04274     }
04275   }
04276 
04277   if (needsSecurityCheck(cx, wrapper)) {
04278     nsresult rv =
04279       doCheckPropertyAccess(cx, obj, id, wrapper,
04280                             nsIXPCSecurityManager::ACCESS_SET_PROPERTY,
04281                             PR_TRUE);
04282 
04283     if (NS_FAILED(rv)) {
04284       // Security check failed. The security manager set a JS
04285       // exception, we must make sure that exception is propagated.
04286 
04287       *_retval = PR_FALSE;
04288 
04289       return NS_OK;
04290     }
04291   }
04292 
04293   if (id == sLocation_id) {
04294     JSString *val = ::JS_ValueToString(cx, *vp);
04295     NS_ENSURE_TRUE(val, NS_ERROR_UNEXPECTED);
04296 
04297     nsCOMPtr<nsIDOMWindowInternal> window(do_QueryWrappedNative(wrapper));
04298     NS_ENSURE_TRUE(window, NS_ERROR_UNEXPECTED);
04299 
04300     nsCOMPtr<nsIDOMLocation> location;
04301     nsresult rv = window->GetLocation(getter_AddRefs(location));
04302     NS_ENSURE_SUCCESS(rv, rv);
04303 
04304     nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
04305     rv = WrapNative(cx, obj, location, NS_GET_IID(nsIDOMLocation), vp,
04306                     getter_AddRefs(holder));
04307     NS_ENSURE_SUCCESS(rv, rv);
04308 
04309     rv = location->SetHref(nsDependentJSString(val));
04310 
04311     return NS_FAILED(rv) ? rv : NS_SUCCESS_I_DID_SOMETHING;
04312   }
04313 
04314   return nsEventReceiverSH::SetProperty(wrapper, cx, obj, id, vp, _retval);
04315 }
04316 
04317 NS_IMETHODIMP
04318 nsWindowSH::AddProperty(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
04319                         JSObject *obj, jsval id, jsval *vp,
04320                         PRBool *_retval)
04321 {
04322   nsGlobalWindow *win = nsGlobalWindow::FromWrapper(wrapper);
04323 
04324 #ifdef DEBUG_SH_FORWARDING
04325   {
04326     nsDependentJSString str(::JS_ValueToString(cx, id));
04327 
04328     if (win->IsInnerWindow()) {
04329 #ifdef DEBUG_PRINT_INNER
04330       printf("Property '%s' add on inner window %p\n",
04331              NS_ConvertUTF16toUTF8(str).get(), (void *)win);
04332 #endif
04333     } else {
04334       printf("Property '%s' add on outer window %p\n",
04335              NS_ConvertUTF16toUTF8(str).get(), (void *)win);
04336     }
04337   }
04338 #endif
04339 
04340   if (win->IsOuterWindow() && !ObjectIsNativeWrapper(cx, obj) ) {
04341     // XXXjst: Do security checks here when we remove the security
04342     // checks on the inner window.
04343 
04344     nsGlobalWindow *innerWin = win->GetCurrentInnerWindowInternal();
04345 
04346     JSObject *innerObj;
04347     if (innerWin && (innerObj = innerWin->GetGlobalJSObject())) {
04348 #ifdef DEBUG_SH_FORWARDING
04349       printf(" --- Forwarding add to inner window %p\n", (void *)innerWin);
04350 #endif
04351 
04352       // Forward the add to the inner object
04353       jsid interned_id;
04354       *_retval = (::JS_ValueToId(cx, id, &interned_id) &&
04355                   OBJ_DEFINE_PROPERTY(cx, innerObj, interned_id, *vp, nsnull,
04356                                       nsnull, JSPROP_ENUMERATE, nsnull));
04357 
04358       return NS_OK;
04359     }
04360   }
04361 
04362   // If we're in a state where we're not supposed to do a security
04363   // check, return early.
04364   if (!sDoSecurityCheckInAddProperty) {
04365     return NS_OK;
04366   }
04367 
04368   if (id == sLocation_id) {
04369     // Don't allow adding a window.location setter or getter, allowing
04370     // that could lead to security bugs (see bug 143369).
04371 
04372     return NS_ERROR_DOM_SECURITY_ERR;
04373   }
04374 
04375   nsresult rv =
04376     doCheckPropertyAccess(cx, obj, id, wrapper,
04377                           nsIXPCSecurityManager::ACCESS_SET_PROPERTY,
04378                           PR_TRUE);
04379 
04380   if (NS_FAILED(rv)) {
04381     // Security check failed. The security manager set a JS
04382     // exception, we must make sure that exception is propagated.
04383 
04384     *_retval = PR_FALSE;
04385 
04386     return NS_OK;
04387   }
04388 
04389   return nsEventReceiverSH::AddProperty(wrapper, cx, obj, id, vp, _retval);
04390 }
04391 
04392 NS_IMETHODIMP
04393 nsWindowSH::DelProperty(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
04394                         JSObject *obj, jsval id, jsval *vp,
04395                         PRBool *_retval)
04396 {
04397   nsGlobalWindow *win = nsGlobalWindow::FromWrapper(wrapper);
04398 
04399 #ifdef DEBUG_SH_FORWARDING
04400   {
04401     nsDependentJSString str(::JS_ValueToString(cx, id));
04402 
04403     if (win->IsInnerWindow()) {
04404 #ifdef DEBUG_PRINT_INNER
04405       printf("Property '%s' del on inner window %p\n",
04406              NS_ConvertUTF16toUTF8(str).get(), (void *)win);
04407 #endif
04408     } else {
04409       printf("Property '%s' del on outer window %p\n",
04410              NS_ConvertUTF16toUTF8(str).get(), (void *)win);
04411     }
04412   }
04413 #endif
04414 
04415   if (win->IsOuterWindow() && !ObjectIsNativeWrapper(cx, obj)) {
04416     // XXXjst: Do security checks here when we remove the security
04417     // checks on the inner window.
04418 
04419     nsGlobalWindow *innerWin = win->GetCurrentInnerWindowInternal();
04420 
04421     JSObject *innerObj;
04422     if (innerWin && (innerObj = innerWin->GetGlobalJSObject())) {
04423 #ifdef DEBUG_SH_FORWARDING
04424       printf(" --- Forwarding del to inner window %p\n", (void *)innerWin);
04425 #endif
04426 
04427       // Forward the del to the inner object
04428       jsid interned_id;
04429       *_retval = (::JS_ValueToId(cx, id, &interned_id) &&
04430                   OBJ_DELETE_PROPERTY(cx, innerObj, interned_id, vp));
04431 
04432       return NS_OK;
04433     }
04434   }
04435 
04436   if (id == sLocation_id) {
04437     // Don't allow deleting window.location, allowing that could lead
04438     // to security bugs (see bug 143369).
04439 
04440     return NS_ERROR_DOM_SECURITY_ERR;
04441   }
04442 
04443   nsresult rv =
04444     doCheckPropertyAccess(cx, obj, id, wrapper,
04445                           nsIXPCSecurityManager::ACCESS_SET_PROPERTY,
04446                           PR_TRUE);
04447 
04448   if (NS_FAILED(rv)) {
04449     // Security check failed. The security manager set a JS
04450     // exception, we must make sure that exception is propagated.
04451 
04452     *_retval = PR_FALSE;
04453   }
04454 
04455   return NS_OK;
04456 }
04457 
04458 static const char*
04459 FindConstructorContractID(PRInt32 aDOMClassInfoID)
04460 {
04461   PRUint32 i;
04462   for (i = 0; i < NS_ARRAY_LENGTH(kConstructorMap); ++i) {
04463     if (kConstructorMap[i].mDOMClassInfoID == aDOMClassInfoID) {
04464       return kConstructorMap[i].mContractID;
04465     }
04466   }
04467   return nsnull;
04468 }
04469 
04470 static nsresult
04471 BaseStubConstructor(nsIWeakReference* aWeakOwner,
04472                     const nsGlobalNameStruct *name_struct, JSContext *cx,
04473                     JSObject *obj, uintN argc, jsval *argv, jsval *rval)
04474 {
04475   nsresult rv;
04476   nsCOMPtr<nsISupports> native;
04477   if (name_struct->mType == nsGlobalNameStruct::eTypeClassConstructor) {
04478     const char *contractid =
04479       FindConstructorContractID(name_struct->mDOMClassInfoID);
04480     native = do_CreateInstance(contractid, &rv);
04481   } else if (name_struct->mType == nsGlobalNameStruct::eTypeExternalConstructor) {
04482     native = do_CreateInstance(name_struct->mCID, &rv);
04483   } else if (name_struct->mType == nsGlobalNameStruct::eTypeExternalConstructorAlias) {
04484     native = do_CreateInstance(name_struct->mAlias->mCID, &rv);
04485   } else {
04486     native = do_CreateInstance(*name_struct->mData->mConstructorCID, &rv);
04487   }
04488   if (NS_FAILED(rv)) {
04489     NS_ERROR("Failed to create the object");
04490     return rv;
04491   }
04492 
04493   nsCOMPtr<nsIJSNativeInitializer_MOZILLA_1_8_BRANCH> initializer18 =
04494     do_QueryInterface(native);
04495   if (initializer18) {
04496     nsCOMPtr<nsPIDOMWindow> owner = do_QueryReferent(aWeakOwner);
04497     NS_ENSURE_STATE(owner && owner->GetOuterWindow() &&
04498                     owner->GetOuterWindow()->GetCurrentInnerWindow() == owner);
04499     rv = initializer18->Initialize(owner, cx, obj, argc, argv);
04500     if (NS_FAILED(rv)) {
04501       return NS_ERROR_NOT_INITIALIZED;
04502     }
04503   } else {
04504     nsCOMPtr<nsIJSNativeInitializer> initializer(do_QueryInterface(native));
04505     if (initializer) {
04506       rv = initializer->Initialize(cx, obj, argc, argv);
04507       if (NS_FAILED(rv)) {
04508         return NS_ERROR_NOT_INITIALIZED;
04509       }
04510     }
04511   }
04512 
04513   nsCOMPtr<nsIScriptObjectOwner> owner(do_QueryInterface(native));
04514   if (owner) {
04515     nsIScriptContext *context = nsJSUtils::GetStaticScriptContext(cx, obj);
04516     if (!context) {
04517       return NS_ERROR_UNEXPECTED;
04518     }
04519 
04520     JSObject* new_obj;
04521     rv = owner->GetScriptObject(context, (void**)&new_obj);
04522 
04523     if (NS_SUCCEEDED(rv)) {
04524       *rval = OBJECT_TO_JSVAL(new_obj);
04525     }
04526 
04527     return rv;
04528   }
04529 
04530   nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
04531   rv = nsDOMGenericSH::WrapNative(cx, obj, native, NS_GET_IID(nsISupports),
04532                                   rval, getter_AddRefs(holder));
04533 
04534   return rv;
04535 }
04536 
04537 static nsresult
04538 DefineInterfaceConstants(JSContext *cx, JSObject *obj, const nsIID *aIID)
04539 {
04540   nsCOMPtr<nsIInterfaceInfoManager> iim =
04541     dont_AddRef(XPTI_GetInterfaceInfoManager());
04542   NS_ENSURE_TRUE(iim, NS_ERROR_UNEXPECTED);
04543 
04544   nsCOMPtr<nsIInterfaceInfo> if_info;
04545 
04546   nsresult rv = iim->GetInfoForIID(aIID, getter_AddRefs(if_info));
04547   NS_ENSURE_TRUE(NS_SUCCEEDED(rv) && if_info, rv);
04548 
04549   PRUint16 constant_count;
04550 
04551   if_info->GetConstantCount(&constant_count);
04552 
04553   if (!constant_count) {
04554     return NS_OK;
04555   }
04556 
04557   nsCOMPtr<nsIInterfaceInfo> parent_if_info;
04558 
04559   rv = if_info->GetParent(getter_AddRefs(parent_if_info));
04560   NS_ENSURE_TRUE(NS_SUCCEEDED(rv) && parent_if_info, rv);
04561 
04562   PRUint16 parent_constant_count, i;
04563   parent_if_info->GetConstantCount(&parent_constant_count);
04564 
04565   for (i = parent_constant_count; i < constant_count; i++) {
04566     const nsXPTConstant *c = nsnull;
04567 
04568     rv = if_info->GetConstant(i, &c);
04569     NS_ENSURE_TRUE(NS_SUCCEEDED(rv) && c, rv);
04570 
04571     PRUint16 type = c->GetType().TagPart();
04572 
04573     jsval v;
04574     switch (type) {
04575       case nsXPTType::T_I8:
04576       case nsXPTType::T_U8:
04577       {
04578         v = INT_TO_JSVAL(c->GetValue()->val.u8);
04579         break;
04580       }
04581       case nsXPTType::T_I16:
04582       case nsXPTType::T_U16:
04583       {
04584         v = INT_TO_JSVAL(c->GetValue()->val.u16);
04585         break;
04586       }
04587       case nsXPTType::T_I32:
04588       case nsXPTType::T_U32:
04589       {
04590         v = INT_TO_JSVAL(c->GetValue()->val.u32);
04591         break;
04592       }
04593       default:
04594       {
04595 #ifdef NS_DEBUG
04596         NS_ERROR("Non-numeric constant found in interface.");
04597 #endif
04598         continue;
04599       }
04600     }
04601 
04602     if (!::JS_DefineProperty(cx, obj, c->GetName(), v, nsnull, nsnull,
04603                              JSPROP_ENUMERATE)) {
04604       return NS_ERROR_UNEXPECTED;
04605     }
04606   }
04607 
04608   return NS_OK;
04609 }
04610 
04611 class nsDOMConstructor : public nsIDOMConstructor
04612 {
04613 protected:
04614   nsDOMConstructor(const PRUnichar *aName,
04615                    nsPIDOMWindow* aOwner)
04616     : mClassName(aName),
04617       mWeakOwner(do_GetWeakReference(aOwner))
04618 
04619   {
04620   }
04621 
04622 public:
04623 
04624   static nsresult Create(const PRUnichar* aName,
04625                          nsPIDOMWindow* aOwner,
04626                          nsDOMConstructor** aResult);
04627 
04628   virtual ~nsDOMConstructor();
04629 
04630   NS_DECL_ISUPPORTS
04631   NS_DECL_NSIDOMCONSTRUCTOR
04632 
04633   nsresult Construct(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
04634                      JSObject *obj, PRUint32 argc, jsval *argv,
04635                      jsval *vp, PRBool *_retval);
04636 
04637   nsresult HasInstance(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
04638                        JSObject *obj, jsval val, PRBool *bp,
04639                        PRBool *_retval);
04640 
04641   nsresult Install(JSContext *cx, JSObject *target, jsval thisAsVal)
04642   {
04643     PRBool doSecurityCheckInAddProperty =
04644       nsDOMClassInfo::sDoSecurityCheckInAddProperty;
04645     nsDOMClassInfo::sDoSecurityCheckInAddProperty = PR_FALSE;
04646 
04647     JSBool ok =
04648       ::JS_DefineUCProperty(cx, target,
04649                             NS_REINTERPRET_CAST(const jschar *, mClassName),
04650                             nsCRT::strlen(mClassName), thisAsVal, nsnull,
04651                             nsnull, 0);
04652 
04653     nsDOMClassInfo::sDoSecurityCheckInAddProperty =
04654       doSecurityCheckInAddProperty;
04655     return ok ? NS_OK : NS_ERROR_UNEXPECTED;
04656   }
04657 
04658 private:
04659   const PRUnichar *mClassName;
04660   nsWeakPtr        mWeakOwner;
04661 };
04662 
04663 //static
04664 nsresult
04665 nsDOMConstructor::Create(const PRUnichar* aName,
04666                          nsPIDOMWindow* aOwner,
04667                          nsDOMConstructor** aResult)
04668 {
04669   *aResult = nsnull;
04670   if (!aOwner->IsOuterWindow()) {
04671     *aResult = new nsDOMConstructor(aName, aOwner);
04672   } else if (!nsContentUtils::CanCallerAccess(aOwner)) {
04673     return NS_ERROR_DOM_SECURITY_ERR;
04674   } else {
04675     *aResult =
04676       new nsDOMConstructor(aName, aOwner->GetCurrentInnerWindow());
04677   }
04678   NS_ENSURE_TRUE(*aResult, NS_ERROR_OUT_OF_MEMORY);
04679   NS_ADDREF(*aResult);
04680   return NS_OK;
04681 }
04682 
04683 NS_IMPL_ADDREF(nsDOMConstructor)
04684 NS_IMPL_RELEASE(nsDOMConstructor)
04685 NS_INTERFACE_MAP_BEGIN(nsDOMConstructor)
04686   NS_INTERFACE_MAP_ENTRY(nsIDOMConstructor)
04687   NS_INTERFACE_MAP_ENTRY(nsISupports)
04688   NS_DOM_INTERFACE_MAP_ENTRY_CLASSINFO(Constructor)
04689 NS_INTERFACE_MAP_END
04690 
04691 nsDOMConstructor::~nsDOMConstructor()
04692 {
04693 }
04694 
04695 nsresult
04696 nsDOMConstructor::Construct(nsIXPConnectWrappedNative *wrapper, JSContext * cx,
04697                             JSObject * obj, PRUint32 argc, jsval * argv,
04698                             jsval * vp, PRBool *_retval)
04699 {
04700   JSObject* class_obj = JSVAL_TO_OBJECT(argv[-2]);
04701   if (!class_obj) {
04702     NS_ERROR("nsDOMConstructor::Construct couldn't get constructor object.");
04703     return NS_ERROR_UNEXPECTED;
04704   }
04705 
04706   extern nsScriptNameSpaceManager *gNameSpaceManager;
04707   if (!mClassName || !gNameSpaceManager) {
04708     NS_ERROR("nsDOMConstructor::Construct can't get name or namespace manager");
04709     return NS_ERROR_UNEXPECTED;
04710   }
04711 
04712   const nsGlobalNameStruct *name_struct = nsnull;
04713   gNameSpaceManager->LookupName(nsDependentString(mClassName), &name_struct);
04714   if (!name_struct) {
04715     NS_ERROR("Name isn't in hash.");
04716     return NS_ERROR_UNEXPECTED;
04717   }
04718 
04719   if ((name_struct->mType != nsGlobalNameStruct::eTypeClassConstructor ||
04720        !FindConstructorContractID(name_struct->mDOMClassInfoID)) &&
04721       (name_struct->mType != nsGlobalNameStruct::eTypeExternalClassInfo ||
04722        !name_struct->mData->mConstructorCID) &&
04723       name_struct->mType != nsGlobalNameStruct::eTypeExternalConstructor &&
04724       name_struct->mType != nsGlobalNameStruct::eTypeExternalConstructorAlias) {
04725     // ignore return value, we return JS_FALSE anyway
04726     NS_ERROR("object instantiated without constructor");
04727     return NS_ERROR_DOM_NOT_SUPPORTED_ERR;
04728   }
04729 
04730   return BaseStubConstructor(mWeakOwner, name_struct, cx, obj, argc, argv, vp);
04731 }
04732 
04733 nsresult
04734 nsDOMConstructor::HasInstance(nsIXPConnectWrappedNative *wrapper,
04735                               JSContext * cx, JSObject * obj,
04736                               jsval v, PRBool *bp, PRBool *_retval)
04737 
04738 {
04739   // No need to look these up in the hash.
04740   if (JSVAL_IS_PRIMITIVE(v)) {
04741     return NS_OK;
04742   }
04743 
04744   JSObject *dom_obj = JSVAL_TO_OBJECT(v);
04745   NS_ASSERTION(dom_obj, "nsDOMConstructor::HasInstance couldn't get object");
04746 
04747   // This might not be the right object, if XPCNativeWrapping
04748   // happened.  Get the wrapped native for this object, then get its
04749   // JS object.
04750   nsCOMPtr<nsIXPConnectWrappedNative> wrapped_native;
04751   nsContentUtils::XPConnect()->
04752     GetWrappedNativeOfJSObject(cx, dom_obj, getter_AddRefs(wrapped_native));
04753   if (wrapped_native) {
04754     wrapped_native->GetJSObject(&dom_obj);
04755   }
04756 
04757   JSClass *dom_class = JS_GET_CLASS(cx, dom_obj);
04758   if (!dom_class) {
04759     NS_ERROR("nsDOMConstructor::HasInstance can't get class.");
04760     return NS_ERROR_UNEXPECTED;
04761   }
04762 
04763   const nsGlobalNameStruct *name_struct = nsnull;
04764 
04765   extern nsScriptNameSpaceManager *gNameSpaceManager;
04766   if (!gNameSpaceManager) {
04767     NS_ERROR("nsDOMConstructor::HasInstance can't get namespace manager.");
04768     return NS_ERROR_UNEXPECTED;
04769   }
04770 
04771   gNameSpaceManager->LookupName(NS_ConvertASCIItoUCS2(dom_class->name),
04772                                 &name_struct);
04773   if (!name_struct) {
04774     // Name isn't in hash, not a DOM object.
04775     return NS_OK;
04776   }
04777 
04778   if (name_struct->mType != nsGlobalNameStruct::eTypeClassConstructor &&
04779       name_struct->mType != nsGlobalNameStruct::eTypeExternalClassInfo &&
04780       name_struct->mType != nsGlobalNameStruct::eTypeExternalConstructorAlias) {
04781     // Doesn't have DOM interfaces.
04782     return NS_OK;
04783   }
04784 
04785   if (!mClassName) {
04786     NS_ERROR("nsDOMConstructor::HasInstance can't get name.");
04787     return NS_ERROR_UNEXPECTED;
04788   }
04789 
04790   const nsGlobalNameStruct *class_name_struct = nsnull;
04791   gNameSpaceManager->LookupName(nsDependentString(mClassName),
04792                                 &class_name_struct);
04793   if (!class_name_struct) {
04794     NS_ERROR("Name isn't in hash.");
04795     return NS_ERROR_UNEXPECTED;
04796   }
04797 
04798   if (name_struct == class_name_struct) {
04799     *bp = JS_TRUE;
04800 
04801     return NS_OK;
04802   }
04803 
04804   const nsIID *class_iid;
04805   if (class_name_struct->mType == nsGlobalNameStruct::eTypeInterface ||
04806       class_name_struct->mType == nsGlobalNameStruct::eTypeClassProto) {
04807     class_iid = &class_name_struct->mIID;
04808   } else if (class_name_struct->mType == nsGlobalNameStruct::eTypeClassConstructor) {
04809     class_iid =
04810       sClassInfoData[class_name_struct->mDOMClassInfoID].mProtoChainInterface;
04811   } else if (class_name_struct->mType == nsGlobalNameStruct::eTypeExternalClassInfo) {
04812     class_iid = class_name_struct->mData->mProtoChainInterface;
04813   } else if (class_name_struct->mType == nsGlobalNameStruct::eTypeExternalConstructorAlias) {
04814     const nsGlobalNameStruct* alias_struct =
04815       gNameSpaceManager->GetConstructorProto(class_name_struct);
04816     if (!alias_struct) {
04817       NS_ERROR("Couldn't get constructor prototype.");
04818       return NS_ERROR_UNEXPECTED;
04819     }
04820 
04821     if (alias_struct->mType == nsGlobalNameStruct::eTypeClassConstructor) {
04822       class_iid =
04823         sClassInfoData[alias_struct->mDOMClassInfoID].mProtoChainInterface;
04824     } else if (alias_struct->mType == nsGlobalNameStruct::eTypeExternalClassInfo) {
04825       class_iid = alias_struct->mData->mProtoChainInterface;
04826     } else {
04827       NS_ERROR("Expected eTypeClassConstructor or eTypeExternalClassInfo.");
04828       return NS_ERROR_UNEXPECTED;
04829     }
04830   } else {
04831     *bp = JS_FALSE;
04832 
04833     return NS_OK;
04834   }
04835 
04836   if (name_struct->mType == nsGlobalNameStruct::eTypeExternalConstructorAlias) {
04837     name_struct = gNameSpaceManager->GetConstructorProto(name_struct);
04838     if (!name_struct) {
04839       NS_ERROR("Couldn't get constructor prototype.");
04840       return NS_ERROR_UNEXPECTED;
04841     }
04842   }
04843 
04844   NS_ASSERTION(name_struct->mType == nsGlobalNameStruct::eTypeClassConstructor ||
04845                name_struct->mType == nsGlobalNameStruct::eTypeExternalClassInfo,
04846                "The constructor was set up with a struct of the wrong type.");
04847 
04848   const nsDOMClassInfoData *ci_data = nsnull;
04849   if (name_struct->mType == nsGlobalNameStruct::eTypeClassConstructor &&
04850       name_struct->mDOMClassInfoID >= 0) {
04851     ci_data = &sClassInfoData[name_struct->mDOMClassInfoID];
04852   } else if (name_struct->mType == nsGlobalNameStruct::eTypeExternalClassInfo) {
04853     ci_data = name_struct->mData;
04854   }
04855 
04856   nsCOMPtr<nsIInterfaceInfoManager> iim =
04857     dont_AddRef(XPTI_GetInterfaceInfoManager());
04858   if (!iim) {
04859     NS_ERROR("nsDOMConstructor::HasInstance can't get interface info mgr.");
04860     return NS_ERROR_UNEXPECTED;
04861   }
04862 
04863   nsCOMPtr<nsIInterfaceInfo> if_info;
04864   PRUint32 count = 0;
04865   const nsIID* class_interface;
04866   while ((class_interface = ci_data->mInterfaces[count++])) {
04867     if (class_iid->Equals(*class_interface)) {
04868       *bp = JS_TRUE;
04869 
04870       return NS_OK;
04871     }
04872 
04873     iim->GetInfoForIID(class_interface, getter_AddRefs(if_info));
04874     if (!if_info) {
04875       NS_ERROR("nsDOMConstructor::HasInstance can't get interface info.");
04876       return NS_ERROR_UNEXPECTED;
04877     }
04878 
04879     if_info->HasAncestor(class_iid, bp);
04880 
04881     if (*bp) {
04882       return NS_OK;
04883     }
04884   }
04885 
04886   return NS_OK;
04887 }
04888 
04889 NS_IMETHODIMP
04890 nsDOMConstructor::ToString(nsAString &aResult)
04891 {
04892   aResult.Assign(PRUnichar('['));
04893   aResult.Append(mClassName);
04894   aResult.Append(PRUnichar(']'));
04895 
04896   return NS_OK;
04897 }
04898 
04899 /*
04900  * The problem of how to deal with garbage collection in a system where:
04901  *  1. the GC runtime contains lazily-created wrappers for other data
04902  *     structures not participating in the GC,
04903  *  2. where those data structures are reachable from each other in a
04904  *     way that is reflected through the wrappers, and
04905  *  3. where the wrappers can carry additional information that is not
04906  *     in the wrapped object
04907  * is a difficult one.  XPConnect is such a system.  It creates wrappers
04908  * around native objects that do not participate in the JS GC and which
04909  * are reachable from each other outside of the knowledge of the JS
04910  * engine (but through getters or functions that are accessible to JS
04911  * users) and it allows these wrappers to be decorated with JS
04912  * properties.  It is worth noting one very important use case for our
04913  * toolkit:  XBL, which uses JS properties on the bound element for
04914  * storing fields.
04915  *
04916  * For DOM nodes, compatibility with behavior in other browsers requires
04917  * that we preserve JS properties on wrappers across garbage collection.
04918  * To do this in a way that the garbage collector is still effective, we
04919  * have to incorporate knowledge of reachability in the underlying
04920  * (wrapped) data structures into the garbage collector's mark phase.
04921  *
04922  * See https://bugzilla.mozilla.org/show_bug.cgi?id=283129 for more details.
04923  */
04924 
04925 #if defined(DEBUG_dbaron)
04926 #define DEBUG_PRESERVE_WRAPPERS
04927 #endif
04928 
04929 struct RootWhenExternallyReferencedEntry : public PLDHashEntryHdr {
04930   // must be first to line up with PLDHashEntryStub
04931   nsIDOMGCParticipant *participant;
04932   PRUint32 refcnt;
04933 };
04934 
04935 struct PreservedWrapperEntry : public PLDHashEntryHdr {
04936   void *key; // must be first to line up with PLDHashEntryStub
04937   nsIXPConnectJSObjectHolder* (*keyToWrapperFunc)(void* aKey);
04938   nsIDOMGCParticipant *participant;
04939   PRBool rootWhenExternallyReferenced;
04940 
04941   // See |WrapperSCCEntry::first|.  Valid only during mark phase of GC.
04942   PreservedWrapperEntry *next;
04943 };
04944 
04945 PR_STATIC_CALLBACK(void)
04946 PreservedWrapperClearEntry(PLDHashTable *table, PLDHashEntryHdr *hdr)
04947 {
04948   PreservedWrapperEntry *entry = NS_STATIC_CAST(PreservedWrapperEntry*, hdr);
04949 
04950   if (entry->rootWhenExternallyReferenced) {
04951     NS_ASSERTION(sRootWhenExternallyReferencedTable.ops,
04952                  "must have been added to rwer table");
04953     RootWhenExternallyReferencedEntry *rwerEntry =
04954       NS_STATIC_CAST(RootWhenExternallyReferencedEntry*,
04955         PL_DHashTableOperate(&sRootWhenExternallyReferencedTable,
04956                              entry->participant, PL_DHASH_LOOKUP));
04957     NS_ASSERTION(PL_DHASH_ENTRY_IS_BUSY(rwerEntry),
04958                  "boolean vs. table mismatch");
04959     if (PL_DHASH_ENTRY_IS_BUSY(rwerEntry) && --rwerEntry->refcnt == 0) {
04960       PL_DHashTableRawRemove(&sRootWhenExternallyReferencedTable, rwerEntry);
04961       if (sRootWhenExternallyReferencedTable.entryCount == 0) {
04962         PL_DHashTableFinish(&sRootWhenExternallyReferencedTable);
04963         sRootWhenExternallyReferencedTable.ops = nsnull;
04964       }
04965     }
04966   }
04967 
04968   memset(hdr, 0, table->entrySize);
04969 }
04970 
04971 static const PLDHashTableOps sPreservedWrapperTableOps = {
04972   PL_DHashAllocTable,
04973   PL_DHashFreeTable,
04974   PL_DHashGetKeyStub,
04975   PL_DHashVoidPtrKeyStub,
04976   PL_DHashMatchEntryStub,
04977   PL_DHashMoveEntryStub,
04978   PreservedWrapperClearEntry,
04979   PL_DHashFinalizeStub,
04980   nsnull
04981 };
04982 
04995 static PLDHashTable sWrapperSCCTable;
04996 
04997 // If we run out of memory constructing sWrapperSCCTable, its |ops|
04998 // member holds this value for the remainder of that GC cycle.
04999 #define WRAPPER_SCC_OPS_OOM_MARKER ((PLDHashTableOps*)1)
05000 
05001 struct WrapperSCCEntry : public PLDHashEntryHdr {
05002   // This could probably be a weak pointer (which would avoid the
05003   // need for hash table ops), but it seems safer this way.
05004   nsCOMPtr<nsIDOMGCParticipant> key; // must be first to line up with PLDHashEntryStub
05005 
05006   // Linked list of preserved wrappers in the strongly connected
05007   // component, to be traversed using |PreservedWrapperEntry::next|.
05008   PreservedWrapperEntry *first;
05009 
05010   PRBool marked;
05011 
05012   WrapperSCCEntry(nsIDOMGCParticipant *aKey)
05013     : key(aKey), first(nsnull), marked(PR_FALSE) {}
05014 };
05015 
05016 PR_STATIC_CALLBACK(void)
05017 WrapperSCCsClearEntry(PLDHashTable *table, PLDHashEntryHdr *hdr)
05018 {
05019   WrapperSCCEntry *entry = NS_STATIC_CAST(WrapperSCCEntry*, hdr);
05020   entry->~WrapperSCCEntry();
05021   memset(hdr, 0, table->entrySize);
05022 }
05023 
05024 PR_STATIC_CALLBACK(PRBool)
05025 WrapperSCCsInitEntry(PLDHashTable *table, PLDHashEntryHdr *hdr,
05026                      const void *key)
05027 {
05028   WrapperSCCEntry *entry = NS_STATIC_CAST(WrapperSCCEntry*, hdr);
05029   new (entry) WrapperSCCEntry(NS_STATIC_CAST(nsIDOMGCParticipant*,
05030                                              NS_CONST_CAST(void*, key)));
05031   return PR_TRUE;
05032 }
05033 
05034 static const PLDHashTableOps sWrapperSCCTableOps = {
05035   PL_DHashAllocTable,
05036   PL_DHashFreeTable,
05037   PL_DHashGetKeyStub,
05038   PL_DHashVoidPtrKeyStub,
05039   PL_DHashMatchEntryStub,
05040   PL_DHashMoveEntryStub,
05041   WrapperSCCsClearEntry,
05042   PL_DHashFinalizeStub,
05043   WrapperSCCsInitEntry
05044 };
05045 
05046 
05047 // static
05048 nsresult
05049 nsDOMClassInfo::PreserveWrapper(void *aKey,
05050                                 nsIXPConnectJSObjectHolder* (*aKeyToWrapperFunc)(void* aKey),
05051                                 nsIDOMGCParticipant *aParticipant,
05052                                 PRBool aRootWhenExternallyReferenced)
05053 {
05054   NS_PRECONDITION(aKey, "unexpected null pointer");
05055   NS_PRECONDITION(aKeyToWrapperFunc, "unexpected null pointer");
05056   NS_PRECONDITION(aParticipant, "unexpected null pointer");
05057   NS_ASSERTION(!sWrapperSCCTable.ops,
05058                "cannot change preserved wrapper table during mark phase");
05059 
05060   if (!sPreservedWrapperTable.ops &&
05061       !PL_DHashTableInit(&sPreservedWrapperTable, &sPreservedWrapperTableOps,
05062                          nsnull, sizeof(PreservedWrapperEntry), 16)) {
05063     sPreservedWrapperTable.ops = nsnull;
05064     return NS_ERROR_OUT_OF_MEMORY;
05065   }
05066 
05067   PreservedWrapperEntry *entry = NS_STATIC_CAST(PreservedWrapperEntry*,
05068     PL_DHashTableOperate(&sPreservedWrapperTable, aKey, PL_DHASH_ADD));
05069   if (!entry)
05070     return NS_ERROR_OUT_OF_MEMORY;
05071   NS_ASSERTION(!entry->key ||
05072                (entry->key == aKey &&
05073                 entry->keyToWrapperFunc == aKeyToWrapperFunc &&
05074                 entry->participant == aParticipant),
05075                "preservation key already used");
05076 
05077   PRBool wasExternallyReferenced = entry->rootWhenExternallyReferenced;
05078   entry->key = aKey;
05079   entry->keyToWrapperFunc = aKeyToWrapperFunc;
05080   entry->participant = aParticipant;
05081   entry->rootWhenExternallyReferenced =
05082     aRootWhenExternallyReferenced || wasExternallyReferenced;
05083 
05084   if (aRootWhenExternallyReferenced && !wasExternallyReferenced) {
05085     if (!sRootWhenExternallyReferencedTable.ops &&
05086         !PL_DHashTableInit(&sRootWhenExternallyReferencedTable,
05087                            PL_DHashGetStubOps(), nsnull,
05088                            sizeof(RootWhenExternallyReferencedEntry), 16)) {
05089       PL_DHashTableRawRemove(&sPreservedWrapperTable, entry);
05090       return NS_ERROR_OUT_OF_MEMORY;
05091     }
05092 
05093     RootWhenExternallyReferencedEntry *rwerEntry =
05094       NS_STATIC_CAST(RootWhenExternallyReferencedEntry*,
05095         PL_DHashTableOperate(&sRootWhenExternallyReferencedTable,
05096                              aParticipant, PL_DHASH_ADD));
05097     if (!rwerEntry) {
05098       PL_DHashTableRawRemove(&sPreservedWrapperTable, entry);
05099       return NS_ERROR_OUT_OF_MEMORY;
05100     }
05101     NS_ASSERTION(rwerEntry->refcnt == 0 ||
05102                  rwerEntry->participant == aParticipant,
05103                  "entry mismatch");
05104     rwerEntry->participant = aParticipant;
05105     ++rwerEntry->refcnt;
05106   }
05107 
05108   return NS_OK;
05109 }
05110 
05111 static nsIXPConnectJSObjectHolder* IdentityKeyToWrapperFunc(void* aKey)
05112 {
05113   return NS_STATIC_CAST(nsIXPConnectJSObjectHolder*, aKey);
05114 }
05115 
05116 // static
05117 nsresult
05118 nsDOMClassInfo::PreserveNodeWrapper(nsIXPConnectWrappedNative *aWrapper,
05119                                     PRBool aRootWhenExternallyReferenced)
05120 {
05121   nsCOMPtr<nsIDOMGCParticipant> participant =
05122     do_QueryInterface(aWrapper->Native());
05123   if (!participant)
05124     // nsJSContext::PreserveWrapper needs us to null-check
05125     return NS_OK;
05126 
05127   return nsDOMClassInfo::PreserveWrapper(aWrapper, IdentityKeyToWrapperFunc,
05128                                          participant,
05129                                          aRootWhenExternallyReferenced);
05130 }
05131 
05132 // static
05133 void
05134 nsDOMClassInfo::ReleaseWrapper(void *aKey)
05135 {
05136   NS_PRECONDITION(aKey, "unexpected null pointer");
05137   NS_ASSERTION(!sWrapperSCCTable.ops,
05138                "cannot change preserved wrapper table during mark phase");
05139 
05140   if (sPreservedWrapperTable.ops) {
05141     PL_DHashTableOperate(&sPreservedWrapperTable, aKey, PL_DHASH_REMOVE);
05142     if (sPreservedWrapperTable.entryCount == 0) {
05143       PL_DHashTableFinish(&sPreservedWrapperTable);
05144       sPreservedWrapperTable.ops = nsnull;
05145     }
05146   }
05147 }
05148 
05149 struct MarkAllWrappersData {
05150   JSContext *cx;
05151   void *arg;
05152 };
05153 
05154 PR_STATIC_CALLBACK(PLDHashOperator)
05155 MarkAllWrappers(PLDHashTable *table, PLDHashEntryHdr *hdr,
05156                 PRUint32 number, void *arg)
05157 {
05158   MarkAllWrappersData *data = NS_STATIC_CAST(MarkAllWrappersData*, arg);
05159   PreservedWrapperEntry *entry = NS_STATIC_CAST(PreservedWrapperEntry*, hdr);
05160 
05161   nsIXPConnectJSObjectHolder *wrapper;
05162   JSObject *wrapper_obj;
05163   if ((wrapper = entry->keyToWrapperFunc(entry->key)) &&
05164       NS_SUCCEEDED(wrapper->GetJSObject(&wrapper_obj)))
05165     JS_MarkGCThing(data->cx, wrapper_obj, 
05166                    "nsDOMClassInfo::sPreservedWrapperTable_OOM", data->arg);
05167 
05168   return PL_DHASH_NEXT;
05169 }
05170 
05171 // static
05172 void
05173 nsDOMClassInfo::MarkReachablePreservedWrappers(nsIDOMGCParticipant *aParticipant,
05174                                                JSContext *cx, void *arg)
05175 {
05176   // Magic value indicating we've hit out-of-memory earlier in this GC.
05177   if (sWrapperSCCTable.ops == WRAPPER_SCC_OPS_OOM_MARKER)
05178     return;
05179 
05180   // The JS engine doesn't have a notification for the beginning of
05181   // the mark phase.  However, we can determine that the mark phase
05182   // has begun by detecting the first mark and lazily call
05183   // BeginGCMark.
05184   if (!sWrapperSCCTable.ops && !nsDOMClassInfo::BeginGCMark(cx)) {
05185     // We didn't have enough memory to create the temporary data
05186     // structures we needed.
05187     sWrapperSCCTable.ops = WRAPPER_SCC_OPS_OOM_MARKER;
05188 
05189     // Just mark all the preserved wrappers.  It won't help the GC free
05190     // up memory, but there's nothing better to do.
05191     if (sPreservedWrapperTable.ops) {
05192       MarkAllWrappersData data;
05193       data.cx = cx;
05194       data.arg = arg;
05195       PL_DHashTableEnumerate(&sPreservedWrapperTable, MarkAllWrappers, &data);
05196     }
05197     return;
05198   }
05199 
05200   nsIDOMGCParticipant *SCCIndex = aParticipant->GetSCCIndex();
05201   WrapperSCCEntry *entry = NS_STATIC_CAST(WrapperSCCEntry*,
05202     PL_DHashTableOperate(&sWrapperSCCTable, SCCIndex, PL_DHASH_LOOKUP));
05203   if (!PL_DHASH_ENTRY_IS_BUSY(entry) || entry->marked)
05204     return;
05205 
05206 #ifdef DEBUG_PRESERVE_WRAPPERS
05207   {
05208     nsAutoString nodeName;
05209     nsCOMPtr<nsIDOMNode> node = do_QueryInterface(entry->key);
05210     if (node)
05211       node->GetNodeName(nodeName);
05212     else
05213       nodeName.AssignLiteral("##not-node##");
05214     printf("  marking entries for SCC root %p \"%s\"\n",
05215            NS_STATIC_CAST(void*, entry->key.get()),
05216            NS_ConvertUTF16toUTF8(nodeName).get());
05217   }
05218 #endif
05219   entry->marked = PR_TRUE;
05220 
05221   // Do the reachable list first to encourage shorter call stacks
05222   // (perhaps slightly less recursion through JS marking).
05223   nsCOMArray<nsIDOMGCParticipant> reachable;
05224   SCCIndex->AppendReachableList(reachable);
05225   for (PRInt32 i = 0, i_end = reachable.Count(); i < i_end; ++i) {
05226     if (reachable[i])
05227       MarkReachablePreservedWrappers(reachable[i], cx, arg);
05228   }
05229 
05230   for (PreservedWrapperEntry *pwe = entry->first; pwe; pwe = pwe->next) {
05231     nsIXPConnectJSObjectHolder *wrapper;
05232     JSObject *wrapper_obj;
05233     if ((wrapper = pwe->keyToWrapperFunc(pwe->key)) &&
05234         NS_SUCCEEDED(wrapper->GetJSObject(&wrapper_obj)))
05235       ::JS_MarkGCThing(cx, wrapper_obj,
05236                        "nsDOMClassInfo::sPreservedWrapperTable", arg);
05237   }
05238 }
05239 
05240 struct ExternallyReferencedEntry : public PLDHashEntryHdr {
05241   nsIDOMGCParticipant* key; // must be first to line up with PLDHashEntryStub
05242 };
05243 
05244 /* static */ nsresult
05245 nsDOMClassInfo::SetExternallyReferenced(nsIDOMGCParticipant *aParticipant)
05246 {
05247   NS_PRECONDITION(aParticipant, "unexpected null pointer");
05248 
05249   if (!sExternallyReferencedTable.ops &&
05250       !PL_DHashTableInit(&sExternallyReferencedTable, PL_DHashGetStubOps(),
05251                          nsnull, sizeof(ExternallyReferencedEntry), 16)) {
05252     sExternallyReferencedTable.ops = nsnull;
05253     return NS_ERROR_OUT_OF_MEMORY;
05254   }
05255 
05256   ExternallyReferencedEntry *entry = NS_STATIC_CAST(ExternallyReferencedEntry*,
05257     PL_DHashTableOperate(&sExternallyReferencedTable, aParticipant, PL_DHASH_ADD));
05258   if (!entry)
05259     return NS_ERROR_OUT_OF_MEMORY;
05260 
05261   NS_ASSERTION(!entry->key, "participant already rooted");
05262   entry->key = aParticipant;
05263 
05264   return NS_OK;
05265 }
05266 
05267 /* static */ void
05268 nsDOMClassInfo::UnsetExternallyReferenced(nsIDOMGCParticipant *aParticipant)
05269 {
05270   NS_PRECONDITION(aParticipant, "unexpected null pointer");
05271 
05272   NS_ASSERTION(sExternallyReferencedTable.ops, "unbalanced call");
05273   if (sExternallyReferencedTable.ops) {
05274 #ifdef DEBUG
05275     PRUint32 count = sExternallyReferencedTable.entryCount;
05276 #endif
05277     PL_DHashTableOperate(&sExternallyReferencedTable, aParticipant,
05278                          PL_DHASH_REMOVE);
05279 #ifdef DEBUG
05280     NS_ASSERTION(count == sExternallyReferencedTable.entryCount + 1,
05281                  "unbalanced call");
05282 #endif
05283   }
05284 
05285   // Don't destroy the table when the entryCount hits zero, since that
05286   // is expected to happen often.  Instead, destroy it at shutdown.
05287 }
05288 
05289 PR_STATIC_CALLBACK(PLDHashOperator)
05290 ClassifyWrapper(PLDHashTable *table, PLDHashEntryHdr *hdr,
05291                 PRUint32 number, void *arg)
05292 {
05293   PreservedWrapperEntry *entry = NS_STATIC_CAST(PreservedWrapperEntry*, hdr);
05294 
05295   WrapperSCCEntry *SCCEntry = NS_STATIC_CAST(WrapperSCCEntry*,
05296     PL_DHashTableOperate(&sWrapperSCCTable, entry->participant->GetSCCIndex(),
05297                          PL_DHASH_ADD));
05298   if (!SCCEntry) {
05299     *NS_STATIC_CAST(PRBool*, arg) = PR_TRUE;
05300     return PL_DHASH_STOP;
05301   }
05302 
05303 #ifdef DEBUG_PRESERVE_WRAPPERS
05304   if (!SCCEntry->first) {
05305     nsAutoString nodeName;
05306     nsCOMPtr<nsIDOMNode> node = do_QueryInterface(SCCEntry->key);
05307     if (node)
05308       node->GetNodeName(nodeName);
05309     else
05310       nodeName.AssignLiteral("##not-node##");
05311     printf("  new SCC root %p \"%s\"\n",
05312            NS_STATIC_CAST(void*, SCCEntry->key.get()),
05313            NS_ConvertUTF16toUTF8(nodeName).get());
05314   }
05315 #endif
05316 
05317   entry->next = SCCEntry->first;
05318   SCCEntry->first = entry;
05319 
05320   return PL_DHASH_NEXT;
05321 }
05322 
05323 PR_STATIC_CALLBACK(PLDHashOperator)
05324 MarkExternallyReferenced(PLDHashTable *table, PLDHashEntryHdr *hdr,
05325                          PRUint32 number, void *arg)
05326 {
05327   ExternallyReferencedEntry *entry =
05328     NS_STATIC_CAST(ExternallyReferencedEntry*, hdr);
05329   JSContext *cx = NS_STATIC_CAST(JSContext*, arg);
05330 
05331   nsIDOMGCParticipant *erParticipant = entry->key;
05332 
05333   if (sRootWhenExternallyReferencedTable.ops) {
05334     RootWhenExternallyReferencedEntry *rwerEntry =
05335       NS_STATIC_CAST(RootWhenExternallyReferencedEntry*,
05336         PL_DHashTableOperate(&sRootWhenExternallyReferencedTable,
05337                              erParticipant, PL_DHASH_LOOKUP));
05338     if (PL_DHASH_ENTRY_IS_BUSY(rwerEntry)) {
05339       NS_ASSERTION(rwerEntry->refcnt > 0, "bad reference count");
05340       // XXX Construct something to say where the mark is coming from?
05341       nsDOMClassInfo::MarkReachablePreservedWrappers(entry->key, cx, nsnull);
05342     }
05343   }
05344 
05345   return PL_DHASH_NEXT;
05346 }
05347 
05348 // static
05349 PRBool
05350 nsDOMClassInfo::BeginGCMark(JSContext *cx)
05351 {
05352   NS_PRECONDITION(!sWrapperSCCTable.ops, "table already initialized");
05353 
05354 #ifdef DEBUG_PRESERVE_WRAPPERS
05355   printf("Classifying preserved wrappers into SCCs:\n");
05356 #endif
05357 
05358   if (!PL_DHashTableInit(&sWrapperSCCTable, &sWrapperSCCTableOps, nsnull,
05359                          sizeof(WrapperSCCEntry), 16)) {
05360     return PR_FALSE;
05361   }
05362 
05363   PRBool failure = PR_FALSE;
05364   if (sPreservedWrapperTable.ops) {
05365     PL_DHashTableEnumerate(&sPreservedWrapperTable, ClassifyWrapper, &failure);
05366   }
05367   if (failure) {
05368     PL_DHashTableFinish(&sWrapperSCCTable);
05369     // caller will reset table ops
05370     return PR_FALSE;
05371   }
05372 
05373 #ifdef DEBUG_PRESERVE_WRAPPERS
05374   printf("Marking:\n");
05375 #endif
05376 
05377   if (sExternallyReferencedTable.ops) {
05378     PL_DHashTableEnumerate(&sExternallyReferencedTable,
05379                            MarkExternallyReferenced, cx);
05380   }
05381 
05382   return PR_TRUE;
05383 }
05384 
05385 // static
05386 void
05387 nsDOMClassInfo::EndGCMark()
05388 {
05389   if (sWrapperSCCTable.ops) {
05390     if (sWrapperSCCTable.ops != WRAPPER_SCC_OPS_OOM_MARKER)
05391       PL_DHashTableFinish(&sWrapperSCCTable);
05392     sWrapperSCCTable.ops = nsnull;
05393   }
05394 }
05395 
05396 // hack to give XBL access to nsDOMClassInfo::PreserveNodeWrapper
05397 nsresult
05398 NS_DOMClassInfo_PreserveNodeWrapper(nsIXPConnectWrappedNative *aWrapper)
05399 {
05400   return nsDOMClassInfo::PreserveNodeWrapper(aWrapper);
05401 }
05402 
05403 // static
05404 nsresult
05405 nsWindowSH::GlobalResolve(nsGlobalWindow *aWin, JSContext *cx,
05406                           JSObject *obj, JSString *str, PRUint32 flags,
05407                           PRBool *did_resolve)
05408 {
05409   *did_resolve = PR_FALSE;
05410 
05411   extern nsScriptNameSpaceManager *gNameSpaceManager;
05412 
05413   NS_ENSURE_TRUE(gNameSpaceManager, NS_ERROR_NOT_INITIALIZED);
05414 
05415   nsDependentJSString name(str);
05416 
05417   const nsGlobalNameStruct *name_struct = nsnull;
05418   const PRUnichar *class_name = nsnull;
05419 
05420   gNameSpaceManager->LookupName(name, &name_struct, &class_name);
05421 
05422   if (!name_struct) {
05423     return NS_OK;
05424   }
05425 
05426   NS_ENSURE_TRUE(class_name, NS_ERROR_UNEXPECTED);
05427 
05428   nsresult rv = NS_OK;
05429 
05430   if (name_struct->mType == nsGlobalNameStruct::eTypeExternalClassInfoCreator) {
05431     nsCOMPtr<nsIDOMCIExtension> creator(do_CreateInstance(name_struct->mCID, &rv));
05432     NS_ENSURE_SUCCESS(rv, rv);
05433 
05434     nsCOMPtr<nsIDOMScriptObjectFactory> sof(do_GetService(kDOMSOF_CID));
05435     NS_ENSURE_TRUE(sof, NS_ERROR_FAILURE);
05436 
05437     rv = creator->RegisterDOMCI(NS_ConvertUCS2toUTF8(name).get(), sof);
05438     NS_ENSURE_SUCCESS(rv, rv);
05439 
05440     rv = gNameSpaceManager->LookupName(name, &name_struct);
05441     if (NS_FAILED(rv) || !name_struct ||
05442         name_struct->mType != nsGlobalNameStruct::eTypeExternalClassInfo) {
05443       NS_ERROR("Couldn't get the DOM ClassInfo data.");
05444 
05445       return NS_OK;
05446     }
05447   }
05448 
05449   if (name_struct->mType == nsGlobalNameStruct::eTypeInterface) {
05450     // We're resolving a name of a DOM interface for which there is no
05451     // direct DOM class, create a constructor object...
05452 
05453     nsRefPtr<nsDOMConstructor> constructor;
05454     rv = nsDOMConstructor::Create(NS_REINTERPRET_CAST(PRUnichar *,
05455                                     ::JS_GetStringChars(str)),
05456                                   NS_STATIC_CAST(nsPIDOMWindow*, aWin),
05457                                   getter_AddRefs(constructor));
05458     NS_ENSURE_SUCCESS(rv, rv);
05459 
05460     PRBool doSecurityCheckInAddProperty = sDoSecurityCheckInAddProperty;
05461     sDoSecurityCheckInAddProperty = PR_FALSE;
05462 
05463     nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
05464     jsval v;
05465 
05466     rv = WrapNative(cx, obj, constructor, NS_GET_IID(nsIDOMConstructor), &v,
05467                     getter_AddRefs(holder));
05468 
05469     sDoSecurityCheckInAddProperty = doSecurityCheckInAddProperty;
05470 
05471     NS_ENSURE_SUCCESS(rv, rv);
05472 
05473     rv = constructor->Install(cx, obj, v);
05474     NS_ENSURE_SUCCESS(rv, rv);
05475 
05476     JSObject *class_obj;
05477     holder->GetJSObject(&class_obj);
05478     NS_ASSERTION(class_obj, "The return value lied");
05479 
05480     // ... and define the constants from the DOM interface on that
05481     // constructor object.
05482 
05483     rv = DefineInterfaceConstants(cx, class_obj, &name_struct->mIID);
05484     NS_ENSURE_SUCCESS(rv, rv);
05485 
05486     *did_resolve = PR_TRUE;
05487 
05488     return NS_OK;
05489   }
05490 
05491   if (name_struct->mType == nsGlobalNameStruct::eTypeClassConstructor ||
05492       name_struct->mType == nsGlobalNameStruct::eTypeExternalClassInfo ||
05493       name_struct->mType == nsGlobalNameStruct::eTypeClassProto ||
05494       name_struct->mType == nsGlobalNameStruct::eTypeExternalConstructorAlias) {
05495     const nsDOMClassInfoData *ci_data = nsnull;
05496     const nsGlobalNameStruct* alias_struct = nsnull;
05497 
05498     if (name_struct->mType == nsGlobalNameStruct::eTypeClassConstructor &&
05499         name_struct->mDOMClassInfoID >= 0) {
05500       ci_data = &sClassInfoData[name_struct->mDOMClassInfoID];
05501     } else if (name_struct->mType == nsGlobalNameStruct::eTypeExternalClassInfo) {
05502       ci_data = name_struct->mData;
05503     } else if (name_struct->mType == nsGlobalNameStruct::eTypeExternalConstructorAlias) {
05504       alias_struct = gNameSpaceManager->GetConstructorProto(name_struct);
05505       NS_ENSURE_TRUE(alias_struct, NS_ERROR_UNEXPECTED);
05506 
05507       if (alias_struct->mType == nsGlobalNameStruct::eTypeClassConstructor) {
05508         ci_data = &sClassInfoData[alias_struct->mDOMClassInfoID];
05509       } else if (alias_struct->mType == nsGlobalNameStruct::eTypeExternalClassInfo) {
05510         ci_data = alias_struct->mData;
05511       }
05512     }
05513 
05514     const PRUnichar *name = NS_REINTERPRET_CAST(PRUnichar *,
05515                                                 ::JS_GetStringChars(str));
05516     nsRefPtr<nsDOMConstructor> constructor;
05517     rv = nsDOMConstructor::Create(name,
05518                                   NS_STATIC_CAST(nsPIDOMWindow*, aWin),
05519                                   getter_AddRefs(constructor));
05520     NS_ENSURE_SUCCESS(rv, rv);
05521 
05522     PRBool doSecurityCheckInAddProperty = sDoSecurityCheckInAddProperty;
05523     sDoSecurityCheckInAddProperty = PR_FALSE;
05524 
05525     nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
05526     jsval v;
05527 
05528     rv = WrapNative(cx, obj, constructor, NS_GET_IID(nsIDOMConstructor), &v,
05529                     getter_AddRefs(holder));
05530 
05531     sDoSecurityCheckInAddProperty = doSecurityCheckInAddProperty;
05532 
05533     NS_ENSURE_SUCCESS(rv, rv);
05534 
05535     rv = constructor->Install(cx, obj, v);
05536     NS_ENSURE_SUCCESS(rv, rv);
05537 
05538     JSObject *class_obj;
05539     holder->GetJSObject(&class_obj);
05540     NS_ASSERTION(class_obj, "The return value lied");
05541 
05542     const nsIID *primary_iid = &NS_GET_IID(nsISupports);
05543 
05544     if (name_struct->mType == nsGlobalNameStruct::eTypeClassProto) {
05545       primary_iid = &name_struct->mIID;
05546     } else if (ci_data && ci_data->mProtoChainInterface) {
05547       primary_iid = ci_data->mProtoChainInterface;
05548     }
05549 
05550     nsXPIDLCString class_parent_name;
05551 
05552     if (!primary_iid->Equals(NS_GET_IID(nsISupports))) {
05553       rv = DefineInterfaceConstants(cx, class_obj, primary_iid);
05554       NS_ENSURE_SUCCESS(rv, rv);
05555 
05556       // Special case for |Node|, which needs constants from Node3
05557       // too for forwards compatibility.
05558       if (primary_iid->Equals(NS_GET_IID(nsIDOMNode))) {
05559         rv = DefineInterfaceConstants(cx, class_obj,
05560                                       &NS_GET_IID(nsIDOM3Node));
05561         NS_ENSURE_SUCCESS(rv, rv);
05562       }
05563 
05564       // Special case for |Event|, Event needs constants from NSEvent
05565       // too for backwards compatibility.
05566       if (primary_iid->Equals(NS_GET_IID(nsIDOMEvent))) {
05567         rv = DefineInterfaceConstants(cx, class_obj,
05568                                       &NS_GET_IID(nsIDOMNSEvent));
05569         NS_ENSURE_SUCCESS(rv, rv);
05570       }
05571 
05572       nsCOMPtr<nsIInterfaceInfoManager> iim =
05573         dont_AddRef(XPTI_GetInterfaceInfoManager());
05574       NS_ENSURE_TRUE(iim, NS_ERROR_NOT_AVAILABLE);
05575 
05576       nsCOMPtr<nsIInterfaceInfo> if_info;
05577       iim->GetInfoForIID(primary_iid, getter_AddRefs(if_info));
05578       NS_ENSURE_TRUE(if_info, NS_ERROR_UNEXPECTED);
05579 
05580       nsCOMPtr<nsIInterfaceInfo> parent;
05581       nsIID *iid = nsnull;
05582 
05583       if (ci_data && !ci_data->mHasClassInterface) {
05584         if_info->GetInterfaceIID(&iid);
05585       } else {
05586         if_info->GetParent(getter_AddRefs(parent));
05587         NS_ENSURE_TRUE(parent, NS_ERROR_UNEXPECTED);
05588 
05589         parent->GetInterfaceIID(&iid);
05590       }
05591 
05592       if (iid) {
05593         if (!iid->Equals(NS_GET_IID(nsISupports))) {
05594           if (ci_data && !ci_data->mHasClassInterface) {
05595             // If the class doesn't have a class interface the primary
05596             // interface is the interface that should be
05597             // constructor.prototype.__proto__.
05598 
05599             if_info->GetName(getter_Copies(class_parent_name));
05600           } else {
05601             // If the class does have a class interface (or there's no
05602             // real class for this name) then the parent of the
05603             // primary interface is what we want on
05604             // constructor.prototype.__proto__.
05605 
05606             NS_ASSERTION(parent, "Whoa, this is bad, null parent here!");
05607 
05608             parent->GetName(getter_Copies(class_parent_name));
05609           }
05610         }
05611 
05612         nsMemory::Free(iid);
05613       }
05614     }
05615 
05616     JSObject *proto = nsnull;
05617 
05618     if (class_parent_name) {
05619       jsval val;
05620 
05621       if (!::JS_GetProperty(cx, obj, CutPrefix(class_parent_name), &val)) {
05622         return NS_ERROR_UNEXPECTED;
05623       }
05624 
05625       JSObject *tmp = JSVAL_IS_OBJECT(val) ? JSVAL_TO_OBJECT(val) : nsnull;
05626 
05627       if (tmp) {
05628         if (!::JS_GetProperty(cx, tmp, "prototype", &val)) {
05629           return NS_ERROR_UNEXPECTED;
05630         }
05631 
05632         if (JSVAL_IS_OBJECT(val)) {
05633           proto = JSVAL_TO_OBJECT(val);
05634         }
05635       }
05636     }
05637 
05638     JSObject *dot_prototype = nsnull;
05639 
05640     if (name_struct->mType == nsGlobalNameStruct::eTypeExternalConstructorAlias) {
05641       name_struct = alias_struct;
05642     }
05643 
05644     if (name_struct->mType == nsGlobalNameStruct::eTypeClassConstructor) {
05645       PRInt32 id = name_struct->mDOMClassInfoID;
05646       NS_ABORT_IF_FALSE(id >= 0, "Negative DOM classinfo?!?");
05647 
05648       nsDOMClassInfoID ci_id = (nsDOMClassInfoID)id;
05649 
05650       nsCOMPtr<nsIClassInfo> ci(GetClassInfoInstance(ci_id));
05651       NS_ENSURE_TRUE(ci, NS_ERROR_UNEXPECTED);
05652 
05653       nsCOMPtr<nsIXPConnectJSObjectHolder> proto_holder;
05654 
05655       // In most cases we want to find the wrapped native prototype in
05656       // aWin's scope and use that prototype for
05657       // ClassName.prototype. But in the case where we're setting up
05658       // "Window.prototype" or "ChromeWindow.prototype" we want to do
05659       // the look up in aWin's outer window's scope since the inner
05660       // window's wrapped native prototype comes from the outer
05661       // window's scope.
05662       nsGlobalWindow *scopeWindow;
05663 
05664       if (ci_id == eDOMClassInfo_Window_id ||
05665           ci_id == eDOMClassInfo_ChromeWindow_id) {
05666         scopeWindow = aWin->GetOuterWindowInternal();
05667 
05668         if (!scopeWindow) {
05669           scopeWindow = aWin;
05670         }
05671       } else {
05672         scopeWindow = aWin;
05673       }
05674 
05675       rv =
05676         sXPConnect->GetWrappedNativePrototype(cx,
05677                                               scopeWindow->GetGlobalJSObject(),
05678                                               ci,
05679                                               getter_AddRefs(proto_holder));
05680       NS_ENSURE_SUCCESS(rv, NS_ERROR_UNEXPECTED);
05681 
05682       rv = proto_holder->GetJSObject(&dot_prototype);
05683       NS_ENSURE_SUCCESS(rv, NS_ERROR_UNEXPECTED);
05684 
05685       JSObject *xpc_proto_proto = ::JS_GetPrototype(cx, dot_prototype);
05686 
05687       if (proto && JS_GET_CLASS(cx, xpc_proto_proto) == sObjectClass) {
05688         if (!::JS_SetPrototype(cx, dot_prototype, proto)) {
05689           return NS_ERROR_UNEXPECTED;
05690         }
05691       }
05692     } else if (name_struct->mType == nsGlobalNameStruct::eTypeExternalClassInfo) {
05693       nsCOMPtr<nsIClassInfo> ci = GetClassInfoInstance(name_struct->mData);
05694       NS_ENSURE_TRUE(ci, NS_ERROR_UNEXPECTED);
05695 
05696       nsCOMPtr<nsIXPConnectJSObjectHolder> proto_holder;
05697 
05698       rv =
05699         sXPConnect->GetWrappedNativePrototype(cx, obj, ci,
05700                                               getter_AddRefs(proto_holder));
05701       NS_ENSURE_SUCCESS(rv, NS_ERROR_UNEXPECTED);
05702 
05703       rv = proto_holder->GetJSObject(&dot_prototype);
05704       NS_ENSURE_SUCCESS(rv, NS_ERROR_UNEXPECTED);
05705 
05706       JSObject *xpc_proto_proto = ::JS_GetPrototype(cx, dot_prototype);
05707 
05708       if (proto && JS_GET_CLASS(cx, xpc_proto_proto) == sObjectClass) {
05709         if (!::JS_SetPrototype(cx, dot_prototype, proto)) {
05710           return NS_ERROR_UNEXPECTED;
05711         }
05712       }
05713     } else {
05714       dot_prototype = ::JS_NewObject(cx, &sDOMConstructorProtoClass, proto,
05715                                      obj);
05716       NS_ENSURE_TRUE(dot_prototype, NS_ERROR_OUT_OF_MEMORY);
05717     }
05718 
05719     v = OBJECT_TO_JSVAL(dot_prototype);
05720 
05721     // Per ECMA, the prototype property is {DontEnum, DontDelete, ReadOnly}
05722     if (!::JS_DefineProperty(cx, class_obj, "prototype", v, nsnull, nsnull,
05723                              JSPROP_PERMANENT | JSPROP_READONLY)) {
05724       return NS_ERROR_UNEXPECTED;
05725     }
05726 
05727     *did_resolve = PR_TRUE;
05728 
05729     return NS_OK;
05730   }
05731 
05732   if (name_struct->mType == nsGlobalNameStruct::eTypeExternalConstructor) {
05733     nsRefPtr<nsDOMConstructor> constructor;
05734     rv = nsDOMConstructor::Create(class_name,
05735                                   NS_STATIC_CAST(nsPIDOMWindow*, aWin),
05736                                   getter_AddRefs(constructor));
05737     NS_ENSURE_SUCCESS(rv, rv);
05738 
05739     jsval val;
05740     nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
05741     rv = WrapNative(cx, obj, constructor, NS_GET_IID(nsIDOMConstructor), &val,
05742                     getter_AddRefs(holder));
05743     NS_ENSURE_SUCCESS(rv, rv);
05744 
05745     rv = constructor->Install(cx, obj, val);
05746     NS_ENSURE_SUCCESS(rv, rv);
05747 
05748     JSObject* class_obj;
05749     holder->GetJSObject(&class_obj);
05750     NS_ASSERTION(class_obj, "Why didn't we get a JSObject?");
05751 
05752     *did_resolve = PR_TRUE;
05753 
05754     return NS_OK;
05755   }
05756 
05757   if (name_struct->mType == nsGlobalNameStruct::eTypeProperty) {
05758     nsCOMPtr<nsISupports> native(do_CreateInstance(name_struct->mCID, &rv));
05759     NS_ENSURE_SUCCESS(rv, rv);
05760 
05761     jsval prop_val; // Property value.
05762 
05763     nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
05764     nsCOMPtr<nsIScriptObjectOwner> owner(do_QueryInterface(native));
05765     if (owner) {
05766       nsIScriptContext *context = nsJSUtils::GetStaticScriptContext(cx, obj);
05767       NS_ENSURE_TRUE(context, NS_ERROR_UNEXPECTED);
05768 
05769       JSObject *prop_obj = nsnull;
05770       rv = owner->GetScriptObject(context, (void**)&prop_obj);
05771       NS_ENSURE_TRUE(prop_obj, NS_ERROR_UNEXPECTED);
05772 
05773       prop_val = OBJECT_TO_JSVAL(prop_obj);
05774     } else {
05775       JSObject *scope;
05776 
05777       if (aWin->IsOuterWindow()) {
05778         nsGlobalWindow *inner = aWin->GetCurrentInnerWindowInternal();
05779         NS_ENSURE_TRUE(inner, NS_ERROR_UNEXPECTED);
05780 
05781         scope = inner->GetGlobalJSObject();
05782       } else {
05783         scope = aWin->GetGlobalJSObject();
05784       }
05785 
05786       rv = WrapNative(cx, scope, native, NS_GET_IID(nsISupports), &prop_val,
05787                       getter_AddRefs(holder));
05788     }
05789 
05790     NS_ENSURE_SUCCESS(rv, rv);
05791 
05792     PRBool retval = ::JS_DefineUCProperty(cx, obj, ::JS_GetStringChars(str),
05793                                           ::JS_GetStringLength(str),
05794                                           prop_val, nsnull, nsnull,
05795                                           JSPROP_ENUMERATE);
05796     *did_resolve = PR_TRUE;
05797 
05798     return retval ? NS_OK : NS_ERROR_FAILURE;
05799   }
05800 
05801   if (name_struct->mType == nsGlobalNameStruct::eTypeDynamicNameSet) {
05802     nsCOMPtr<nsIScriptExternalNameSet> nameset =
05803       do_CreateInstance(name_struct->mCID, &rv);
05804     NS_ENSURE_SUCCESS(rv, rv);
05805 
05806     nsIScriptContext *context = aWin->GetContext();
05807     NS_ENSURE_TRUE(context, NS_ERROR_UNEXPECTED);
05808 
05809     rv = nameset->InitializeNameSet(context);
05810 
05811     *did_resolve = PR_TRUE;
05812   }
05813 
05814   return rv;
05815 }
05816 
05817 // Native code for window._content getter, this simply maps
05818 // window._content to window.content for backwards compatibility only.
05819 static JSBool JS_DLL_CALLBACK
05820 ContentWindowGetter(JSContext *cx, JSObject *obj, uintN argc, jsval *argv,
05821                     jsval *rval)
05822 {
05823   return ::JS_GetProperty(cx, obj, "content", rval);
05824 }
05825 
05826 NS_IMETHODIMP
05827 nsWindowSH::NewResolve(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
05828                        JSObject *obj, jsval id, PRUint32 flags,
05829                        JSObject **objp, PRBool *_retval)
05830 {
05831   nsGlobalWindow *win = nsGlobalWindow::FromWrapper(wrapper);
05832 
05833 #ifdef DEBUG_SH_FORWARDING
05834   {
05835     nsDependentJSString str(::JS_ValueToString(cx, id));
05836 
05837     if (win->IsInnerWindow()) {
05838 #ifdef DEBUG_PRINT_INNER
05839       printf("Property '%s' resolve on inner window %p\n",
05840              NS_ConvertUTF16toUTF8(str).get(), (void *)win);
05841 #endif
05842     } else {
05843       printf("Property '%s' resolve on outer window %p\n",
05844              NS_ConvertUTF16toUTF8(str).get(), (void *)win);
05845     }
05846   }
05847 #endif
05848 
05849   // Note, we won't forward resolve of the location property to the
05850   // inner window, we need to deal with that one for the outer too
05851   // since we've got special security protection code for that
05852   // property.  Also note that we want to enter this block even for
05853   // native wrappers, so that we'll ensure an inner window to wrap
05854   // against for the result of whatever we're getting.
05855   if (win->IsOuterWindow() && id != sLocation_id) {
05856     // XXXjst: Do security checks here when we remove the security
05857     // checks on the inner window.
05858 
05859     nsGlobalWindow *innerWin = win->GetCurrentInnerWindowInternal();
05860 
05861     if ((!innerWin || !innerWin->GetExtantDocument()) &&
05862         !win->IsCreatingInnerWindow()) {
05863       // We're resolving a property on an outer window for which there
05864       // is no inner window yet, and we're not in the midst of
05865       // creating the inner window or in the middle of initializing
05866       // XPConnect classes on it. If the context is already
05867       // initialized, force creation of a new inner window. This will
05868       // create a synthetic about:blank document, and an inner window
05869       // which may be reused by the actual document being loaded into
05870       // this outer window. This way properties defined on the window
05871       // before the document load started will be visible to the
05872       // document once it's loaded, assuming same origin etc.
05873       nsIScriptContext *scx = win->GetContextInternal();
05874 
05875       if (scx && scx->IsContextInitialized()) {
05876         nsCOMPtr<nsIDOMDocument> doc;
05877         win->GetDocument(getter_AddRefs(doc));
05878 
05879         // Grab the new inner window.
05880         innerWin = win->GetCurrentInnerWindowInternal();
05881 
05882         if (!innerWin) {
05883           return NS_ERROR_OUT_OF_MEMORY;
05884         }
05885       }
05886     }
05887 
05888     JSObject *innerObj;
05889     if (!ObjectIsNativeWrapper(cx, obj) &&
05890         innerWin && (innerObj = innerWin->GetGlobalJSObject())) {
05891 #ifdef DEBUG_SH_FORWARDING
05892       printf(" --- Forwarding resolve to inner window %p\n", (void *)innerWin);
05893 #endif
05894 
05895       jsid interned_id;
05896       JSObject *pobj;
05897       JSProperty *prop = nsnull;
05898 
05899       *_retval = (::JS_ValueToId(cx, id, &interned_id) &&
05900                   OBJ_LOOKUP_PROPERTY(cx, innerObj, interned_id, &pobj,
05901                                       &prop));
05902 
05903       if (*_retval && prop) {
05904 #ifdef DEBUG_SH_FORWARDING
05905         printf(" --- Resolve on inner window found property.\n");
05906 #endif
05907 
05908         OBJ_DROP_PROPERTY(cx, pobj, prop);
05909 
05910         *objp = pobj;
05911       }
05912 
05913       return NS_OK;
05914     }
05915   }
05916 
05917   if (!JSVAL_IS_STRING(id)) {
05918     if (JSVAL_IS_INT(id) && !(flags & JSRESOLVE_ASSIGNING)) {
05919       // If we're resolving a numeric property, treat that as if
05920       // window.frames[n] is resolved (since window.frames ===
05921       // window), if window.frames[n] is a child frame, define a
05922       // property for this index.
05923 
05924       nsCOMPtr<nsIDOMWindow> frame = GetChildFrame(win, id);
05925 
05926       if (frame) {
05927         // A numeric property accessed and the numeric property is a
05928         // child frame. Define a property for this index.
05929 
05930         PRBool doSecurityCheckInAddProperty = sDoSecurityCheckInAddProperty;
05931         sDoSecurityCheckInAddProperty = PR_FALSE;
05932 
05933         *_retval = ::JS_DefineElement(cx, obj, JSVAL_TO_INT(id), JSVAL_VOID,
05934                                       nsnull, nsnull, 0);
05935 
05936         sDoSecurityCheckInAddProperty = doSecurityCheckInAddProperty;
05937 
05938         if (*_retval) {
05939           *objp = obj;
05940         }
05941       }
05942     }
05943 
05944     return NS_OK;
05945   }
05946 
05947   nsIScriptContext *my_context = win->GetContextInternal();
05948 
05949   nsresult rv = NS_OK;
05950 
05951   // Resolve standard classes on my_context's JSContext (or on cx,
05952   // if we don't have a my_context yet), in case the two contexts
05953   // have different origins.  We want lazy standard class
05954   // initialization to behave as if it were done eagerly, on each
05955   // window's own context (not on some other window-caller's
05956   // context).
05957 
05958   JSContext *my_cx;
05959 
05960   if (!my_context) {
05961     my_cx = cx;
05962   } else {
05963     my_cx = (JSContext *)my_context->GetNativeContext();
05964   }
05965 
05966   // Resolving a standard class won't do any evil, and it's possible
05967   // for caps to get the answer wrong, so disable the security check
05968   // for this case.
05969 
05970   JSBool did_resolve = JS_FALSE;
05971   PRBool doSecurityCheckInAddProperty = sDoSecurityCheckInAddProperty;
05972   sDoSecurityCheckInAddProperty = PR_FALSE;
05973 
05974   // Don't resolve standard classes on XPCNativeWrapper.
05975   JSBool ok = !ObjectIsNativeWrapper(cx, obj) ?
05976               ::JS_ResolveStandardClass(my_cx, obj, id, &did_resolve) :
05977               JS_TRUE;
05978 
05979   sDoSecurityCheckInAddProperty = doSecurityCheckInAddProperty;
05980 
05981   if (!ok) {
05982     // Trust the JS engine (or the script security manager) to set
05983     // the exception in the JS engine.
05984 
05985     jsval exn;
05986     if (!JS_GetPendingException(my_cx, &exn)) {
05987       return NS_ERROR_UNEXPECTED;
05988     }
05989 
05990     // Return NS_OK to avoid stomping over the exception that was passed
05991     // down from the ResolveStandardClass call.
05992     // Note that the order of the JS_ClearPendingException and
05993     // JS_SetPendingException is important in the case that my_cx == cx.
05994 
05995     JS_ClearPendingException(my_cx);
05996     JS_SetPendingException(cx, exn);
05997     *_retval = JS_FALSE;
05998     return NS_OK;
05999   }
06000 
06001   if (did_resolve) {
06002     *objp = obj;
06003 
06004     return NS_OK;
06005   }
06006 
06007   if (!(flags & JSRESOLVE_ASSIGNING)) {
06008     // We want this code to be before the child frame lookup code
06009     // below so that a child frame named 'constructor' doesn't
06010     // shadow the window's constructor property.
06011     if (id == sConstructor_id) {
06012       return ResolveConstructor(cx, obj, objp);
06013     }
06014   }
06015 
06016   if (!my_context || !my_context->IsContextInitialized()) {
06017     // The context is not yet initialized so there's nothing we can do
06018     // here yet.
06019 
06020     return NS_OK;
06021   }
06022 
06023 
06024   // Hmm, we do an awful lot of QIs here; maybe we should add a
06025   // method on an interface that would let us just call into the
06026   // window code directly...
06027 
06028   JSString *str = JSVAL_TO_STRING(id);
06029 
06030   // Don't resolve named iframes on native wrappers
06031   if (!ObjectIsNativeWrapper(cx, obj)) {
06032     nsCOMPtr<nsIDocShellTreeNode> dsn(do_QueryInterface(win->GetDocShell()));
06033 
06034     PRInt32 count = 0;
06035 
06036     if (dsn) {
06037       dsn->GetChildCount(&count);
06038     }
06039 
06040     if (count > 0) {
06041       nsCOMPtr<nsIDocShellTreeItem> child;
06042 
06043       const jschar *chars = ::JS_GetStringChars(str);
06044 
06045       dsn->FindChildWithName(NS_REINTERPRET_CAST(const PRUnichar*, chars),
06046                              PR_FALSE, PR_TRUE, nsnull, nsnull,
06047                              getter_AddRefs(child));
06048 
06049       nsCOMPtr<nsIDOMWindow> child_win(do_GetInterface(child));
06050 
06051       if (child_win) {
06052         // We found a subframe of the right name, define the property
06053         // on the wrapper so that ::NewResolve() doesn't get called
06054         // again for this property name.
06055 
06056         JSObject *wrapperObj;
06057         wrapper->GetJSObject(&wrapperObj);
06058 
06059         jsval v;
06060         nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
06061         rv = WrapNative(cx, wrapperObj, child_win,
06062                         NS_GET_IID(nsIDOMWindowInternal), &v,
06063                         getter_AddRefs(holder));
06064         NS_ENSURE_SUCCESS(rv, rv);
06065 
06066         // Script is accessing a child frame and this access can
06067         // potentially come from a context from a different domain.
06068         // ::JS_DefineUCProperty() will call
06069         // nsWindowSH::AddProperty(), and that method will do a
06070         // security check and that security check will fail since
06071         // other domains can't add properties to a global object in
06072         // this domain. Set the sDoSecurityCheckInAddProperty flag to
06073         // false (and set it to true immediagtely when we're done) to
06074         // tell nsWindowSH::AddProperty() that defining this new
06075         // property is 'ok' in this case, even if the call comes from
06076         // a different context.
06077 
06078         sDoSecurityCheckInAddProperty = PR_FALSE;
06079 
06080         PRBool ok = ::JS_DefineUCProperty(cx, obj, chars,
06081                                           ::JS_GetStringLength(str), v, nsnull,
06082                                           nsnull, 0);
06083 
06084         sDoSecurityCheckInAddProperty = PR_TRUE;
06085 
06086         if (!ok) {
06087           return NS_ERROR_FAILURE;
06088         }
06089 
06090         *objp = obj;
06091 
06092         return NS_OK;
06093       }
06094     }
06095   }
06096 
06097   // It is not worth calling GlobalResolve() if we are resolving
06098   // for assignment, since only read-write properties get dealt
06099   // with there.
06100   if (!(flags & JSRESOLVE_ASSIGNING)) {
06101     // Call GlobalResolve() after we call FindChildWithName() so
06102     // that named child frames will override external properties
06103     // which have been registered with the script namespace manager.
06104 
06105     JSBool did_resolve = JS_FALSE;
06106     rv = GlobalResolve(win, cx, obj, str, flags, &did_resolve);
06107     NS_ENSURE_SUCCESS(rv, rv);
06108 
06109     if (did_resolve) {
06110       // GlobalResolve() resolved something, so we're done here.
06111       *objp = obj;
06112 
06113       return NS_OK;
06114     }
06115   }
06116 
06117   if (id == s_content_id) {
06118     // Map window._content to window.content for backwards
06119     // compatibility, this should spit out an message on the JS
06120     // console.
06121 
06122     JSObject *windowObj = win->GetGlobalJSObject();
06123 
06124     JSFunction *fun = ::JS_NewFunction(cx, ContentWindowGetter, 0, 0,
06125                                        windowObj, "_content");
06126     if (!fun) {
06127       return NS_ERROR_OUT_OF_MEMORY;
06128     }
06129 
06130     JSObject *funObj = ::JS_GetFunctionObject(fun);
06131 
06132     nsAutoGCRoot root(&funObj, &rv);
06133     NS_ENSURE_SUCCESS(rv, rv);
06134 
06135     if (!::JS_DefineUCProperty(cx, windowObj, ::JS_GetStringChars(str),
06136                                ::JS_GetStringLength(str), JSVAL_VOID,
06137                                (JSPropertyOp)funObj, nsnull,
06138                                JSPROP_ENUMERATE | JSPROP_GETTER |
06139                                JSPROP_SHARED)) {
06140       return NS_ERROR_FAILURE;
06141     }
06142 
06143     *objp = obj;
06144 
06145     return NS_OK;
06146   }
06147 
06148   if (id == sLocation_id) {
06149     // This must be done even if we're just getting the value of
06150     // window.location (i.e. no checking flags & JSRESOLVE_ASSIGNING
06151     // here) since we must define window.location to prevent the
06152     // getter from being overriden (for security reasons).
06153 
06154     nsCOMPtr<nsIDOMLocation> location;
06155     rv = win->GetLocation(getter_AddRefs(location));
06156     NS_ENSURE_SUCCESS(rv, rv);
06157 
06158     // Make sure we wrap the location object in the inner window's
06159     // scope if we've got an inner window.
06160     JSObject *scope = nsnull;
06161     if (win->IsOuterWindow()) {
06162       nsGlobalWindow *innerWin = win->GetCurrentInnerWindowInternal();
06163 
06164       if (innerWin) {
06165         scope = innerWin->GetGlobalJSObject();
06166       }
06167     }
06168 
06169     if (!scope) {
06170       wrapper->GetJSObject(&scope);
06171     }
06172 
06173     jsval v;
06174     nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
06175     rv = WrapNative(cx, scope, location, NS_GET_IID(nsIDOMLocation), &v,
06176                     getter_AddRefs(holder));
06177     NS_ENSURE_SUCCESS(rv, rv);
06178 
06179     PRBool doSecurityCheckInAddProperty = sDoSecurityCheckInAddProperty;
06180     sDoSecurityCheckInAddProperty = PR_FALSE;
06181 
06182     JSBool ok = ::JS_DefineUCProperty(cx, obj, ::JS_GetStringChars(str),
06183                                       ::JS_GetStringLength(str), v, nsnull,
06184                                       nsnull, JSPROP_ENUMERATE);
06185 
06186     sDoSecurityCheckInAddProperty = doSecurityCheckInAddProperty;
06187 
06188     if (!ok) {
06189       return NS_ERROR_FAILURE;
06190     }
06191 
06192     *objp = obj;
06193 
06194     return NS_OK;
06195   }
06196 
06197   if (flags & JSRESOLVE_ASSIGNING) {
06198     if (IsReadonlyReplaceable(id) ||
06199         (!(flags & JSRESOLVE_QUALIFIED) && IsWritableReplaceable(id))) {
06200       // A readonly "replaceable" property is being set, or a
06201       // readwrite "replaceable" property is being set w/o being
06202       // fully qualified. Define the property on obj with the value
06203       // undefined to override the predefined property. This is done
06204       // for compatibility with other browsers.
06205 
06206       if (!::JS_DefineUCProperty(cx, obj, ::JS_GetStringChars(str),
06207                                  ::JS_GetStringLength(str),
06208                                  JSVAL_VOID, nsnull, nsnull,
06209                                  JSPROP_ENUMERATE)) {
06210         return NS_ERROR_FAILURE;
06211       }
06212 
06213       *objp = obj;
06214 
06215       return NS_OK;
06216     }
06217   } else {
06218     if (id == sNavigator_id) {
06219       nsCOMPtr<nsIDOMNavigator> navigator;
06220       rv = win->GetNavigator(getter_AddRefs(navigator));
06221       NS_ENSURE_SUCCESS(rv, rv);
06222 
06223       jsval v;
06224       nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
06225       rv = WrapNative(cx, obj, navigator, NS_GET_IID(nsIDOMNavigator), &v,
06226                       getter_AddRefs(holder));
06227       NS_ENSURE_SUCCESS(rv, rv);
06228 
06229       if (!::JS_DefineUCProperty(cx, obj, ::JS_GetStringChars(str),
06230                                  ::JS_GetStringLength(str), v, nsnull,
06231                                  nsnull, JSPROP_ENUMERATE)) {
06232         return NS_ERROR_FAILURE;
06233       }
06234 
06235       *objp = obj;
06236 
06237       return NS_OK;
06238     }
06239 
06240     if (id == sDocument_id) {
06241       nsCOMPtr<nsIDOMDocument> document;
06242       rv = win->GetDocument(getter_AddRefs(document));
06243       NS_ENSURE_SUCCESS(rv, rv);
06244 
06245       jsval v;
06246       nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
06247       rv = WrapNative(cx, obj, document, NS_GET_IID(nsIDOMDocument), &v,
06248                       getter_AddRefs(holder));
06249       NS_ENSURE_SUCCESS(rv, rv);
06250 
06251       // The PostCreate hook for the document will handle defining the
06252       // property
06253       *objp = obj;
06254 
06255       return NS_OK;
06256     }
06257 
06258     if (id == sWindow_id) {
06259       // window should *always* be the outer window object.
06260       win = win->GetOuterWindowInternal();
06261       NS_ENSURE_TRUE(win, NS_ERROR_NOT_AVAILABLE);
06262 
06263       PRBool doSecurityCheckInAddProperty = sDoSecurityCheckInAddProperty;
06264       sDoSecurityCheckInAddProperty = PR_FALSE;
06265 
06266       PRBool ok =
06267         ::JS_DefineUCProperty(cx, obj, ::JS_GetStringChars(str),
06268                               ::JS_GetStringLength(str),
06269                               OBJECT_TO_JSVAL(win->GetGlobalJSObject()),
06270                               nsnull, nsnull,
06271                               JSPROP_READONLY | JSPROP_ENUMERATE);
06272 
06273       sDoSecurityCheckInAddProperty = doSecurityCheckInAddProperty;
06274 
06275       if (!ok) {
06276         return NS_ERROR_FAILURE;
06277       }
06278 
06279       *objp = obj;
06280 
06281       return NS_OK;
06282     }
06283 
06284     // Do a security check when resolving heretofore unknown string
06285     // properties on window objects to prevent detection of a
06286     // property's existence across origins. We only do this when
06287     // resolving for a GET, no need to do it for set since we'll do
06288     // a security check in nsWindowSH::SetProperty() in that case.
06289     rv =
06290       doCheckPropertyAccess(cx, obj, id, wrapper,
06291                             nsIXPCSecurityManager::ACCESS_GET_PROPERTY,
06292                             PR_TRUE);
06293     if (NS_FAILED(rv)) {
06294       // Security check failed. The security manager set a JS
06295       // exception, we must make sure that exception is propagated, so
06296       // return NS_OK here.
06297 
06298       *_retval = PR_FALSE;
06299 
06300       return NS_OK;
06301     }
06302   }
06303 
06304   return nsEventReceiverSH::NewResolve(wrapper, cx, obj, id, flags, objp,
06305                                        _retval);
06306 }
06307 
06308 NS_IMETHODIMP
06309 nsWindowSH::NewEnumerate(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
06310                          JSObject *obj, PRUint32 enum_op, jsval *statep,
06311                          jsid *idp, PRBool *_retval)
06312 {
06313   switch (enum_op) {
06314     case JSENUMERATE_INIT:
06315     {
06316       // First, do the security check that nsDOMClassInfo does to see
06317       // if we need to do any work at all.
06318       nsDOMClassInfo::Enumerate(wrapper, cx, obj, _retval);
06319       if (!*_retval) {
06320         return NS_OK;
06321       }
06322 
06323       // The security check passed, let's see if we need to get the inner
06324       // window's JS object or if we can just start enumerating.
06325       nsGlobalWindow *win = nsGlobalWindow::FromWrapper(wrapper);
06326       JSObject *enumobj = win->GetGlobalJSObject();
06327       if (win->IsOuterWindow()) {
06328         nsGlobalWindow *inner = win->GetCurrentInnerWindowInternal();
06329         if (inner) {
06330           enumobj = inner->GetGlobalJSObject();
06331         }
06332       }
06333 
06334       // Great, we have the js object, now let's enumerate it.
06335       JSObject *iterator = JS_NewPropertyIterator(cx, enumobj);
06336       if (!iterator) {
06337         return NS_ERROR_OUT_OF_MEMORY;
06338       }
06339 
06340       *statep = OBJECT_TO_JSVAL(iterator);
06341       if (idp) {
06342         // Note: With these property iterators, we can't tell ahead of time how
06343         // many properties we're going to be iterating over.
06344         *idp = JSVAL_ZERO;
06345       }
06346       break;
06347     }
06348     case JSENUMERATE_NEXT:
06349     {
06350       JSObject *iterator = (JSObject*)JSVAL_TO_OBJECT(*statep);
06351       if (!JS_NextProperty(cx, iterator, idp)) {
06352         return NS_ERROR_UNEXPECTED;
06353       }
06354 
06355       if (*idp != JSVAL_VOID) {
06356         break;
06357       }
06358 
06359       // Fall through.
06360     }
06361     case JSENUMERATE_DESTROY:
06362       // Let GC at our iterator object.
06363       *statep = JSVAL_NULL;
06364       break;
06365 
06366     default:
06367       NS_NOTREACHED("Bad call from the JS engine");
06368       return NS_ERROR_FAILURE;
06369   }
06370 
06371   return NS_OK;
06372 }
06373 
06374 NS_IMETHODIMP
06375 nsWindowSH::Finalize(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
06376                      JSObject *obj)
06377 {
06378   nsCOMPtr<nsIScriptGlobalObject> sgo(do_QueryWrappedNative(wrapper));
06379   NS_ENSURE_TRUE(sgo, NS_ERROR_UNEXPECTED);
06380 
06381   sgo->OnFinalize(obj);
06382 
06383   return nsEventReceiverSH::Finalize(wrapper, cx, obj);
06384 }
06385 
06386 NS_IMETHODIMP
06387 nsWindowSH::Equality(nsIXPConnectWrappedNative *wrapper, JSContext * cx,
06388                      JSObject * obj, jsval val, PRBool *bp)
06389 {
06390   *bp = PR_FALSE;
06391 
06392   if (JSVAL_IS_PRIMITIVE(val)) {
06393     return NS_OK;
06394   }
06395 
06396   nsCOMPtr<nsIXPConnectWrappedNative> other_wrapper;
06397   nsContentUtils::XPConnect()->
06398     GetWrappedNativeOfJSObject(cx, JSVAL_TO_OBJECT(val),
06399                                getter_AddRefs(other_wrapper));
06400   if (!other_wrapper) {
06401     // Not equal.
06402 
06403     return NS_OK;
06404   }
06405 
06406   nsGlobalWindow *win = nsGlobalWindow::FromWrapper(wrapper);
06407 
06408   NS_ASSERTION(win->IsOuterWindow(),
06409                "Inner window detected in Equality hook!");
06410 
06411   nsCOMPtr<nsPIDOMWindow> other = do_QueryWrappedNative(other_wrapper);
06412 
06413   if (other) {
06414     NS_ASSERTION(other->IsOuterWindow(),
06415                  "Inner window detected in Equality hook!");
06416 
06417     *bp = win->GetOuterWindow() == other->GetOuterWindow();
06418   }
06419 
06420   return NS_OK;
06421 }
06422 
06423 NS_IMETHODIMP
06424 nsWindowSH::OuterObject(nsIXPConnectWrappedNative *wrapper, JSContext * cx,
06425                         JSObject * obj, JSObject * *_retval)
06426 {
06427   nsGlobalWindow *win =
06428     nsGlobalWindow::FromWrapper(wrapper)->GetOuterWindowInternal();
06429 
06430   if (!win) {
06431     // If we no longer have an outer window. No code should ever be
06432     // running on a window w/o an outer, which means this hook should
06433     // never be called when we have no outer. But just in case, return
06434     // null to prevent leaking an inner window to code in a different
06435     // window.
06436 
06437     *_retval = nsnull;
06438 
06439     return NS_ERROR_UNEXPECTED;
06440   }
06441 
06442   // Return the outer window.
06443 
06444   *_retval = win->GetGlobalJSObject();
06445 
06446   return NS_OK;
06447 }
06448 
06449 NS_IMETHODIMP
06450 nsWindowSH::InnerObject(nsIXPConnectWrappedNative *wrapper, JSContext * cx,
06451                         JSObject * obj, JSObject * *_retval)
06452 {
06453   nsGlobalWindow *win = nsGlobalWindow::FromWrapper(wrapper);
06454 
06455   if (win->IsInnerWindow() || win->IsFrozen()) {
06456     // Return the inner window, or the outer if we're dealing with a
06457     // frozen outer.
06458 
06459     *_retval = obj;
06460   } else {
06461     // Try to find the current inner window.
06462 
06463     nsGlobalWindow *inner = win->GetCurrentInnerWindowInternal();
06464     if (!inner) {
06465       // Yikes! No inner window! Instead of leaking the outer window into the
06466       // scope chain, let's return an error.
06467 
06468       *_retval = nsnull;
06469 
06470       return NS_ERROR_UNEXPECTED;
06471     }
06472 
06473     *_retval = inner->GetGlobalJSObject();
06474   }
06475 
06476   return NS_OK;
06477 }
06478 
06479 // DOM Location helper
06480 
06481 NS_IMETHODIMP
06482 nsLocationSH::CheckAccess(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
06483                           JSObject *obj, jsval id, PRUint32 mode,
06484                           jsval *vp, PRBool *_retval)
06485 {
06486   if ((mode & JSACC_TYPEMASK) == JSACC_PROTO && (mode & JSACC_WRITE)) {
06487     // No setting location.__proto__, ever!
06488 
06489     // Let XPConnect know that the access was not granted.
06490     *_retval = PR_FALSE;
06491 
06492     return NS_ERROR_DOM_SECURITY_ERR;
06493   }
06494 
06495   return nsDOMGenericSH::CheckAccess(wrapper, cx, obj, id, mode, vp, _retval);
06496 }
06497 
06498 NS_IMETHODIMP
06499 nsLocationSH::PreCreate(nsISupports *nativeObj, JSContext *cx,
06500                         JSObject *globalObj, JSObject **parentObj)
06501 {
06502   // window.location can be held onto by both evil pages that want to track the
06503   // user's progress on the web and bookmarklets that want to use the location
06504   // object. Parent it to the outer window so that access checks do the Right
06505   // Thing.
06506   *parentObj = globalObj;
06507 
06508   nsCOMPtr<nsIDOMLocation> safeLoc(do_QueryInterface(nativeObj));
06509   if (!safeLoc) {
06510     // Oops, this wasn't really a location object. This can happen if someone
06511     // tries to use our scriptable helper as a real object and tries to wrap
06512     // it, see bug 319296
06513     return NS_OK;
06514   }
06515 
06516   nsLocation *loc = (nsLocation *)safeLoc.get();
06517   nsIDocShell *ds = loc->GetDocShell();
06518   if (!ds) {
06519     NS_WARNING("Refusing to create a location in the wrong scope");
06520     return NS_ERROR_UNEXPECTED;
06521   }
06522 
06523   nsCOMPtr<nsIScriptGlobalObject> sgo = do_GetInterface(ds);
06524 
06525   if (sgo) {
06526     JSObject *global = sgo->GetGlobalJSObject();
06527 
06528     if (global) {
06529       *parentObj = global;
06530     }
06531   }
06532 
06533   return NS_OK;
06534 }
06535 
06536 // DOM Navigator helper
06537 nsresult
06538 nsNavigatorSH::PreCreate(nsISupports *nativeObj, JSContext *cx,
06539                          JSObject *globalObj, JSObject **parentObj)
06540 {
06541   // window.navigator is persisted across document transitions if
06542   // we're loading a page from the same origin. Because of that we
06543   // need to parent the navigator wrapper at the outer window to avoid
06544   // holding on to the inner window where the navigator was initially
06545   // created too long.
06546   *parentObj = globalObj;
06547 
06548   nsCOMPtr<nsIDOMNavigator> safeNav(do_QueryInterface(nativeObj));
06549   if (!safeNav) {
06550     // Oops, this wasn't really a navigator object. This can happen if someone
06551     // tries to use our scriptable helper as a real object and tries to wrap
06552     // it, see bug 319296.
06553     return NS_OK;
06554   }
06555 
06556   nsNavigator *nav = (nsNavigator *)safeNav.get();
06557   nsIDocShell *ds = nav->GetDocShell();
06558   if (!ds) {
06559     NS_WARNING("Refusing to create a navigator in the wrong scope");
06560     return NS_ERROR_UNEXPECTED;
06561   }
06562 
06563   nsCOMPtr<nsIScriptGlobalObject> sgo = do_GetInterface(ds);
06564 
06565   if (sgo) {
06566     JSObject *global = sgo->GetGlobalJSObject();
06567 
06568     if (global) {
06569       *parentObj = global;
06570     }
06571   }
06572 
06573   return NS_OK;
06574 }
06575 
06576 // DOM Node helper
06577 
06578 NS_IMETHODIMP
06579 nsNodeSH::PreCreate(nsISupports *nativeObj, JSContext *cx, JSObject *globalObj,
06580                     JSObject **parentObj)
06581 {
06582   nsCOMPtr<nsIContent> content(do_QueryInterface(nativeObj));
06583   nsCOMPtr<nsIDocument> doc;
06584 
06585   if (content) {
06586     // Make sure that we get the owner document of the content node, in case
06587     // we're in document teardown.  If we are, it's important to *not* use
06588     // globalObj as the nodes parent since that would give the node the
06589     // principal of globalObj (i.e. the principal of the document that's being
06590     // loaded) and not the principal of the document that's being unloaded.
06591     // See http://bugzilla.mozilla.org/show_bug.cgi?id=227417
06592     doc = content->GetOwnerDoc();
06593   }
06594 
06595   if (!doc) {
06596     doc = do_QueryInterface(nativeObj);
06597 
06598     if (!doc) {
06599       // No document reachable from nativeObj, use the global object
06600       // that was passed to this method.
06601 
06602       *parentObj = globalObj;
06603 
06604       return NS_OK;
06605     }
06606   }
06607 
06608   nsISupports *native_parent;
06609 
06610   if (content) {
06611     if (content->IsContentOfType(nsIContent::eXUL)) {
06612       // For XUL elements, use the parent, if any.
06613       native_parent = content->GetParent();
06614 
06615       if (!native_parent) {
06616         native_parent = doc;
06617       }
06618     } else {
06619       // For non-XUL elements, use the document as scope parent.
06620       native_parent = doc;
06621 
06622       // But for HTML form controls, use the form as scope parent.
06623       if (content->IsContentOfType(nsIContent::eELEMENT |
06624                                    nsIContent::eHTML |
06625                                    nsIContent::eHTML_FORM_CONTROL)) {
06626         nsCOMPtr<nsIFormControl> form_control(do_QueryInterface(content));
06627 
06628         if (form_control) {
06629           nsCOMPtr<nsIDOMHTMLFormElement> form;
06630           form_control->GetForm(getter_AddRefs(form));
06631 
06632           if (form) {
06633             // Found a form, use it.
06634             native_parent = form;
06635           }
06636         }
06637       }
06638     }
06639   } else {
06640     // We're called for a document object (since content is null),
06641     // set the parent to be the document's global object, if there
06642     // is one
06643 
06644     // Get the scope object from the document.
06645     nsCOMPtr<nsIDocument_MOZILLA_1_8_0_BRANCH> doc18(do_QueryInterface(doc));
06646     if (!doc18) {
06647       NS_ERROR("Unexpected document");
06648       return NS_ERROR_FAILURE;
06649     }
06650     native_parent = doc18->GetScopeObject();
06651 
06652     if (!native_parent) {
06653       // No global object reachable from this document, use the
06654       // global object that was passed to this method.
06655 
06656       *parentObj = globalObj;
06657 
06658       return NS_OK;
06659     }
06660   }
06661 
06662   // XXXjst: Maybe we need to find the global to use from the
06663   // nsIScriptGlobalObject that's reachable from the node we're about
06664   // to wrap here? But that's not always reachable, let's use
06665   // globalObj for now...
06666 
06667   jsval v;
06668   nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
06669   nsresult rv = WrapNative(cx, globalObj, native_parent,
06670                            NS_GET_IID(nsISupports), &v,
06671                            getter_AddRefs(holder));
06672 
06673   *parentObj = JSVAL_TO_OBJECT(v);
06674 
06675   return rv;
06676 }
06677 
06678 NS_IMETHODIMP
06679 nsNodeSH::AddProperty(nsIXPConnectWrappedNative *wrapper, JSContext *cx,
06680                       JSObject *obj, jsval id, jsval *vp, PRBool *_retval)
06681 {
06682   // This can fail on out-of-memory, which should end up throwing a JS
06683   // exception.
06684   nsresult rv = nsDOMClassInfo::PreserveNodeWrapper(wrapper);
06685   NS_ENSURE_SUCCESS(rv, rv);
06686 
06687   return nsEventReceiverSH::AddProperty(wrapper, cx, obj, id, vp, _retval);
06688 }
06689 
06690 NS_IMETHODIMP
06691 nsNodeSH::GetFlags(PRUint32 *aFlags)
06692 {
06693   *aFlags = DOMCLASSINFO_STANDARD_FLAGS | nsIClassInfo::CONTENT_NODE;
06694 
06695   return NS_OK;
06696 }
06697 
06698 // EventReceiver helper
06699 
06700 // static
06701 PRBool
06702 nsEventReceiverSH::ReallyIsEventName(jsval id, jschar aFirstChar)
06703 {
06704   // I wonder if this is faster than using a hash...
06705 
06706   switch (aFirstChar) {
06707   case 'a' :
06708     return id == sOnabort_id;
06709   case 'b' :
06710     return (id == sOnbeforeunload_id ||
06711             id == sOnblur_id);
06712   case 'e' :
06713     return id == sOnerror_id;
06714   case 'f' :
06715     return id == sOnfocus_id;
06716   case 'c' :
06717     return (id == sOnchange_id       ||
06718             id == sOnclick_id        ||
06719             id == sOncontextmenu_id);
06720   case 'd' :
06721     return id == sOndblclick_id;
06722   case 'l' :
06723     return id == sOnload_id;
06724   case 'p' :
06725     return (id == sOnpaint_id        ||
06726             id == sOnpageshow_id     ||
06727             id == sOnpagehide_id);
06728   case 'k' :
06729     return (id == sOnkeydown_id      ||
06730             id == sOnkeypress_id     ||
06731             id == sOnkeyup_id);
06732   case 'u' :
06733     return id == sOnunload_id;
06734   case 'm' :
06735     return (id == sOnmousemove_id    ||
06736             id == sOnmouseout_id     ||
06737             id == sOnmouseover_id    ||
06738             id == sOnmouseup_id      ||
06739             id == sOnmousedown_id);
06740   case 'r' :
06741     return (id == sOnreset_id        ||
06742             id == sOnresize_id);
06743   case 's' :
06744     return (id == sOnscroll_id       ||
06745             id == sOnselect_id       ||
06746             id == sOnsubmit_id);
06747   }
06748 
06749   return PR_FALSE;
06750 }
06751 
06752 // static
06753 JSBool JS_DLL_CALLBACK
06754 nsEventReceiverSH::AddEventListenerHelper(JSContext *cx, JSObject *obj,
06755                                           uintN argc, jsval *argv, jsval *rval)
06756 {
06757   if (argc < 3 || argc > 4) {
06758     ThrowJSException(cx, NS_ERROR_XPC_NOT_ENOUGH_ARGS);
06759 
06760     return JS_FALSE;
06761   }
06762 
06763   // Can't use the macro OBJ_TO_INNER_OBJECT here due to it using the
06764   // non-exported function js_GetSlotThreadSafe().
06765   {
06766     JSClass *clasp = JS_GET_CLASS(cx, obj);
06767     if (clasp->flags & JSCLASS_IS_EXTENDED) {
06768       JSExtendedClass *xclasp = (JSExtendedClass*)clasp;
06769       if (xclasp->innerObject)
06770         obj = xclasp->innerObject(cx, obj);
06771     }
06772   }
06773 
06774   nsCOMPtr<nsIXPConnectWrappedNative> wrapper;
06775   nsresult rv =
06776     sXPConnect->GetWrappedNativeOfJSObject(cx, obj, getter_AddRefs(wrapper));
06777   if (NS_FAILED(rv)) {
06778     nsDOMClassInfo::ThrowJSException(cx, rv);
06779 
06780     return JS_FALSE;
06781   }
06782 
06783   // Set obj to be the object on which we'll actually register the
06784   // event listener.
06785   wrapper->GetJSObject(&obj);
06786 
06787   // Check that the caller has permission to call obj's addEventListener.
06788   if (NS_FAILED(sSecMan->CheckPropertyAccess(cx, obj,
06789                                              JS_GET_CLASS(cx, obj)->name,
06790                                              sAddEventListener_id,
06791                                              nsIXPCSecurityManager::ACCESS_GET_PROPERTY)) ||
06792       NS_FAILED(sSecMan->CheckPropertyAccess(cx, obj,
06793                                              JS_GET_CLASS(cx, obj)->name,
06794                                              sAddEventListener_id,
06795                                              nsIXPCSecurityManager::ACCESS_CALL_METHOD))) {
06796     // The caller doesn't have access to get or call the callee
06797     // object's addEventListener method. The security manager already
06798     // threw an exception for us, so simply return false.
06799 
06800     return JS_FALSE;
06801   }
06802 
06803   if (JSVAL_IS_PRIMITIVE(argv[1])) {
06804     // The second argument must be a function, or a
06805     // nsIDOMEventListener. Throw an error.
06806     ThrowJSException(cx, NS_ERROR_XPC_BAD_CONVERT_JS);
06807 
06808     return JS_FALSE;
06809   }
06810 
06811   JSString* jsstr = JS_ValueToString(cx, argv[0]);
06812   if (!jsstr) {
06813     nsDOMClassInfo::ThrowJSException(cx, NS_ERROR_OUT_OF_MEMORY);
06814 
06815     return JS_FALSE;
06816   }
06817 
06818   nsDependentJSString type(jsstr);
06819 
06820   nsCOMPtr<nsIDOMEventListener> listener;
06821 
06822   {
06823     nsCOMPtr<nsISupports> tmp;
06824     sXPConnect->WrapJS(cx, JSVAL_TO_OBJECT(argv[1]),
06825                        NS_GET_IID(nsIDOMEventListener), getter_AddRefs(tmp));
06826 
06827     listener = do_QueryInterface(tmp, &rv);
06828     if (NS_FAILED(rv)) {
06829       ThrowJSException(cx, rv);
06830 
06831       return JS_FALSE;
06832     }
06833   }
06834 
06835   JSBool useCapture;
06836   if (!JS_ValueToBoolean(cx, argv[2], &useCapture)) {
06837     return JS_FALSE;
06838   }
06839 
06840   if (argc == 4) {
06841     JSBool wantsUntrusted;
06842     if (!JS_ValueToBoolean(cx, argv[3], &wantsUntrusted)) {
06843       return JS_FALSE;
06844     }
06845 
06846     nsCOMPtr<nsIDOMNSEventTarget> eventTarget(do_QueryWrappedNative(wrapper,
06847                                                                     &rv));
06848     if (NS_FAILED(rv)) {
06849       ThrowJSException(cx, rv);
06850 
06851       return JS_FALSE;
06852     }
06853 
06854     rv = eventTarget->AddEventListener(type, listener, useCapture,
06855                                        wantsUntrusted);
06856     if (NS_FAILED(rv)) {
06857       ThrowJSException(cx, rv);
06858 
06859       return JS_FALSE;
06860     }
06861   } else {
06862     nsCOMPtr<nsIDOMEventTarget> eventTarget(do_QueryWrappedNative(wrapper,
06863                                                                   &rv));
06864     if (NS_FAILED(rv)) {
06865       ThrowJSException(cx, rv);
06866 
06867       return JS_FALSE;
06868     }
06869 
06870     rv = eventTarget->AddEventListener(type, listener, useCapture);
06871     if (NS_FAILED(rv)) {
06872       ThrowJSException(cx, rv);
06873 
06874       return JS_FALSE;
06875     }
06876   }
06877   
06878   return JS_TRUE;
06879 }
06880 
06881 nsresult
06882 nsEventReceiverSH::RegisterCompileHandler(nsIXPConnectWrappedNative *wrapper,
06883                                           JSContext *cx, JSObject *obj,
06884                                           jsval id, PRBool compile,
06885                                           PRBool remove,
06886                                           PRBool *did_define)
06887 {
06888   NS_PRECONDITION(!compile || !remove,
06889                   "Can't both compile and remove at the same time");
06890   *did_define = PR_FALSE;
06891 
06892   if (!IsEventName(id)) {
06893     return NS_OK;
06894   }
06895 
06896   if (ObjectIsNativeWrapper(cx, obj)) {
06897     return NS_ERROR_NOT_AVAILABLE;
06898   }
06899 
06900   nsIScriptContext *script_cx = nsJSUtils::GetStaticScriptContext(cx, obj);
06901   NS_ENSURE_TRUE(script_cx, NS_ERROR_UNEXPECTED);
06902 
06903   nsCOMPtr<nsIDOMEventReceiver> receiver(do_QueryWrappedNative(wrapper));
06904   NS_ENSURE_TRUE(receiver, NS_ERROR_UNEXPECTED);
06905 
06906   nsCOMPtr<nsIEventListenerManager> manager;
06907   receiver->GetListenerManager(getter_AddRefs(manager));
06908   NS_ENSURE_TRUE(manager, NS_ERROR_UNEXPECTED);
06909 
06910   nsCOMPtr<nsIAtom> atom(do_GetAtom(nsDependentJSString(id)));
06911   NS_ENSURE_TRUE(atom, NS_ERROR_OUT_OF_MEMORY);
06912 
06913   nsresult rv;
06914 
06915   JSObject *scope = GetGlobalJSObject(cx, obj);
06916 
06917   if (compile) {
06918     rv = manager->CompileScriptEventListener(script_cx, scope, receiver, atom,
06919                                              did_define);
06920   } else if (remove) {
06921     rv = manager->RemoveScriptEventListener(atom);
06922   } else {
06923     rv = manager->RegisterScriptEventListener(script_cx, scope, receiver,
06924                                               atom);
06925   }
06926 
06927   return NS_FAILED(rv) ? rv : NS_SUCCESS_I_DID_SOMETHING;
06928 }
06929 
06930 NS_IMETHODIMP
06931 nsEventReceiverSH::NewResolve(nsIXPConnectWrappedNative *wrapper,
06932                               JSContext *cx, JSObject *obj, jsval id,
06933                               PRUint32 flags, JSObject **objp, PRBool *_retval)
06934 {
06935   if (id == sOnload_id || id == sOnerror_id) {
06936     // Pass true for aRootWhenExternallyReferenced, so we make sure that
06937     // this node can't go away while waiting for a network load that
06938     // could fire an event handler.
06939     nsresult rv = nsDOMClassInfo::PreserveNodeWrapper(wrapper, PR_TRUE);
06940     NS_ENSURE_SUCCESS(rv, rv);
06941   }
06942 
06943   // If we're assigning to an on* property, we'll register the handler
06944   // in our ::SetProperty() hook, so no need to do it here too.
06945   if (!JSVAL_IS_STRING(id) || (flags & JSRESOLVE_ASSIGNING)) {
06946     return NS_OK;
06947   }
06948 
06949   if (id == sAddEventListener_id && !(flags & JSRESOLVE_ASSIGNING)) {
06950     JSString *str = JSVAL_TO_STRING(id);