OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "native_client/src/trusted/plugin/pnacl_translate_thread.h" | 5 #include "native_client/src/trusted/plugin/pnacl_translate_thread.h" |
6 | 6 |
7 #include "native_client/src/trusted/desc/nacl_desc_wrapper.h" | 7 #include "native_client/src/trusted/desc/nacl_desc_wrapper.h" |
8 #include "native_client/src/trusted/plugin/plugin.h" | 8 #include "native_client/src/trusted/plugin/plugin.h" |
9 #include "native_client/src/trusted/plugin/pnacl_resources.h" | 9 #include "native_client/src/trusted/plugin/pnacl_resources.h" |
10 #include "native_client/src/trusted/plugin/srpc_params.h" | 10 #include "native_client/src/trusted/plugin/srpc_params.h" |
11 #include "native_client/src/trusted/plugin/utility.h" | 11 #include "native_client/src/trusted/plugin/utility.h" |
12 | 12 |
13 namespace plugin { | 13 namespace plugin { |
14 | 14 |
15 PnaclTranslateThread::PnaclTranslateThread() : subprocesses_should_die_(false), | 15 PnaclTranslateThread::PnaclTranslateThread() : subprocesses_should_die_(false), |
16 manifest_(NULL), | 16 manifest_(NULL), |
17 ld_manifest_(NULL), | 17 ld_manifest_(NULL), |
18 obj_file_(NULL), | 18 obj_file_(NULL), |
19 nexe_file_(NULL), | 19 nexe_file_(NULL), |
20 pexe_wrapper_(NULL), | |
21 coordinator_error_info_(NULL), | 20 coordinator_error_info_(NULL), |
22 resources_(NULL), | 21 resources_(NULL), |
23 plugin_(NULL) { | 22 plugin_(NULL) { |
24 NaClXMutexCtor(&subprocess_mu_); | 23 NaClXMutexCtor(&subprocess_mu_); |
25 } | 24 } |
26 | 25 |
27 void PnaclTranslateThread::RunTranslate( | |
28 const pp::CompletionCallback& finish_callback, | |
29 const Manifest* manifest, | |
30 const Manifest* ld_manifest, | |
31 LocalTempFile* obj_file, | |
32 LocalTempFile* nexe_file, | |
33 nacl::DescWrapper* pexe_wrapper, | |
34 ErrorInfo* error_info, | |
35 PnaclResources* resources, | |
36 Plugin* plugin) { | |
37 PLUGIN_PRINTF(("PnaclTranslateThread::RunTranslate)\n")); | |
38 manifest_ = manifest; | |
39 ld_manifest_ = ld_manifest; | |
40 obj_file_ = obj_file; | |
41 nexe_file_ = nexe_file; | |
42 pexe_wrapper_ = pexe_wrapper; | |
43 coordinator_error_info_ = error_info; | |
44 resources_ = resources; | |
45 plugin_ = plugin; | |
46 | |
47 // Invoke llc followed by ld off the main thread. This allows use of | |
48 // blocking RPCs that would otherwise block the JavaScript main thread. | |
49 report_translate_finished_ = finish_callback; | |
50 translate_thread_.reset(new NaClThread); | |
51 if (translate_thread_ == NULL) { | |
52 TranslateFailed("could not allocate thread struct."); | |
53 return; | |
54 } | |
55 const int32_t kArbitraryStackSize = 128 * 1024; | |
56 if (!NaClThreadCreateJoinable(translate_thread_.get(), | |
57 DoTranslateThread, | |
58 this, | |
59 kArbitraryStackSize)) { | |
60 TranslateFailed("could not create thread."); | |
61 } | |
62 } | |
63 | |
64 NaClSubprocess* PnaclTranslateThread::StartSubprocess( | 26 NaClSubprocess* PnaclTranslateThread::StartSubprocess( |
65 const nacl::string& url_for_nexe, | 27 const nacl::string& url_for_nexe, |
66 const Manifest* manifest, | 28 const Manifest* manifest, |
67 ErrorInfo* error_info) { | 29 ErrorInfo* error_info) { |
68 PLUGIN_PRINTF(("PnaclTranslateThread::StartSubprocess (url_for_nexe=%s)\n", | 30 PLUGIN_PRINTF(("PnaclTranslateThread::StartSubprocess (url_for_nexe=%s)\n", |
69 url_for_nexe.c_str())); | 31 url_for_nexe.c_str())); |
70 nacl::DescWrapper* wrapper = resources_->WrapperForUrl(url_for_nexe); | 32 nacl::DescWrapper* wrapper = resources_->WrapperForUrl(url_for_nexe); |
71 nacl::scoped_ptr<NaClSubprocess> subprocess( | 33 nacl::scoped_ptr<NaClSubprocess> subprocess( |
72 plugin_->LoadHelperNaClModule(wrapper, manifest, error_info)); | 34 plugin_->LoadHelperNaClModule(wrapper, manifest, error_info)); |
73 if (subprocess.get() == NULL) { | 35 if (subprocess.get() == NULL) { |
74 PLUGIN_PRINTF(( | 36 PLUGIN_PRINTF(( |
75 "PnaclTranslateThread::StartSubprocess: subprocess creation failed\n")); | 37 "PnaclTranslateThread::StartSubprocess: subprocess creation failed\n")); |
76 return NULL; | 38 return NULL; |
77 } | 39 } |
78 return subprocess.release(); | 40 return subprocess.release(); |
79 } | 41 } |
80 | 42 |
81 void WINAPI PnaclTranslateThread::DoTranslateThread(void* arg) { | 43 void WINAPI PnaclTranslateThread::DoTranslateThread(void* arg) { |
82 PnaclTranslateThread* translator = | 44 PnaclTranslateThread* translator = |
83 reinterpret_cast<PnaclTranslateThread*>(arg); | 45 reinterpret_cast<PnaclTranslateThread*>(arg); |
84 translator->DoTranslate(); | 46 translator->DoTranslate(); |
85 } | 47 } |
86 | 48 |
87 void PnaclTranslateThread::DoTranslate() { | |
88 ErrorInfo error_info; | |
89 nacl::scoped_ptr<NaClSubprocess> llc_subprocess( | |
90 StartSubprocess(PnaclUrls::GetLlcUrl(), manifest_, &error_info)); | |
91 if (llc_subprocess == NULL) { | |
92 TranslateFailed("Compile process could not be created: " + | |
93 error_info.message()); | |
94 return; | |
95 } | |
96 // Run LLC. | |
97 SrpcParams params; | |
98 nacl::DescWrapper* llc_out_file = obj_file_->write_wrapper(); | |
99 PluginReverseInterface* llc_reverse = | |
100 llc_subprocess->service_runtime()->rev_interface(); | |
101 llc_reverse->AddQuotaManagedFile(obj_file_->identifier(), | |
102 obj_file_->write_file_io()); | |
103 if (!llc_subprocess->InvokeSrpcMethod("RunWithDefaultCommandLine", | |
104 "hh", | |
105 ¶ms, | |
106 pexe_wrapper_->desc(), | |
107 llc_out_file->desc())) { | |
108 TranslateFailed("compile failed."); | |
109 return; | |
110 } | |
111 // LLC returns values that are used to determine how linking is done. | |
112 int is_shared_library = (params.outs()[0]->u.ival != 0); | |
113 nacl::string soname = params.outs()[1]->arrays.str; | |
114 nacl::string lib_dependencies = params.outs()[2]->arrays.str; | |
115 PLUGIN_PRINTF(("PnaclCoordinator: compile (translator=%p) succeeded" | |
116 " is_shared_library=%d, soname='%s', lib_dependencies='%s')\n", | |
117 this, is_shared_library, soname.c_str(), | |
118 lib_dependencies.c_str())); | |
119 // Shut down the llc subprocess. | |
120 llc_subprocess.reset(NULL); | |
121 if (SubprocessesShouldDie()) { | |
122 TranslateFailed("stopped by coordinator."); | |
123 return; | |
124 } | |
125 if(!RunLdSubprocess(is_shared_library, soname, lib_dependencies)) { | |
126 return; | |
127 } | |
128 pp::Core* core = pp::Module::Get()->core(); | |
129 core->CallOnMainThread(0, report_translate_finished_, PP_OK); | |
130 } | |
131 | |
132 bool PnaclTranslateThread::RunLdSubprocess(int is_shared_library, | 49 bool PnaclTranslateThread::RunLdSubprocess(int is_shared_library, |
133 const nacl::string& soname, | 50 const nacl::string& soname, |
134 const nacl::string& lib_dependencies | 51 const nacl::string& lib_dependencies |
135 ) { | 52 ) { |
136 ErrorInfo error_info; | 53 ErrorInfo error_info; |
137 nacl::scoped_ptr<NaClSubprocess> ld_subprocess( | 54 nacl::scoped_ptr<NaClSubprocess> ld_subprocess( |
138 StartSubprocess(PnaclUrls::GetLdUrl(), ld_manifest_, &error_info)); | 55 StartSubprocess(PnaclUrls::GetLdUrl(), ld_manifest_, &error_info)); |
139 if (ld_subprocess == NULL) { | 56 if (ld_subprocess == NULL) { |
140 TranslateFailed("Link process could not be created: " + | 57 TranslateFailed("Link process could not be created: " + |
141 error_info.message()); | 58 error_info.message()); |
(...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
201 translate_thread_.get())); | 118 translate_thread_.get())); |
202 if (translate_thread_ != NULL) { | 119 if (translate_thread_ != NULL) { |
203 SetSubprocessesShouldDie(); | 120 SetSubprocessesShouldDie(); |
204 NaClThreadJoin(translate_thread_.get()); | 121 NaClThreadJoin(translate_thread_.get()); |
205 PLUGIN_PRINTF(("~PnaclTranslateThread joined\n")); | 122 PLUGIN_PRINTF(("~PnaclTranslateThread joined\n")); |
206 } | 123 } |
207 NaClMutexDtor(&subprocess_mu_); | 124 NaClMutexDtor(&subprocess_mu_); |
208 } | 125 } |
209 | 126 |
210 } // namespace plugin | 127 } // namespace plugin |
OLD | NEW |