2 // Copyright (C) 2005, 2006, 2007, 2008, 2009, 2010 Free Software
5 // This program is free software; you can redistribute it and/or modify
6 // it under the terms of the GNU General Public License as published by
7 // the Free Software Foundation; either version 3 of the License, or
8 // (at your option) any later version.
10 // This program is distributed in the hope that it will be useful,
11 // but WITHOUT ANY WARRANTY; without even the implied warranty of
12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 // GNU General Public License for more details.
15 // You should have received a copy of the GNU General Public License
16 // along with this program; if not, write to the Free Software
17 // Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
20 #ifndef GNASH_GLOBAL_H
21 #define GNASH_GLOBAL_H
24 #include <boost/preprocessor/arithmetic/inc.hpp>
25 #include <boost/preprocessor/repetition/enum_params.hpp>
26 #include <boost/preprocessor/repetition/repeat.hpp>
27 #include <boost/preprocessor/repetition/repeat_from_to.hpp>
28 #include <boost/preprocessor/seq/for_each.hpp>
29 #include <boost/scoped_ptr.hpp>
31 #include "as_object.h"
34 #include "ClassHierarchy.h"
36 // Forward declarations
38 class builtin_function
;
46 /// The Global object ultimately contains all objects in an ActionScript run
48 /// An ActionScript run is a single version (AS1/2 or AS3) and includes all
49 /// resources parsed from the SWF, created dynamically, loaded, or imported
50 /// that are available to ActionScript code.
52 /// Each VM (VM for AS1/2, Machine for AS3) has different resources in its
53 /// Global object. The two objects should be entirely separate.
54 class Global_as
: public as_object
58 typedef as_value(*ASFunction
)(const fn_call
& fn
);
59 typedef void(*Properties
)(as_object
&);
61 explicit Global_as(VM
& vm
);
64 void registerClasses();
66 as_object
* createArray();
72 /// Create an ActionScript function
73 builtin_function
* createFunction(Global_as::ASFunction function
);
75 /// Create an ActionScript class
77 /// An AS2 class is generally a function (the constructor) with a
79 as_object
* createClass(Global_as::ASFunction ctor
,
80 as_object
* prototype
);
82 void makeObject(as_object
& o
) const;
86 virtual void markReachableResources() const;
90 void loadExtensions();
91 boost::scoped_ptr
<Extension
> _et
;
93 ClassHierarchy _classes
;
95 as_object
* _objectProto
;
99 as_object
* createObject(const Global_as
& gl
);
102 /// Register a built-in object
104 /// This is used for simple objects that are part of the player API.
106 /// In the reference player these objects are always constructed in
107 /// ActionScript, though their functions may be native.
109 /// They include (AS2) Mouse, Selection and Stage, and (AS3) all constant
110 /// enumeration objects.
112 /// @param p a pointer to a function that will attach properties to the
114 /// @param where the object to which the created object will be attached
115 /// @param uri an ObjectURI describing the name and namespace of the
117 /// @return the built-in object with properties attached.
119 registerBuiltinObject(as_object
& where
, Global_as::Properties p
,
120 const ObjectURI
& uri
)
123 // This is going to be the global Mouse "class"/"function"
124 Global_as
& gl
= getGlobal(where
);
125 as_object
* obj
= createObject(gl
);
128 where
.init_member(uri
, obj
, as_object::DefaultFlags
);
133 /// Register a built-in class
135 /// This is used for classes that are part of the player API.
137 /// In the reference player these classes are always constructed in
138 /// ActionScript, though their functions may be native, and the constructor
139 /// may also call native functions.
141 /// @param c a pointer to a function that will attach properties to the
142 /// class itself. These are known as static properties.
143 /// @param p a pointer to a function that will attach properties to the
144 /// class prototype. These are instance properties.
145 /// @param ctor the constructor function for the new class.
146 /// @param where the object to which the created object will be attached
147 /// @param uri an ObjectURI describing the name and namespace of the
149 /// @return the built-in class with prototype and properties attached.
151 registerBuiltinClass(as_object
& where
, Global_as::ASFunction ctor
,
152 Global_as::Properties p
, Global_as::Properties c
, const ObjectURI
& uri
)
154 Global_as
& gl
= getGlobal(where
);
155 as_object
* proto
= createObject(gl
);
156 as_object
* cl
= gl
.createClass(ctor
, proto
);
158 // Attach class properties to class
161 // Attach prototype properties to prototype
164 // Register class with specified object.
165 where
.init_member(uri
, cl
, as_object::DefaultFlags
);
169 /// Call an as_value on an as_object.
171 /// The call will fail harmlessly if the as_value is not callable.
172 inline DSOEXPORT as_value
173 invoke(const as_value
& method
, const as_environment
& env
, as_object
* this_ptr
,
174 fn_call::Args
& args
, as_object
* super
= 0,
175 const movie_definition
* callerDef
= 0)
179 fn_call
call(this_ptr
, env
, args
);
181 call
.callerDef
= callerDef
;
184 if (as_object
* func
= toObject(method
, getVM(env
))) {
186 val
= func
->call(call
);
189 IF_VERBOSE_ASCODING_ERRORS(
190 log_aserror("Attempt to call a value which is not "
191 "a function (%s)", method
);
196 catch (ActionTypeError
& e
) {
197 assert(val
.is_undefined());
198 IF_VERBOSE_ASCODING_ERRORS(
199 log_aserror("%s", e
.what());
205 /// Helper macro for callMethod arguments.
206 #define VALUE_ARG(z, n, t) BOOST_PP_COMMA_IF(n) t arg##n
208 /// Call a member function of this object in an AS-compatible way
210 /// This is a macro to cope with a varying number of arguments. The function
211 /// signature is as follows:
213 /// as_value callMethod(as_object* obj, const ObjectURI& uri,
214 /// const as_value& arg1, ..., const as_value& argN);
216 /// If the member function exists and is a function, invoke() is called on
217 /// the member with the object as the this pointer.
219 /// @param obj The object to call the method on. This may be null, in
220 /// which case the call is a no-op. This is because calling
221 /// methods on null or non-objects in AS is harmless.
222 /// @param name The name of the method.
224 /// @param arg0..argN The arguments to pass
226 /// @return The return value of the call (possibly undefined).
227 #define CALL_METHOD(x, n, t) \
229 callMethod(as_object* obj, const ObjectURI& uri BOOST_PP_COMMA_IF(n)\
230 BOOST_PP_REPEAT(n, VALUE_ARG, const as_value&)) {\
231 if (!obj) return as_value();\
233 if (!obj->get_member(uri, &func)) return as_value();\
235 BOOST_PP_EXPR_IF(n, (args += BOOST_PP_REPEAT(n, VALUE_ARG, ));)\
236 return invoke(func, as_environment(getVM(*obj)), obj, args);\
239 /// The maximum number of as_value arguments allowed in callMethod functions.
241 BOOST_PP_REPEAT(BOOST_PP_INC(MAX_ARGS
), CALL_METHOD
, )
243 /// Convenience function for finding a class constructor.
245 /// Only currently useful in AS2.
247 getClassConstructor(const fn_call
& fn
, const std::string
& s
)
249 const as_value
ctor(findObject(fn
.env(), s
));
250 return ctor
.to_function();