mirror of
https://gitee.com/openharmony/js_api_module
synced 2024-11-27 06:31:12 +00:00
merge js_worker_module_master and mv to js_worker_module
Signed-off-by: lengchangjing <lengchangjing@huawei.com>
This commit is contained in:
commit
fedc3590e0
49
js_worker_module/BUILD.gn
Normal file
49
js_worker_module/BUILD.gn
Normal file
@ -0,0 +1,49 @@
|
||||
# Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
import("//build/ohos.gni")
|
||||
|
||||
ohos_shared_library("worker") {
|
||||
include_dirs = [
|
||||
"//base/compileruntime/js_worker_module/worker",
|
||||
"//base/compileruntime/js_worker_module/helper",
|
||||
"//base/compileruntime/js_worker_module/plugin",
|
||||
]
|
||||
|
||||
sources = [
|
||||
"helper/napi_helper.cpp",
|
||||
"plugin/timer.cpp",
|
||||
"worker/message_queue.cpp",
|
||||
"worker/native_module_worker.cpp",
|
||||
"worker/thread.cpp",
|
||||
"worker/worker.cpp",
|
||||
"worker/worker_runner.cpp",
|
||||
]
|
||||
|
||||
deps = [ "//foundation/arkui/napi:ace_napi" ]
|
||||
|
||||
if (is_standard_system) {
|
||||
external_deps = [ "hiviewdfx_hilog_native:libhilog" ]
|
||||
} else {
|
||||
external_deps = [ "hilog:libhilog" ]
|
||||
}
|
||||
|
||||
subsystem_name = "utils"
|
||||
part_name = "jsapi_worker"
|
||||
|
||||
relative_install_dir = "module"
|
||||
}
|
||||
|
||||
group("jsapi_packages") {
|
||||
deps = [ ":worker" ]
|
||||
}
|
177
js_worker_module/LICENSE
Normal file
177
js_worker_module/LICENSE
Normal file
@ -0,0 +1,177 @@
|
||||
|
||||
Apache License
|
||||
Version 2.0, January 2004
|
||||
http://www.apache.org/licenses/
|
||||
|
||||
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
|
||||
|
||||
1. Definitions.
|
||||
|
||||
"License" shall mean the terms and conditions for use, reproduction,
|
||||
and distribution as defined by Sections 1 through 9 of this document.
|
||||
|
||||
"Licensor" shall mean the copyright owner or entity authorized by
|
||||
the copyright owner that is granting the License.
|
||||
|
||||
"Legal Entity" shall mean the union of the acting entity and all
|
||||
other entities that control, are controlled by, or are under common
|
||||
control with that entity. For the purposes of this definition,
|
||||
"control" means (i) the power, direct or indirect, to cause the
|
||||
direction or management of such entity, whether by contract or
|
||||
otherwise, or (ii) ownership of fifty percent (50%) or more of the
|
||||
outstanding shares, or (iii) beneficial ownership of such entity.
|
||||
|
||||
"You" (or "Your") shall mean an individual or Legal Entity
|
||||
exercising permissions granted by this License.
|
||||
|
||||
"Source" form shall mean the preferred form for making modifications,
|
||||
including but not limited to software source code, documentation
|
||||
source, and configuration files.
|
||||
|
||||
"Object" form shall mean any form resulting from mechanical
|
||||
transformation or translation of a Source form, including but
|
||||
not limited to compiled object code, generated documentation,
|
||||
and conversions to other media types.
|
||||
|
||||
"Work" shall mean the work of authorship, whether in Source or
|
||||
Object form, made available under the License, as indicated by a
|
||||
copyright notice that is included in or attached to the work
|
||||
(an example is provided in the Appendix below).
|
||||
|
||||
"Derivative Works" shall mean any work, whether in Source or Object
|
||||
form, that is based on (or derived from) the Work and for which the
|
||||
editorial revisions, annotations, elaborations, or other modifications
|
||||
represent, as a whole, an original work of authorship. For the purposes
|
||||
of this License, Derivative Works shall not include works that remain
|
||||
separable from, or merely link (or bind by name) to the interfaces of,
|
||||
the Work and Derivative Works thereof.
|
||||
|
||||
"Contribution" shall mean any work of authorship, including
|
||||
the original version of the Work and any modifications or additions
|
||||
to that Work or Derivative Works thereof, that is intentionally
|
||||
submitted to Licensor for inclusion in the Work by the copyright owner
|
||||
or by an individual or Legal Entity authorized to submit on behalf of
|
||||
the copyright owner. For the purposes of this definition, "submitted"
|
||||
means any form of electronic, verbal, or written communication sent
|
||||
to the Licensor or its representatives, including but not limited to
|
||||
communication on electronic mailing lists, source code control systems,
|
||||
and issue tracking systems that are managed by, or on behalf of, the
|
||||
Licensor for the purpose of discussing and improving the Work, but
|
||||
excluding communication that is conspicuously marked or otherwise
|
||||
designated in writing by the copyright owner as "Not a Contribution."
|
||||
|
||||
"Contributor" shall mean Licensor and any individual or Legal Entity
|
||||
on behalf of whom a Contribution has been received by Licensor and
|
||||
subsequently incorporated within the Work.
|
||||
|
||||
2. Grant of Copyright License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
copyright license to reproduce, prepare Derivative Works of,
|
||||
publicly display, publicly perform, sublicense, and distribute the
|
||||
Work and such Derivative Works in Source or Object form.
|
||||
|
||||
3. Grant of Patent License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
(except as stated in this section) patent license to make, have made,
|
||||
use, offer to sell, sell, import, and otherwise transfer the Work,
|
||||
where such license applies only to those patent claims licensable
|
||||
by such Contributor that are necessarily infringed by their
|
||||
Contribution(s) alone or by combination of their Contribution(s)
|
||||
with the Work to which such Contribution(s) was submitted. If You
|
||||
institute patent litigation against any entity (including a
|
||||
cross-claim or counterclaim in a lawsuit) alleging that the Work
|
||||
or a Contribution incorporated within the Work constitutes direct
|
||||
or contributory patent infringement, then any patent licenses
|
||||
granted to You under this License for that Work shall terminate
|
||||
as of the date such litigation is filed.
|
||||
|
||||
4. Redistribution. You may reproduce and distribute copies of the
|
||||
Work or Derivative Works thereof in any medium, with or without
|
||||
modifications, and in Source or Object form, provided that You
|
||||
meet the following conditions:
|
||||
|
||||
(a) You must give any other recipients of the Work or
|
||||
Derivative Works a copy of this License; and
|
||||
|
||||
(b) You must cause any modified files to carry prominent notices
|
||||
stating that You changed the files; and
|
||||
|
||||
(c) You must retain, in the Source form of any Derivative Works
|
||||
that You distribute, all copyright, patent, trademark, and
|
||||
attribution notices from the Source form of the Work,
|
||||
excluding those notices that do not pertain to any part of
|
||||
the Derivative Works; and
|
||||
|
||||
(d) If the Work includes a "NOTICE" text file as part of its
|
||||
distribution, then any Derivative Works that You distribute must
|
||||
include a readable copy of the attribution notices contained
|
||||
within such NOTICE file, excluding those notices that do not
|
||||
pertain to any part of the Derivative Works, in at least one
|
||||
of the following places: within a NOTICE text file distributed
|
||||
as part of the Derivative Works; within the Source form or
|
||||
documentation, if provided along with the Derivative Works; or,
|
||||
within a display generated by the Derivative Works, if and
|
||||
wherever such third-party notices normally appear. The contents
|
||||
of the NOTICE file are for informational purposes only and
|
||||
do not modify the License. You may add Your own attribution
|
||||
notices within Derivative Works that You distribute, alongside
|
||||
or as an addendum to the NOTICE text from the Work, provided
|
||||
that such additional attribution notices cannot be construed
|
||||
as modifying the License.
|
||||
|
||||
You may add Your own copyright statement to Your modifications and
|
||||
may provide additional or different license terms and conditions
|
||||
for use, reproduction, or distribution of Your modifications, or
|
||||
for any such Derivative Works as a whole, provided Your use,
|
||||
reproduction, and distribution of the Work otherwise complies with
|
||||
the conditions stated in this License.
|
||||
|
||||
5. Submission of Contributions. Unless You explicitly state otherwise,
|
||||
any Contribution intentionally submitted for inclusion in the Work
|
||||
by You to the Licensor shall be under the terms and conditions of
|
||||
this License, without any additional terms or conditions.
|
||||
Notwithstanding the above, nothing herein shall supersede or modify
|
||||
the terms of any separate license agreement you may have executed
|
||||
with Licensor regarding such Contributions.
|
||||
|
||||
6. Trademarks. This License does not grant permission to use the trade
|
||||
names, trademarks, service marks, or product names of the Licensor,
|
||||
except as required for reasonable and customary use in describing the
|
||||
origin of the Work and reproducing the content of the NOTICE file.
|
||||
|
||||
7. Disclaimer of Warranty. Unless required by applicable law or
|
||||
agreed to in writing, Licensor provides the Work (and each
|
||||
Contributor provides its Contributions) on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
implied, including, without limitation, any warranties or conditions
|
||||
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
|
||||
PARTICULAR PURPOSE. You are solely responsible for determining the
|
||||
appropriateness of using or redistributing the Work and assume any
|
||||
risks associated with Your exercise of permissions under this License.
|
||||
|
||||
8. Limitation of Liability. In no event and under no legal theory,
|
||||
whether in tort (including negligence), contract, or otherwise,
|
||||
unless required by applicable law (such as deliberate and grossly
|
||||
negligent acts) or agreed to in writing, shall any Contributor be
|
||||
liable to You for damages, including any direct, indirect, special,
|
||||
incidental, or consequential damages of any character arising as a
|
||||
result of this License or out of the use or inability to use the
|
||||
Work (including but not limited to damages for loss of goodwill,
|
||||
work stoppage, computer failure or malfunction, or any and all
|
||||
other commercial damages or losses), even if such Contributor
|
||||
has been advised of the possibility of such damages.
|
||||
|
||||
9. Accepting Warranty or Additional Liability. While redistributing
|
||||
the Work or Derivative Works thereof, You may choose to offer,
|
||||
and charge a fee for, acceptance of support, warranty, indemnity,
|
||||
or other liability obligations and/or rights consistent with this
|
||||
License. However, in accepting such obligations, You may act only
|
||||
on Your own behalf and on Your sole responsibility, not on behalf
|
||||
of any other Contributor, and only if You agree to indemnify,
|
||||
defend, and hold each Contributor harmless for any liability
|
||||
incurred by, or claims asserted against, such Contributor by reason
|
||||
of your accepting any such warranty or additional liability.
|
||||
|
||||
END OF TERMS AND CONDITIONS
|
367
js_worker_module/README.md
Normal file
367
js_worker_module/README.md
Normal file
@ -0,0 +1,367 @@
|
||||
# js_worker_module
|
||||
|
||||
### Introduction
|
||||
|
||||
Worker enables JS to have the ability of multithreading, and completes the communication between worker thread and host thread through PostMessage.
|
||||
|
||||
### Interface description
|
||||
For interface implementation, see: js_worker_module/jsapi/worker
|
||||
|
||||
#### Worker object description
|
||||
|
||||
The object object used by the host thread to communicate with the worker thread.
|
||||
|
||||
##### Interface
|
||||
|
||||
1.
|
||||
|
||||
- name
|
||||
|
||||
|constructor(scriptURL:string, options? WorkerOptions) | worker constructor to Creates a worker instance |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
```
|
||||
|
||||
2.
|
||||
|
||||
- name
|
||||
|
||||
| postMessage(message:Object, options?:PostMessageOptions) | Sends a message to the worker thread |
|
||||
|---|---|
|
||||
| postMessage(message:Object, transfer:ArrayBuffer[]) | Sends a message to the worker thread |
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
// example 1
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.postMessage("hello world");
|
||||
|
||||
// example 2
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
var buffer = new ArrayBuffer(8);
|
||||
worker.postMessage(buffer, [buffer]);
|
||||
```
|
||||
|
||||
3.
|
||||
|
||||
- name
|
||||
|
||||
| on(type:string, listener:EventListener) | Adds an event listener to the worker |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.on("alert", (e)=>{
|
||||
console.log("worker on...");
|
||||
})
|
||||
```
|
||||
|
||||
4.
|
||||
|
||||
- name
|
||||
|
||||
| once(type:string, listener:EventListener) | Adds an event listener to the worker and removes the event listener automically after it is invoked once |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.once("alert", (e)=>{
|
||||
console.log("worker on...");
|
||||
})
|
||||
```
|
||||
|
||||
5.
|
||||
|
||||
- name
|
||||
|
||||
| off(type:string, listener?:EventListener) | Removes an event listener to the worker |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.off("alert");
|
||||
```
|
||||
|
||||
6.
|
||||
|
||||
- name
|
||||
|
||||
| terminate() | Terminates the worker thread to stop the worker from receiving messages |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.terminate();
|
||||
```
|
||||
|
||||
7.
|
||||
|
||||
- name
|
||||
|
||||
| removeEventListener(type:string, listener?:EventListener) | Removes an event defined for the worker |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.removeEventListener("alert");
|
||||
```
|
||||
|
||||
8.
|
||||
|
||||
- name
|
||||
|
||||
| dispatchEvent(event: Event) | Dispatches the event defined for the worker |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.dispatchEvent({type:"alert"});
|
||||
```
|
||||
|
||||
9.
|
||||
|
||||
- name
|
||||
|
||||
| removeAllListener() | Removes all event listeners for the worker |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.removeAllListener();
|
||||
```
|
||||
|
||||
##### Attribute
|
||||
|
||||
1.
|
||||
|
||||
- name
|
||||
|
||||
| onexit?:(code:number)=>void | The onexit attribute of the worker specifies the event handler to be called when the worker exits. The handler is executed in the host thread |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.onexit = function(e) {
|
||||
console.log("onexit...");
|
||||
}
|
||||
```
|
||||
|
||||
2.
|
||||
|
||||
- name
|
||||
|
||||
| onerror?:(ev:ErrorEvent)=>void | The onerror attribute of the worker specifies the event handler to be called when an exception occurs during worker execution. The event handler is executed in the host thread |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.onerror = function(e) {
|
||||
console.log("onerror...");
|
||||
}
|
||||
```
|
||||
|
||||
3.
|
||||
|
||||
- name
|
||||
|
||||
| onmessage?:(ev:MessageEvent)=>void | The onmessage attribute of the worker specifies the event handler to be called then the host thread receives a message created by itself and sent by the worker through the parentPort.postMessage. The event handler is executed in the host thread |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.onmessage = function(e) {
|
||||
console.log("onmessage...");
|
||||
}
|
||||
```
|
||||
|
||||
4.
|
||||
|
||||
- name
|
||||
|
||||
| onmessageerror?:(event:MessageEvent)=>void | The onmessage attribute of the worker specifies the event handler when the worker receives a message that cannot be serialized. The event handler is executed in the host thread |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.onmessageerror = function(e) {
|
||||
console.log("onmessageerror...");
|
||||
}
|
||||
```
|
||||
|
||||
#### parentPort object description
|
||||
|
||||
Object of the worker thread used to communicate with the host thread
|
||||
|
||||
##### Interface
|
||||
|
||||
1.
|
||||
|
||||
- name
|
||||
|
||||
| postMessage(message:Object, options?:PostMessageOptions) | Send a message to host thread |
|
||||
|---|---|
|
||||
| postMessage(message:Object, transfer:ArrayBuffer[]) | Send a message to host thread |
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
// main.js
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.postMessage("hello world");
|
||||
|
||||
// worker.js
|
||||
import worker from "@ohos.worker"
|
||||
const parentPort = worker.parentPort;
|
||||
parentPort.onmessage = function(e) {
|
||||
parentPort.postMessage("hello world from worker.js");
|
||||
}
|
||||
```
|
||||
|
||||
2.
|
||||
|
||||
- name
|
||||
|
||||
| close() | Close the worker thread to stop the worker from receiving messages |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
// main.js
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.postMessage("hello world");
|
||||
|
||||
// worker.js
|
||||
import worker from "@ohos.worker"
|
||||
const parentPort = worker.parentPort;
|
||||
parentPort.onmessage = function(e) {
|
||||
parentPort.close();
|
||||
}
|
||||
```
|
||||
|
||||
##### Attribute
|
||||
|
||||
1.
|
||||
|
||||
- name
|
||||
|
||||
| onmessage?:(event:MessageEvent)=>void | The onmessage attribute of parentPort specifies the event handler to be called then the worker thread receives a message sent by the host thread through worker postMessage. The event handler is executed in the worker thread |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
// main.js
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.postMessage("hello world");
|
||||
|
||||
// worker.js
|
||||
import worker from "@ohos.worker"
|
||||
const parentPort = worker.parentPort;
|
||||
parentPort.onmessage = function(e) {
|
||||
console.log("receive main.js message");
|
||||
}
|
||||
```
|
||||
|
||||
2.
|
||||
|
||||
- name
|
||||
|
||||
| onerror?:(ev: ErrorEvent)=>void | The onerror attribute of parentPort specifies the event handler to be called when an exception occurs during worker execution. The event handler is executed in the worker thread |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
// main.js
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.postMessage("hello world");
|
||||
|
||||
// worker.js
|
||||
import worker from "@ohos.worker"
|
||||
const parentPort = worker.parentPort;
|
||||
parentPort.onerror = function(e) {
|
||||
console.log("onerror...");
|
||||
}
|
||||
|
||||
```
|
||||
|
||||
3.
|
||||
|
||||
- name
|
||||
|
||||
| onmessageerror?:(event: MessageEvent)=>void | The onmessage attribute of parentPort specifies the event handler to be called then the worker receives a message that cannot be deserialized. The event handler is executed in the worker thread. |
|
||||
|---|---|
|
||||
|
||||
- example
|
||||
|
||||
```
|
||||
// main.js
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.postMessage("hello world");
|
||||
|
||||
// worker.js
|
||||
import worker from "@ohos.worker"
|
||||
const parentPort = worker.parentPort;
|
||||
parentPort.onmessageerror = function(e) {
|
||||
console.log("onmessageerror...");
|
||||
}
|
||||
```
|
||||
|
||||
### Repositories Involved
|
||||
|
||||
- ace_ace_engine(foundation/arkui/ace_engine-readme.md)
|
||||
- ace_napi(foundation/arkui/napi-readme.md)
|
||||
|
||||
## Related warehouse
|
||||
[js_worker_module Subsystem](base/compileruntime/js_worker_module-readme.md)
|
||||
|
||||
### License
|
||||
|
||||
Worker is available under [Mozilla license](https://www.mozilla.org/en-US/MPL/), and the documentation is detailed in [documentation](https://gitee.com/openharmony/js_worker_module/blob/master/mozilla_docs.txt). See [LICENSE](https://gitee.com/openharmony/js_worker_module/blob/master/LICENSE) for the full license text.
|
368
js_worker_module/README.zh.md
Normal file
368
js_worker_module/README.zh.md
Normal file
@ -0,0 +1,368 @@
|
||||
# js_worker_module
|
||||
|
||||
### 简介
|
||||
|
||||
worker能够让js拥有多线程的能力,通过postMessage完成worker线程与宿主线程通信。
|
||||
|
||||
### 接口说明
|
||||
接口实现详见:js_worker_module/jsapi/worker
|
||||
|
||||
#### Worker对象描述
|
||||
|
||||
宿主线程用于与worker线程通信的Object对象。
|
||||
|
||||
##### 接口
|
||||
|
||||
1.
|
||||
|
||||
- 接口名
|
||||
|
||||
|constructor(scriptURL:string, options? WorkerOptions) | 构造函数 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
```
|
||||
|
||||
2.
|
||||
|
||||
- 接口名
|
||||
|
||||
| postMessage(message:Object, options?:PostMessageOptions) | 向worker线程发送消息 |
|
||||
|---|---|
|
||||
| postMessage(message:Object, transfer:ArrayBuffer[]) | 向worker线程发送消息 |
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
// 示例一
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.postMessage("hello world");
|
||||
|
||||
// 示例二
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
var buffer = new ArrayBuffer(8);
|
||||
worker.postMessage(buffer, [buffer]);
|
||||
```
|
||||
|
||||
3.
|
||||
|
||||
- 接口名
|
||||
|
||||
| on(type:string, listener:EventListener) | 向worker添加一个事件监听 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.on("alert", (e)=>{
|
||||
console.log("worker on...");
|
||||
})
|
||||
```
|
||||
|
||||
4.
|
||||
|
||||
- 接口名
|
||||
|
||||
| once(type:string, listener:EventListener) | 向worker添加一个事件监听, 事件监听只执行一次便自动删除 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.once("alert", (e)=>{
|
||||
console.log("worker on...");
|
||||
})
|
||||
```
|
||||
|
||||
5.
|
||||
|
||||
- 接口名
|
||||
|
||||
| off(type:string, listener?:EventListener) | 删除worker的事件监听 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.off("alert");
|
||||
```
|
||||
|
||||
6.
|
||||
|
||||
- 接口名
|
||||
|
||||
| terminate() | 关闭worker线程,终止worker发送消息 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.terminate();
|
||||
```
|
||||
|
||||
7.
|
||||
|
||||
- 接口名
|
||||
|
||||
| removeEventListener(type:string, listener?:EventListener) | 删除worker的事件监听 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.removeEventListener("alert");
|
||||
```
|
||||
|
||||
8.
|
||||
|
||||
- 接口名
|
||||
|
||||
| dispatchEvent(event: Event) | 分发定义在worker的事件 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.dispatchEvent({type:"alert"});
|
||||
```
|
||||
|
||||
9.
|
||||
|
||||
- 接口名
|
||||
|
||||
| removeAllListener() | 删除worker的所有事件监听 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.removeAllListener();
|
||||
```
|
||||
|
||||
##### 属性
|
||||
|
||||
1.
|
||||
|
||||
- 属性名
|
||||
|
||||
| onexit?:(code:number)=>void | worker退出时被调用的事件处理程序,处理程序在宿主线程中执行 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.onexit = function(e) {
|
||||
console.log("onexit...");
|
||||
}
|
||||
```
|
||||
|
||||
2.
|
||||
|
||||
- 属性名
|
||||
|
||||
| onerror?:(ev:ErrorEvent)=>void | worker在执行过程中发生异常被调用的事件处理程序,处理程序在宿主线程中执行 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.onerror = function(e) {
|
||||
console.log("onerror...");
|
||||
}
|
||||
```
|
||||
|
||||
3.
|
||||
|
||||
- 属性名
|
||||
|
||||
| onmessage?:(ev:MessageEvent)=>void | 宿主线程收到来自其创建的worker通过parentPort.postMessage接口发送的消息时被调用的事件处理程序, 处理程序在宿主线程中执行 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.onmessage = function(e) {
|
||||
console.log("onmessage...");
|
||||
}
|
||||
```
|
||||
|
||||
4.
|
||||
|
||||
- 属性名
|
||||
|
||||
| onmessageerror?:(event:MessageEvent)=>void | worker对象接收到一条无法序列化的消息时被调用的事件处理程序, 处理程序在宿主线程中执行 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.onmessageerror = function(e) {
|
||||
console.log("onmessageerror...");
|
||||
}
|
||||
```
|
||||
|
||||
#### parentPort对象描述
|
||||
|
||||
worker线程用于与宿主线程通信的Object对象。
|
||||
|
||||
##### 接口
|
||||
|
||||
1.
|
||||
|
||||
- 接口名
|
||||
|
||||
| postMessage(message:Object, options?:PostMessageOptions) | 向宿主线程发送消息 |
|
||||
|---|---|
|
||||
| postMessage(message:Object, transfer:ArrayBuffer[]) | 向宿主线程发送消息 |
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
// main.js
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.postMessage("hello world");
|
||||
|
||||
// worker.js
|
||||
import worker from "@ohos.worker"
|
||||
const parentPort = worker.parentPort;
|
||||
parentPort.onmessage = function(e) {
|
||||
parentPort.postMessage("hello world from worker.js");
|
||||
}
|
||||
```
|
||||
|
||||
2.
|
||||
|
||||
- 接口名
|
||||
|
||||
| close() | 关闭worker线程,终止worker接收消息 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
// main.js
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.postMessage("hello world");
|
||||
|
||||
// worker.js
|
||||
import worker from "@ohos.worker"
|
||||
const parentPort = worker.parentPort;
|
||||
parentPort.onmessage = function(e) {
|
||||
parentPort.close();
|
||||
}
|
||||
```
|
||||
|
||||
##### 属性
|
||||
|
||||
1.
|
||||
|
||||
- 属性名
|
||||
|
||||
| onmessage?:(event:MessageEvent)=>void | 宿主线程收到来自其创建的worker通过worker.postMessage接口发送的消息时被调用的事件处理程序,处理程序在worker线程中执行 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
// main.js
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.postMessage("hello world");
|
||||
|
||||
// worker.js
|
||||
import worker from "@ohos.worker"
|
||||
const parentPort = worker.parentPort;
|
||||
parentPort.onmessage = function(e) {
|
||||
console.log("receive main.js message");
|
||||
}
|
||||
```
|
||||
|
||||
2.
|
||||
|
||||
- 属性名
|
||||
|
||||
| onerror?:(ev: ErrorEvent)=>void | worker在执行过程中发生异常被调用的事件处理程序,处理程序在worker线程中执行 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
// main.js
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.postMessage("hello world");
|
||||
|
||||
// worker.js
|
||||
import worker from "@ohos.worker"
|
||||
const parentPort = worker.parentPort;
|
||||
parentPort.onerror = function(e) {
|
||||
console.log("onerror...");
|
||||
}
|
||||
|
||||
```
|
||||
|
||||
3.
|
||||
|
||||
- 属性名
|
||||
|
||||
| onmessageerror?:(event: MessageEvent)=>void | worker对象接收到一条无法被反序列化的消息时被调用的事件处理程序, 处理程序在worker线程中执行 |
|
||||
|---|---|
|
||||
|
||||
- 使用示例
|
||||
|
||||
```
|
||||
// main.js
|
||||
import worker from "@ohos.worker"
|
||||
const worker = new worker.Worker("workers/worker.js");
|
||||
worker.postMessage("hello world");
|
||||
|
||||
// worker.js
|
||||
import worker from "@ohos.worker"
|
||||
const parentPort = worker.parentPort;
|
||||
parentPort.onmessageerror = function(e) {
|
||||
console.log("onmessageerror...");
|
||||
}
|
||||
```
|
||||
|
||||
### 涉及仓
|
||||
|
||||
- ace_ace_engine(foundation/arkui/ace_engine-readme_zh.md)
|
||||
- ace_napi(foundation/arkui/napi-readme_zh.md)
|
||||
|
||||
## 相关仓
|
||||
[js_worker_module 子系统](base/compileruntime/js_worker_module-readme_zh.md)
|
||||
|
||||
|
||||
### 许可证
|
||||
|
||||
Worker在[Mozilla许可证](https://www.mozilla.org/en-US/MPL/)下可用,说明文档详见[说明文档](https://gitee.com/openharmony/js_worker_module/blob/master/mozilla_docs.txt)。有关完整的许可证文本,有关完整的许可证文本,请参见[许可证](https://gitee.com/openharmony/js_worker_module/blob/master/LICENSE)
|
58
js_worker_module/bundle.json
Normal file
58
js_worker_module/bundle.json
Normal file
@ -0,0 +1,58 @@
|
||||
{
|
||||
"name": "@ohos/js_worker_module",
|
||||
"version": "",
|
||||
"description": "Provide JS multi-threading capability | 提供JS多线程能力",
|
||||
"homePage": "https://gitee.com/openharmony",
|
||||
"license": "Apache V2",
|
||||
"repository": "https://gitee.com/openharmony/js_worker_module",
|
||||
"domain": "os",
|
||||
"language": "",
|
||||
"publishAs": "code-segment",
|
||||
"private": false,
|
||||
"scripts": {},
|
||||
"tags": [
|
||||
"js"
|
||||
],
|
||||
"keywords": [
|
||||
"js",
|
||||
"worker",
|
||||
"module"
|
||||
],
|
||||
"envs": {},
|
||||
"dirs": {},
|
||||
"author": {
|
||||
"name": "",
|
||||
"email": "",
|
||||
"url": ""
|
||||
},
|
||||
"contributors": [
|
||||
{
|
||||
"name": "",
|
||||
"email": "",
|
||||
"url": ""
|
||||
}
|
||||
],
|
||||
"segment": {
|
||||
"destPath": "base/compileruntime/js_worker_module"
|
||||
},
|
||||
"component": {
|
||||
"name": "jsapi_worker",
|
||||
"subsystem": "utils",
|
||||
"syscap": [],
|
||||
"features": [],
|
||||
"adapted_system_type": [],
|
||||
"rom": "",
|
||||
"ram": "",
|
||||
"deps": {
|
||||
"components": [],
|
||||
"third_party": []
|
||||
},
|
||||
"build": {
|
||||
"sub_component": [
|
||||
"//base/compileruntime/js_worker_module:jsapi_packages"
|
||||
],
|
||||
"inner_kits": [],
|
||||
"test": []
|
||||
}
|
||||
}
|
||||
}
|
177
js_worker_module/helper/napi_helper.cpp
Normal file
177
js_worker_module/helper/napi_helper.cpp
Normal file
@ -0,0 +1,177 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "base/compileruntime/js_worker_module/helper/napi_helper.h"
|
||||
|
||||
#include "native_engine/native_value.h"
|
||||
|
||||
namespace CompilerRuntime::WorkerModule::Helper {
|
||||
const static int32_t MAXCHARLENGTH = 200;
|
||||
|
||||
bool NapiHelper::IsString(napi_value value)
|
||||
{
|
||||
auto valNative = reinterpret_cast<NativeValue*>(value);
|
||||
return valNative == nullptr ? false : valNative->TypeOf() == NATIVE_STRING;
|
||||
}
|
||||
|
||||
bool NapiHelper::IsArray(napi_value value)
|
||||
{
|
||||
auto valNative = reinterpret_cast<NativeValue*>(value);
|
||||
return valNative == nullptr ? false : valNative->IsArray();
|
||||
}
|
||||
|
||||
bool NapiHelper::IsConstructor(napi_env env, napi_callback_info cbInfo)
|
||||
{
|
||||
napi_value* funcObj = nullptr;
|
||||
napi_get_new_target(env, cbInfo, funcObj);
|
||||
return funcObj != nullptr;
|
||||
}
|
||||
|
||||
size_t NapiHelper::GetCallbackInfoArgc(napi_env env, napi_callback_info cbInfo)
|
||||
{
|
||||
size_t argc = 0;
|
||||
napi_get_cb_info(env, cbInfo, &argc, nullptr, nullptr, nullptr);
|
||||
return argc;
|
||||
}
|
||||
|
||||
napi_value NapiHelper::GetNamePropertyInParentPort(napi_env env, napi_ref parentPort, const char* name)
|
||||
{
|
||||
napi_value obj = nullptr;
|
||||
napi_get_reference_value(env, parentPort, &obj);
|
||||
|
||||
napi_value value = nullptr;
|
||||
napi_get_named_property(env, obj, name, &value);
|
||||
|
||||
return value;
|
||||
}
|
||||
|
||||
napi_value NapiHelper::GetUndefinedValue(napi_env env)
|
||||
{
|
||||
napi_value result = nullptr;
|
||||
napi_get_undefined(env, &result);
|
||||
return result;
|
||||
}
|
||||
|
||||
bool NapiHelper::IsCallable(napi_env env, napi_value value)
|
||||
{
|
||||
bool result = false;
|
||||
napi_is_callable(env, value, &result);
|
||||
return result;
|
||||
}
|
||||
|
||||
bool NapiHelper::IsCallable(napi_env env, napi_ref value)
|
||||
{
|
||||
napi_value obj = nullptr;
|
||||
napi_get_reference_value(env, value, &obj);
|
||||
if (obj == nullptr) {
|
||||
return false;
|
||||
}
|
||||
return IsCallable(env, obj);
|
||||
}
|
||||
|
||||
void NapiHelper::SetNamePropertyInGlobal(napi_env env, const char* name, napi_value value)
|
||||
{
|
||||
napi_value object = nullptr;
|
||||
napi_get_global(env, &object);
|
||||
napi_set_named_property(env, object, name, value);
|
||||
}
|
||||
|
||||
bool NapiHelper::IsObject(napi_value value)
|
||||
{
|
||||
auto nativeValue = reinterpret_cast<NativeValue*>(value);
|
||||
return nativeValue->TypeOf() == NATIVE_OBJECT;
|
||||
}
|
||||
|
||||
char* NapiHelper::GetString(napi_env env, napi_value value)
|
||||
{
|
||||
size_t bufferSize = 0;
|
||||
size_t strLength = 0;
|
||||
napi_get_value_string_utf8(env, value, nullptr, 0, &bufferSize);
|
||||
if (bufferSize > MAXCHARLENGTH) {
|
||||
return nullptr;
|
||||
}
|
||||
char* buffer = new char[bufferSize + 1] { 0 };
|
||||
napi_get_value_string_utf8(env, value, buffer, bufferSize + 1, &strLength);
|
||||
return buffer;
|
||||
}
|
||||
|
||||
napi_value NapiHelper::CreateBooleanValue(napi_env env, bool value)
|
||||
{
|
||||
napi_value result = nullptr;
|
||||
napi_get_boolean(env, value, &result);
|
||||
return result;
|
||||
}
|
||||
|
||||
napi_value NapiHelper::GetGlobalObject(napi_env env)
|
||||
{
|
||||
napi_value object = nullptr;
|
||||
napi_get_global(env, &object);
|
||||
return object;
|
||||
}
|
||||
|
||||
napi_ref NapiHelper::CreateReference(napi_env env, napi_value value, uint32_t refcount)
|
||||
{
|
||||
napi_ref callback = nullptr;
|
||||
napi_create_reference(env, value, refcount, &callback);
|
||||
return callback;
|
||||
}
|
||||
|
||||
napi_value NapiHelper::CreateUint32(napi_env env, uint32_t value)
|
||||
{
|
||||
napi_value result = nullptr;
|
||||
napi_create_uint32(env, value, &result);
|
||||
return result;
|
||||
}
|
||||
|
||||
uv_loop_t* NapiHelper::GetLibUV(napi_env env)
|
||||
{
|
||||
uv_loop_t* loop;
|
||||
napi_get_uv_event_loop(env, &loop);
|
||||
return loop;
|
||||
}
|
||||
|
||||
napi_value NapiHelper::GetReferenceValue(napi_env env, napi_ref ref)
|
||||
{
|
||||
napi_value result = nullptr;
|
||||
napi_get_reference_value(env, ref, &result);
|
||||
return result;
|
||||
}
|
||||
|
||||
void NapiHelper::DeleteReference(napi_env env, napi_ref ref)
|
||||
{
|
||||
napi_delete_reference(env, ref);
|
||||
}
|
||||
|
||||
napi_value NapiHelper::GetNameProperty(napi_env env, napi_value obj, const char* name)
|
||||
{
|
||||
napi_value result = nullptr;
|
||||
napi_get_named_property(env, obj, name, &result);
|
||||
return result;
|
||||
}
|
||||
|
||||
bool NapiHelper::GetBooleanValue(napi_env env, napi_value value)
|
||||
{
|
||||
bool result = false;
|
||||
napi_get_value_bool(env, value, &result);
|
||||
return result;
|
||||
}
|
||||
|
||||
bool NapiHelper::StrictEqual(napi_env env, napi_value value, napi_value cmpValue)
|
||||
{
|
||||
bool isEqual = false;
|
||||
napi_strict_equals(env, value, cmpValue, &isEqual);
|
||||
return isEqual;
|
||||
}
|
||||
} // namespace CompilerRuntime::WorkerModule::Helper
|
49
js_worker_module/helper/napi_helper.h
Normal file
49
js_worker_module/helper/napi_helper.h
Normal file
@ -0,0 +1,49 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef JS_WORKER_MODULE_HELPER_NAPI_HELPER_H_
|
||||
#define JS_WORKER_MODULE_HELPER_NAPI_HELPER_H_
|
||||
|
||||
#include <uv.h>
|
||||
#include "napi/native_api.h"
|
||||
#include "napi/native_node_api.h"
|
||||
|
||||
namespace CompilerRuntime::WorkerModule::Helper {
|
||||
class NapiHelper {
|
||||
public:
|
||||
static bool IsString(napi_value value);
|
||||
static bool IsArray(napi_value value);
|
||||
static bool IsConstructor(napi_env env, napi_callback_info cbInfo);
|
||||
static bool IsCallable(napi_env env, napi_value value);
|
||||
static bool IsCallable(napi_env env, napi_ref value);
|
||||
static size_t GetCallbackInfoArgc(napi_env env, napi_callback_info cbInfo);
|
||||
static napi_value GetNamePropertyInParentPort(napi_env env, napi_ref parentPort, const char* name);
|
||||
static void SetNamePropertyInGlobal(napi_env env, const char* name, napi_value value);
|
||||
static napi_value GetUndefinedValue(napi_env env);
|
||||
static bool IsObject(napi_value value);
|
||||
static char* GetString(napi_env env, napi_value value);
|
||||
static napi_value CreateBooleanValue(napi_env env, bool value);
|
||||
static napi_value GetGlobalObject(napi_env env);
|
||||
static napi_ref CreateReference(napi_env env, napi_value value, uint32_t initial_refcount);
|
||||
static napi_value CreateUint32(napi_env env, uint32_t value);
|
||||
static uv_loop_t* GetLibUV(napi_env env);
|
||||
static napi_value GetReferenceValue(napi_env env, napi_ref ref);
|
||||
static void DeleteReference(napi_env env, napi_ref ref);
|
||||
static napi_value GetNameProperty(napi_env env, napi_value obj, const char* name);
|
||||
static bool GetBooleanValue(napi_env env, napi_value value);
|
||||
static bool StrictEqual(napi_env env, napi_value value, napi_value cmpValue);
|
||||
};
|
||||
} // namespace CompilerRuntime::WorkerModule::Helper
|
||||
#endif // JS_WORKER_MODULE_HELPER_NAPI_HELPER_H_
|
71
js_worker_module/helper/object_helper.h
Normal file
71
js_worker_module/helper/object_helper.h
Normal file
@ -0,0 +1,71 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef JS_WORKER_MODULE_WORKER_OBJECT_HELPER_H_
|
||||
#define JS_WORKER_MODULE_WORKER_OBJECT_HELPER_H_
|
||||
|
||||
namespace CompilerRuntime::WorkerModule::Helper {
|
||||
class DereferenceHelp {
|
||||
public:
|
||||
template<typename Inner, typename Outer>
|
||||
static Outer* DereferenceOf(const Inner Outer::*field, const Inner* pointer)
|
||||
{
|
||||
if (field != nullptr && pointer != nullptr) {
|
||||
auto fieldOffset = reinterpret_cast<uintptr_t>(&(static_cast<Outer*>(0)->*field));
|
||||
auto outPointer = reinterpret_cast<Outer*>(reinterpret_cast<uintptr_t>(pointer) - fieldOffset);
|
||||
return outPointer;
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
};
|
||||
|
||||
class CloseHelp {
|
||||
public:
|
||||
template<typename T>
|
||||
static void DeletePointer(const T* value, bool isArray)
|
||||
{
|
||||
if (value == nullptr) {
|
||||
return;
|
||||
}
|
||||
if (isArray) {
|
||||
delete[] value;
|
||||
} else {
|
||||
delete value;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
template<typename T>
|
||||
class ObjectScope {
|
||||
public:
|
||||
ObjectScope(const T* data, bool isArray) : data_(data), isArray_(isArray) {}
|
||||
~ObjectScope()
|
||||
{
|
||||
if (data_ == nullptr) {
|
||||
return;
|
||||
}
|
||||
if (isArray_) {
|
||||
delete[] data_;
|
||||
} else {
|
||||
delete data_;
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
const T* data_;
|
||||
bool isArray_;
|
||||
};
|
||||
} // namespace CompilerRuntime::WorkerModule::Helper
|
||||
#endif // JS_WORKER_MODULE_WORKER_OBJECT_HELPER_H_
|
95
js_worker_module/mozilla_docs.txt
Normal file
95
js_worker_module/mozilla_docs.txt
Normal file
@ -0,0 +1,95 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
The definitions of some interfaces implemented in jsapi/workers/worker.cpp are released under Mozilla license.
|
||||
|
||||
The definitions and functions of these interfaces are consistent with the standard interfaces under mozila license,
|
||||
but the implementation of specific functions is independent and self-developed.
|
||||
|
||||
All interfaces are described in d.ts, the following is the interface written in d.ts under to Mozilla license
|
||||
|
||||
export interface WorkerOptions {
|
||||
type?: "classic" | "module";
|
||||
name?: string;
|
||||
shared?: boolean;
|
||||
}
|
||||
|
||||
export interface Event {
|
||||
readonly type: string;
|
||||
readonly timeStamp: number;
|
||||
}
|
||||
|
||||
interface ErrorEvent extends Event {
|
||||
readonly message: string;
|
||||
readonly filename: string;
|
||||
readonly lineno: number;
|
||||
readonly colno: number;
|
||||
readonly error: Object;
|
||||
}
|
||||
|
||||
declare interface MessageEvent<T = Object> extends Event {
|
||||
readonly data: T;
|
||||
}
|
||||
|
||||
export interface PostMessageOptions {
|
||||
transfer?: Object[];
|
||||
}
|
||||
|
||||
export interface EventListener {
|
||||
(evt: Event): void | Promise<void>;
|
||||
}
|
||||
|
||||
type MessageType = "message" | "messageerror";
|
||||
|
||||
declare interface EventTarget {
|
||||
addEventListener(
|
||||
type: string,
|
||||
listener: EventListener
|
||||
): void;
|
||||
dispatchEvent(event: Event): boolean;
|
||||
removeEventListener(
|
||||
type: string,
|
||||
callback?: EventListener
|
||||
): void;
|
||||
removeAllListener(): void;
|
||||
}
|
||||
|
||||
declare interface WorkerGlobalScope extends EventTarget {
|
||||
readonly name: string;
|
||||
onerror?: (ev: ErrorEvent) => void;
|
||||
readonly self: WorkerGlobalScope & typeof globalThis;
|
||||
}
|
||||
|
||||
declare interface DedicatedWorkerGlobalScope extends WorkerGlobalScope {
|
||||
onmessage?: (this: DedicatedWorkerGlobalScope, ev: MessageEvent) => void;
|
||||
onmessageerror?: (this: DedicatedWorkerGlobalScope, ev: MessageEvent) => void;
|
||||
close(): void;
|
||||
postMessage(messageObject: Object, transfer: Transferable[]): void;
|
||||
postMessage(messageObject: Object, options?: PostMessageOptions): void;
|
||||
}
|
||||
|
||||
declare namespace worker {
|
||||
class Worker extends EventTarget {
|
||||
constructor(scriptURL: string, options?: WorkerOptions);
|
||||
onexit?: (code: number) => void;
|
||||
onerror?: (err: ErrorEvent) => void;
|
||||
onmessage?: (event: MessageEvent) => void;
|
||||
onmessageerror?: (event: MessageEvent) => void;
|
||||
postMessage(message: Object, transfer: ArrayBuffer[]): void;
|
||||
postMessage(message: Object, options?: PostMessageOptions): void;
|
||||
terminate(): void;
|
||||
}
|
||||
const parentPort: DedicatedWorkerGlobalScope;
|
||||
}
|
187
js_worker_module/plugin/timer.cpp
Normal file
187
js_worker_module/plugin/timer.cpp
Normal file
@ -0,0 +1,187 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "base/compileruntime/js_worker_module/plugin/timer.h"
|
||||
|
||||
#include "utils/log.h"
|
||||
|
||||
namespace CompilerRuntime::WorkerModule::Plugin {
|
||||
uint32_t Timer::timeCallbackId = 0;
|
||||
std::map<uint32_t, TimerCallbackInfo*> Timer::timerTable;
|
||||
std::mutex Timer::timeLock;
|
||||
|
||||
TimerCallbackInfo::~TimerCallbackInfo()
|
||||
{
|
||||
Helper::NapiHelper::DeleteReference(env_, callback_);
|
||||
for (size_t idx = 0; idx < argc_; idx++) {
|
||||
Helper::NapiHelper::DeleteReference(env_, argv_[idx]);
|
||||
}
|
||||
Helper::CloseHelp::DeletePointer(argv_, true);
|
||||
|
||||
uv_timer_stop(&timeReq_);
|
||||
uv_close(reinterpret_cast<uv_handle_t*>(&timeReq_), nullptr);
|
||||
}
|
||||
|
||||
bool Timer::RegisterTime(napi_env env)
|
||||
{
|
||||
if (env == nullptr) {
|
||||
return false;
|
||||
}
|
||||
napi_property_descriptor properties[] = {
|
||||
DECLARE_NAPI_FUNCTION("setTimeout", SetTimeout),
|
||||
DECLARE_NAPI_FUNCTION("setInterval", SetInterval),
|
||||
DECLARE_NAPI_FUNCTION("clearTimeout", ClearTimer),
|
||||
DECLARE_NAPI_FUNCTION("clearInterval", ClearTimer)
|
||||
};
|
||||
napi_value globalObj = Helper::NapiHelper::GetGlobalObject(env);
|
||||
napi_status status = napi_define_properties(env, globalObj, sizeof(properties) / sizeof(properties[0]), properties);
|
||||
return status == napi_ok;
|
||||
}
|
||||
|
||||
napi_value Timer::SetTimeout(napi_env env, napi_callback_info cbinfo)
|
||||
{
|
||||
return Timer::SetTimeoutInner(env, cbinfo, false);
|
||||
}
|
||||
|
||||
napi_value Timer::SetInterval(napi_env env, napi_callback_info cbinfo)
|
||||
{
|
||||
return Timer::SetTimeoutInner(env, cbinfo, true);
|
||||
}
|
||||
|
||||
napi_value Timer::ClearTimer(napi_env env, napi_callback_info cbinfo)
|
||||
{
|
||||
// 1. check args
|
||||
size_t argc = Helper::NapiHelper::GetCallbackInfoArgc(env, cbinfo);
|
||||
if (argc <= 0) {
|
||||
HILOG_WARN("first arg should be number");
|
||||
return nullptr;
|
||||
}
|
||||
napi_value* argv = new napi_value[argc];
|
||||
Helper::ObjectScope<napi_value> scope(argv, true);
|
||||
napi_value thisVar = nullptr;
|
||||
napi_get_cb_info(env, cbinfo, &argc, argv, &thisVar, nullptr);
|
||||
|
||||
uint32_t tId;
|
||||
napi_status status = napi_get_value_uint32(env, argv[0], &tId);
|
||||
if (status != napi_ok) {
|
||||
HILOG_WARN("handler should be number");
|
||||
return nullptr;
|
||||
}
|
||||
auto iter = timerTable.find(tId);
|
||||
if (iter == timerTable.end()) {
|
||||
HILOG_INFO("handler not in table");
|
||||
return nullptr;
|
||||
}
|
||||
TimerCallbackInfo* callbackInfo = iter->second;
|
||||
timerTable.erase(tId);
|
||||
Helper::CloseHelp::DeletePointer(callbackInfo, false);
|
||||
return Helper::NapiHelper::GetUndefinedValue(env);
|
||||
}
|
||||
|
||||
void Timer::TimerCallback(uv_timer_t* handle)
|
||||
{
|
||||
TimerCallbackInfo* callbackInfo = Helper::DereferenceHelp::DereferenceOf(&TimerCallbackInfo::timeReq_, handle);
|
||||
if (callbackInfo == nullptr) {
|
||||
return;
|
||||
}
|
||||
napi_value callback = Helper::NapiHelper::GetReferenceValue(callbackInfo->env_, callbackInfo->callback_);
|
||||
napi_value undefinedValue = Helper::NapiHelper::GetUndefinedValue(callbackInfo->env_);
|
||||
napi_value callbackResult = nullptr;
|
||||
napi_value* callbackArgv = new napi_value[callbackInfo->argc_];
|
||||
Helper::ObjectScope<napi_value> scope(callbackArgv, true);
|
||||
for (size_t idx = 0; idx < callbackInfo->argc_; idx++) {
|
||||
callbackArgv[idx] = Helper::NapiHelper::GetReferenceValue(callbackInfo->env_, callbackInfo->argv_[idx]);
|
||||
}
|
||||
napi_call_function(callbackInfo->env_, undefinedValue, callback,
|
||||
callbackInfo->argc_, callbackArgv, &callbackResult);
|
||||
if (callbackResult == nullptr) {
|
||||
HILOG_WARN("call callback error");
|
||||
return;
|
||||
}
|
||||
if (!callbackInfo->repeat_) {
|
||||
timerTable.erase(callbackInfo->tId_);
|
||||
Helper::CloseHelp::DeletePointer(callbackInfo, false);
|
||||
} else {
|
||||
uv_timer_again(handle);
|
||||
}
|
||||
}
|
||||
|
||||
napi_value Timer::SetTimeoutInner(napi_env env, napi_callback_info cbinfo, bool repeat)
|
||||
{
|
||||
// 1. check args
|
||||
size_t argc = Helper::NapiHelper::GetCallbackInfoArgc(env, cbinfo);
|
||||
if (argc <= 0) {
|
||||
napi_throw_error(env, nullptr, "callback must be a function. received undefined");
|
||||
return nullptr;
|
||||
}
|
||||
napi_value* argv = new napi_value[argc];
|
||||
Helper::ObjectScope<napi_value> scope(argv, true);
|
||||
napi_value thisVar = nullptr;
|
||||
napi_get_cb_info(env, cbinfo, &argc, argv, &thisVar, nullptr);
|
||||
if (!Helper::NapiHelper::IsCallable(env, argv[0])) {
|
||||
napi_throw_error(env, nullptr, "callback must be a function.");
|
||||
return nullptr;
|
||||
}
|
||||
uint32_t timeout = 0;
|
||||
if (argc > 1) {
|
||||
napi_status status = napi_get_value_uint32(env, argv[1], &timeout);
|
||||
if (status != napi_ok) {
|
||||
HILOG_WARN("timeout should be number");
|
||||
timeout = 0;
|
||||
}
|
||||
}
|
||||
// 2. get callback args
|
||||
size_t callbackArgc = argc >= 2 ? argc - 2 : 0; // 2 include callback and timeout
|
||||
napi_ref* callbackArgv = nullptr;
|
||||
if (callbackArgc > 0) {
|
||||
callbackArgv = new napi_ref[callbackArgc];
|
||||
for (size_t idx = 0; idx < callbackArgc; idx++) {
|
||||
callbackArgv[idx] =
|
||||
Helper::NapiHelper::CreateReference(env, argv[idx + 2], 1); // 2 include callback and timeout
|
||||
}
|
||||
}
|
||||
|
||||
// 3. generate time callback id;
|
||||
uint32_t tId = 0;
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(timeLock);
|
||||
tId = timeCallbackId++;
|
||||
}
|
||||
// 4. generate time callback info
|
||||
napi_ref callbackRef = Helper::NapiHelper::CreateReference(env, argv[0], 1);
|
||||
TimerCallbackInfo* callbackInfo =
|
||||
new TimerCallbackInfo(env, tId, timeout, callbackRef, repeat, callbackArgc, callbackArgv);
|
||||
// 5. push callback info into timerTable
|
||||
timerTable[tId] = callbackInfo;
|
||||
|
||||
// 6. start timer
|
||||
uv_timer_start(&callbackInfo->timeReq_, TimerCallback, timeout, timeout > 0 ? timeout : 1);
|
||||
return Helper::NapiHelper::CreateUint32(env, tId);
|
||||
}
|
||||
|
||||
void Timer::ClearEnvironmentTimer(napi_env env)
|
||||
{
|
||||
auto iter = timerTable.begin();
|
||||
while (iter != timerTable.end()) {
|
||||
TimerCallbackInfo* callbackInfo = iter->second;
|
||||
if (callbackInfo->env_ == env) {
|
||||
iter = timerTable.erase(iter);
|
||||
Helper::CloseHelp::DeletePointer(callbackInfo, false);
|
||||
} else {
|
||||
iter++;
|
||||
}
|
||||
}
|
||||
}
|
||||
} // namespace CompilerRuntime::WorkerModule::Plugin
|
69
js_worker_module/plugin/timer.h
Normal file
69
js_worker_module/plugin/timer.h
Normal file
@ -0,0 +1,69 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef JS_WORKER_MODULE_PLUGIN_TIMER_H_
|
||||
#define JS_WORKER_MODULE_PLUGIN_TIMER_H_
|
||||
|
||||
#include <map>
|
||||
#include <uv.h>
|
||||
|
||||
#include "base/compileruntime/js_worker_module/helper/napi_helper.h"
|
||||
#include "base/compileruntime/js_worker_module/helper/object_helper.h"
|
||||
#include "napi/native_api.h"
|
||||
#include "napi/native_node_api.h"
|
||||
|
||||
namespace CompilerRuntime::WorkerModule::Plugin {
|
||||
struct TimerCallbackInfo {
|
||||
napi_env env_;
|
||||
uint32_t tId_;
|
||||
uint32_t timeout_;
|
||||
napi_ref callback_;
|
||||
bool repeat_;
|
||||
uv_timer_t timeReq_;
|
||||
size_t argc_;
|
||||
napi_ref* argv_;
|
||||
|
||||
TimerCallbackInfo(napi_env env, uint32_t tId, uint32_t timeout, napi_ref callback,
|
||||
bool repeat, size_t argc, napi_ref* argv)
|
||||
: env_(env), tId_(tId), timeout_(timeout), callback_(callback),
|
||||
repeat_(repeat), argc_(argc), argv_(argv)
|
||||
{
|
||||
uv_loop_t* loop = Helper::NapiHelper::GetLibUV(env_);
|
||||
uv_timer_init(loop, &timeReq_);
|
||||
}
|
||||
|
||||
~TimerCallbackInfo();
|
||||
};
|
||||
|
||||
class Timer {
|
||||
public:
|
||||
Timer() = default;
|
||||
~Timer() = default;
|
||||
static bool RegisterTime(napi_env env);
|
||||
static void ClearEnvironmentTimer(napi_env env);
|
||||
|
||||
private:
|
||||
static napi_value SetTimeout(napi_env env, napi_callback_info cbinfo);
|
||||
static napi_value SetInterval(napi_env env, napi_callback_info cbinfo);
|
||||
static napi_value ClearTimer(napi_env env, napi_callback_info cbinfo);
|
||||
static napi_value SetTimeoutInner(napi_env env, napi_callback_info cbinfo, bool repeat);
|
||||
static void TimerCallback(uv_timer_t* handle);
|
||||
|
||||
static uint32_t timeCallbackId;
|
||||
static std::map<uint32_t, TimerCallbackInfo*> timerTable;
|
||||
static std::mutex timeLock;
|
||||
};
|
||||
} // namespace CompilerRuntime::WorkerModule::Plugin
|
||||
#endif // JS_WORKER_MODULE_PLUGIN_TIMER_H_
|
60
js_worker_module/worker/message_queue.cpp
Normal file
60
js_worker_module/worker/message_queue.cpp
Normal file
@ -0,0 +1,60 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "base/compileruntime/js_worker_module/worker/message_queue.h"
|
||||
#include "utils/log.h"
|
||||
|
||||
namespace CompilerRuntime::WorkerModule {
|
||||
void MessageQueue::EnQueue(MessageDataType data)
|
||||
{
|
||||
queueLock_.lock();
|
||||
queue_.push(data);
|
||||
queueLock_.unlock();
|
||||
}
|
||||
|
||||
bool MessageQueue::DeQueue(MessageDataType *data)
|
||||
{
|
||||
queueLock_.lock();
|
||||
if (queue_.empty()) {
|
||||
queueLock_.unlock();
|
||||
return false;
|
||||
}
|
||||
if (data != nullptr) {
|
||||
*data = queue_.front();
|
||||
queue_.pop();
|
||||
queueLock_.unlock();
|
||||
} else {
|
||||
HILOG_ERROR("worker:: data is nullptr.");
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool MessageQueue::IsEmpty() const
|
||||
{
|
||||
return queue_.empty();
|
||||
}
|
||||
|
||||
void MessageQueue::Clear(napi_env env)
|
||||
{
|
||||
queueLock_.lock();
|
||||
size_t size = queue_.size();
|
||||
for (size_t i = 0; i < size; i++) {
|
||||
MessageDataType data = queue_.front();
|
||||
napi_delete_serialization_data(env, data);
|
||||
queue_.pop();
|
||||
}
|
||||
queueLock_.unlock();
|
||||
}
|
||||
} // namespace CompilerRuntime::WorkerModule
|
42
js_worker_module/worker/message_queue.h
Normal file
42
js_worker_module/worker/message_queue.h
Normal file
@ -0,0 +1,42 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef JS_WORKER_MODULE_WORKER_MESSAGE_QUEUE_H_
|
||||
#define JS_WORKER_MODULE_WORKER_MESSAGE_QUEUE_H_
|
||||
|
||||
#include <mutex>
|
||||
#include <queue>
|
||||
#include "napi/native_api.h"
|
||||
#include "napi/native_node_api.h"
|
||||
|
||||
namespace CompilerRuntime::WorkerModule {
|
||||
using MessageDataType = napi_value;
|
||||
class MessageQueue final {
|
||||
public:
|
||||
void EnQueue(MessageDataType data);
|
||||
bool DeQueue(MessageDataType *data);
|
||||
bool IsEmpty() const;
|
||||
void Clear(napi_env env);
|
||||
size_t GetSize() const
|
||||
{
|
||||
return queue_.size();
|
||||
}
|
||||
|
||||
private:
|
||||
std::mutex queueLock_;
|
||||
std::queue<MessageDataType> queue_;
|
||||
};
|
||||
} // namespace CompilerRuntime::WorkerModule
|
||||
#endif // JS_WORKER_MODULE_WORKER_MESSAGE_QUEUE_H_
|
36
js_worker_module/worker/native_module_worker.cpp
Normal file
36
js_worker_module/worker/native_module_worker.cpp
Normal file
@ -0,0 +1,36 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "base/compileruntime/js_worker_module/worker/worker.h"
|
||||
|
||||
/*
|
||||
* module define
|
||||
*/
|
||||
static napi_module g_workerModule = {
|
||||
.nm_version = 1,
|
||||
.nm_flags = 0,
|
||||
.nm_filename = nullptr,
|
||||
.nm_register_func = CompilerRuntime::WorkerModule::Worker::InitWorker,
|
||||
.nm_modname = "worker",
|
||||
.nm_priv = reinterpret_cast<void*>(0),
|
||||
.reserved = { 0 },
|
||||
};
|
||||
/*
|
||||
* module register
|
||||
*/
|
||||
extern "C" __attribute__((constructor)) void Register()
|
||||
{
|
||||
napi_module_register(&g_workerModule);
|
||||
}
|
29
js_worker_module/worker/thread.cpp
Normal file
29
js_worker_module/worker/thread.cpp
Normal file
@ -0,0 +1,29 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "base/compileruntime/js_worker_module/worker/thread.h"
|
||||
|
||||
namespace CompilerRuntime::WorkerModule {
|
||||
Thread::Thread() : tId_() {}
|
||||
|
||||
bool Thread::Start()
|
||||
{
|
||||
int ret = uv_thread_create(&tId_, [](void* arg) {
|
||||
Thread* thread = reinterpret_cast<Thread*>(arg);
|
||||
thread->Run();
|
||||
}, this);
|
||||
return ret != 0;
|
||||
}
|
||||
} // namespace CompilerRuntime::WorkerModule
|
39
js_worker_module/worker/thread.h
Normal file
39
js_worker_module/worker/thread.h
Normal file
@ -0,0 +1,39 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef JS_WORKER_MODULE_WORKER_THREAD_H_
|
||||
#define JS_WORKER_MODULE_WORKER_THREAD_H_
|
||||
|
||||
#include <uv.h>
|
||||
|
||||
namespace CompilerRuntime::WorkerModule {
|
||||
class Thread {
|
||||
public:
|
||||
Thread();
|
||||
virtual ~Thread() = default;
|
||||
bool Start();
|
||||
virtual void Run() = 0;
|
||||
|
||||
uv_thread_t GetThreadId() const
|
||||
{
|
||||
return tId_;
|
||||
}
|
||||
|
||||
private:
|
||||
uv_thread_t tId_ {0};
|
||||
};
|
||||
} // namespace CompilerRuntime::WorkerModule
|
||||
|
||||
#endif // #define JS_WORKER_MODULE_WORKER_THREAD_H_
|
1444
js_worker_module/worker/worker.cpp
Normal file
1444
js_worker_module/worker/worker.cpp
Normal file
File diff suppressed because it is too large
Load Diff
457
js_worker_module/worker/worker.h
Normal file
457
js_worker_module/worker/worker.h
Normal file
@ -0,0 +1,457 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef JS_WORKER_MODULE_WORKER_WORKER_H_
|
||||
#define JS_WORKER_MODULE_WORKER_WORKER_H_
|
||||
|
||||
#include <list>
|
||||
#include <map>
|
||||
#include <mutex>
|
||||
#include "base/compileruntime/js_worker_module/worker/message_queue.h"
|
||||
#include "base/compileruntime/js_worker_module/helper/napi_helper.h"
|
||||
#include "base/compileruntime/js_worker_module/helper/object_helper.h"
|
||||
#include "base/compileruntime/js_worker_module/worker/worker_runner.h"
|
||||
#include "napi/native_api.h"
|
||||
#include "napi/native_node_api.h"
|
||||
#include "native_engine/native_engine.h"
|
||||
#include "utils/log.h"
|
||||
|
||||
namespace CompilerRuntime::WorkerModule {
|
||||
class Worker {
|
||||
public:
|
||||
static const int8_t WORKERPARAMNUM = 2;
|
||||
|
||||
enum RunnerState { STARTING, RUNNING, TERMINATEING, TERMINATED };
|
||||
enum HostState { ACTIVE, INACTIVE };
|
||||
enum ListenerMode { ONCE, PERMANENT };
|
||||
|
||||
enum ScriptMode { CLASSIC, MODULE };
|
||||
|
||||
struct WorkerListener {
|
||||
WorkerListener(napi_env env, napi_ref callback, ListenerMode mode)
|
||||
: env_(env), callback_(callback), mode_(mode)
|
||||
{}
|
||||
|
||||
~WorkerListener()
|
||||
{
|
||||
Helper::NapiHelper::DeleteReference(env_, callback_);
|
||||
callback_ = nullptr;
|
||||
}
|
||||
|
||||
bool NextIsAvailable() const
|
||||
{
|
||||
return mode_ != ONCE;
|
||||
}
|
||||
|
||||
void SetMode(ListenerMode mode)
|
||||
{
|
||||
mode_ = mode;
|
||||
}
|
||||
|
||||
bool operator==(const WorkerListener& listener) const;
|
||||
|
||||
napi_env env_ {NULL};
|
||||
napi_ref callback_ {NULL};
|
||||
ListenerMode mode_ {PERMANENT};
|
||||
};
|
||||
|
||||
struct FindWorkerListener {
|
||||
FindWorkerListener(napi_env env, napi_ref ref) : env_(env), ref_(ref) {}
|
||||
|
||||
bool operator()(const WorkerListener* listener) const
|
||||
{
|
||||
napi_value compareObj = Helper::NapiHelper::GetReferenceValue(env_, listener->callback_);
|
||||
napi_value obj = Helper::NapiHelper::GetReferenceValue(env_, ref_);
|
||||
// the env of listener and cmp listener must be same env because of Synchronization method
|
||||
return Helper::NapiHelper::StrictEqual(env_, compareObj, obj);
|
||||
}
|
||||
|
||||
napi_env env_ {nullptr};
|
||||
napi_ref ref_ {nullptr};
|
||||
};
|
||||
|
||||
/**
|
||||
* Creates a worker instance.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param thisVar URL of the script to be executed by the worker.
|
||||
*/
|
||||
Worker(napi_env env, napi_ref thisVar);
|
||||
|
||||
/**
|
||||
* The destructor of the Worker.
|
||||
*/
|
||||
~Worker();
|
||||
|
||||
/**
|
||||
* The host thread receives the information.
|
||||
*
|
||||
* @param req The value of the object passed in by the js layer.
|
||||
*/
|
||||
static void HostOnMessage(const uv_async_t* req);
|
||||
|
||||
/**
|
||||
* The host thread receives the information.
|
||||
*
|
||||
* @param req The value of the object passed in by the js layer.
|
||||
*/
|
||||
static void HostOnError(const uv_async_t* req);
|
||||
|
||||
/**
|
||||
* The worker thread receives the information.
|
||||
*
|
||||
* @param req The value of the object passed in by the js layer.
|
||||
*/
|
||||
static void WorkerOnMessage(const uv_async_t* req);
|
||||
|
||||
/**
|
||||
* ExecuteIn in thread.
|
||||
*
|
||||
* @param data The worker pointer.
|
||||
*/
|
||||
static void ExecuteInThread(const void* data);
|
||||
|
||||
/**
|
||||
* Post a message.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param thisVar The callback information of the js layer.
|
||||
*/
|
||||
static napi_value PostMessage(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* Add event listeners to host.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value PostMessageToHost(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* Terminates the worker thread to stop the worker from receiving messages.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value Terminate(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* Close the worker.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value CloseWorker(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* Adds an event listener to the worker.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value On(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* Adds an event listener to the worker and removes the event listener automatically after it is invoked once.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value Once(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* Removes an event listener to the worker.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value Off(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* Add event listeners.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value AddEventListener(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* Dispatch the event.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value DispatchEvent(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* Remove the event listener.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value RemoveEventListener(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* Remove all listener.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value RemoveAllListener(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* Add the listener.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value AddListener(napi_env env, napi_callback_info cbinfo, ListenerMode mode);
|
||||
|
||||
/**
|
||||
* Remove the listener.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value RemoveListener(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* The constructor of worker.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value WorkerConstructor(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* Initialize the worker.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value InitWorker(napi_env env, napi_value exports);
|
||||
|
||||
/**
|
||||
* Cancel the task.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value CancelTask(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* The parent port cancels the task.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value ParentPortCancelTask(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* The parent port adds an event listener.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value ParentPortAddEventListener(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* The parent port removes all event listener.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value ParentPortRemoveAllListener(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* The parent port dispatch the event listener.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value ParentPortDispatchEvent(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
/**
|
||||
* The parent port removes the event listener.
|
||||
*
|
||||
* @param env NAPI environment parameters.
|
||||
* @param cbinfo The callback information of the js layer.
|
||||
*/
|
||||
static napi_value ParentPortRemoveEventListener(napi_env env, napi_callback_info cbinfo);
|
||||
|
||||
void StartExecuteInThread(napi_env env, const char* script);
|
||||
|
||||
bool UpdateWorkerState(RunnerState state);
|
||||
bool UpdateHostState(HostState state);
|
||||
|
||||
bool IsRunning() const
|
||||
{
|
||||
return runnerState_.load(std::memory_order_acquire) == RUNNING;
|
||||
}
|
||||
|
||||
bool IsTerminated() const
|
||||
{
|
||||
return runnerState_.load(std::memory_order_acquire) >= TERMINATED;
|
||||
}
|
||||
|
||||
bool IsTerminating() const
|
||||
{
|
||||
return runnerState_.load(std::memory_order_acquire) == TERMINATEING;
|
||||
}
|
||||
|
||||
void SetScriptMode(ScriptMode mode)
|
||||
{
|
||||
scriptMode_ = mode;
|
||||
}
|
||||
|
||||
void AddListenerInner(napi_env env, const char* type, const WorkerListener* listener);
|
||||
void RemoveListenerInner(napi_env env, const char* type, napi_ref callback);
|
||||
void RemoveAllListenerInner();
|
||||
|
||||
uv_loop_t* GetWorkerLoop() const
|
||||
{
|
||||
if (workerEnv_ != nullptr) {
|
||||
return Helper::NapiHelper::GetLibUV(workerEnv_);
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void SetWorkerEnv(napi_env workerEnv)
|
||||
{
|
||||
workerEnv_ = workerEnv;
|
||||
}
|
||||
|
||||
std::string GetScript() const
|
||||
{
|
||||
return script_;
|
||||
}
|
||||
|
||||
std::string GetName() const
|
||||
{
|
||||
return name_;
|
||||
}
|
||||
|
||||
bool ClearWorkerTasks()
|
||||
{
|
||||
if (hostEnv_ != nullptr) {
|
||||
workerMessageQueue_.Clear(hostEnv_);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool HostIsStop() const
|
||||
{
|
||||
return hostState_.load(std::memory_order_acquire) == INACTIVE;
|
||||
}
|
||||
|
||||
bool IsSameWorkerEnv(napi_env env) const
|
||||
{
|
||||
return workerEnv_ == env;
|
||||
}
|
||||
|
||||
void Loop()
|
||||
{
|
||||
uv_loop_t* loop = GetWorkerLoop();
|
||||
if (loop != nullptr) {
|
||||
uv_run(loop, UV_RUN_DEFAULT);
|
||||
} else {
|
||||
HILOG_ERROR("worker:: Worker loop is nullptr when start worker loop");
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
void WorkerOnMessageInner();
|
||||
void HostOnMessageInner();
|
||||
void HostOnErrorInner();
|
||||
void HostOnMessageErrorInner();
|
||||
void WorkerOnMessageErrorInner();
|
||||
void WorkerOnErrorInner(napi_value error);
|
||||
|
||||
void HandleException();
|
||||
bool CallWorkerFunction(size_t argc, const napi_value* argv, const char* methodName, bool tryCatch);
|
||||
void CallHostFunction(size_t argc, const napi_value* argv, const char* methodName) const;
|
||||
|
||||
void HandleEventListeners(napi_env env, napi_value recv, size_t argc, const napi_value* argv, const char* type);
|
||||
void ParentPortHandleEventListeners(napi_env env, napi_value recv,
|
||||
size_t argc, const napi_value* argv, const char* type);
|
||||
void TerminateInner();
|
||||
|
||||
void PostMessageInner(MessageDataType data);
|
||||
void PostMessageToHostInner(MessageDataType data);
|
||||
|
||||
void TerminateWorker();
|
||||
void CloseInner();
|
||||
|
||||
void PublishWorkerOverSignal();
|
||||
void CloseWorkerCallback();
|
||||
void CloseHostCallback() const;
|
||||
|
||||
void ReleaseWorkerThreadContent();
|
||||
void ReleaseHostThreadContent();
|
||||
bool PrepareForWorkerInstance();
|
||||
void ParentPortAddListenerInner(napi_env env, const char* type, const WorkerListener* listener);
|
||||
void ParentPortRemoveAllListenerInner();
|
||||
void ParentPortRemoveListenerInner(napi_env env, const char* type, napi_ref callback);
|
||||
void PreparePandafile();
|
||||
|
||||
#if !defined(WINDOWS_PLATFORM) && !defined(MAC_PLATFORM)
|
||||
static void HandleDebuggerTask(const uv_async_t* req);
|
||||
void DebuggerOnPostTask(std::function<void()>&& task);
|
||||
#endif
|
||||
|
||||
napi_env GetHostEnv() const
|
||||
{
|
||||
return hostEnv_;
|
||||
}
|
||||
|
||||
napi_env GetWorkerEnv() const
|
||||
{
|
||||
return workerEnv_;
|
||||
}
|
||||
|
||||
std::string script_ {};
|
||||
std::string name_ {};
|
||||
ScriptMode scriptMode_ {CLASSIC};
|
||||
|
||||
MessageQueue workerMessageQueue_ {};
|
||||
MessageQueue hostMessageQueue_ {};
|
||||
MessageQueue errorQueue_ {};
|
||||
|
||||
uv_async_t workerOnMessageSignal_ {};
|
||||
uv_async_t hostOnMessageSignal_ {};
|
||||
uv_async_t hostOnErrorSignal_ {};
|
||||
#if !defined(WINDOWS_PLATFORM) && !defined(MAC_PLATFORM)
|
||||
uv_async_t debuggerOnPostTaskSignal_ {};
|
||||
std::function<void()> debuggerTask_;
|
||||
#endif
|
||||
|
||||
std::atomic<RunnerState> runnerState_ {STARTING};
|
||||
std::atomic<HostState> hostState_ {ACTIVE};
|
||||
std::unique_ptr<WorkerRunner> runner_ {};
|
||||
|
||||
napi_env hostEnv_ {nullptr};
|
||||
napi_env workerEnv_ {nullptr};
|
||||
|
||||
napi_ref workerRef_ {nullptr};
|
||||
napi_ref parentPort_ {nullptr};
|
||||
|
||||
std::map<std::string, std::list<WorkerListener*>> eventListeners_ {};
|
||||
std::map<std::string, std::list<WorkerListener*>> parentPortEventListeners_ {};
|
||||
|
||||
std::recursive_mutex liveStatusLock_ {};
|
||||
};
|
||||
} // namespace CompilerRuntime::WorkerModule
|
||||
#endif // JS_WORKER_MODULE_WORKER_WORKER_H_
|
49
js_worker_module/worker/worker_runner.cpp
Normal file
49
js_worker_module/worker/worker_runner.cpp
Normal file
@ -0,0 +1,49 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "base/compileruntime/js_worker_module/worker/worker_runner.h"
|
||||
|
||||
#include "base/compileruntime/js_worker_module/helper/object_helper.h"
|
||||
|
||||
namespace CompilerRuntime::WorkerModule {
|
||||
WorkerRunner::WorkerRunner(WorkerStartCallback callback) : callback_(callback), selfThreadId_(uv_thread_self()) {}
|
||||
|
||||
WorkerRunner::~WorkerRunner()
|
||||
{
|
||||
Helper::CloseHelp::DeletePointer(workerInnerRunner_, false);
|
||||
}
|
||||
|
||||
void WorkerRunner::WorkerInnerRunner::Run()
|
||||
{
|
||||
if (runner_ != nullptr) {
|
||||
runner_->Run();
|
||||
}
|
||||
}
|
||||
|
||||
WorkerRunner::WorkerInnerRunner::WorkerInnerRunner(const WorkerRunner* runner) : runner_(runner) {}
|
||||
|
||||
void WorkerRunner::Run() const
|
||||
{
|
||||
if (callback_.callback != nullptr) {
|
||||
callback_.callback(callback_.data);
|
||||
}
|
||||
}
|
||||
|
||||
bool WorkerRunner::Execute()
|
||||
{
|
||||
workerInnerRunner_ = new WorkerInnerRunner(this);
|
||||
return workerInnerRunner_->Start();
|
||||
}
|
||||
} // namespace CompilerRuntime::WorkerModule
|
62
js_worker_module/worker/worker_runner.h
Normal file
62
js_worker_module/worker/worker_runner.h
Normal file
@ -0,0 +1,62 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Huawei Device Co., Ltd.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef JS_WORKER_MODULE_WORKER_WORKER_RUNNER_H_
|
||||
#define JS_WORKER_MODULE_WORKER_WORKER_RUNNER_H_
|
||||
|
||||
#include <functional>
|
||||
|
||||
#include "native_engine/native_engine.h"
|
||||
#include "base/compileruntime/js_worker_module/worker/thread.h"
|
||||
|
||||
namespace CompilerRuntime::WorkerModule {
|
||||
struct WorkerStartCallback {
|
||||
using CallbackFunction = std::function<void(void*)>;
|
||||
|
||||
explicit WorkerStartCallback(CallbackFunction function = nullptr, void* dataArgs = nullptr)
|
||||
: callback(function), data(dataArgs)
|
||||
{}
|
||||
|
||||
CallbackFunction callback;
|
||||
void* data;
|
||||
};
|
||||
|
||||
class WorkerRunner {
|
||||
public:
|
||||
// real thread execute
|
||||
class WorkerInnerRunner : public Thread {
|
||||
public:
|
||||
explicit WorkerInnerRunner(const WorkerRunner* runner);
|
||||
~WorkerInnerRunner() = default;
|
||||
void Run() override;
|
||||
|
||||
private:
|
||||
const WorkerRunner* runner_;
|
||||
};
|
||||
|
||||
explicit WorkerRunner(WorkerStartCallback callback);
|
||||
~WorkerRunner();
|
||||
|
||||
bool Execute();
|
||||
void Run() const;
|
||||
void Stop();
|
||||
|
||||
private:
|
||||
WorkerInnerRunner* workerInnerRunner_ {nullptr};
|
||||
WorkerStartCallback callback_;
|
||||
uv_thread_t selfThreadId_ {0};
|
||||
};
|
||||
} // namespace CompilerRuntime::WorkerModule
|
||||
#endif // JS_WORKER_MODULE_WORKER_WORKER_RUNNER_H_
|
Loading…
Reference in New Issue
Block a user