2022-10-04 13:21:05 +08:00
|
|
|
|
//----------------------------------------
|
|
|
|
|
//
|
|
|
|
|
// Copyright © yanghy. All Rights Reserved.
|
|
|
|
|
//
|
2022-10-04 16:38:43 +08:00
|
|
|
|
// Licensed under GNU General Public License v3.0
|
2022-10-04 13:21:05 +08:00
|
|
|
|
//
|
|
|
|
|
//----------------------------------------
|
|
|
|
|
|
|
|
|
|
package cef
|
|
|
|
|
|
|
|
|
|
import (
|
2022-10-04 22:34:57 +08:00
|
|
|
|
"bytes"
|
|
|
|
|
"encoding/binary"
|
2022-11-02 12:47:47 +08:00
|
|
|
|
. "github.com/energye/energy/common"
|
2022-10-04 22:34:57 +08:00
|
|
|
|
. "github.com/energye/energy/consts"
|
|
|
|
|
"github.com/energye/energy/ipc"
|
2022-10-28 16:49:35 +08:00
|
|
|
|
"github.com/energye/energy/logger"
|
2022-10-04 13:21:05 +08:00
|
|
|
|
"github.com/energye/golcl/lcl/api"
|
|
|
|
|
"net"
|
|
|
|
|
"reflect"
|
|
|
|
|
"strings"
|
|
|
|
|
"unsafe"
|
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
const (
|
|
|
|
|
IPC_FN_TYPE_IPCJSEmitGo = 1 // JS fires the Go registerEvent
|
|
|
|
|
IPC_FN_TYPE_IPCGoEmitJSRet = 2 // Go fires the JS registerEvent
|
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
var (
|
2022-12-07 15:50:59 +08:00
|
|
|
|
//TODO 注释后面改
|
|
|
|
|
//setCefIPCCallbackFunc *dylib.LazyProc
|
2022-10-04 13:21:05 +08:00
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
type rGoResult struct {
|
|
|
|
|
value uintptr //Pointer
|
|
|
|
|
valueType uintptr //PInteger
|
|
|
|
|
valueLength uintptr //PInteger
|
|
|
|
|
bindType uintptr //PInteger
|
|
|
|
|
exception uintptr //PInteger
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func (m *rGoResult) set(value, valueType, valueLength, bindType, exception uintptr) {
|
|
|
|
|
m.value = value
|
|
|
|
|
m.valueType = valueType
|
|
|
|
|
m.valueLength = valueLength
|
|
|
|
|
m.bindType = bindType
|
|
|
|
|
m.exception = exception
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
type rIPCEventParam struct {
|
|
|
|
|
BrowserId int32
|
|
|
|
|
IPCId int32
|
|
|
|
|
FullName uintptr //string
|
|
|
|
|
FrameId uintptr //string
|
|
|
|
|
ParamType int32 //js中ipc.emit参数类型: 1:没有入参和回调函数 2:有入参 没有回调函数 3:没有入参 有回调函数 4:有入参 有回调函数
|
|
|
|
|
ValueTypeArrLen int32 //参数个数
|
|
|
|
|
ValueTypeArr uintptr //ValueTypeArr: array of byte;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func cefIPCInit() {
|
2022-12-07 15:50:59 +08:00
|
|
|
|
//TODO 注释后面改
|
|
|
|
|
//setCefIPCCallbackFunc = api.GetLibLCL().NewProc("SetCEFIPCCallbackFunc")
|
|
|
|
|
//setCefIPCCallbackFunc.Call(cefIPCCallbackFuncEvent)
|
2022-10-04 13:21:05 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func cefIPCEventProc(fnType uintptr, args uintptr, argsLen int) uintptr {
|
2022-10-28 16:49:35 +08:00
|
|
|
|
defer func() {
|
|
|
|
|
if err := recover(); err != nil {
|
|
|
|
|
logger.Error("IPCEventProc Error:", err)
|
|
|
|
|
}
|
|
|
|
|
}()
|
2022-10-04 13:21:05 +08:00
|
|
|
|
getVal := func(i int) uintptr {
|
2022-10-04 22:34:57 +08:00
|
|
|
|
return GetParamOf(i, args)
|
2022-10-04 13:21:05 +08:00
|
|
|
|
}
|
|
|
|
|
getPtr := func(i int) unsafe.Pointer {
|
|
|
|
|
return unsafe.Pointer(getVal(i))
|
|
|
|
|
}
|
|
|
|
|
if fnType == IPC_FN_TYPE_IPCJSEmitGo {
|
|
|
|
|
eventParam := (*rIPCEventParam)(getPtr(0))
|
|
|
|
|
result := (*rGoResult)(getPtr(1))
|
|
|
|
|
if eventParam == nil || result == nil {
|
|
|
|
|
return 0
|
|
|
|
|
}
|
|
|
|
|
ipcJSEmitGo(eventParam, result, args)
|
|
|
|
|
} else if fnType == IPC_FN_TYPE_IPCGoEmitJSRet {
|
|
|
|
|
ipcId := *(*int32)(getPtr(0))
|
|
|
|
|
tmType := *(*int32)(getPtr(1))
|
|
|
|
|
result := (*rGoResult)(getPtr(2))
|
2022-10-04 22:34:57 +08:00
|
|
|
|
ipcGoEmitJS(ipcId, TriggerMode(tmType), result, args)
|
2022-10-04 13:21:05 +08:00
|
|
|
|
result.set(0, 0, 0, 0, 0)
|
|
|
|
|
result = nil
|
|
|
|
|
}
|
|
|
|
|
return 0
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//ipc - go emit js on event
|
2022-10-04 22:34:57 +08:00
|
|
|
|
func ipcGoEmitJS(ipcId int32, triggerMode TriggerMode, result *rGoResult, args uintptr) {
|
|
|
|
|
inArgument := ipc.NewArgumentList()
|
2022-10-04 13:21:05 +08:00
|
|
|
|
inArgument.SetBool(1, true)
|
|
|
|
|
if CEF_V8_EXCEPTION(result.exception) == CVE_ERROR_OK {
|
|
|
|
|
switch V8_JS_VALUE_TYPE(result.valueType) {
|
|
|
|
|
case V8_VALUE_STRING:
|
2022-12-03 21:56:51 +08:00
|
|
|
|
inArgument.SetString(0, api.GoStr(result.value))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
case V8_VALUE_INT:
|
|
|
|
|
inArgument.SetInt32(0, int32(result.value))
|
|
|
|
|
case V8_VALUE_DOUBLE:
|
2022-10-04 22:34:57 +08:00
|
|
|
|
inArgument.SetFloat64(0, *(*float64)(GetParamPtr(result.value, 0)))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
case V8_VALUE_BOOLEAN:
|
2022-10-04 22:34:57 +08:00
|
|
|
|
inArgument.SetBool(0, *(*bool)(GetParamPtr(result.value, 0)))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
default:
|
|
|
|
|
inArgument.SetBool(1, false)
|
|
|
|
|
inArgument.SetString(0, "不支持的数据类型")
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
inArgument.SetBool(1, false)
|
2022-12-03 21:56:51 +08:00
|
|
|
|
inArgument.SetString(0, api.GoStr(result.value))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
}
|
2022-10-04 22:34:57 +08:00
|
|
|
|
if triggerMode == Tm_Callback { //回调函数
|
|
|
|
|
if callback, ok := executeJS.emitCallback.EmitCollection.Load(ipcId); ok {
|
|
|
|
|
executeJS.emitCallback.EmitCollection.Delete(ipcId)
|
2022-10-30 00:35:04 +08:00
|
|
|
|
ctx := ipc.NewIPCContext("", 0, 0, 0, nil, nil, &ipc.IPCContextResult{}, inArgument)
|
2022-10-04 22:34:57 +08:00
|
|
|
|
callback.(ipc.IPCCallback)(ctx)
|
2022-10-04 13:21:05 +08:00
|
|
|
|
ctx.Free()
|
|
|
|
|
}
|
2022-10-04 22:34:57 +08:00
|
|
|
|
} else if triggerMode == Tm_Sync { //同步调用
|
|
|
|
|
if chn, ok := executeJS.emitSync.EmitCollection.Load(ipcId); ok {
|
2022-10-30 00:35:04 +08:00
|
|
|
|
ctx := ipc.NewIPCContext("", 0, 0, 0, nil, nil, &ipc.IPCContextResult{}, inArgument)
|
2022-10-04 22:34:57 +08:00
|
|
|
|
var c = chn.(chan ipc.IIPCContext)
|
2022-10-04 13:21:05 +08:00
|
|
|
|
c <- ctx
|
|
|
|
|
close(c)
|
2022-10-04 22:34:57 +08:00
|
|
|
|
executeJS.emitSync.EmitCollection.Delete(ctx.EventId())
|
2022-10-04 13:21:05 +08:00
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//ipc - js emit go on event
|
|
|
|
|
func ipcJSEmitGo(eventParam *rIPCEventParam, result *rGoResult, args uintptr) {
|
|
|
|
|
getVal := func(i int) uintptr {
|
2022-10-04 22:34:57 +08:00
|
|
|
|
return GetParamOf(i, args)
|
2022-10-04 13:21:05 +08:00
|
|
|
|
}
|
|
|
|
|
getPtr := func(i int) unsafe.Pointer {
|
|
|
|
|
return unsafe.Pointer(getVal(i))
|
|
|
|
|
}
|
|
|
|
|
var (
|
2022-10-04 22:34:57 +08:00
|
|
|
|
inArgument = ipc.NewArgumentList()
|
2022-12-03 21:56:51 +08:00
|
|
|
|
fullName = api.GoStr(eventParam.FullName)
|
2022-10-04 13:21:05 +08:00
|
|
|
|
valueTypeLen = eventParam.ValueTypeArrLen //入参类型数组
|
|
|
|
|
accIdx = 2 //占用的下标
|
|
|
|
|
)
|
|
|
|
|
if valueTypeLen > 0 {
|
|
|
|
|
//取入参
|
|
|
|
|
for i := 0; i < int(valueTypeLen); i++ {
|
2022-10-04 22:34:57 +08:00
|
|
|
|
valueType := V8_JS_VALUE_TYPE(*(*byte)(GetParamPtr(eventParam.ValueTypeArr, i)))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
switch valueType {
|
|
|
|
|
case V8_VALUE_STRING:
|
2022-12-03 21:56:51 +08:00
|
|
|
|
inArgument.SetString(i, api.GoStr(getVal(i+accIdx)))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
case V8_VALUE_INT:
|
|
|
|
|
inArgument.SetInt32(i, int32(getVal(i+accIdx)))
|
|
|
|
|
case V8_VALUE_DOUBLE:
|
|
|
|
|
inArgument.SetFloat64(i, *(*float64)(getPtr(i + accIdx)))
|
|
|
|
|
case V8_VALUE_BOOLEAN:
|
2022-12-03 21:56:51 +08:00
|
|
|
|
inArgument.SetBool(i, api.GoBool(getVal(i+accIdx)))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//检索v8绑定
|
|
|
|
|
bindType, name, vType, _, exception := searchBindV8Value(fullName)
|
|
|
|
|
if exception == CVE_ERROR_OK {
|
|
|
|
|
if vType == V8_VALUE_OBJECT || vType == V8_VALUE_ROOT_OBJECT {
|
2022-12-03 21:56:51 +08:00
|
|
|
|
result.set(api.PascalStr(name), uintptr(vType), 0, uintptr(bindType), uintptr(CVE_ERROR_OK))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
} else {
|
|
|
|
|
if bindType == IS_OBJECT {
|
|
|
|
|
name = name[len(objectRootName)+1:]
|
|
|
|
|
}
|
2022-10-04 22:34:57 +08:00
|
|
|
|
if jsValue, ok := VariableBind.GetValueBind(name); ok {
|
|
|
|
|
jsValue.Lock()
|
|
|
|
|
defer jsValue.UnLock()
|
2022-10-04 13:21:05 +08:00
|
|
|
|
if jsValue.ValueType() == V8_VALUE_FUNCTION { //func
|
|
|
|
|
var fnInfo = jsValue.getFuncInfo()
|
|
|
|
|
if fnInfo != nil {
|
|
|
|
|
inArgumentAdapter(0, inArgument, fnInfo)
|
|
|
|
|
var outParams, ok = jsValue.invoke(inArgument.ToReflectValue())
|
|
|
|
|
if ok {
|
|
|
|
|
if eventParam.ParamType > 2 {
|
|
|
|
|
var tmpOutParams = make([]reflect.Value, 1)
|
|
|
|
|
if fnInfo.OutNum > 0 {
|
|
|
|
|
tmpOutParams[0] = outParams[fnInfo.OutParamIdx]
|
|
|
|
|
inArgument.ReflectValueConvert(tmpOutParams) //出参转换
|
|
|
|
|
data := inArgument.GetData(0)
|
|
|
|
|
switch GO_VALUE_TYPE(data.VType()) {
|
|
|
|
|
case GO_VALUE_STRING:
|
2022-12-03 21:56:51 +08:00
|
|
|
|
result.set(api.PascalStr(data.GetString()), uintptr(V8_VALUE_STRING), 0, uintptr(bindType), uintptr(CVE_ERROR_OK))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
case GO_VALUE_INT, GO_VALUE_INT8, GO_VALUE_INT16, GO_VALUE_INT32, GO_VALUE_INT64, GO_VALUE_UINT, GO_VALUE_UINT8, GO_VALUE_UINT16, GO_VALUE_UINT32, GO_VALUE_UINT64, GO_VALUE_UINTPTR:
|
|
|
|
|
result.set(uintptr(data.GetInt32()), uintptr(V8_VALUE_INT), 0, uintptr(bindType), uintptr(CVE_ERROR_OK))
|
|
|
|
|
case GO_VALUE_FLOAT32, GO_VALUE_FLOAT64:
|
|
|
|
|
var ret = data.GetDouble()
|
|
|
|
|
result.set(uintptr(unsafe.Pointer(&ret)), uintptr(V8_VALUE_DOUBLE), 0, uintptr(bindType), uintptr(CVE_ERROR_OK))
|
|
|
|
|
case GO_VALUE_BOOL:
|
2022-12-03 21:56:51 +08:00
|
|
|
|
result.set(api.PascalBool(data.GetBool()), uintptr(V8_VALUE_BOOLEAN), 0, uintptr(bindType), uintptr(CVE_ERROR_OK))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
//没有出参
|
|
|
|
|
result.set(0, uintptr(V8_NO_OUT_VALUE), 0, uintptr(bindType), uintptr(CVE_ERROR_OK))
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
} else {
|
2022-12-03 21:56:51 +08:00
|
|
|
|
result.set(api.PascalStr(outParams[0].Interface().(string)), uintptr(V8_VALUE_STRING), 0, uintptr(bindType), uintptr(CVE_ERROR_UNKNOWN_ERROR))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
} else { //field
|
|
|
|
|
inArgs := inArgument.Items()
|
|
|
|
|
if inArgs != nil && len(inArgs) > 0 {
|
|
|
|
|
var (
|
|
|
|
|
errorMsg string
|
|
|
|
|
oldValuePtr unsafe.Pointer
|
|
|
|
|
err error
|
|
|
|
|
)
|
|
|
|
|
//字段赋值
|
|
|
|
|
fieldNewValue := inArgs[0]
|
|
|
|
|
oldValuePtr, err = jsValue.ValueToPtr()
|
|
|
|
|
if err != nil {
|
|
|
|
|
errorMsg = cefErrorMessage(CVE_ERROR_TYPE_NOT_SUPPORTED)
|
|
|
|
|
} else {
|
|
|
|
|
if fieldNewValue.IsString() {
|
2022-11-29 20:04:08 +08:00
|
|
|
|
errorMsg = cefErrorMessage(setPtrValue(jsValue, V8_VALUE_STRING, fieldNewValue.GetString(), 0, 0, false))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
} else if fieldNewValue.IsIntAuto() {
|
2022-11-29 20:04:08 +08:00
|
|
|
|
errorMsg = cefErrorMessage(setPtrValue(jsValue, V8_VALUE_INT, Empty, fieldNewValue.GetInt32(), 0, false))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
} else if fieldNewValue.IsFloatAuto() {
|
2022-11-29 20:04:08 +08:00
|
|
|
|
errorMsg = cefErrorMessage(setPtrValue(jsValue, V8_VALUE_DOUBLE, Empty, 0, fieldNewValue.GetFloat64(), false))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
} else if fieldNewValue.IsBoolean() {
|
2022-11-29 20:04:08 +08:00
|
|
|
|
errorMsg = cefErrorMessage(setPtrValue(jsValue, V8_VALUE_BOOLEAN, Empty, 0, 0, fieldNewValue.GetBool()))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
} else {
|
|
|
|
|
errorMsg = cefErrorMessage(CVE_ERROR_TYPE_NOT_SUPPORTED)
|
|
|
|
|
}
|
|
|
|
|
}
|
2022-10-04 22:34:57 +08:00
|
|
|
|
if Empty == errorMsg {
|
2022-10-04 13:21:05 +08:00
|
|
|
|
result.set(uintptr(oldValuePtr), uintptr(jsValue.ValueType()), 0, uintptr(bindType), uintptr(CVE_ERROR_OK))
|
|
|
|
|
} else {
|
2022-12-03 21:56:51 +08:00
|
|
|
|
result.set(api.PascalStr(errorMsg), uintptr(V8_VALUE_STRING), 0, uintptr(bindType), uintptr(CVE_ERROR_TYPE_NOT_SUPPORTED))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
//字段取值
|
|
|
|
|
switch jsValue.ValueType() {
|
|
|
|
|
case V8_VALUE_STRING, V8_VALUE_INT, V8_VALUE_DOUBLE, V8_VALUE_BOOLEAN:
|
|
|
|
|
var ret, err = jsValue.ValueToPtr()
|
|
|
|
|
if err != nil {
|
|
|
|
|
result.set(0, 0, 0, uintptr(bindType), uintptr(CVE_ERROR_TYPE_NOT_SUPPORTED))
|
|
|
|
|
} else {
|
|
|
|
|
result.set(uintptr(ret), uintptr(jsValue.ValueType()), 0, uintptr(bindType), uintptr(CVE_ERROR_OK))
|
|
|
|
|
}
|
|
|
|
|
default:
|
|
|
|
|
result.set(0, 0, 0, uintptr(bindType), uintptr(CVE_ERROR_TYPE_NOT_SUPPORTED))
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
result.set(0, 0, 0, 0, uintptr(CVE_ERROR_NOT_FOUND_FIELD))
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
//尝试触发用户自定义 ipc fullName emit
|
2022-10-04 22:34:57 +08:00
|
|
|
|
if callback := ipc.IPC.Browser().Events().Get(fullName); callback != nil {
|
2022-10-04 13:21:05 +08:00
|
|
|
|
var (
|
2022-12-03 21:56:51 +08:00
|
|
|
|
channelId = StrToInt64(api.GoStr(eventParam.FrameId))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
ipcType IPC_TYPE
|
2022-10-30 00:35:04 +08:00
|
|
|
|
conn net.Conn
|
2022-10-04 13:21:05 +08:00
|
|
|
|
)
|
2022-10-04 22:34:57 +08:00
|
|
|
|
if chn := ipc.IPC.Browser().Channel(channelId); chn != nil {
|
|
|
|
|
ipcType = chn.IPCType
|
2022-10-30 00:35:04 +08:00
|
|
|
|
conn = chn.Conn
|
2022-10-04 13:21:05 +08:00
|
|
|
|
}
|
2022-10-30 00:35:04 +08:00
|
|
|
|
ctx := ipc.NewIPCContext(fullName, eventParam.BrowserId, channelId, ipcType, conn, &ipc.IPCEventMessage{}, &ipc.IPCContextResult{}, inArgument)
|
2022-10-04 13:21:05 +08:00
|
|
|
|
callback(ctx)
|
2022-10-04 22:34:57 +08:00
|
|
|
|
result.set(uintptr(ctx.Result().Result()), uintptr(ctx.Result().VType()), 0, uintptr(IS_COMMON), uintptr(CVE_ERROR_OK))
|
2022-10-04 13:21:05 +08:00
|
|
|
|
} else {
|
|
|
|
|
result.set(0, 0, 0, 0, uintptr(CVE_ERROR_NOT_FOUND_FIELD))
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//检索绑定的JsValue
|
|
|
|
|
//返回值
|
|
|
|
|
// bindType 绑定类型 0通用类型,1对象类型
|
|
|
|
|
// fullName 绑定全名称
|
|
|
|
|
// vType js绑定值类型
|
|
|
|
|
// eventID 事件ID
|
|
|
|
|
// exception 错误码
|
|
|
|
|
func searchBindV8Value(fullName string) (IS_CO, string, V8_JS_VALUE_TYPE, int32, CEF_V8_EXCEPTION) {
|
|
|
|
|
if fullName == "" {
|
|
|
|
|
return 0, "", 0, 0, CVE_ERROR_NOT_FOUND_FIELD
|
|
|
|
|
}
|
|
|
|
|
var fnArr = strings.Split(fullName, ".")
|
|
|
|
|
var fnArrLen = len(fnArr)
|
|
|
|
|
if len(fnArr) > 0 && fnArr[0] == "window" {
|
|
|
|
|
fnArr = fnArr[1:]
|
|
|
|
|
fnArrLen = len(fnArr)
|
|
|
|
|
}
|
|
|
|
|
if fnArrLen == 0 {
|
|
|
|
|
return 0, "", 0, 0, CVE_ERROR_NOT_FOUND_FIELD
|
|
|
|
|
}
|
|
|
|
|
//对象类型
|
|
|
|
|
if fnArr[0] == commonRootName {
|
|
|
|
|
if fnArrLen == 1 { //commonRootObject 对象
|
|
|
|
|
fullName = strings.Join(fnArr, ".")
|
|
|
|
|
return IS_COMMON, fullName, V8_VALUE_ROOT_OBJECT, 0, CVE_ERROR_OK
|
|
|
|
|
} else if fnArrLen == 2 {
|
2022-10-04 22:34:57 +08:00
|
|
|
|
if jsValue, ok := VariableBind.GetValueBind(fnArr[1]); ok { //通用类型 fnArr[1] 1是因为 obj.field ,这个field 就是1
|
2022-10-04 13:21:05 +08:00
|
|
|
|
return IS_COMMON, jsValue.Name(), jsValue.ValueType(), int32(jsValue.getEventId()), CVE_ERROR_OK
|
|
|
|
|
} else {
|
|
|
|
|
//不存在
|
|
|
|
|
return 0, "", 0, 0, CVE_ERROR_NOT_FOUND_FIELD
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
//不正确的变量名或不存在
|
|
|
|
|
return 0, "", 0, 0, CVE_ERROR_NOT_FOUND_FIELD
|
|
|
|
|
}
|
|
|
|
|
} else if fnArr[0] == objectRootName {
|
|
|
|
|
if fnArrLen == 1 {
|
|
|
|
|
//objectRootObject对象
|
|
|
|
|
fullName = strings.Join(fnArr, ".")
|
|
|
|
|
return IS_OBJECT, fullName, V8_VALUE_ROOT_OBJECT, 0, CVE_ERROR_OK
|
|
|
|
|
}
|
|
|
|
|
//对象类型查找关系
|
|
|
|
|
var preObj *structObjectInfo
|
|
|
|
|
var subObj = objectSti.StructsObject
|
|
|
|
|
var faLen = len(fnArr)
|
|
|
|
|
for i := 0; i < faLen; i++ {
|
|
|
|
|
if obj, ok := subObj[fnArr[i]]; ok {
|
|
|
|
|
subObj = obj.SubStructObjectInfo
|
|
|
|
|
preObj = obj
|
|
|
|
|
} else if i > 0 && i+1 < faLen {
|
|
|
|
|
return 0, "", 0, 0, CVE_ERROR_NOT_FOUND_FIELD
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
if preObj != nil {
|
|
|
|
|
var fieldName = fnArr[fnArrLen-1]
|
|
|
|
|
fullName = strings.Join(fnArr, ".")
|
|
|
|
|
if preObj.ObjName == fieldName {
|
|
|
|
|
//返回object Obj对象
|
|
|
|
|
return IS_OBJECT, fullName, V8_VALUE_OBJECT, 0, CVE_ERROR_OK
|
|
|
|
|
} else {
|
|
|
|
|
//字段 或 函数
|
|
|
|
|
if fieldInfo, ok := preObj.FieldsInfo[fieldName]; ok {
|
|
|
|
|
return IS_OBJECT, fullName, fieldInfo.ValueType.Jsv, int32(fieldInfo.EventId), CVE_ERROR_OK
|
|
|
|
|
} else if fnInfo, ok := preObj.FuncsInfo[fieldName]; ok {
|
|
|
|
|
return IS_OBJECT, fullName, V8_VALUE_FUNCTION, int32(fnInfo.EventId), CVE_ERROR_OK
|
|
|
|
|
}
|
|
|
|
|
return 0, "", 0, 0, CVE_ERROR_NOT_FOUND_FIELD
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
return 0, "", 0, 0, CVE_ERROR_NOT_FOUND_FIELD
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
return 0, "", 0, 0, CVE_ERROR_NOT_FOUND_FIELD
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
2022-10-04 22:34:57 +08:00
|
|
|
|
func inArgumentAdapter(argsIdxOffset int, inArgument ipc.IArgumentList, fnInfo *funcInfo) {
|
2022-10-04 13:21:05 +08:00
|
|
|
|
items := inArgument.Items()
|
|
|
|
|
inParamType := fnInfo.InParam
|
|
|
|
|
for i := argsIdxOffset; i < inArgument.Size(); i++ {
|
|
|
|
|
if items[i].IsIntAuto() && inParamType[i-argsIdxOffset].IsGoIntAuto() {
|
|
|
|
|
inArgument.SetIntAuto(i, items[i].GetInt32(), fnInfo.InParam[i-argsIdxOffset].Gov)
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2022-10-04 22:34:57 +08:00
|
|
|
|
func outArgumentAdapter(argsIdxOffset int, outArgument ipc.IArgumentList, fnInfo *funcInfo) {
|
2022-10-04 13:21:05 +08:00
|
|
|
|
items := outArgument.Items()
|
|
|
|
|
outParamType := fnInfo.OutParam
|
|
|
|
|
for i := argsIdxOffset; i < outArgument.Size(); i++ {
|
|
|
|
|
if items[i].IsIntAuto() && outParamType[i-argsIdxOffset].IsGoIntAuto() {
|
|
|
|
|
outArgument.SetIntAuto(i, items[i].GetInt32(), fnInfo.InParam[i-argsIdxOffset].Gov)
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
2022-10-04 22:34:57 +08:00
|
|
|
|
|
|
|
|
|
func internalBrowserIPCOnEventInit() {
|
|
|
|
|
var ipcJsBindGetValueSuccess = func(buf *bytes.Buffer, valueType int8, data []byte) {
|
|
|
|
|
//rec
|
|
|
|
|
// eventID []byte 4bit
|
|
|
|
|
//ret
|
|
|
|
|
// isSuccess []byte 1bit
|
|
|
|
|
// valueType []byte 1bit
|
|
|
|
|
// value []byte MaxInt32bit
|
|
|
|
|
binary.Write(buf, binary.BigEndian, true) //成功
|
|
|
|
|
binary.Write(buf, binary.BigEndian, valueType) //字段类型
|
|
|
|
|
binary.Write(buf, binary.BigEndian, data) //字段值
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
var ipcJsBindGetValueFail = func(buf *bytes.Buffer, err CEF_V8_EXCEPTION) {
|
|
|
|
|
binary.Write(buf, binary.BigEndian, false) //失败
|
|
|
|
|
binary.Write(buf, binary.BigEndian, int8(err))
|
|
|
|
|
}
|
|
|
|
|
//var occIdx = ipcAccIdx
|
|
|
|
|
//主进程监听回调
|
|
|
|
|
ipc.IPC.Browser().SetOnEvent(func(event ipc.IEventOn) {
|
|
|
|
|
//var fieldReadWriteLock = new(sync.Mutex)
|
|
|
|
|
//获取字段值-同步
|
|
|
|
|
event.On(ipc.Ln_GET_BIND_FIELD_VALUE, func(context ipc.IIPCContext) {
|
|
|
|
|
args := context.Arguments()
|
|
|
|
|
defer args.Clear()
|
|
|
|
|
fullName := args.GetString(0)
|
|
|
|
|
var jsValue, ok = VariableBind.GetValueBind(fullName)
|
|
|
|
|
buf := &bytes.Buffer{}
|
|
|
|
|
defer buf.Reset()
|
|
|
|
|
if ok {
|
|
|
|
|
jsValue.Lock()
|
|
|
|
|
defer jsValue.UnLock()
|
|
|
|
|
var valueType = int8(jsValue.ValueType())
|
|
|
|
|
ipcJsBindGetValueSuccess(buf, valueType, jsValue.Bytes())
|
|
|
|
|
} else {
|
|
|
|
|
ipcJsBindGetValueFail(buf, CVE_ERROR_NOT_FOUND_FIELD)
|
|
|
|
|
}
|
|
|
|
|
context.Response(buf.Bytes())
|
|
|
|
|
buf = nil
|
|
|
|
|
context.Free()
|
|
|
|
|
})
|
|
|
|
|
//设置字段值-同步
|
|
|
|
|
event.On(ipc.Ln_SET_BIND_FIELD_VALUE, func(context ipc.IIPCContext) {
|
|
|
|
|
args := context.Arguments()
|
|
|
|
|
defer args.Clear()
|
|
|
|
|
fullName := args.GetString(0)
|
|
|
|
|
item := args.Item(1)
|
|
|
|
|
newValueType := item.VTypeToJS()
|
|
|
|
|
jsValue, ok := VariableBind.GetValueBind(fullName)
|
|
|
|
|
isSuccess := false
|
|
|
|
|
retArgs := ipc.NewArgumentList()
|
|
|
|
|
defer retArgs.Clear()
|
|
|
|
|
if ok {
|
|
|
|
|
jsValue.Lock()
|
|
|
|
|
defer jsValue.UnLock()
|
|
|
|
|
switch newValueType { //设置值,这里是通用类型只需要知道js里设置的什么类型即可
|
|
|
|
|
case V8_VALUE_STRING:
|
2022-11-29 20:04:08 +08:00
|
|
|
|
isSuccess = Empty == cefErrorMessage(setPtrValue(jsValue, newValueType, item.GetString(), 0, 0, false))
|
2022-10-04 22:34:57 +08:00
|
|
|
|
case V8_VALUE_INT:
|
2022-11-29 20:04:08 +08:00
|
|
|
|
isSuccess = Empty == cefErrorMessage(setPtrValue(jsValue, newValueType, Empty, item.GetInt32(), 0, false))
|
2022-10-04 22:34:57 +08:00
|
|
|
|
case V8_VALUE_DOUBLE:
|
2022-11-29 20:04:08 +08:00
|
|
|
|
isSuccess = Empty == cefErrorMessage(setPtrValue(jsValue, newValueType, Empty, 0, item.GetFloat64(), false))
|
2022-10-04 22:34:57 +08:00
|
|
|
|
case V8_VALUE_BOOLEAN:
|
2022-11-29 20:04:08 +08:00
|
|
|
|
isSuccess = Empty == cefErrorMessage(setPtrValue(jsValue, newValueType, Empty, 0, 0, item.GetBool()))
|
2022-10-04 22:34:57 +08:00
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
retArgs.SetInt8(1, int8(CVE_ERROR_NOT_FOUND_FIELD))
|
|
|
|
|
}
|
|
|
|
|
retArgs.SetBool(0, isSuccess)
|
|
|
|
|
context.Response(retArgs.Package())
|
|
|
|
|
context.Free()
|
|
|
|
|
})
|
|
|
|
|
//执行函数-同步
|
|
|
|
|
event.On(ipc.Ln_EXECUTE_BIND_FUNC, func(context ipc.IIPCContext) {
|
|
|
|
|
args := context.Arguments()
|
|
|
|
|
fullName := args.GetString(args.Size() - 1)
|
|
|
|
|
dataItems := args.RangeItems(0, args.Size()-1)
|
|
|
|
|
var inArgument = ipc.NewArgumentList()
|
|
|
|
|
inArgument.SetItems(dataItems)
|
|
|
|
|
var jsValue, ok = VariableBind.GetValueBind(fullName)
|
|
|
|
|
var (
|
|
|
|
|
outParams []reflect.Value
|
|
|
|
|
isSuccess bool
|
|
|
|
|
)
|
|
|
|
|
var buf = &bytes.Buffer{}
|
|
|
|
|
defer buf.Reset()
|
|
|
|
|
if ok {
|
|
|
|
|
jsValue.Lock()
|
|
|
|
|
defer jsValue.UnLock()
|
|
|
|
|
var fnInfo = jsValue.getFuncInfo()
|
|
|
|
|
if fnInfo != nil {
|
|
|
|
|
outParams, isSuccess = jsValue.invoke(inArgument.ToReflectValue())
|
|
|
|
|
inArgument.Clear()
|
|
|
|
|
var outArguments = ipc.NewArgumentList()
|
|
|
|
|
outArguments.ReflectValueConvert(outParams)
|
|
|
|
|
binary.Write(buf, binary.BigEndian, isSuccess)
|
|
|
|
|
binary.Write(buf, binary.BigEndian, outArguments.Package())
|
|
|
|
|
outArguments.Clear()
|
|
|
|
|
} else {
|
|
|
|
|
binary.Write(buf, binary.BigEndian, isSuccess)
|
|
|
|
|
binary.Write(buf, binary.BigEndian, int8(CVE_ERROR_NOT_FOUND_FUNC))
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
binary.Write(buf, binary.BigEndian, isSuccess)
|
|
|
|
|
binary.Write(buf, binary.BigEndian, int8(CVE_ERROR_NOT_FOUND_FUNC))
|
|
|
|
|
}
|
|
|
|
|
context.Response(buf.Bytes())
|
|
|
|
|
buf = nil
|
|
|
|
|
args.Clear()
|
|
|
|
|
context.Free()
|
|
|
|
|
})
|
|
|
|
|
})
|
|
|
|
|
}
|