[Author: zork]
[google-gears.git] / gears / base / common / base_class.h
blob0eaaa35f3b800d3e3424cc66531e70574f6df300
1 // Copyright 2006, Google Inc.
2 //
3 // Redistribution and use in source and binary forms, with or without
4 // modification, are permitted provided that the following conditions are met:
5 //
6 // 1. Redistributions of source code must retain the above copyright notice,
7 // this list of conditions and the following disclaimer.
8 // 2. Redistributions in binary form must reproduce the above copyright notice,
9 // this list of conditions and the following disclaimer in the documentation
10 // and/or other materials provided with the distribution.
11 // 3. Neither the name of Google Inc. nor the names of its contributors may be
12 // used to endorse or promote products derived from this software without
13 // specific prior written permission.
15 // THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
16 // WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
17 // MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
18 // EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
19 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
20 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
21 // OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
22 // WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
23 // OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
24 // ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 // The C++ base class that all Gears objects should derive from.
28 #ifndef GEARS_BASE_COMMON_BASE_CLASS_H__
29 #define GEARS_BASE_COMMON_BASE_CLASS_H__
31 #include "gears/base/common/common.h" // for DISALLOW_EVIL_CONSTRUCTORS
32 #include "gears/base/common/scoped_token.h"
33 #include "gears/base/common/security_model.h"
34 #include "gears/base/common/string16.h" // for string16
36 #include "gears/base/common/js_types.h"
38 #if BROWSER_FF
40 #include "ff/genfiles/base_interface_ff.h"
42 #elif BROWSER_IE
44 // no "base_interface_ie.h" because IE doesn't require a COM base interface
46 #elif BROWSER_NPAPI
48 // no "base_interface_npapi.h" because NPAPI doesn't use COM.
50 #endif
52 #if BROWSER_FF
54 // Implementations of boilerplate code.
55 #define GEARS_IMPL_BASECLASS \
56 NS_IMETHOD GetNativeBaseClass(ModuleImplBaseClass **retval) { \
57 *retval = this; \
58 return NS_OK; \
61 #elif BROWSER_IE
62 #elif BROWSER_NPAPI
63 #elif BROWSER_SAFARI
64 #endif // BROWSER_xyz
66 class ModuleWrapperBaseClass;
67 class JsRunnerInterface;
69 // Exposes the minimal set of information that Gears objects need to work
70 // consistently across the main-thread and worker-thread JavaScript engines.
71 class ModuleImplBaseClass {
72 public:
73 // TODO_REMOVE_NSISUPPORTS: this constructor only used for isupports-based
74 // modules.
75 ModuleImplBaseClass()
76 : module_name_(NULL), is_initialized_(false) {}
77 explicit ModuleImplBaseClass(const char *name)
78 : module_name_(name), is_initialized_(false) {}
80 const char *get_module_name() const {
81 return module_name_;
84 // Initialization functions
86 // Init from sibling -- should be used for most objects.
87 // Init from DOM -- should only be used for main-thread factories.
88 bool InitBaseFromSibling(const ModuleImplBaseClass *other);
89 #if BROWSER_FF
90 bool InitBaseFromDOM();
91 #elif BROWSER_IE
92 bool InitBaseFromDOM(IUnknown *site);
93 #elif BROWSER_NPAPI
94 bool InitBaseFromDOM(JsContextPtr instance);
95 #elif BROWSER_SAFARI
96 bool InitBaseFromDOM(const char *url_str);
97 #endif
99 // Host environment information
100 bool EnvIsWorker() const;
101 const std::string16& EnvPageLocationUrl() const;
102 #if BROWSER_FF || BROWSER_NPAPI
103 JsContextPtr EnvPageJsContext() const;
104 #elif BROWSER_IE
105 IUnknown* EnvPageIUnknownSite() const;
106 #endif
107 const SecurityOrigin& EnvPageSecurityOrigin() const;
109 JsRunnerInterface *GetJsRunner() const;
111 #if BROWSER_FF
112 // JavaScript worker-thread parameter information
113 void JsWorkerSetParams(int argc, JsToken *argv, JsToken *retval);
114 int JsWorkerGetArgc() const;
115 JsToken* JsWorkerGetArgv() const;
116 JsToken* JsWorkerGetRetVal() const;
117 #elif BROWSER_IE
118 // These do not exist in IE yet.
119 #endif
121 // Methods for dealing with the JavaScript wrapper interface.
122 void SetJsWrapper(ModuleWrapperBaseClass *wrapper) { js_wrapper_ = wrapper; }
123 ModuleWrapperBaseClass *GetWrapper() const {
124 assert(js_wrapper_);
125 return js_wrapper_;
127 void AddReference();
128 void RemoveReference();
130 // TODO(aa): Remove and replace call sites with GetWrapper()->GetToken().
131 JsToken GetWrapperToken() const;
133 private:
134 // TODO(cprince): This state should be constant per (thread,page) tuple.
135 // Instead of making a copy for every object (ModuleImplBaseClass), we could
136 // keep a reference to one shared class per tuple.
137 // (Recall idea for PageSharedState + PageThreadSharedState classes.)
138 const char *module_name_;
139 bool is_initialized_;
140 bool env_is_worker_;
141 #if BROWSER_FF || BROWSER_NPAPI
142 // TODO_REMOVE_NSISUPPORTS: Remove this member once all modules are based on
143 // Dispatcher. env_page_js_context_ is only really used to initialize
144 // JsParamFetcher, which isn't needed with Dispatcher.
145 JsContextPtr env_page_js_context_;
146 #elif BROWSER_IE
147 // Pointer to the object that hosts this object. On Win32, this is the pointer
148 // passed to SetSite. On WinCE this is the JS IDispatch pointer.
149 CComPtr<IUnknown> env_page_iunknown_site_;
150 #endif
151 SecurityOrigin env_page_origin_;
153 // Init manually -- should only be used for worker-thread factories.
154 friend class PoolThreadsManager;
155 bool InitBaseManually(bool is_worker,
156 #if BROWSER_FF || BROWSER_NPAPI
157 JsContextPtr cx,
158 #elif BROWSER_IE
159 IUnknown *site,
160 #endif
161 const SecurityOrigin &page_origin,
162 JsRunnerInterface *js_runner);
164 #if BROWSER_FF
165 int worker_js_argc_;
166 JsToken *worker_js_argv_;
167 JsToken *worker_js_retval_;
168 #elif BROWSER_IE
169 // These do not exist in IE yet.
170 #endif
172 JsRunnerInterface *js_runner_;
173 // Weak pointer to our JavaScript wrapper.
174 ModuleWrapperBaseClass *js_wrapper_;
176 DISALLOW_EVIL_CONSTRUCTORS(ModuleImplBaseClass);
180 // ModuleWrapper has a member scoped_ptr<ModuleImplBaseClass>, so this
181 // destructor needs to be virtual. However, adding a virtual destructor
182 // causes a crash in Firefox because nsCOMPtr expects (nsISupports *)ptr ==
183 // (ModuleImplBaseClass *)ptr. Therefore, until we convert all the old XPCOM-
184 // based firefox modules to be Dispatcher-based, we need this separate base
185 // class.
186 // TODO_REMOVE_NSISUPPORTS: Remove this class and make ~ModuleImplBaseClass
187 // virtual when this is the only ModuleImplBaseClass.
188 class ModuleImplBaseClassVirtual : public ModuleImplBaseClass {
189 public:
190 ModuleImplBaseClassVirtual() : ModuleImplBaseClass() {}
191 ModuleImplBaseClassVirtual(const char *name) : ModuleImplBaseClass(name) {}
192 virtual ~ModuleImplBaseClassVirtual(){}
194 private:
195 DISALLOW_EVIL_CONSTRUCTORS(ModuleImplBaseClassVirtual);
198 class DispatcherInterface;
200 // Interface for the wrapper class that binds the Gears object to the
201 // JavaScript engine.
202 class ModuleWrapperBaseClass {
203 public:
204 // Returns a token for this wrapper class that can be returned via the
205 // JsRunnerInterface.
206 virtual JsToken GetWrapperToken() const = 0;
208 // Gets the Dispatcher for this module.
209 virtual DispatcherInterface *GetDispatcher() const = 0;
211 // Adds a reference to the wrapper class.
212 virtual void AddReference() = 0;
214 // Removes a reference to the wrapper class.
215 virtual void RemoveReference() = 0;
217 protected:
218 // Don't allow direct deletion via this interface.
219 virtual ~ModuleWrapperBaseClass() { }
222 // GComPtr: automatically call Release()
223 class ReleaseWrapperFunctor {
224 public:
225 void operator()(ModuleImplBaseClass *x) const {
226 if (x != NULL) { x->RemoveReference(); }
230 template<class Module>
231 class GComPtr : public scoped_token<Module*, ReleaseWrapperFunctor> {
232 public:
233 explicit GComPtr(Module *v)
234 : scoped_token<Module*, ReleaseWrapperFunctor>(v) {}
236 Module *operator->() const { return this->get(); }
238 // IE expects that when you return an object to script, it has already been
239 // AddRef()'d. NPAPI and Firefox do not do this. Gears modules should call
240 // this method after returning a newly created object to script to do the
241 // right thing.
242 void ReleaseNewObjectToScript() {
243 #ifdef BROWSER_IE
244 // Leave the object AddRef()'d for IE
245 #else
246 this->get()->RemoveReference();
247 #endif
248 this->release();
252 // Creates new Module of the given type. Returns NULL on failure. The new
253 // module's ref count is initialized to 1. Callers should use GComPtr and
254 // ReleaseNewObjectToScript() with the result of this function to ensure
255 // consistent behavior across platforms.
256 template<class Module>
257 Module *CreateModule(JsRunnerInterface *js_runner);
259 #endif // GEARS_BASE_COMMON_BASE_CLASS_H__