summaryrefslogtreecommitdiffstats
path: root/src/libs/xpcom18a4/xpcom/glue
diff options
context:
space:
mode:
authorDaniel Baumann <daniel.baumann@progress-linux.org>2024-05-06 03:01:46 +0000
committerDaniel Baumann <daniel.baumann@progress-linux.org>2024-05-06 03:01:46 +0000
commitf8fe689a81f906d1b91bb3220acde2a4ecb14c5b (patch)
tree26484e9d7e2c67806c2d1760196ff01aaa858e8c /src/libs/xpcom18a4/xpcom/glue
parentInitial commit. (diff)
downloadvirtualbox-upstream.tar.xz
virtualbox-upstream.zip
Adding upstream version 6.0.4-dfsg.upstream/6.0.4-dfsgupstream
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'src/libs/xpcom18a4/xpcom/glue')
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/.cvsignore1
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/Makefile.in86
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsCOMPtr.cpp124
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsCOMPtr.h1405
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsComponentManagerUtils.cpp133
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsDebug.cpp119
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsDebug.h276
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsGenericFactory.cpp547
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsGenericFactory.h129
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsIGenericFactory.h480
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsIInterfaceRequestorUtils.cpp64
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsIInterfaceRequestorUtils.h83
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsISupportsImpl.h1246
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsISupportsUtils.h230
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsIWeakReferenceUtils.h162
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsMemory.cpp151
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsMemory.h154
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsServiceManagerUtils.h183
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsTraceRefcnt.cpp125
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsTraceRefcnt.h135
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsWeakReference.cpp169
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/nsWeakReference.h150
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/objs.mk60
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/standalone/.cvsignore8
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/standalone/Makefile.in88
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/standalone/nsGREDirServiceProvider.cpp596
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/standalone/nsGREDirServiceProvider.h68
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/standalone/nsXPCOMGlue.cpp524
-rw-r--r--src/libs/xpcom18a4/xpcom/glue/standalone/nsXPCOMGlue.h109
29 files changed, 7605 insertions, 0 deletions
diff --git a/src/libs/xpcom18a4/xpcom/glue/.cvsignore b/src/libs/xpcom18a4/xpcom/glue/.cvsignore
new file mode 100644
index 00000000..f3c7a7c5
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/.cvsignore
@@ -0,0 +1 @@
+Makefile
diff --git a/src/libs/xpcom18a4/xpcom/glue/Makefile.in b/src/libs/xpcom18a4/xpcom/glue/Makefile.in
new file mode 100644
index 00000000..a3b1f24d
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/Makefile.in
@@ -0,0 +1,86 @@
+# ***** BEGIN LICENSE BLOCK *****
+# Version: MPL 1.1/GPL 2.0/LGPL 2.1
+#
+# The contents of this file are subject to the Mozilla Public License Version
+# 1.1 (the "License"); you may not use this file except in compliance with
+# the License. You may obtain a copy of the License at
+# http://www.mozilla.org/MPL/
+#
+# Software distributed under the License is distributed on an "AS IS" basis,
+# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+# for the specific language governing rights and limitations under the
+# License.
+#
+# The Original Code is mozilla.org code.
+#
+# The Initial Developer of the Original Code is
+# Netscape Communications Corporation.
+# Portions created by the Initial Developer are Copyright (C) 2001
+# the Initial Developer. All Rights Reserved.
+#
+# Contributor(s):
+#
+# Alternatively, the contents of this file may be used under the terms of
+# either the GNU General Public License Version 2 or later (the "GPL"), or
+# the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+# in which case the provisions of the GPL or the LGPL are applicable instead
+# of those above. If you wish to allow use of your version of this file only
+# under the terms of either the GPL or the LGPL, and not to allow others to
+# use your version of this file under the terms of the MPL, indicate your
+# decision by deleting the provisions above and replace them with the notice
+# and other provisions required by the GPL or the LGPL. If you do not delete
+# the provisions above, a recipient may use your version of this file under
+# the terms of any one of the MPL, the GPL or the LGPL.
+#
+# ***** END LICENSE BLOCK *****
+
+DEPTH = ../..
+topsrcdir = @top_srcdir@
+srcdir = @srcdir@
+VPATH = @srcdir@
+
+include $(DEPTH)/config/autoconf.mk
+include $(srcdir)/objs.mk
+
+DIRS = standalone
+
+MODULE = xpcom
+LIBRARY_NAME = xpcomglue_s
+
+REQUIRES = $(NULL)
+
+LOCAL_INCLUDES = \
+ -I$(srcdir)/../build \
+ $(NULL)
+
+CPPSRCS = \
+ $(XPCOM_GLUE_SRC_LCSRCS) \
+ $(NULL)
+
+SDK_HEADERS = \
+ nsIGenericFactory.h \
+ nsIInterfaceRequestorUtils.h \
+ nsISupportsImpl.h \
+ nsISupportsUtils.h \
+ nsIWeakReferenceUtils.h \
+ $(XPCOM_GLUE_SRC_LEXPORTS) \
+ $(NULL)
+
+SDK_LIBRARY = \
+ $(LIB_PREFIX)xpcomglue_s.$(LIB_SUFFIX) \
+ $(NULL)
+
+# we don't want the shared lib, but we want to force the creation of a static lib.
+FORCE_STATIC_LIB = 1
+
+# Force use of PIC
+FORCE_USE_PIC = 1
+
+include $(topsrcdir)/config/rules.mk
+
+# hack to work around objdir bustage
+export::
+ rm -f $(XPCOM_GLUE_SRC_CSRCS:.cpp=.$(OBJ_SUFFIX))
+
+DEFINES += \
+ -D_IMPL_NS_COM
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsCOMPtr.cpp b/src/libs/xpcom18a4/xpcom/glue/nsCOMPtr.cpp
new file mode 100644
index 00000000..cac3c6d4
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsCOMPtr.cpp
@@ -0,0 +1,124 @@
+/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ * Scott Collins <scc@netscape.com>
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#include "nsCOMPtr.h"
+
+nsresult
+nsQueryInterface::operator()( const nsIID& aIID, void** answer ) const
+ {
+ nsresult status;
+ if ( mRawPtr )
+ {
+ status = mRawPtr->QueryInterface(aIID, answer);
+#ifdef NSCAP_FEATURE_TEST_NONNULL_QUERY_SUCCEEDS
+ NS_WARN_IF_FALSE(NS_SUCCEEDED(status), "interface not found---were you expecting that?");
+#endif
+ }
+ else
+ status = NS_ERROR_NULL_POINTER;
+
+ return status;
+ }
+
+nsresult
+nsQueryInterfaceWithError::operator()( const nsIID& aIID, void** answer ) const
+ {
+ nsresult status;
+ if ( mRawPtr )
+ {
+ status = mRawPtr->QueryInterface(aIID, answer);
+#ifdef NSCAP_FEATURE_TEST_NONNULL_QUERY_SUCCEEDS
+ NS_WARN_IF_FALSE(NS_SUCCEEDED(status), "interface not found---were you expecting that?");
+#endif
+ }
+ else
+ status = NS_ERROR_NULL_POINTER;
+
+ if ( mErrorPtr )
+ *mErrorPtr = status;
+ return status;
+ }
+
+nsCOMPtr_base::~nsCOMPtr_base()
+ {
+ NSCAP_LOG_RELEASE(this, mRawPtr);
+ if ( mRawPtr )
+ NSCAP_RELEASE(this, mRawPtr);
+ }
+
+void
+nsCOMPtr_base::assign_with_AddRef( nsISupports* rawPtr )
+ {
+ if ( rawPtr )
+ NSCAP_ADDREF(this, rawPtr);
+ assign_assuming_AddRef(rawPtr);
+ }
+
+void
+nsCOMPtr_base::assign_from_qi( const nsQueryInterface qi, const nsIID& iid )
+ {
+ nsISupports* newRawPtr;
+ if ( NS_FAILED( qi(iid, NS_REINTERPRET_CAST(void**, &newRawPtr)) ) )
+ newRawPtr = 0;
+ assign_assuming_AddRef(newRawPtr);
+ }
+
+void
+nsCOMPtr_base::assign_from_qi_with_error( const nsQueryInterfaceWithError& qi, const nsIID& iid )
+ {
+ nsISupports* newRawPtr;
+ if ( NS_FAILED( qi(iid, NS_REINTERPRET_CAST(void**, &newRawPtr)) ) )
+ newRawPtr = 0;
+ assign_assuming_AddRef(newRawPtr);
+ }
+
+void
+nsCOMPtr_base::assign_from_helper( const nsCOMPtr_helper& helper, const nsIID& iid )
+ {
+ nsISupports* newRawPtr;
+ if ( NS_FAILED( helper(iid, NS_REINTERPRET_CAST(void**, &newRawPtr)) ) )
+ newRawPtr = 0;
+ assign_assuming_AddRef(newRawPtr);
+ }
+
+void**
+nsCOMPtr_base::begin_assignment()
+ {
+ assign_assuming_AddRef(0);
+ return NS_REINTERPRET_CAST(void**, &mRawPtr);
+ }
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsCOMPtr.h b/src/libs/xpcom18a4/xpcom/glue/nsCOMPtr.h
new file mode 100644
index 00000000..b5a0fd78
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsCOMPtr.h
@@ -0,0 +1,1405 @@
+/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ * Scott Collins <scc@mozilla.org> (original author)
+ * L. David Baron <dbaron@dbaron.org>
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#ifndef nsCOMPtr_h___
+#define nsCOMPtr_h___
+
+/*
+ Having problems?
+
+ See the User Manual at:
+ http://www.mozilla.org/projects/xpcom/nsCOMPtr.html
+
+
+ nsCOMPtr
+ better than a raw pointer
+ for owning objects
+ -- scc
+*/
+
+
+ // Wrapping includes can speed up compiles (see "Large Scale C++ Software Design")
+#ifndef nsDebug_h___
+#include "nsDebug.h"
+ // for |NS_PRECONDITION|
+#endif
+
+#ifndef nsISupportsUtils_h__
+#include "nsISupportsUtils.h"
+ // for |nsresult|, |NS_ADDREF|, |NS_GET_IID| et al
+#endif
+
+#ifndef nscore_h___
+#include "nscore.h"
+ // for |NS_..._CAST|, |NS_COM|
+#endif
+
+
+/*
+ WARNING:
+ This file defines several macros for internal use only. These macros begin with the
+ prefix |NSCAP_|. Do not use these macros in your own code. They are for internal use
+ only for cross-platform compatibility, and are subject to change without notice.
+*/
+
+
+#ifdef _MSC_VER
+ #define NSCAP_FEATURE_INLINE_STARTASSIGNMENT
+ // under VC++, we win by inlining StartAssignment
+
+ // Also under VC++, at the highest warning level, we are overwhelmed with warnings
+ // about (unused) inline functions being removed. This is to be expected with
+ // templates, so we disable the warning.
+ #pragma warning( disable: 4514 )
+#endif
+
+#define NSCAP_FEATURE_USE_BASE
+
+#ifdef NS_DEBUG
+ #define NSCAP_FEATURE_TEST_DONTQUERY_CASES
+ #undef NSCAP_FEATURE_USE_BASE
+//#define NSCAP_FEATURE_TEST_NONNULL_QUERY_SUCCEEDS
+#endif
+
+ /*
+ |...TEST_DONTQUERY_CASES| and |...DEBUG_PTR_TYPES| introduce some code that is
+ problematic on a select few of our platforms, e.g., QNX. Therefore, I'm providing
+ a mechanism by which these features can be explicitly disabled from the command-line.
+ */
+
+#ifdef NSCAP_DISABLE_TEST_DONTQUERY_CASES
+ #undef NSCAP_FEATURE_TEST_DONTQUERY_CASES
+#endif
+
+#if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 3)
+ // Our use of nsCOMPtr_base::mRawPtr violates the C++ standard's aliasing
+ // rules. Mark it with the may_alias attribute so that gcc 3.3 and higher
+ // don't reorder instructions based on aliasing assumptions for
+ // this variable. Fortunately, gcc versions < 3.3 do not do any
+ // optimizations that break nsCOMPtr.
+
+ #define NS_MAY_ALIAS_PTR(t) t* __attribute__((__may_alias__))
+#else
+ #define NS_MAY_ALIAS_PTR(t) t*
+#endif
+
+#if defined(NSCAP_DISABLE_DEBUG_PTR_TYPES)
+ #define NSCAP_FEATURE_USE_BASE
+#endif
+
+
+#ifdef HAVE_CPP_BOOL
+ typedef bool NSCAP_BOOL;
+#else
+ typedef PRBool NSCAP_BOOL;
+#endif
+
+
+
+
+ /*
+ The following three macros (|NSCAP_ADDREF|, |NSCAP_RELEASE|, and |NSCAP_LOG_ASSIGNMENT|)
+ allow external clients the ability to add logging or other interesting debug facilities.
+ In fact, if you want |nsCOMPtr| to participate in the standard logging facility, you
+ provide (e.g., in "nsTraceRefcnt.h") suitable definitions
+
+ #define NSCAP_ADDREF(this, ptr) NS_ADDREF(ptr)
+ #define NSCAP_RELEASE(this, ptr) NS_RELEASE(ptr)
+ */
+
+#ifndef NSCAP_ADDREF
+ #define NSCAP_ADDREF(this, ptr) (ptr)->AddRef()
+#endif
+
+#ifndef NSCAP_RELEASE
+ #define NSCAP_RELEASE(this, ptr) (ptr)->Release()
+#endif
+
+ // Clients can define |NSCAP_LOG_ASSIGNMENT| to perform logging.
+#ifdef NSCAP_LOG_ASSIGNMENT
+ // Remember that |NSCAP_LOG_ASSIGNMENT| was defined by some client so that we know
+ // to instantiate |~nsGetterAddRefs| in turn to note the external assignment into
+ // the |nsCOMPtr|.
+ #define NSCAP_LOG_EXTERNAL_ASSIGNMENT
+#else
+ // ...otherwise, just strip it out of the code
+ #define NSCAP_LOG_ASSIGNMENT(this, ptr)
+#endif
+
+#ifndef NSCAP_LOG_RELEASE
+ #define NSCAP_LOG_RELEASE(this, ptr)
+#endif
+
+
+
+
+ /*
+ WARNING:
+ VC++4.2 is very picky. To compile under VC++4.2, the classes must be defined
+ in an order that satisfies:
+
+ nsDerivedSafe < nsCOMPtr
+ already_AddRefed < nsCOMPtr
+ nsCOMPtr < nsGetterAddRefs
+
+ The other compilers probably won't complain, so please don't reorder these
+ classes, on pain of breaking 4.2 compatibility.
+ */
+
+
+template <class T>
+class nsDerivedSafe : public T
+ /*
+ No client should ever see or have to type the name of this class. It is the
+ artifact that makes it a compile-time error to call |AddRef| and |Release|
+ on a |nsCOMPtr|. DO NOT USE THIS TYPE DIRECTLY IN YOUR CODE.
+
+ See |nsCOMPtr::operator->|, |nsCOMPtr::operator*|, et al.
+
+ This type should be a nested class inside |nsCOMPtr<T>|.
+ */
+ {
+ private:
+#ifdef HAVE_CPP_ACCESS_CHANGING_USING
+ using T::AddRef;
+ using T::Release;
+#else
+ nsrefcnt AddRef(void);
+ nsrefcnt Release(void);
+#endif
+
+#if !defined(AIX) && !defined(IRIX)
+ void operator delete( void*, size_t ); // NOT TO BE IMPLEMENTED
+ // declaring |operator delete| private makes calling delete on an interface pointer a compile error
+#endif
+
+ nsDerivedSafe<T>& operator=( const T& ); // NOT TO BE IMPLEMENTED
+ // you may not call |operator=()| through a dereferenced |nsCOMPtr|, because you'd get the wrong one
+
+ /*
+ Compiler warnings and errors: nsDerivedSafe operator=() hides inherited operator=().
+ If you see that, that means somebody checked in a [XP]COM interface class that declares an
+ |operator=()|, and that's _bad_. So bad, in fact, that this declaration exists explicitly
+ to stop people from doing it.
+ */
+
+ protected:
+ nsDerivedSafe(); // NOT TO BE IMPLEMENTED
+ /*
+ This ctor exists to avoid compile errors and warnings about nsDeriviedSafe using the
+ default ctor but inheriting classes without an empty ctor. See bug 209667.
+ */
+ };
+
+#if !defined(HAVE_CPP_ACCESS_CHANGING_USING) && defined(NEED_CPP_UNUSED_IMPLEMENTATIONS)
+template <class T>
+nsrefcnt
+nsDerivedSafe<T>::AddRef()
+ {
+ return 0;
+ }
+
+template <class T>
+nsrefcnt
+nsDerivedSafe<T>::Release()
+ {
+ return 0;
+ }
+
+#endif
+
+
+
+template <class T>
+struct already_AddRefed
+ /*
+ ...cooperates with |nsCOMPtr| to allow you to assign in a pointer _without_
+ |AddRef|ing it. You might want to use this as a return type from a function
+ that produces an already |AddRef|ed pointer as a result.
+
+ See also |getter_AddRefs()|, |dont_AddRef()|, and |class nsGetterAddRefs|.
+
+ This type should be a nested class inside |nsCOMPtr<T>|.
+
+ Yes, |already_AddRefed| could have been implemented as an |nsCOMPtr_helper| to
+ avoid adding specialized machinery to |nsCOMPtr| ... but this is the simplest
+ case, and perhaps worth the savings in time and space that its specific
+ implementation affords over the more general solution offered by
+ |nsCOMPtr_helper|.
+ */
+ {
+ already_AddRefed( T* aRawPtr )
+ : mRawPtr(aRawPtr)
+ {
+ // nothing else to do here
+ }
+
+ T* get() const { return mRawPtr; }
+
+ T* mRawPtr;
+ };
+
+template <class T>
+inline
+const already_AddRefed<T>
+getter_AddRefs( T* aRawPtr )
+ /*
+ ...makes typing easier, because it deduces the template type, e.g.,
+ you write |dont_AddRef(fooP)| instead of |already_AddRefed<IFoo>(fooP)|.
+ */
+ {
+ return already_AddRefed<T>(aRawPtr);
+ }
+
+template <class T>
+inline
+const already_AddRefed<T>
+getter_AddRefs( const already_AddRefed<T> aAlreadyAddRefedPtr )
+ {
+ return aAlreadyAddRefedPtr;
+ }
+
+template <class T>
+inline
+const already_AddRefed<T>
+dont_AddRef( T* aRawPtr )
+ {
+ return already_AddRefed<T>(aRawPtr);
+ }
+
+template <class T>
+inline
+const already_AddRefed<T>
+dont_AddRef( const already_AddRefed<T> aAlreadyAddRefedPtr )
+ {
+ return aAlreadyAddRefedPtr;
+ }
+
+
+
+class nsCOMPtr_helper
+ /*
+ An |nsCOMPtr_helper| transforms commonly called getters into typesafe forms
+ that are more convenient to call, and more efficient to use with |nsCOMPtr|s.
+ Good candidates for helpers are |QueryInterface()|, |CreateInstance()|, etc.
+
+ Here are the rules for a helper:
+ - it implements |operator()| to produce an interface pointer
+ - (except for its name) |operator()| is a valid [XP]COM `getter'
+ - the interface pointer that it returns is already |AddRef()|ed (as from any good getter)
+ - it matches the type requested with the supplied |nsIID| argument
+ - its constructor provides an optional |nsresult*| that |operator()| can fill
+ in with an error when it is executed
+
+ See |class nsGetInterface| for an example.
+ */
+ {
+ public:
+ virtual nsresult NS_FASTCALL operator()( const nsIID&, void** ) const = 0;
+ };
+
+/*
+ |nsQueryInterface| could have been implemented as an |nsCOMPtr_helper| to
+ avoid adding specialized machinery in |nsCOMPtr|, But |do_QueryInterface|
+ is called often enough that the codesize savings are big enough to
+ warrant the specialcasing.
+*/
+
+class NS_COM nsQueryInterface
+ {
+ public:
+ nsQueryInterface( nsISupports* aRawPtr )
+ : mRawPtr(aRawPtr)
+ {
+ // nothing else to do here
+ }
+
+ nsresult NS_FASTCALL operator()( const nsIID& aIID, void** ) const;
+
+ private:
+ nsISupports* mRawPtr;
+ };
+
+class NS_COM nsQueryInterfaceWithError
+ {
+ public:
+ nsQueryInterfaceWithError( nsISupports* aRawPtr, nsresult* error )
+ : mRawPtr(aRawPtr),
+ mErrorPtr(error)
+ {
+ // nothing else to do here
+ }
+
+ nsresult NS_FASTCALL operator()( const nsIID& aIID, void** ) const;
+
+ private:
+ nsISupports* mRawPtr;
+ nsresult* mErrorPtr;
+ };
+
+inline
+nsQueryInterface
+do_QueryInterface( nsISupports* aRawPtr )
+ {
+ return nsQueryInterface(aRawPtr);
+ }
+
+inline
+nsQueryInterfaceWithError
+do_QueryInterface( nsISupports* aRawPtr, nsresult* error )
+ {
+ return nsQueryInterfaceWithError(aRawPtr, error);
+ }
+
+template <class T>
+inline
+void
+do_QueryInterface( already_AddRefed<T>& )
+ {
+ // This signature exists soley to _stop_ you from doing the bad thing.
+ // Saying |do_QueryInterface()| on a pointer that is not otherwise owned by
+ // someone else is an automatic leak. See <http://bugzilla.mozilla.org/show_bug.cgi?id=8221>.
+ }
+
+template <class T>
+inline
+void
+do_QueryInterface( already_AddRefed<T>&, nsresult* )
+ {
+ // This signature exists soley to _stop_ you from doing the bad thing.
+ // Saying |do_QueryInterface()| on a pointer that is not otherwise owned by
+ // someone else is an automatic leak. See <http://bugzilla.mozilla.org/show_bug.cgi?id=8221>.
+ }
+
+
+
+class nsCOMPtr_base
+ /*
+ ...factors implementation for all template versions of |nsCOMPtr|.
+
+ This should really be an |nsCOMPtr<nsISupports>|, but this wouldn't work
+ because unlike the
+
+ Here's the way people normally do things like this
+
+ template <class T> class Foo { ... };
+ template <> class Foo<void*> { ... };
+ template <class T> class Foo<T*> : private Foo<void*> { ... };
+ */
+ {
+ public:
+
+ nsCOMPtr_base( nsISupports* rawPtr = 0 )
+ : mRawPtr(rawPtr)
+ {
+ // nothing else to do here
+ }
+
+ NS_COM NS_FASTCALL ~nsCOMPtr_base();
+
+ NS_COM void NS_FASTCALL assign_with_AddRef( nsISupports* );
+ NS_COM void NS_FASTCALL assign_from_qi( const nsQueryInterface, const nsIID& );
+ NS_COM void NS_FASTCALL assign_from_qi_with_error( const nsQueryInterfaceWithError&, const nsIID& );
+ NS_COM void NS_FASTCALL assign_from_helper( const nsCOMPtr_helper&, const nsIID& );
+ NS_COM void** NS_FASTCALL begin_assignment();
+
+ protected:
+ NS_MAY_ALIAS_PTR(nsISupports) mRawPtr;
+
+ void
+ assign_assuming_AddRef( nsISupports* newPtr )
+ {
+ /*
+ |AddRef()|ing the new value (before entering this function) before
+ |Release()|ing the old lets us safely ignore the self-assignment case.
+ We must, however, be careful only to |Release()| _after_ doing the
+ assignment, in case the |Release()| leads to our _own_ destruction,
+ which would, in turn, cause an incorrect second |Release()| of our old
+ pointer. Thank <waterson@netscape.com> for discovering this.
+ */
+ nsISupports* oldPtr = mRawPtr;
+ mRawPtr = newPtr;
+ NSCAP_LOG_ASSIGNMENT(this, newPtr);
+ NSCAP_LOG_RELEASE(this, oldPtr);
+ if ( oldPtr )
+ NSCAP_RELEASE(this, oldPtr);
+ }
+ };
+
+// template <class T> class nsGetterAddRefs;
+
+template <class T>
+class nsCOMPtr
+#ifdef NSCAP_FEATURE_USE_BASE
+ : private nsCOMPtr_base
+#endif
+ {
+
+#ifdef NSCAP_FEATURE_USE_BASE
+ #define NSCAP_CTOR_BASE(x) nsCOMPtr_base(x)
+#else
+ #define NSCAP_CTOR_BASE(x) mRawPtr(x)
+
+ private:
+ void assign_with_AddRef( nsISupports* );
+ void assign_from_qi( const nsQueryInterface, const nsIID& );
+ void assign_from_qi_with_error( const nsQueryInterfaceWithError&, const nsIID& );
+ void assign_from_helper( const nsCOMPtr_helper&, const nsIID& );
+ void** begin_assignment();
+
+ void
+ assign_assuming_AddRef( T* newPtr )
+ {
+ T* oldPtr = mRawPtr;
+ mRawPtr = newPtr;
+ NSCAP_LOG_ASSIGNMENT(this, newPtr);
+ NSCAP_LOG_RELEASE(this, oldPtr);
+ if ( oldPtr )
+ NSCAP_RELEASE(this, oldPtr);
+ }
+
+ private:
+ T* mRawPtr;
+#endif
+
+ public:
+ typedef T element_type;
+
+#ifndef NSCAP_FEATURE_USE_BASE
+ ~nsCOMPtr()
+ {
+ NSCAP_LOG_RELEASE(this, mRawPtr);
+ if ( mRawPtr )
+ NSCAP_RELEASE(this, mRawPtr);
+ }
+#endif
+
+#ifdef NSCAP_FEATURE_TEST_DONTQUERY_CASES
+ void
+ Assert_NoQueryNeeded()
+ {
+ if ( mRawPtr )
+ {
+ nsCOMPtr<T> query_result( do_QueryInterface(mRawPtr) );
+ NS_ASSERTION(query_result.get() == mRawPtr, "QueryInterface needed");
+ }
+ }
+
+ #define NSCAP_ASSERT_NO_QUERY_NEEDED() Assert_NoQueryNeeded();
+#else
+ #define NSCAP_ASSERT_NO_QUERY_NEEDED()
+#endif
+
+
+ // Constructors
+
+ nsCOMPtr()
+ : NSCAP_CTOR_BASE(0)
+ // default constructor
+ {
+ NSCAP_LOG_ASSIGNMENT(this, 0);
+ }
+
+ nsCOMPtr( const nsCOMPtr<T>& aSmartPtr )
+ : NSCAP_CTOR_BASE(aSmartPtr.mRawPtr)
+ // copy-constructor
+ {
+ if ( mRawPtr )
+ NSCAP_ADDREF(this, mRawPtr);
+ NSCAP_LOG_ASSIGNMENT(this, aSmartPtr.mRawPtr);
+ }
+
+ nsCOMPtr( T* aRawPtr )
+ : NSCAP_CTOR_BASE(aRawPtr)
+ // construct from a raw pointer (of the right type)
+ {
+ if ( mRawPtr )
+ NSCAP_ADDREF(this, mRawPtr);
+ NSCAP_LOG_ASSIGNMENT(this, aRawPtr);
+ NSCAP_ASSERT_NO_QUERY_NEEDED();
+ }
+
+ nsCOMPtr( const already_AddRefed<T>& aSmartPtr )
+ : NSCAP_CTOR_BASE(aSmartPtr.mRawPtr)
+ // construct from |dont_AddRef(expr)|
+ {
+ NSCAP_LOG_ASSIGNMENT(this, aSmartPtr.mRawPtr);
+ NSCAP_ASSERT_NO_QUERY_NEEDED();
+ }
+
+ nsCOMPtr( const nsQueryInterface qi )
+ : NSCAP_CTOR_BASE(0)
+ // construct from |do_QueryInterface(expr)|
+ {
+ NSCAP_LOG_ASSIGNMENT(this, 0);
+ assign_from_qi(qi, NS_GET_IID(T));
+ }
+
+ nsCOMPtr( const nsQueryInterfaceWithError& qi )
+ : NSCAP_CTOR_BASE(0)
+ // construct from |do_QueryInterface(expr, &rv)|
+ {
+ NSCAP_LOG_ASSIGNMENT(this, 0);
+ assign_from_qi_with_error(qi, NS_GET_IID(T));
+ }
+
+ nsCOMPtr( const nsCOMPtr_helper& helper )
+ : NSCAP_CTOR_BASE(0)
+ // ...and finally, anything else we might need to construct from
+ // can exploit the |nsCOMPtr_helper| facility
+ {
+ NSCAP_LOG_ASSIGNMENT(this, 0);
+ assign_from_helper(helper, NS_GET_IID(T));
+ NSCAP_ASSERT_NO_QUERY_NEEDED();
+ }
+
+
+ // Assignment operators
+
+ nsCOMPtr<T>&
+ operator=( const nsCOMPtr<T>& rhs )
+ // copy assignment operator
+ {
+ assign_with_AddRef(rhs.mRawPtr);
+ return *this;
+ }
+
+ nsCOMPtr<T>&
+ operator=( T* rhs )
+ // assign from a raw pointer (of the right type)
+ {
+ assign_with_AddRef(rhs);
+ NSCAP_ASSERT_NO_QUERY_NEEDED();
+ return *this;
+ }
+
+ nsCOMPtr<T>&
+ operator=( const already_AddRefed<T>& rhs )
+ // assign from |dont_AddRef(expr)|
+ {
+ assign_assuming_AddRef(rhs.mRawPtr);
+ NSCAP_ASSERT_NO_QUERY_NEEDED();
+ return *this;
+ }
+
+ nsCOMPtr<T>&
+ operator=( const nsQueryInterface rhs )
+ // assign from |do_QueryInterface(expr)|
+ {
+ assign_from_qi(rhs, NS_GET_IID(T));
+ return *this;
+ }
+
+ nsCOMPtr<T>&
+ operator=( const nsQueryInterfaceWithError& rhs )
+ // assign from |do_QueryInterface(expr, &rv)|
+ {
+ assign_from_qi_with_error(rhs, NS_GET_IID(T));
+ return *this;
+ }
+
+ nsCOMPtr<T>&
+ operator=( const nsCOMPtr_helper& rhs )
+ // ...and finally, anything else we might need to assign from
+ // can exploit the |nsCOMPtr_helper| facility.
+ {
+ assign_from_helper(rhs, NS_GET_IID(T));
+ NSCAP_ASSERT_NO_QUERY_NEEDED();
+ return *this;
+ }
+
+ void
+ swap( nsCOMPtr<T>& rhs )
+ // ...exchange ownership with |rhs|; can save a pair of refcount operations
+ {
+#ifdef NSCAP_FEATURE_USE_BASE
+ nsISupports* temp = rhs.mRawPtr;
+#else
+ T* temp = rhs.mRawPtr;
+#endif
+ NSCAP_LOG_ASSIGNMENT(&rhs, mRawPtr);
+ NSCAP_LOG_ASSIGNMENT(this, temp);
+ NSCAP_LOG_RELEASE(this, mRawPtr);
+ NSCAP_LOG_RELEASE(&rhs, temp);
+ rhs.mRawPtr = mRawPtr;
+ mRawPtr = temp;
+ // |rhs| maintains the same invariants, so we don't need to |NSCAP_ASSERT_NO_QUERY_NEEDED|
+ }
+
+ void
+ swap( T*& rhs )
+ // ...exchange ownership with |rhs|; can save a pair of refcount operations
+ {
+#ifdef NSCAP_FEATURE_USE_BASE
+ nsISupports* temp = rhs;
+#else
+ T* temp = rhs;
+#endif
+ NSCAP_LOG_ASSIGNMENT(this, temp);
+ NSCAP_LOG_RELEASE(this, mRawPtr);
+ rhs = NS_REINTERPRET_CAST(T*, mRawPtr);
+ mRawPtr = temp;
+ NSCAP_ASSERT_NO_QUERY_NEEDED();
+ }
+
+
+ // Other pointer operators
+
+ nsDerivedSafe<T>*
+ get() const
+ /*
+ Prefer the implicit conversion provided automatically by |operator nsDerivedSafe<T>*() const|.
+ Use |get()| _only_ to resolve ambiguity.
+
+ Returns a |nsDerivedSafe<T>*| to deny clients the use of |AddRef| and |Release|.
+ */
+ {
+ return NS_REINTERPRET_CAST(nsDerivedSafe<T>*, mRawPtr);
+ }
+
+ operator nsDerivedSafe<T>*() const
+ /*
+ ...makes an |nsCOMPtr| act like its underlying raw pointer type (except against |AddRef()|, |Release()|,
+ and |delete|) whenever it is used in a context where a raw pointer is expected. It is this operator
+ that makes an |nsCOMPtr| substitutable for a raw pointer.
+
+ Prefer the implicit use of this operator to calling |get()|, except where necessary to resolve ambiguity.
+ */
+ {
+ return get();
+ }
+
+ nsDerivedSafe<T>*
+ operator->() const
+ {
+ NS_PRECONDITION(mRawPtr != 0, "You can't dereference a NULL nsCOMPtr with operator->().");
+ return get();
+ }
+
+#ifdef CANT_RESOLVE_CPP_CONST_AMBIGUITY
+ // broken version for IRIX
+
+ nsCOMPtr<T>*
+ get_address() const
+ // This is not intended to be used by clients. See |address_of|
+ // below.
+ {
+ return NS_CONST_CAST(nsCOMPtr<T>*, this);
+ }
+
+#else // CANT_RESOLVE_CPP_CONST_AMBIGUITY
+
+ nsCOMPtr<T>*
+ get_address()
+ // This is not intended to be used by clients. See |address_of|
+ // below.
+ {
+ return this;
+ }
+
+ const nsCOMPtr<T>*
+ get_address() const
+ // This is not intended to be used by clients. See |address_of|
+ // below.
+ {
+ return this;
+ }
+
+#endif // CANT_RESOLVE_CPP_CONST_AMBIGUITY
+
+ public:
+ nsDerivedSafe<T>&
+ operator*() const
+ {
+ NS_PRECONDITION(mRawPtr != 0, "You can't dereference a NULL nsCOMPtr with operator*().");
+ return *get();
+ }
+
+#if 0
+ private:
+ friend class nsGetterAddRefs<T>;
+#endif
+
+ T**
+ StartAssignment()
+ {
+#ifndef NSCAP_FEATURE_INLINE_STARTASSIGNMENT
+ return NS_REINTERPRET_CAST(T**, begin_assignment());
+#else
+ assign_assuming_AddRef(0);
+ return NS_REINTERPRET_CAST(T**, &mRawPtr);
+#endif
+ }
+ };
+
+
+
+ /*
+ Specializing |nsCOMPtr| for |nsISupports| allows us to use |nsCOMPtr<nsISupports>| the
+ same way people use |nsISupports*| and |void*|, i.e., as a `catch-all' pointer pointing
+ to any valid [XP]COM interface. Otherwise, an |nsCOMPtr<nsISupports>| would only be able
+ to point to the single [XP]COM-correct |nsISupports| instance within an object; extra
+ querying ensues. Clients need to be able to pass around arbitrary interface pointers,
+ without hassles, through intermediary code that doesn't know the exact type.
+ */
+
+NS_SPECIALIZE_TEMPLATE
+class nsCOMPtr<nsISupports>
+ : private nsCOMPtr_base
+ {
+ public:
+ typedef nsISupports element_type;
+
+ // Constructors
+
+ nsCOMPtr()
+ : nsCOMPtr_base(0)
+ // default constructor
+ {
+ NSCAP_LOG_ASSIGNMENT(this, 0);
+ }
+
+ nsCOMPtr( const nsCOMPtr<nsISupports>& aSmartPtr )
+ : nsCOMPtr_base(aSmartPtr.mRawPtr)
+ // copy constructor
+ {
+ if ( mRawPtr )
+ NSCAP_ADDREF(this, mRawPtr);
+ NSCAP_LOG_ASSIGNMENT(this, aSmartPtr.mRawPtr);
+ }
+
+ nsCOMPtr( nsISupports* aRawPtr )
+ : nsCOMPtr_base(aRawPtr)
+ // construct from a raw pointer (of the right type)
+ {
+ if ( mRawPtr )
+ NSCAP_ADDREF(this, mRawPtr);
+ NSCAP_LOG_ASSIGNMENT(this, aRawPtr);
+ }
+
+ nsCOMPtr( const already_AddRefed<nsISupports>& aSmartPtr )
+ : nsCOMPtr_base(aSmartPtr.mRawPtr)
+ // construct from |dont_AddRef(expr)|
+ {
+ NSCAP_LOG_ASSIGNMENT(this, aSmartPtr.mRawPtr);
+ }
+
+ nsCOMPtr( const nsQueryInterface qi )
+ : nsCOMPtr_base(0)
+ // assign from |do_QueryInterface(expr)|
+ {
+ NSCAP_LOG_ASSIGNMENT(this, 0);
+ assign_from_qi(qi, NS_GET_IID(nsISupports));
+ }
+
+ nsCOMPtr( const nsQueryInterfaceWithError& qi )
+ : nsCOMPtr_base(0)
+ // assign from |do_QueryInterface(expr, &rv)|
+ {
+ NSCAP_LOG_ASSIGNMENT(this, 0);
+ assign_from_qi_with_error(qi, NS_GET_IID(nsISupports));
+ }
+
+ nsCOMPtr( const nsCOMPtr_helper& helper )
+ : nsCOMPtr_base(0)
+ // ...and finally, anything else we might need to construct from
+ // can exploit the |nsCOMPtr_helper| facility
+ {
+ NSCAP_LOG_ASSIGNMENT(this, 0);
+ assign_from_helper(helper, NS_GET_IID(nsISupports));
+ }
+
+
+ // Assignment operators
+
+ nsCOMPtr<nsISupports>&
+ operator=( const nsCOMPtr<nsISupports>& rhs )
+ // copy assignment operator
+ {
+ assign_with_AddRef(rhs.mRawPtr);
+ return *this;
+ }
+
+ nsCOMPtr<nsISupports>&
+ operator=( nsISupports* rhs )
+ // assign from a raw pointer (of the right type)
+ {
+ assign_with_AddRef(rhs);
+ return *this;
+ }
+
+ nsCOMPtr<nsISupports>&
+ operator=( const already_AddRefed<nsISupports>& rhs )
+ // assign from |dont_AddRef(expr)|
+ {
+ assign_assuming_AddRef(rhs.mRawPtr);
+ return *this;
+ }
+
+ nsCOMPtr<nsISupports>&
+ operator=( const nsQueryInterface rhs )
+ // assign from |do_QueryInterface(expr)|
+ {
+ assign_from_qi(rhs, NS_GET_IID(nsISupports));
+ return *this;
+ }
+
+ nsCOMPtr<nsISupports>&
+ operator=( const nsQueryInterfaceWithError& rhs )
+ // assign from |do_QueryInterface(expr, &rv)|
+ {
+ assign_from_qi_with_error(rhs, NS_GET_IID(nsISupports));
+ return *this;
+ }
+
+ nsCOMPtr<nsISupports>&
+ operator=( const nsCOMPtr_helper& rhs )
+ // ...and finally, anything else we might need to assign from
+ // can exploit the |nsCOMPtr_helper| facility.
+ {
+ assign_from_helper(rhs, NS_GET_IID(nsISupports));
+ return *this;
+ }
+
+ void
+ swap( nsCOMPtr<nsISupports>& rhs )
+ // ...exchange ownership with |rhs|; can save a pair of refcount operations
+ {
+ nsISupports* temp = rhs.mRawPtr;
+ NSCAP_LOG_ASSIGNMENT(&rhs, mRawPtr);
+ NSCAP_LOG_ASSIGNMENT(this, temp);
+ NSCAP_LOG_RELEASE(this, mRawPtr);
+ NSCAP_LOG_RELEASE(&rhs, temp);
+ rhs.mRawPtr = mRawPtr;
+ mRawPtr = temp;
+ }
+
+ void
+ swap( nsISupports*& rhs )
+ // ...exchange ownership with |rhs|; can save a pair of refcount operations
+ {
+ nsISupports* temp = rhs;
+ NSCAP_LOG_ASSIGNMENT(this, temp);
+ NSCAP_LOG_RELEASE(this, mRawPtr);
+ rhs = mRawPtr;
+ mRawPtr = temp;
+ }
+
+
+ // Other pointer operators
+
+ nsDerivedSafe<nsISupports>*
+ get() const
+ /*
+ Prefer the implicit conversion provided automatically by |operator nsDerivedSafe<nsISupports>*() const|.
+ Use |get()| _only_ to resolve ambiguity.
+
+ Returns a |nsDerivedSafe<nsISupports>*| to deny clients the use of |AddRef| and |Release|.
+ */
+ {
+ return NS_REINTERPRET_CAST(nsDerivedSafe<nsISupports>*, mRawPtr);
+ }
+
+ operator nsDerivedSafe<nsISupports>*() const
+ /*
+ ...makes an |nsCOMPtr| act like its underlying raw pointer type (except against |AddRef()|, |Release()|,
+ and |delete|) whenever it is used in a context where a raw pointer is expected. It is this operator
+ that makes an |nsCOMPtr| substitutable for a raw pointer.
+
+ Prefer the implicit use of this operator to calling |get()|, except where necessary to resolve ambiguity.
+ */
+ {
+ return get();
+ }
+
+ nsDerivedSafe<nsISupports>*
+ operator->() const
+ {
+ NS_PRECONDITION(mRawPtr != 0, "You can't dereference a NULL nsCOMPtr with operator->().");
+ return get();
+ }
+
+#ifdef CANT_RESOLVE_CPP_CONST_AMBIGUITY
+ // broken version for IRIX
+
+ nsCOMPtr<nsISupports>*
+ get_address() const
+ // This is not intended to be used by clients. See |address_of|
+ // below.
+ {
+ return NS_CONST_CAST(nsCOMPtr<nsISupports>*, this);
+ }
+
+#else // CANT_RESOLVE_CPP_CONST_AMBIGUITY
+
+ nsCOMPtr<nsISupports>*
+ get_address()
+ // This is not intended to be used by clients. See |address_of|
+ // below.
+ {
+ return this;
+ }
+
+ const nsCOMPtr<nsISupports>*
+ get_address() const
+ // This is not intended to be used by clients. See |address_of|
+ // below.
+ {
+ return this;
+ }
+
+#endif // CANT_RESOLVE_CPP_CONST_AMBIGUITY
+
+ public:
+
+ nsDerivedSafe<nsISupports>&
+ operator*() const
+ {
+ NS_PRECONDITION(mRawPtr != 0, "You can't dereference a NULL nsCOMPtr with operator*().");
+ return *get();
+ }
+
+#if 0
+ private:
+ friend class nsGetterAddRefs<nsISupports>;
+#endif
+
+ nsISupports**
+ StartAssignment()
+ {
+#ifndef NSCAP_FEATURE_INLINE_STARTASSIGNMENT
+ return NS_REINTERPRET_CAST(nsISupports**, begin_assignment());
+#else
+ assign_assuming_AddRef(0);
+ return NS_REINTERPRET_CAST(nsISupports**, &mRawPtr);
+#endif
+ }
+ };
+
+#ifndef NSCAP_FEATURE_USE_BASE
+template <class T>
+void
+nsCOMPtr<T>::assign_with_AddRef( nsISupports* rawPtr )
+ {
+ if ( rawPtr )
+ NSCAP_ADDREF(this, rawPtr);
+ assign_assuming_AddRef(NS_REINTERPRET_CAST(T*, rawPtr));
+ }
+
+template <class T>
+void
+nsCOMPtr<T>::assign_from_qi( const nsQueryInterface qi, const nsIID& aIID )
+ {
+ T* newRawPtr;
+ if ( NS_FAILED( qi(aIID, NS_REINTERPRET_CAST(void**, &newRawPtr)) ) )
+ newRawPtr = 0;
+ assign_assuming_AddRef(newRawPtr);
+ }
+
+template <class T>
+void
+nsCOMPtr<T>::assign_from_qi_with_error( const nsQueryInterfaceWithError& qi, const nsIID& aIID )
+ {
+ T* newRawPtr;
+ if ( NS_FAILED( qi(aIID, NS_REINTERPRET_CAST(void**, &newRawPtr)) ) )
+ newRawPtr = 0;
+ assign_assuming_AddRef(newRawPtr);
+ }
+
+template <class T>
+void
+nsCOMPtr<T>::assign_from_helper( const nsCOMPtr_helper& helper, const nsIID& aIID )
+ {
+ T* newRawPtr;
+ if ( NS_FAILED( helper(aIID, NS_REINTERPRET_CAST(void**, &newRawPtr)) ) )
+ newRawPtr = 0;
+ assign_assuming_AddRef(newRawPtr);
+ }
+
+template <class T>
+void**
+nsCOMPtr<T>::begin_assignment()
+ {
+ assign_assuming_AddRef(0);
+ return NS_REINTERPRET_CAST(void**, &mRawPtr);
+ }
+#endif
+
+#ifdef CANT_RESOLVE_CPP_CONST_AMBIGUITY
+
+// This is the broken version for IRIX, which can't handle the version below.
+
+template <class T>
+inline
+nsCOMPtr<T>*
+address_of( const nsCOMPtr<T>& aPtr )
+ {
+ return aPtr.get_address();
+ }
+
+#else // CANT_RESOLVE_CPP_CONST_AMBIGUITY
+
+template <class T>
+inline
+nsCOMPtr<T>*
+address_of( nsCOMPtr<T>& aPtr )
+ {
+ return aPtr.get_address();
+ }
+
+template <class T>
+inline
+const nsCOMPtr<T>*
+address_of( const nsCOMPtr<T>& aPtr )
+ {
+ return aPtr.get_address();
+ }
+
+#endif // CANT_RESOLVE_CPP_CONST_AMBIGUITY
+
+template <class T>
+class nsGetterAddRefs
+ /*
+ ...
+
+ This class is designed to be used for anonymous temporary objects in the
+ argument list of calls that return COM interface pointers, e.g.,
+
+ nsCOMPtr<IFoo> fooP;
+ ...->QueryInterface(iid, getter_AddRefs(fooP))
+
+ DO NOT USE THIS TYPE DIRECTLY IN YOUR CODE. Use |getter_AddRefs()| instead.
+
+ When initialized with a |nsCOMPtr|, as in the example above, it returns
+ a |void**|, a |T**|, or an |nsISupports**| as needed, that the outer call (|QueryInterface| in this
+ case) can fill in.
+
+ This type should be a nested class inside |nsCOMPtr<T>|.
+ */
+ {
+ public:
+ explicit
+ nsGetterAddRefs( nsCOMPtr<T>& aSmartPtr )
+ : mTargetSmartPtr(aSmartPtr)
+ {
+ // nothing else to do
+ }
+
+#if defined(NSCAP_FEATURE_TEST_DONTQUERY_CASES) || defined(NSCAP_LOG_EXTERNAL_ASSIGNMENT)
+ ~nsGetterAddRefs()
+ {
+#ifdef NSCAP_LOG_EXTERNAL_ASSIGNMENT
+ NSCAP_LOG_ASSIGNMENT(NS_REINTERPRET_CAST(void *, address_of(mTargetSmartPtr)), mTargetSmartPtr.get());
+#endif
+
+#ifdef NSCAP_FEATURE_TEST_DONTQUERY_CASES
+ mTargetSmartPtr.Assert_NoQueryNeeded();
+#endif
+ }
+#endif
+
+ operator void**()
+ {
+ return NS_REINTERPRET_CAST(void**, mTargetSmartPtr.StartAssignment());
+ }
+
+ operator nsISupports**()
+ {
+ return NS_REINTERPRET_CAST(nsISupports**, mTargetSmartPtr.StartAssignment());
+ }
+
+ operator T**()
+ {
+ return mTargetSmartPtr.StartAssignment();
+ }
+
+ T*&
+ operator*()
+ {
+ return *(mTargetSmartPtr.StartAssignment());
+ }
+
+ private:
+ nsCOMPtr<T>& mTargetSmartPtr;
+ };
+
+
+NS_SPECIALIZE_TEMPLATE
+class nsGetterAddRefs<nsISupports>
+ {
+ public:
+ explicit
+ nsGetterAddRefs( nsCOMPtr<nsISupports>& aSmartPtr )
+ : mTargetSmartPtr(aSmartPtr)
+ {
+ // nothing else to do
+ }
+
+#ifdef NSCAP_LOG_EXTERNAL_ASSIGNMENT
+ ~nsGetterAddRefs()
+ {
+ NSCAP_LOG_ASSIGNMENT(NS_REINTERPRET_CAST(void *, address_of(mTargetSmartPtr)), mTargetSmartPtr.get());
+ }
+#endif
+
+ operator void**()
+ {
+ return NS_REINTERPRET_CAST(void**, mTargetSmartPtr.StartAssignment());
+ }
+
+ operator nsISupports**()
+ {
+ return mTargetSmartPtr.StartAssignment();
+ }
+
+ nsISupports*&
+ operator*()
+ {
+ return *(mTargetSmartPtr.StartAssignment());
+ }
+
+ private:
+ nsCOMPtr<nsISupports>& mTargetSmartPtr;
+ };
+
+
+template <class T>
+inline
+nsGetterAddRefs<T>
+getter_AddRefs( nsCOMPtr<T>& aSmartPtr )
+ /*
+ Used around a |nsCOMPtr| when
+ ...makes the class |nsGetterAddRefs<T>| invisible.
+ */
+ {
+ return nsGetterAddRefs<T>(aSmartPtr);
+ }
+
+
+
+ // Comparing two |nsCOMPtr|s
+
+template <class T, class U>
+inline
+NSCAP_BOOL
+operator==( const nsCOMPtr<T>& lhs, const nsCOMPtr<U>& rhs )
+ {
+ return NS_STATIC_CAST(const T*, lhs.get()) == NS_STATIC_CAST(const U*, rhs.get());
+ }
+
+
+template <class T, class U>
+inline
+NSCAP_BOOL
+operator!=( const nsCOMPtr<T>& lhs, const nsCOMPtr<U>& rhs )
+ {
+ return NS_STATIC_CAST(const T*, lhs.get()) != NS_STATIC_CAST(const U*, rhs.get());
+ }
+
+
+ // Comparing an |nsCOMPtr| to a raw pointer
+
+template <class T, class U>
+inline
+NSCAP_BOOL
+operator==( const nsCOMPtr<T>& lhs, const U* rhs )
+ {
+ return NS_STATIC_CAST(const T*, lhs.get()) == rhs;
+ }
+
+template <class T, class U>
+inline
+NSCAP_BOOL
+operator==( const U* lhs, const nsCOMPtr<T>& rhs )
+ {
+ return lhs == NS_STATIC_CAST(const T*, rhs.get());
+ }
+
+template <class T, class U>
+inline
+NSCAP_BOOL
+operator!=( const nsCOMPtr<T>& lhs, const U* rhs )
+ {
+ return NS_STATIC_CAST(const T*, lhs.get()) != rhs;
+ }
+
+template <class T, class U>
+inline
+NSCAP_BOOL
+operator!=( const U* lhs, const nsCOMPtr<T>& rhs )
+ {
+ return lhs != NS_STATIC_CAST(const T*, rhs.get());
+ }
+
+ // To avoid ambiguities caused by the presence of builtin |operator==|s
+ // creating a situation where one of the |operator==| defined above
+ // has a better conversion for one argument and the builtin has a
+ // better conversion for the other argument, define additional
+ // |operator==| without the |const| on the raw pointer.
+ // See bug 65664 for details.
+
+// This is defined by an autoconf test, but VC++ also has a bug that
+// prevents us from using these. (It also, fortunately, has the bug
+// that we don't need them either.)
+#if defined(_MSC_VER) && (_MSC_VER < 1310)
+#define NSCAP_DONT_PROVIDE_NONCONST_OPEQ
+#endif
+
+#ifndef NSCAP_DONT_PROVIDE_NONCONST_OPEQ
+template <class T, class U>
+inline
+NSCAP_BOOL
+operator==( const nsCOMPtr<T>& lhs, U* rhs )
+ {
+ return NS_STATIC_CAST(const T*, lhs.get()) == NS_CONST_CAST(const U*, rhs);
+ }
+
+template <class T, class U>
+inline
+NSCAP_BOOL
+operator==( U* lhs, const nsCOMPtr<T>& rhs )
+ {
+ return NS_CONST_CAST(const U*, lhs) == NS_STATIC_CAST(const T*, rhs.get());
+ }
+
+template <class T, class U>
+inline
+NSCAP_BOOL
+operator!=( const nsCOMPtr<T>& lhs, U* rhs )
+ {
+ return NS_STATIC_CAST(const T*, lhs.get()) != NS_CONST_CAST(const U*, rhs);
+ }
+
+template <class T, class U>
+inline
+NSCAP_BOOL
+operator!=( U* lhs, const nsCOMPtr<T>& rhs )
+ {
+ return NS_CONST_CAST(const U*, lhs) != NS_STATIC_CAST(const T*, rhs.get());
+ }
+#endif
+
+
+
+ // Comparing an |nsCOMPtr| to |0|
+
+class NSCAP_Zero;
+
+template <class T>
+inline
+NSCAP_BOOL
+operator==( const nsCOMPtr<T>& lhs, NSCAP_Zero* rhs )
+ // specifically to allow |smartPtr == 0|
+ {
+ return NS_STATIC_CAST(const void*, lhs.get()) == NS_REINTERPRET_CAST(const void*, rhs);
+ }
+
+template <class T>
+inline
+NSCAP_BOOL
+operator==( NSCAP_Zero* lhs, const nsCOMPtr<T>& rhs )
+ // specifically to allow |0 == smartPtr|
+ {
+ return NS_REINTERPRET_CAST(const void*, lhs) == NS_STATIC_CAST(const void*, rhs.get());
+ }
+
+template <class T>
+inline
+NSCAP_BOOL
+operator!=( const nsCOMPtr<T>& lhs, NSCAP_Zero* rhs )
+ // specifically to allow |smartPtr != 0|
+ {
+ return NS_STATIC_CAST(const void*, lhs.get()) != NS_REINTERPRET_CAST(const void*, rhs);
+ }
+
+template <class T>
+inline
+NSCAP_BOOL
+operator!=( NSCAP_Zero* lhs, const nsCOMPtr<T>& rhs )
+ // specifically to allow |0 != smartPtr|
+ {
+ return NS_REINTERPRET_CAST(const void*, lhs) != NS_STATIC_CAST(const void*, rhs.get());
+ }
+
+
+#ifdef HAVE_CPP_TROUBLE_COMPARING_TO_ZERO
+
+ // We need to explicitly define comparison operators for `int'
+ // because the compiler is lame.
+
+template <class T>
+inline
+NSCAP_BOOL
+operator==( const nsCOMPtr<T>& lhs, int rhs )
+ // specifically to allow |smartPtr == 0|
+ {
+ return NS_STATIC_CAST(const void*, lhs.get()) == NS_REINTERPRET_CAST(const void*, rhs);
+ }
+
+template <class T>
+inline
+NSCAP_BOOL
+operator==( int lhs, const nsCOMPtr<T>& rhs )
+ // specifically to allow |0 == smartPtr|
+ {
+ return NS_REINTERPRET_CAST(const void*, lhs) == NS_STATIC_CAST(const void*, rhs.get());
+ }
+
+#endif // !defined(HAVE_CPP_TROUBLE_COMPARING_TO_ZERO)
+
+ // Comparing any two [XP]COM objects for identity
+
+inline
+NSCAP_BOOL
+SameCOMIdentity( nsISupports* lhs, nsISupports* rhs )
+ {
+ return nsCOMPtr<nsISupports>( do_QueryInterface(lhs) ) == nsCOMPtr<nsISupports>( do_QueryInterface(rhs) );
+ }
+
+
+
+template <class SourceType, class DestinationType>
+inline
+nsresult
+CallQueryInterface( nsCOMPtr<SourceType>& aSourcePtr, DestinationType** aDestPtr )
+ {
+ return CallQueryInterface(aSourcePtr.get(), aDestPtr);
+ }
+
+#endif // !defined(nsCOMPtr_h___)
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsComponentManagerUtils.cpp b/src/libs/xpcom18a4/xpcom/glue/nsComponentManagerUtils.cpp
new file mode 100644
index 00000000..5733fc36
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsComponentManagerUtils.cpp
@@ -0,0 +1,133 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#ifndef nsXPCOM_h__
+#include "nsXPCOM.h"
+#endif
+
+#ifndef nsCOMPtr_h__
+#include "nsCOMPtr.h"
+#endif
+
+#include "nsComponentManagerUtils.h"
+#include "nsIServiceManagerUtils.h"
+
+nsresult
+nsCreateInstanceByCID::operator()( const nsIID& aIID, void** aInstancePtr ) const
+{
+ nsCOMPtr<nsIComponentManager> compMgr;
+ nsresult status = NS_GetComponentManager(getter_AddRefs(compMgr));
+ if (compMgr)
+ status = compMgr->CreateInstance(mCID, mOuter, aIID, aInstancePtr);
+ else if (NS_SUCCEEDED(status))
+ status = NS_ERROR_UNEXPECTED;
+
+ if ( NS_FAILED(status) )
+ *aInstancePtr = 0;
+
+ if ( mErrorPtr )
+ *mErrorPtr = status;
+ return status;
+}
+
+nsresult
+nsCreateInstanceByContractID::operator()( const nsIID& aIID, void** aInstancePtr ) const
+{
+ nsresult status;
+ if ( mContractID ) {
+ nsCOMPtr<nsIComponentManager> compMgr;
+ status = NS_GetComponentManager(getter_AddRefs(compMgr));
+ if (compMgr)
+ status = compMgr->CreateInstanceByContractID(mContractID, mOuter,
+ aIID, aInstancePtr);
+ else if (NS_SUCCEEDED(status))
+ status = NS_ERROR_UNEXPECTED;
+ }
+ else
+ status = NS_ERROR_NULL_POINTER;
+
+ if (NS_FAILED(status))
+ *aInstancePtr = 0;
+ if ( mErrorPtr )
+ *mErrorPtr = status;
+ return status;
+}
+
+
+nsresult
+nsGetServiceByCID::operator()( const nsIID& aIID, void** aInstancePtr ) const
+{
+ nsresult status = NS_ERROR_FAILURE;
+ if ( mServiceManager ) {
+ status = mServiceManager->GetService(mCID, aIID, (void**)aInstancePtr);
+ } else {
+ nsCOMPtr<nsIServiceManager> mgr;
+ NS_GetServiceManager(getter_AddRefs(mgr));
+ if (mgr)
+ status = mgr->GetService(mCID, aIID, (void**)aInstancePtr);
+ }
+ if ( NS_FAILED(status) )
+ *aInstancePtr = 0;
+
+ if ( mErrorPtr )
+ *mErrorPtr = status;
+ return status;
+}
+
+nsresult
+nsGetServiceByContractID::operator()( const nsIID& aIID, void** aInstancePtr ) const
+{
+ nsresult status = NS_ERROR_FAILURE;
+ if ( mServiceManager ) {
+ status = mServiceManager->GetServiceByContractID(mContractID, aIID, (void**)aInstancePtr);
+ } else {
+ nsCOMPtr<nsIServiceManager> mgr;
+ NS_GetServiceManager(getter_AddRefs(mgr));
+ if (mgr)
+ status = mgr->GetServiceByContractID(mContractID, aIID, (void**)aInstancePtr);
+ }
+
+ if ( NS_FAILED(status) )
+ *aInstancePtr = 0;
+
+ if ( mErrorPtr )
+ *mErrorPtr = status;
+ return status;
+}
+
+
+
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsDebug.cpp b/src/libs/xpcom18a4/xpcom/glue/nsDebug.cpp
new file mode 100644
index 00000000..9e947f30
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsDebug.cpp
@@ -0,0 +1,119 @@
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is XPCOM
+ *
+ * The Initial Developer of the Original Code is Doug Turner <dougt@meer.net>
+ *
+ * Portions created by the Initial Developer are Copyright (C) 2003
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either the GNU General Public License Version 2 or later (the "GPL"), or
+ * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#include "nsXPCOM.h"
+#include "nsXPCOMPrivate.h"
+#include "nsCOMPtr.h"
+#include "nsIServiceManager.h"
+#include "nsDebug.h"
+#include "nsDebugImpl.h"
+
+static nsIDebug* gDebugObject = nsnull;
+
+// Note: Although the machinery here is similar to nsMemory.cpp, we cannot use
+// NS_ASSERTION macros below because they end up in nsDebug::Assertion and
+// therefore may produce endless recursion.
+
+static NS_METHOD FreeDebugObject(void)
+{
+ NS_IF_RELEASE(gDebugObject);
+ return NS_OK;
+}
+
+#define ENSURE_DEBUGOBJECT \
+ (gDebugObject ? PR_TRUE : (PRBool)(SetupDebugObject() != nsnull))
+
+static nsIDebug* SetupDebugObject()
+{
+ if (!gDebugObject)
+ {
+ NS_GetDebug(&gDebugObject);
+ if (gDebugObject)
+ NS_RegisterXPCOMExitRoutine(FreeDebugObject, 0);
+ }
+ return gDebugObject;
+}
+
+#ifdef XPCOM_GLUE
+nsresult GlueStartupDebug()
+{
+ if (!gDebugObject)
+ {
+ NS_GetDebug(&gDebugObject);
+ if (!gDebugObject)
+ return NS_ERROR_FAILURE;
+ }
+ return NS_OK;
+}
+
+void GlueShutdownDebug()
+{
+ NS_IF_RELEASE(gDebugObject);
+}
+#endif
+
+NS_COM void nsDebug::Abort(const char* aFile, PRIntn aLine)
+{
+ if (!ENSURE_DEBUGOBJECT)
+ return;
+
+ gDebugObject->Abort(aFile, aLine);
+}
+
+NS_COM void nsDebug::Break(const char* aFile, PRIntn aLine)
+{
+ if (!ENSURE_DEBUGOBJECT)
+ return;
+
+ gDebugObject->Break(aFile, aLine);
+}
+
+NS_COM void nsDebug::Warning(const char* aStr,
+ const char* aFile,
+ PRIntn aLine)
+{
+ if (!ENSURE_DEBUGOBJECT)
+ return;
+ gDebugObject->Warning(aStr, aFile, aLine);
+}
+
+NS_COM void nsDebug::Assertion(const char* aStr, const char* aExpr,
+ const char* aFile, PRIntn aLine)
+{
+ if (!ENSURE_DEBUGOBJECT)
+ return;
+ gDebugObject->Assertion(aStr, aExpr, aFile, aLine);
+}
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsDebug.h b/src/libs/xpcom18a4/xpcom/glue/nsDebug.h
new file mode 100644
index 00000000..f2ed4c56
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsDebug.h
@@ -0,0 +1,276 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#ifndef nsDebug_h___
+#define nsDebug_h___
+
+#ifndef nscore_h___
+#include "nscore.h"
+#endif
+
+#ifndef nsError_h__
+#include "nsError.h"
+#endif
+
+#ifdef DEBUG
+#define NS_DEBUG
+#endif
+
+/**
+ * Namespace for debugging methods. Note that your code must use the
+ * macros defined later in this file so that the debug code can be
+ * conditionally compiled out.
+ */
+
+/* in case this is included by a C file */
+#ifdef __cplusplus
+
+class nsDebug {
+public:
+
+ /**
+ * Log a warning message to the debug log.
+ */
+ static NS_COM void Warning(const char* aMessage,
+ const char* aFile, PRIntn aLine);
+
+ /**
+ * Abort the executing program. This works on all architectures.
+ */
+ static NS_COM void Abort(const char* aFile, PRIntn aLine);
+
+ /**
+ * Break the executing program into the debugger.
+ */
+ static NS_COM void Break(const char* aFile, PRIntn aLine);
+
+ /**
+ * Log an assertion message to the debug log
+ */
+ static NS_COM void Assertion(const char* aStr, const char* aExpr,
+ const char* aFile, PRIntn aLine);
+};
+
+#ifdef DEBUG
+
+/**
+ * Abort the execution of the program if the expression evaluates to
+ * false.
+ *
+ * There is no status value returned from the macro.
+ *
+ * Note that the non-debug version of this macro does <b>not</b>
+ * evaluate the expression argument. Hence side effect statements
+ * as arguments to the macro will yield improper execution in a
+ * non-debug build. For example:
+ *
+ * NS_ABORT_IF_FALSE(0 == foo++, "yikes foo should be zero");
+ *
+ * Note also that the non-debug version of this macro does <b>not</b>
+ * evaluate the message argument.
+ */
+#define NS_ABORT_IF_FALSE(_expr, _msg) \
+ PR_BEGIN_MACRO \
+ if (!(_expr)) { \
+ nsDebug::Assertion(_msg, #_expr, __FILE__, __LINE__); \
+ } \
+ PR_END_MACRO
+
+/**
+ * Warn if a given condition is false.
+ *
+ * Program execution continues past the usage of this macro.
+ *
+ * Note also that the non-debug version of this macro does <b>not</b>
+ * evaluate the message argument.
+ */
+#define NS_WARN_IF_FALSE(_expr,_msg) \
+ PR_BEGIN_MACRO \
+ if (!(_expr)) { \
+ nsDebug::Assertion(_msg, #_expr, __FILE__, __LINE__); \
+ } \
+ PR_END_MACRO
+
+/**
+ * Test a precondition for truth. If the expression is not true then
+ * trigger a program failure.
+ */
+#define NS_PRECONDITION(expr, str) \
+ PR_BEGIN_MACRO \
+ if (!(expr)) { \
+ nsDebug::Assertion(str, #expr, __FILE__, __LINE__); \
+ } \
+ PR_END_MACRO
+
+/**
+ * Test an assertion for truth. If the expression is not true then
+ * trigger a program failure.
+ */
+#define NS_ASSERTION(expr, str) \
+ PR_BEGIN_MACRO \
+ if (!(expr)) { \
+ nsDebug::Assertion(str, #expr, __FILE__, __LINE__); \
+ } \
+ PR_END_MACRO
+
+/**
+ * Test a post-condition for truth. If the expression is not true then
+ * trigger a program failure.
+ */
+#define NS_POSTCONDITION(expr, str) \
+ PR_BEGIN_MACRO \
+ if (!(expr)) { \
+ nsDebug::Assertion(str, #expr, __FILE__, __LINE__); \
+ } \
+ PR_END_MACRO
+
+/**
+ * This macros triggers a program failure if executed. It indicates that
+ * an attempt was made to execute some unimplimented functionality.
+ */
+#define NS_NOTYETIMPLEMENTED(str) \
+ nsDebug::Assertion(str, "NotYetImplemented", __FILE__, __LINE__)
+
+/**
+ * This macros triggers a program failure if executed. It indicates that
+ * an attempt was made to execute some unimplimented functionality.
+ */
+#define NS_NOTREACHED(str) \
+ nsDebug::Assertion(str, "Not Reached", __FILE__, __LINE__)
+
+/**
+ * Log an error message.
+ */
+#define NS_ERROR(str) \
+ nsDebug::Assertion(str, "Error", __FILE__, __LINE__)
+
+/**
+ * Log a warning message.
+ */
+#define NS_WARNING(str) \
+ nsDebug::Warning(str, __FILE__, __LINE__)
+
+/**
+ * Trigger an abort
+ */
+#define NS_ABORT() \
+ nsDebug::Abort(__FILE__, __LINE__)
+
+/**
+ * Cause a break
+ */
+#define NS_BREAK() \
+ nsDebug::Break(__FILE__, __LINE__)
+
+#else /* NS_DEBUG */
+
+/**
+ * The non-debug version of these macros do not evaluate the
+ * expression or the message arguments to the macro.
+ */
+#define NS_ABORT_IF_FALSE(_expr, _msg) /* nothing */
+#define NS_WARN_IF_FALSE(_expr, _msg) /* nothing */
+#define NS_PRECONDITION(expr, str) /* nothing */
+#define NS_ASSERTION(expr, str) /* nothing */
+#define NS_POSTCONDITION(expr, str) /* nothing */
+#define NS_NOTYETIMPLEMENTED(str) /* nothing */
+#define NS_NOTREACHED(str) /* nothing */
+#define NS_ERROR(str) /* nothing */
+#define NS_WARNING(str) /* nothing */
+#define NS_ABORT() /* nothing */
+#define NS_BREAK() /* nothing */
+
+#endif /* ! NS_DEBUG */
+#endif /* __cplusplus */
+
+// Macros for checking the trueness of an expression passed in within an
+// interface implementation. These need to be compiled regardless of the
+// NS_DEBUG flag
+///////////////////////////////////////////////////////////////////////////////
+
+#define NS_ENSURE_TRUE(x, ret) \
+ PR_BEGIN_MACRO \
+ if (NS_UNLIKELY(!(x))) { \
+ NS_WARNING("NS_ENSURE_TRUE(" #x ") failed"); \
+ return ret; \
+ } \
+ PR_END_MACRO
+
+#define NS_ENSURE_FALSE(x, ret) \
+ NS_ENSURE_TRUE(!(x), ret)
+
+///////////////////////////////////////////////////////////////////////////////
+// Macros for checking results
+///////////////////////////////////////////////////////////////////////////////
+
+#define NS_ENSURE_SUCCESS(res, ret) \
+ NS_ENSURE_TRUE(NS_SUCCEEDED(res), ret)
+
+///////////////////////////////////////////////////////////////////////////////
+// Macros for checking state and arguments upon entering interface boundaries
+///////////////////////////////////////////////////////////////////////////////
+
+#define NS_ENSURE_ARG(arg) \
+ NS_ENSURE_TRUE(arg, NS_ERROR_INVALID_ARG)
+
+#define NS_ENSURE_ARG_POINTER(arg) \
+ NS_ENSURE_TRUE(arg, NS_ERROR_INVALID_POINTER)
+
+#define NS_ENSURE_ARG_MIN(arg, min) \
+ NS_ENSURE_TRUE((arg) >= min, NS_ERROR_INVALID_ARG)
+
+#define NS_ENSURE_ARG_MAX(arg, max) \
+ NS_ENSURE_TRUE((arg) <= max, NS_ERROR_INVALID_ARG)
+
+#define NS_ENSURE_ARG_RANGE(arg, min, max) \
+ NS_ENSURE_TRUE(((arg) >= min) && ((arg) <= max), NS_ERROR_INVALID_ARG)
+
+#define NS_ENSURE_STATE(state) \
+ NS_ENSURE_TRUE(state, NS_ERROR_UNEXPECTED)
+
+#define NS_ENSURE_NO_AGGREGATION(outer) \
+ NS_ENSURE_FALSE(outer, NS_ERROR_NO_AGGREGATION)
+
+#define NS_ENSURE_PROPER_AGGREGATION(outer, iid) \
+ NS_ENSURE_FALSE(outer && !iid.Equals(NS_GET_IID(nsISupports)), NS_ERROR_INVALID_ARG)
+
+///////////////////////////////////////////////////////////////////////////////
+
+#define NS_CheckThreadSafe(owningThread, msg) \
+ NS_ASSERTION(owningThread == PR_GetCurrentThread(), msg)
+
+#endif /* nsDebug_h___ */
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsGenericFactory.cpp b/src/libs/xpcom18a4/xpcom/glue/nsGenericFactory.cpp
new file mode 100644
index 00000000..2d791943
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsGenericFactory.cpp
@@ -0,0 +1,547 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ * Pierre Phaneuf <pp@ludusdesign.com>
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+
+// DO NOT COPY THIS CODE INTO YOUR SOURCE! USE NS_IMPL_NSGETMODULE()
+
+#include "nsGenericFactory.h"
+#include "nsMemory.h"
+#include "nsCOMPtr.h"
+#include "nsIComponentManager.h"
+#include "nsIComponentRegistrar.h"
+
+#ifdef XPCOM_GLUE
+#include "nsXPCOMGlue.h"
+#include "nsXPCOMPrivate.h"
+#else
+#include "nsIInterfaceRequestorUtils.h"
+#include "nsINativeComponentLoader.h"
+#endif
+
+nsGenericFactory::nsGenericFactory(const nsModuleComponentInfo *info)
+ : mInfo(info)
+{
+ if (mInfo && mInfo->mClassInfoGlobal)
+ *mInfo->mClassInfoGlobal = NS_STATIC_CAST(nsIClassInfo *, this);
+}
+
+nsGenericFactory::~nsGenericFactory()
+{
+ if (mInfo) {
+ if (mInfo->mFactoryDestructor)
+ mInfo->mFactoryDestructor();
+ if (mInfo->mClassInfoGlobal)
+ *mInfo->mClassInfoGlobal = 0;
+ }
+}
+
+NS_IMPL_THREADSAFE_ISUPPORTS3(nsGenericFactory,
+ nsIGenericFactory,
+ nsIFactory,
+ nsIClassInfo)
+
+NS_IMETHODIMP nsGenericFactory::CreateInstance(nsISupports *aOuter,
+ REFNSIID aIID, void **aResult)
+{
+ if (mInfo->mConstructor) {
+ return mInfo->mConstructor(aOuter, aIID, aResult);
+ }
+
+ return NS_ERROR_FACTORY_NOT_REGISTERED;
+}
+
+NS_IMETHODIMP nsGenericFactory::LockFactory(PRBool aLock)
+{
+ // XXX do we care if (mInfo->mFlags & THREADSAFE)?
+ return NS_OK;
+}
+
+NS_IMETHODIMP nsGenericFactory::GetInterfaces(PRUint32 *countp,
+ nsIID* **array)
+{
+ if (!mInfo->mGetInterfacesProc) {
+ *countp = 0;
+ *array = nsnull;
+ return NS_OK;
+ }
+ return mInfo->mGetInterfacesProc(countp, array);
+}
+
+NS_IMETHODIMP nsGenericFactory::GetHelperForLanguage(PRUint32 language,
+ nsISupports **helper)
+{
+ if (mInfo->mGetLanguageHelperProc)
+ return mInfo->mGetLanguageHelperProc(language, helper);
+ *helper = nsnull;
+ return NS_OK;
+}
+
+NS_IMETHODIMP nsGenericFactory::GetContractID(char **aContractID)
+{
+ if (mInfo->mContractID) {
+ *aContractID = (char *)nsMemory::Alloc(strlen(mInfo->mContractID) + 1);
+ if (!*aContractID)
+ return NS_ERROR_OUT_OF_MEMORY;
+ strcpy(*aContractID, mInfo->mContractID);
+ } else {
+ *aContractID = nsnull;
+ }
+ return NS_OK;
+}
+
+NS_IMETHODIMP nsGenericFactory::GetClassDescription(char * *aClassDescription)
+{
+ if (mInfo->mDescription) {
+ *aClassDescription = (char *)
+ nsMemory::Alloc(strlen(mInfo->mDescription) + 1);
+ if (!*aClassDescription)
+ return NS_ERROR_OUT_OF_MEMORY;
+ strcpy(*aClassDescription, mInfo->mDescription);
+ } else {
+ *aClassDescription = nsnull;
+ }
+ return NS_OK;
+}
+
+NS_IMETHODIMP nsGenericFactory::GetClassID(nsCID * *aClassID)
+{
+ *aClassID =
+ NS_REINTERPRET_CAST(nsCID*,
+ nsMemory::Clone(&mInfo->mCID, sizeof mInfo->mCID));
+ if (! *aClassID)
+ return NS_ERROR_OUT_OF_MEMORY;
+ return NS_OK;
+}
+
+NS_IMETHODIMP nsGenericFactory::GetClassIDNoAlloc(nsCID *aClassID)
+{
+ *aClassID = mInfo->mCID;
+ return NS_OK;
+}
+
+NS_IMETHODIMP nsGenericFactory::GetImplementationLanguage(PRUint32 *langp)
+{
+ *langp = nsIProgrammingLanguage::CPLUSPLUS;
+ return NS_OK;
+}
+
+NS_IMETHODIMP nsGenericFactory::GetFlags(PRUint32 *flagsp)
+{
+ *flagsp = mInfo->mFlags;
+ return NS_OK;
+}
+
+// nsIGenericFactory: component-info accessors
+NS_IMETHODIMP nsGenericFactory::SetComponentInfo(const nsModuleComponentInfo *info)
+{
+ if (mInfo && mInfo->mClassInfoGlobal)
+ *mInfo->mClassInfoGlobal = 0;
+ mInfo = info;
+ if (mInfo && mInfo->mClassInfoGlobal)
+ *mInfo->mClassInfoGlobal = NS_STATIC_CAST(nsIClassInfo *, this);
+ return NS_OK;
+}
+
+NS_IMETHODIMP nsGenericFactory::GetComponentInfo(const nsModuleComponentInfo **infop)
+{
+ *infop = mInfo;
+ return NS_OK;
+}
+
+NS_METHOD nsGenericFactory::Create(nsISupports* outer, const nsIID& aIID, void* *aInstancePtr)
+{
+ // sorry, aggregation not spoken here.
+ nsresult res = NS_ERROR_NO_AGGREGATION;
+ if (outer == NULL) {
+ nsGenericFactory* factory = new nsGenericFactory;
+ if (factory != NULL) {
+ res = factory->QueryInterface(aIID, aInstancePtr);
+ if (res != NS_OK)
+ delete factory;
+ } else {
+ res = NS_ERROR_OUT_OF_MEMORY;
+ }
+ }
+ return res;
+}
+
+NS_COM nsresult
+NS_NewGenericFactory(nsIGenericFactory* *result,
+ const nsModuleComponentInfo *info)
+{
+ nsresult rv;
+ nsIGenericFactory* fact;
+ rv = nsGenericFactory::Create(NULL, NS_GET_IID(nsIGenericFactory), (void**)&fact);
+ if (NS_FAILED(rv)) return rv;
+ rv = fact->SetComponentInfo(info);
+ if (NS_FAILED(rv)) goto error;
+ *result = fact;
+ return rv;
+
+ error:
+ NS_RELEASE(fact);
+ return rv;
+}
+
+////////////////////////////////////////////////////////////////////////////////
+
+nsGenericModule::nsGenericModule(const char* moduleName, PRUint32 componentCount,
+ const nsModuleComponentInfo* components,
+ nsModuleConstructorProc ctor,
+ nsModuleDestructorProc dtor,
+ const char** aLibDepends)
+ : mInitialized(PR_FALSE),
+ mModuleName(moduleName),
+ mComponentCount(componentCount),
+ mComponents(components),
+ mFactoriesNotToBeRegistered(nsnull),
+ mCtor(ctor),
+ mDtor(dtor),
+ mLibraryDependencies(aLibDepends)
+{
+}
+
+nsGenericModule::~nsGenericModule()
+{
+ Shutdown();
+
+#ifdef XPCOM_GLUE
+ XPCOMGlueShutdown();
+#endif
+
+}
+
+NS_IMPL_THREADSAFE_ISUPPORTS1(nsGenericModule, nsIModule)
+
+nsresult
+nsGenericModule::AddFactoryNode(nsIGenericFactory* fact)
+{
+ if (!fact)
+ return NS_ERROR_FAILURE;
+
+ FactoryNode *node = new FactoryNode(fact, mFactoriesNotToBeRegistered);
+ if (!node)
+ return NS_ERROR_OUT_OF_MEMORY;
+
+ mFactoriesNotToBeRegistered = node;
+ return NS_OK;
+}
+
+
+// Perform our one-time intialization for this module
+nsresult
+nsGenericModule::Initialize(nsIComponentManager *compMgr)
+{
+ nsresult rv;
+
+ if (mInitialized) {
+ return NS_OK;
+ }
+
+ if (mCtor) {
+ rv = mCtor(this);
+ if (NS_FAILED(rv))
+ return rv;
+ }
+
+
+#ifdef XPCOM_GLUE
+ rv = XPCOMGlueStartup(".");
+ if (NS_FAILED(rv))
+ return rv;
+#endif
+
+ nsCOMPtr<nsIComponentRegistrar> registrar = do_QueryInterface(compMgr, &rv);
+ if (NS_FAILED(rv))
+ return rv;
+
+ // Eagerly populate factory/class object hash for entries
+ // without constructors. If we didn't, the class object would
+ // never get created. Also create the factory, which doubles
+ // as the class object, if the EAGER_CLASSINFO flag was given.
+ // This allows objects to be created (within their modules)
+ // via operator new rather than CreateInstance, yet still be
+ // QI'able to nsIClassInfo.
+ const nsModuleComponentInfo* desc = mComponents;
+ for (PRUint32 i = 0; i < mComponentCount; i++) {
+ if (!desc->mConstructor ||
+ (desc->mFlags & nsIClassInfo::EAGER_CLASSINFO)) {
+ nsCOMPtr<nsIGenericFactory> fact;
+ nsresult rv = NS_NewGenericFactory(getter_AddRefs(fact), desc);
+ if (NS_FAILED(rv)) return rv;
+
+ // if we don't have a mConstructor, then we should not populate
+ // the component manager.
+ if (!desc->mConstructor) {
+ rv = AddFactoryNode(fact);
+ } else {
+ rv = registrar->RegisterFactory(desc->mCID,
+ desc->mDescription,
+ desc->mContractID,
+ fact);
+ }
+ if (NS_FAILED(rv)) return rv;
+ }
+ desc++;
+ }
+
+ mInitialized = PR_TRUE;
+ return NS_OK;
+}
+
+// Shutdown this module, releasing all of the module resources
+void
+nsGenericModule::Shutdown()
+{
+ // Free cached factories that were not registered.
+ FactoryNode* node;
+ while (mFactoriesNotToBeRegistered)
+ {
+ node = mFactoriesNotToBeRegistered->mNext;
+ delete mFactoriesNotToBeRegistered;
+ mFactoriesNotToBeRegistered = node;
+ }
+
+ if (mInitialized) {
+ mInitialized = PR_FALSE;
+
+ if (mDtor)
+ mDtor(this);
+ }
+}
+
+// Create a factory object for creating instances of aClass.
+NS_IMETHODIMP
+nsGenericModule::GetClassObject(nsIComponentManager *aCompMgr,
+ const nsCID& aClass,
+ const nsIID& aIID,
+ void** r_classObj)
+{
+ nsresult rv;
+
+ // Defensive programming: Initialize *r_classObj in case of error below
+ if (!r_classObj) {
+ return NS_ERROR_INVALID_POINTER;
+ }
+ *r_classObj = NULL;
+
+ // Do one-time-only initialization if necessary
+ if (!mInitialized) {
+ rv = Initialize(aCompMgr);
+ if (NS_FAILED(rv)) {
+ // Initialization failed! yikes!
+ return rv;
+ }
+ }
+
+ // Choose the appropriate factory, based on the desired instance
+ // class type (aClass).
+ const nsModuleComponentInfo* desc = mComponents;
+ for (PRUint32 i = 0; i < mComponentCount; i++) {
+ if (desc->mCID.Equals(aClass)) {
+ nsCOMPtr<nsIGenericFactory> fact;
+ rv = NS_NewGenericFactory(getter_AddRefs(fact), desc);
+ if (NS_FAILED(rv)) return rv;
+ return fact->QueryInterface(aIID, r_classObj);
+ }
+ desc++;
+ }
+ // not found in descriptions
+#ifndef XPCOM_GLUE
+#ifdef DEBUG
+ char* cs = aClass.ToString();
+ fprintf(stderr, "+++ nsGenericModule %s: unable to create factory for %s\n", mModuleName, cs);
+ // leak until we resolve the nsID Allocator.
+ // nsCRT::free(cs);
+#endif // XXX put in stop-gap so that we don't search for this one again
+#endif
+ return NS_ERROR_FACTORY_NOT_REGISTERED;
+}
+
+NS_IMETHODIMP
+nsGenericModule::RegisterSelf(nsIComponentManager *aCompMgr,
+ nsIFile* aPath,
+ const char* registryLocation,
+ const char* componentType)
+{
+ nsresult rv = NS_OK;
+
+#ifdef DEBUG
+ fprintf(stderr, "*** Registering %s components (all right -- a generic module!)\n", mModuleName);
+#endif
+
+ const nsModuleComponentInfo* cp = mComponents;
+ for (PRUint32 i = 0; i < mComponentCount; i++) {
+ // Register the component only if it has a constructor
+ if (cp->mConstructor) {
+ nsCOMPtr<nsIComponentRegistrar> registrar = do_QueryInterface(aCompMgr, &rv);
+ if (registrar)
+ rv = registrar->RegisterFactoryLocation(cp->mCID,
+ cp->mDescription,
+ cp->mContractID,
+ aPath,
+ registryLocation,
+ componentType);
+ if (NS_FAILED(rv)) {
+#ifdef DEBUG
+ fprintf(stderr, "nsGenericModule %s: unable to register %s component => %x\n",
+ mModuleName?mModuleName:"(null)", cp->mDescription?cp->mDescription:"(null)", rv);
+#endif
+ break;
+ }
+ }
+ // Call the registration hook of the component, if any
+ if (cp->mRegisterSelfProc)
+ {
+ rv = cp->mRegisterSelfProc(aCompMgr, aPath, registryLocation,
+ componentType, cp);
+ if (NS_FAILED(rv)) {
+#ifdef DEBUG
+ fprintf(stderr, "nsGenericModule %s: Register hook for %s component returned error => %x\n",
+ mModuleName?mModuleName:"(null)", cp->mDescription?cp->mDescription:"(null)", rv);
+#endif
+ break;
+ }
+ }
+ cp++;
+ }
+
+#ifndef XPCOM_GLUE
+ // We want to tell the component loader of any dependencies
+ // we have so that the loader can resolve them for us.
+
+ nsCOMPtr<nsINativeComponentLoader> loader = do_GetInterface(aCompMgr);
+ if (loader && mLibraryDependencies)
+ {
+ for(int i=0; mLibraryDependencies[i] != nsnull &&
+ mLibraryDependencies[i][0] != '\0'; i++)
+ {
+ loader->AddDependentLibrary(aPath,
+ mLibraryDependencies[i]);
+ }
+ loader = nsnull;
+ }
+#endif
+
+
+
+ return rv;
+}
+
+NS_IMETHODIMP
+nsGenericModule::UnregisterSelf(nsIComponentManager* aCompMgr,
+ nsIFile* aPath,
+ const char* registryLocation)
+{
+#ifdef DEBUG
+ fprintf(stderr, "*** Unregistering %s components (all right -- a generic module!)\n", mModuleName);
+#endif
+ const nsModuleComponentInfo* cp = mComponents;
+ for (PRUint32 i = 0; i < mComponentCount; i++) {
+ // Call the unregistration hook of the component, if any
+ if (cp->mUnregisterSelfProc)
+ {
+ cp->mUnregisterSelfProc(aCompMgr, aPath, registryLocation, cp);
+ }
+
+ // Unregister the component
+ nsresult rv;
+ nsCOMPtr<nsIComponentRegistrar> registrar = do_QueryInterface(aCompMgr, &rv);
+ if (registrar)
+ rv = registrar->UnregisterFactoryLocation(cp->mCID, aPath);
+ if (NS_FAILED(rv)) {
+#ifdef DEBUG
+ fprintf(stderr, "nsGenericModule %s: unable to unregister %s component => %x\n",
+ mModuleName, cp->mDescription, rv);
+#endif
+ }
+ cp++;
+ }
+
+ return NS_OK;
+}
+
+NS_IMETHODIMP
+nsGenericModule::CanUnload(nsIComponentManager *aCompMgr, PRBool *okToUnload)
+{
+ if (!okToUnload) {
+ return NS_ERROR_INVALID_POINTER;
+ }
+ *okToUnload = PR_FALSE;
+ return NS_ERROR_FAILURE;
+}
+
+NS_COM nsresult
+NS_NewGenericModule2(nsModuleInfo* info, nsIModule* *result)
+{
+ nsresult rv = NS_OK;
+
+ // Create and initialize the module instance
+ nsGenericModule *m =
+ new nsGenericModule(info->mModuleName, info->mCount, info->mComponents,
+ info->mCtor, info->mDtor, info->mLibraryDependencies);
+
+ if (!m)
+ return NS_ERROR_OUT_OF_MEMORY;
+
+ // Increase refcnt and store away nsIModule interface to m in result
+ NS_ADDREF(*result = m);
+ return rv;
+}
+
+NS_COM nsresult
+NS_NewGenericModule(const char* moduleName,
+ PRUint32 componentCount,
+ nsModuleComponentInfo* components,
+ nsModuleDestructorProc dtor,
+ nsIModule* *result)
+{
+ nsModuleInfo info;
+ memset(&info, 0, sizeof(info));
+
+ info.mVersion = NS_MODULEINFO_VERSION;
+ info.mModuleName = moduleName;
+ info.mComponents = components;
+ info.mCount = componentCount;
+ info.mDtor = dtor;
+ info.mLibraryDependencies = nsnull;
+
+ return NS_NewGenericModule2(&info, result);
+}
+
+////////////////////////////////////////////////////////////////////////////////
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsGenericFactory.h b/src/libs/xpcom18a4/xpcom/glue/nsGenericFactory.h
new file mode 100644
index 00000000..64afd0de
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsGenericFactory.h
@@ -0,0 +1,129 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#ifndef nsGenericFactory_h___
+#define nsGenericFactory_h___
+
+#include "nsCOMPtr.h"
+#include "nsIGenericFactory.h"
+#include "nsIClassInfo.h"
+
+/**
+ * Most factories follow this simple pattern, so why not just use a function
+ * pointer for most creation operations?
+ */
+class nsGenericFactory : public nsIGenericFactory, public nsIClassInfo {
+public:
+ NS_DEFINE_STATIC_CID_ACCESSOR(NS_GENERICFACTORY_CID);
+
+ nsGenericFactory(const nsModuleComponentInfo *info = NULL);
+
+ NS_DECL_ISUPPORTS
+ NS_DECL_NSICLASSINFO
+
+ /* nsIGenericFactory methods */
+ NS_IMETHOD SetComponentInfo(const nsModuleComponentInfo *info);
+ NS_IMETHOD GetComponentInfo(const nsModuleComponentInfo **infop);
+
+ NS_IMETHOD CreateInstance(nsISupports *aOuter, REFNSIID aIID, void **aResult);
+
+ NS_IMETHOD LockFactory(PRBool aLock);
+
+ static NS_METHOD Create(nsISupports* outer, const nsIID& aIID, void* *aInstancePtr);
+private:
+ ~nsGenericFactory();
+
+ const nsModuleComponentInfo *mInfo;
+};
+
+////////////////////////////////////////////////////////////////////////////////
+
+#include "nsIModule.h"
+#include "plhash.h"
+
+class nsGenericModule : public nsIModule
+{
+public:
+ nsGenericModule(const char* moduleName,
+ PRUint32 componentCount,
+ const nsModuleComponentInfo* components,
+ nsModuleConstructorProc ctor,
+ nsModuleDestructorProc dtor,
+ const char** alibDepends);
+
+private:
+ ~nsGenericModule();
+
+public:
+ NS_DECL_ISUPPORTS
+
+ NS_DECL_NSIMODULE
+
+ struct FactoryNode
+ {
+ FactoryNode(nsIGenericFactory* fact, FactoryNode* next)
+ {
+ mFactory = fact;
+ mNext = next;
+ }
+ ~FactoryNode(){}
+
+ nsCOMPtr<nsIGenericFactory> mFactory;
+ FactoryNode* mNext;
+ };
+
+
+
+
+protected:
+ nsresult Initialize(nsIComponentManager* compMgr);
+
+ void Shutdown();
+ nsresult AddFactoryNode(nsIGenericFactory* fact);
+
+ PRBool mInitialized;
+ const char* mModuleName;
+ PRUint32 mComponentCount;
+ const nsModuleComponentInfo* mComponents;
+ FactoryNode* mFactoriesNotToBeRegistered;
+ nsModuleConstructorProc mCtor;
+ nsModuleDestructorProc mDtor;
+ const char** mLibraryDependencies;
+};
+
+#endif /* nsGenericFactory_h___ */
+
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsIGenericFactory.h b/src/libs/xpcom18a4/xpcom/glue/nsIGenericFactory.h
new file mode 100644
index 00000000..82506e8e
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsIGenericFactory.h
@@ -0,0 +1,480 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#ifndef nsIGenericFactory_h___
+#define nsIGenericFactory_h___
+
+#include "nsIFactory.h"
+#include "nsIModule.h"
+#include "nsIClassInfo.h"
+#ifdef HAVE_DEPENDENT_LIBS
+#include "dependentLibs.h"
+#endif
+
+// {3bc97f01-ccdf-11d2-bab8-b548654461fc}
+#define NS_GENERICFACTORY_CID \
+ { 0x3bc97f01, 0xccdf, 0x11d2, \
+ { 0xba, 0xb8, 0xb5, 0x48, 0x65, 0x44, 0x61, 0xfc } }
+
+// {3bc97f00-ccdf-11d2-bab8-b548654461fc}
+#define NS_IGENERICFACTORY_IID \
+ { 0x3bc97f00, 0xccdf, 0x11d2, \
+ { 0xba, 0xb8, 0xb5, 0x48, 0x65, 0x44, 0x61, 0xfc } }
+
+#define NS_GENERICFACTORY_CONTRACTID "@mozilla.org/generic-factory;1"
+#define NS_GENERICFACTORY_CLASSNAME "Generic Factory"
+
+struct nsModuleComponentInfo; // forward declaration
+
+/**
+ * Provides a Generic nsIFactory implementation that can be used by
+ * DLLs with very simple factory needs.
+ */
+class nsIGenericFactory : public nsIFactory {
+public:
+ NS_DEFINE_STATIC_IID_ACCESSOR(NS_IGENERICFACTORY_IID)
+
+ NS_IMETHOD SetComponentInfo(const nsModuleComponentInfo *info) = 0;
+ NS_IMETHOD GetComponentInfo(const nsModuleComponentInfo **infop) = 0;
+};
+
+NS_COM nsresult
+NS_NewGenericFactory(nsIGenericFactory **result,
+ const nsModuleComponentInfo *info);
+
+
+/** Component Callbacks **/
+
+ /**
+ * NSConstructorProcPtr
+ *
+ * This function will be used by the generic factory to create an
+ * instance of the given CID.
+ *
+ * @param aOuter : Pointer to a component that wishes to be aggregated
+ * in the resulting instance. This will be nsnull if no
+ * aggregation is requested.
+ * @param iid : The IID of the interface being requested in
+ * the component which is being currently created.
+ * @param result : [out] Pointer to the newly created instance, if successful.
+ *
+ * @return NS_OK Component successfully created and the interface
+ * being requested was successfully returned in result.
+ * NS_NOINTERFACE Interface not accessible.
+ * NS_ERROR_NO_AGGREGATION if an 'outer' object is supplied, but the
+ * component is not aggregatable.
+ * NS_ERROR* Method failure.
+ **/
+typedef NS_CALLBACK(NSConstructorProcPtr)(nsISupports *aOuter,
+ REFNSIID aIID,
+ void **aResult);
+
+/**
+ * NSRegisterSelfProcPtr
+ *
+ * One time registration call back. Allows you to perform registration
+ * specific activity like adding yourself to a category.
+ *
+ * @param aCompMgr : The global component manager
+ * @param aFile : Component File. This file must have an associated
+ * loader and export the required symbols which this
+ * loader defines.
+ * @param aLoaderStr : Opaque loader specific string. This value is
+ * passed into the nsIModule's registerSelf
+ * callback and must be fowarded unmodified when
+ * registering factories via their location.
+ * @param aType : Component Type of CID aClass. This value is
+ * passed into the nsIModule's registerSelf
+ * callback and must be fowarded unmodified when
+ * registering factories via their location.
+ * @param aInfo : Pointer to array of nsModuleComponentInfo
+ *
+ * @param aInfo
+ * @return NS_OK Registration was successful.
+ * NS_ERROR* Method failure.
+ **/
+typedef NS_CALLBACK(NSRegisterSelfProcPtr)(nsIComponentManager *aCompMgr,
+ nsIFile *aPath,
+ const char *aLoaderStr,
+ const char *aType,
+ const nsModuleComponentInfo *aInfo);
+
+/**
+ * NSUnregisterSelfProcPtr
+ *
+ * One time unregistration call back. Allows you to perform unregistration
+ * specific activity like removing yourself from a category.
+ *
+ * @param aCompMgr : The global component manager
+ * @param aFile : Component File. This file must have an associated
+ * loader and export the required symbols which this
+ * loader defines.
+ * @param aLoaderStr : Opaque loader specific string. This value is
+ * passed into the nsIModule's registerSelf
+ * callback and must be fowarded unmodified when
+ * registering factories via their location
+ * @param aInfo : Pointer to array of nsModuleComponentInfo
+ *
+ * @param aInfo
+ * @return NS_OK Registration was successful.
+ * NS_ERROR* Method failure.
+
+ **/
+typedef NS_CALLBACK(NSUnregisterSelfProcPtr)(nsIComponentManager *aCompMgr,
+ nsIFile *aPath,
+ const char *aLoaderStr,
+ const nsModuleComponentInfo *aInfo);
+
+/**
+ * NSFactoryDestructorProcPtr
+ *
+ * This function will be called when the factory is being destroyed.
+ *
+ **/
+typedef NS_CALLBACK(NSFactoryDestructorProcPtr)(void);
+
+
+/**
+ * NSGetInterfacesProcPtr
+ *
+ * This function is used to implement class info.
+ *
+ * Get an ordered list of the interface ids that instances of the class
+ * promise to implement. Note that nsISupports is an implicit member
+ * of any such list and need not be included.
+ *
+ * Should set *count = 0 and *array = null and return NS_OK if getting the
+ * list is not supported.
+ *
+ * @see nsIClassInfo.idl
+ **/
+typedef NS_CALLBACK(NSGetInterfacesProcPtr)(PRUint32 *countp,
+ nsIID* **array);
+
+/**
+ * NSGetLanguageHelperProcPtr
+ *
+ * This function is used to implement class info.
+ *
+ * Get a language mapping specific helper object that may assist in using
+ * objects of this class in a specific lanaguage. For instance, if asked
+ * for the helper for nsIProgrammingLanguage::JAVASCRIPT this might return
+ * an object that can be QI'd into the nsIXPCScriptable interface to assist
+ * XPConnect in supplying JavaScript specific behavior to callers of the
+ * instance object.
+ *
+ * @see: nsIClassInfo.idl, nsIProgrammingLanguage.idl
+ *
+ * Should return null if no helper available for given language.
+ **/
+typedef NS_CALLBACK(NSGetLanguageHelperProcPtr)(PRUint32 language,
+ nsISupports **helper);
+
+/**
+ * nsModuleComponentInfo
+ *
+ * Use this type to define a list of module component info to pass to
+ * NS_NewGenericModule.
+ *
+ * @param mDescription : Class Name of given object
+ * @param mCID : CID of given object
+ * @param mContractID : Contract ID of given object
+ * @param mConstructor : Constructor of given object
+ * @param mRegisterSelfProc : (optional) Registration Callback
+ * @param mUnregisterSelfProc : (optional) Unregistration Callback
+ * @param mFactoryDestructor : (optional) Destruction Callback
+ * @param mGetInterfacesProc : (optional) Interfaces Callback
+ * @param mGetLanguageHelperProc : (optional) Language Helper Callback
+ * @param mClassInfoGlobal : (optional) Global Class Info of given object
+ * @param mFlags : (optional) Class Info Flags @see nsIClassInfo
+ *
+ * E.g.:
+ * static nsModuleComponentInfo components[] = { ... };
+ *
+ * See xpcom/sample/nsSampleModule.cpp for more info.
+ */
+struct nsModuleComponentInfo {
+ const char* mDescription;
+ nsCID mCID;
+ const char* mContractID;
+ NSConstructorProcPtr mConstructor;
+ NSRegisterSelfProcPtr mRegisterSelfProc;
+ NSUnregisterSelfProcPtr mUnregisterSelfProc;
+ NSFactoryDestructorProcPtr mFactoryDestructor;
+ NSGetInterfacesProcPtr mGetInterfacesProc;
+ NSGetLanguageHelperProcPtr mGetLanguageHelperProc;
+ nsIClassInfo ** mClassInfoGlobal;
+ PRUint32 mFlags;
+};
+
+
+/** Module Callbacks **/
+
+
+/**
+ * nsModuleConstructorProc
+ *
+ * This function is called when the module is first being constructed.
+ * @param self module which is being constructed.
+ *
+ * @return NS_OK Construction successful.
+ * NS_ERROR* Method failure which will result in module not being
+ * loaded.
+ **/
+typedef nsresult (PR_CALLBACK *nsModuleConstructorProc) (nsIModule *self);
+
+
+/**
+ * nsModuleDestructorProc
+ *
+ * This function is called when the module is being destroyed.
+ * @param self module which is being destroyed.
+ *
+ **/
+typedef void (PR_CALLBACK *nsModuleDestructorProc) (nsIModule *self);
+
+/**
+ * nsModuleInfo
+ *
+ * Use this structure to define meta-information about the module
+ * itself, including the name, its components, and an optional
+ * module-level initialization or shutdown routine.
+ *
+ * @param mVersion : Module Info Version
+ * @param mModuleName : Module Name
+ * @param mComponents : Array of Components
+ * @param mCount : Count of mComponents
+ * @param mCtor : Module user defined constructor
+ * @param mDtor : Module user defined destructor
+ * @param mLibraryDependencies : array of library which this module is
+ * dependent on.
+ *
+ **/
+
+struct nsModuleInfo {
+ PRUint32 mVersion;
+ const char* mModuleName;
+ const nsModuleComponentInfo* mComponents;
+ PRUint32 mCount;
+ nsModuleConstructorProc mCtor;
+ nsModuleDestructorProc mDtor;
+ const char** mLibraryDependencies;
+};
+
+/**
+ * Rev this if you change the nsModuleInfo, and are worried about
+ * binary compatibility. (Ostensibly fix NS_NewGenericModule2() to deal
+ * with older rev's at the same time.)
+ */
+#define NS_MODULEINFO_VERSION 0x00015000UL // 1.5
+
+/**
+ * Create a new generic module. Use the NS_IMPL_NSGETMODULE macro, or
+ * one of its relatives, rather than using this directly.
+ */
+NS_COM nsresult
+NS_NewGenericModule2(nsModuleInfo *info, nsIModule* *result);
+
+/**
+ * Obsolete. Use NS_NewGenericModule2() instead.
+ */
+NS_COM nsresult
+NS_NewGenericModule(const char* moduleName,
+ PRUint32 componentCount,
+ nsModuleComponentInfo* components,
+ nsModuleDestructorProc dtor,
+ nsIModule* *result);
+
+#if defined(XPCOM_TRANSLATE_NSGM_ENTRY_POINT)
+# define NS_MODULEINFO nsModuleInfo
+# define NSMODULEINFO(_name) _name##_gModuleInfo
+# define NSGETMODULE_ENTRY_POINT(_info)
+# define NSDEPENDENT_LIBS(_name) const char* _name##_gDependlibs[]={DEPENDENT_LIBS "\0"};
+# define NSDEPENDENT_LIBS_NAME(_name) _name##_gDependlibs
+#else
+# define NS_MODULEINFO static nsModuleInfo
+# define NSMODULEINFO(_name) gModuleInfo
+# define NSDEPENDENT_LIBS(_name) static const char* gDependlibs[]={DEPENDENT_LIBS "\0"};
+# define NSDEPENDENT_LIBS_NAME(_name) gDependlibs
+# define NSGETMODULE_ENTRY_POINT(_info) \
+extern "C" NS_EXPORT nsresult \
+NSGetModule(nsIComponentManager *servMgr, \
+ nsIFile* location, \
+ nsIModule** result) \
+{ \
+ (void)servMgr; \
+ (void)location; \
+ return NS_NewGenericModule2(&(_info), result); \
+}
+#endif
+
+/**
+ * Ease of use Macros which define NSGetModule for your component.
+ * See xpcom/sample/nsSampleModule.cpp for more info.
+ *
+ **/
+
+#define NS_IMPL_NSGETMODULE(_name, _components) \
+ NS_IMPL_NSGETMODULE_WITH_CTOR_DTOR(_name, _components, nsnull, nsnull)
+
+#define NS_IMPL_NSGETMODULE_WITH_CTOR(_name, _components, _ctor) \
+ NS_IMPL_NSGETMODULE_WITH_CTOR_DTOR(_name, _components, _ctor, nsnull)
+
+#define NS_IMPL_NSGETMODULE_WITH_DTOR(_name, _components, _dtor) \
+ NS_IMPL_NSGETMODULE_WITH_CTOR_DTOR(_name, _components, nsnull, _dtor)
+
+#ifndef DEPENDENT_LIBS
+
+#define NS_IMPL_NSGETMODULE_WITH_CTOR_DTOR(_name, _components, _ctor, _dtor) \
+NS_MODULEINFO NSMODULEINFO(_name) = { \
+ NS_MODULEINFO_VERSION, \
+ (#_name), \
+ (_components), \
+ (sizeof(_components) / sizeof(_components[0])), \
+ (_ctor), \
+ (_dtor), \
+ (nsnull) \
+}; \
+NSGETMODULE_ENTRY_POINT(NSMODULEINFO(_name))
+
+#else // DEPENDENT_LIBS
+
+#define NS_IMPL_NSGETMODULE_WITH_CTOR_DTOR(_name, _components, _ctor, _dtor) \
+NSDEPENDENT_LIBS(_name) \
+NS_MODULEINFO NSMODULEINFO(_name) = { \
+ NS_MODULEINFO_VERSION, \
+ (#_name), \
+ (_components), \
+ (sizeof(_components) / sizeof(_components[0])), \
+ (_ctor), \
+ (_dtor), \
+ (NSDEPENDENT_LIBS_NAME(_name)) \
+}; \
+NSGETMODULE_ENTRY_POINT(NSMODULEINFO(_name))
+
+#endif
+
+////////////////////////////////////////////////////////////////////////////////
+
+#define NS_GENERIC_FACTORY_CONSTRUCTOR(_InstanceClass) \
+static NS_IMETHODIMP \
+_InstanceClass##Constructor(nsISupports *aOuter, REFNSIID aIID, \
+ void **aResult) \
+{ \
+ nsresult rv; \
+ \
+ _InstanceClass * inst; \
+ \
+ *aResult = NULL; \
+ if (NULL != aOuter) { \
+ rv = NS_ERROR_NO_AGGREGATION; \
+ return rv; \
+ } \
+ \
+ NS_NEWXPCOM(inst, _InstanceClass); \
+ if (NULL == inst) { \
+ rv = NS_ERROR_OUT_OF_MEMORY; \
+ return rv; \
+ } \
+ NS_ADDREF(inst); \
+ rv = inst->QueryInterface(aIID, aResult); \
+ NS_RELEASE(inst); \
+ \
+ return rv; \
+} \
+
+
+#define NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(_InstanceClass, _InitMethod) \
+static NS_IMETHODIMP \
+_InstanceClass##Constructor(nsISupports *aOuter, REFNSIID aIID, \
+ void **aResult) \
+{ \
+ nsresult rv; \
+ \
+ _InstanceClass * inst; \
+ \
+ *aResult = NULL; \
+ if (NULL != aOuter) { \
+ rv = NS_ERROR_NO_AGGREGATION; \
+ return rv; \
+ } \
+ \
+ NS_NEWXPCOM(inst, _InstanceClass); \
+ if (NULL == inst) { \
+ rv = NS_ERROR_OUT_OF_MEMORY; \
+ return rv; \
+ } \
+ NS_ADDREF(inst); \
+ rv = inst->_InitMethod(); \
+ if(NS_SUCCEEDED(rv)) { \
+ rv = inst->QueryInterface(aIID, aResult); \
+ } \
+ NS_RELEASE(inst); \
+ \
+ return rv; \
+} \
+
+// 'Constructor' that uses an existing getter function that gets a singleton.
+// NOTE: assumes that getter does an AddRef - so additional AddRef is not done.
+#define NS_GENERIC_FACTORY_SINGLETON_CONSTRUCTOR(_InstanceClass, _GetterProc) \
+static NS_IMETHODIMP \
+_InstanceClass##Constructor(nsISupports *aOuter, REFNSIID aIID, \
+ void **aResult) \
+{ \
+ nsresult rv; \
+ \
+ _InstanceClass * inst; \
+ \
+ *aResult = NULL; \
+ if (NULL != aOuter) { \
+ rv = NS_ERROR_NO_AGGREGATION; \
+ return rv; \
+ } \
+ \
+ inst = _GetterProc(); \
+ if (NULL == inst) { \
+ rv = NS_ERROR_OUT_OF_MEMORY; \
+ return rv; \
+ } \
+ /* NS_ADDREF(inst); */ \
+ rv = inst->QueryInterface(aIID, aResult); \
+ NS_RELEASE(inst); \
+ \
+ return rv; \
+} \
+
+#endif /* nsIGenericFactory_h___ */
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsIInterfaceRequestorUtils.cpp b/src/libs/xpcom18a4/xpcom/glue/nsIInterfaceRequestorUtils.cpp
new file mode 100644
index 00000000..b440c342
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsIInterfaceRequestorUtils.cpp
@@ -0,0 +1,64 @@
+/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ * Scott Collins <scc@netscape.com>
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#include "nsIInterfaceRequestor.h"
+#include "nsIInterfaceRequestorUtils.h"
+
+nsresult
+nsGetInterface::operator()( const nsIID& aIID, void** aInstancePtr ) const
+{
+ nsresult status;
+
+ if ( mSource )
+ {
+ nsCOMPtr<nsIInterfaceRequestor> factoryPtr = do_QueryInterface(mSource, &status);
+ NS_ASSERTION(factoryPtr, "Did you know you were calling |do_GetInterface()| on an object that doesn't support the |nsIInterfaceRequestor| interface?");
+
+ if ( factoryPtr )
+ status = factoryPtr->GetInterface(aIID, aInstancePtr);
+
+ if ( NS_FAILED(status) )
+ *aInstancePtr = 0;
+ }
+ else
+ status = NS_ERROR_NULL_POINTER;
+
+ if ( mErrorPtr )
+ *mErrorPtr = status;
+ return status;
+}
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsIInterfaceRequestorUtils.h b/src/libs/xpcom18a4/xpcom/glue/nsIInterfaceRequestorUtils.h
new file mode 100644
index 00000000..e971dd4b
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsIInterfaceRequestorUtils.h
@@ -0,0 +1,83 @@
+/* -*- Mode: IDL; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
+ *
+ * ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is the Mozilla browser.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications, Inc.
+ * Portions created by the Initial Developer are Copyright (C) 1999
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#ifndef __nsInterfaceRequestorUtils_h
+#define __nsInterfaceRequestorUtils_h
+
+#include "nsCOMPtr.h"
+
+// a type-safe shortcut for calling the |GetInterface()| member function
+// T must inherit from nsIInterfaceRequestor, but the cast may be ambiguous.
+template <class T, class DestinationType>
+inline
+nsresult
+CallGetInterface( T* aSource, DestinationType** aDestination )
+ {
+ NS_PRECONDITION(aSource, "null parameter");
+ NS_PRECONDITION(aDestination, "null parameter");
+
+ return aSource->GetInterface(NS_GET_IID(DestinationType),
+ NS_REINTERPRET_CAST(void**, aDestination));
+ }
+
+class NS_COM nsGetInterface : public nsCOMPtr_helper
+ {
+ public:
+ nsGetInterface( nsISupports* aSource, nsresult* error )
+ : mSource(aSource),
+ mErrorPtr(error)
+ {
+ // nothing else to do here
+ }
+
+ virtual nsresult NS_FASTCALL operator()( const nsIID&, void** ) const;
+
+ private:
+ nsCOMPtr<nsISupports> mSource;
+ nsresult* mErrorPtr;
+ };
+
+inline
+const nsGetInterface
+do_GetInterface( nsISupports* aSource, nsresult* error = 0 )
+ {
+ return nsGetInterface(aSource, error);
+ }
+
+#endif // __nsInterfaceRequestorUtils_h
+
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsISupportsImpl.h b/src/libs/xpcom18a4/xpcom/glue/nsISupportsImpl.h
new file mode 100644
index 00000000..588a2c73
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsISupportsImpl.h
@@ -0,0 +1,1246 @@
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is XPCOM.
+ *
+ * The Initial Developer of the Original Code is Netscape Communications Corp.
+ * Portions created by the Initial Developer are Copyright (C) 2001
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either the GNU General Public License Version 2 or later (the "GPL"), or
+ * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+
+#ifndef nsISupportsImpl_h__
+#define nsISupportsImpl_h__
+
+#ifndef nscore_h___
+#include "nscore.h"
+#endif
+
+#ifndef nsISupportsBase_h__
+#include "nsISupportsBase.h"
+#endif
+
+#include "prthread.h" /* needed for thread-safety checks */
+#include "pratom.h" /* needed for PR_AtomicIncrement and PR_AtomicDecrement */
+
+#include "nsDebug.h"
+#include "nsTraceRefcnt.h"
+#ifdef VBOX
+# include "iprt/asm.h"
+# include "iprt/assert.h"
+#endif
+
+////////////////////////////////////////////////////////////////////////////////
+// Macros to help detect thread-safety:
+
+#if defined(NS_DEBUG)
+
+class nsAutoOwningThread {
+public:
+ nsAutoOwningThread() { mThread = PR_GetCurrentThread(); }
+ void *GetThread() const { return mThread; }
+
+private:
+ void *mThread;
+};
+
+#define NS_DECL_OWNINGTHREAD nsAutoOwningThread _mOwningThread;
+#define NS_ASSERT_OWNINGTHREAD(_class) \
+ NS_CheckThreadSafe(_mOwningThread.GetThread(), #_class " not thread-safe")
+
+#else // !(defined(NS_DEBUG))
+
+#define NS_DECL_OWNINGTHREAD /* nothing */
+#define NS_ASSERT_OWNINGTHREAD(_class) ((void)0)
+
+#endif // !(defined(NS_DEBUG))
+
+class nsAutoRefCnt {
+
+ public:
+ nsAutoRefCnt() : mValue(0)
+#ifdef VBOX
+ , mState(0)
+#endif
+ {}
+ nsAutoRefCnt(nsrefcnt aValue) : mValue(aValue) {}
+
+ // only support prefix increment/decrement
+ nsrefcnt operator++() { return ++mValue; }
+ nsrefcnt operator--() { return --mValue; }
+
+ nsrefcnt operator=(nsrefcnt aValue) { return (mValue = aValue); }
+ operator nsrefcnt() const { return mValue; }
+ nsrefcnt get() const { return mValue; }
+#ifdef VBOX
+ nsrefcnt *ref() { return &mValue; }
+ PRUint32 getState() const { return mState; }
+ PRUint32 *refState() { return &mState; }
+#endif
+ private:
+ // do not define these to enforce the faster prefix notation
+ nsrefcnt operator++(int);
+ nsrefcnt operator--(int);
+ nsrefcnt mValue;
+#ifdef VBOX
+ PRUint32 mState;
+#endif
+};
+
+///////////////////////////////////////////////////////////////////////////////
+
+/**
+ * Declare the reference count variable and the implementations of the
+ * AddRef and QueryInterface methods.
+ */
+
+#define NS_DECL_ISUPPORTS \
+public: \
+ NS_IMETHOD QueryInterface(REFNSIID aIID, \
+ void** aInstancePtr); \
+ NS_IMETHOD_(nsrefcnt) AddRef(void); \
+ NS_IMETHOD_(nsrefcnt) Release(void); \
+protected: \
+ nsAutoRefCnt mRefCnt; \
+ NS_DECL_OWNINGTHREAD \
+public:
+
+
+///////////////////////////////////////////////////////////////////////////////
+
+/**
+ * Previously used to initialize the reference count, but no longer needed.
+ *
+ * DEPRECATED.
+ */
+#define NS_INIT_ISUPPORTS() ((void)0)
+
+/**
+ * Use this macro to implement the AddRef method for a given <i>_class</i>
+ * @param _class The name of the class implementing the method
+ */
+#define NS_IMPL_ADDREF(_class) \
+NS_IMETHODIMP_(nsrefcnt) _class::AddRef(void) \
+{ \
+ NS_PRECONDITION(PRInt32(mRefCnt) >= 0, "illegal refcnt"); \
+ NS_ASSERT_OWNINGTHREAD(_class); \
+ ++mRefCnt; \
+ NS_LOG_ADDREF(this, mRefCnt, #_class, sizeof(*this)); \
+ return mRefCnt; \
+}
+
+/**
+ * Use this macro to implement the AddRef method for a given <i>_class</i>
+ * implemented as a wholly owned aggregated object intended to implement
+ * interface(s) for its owner
+ * @param _class The name of the class implementing the method
+ * @param _aggregator the owning/containing object
+ */
+#define NS_IMPL_ADDREF_USING_AGGREGATOR(_class, _aggregator) \
+NS_IMETHODIMP_(nsrefcnt) _class::AddRef(void) \
+{ \
+ NS_PRECONDITION(_aggregator, "null aggregator"); \
+ return (_aggregator)->AddRef(); \
+}
+
+/**
+ * Use this macro to implement the Release method for a given
+ * <i>_class</i>.
+ * @param _class The name of the class implementing the method
+ * @param _destroy A statement that is executed when the object's
+ * refcount drops to zero.
+ *
+ * For example,
+ *
+ * NS_IMPL_RELEASE_WITH_DESTROY(Foo, Destroy(this))
+ *
+ * will cause
+ *
+ * Destroy(this);
+ *
+ * to be invoked when the object's refcount drops to zero. This
+ * allows for arbitrary teardown activity to occur (e.g., deallocation
+ * of object allocated with placement new).
+ */
+#define NS_IMPL_RELEASE_WITH_DESTROY(_class, _destroy) \
+NS_IMETHODIMP_(nsrefcnt) _class::Release(void) \
+{ \
+ NS_PRECONDITION(0 != mRefCnt, "dup release"); \
+ NS_ASSERT_OWNINGTHREAD(_class); \
+ --mRefCnt; \
+ NS_LOG_RELEASE(this, mRefCnt, #_class); \
+ if (mRefCnt == 0) { \
+ mRefCnt = 1; /* stabilize */ \
+ _destroy; \
+ return 0; \
+ } \
+ return mRefCnt; \
+}
+
+/**
+ * Use this macro to implement the Release method for a given <i>_class</i>
+ * @param _class The name of the class implementing the method
+ *
+ * A note on the 'stabilization' of the refcnt to one. At that point,
+ * the object's refcount will have gone to zero. The object's
+ * destructor may trigger code that attempts to QueryInterface() and
+ * Release() 'this' again. Doing so will temporarily increment and
+ * decrement the refcount. (Only a logic error would make one try to
+ * keep a permanent hold on 'this'.) To prevent re-entering the
+ * destructor, we make sure that no balanced refcounting can return
+ * the refcount to |0|.
+ */
+#define NS_IMPL_RELEASE(_class) \
+ NS_IMPL_RELEASE_WITH_DESTROY(_class, NS_DELETEXPCOM(this))
+
+/**
+ * Use this macro to implement the Release method for a given <i>_class</i>
+ * implemented as a wholly owned aggregated object intended to implement
+ * interface(s) for its owner
+ * @param _class The name of the class implementing the method
+ * @param _aggregator the owning/containing object
+ */
+#define NS_IMPL_RELEASE_USING_AGGREGATOR(_class, _aggregator) \
+NS_IMETHODIMP_(nsrefcnt) _class::Release(void) \
+{ \
+ NS_PRECONDITION(_aggregator, "null aggregator"); \
+ return (_aggregator)->Release(); \
+}
+
+
+
+///////////////////////////////////////////////////////////////////////////////
+
+/*
+ * Some convenience macros for implementing QueryInterface
+ */
+
+/**
+ * This implements query interface with two assumptions: First, the
+ * class in question implements nsISupports and its own interface and
+ * nothing else. Second, the implementation of the class's primary
+ * inheritance chain leads to its own interface.
+ *
+ * @param _class The name of the class implementing the method
+ * @param _classiiddef The name of the #define symbol that defines the IID
+ * for the class (e.g. NS_ISUPPORTS_IID)
+ */
+
+#define NS_IMPL_QUERY_HEAD(_class) \
+NS_IMETHODIMP _class::QueryInterface(REFNSIID aIID, void** aInstancePtr) \
+{ \
+ NS_ASSERTION(aInstancePtr, \
+ "QueryInterface requires a non-NULL destination!"); \
+ nsISupports* foundInterface;
+
+#define NS_IMPL_QUERY_BODY(_interface) \
+ if ( aIID.Equals(NS_GET_IID(_interface)) ) \
+ foundInterface = NS_STATIC_CAST(_interface*, this); \
+ else
+
+#define NS_IMPL_QUERY_BODY_CONDITIONAL(_interface, condition) \
+ if ( (condition) && aIID.Equals(NS_GET_IID(_interface))) \
+ foundInterface = NS_STATIC_CAST(_interface*, this); \
+ else
+
+#define NS_IMPL_QUERY_BODY_AMBIGUOUS(_interface, _implClass) \
+ if ( aIID.Equals(NS_GET_IID(_interface)) ) \
+ foundInterface = NS_STATIC_CAST(_interface*, \
+ NS_STATIC_CAST(_implClass*, this)); \
+ else
+
+#define NS_IMPL_QUERY_BODY_AGGREGATED(_interface, _aggregate) \
+ if ( aIID.Equals(NS_GET_IID(_interface)) ) \
+ foundInterface = NS_STATIC_CAST(_interface*, _aggregate); \
+ else
+
+#define NS_IMPL_QUERY_TAIL_GUTS \
+ foundInterface = 0; \
+ nsresult status; \
+ if ( !foundInterface ) \
+ status = NS_NOINTERFACE; \
+ else \
+ { \
+ NS_ADDREF(foundInterface); \
+ status = NS_OK; \
+ } \
+ *aInstancePtr = foundInterface; \
+ return status; \
+}
+
+#define NS_IMPL_QUERY_TAIL_INHERITING(_baseclass) \
+ foundInterface = 0; \
+ nsresult status; \
+ if ( !foundInterface ) \
+ status = _baseclass::QueryInterface(aIID, (void**)&foundInterface); \
+ else \
+ { \
+ NS_ADDREF(foundInterface); \
+ status = NS_OK; \
+ } \
+ *aInstancePtr = foundInterface; \
+ return status; \
+}
+
+#define NS_IMPL_QUERY_TAIL_USING_AGGREGATOR(_aggregator) \
+ foundInterface = 0; \
+ nsresult status; \
+ if ( !foundInterface ) { \
+ NS_ASSERTION(_aggregator, "null aggregator"); \
+ status = _aggregator->QueryInterface(aIID, (void**)&foundInterface); \
+ } else \
+ { \
+ NS_ADDREF(foundInterface); \
+ status = NS_OK; \
+ } \
+ *aInstancePtr = foundInterface; \
+ return status; \
+}
+
+#define NS_IMPL_QUERY_TAIL(_supports_interface) \
+ NS_IMPL_QUERY_BODY_AMBIGUOUS(nsISupports, _supports_interface) \
+ NS_IMPL_QUERY_TAIL_GUTS
+
+
+ /*
+ This is the new scheme. Using this notation now will allow us to switch to
+ a table driven mechanism when it's ready. Note the difference between this
+ and the (currently) underlying NS_IMPL_QUERY_INTERFACE mechanism. You must
+ explicitly mention |nsISupports| when using the interface maps.
+ */
+#define NS_INTERFACE_MAP_BEGIN(_implClass) NS_IMPL_QUERY_HEAD(_implClass)
+#define NS_INTERFACE_MAP_ENTRY(_interface) NS_IMPL_QUERY_BODY(_interface)
+#define NS_INTERFACE_MAP_ENTRY_CONDITIONAL(_interface, condition) \
+ NS_IMPL_QUERY_BODY_CONDITIONAL(_interface, condition)
+#define NS_INTERFACE_MAP_ENTRY_AGGREGATED(_interface,_aggregate) \
+ NS_IMPL_QUERY_BODY_AGGREGATED(_interface,_aggregate)
+
+#define NS_INTERFACE_MAP_END NS_IMPL_QUERY_TAIL_GUTS
+#define NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(_interface, _implClass) \
+ NS_IMPL_QUERY_BODY_AMBIGUOUS(_interface, _implClass)
+#define NS_INTERFACE_MAP_END_INHERITING(_baseClass) \
+ NS_IMPL_QUERY_TAIL_INHERITING(_baseClass)
+#define NS_INTERFACE_MAP_END_AGGREGATED(_aggregator) \
+ NS_IMPL_QUERY_TAIL_USING_AGGREGATOR(_aggregator)
+
+#define NS_IMPL_QUERY_INTERFACE0(_class) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(nsISupports) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_QUERY_INTERFACE1(_class, _i1) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_QUERY_INTERFACE2(_class, _i1, _i2) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_QUERY_INTERFACE3(_class, _i1, _i2, _i3) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_QUERY_INTERFACE4(_class, _i1, _i2, _i3, _i4) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_QUERY_INTERFACE5(_class, _i1, _i2, _i3, _i4, _i5) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY(_i5) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_QUERY_INTERFACE6(_class, _i1, _i2, _i3, _i4, _i5, _i6) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY(_i5) \
+ NS_INTERFACE_MAP_ENTRY(_i6) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_QUERY_INTERFACE7(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY(_i5) \
+ NS_INTERFACE_MAP_ENTRY(_i6) \
+ NS_INTERFACE_MAP_ENTRY(_i7) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_QUERY_INTERFACE8(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY(_i5) \
+ NS_INTERFACE_MAP_ENTRY(_i6) \
+ NS_INTERFACE_MAP_ENTRY(_i7) \
+ NS_INTERFACE_MAP_ENTRY(_i8) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_QUERY_INTERFACE9(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY(_i5) \
+ NS_INTERFACE_MAP_ENTRY(_i6) \
+ NS_INTERFACE_MAP_ENTRY(_i7) \
+ NS_INTERFACE_MAP_ENTRY(_i8) \
+ NS_INTERFACE_MAP_ENTRY(_i9) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_QUERY_INTERFACE10(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9, _i10) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY(_i5) \
+ NS_INTERFACE_MAP_ENTRY(_i6) \
+ NS_INTERFACE_MAP_ENTRY(_i7) \
+ NS_INTERFACE_MAP_ENTRY(_i8) \
+ NS_INTERFACE_MAP_ENTRY(_i9) \
+ NS_INTERFACE_MAP_ENTRY(_i10) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_QUERY_INTERFACE11(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9, _i10, _i11) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY(_i5) \
+ NS_INTERFACE_MAP_ENTRY(_i6) \
+ NS_INTERFACE_MAP_ENTRY(_i7) \
+ NS_INTERFACE_MAP_ENTRY(_i8) \
+ NS_INTERFACE_MAP_ENTRY(_i9) \
+ NS_INTERFACE_MAP_ENTRY(_i10) \
+ NS_INTERFACE_MAP_ENTRY(_i11) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_INTERFACE_MAP_END
+
+
+#define NS_IMPL_THREADSAFE_QUERY_INTERFACE0 NS_IMPL_QUERY_INTERFACE0
+#define NS_IMPL_THREADSAFE_QUERY_INTERFACE1 NS_IMPL_QUERY_INTERFACE1
+#define NS_IMPL_THREADSAFE_QUERY_INTERFACE2 NS_IMPL_QUERY_INTERFACE2
+#define NS_IMPL_THREADSAFE_QUERY_INTERFACE3 NS_IMPL_QUERY_INTERFACE3
+#define NS_IMPL_THREADSAFE_QUERY_INTERFACE4 NS_IMPL_QUERY_INTERFACE4
+#define NS_IMPL_THREADSAFE_QUERY_INTERFACE5 NS_IMPL_QUERY_INTERFACE5
+#define NS_IMPL_THREADSAFE_QUERY_INTERFACE6 NS_IMPL_QUERY_INTERFACE6
+#define NS_IMPL_THREADSAFE_QUERY_INTERFACE7 NS_IMPL_QUERY_INTERFACE7
+#define NS_IMPL_THREADSAFE_QUERY_INTERFACE8 NS_IMPL_QUERY_INTERFACE8
+#define NS_IMPL_THREADSAFE_QUERY_INTERFACE9 NS_IMPL_QUERY_INTERFACE9
+#define NS_IMPL_THREADSAFE_QUERY_INTERFACE10 NS_IMPL_QUERY_INTERFACE10
+#define NS_IMPL_THREADSAFE_QUERY_INTERFACE11 NS_IMPL_QUERY_INTERFACE11
+
+/**
+ * Declare that you're going to inherit from something that already
+ * implements nsISupports, but also implements an additional interface, thus
+ * causing an ambiguity. In this case you don't need another mRefCnt, you
+ * just need to forward the definitions to the appropriate superclass. E.g.
+ *
+ * class Bar : public Foo, public nsIBar { // both provide nsISupports
+ * public:
+ * NS_DECL_ISUPPORTS_INHERITED
+ * ...other nsIBar and Bar methods...
+ * };
+ */
+#define NS_DECL_ISUPPORTS_INHERITED \
+public: \
+ NS_IMETHOD QueryInterface(REFNSIID aIID, \
+ void** aInstancePtr); \
+ NS_IMETHOD_(nsrefcnt) AddRef(void); \
+ NS_IMETHOD_(nsrefcnt) Release(void); \
+
+/**
+ * These macros can be used in conjunction with NS_DECL_ISUPPORTS_INHERITED
+ * to implement the nsISupports methods, forwarding the invocations to a
+ * superclass that already implements nsISupports.
+ *
+ * Note that I didn't make these inlined because they're virtual methods.
+ */
+
+#define NS_IMPL_ADDREF_INHERITED(Class, Super) \
+NS_IMETHODIMP_(nsrefcnt) Class::AddRef(void) \
+{ \
+ return Super::AddRef(); \
+} \
+
+#define NS_IMPL_RELEASE_INHERITED(Class, Super) \
+NS_IMETHODIMP_(nsrefcnt) Class::Release(void) \
+{ \
+ return Super::Release(); \
+} \
+
+#define NS_IMPL_QUERY_INTERFACE_INHERITED0(Class, Super) \
+ NS_IMPL_QUERY_HEAD(Class) \
+ NS_IMPL_QUERY_TAIL_INHERITING(Super) \
+
+#define NS_IMPL_QUERY_INTERFACE_INHERITED1(Class, Super, i1) \
+ NS_IMPL_QUERY_HEAD(Class) \
+ NS_IMPL_QUERY_BODY(i1) \
+ NS_IMPL_QUERY_TAIL_INHERITING(Super) \
+
+#define NS_IMPL_QUERY_INTERFACE_INHERITED2(Class, Super, i1, i2) \
+ NS_IMPL_QUERY_HEAD(Class) \
+ NS_IMPL_QUERY_BODY(i1) \
+ NS_IMPL_QUERY_BODY(i2) \
+ NS_IMPL_QUERY_TAIL_INHERITING(Super) \
+
+#define NS_IMPL_QUERY_INTERFACE_INHERITED3(Class, Super, i1, i2, i3) \
+ NS_IMPL_QUERY_HEAD(Class) \
+ NS_IMPL_QUERY_BODY(i1) \
+ NS_IMPL_QUERY_BODY(i2) \
+ NS_IMPL_QUERY_BODY(i3) \
+ NS_IMPL_QUERY_TAIL_INHERITING(Super) \
+
+#define NS_IMPL_QUERY_INTERFACE_INHERITED4(Class, Super, i1, i2, i3, i4) \
+ NS_IMPL_QUERY_HEAD(Class) \
+ NS_IMPL_QUERY_BODY(i1) \
+ NS_IMPL_QUERY_BODY(i2) \
+ NS_IMPL_QUERY_BODY(i3) \
+ NS_IMPL_QUERY_BODY(i4) \
+ NS_IMPL_QUERY_TAIL_INHERITING(Super) \
+
+#define NS_IMPL_QUERY_INTERFACE_INHERITED5(Class,Super,i1,i2,i3,i4,i5) \
+ NS_IMPL_QUERY_HEAD(Class) \
+ NS_IMPL_QUERY_BODY(i1) \
+ NS_IMPL_QUERY_BODY(i2) \
+ NS_IMPL_QUERY_BODY(i3) \
+ NS_IMPL_QUERY_BODY(i4) \
+ NS_IMPL_QUERY_BODY(i5) \
+ NS_IMPL_QUERY_TAIL_INHERITING(Super) \
+
+#define NS_IMPL_QUERY_INTERFACE_INHERITED6(Class,Super,i1,i2,i3,i4,i5,i6) \
+ NS_IMPL_QUERY_HEAD(Class) \
+ NS_IMPL_QUERY_BODY(i1) \
+ NS_IMPL_QUERY_BODY(i2) \
+ NS_IMPL_QUERY_BODY(i3) \
+ NS_IMPL_QUERY_BODY(i4) \
+ NS_IMPL_QUERY_BODY(i5) \
+ NS_IMPL_QUERY_BODY(i6) \
+ NS_IMPL_QUERY_TAIL_INHERITING(Super) \
+
+/**
+ * Convenience macros for implementing all nsISupports methods for
+ * a simple class.
+ * @param _class The name of the class implementing the method
+ * @param _classiiddef The name of the #define symbol that defines the IID
+ * for the class (e.g. NS_ISUPPORTS_IID)
+ */
+
+#define NS_IMPL_ISUPPORTS0(_class) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE0(_class)
+
+#define NS_IMPL_ISUPPORTS1(_class, _interface) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE1(_class, _interface)
+
+#define NS_IMPL_ISUPPORTS2(_class, _i1, _i2) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE2(_class, _i1, _i2)
+
+#define NS_IMPL_ISUPPORTS3(_class, _i1, _i2, _i3) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE3(_class, _i1, _i2, _i3)
+
+#define NS_IMPL_ISUPPORTS4(_class, _i1, _i2, _i3, _i4) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE4(_class, _i1, _i2, _i3, _i4)
+
+#define NS_IMPL_ISUPPORTS5(_class, _i1, _i2, _i3, _i4, _i5) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE5(_class, _i1, _i2, _i3, _i4, _i5)
+
+#define NS_IMPL_ISUPPORTS6(_class, _i1, _i2, _i3, _i4, _i5, _i6) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE6(_class, _i1, _i2, _i3, _i4, _i5, _i6)
+
+#define NS_IMPL_ISUPPORTS7(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE7(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7)
+
+#define NS_IMPL_ISUPPORTS8(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, _i8) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE8(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, _i8)
+
+#define NS_IMPL_ISUPPORTS9(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, _i8, \
+ _i9) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE9(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, _i8, _i9)
+
+#define NS_IMPL_ISUPPORTS10(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, _i8, \
+ _i9, _i10) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE10(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, _i8, \
+ _i9, _i10)
+
+#define NS_IMPL_ISUPPORTS11(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, _i8, \
+ _i9, _i10, _i11) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE11(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, _i8, \
+ _i9, _i10, _i11)
+
+#define NS_IMPL_ISUPPORTS_INHERITED0(Class, Super) \
+ NS_IMPL_QUERY_INTERFACE_INHERITED0(Class, Super) \
+ NS_IMPL_ADDREF_INHERITED(Class, Super) \
+ NS_IMPL_RELEASE_INHERITED(Class, Super) \
+
+#define NS_IMPL_ISUPPORTS_INHERITED1(Class, Super, i1) \
+ NS_IMPL_QUERY_INTERFACE_INHERITED1(Class, Super, i1) \
+ NS_IMPL_ADDREF_INHERITED(Class, Super) \
+ NS_IMPL_RELEASE_INHERITED(Class, Super) \
+
+#define NS_IMPL_ISUPPORTS_INHERITED2(Class, Super, i1, i2) \
+ NS_IMPL_QUERY_INTERFACE_INHERITED2(Class, Super, i1, i2) \
+ NS_IMPL_ADDREF_INHERITED(Class, Super) \
+ NS_IMPL_RELEASE_INHERITED(Class, Super) \
+
+#define NS_IMPL_ISUPPORTS_INHERITED3(Class, Super, i1, i2, i3) \
+ NS_IMPL_QUERY_INTERFACE_INHERITED3(Class, Super, i1, i2, i3) \
+ NS_IMPL_ADDREF_INHERITED(Class, Super) \
+ NS_IMPL_RELEASE_INHERITED(Class, Super) \
+
+#define NS_IMPL_ISUPPORTS_INHERITED4(Class, Super, i1, i2, i3, i4) \
+ NS_IMPL_QUERY_INTERFACE_INHERITED4(Class, Super, i1, i2, i3, i4) \
+ NS_IMPL_ADDREF_INHERITED(Class, Super) \
+ NS_IMPL_RELEASE_INHERITED(Class, Super) \
+
+#define NS_IMPL_ISUPPORTS_INHERITED5(Class, Super, i1, i2, i3, i4, i5) \
+ NS_IMPL_QUERY_INTERFACE_INHERITED5(Class, Super, i1, i2, i3, i4, i5) \
+ NS_IMPL_ADDREF_INHERITED(Class, Super) \
+ NS_IMPL_RELEASE_INHERITED(Class, Super) \
+
+#define NS_IMPL_ISUPPORTS_INHERITED6(Class, Super, i1, i2, i3, i4, i5, i6) \
+ NS_IMPL_QUERY_INTERFACE_INHERITED6(Class, Super, i1, i2, i3, i4, i5, i6) \
+ NS_IMPL_ADDREF_INHERITED(Class, Super) \
+ NS_IMPL_RELEASE_INHERITED(Class, Super) \
+
+///////////////////////////////////////////////////////////////////////////////
+/**
+ *
+ * Threadsafe implementations of the ISupports convenience macros
+ *
+ */
+
+/**
+ * Use this macro to implement the AddRef method for a given <i>_class</i>
+ * @param _class The name of the class implementing the method
+ */
+
+#ifdef VBOX
+#define NS_IMPL_THREADSAFE_ADDREF(_class) \
+NS_IMETHODIMP_(nsrefcnt) _class::AddRef(void) \
+{ \
+ nsrefcnt count = mRefCnt.get(); \
+ PRUint32 state = mRefCnt.getState(); \
+ AssertReleaseMsg( state <= 1 \
+ && ( (state == 0 && count == 0) \
+ || (state == 1 && count < PR_UINT32_MAX/2)), \
+ ("AddRef: illegal refcnt=%u state=%d\n", count, state)); \
+ switch (state) \
+ { \
+ case 0: \
+ if (!ASMAtomicCmpXchgU32(mRefCnt.refState(), 1, 0)) \
+ AssertReleaseMsgFailed(("AddRef: racing for first increment\n")); \
+ count = ASMAtomicIncU32(mRefCnt.ref()); \
+ AssertReleaseMsg(count == 1, \
+ ("AddRef: unexpected refcnt=%u\n", count)); \
+ break; \
+ case 1: \
+ count = ASMAtomicIncU32(mRefCnt.ref()); \
+ AssertReleaseMsg(count <= PR_UINT32_MAX/2, \
+ ("AddRef: unexpected refcnt=%u\n", count)); \
+ break; \
+ case 2: \
+ AssertReleaseMsgFailed(("AddRef: freed object\n")); \
+ break; \
+ default: \
+ AssertReleaseMsgFailed(("AddRef: garbage object\n")); \
+ } \
+ NS_LOG_ADDREF(this, count, #_class, sizeof(*this)); \
+ return count; \
+}
+#else
+#define NS_IMPL_THREADSAFE_ADDREF(_class) \
+NS_IMETHODIMP_(nsrefcnt) _class::AddRef(void) \
+{ \
+ NS_PRECONDITION(PRInt32(mRefCnt) >= 0, "illegal refcnt"); \
+ nsrefcnt count; \
+ count = PR_AtomicIncrement((PRInt32*)&mRefCnt); \
+ NS_LOG_ADDREF(this, count, #_class, sizeof(*this)); \
+ return count; \
+}
+#endif
+
+/**
+ * Use this macro to implement the Release method for a given <i>_class</i>
+ * @param _class The name of the class implementing the method
+ */
+
+#ifdef VBOX
+#define NS_IMPL_THREADSAFE_RELEASE(_class) \
+NS_IMETHODIMP_(nsrefcnt) _class::Release(void) \
+{ \
+ nsrefcnt count = mRefCnt.get(); \
+ PRUint32 state = mRefCnt.getState(); \
+ AssertReleaseMsg(state == 1 && count <= PR_UINT32_MAX/2, \
+ ("Release: illegal refcnt=%u state=%d\n", count, state)); \
+ switch (state) \
+ { \
+ case 0: \
+ AssertReleaseMsgFailed(("Release: new object\n")); \
+ break; \
+ case 1: \
+ count = ASMAtomicDecU32(mRefCnt.ref()); \
+ AssertReleaseMsg(count < PR_UINT32_MAX/2, \
+ ("Release: unexpected refcnt=%u\n", count)); \
+ if (count == 0) \
+ { \
+ if (!ASMAtomicCmpXchgU32(mRefCnt.refState(), 2, 1)) \
+ AssertReleaseMsgFailed(("Release: racing for state free\n")); \
+ /* Use better stabilization: reserve everything with top bit set. */ \
+ if (!ASMAtomicCmpXchgU32(mRefCnt.ref(), PR_UINT32_MAX/4*3, 0)) \
+ AssertReleaseMsgFailed(("Release: racing for refcnt stabilize\n")); \
+ NS_DELETEXPCOM(this); \
+ } \
+ break; \
+ case 2: \
+ AssertReleaseMsgFailed(("Release: freed object\n")); \
+ break; \
+ default: \
+ AssertReleaseMsgFailed(("Release: garbage object\n")); \
+ } \
+ NS_LOG_RELEASE(this, count, #_class); \
+ return count; \
+}
+#else
+#define NS_IMPL_THREADSAFE_RELEASE(_class) \
+NS_IMETHODIMP_(nsrefcnt) _class::Release(void) \
+{ \
+ nsrefcnt count; \
+ NS_PRECONDITION(0 != mRefCnt, "dup release"); \
+ count = PR_AtomicDecrement((PRInt32 *)&mRefCnt); \
+ NS_LOG_RELEASE(this, count, #_class); \
+ if (0 == count) { \
+ mRefCnt = 1; /* stabilize */ \
+ /* enable this to find non-threadsafe destructors: */ \
+ /* NS_ASSERT_OWNINGTHREAD(_class); */ \
+ NS_DELETEXPCOM(this); \
+ return 0; \
+ } \
+ return count; \
+}
+#endif
+
+#define NS_IMPL_THREADSAFE_ISUPPORTS0(_class) \
+ NS_IMPL_THREADSAFE_ADDREF(_class) \
+ NS_IMPL_THREADSAFE_RELEASE(_class) \
+ NS_IMPL_THREADSAFE_QUERY_INTERFACE0(_class)
+
+#define NS_IMPL_THREADSAFE_ISUPPORTS1(_class, _interface) \
+ NS_IMPL_THREADSAFE_ADDREF(_class) \
+ NS_IMPL_THREADSAFE_RELEASE(_class) \
+ NS_IMPL_THREADSAFE_QUERY_INTERFACE1(_class, _interface)
+
+#define NS_IMPL_THREADSAFE_ISUPPORTS2(_class, _i1, _i2) \
+ NS_IMPL_THREADSAFE_ADDREF(_class) \
+ NS_IMPL_THREADSAFE_RELEASE(_class) \
+ NS_IMPL_THREADSAFE_QUERY_INTERFACE2(_class, _i1, _i2)
+
+#define NS_IMPL_THREADSAFE_ISUPPORTS3(_class, _i1, _i2, _i3) \
+ NS_IMPL_THREADSAFE_ADDREF(_class) \
+ NS_IMPL_THREADSAFE_RELEASE(_class) \
+ NS_IMPL_THREADSAFE_QUERY_INTERFACE3(_class, _i1, _i2, _i3)
+
+#define NS_IMPL_THREADSAFE_ISUPPORTS4(_class, _i1, _i2, _i3, _i4) \
+ NS_IMPL_THREADSAFE_ADDREF(_class) \
+ NS_IMPL_THREADSAFE_RELEASE(_class) \
+ NS_IMPL_THREADSAFE_QUERY_INTERFACE4(_class, _i1, _i2, _i3, _i4)
+
+#define NS_IMPL_THREADSAFE_ISUPPORTS5(_class, _i1, _i2, _i3, _i4, _i5) \
+ NS_IMPL_THREADSAFE_ADDREF(_class) \
+ NS_IMPL_THREADSAFE_RELEASE(_class) \
+ NS_IMPL_THREADSAFE_QUERY_INTERFACE5(_class, _i1, _i2, _i3, _i4, _i5)
+
+#define NS_IMPL_THREADSAFE_ISUPPORTS6(_class, _i1, _i2, _i3, _i4, _i5, _i6) \
+ NS_IMPL_THREADSAFE_ADDREF(_class) \
+ NS_IMPL_THREADSAFE_RELEASE(_class) \
+ NS_IMPL_THREADSAFE_QUERY_INTERFACE6(_class, _i1, _i2, _i3, _i4, _i5, _i6)
+
+#define NS_IMPL_THREADSAFE_ISUPPORTS7(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7) \
+ NS_IMPL_THREADSAFE_ADDREF(_class) \
+ NS_IMPL_THREADSAFE_RELEASE(_class) \
+ NS_IMPL_THREADSAFE_QUERY_INTERFACE7(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7)
+
+#define NS_IMPL_THREADSAFE_ISUPPORTS8(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8) \
+ NS_IMPL_THREADSAFE_ADDREF(_class) \
+ NS_IMPL_THREADSAFE_RELEASE(_class) \
+ NS_IMPL_THREADSAFE_QUERY_INTERFACE8(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8)
+
+#define NS_IMPL_THREADSAFE_ISUPPORTS9(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9) \
+ NS_IMPL_THREADSAFE_ADDREF(_class) \
+ NS_IMPL_THREADSAFE_RELEASE(_class) \
+ NS_IMPL_THREADSAFE_QUERY_INTERFACE9(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9)
+
+#define NS_IMPL_THREADSAFE_ISUPPORTS10(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9, _i10) \
+ NS_IMPL_THREADSAFE_ADDREF(_class) \
+ NS_IMPL_THREADSAFE_RELEASE(_class) \
+ NS_IMPL_THREADSAFE_QUERY_INTERFACE10(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9, _i10)
+
+#define NS_IMPL_THREADSAFE_ISUPPORTS11(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9, _i10, _i11) \
+ NS_IMPL_THREADSAFE_ADDREF(_class) \
+ NS_IMPL_THREADSAFE_RELEASE(_class) \
+ NS_IMPL_THREADSAFE_QUERY_INTERFACE11(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9, _i10, _i11)
+
+///////////////////////////////////////////////////////////////////////////////
+// Macros for implementing nsIClassInfo-related stuff.
+///////////////////////////////////////////////////////////////////////////////
+
+// include here instead of at the top because it requires the nsISupport decl
+#include "nsIClassInfo.h"
+
+#define NS_CLASSINFO_NAME(_class) _class##_classInfoGlobal
+#define NS_CI_INTERFACE_GETTER_NAME(_class) _class##_GetInterfacesHelper
+
+#define NS_DECL_CI_INTERFACE_GETTER(_class) \
+ extern NS_IMETHODIMP NS_CI_INTERFACE_GETTER_NAME(_class)(PRUint32 *, \
+ nsIID ***);
+
+#define NS_DECL_CLASSINFO(_class) \
+ NS_DECL_CI_INTERFACE_GETTER(_class) \
+ nsIClassInfo *NS_CLASSINFO_NAME(_class);
+
+#define NS_IMPL_QUERY_CLASSINFO(_class) \
+ if ( aIID.Equals(NS_GET_IID(nsIClassInfo)) ) { \
+ extern nsIClassInfo *NS_CLASSINFO_NAME(_class); \
+ foundInterface = NS_STATIC_CAST(nsIClassInfo*, NS_CLASSINFO_NAME(_class));\
+ } else
+
+#define NS_CLASSINFO_HELPER_BEGIN(_class, _c) \
+NS_IMETHODIMP \
+NS_CI_INTERFACE_GETTER_NAME(_class)(PRUint32 *count, nsIID ***array) \
+{ \
+ *count = _c; \
+ *array = (nsIID **)nsMemory::Alloc(sizeof (nsIID *) * _c);
+
+#define NS_CLASSINFO_HELPER_ENTRY(_i, _interface) \
+ (*array)[_i] = (nsIID *)nsMemory::Clone(&NS_GET_IID(_interface), \
+ sizeof(nsIID));
+
+#define NS_CLASSINFO_HELPER_END \
+ return NS_OK; \
+}
+
+#define NS_IMPL_CI_INTERFACE_GETTER1(_class, _interface) \
+ NS_CLASSINFO_HELPER_BEGIN(_class, 1) \
+ NS_CLASSINFO_HELPER_ENTRY(0, _interface) \
+ NS_CLASSINFO_HELPER_END
+
+#define NS_IMPL_QUERY_INTERFACE1_CI(_class, _i1) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_IMPL_QUERY_CLASSINFO(_class) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_ISUPPORTS1_CI(_class, _interface) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE1_CI(_class, _interface) \
+ NS_IMPL_CI_INTERFACE_GETTER1(_class, _interface)
+
+#define NS_IMPL_CI_INTERFACE_GETTER2(_class, _i1, _i2) \
+ NS_CLASSINFO_HELPER_BEGIN(_class, 2) \
+ NS_CLASSINFO_HELPER_ENTRY(0, _i1) \
+ NS_CLASSINFO_HELPER_ENTRY(1, _i2) \
+ NS_CLASSINFO_HELPER_END
+
+#define NS_IMPL_QUERY_INTERFACE2_CI(_class, _i1, _i2) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_IMPL_QUERY_CLASSINFO(_class) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_ISUPPORTS2_CI(_class, _i1, _i2) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE2_CI(_class, _i1, _i2) \
+ NS_IMPL_CI_INTERFACE_GETTER2(_class, _i1, _i2)
+
+#define NS_IMPL_CI_INTERFACE_GETTER3(_class, _i1, _i2, _i3) \
+ NS_CLASSINFO_HELPER_BEGIN(_class, 3) \
+ NS_CLASSINFO_HELPER_ENTRY(0, _i1) \
+ NS_CLASSINFO_HELPER_ENTRY(1, _i2) \
+ NS_CLASSINFO_HELPER_ENTRY(2, _i3) \
+ NS_CLASSINFO_HELPER_END
+
+#define NS_IMPL_QUERY_INTERFACE3_CI(_class, _i1, _i2, _i3) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_IMPL_QUERY_CLASSINFO(_class) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_ISUPPORTS3_CI(_class, _i1, _i2, _i3) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE3_CI(_class, _i1, _i2, _i3) \
+ NS_IMPL_CI_INTERFACE_GETTER3(_class, _i1, _i2, _i3)
+
+#define NS_IMPL_CI_INTERFACE_GETTER4(_class, _i1, _i2, _i3, _i4) \
+ NS_CLASSINFO_HELPER_BEGIN(_class, 4) \
+ NS_CLASSINFO_HELPER_ENTRY(0, _i1) \
+ NS_CLASSINFO_HELPER_ENTRY(1, _i2) \
+ NS_CLASSINFO_HELPER_ENTRY(2, _i3) \
+ NS_CLASSINFO_HELPER_ENTRY(3, _i4) \
+ NS_CLASSINFO_HELPER_END
+
+#define NS_IMPL_QUERY_INTERFACE4_CI(_class, _i1, _i2, _i3, _i4) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_IMPL_QUERY_CLASSINFO(_class) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_ISUPPORTS4_CI(_class, _i1, _i2, _i3, _i4) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE4_CI(_class, _i1, _i2, _i3, _i4) \
+ NS_IMPL_CI_INTERFACE_GETTER4(_class, _i1, _i2, _i3, _i4)
+
+#define NS_IMPL_CI_INTERFACE_GETTER5(_class, _i1, _i2, _i3, _i4, _i5) \
+ NS_CLASSINFO_HELPER_BEGIN(_class, 5) \
+ NS_CLASSINFO_HELPER_ENTRY(0, _i1) \
+ NS_CLASSINFO_HELPER_ENTRY(1, _i2) \
+ NS_CLASSINFO_HELPER_ENTRY(2, _i3) \
+ NS_CLASSINFO_HELPER_ENTRY(3, _i4) \
+ NS_CLASSINFO_HELPER_ENTRY(4, _i5) \
+ NS_CLASSINFO_HELPER_END
+
+#define NS_IMPL_QUERY_INTERFACE5_CI(_class, _i1, _i2, _i3, _i4, _i5) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY(_i5) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_IMPL_QUERY_CLASSINFO(_class) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_ISUPPORTS5_CI(_class, _i1, _i2, _i3, _i4, _i5) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE5_CI(_class, _i1, _i2, _i3, _i4, _i5) \
+ NS_IMPL_CI_INTERFACE_GETTER5(_class, _i1, _i2, _i3, _i4, _i5)
+
+#define NS_IMPL_CI_INTERFACE_GETTER6(_class, _i1, _i2, _i3, _i4, _i5, _i6) \
+ NS_CLASSINFO_HELPER_BEGIN(_class, 6) \
+ NS_CLASSINFO_HELPER_ENTRY(0, _i1) \
+ NS_CLASSINFO_HELPER_ENTRY(1, _i2) \
+ NS_CLASSINFO_HELPER_ENTRY(2, _i3) \
+ NS_CLASSINFO_HELPER_ENTRY(3, _i4) \
+ NS_CLASSINFO_HELPER_ENTRY(4, _i5) \
+ NS_CLASSINFO_HELPER_ENTRY(5, _i6) \
+ NS_CLASSINFO_HELPER_END
+
+#define NS_IMPL_QUERY_INTERFACE6_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY(_i5) \
+ NS_INTERFACE_MAP_ENTRY(_i6) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_IMPL_QUERY_CLASSINFO(_class) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_ISUPPORTS6_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE6_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6) \
+ NS_IMPL_CI_INTERFACE_GETTER6(_class, _i1, _i2, _i3, _i4, _i5, _i6)
+
+#define NS_IMPL_CI_INTERFACE_GETTER7(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7) \
+ NS_CLASSINFO_HELPER_BEGIN(_class, 7) \
+ NS_CLASSINFO_HELPER_ENTRY(0, _i1) \
+ NS_CLASSINFO_HELPER_ENTRY(1, _i2) \
+ NS_CLASSINFO_HELPER_ENTRY(2, _i3) \
+ NS_CLASSINFO_HELPER_ENTRY(3, _i4) \
+ NS_CLASSINFO_HELPER_ENTRY(4, _i5) \
+ NS_CLASSINFO_HELPER_ENTRY(5, _i6) \
+ NS_CLASSINFO_HELPER_ENTRY(6, _i7) \
+ NS_CLASSINFO_HELPER_END
+
+#define NS_IMPL_QUERY_INTERFACE7_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY(_i5) \
+ NS_INTERFACE_MAP_ENTRY(_i6) \
+ NS_INTERFACE_MAP_ENTRY(_i7) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_IMPL_QUERY_CLASSINFO(_class) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_ISUPPORTS7_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE7_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7) \
+ NS_IMPL_CI_INTERFACE_GETTER7(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7)
+
+#define NS_IMPL_CI_INTERFACE_GETTER8(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8) \
+ NS_CLASSINFO_HELPER_BEGIN(_class, 8) \
+ NS_CLASSINFO_HELPER_ENTRY(0, _i1) \
+ NS_CLASSINFO_HELPER_ENTRY(1, _i2) \
+ NS_CLASSINFO_HELPER_ENTRY(2, _i3) \
+ NS_CLASSINFO_HELPER_ENTRY(3, _i4) \
+ NS_CLASSINFO_HELPER_ENTRY(4, _i5) \
+ NS_CLASSINFO_HELPER_ENTRY(5, _i6) \
+ NS_CLASSINFO_HELPER_ENTRY(6, _i7) \
+ NS_CLASSINFO_HELPER_ENTRY(7, _i8) \
+ NS_CLASSINFO_HELPER_END
+
+#define NS_IMPL_QUERY_INTERFACE8_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY(_i5) \
+ NS_INTERFACE_MAP_ENTRY(_i6) \
+ NS_INTERFACE_MAP_ENTRY(_i7) \
+ NS_INTERFACE_MAP_ENTRY(_i8) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_IMPL_QUERY_CLASSINFO(_class) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_ISUPPORTS8_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, _i8) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE8_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, _i8) \
+ NS_IMPL_CI_INTERFACE_GETTER8(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, _i8)
+
+#define NS_IMPL_CI_INTERFACE_GETTER9(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9) \
+ NS_CLASSINFO_HELPER_BEGIN(_class, 9) \
+ NS_CLASSINFO_HELPER_ENTRY(0, _i1) \
+ NS_CLASSINFO_HELPER_ENTRY(1, _i2) \
+ NS_CLASSINFO_HELPER_ENTRY(2, _i3) \
+ NS_CLASSINFO_HELPER_ENTRY(3, _i4) \
+ NS_CLASSINFO_HELPER_ENTRY(4, _i5) \
+ NS_CLASSINFO_HELPER_ENTRY(5, _i6) \
+ NS_CLASSINFO_HELPER_ENTRY(6, _i7) \
+ NS_CLASSINFO_HELPER_ENTRY(7, _i8) \
+ NS_CLASSINFO_HELPER_ENTRY(8, _i9) \
+ NS_CLASSINFO_HELPER_END
+
+#define NS_IMPL_QUERY_INTERFACE9_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY(_i5) \
+ NS_INTERFACE_MAP_ENTRY(_i6) \
+ NS_INTERFACE_MAP_ENTRY(_i7) \
+ NS_INTERFACE_MAP_ENTRY(_i8) \
+ NS_INTERFACE_MAP_ENTRY(_i9) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_IMPL_QUERY_CLASSINFO(_class) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_ISUPPORTS9_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, \
+ _i8, _i9) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE9_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, \
+ _i8, _i9) \
+ NS_IMPL_CI_INTERFACE_GETTER9(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, \
+ _i8, _i9)
+
+#define NS_IMPL_CI_INTERFACE_GETTER10(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9, _i10) \
+ NS_CLASSINFO_HELPER_BEGIN(_class, 10) \
+ NS_CLASSINFO_HELPER_ENTRY(0, _i1) \
+ NS_CLASSINFO_HELPER_ENTRY(1, _i2) \
+ NS_CLASSINFO_HELPER_ENTRY(2, _i3) \
+ NS_CLASSINFO_HELPER_ENTRY(3, _i4) \
+ NS_CLASSINFO_HELPER_ENTRY(4, _i5) \
+ NS_CLASSINFO_HELPER_ENTRY(5, _i6) \
+ NS_CLASSINFO_HELPER_ENTRY(6, _i7) \
+ NS_CLASSINFO_HELPER_ENTRY(7, _i8) \
+ NS_CLASSINFO_HELPER_ENTRY(8, _i9) \
+ NS_CLASSINFO_HELPER_ENTRY(9, _i10) \
+ NS_CLASSINFO_HELPER_END
+
+#define NS_IMPL_CI_INTERFACE_GETTER11(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9, _i10, _i11) \
+ NS_CLASSINFO_HELPER_BEGIN(_class, 10) \
+ NS_CLASSINFO_HELPER_ENTRY(0, _i1) \
+ NS_CLASSINFO_HELPER_ENTRY(1, _i2) \
+ NS_CLASSINFO_HELPER_ENTRY(2, _i3) \
+ NS_CLASSINFO_HELPER_ENTRY(3, _i4) \
+ NS_CLASSINFO_HELPER_ENTRY(4, _i5) \
+ NS_CLASSINFO_HELPER_ENTRY(5, _i6) \
+ NS_CLASSINFO_HELPER_ENTRY(6, _i7) \
+ NS_CLASSINFO_HELPER_ENTRY(7, _i8) \
+ NS_CLASSINFO_HELPER_ENTRY(8, _i9) \
+ NS_CLASSINFO_HELPER_ENTRY(9, _i10) \
+ NS_CLASSINFO_HELPER_ENTRY(10, _i11) \
+ NS_CLASSINFO_HELPER_END
+
+#define NS_IMPL_QUERY_INTERFACE10_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9, _i10) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY(_i5) \
+ NS_INTERFACE_MAP_ENTRY(_i6) \
+ NS_INTERFACE_MAP_ENTRY(_i7) \
+ NS_INTERFACE_MAP_ENTRY(_i8) \
+ NS_INTERFACE_MAP_ENTRY(_i9) \
+ NS_INTERFACE_MAP_ENTRY(_i10) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_IMPL_QUERY_CLASSINFO(_class) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_QUERY_INTERFACE11_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, \
+ _i7, _i8, _i9, _i10, _i11) \
+ NS_INTERFACE_MAP_BEGIN(_class) \
+ NS_INTERFACE_MAP_ENTRY(_i1) \
+ NS_INTERFACE_MAP_ENTRY(_i2) \
+ NS_INTERFACE_MAP_ENTRY(_i3) \
+ NS_INTERFACE_MAP_ENTRY(_i4) \
+ NS_INTERFACE_MAP_ENTRY(_i5) \
+ NS_INTERFACE_MAP_ENTRY(_i6) \
+ NS_INTERFACE_MAP_ENTRY(_i7) \
+ NS_INTERFACE_MAP_ENTRY(_i8) \
+ NS_INTERFACE_MAP_ENTRY(_i9) \
+ NS_INTERFACE_MAP_ENTRY(_i10) \
+ NS_INTERFACE_MAP_ENTRY(_i11) \
+ NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, _i1) \
+ NS_IMPL_QUERY_CLASSINFO(_class) \
+ NS_INTERFACE_MAP_END
+
+#define NS_IMPL_ISUPPORTS10_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, \
+ _i8, _i9, _i10) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE10_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, \
+ _i8, _i9, _i10) \
+ NS_IMPL_CI_INTERFACE_GETTER10(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, \
+ _i8, _i9, _i10)
+
+#define NS_IMPL_ISUPPORTS11_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, \
+ _i8, _i9, _i10, _i11) \
+ NS_IMPL_ADDREF(_class) \
+ NS_IMPL_RELEASE(_class) \
+ NS_IMPL_QUERY_INTERFACE11_CI(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, \
+ _i8, _i9, _i10, _i11) \
+ NS_IMPL_CI_INTERFACE_GETTER11(_class, _i1, _i2, _i3, _i4, _i5, _i6, _i7, \
+ _i8, _i9, _i10, _i11)
+
+#define NS_INTERFACE_MAP_END_THREADSAFE NS_IMPL_QUERY_TAIL_GUTS
+
+#endif
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsISupportsUtils.h b/src/libs/xpcom18a4/xpcom/glue/nsISupportsUtils.h
new file mode 100644
index 00000000..d8d002b1
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsISupportsUtils.h
@@ -0,0 +1,230 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ * Pierre Phaneuf <pp@ludusdesign.com>
+ * Scott Collins <scc@ScottCollins.net>
+ * Dan Mosedale <dmose@mozilla.org>
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#ifndef nsISupportsUtils_h__
+#define nsISupportsUtils_h__
+
+#ifndef nscore_h___
+#include "nscore.h"
+#endif
+
+#ifndef nsISupportsBase_h__
+#include "nsISupportsBase.h"
+#endif
+
+#ifndef nsError_h__
+#include "nsError.h"
+#endif
+
+#ifndef nsDebug_h___
+#include "nsDebug.h"
+#endif
+
+#ifndef nsISupportsImpl_h__
+#include "nsISupportsImpl.h"
+#endif
+
+/**
+ * Macro for instantiating a new object that implements nsISupports.
+ * Note that you can only use this if you adhere to the no arguments
+ * constructor com policy (which you really should!).
+ * @param _result Where the new instance pointer is stored
+ * @param _type The type of object to call "new" with.
+ */
+#define NS_NEWXPCOM(_result,_type) \
+ PR_BEGIN_MACRO \
+ _result = new _type(); \
+ PR_END_MACRO
+
+/**
+ * Macro for deleting an object that implements nsISupports.
+ * @param _ptr The object to delete.
+ */
+#define NS_DELETEXPCOM(_ptr) \
+ PR_BEGIN_MACRO \
+ delete (_ptr); \
+ PR_END_MACRO
+
+/**
+ * Macro for adding a reference to an interface.
+ * @param _ptr The interface pointer.
+ */
+#define NS_ADDREF(_ptr) \
+ (_ptr)->AddRef()
+
+/**
+ * Macro for adding a reference to this. This macro should be used
+ * because NS_ADDREF (when tracing) may require an ambiguous cast
+ * from the pointers primary type to nsISupports. This macro sidesteps
+ * that entire problem.
+ */
+#define NS_ADDREF_THIS() \
+ AddRef()
+
+
+extern "C++" {
+// ...because some one is accidentally including this file inside
+// an |extern "C"|
+
+
+// Making this a |inline| |template| allows |expr| to be evaluated only once,
+// yet still denies you the ability to |AddRef()| an |nsCOMPtr|.
+template <class T>
+inline
+nsrefcnt
+ns_if_addref( T expr )
+{
+ return expr ? expr->AddRef() : 0;
+}
+
+} /* extern "C++" */
+
+/**
+ * Macro for adding a reference to an interface that checks for NULL.
+ * @param _expr The interface pointer.
+ */
+#define NS_IF_ADDREF(_expr) ns_if_addref(_expr)
+
+/*
+ * Given these declarations, it explicitly OK and efficient to end a `getter' with:
+ *
+ * NS_IF_ADDREF(*result = mThing);
+ *
+ * even if |mThing| is an |nsCOMPtr|. If |mThing| is an |nsCOMPtr|, however, it is still
+ * _illegal_ to say |NS_IF_ADDREF(mThing)|.
+ */
+
+/**
+ * Macro for releasing a reference to an interface.
+ * @param _ptr The interface pointer.
+ */
+#define NS_RELEASE(_ptr) \
+ PR_BEGIN_MACRO \
+ (_ptr)->Release(); \
+ (_ptr) = 0; \
+ PR_END_MACRO
+
+/**
+ * Macro for releasing a reference to an interface.
+ * @param _ptr The interface pointer.
+ */
+#define NS_RELEASE_THIS() \
+ Release()
+
+/**
+ * Macro for releasing a reference to an interface, except that this
+ * macro preserves the return value from the underlying Release call.
+ * The interface pointer argument will only be NULLed if the reference count
+ * goes to zero.
+ *
+ * @param _ptr The interface pointer.
+ */
+#define NS_RELEASE2(_ptr,_rv) \
+ PR_BEGIN_MACRO \
+ _rv = (_ptr)->Release(); \
+ if (0 == (_rv)) (_ptr) = 0; \
+ PR_END_MACRO
+
+/**
+ * Macro for releasing a reference to an interface that checks for NULL;
+ * @param _ptr The interface pointer.
+ */
+#define NS_IF_RELEASE(_ptr) \
+ PR_BEGIN_MACRO \
+ if (_ptr) { \
+ (_ptr)->Release(); \
+ (_ptr) = 0; \
+ } \
+ PR_END_MACRO
+
+/*
+ * Often you have to cast an implementation pointer, e.g., |this|, to an
+ * |nsISupports*|, but because you have multiple inheritance, a simple cast
+ * is ambiguous. One could simply say, e.g., (given a base |nsIBase|),
+ * |NS_STATIC_CAST(nsIBase*, this)|; but that disguises the fact that what
+ * you are really doing is disambiguating the |nsISupports|. You could make
+ * that more obvious with a double cast, e.g., |NS_STATIC_CAST(nsISupports*,
+ * NS_STATIC_CAST(nsIBase*, this))|, but that is bulky and harder to read...
+ *
+ * The following macro is clean, short, and obvious. In the example above,
+ * you would use it like this: |NS_ISUPPORTS_CAST(nsIBase*, this)|.
+ */
+
+#define NS_ISUPPORTS_CAST(__unambiguousBase, __expr) \
+ NS_STATIC_CAST(nsISupports*, NS_STATIC_CAST(__unambiguousBase, __expr))
+
+extern "C++" {
+// ...because some one is accidentally including this file inside
+// an |extern "C"|
+
+class nsISupports;
+
+template <class T>
+struct nsCOMTypeInfo
+{
+ static const nsIID& GetIID() { return T::GetIID(); }
+};
+
+NS_SPECIALIZE_TEMPLATE
+struct nsCOMTypeInfo<nsISupports>
+{
+ static const nsIID& GetIID() {
+ static const nsIID iid_NS_ISUPPORTS_IID = NS_ISUPPORTS_IID; return iid_NS_ISUPPORTS_IID;
+ }
+};
+
+#define NS_GET_IID(T) nsCOMTypeInfo<T>::GetIID()
+
+// a type-safe shortcut for calling the |QueryInterface()| member function
+template <class T, class DestinationType>
+inline
+nsresult
+CallQueryInterface( T* aSource, DestinationType** aDestination )
+{
+ NS_PRECONDITION(aSource, "null parameter");
+ NS_PRECONDITION(aDestination, "null parameter");
+
+ return aSource->QueryInterface(NS_GET_IID(DestinationType),
+ NS_REINTERPRET_CAST(void**, aDestination));
+}
+
+} // extern "C++"
+
+#endif /* __nsISupportsUtils_h */
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsIWeakReferenceUtils.h b/src/libs/xpcom18a4/xpcom/glue/nsIWeakReferenceUtils.h
new file mode 100644
index 00000000..17d1bd79
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsIWeakReferenceUtils.h
@@ -0,0 +1,162 @@
+/* -*- Mode: IDL; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ * Scott Collins <scc@mozilla.org> (Original Author)
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#ifndef nsIWeakReferenceUtils_h__
+#define nsIWeakReferenceUtils_h__
+
+#ifndef nsCOMPtr_h__
+#include "nsCOMPtr.h"
+#endif
+
+typedef nsCOMPtr<nsIWeakReference> nsWeakPtr;
+
+/**
+ *
+ */
+
+// a type-safe shortcut for calling the |QueryReferent()| member function
+// T must inherit from nsIWeakReference, but the cast may be ambiguous.
+template <class T, class DestinationType>
+inline
+nsresult
+CallQueryReferent( T* aSource, DestinationType** aDestination )
+ {
+ NS_PRECONDITION(aSource, "null parameter");
+ NS_PRECONDITION(aDestination, "null parameter");
+
+ return aSource->QueryReferent(NS_GET_IID(DestinationType),
+ NS_REINTERPRET_CAST(void**, aDestination));
+ }
+
+
+class NS_COM nsQueryReferent : public nsCOMPtr_helper
+ {
+ public:
+ nsQueryReferent( nsIWeakReference* aWeakPtr, nsresult* error )
+ : mWeakPtr(aWeakPtr),
+ mErrorPtr(error)
+ {
+ // nothing else to do here
+ }
+
+ virtual nsresult NS_FASTCALL operator()( const nsIID& aIID, void** ) const;
+
+ private:
+ nsIWeakReference* mWeakPtr;
+ nsresult* mErrorPtr;
+ };
+
+inline
+const nsQueryReferent
+do_QueryReferent( nsIWeakReference* aRawPtr, nsresult* error = 0 )
+ {
+ return nsQueryReferent(aRawPtr, error);
+ }
+
+
+
+class NS_COM nsGetWeakReference : public nsCOMPtr_helper
+ {
+ public:
+ nsGetWeakReference( nsISupports* aRawPtr, nsresult* error )
+ : mRawPtr(aRawPtr),
+ mErrorPtr(error)
+ {
+ // nothing else to do here
+ }
+
+ virtual nsresult NS_FASTCALL operator()( const nsIID&, void** ) const;
+
+ private:
+ nsISupports* mRawPtr;
+ nsresult* mErrorPtr;
+ };
+
+ /**
+ * |do_GetWeakReference| is a convenience function that bundles up all the work needed
+ * to get a weak reference to an arbitrary object, i.e., the |QueryInterface|, test, and
+ * call through to |GetWeakReference|, and put it into your |nsCOMPtr|.
+ * It is specifically designed to cooperate with |nsCOMPtr| (or |nsWeakPtr|) like so:
+ * |nsWeakPtr myWeakPtr = do_GetWeakReference(aPtr);|.
+ */
+inline
+const nsGetWeakReference
+do_GetWeakReference( nsISupports* aRawPtr, nsresult* error = 0 )
+ {
+ return nsGetWeakReference(aRawPtr, error);
+ }
+
+inline
+void
+do_GetWeakReference( nsIWeakReference* aRawPtr, nsresult* error = 0 )
+ {
+ // This signature exists soley to _stop_ you from doing a bad thing.
+ // Saying |do_GetWeakReference()| on a weak reference itself,
+ // is very likely to be a programmer error.
+ }
+
+template <class T>
+inline
+void
+do_GetWeakReference( already_AddRefed<T>& )
+ {
+ // This signature exists soley to _stop_ you from doing the bad thing.
+ // Saying |do_GetWeakReference()| on a pointer that is not otherwise owned by
+ // someone else is an automatic leak. See <http://bugzilla.mozilla.org/show_bug.cgi?id=8221>.
+ }
+
+template <class T>
+inline
+void
+do_GetWeakReference( already_AddRefed<T>&, nsresult* )
+ {
+ // This signature exists soley to _stop_ you from doing the bad thing.
+ // Saying |do_GetWeakReference()| on a pointer that is not otherwise owned by
+ // someone else is an automatic leak. See <http://bugzilla.mozilla.org/show_bug.cgi?id=8221>.
+ }
+
+
+
+ /**
+ * Deprecated, use |do_GetWeakReference| instead.
+ */
+extern NS_COM
+nsIWeakReference*
+NS_GetWeakReference( nsISupports* , nsresult* aResult=0 );
+
+#endif
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsMemory.cpp b/src/libs/xpcom18a4/xpcom/glue/nsMemory.cpp
new file mode 100644
index 00000000..2449c58e
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsMemory.cpp
@@ -0,0 +1,151 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#include "nsXPCOM.h"
+#include "nsMemory.h"
+#include "nsXPCOMPrivate.h"
+
+static nsIMemory* gMemory = nsnull;
+
+static NS_METHOD FreeGlobalMemory(void)
+{
+ NS_ASSERTION(gMemory, "must be not null after SetupGlobalMemory");
+ NS_IF_RELEASE(gMemory);
+ return NS_OK;
+}
+
+#define ENSURE_ALLOCATOR \
+ (gMemory ? PR_TRUE : (PRBool)(SetupGlobalMemory() != nsnull))
+
+static nsIMemory*
+SetupGlobalMemory()
+{
+ NS_ASSERTION(!gMemory, "must be called once");
+ if (!gMemory)
+ {
+ NS_GetMemoryManager(&gMemory);
+ NS_ASSERTION(gMemory, "can't get memory manager!");
+ if (gMemory)
+ NS_RegisterXPCOMExitRoutine(FreeGlobalMemory, 0);
+ }
+ return gMemory;
+}
+
+#ifdef XPCOM_GLUE
+nsresult GlueStartupMemory()
+{
+ NS_ASSERTION(!gMemory, "must be called once");
+ if (!gMemory)
+ {
+ NS_GetMemoryManager(&gMemory);
+ NS_ASSERTION(gMemory, "can't get memory manager!");
+ if (!gMemory)
+ return NS_ERROR_FAILURE;
+ }
+ return NS_OK;
+}
+
+void GlueShutdownMemory()
+{
+ NS_IF_RELEASE(gMemory);
+}
+#endif
+
+////////////////////////////////////////////////////////////////////////////////
+// nsMemory static helper routines
+
+NS_COM void*
+nsMemory::Alloc(PRSize size)
+{
+ if (!ENSURE_ALLOCATOR)
+ return nsnull;
+
+ return gMemory->Alloc(size);
+}
+
+NS_COM void*
+nsMemory::Realloc(void* ptr, PRSize size)
+{
+ if (!ENSURE_ALLOCATOR)
+ return nsnull;
+
+ return gMemory->Realloc(ptr, size);
+}
+
+NS_COM void
+nsMemory::Free(void* ptr)
+{
+ if (!ENSURE_ALLOCATOR)
+ return;
+
+ gMemory->Free(ptr);
+}
+
+NS_COM nsresult
+nsMemory::HeapMinimize(PRBool aImmediate)
+{
+ if (!ENSURE_ALLOCATOR)
+ return NS_ERROR_FAILURE;
+
+ return gMemory->HeapMinimize(aImmediate);
+}
+
+NS_COM void*
+nsMemory::Clone(const void* ptr, PRSize size)
+{
+ if (!ENSURE_ALLOCATOR)
+ return nsnull;
+
+ void* newPtr = gMemory->Alloc(size);
+ if (newPtr)
+ memcpy(newPtr, ptr, size);
+ return newPtr;
+}
+
+NS_COM nsIMemory*
+nsMemory::GetGlobalMemoryService()
+{
+ if (!ENSURE_ALLOCATOR)
+ return nsnull;
+
+ nsIMemory* result = gMemory;
+ NS_IF_ADDREF(result);
+ return result;
+}
+
+//----------------------------------------------------------------------
+
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsMemory.h b/src/libs/xpcom18a4/xpcom/glue/nsMemory.h
new file mode 100644
index 00000000..4ee48bf0
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsMemory.h
@@ -0,0 +1,154 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#ifndef nsMemory_h__
+#define nsMemory_h__
+
+#include "nsIMemory.h"
+
+#define NS_MEMORY_CONTRACTID "@mozilla.org/xpcom/memory-service;1"
+#define NS_MEMORY_CLASSNAME "Global Memory Service"
+#define NS_MEMORY_CID \
+{ /* 30a04e40-38e7-11d4-8cf5-0060b0fc14a3 */ \
+ 0x30a04e40, \
+ 0x38e7, \
+ 0x11d4, \
+ {0x8c, 0xf5, 0x00, 0x60, 0xb0, 0xfc, 0x14, 0xa3} \
+}
+
+
+/**
+ * Static helper routines to manage memory. These routines allow easy access
+ * to xpcom's built-in (global) nsIMemory implementation, without needing
+ * to go through the service manager to get it. However this requires clients
+ * to link with the xpcom DLL.
+ *
+ * This class is not threadsafe and is intented for use only on the main
+ * thread.
+ */
+class nsMemory
+{
+public:
+ static NS_COM void* Alloc(size_t size);
+ static NS_COM void* Realloc(void* ptr, size_t size);
+ static NS_COM void Free(void* ptr);
+ static NS_COM nsresult HeapMinimize(PRBool aImmediate);
+ static NS_COM void* Clone(const void* ptr, size_t size);
+ static NS_COM nsIMemory* GetGlobalMemoryService(); // AddRefs
+};
+
+/**
+ * Macro to free all elements of an XPCOM array of a given size using
+ * freeFunc, then frees the array itself using nsMemory::Free().
+ *
+ * Note that this macro (and its wrappers) can be used to deallocate a
+ * partially- or completely-built array while unwinding an error
+ * condition inside the XPCOM routine that was going to return the
+ * array. For this to work on a partially-built array, your code
+ * needs to be building the array from index 0 upwards, and simply
+ * pass the number of elements that have already been built (and thus
+ * need to be freed) as |size|.
+ *
+ * Thanks to <alecf@netscape.com> for suggesting this form, which
+ * allows the macro to be used with NS_RELEASE / NS_RELEASE_IF in
+ * addition to nsMemory::Free.
+ *
+ * @param size Number of elements in the array. If not a constant, this
+ * should be a PRInt32. Note that this means this macro
+ * will not work if size >= 2^31.
+ * @param array The array to be freed.
+ * @param freeFunc The function or macro to be used to free it.
+ * For arrays of nsISupports (or any class derived
+ * from it), NS_IF_RELEASE (or NS_RELEASE) should be
+ * passed as freeFunc. For most (all?) other pointer
+ * types (including XPCOM strings and wstrings),
+ * nsMemory::Free should be used, since the
+ * shared-allocator (nsMemory) is what will have been
+ * used to allocate the memory.
+ */
+#define NS_FREE_XPCOM_POINTER_ARRAY(size, array, freeFunc) \
+ PR_BEGIN_MACRO \
+ PRInt32 iter_ = PRInt32(size); \
+ while (--iter_ >= 0) \
+ freeFunc((array)[iter_]); \
+ nsMemory::Free((array)); \
+ PR_END_MACRO
+
+// convenience macros for commonly used calls. mmmmm. syntactic sugar.
+
+/**
+ * Macro to free arrays of non-refcounted objects allocated by the
+ * shared allocator (nsMemory) such as strings and wstrings. A
+ * convenience wrapper around NS_FREE_XPCOM_POINTER_ARRAY.
+ *
+ * @param size Number of elements in the array. If not a constant, this
+ * should be a PRInt32. Note that this means this macro
+ * will not work if size >= 2^31.
+ * @param array The array to be freed.
+ */
+#define NS_FREE_XPCOM_ALLOCATED_POINTER_ARRAY(size, array) \
+ NS_FREE_XPCOM_POINTER_ARRAY((size), (array), nsMemory::Free)
+
+/**
+ * Macro to free an array of pointers to nsISupports (or classes
+ * derived from it). A convenience wrapper around
+ * NS_FREE_XPCOM_POINTER_ARRAY.
+ *
+ * Note that if you know that none of your nsISupports pointers are
+ * going to be 0, you can gain a bit of speed by calling
+ * NS_FREE_XPCOM_POINTER_ARRAY directly and using NS_RELEASE as your
+ * free function.
+ *
+ * @param size Number of elements in the array. If not a constant, this
+ * should be a PRInt32. Note that this means this macro
+ * will not work if size >= 2^31.
+ * @param array The array to be freed.
+ */
+#define NS_FREE_XPCOM_ISUPPORTS_POINTER_ARRAY(size, array) \
+ NS_FREE_XPCOM_POINTER_ARRAY((size), (array), NS_IF_RELEASE)
+
+/**
+ * Helpful array length function for calculating the length of a
+ * statically declared array.
+ */
+
+#define NS_ARRAY_LENGTH(array_) \
+ (sizeof(array_)/sizeof(array_[0]))
+
+
+#endif // nsMemory_h__
+
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsServiceManagerUtils.h b/src/libs/xpcom18a4/xpcom/glue/nsServiceManagerUtils.h
new file mode 100644
index 00000000..b225b6a2
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsServiceManagerUtils.h
@@ -0,0 +1,183 @@
+/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is XPCOM.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#ifndef nsIServiceManagerUtils_h__
+#define nsIServiceManagerUtils_h__
+
+#include "nsIServiceManager.h"
+#include "nsIServiceManagerObsolete.h"
+#include "nsCOMPtr.h"
+
+////////////////////////////////////////////////////////////////////////////
+// Using servicemanager with COMPtrs
+class NS_COM nsGetServiceByCID : public nsCOMPtr_helper
+{
+ public:
+ nsGetServiceByCID( const nsCID& aCID, nsISupports* aServiceManager, nsresult* aErrorPtr )
+ : mCID(aCID),
+ mServiceManager( do_QueryInterface(aServiceManager) ),
+ mErrorPtr(aErrorPtr)
+ {
+ // nothing else to do
+ }
+
+ virtual nsresult NS_FASTCALL operator()( const nsIID&, void** ) const;
+
+ private:
+ const nsCID& mCID;
+ nsCOMPtr<nsIServiceManager> mServiceManager;
+ nsresult* mErrorPtr;
+};
+
+inline
+const nsGetServiceByCID
+do_GetService( const nsCID& aCID, nsresult* error = 0 )
+{
+ return nsGetServiceByCID(aCID, 0, error);
+}
+
+inline
+const nsGetServiceByCID
+do_GetService( const nsCID& aCID, nsISupports* aServiceManager, nsresult* error = 0 )
+{
+ return nsGetServiceByCID(aCID, aServiceManager, error);
+}
+
+class NS_COM nsGetServiceByContractID : public nsCOMPtr_helper
+{
+ public:
+ nsGetServiceByContractID( const char* aContractID, nsISupports* aServiceManager, nsresult* aErrorPtr )
+ : mContractID(aContractID),
+ mServiceManager( do_QueryInterface(aServiceManager) ),
+ mErrorPtr(aErrorPtr)
+ {
+ // nothing else to do
+ }
+
+ virtual nsresult NS_FASTCALL operator()( const nsIID&, void** ) const;
+
+ private:
+ const char* mContractID;
+ nsCOMPtr<nsIServiceManager> mServiceManager;
+ nsresult* mErrorPtr;
+};
+
+inline
+const nsGetServiceByContractID
+do_GetService( const char* aContractID, nsresult* error = 0 )
+{
+ return nsGetServiceByContractID(aContractID, 0, error);
+}
+
+inline
+const nsGetServiceByContractID
+do_GetService( const char* aContractID, nsISupports* aServiceManager, nsresult* error = 0 )
+{
+ return nsGetServiceByContractID(aContractID, aServiceManager, error);
+}
+
+class nsGetServiceFromCategory : public nsCOMPtr_helper
+{
+ public:
+ nsGetServiceFromCategory(const char* aCategory, const char* aEntry,
+ nsISupports* aServiceManager,
+ nsresult* aErrorPtr)
+ : mCategory(aCategory),
+ mEntry(aEntry),
+ mServiceManager( do_QueryInterface(aServiceManager) ),
+ mErrorPtr(aErrorPtr)
+ {
+ // nothing else to do
+ }
+
+ virtual nsresult NS_FASTCALL operator()( const nsIID&, void** ) const;
+ protected:
+ const char* mCategory;
+ const char* mEntry;
+ nsCOMPtr<nsIServiceManager> mServiceManager;
+ nsresult* mErrorPtr;
+};
+
+inline
+const nsGetServiceFromCategory
+do_GetServiceFromCategory( const char* category, const char* entry,
+ nsresult* error = 0)
+{
+ return nsGetServiceFromCategory(category, entry, 0, error);
+}
+
+// type-safe shortcuts for calling |GetService|
+template <class DestinationType>
+inline
+nsresult
+CallGetService( const nsCID &aClass,
+ DestinationType** aDestination)
+{
+ NS_PRECONDITION(aDestination, "null parameter");
+
+ nsCOMPtr<nsIServiceManager> mgr;
+ nsresult rv = NS_GetServiceManager(getter_AddRefs(mgr));
+
+ if (NS_FAILED(rv))
+ return rv;
+
+ return mgr->GetService(aClass,
+ NS_GET_IID(DestinationType),
+ NS_REINTERPRET_CAST(void**, aDestination));
+}
+
+template <class DestinationType>
+inline
+nsresult
+CallGetService( const char *aContractID,
+ DestinationType** aDestination)
+{
+ NS_PRECONDITION(aContractID, "null parameter");
+ NS_PRECONDITION(aDestination, "null parameter");
+
+ nsCOMPtr<nsIServiceManager> mgr;
+ nsresult rv = NS_GetServiceManager(getter_AddRefs(mgr));
+
+ if (NS_FAILED(rv))
+ return rv;
+
+ return mgr->GetServiceByContractID(aContractID,
+ NS_GET_IID(DestinationType),
+ NS_REINTERPRET_CAST(void**, aDestination));
+}
+
+#endif
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsTraceRefcnt.cpp b/src/libs/xpcom18a4/xpcom/glue/nsTraceRefcnt.cpp
new file mode 100644
index 00000000..14e9469b
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsTraceRefcnt.cpp
@@ -0,0 +1,125 @@
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is XPCOM
+ *
+ * The Initial Developer of the Original Code is Doug Turner <dougt@meer.net>
+ *
+ * Portions created by the Initial Developer are Copyright (C) 2003
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either the GNU General Public License Version 2 or later (the "GPL"), or
+ * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#include "nsXPCOM.h"
+#include "nsXPCOMPrivate.h"
+#include "nsCOMPtr.h"
+#include "nsIServiceManager.h"
+#include "nsTraceRefcnt.h"
+#include "nsTraceRefcntImpl.h"
+
+static nsITraceRefcnt* gTraceRefcntObject = nsnull;
+
+static NS_METHOD FreeTraceRefcntObject(void)
+{
+ NS_IF_RELEASE(gTraceRefcntObject);
+ return NS_OK;
+}
+
+#define ENSURE_TRACEOBJECT \
+ (gTraceRefcntObject || SetupTraceRefcntObject() != nsnull)
+
+static nsITraceRefcnt* SetupTraceRefcntObject()
+{
+ NS_GetTraceRefcnt(&gTraceRefcntObject);
+ if (gTraceRefcntObject)
+ NS_RegisterXPCOMExitRoutine(FreeTraceRefcntObject, 0);
+ return gTraceRefcntObject;
+}
+
+#ifdef XPCOM_GLUE
+nsresult GlueStartupTraceRefcnt()
+{
+ NS_GetTraceRefcnt(&gTraceRefcntObject);
+ if (!gTraceRefcntObject)
+ return NS_ERROR_FAILURE;
+ return NS_OK;
+}
+
+void GlueShutdownTraceRefcnt()
+{
+ NS_IF_RELEASE(gTraceRefcntObject);
+}
+#endif
+
+NS_COM void
+nsTraceRefcnt::LogAddRef(void * aPtr, nsrefcnt aNewRefcnt, const char *aTypeName, PRUint32 aInstanceSize)
+{
+ if (!ENSURE_TRACEOBJECT)
+ return;
+ gTraceRefcntObject->LogAddRef(aPtr, aNewRefcnt, aTypeName, aInstanceSize);
+}
+
+NS_COM void
+nsTraceRefcnt::LogRelease(void * aPtr, nsrefcnt aNewRefcnt, const char *aTypeName)
+{
+ if (!ENSURE_TRACEOBJECT)
+ return;
+ gTraceRefcntObject->LogRelease(aPtr, aNewRefcnt, aTypeName);
+}
+
+NS_COM void
+nsTraceRefcnt::LogCtor(void * aPtr, const char *aTypeName, PRUint32 aInstanceSize)
+{
+ if (!ENSURE_TRACEOBJECT)
+ return;
+ gTraceRefcntObject->LogCtor(aPtr, aTypeName, aInstanceSize);
+}
+
+NS_COM void
+nsTraceRefcnt::LogDtor(void * aPtr, const char *aTypeName, PRUint32 aInstanceSize)
+{
+ if (!ENSURE_TRACEOBJECT)
+ return;
+ gTraceRefcntObject->LogDtor(aPtr, aTypeName, aInstanceSize);
+}
+
+NS_COM void
+nsTraceRefcnt::LogAddCOMPtr(void * aPtr, nsISupports *aObject)
+{
+ if (!ENSURE_TRACEOBJECT)
+ return;
+ gTraceRefcntObject->LogAddCOMPtr(aPtr, aObject);
+}
+
+NS_COM void
+nsTraceRefcnt::LogReleaseCOMPtr(void * aPtr, nsISupports *aObject)
+{
+ if (!ENSURE_TRACEOBJECT)
+ return;
+ gTraceRefcntObject->LogReleaseCOMPtr(aPtr, aObject);
+}
+
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsTraceRefcnt.h b/src/libs/xpcom18a4/xpcom/glue/nsTraceRefcnt.h
new file mode 100644
index 00000000..afafda4b
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsTraceRefcnt.h
@@ -0,0 +1,135 @@
+/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is Mozilla Communicator client code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ * L. David Baron <dbaron@dbaron.org>
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+#ifndef nsTraceRefcnt_h___
+#define nsTraceRefcnt_h___
+
+#include "nscore.h"
+
+class nsISupports;
+
+// By default refcnt logging is not part of the build.
+#undef NS_BUILD_REFCNT_LOGGING
+
+#if (defined(DEBUG) || defined(FORCE_BUILD_REFCNT_LOGGING))
+// Make refcnt logging part of the build. This doesn't mean that
+// actual logging will occur (that requires a separate enable; see
+// nsTraceRefcnt.h for more information).
+#define NS_BUILD_REFCNT_LOGGING 1
+#endif
+
+// If NO_BUILD_REFCNT_LOGGING is defined then disable refcnt logging
+// in the build. This overrides FORCE_BUILD_REFCNT_LOGGING.
+#if defined(NO_BUILD_REFCNT_LOGGING)
+#undef NS_BUILD_REFCNT_LOGGING
+#endif
+
+#ifdef NS_BUILD_REFCNT_LOGGING
+
+#define NS_LOG_ADDREF(_p, _rc, _type, _size) \
+ nsTraceRefcnt::LogAddRef((_p), (_rc), (_type), (PRUint32) (_size))
+
+#define NS_LOG_RELEASE(_p, _rc, _type) \
+ nsTraceRefcnt::LogRelease((_p), (_rc), (_type))
+
+#define MOZ_DECL_CTOR_COUNTER(_type)
+
+#define MOZ_COUNT_CTOR(_type) \
+PR_BEGIN_MACRO \
+ nsTraceRefcnt::LogCtor((void*)this, #_type, sizeof(*this)); \
+PR_END_MACRO
+
+#define MOZ_COUNT_DTOR(_type) \
+PR_BEGIN_MACRO \
+ nsTraceRefcnt::LogDtor((void*)this, #_type, sizeof(*this)); \
+PR_END_MACRO
+
+#ifdef HAVE_CPP_DYNAMIC_CAST_TO_VOID_PTR // from autoconf (XXX needs to be
+ // set for non-autoconf platforms)
+
+// nsCOMPtr.h allows these macros to be defined by clients
+// These logging functions require dynamic_cast<void *>, so we don't
+// define these macros if we don't have dynamic_cast.
+#define NSCAP_LOG_ASSIGNMENT(_c, _p) \
+ if (_p) \
+ nsTraceRefcnt::LogAddCOMPtr((_c),NS_STATIC_CAST(nsISupports*,_p))
+
+#define NSCAP_LOG_RELEASE(_c, _p) \
+ if (_p) \
+ nsTraceRefcnt::LogReleaseCOMPtr((_c), NS_STATIC_CAST(nsISupports*,_p))
+
+#endif /* HAVE_CPP_DYNAMIC_CAST_TO_VOID_PTR */
+
+#else /* !NS_BUILD_REFCNT_LOGGING */
+
+#define NS_LOG_ADDREF(_p, _rc, _type, _size)
+#define NS_LOG_RELEASE(_p, _rc, _type)
+#define MOZ_DECL_CTOR_COUNTER(_type)
+#define MOZ_COUNT_CTOR(_type)
+#define MOZ_COUNT_DTOR(_type)
+
+#endif /* NS_BUILD_REFCNT_LOGGING */
+
+//----------------------------------------------------------------------
+
+/**
+ * Note: The implementations for these methods are no-ops in a build
+ * where NS_BUILD_REFCNT_LOGGING is disabled.
+ */
+class nsTraceRefcnt {
+public:
+ static NS_COM void LogAddRef(void* aPtr,
+ nsrefcnt aNewRefCnt,
+ const char* aTypeName,
+ PRUint32 aInstanceSize);
+
+ static NS_COM void LogRelease(void* aPtr,
+ nsrefcnt aNewRefCnt,
+ const char* aTypeName);
+
+ static NS_COM void LogCtor(void* aPtr, const char* aTypeName,
+ PRUint32 aInstanceSize);
+
+ static NS_COM void LogDtor(void* aPtr, const char* aTypeName,
+ PRUint32 aInstanceSize);
+
+ static NS_COM void LogAddCOMPtr(void *aCOMPtr, nsISupports *aObject);
+
+ static NS_COM void LogReleaseCOMPtr(void *aCOMPtr, nsISupports *aObject);
+
+};
+#endif /* nsTraceRefcnt_h___ */
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsWeakReference.cpp b/src/libs/xpcom18a4/xpcom/glue/nsWeakReference.cpp
new file mode 100644
index 00000000..76d9f593
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsWeakReference.cpp
@@ -0,0 +1,169 @@
+/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
+ *
+ * ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is the Mozilla browser.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications, Inc.
+ * Portions created by the Initial Developer are Copyright (C) 1999
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ * Scott Collins <scc@netscape.com>
+ * Pierre Phaneuf <pp@ludusdesign.com>
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+// nsWeakReference.cpp
+
+#include "nsWeakReference.h"
+#include "nsCOMPtr.h"
+
+nsresult
+nsQueryReferent::operator()( const nsIID& aIID, void** answer ) const
+ {
+ nsresult status;
+ if ( mWeakPtr )
+ {
+ if ( NS_FAILED(status = mWeakPtr->QueryReferent(aIID, answer)) )
+ *answer = 0;
+ }
+ else
+ status = NS_ERROR_NULL_POINTER;
+
+ if ( mErrorPtr )
+ *mErrorPtr = status;
+ return status;
+ }
+
+nsresult
+nsGetWeakReference::operator()( const nsIID&, void** aResult ) const
+ {
+ nsresult status;
+ // nsIWeakReference** result = &NS_STATIC_CAST(nsIWeakReference*, *aResult);
+ *aResult = 0;
+
+ if ( mRawPtr )
+ {
+ nsCOMPtr<nsISupportsWeakReference> factoryPtr = do_QueryInterface(mRawPtr, &status);
+ NS_ASSERTION(factoryPtr, "Oops! You're asking for a weak reference to an object that doesn't support that.");
+ if ( factoryPtr )
+ {
+ nsIWeakReference* temp;
+ status = factoryPtr->GetWeakReference(&temp);
+ *aResult = temp;
+ }
+ // else, |status| has already been set by |do_QueryInterface|
+ }
+ else
+ status = NS_ERROR_NULL_POINTER;
+
+ if ( mErrorPtr )
+ *mErrorPtr = status;
+ return status;
+ }
+
+
+NS_COM nsIWeakReference* // or else |already_AddRefed<nsIWeakReference>|
+NS_GetWeakReference( nsISupports* aInstancePtr, nsresult* aErrorPtr )
+ {
+ void* result = 0;
+ nsGetWeakReference(aInstancePtr, aErrorPtr)(NS_GET_IID(nsIWeakReference), &result);
+ return NS_STATIC_CAST(nsIWeakReference*, result);
+ }
+
+NS_COM nsresult
+nsSupportsWeakReference::GetWeakReference( nsIWeakReference** aInstancePtr )
+ {
+ if ( !aInstancePtr )
+ return NS_ERROR_NULL_POINTER;
+
+ if ( !mProxy )
+ mProxy = new nsWeakReference(this);
+ *aInstancePtr = mProxy;
+
+ nsresult status;
+ if ( !*aInstancePtr )
+ status = NS_ERROR_OUT_OF_MEMORY;
+ else
+ {
+ NS_ADDREF(*aInstancePtr);
+ status = NS_OK;
+ }
+
+ return status;
+ }
+
+NS_IMETHODIMP_(nsrefcnt)
+nsWeakReference::AddRef()
+ {
+ return ++mRefCount;
+ }
+
+NS_IMETHODIMP_(nsrefcnt)
+nsWeakReference::Release()
+ {
+ nsrefcnt temp = --mRefCount;
+ if ( !mRefCount )
+ delete this;
+ return temp;
+ }
+
+NS_IMETHODIMP
+nsWeakReference::QueryInterface( const nsIID& aIID, void** aInstancePtr )
+ {
+ NS_ASSERTION(aInstancePtr, "QueryInterface requires a non-NULL destination!");
+
+ if ( !aInstancePtr )
+ return NS_ERROR_NULL_POINTER;
+
+ nsISupports* foundInterface;
+ if ( aIID.Equals(NS_GET_IID(nsIWeakReference)) )
+ foundInterface = NS_STATIC_CAST(nsIWeakReference*, this);
+ else if ( aIID.Equals(NS_GET_IID(nsISupports)) )
+ foundInterface = NS_STATIC_CAST(nsISupports*, this);
+ else
+ foundInterface = 0;
+
+ nsresult status;
+ if ( !foundInterface )
+ status = NS_NOINTERFACE;
+ else
+ {
+ NS_ADDREF(foundInterface);
+ status = NS_OK;
+ }
+
+ *aInstancePtr = foundInterface;
+ return status;
+ }
+
+NS_IMETHODIMP
+nsWeakReference::QueryReferent( const nsIID& aIID, void** aInstancePtr )
+ {
+ return mReferent ? mReferent->QueryInterface(aIID, aInstancePtr) : NS_ERROR_NULL_POINTER;
+ }
diff --git a/src/libs/xpcom18a4/xpcom/glue/nsWeakReference.h b/src/libs/xpcom18a4/xpcom/glue/nsWeakReference.h
new file mode 100644
index 00000000..96e63f22
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/nsWeakReference.h
@@ -0,0 +1,150 @@
+/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
+ *
+ * ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is the Mozilla browser.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications, Inc.
+ * Portions created by the Initial Developer are Copyright (C) 1999
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ * Scott Collins <scc@netscape.com>
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#ifndef nsWeakReference_h__
+#define nsWeakReference_h__
+
+// nsWeakReference.h
+
+#include "nsIWeakReference.h"
+
+class nsWeakReference;
+
+#undef IMETHOD_VISIBILITY
+#define IMETHOD_VISIBILITY NS_VISIBILITY_DEFAULT
+
+class NS_COM nsSupportsWeakReference : public nsISupportsWeakReference
+ {
+ public:
+ nsSupportsWeakReference()
+ : mProxy(0)
+ {
+ // nothing else to do here
+ }
+
+ NS_DECL_NSISUPPORTSWEAKREFERENCE
+
+ protected:
+ inline ~nsSupportsWeakReference();
+
+ private:
+ friend class nsWeakReference;
+
+ void
+ NoticeProxyDestruction()
+ // ...called (only) by an |nsWeakReference| from _its_ dtor.
+ {
+ mProxy = 0;
+ }
+
+ nsWeakReference* mProxy;
+
+ protected:
+
+ inline void ClearWeakReferences();
+ PRBool HasWeakReferences() const {return mProxy != 0;}
+ };
+
+#undef IMETHOD_VISIBILITY
+#define IMETHOD_VISIBILITY NS_VISIBILITY_HIDDEN
+
+class NS_COM nsWeakReference : public nsIWeakReference
+ {
+ public:
+ // nsISupports...
+ NS_IMETHOD_(nsrefcnt) AddRef();
+ NS_IMETHOD_(nsrefcnt) Release();
+ NS_IMETHOD QueryInterface( const nsIID&, void** );
+
+ // nsIWeakReference...
+ NS_DECL_NSIWEAKREFERENCE
+
+ private:
+ friend class nsSupportsWeakReference;
+
+ nsWeakReference( nsSupportsWeakReference* referent )
+ : mRefCount(0),
+ mReferent(referent)
+ // ...I can only be constructed by an |nsSupportsWeakReference|
+ {
+ // nothing else to do here
+ }
+
+ ~nsWeakReference()
+ // ...I will only be destroyed by calling |delete| myself.
+ {
+ if ( mReferent )
+ mReferent->NoticeProxyDestruction();
+ }
+
+ void
+ NoticeReferentDestruction()
+ // ...called (only) by an |nsSupportsWeakReference| from _its_ dtor.
+ {
+ mReferent = 0;
+ }
+
+ nsrefcnt mRefCount;
+ nsSupportsWeakReference* mReferent;
+ };
+
+inline
+void
+nsSupportsWeakReference::ClearWeakReferences()
+ /*
+ Usually being called from |nsSupportsWeakReference::~nsSupportsWeakReference|
+ will be good enough, but you may have a case where you need to call disconnect
+ your weak references in an outer destructor (to prevent some client holding a
+ weak reference from re-entering your destructor).
+ */
+ {
+ if ( mProxy )
+ {
+ mProxy->NoticeReferentDestruction();
+ mProxy = 0;
+ }
+ }
+
+inline
+nsSupportsWeakReference::~nsSupportsWeakReference()
+ {
+ ClearWeakReferences();
+ }
+
+#endif
diff --git a/src/libs/xpcom18a4/xpcom/glue/objs.mk b/src/libs/xpcom18a4/xpcom/glue/objs.mk
new file mode 100644
index 00000000..d6d04a5a
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/objs.mk
@@ -0,0 +1,60 @@
+# ***** BEGIN LICENSE BLOCK *****
+# Version: MPL 1.1/GPL 2.0/LGPL 2.1
+#
+# The contents of this file are subject to the Mozilla Public License Version
+# 1.1 (the "License"); you may not use this file except in compliance with
+# the License. You may obtain a copy of the License at
+# http://www.mozilla.org/MPL/
+#
+# Software distributed under the License is distributed on an "AS IS" basis,
+# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+# for the specific language governing rights and limitations under the
+# License.
+#
+# The Original Code is mozilla.org.
+#
+# The Initial Developer of the Original Code is
+# Netscape Communications Corporation.
+# Portions created by the Initial Developer are Copyright (C) 2002
+# the Initial Developer. All Rights Reserved.
+#
+# Contributor(s):
+#
+# Alternatively, the contents of this file may be used under the terms of
+# either the GNU General Public License Version 2 or later (the "GPL"), or
+# the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+# in which case the provisions of the GPL or the LGPL are applicable instead
+# of those above. If you wish to allow use of your version of this file only
+# under the terms of either the GPL or the LGPL, and not to allow others to
+# use your version of this file under the terms of the MPL, indicate your
+# decision by deleting the provisions above and replace them with the notice
+# and other provisions required by the GPL or the LGPL. If you do not delete
+# the provisions above, a recipient may use your version of this file under
+# the terms of any one of the MPL, the GPL or the LGPL.
+#
+# ***** END LICENSE BLOCK *****
+
+XPCOM_GLUE_SRC_LCSRCS = \
+ nsCOMPtr.cpp \
+ nsComponentManagerUtils.cpp \
+ nsDebug.cpp \
+ nsGenericFactory.cpp \
+ nsIInterfaceRequestorUtils.cpp \
+ nsMemory.cpp \
+ nsTraceRefcnt.cpp \
+ nsWeakReference.cpp \
+ $(NULL) \
+
+XPCOM_GLUE_SRC_LEXPORTS = \
+ nsCOMPtr.h \
+ nsDebug.h \
+ nsGenericFactory.h \
+ nsIGenericFactory.h \
+ nsMemory.h \
+ nsTraceRefcnt.h \
+ nsWeakReference.h \
+ $(NULL)
+
+
+
+XPCOM_GLUE_SRC_CSRCS := $(addprefix $(topsrcdir)/xpcom/glue/, $(XPCOM_GLUE_SRC_LCSRCS))
diff --git a/src/libs/xpcom18a4/xpcom/glue/standalone/.cvsignore b/src/libs/xpcom18a4/xpcom/glue/standalone/.cvsignore
new file mode 100644
index 00000000..a0182c1f
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/standalone/.cvsignore
@@ -0,0 +1,8 @@
+Makefile
+nsCOMPtr.cpp
+nsDebug.cpp
+nsGenericFactory.cpp
+nsIInterfaceRequestorUtils.cpp
+nsMemory.cpp
+nsWeakReference.cpp
+nsComponentManagerUtils.cpp
diff --git a/src/libs/xpcom18a4/xpcom/glue/standalone/Makefile.in b/src/libs/xpcom18a4/xpcom/glue/standalone/Makefile.in
new file mode 100644
index 00000000..ae23d8e0
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/standalone/Makefile.in
@@ -0,0 +1,88 @@
+# ***** BEGIN LICENSE BLOCK *****
+# Version: MPL 1.1/GPL 2.0/LGPL 2.1
+#
+# The contents of this file are subject to the Mozilla Public License Version
+# 1.1 (the "License"); you may not use this file except in compliance with
+# the License. You may obtain a copy of the License at
+# http://www.mozilla.org/MPL/
+#
+# Software distributed under the License is distributed on an "AS IS" basis,
+# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+# for the specific language governing rights and limitations under the
+# License.
+#
+# The Original Code is mozilla.org.
+#
+# The Initial Developer of the Original Code is
+# Netscape Communications Corporation.
+# Portions created by the Initial Developer are Copyright (C) 2002
+# the Initial Developer. All Rights Reserved.
+#
+# Contributor(s):
+#
+# Alternatively, the contents of this file may be used under the terms of
+# either the GNU General Public License Version 2 or later (the "GPL"), or
+# the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+# in which case the provisions of the GPL or the LGPL are applicable instead
+# of those above. If you wish to allow use of your version of this file only
+# under the terms of either the GPL or the LGPL, and not to allow others to
+# use your version of this file under the terms of the MPL, indicate your
+# decision by deleting the provisions above and replace them with the notice
+# and other provisions required by the GPL or the LGPL. If you do not delete
+# the provisions above, a recipient may use your version of this file under
+# the terms of any one of the MPL, the GPL or the LGPL.
+#
+# ***** END LICENSE BLOCK *****
+
+DEPTH = ../../..
+topsrcdir = @top_srcdir@
+srcdir = @srcdir@
+VPATH = @srcdir@
+
+include $(DEPTH)/config/autoconf.mk
+include $(srcdir)/../objs.mk
+
+MODULE = xpcom
+LIBRARY_NAME = xpcomglue
+
+REQUIRES = string \
+ $(NULL)
+
+LOCAL_INCLUDES = \
+ -I$(srcdir)/../../build \
+ $(NULL)
+
+CPPSRCS = \
+ $(XPCOM_GLUE_SRC_LCSRCS) \
+ nsXPCOMGlue.cpp \
+ nsGREDirServiceProvider.cpp \
+ $(NULL)
+
+SDK_HEADERS = \
+ nsXPCOMGlue.h \
+ $(NULL)
+
+SDK_LIBRARY = \
+ $(LIB_PREFIX)xpcomglue.$(LIB_SUFFIX) \
+ $(NULL)
+
+# we don't want the shared lib, but we want to force the creation of a static lib.
+FORCE_STATIC_LIB = 1
+
+# Force use of PIC
+FORCE_USE_PIC = 1
+
+GARBAGE += $(XPCOM_GLUE_SRC_LCSRCS) $(wildcard *.$(OBJ_SUFFIX))
+
+ifeq ($(OS_ARCH),WINNT)
+GARBAGE += $(addprefix $(srcdir)/,$(XPCOM_GLUE_SRC_LCSRCS))
+endif
+
+SRCS_IN_OBJDIR = 1
+
+include $(topsrcdir)/config/rules.mk
+
+export:: $(XPCOM_GLUE_SRC_CSRCS)
+ $(INSTALL) $^ .
+
+DEFINES += -DXPCOM_GLUE
diff --git a/src/libs/xpcom18a4/xpcom/glue/standalone/nsGREDirServiceProvider.cpp b/src/libs/xpcom18a4/xpcom/glue/standalone/nsGREDirServiceProvider.cpp
new file mode 100644
index 00000000..4a1247eb
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/standalone/nsGREDirServiceProvider.cpp
@@ -0,0 +1,596 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is Mozilla Communicator.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corp.
+ * Portions created by the Initial Developer are Copyright (C) 2003
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ * Sean Su <ssu@netscape.com>
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either the GNU General Public License Version 2 or later (the "GPL"), or
+ * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#include "nsBuildID.h"
+
+#include "nsEmbedString.h"
+#include "nsXPCOMPrivate.h"
+#include "nsXPCOMGlue.h"
+#include "nsILocalFile.h"
+#include "nsIDirectoryService.h"
+#include "nsDirectoryServiceDefs.h"
+#include "nsCOMPtr.h"
+
+#include "nspr.h"
+#include "plstr.h"
+
+#ifdef XP_WIN32
+#include <windows.h>
+#include <stdlib.h>
+#elif defined(XP_OS2)
+#define INCL_DOS
+#include <os2.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include "prenv.h"
+#elif defined(XP_MACOSX)
+#include <Processes.h>
+#include <CFBundle.h>
+#elif defined(XP_UNIX)
+#include <unistd.h>
+#include <stdlib.h>
+#include <sys/param.h>
+#include <dlfcn.h>
+#include "prenv.h"
+#elif defined(XP_BEOS)
+#include <FindDirectory.h>
+#include <Path.h>
+#include <unistd.h>
+#include <stdlib.h>
+#include <sys/param.h>
+#include <OS.h>
+#include <image.h>
+#include "prenv.h"
+#endif
+
+#include <sys/stat.h>
+
+#include "nsGREDirServiceProvider.h"
+
+PRBool GRE_GetCurrentProcessDirectory(char* buffer);
+PRBool GRE_GetPathFromConfigDir(const char* dirname, char* buffer);
+PRBool GRE_GetPathFromConfigFile(const char* dirname, char* buffer);
+
+//*****************************************************************************
+// nsGREDirServiceProvider::nsISupports
+//*****************************************************************************
+
+NS_IMPL_ISUPPORTS1(nsGREDirServiceProvider, nsIDirectoryServiceProvider)
+
+//*****************************************************************************
+// nsGREDirServiceProvider::nsIDirectoryServiceProvider
+//*****************************************************************************
+
+NS_IMETHODIMP
+nsGREDirServiceProvider::GetFile(const char *prop, PRBool *persistant, nsIFile **_retval)
+{
+ *_retval = nsnull;
+ *persistant = PR_TRUE;
+
+ //---------------------------------------------------------------
+ // Note that by returning a valid localFile's for NS_GRE_DIR,
+ // your app is indicating to XPCOM that it found a GRE version
+ // with which it's compatible with and intends to be "run against"
+ // that GRE.
+ //
+ // Please see http://www.mozilla.org/projects/embedding/GRE.html
+ // for more info on GRE.
+ //---------------------------------------------------------------
+ if(strcmp(prop, NS_GRE_DIR) == 0)
+ {
+ nsILocalFile* lfile = nsnull;
+ nsresult rv = GRE_GetGREDirectory(&lfile);
+ *_retval = lfile;
+ return rv;
+ }
+
+ return NS_ERROR_FAILURE;
+}
+
+//*****************************************************************************
+// Implementations from nsXPCOMGlue.h and helper functions.
+//*****************************************************************************
+
+PRBool
+GRE_GetCurrentProcessDirectory(char* buffer)
+{
+ *buffer = '\0';
+
+#ifdef XP_WIN
+ if ( ::GetModuleFileName(0, buffer, MAXPATHLEN) ) {
+ // chop of the executable name by finding the rightmost backslash
+ char* lastSlash = PL_strrchr(buffer, '\\');
+ if (lastSlash) {
+ *(lastSlash) = '\0';
+ return PR_TRUE;
+ }
+ }
+
+#elif defined(XP_MACOSX)
+ // Works even if we're not bundled.
+ CFBundleRef appBundle = CFBundleGetMainBundle();
+ if (appBundle != nsnull)
+ {
+ CFURLRef bundleURL = CFBundleCopyExecutableURL(appBundle);
+ if (bundleURL != nsnull)
+ {
+ CFURLRef parentURL = CFURLCreateCopyDeletingLastPathComponent(kCFAllocatorDefault, bundleURL);
+ if (parentURL)
+ {
+ CFStringRef path = CFURLCopyFileSystemPath(parentURL, kCFURLPOSIXPathStyle);
+ if (path)
+ {
+ CFStringGetCString(path, buffer, MAXPATHLEN, kCFStringEncodingUTF8);
+ CFRelease(path);
+ }
+ CFRelease(parentURL);
+ }
+ CFRelease(bundleURL);
+ }
+#if 0 /* bird: Causes crashes in objc_msgSend() later if released. I dunno why really.
+ Something could be seriously screwed up somewhere else, but this'll have
+ to do for now. (appBundle isn't released in the other place it's used.) */
+ CFRelease(appBundle);
+#endif
+ }
+ if (*buffer) return PR_TRUE;
+
+#elif defined(XP_UNIX)
+
+#if 0 /* we need .so location. */
+ // Actually we have a way on linux.
+ static volatile bool fPathSet = false;
+ static char szPath[MAXPATHLEN];
+ if (!fPathSet)
+ {
+ char buf2[MAXPATHLEN + 3];
+ buf2[0] = '\0';
+
+ /*
+ * Env.var. VBOX_XPCOM_HOME first.
+ */
+ char *psz = PR_GetEnv("VBOX_XPCOM_HOME");
+ if (psz)
+ {
+ if (strlen(psz) < MAXPATHLEN)
+ {
+ if (!realpath(psz, buf2))
+ strcpy(buf2, psz);
+ strcat(buf2, "/x"); /* for the filename stripping */
+ }
+ }
+
+ /*
+ * The dynamic loader.
+ */
+ if (!buf2[0])
+ {
+ Dl_info DlInfo = {0};
+ if ( !dladdr((const void *)GRE_GetCurrentProcessDirectory, &DlInfo)
+ && DlInfo.dli_fname)
+ {
+ if (!realpath(DlInfo.dli_fname, buf2))
+ buf2[0] = '\0';
+ }
+ }
+
+ /*
+ * Executable location.
+ */
+ if (!buf2[0])
+ {
+ char buf[MAXPATHLEN];
+ int cchLink = readlink("/proc/self/exe", buf, sizeof(buf) - 1);
+ if (cchLink > 0 || cchLink != sizeof(buf) - 1)
+ {
+ buf[cchLink] = '\0';
+ if (!realpath(buf, buf2))
+ buf2[0] = '\0';
+ }
+ }
+
+ /*
+ * Copy to static buffer on success.
+ */
+ if (buf2[0])
+ {
+ char *p = strrchr(buf2, '/');
+ if (p)
+ {
+ p[p == buf2] = '\0';
+ #ifdef DEBUG
+ printf("debug: (1) VBOX_XPCOM_HOME=%s\n", buf2);
+ #endif
+ strcpy(szPath, buf2);
+ fPathSet = true;
+ }
+ }
+ }
+ if (fPathSet)
+ {
+ strcpy(buffer, szPath);
+ return PR_TRUE;
+ }
+#endif
+
+ // In the absence of a good way to get the executable directory let
+ // us try this for unix:
+ // - if VBOX_XPCOM_HOME is defined, that is it
+ // - else give the current directory
+
+ // The MOZ_DEFAULT_VBOX_XPCOM_HOME variable can be set at configure time with
+ // a --with-default-mozilla-five-home=foo autoconf flag.
+ //
+ // The idea here is to allow for builds that have a default VBOX_XPCOM_HOME
+ // regardless of the environment. This makes it easier to write apps that
+ // embed mozilla without having to worry about setting up the environment
+ //
+ // We do this py putenv()ing the default value into the environment. Note that
+ // we only do this if it is not already set.
+#ifdef MOZ_DEFAULT_VBOX_XPCOM_HOME
+ if (PR_GetEnv("VBOX_XPCOM_HOME") == nsnull)
+ {
+ putenv("VBOX_XPCOM_HOME=" MOZ_DEFAULT_VBOX_XPCOM_HOME);
+ }
+#endif
+
+ char *moz5 = PR_GetEnv("VBOX_XPCOM_HOME");
+
+ if (moz5 && *moz5)
+ {
+ if (!realpath(moz5, buffer))
+ strcpy(buffer, moz5);
+
+ return PR_TRUE;
+ }
+ else
+ {
+#if defined(DEBUG)
+ static PRBool firstWarning = PR_TRUE;
+
+ if(firstWarning) {
+ // Warn that VBOX_XPCOM_HOME not set, once.
+ printf("Warning: VBOX_XPCOM_HOME not set.\n");
+ firstWarning = PR_FALSE;
+ }
+#endif /* DEBUG */
+
+ // Fall back to current directory.
+ if (getcwd(buffer, MAXPATHLEN))
+ {
+ return PR_TRUE;
+ }
+ }
+
+#elif defined(XP_OS2)
+ PPIB ppib;
+ PTIB ptib;
+ char* p;
+ DosGetInfoBlocks( &ptib, &ppib);
+ DosQueryModuleName( ppib->pib_hmte, MAXPATHLEN, buffer);
+ p = strrchr( buffer, '\\'); // XXX DBCS misery
+ if (p) {
+ *p = '\0';
+ return PR_TRUE;
+ }
+
+#elif defined(XP_BEOS)
+
+ char *moz5 = getenv("VBOX_XPCOM_HOME");
+ if (moz5)
+ {
+ strcpy(buffer, moz5);
+ return PR_TRUE;
+ }
+ else
+ {
+ int32 cookie = 0;
+ image_info info;
+ char *p;
+ *buffer = 0;
+ if(get_next_image_info(0, &cookie, &info) == B_OK)
+ {
+ strcpy(buffer, info.name);
+ if((p = strrchr(buffer, '/')) != 0)
+ {
+ *p = 0;
+
+ return PR_TRUE;
+ }
+ }
+ }
+
+#endif
+
+ return PR_FALSE;
+}
+
+/**
+ * the GRE location is stored in a static buffer so that we don't have
+ * to compute it multiple times.
+ */
+
+static char sGRELocation[MAXPATHLEN] = "";
+
+extern "C" char const *
+GRE_GetGREPath()
+{
+ // we've already done this...
+ if (*sGRELocation)
+ return sGRELocation;
+
+ char buffer[MAXPATHLEN];
+
+ // If the xpcom library exists in the current process directory,
+ // then we will not use any GRE. The assumption here is that the
+ // GRE is in the same directory as the executable.
+ if (GRE_GetCurrentProcessDirectory(buffer)) {
+ PRUint32 pathlen = strlen(buffer);
+ strcpy(buffer + pathlen, XPCOM_FILE_PATH_SEPARATOR XPCOM_DLL);
+
+ struct stat libStat;
+ int statResult = stat(buffer, &libStat);
+
+ if (statResult != -1) {
+ //found our xpcom lib in the current process directory
+ buffer[pathlen] = '\0';
+ strcpy(sGRELocation, buffer);
+ return sGRELocation;
+ }
+ }
+
+ // if GRE_HOME is in the environment, use that GRE
+ const char* env = PR_GetEnv("GRE_HOME");
+ if (env && *env) {
+#if XP_UNIX
+ if (!realpath(env, sGRELocation))
+ strcpy(sGRELocation, env);
+#elif XP_WIN32
+ if (!_fullpath(sGRELocation, env, MAXPATHLEN))
+ strcpy(sGRELocation, env);
+#endif
+ // xxxbsmedberg: it would help that other platforms had a "make absolute" function
+ return sGRELocation;
+ }
+
+ // the Gecko bits that sit next to the application or in the LD_LIBRARY_PATH
+ env = PR_GetEnv("USE_LOCAL_GRE");
+ if (env && *env)
+ return nsnull;
+
+#if XP_UNIX
+ // check in the HOME directory
+ env = PR_GetEnv("HOME");
+ if (env && *env) {
+# ifdef VBOX
+ snprintf(buffer, sizeof(buffer), "%s" XPCOM_FILE_PATH_SEPARATOR GRE_CONF_NAME, env);
+# else
+ sprintf(buffer, "%s" XPCOM_FILE_PATH_SEPARATOR GRE_CONF_NAME, env);
+# endif
+
+ if (GRE_GetPathFromConfigFile(buffer, sGRELocation)) {
+ return sGRELocation;
+ }
+ }
+#endif
+
+ env = PR_GetEnv("MOZ_GRE_CONF");
+ if (env) {
+ if (GRE_GetPathFromConfigFile(env, sGRELocation)) {
+ return sGRELocation;
+ }
+ }
+
+#if XP_UNIX
+ // Look for a group of config files in /etc/gre.d/
+ if (GRE_GetPathFromConfigDir(GRE_CONF_DIR, sGRELocation)) {
+ return sGRELocation;
+ }
+
+ // Look for a global /etc/gre.conf file
+ if (GRE_GetPathFromConfigFile(GRE_CONF_PATH, sGRELocation)) {
+ return sGRELocation;
+ }
+#endif
+
+#if XP_WIN32
+ char szKey[256];
+ HKEY hRegKey = NULL;
+ DWORD dwLength = MAXPATHLEN;
+
+ // A couple of key points here:
+ // 1. Note the usage of the "Software\\Mozilla\\GRE" subkey - this allows
+ // us to have multiple versions of GREs on the same machine by having
+ // subkeys such as 1.0, 1.1, 2.0 etc. under it.
+ // 2. In this sample below we're looking for the location of GRE version 1.2
+ // i.e. we're compatible with GRE 1.2 and we're trying to find it's install
+ // location.
+ //
+ // Please see http://www.mozilla.org/projects/embedding/GRE.html for
+ // more info.
+ //
+ strcpy(szKey, GRE_WIN_REG_LOC GRE_BUILD_ID);
+
+ if (::RegOpenKeyEx(HKEY_CURRENT_USER, szKey, 0, KEY_QUERY_VALUE, &hRegKey) == ERROR_SUCCESS) {
+ if (::RegQueryValueEx(hRegKey, "GreHome", NULL, NULL, (BYTE *)sGRELocation, &dwLength) != ERROR_SUCCESS) {
+ *sGRELocation = '\0';
+ }
+ ::RegCloseKey(hRegKey);
+
+ if (*sGRELocation)
+ return sGRELocation;
+ }
+
+ if (::RegOpenKeyEx(HKEY_LOCAL_MACHINE, szKey, 0, KEY_QUERY_VALUE, &hRegKey) == ERROR_SUCCESS) {
+ if (::RegQueryValueEx(hRegKey, "GreHome", NULL, NULL, (BYTE *)sGRELocation, &dwLength) != ERROR_SUCCESS) {
+ *sGRELocation = '\0';
+ }
+ ::RegCloseKey(hRegKey);
+
+ if (*sGRELocation)
+ return sGRELocation;
+ }
+#endif
+
+ return nsnull;
+}
+
+PRBool
+GRE_GetPathFromConfigDir(const char* dirname, char* buffer)
+{
+ // Open the directory provided and try to read any files in that
+ // directory that end with .conf. We look for an entry that might
+ // point to the GRE that we're interested in.
+ PRDir *dir = PR_OpenDir(dirname);
+ if (!dir)
+ return nsnull;
+
+ PRBool found = PR_FALSE;
+ PRDirEntry *entry;
+
+ while (!found && (entry = PR_ReadDir(dir, PR_SKIP_BOTH))) {
+
+ // Only look for files that end in .conf
+ char *offset = PL_strrstr(entry->name, ".conf");
+ if (!offset)
+ continue;
+
+ if (offset != entry->name + strlen(entry->name) - 5)
+ continue;
+
+ nsEmbedCString fullPath;
+ NS_CStringAppendData(fullPath, dirname);
+ NS_CStringAppendData(fullPath, XPCOM_FILE_PATH_SEPARATOR);
+ NS_CStringAppendData(fullPath, entry->name);
+
+ found = GRE_GetPathFromConfigFile(fullPath.get(), buffer);
+ }
+
+ PR_CloseDir(dir);
+
+ return found;
+}
+
+PRBool
+GRE_GetPathFromConfigFile(const char* filename, char* pathBuffer)
+{
+ *pathBuffer = '\0';
+ char buffer[1024];
+ FILE *cfg;
+ PRBool foundHeader = PR_FALSE;
+ PRInt32 versionLen = sizeof(GRE_BUILD_ID)-1;
+
+ if((cfg=fopen(filename,"r"))==nsnull) {
+ return nsnull;
+ }
+
+ while (fgets(buffer, 1024, cfg) != nsnull) {
+ // skip over comment lines and blank lines
+ if (buffer[0] == '#' || buffer[0] == '\n') {
+ continue;
+ }
+
+ // we found a section heading, check to see if it is the one we are intersted in.
+ if (buffer[0] == '[') {
+ if (!strncmp (buffer+1, GRE_BUILD_ID, versionLen)) {
+ foundHeader = PR_TRUE;
+ }
+ continue;
+ }
+
+ if (foundHeader && !strncmp (buffer, "GRE_PATH=", 9)) {
+ strcpy(pathBuffer, buffer + 9);
+ // kill the line feed if any
+ PRInt32 len = strlen(pathBuffer);
+ len--;
+
+ if (pathBuffer[len] == '\n')
+ pathBuffer[len] = '\0';
+ break;
+ }
+ }
+ fclose(cfg);
+ return (*pathBuffer != '\0');
+}
+
+extern "C" nsresult
+GRE_GetGREDirectory(nsILocalFile* *_retval)
+{
+ NS_ENSURE_ARG_POINTER(_retval);
+ nsresult rv = NS_ERROR_FAILURE;
+
+ // Get the path of the GRE which is compatible with our embedding application
+ // from the registry
+
+ const char *pGREDir = GRE_GetGREPath();
+ if(pGREDir) {
+ nsCOMPtr<nsILocalFile> tempLocal;
+ nsEmbedCString leaf;
+ NS_CStringSetData(leaf, pGREDir);
+ rv = NS_NewNativeLocalFile(leaf, PR_TRUE, getter_AddRefs(tempLocal));
+
+ if (NS_SUCCEEDED(rv)) {
+ *_retval = tempLocal;
+ NS_ADDREF(*_retval);
+ }
+ }
+ return rv;
+}
+
+static char sXPCOMPath[MAXPATHLEN];
+
+extern "C" const char*
+GRE_GetXPCOMPath()
+{
+ const char* grePath = GRE_GetGREPath();
+
+ if (!grePath) {
+ grePath = PR_GetEnv("VBOX_XPCOM_HOME");
+ if (!grePath || !*grePath) {
+ return nsnull;
+ }
+ }
+
+#ifdef VBOX
+ snprintf(sXPCOMPath, sizeof(sXPCOMPath), "%s" XPCOM_FILE_PATH_SEPARATOR XPCOM_DLL, grePath);
+#else
+ sprintf(sXPCOMPath, "%s" XPCOM_FILE_PATH_SEPARATOR XPCOM_DLL, grePath);
+#endif
+
+ return sXPCOMPath;
+}
diff --git a/src/libs/xpcom18a4/xpcom/glue/standalone/nsGREDirServiceProvider.h b/src/libs/xpcom18a4/xpcom/glue/standalone/nsGREDirServiceProvider.h
new file mode 100644
index 00000000..0638a127
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/standalone/nsGREDirServiceProvider.h
@@ -0,0 +1,68 @@
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is Mozilla Communicator.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corp.
+ * Portions created by the Initial Developer are Copyright (C) 2003
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ * Sean Su <ssu@netscape.com>
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either the GNU General Public License Version 2 or later (the "GPL"), or
+ * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#ifndef nsGREDirServiceProvider_h_
+#define nsGREDirServiceProvider_h_
+
+#include "nsIDirectoryService.h"
+
+#ifndef MAXPATHLEN
+#ifdef _MAX_PATH
+#define MAXPATHLEN _MAX_PATH
+#elif defined(CCHMAXPATH)
+#define MAXPATHLEN CCHMAXPATH
+#else
+#define MAXPATHLEN 1024
+#endif
+#endif
+
+/**
+ * the directoryserviceprovider used by GRE_Startup when calling NS_InitXPCOM2
+ */
+class nsGREDirServiceProvider : public nsIDirectoryServiceProvider
+{
+public:
+ nsGREDirServiceProvider() { }
+
+ NS_DECL_ISUPPORTS
+ NS_DECL_NSIDIRECTORYSERVICEPROVIDER
+
+private:
+ ~nsGREDirServiceProvider() { }
+};
+
+#endif // nsGREDirServiceProvider.h
diff --git a/src/libs/xpcom18a4/xpcom/glue/standalone/nsXPCOMGlue.cpp b/src/libs/xpcom18a4/xpcom/glue/standalone/nsXPCOMGlue.cpp
new file mode 100644
index 00000000..091538fa
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/standalone/nsXPCOMGlue.cpp
@@ -0,0 +1,524 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/* vim:set ts=4 sw=4 et cindent: */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#include "nsXPCOMGlue.h"
+
+#include "nspr.h"
+#include "nsMemory.h"
+#include "nsGREDirServiceProvider.h"
+#include "nsXPCOMPrivate.h"
+#include <stdlib.h>
+#ifdef VBOX
+# include <limits.h>
+#endif
+
+#if XP_WIN32
+#include <windows.h>
+#endif
+
+void GRE_AddGREToEnvironment();
+
+// functions provided by nsMemory.cpp and nsDebug.cpp
+nsresult GlueStartupMemory();
+void GlueShutdownMemory();
+nsresult GlueStartupDebug();
+void GlueShutdownDebug();
+
+static PRLibrary *xpcomLib;
+static XPCOMFunctions xpcomFunctions;
+
+extern "C"
+nsresult XPCOMGlueStartup(const char* xpcomFile)
+{
+#ifdef XPCOM_GLUE_NO_DYNAMIC_LOADING
+ return NS_OK;
+#else
+ nsresult rv = NS_OK;
+ GetFrozenFunctionsFunc function = nsnull;
+
+ xpcomFunctions.version = XPCOM_GLUE_VERSION;
+ xpcomFunctions.size = sizeof(XPCOMFunctions);
+
+ //
+ // if xpcomFile == ".", then we assume xpcom is already loaded, and we'll
+ // use NSPR to find NS_GetFrozenFunctions from the list of already loaded
+ // libraries.
+ //
+ // otherwise, we try to load xpcom and then look for NS_GetFrozenFunctions.
+ // if xpcomFile == NULL, then we try to load xpcom by name w/o a fully
+ // qualified path.
+ //
+
+ if (xpcomFile && (xpcomFile[0] == '.' && xpcomFile[1] == '\0')) {
+ function = (GetFrozenFunctionsFunc)
+ PR_FindSymbolAndLibrary("NS_GetFrozenFunctions", &xpcomLib);
+ if (!function) {
+ // The symbol was not found, so failover to loading XPCOM_DLL,
+ // and look for the symbol there. See bug 240986 for details.
+ xpcomFile = nsnull;
+ }
+ else {
+ char *libPath = PR_GetLibraryFilePathname(XPCOM_DLL, (PRFuncPtr) function);
+ if (!libPath)
+ rv = NS_ERROR_FAILURE;
+ else {
+ rv = (*function)(&xpcomFunctions, libPath);
+ PR_Free(libPath);
+ }
+ }
+ }
+
+ if (!function) {
+ PRLibSpec libSpec;
+
+ libSpec.type = PR_LibSpec_Pathname;
+ if (!xpcomFile)
+ libSpec.value.pathname = XPCOM_DLL;
+ else
+ libSpec.value.pathname = xpcomFile;
+
+ xpcomLib = PR_LoadLibraryWithFlags(libSpec, PR_LD_LAZY|PR_LD_GLOBAL);
+#ifdef RT_OS_DARWIN /* vbox */
+ /* works around bundle problem. */
+ if (!xpcomLib) {
+ const char *home = PR_GetEnv("VBOX_XPCOM_HOME");
+ if (home) {
+ char path[PATH_MAX];
+ snprintf(path, sizeof(path), "%s/%s", home, libSpec.value.pathname);
+ libSpec.value.pathname = path;
+ xpcomLib = PR_LoadLibraryWithFlags(libSpec, PR_LD_LAZY|PR_LD_GLOBAL);
+ }
+ }
+#endif
+ if (!xpcomLib)
+ return NS_ERROR_FAILURE;
+
+ function = (GetFrozenFunctionsFunc) PR_FindSymbol(xpcomLib, "NS_GetFrozenFunctions");
+
+ if (!function)
+ rv = NS_ERROR_FAILURE;
+ else
+ rv = (*function)(&xpcomFunctions, libSpec.value.pathname);
+ }
+
+ if (NS_FAILED(rv))
+ goto bail;
+
+ rv = GlueStartupDebug();
+ if (NS_FAILED(rv))
+ goto bail;
+
+ // startup the nsMemory
+ rv = GlueStartupMemory();
+ if (NS_FAILED(rv)) {
+ GlueShutdownDebug();
+ goto bail;
+ }
+
+ GRE_AddGREToEnvironment();
+ return NS_OK;
+
+bail:
+ PR_UnloadLibrary(xpcomLib);
+ xpcomLib = nsnull;
+ memset(&xpcomFunctions, 0, sizeof(xpcomFunctions));
+ return NS_ERROR_FAILURE;
+#endif
+}
+
+extern "C"
+nsresult XPCOMGlueShutdown()
+{
+#ifdef XPCOM_GLUE_NO_DYNAMIC_LOADING
+ return NS_OK;
+#else
+
+ GlueShutdownMemory();
+
+ GlueShutdownDebug();
+
+ if (xpcomLib) {
+ PR_UnloadLibrary(xpcomLib);
+ xpcomLib = nsnull;
+ }
+
+ memset(&xpcomFunctions, 0, sizeof(xpcomFunctions));
+ return NS_OK;
+#endif
+}
+
+#ifndef XPCOM_GLUE_NO_DYNAMIC_LOADING
+extern "C" NS_COM nsresult
+NS_InitXPCOM2(nsIServiceManager* *result,
+ nsIFile* binDirectory,
+ nsIDirectoryServiceProvider* appFileLocationProvider)
+{
+ if (!xpcomFunctions.init)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.init(result, binDirectory, appFileLocationProvider);
+}
+
+extern "C" NS_COM nsresult
+NS_ShutdownXPCOM(nsIServiceManager* servMgr)
+{
+ if (!xpcomFunctions.shutdown)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.shutdown(servMgr);
+}
+
+extern "C" NS_COM nsresult
+NS_GetServiceManager(nsIServiceManager* *result)
+{
+ if (!xpcomFunctions.getServiceManager)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.getServiceManager(result);
+}
+
+extern "C" NS_COM nsresult
+NS_GetComponentManager(nsIComponentManager* *result)
+{
+ if (!xpcomFunctions.getComponentManager)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.getComponentManager(result);
+}
+
+extern "C" NS_COM nsresult
+NS_GetComponentRegistrar(nsIComponentRegistrar* *result)
+{
+ if (!xpcomFunctions.getComponentRegistrar)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.getComponentRegistrar(result);
+}
+
+extern "C" NS_COM nsresult
+NS_GetMemoryManager(nsIMemory* *result)
+{
+ if (!xpcomFunctions.getMemoryManager)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.getMemoryManager(result);
+}
+
+extern "C" NS_COM nsresult
+NS_NewLocalFile(const nsAString &path, PRBool followLinks, nsILocalFile* *result)
+{
+ if (!xpcomFunctions.newLocalFile)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.newLocalFile(path, followLinks, result);
+}
+
+extern "C" NS_COM nsresult
+NS_NewNativeLocalFile(const nsACString &path, PRBool followLinks, nsILocalFile* *result)
+{
+ if (!xpcomFunctions.newNativeLocalFile)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.newNativeLocalFile(path, followLinks, result);
+}
+
+extern "C" NS_COM nsresult
+NS_RegisterXPCOMExitRoutine(XPCOMExitRoutine exitRoutine, PRUint32 priority)
+{
+ if (!xpcomFunctions.registerExitRoutine)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.registerExitRoutine(exitRoutine, priority);
+}
+
+extern "C" NS_COM nsresult
+NS_UnregisterXPCOMExitRoutine(XPCOMExitRoutine exitRoutine)
+{
+ if (!xpcomFunctions.unregisterExitRoutine)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.unregisterExitRoutine(exitRoutine);
+}
+
+extern "C" NS_COM nsresult
+NS_GetDebug(nsIDebug* *result)
+{
+ if (!xpcomFunctions.getDebug)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.getDebug(result);
+}
+
+
+extern "C" NS_COM nsresult
+NS_GetTraceRefcnt(nsITraceRefcnt* *result)
+{
+ if (!xpcomFunctions.getTraceRefcnt)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.getTraceRefcnt(result);
+}
+
+
+extern "C" NS_COM nsresult
+NS_StringContainerInit(nsStringContainer &aStr)
+{
+ if (!xpcomFunctions.stringContainerInit)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.stringContainerInit(aStr);
+}
+
+extern "C" NS_COM void
+NS_StringContainerFinish(nsStringContainer &aStr)
+{
+ if (xpcomFunctions.stringContainerFinish)
+ xpcomFunctions.stringContainerFinish(aStr);
+}
+
+extern "C" NS_COM PRUint32
+NS_StringGetData(const nsAString &aStr, const PRUnichar **aBuf, PRBool *aTerm)
+{
+ if (!xpcomFunctions.stringGetData) {
+ *aBuf = nsnull;
+ return 0;
+ }
+ return xpcomFunctions.stringGetData(aStr, aBuf, aTerm);
+}
+
+extern "C" NS_COM PRUnichar *
+NS_StringCloneData(const nsAString &aStr)
+{
+ if (!xpcomFunctions.stringCloneData)
+ return nsnull;
+ return xpcomFunctions.stringCloneData(aStr);
+}
+
+extern "C" NS_COM nsresult
+NS_StringSetData(nsAString &aStr, const PRUnichar *aBuf, PRUint32 aCount)
+{
+ if (!xpcomFunctions.stringSetData)
+ return NS_ERROR_NOT_INITIALIZED;
+
+ return xpcomFunctions.stringSetData(aStr, aBuf, aCount);
+}
+
+extern "C" NS_COM nsresult
+NS_StringSetDataRange(nsAString &aStr, PRUint32 aCutStart, PRUint32 aCutLength,
+ const PRUnichar *aBuf, PRUint32 aCount)
+{
+ if (!xpcomFunctions.stringSetDataRange)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.stringSetDataRange(aStr, aCutStart, aCutLength, aBuf, aCount);
+}
+
+extern "C" NS_COM nsresult
+NS_StringCopy(nsAString &aDest, const nsAString &aSrc)
+{
+ if (!xpcomFunctions.stringCopy)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.stringCopy(aDest, aSrc);
+}
+
+
+extern "C" NS_COM nsresult
+NS_CStringContainerInit(nsCStringContainer &aStr)
+{
+ if (!xpcomFunctions.cstringContainerInit)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.cstringContainerInit(aStr);
+}
+
+extern "C" NS_COM void
+NS_CStringContainerFinish(nsCStringContainer &aStr)
+{
+ if (xpcomFunctions.cstringContainerFinish)
+ xpcomFunctions.cstringContainerFinish(aStr);
+}
+
+extern "C" NS_COM PRUint32
+NS_CStringGetData(const nsACString &aStr, const char **aBuf, PRBool *aTerm)
+{
+ if (!xpcomFunctions.cstringGetData) {
+ *aBuf = nsnull;
+ return 0;
+ }
+ return xpcomFunctions.cstringGetData(aStr, aBuf, aTerm);
+}
+
+extern "C" NS_COM char *
+NS_CStringCloneData(const nsACString &aStr)
+{
+ if (!xpcomFunctions.cstringCloneData)
+ return nsnull;
+ return xpcomFunctions.cstringCloneData(aStr);
+}
+
+extern "C" NS_COM nsresult
+NS_CStringSetData(nsACString &aStr, const char *aBuf, PRUint32 aCount)
+{
+ if (!xpcomFunctions.cstringSetData)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.cstringSetData(aStr, aBuf, aCount);
+}
+
+extern "C" NS_COM nsresult
+NS_CStringSetDataRange(nsACString &aStr, PRUint32 aCutStart, PRUint32 aCutLength,
+ const char *aBuf, PRUint32 aCount)
+{
+ if (!xpcomFunctions.cstringSetDataRange)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.cstringSetDataRange(aStr, aCutStart, aCutLength, aBuf, aCount);
+}
+
+extern "C" NS_COM nsresult
+NS_CStringCopy(nsACString &aDest, const nsACString &aSrc)
+{
+ if (!xpcomFunctions.cstringCopy)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.cstringCopy(aDest, aSrc);
+}
+
+extern "C" NS_COM nsresult
+NS_CStringToUTF16(const nsACString &aSrc, PRUint32 aSrcEncoding, nsAString &aDest)
+{
+ if (!xpcomFunctions.cstringToUTF16)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.cstringToUTF16(aSrc, aSrcEncoding, aDest);
+}
+
+extern "C" NS_COM nsresult
+NS_UTF16ToCString(const nsAString &aSrc, PRUint32 aDestEncoding, nsACString &aDest)
+{
+ if (!xpcomFunctions.utf16ToCString)
+ return NS_ERROR_NOT_INITIALIZED;
+ return xpcomFunctions.utf16ToCString(aSrc, aDestEncoding, aDest);
+}
+
+#endif // #ifndef XPCOM_GLUE_NO_DYNAMIC_LOADING
+
+
+static char sEnvString[MAXPATHLEN*10];
+static char* spEnvString = 0;
+
+void
+GRE_AddGREToEnvironment()
+{
+ const char* grePath = GRE_GetGREPath();
+ char szPath[MAXPATHLEN];
+ if (!grePath)
+ return;
+
+ const char* path = PR_GetEnv(XPCOM_SEARCH_KEY);
+ if (!path)
+ path = "";
+#ifdef VBOX
+ else
+ {
+ /* sEnvString is part of the environment because of putenv().
+ * path is only temporarily used and not argument of putenv() itself */
+ snprintf(szPath, sizeof(szPath), "%s", path);
+ path = szPath;
+ }
+#endif
+
+ if (spEnvString) PR_smprintf_free(spEnvString);
+
+ /**
+ * if the PATH string is longer than our static buffer, allocate a
+ * buffer for the environment string. This buffer will be leaked at shutdown!
+ */
+ if (strlen(grePath) + strlen(path) +
+ sizeof(XPCOM_SEARCH_KEY) + sizeof(XPCOM_ENV_PATH_SEPARATOR) > MAXPATHLEN*10) {
+ if (PR_smprintf(XPCOM_SEARCH_KEY "=%s" XPCOM_ENV_PATH_SEPARATOR "%s",
+ grePath,
+ path)) {
+ PR_SetEnv(spEnvString);
+ }
+ } else {
+ if (sprintf(sEnvString,
+ XPCOM_SEARCH_KEY "=%s" XPCOM_ENV_PATH_SEPARATOR "%s",
+ grePath,
+ path) > 0) {
+ PR_SetEnv(sEnvString);
+ }
+ }
+
+#if XP_WIN32
+ // On windows, the current directory is searched before the
+ // PATH environment variable. This is a very bad thing
+ // since libraries in the cwd will be picked up before
+ // any that are in either the application or GRE directory.
+
+ if (grePath) {
+ SetCurrentDirectory(grePath);
+ }
+#endif
+}
+
+
+// Default GRE startup/shutdown code
+
+extern "C"
+nsresult GRE_Startup()
+{
+ const char* xpcomLocation = GRE_GetXPCOMPath();
+
+ // Startup the XPCOM Glue that links us up with XPCOM.
+ nsresult rv = XPCOMGlueStartup(xpcomLocation);
+
+ if (NS_FAILED(rv)) {
+ NS_WARNING("gre: XPCOMGlueStartup failed");
+ return rv;
+ }
+
+ nsGREDirServiceProvider *provider = new nsGREDirServiceProvider();
+ if ( !provider ) {
+ NS_WARNING("GRE_Startup failed");
+ XPCOMGlueShutdown();
+ return NS_ERROR_OUT_OF_MEMORY;
+ }
+
+ nsCOMPtr<nsIServiceManager> servMan;
+ NS_ADDREF( provider );
+ rv = NS_InitXPCOM2(getter_AddRefs(servMan), nsnull, provider);
+ NS_RELEASE(provider);
+
+ if ( NS_FAILED(rv) || !servMan) {
+ NS_WARNING("gre: NS_InitXPCOM failed");
+ XPCOMGlueShutdown();
+ return rv;
+ }
+
+ return NS_OK;
+}
+
+extern "C"
+nsresult GRE_Shutdown()
+{
+ NS_ShutdownXPCOM(nsnull);
+ XPCOMGlueShutdown();
+ return NS_OK;
+}
diff --git a/src/libs/xpcom18a4/xpcom/glue/standalone/nsXPCOMGlue.h b/src/libs/xpcom18a4/xpcom/glue/standalone/nsXPCOMGlue.h
new file mode 100644
index 00000000..6044e084
--- /dev/null
+++ b/src/libs/xpcom18a4/xpcom/glue/standalone/nsXPCOMGlue.h
@@ -0,0 +1,109 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Netscape Communications Corporation.
+ * Portions created by the Initial Developer are Copyright (C) 1998
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either of the GNU General Public License Version 2 or later (the "GPL"),
+ * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#include "nscore.h"
+
+class nsILocalFile;
+
+/**
+ * Initialize the XPCOM glue by dynamically linking against the XPCOM
+ * shared library indicated by xpcomFile.
+ */
+
+extern "C"
+nsresult XPCOMGlueStartup(const char* xpcomFile);
+
+
+/**
+ * Finish the XPCOM glue after it is no longer needed.
+ */
+
+extern "C"
+nsresult XPCOMGlueShutdown();
+
+
+/**
+ * Locate the path of a compatible GRE.
+ *
+ * @return string buffer pointing to the GRE path (without a trailing
+ * directory separator). Callers do no need to free this buffer.
+ */
+
+extern "C"
+char const * GRE_GetGREPath();
+
+
+/**
+ * Locate the path of a compatible GRE. This is returned as an
+ * nsILocalFile instead of a char*.
+ *
+ * @param _retval Ordinary XPCOM getter, returns an addrefed interface.
+ */
+
+extern "C"
+nsresult GRE_GetGREDirectory(nsILocalFile* *_retval);
+
+
+/**
+ * Locate the path of the XPCOM binary of a compatible GRE.
+ * The result of this function is normally passed directly to
+ * XPCOMGlueStartup.
+ *
+ * @return string buffer pointing to the XPCOM DLL path. Callers do
+ * not need to free this buffer.
+ */
+
+extern "C"
+char const * GRE_GetXPCOMPath();
+
+
+/**
+ * Embedding applications which don't need a custom
+ * directoryserviceprovider may use GRE_Startup to start the XPCOM
+ * glue and initialize the GRE in one step.
+ */
+
+extern "C"
+nsresult GRE_Startup();
+
+
+/**
+ * Shut down XPCOM and the XPCOM glue in one step.
+ */
+
+extern "C"
+nsresult GRE_Shutdown();