Skip to content

Commit

Permalink
Javet v0.8.8 (#34)
Browse files Browse the repository at this point in the history
* Re-organized doc.
* Added ``getJSFunctionType()``, ``getSourceCode()`` and ``setSourceCode()`` to ``IV8ValueFunction``
  • Loading branch information
caoccao authored May 19, 2021
1 parent 049593a commit 0b452da
Show file tree
Hide file tree
Showing 75 changed files with 1,407 additions and 405 deletions.
21 changes: 7 additions & 14 deletions README.rst
Original file line number Diff line number Diff line change
Expand Up @@ -40,22 +40,22 @@ Maven
<dependency>
<groupId>com.caoccao.javet</groupId>
<artifactId>javet</artifactId>
<version>0.8.7</version>
<version>0.8.8</version>
</dependency>
Gradle Kotlin DSL
^^^^^^^^^^^^^^^^^

.. code-block:: kotlin
implementation("com.caoccao.javet:javet:0.8.7")
implementation("com.caoccao.javet:javet:0.8.8")
Gradle Groovy DSL
^^^^^^^^^^^^^^^^^

.. code-block:: groovy
implementation 'com.caoccao.javet:javet:0.8.7'
implementation 'com.caoccao.javet:javet:0.8.8'
Hello Javet
-----------
Expand All @@ -75,21 +75,14 @@ Hello Javet
Documents
=========

* Presentations

* `Javet Intro <https://docs.google.com/presentation/d/1lQ8xIHuywuE0ydqm2w6xq8OeQZO_WeTLYXW9bNflQb8/>`_

* `Development <docs/development/index.rst>`_

* `Build <docs/development/build.rst>`_
* `Design <docs/development/design.rst>`_
* `Performance <docs/development/performance.rst>`_

* `Javet Intro <https://docs.google.com/presentation/d/1lQ8xIHuywuE0ydqm2w6xq8OeQZO_WeTLYXW9bNflQb8/>`_
* `Tutorial <docs/tutorial/index.rst>`_
* `Reference <docs/reference/index.rst>`_
* `Release Notes <docs/release_notes.rst>`_
* `FAQ <docs/faq/index.rst>`_
* `Development <docs/development/index.rst>`_

License
=======

Javet follows `APACHE LICENSE, VERSION 2.0 <LICENSE>`_.
`APACHE LICENSE, VERSION 2.0 <LICENSE>`_.
14 changes: 13 additions & 1 deletion build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ repositories {
}

group = "com.caoccao.javet"
version = "0.8.7"
version = "0.8.8"

repositories {
mavenCentral()
Expand Down Expand Up @@ -76,3 +76,15 @@ tasks.register<Test>("performanceTest") {
includeTags("performance")
}
}

tasks.withType<JavaCompile> {
options.encoding = "UTF-8"
}

tasks.withType<Test> {
systemProperty("file.encoding", "UTF-8")
}

tasks.withType<Javadoc>{
options.encoding = "UTF-8"
}
17 changes: 14 additions & 3 deletions cpp/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -37,15 +37,18 @@ endif()
# Preparation
if(DEFINED V8_DIR)
list(APPEND includeDirs
${V8_DIR}/include)
${V8_DIR}
${V8_DIR}/include
${V8_DIR}/out.gn/x64.release/gen)
list(APPEND importLibraries v8_monolith)
set(JAVET_LIB_TYPE "v8")
endif()
if(DEFINED NODE_DIR)
list(APPEND includeDirs
${NODE_DIR}/src
${NODE_DIR}/deps/uv/include
${NODE_DIR}/deps/v8/include)
${NODE_DIR}/deps/v8
${NODE_DIR}/deps/v8/include
${NODE_DIR}/src)
list(APPEND importLibraries
brotli cares histogram llhttp nghttp2 openssl torque_base uvwasi
v8_base_without_compiler v8_compiler v8_init v8_initializers
Expand Down Expand Up @@ -79,6 +82,10 @@ if(CMAKE_SYSTEM_NAME STREQUAL "Windows")
add_library(Javet SHARED ${sourceFiles} "jni/javet_resource_v8.rc")
endif()
if(DEFINED NODE_DIR)
list(APPEND includeDirs
${NODE_DIR}/out/Release/obj/global_intermediate/generate-bytecode-output-root
${NODE_DIR}/out/Release/obj/global_intermediate/inspector-generated-output-root
${NODE_DIR}/out/Release/obj/global_intermediate/torque-output-root)
foreach(importLibrary ${importLibraries})
set_target_properties(${importLibrary} PROPERTIES IMPORTED_LOCATION ${NODE_DIR}/out/release/lib/${importLibrary}.lib)
endforeach(importLibrary)
Expand Down Expand Up @@ -108,6 +115,10 @@ elseif(CMAKE_SYSTEM_NAME STREQUAL "Linux")
endif()
if(DEFINED NODE_DIR)
set(CMAKE_POSITION_INDEPENDENT_CODE ON)
list(APPEND includeDirs
${NODE_DIR}/out/Release/obj/gen/generate-bytecode-output-root
${NODE_DIR}/out/Release/obj/gen/inspector-generated-output-root
${NODE_DIR}/out/Release/obj/gen/torque-output-root)
foreach(importLibrary ${importLibraries})
set_target_properties(${importLibrary} PROPERTIES IMPORTED_LOCATION ${NODE_DIR}/out/Release/lib${importLibrary}.a)
endforeach(importLibrary)
Expand Down
2 changes: 1 addition & 1 deletion cpp/build.cmd
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
@echo off
REM Usage for V8: build -DV8_DIR=C:\v8
REM Usage for Node: build -DNODE_DIR=C:\node
SET JAVET_VERSION=0.8.7
SET JAVET_VERSION=0.8.8
rd /s/q build
mkdir build
cd build
Expand Down
2 changes: 1 addition & 1 deletion cpp/build.sh
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

# Usage for V8: build -DV8_DIR=~/v8
# Usage for Node: build -DNODE_DIR=~/node
JAVET_VERSION=0.8.7
JAVET_VERSION=0.8.8
rm -rf build
mkdir build
cd build
Expand Down
1 change: 0 additions & 1 deletion cpp/jni/com_caoccao_javet_interop_NodeNative.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,6 @@
#include "javet_logging.h"
#include "javet_native.h"
#include "javet_node.h"
#include "javet_types.h"
#include "javet_v8.h"
#include "javet_v8_runtime.h"

Expand Down
183 changes: 155 additions & 28 deletions cpp/jni/com_caoccao_javet_interop_V8Native.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -25,9 +25,9 @@
#include "javet_logging.h"
#include "javet_native.h"
#include "javet_node.h"
#include "javet_types.h"
#include "javet_v8.h"
#include "javet_v8_runtime.h"
#include "javet_v8_internal.h"

/*
* Development Guide:
Expand All @@ -39,16 +39,6 @@
#define IS_JAVA_STRING(jniEnv, obj) jniEnv->IsInstanceOf(obj, Javet::V8Native::jclassV8ValueString)
#define TO_JAVA_INTEGER(jniEnv, obj) jniEnv->CallIntMethod(obj, Javet::V8Native::jmethodIDV8ValueIntegerToPrimitive)
#define TO_JAVA_STRING(jniEnv, obj) (jstring)jniEnv->CallObjectMethod(obj, Javet::V8Native::jmethodIDV8ValueStringToPrimitive)
#define IS_V8_ARRAY(type) (type == Javet::Enums::V8ValueReferenceType::Array)
#define IS_V8_ARRAY_BUFFER(type) (type == Javet::Enums::V8ValueReferenceType::ArrayBuffer)
#define IS_V8_ARGUMENTS(type) (type == Javet::Enums::V8ValueReferenceType::Arguments)
#define IS_V8_FUNCTION(type) (type == Javet::Enums::V8ValueReferenceType::Function)
#define IS_V8_MAP(type) (type == Javet::Enums::V8ValueReferenceType::Map)
#define IS_V8_MODULE(type) (type == Javet::Enums::V8ValueReferenceType::Module)
#define IS_V8_OBJECT(type) (type == Javet::Enums::V8ValueReferenceType::Object)
#define IS_V8_PROMISE(type) (type == Javet::Enums::V8ValueReferenceType::Promise)
#define IS_V8_SCRIPT(type) (type == Javet::Enums::V8ValueReferenceType::Script)
#define IS_V8_SET(type) (type == Javet::Enums::V8ValueReferenceType::Set)

namespace Javet {
#ifdef ENABLE_NODE
Expand Down Expand Up @@ -463,6 +453,20 @@ JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getIdentityHash
return v8LocalObject->GetIdentityHash();
}

JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getInternalProperties
(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) {
RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle);
if (IS_V8_FUNCTION(v8ValueType)) {
// This feature is not enabled yet.
v8_inspector::V8InspectorClient v8InspectorClient;
v8_inspector::V8InspectorImpl v8InspectorImpl(v8Runtime->v8Isolate, &v8InspectorClient);
v8_inspector::V8Debugger v8Debugger(v8Runtime->v8Isolate, &v8InspectorImpl);
auto v8InternalProperties = v8Debugger.internalProperties(v8Context, v8LocalObject.As<v8::Function>()).ToLocalChecked();
return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8InternalProperties);
}
return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime->externalV8Runtime);
}

JNIEXPORT jlongArray JNICALL Java_com_caoccao_javet_interop_V8Native_getInternalStatistic
(JNIEnv* jniEnv, jobject caller) {
#ifdef ENABLE_MONITOR
Expand All @@ -472,26 +476,45 @@ JNIEXPORT jlongArray JNICALL Java_com_caoccao_javet_interop_V8Native_getInternal
#endif
}

JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getLength
JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getJSFunctionType
(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) {
RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle);
if (IS_V8_ARRAY(v8ValueType)) {
return (jint)v8LocalObject.As<v8::Array>()->Length();
if (IS_V8_FUNCTION(v8ValueType)) {
auto v8InternalFunction = V8InternalJSFunction::cast(*v8::Utils::OpenHandle(*v8LocalObject));
auto v8InternalShared = v8InternalFunction.shared();
if (v8InternalShared.native()) {
return Javet::Enums::JSFunctionType::Native;
}
else if (v8InternalShared.IsApiFunction()) {
return Javet::Enums::JSFunctionType::API;
}
else if (v8InternalShared.IsUserJavaScript()) {
return Javet::Enums::JSFunctionType::UserDefined;
}
}
if (v8LocalObject->IsTypedArray()) {
return (jint)v8LocalObject.As<v8::TypedArray>()->Length();
return Javet::Enums::JSFunctionType::Unknown;
}

JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getJSScopeType
(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) {
RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle);
if (IS_V8_FUNCTION(v8ValueType)) {
auto v8InternalFunction = V8InternalJSFunction::cast(*v8::Utils::OpenHandle(*v8LocalObject));
auto v8InternalShared = v8InternalFunction.shared();
auto v8InternalScopeInfo = v8InternalShared.scope_info();
return v8InternalScopeInfo.scope_type();
}
return 0;
return Javet::Enums::JSScopeType::Unknown;
}

JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getSize
JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getLength
(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) {
RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle);
if (IS_V8_MAP(v8ValueType)) {
return (jint)v8LocalObject.As<v8::Map>()->Size();
if (IS_V8_ARRAY(v8ValueType)) {
return (jint)v8LocalObject.As<v8::Array>()->Length();
}
if (IS_V8_SET(v8ValueType)) {
return (jint)v8LocalObject.As<v8::Set>()->Size();
if (v8LocalObject->IsTypedArray()) {
return (jint)v8LocalObject.As<v8::TypedArray>()->Length();
}
return 0;
}
Expand Down Expand Up @@ -530,6 +553,38 @@ JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getProperty
return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime->externalV8Runtime);
}

JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getSize
(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) {
RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle);
if (IS_V8_MAP(v8ValueType)) {
return (jint)v8LocalObject.As<v8::Map>()->Size();
}
if (IS_V8_SET(v8ValueType)) {
return (jint)v8LocalObject.As<v8::Set>()->Size();
}
return 0;
}

JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_getSourceCode
(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) {
RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle);
if (IS_V8_FUNCTION(v8ValueType)) {
auto v8InternalFunction = V8InternalJSFunction::cast(*v8::Utils::OpenHandle(*v8LocalObject));
auto v8InternalShared = v8InternalFunction.shared();
if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) {
auto v8InternalScript = V8InternalScript::cast(v8InternalShared.script());
auto v8InternalSource = V8InternalString::cast(v8InternalScript.source());
const int startPosition = v8InternalShared.StartPosition();
const int endPosition = v8InternalShared.EndPosition();
auto sourceCode = v8InternalSource.ToCString(
V8InternalAllowNullsFlag::DISALLOW_NULLS, V8InternalRobustnessFlag::ROBUST_STRING_TRAVERSAL,
startPosition, endPosition - startPosition);
return Javet::Converter::ToJavaString(jniEnv, sourceCode.get());
}
}
return nullptr;
}

JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_getVersion
(JNIEnv* jniEnv, jobject caller) {
return Javet::Converter::ToJavaString(jniEnv, v8::V8::GetVersion());
Expand Down Expand Up @@ -830,6 +885,12 @@ JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_resetV8Isolate
v8Runtime->CreateV8Context(jniEnv, mGlobalName);
}

JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_sameValue
(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle1, jlong v8ValueHandle2) {
RUNTIME_AND_2_VALUES_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle1, v8ValueHandle2);
return v8LocalObject1->SameValue(v8LocalObject2);
}

JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_scriptRun
(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jboolean mResultRequired) {
RUNTIME_AND_SCRIPT_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle);
Expand Down Expand Up @@ -907,6 +968,78 @@ JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_setProperty
return false;
}

JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_setSourceCode
(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jstring mSourceCode) {
RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle);
if (IS_V8_FUNCTION(v8ValueType)) {
auto v8InternalFunction = V8InternalJSFunction::cast(*v8::Utils::OpenHandle(*v8LocalObject));
auto v8InternalShared = v8InternalFunction.shared();
if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) {
auto v8InternalScopeInfo = v8InternalShared.scope_info();
if (v8InternalScopeInfo.scope_type() == V8InternalScopeType::FUNCTION_SCOPE && v8InternalScopeInfo.HasPositionInfo()) {
auto v8InternalIsolate = reinterpret_cast<V8InternalIsolate*>(v8Runtime->v8Isolate);
auto v8InternalScript = V8InternalScript::cast(v8InternalShared.script());
auto v8InternalSource = V8InternalString::cast(v8InternalScript.source());
const int startPosition = v8InternalShared.StartPosition();
const int endPosition = v8InternalShared.EndPosition();
const int sourceLength = v8InternalSource.length();

// Build the new source code.
auto umSourceCode = Javet::Converter::ToV8String(jniEnv, v8Context, mSourceCode);
V8LocalString newSourceCode;
if (startPosition > 0) {
int utf8Length = 0;
auto stdStringHeader(v8InternalSource.ToCString(
V8InternalAllowNullsFlag::DISALLOW_NULLS, V8InternalRobustnessFlag::ROBUST_STRING_TRAVERSAL,
0, startPosition, &utf8Length));
auto v8LocalStringHeader = v8::String::NewFromUtf8(
v8Context->GetIsolate(), stdStringHeader.get(), v8::NewStringType::kNormal, utf8Length).ToLocalChecked();
newSourceCode = v8LocalStringHeader;
}
if (newSourceCode.IsEmpty()) {
newSourceCode = umSourceCode;
}
else {
newSourceCode = v8::String::Concat(v8Runtime->v8Isolate, newSourceCode, umSourceCode);
}
if (endPosition < sourceLength) {
int utf8Length = 0;
auto stdStringFooter(v8InternalSource.ToCString(
V8InternalAllowNullsFlag::DISALLOW_NULLS, V8InternalRobustnessFlag::ROBUST_STRING_TRAVERSAL,
endPosition, sourceLength, &utf8Length));
auto v8LocalStringFooter = v8::String::NewFromUtf8(
v8Context->GetIsolate(), stdStringFooter.get(), v8::NewStringType::kNormal, utf8Length).ToLocalChecked();
if (newSourceCode.IsEmpty()) {
newSourceCode = v8LocalStringFooter;
}
else {
newSourceCode = v8::String::Concat(v8Runtime->v8Isolate, newSourceCode, v8LocalStringFooter);
}
}

// Discard compiled data and set lazy compile.
if (v8InternalShared.CanDiscardCompiled() && v8InternalShared.is_compiled()) {
V8InternalSharedFunctionInfo::DiscardCompiled(v8InternalIsolate, v8::internal::handle(v8InternalShared, v8InternalIsolate));
v8InternalFunction.set_code(v8InternalIsolate->builtins()->builtin(V8InternalBuiltins::kCompileLazy));
}

/*
* Set the source and update the start and end position.
* Note: The source code is shared among all script objects, but position info is not.
* So the caller is responsible for restoring the original source code,
* otherwise the next script execution will likely fail because the position info
* of the next script is incorrect.
*/
v8InternalScript.set_source(*v8::Utils::OpenHandle(*newSourceCode), V8InternalWriteBarrierMode::UPDATE_WRITE_BARRIER);
const int newEndPosition = startPosition + umSourceCode->Length();
v8InternalShared.scope_info().SetPositionInfo(startPosition, newEndPosition);
return true;
}
}
}
return false;
}

JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_setWeak
(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject objectReference) {
RUNTIME_AND_DATA_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle);
Expand All @@ -918,12 +1051,6 @@ JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_setWeak
}
}

JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_sameValue
(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle1, jlong v8ValueHandle2) {
RUNTIME_AND_2_VALUES_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle1, v8ValueHandle2);
return v8LocalObject1->SameValue(v8LocalObject2);
}

JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_strictEquals
(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle1, jlong v8ValueHandle2) {
RUNTIME_AND_2_VALUES_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle1, v8ValueHandle2);
Expand Down
Loading

0 comments on commit 0b452da

Please sign in to comment.