Duktape is an embeddable Javascript engine,
with a focus on portability and compact footprint.
Duktape is easy to integrate into a C/C project: add duktape.c
,
duktape.h
, and duk_config.h
to your build, and use the
Duktape API to call ECMAScript functions from C code and vice versa.
- Embeddable, portable, compact:
can run on platforms with 160kB flash and 64kB RAM - ECMAScript E5/E5.1,
with some semantics updated from ES2015 - Partial support for
ECMAScript 2015 (E6) and
ECMAScript 2016 (E7), see
Post-ES5 feature status and
kangax/compat-table - ES2015 TypedArray
and Node.js Buffer bindings - CBOR bindings
- Encoding API bindings based on the WHATWG Encoding Living Standard
- performance.now()
- Built-in debugger
- Built-in regular expression engine
- Built-in Unicode support
- Minimal, retargetable platform dependencies
- Combined reference counting and mark-and-sweep garbage collection
with finalization - Coroutines
- Property virtualization using a subset of ECMAScript ES2015 Proxy object
- Bytecode dump/load for caching compiled functions
- Distributable includes an optional logging framework, CommonJS-based module
loading implementations, etc - Liberal license (MIT)
For a “Hello world” example:
Config | Code footprint (kB) | Startup RAM (kB) |
---|---|---|
thumb default | 148 | 78 |
thumb lowmem | 96 | 27 |
thumb full lowmem | 119 | 1.5 |
x86 default | 187 | 78 |
x86 lowmem | 124 | 27 |
x86 full lowmem | 148 | 1.5 |
See GCC options
for minimizing code footprint. Full lowmem
uses “pointer compression” and ROM-based strings/objects. ROM-based strings/objects can
also be used without other low memory options.
- Stable
- Duktape Wiki: wiki.duktape.org
- User community Q&A: Stack Overflow duktape tag
- Bugs and feature requests: GitHub issues
- General discussion: IRC
#duktape
onchat.freenode.net
(webchat)
See: Projects using Duktape.
If you’re using Duktape in your project, send an e-mail or open a GitHub
issue to be added to the list.
There are multiple Javascript engines targeting similar use cases as Duktape, at least:
- Espruino (MPL v2.0)
- JerryScript (Apache License v2.0)
- MuJS (Affero GPL)
- quad-wheel (MIT License)
- QuickJS (MIT License)
- tiny-js (MIT license)
- v7 (GPL v2.0)
Also see List of ECMAScript engines.
(See Getting started for a more
detailed introduction.)
Add Duktape C source and header to your build. Any build system can
be used. The distributable contains an example Makefile for reference.
In the simplest case:
$ gcc -std=c99 -otest test.c duktape.c -lm
$ ./test
1 2=3
To customize Duktape configuration,
here to disable ECMAScript 6 Proxy
object support:
$ python2 duktape-2.5.0/tools/configure.py --output-directory src-duktape -UDUK_USE_ES6_PROXY $ ls src-duktape/ duk_config.h duk_source_meta.json duktape.c duktape.h $ gcc -std=c99 -otest -Isrc-duktape test.c src-duktape/duktape.c -lm $ ./test 1 2=3
Initialize and use Duktape somewhere in your program:
#include#include "duktape.h" int main(int argc, char *argv[]) { duk_context *ctx = duk_create_heap_default(); duk_eval_string(ctx, "1 2"); printf("1 2=%dn", (int) duk_get_int(ctx, -1)); duk_destroy_heap(ctx); return 0; }
To call a C function from ECMAScript code, first declare your
C functions:
static duk_ret_t native_print(duk_context *ctx) { printf("%sn", duk_to_string(ctx, 0)); return 0; } static duk_ret_t native_adder(duk_context *ctx) { int i; int n = duk_get_top(ctx); double res = 0.0; for (i = 0; i < n; i ) { res = duk_to_number(ctx, i); } duk_push_number(ctx, res); return 1; }
Register your functions e.g. into the global object:
duk_push_c_function(ctx, native_print, 1 ); duk_put_global_string(ctx, "print"); duk_push_c_function(ctx, native_adder, DUK_VARARGS); duk_put_global_string(ctx, "adder");
You can then call your function from ECMAScript code:
duk_eval_string_noresult(ctx, "print('2 3=' adder(2, 3));");