|
1 // sandbox.cpp |
|
2 // |
|
3 // Copyright (c) 2010 Accenture. All rights reserved. |
|
4 // This component and the accompanying materials are made available |
|
5 // under the terms of the "Eclipse Public License v1.0" |
|
6 // which accompanies this distribution, and is available |
|
7 // at the URL "http://www.eclipse.org/legal/epl-v10.html". |
|
8 // |
|
9 // Initial Contributors: |
|
10 // Accenture - Initial contribution |
|
11 // |
|
12 #include <e32base.h> |
|
13 #include "sandbox.h" |
|
14 #include <APMREC.H> |
|
15 #include <fshell/memoryaccess.h> |
|
16 |
|
17 enum TMsg |
|
18 { |
|
19 EGetRecog, |
|
20 EGetRecog2, |
|
21 ECloseServer, |
|
22 EGetVTablePtr, |
|
23 EMaxArgs, |
|
24 }; |
|
25 |
|
26 #ifndef SERVER |
|
27 |
|
28 |
|
29 class RSandboxSession : public RSessionBase |
|
30 { |
|
31 public: |
|
32 TInt Connect(const TDesC& aServerName) |
|
33 { |
|
34 return CreateSession(aServerName, TVersion(0,0,0)); |
|
35 } |
|
36 |
|
37 TInt GetRecogniserInfo(TUid aImplementationUid, RArray<TDataType>& aMimeTypes) |
|
38 { |
|
39 TInt size = SendReceive(EGetRecog, TIpcArgs(aImplementationUid.iUid)); |
|
40 if (size < 0) return size; |
|
41 TInt err = aMimeTypes.Reserve(size/sizeof(TDataType)); |
|
42 if (err) return err; |
|
43 RBuf8 buf; |
|
44 err = buf.Create(size); |
|
45 if (err) return err; |
|
46 err = SendReceive(EGetRecog2, TIpcArgs(&buf)); |
|
47 if (err) { buf.Close(); return err; } |
|
48 |
|
49 const TDataType* ptr = (const TDataType*)buf.Ptr(); |
|
50 for (TInt i = 0; i < size/sizeof(TDataType); i++) |
|
51 { |
|
52 err = aMimeTypes.Append(ptr[i]); |
|
53 if (err) break; |
|
54 } |
|
55 buf.Close(); |
|
56 return err; |
|
57 } |
|
58 |
|
59 TInt GetVTablePtrFromEcomUid(TUid aUid, TAny*& vtablePtr) |
|
60 { |
|
61 TPckgBuf<TAny*> pkg(NULL); |
|
62 TInt err = SendReceive(EGetVTablePtr, TIpcArgs(aUid.iUid, &pkg)); |
|
63 if (err) return err; |
|
64 vtablePtr = pkg(); |
|
65 return KErrNone; |
|
66 } |
|
67 |
|
68 void Byebye() |
|
69 { |
|
70 SendReceive(ECloseServer); |
|
71 } |
|
72 }; |
|
73 |
|
74 #define GETSESSIONL(process, session) \ |
|
75 RProcess process; \ |
|
76 User::LeaveIfError(process.Create(_L("QR3Sandbox.exe"), KNullDesC)); \ |
|
77 TRequestStatus stat; \ |
|
78 process.Rendezvous(stat); \ |
|
79 process.Resume(); \ |
|
80 User::WaitForRequest(stat); \ |
|
81 \ |
|
82 RSandboxSession session; \ |
|
83 User::LeaveIfError(session.Connect(sandbox.FullName())); |
|
84 |
|
85 |
|
86 void Sandbox::GetRecogniserInfoL(TUid aImplementationUid, RArray<TDataType>& aMimeTypes) |
|
87 { |
|
88 GETSESSIONL(sandbox, sess); |
|
89 |
|
90 User::LeaveIfError(sess.GetRecogniserInfo(aImplementationUid, aMimeTypes)); |
|
91 |
|
92 sess.Byebye(); |
|
93 sandbox.Close(); |
|
94 } |
|
95 |
|
96 void Sandbox::GetDllNameFromEcomUidL(RMemoryAccess& aMemAccess, TUid aUid, TFileName& aFileName) |
|
97 { |
|
98 // Try and instanciate object and figure out what DLL it belongs to by looking up its vtable pointer |
|
99 // We do the instanciation in a separate process so as to avoid worrying about cleanup or side-effects of instanciation |
|
100 |
|
101 GETSESSIONL(sandbox, sess); |
|
102 |
|
103 TAny* vtablePtr = NULL; |
|
104 TInt err = sess.GetVTablePtrFromEcomUid(aUid, vtablePtr); |
|
105 |
|
106 TFullName8 dllName; |
|
107 if (!err) |
|
108 { |
|
109 err = aMemAccess.FindAddressInCodeSegments(dllName, vtablePtr); |
|
110 } |
|
111 sess.Byebye(); // We have to call FindAddressInCodeSegments before sandbox exits, because when it does the code segment will most likely be unloaded! |
|
112 sandbox.Close(); |
|
113 User::LeaveIfError(err); |
|
114 |
|
115 aFileName.Copy(dllName); |
|
116 } |
|
117 |
|
118 |
|
119 #else |
|
120 |
|
121 #include <e32property.h> |
|
122 #include <ecom/ecom.h> |
|
123 |
|
124 void GoL(); |
|
125 |
|
126 class CSandboxSession : public CSession2 |
|
127 { |
|
128 void ServiceL(const RMessage2 &aMessage); |
|
129 RBuf8 iBuf; |
|
130 }; |
|
131 |
|
132 class CSandboxServer : public CServer2 |
|
133 { |
|
134 public: |
|
135 CSandboxServer() : CServer2(0,ESharableSessions) {} |
|
136 |
|
137 protected: |
|
138 CSession2* NewSessionL(const TVersion& /*aVersion*/, const RMessage2& /*aMessage*/) const |
|
139 { |
|
140 return new(ELeave) CSandboxSession(); |
|
141 } |
|
142 }; |
|
143 |
|
144 |
|
145 TInt E32Main() |
|
146 { |
|
147 User::SetJustInTime(EFalse); // Don't want to debug problems in the sandbox |
|
148 |
|
149 CTrapCleanup* cleanup=CTrapCleanup::New(); |
|
150 TRAPD(err, GoL()); |
|
151 return err; |
|
152 } |
|
153 |
|
154 void GoL() |
|
155 { |
|
156 CActiveScheduler* s=new(ELeave) CActiveScheduler; |
|
157 CActiveScheduler::Install(s); |
|
158 CSandboxServer* server = new(ELeave) CSandboxServer(); |
|
159 // Scope the TFullName |
|
160 { |
|
161 TFullName serverName = RProcess().FullName(); |
|
162 server->StartL(serverName); |
|
163 } |
|
164 RProcess::Rendezvous(KErrNone); |
|
165 CActiveScheduler::Start(); |
|
166 } |
|
167 |
|
168 void CSandboxSession::ServiceL(const RMessage2 &aMessage) |
|
169 { |
|
170 if (aMessage.Function() >= EMaxArgs) |
|
171 { |
|
172 aMessage.Complete(KErrArgument); |
|
173 return; |
|
174 } |
|
175 |
|
176 if (aMessage.Function() == EGetRecog2) |
|
177 { |
|
178 aMessage.WriteL(0, iBuf); |
|
179 iBuf.Close(); |
|
180 aMessage.Complete(KErrNone); |
|
181 } |
|
182 else if (aMessage.Function() == EGetRecog) |
|
183 { |
|
184 if (iBuf.MaxLength() == 0) |
|
185 { |
|
186 iBuf.ReAllocL(1024); // Must be > sizeof(TDataType) otherwise the reallocating logic below is flawed |
|
187 } |
|
188 TUid uid = TUid::Uid(aMessage.Int0()); |
|
189 TUid destructorKey; |
|
190 CApaDataRecognizerType* rec = static_cast<CApaDataRecognizerType*>(REComSession::CreateImplementationL(uid, destructorKey)); |
|
191 TInt count = rec->MimeTypesCount(); |
|
192 for (TInt j = 0; j < count; j++) |
|
193 { |
|
194 TDataType type = rec->SupportedDataTypeL(j); |
|
195 TPckg<TDataType> buf(type); |
|
196 if (iBuf.Length() + buf.Length() >= iBuf.MaxLength()) |
|
197 { |
|
198 iBuf.ReAllocL(iBuf.MaxLength() * 2); |
|
199 } |
|
200 iBuf.Append(buf); |
|
201 } |
|
202 |
|
203 aMessage.Complete(iBuf.Size()); |
|
204 } |
|
205 else if (aMessage.Function() == ECloseServer) |
|
206 { |
|
207 aMessage.Complete(KErrNone); |
|
208 CActiveScheduler::Stop(); |
|
209 } |
|
210 else if (aMessage.Function() == EGetVTablePtr) |
|
211 { |
|
212 TUid destructorKey; |
|
213 TAny* obj = NULL; |
|
214 obj = REComSession::CreateImplementationL(TUid::Uid(aMessage.Int0()), destructorKey); |
|
215 TAny* vtablePtr = *((TAny**)obj); |
|
216 TPckg<TAny*> res(vtablePtr); |
|
217 aMessage.WriteL(1, res); |
|
218 aMessage.Complete(KErrNone); |
|
219 } |
|
220 else |
|
221 { |
|
222 ASSERT(0); |
|
223 } |
|
224 } |
|
225 |
|
226 #endif |