Commit 4411204b authored by Scott Graham's avatar Scott Graham Committed by Commit Bot

fuchsia: Beginnings of FIDL JS bindings

This is the very initial stages of writing a bindings generator to allow
interop to/from JS with FIDL.

The main pieces are:
- the build time generator which consumes the JSON IR from `fidlc` and
  outputs a fidl.js
- integration with gn in fidl_library.gni
- a JS runtime support library (mostly helps with message encoding)
- new unittest binary (which also currently holds some Zircon
  integration points that will eventually be moved to a C++ runtime
  support library.)

There are many, many things it does not yet handle, e.g. responses
(either sync or async), events, passing structs, passing unions, ...

For reference, test/simple.fidl generates this
https://gist.github.com/sgraham/3935c64d5bc1b67eea1f6e3b38fef6f1


Bug: 883496
Change-Id: I58e5d2b81213f20a3198b68cbd2bc01660ba58f7
Reviewed-on: https://chromium-review.googlesource.com/c/1222697Reviewed-by: default avatarJeremy Roman <jbroman@chromium.org>
Reviewed-by: default avatarAdam Klein <adamk@chromium.org>
Reviewed-by: default avatarWez <wez@chromium.org>
Commit-Queue: Scott Graham <scottmg@chromium.org>
Cr-Commit-Position: refs/heads/master@{#596329}
parent 0aa1d243
...@@ -216,7 +216,10 @@ group("gn_all") { ...@@ -216,7 +216,10 @@ group("gn_all") {
} else if (is_ios) { } else if (is_ios) {
deps += [ "//ios:all" ] deps += [ "//ios:all" ]
} else if (is_fuchsia) { } else if (is_fuchsia) {
deps += [ ":d8_fuchsia" ] deps += [
":d8_fuchsia",
"tools/fuchsia/fidlgen_js:fidlgen_js_unittests",
]
} }
deps += root_extra_deps deps += root_extra_deps
......
...@@ -14,12 +14,14 @@ assert(is_fuchsia) ...@@ -14,12 +14,14 @@ assert(is_fuchsia)
# namespace - (optional) Namespace for the library. # namespace - (optional) Namespace for the library.
# deps - (optional) List of other fidl_library() targets that this # deps - (optional) List of other fidl_library() targets that this
# FIDL library depends on. # FIDL library depends on.
# languages - Generate bindings for the given languages, defaults to
# [ "cpp" ]. "js" also supported.
# #
# $namespace.$library_name must match the the library name specified in the FIDL # $namespace.$library_name must match the the library name specified in the FIDL
# files. # files.
template("fidl_library") { template("fidl_library") {
forward_variables_from(invoker, [ "namespace" ]) forward_variables_from(invoker, [ "namespace", "languages" ])
_library_basename = target_name _library_basename = target_name
if (defined(invoker.library_name)) { if (defined(invoker.library_name)) {
...@@ -35,6 +37,10 @@ template("fidl_library") { ...@@ -35,6 +37,10 @@ template("fidl_library") {
_library_path = _library_basename _library_path = _library_basename
} }
if (!defined(invoker.languages)) {
languages = [ "cpp" ]
}
_response_file = "$target_gen_dir/$target_name.rsp" _response_file = "$target_gen_dir/$target_name.rsp"
_json_representation = "$target_gen_dir/${_library_name}.fidl.json" _json_representation = "$target_gen_dir/${_library_name}.fidl.json"
_output_gen_dir = "$target_gen_dir/fidl" _output_gen_dir = "$target_gen_dir/fidl"
...@@ -131,6 +137,7 @@ template("fidl_library") { ...@@ -131,6 +137,7 @@ template("fidl_library") {
action("${target_name}_cpp_gen") { action("${target_name}_cpp_gen") {
visibility = [ ":${invoker.target_name}" ] visibility = [ ":${invoker.target_name}" ]
forward_variables_from(invoker, [ "testonly" ])
deps = [ deps = [
":${invoker.target_name}_compile", ":${invoker.target_name}_compile",
...@@ -162,6 +169,40 @@ template("fidl_library") { ...@@ -162,6 +169,40 @@ template("fidl_library") {
] ]
} }
_output_js_path = "$_output_gen_dir/${_library_path}/js/fidl.js"
action("${target_name}_js_gen") {
visibility = [ ":${invoker.target_name}" ]
forward_variables_from(invoker, [ "testonly" ])
deps = [
":${invoker.target_name}_compile",
]
inputs = [
# Depend on the SDK hash, to ensure rebuild if the SDK tools change.
rebase_path("$fuchsia_sdk/.hash"),
_json_representation,
"//tools/fuchsia/fidlgen_js/fidl.py", # The schema helper file.
]
outputs = [
_output_js_path,
]
script = "//tools/fuchsia/fidlgen_js/gen.py"
args = [
rebase_path(_json_representation),
"--output",
rebase_path("${_output_js_path}"),
]
data = []
foreach(o, outputs) {
data += [ rebase_path(o) ]
}
}
config("${target_name}_config") { config("${target_name}_config") {
visibility = [ ":${invoker.target_name}" ] visibility = [ ":${invoker.target_name}" ]
include_dirs = [ _output_gen_dir ] include_dirs = [ _output_gen_dir ]
...@@ -185,10 +226,11 @@ template("fidl_library") { ...@@ -185,10 +226,11 @@ template("fidl_library") {
if (!defined(deps)) { if (!defined(deps)) {
deps = [] deps = []
} }
deps += [ deps += [ ":${invoker.target_name}_compile" ]
":${invoker.target_name}_compile",
":${invoker.target_name}_cpp_gen", foreach(language, languages) {
] deps += [ ":${invoker.target_name}_${language}_gen" ]
}
if (!defined(public_deps)) { if (!defined(public_deps)) {
public_deps = [] public_deps = []
......
# Copyright 2018 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
import("//build/config/fuchsia/fidl_library.gni")
import("//testing/test.gni")
test("fidlgen_js_unittests") {
testonly = true
sources = [
"test/fidlgen_js_unittest.cc",
]
deps = [
":fidljstest",
":runtime",
"//base/test:test_support",
"//gin:gin_test",
"//testing/gtest",
"//v8",
]
configs += [
"//tools/v8_context_snapshot:use_v8_context_snapshot",
"//v8:external_startup_data",
]
data_deps = [
"//tools/v8_context_snapshot:v8_context_snapshot",
]
data = [
"runtime/fidl.mjs",
]
}
static_library("runtime") {
sources = [
"runtime/zircon.cc",
"runtime/zircon.h",
]
deps = [
"//gin",
"//v8",
]
}
fidl_library("fidljstest") {
testonly = true
sources = [
"test/simple.fidl",
]
languages = [
"cpp",
"js",
]
}
include_rules = [
"+gin",
"+v8/include",
]
This diff is collapsed.
#!/usr/bin/env python
# Copyright 2018 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
import argparse
from fidl import *
import json
class _CompoundIdentifier(object):
def __init__(self, library, name):
self.library = library
self.name = name
def _ParseLibraryName(lib):
return lib.split('.')
def _ParseCompoundIdentifier(ident):
parts = ident.split('/', 2)
raw_library = ''
raw_name = parts[0]
if len(parts) == 2:
raw_library, raw_name = parts
library = _ParseLibraryName(raw_library)
return _CompoundIdentifier(library, raw_name)
def _ChangeIfReserved(name):
# TODO(crbug.com/883496): Remap any JS keywords.
return name
def _CompileCompoundIdentifier(compound, ext=''):
result = _ChangeIfReserved(compound.name) + ext
return result
def _CompileIdentifier(ident):
return _ChangeIfReserved(ident)
def _JsTypeForPrimitiveType(t):
mapping = {
IntegerType.INT16: 'number',
IntegerType.INT32: 'number',
IntegerType.INT64: 'BigInt',
IntegerType.INT8: 'number',
IntegerType.UINT16: 'number',
IntegerType.UINT32: 'number',
IntegerType.UINT64: 'BigInt',
IntegerType.UINT8: 'number',
}
return mapping[t]
def _InlineSizeOfType(t):
if t.kind == TypeKind.PRIMITIVE:
return {
'int16': 2,
'int32': 4,
'int64': 8,
'int8': 1,
'uint16': 2,
'uint32': 4,
'uint64': 8,
'uint8': 1,
}[t.subtype]
else:
raise NotImplementedError()
def _CompileConstant(val):
if val.kind == ConstantKind.IDENTIFIER:
raise NotImplementedError()
elif val.kind == ConstantKind.LITERAL:
return _CompileLiteral(val.literal)
else:
raise Exception('unexpected kind')
def _CompileLiteral(val):
if val.kind == LiteralKind.STRING:
# TODO(crbug.com/883496): This needs to encode the string in an escaped
# form suitable to JS. Currently using the escaped Python representation,
# which is passably compatible, but surely has differences in edge cases.
return repr(val.value)
elif val.kind == LiteralKind.NUMERIC:
return val.value
elif val.kind == LiteralKind.TRUE:
return 'true'
elif val.kind == LiteralKind.FALSE:
return 'false'
elif val.kind == LiteralKind.DEFAULT:
return 'default'
else:
raise Exception('unexpected kind')
class Compiler(object):
def __init__(self, fidl, output_file):
self.fidl = fidl
self.f = output_file
def Compile(self):
self._EmitHeader()
for c in self.fidl.const_declarations:
self._CompileConst(c)
for e in self.fidl.enum_declarations:
self._CompileEnum(e)
if self.fidl.union_declarations:
raise NotImplementedError()
if self.fidl.struct_declarations:
raise NotImplementedError()
for i in self.fidl.interface_declarations:
self._CompileInterface(i)
def _EmitHeader(self):
self.f.write('''// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
//
// WARNING: This file is machine generated by fidlgen_js.
''')
def _CompileConst(self, c):
self.f.write('''/**
* @const {%(type)s}
*/
const %(name)s = %(value)s;
''' % c.to_dict())
def _CompileEnum(self, enum):
compound = _ParseCompoundIdentifier(enum.name)
name = _CompileCompoundIdentifier(compound)
js_type = _JsTypeForPrimitiveType(enum.type)
data = { 'js_type': js_type, 'type': enum.type.value, 'name': name }
self.f.write('''/**
* @enum {%(js_type)s}
*/
const %(name)s = {
''' % data)
for member in enum.members:
self.f.write(''' %s: %s,\n''' %
(member.name, _CompileConstant(member.value)))
self.f.write('};\n')
self.f.write('const _kTT_%(name)s = _kTT_%(type)s;\n\n' % data)
def _CompileType(self, t):
if t.kind == TypeKind.PRIMITIVE:
return t.subtype
elif t.kind == TypeKind.STRING:
return 'String' + ('_Nullable' if t.nullable else '_Nonnull')
elif t.kind == TypeKind.IDENTIFIER:
compound = _ParseCompoundIdentifier(t.identifier)
name = _CompileCompoundIdentifier(compound)
return name
elif t.kind == TypeKind.VECTOR:
element_ttname = self._CompileType(t.element_type)
ttname = ('VEC_' + ('Nullable_' if t.nullable else 'Nonnull_') +
element_ttname)
throw_if_null = '/* v may be null */'
pointer_set = ''' if (v === null || v === undefined) {
e.data.setUint32(o + 8, 0, $fidl__kLE);
e.data.setUint32(o + 12, 0, $fidl__kLE);
} else {
e.data.setUint32(o + 8, 0xffffffff, $fidl__kLE);
e.data.setUint32(o + 12, 0xffffffff, $fidl__kLE);
}'''
if not t.nullable:
throw_if_null = ('if (v === null || v === undefined) '
'throw "non-null vector required";')
pointer_set = ''' e.data.setUint32(o + 8, 0xffffffff, $fidl__kLE);
e.data.setUint32(o + 12, 0xffffffff, $fidl__kLE);'''
self.f.write(
'''const _kTT_%(ttname)s = {
enc: function(e, o, v) {
%(throw_if_null)s
e.data.setUint32(o, v.length, $fidl__kLE);
e.data.setUint32(o + 4, 0, $fidl__kLE);
%(pointer_set)s
e.outOfLine.push([function(e, body) {
var start = e.alloc(body.length * %(element_size)s);
for (var i = 0; i < body.length; i++) {
_kTT_%(element_ttname)s.enc(e, start + (i * %(element_size)s), body[i]);
}
},
v]);
},
};
''' % { 'ttname': ttname,
'element_ttname': element_ttname,
'element_size': _InlineSizeOfType(t.element_type),
'pointer_set': pointer_set,
'throw_if_null': throw_if_null })
return ttname
else:
raise NotImplementedError()
def _GenerateJsInterfaceForInterface(self, name, interface):
"""Generates a JS @interface for the given FIDL interface."""
self.f.write('''/**
* @interface
*/
function %(name)s() {}
''' % { 'name': name })
# Define a JS interface part for the interface for typechecking.
for method in interface.methods:
method_name = _CompileIdentifier(method.name)
if method.has_request:
param_names = [_CompileIdentifier(x.name)
for x in method.maybe_request]
if len(param_names):
self.f.write('/**\n')
# TODO(crbug.com/883496): Emit @param type comments here.
self.f.write(' */\n')
self.f.write('%(name)s.prototype.%(method_name)s = '
'function(%(param_names)s) {};\n\n' % {
'name': name,
'method_name': method_name,
'param_names': ', '.join(param_names)})
# Emit message ordinals for later use.
for method in interface.methods:
method_name = _CompileIdentifier(method.name)
self.f.write(
'const _k%(name)s_%(method_name)s_Ordinal = %(ordinal)s;\n' % {
'name': name,
'method_name': method_name,
'ordinal': method.ordinal})
self.f.write('\n')
def _GenerateJsProxyForInterface(self, name, interface):
"""Generates the JS side implementation of a proxy class implementing the
given interface."""
proxy_name = name + 'Proxy'
self.f.write('''/**
* @constructor
* @implements %(name)s
*/
function %(proxy_name)s() {
this.channel = zx.ZX_HANDLE_INVALID;
}
%(proxy_name)s.prototype.$bind = function(channel) {
this.channel = channel;
};
''' % { 'name': name,
'proxy_name': proxy_name })
for method in interface.methods:
method_name = _CompileIdentifier(method.name)
if method.has_request:
type_tables = []
for param in method.maybe_request:
type_tables.append(self._CompileType(param.type))
param_names = [_CompileIdentifier(x.name) for x in method.maybe_request]
self.f.write(
'''%(proxy_name)s.prototype.%(method_name)s = function(%(param_names)s) {
if (this.channel === zx.ZX_HANDLE_INVALID) {
throw "channel closed";
}
var $encoder = new $fidl_Encoder(_k%(name)s_%(method_name)s_Ordinal);
$encoder.alloc(%(size)s - $fidl_kMessageHeaderSize);
''' % { 'name': name,
'proxy_name': proxy_name,
'method_name': method_name,
'param_names': ', '.join(param_names),
'size': method.maybe_request_size})
for param, ttname in zip(method.maybe_request, type_tables):
self.f.write(
''' _kTT_%(type_table)s.enc($encoder, %(offset)s, %(param_name)s);
''' % { 'type_table': ttname,
'param_name': _CompileIdentifier(param.name),
'offset': param.offset })
self.f.write(
''' var $result = zx.channelWrite(this.channel,
$encoder.messageData(),
$encoder.messageHandles());
if ($result !== zx.ZX_OK) {
throw "zx.channelWrite failed: " + $result;
}
};
''')
def _CompileInterface(self, interface):
compound = _ParseCompoundIdentifier(interface.name)
name = _CompileCompoundIdentifier(compound)
self._GenerateJsInterfaceForInterface(name, interface)
self._GenerateJsProxyForInterface(name, interface)
def main():
parser = argparse.ArgumentParser()
parser.add_argument('json')
parser.add_argument('--output', required=True)
args = parser.parse_args()
fidl = fidl_from_dict(json.load(open(args.json, 'r')))
with open(args.output, 'w') as f:
c = Compiler(fidl, f)
c.Compile()
if __name__ == '__main__':
main()
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// This is the JS runtime support library for code generated by fidlgen_js. It
// mostly consists of helpers to facilitate encoding and decoding of FIDL
// messages.
const $fidl_kInitialBufferSize = 1024;
const $fidl_kMessageHeaderSize = 16;
const $fidl_kMessageTxidOffset = 0;
const $fidl_kMessageOrdinalOffset = 12;
const $fidl__kAlignment = 8;
const $fidl__kAlignmentMask = 0x7;
const $fidl__kLE = true;
function $fidl__align(size) {
return size + (($fidl__kAlignment - (size & $fidl__kAlignmentMask)) &
$fidl__kAlignmentMask);
}
/**
* @constructor
* @param {number} ordinal
*/
function $fidl_Encoder(ordinal) {
var buf = new ArrayBuffer($fidl_kInitialBufferSize);
this.data = new DataView(buf);
this.extent = 0;
this.handles = [];
this.outOfLine = [];
this._encodeMessageHeader(ordinal);
}
/**
* @param {number} ordinal
*/
$fidl_Encoder.prototype._encodeMessageHeader = function(ordinal) {
this.alloc($fidl_kMessageHeaderSize);
this.data.setUint32($fidl_kMessageOrdinalOffset, ordinal, $fidl__kLE);
};
/**
* @param {number} size
*/
$fidl_Encoder.prototype.alloc = function(size) {
var offset = this.extent;
this._claimMemory($fidl__align(size));
return offset;
};
/**
* @param {number} claimSize
*/
$fidl_Encoder.prototype._claimMemory = function(claimSize) {
this.extent += claimSize;
if (this.extent > this.data.byteLength) {
var newSize = this.data.byteLength + claimSize;
newSize += newSize * 2;
this._grow(newSize);
}
};
/**
* @param {number} newSize
*/
$fidl_Encoder.prototype._grow = function(newSize) {
var newBuffer = new ArrayBuffer(newSize);
new Uint8Array(newBuffer).set(new Uint8Array(this.data.buffer));
this.data = new DataView(newBuffer);
};
$fidl_Encoder.prototype.messageData = function() {
// Add all out of line data.
var len = this.outOfLine.length;
for (var i = 0; i < len; i++) {
this.outOfLine[i][0](this, this.outOfLine[i][1]);
}
// Return final result.
return new DataView(this.data.buffer, 0, this.extent);
};
$fidl_Encoder.prototype.messageHandles = function() {
return this.handles;
};
// Type tables and encoding helpers for generated Proxy code.
const _kTT_int8 = {
enc: function(e, o, v) { e.data.setInt8(o, v, $fidl__kLE); },
};
const _kTT_int16 = {
enc: function(e, o, v) { e.data.setInt16(o, v, $fidl__kLE); },
};
const _kTT_int32 = {
enc: function(e, o, v) { e.data.setUint32(o, v, $fidl__kLE); },
};
const _kTT_uint8 = {
enc: function(e, o, v) { e.data.setUint8(o, v, $fidl__kLE); },
};
const _kTT_uint16 = {
enc: function(e, o, v) { e.data.setUint16(o, v, $fidl__kLE); },
};
const _kTT_uint32 = {
enc: function(e, o, v) { e.data.setUint32(o, v, $fidl__kLE); },
};
const _kTT_String_Nonnull = {
enc: function(e, o, v) {
if (v === null || v === undefined) throw "non-null string required";
// Both size and data are uint64, but that's awkward in JS, so for now only
// support a maximum of 32b lengths.
var asUtf8 = zx.strToUtf8Array(v);
e.data.setUint32(o, asUtf8.length, $fidl__kLE);
e.data.setUint32(o + 4, 0, $fidl__kLE);
e.data.setUint32(o + 8, 0xffffffff, $fidl__kLE);
e.data.setUint32(o + 12, 0xffffffff, $fidl__kLE);
e.outOfLine.push([$fidl_OutOfLineStringEnc, asUtf8]);
},
};
function $fidl_OutOfLineStringEnc(e, strAsUtf8Array) {
var start = e.alloc(strAsUtf8Array.length);
for (var i = 0; i < strAsUtf8Array.length; i++) {
e.data.setUint8(start + i, strAsUtf8Array[i], $fidl__kLE);
}
}
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "tools/fuchsia/fidlgen_js/runtime/zircon.h"
#include <lib/zx/channel.h>
#include <zircon/errors.h>
#include <zircon/syscalls.h>
#include <zircon/types.h>
#include "base/bind.h"
#include "gin/arguments.h"
#include "gin/array_buffer.h"
#include "gin/converter.h"
#include "gin/data_object_builder.h"
#include "gin/function_template.h"
namespace {
v8::Local<v8::Object> ZxChannelCreate(v8::Isolate* isolate) {
zx::channel c1, c2;
zx_status_t status = zx::channel::create(0, &c1, &c2);
return gin::DataObjectBuilder(isolate)
.Set("status", status)
.Set("first", c1.release())
.Set("second", c2.release())
.Build();
}
zx_status_t ZxChannelWrite(gin::Arguments* args) {
zx_handle_t handle;
if (!args->GetNext(&handle)) {
args->ThrowError();
return ZX_ERR_INVALID_ARGS;
}
gin::ArrayBufferView data;
if (!args->GetNext(&data)) {
args->ThrowError();
return ZX_ERR_INVALID_ARGS;
}
std::vector<zx_handle_t> handles;
if (!args->GetNext(&handles)) {
args->ThrowError();
return ZX_ERR_INVALID_ARGS;
}
zx_status_t status =
zx_channel_write(handle, 0, data.bytes(), data.num_bytes(),
handles.data(), handles.size());
return status;
}
v8::Local<v8::Value> StrToUtf8Array(gin::Arguments* args) {
std::string str;
// This converts the string to utf8 from ucs2, so then just repackage the
// string as an array and return it.
if (!args->GetNext(&str)) {
args->ThrowError();
return v8::Local<v8::Object>();
}
// TODO(crbug.com/883496): Not sure how to make a Uint8Array to return here
// which would be a bit more efficient.
std::vector<int> data;
std::copy(str.begin(), str.end(), std::back_inserter(data));
return gin::ConvertToV8(args->isolate(), data);
}
v8::Local<v8::Object> GetOrCreateZxObject(v8::Isolate* isolate,
v8::Local<v8::Object> global) {
v8::Local<v8::Object> zx;
v8::Local<v8::Value> zx_value = global->Get(gin::StringToV8(isolate, "zx"));
if (zx_value.IsEmpty() || !zx_value->IsObject()) {
zx = v8::Object::New(isolate);
global->Set(gin::StringToSymbol(isolate, "zx"), zx);
} else {
zx = v8::Local<v8::Object>::Cast(zx);
}
return zx;
}
} // namespace
namespace fidljs {
void InjectZxBindings(v8::Isolate* isolate, v8::Local<v8::Object> global) {
v8::Local<v8::Object> zx = GetOrCreateZxObject(isolate, global);
#define SET_CONSTANT(k) \
zx->Set(gin::StringToSymbol(isolate, #k), gin::ConvertToV8(isolate, k))
// zx_status_t.
SET_CONSTANT(ZX_OK);
SET_CONSTANT(ZX_ERR_INTERNAL);
SET_CONSTANT(ZX_ERR_NOT_SUPPORTED);
SET_CONSTANT(ZX_ERR_NO_RESOURCES);
SET_CONSTANT(ZX_ERR_NO_MEMORY);
SET_CONSTANT(ZX_ERR_INTERNAL_INTR_RETRY);
SET_CONSTANT(ZX_ERR_INVALID_ARGS);
SET_CONSTANT(ZX_ERR_BAD_HANDLE);
SET_CONSTANT(ZX_ERR_WRONG_TYPE);
SET_CONSTANT(ZX_ERR_BAD_SYSCALL);
SET_CONSTANT(ZX_ERR_OUT_OF_RANGE);
SET_CONSTANT(ZX_ERR_BUFFER_TOO_SMALL);
SET_CONSTANT(ZX_ERR_BAD_STATE);
SET_CONSTANT(ZX_ERR_TIMED_OUT);
SET_CONSTANT(ZX_ERR_SHOULD_WAIT);
SET_CONSTANT(ZX_ERR_CANCELED);
SET_CONSTANT(ZX_ERR_PEER_CLOSED);
SET_CONSTANT(ZX_ERR_NOT_FOUND);
SET_CONSTANT(ZX_ERR_ALREADY_EXISTS);
SET_CONSTANT(ZX_ERR_ALREADY_BOUND);
SET_CONSTANT(ZX_ERR_UNAVAILABLE);
SET_CONSTANT(ZX_ERR_ACCESS_DENIED);
SET_CONSTANT(ZX_ERR_IO);
SET_CONSTANT(ZX_ERR_IO_REFUSED);
SET_CONSTANT(ZX_ERR_IO_DATA_INTEGRITY);
SET_CONSTANT(ZX_ERR_IO_DATA_LOSS);
SET_CONSTANT(ZX_ERR_IO_NOT_PRESENT);
SET_CONSTANT(ZX_ERR_IO_OVERRUN);
SET_CONSTANT(ZX_ERR_IO_MISSED_DEADLINE);
SET_CONSTANT(ZX_ERR_IO_INVALID);
SET_CONSTANT(ZX_ERR_BAD_PATH);
SET_CONSTANT(ZX_ERR_NOT_DIR);
SET_CONSTANT(ZX_ERR_NOT_FILE);
SET_CONSTANT(ZX_ERR_FILE_BIG);
SET_CONSTANT(ZX_ERR_NO_SPACE);
SET_CONSTANT(ZX_ERR_NOT_EMPTY);
SET_CONSTANT(ZX_ERR_STOP);
SET_CONSTANT(ZX_ERR_NEXT);
SET_CONSTANT(ZX_ERR_ASYNC);
SET_CONSTANT(ZX_ERR_PROTOCOL_NOT_SUPPORTED);
SET_CONSTANT(ZX_ERR_ADDRESS_UNREACHABLE);
SET_CONSTANT(ZX_ERR_ADDRESS_IN_USE);
SET_CONSTANT(ZX_ERR_NOT_CONNECTED);
SET_CONSTANT(ZX_ERR_CONNECTION_REFUSED);
SET_CONSTANT(ZX_ERR_CONNECTION_RESET);
SET_CONSTANT(ZX_ERR_CONNECTION_ABORTED);
// Handle APIs.
zx->Set(gin::StringToSymbol(isolate, "handleClose"),
gin::CreateFunctionTemplate(isolate,
base::BindRepeating(&zx_handle_close))
->GetFunction());
SET_CONSTANT(ZX_HANDLE_INVALID);
// Channel APIs.
zx->Set(gin::StringToSymbol(isolate, "channelCreate"),
gin::CreateFunctionTemplate(isolate,
base::BindRepeating(&ZxChannelCreate))
->GetFunction());
zx->Set(
gin::StringToSymbol(isolate, "channelWrite"),
gin::CreateFunctionTemplate(isolate, base::BindRepeating(&ZxChannelWrite))
->GetFunction());
SET_CONSTANT(ZX_CHANNEL_READABLE);
SET_CONSTANT(ZX_CHANNEL_WRITABLE);
SET_CONSTANT(ZX_CHANNEL_PEER_CLOSED);
SET_CONSTANT(ZX_CHANNEL_READ_MAY_DISCARD);
SET_CONSTANT(ZX_CHANNEL_MAX_MSG_BYTES);
SET_CONSTANT(ZX_CHANNEL_MAX_MSG_HANDLES);
// Utility to make string handling easier to convert from a UCS2 JS string to
// an array of UTF-8 (which is how strings are represented in FIDL).
// TODO(crbug.com/883496): This is not really zx, should move to a generic
// runtime helper file if there are more similar C++ helpers required.
zx->Set(
gin::StringToSymbol(isolate, "strToUtf8Array"),
gin::CreateFunctionTemplate(isolate, base::BindRepeating(&StrToUtf8Array))
->GetFunction());
#undef SET_CONSTANT
}
} // namespace fidljs
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef TOOLS_FUCHSIA_FIDLGEN_JS_RUNTIME_ZIRCON_H_
#define TOOLS_FUCHSIA_FIDLGEN_JS_RUNTIME_ZIRCON_H_
#include "v8/include/v8.h"
namespace fidljs {
// Adds Zircon APIs bindings to |global|, for use by JavaScript callers.
void InjectZxBindings(v8::Isolate* isolate, v8::Local<v8::Object> global);
} // namespace fidljs
#endif // TOOLS_FUCHSIA_FIDLGEN_JS_RUNTIME_ZIRCON_H_
This diff is collapsed.
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
library fidljstest;
enum Blorp : int8 {
ALPHA = 1;
BETA = 2;
GAMMA = 0x48;
};
interface Testola {
1: DoSomething();
2: PrintInt(int32 num);
3: PrintMsg(string msg);
4: VariousArgs(Blorp blorp, string:32 msg, vector<uint32> stuff);
};
Copyright (c) 2013, Ethan Furman.
All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions
are met:
Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following
disclaimer in the documentation and/or other materials
provided with the distribution.
Neither the name Ethan Furman nor the names of any
contributors may be used to endorse or promote products
derived from this software without specific prior written
permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
POSSIBILITY OF SUCH DAMAGE.
Name: enum34
Short Name: enum34
URL: https://bitbucket.org/stoneleaf/enum34
License: BSD
License File: LICENSE
Revision: f24487b
Security Critical: no
Description:
'Enum' backported from Python 3.4 to earlier Python versions. Only LICENSE and
__init__.py are taken, other packaging files, documentation, etc. removed.
Only used at build time.
This diff is collapsed.
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment