3 * Copyright (c) 2012 The Chromium Authors. All rights reserved.
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
8 // A class containing information regarding a socket connection to a
9 // service runtime instance.
11 #ifndef NATIVE_CLIENT_SRC_TRUSTED_PLUGIN_SERVICE_RUNTIME_H_
12 #define NATIVE_CLIENT_SRC_TRUSTED_PLUGIN_SERVICE_RUNTIME_H_
16 #include "native_client/src/include/nacl_macros.h"
17 #include "native_client/src/include/nacl_scoped_ptr.h"
18 #include "native_client/src/include/nacl_string.h"
19 #include "native_client/src/shared/platform/nacl_sync.h"
20 #include "native_client/src/shared/srpc/nacl_srpc.h"
21 #include "native_client/src/trusted/desc/nacl_desc_wrapper.h"
22 #include "native_client/src/trusted/nonnacl_util/sel_ldr_launcher.h"
23 #include "native_client/src/trusted/reverse_service/reverse_service.h"
24 #include "native_client/src/trusted/weak_ref/weak_ref.h"
26 #include "ppapi/c/trusted/ppb_file_io_trusted.h"
27 #include "ppapi/cpp/completion_callback.h"
29 #include "ppapi/native_client/src/trusted/plugin/utility.h"
46 class PnaclCoordinator
;
50 // Struct of params used by StartSelLdr. Use a struct so that callback
51 // creation templates aren't overwhelmed with too many parameters.
52 struct SelLdrStartParams
{
53 SelLdrStartParams(const nacl::string
& url
,
54 ErrorInfo
* error_info
,
57 bool enable_dev_interfaces
,
58 bool enable_dyncode_syscalls
,
59 bool enable_exception_handling
,
60 bool enable_crash_throttling
)
62 error_info(error_info
),
64 uses_ppapi(uses_ppapi
),
65 enable_dev_interfaces(enable_dev_interfaces
),
66 enable_dyncode_syscalls(enable_dyncode_syscalls
),
67 enable_exception_handling(enable_exception_handling
),
68 enable_crash_throttling(enable_crash_throttling
) {
71 ErrorInfo
* error_info
;
74 bool enable_dev_interfaces
;
75 bool enable_dyncode_syscalls
;
76 bool enable_exception_handling
;
77 bool enable_crash_throttling
;
80 // Callback resources are essentially our continuation state.
82 struct LogToJavaScriptConsoleResource
{
84 explicit LogToJavaScriptConsoleResource(std::string msg
)
89 struct PostMessageResource
{
91 explicit PostMessageResource(std::string msg
)
96 struct OpenManifestEntryResource
{
98 OpenManifestEntryResource(const std::string
& target_url
,
99 struct NaClFileInfo
* finfo
,
105 op_complete_ptr(op_complete
) {}
107 struct NaClFileInfo
* file_info
;
108 ErrorInfo
* error_info
;
109 bool* op_complete_ptr
;
112 struct CloseManifestEntryResource
{
114 CloseManifestEntryResource(int32_t desc_to_close
,
117 : desc(desc_to_close
),
118 op_complete_ptr(op_complete
),
119 op_result_ptr(op_result
) {}
122 bool* op_complete_ptr
;
132 QuotaData(QuotaDataType type_
, PP_Resource resource_
)
133 : type(type_
), resource(resource_
) {}
135 : type(PepperQuotaType
), resource(0) {}
138 PP_Resource resource
;
141 struct QuotaRequest
{
143 QuotaRequest(QuotaData quota_data
,
144 int64_t start_offset
,
145 int64_t quota_bytes_requested
,
146 int64_t* quota_bytes_granted
,
149 offset(start_offset
),
150 bytes_requested(quota_bytes_requested
),
151 bytes_granted(quota_bytes_granted
),
152 op_complete_ptr(op_complete
) { }
156 int64_t bytes_requested
;
157 int64_t* bytes_granted
;
158 bool* op_complete_ptr
;
161 // Do not invoke from the main thread, since the main methods will
162 // invoke CallOnMainThread and then wait on a condvar for the task to
163 // complete: if invoked from the main thread, the main method not
164 // returning (and thus unblocking the main thread) means that the
165 // main-thread continuation methods will never get called, and thus
166 // we'd get a deadlock.
167 class PluginReverseInterface
: public nacl::ReverseInterface
{
169 PluginReverseInterface(nacl::WeakRefAnchor
* anchor
,
171 const Manifest
* manifest
,
172 ServiceRuntime
* service_runtime
,
173 pp::CompletionCallback init_done_cb
,
174 pp::CompletionCallback crash_cb
);
176 virtual ~PluginReverseInterface();
180 virtual void Log(nacl::string message
);
182 virtual void DoPostMessage(nacl::string message
);
184 virtual void StartupInitializationComplete();
186 virtual bool EnumerateManifestKeys(std::set
<nacl::string
>* out_keys
);
188 virtual bool OpenManifestEntry(nacl::string url_key
,
189 struct NaClFileInfo
*info
);
191 virtual bool CloseManifestEntry(int32_t desc
);
193 virtual void ReportCrash();
195 virtual void ReportExitStatus(int exit_status
);
197 virtual int64_t RequestQuotaForWrite(nacl::string file_id
,
199 int64_t bytes_to_write
);
201 void AddQuotaManagedFile(const nacl::string
& file_id
,
202 const pp::FileIO
& file_io
);
203 void AddTempQuotaManagedFile(const nacl::string
& file_id
);
206 virtual void Log_MainThreadContinuation(LogToJavaScriptConsoleResource
* p
,
209 virtual void PostMessage_MainThreadContinuation(PostMessageResource
* p
,
212 virtual void OpenManifestEntry_MainThreadContinuation(
213 OpenManifestEntryResource
* p
,
216 virtual void StreamAsFile_MainThreadContinuation(
217 OpenManifestEntryResource
* p
,
220 virtual void BitcodeTranslate_MainThreadContinuation(
221 OpenManifestEntryResource
* p
,
224 virtual void CloseManifestEntry_MainThreadContinuation(
225 CloseManifestEntryResource
* cls
,
228 virtual void QuotaRequest_MainThreadContinuation(
229 QuotaRequest
* request
,
232 virtual void QuotaRequest_MainThreadResponse(
233 QuotaRequest
* request
,
237 nacl::WeakRefAnchor
* anchor_
; // holds a ref
238 Plugin
* plugin_
; // value may be copied, but should be used only in
239 // main thread in WeakRef-protected callbacks.
240 const Manifest
* manifest_
;
241 ServiceRuntime
* service_runtime_
;
244 std::map
<int64_t, QuotaData
> quota_map_
;
247 nacl::scoped_ptr
<PnaclCoordinator
> pnacl_coordinator_
;
249 pp::CompletionCallback init_done_cb_
;
250 pp::CompletionCallback crash_cb_
;
253 // ServiceRuntime abstracts a NativeClient sel_ldr instance.
254 class ServiceRuntime
{
256 // TODO(sehr): This class should also implement factory methods, using the
257 // Start method below.
258 ServiceRuntime(Plugin
* plugin
,
259 const Manifest
* manifest
,
260 bool should_report_uma
,
261 pp::CompletionCallback init_done_cb
,
262 pp::CompletionCallback crash_cb
);
263 // The destructor terminates the sel_ldr process.
266 // Spawn the sel_ldr instance. On success, returns true.
267 // On failure, returns false and |error_string| is set to something
268 // describing the error.
269 bool StartSelLdr(const SelLdrStartParams
& params
);
271 // If starting sel_ldr from a background thread, wait for sel_ldr to
273 void WaitForSelLdrStart();
275 // Signal to waiting threads that StartSelLdr is complete.
276 // Done externally, in case external users want to write to shared
277 // memory that is yet to be fenced.
278 void SignalStartSelLdrDone();
280 // Establish an SrpcClient to the sel_ldr instance and load the nexe.
281 // The nexe to be started is passed through |nacl_file_desc|.
282 // On success, returns true. On failure, returns false and |error_string|
283 // is set to something describing the error.
284 bool LoadNexeAndStart(nacl::DescWrapper
* nacl_file_desc
,
285 ErrorInfo
* error_info
,
286 const pp::CompletionCallback
& crash_cb
);
288 // Starts the application channel to the nexe.
289 SrpcClient
* SetupAppChannel();
291 bool Log(int severity
, const nacl::string
& msg
);
292 Plugin
* plugin() const { return plugin_
; }
295 // exit_status is -1 when invalid; when we set it, we will ensure
296 // that it is non-negative (the portion of the exit status from the
297 // nexe that is transferred is the low 8 bits of the argument to the
299 int exit_status(); // const, but grabs mutex etc.
300 void set_exit_status(int exit_status
);
302 nacl::string
GetCrashLogOutput();
304 // To establish quota callbacks the pnacl coordinator needs to communicate
305 // with the reverse interface.
306 PluginReverseInterface
* rev_interface() const { return rev_interface_
; }
309 NACL_DISALLOW_COPY_AND_ASSIGN(ServiceRuntime
);
310 bool InitCommunication(nacl::DescWrapper
* shm
, ErrorInfo
* error_info
);
312 NaClSrpcChannel command_channel_
;
314 bool should_report_uma_
;
315 nacl::ReverseService
* reverse_service_
;
316 nacl::scoped_ptr
<nacl::SelLdrLauncherBase
> subprocess_
;
318 nacl::WeakRefAnchor
* anchor_
;
320 PluginReverseInterface
* rev_interface_
;
322 // Mutex to protect exit_status_.
323 // Also, in conjunction with cond_ it is used to signal when
324 // StartSelLdr is complete with either success or error.
328 bool start_sel_ldr_done_
;
331 } // namespace plugin
333 #endif // NATIVE_CLIENT_SRC_TRUSTED_PLUGIN_SERVICE_RUNTIME_H_