Skip to content

Commit eb34626

Browse files
author
llgoer
committed
更新到2019-10-27版本
1 parent 6e76fd9 commit eb34626

20 files changed

+451
-105
lines changed

Changelog

+6
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,9 @@
1+
2019-10-27:
2+
3+
- added example of C class in a module (examples/test_point.js)
4+
- added JS_GetTypedArrayBuffer()
5+
- misc bug fixes
6+
17
2019-09-18:
28

39
- added os.exec and other system calls

Makefile

+19-11
Original file line numberDiff line numberDiff line change
@@ -146,7 +146,10 @@ ifeq ($(CROSS_PREFIX),)
146146
ifdef CONFIG_ASAN
147147
PROGS+=
148148
else
149-
PROGS+=examples/hello examples/hello_module examples/c_module
149+
PROGS+=examples/hello examples/hello_module examples/test_fib
150+
ifndef CONFIG_DARWIN
151+
PROGS+=examples/fib.so examples/point.so
152+
endif
150153
endif
151154
endif
152155

@@ -166,7 +169,7 @@ LIBS+=-ldl
166169
endif
167170

168171
$(OBJDIR):
169-
mkdir -p $(OBJDIR)
172+
mkdir -p $(OBJDIR) $(OBJDIR)/examples $(OBJDIR)/tests
170173

171174
qjs$(EXE): $(QJS_OBJS)
172175
$(CC) $(LDFLAGS) $(LDEXPORT) -o $@ $^ $(LIBS)
@@ -324,8 +327,9 @@ unicode_gen: $(OBJDIR)/unicode_gen.host.o $(OBJDIR)/cutils.host.o libunicode.c u
324327

325328
clean:
326329
rm -f repl.c repl-bn.c qjscalc.c out.c
327-
rm -f *.a *.so *.o *.d *~ jscompress unicode_gen regexp_test $(PROGS)
328-
rm -f hello.c hello_module.c c_module.c
330+
rm -f *.a *.o *.d *~ jscompress unicode_gen regexp_test $(PROGS)
331+
rm -f hello.c hello_module.c test_fib.c
332+
rm -f examples/*.so tests/*.so
329333
rm -rf $(OBJDIR)/ *.dSYM/ qjs-debug qjsbn-debug
330334
rm -rf run-test262-debug run-test262-32 run-test262-bn32
331335

@@ -372,14 +376,17 @@ examples/hello_module: $(QJSC) libquickjs$(LTOEXT).a $(HELLO_MODULE_SRCS)
372376

373377
# use of an external C module (static compilation)
374378

375-
c_module.c: $(QJSC) examples/c_module.js
376-
$(QJSC) -e -M examples/fib.so,fib -m -o $@ examples/c_module.js
379+
test_fib.c: $(QJSC) examples/test_fib.js
380+
$(QJSC) -e -M examples/fib.so,fib -m -o $@ examples/test_fib.js
377381

378-
examples/c_module: $(OBJDIR)/c_module.o $(OBJDIR)/fib.o libquickjs$(LTOEXT).a
382+
examples/test_fib: $(OBJDIR)/test_fib.o $(OBJDIR)/examples/fib.o libquickjs$(LTOEXT).a
379383
$(CC) $(LDFLAGS) -o $@ $^ $(LIBS)
380384

381-
$(OBJDIR)/fib.o: examples/fib.c
382-
$(CC) $(CFLAGS_OPT) -c -o $@ $<
385+
examples/fib.so: $(OBJDIR)/examples/fib.pic.o
386+
$(CC) $(LDFLAGS) -shared -o $@ $^
387+
388+
examples/point.so: $(OBJDIR)/examples/point.pic.o
389+
$(CC) $(LDFLAGS) -shared -o $@ $^
383390

384391
###############################################################################
385392
# documentation
@@ -404,7 +411,7 @@ doc/%.html: doc/%.html.pre
404411
# tests
405412

406413
ifndef CONFIG_DARWIN
407-
test: bjson.so
414+
test: tests/bjson.so
408415
endif
409416

410417
test: qjs qjsbn
@@ -415,6 +422,7 @@ test: qjs qjsbn
415422
./qjs tests/test_std.js
416423
ifndef CONFIG_DARWIN
417424
./qjs tests/test_bjson.js
425+
./qjs examples/test_point.js
418426
endif
419427
./qjsbn tests/test_closure.js
420428
./qjsbn tests/test_op.js
@@ -492,7 +500,7 @@ bench-v8: qjs qjs32
492500
make -C tests/bench-v8
493501
./qjs -d tests/bench-v8/combined.js
494502

495-
bjson.so: $(OBJDIR)/bjson.pic.o
503+
tests/bjson.so: $(OBJDIR)/tests/bjson.pic.o
496504
$(CC) $(LDFLAGS) -shared -o $@ $^ $(LIBS)
497505

498506
-include $(wildcard $(OBJDIR)/*.d)

TODO

+4-4
Original file line numberDiff line numberDiff line change
@@ -55,7 +55,7 @@ Extensions:
5555
- limited support for web assembly
5656
- get rid of __loadScript, use more common name
5757
- BSD sockets
58-
- Process or thread control
58+
- Workers
5959
- use custom printf to avoid C library compatibility issues
6060
- use custom timezone support to avoid C library compatibility issues
6161

@@ -75,6 +75,6 @@ REPL:
7575
Test262o: 0/11262 errors, 463 excluded
7676
Test262o commit: 7da91bceb9ce7613f87db47ddd1292a2dda58b42 (es5-tests branch)
7777

78-
Test262: 2/67351 errors, 839 excluded, 1370 skipped
79-
Test262bn: 2/69452 errors, 772 excluded, 383 skipped
80-
test262 commit: d65b9b35be091147edf31ec527a47cb95a327217
78+
Test262: 2/67433 errors, 901 excluded, 1658 skipped
79+
Test262bn: 2/69536 errors, 834 excluded, 670 skipped
80+
test262 commit: 21195de94cfc36eadbde00a825ca7efb3d9c3dde

VERSION

+1-1
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
2019-09-18
1+
2019-10-27

doc/quickjs.html

+12-9
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

doc/quickjs.pdf

287 Bytes
Binary file not shown.

doc/quickjs.texi

+11-9
Original file line numberDiff line numberDiff line change
@@ -127,7 +127,9 @@ Go to interactive mode (it is not the default when files are provided on the com
127127

128128
@item -m
129129
@item --module
130-
Load as ES6 module (default=autodetect).
130+
Load as ES6 module (default=autodetect). A module is autodetected if
131+
the filename extension is @code{.mjs} or if the first keyword of the
132+
source is @code{import}.
131133

132134
@item --script
133135
Load as ES6 script (default=autodetect).
@@ -202,13 +204,8 @@ QuickJS archive.
202204

203205
@section Test262 (ECMAScript Test Suite)
204206

205-
A test262 runner is included in the QuickJS archive.
206-
207-
For reference, the full test262 tests are provided in the archive
208-
@file{qjs-tests-yyyy-mm-dd.tar.xz}. You just need to untar it into the
209-
QuickJS source code directory.
210-
211-
Alternatively, the test262 tests can be installed with:
207+
A test262 runner is included in the QuickJS archive. The test262 tests
208+
can be installed in the QuickJS source directory with:
212209

213210
@example
214211
git clone https://github.com/tc39/test262.git test262
@@ -494,8 +491,13 @@ position @code{position} (wrapper to the libc @code{fread}).
494491
Return the next line from the file, assuming UTF-8 encoding, excluding
495492
the trailing line feed.
496493

494+
@item readAsString(max_size = undefined)
495+
Read @code{max_size} bytes from the file and return them as a string
496+
assuming UTF-8 encoding. If @code{max_size} is not present, the file
497+
is read up its end.
498+
497499
@item getByte()
498-
Return the next byte from the file.
500+
Return the next byte from the file. Return -1 if the end of file is reached.
499501

500502
@item putByte(c)
501503
Write one byte to the file.

examples/point.c

+151
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,151 @@
1+
/*
2+
* QuickJS: Example of C module with a class
3+
*
4+
* Copyright (c) 2019 Fabrice Bellard
5+
*
6+
* Permission is hereby granted, free of charge, to any person obtaining a copy
7+
* of this software and associated documentation files (the "Software"), to deal
8+
* in the Software without restriction, including without limitation the rights
9+
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10+
* copies of the Software, and to permit persons to whom the Software is
11+
* furnished to do so, subject to the following conditions:
12+
*
13+
* The above copyright notice and this permission notice shall be included in
14+
* all copies or substantial portions of the Software.
15+
*
16+
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17+
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18+
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19+
* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20+
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21+
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22+
* THE SOFTWARE.
23+
*/
24+
#include "../quickjs.h"
25+
#include <math.h>
26+
27+
#define countof(x) (sizeof(x) / sizeof((x)[0]))
28+
29+
/* Point Class */
30+
31+
typedef struct {
32+
int x;
33+
int y;
34+
} JSPointData;
35+
36+
static JSClassID js_point_class_id;
37+
38+
static void js_point_finalizer(JSRuntime *rt, JSValue val)
39+
{
40+
JSPointData *s = JS_GetOpaque(val, js_point_class_id);
41+
/* Note: 's' can be NULL in case JS_SetOpaque() was not called */
42+
js_free_rt(rt, s);
43+
}
44+
45+
static JSValue js_point_ctor(JSContext *ctx,
46+
JSValueConst new_target,
47+
int argc, JSValueConst *argv)
48+
{
49+
JSPointData *s;
50+
JSValue obj = JS_UNDEFINED;
51+
JSValue proto;
52+
53+
s = js_mallocz(ctx, sizeof(*s));
54+
if (!s)
55+
return JS_EXCEPTION;
56+
if (JS_ToInt32(ctx, &s->x, argv[0]))
57+
goto fail;
58+
if (JS_ToInt32(ctx, &s->y, argv[1]))
59+
goto fail;
60+
/* using new_target to get the prototype is necessary when the
61+
class is extended. */
62+
proto = JS_GetPropertyStr(ctx, new_target, "prototype");
63+
if (JS_IsException(proto))
64+
goto fail;
65+
obj = JS_NewObjectProtoClass(ctx, proto, js_point_class_id);
66+
JS_FreeValue(ctx, proto);
67+
if (JS_IsException(obj))
68+
goto fail;
69+
JS_SetOpaque(obj, s);
70+
return obj;
71+
fail:
72+
js_free(ctx, s);
73+
JS_FreeValue(ctx, obj);
74+
return JS_EXCEPTION;
75+
}
76+
77+
static JSValue js_point_get_xy(JSContext *ctx, JSValueConst this_val, int magic)
78+
{
79+
JSPointData *s = JS_GetOpaque2(ctx, this_val, js_point_class_id);
80+
if (!s)
81+
return JS_EXCEPTION;
82+
if (magic == 0)
83+
return JS_NewInt32(ctx, s->x);
84+
else
85+
return JS_NewInt32(ctx, s->y);
86+
}
87+
88+
static JSValue js_point_set_xy(JSContext *ctx, JSValueConst this_val, JSValue val, int magic)
89+
{
90+
JSPointData *s = JS_GetOpaque2(ctx, this_val, js_point_class_id);
91+
int v;
92+
if (!s)
93+
return JS_EXCEPTION;
94+
if (JS_ToInt32(ctx, &v, val))
95+
return JS_EXCEPTION;
96+
if (magic == 0)
97+
s->x = v;
98+
else
99+
s->y = v;
100+
return JS_UNDEFINED;
101+
}
102+
103+
static JSValue js_point_norm(JSContext *ctx, JSValueConst this_val,
104+
int argc, JSValueConst *argv)
105+
{
106+
JSPointData *s = JS_GetOpaque2(ctx, this_val, js_point_class_id);
107+
if (!s)
108+
return JS_EXCEPTION;
109+
return JS_NewFloat64(ctx, sqrt((double)s->x * s->x + (double)s->y * s->y));
110+
}
111+
112+
static JSClassDef js_point_class = {
113+
"Point",
114+
.finalizer = js_point_finalizer,
115+
};
116+
117+
static const JSCFunctionListEntry js_point_proto_funcs[] = {
118+
JS_CGETSET_MAGIC_DEF("x", js_point_get_xy, js_point_set_xy, 0),
119+
JS_CGETSET_MAGIC_DEF("y", js_point_get_xy, js_point_set_xy, 1),
120+
JS_CFUNC_DEF("norm", 0, js_point_norm),
121+
};
122+
123+
static int js_point_init(JSContext *ctx, JSModuleDef *m)
124+
{
125+
JSValue point_proto, point_class;
126+
127+
/* create the Point class */
128+
JS_NewClassID(&js_point_class_id);
129+
JS_NewClass(JS_GetRuntime(ctx), js_point_class_id, &js_point_class);
130+
131+
point_proto = JS_NewObject(ctx);
132+
JS_SetPropertyFunctionList(ctx, point_proto, js_point_proto_funcs, countof(js_point_proto_funcs));
133+
JS_SetClassProto(ctx, js_point_class_id, point_proto);
134+
135+
point_class = JS_NewCFunction2(ctx, js_point_ctor, "Point", 2, JS_CFUNC_constructor, 0);
136+
/* set proto.constructor and ctor.prototype */
137+
JS_SetConstructor(ctx, point_class, point_proto);
138+
139+
JS_SetModuleExport(ctx, m, "Point", point_class);
140+
return 0;
141+
}
142+
143+
JSModuleDef *js_init_module(JSContext *ctx, const char *module_name)
144+
{
145+
JSModuleDef *m;
146+
m = JS_NewCModule(ctx, module_name, js_point_init);
147+
if (!m)
148+
return NULL;
149+
JS_AddModuleExport(ctx, m, "Point");
150+
return m;
151+
}
File renamed without changes.

examples/test_point.js

+40
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
/* example of JS module importing a C module */
2+
import { Point } from "./point.so";
3+
4+
function assert(b, str)
5+
{
6+
if (b) {
7+
return;
8+
} else {
9+
throw Error("assertion failed: " + str);
10+
}
11+
}
12+
13+
class ColorPoint extends Point {
14+
constructor(x, y, color) {
15+
super(x, y);
16+
this.color = color;
17+
}
18+
get_color() {
19+
return this.color;
20+
}
21+
};
22+
23+
function main()
24+
{
25+
var pt, pt2;
26+
27+
pt = new Point(2, 3);
28+
assert(pt.x === 2);
29+
assert(pt.y === 3);
30+
pt.x = 4;
31+
assert(pt.x === 4);
32+
assert(pt.norm() == 5);
33+
34+
pt2 = new ColorPoint(2, 3, 0xffffff);
35+
assert(pt2.x === 2);
36+
assert(pt2.color === 0xffffff);
37+
assert(pt2.get_color() === 0xffffff);
38+
}
39+
40+
main();

0 commit comments

Comments
 (0)