Coverage Report

Created: 2018-09-25 14:53

/src/mozilla-central/dom/plugins/base/nsNPAPIPlugin.cpp
Line
Count
Source (jump to first uncovered line)
1
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2
/* This Source Code Form is subject to the terms of the Mozilla Public
3
 * License, v. 2.0. If a copy of the MPL was not distributed with this
4
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
5
6
#include "base/basictypes.h"
7
8
/* This must occur *after* layers/PLayerTransaction.h to avoid typedefs conflicts. */
9
#include "mozilla/ArrayUtils.h"
10
11
#include "pratom.h"
12
#include "prenv.h"
13
14
#include "jsfriendapi.h"
15
16
#include "nsPluginHost.h"
17
#include "nsNPAPIPlugin.h"
18
#include "nsNPAPIPluginInstance.h"
19
#include "nsNPAPIPluginStreamListener.h"
20
#include "nsPluginStreamListenerPeer.h"
21
#include "nsIServiceManager.h"
22
#include "nsThreadUtils.h"
23
#include "mozilla/CycleCollectedJSContext.h" // for nsAutoMicroTask
24
#include "mozilla/Preferences.h"
25
#include "nsPluginInstanceOwner.h"
26
27
#include "nsPluginsDir.h"
28
#include "nsPluginLogging.h"
29
30
#include "nsPIDOMWindow.h"
31
#include "nsGlobalWindow.h"
32
#include "nsIDocument.h"
33
#include "nsIContent.h"
34
#include "nsIIDNService.h"
35
#include "nsIScriptGlobalObject.h"
36
#include "nsIScriptContext.h"
37
#include "nsDOMJSUtils.h"
38
#include "nsIPrincipal.h"
39
#include "nsWildCard.h"
40
#include "nsContentUtils.h"
41
#include "mozilla/dom/Element.h"
42
#include "mozilla/dom/ScriptSettings.h"
43
#include "mozilla/dom/ToJSValue.h"
44
#include "nsIXULRuntime.h"
45
#include "nsIXPConnect.h"
46
47
#include "nsIObserverService.h"
48
#include <prinrval.h>
49
50
#ifdef MOZ_WIDGET_COCOA
51
#include <Carbon/Carbon.h>
52
#include <ApplicationServices/ApplicationServices.h>
53
#include <OpenGL/OpenGL.h>
54
#include "nsCocoaFeatures.h"
55
#include "PluginUtilsOSX.h"
56
#endif
57
58
// needed for nppdf plugin
59
#if (MOZ_WIDGET_GTK)
60
#include <gdk/gdk.h>
61
#include <gdk/gdkx.h>
62
#endif
63
64
#include "nsJSUtils.h"
65
#include "nsJSNPRuntime.h"
66
#include "nsIHttpAuthManager.h"
67
#include "nsICookieService.h"
68
#include "nsILoadContext.h"
69
#include "nsIDocShell.h"
70
71
#include "nsNetUtil.h"
72
#include "nsNetCID.h"
73
74
#include "mozilla/Mutex.h"
75
#include "mozilla/PluginLibrary.h"
76
using mozilla::PluginLibrary;
77
78
#include "mozilla/plugins/PluginModuleParent.h"
79
using mozilla::plugins::PluginModuleChromeParent;
80
using mozilla::plugins::PluginModuleContentParent;
81
82
#ifdef MOZ_X11
83
#include "mozilla/X11Util.h"
84
#endif
85
86
#ifdef XP_WIN
87
#include <windows.h>
88
#include "mozilla/WindowsVersion.h"
89
#ifdef ACCESSIBILITY
90
#include "mozilla/a11y/Compatibility.h"
91
#endif
92
#endif
93
94
#include "nsIAudioChannelAgent.h"
95
#include "AudioChannelService.h"
96
97
using namespace mozilla;
98
using namespace mozilla::plugins::parent;
99
100
// We should make this const...
101
static NPNetscapeFuncs sBrowserFuncs = {
102
  sizeof(sBrowserFuncs),
103
  (NP_VERSION_MAJOR << 8) + NP_VERSION_MINOR,
104
  _geturl,
105
  _posturl,
106
  _requestread,
107
  nullptr, // _newstream, unimplemented
108
  nullptr, // _write, unimplemented
109
  nullptr, // _destroystream, unimplemented
110
  _status,
111
  _useragent,
112
  _memalloc,
113
  _memfree,
114
  _memflush,
115
  _reloadplugins,
116
  _getJavaEnv,
117
  _getJavaPeer,
118
  _geturlnotify,
119
  _posturlnotify,
120
  _getvalue,
121
  _setvalue,
122
  _invalidaterect,
123
  _invalidateregion,
124
  _forceredraw,
125
  _getstringidentifier,
126
  _getstringidentifiers,
127
  _getintidentifier,
128
  _identifierisstring,
129
  _utf8fromidentifier,
130
  _intfromidentifier,
131
  _createobject,
132
  _retainobject,
133
  _releaseobject,
134
  _invoke,
135
  _invokeDefault,
136
  _evaluate,
137
  _getproperty,
138
  _setproperty,
139
  _removeproperty,
140
  _hasproperty,
141
  _hasmethod,
142
  _releasevariantvalue,
143
  _setexception,
144
  _pushpopupsenabledstate,
145
  _poppopupsenabledstate,
146
  _enumerate,
147
  nullptr, // pluginthreadasynccall, not used
148
  _construct,
149
  _getvalueforurl,
150
  _setvalueforurl,
151
  nullptr, //NPN GetAuthenticationInfo, not supported
152
  _scheduletimer,
153
  _unscheduletimer,
154
  _popupcontextmenu,
155
  _convertpoint,
156
  nullptr, // handleevent, unimplemented
157
  nullptr, // unfocusinstance, unimplemented
158
  _urlredirectresponse,
159
  _initasyncsurface,
160
  _finalizeasyncsurface,
161
  _setcurrentasyncsurface
162
};
163
164
// POST/GET stream type
165
enum eNPPStreamTypeInternal {
166
  eNPPStreamTypeInternal_Get,
167
  eNPPStreamTypeInternal_Post
168
};
169
170
void NS_NotifyBeginPluginCall(NSPluginCallReentry aReentryState)
171
0
{
172
0
  nsNPAPIPluginInstance::BeginPluginCall(aReentryState);
173
0
}
174
175
void NS_NotifyPluginCall(NSPluginCallReentry aReentryState)
176
0
{
177
0
  nsNPAPIPluginInstance::EndPluginCall(aReentryState);
178
0
}
179
180
nsNPAPIPlugin::nsNPAPIPlugin()
181
0
{
182
0
  memset((void*)&mPluginFuncs, 0, sizeof(mPluginFuncs));
183
0
  mPluginFuncs.size = sizeof(mPluginFuncs);
184
0
  mPluginFuncs.version = (NP_VERSION_MAJOR << 8) | NP_VERSION_MINOR;
185
0
186
0
  mLibrary = nullptr;
187
0
}
188
189
nsNPAPIPlugin::~nsNPAPIPlugin()
190
0
{
191
0
  delete mLibrary;
192
0
  mLibrary = nullptr;
193
0
}
194
195
void
196
nsNPAPIPlugin::PluginCrashed(const nsAString& pluginDumpID,
197
                             const nsAString& browserDumpID)
198
0
{
199
0
  RefPtr<nsPluginHost> host = nsPluginHost::GetInst();
200
0
  host->PluginCrashed(this, pluginDumpID, browserDumpID);
201
0
}
202
203
inline PluginLibrary*
204
GetNewPluginLibrary(nsPluginTag *aPluginTag)
205
0
{
206
0
  AUTO_PROFILER_LABEL("GetNewPluginLibrary", OTHER);
207
0
208
0
  if (!aPluginTag) {
209
0
    return nullptr;
210
0
  }
211
0
212
0
  if (XRE_IsContentProcess()) {
213
0
    return PluginModuleContentParent::LoadModule(aPluginTag->mId, aPluginTag);
214
0
  }
215
0
216
0
  return PluginModuleChromeParent::LoadModule(aPluginTag->mFullPath.get(), aPluginTag->mId, aPluginTag);
217
0
}
218
219
// Creates an nsNPAPIPlugin object. One nsNPAPIPlugin object exists per plugin (not instance).
220
nsresult
221
nsNPAPIPlugin::CreatePlugin(nsPluginTag *aPluginTag, nsNPAPIPlugin** aResult)
222
0
{
223
0
  AUTO_PROFILER_LABEL("nsNPAPIPlugin::CreatePlugin", OTHER);
224
0
  *aResult = nullptr;
225
0
226
0
  if (!aPluginTag) {
227
0
    return NS_ERROR_FAILURE;
228
0
  }
229
0
230
0
  RefPtr<nsNPAPIPlugin> plugin = new nsNPAPIPlugin();
231
0
232
0
  PluginLibrary* pluginLib = GetNewPluginLibrary(aPluginTag);
233
0
  if (!pluginLib) {
234
0
    return NS_ERROR_FAILURE;
235
0
  }
236
0
237
#if defined(XP_MACOSX)
238
  if (!pluginLib->HasRequiredFunctions()) {
239
    NS_WARNING("Not all necessary functions exposed by plugin, it will not load.");
240
    delete pluginLib;
241
    return NS_ERROR_FAILURE;
242
  }
243
#endif
244
245
0
  plugin->mLibrary = pluginLib;
246
0
  pluginLib->SetPlugin(plugin);
247
0
248
0
// Exchange NPAPI entry points.
249
#if defined(XP_WIN)
250
  // NP_GetEntryPoints must be called before NP_Initialize on Windows.
251
  NPError pluginCallError;
252
  nsresult rv = pluginLib->NP_GetEntryPoints(&plugin->mPluginFuncs, &pluginCallError);
253
  if (rv != NS_OK || pluginCallError != NPERR_NO_ERROR) {
254
    return NS_ERROR_FAILURE;
255
  }
256
257
  // NP_Initialize must be called after NP_GetEntryPoints on Windows.
258
  rv = pluginLib->NP_Initialize(&sBrowserFuncs, &pluginCallError);
259
  if (rv != NS_OK || pluginCallError != NPERR_NO_ERROR) {
260
    return NS_ERROR_FAILURE;
261
  }
262
#elif defined(XP_MACOSX)
263
  // NP_Initialize must be called before NP_GetEntryPoints on Mac OS X.
264
  // We need to match WebKit's behavior.
265
  NPError pluginCallError;
266
  nsresult rv = pluginLib->NP_Initialize(&sBrowserFuncs, &pluginCallError);
267
  if (rv != NS_OK || pluginCallError != NPERR_NO_ERROR) {
268
    return NS_ERROR_FAILURE;
269
  }
270
271
  rv = pluginLib->NP_GetEntryPoints(&plugin->mPluginFuncs, &pluginCallError);
272
  if (rv != NS_OK || pluginCallError != NPERR_NO_ERROR) {
273
    return NS_ERROR_FAILURE;
274
  }
275
#else
276
  NPError pluginCallError;
277
0
  nsresult rv = pluginLib->NP_Initialize(&sBrowserFuncs, &plugin->mPluginFuncs, &pluginCallError);
278
0
  if (rv != NS_OK || pluginCallError != NPERR_NO_ERROR) {
279
0
    return NS_ERROR_FAILURE;
280
0
  }
281
0
#endif
282
0
283
0
  plugin.forget(aResult);
284
0
  return NS_OK;
285
0
}
286
287
PluginLibrary*
288
nsNPAPIPlugin::GetLibrary()
289
0
{
290
0
  return mLibrary;
291
0
}
292
293
NPPluginFuncs*
294
nsNPAPIPlugin::PluginFuncs()
295
0
{
296
0
  return &mPluginFuncs;
297
0
}
298
299
nsresult
300
nsNPAPIPlugin::Shutdown()
301
0
{
302
0
  NPP_PLUGIN_LOG(PLUGIN_LOG_BASIC,
303
0
                 ("NPP Shutdown to be called: this=%p\n", this));
304
0
305
0
  NPError shutdownError;
306
0
  mLibrary->NP_Shutdown(&shutdownError);
307
0
308
0
  return NS_OK;
309
0
}
310
311
nsresult
312
nsNPAPIPlugin::RetainStream(NPStream *pstream, nsISupports **aRetainedPeer)
313
0
{
314
0
  if (!aRetainedPeer)
315
0
    return NS_ERROR_NULL_POINTER;
316
0
317
0
  *aRetainedPeer = nullptr;
318
0
319
0
  if (!pstream || !pstream->ndata)
320
0
    return NS_ERROR_NULL_POINTER;
321
0
322
0
  nsNPAPIStreamWrapper* streamWrapper = static_cast<nsNPAPIStreamWrapper*>(pstream->ndata);
323
0
  nsNPAPIPluginStreamListener* listener = streamWrapper->GetStreamListener();
324
0
  if (!listener) {
325
0
    return NS_ERROR_NULL_POINTER;
326
0
  }
327
0
328
0
  nsIStreamListener* streamListener = listener->GetStreamListenerPeer();
329
0
  if (!streamListener) {
330
0
    return NS_ERROR_NULL_POINTER;
331
0
  }
332
0
333
0
  *aRetainedPeer = streamListener;
334
0
  NS_ADDREF(*aRetainedPeer);
335
0
  return NS_OK;
336
0
}
337
338
// Create a new NPP GET or POST (given in the type argument) url
339
// stream that may have a notify callback
340
NPError
341
MakeNewNPAPIStreamInternal(NPP npp, const char *relativeURL, const char *target,
342
                          eNPPStreamTypeInternal type,
343
                          bool bDoNotify = false,
344
                          void *notifyData = nullptr, uint32_t len = 0,
345
                          const char *buf = nullptr)
346
0
{
347
0
  if (!npp)
348
0
    return NPERR_INVALID_INSTANCE_ERROR;
349
0
350
0
  PluginDestructionGuard guard(npp);
351
0
352
0
  nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *) npp->ndata;
353
0
  if (!inst || !inst->IsRunning())
354
0
    return NPERR_INVALID_INSTANCE_ERROR;
355
0
356
0
  nsCOMPtr<nsIPluginHost> pluginHostCOM = do_GetService(MOZ_PLUGIN_HOST_CONTRACTID);
357
0
  nsPluginHost *pluginHost = static_cast<nsPluginHost*>(pluginHostCOM.get());
358
0
  if (!pluginHost) {
359
0
    return NPERR_GENERIC_ERROR;
360
0
  }
361
0
362
0
  RefPtr<nsNPAPIPluginStreamListener> listener;
363
0
  // Set aCallNotify here to false.  If pluginHost->GetURL or PostURL fail,
364
0
  // the listener's destructor will do the notification while we are about to
365
0
  // return a failure code.
366
0
  // Call SetCallNotify(true) below after we are sure we cannot return a failure
367
0
  // code.
368
0
  if (!target) {
369
0
    inst->NewStreamListener(relativeURL, notifyData,
370
0
                            getter_AddRefs(listener));
371
0
    if (listener) {
372
0
      listener->SetCallNotify(false);
373
0
    }
374
0
  }
375
0
376
0
  switch (type) {
377
0
  case eNPPStreamTypeInternal_Get:
378
0
    {
379
0
      if (NS_FAILED(pluginHost->GetURL(inst, relativeURL, target, listener,
380
0
                                       nullptr, nullptr, false)))
381
0
        return NPERR_GENERIC_ERROR;
382
0
      break;
383
0
    }
384
0
  case eNPPStreamTypeInternal_Post:
385
0
    {
386
0
      if (NS_FAILED(pluginHost->PostURL(inst, relativeURL, len, buf,
387
0
                                        target, listener, nullptr, nullptr,
388
0
                                        false, 0, nullptr)))
389
0
        return NPERR_GENERIC_ERROR;
390
0
      break;
391
0
    }
392
0
  default:
393
0
    NS_ERROR("how'd I get here");
394
0
  }
395
0
396
0
  if (listener) {
397
0
    // SetCallNotify(bDoNotify) here, see comment above.
398
0
    listener->SetCallNotify(bDoNotify);
399
0
  }
400
0
401
0
  return NPERR_NO_ERROR;
402
0
}
403
404
#if defined(MOZ_MEMORY) && defined(XP_WIN)
405
extern "C" size_t malloc_usable_size(const void *ptr);
406
#endif
407
408
namespace {
409
410
static char *gNPPException;
411
412
static nsIDocument *
413
GetDocumentFromNPP(NPP npp)
414
0
{
415
0
  NS_ENSURE_TRUE(npp, nullptr);
416
0
417
0
  nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *)npp->ndata;
418
0
  NS_ENSURE_TRUE(inst, nullptr);
419
0
420
0
  PluginDestructionGuard guard(inst);
421
0
422
0
  RefPtr<nsPluginInstanceOwner> owner = inst->GetOwner();
423
0
  NS_ENSURE_TRUE(owner, nullptr);
424
0
425
0
  nsCOMPtr<nsIDocument> doc;
426
0
  owner->GetDocument(getter_AddRefs(doc));
427
0
428
0
  return doc;
429
0
}
430
431
static NPIdentifier
432
doGetIdentifier(JSContext *cx, const NPUTF8* name)
433
0
{
434
0
  NS_ConvertUTF8toUTF16 utf16name(name);
435
0
436
0
  JSString *str = ::JS_AtomizeAndPinUCStringN(cx, utf16name.get(), utf16name.Length());
437
0
438
0
  if (!str)
439
0
    return nullptr;
440
0
441
0
  return StringToNPIdentifier(cx, str);
442
0
}
443
444
#if defined(MOZ_MEMORY) && defined(XP_WIN)
445
BOOL
446
InHeap(HANDLE hHeap, LPVOID lpMem)
447
{
448
  BOOL success = FALSE;
449
  PROCESS_HEAP_ENTRY he;
450
  he.lpData = nullptr;
451
  while (HeapWalk(hHeap, &he) != 0) {
452
    if (he.lpData == lpMem) {
453
      success = TRUE;
454
      break;
455
    }
456
  }
457
  HeapUnlock(hHeap);
458
  return success;
459
}
460
#endif
461
462
} /* anonymous namespace */
463
464
NPPExceptionAutoHolder::NPPExceptionAutoHolder()
465
  : mOldException(gNPPException)
466
0
{
467
0
  gNPPException = nullptr;
468
0
}
469
470
NPPExceptionAutoHolder::~NPPExceptionAutoHolder()
471
0
{
472
0
  NS_ASSERTION(!gNPPException, "NPP exception not properly cleared!");
473
0
474
0
  gNPPException = mOldException;
475
0
}
476
477
NPP NPPStack::sCurrentNPP = nullptr;
478
479
const char *
480
PeekException()
481
0
{
482
0
  return gNPPException;
483
0
}
484
485
void
486
PopException()
487
0
{
488
0
  NS_ASSERTION(gNPPException, "Uh, no NPP exception to pop!");
489
0
490
0
  if (gNPPException) {
491
0
    free(gNPPException);
492
0
493
0
    gNPPException = nullptr;
494
0
  }
495
0
}
496
497
//
498
// Static callbacks that get routed back through the new C++ API
499
//
500
501
namespace mozilla {
502
namespace plugins {
503
namespace parent {
504
505
NPError
506
_geturl(NPP npp, const char* relativeURL, const char* target)
507
0
{
508
0
  if (!NS_IsMainThread()) {
509
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_geturl called from the wrong thread\n"));
510
0
    return NPERR_INVALID_PARAM;
511
0
  }
512
0
513
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NORMAL,
514
0
  ("NPN_GetURL: npp=%p, target=%s, url=%s\n", (void *)npp, target,
515
0
   relativeURL));
516
0
517
0
  PluginDestructionGuard guard(npp);
518
0
519
0
  return MakeNewNPAPIStreamInternal(npp, relativeURL, target,
520
0
                                    eNPPStreamTypeInternal_Get);
521
0
}
522
523
NPError
524
_geturlnotify(NPP npp, const char* relativeURL, const char* target,
525
              void* notifyData)
526
0
{
527
0
  if (!NS_IsMainThread()) {
528
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_geturlnotify called from the wrong thread\n"));
529
0
    return NPERR_INVALID_PARAM;
530
0
  }
531
0
532
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NORMAL,
533
0
    ("NPN_GetURLNotify: npp=%p, target=%s, notify=%p, url=%s\n", (void*)npp,
534
0
     target, notifyData, relativeURL));
535
0
536
0
  PluginDestructionGuard guard(npp);
537
0
538
0
  return MakeNewNPAPIStreamInternal(npp, relativeURL, target,
539
0
                                    eNPPStreamTypeInternal_Get, true,
540
0
                                    notifyData);
541
0
}
542
543
NPError
544
_posturlnotify(NPP npp, const char *relativeURL, const char *target,
545
               uint32_t len, const char *buf, NPBool file, void *notifyData)
546
0
{
547
0
  if (!NS_IsMainThread()) {
548
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_posturlnotify called from the wrong thread\n"));
549
0
    return NPERR_INVALID_PARAM;
550
0
  }
551
0
  if (!buf)
552
0
    return NPERR_INVALID_PARAM;
553
0
554
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NORMAL,
555
0
                 ("NPN_PostURLNotify: npp=%p, target=%s, len=%d, file=%d, "
556
0
                  "notify=%p, url=%s, buf=%s\n",
557
0
                  (void*)npp, target, len, file, notifyData, relativeURL,
558
0
                  buf));
559
0
560
0
  PluginDestructionGuard guard(npp);
561
0
562
0
  return MakeNewNPAPIStreamInternal(npp, relativeURL, target,
563
0
                                    eNPPStreamTypeInternal_Post, true,
564
0
                                    notifyData, len, buf);
565
0
}
566
567
NPError
568
_posturl(NPP npp, const char *relativeURL, const char *target,
569
         uint32_t len, const char *buf, NPBool file)
570
0
{
571
0
  if (!NS_IsMainThread()) {
572
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_posturl called from the wrong thread\n"));
573
0
    return NPERR_INVALID_PARAM;
574
0
  }
575
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NORMAL,
576
0
                 ("NPN_PostURL: npp=%p, target=%s, file=%d, len=%d, url=%s, "
577
0
                  "buf=%s\n",
578
0
                  (void*)npp, target, file, len, relativeURL, buf));
579
0
580
0
  PluginDestructionGuard guard(npp);
581
0
582
0
  return MakeNewNPAPIStreamInternal(npp, relativeURL, target,
583
0
                                    eNPPStreamTypeInternal_Post, false, nullptr,
584
0
                                    len, buf);
585
0
}
586
587
void
588
_status(NPP npp, const char *message)
589
0
{
590
0
  // NPN_Status is no longer supported.
591
0
}
592
593
void
594
_memfree (void *ptr)
595
0
{
596
0
  if (!NS_IsMainThread()) {
597
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_memfree called from the wrong thread\n"));
598
0
  }
599
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NOISY, ("NPN_MemFree: ptr=%p\n", ptr));
600
0
601
0
  if (ptr)
602
0
    free(ptr);
603
0
}
604
605
uint32_t
606
_memflush(uint32_t size)
607
0
{
608
0
  if (!NS_IsMainThread()) {
609
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_memflush called from the wrong thread\n"));
610
0
  }
611
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NOISY, ("NPN_MemFlush: size=%d\n", size));
612
0
613
0
  nsMemory::HeapMinimize(true);
614
0
  return 0;
615
0
}
616
617
void
618
_reloadplugins(NPBool reloadPages)
619
0
{
620
0
  if (!NS_IsMainThread()) {
621
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_reloadplugins called from the wrong thread\n"));
622
0
    return;
623
0
  }
624
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NORMAL,
625
0
                 ("NPN_ReloadPlugins: reloadPages=%d\n", reloadPages));
626
0
627
0
  nsCOMPtr<nsIPluginHost> pluginHost(do_GetService(MOZ_PLUGIN_HOST_CONTRACTID));
628
0
  if (!pluginHost)
629
0
    return;
630
0
631
0
  pluginHost->ReloadPlugins();
632
0
}
633
634
void
635
_invalidaterect(NPP npp, NPRect *invalidRect)
636
0
{
637
0
  if (!NS_IsMainThread()) {
638
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_invalidaterect called from the wrong thread\n"));
639
0
    return;
640
0
  }
641
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NORMAL,
642
0
                 ("NPN_InvalidateRect: npp=%p, top=%d, left=%d, bottom=%d, "
643
0
                  "right=%d\n", (void *)npp, invalidRect->top,
644
0
                  invalidRect->left, invalidRect->bottom, invalidRect->right));
645
0
646
0
  if (!npp || !npp->ndata) {
647
0
    NS_WARNING("_invalidaterect: npp or npp->ndata == 0");
648
0
    return;
649
0
  }
650
0
651
0
  nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance*)npp->ndata;
652
0
653
0
  PluginDestructionGuard guard(inst);
654
0
655
0
  inst->InvalidateRect((NPRect *)invalidRect);
656
0
}
657
658
void
659
_invalidateregion(NPP npp, NPRegion invalidRegion)
660
0
{
661
0
  if (!NS_IsMainThread()) {
662
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_invalidateregion called from the wrong thread\n"));
663
0
    return;
664
0
  }
665
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NORMAL,
666
0
                 ("NPN_InvalidateRegion: npp=%p, region=%p\n", (void*)npp,
667
0
                  (void*)invalidRegion));
668
0
669
0
  if (!npp || !npp->ndata) {
670
0
    NS_WARNING("_invalidateregion: npp or npp->ndata == 0");
671
0
    return;
672
0
  }
673
0
674
0
  nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance*)npp->ndata;
675
0
676
0
  PluginDestructionGuard guard(inst);
677
0
678
0
  inst->InvalidateRegion((NPRegion)invalidRegion);
679
0
}
680
681
void
682
_forceredraw(NPP npp)
683
0
{
684
0
}
685
686
NPObject*
687
_getwindowobject(NPP npp)
688
0
{
689
0
  if (!NS_IsMainThread()) {
690
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_getwindowobject called from the wrong thread\n"));
691
0
    return nullptr;
692
0
  }
693
0
694
0
  // The window want to return here is the outer window, *not* the inner (since
695
0
  // we don't know what the plugin will do with it).
696
0
  nsIDocument* doc = GetDocumentFromNPP(npp);
697
0
  NS_ENSURE_TRUE(doc, nullptr);
698
0
  nsCOMPtr<nsPIDOMWindowOuter> outer = doc->GetWindow();
699
0
  NS_ENSURE_TRUE(outer, nullptr);
700
0
701
0
  JS::Rooted<JSObject*> windowProxy(dom::RootingCx(),
702
0
                                    nsGlobalWindowOuter::Cast(outer)->GetGlobalJSObject());
703
0
  JS::Rooted<JSObject*> global(dom::RootingCx(),
704
0
                               JS::GetNonCCWObjectGlobal(windowProxy));
705
0
  return nsJSObjWrapper::GetNewOrUsed(npp, windowProxy, global);
706
0
}
707
708
NPObject*
709
_getpluginelement(NPP npp)
710
0
{
711
0
  if (!NS_IsMainThread()) {
712
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_getpluginelement called from the wrong thread\n"));
713
0
    return nullptr;
714
0
  }
715
0
716
0
  nsNPAPIPluginInstance* inst = static_cast<nsNPAPIPluginInstance*>(npp->ndata);
717
0
  if (!inst)
718
0
    return nullptr;
719
0
720
0
  RefPtr<dom::Element> element;
721
0
  inst->GetDOMElement(getter_AddRefs(element));
722
0
723
0
  if (!element)
724
0
    return nullptr;
725
0
726
0
  nsIDocument *doc = GetDocumentFromNPP(npp);
727
0
  if (NS_WARN_IF(!doc)) {
728
0
    return nullptr;
729
0
  }
730
0
731
0
  dom::AutoJSAPI jsapi;
732
0
  if (NS_WARN_IF(!jsapi.Init(doc->GetInnerWindow()))) {
733
0
    return nullptr;
734
0
  }
735
0
  JSContext* cx = jsapi.cx();
736
0
737
0
  nsCOMPtr<nsIXPConnect> xpc(nsIXPConnect::XPConnect());
738
0
  NS_ENSURE_TRUE(xpc, nullptr);
739
0
740
0
  JS::RootedValue val(cx);
741
0
  if (!ToJSValue(cx, element, &val)) {
742
0
    return nullptr;
743
0
  }
744
0
745
0
  if (NS_WARN_IF(!val.isObject())) {
746
0
    return nullptr;
747
0
  }
748
0
749
0
  JS::RootedObject obj(cx, &val.toObject());
750
0
  JS::RootedObject global(cx, JS::CurrentGlobalOrNull(cx));
751
0
  return nsJSObjWrapper::GetNewOrUsed(npp, obj, global);
752
0
}
753
754
NPIdentifier
755
_getstringidentifier(const NPUTF8* name)
756
0
{
757
0
  if (!name) {
758
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS, ("NPN_getstringidentifier: passed null name"));
759
0
    return nullptr;
760
0
  }
761
0
  if (!NS_IsMainThread()) {
762
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_getstringidentifier called from the wrong thread\n"));
763
0
  }
764
0
765
0
  AutoSafeJSContext cx;
766
0
  return doGetIdentifier(cx, name);
767
0
}
768
769
void
770
_getstringidentifiers(const NPUTF8** names, int32_t nameCount,
771
                      NPIdentifier *identifiers)
772
0
{
773
0
  if (!NS_IsMainThread()) {
774
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_getstringidentifiers called from the wrong thread\n"));
775
0
  }
776
0
777
0
  AutoSafeJSContext cx;
778
0
779
0
  for (int32_t i = 0; i < nameCount; ++i) {
780
0
    if (names[i]) {
781
0
      identifiers[i] = doGetIdentifier(cx, names[i]);
782
0
    } else {
783
0
      NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS, ("NPN_getstringidentifiers: passed null name"));
784
0
      identifiers[i] = nullptr;
785
0
    }
786
0
  }
787
0
}
788
789
NPIdentifier
790
_getintidentifier(int32_t intid)
791
0
{
792
0
  if (!NS_IsMainThread()) {
793
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_getstringidentifier called from the wrong thread\n"));
794
0
  }
795
0
  return IntToNPIdentifier(intid);
796
0
}
797
798
NPUTF8*
799
_utf8fromidentifier(NPIdentifier id)
800
0
{
801
0
  if (!NS_IsMainThread()) {
802
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_utf8fromidentifier called from the wrong thread\n"));
803
0
  }
804
0
  if (!id)
805
0
    return nullptr;
806
0
807
0
  if (!NPIdentifierIsString(id)) {
808
0
    return nullptr;
809
0
  }
810
0
811
0
  JSString *str = NPIdentifierToString(id);
812
0
  nsAutoString autoStr;
813
0
  AssignJSFlatString(autoStr, JS_ASSERT_STRING_IS_FLAT(str));
814
0
815
0
  return ToNewUTF8String(autoStr);
816
0
}
817
818
int32_t
819
_intfromidentifier(NPIdentifier id)
820
0
{
821
0
  if (!NS_IsMainThread()) {
822
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_intfromidentifier called from the wrong thread\n"));
823
0
  }
824
0
825
0
  if (!NPIdentifierIsInt(id)) {
826
0
    return INT32_MIN;
827
0
  }
828
0
829
0
  return NPIdentifierToInt(id);
830
0
}
831
832
bool
833
_identifierisstring(NPIdentifier id)
834
0
{
835
0
  if (!NS_IsMainThread()) {
836
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_identifierisstring called from the wrong thread\n"));
837
0
  }
838
0
839
0
  return NPIdentifierIsString(id);
840
0
}
841
842
NPObject*
843
_createobject(NPP npp, NPClass* aClass)
844
0
{
845
0
  if (!NS_IsMainThread()) {
846
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_createobject called from the wrong thread\n"));
847
0
    return nullptr;
848
0
  }
849
0
  if (!npp) {
850
0
    NS_ERROR("Null npp passed to _createobject()!");
851
0
852
0
    return nullptr;
853
0
  }
854
0
855
0
  PluginDestructionGuard guard(npp);
856
0
857
0
  if (!aClass) {
858
0
    NS_ERROR("Null class passed to _createobject()!");
859
0
860
0
    return nullptr;
861
0
  }
862
0
863
0
  NPPAutoPusher nppPusher(npp);
864
0
865
0
  NPObject *npobj;
866
0
867
0
  if (aClass->allocate) {
868
0
    npobj = aClass->allocate(npp, aClass);
869
0
  } else {
870
0
    npobj = (NPObject*) malloc(sizeof(NPObject));
871
0
  }
872
0
873
0
  if (npobj) {
874
0
    npobj->_class = aClass;
875
0
    npobj->referenceCount = 1;
876
0
    NS_LOG_ADDREF(npobj, 1, "BrowserNPObject", sizeof(NPObject));
877
0
  }
878
0
879
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NOISY,
880
0
                 ("Created NPObject %p, NPClass %p\n", npobj, aClass));
881
0
882
0
  return npobj;
883
0
}
884
885
NPObject*
886
_retainobject(NPObject* npobj)
887
0
{
888
0
  if (!NS_IsMainThread()) {
889
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_retainobject called from the wrong thread\n"));
890
0
  }
891
0
  if (npobj) {
892
#ifdef NS_BUILD_REFCNT_LOGGING
893
    int32_t refCnt =
894
#endif
895
      PR_ATOMIC_INCREMENT((int32_t*)&npobj->referenceCount);
896
0
    NS_LOG_ADDREF(npobj, refCnt, "BrowserNPObject", sizeof(NPObject));
897
0
  }
898
0
899
0
  return npobj;
900
0
}
901
902
void
903
_releaseobject(NPObject* npobj)
904
0
{
905
0
  // If nothing is passed, just return, even if we're on the wrong thread.
906
0
  if (!npobj) {
907
0
    return;
908
0
  }
909
0
910
0
  int32_t refCnt = PR_ATOMIC_DECREMENT((int32_t*)&npobj->referenceCount);
911
0
  NS_LOG_RELEASE(npobj, refCnt, "BrowserNPObject");
912
0
913
0
  if (refCnt == 0) {
914
0
    nsNPObjWrapper::OnDestroy(npobj);
915
0
916
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_NOISY,
917
0
                   ("Deleting NPObject %p, refcount hit 0\n", npobj));
918
0
919
0
    if (npobj->_class && npobj->_class->deallocate) {
920
0
      npobj->_class->deallocate(npobj);
921
0
    } else {
922
0
      free(npobj);
923
0
    }
924
0
  }
925
0
}
926
927
bool
928
_invoke(NPP npp, NPObject* npobj, NPIdentifier method, const NPVariant *args,
929
        uint32_t argCount, NPVariant *result)
930
0
{
931
0
  if (!NS_IsMainThread()) {
932
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_invoke called from the wrong thread\n"));
933
0
    return false;
934
0
  }
935
0
  if (!npp || !npobj || !npobj->_class || !npobj->_class->invoke)
936
0
    return false;
937
0
938
0
  PluginDestructionGuard guard(npp);
939
0
940
0
  NPPExceptionAutoHolder nppExceptionHolder;
941
0
  NPPAutoPusher nppPusher(npp);
942
0
943
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NOISY,
944
0
                 ("NPN_Invoke(npp %p, npobj %p, method %p, args %d\n", npp,
945
0
                  npobj, method, argCount));
946
0
947
0
  return npobj->_class->invoke(npobj, method, args, argCount, result);
948
0
}
949
950
bool
951
_invokeDefault(NPP npp, NPObject* npobj, const NPVariant *args,
952
               uint32_t argCount, NPVariant *result)
953
0
{
954
0
  if (!NS_IsMainThread()) {
955
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_invokedefault called from the wrong thread\n"));
956
0
    return false;
957
0
  }
958
0
  if (!npp || !npobj || !npobj->_class || !npobj->_class->invokeDefault)
959
0
    return false;
960
0
961
0
  NPPExceptionAutoHolder nppExceptionHolder;
962
0
  NPPAutoPusher nppPusher(npp);
963
0
964
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NOISY,
965
0
                 ("NPN_InvokeDefault(npp %p, npobj %p, args %d\n", npp,
966
0
                  npobj, argCount));
967
0
968
0
  return npobj->_class->invokeDefault(npobj, args, argCount, result);
969
0
}
970
971
bool
972
_evaluate(NPP npp, NPObject* npobj, NPString *script, NPVariant *result)
973
0
{
974
0
  if (!NS_IsMainThread()) {
975
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_evaluate called from the wrong thread\n"));
976
0
    return false;
977
0
  }
978
0
  if (!npp)
979
0
    return false;
980
0
981
0
  NPPAutoPusher nppPusher(npp);
982
0
983
0
  nsIDocument *doc = GetDocumentFromNPP(npp);
984
0
  NS_ENSURE_TRUE(doc, false);
985
0
986
0
  nsGlobalWindowInner* win = nsGlobalWindowInner::Cast(doc->GetInnerWindow());
987
0
  if (NS_WARN_IF(!win || !win->FastGetGlobalJSObject())) {
988
0
    return false;
989
0
  }
990
0
991
0
  nsAutoMicroTask mt;
992
0
  dom::AutoEntryScript aes(win, "NPAPI NPN_evaluate");
993
0
  JSContext* cx = aes.cx();
994
0
995
0
  JS::Rooted<JSObject*> obj(cx, nsNPObjWrapper::GetNewOrUsed(npp, cx, npobj));
996
0
997
0
  if (!obj) {
998
0
    return false;
999
0
  }
1000
0
1001
0
  obj = js::ToWindowIfWindowProxy(obj);
1002
0
  MOZ_ASSERT(obj, "ToWindowIfWindowProxy should never return null");
1003
0
1004
0
  if (result) {
1005
0
    // Initialize the out param to void
1006
0
    VOID_TO_NPVARIANT(*result);
1007
0
  }
1008
0
1009
0
  if (!script || !script->UTF8Length || !script->UTF8Characters) {
1010
0
    // Nothing to evaluate.
1011
0
1012
0
    return true;
1013
0
  }
1014
0
1015
0
  NS_ConvertUTF8toUTF16 utf16script(script->UTF8Characters,
1016
0
                                    script->UTF8Length);
1017
0
1018
0
  nsIPrincipal *principal = doc->NodePrincipal();
1019
0
1020
0
  nsAutoCString specStr;
1021
0
  const char *spec;
1022
0
1023
0
  nsCOMPtr<nsIURI> uri;
1024
0
  principal->GetURI(getter_AddRefs(uri));
1025
0
1026
0
  if (uri) {
1027
0
    uri->GetSpec(specStr);
1028
0
    spec = specStr.get();
1029
0
  } else {
1030
0
    // No URI in a principal means it's the system principal. If the
1031
0
    // document URI is a chrome:// URI, pass that in as the URI of the
1032
0
    // script, else pass in null for the filename as there's no way to
1033
0
    // know where this document really came from. Passing in null here
1034
0
    // also means that the script gets treated by XPConnect as if it
1035
0
    // needs additional protection, which is what we want for unknown
1036
0
    // chrome code anyways.
1037
0
1038
0
    uri = doc->GetDocumentURI();
1039
0
    bool isChrome = false;
1040
0
1041
0
    if (uri && NS_SUCCEEDED(uri->SchemeIs("chrome", &isChrome)) && isChrome) {
1042
0
      uri->GetSpec(specStr);
1043
0
      spec = specStr.get();
1044
0
    } else {
1045
0
      spec = nullptr;
1046
0
    }
1047
0
  }
1048
0
1049
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NOISY,
1050
0
                 ("NPN_Evaluate(npp %p, npobj %p, script <<<%s>>>) called\n",
1051
0
                  npp, npobj, script->UTF8Characters));
1052
0
1053
0
  JS::CompileOptions options(cx);
1054
0
  options.setFileAndLine(spec, 0);
1055
0
  JS::Rooted<JS::Value> rval(cx);
1056
0
  JS::AutoObjectVector scopeChain(cx);
1057
0
  if (!JS_IsGlobalObject(obj) && !scopeChain.append(obj)) {
1058
0
    return false;
1059
0
  }
1060
0
  // nsNPObjWrapper::GetNewOrUsed returns an object in the current compartment
1061
0
  // of the JSContext (it might be a CCW).
1062
0
  MOZ_RELEASE_ASSERT(js::GetObjectCompartment(obj) ==
1063
0
                     js::GetContextCompartment(cx),
1064
0
                     "nsNPObjWrapper::GetNewOrUsed must wrap its return value");
1065
0
  obj = JS::CurrentGlobalOrNull(cx);
1066
0
  MOZ_ASSERT(obj);
1067
0
  nsresult rv = NS_OK;
1068
0
  {
1069
0
    nsJSUtils::ExecutionContext exec(cx, obj);
1070
0
    exec.SetScopeChain(scopeChain);
1071
0
    exec.CompileAndExec(options, utf16script);
1072
0
    rv = exec.ExtractReturnValue(&rval);
1073
0
  }
1074
0
1075
0
  if (!JS_WrapValue(cx, &rval)) {
1076
0
    return false;
1077
0
  }
1078
0
1079
0
  return NS_SUCCEEDED(rv) &&
1080
0
         (!result || JSValToNPVariant(npp, cx, rval, result));
1081
0
}
1082
1083
bool
1084
_getproperty(NPP npp, NPObject* npobj, NPIdentifier property,
1085
             NPVariant *result)
1086
0
{
1087
0
  if (!NS_IsMainThread()) {
1088
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_getproperty called from the wrong thread\n"));
1089
0
    return false;
1090
0
  }
1091
0
  if (!npp || !npobj || !npobj->_class || !npobj->_class->getProperty)
1092
0
    return false;
1093
0
1094
0
  NPPExceptionAutoHolder nppExceptionHolder;
1095
0
  NPPAutoPusher nppPusher(npp);
1096
0
1097
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NOISY,
1098
0
                 ("NPN_GetProperty(npp %p, npobj %p, property %p) called\n",
1099
0
                  npp, npobj, property));
1100
0
1101
0
  if (!npobj->_class->getProperty(npobj, property, result))
1102
0
    return false;
1103
0
1104
0
  return true;
1105
0
}
1106
1107
bool
1108
_setproperty(NPP npp, NPObject* npobj, NPIdentifier property,
1109
             const NPVariant *value)
1110
0
{
1111
0
  if (!NS_IsMainThread()) {
1112
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_setproperty called from the wrong thread\n"));
1113
0
    return false;
1114
0
  }
1115
0
  if (!npp || !npobj || !npobj->_class || !npobj->_class->setProperty)
1116
0
    return false;
1117
0
1118
0
  NPPExceptionAutoHolder nppExceptionHolder;
1119
0
  NPPAutoPusher nppPusher(npp);
1120
0
1121
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NOISY,
1122
0
                 ("NPN_SetProperty(npp %p, npobj %p, property %p) called\n",
1123
0
                  npp, npobj, property));
1124
0
1125
0
  return npobj->_class->setProperty(npobj, property, value);
1126
0
}
1127
1128
bool
1129
_removeproperty(NPP npp, NPObject* npobj, NPIdentifier property)
1130
0
{
1131
0
  if (!NS_IsMainThread()) {
1132
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_removeproperty called from the wrong thread\n"));
1133
0
    return false;
1134
0
  }
1135
0
  if (!npp || !npobj || !npobj->_class || !npobj->_class->removeProperty)
1136
0
    return false;
1137
0
1138
0
  NPPExceptionAutoHolder nppExceptionHolder;
1139
0
  NPPAutoPusher nppPusher(npp);
1140
0
1141
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NOISY,
1142
0
                 ("NPN_RemoveProperty(npp %p, npobj %p, property %p) called\n",
1143
0
                  npp, npobj, property));
1144
0
1145
0
  return npobj->_class->removeProperty(npobj, property);
1146
0
}
1147
1148
bool
1149
_hasproperty(NPP npp, NPObject* npobj, NPIdentifier propertyName)
1150
0
{
1151
0
  if (!NS_IsMainThread()) {
1152
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_hasproperty called from the wrong thread\n"));
1153
0
    return false;
1154
0
  }
1155
0
  if (!npp || !npobj || !npobj->_class || !npobj->_class->hasProperty)
1156
0
    return false;
1157
0
1158
0
  NPPExceptionAutoHolder nppExceptionHolder;
1159
0
  NPPAutoPusher nppPusher(npp);
1160
0
1161
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NOISY,
1162
0
                 ("NPN_HasProperty(npp %p, npobj %p, property %p) called\n",
1163
0
                  npp, npobj, propertyName));
1164
0
1165
0
  return npobj->_class->hasProperty(npobj, propertyName);
1166
0
}
1167
1168
bool
1169
_hasmethod(NPP npp, NPObject* npobj, NPIdentifier methodName)
1170
0
{
1171
0
  if (!NS_IsMainThread()) {
1172
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_hasmethod called from the wrong thread\n"));
1173
0
    return false;
1174
0
  }
1175
0
  if (!npp || !npobj || !npobj->_class || !npobj->_class->hasMethod)
1176
0
    return false;
1177
0
1178
0
  NPPExceptionAutoHolder nppExceptionHolder;
1179
0
  NPPAutoPusher nppPusher(npp);
1180
0
1181
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NOISY,
1182
0
                 ("NPN_HasMethod(npp %p, npobj %p, property %p) called\n",
1183
0
                  npp, npobj, methodName));
1184
0
1185
0
  return npobj->_class->hasMethod(npobj, methodName);
1186
0
}
1187
1188
bool
1189
_enumerate(NPP npp, NPObject *npobj, NPIdentifier **identifier,
1190
           uint32_t *count)
1191
0
{
1192
0
  if (!NS_IsMainThread()) {
1193
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_enumerate called from the wrong thread\n"));
1194
0
    return false;
1195
0
  }
1196
0
  if (!npp || !npobj || !npobj->_class)
1197
0
    return false;
1198
0
1199
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NOISY,
1200
0
                 ("NPN_Enumerate(npp %p, npobj %p) called\n", npp, npobj));
1201
0
1202
0
  if (!NP_CLASS_STRUCT_VERSION_HAS_ENUM(npobj->_class) ||
1203
0
      !npobj->_class->enumerate) {
1204
0
    *identifier = 0;
1205
0
    *count = 0;
1206
0
    return true;
1207
0
  }
1208
0
1209
0
  NPPExceptionAutoHolder nppExceptionHolder;
1210
0
  NPPAutoPusher nppPusher(npp);
1211
0
1212
0
  return npobj->_class->enumerate(npobj, identifier, count);
1213
0
}
1214
1215
bool
1216
_construct(NPP npp, NPObject* npobj, const NPVariant *args,
1217
               uint32_t argCount, NPVariant *result)
1218
0
{
1219
0
  if (!NS_IsMainThread()) {
1220
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_construct called from the wrong thread\n"));
1221
0
    return false;
1222
0
  }
1223
0
  if (!npp || !npobj || !npobj->_class ||
1224
0
      !NP_CLASS_STRUCT_VERSION_HAS_CTOR(npobj->_class) ||
1225
0
      !npobj->_class->construct) {
1226
0
    return false;
1227
0
  }
1228
0
1229
0
  NPPExceptionAutoHolder nppExceptionHolder;
1230
0
  NPPAutoPusher nppPusher(npp);
1231
0
1232
0
  return npobj->_class->construct(npobj, args, argCount, result);
1233
0
}
1234
1235
void
1236
_releasevariantvalue(NPVariant* variant)
1237
0
{
1238
0
  if (!NS_IsMainThread()) {
1239
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_releasevariantvalue called from the wrong thread\n"));
1240
0
  }
1241
0
  switch (variant->type) {
1242
0
  case NPVariantType_Void :
1243
0
  case NPVariantType_Null :
1244
0
  case NPVariantType_Bool :
1245
0
  case NPVariantType_Int32 :
1246
0
  case NPVariantType_Double :
1247
0
    break;
1248
0
  case NPVariantType_String :
1249
0
    {
1250
0
      const NPString *s = &NPVARIANT_TO_STRING(*variant);
1251
0
1252
0
      if (s->UTF8Characters) {
1253
#if defined(MOZ_MEMORY) && defined(XP_WIN)
1254
        if (malloc_usable_size((void *)s->UTF8Characters) != 0) {
1255
          free((void*)s->UTF8Characters);
1256
        } else {
1257
          void *p = (void *)s->UTF8Characters;
1258
          DWORD nheaps = 0;
1259
          AutoTArray<HANDLE, 50> heaps;
1260
          nheaps = GetProcessHeaps(0, heaps.Elements());
1261
          heaps.AppendElements(nheaps);
1262
          GetProcessHeaps(nheaps, heaps.Elements());
1263
          for (DWORD i = 0; i < nheaps; i++) {
1264
            if (InHeap(heaps[i], p)) {
1265
              HeapFree(heaps[i], 0, p);
1266
              break;
1267
            }
1268
          }
1269
        }
1270
#else
1271
        free((void *)s->UTF8Characters);
1272
0
#endif
1273
0
      }
1274
0
      break;
1275
0
    }
1276
0
  case NPVariantType_Object:
1277
0
    {
1278
0
      NPObject *npobj = NPVARIANT_TO_OBJECT(*variant);
1279
0
1280
0
      if (npobj)
1281
0
        _releaseobject(npobj);
1282
0
1283
0
      break;
1284
0
    }
1285
0
  default:
1286
0
    NS_ERROR("Unknown NPVariant type!");
1287
0
  }
1288
0
1289
0
  VOID_TO_NPVARIANT(*variant);
1290
0
}
1291
1292
void
1293
_setexception(NPObject* npobj, const NPUTF8 *message)
1294
0
{
1295
0
  if (!NS_IsMainThread()) {
1296
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_setexception called from the wrong thread\n"));
1297
0
    return;
1298
0
  }
1299
0
1300
0
  if (!message) return;
1301
0
1302
0
  if (gNPPException) {
1303
0
    // If a plugin throws multiple exceptions, we'll only report the
1304
0
    // last one for now.
1305
0
    free(gNPPException);
1306
0
  }
1307
0
1308
0
  gNPPException = strdup(message);
1309
0
}
1310
1311
NPError
1312
_getvalue(NPP npp, NPNVariable variable, void *result)
1313
0
{
1314
0
  if (!NS_IsMainThread()) {
1315
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_getvalue called from the wrong thread\n"));
1316
0
    return NPERR_INVALID_PARAM;
1317
0
  }
1318
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NORMAL, ("NPN_GetValue: npp=%p, var=%d\n",
1319
0
                                     (void*)npp, (int)variable));
1320
0
1321
0
  nsresult res;
1322
0
1323
0
  PluginDestructionGuard guard(npp);
1324
0
1325
0
  // Cast NPNVariable enum to int to avoid warnings about including switch
1326
0
  // cases for android_npapi.h's non-standard ANPInterface values.
1327
0
  switch (static_cast<int>(variable)) {
1328
0
1329
0
#if defined(XP_UNIX) && !defined(XP_MACOSX)
1330
0
  case NPNVxDisplay : {
1331
0
#if defined(MOZ_X11)
1332
0
    if (npp) {
1333
0
      nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *) npp->ndata;
1334
0
      bool windowless = false;
1335
0
      inst->IsWindowless(&windowless);
1336
0
      // The documentation on the types for many variables in NP(N|P)_GetValue
1337
0
      // is vague.  Often boolean values are NPBool (1 byte), but
1338
0
      // https://developer.mozilla.org/en/XEmbed_Extension_for_Mozilla_Plugins
1339
0
      // treats NPPVpluginNeedsXEmbed as PRBool (int), and
1340
0
      // on x86/32-bit, flash stores to this using |movl 0x1,&needsXEmbed|.
1341
0
      // thus we can't use NPBool for needsXEmbed, or the three bytes above
1342
0
      // it on the stack would get clobbered. so protect with the larger bool.
1343
0
      int needsXEmbed = 0;
1344
0
      if (!windowless) {
1345
0
        res = inst->GetValueFromPlugin(NPPVpluginNeedsXEmbed, &needsXEmbed);
1346
0
        // If the call returned an error code make sure we still use our default value.
1347
0
        if (NS_FAILED(res)) {
1348
0
          needsXEmbed = 0;
1349
0
        }
1350
0
      }
1351
0
      if (windowless || needsXEmbed) {
1352
0
        (*(Display **)result) = mozilla::DefaultXDisplay();
1353
0
        return NPERR_NO_ERROR;
1354
0
      }
1355
0
    }
1356
0
#endif
1357
0
    return NPERR_GENERIC_ERROR;
1358
0
  }
1359
0
1360
0
  case NPNVxtAppContext:
1361
0
    return NPERR_GENERIC_ERROR;
1362
0
#endif
1363
0
1364
0
#if defined(XP_WIN) || defined(MOZ_WIDGET_GTK)
1365
0
  case NPNVnetscapeWindow: {
1366
0
    if (!npp || !npp->ndata)
1367
0
      return NPERR_INVALID_INSTANCE_ERROR;
1368
0
1369
0
    nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *) npp->ndata;
1370
0
1371
0
    RefPtr<nsPluginInstanceOwner> owner = inst->GetOwner();
1372
0
    NS_ENSURE_TRUE(owner, NPERR_NO_ERROR);
1373
0
1374
0
    if (NS_SUCCEEDED(owner->GetNetscapeWindow(result))) {
1375
0
      return NPERR_NO_ERROR;
1376
0
    }
1377
0
    return NPERR_GENERIC_ERROR;
1378
0
  }
1379
0
#endif
1380
0
1381
0
  case NPNVjavascriptEnabledBool: {
1382
0
    *(NPBool*)result = false;
1383
0
    bool js = false;
1384
0
    res = Preferences::GetBool("javascript.enabled", &js);
1385
0
    if (NS_SUCCEEDED(res)) {
1386
0
      *(NPBool*)result = js;
1387
0
    }
1388
0
    return NPERR_NO_ERROR;
1389
0
  }
1390
0
1391
0
  case NPNVasdEnabledBool:
1392
0
    *(NPBool*)result = false;
1393
0
    return NPERR_NO_ERROR;
1394
0
1395
0
  case NPNVisOfflineBool: {
1396
0
    bool offline = false;
1397
0
    nsCOMPtr<nsIIOService> ioservice =
1398
0
      do_GetService(NS_IOSERVICE_CONTRACTID, &res);
1399
0
    if (NS_SUCCEEDED(res))
1400
0
      res = ioservice->GetOffline(&offline);
1401
0
    if (NS_FAILED(res))
1402
0
      return NPERR_GENERIC_ERROR;
1403
0
1404
0
    *(NPBool*)result = offline;
1405
0
    return NPERR_NO_ERROR;
1406
0
  }
1407
0
1408
0
  case NPNVToolkit: {
1409
0
#ifdef MOZ_WIDGET_GTK
1410
0
    *((NPNToolkitType*)result) = NPNVGtk2;
1411
0
#endif
1412
0
1413
0
    if (*(NPNToolkitType*)result)
1414
0
        return NPERR_NO_ERROR;
1415
0
1416
0
    return NPERR_GENERIC_ERROR;
1417
0
  }
1418
0
1419
0
  case NPNVSupportsXEmbedBool: {
1420
0
#ifdef MOZ_WIDGET_GTK
1421
0
    *(NPBool*)result = true;
1422
#else
1423
    *(NPBool*)result = false;
1424
#endif
1425
0
    return NPERR_NO_ERROR;
1426
0
  }
1427
0
1428
0
  case NPNVWindowNPObject: {
1429
0
    *(NPObject **)result = _getwindowobject(npp);
1430
0
1431
0
    return *(NPObject **)result ? NPERR_NO_ERROR : NPERR_GENERIC_ERROR;
1432
0
  }
1433
0
1434
0
  case NPNVPluginElementNPObject: {
1435
0
    *(NPObject **)result = _getpluginelement(npp);
1436
0
1437
0
    return *(NPObject **)result ? NPERR_NO_ERROR : NPERR_GENERIC_ERROR;
1438
0
  }
1439
0
1440
0
  case NPNVSupportsWindowless: {
1441
0
#if defined(XP_WIN) || defined(XP_MACOSX) || \
1442
0
    (defined(MOZ_X11) && defined(MOZ_WIDGET_GTK))
1443
0
    *(NPBool*)result = true;
1444
#else
1445
    *(NPBool*)result = false;
1446
#endif
1447
0
    return NPERR_NO_ERROR;
1448
0
  }
1449
0
1450
0
  case NPNVprivateModeBool: {
1451
0
    bool privacy;
1452
0
    nsNPAPIPluginInstance *inst = static_cast<nsNPAPIPluginInstance*>(npp->ndata);
1453
0
    if (!inst)
1454
0
      return NPERR_GENERIC_ERROR;
1455
0
1456
0
    nsresult rv = inst->IsPrivateBrowsing(&privacy);
1457
0
    if (NS_FAILED(rv))
1458
0
      return NPERR_GENERIC_ERROR;
1459
0
    *(NPBool*)result = (NPBool)privacy;
1460
0
    return NPERR_NO_ERROR;
1461
0
  }
1462
0
1463
0
  case NPNVdocumentOrigin: {
1464
0
    nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *)npp->ndata;
1465
0
    if (!inst) {
1466
0
      return NPERR_GENERIC_ERROR;
1467
0
    }
1468
0
1469
0
    RefPtr<dom::Element> element;
1470
0
    inst->GetDOMElement(getter_AddRefs(element));
1471
0
    if (!element) {
1472
0
      return NPERR_GENERIC_ERROR;
1473
0
    }
1474
0
1475
0
    nsIPrincipal* principal = element->NodePrincipal();
1476
0
1477
0
    nsAutoString utf16Origin;
1478
0
    res = nsContentUtils::GetUTFOrigin(principal, utf16Origin);
1479
0
    if (NS_FAILED(res)) {
1480
0
      return NPERR_GENERIC_ERROR;
1481
0
    }
1482
0
1483
0
    nsCOMPtr<nsIIDNService> idnService = do_GetService(NS_IDNSERVICE_CONTRACTID);
1484
0
    if (!idnService) {
1485
0
      return NPERR_GENERIC_ERROR;
1486
0
    }
1487
0
1488
0
    // This is a bit messy: we convert to UTF-8 here, but then
1489
0
    // nsIDNService::Normalize will convert back to UTF-16 for processing,
1490
0
    // and back to UTF-8 again to return the result.
1491
0
    // Alternative: perhaps we should add a NormalizeUTF16 version of the API,
1492
0
    // and just convert to UTF-8 for the final return (resulting in one
1493
0
    // encoding form conversion instead of three).
1494
0
    NS_ConvertUTF16toUTF8 utf8Origin(utf16Origin);
1495
0
    nsAutoCString normalizedUTF8Origin;
1496
0
    res = idnService->Normalize(utf8Origin, normalizedUTF8Origin);
1497
0
    if (NS_FAILED(res)) {
1498
0
      return NPERR_GENERIC_ERROR;
1499
0
    }
1500
0
1501
0
    *(char**)result = ToNewCString(normalizedUTF8Origin);
1502
0
    return *(char**)result ? NPERR_NO_ERROR : NPERR_GENERIC_ERROR;
1503
0
  }
1504
0
1505
#ifdef XP_MACOSX
1506
  case NPNVpluginDrawingModel: {
1507
    if (npp) {
1508
      nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance*)npp->ndata;
1509
      if (inst) {
1510
        NPDrawingModel drawingModel;
1511
        inst->GetDrawingModel((int32_t*)&drawingModel);
1512
        *(NPDrawingModel*)result = drawingModel;
1513
        return NPERR_NO_ERROR;
1514
      }
1515
    }
1516
    return NPERR_GENERIC_ERROR;
1517
  }
1518
1519
#ifndef NP_NO_QUICKDRAW
1520
  case NPNVsupportsQuickDrawBool: {
1521
    *(NPBool*)result = false;
1522
1523
    return NPERR_NO_ERROR;
1524
  }
1525
#endif
1526
1527
  case NPNVsupportsCoreGraphicsBool: {
1528
    *(NPBool*)result = true;
1529
1530
    return NPERR_NO_ERROR;
1531
  }
1532
1533
  case NPNVsupportsCoreAnimationBool: {
1534
    *(NPBool*)result = true;
1535
1536
    return NPERR_NO_ERROR;
1537
  }
1538
1539
  case NPNVsupportsInvalidatingCoreAnimationBool: {
1540
    *(NPBool*)result = true;
1541
1542
    return NPERR_NO_ERROR;
1543
  }
1544
1545
  case NPNVsupportsCompositingCoreAnimationPluginsBool: {
1546
    *(NPBool*)result = PR_TRUE;
1547
1548
    return NPERR_NO_ERROR;
1549
  }
1550
1551
#ifndef NP_NO_CARBON
1552
  case NPNVsupportsCarbonBool: {
1553
    *(NPBool*)result = false;
1554
1555
    return NPERR_NO_ERROR;
1556
  }
1557
#endif
1558
  case NPNVsupportsCocoaBool: {
1559
    *(NPBool*)result = true;
1560
1561
    return NPERR_NO_ERROR;
1562
  }
1563
1564
  case NPNVsupportsUpdatedCocoaTextInputBool: {
1565
    *(NPBool*)result = true;
1566
    return NPERR_NO_ERROR;
1567
  }
1568
#endif
1569
1570
#if defined(XP_MACOSX) || defined(XP_WIN)
1571
  case NPNVcontentsScaleFactor: {
1572
    nsNPAPIPluginInstance *inst =
1573
      (nsNPAPIPluginInstance *) (npp ? npp->ndata : nullptr);
1574
    double scaleFactor = inst ? inst->GetContentsScaleFactor() : 1.0;
1575
    *(double*)result = scaleFactor;
1576
    return NPERR_NO_ERROR;
1577
  }
1578
#endif
1579
1580
0
  case NPNVCSSZoomFactor: {
1581
0
    nsNPAPIPluginInstance *inst =
1582
0
      (nsNPAPIPluginInstance *) (npp ? npp->ndata : nullptr);
1583
0
    double scaleFactor = inst ? inst->GetCSSZoomFactor() : 1.0;
1584
0
    *(double*)result = scaleFactor;
1585
0
    return NPERR_NO_ERROR;
1586
0
  }
1587
0
1588
0
  // we no longer hand out any XPCOM objects
1589
0
  case NPNVDOMElement:
1590
0
  case NPNVDOMWindow:
1591
0
  case NPNVserviceManager:
1592
0
    // old XPCOM objects, no longer supported, but null out the out
1593
0
    // param to avoid crashing plugins that still try to use this.
1594
0
    *(nsISupports**)result = nullptr;
1595
0
    MOZ_FALLTHROUGH;
1596
0
1597
0
  default:
1598
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_NORMAL, ("NPN_getvalue unhandled get value: %d\n", variable));
1599
0
    return NPERR_GENERIC_ERROR;
1600
0
  }
1601
0
}
1602
1603
NPError
1604
_setvalue(NPP npp, NPPVariable variable, void *result)
1605
0
{
1606
0
  if (!NS_IsMainThread()) {
1607
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_setvalue called from the wrong thread\n"));
1608
0
    return NPERR_INVALID_PARAM;
1609
0
  }
1610
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NORMAL, ("NPN_SetValue: npp=%p, var=%d\n",
1611
0
                                     (void*)npp, (int)variable));
1612
0
1613
0
  if (!npp)
1614
0
    return NPERR_INVALID_INSTANCE_ERROR;
1615
0
1616
0
  nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *) npp->ndata;
1617
0
1618
0
  NS_ASSERTION(inst, "null instance");
1619
0
1620
0
  if (!inst)
1621
0
    return NPERR_INVALID_INSTANCE_ERROR;
1622
0
1623
0
  PluginDestructionGuard guard(inst);
1624
0
1625
0
  // Cast NPNVariable enum to int to avoid warnings about including switch
1626
0
  // cases for android_npapi.h's non-standard ANPInterface values.
1627
0
  switch (static_cast<int>(variable)) {
1628
0
1629
0
    // we should keep backward compatibility with NPAPI where the
1630
0
    // actual pointer value is checked rather than its content
1631
0
    // when passing booleans
1632
0
    case NPPVpluginWindowBool: {
1633
#ifdef XP_MACOSX
1634
      // This setting doesn't apply to OS X (only to Windows and Unix/Linux).
1635
      // See https://developer.mozilla.org/En/NPN_SetValue#section_5.  Return
1636
      // NPERR_NO_ERROR here to conform to other browsers' behavior on OS X
1637
      // (e.g. Safari and Opera).
1638
      return NPERR_NO_ERROR;
1639
#else
1640
      NPBool bWindowless = (result == nullptr);
1641
0
      return inst->SetWindowless(bWindowless);
1642
0
#endif
1643
0
    }
1644
0
    case NPPVpluginTransparentBool: {
1645
0
      NPBool bTransparent = (result != nullptr);
1646
0
      return inst->SetTransparent(bTransparent);
1647
0
    }
1648
0
1649
0
    case NPPVjavascriptPushCallerBool: {
1650
0
      return NPERR_NO_ERROR;
1651
0
    }
1652
0
1653
0
    case NPPVpluginKeepLibraryInMemory: {
1654
0
      NPBool bCached = (result != nullptr);
1655
0
      inst->SetCached(bCached);
1656
0
      return NPERR_NO_ERROR;
1657
0
    }
1658
0
1659
0
    case NPPVpluginUsesDOMForCursorBool: {
1660
0
      bool useDOMForCursor = (result != nullptr);
1661
0
      return inst->SetUsesDOMForCursor(useDOMForCursor);
1662
0
    }
1663
0
1664
0
    case NPPVpluginIsPlayingAudio: {
1665
0
      const bool isPlaying = result;
1666
0
1667
0
      nsNPAPIPluginInstance* inst = (nsNPAPIPluginInstance*) npp->ndata;
1668
0
      MOZ_ASSERT(inst);
1669
0
1670
0
      if (!isPlaying && !inst->HasAudioChannelAgent()) {
1671
0
        return NPERR_NO_ERROR;
1672
0
      }
1673
0
1674
0
      if (isPlaying) {
1675
0
        inst->NotifyStartedPlaying();
1676
0
      } else {
1677
0
        inst->NotifyStoppedPlaying();
1678
0
      }
1679
0
1680
0
      return NPERR_NO_ERROR;
1681
0
    }
1682
0
1683
0
    case NPPVpluginDrawingModel: {
1684
0
      if (inst) {
1685
0
        inst->SetDrawingModel((NPDrawingModel)NS_PTR_TO_INT32(result));
1686
0
        return NPERR_NO_ERROR;
1687
0
      }
1688
0
      return NPERR_GENERIC_ERROR;
1689
0
    }
1690
0
1691
#ifdef XP_MACOSX
1692
    case NPPVpluginEventModel: {
1693
      if (inst) {
1694
        inst->SetEventModel((NPEventModel)NS_PTR_TO_INT32(result));
1695
        return NPERR_NO_ERROR;
1696
      }
1697
      else {
1698
        return NPERR_GENERIC_ERROR;
1699
      }
1700
    }
1701
#endif
1702
0
    default:
1703
0
      return NPERR_GENERIC_ERROR;
1704
0
  }
1705
0
}
1706
1707
NPError
1708
_requestread(NPStream *pstream, NPByteRange *rangeList)
1709
0
{
1710
0
  return NPERR_STREAM_NOT_SEEKABLE;
1711
0
}
1712
1713
// Deprecated, only stubbed out
1714
void* /* OJI type: JRIEnv* */
1715
_getJavaEnv()
1716
0
{
1717
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NORMAL, ("NPN_GetJavaEnv\n"));
1718
0
  return nullptr;
1719
0
}
1720
1721
const char *
1722
_useragent(NPP npp)
1723
0
{
1724
0
  if (!NS_IsMainThread()) {
1725
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_useragent called from the wrong thread\n"));
1726
0
    return nullptr;
1727
0
  }
1728
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NORMAL, ("NPN_UserAgent: npp=%p\n", (void*)npp));
1729
0
1730
0
  nsCOMPtr<nsIPluginHost> pluginHostCOM(do_GetService(MOZ_PLUGIN_HOST_CONTRACTID));
1731
0
  nsPluginHost *pluginHost = static_cast<nsPluginHost*>(pluginHostCOM.get());
1732
0
  if (!pluginHost) {
1733
0
    return nullptr;
1734
0
  }
1735
0
1736
0
  const char *retstr;
1737
0
  nsresult rv = pluginHost->UserAgent(&retstr);
1738
0
  if (NS_FAILED(rv))
1739
0
    return nullptr;
1740
0
1741
0
  return retstr;
1742
0
}
1743
1744
void *
1745
_memalloc (uint32_t size)
1746
0
{
1747
0
  if (!NS_IsMainThread()) {
1748
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_NORMAL,("NPN_memalloc called from the wrong thread\n"));
1749
0
  }
1750
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NOISY, ("NPN_MemAlloc: size=%d\n", size));
1751
0
  return moz_xmalloc(size);
1752
0
}
1753
1754
// Deprecated, only stubbed out
1755
void* /* OJI type: jref */
1756
_getJavaPeer(NPP npp)
1757
0
{
1758
0
  NPN_PLUGIN_LOG(PLUGIN_LOG_NORMAL, ("NPN_GetJavaPeer: npp=%p\n", (void*)npp));
1759
0
  return nullptr;
1760
0
}
1761
1762
void
1763
_pushpopupsenabledstate(NPP npp, NPBool enabled)
1764
0
{
1765
0
  if (!NS_IsMainThread()) {
1766
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_pushpopupsenabledstate called from the wrong thread\n"));
1767
0
    return;
1768
0
  }
1769
0
  nsNPAPIPluginInstance *inst = npp ? (nsNPAPIPluginInstance *)npp->ndata : nullptr;
1770
0
  if (!inst)
1771
0
    return;
1772
0
1773
0
  inst->PushPopupsEnabledState(enabled);
1774
0
}
1775
1776
void
1777
_poppopupsenabledstate(NPP npp)
1778
0
{
1779
0
  if (!NS_IsMainThread()) {
1780
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_poppopupsenabledstate called from the wrong thread\n"));
1781
0
    return;
1782
0
  }
1783
0
  nsNPAPIPluginInstance *inst = npp ? (nsNPAPIPluginInstance *)npp->ndata : nullptr;
1784
0
  if (!inst)
1785
0
    return;
1786
0
1787
0
  inst->PopPopupsEnabledState();
1788
0
}
1789
1790
NPError
1791
_getvalueforurl(NPP instance, NPNURLVariable variable, const char *url,
1792
                char **value, uint32_t *len)
1793
0
{
1794
0
  if (!NS_IsMainThread()) {
1795
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_getvalueforurl called from the wrong thread\n"));
1796
0
    return NPERR_GENERIC_ERROR;
1797
0
  }
1798
0
1799
0
  if (!instance) {
1800
0
    return NPERR_INVALID_PARAM;
1801
0
  }
1802
0
1803
0
  if (!url || !*url || !len) {
1804
0
    return NPERR_INVALID_URL;
1805
0
  }
1806
0
1807
0
  *len = 0;
1808
0
1809
0
  switch (variable) {
1810
0
  case NPNURLVProxy:
1811
0
    // NPNURLVProxy is no longer supported.
1812
0
    *value = nullptr;
1813
0
    return NPERR_GENERIC_ERROR;
1814
0
1815
0
  case NPNURLVCookie:
1816
0
    // NPNURLVCookie is no longer supported.
1817
0
    *value = nullptr;
1818
0
    return NPERR_GENERIC_ERROR;
1819
0
1820
0
  default:
1821
0
    // Fall through and return an error...
1822
0
    ;
1823
0
  }
1824
0
1825
0
  return NPERR_GENERIC_ERROR;
1826
0
}
1827
1828
NPError
1829
_setvalueforurl(NPP instance, NPNURLVariable variable, const char *url,
1830
                const char *value, uint32_t len)
1831
0
{
1832
0
  if (!NS_IsMainThread()) {
1833
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_setvalueforurl called from the wrong thread\n"));
1834
0
    return NPERR_GENERIC_ERROR;
1835
0
  }
1836
0
1837
0
  if (!instance) {
1838
0
    return NPERR_INVALID_PARAM;
1839
0
  }
1840
0
1841
0
  if (!url || !*url) {
1842
0
    return NPERR_INVALID_URL;
1843
0
  }
1844
0
1845
0
  switch (variable) {
1846
0
  case NPNURLVCookie:
1847
0
    // NPNURLVCookie is no longer supported.
1848
0
    return NPERR_GENERIC_ERROR;
1849
0
1850
0
  case NPNURLVProxy:
1851
0
    // We don't support setting proxy values, fall through...
1852
0
  default:
1853
0
    // Fall through and return an error...
1854
0
    ;
1855
0
  }
1856
0
1857
0
  return NPERR_GENERIC_ERROR;
1858
0
}
1859
1860
uint32_t
1861
_scheduletimer(NPP instance, uint32_t interval, NPBool repeat, PluginTimerFunc timerFunc)
1862
0
{
1863
0
  if (!NS_IsMainThread()) {
1864
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_scheduletimer called from the wrong thread\n"));
1865
0
    return 0;
1866
0
  }
1867
0
1868
0
  nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *)instance->ndata;
1869
0
  if (!inst)
1870
0
    return 0;
1871
0
1872
0
  return inst->ScheduleTimer(interval, repeat, timerFunc);
1873
0
}
1874
1875
void
1876
_unscheduletimer(NPP instance, uint32_t timerID)
1877
0
{
1878
0
  if (!NS_IsMainThread()) {
1879
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_unscheduletimer called from the wrong thread\n"));
1880
0
    return;
1881
0
  }
1882
0
1883
0
  nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *)instance->ndata;
1884
0
  if (!inst)
1885
0
    return;
1886
0
1887
0
  inst->UnscheduleTimer(timerID);
1888
0
}
1889
1890
NPError
1891
_popupcontextmenu(NPP instance, NPMenu* menu)
1892
0
{
1893
0
  if (!NS_IsMainThread()) {
1894
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_popupcontextmenu called from the wrong thread\n"));
1895
0
    return 0;
1896
0
  }
1897
0
1898
#ifdef MOZ_WIDGET_COCOA
1899
  nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *)instance->ndata;
1900
1901
  double pluginX, pluginY;
1902
  double screenX, screenY;
1903
1904
  const NPCocoaEvent* currentEvent = static_cast<NPCocoaEvent*>(inst->GetCurrentEvent());
1905
  if (!currentEvent) {
1906
    return NPERR_GENERIC_ERROR;
1907
  }
1908
1909
  // Ensure that the events has an x/y value.
1910
  if (currentEvent->type != NPCocoaEventMouseDown    &&
1911
      currentEvent->type != NPCocoaEventMouseUp      &&
1912
      currentEvent->type != NPCocoaEventMouseMoved   &&
1913
      currentEvent->type != NPCocoaEventMouseEntered &&
1914
      currentEvent->type != NPCocoaEventMouseExited  &&
1915
      currentEvent->type != NPCocoaEventMouseDragged) {
1916
      return NPERR_GENERIC_ERROR;
1917
  }
1918
1919
  pluginX = currentEvent->data.mouse.pluginX;
1920
  pluginY = currentEvent->data.mouse.pluginY;
1921
1922
  if ((pluginX < 0.0) || (pluginY < 0.0))
1923
    return NPERR_GENERIC_ERROR;
1924
1925
  NPBool success = _convertpoint(instance,
1926
                                 pluginX,  pluginY, NPCoordinateSpacePlugin,
1927
                                 &screenX, &screenY, NPCoordinateSpaceScreen);
1928
1929
  if (success) {
1930
    return mozilla::plugins::PluginUtilsOSX::ShowCocoaContextMenu(menu,
1931
                                    screenX, screenY,
1932
                                    nullptr,
1933
                                    nullptr);
1934
  } else {
1935
    NS_WARNING("Convertpoint failed, could not created contextmenu.");
1936
    return NPERR_GENERIC_ERROR;
1937
  }
1938
#else
1939
0
    NS_WARNING("Not supported on this platform!");
1940
0
    return NPERR_GENERIC_ERROR;
1941
0
#endif
1942
0
}
1943
1944
NPBool
1945
_convertpoint(NPP instance, double sourceX, double sourceY, NPCoordinateSpace sourceSpace, double *destX, double *destY, NPCoordinateSpace destSpace)
1946
0
{
1947
0
  if (!NS_IsMainThread()) {
1948
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_convertpoint called from the wrong thread\n"));
1949
0
    return 0;
1950
0
  }
1951
0
1952
0
  nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *)instance->ndata;
1953
0
  if (!inst)
1954
0
    return false;
1955
0
1956
0
  return inst->ConvertPoint(sourceX, sourceY, sourceSpace, destX, destY, destSpace);
1957
0
}
1958
1959
void
1960
_urlredirectresponse(NPP instance, void* notifyData, NPBool allow)
1961
0
{
1962
0
  if (!NS_IsMainThread()) {
1963
0
    NPN_PLUGIN_LOG(PLUGIN_LOG_ALWAYS,("NPN_convertpoint called from the wrong thread\n"));
1964
0
    return;
1965
0
  }
1966
0
1967
0
  nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *)instance->ndata;
1968
0
  if (!inst) {
1969
0
    return;
1970
0
  }
1971
0
1972
0
  inst->URLRedirectResponse(notifyData, allow);
1973
0
}
1974
1975
NPError
1976
_initasyncsurface(NPP instance, NPSize *size, NPImageFormat format, void *initData, NPAsyncSurface *surface)
1977
0
{
1978
0
  nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *)instance->ndata;
1979
0
  if (!inst) {
1980
0
    return NPERR_GENERIC_ERROR;
1981
0
  }
1982
0
1983
0
  return inst->InitAsyncSurface(size, format, initData, surface);
1984
0
}
1985
1986
NPError
1987
_finalizeasyncsurface(NPP instance, NPAsyncSurface *surface)
1988
0
{
1989
0
  nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *)instance->ndata;
1990
0
  if (!inst) {
1991
0
    return NPERR_GENERIC_ERROR;
1992
0
  }
1993
0
1994
0
  return inst->FinalizeAsyncSurface(surface);
1995
0
}
1996
1997
void
1998
_setcurrentasyncsurface(NPP instance, NPAsyncSurface *surface, NPRect *changed)
1999
0
{
2000
0
  nsNPAPIPluginInstance *inst = (nsNPAPIPluginInstance *)instance->ndata;
2001
0
  if (!inst) {
2002
0
    return;
2003
0
  }
2004
0
2005
0
  inst->SetCurrentAsyncSurface(surface, changed);
2006
0
}
2007
2008
} /* namespace parent */
2009
} /* namespace plugins */
2010
} /* namespace mozilla */