1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
|
// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef WEBKIT_ACTIVEX_SHIM_DISPATCH_OBJECT_H__
#define WEBKIT_ACTIVEX_SHIM_DISPATCH_OBJECT_H__
#include <oaidl.h>
#include <list>
#include "webkit/glue/plugins/nphostapi.h"
namespace activex_shim {
struct DispatchNPObject;
// DispatchObject provides service to translate calls on NPObject to the
// underlying IDispatch interface. It is isolated from the ActiveXPlugin, so
// that when we have scripts like:
// wmp.controls.stop();
// We can create a spawned dispatch object for "controls" -- an IDispatch
// interface returned from property "controls" of the wmp activex control.
class DispatchObject {
public:
DispatchObject(DispatchObject* root);
virtual ~DispatchObject();
// This is used when NPP_GetValue is called by browser and asked for
// NPPVpluginScriptableNPObject.
NPObject* GetScriptableNPObject();
// Object scripting
NPObject* NPAllocate(NPClass* theClass);
void NPInvalidate();
bool NPHasMethod(NPIdentifier name);
bool NPHasProperty(NPIdentifier name);
bool NPInvoke(NPIdentifier name, const NPVariant* args,
uint32_t argCount, NPVariant* result);
bool NPInvokeDefault(const NPVariant* args, uint32_t argCount,
NPVariant* result);
bool NPGetProperty(NPIdentifier name, NPVariant* variant);
bool NPSetProperty(NPIdentifier name, const NPVariant* variant);
bool NPRemoveProperty(NPIdentifier propertyName);
// Called by NPDeallocate so that we can remove our reference.
void OnDeallocateObject(DispatchNPObject* obj);
DispatchObject* root() { return root_== NULL ? this : root_; }
// Only the root object needs to take care of this.
void AddSpawned(DispatchObject* obj);
// If a spawned child is released earlier than the root object, it needs to
// call this function to remove itself from the children list, to avoid
// another destruction when the root object is being destructed.
void RemoveSpawned(DispatchObject* obj);
protected:
// Only the root object can release spawned dispatch object. The root object
// is coupled with the actual ActiveX control. Thus if the control is dead
// we must also release all Dispatch interfaces from that control.
void ReleaseSpawned();
// root_ is the owner of this object. If root_ == NULL, then this object
// itself is the root.
DispatchObject* const root_;
private:
typedef std::list<DispatchObject*> SpawnedChildrenList;
// Must be overrided by subclass to be functional.
virtual IDispatch* GetDispatch() = 0;
// If this is true, when the related npobject is released, it should delete
// this object as well.
virtual bool NPObjectOwnsMe() = 0;
// We create only one NPObject per ActiveXPlugin. It may have different life
// span than ActiveXPlugin thus we need a separate object created
// specifically for this purpose.
DispatchNPObject* npobject_;
// A list of spawned children from this root object (if it is).
SpawnedChildrenList spawned_children_;
bool deleting_spawned_children_;
};
// The spawned dipatch object contains a reference to an IDispatch interface
// that it owns. Its lifetime is controlled by the lifetime of related
// NPObject, and the root DispatchObject it is spawned from.
class SpawnedDispatchObject : public DispatchObject {
public:
// Constructor will addref to the dispatch interface, and add itself to
// spawned children of root.
SpawnedDispatchObject(IDispatch* dispatch, DispatchObject* root);
~SpawnedDispatchObject();
private:
virtual IDispatch* GetDispatch() { return dispatch_; }
virtual bool NPObjectOwnsMe() { return true; }
IDispatch* dispatch_;
};
// A simple extension of the NPObject. So that we can put additional information
// like who is the underlying DispatchObject with the NPObject. When methods of
// NPObject are requested we can resort to the DispatchObject to handle them.
struct DispatchNPObject : public NPObject {
DispatchObject* dispatch_object;
};
// These functions are to support scriptable plugin object.
NPObject* NPAllocate(NPP npp, NPClass* theClass);
void NPDeallocate(NPObject* obj);
void NPInvalidate(NPObject* obj);
bool NPHasMethod(NPObject* obj, NPIdentifier name);
bool NPInvoke(NPObject* obj, NPIdentifier name, const NPVariant* args,
uint32_t argCount, NPVariant* result);
bool NPInvokeDefault(NPObject* obj, const NPVariant* args, uint32_t argCount,
NPVariant* result);
bool NPHasProperty(NPObject* obj, NPIdentifier name);
bool NPGetProperty(NPObject* obj, NPIdentifier name, NPVariant* variant);
bool NPSetProperty(NPObject* obj, NPIdentifier name, const NPVariant* variant);
bool NPRemoveProperty(NPObject* npobj, NPIdentifier propertyName);
} // namespace activex_shim
#endif // #ifndef WEBKIT_ACTIVEX_SHIM_DISPATCH_OBJECT_H__
|