add macro so new strings get found by xgettext, so they can be translated.
[gnash.git] / libcore / asobj / System_as.cpp
blob41ccae0b6a3315d695098bdd77e6c5ab6efbab7f
1 // System.cpp: ActionScript "System" class, for Gnash.
2 //
3 // Copyright (C) 2005, 2006, 2007, 2008, 2009, 2010,
4 // 2011 Free Software Foundation, Inc
5 //
6 // This program is free software; you can redistribute it and/or modify
7 // it under the terms of the GNU General Public License as published by
8 // the Free Software Foundation; either version 3 of the License, or
9 // (at your option) any later version.
10 //
11 // This program is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 // GNU General Public License for more details.
16 // You should have received a copy of the GNU General Public License
17 // along with this program; if not, write to the Free Software
18 // Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
21 #include "System_as.h"
23 #include <sstream>
24 #include <string>
25 #include <iomanip>
26 #include <boost/tuple/tuple.hpp>
28 #include "movie_root.h" // interface callback
29 #include "log.h"
30 #include "fn_call.h"
31 #include "Global_as.h"
32 #include "NativeFunction.h"
33 #include "VM.h" // for getPlayerVersion()
34 #include "GnashAlgorithm.h"
35 #include "RunResources.h"
36 #include "HostInterface.h"
38 namespace gnash {
41 // Forward declarations.
42 namespace {
44 inline char trueFalse(bool x) { return x ? 't' : 'f'; }
46 std::string systemLanguage(as_object& proto);
48 as_value system_security_allowdomain(const fn_call& fn);
49 as_value system_security_allowinsecuredomain(const fn_call& fn);
50 as_value system_security_loadpolicyfile(const fn_call& fn);
51 as_value system_setClipboard(const fn_call& fn);
52 as_value system_showsettings(const fn_call& fn);
53 as_value system_exactsettings(const fn_call& fn);
54 as_value system_usecodepage(const fn_call& fn);
55 void attachSystemSecurityInterface(as_object& o);
56 void attachSystemCapabilitiesInterface(as_object& o);
57 void attachSystemInterface(as_object& proto);
60 void
61 system_class_init(as_object& where, const ObjectURI& uri)
63 registerBuiltinObject(where, attachSystemInterface, uri);
67 void
68 registerSystemNative(as_object& where)
70 VM& vm = getVM(where);
72 vm.registerNative(system_security_allowdomain, 12, 0);
73 vm.registerNative(system_showsettings, 2107, 0);
75 // From http://osflash.org/flashcoders/undocumented/asnative
77 // Run once in startup script then deleted...
78 // System.Capabilities.Query 11, 0
80 // System.Product.isRunning 2201, 0
81 // System.Product.isInstalled 2201, 1
82 // System.Product.launch 2201, 2
83 // System.Product.download 2201, 3
86 namespace {
88 void
89 attachSystemSecurityInterface(as_object& o)
91 VM& vm = getVM(o);
92 o.init_member("allowDomain", vm.getNative(12, 0));
94 Global_as& gl = getGlobal(o);
95 o.init_member("allowInsecureDomain",
96 gl.createFunction(system_security_allowinsecuredomain));
97 o.init_member("loadPolicyFile",
98 gl.createFunction(system_security_loadpolicyfile));
101 void
102 attachSystemCapabilitiesInterface(as_object& o)
104 RcInitFile& rcfile = RcInitFile::getDefaultInstance();
107 // Filesystem, access, miscellaneous hardware information
110 // "Windows XP", "Windows 2000", "Windows NT", "Windows 98/ME",
111 // "Windows 95", "Windows CE", "Linux", "MacOS"
112 // Override in gnashrc
113 VM& vm = getVM(o);
115 const std::string os = vm.getOSName();
117 const std::string language = systemLanguage(o);
119 // FIXME: these need to be implemented properly
120 // Does the NetStream object natively support SSL?
121 const bool hasTLS = true;
123 // Microphone and camera access disabled
124 const bool avHardwareDisable = false;
126 // Not sure: seems to be whether the movie can 'float' above web pages,
127 // and is useful for disabling certain annoying adverts.
128 const bool windowlessDisable = false;
130 const bool hasPrinting = true;
131 const bool hasAccessibility = true;
132 const bool isDebugger = false;
133 const bool localFileReadDisable = false;
136 // Display information (needs active GUI)
139 const movie_root& m = vm.getRoot();
141 int resX;
142 int resY;
144 boost::tie(resX, resY) = m.callInterface<std::pair<int, int> >(
145 HostMessage(HostMessage::SCREEN_RESOLUTION));
147 const double screenDPI = m.callInterface<double>(HostMessage(
148 HostMessage::SCREEN_DPI));
150 const double aspectRatio = m.callInterface<double>(HostMessage(
151 HostMessage::PIXEL_ASPECT_RATIO));
153 // Note that the pp uses the current locale to display the
154 // ratio (for the decimal separator).
155 std::ostringstream s;
156 s << std::setprecision(7) << aspectRatio;
157 const std::string pixelAspectRatio = s.str();
159 // "StandAlone", "External", "PlugIn", "ActiveX" (get from GUI)
160 const std::string playerType = m.callInterface<std::string>(HostMessage(
161 HostMessage::PLAYER_TYPE));
163 const std::string screenColor = m.callInterface<std::string>(HostMessage(
164 HostMessage::SCREEN_COLOR));
167 // Media
170 // Is audio available?
171 const bool hasAudio = (vm.getRoot().runResources().soundHandler());
173 // FIXME: these need to be implemented properly. They are mostly
174 // self-explanatory.
175 const bool hasAudioEncoder = true;
176 const bool hasEmbeddedVideo = true;
177 const bool hasMP3 = true;
178 const bool hasScreenBroadcast = true;
179 const bool hasScreenPlayback = true;
180 const bool hasStreamingAudio = true;
181 const bool hasStreamingVideo = true;
182 const bool hasVideoEncoder = true;
185 // Player version
188 // "LNX 9,0,22,0", "MAC 8,0,99,0"
189 // Override in gnashrc
190 const std::string version = vm.getPlayerVersion();
192 // "Macromedia Windows", "Macromedia Linux", "Macromedia MacOS"
193 // Override in gnashrc
194 const std::string manufacturer = rcfile.getFlashSystemManufacturer();
196 // serverString
197 // A URL-encoded string to send system info to a server.
198 // Boolean values are represented as t or f.
199 // Privacy concerns should probably be addressed by
200 // allowing this string to be sent or not; individual
201 // values that might affect privacy can be overridden
202 // in gnashrc.
204 // hasIME seems not to be included in the server string, though
205 // it is documented to have a server string of IME.
206 // Linux player version 9 has no hasIME property (but no need
207 // to emulate that.)
209 // TLS and hasTLS are documented for AS3, player version 9.
211 // WD is included in the server string for player version 9,
212 // but not documented. It corresponds to the equally undocumented
213 // windowlessDisable.
215 // This should be the standard order of parameters in the server
216 // string.
217 std::ostringstream serverString;
218 serverString << "A=" << trueFalse(hasAudio)
219 << "&SA=" << trueFalse(hasStreamingAudio)
220 << "&SV=" << trueFalse(hasStreamingVideo)
221 << "&EV=" << trueFalse(hasEmbeddedVideo)
222 << "&MP3=" << trueFalse(hasMP3)
223 << "&AE=" << trueFalse(hasAudioEncoder)
224 << "&VE=" << trueFalse(hasVideoEncoder)
225 << "&ACC=" << trueFalse(hasAccessibility)
226 << "&PR=" << trueFalse(hasPrinting)
227 << "&SP=" << trueFalse(hasScreenPlayback)
228 << "&SB=" << trueFalse(hasScreenBroadcast)
229 << "&DEB=" << trueFalse(isDebugger)
230 << "&V=" << URL::encode(version)
231 << "&M=" << URL::encode(manufacturer)
232 << "&R=" << resX << "x" << resY
233 << "&DP=" << screenDPI
234 << "&COL=" << screenColor
235 << "&AR=" << pixelAspectRatio
236 << "&OS=" << URL::encode(os)
237 << "&L=" << language
238 << "&PT=" << playerType
239 << "&AVD=" << trueFalse(avHardwareDisable)
240 << "&LFD=" << trueFalse(localFileReadDisable)
241 << "&WD=" << trueFalse(windowlessDisable)
242 << "&TLS=" << trueFalse(hasTLS);
244 const int flags = PropFlags::dontDelete
245 | PropFlags::dontEnum | PropFlags::readOnly;
247 o.init_member("hasAccessibility", hasAccessibility, flags);
248 o.init_member("pixelAspectRatio", pixelAspectRatio, flags);
249 o.init_member("screenColor", screenColor, flags);
250 o.init_member("screenDPI", screenDPI, flags);
251 o.init_member("screenResolutionY", resY, flags);
252 o.init_member("screenResolutionX", resX, flags);
253 o.init_member("hasTLS", hasTLS, flags);
254 o.init_member("hasVideoEncoder", hasVideoEncoder, flags);
255 o.init_member("hasAudioEncoder", hasAudioEncoder, flags);
256 o.init_member("hasMP3", hasMP3, flags);
257 o.init_member("hasAudio", hasAudio, flags);
258 o.init_member("serverString", serverString.str(), flags);
259 o.init_member("version", version, flags);
260 o.init_member("hasStreamingAudio", hasStreamingAudio, flags);
261 o.init_member("hasStreamingVideo", hasStreamingVideo, flags);
262 o.init_member("hasEmbeddedVideo", hasEmbeddedVideo, flags);
263 o.init_member("hasPrinting", hasPrinting, flags);
264 o.init_member("hasScreenPlayback", hasScreenPlayback, flags);
265 o.init_member("hasScreenBroadcast", hasScreenBroadcast, flags);
266 o.init_member("isDebugger", isDebugger, flags);
267 o.init_member("playerType", playerType, flags);
268 o.init_member("avHardwareDisable", avHardwareDisable, flags);
269 o.init_member("localFileReadDisable", localFileReadDisable, flags);
270 o.init_member("windowlessDisable", windowlessDisable, flags);
271 o.init_member("os", os, flags);
272 o.init_member("manufacturer", manufacturer, flags);
273 o.init_member("language", language, flags);
276 void
277 attachSystemInterface(as_object& proto)
279 Global_as& gl = getGlobal(proto);
281 VM& vm = getVM(proto);
282 registerBuiltinObject(proto, attachSystemSecurityInterface,
283 getURI(vm, "security"));
284 registerBuiltinObject(proto, attachSystemCapabilitiesInterface,
285 getURI(vm, "capabilities"));
287 proto.init_member("setClipboard",
288 gl.createFunction(system_setClipboard));
290 proto.init_member("showSettings", vm.getNative(2107, 0));
291 proto.init_property("useCodepage", &system_usecodepage,
292 &system_usecodepage);
294 const int flags = PropFlags::dontDelete
295 | PropFlags::dontEnum
296 | PropFlags::readOnly
297 | PropFlags::onlySWF6Up;
299 proto.init_property("exactSettings", &system_exactsettings,
300 &system_exactsettings, flags);
304 // This function returns false if no arguments were passed, true if any
305 // arguments were passed at all, even if they are not strings. There is
306 // currently no known way of accessing the list of allowed domains.
307 as_value
308 system_security_allowdomain(const fn_call& fn)
310 LOG_ONCE(log_unimpl(_("System.security.allowDomain")));
311 if (!fn.nargs) {
312 return as_value(false);
314 return as_value(true);
318 as_value
319 system_security_allowinsecuredomain(const fn_call& /*fn*/)
321 LOG_ONCE(log_unimpl(_("System.security.allowInsecureDomain")));
322 return as_value();
326 as_value
327 system_security_loadpolicyfile(const fn_call& /*fn*/)
329 LOG_ONCE(log_unimpl(_("System.security.loadPolicyFile")));
330 return as_value();
333 as_value
334 system_setClipboard(const fn_call& fn)
336 if (!fn.nargs) {
337 return as_value();
340 const std::string& s = fn.arg(0).to_string();
341 movie_root& m = getRoot(fn);
342 m.callInterface(HostMessage(HostMessage::SET_CLIPBOARD, s));
344 return as_value();
347 as_value
348 system_showsettings(const fn_call& /*fn*/)
350 LOG_ONCE(log_unimpl(_("System.showSettings")));
351 return as_value();
354 // FIXME: should return true if shared object files
355 // are stored under an exact domain name (www.gnashdev.org or
356 // gnashdev.org); false if both are stored under gnashdev.org.
357 // Can be set.
358 as_value
359 system_exactsettings(const fn_call& fn)
361 // Getter
362 if (fn.nargs == 0) {
363 // Is always true until we implement it.
364 return as_value(true);
366 else {
367 LOG_ONCE(log_unimpl(_("System.exactSettings")));
368 return as_value();
373 // FIXME: if true, SWF6+ should treat DisplayObjects as Latin
374 // charset variants. If false (default), as UtrueFalse-8.
375 // Can be set.
376 as_value
377 system_usecodepage(const fn_call& fn)
379 // Getter
380 if (!fn.nargs) {
381 // Is always false until we implement it.
382 return as_value(false);
384 else {
385 LOG_ONCE(log_unimpl(_("System.useCodepage")));
386 return as_value();
390 std::string
391 systemLanguage(as_object& proto)
393 // Two-letter language code ('en', 'de') corresponding to ISO 639-1
394 // Chinese can be either zh-CN or zh-TW. English used to have a
395 // country (GB, US) qualifier, but that was dropped in version 7 of
396 // the player.
397 // This method relies on getting a POSIX-style language code of the form
398 // "zh_TW.utf8", "zh_CN" or "it" from the VM.
399 // It is obviously very easy to extend support to all language codes, but
400 // some scripts rely on there being only 20 possible languages. It could
401 // be a run time option if it's important enough to care.
403 std::string lang = getVM(proto).getSystemLanguage();
405 const char* languages[] = {"en", "fr", "ko", "ja", "sv",
406 "de", "es", "it", "zh", "pt",
407 "pl", "hu", "cs", "tr", "fi",
408 "da", "nl", "no", "ru"};
410 const size_t size = arraySize(languages);
412 if (std::find(languages, languages + size, lang.substr(0, 2)) !=
413 languages + size) {
414 if (lang.substr(0, 2) == "zh") {
415 // Chinese is the only language since the pp version 7
416 // to need an additional qualifier.
417 if (lang.substr(2, 3) == "_TW") lang = "zh-TW";
418 else if (lang.substr(2, 3) == "_CN") lang = "zh-CN";
419 else lang = "xu";
421 else {
422 // All other matching cases: retain just the first
423 // two DisplayObjects.
424 lang.erase(2);
427 else {
428 // Unknown language. We also return this if
429 // getSystemLanguage() returns something unexpected.
430 lang = "xu";
433 return lang;
436 } // anonymous namespace
437 } // gnash namespace