diff --git a/docs/03.API-EXAMPLE.md b/docs/03.API-EXAMPLE.md index 3d848cde6..0fbf470f9 100644 --- a/docs/03.API-EXAMPLE.md +++ b/docs/03.API-EXAMPLE.md @@ -1,8 +1,43 @@ JerryScript Engine can be embedded into any application, providing the way to run JavaScript in a large range of environments - from desktops to low-memory microcontrollers. -This guide is intended to introduce you to JerryScript embedding API through creation of simple JavaScript shell. +This guide is intended to introduce you to JerryScript embedding API and to create a minimal JavaScript shell. +The examples are not using all API methods please also check out the API reference document which contains additional examples. -## Step 1. Execute JavaScript from your application + +## Before trying out the examples: Get and build JerryScript library + +Before getting started using the JerryScript library it should be cloned and built for a target os/device. + +There are quite a few configuration options but for these examples the JerryScript is built +**with default configuration** and installed to a user directory on a Linux system. +This is done by the following commands: + +```sh +$ mkdir jerry +$ cd jerry +$ git clone https://github.com/jerryscript-project/jerryscript.git +$ jerryscript/tools/build.py --builddir=$(pwd)/example_build --cmake-param="-DCMAKE_INSTALL_PREFIX=$(pwd)/example_install/" +$ make -C $(pwd)/example_build install +``` + +With this the JerryScript library is installed into the `$(pwd)/example_install/{include,lib}` directories. + +In this guide we will use `pkg-config` to ease the usage of headers and libraries. +In order to do so, the following export is required (executed from the jerry directory): + +```sh +$ export PKG_CONFIG_PATH=$(pwd)/example_install/lib/pkgconfig/ +``` + +Test if the `pkg-config` works for JerryScript: + +```sh +$ pkg-config --cflags --libs libjerry-core libjerry-port-default libjerry-ext libjerry-libm +``` + +## Example 1. Execute JavaScript from your application + +The most basic example to test the engine is to create an `api-example-1.c` file containing the following code: [doctest]: # () @@ -20,39 +55,213 @@ main (void) } ``` -The application will return with zero exit code. +To compile it one can use the following command: -## Step 2. Split engine initialization and script execution +```sh +$ gcc api-example-1.c -o api-example-1 $(pkg-config --cflags --libs libjerry-core libjerry-port-default libjerry-libm) +``` -Here we perform the same actions, as `jerry_run_simple`, while splitting into several steps: +If everything is correct the application returns with a zero exit code: -- engine initialization -- script code setup -- script execution -- engine cleanup +``` +$ ./api-example-1 +$ echo $? +``` +## Example 2. Split engine initialization and script execution. + +In this example the engine is initialized directly with the `jerry_init` method +and cleaned up with the `jerry_cleanup` method. The example JavaScript code +is directly parsed and executed via the `jerry_eval` method. Each `jerry_value_t` +returned by the API methods is freed with the `jerry_release_value` method. + +To make sure that the code parsing and execution was ok, the `jerry_value_is_error` +method is used to check for any errors. + +Use the following code for the `api-example-2.c` file: [doctest]: # () ```c #include "jerryscript.h" -#include "jerryscript-ext/handler.h" int main (void) { - const jerry_char_t script[] = "print ('Hello, World!');"; + const jerry_char_t script[] = "var str = 'Hello, World!';"; + const jerry_length_t script_size = sizeof (script) - 1; + /* Note: sizeof can be used here only because the compiler knows the static character arrays's size. + * If this is not the case, strlen should be used instead. + */ /* Initialize engine */ jerry_init (JERRY_INIT_EMPTY); - /* Register 'print' function from the extensions */ - jerryx_handler_register_global ((const jerry_char_t *) "print", - jerryx_handler_print); + /* Run the demo script with 'eval' */ + jerry_value_t eval_ret = jerry_eval (script, + script_size, + JERRY_PARSE_NO_OPTS); + + /* Check if there was any error (syntax or runtime) */ + bool run_ok = !jerry_value_is_error (eval_ret); + + /* Parsed source code must be freed */ + jerry_release_value (eval_ret); + + /* Cleanup engine */ + jerry_cleanup (); + + return (run_ok ? 0 : 1); +} +``` + +To compile it one can use the following command: + +```sh +$ gcc api-example-2.c -o api-example-2 $(pkg-config --cflags --libs libjerry-core libjerry-port-default libjerry-libm) +``` + +If everything is correct the application returns with a zero exit code: + +``` +$ ./api-example-2 +$ echo $? +``` + +## Example 3. Split JavaScript parsing and script execution + +In this example the `jerry_eval` is replaced with a more common API calls: + +- script code setup - `jerry_parse`. +- script execution - `jerry_run`. + +The `api-example-3.c` file should contain the following code: + +[doctest]: # () + +```c +#include "jerryscript.h" + +int +main (void) +{ + bool run_ok = false; + + const jerry_char_t script[] = "var str = 'Hello, World!';"; + + /* Initialize engine */ + jerry_init (JERRY_INIT_EMPTY); /* Setup Global scope code */ jerry_value_t parsed_code = jerry_parse (NULL, 0, script, sizeof (script) - 1, JERRY_PARSE_NO_OPTS); + /* Check if there is any JS code parse error */ + if (!jerry_value_is_error (parsed_code)) + { + /* Execute the parsed source code in the Global scope */ + jerry_value_t ret_value = jerry_run (parsed_code); + + /* Check the execution return value if there is any error */ + run_ok = !jerry_value_is_error (ret_value); + + /* Returned value must be freed */ + jerry_release_value (ret_value); + } + + /* Parsed source code must be freed */ + jerry_release_value (parsed_code); + + /* Cleanup engine */ + jerry_cleanup (); + + return (run_ok ? 0 : 1); +} +``` + +To compile it one can use the following command: + +```sh +$ gcc api-example-3.c -o api-example-3 $(pkg-config --cflags --libs libjerry-core libjerry-port-default libjerry-libm) +``` + +If everything is correct the application returns with a zero exit code: + +``` +$ ./api-example-3 +$ echo $? +``` + +## Example 4. Adding a C method for JavaScript + +The previous examples were not that eye catching as there were no visual output by the JavaScript code +and C program. + +In this example a very simple "print" method is added which prints out a static string. +This method will be implemented in C and will be called from the JavaScript code. +For this a few extra API methods are required: + +- `jerry_get_global_object` +- `jerry_create_string` +- `jerry_set_property` +- `jerry_create_external_function` + +The `api-example-4.c` file should contain the following code: + +[doctest]: # () + +```c +#include +#include "jerryscript.h" + +static jerry_value_t +print_handler (const jerry_value_t function_object, + const jerry_value_t function_this, + const jerry_value_t arguments[], + const jerry_length_t argument_count) +{ + /* No arguments are used in this example */ + /* Print out a static string */ + printf ("Print handler was called\n"); + + /* Return an "undefined" value to the JavaScript engine */ + return jerry_create_undefined (); +} + +int +main (void) +{ + const jerry_char_t script[] = "print ();"; + const jerry_length_t script_size = sizeof (script) - 1; + + /* Initialize engine */ + jerry_init (JERRY_INIT_EMPTY); + + /* Add the "print" method for the JavaScript global object */ + { + /* Get the "global" object */ + jerry_value_t global_object = jerry_get_global_object (); + /* Create a "print" JS string */ + jerry_value_t property_name_print = jerry_create_string ((const jerry_char_t *) "print"); + /* Create a function from a native C method (this function will be called from JS) */ + jerry_value_t property_value_func = jerry_create_external_function (print_handler); + /* Add the "print" property with the function value to the "global" object */ + jerry_value_t set_result = jerry_set_property (global_object, property_name_print, property_value_func); + + /* Check if there was no error when adding the property (in this case it should never happen) */ + if (jerry_value_is_error (set_result)) { + printf ("Failed to add the 'print' property\n"); + } + + /* Release all jerry_value_t-s */ + jerry_release_value (set_result); + jerry_release_value (property_value_func); + jerry_release_value (property_name_print); + jerry_release_value (global_object); + } + + /* Setup Global scope code */ + jerry_value_t parsed_code = jerry_parse (NULL, 0, script, script_size, JERRY_PARSE_NO_OPTS); + if (!jerry_value_is_error (parsed_code)) { /* Execute the parsed source code in the Global scope */ @@ -72,46 +281,118 @@ main (void) } ``` -Our code is more complex now, but it introduces possibilities to interact with JerryScript step-by-step: setup native objects, call JavaScript functions, etc. -## Step 3. Execution in 'eval'-mode +To compile it one can use the following command: + +```sh +$ gcc api-example-4.c -o api-example-4 $(pkg-config --cflags --libs libjerry-core libjerry-port-default libjerry-libm) +``` + +If everything is correct the application should print out the message present in the `print_handler` method: + +``` +$ ./api-example-4 +``` + +## Example 5. Passing and processing arguments for native C code + +In the previous example the `print_handler` simply wrote a static string to the standard output. +However in most cases this is not useful, ideally the method's argument(s) should be printed. + +In this example the `print_handler` is extended to convert the first +argument (which probably comes from a JavaScript source) to a JS string and prints it out to the standard output. + +New API methods used: + +- `jerry_value_to_string` +- `jerry_string_to_utf8_char_buffer` + +The `api-example-5.c` file should contain the following code: [doctest]: # () ```c +#include #include "jerryscript.h" -#include "jerryscript-ext/handler.h" + +static jerry_value_t +print_handler (const jerry_value_t function_object, + const jerry_value_t function_this, + const jerry_value_t arguments[], + const jerry_length_t arguments_count) +{ + /* There should be at least one argument */ + if (arguments_count > 0) + { + /* Convert the first argument to a string (JS "toString" operation) */ + jerry_value_t string_value = jerry_value_to_string (arguments[0]); + + /* A naive allocation of buffer for the string */ + jerry_char_t buffer[256]; + + /* Copy the whole string to the buffer, without a null termination character, + * Please note that if the string does not fit into the buffer nothing will be copied. + * More details on the API reference page + */ + jerry_size_t copied_bytes = jerry_string_to_utf8_char_buffer (string_value, buffer, sizeof (buffer) - 1); + buffer[copied_bytes] = '\0'; + + /* Release the "toString" result */ + jerry_release_value (string_value); + + printf ("%s\n", (const char *)buffer); + } + + /* Return an "undefined" value to the JavaScript engine */ + return jerry_create_undefined (); +} int main (void) { - const jerry_char_t script_1[] = "var s = 'Hello, World!';"; - const jerry_char_t script_2[] = "print (s);"; + const jerry_char_t script[] = "print ('Hello from JS!');"; + const jerry_length_t script_size = sizeof (script) - 1; /* Initialize engine */ jerry_init (JERRY_INIT_EMPTY); - /* Register 'print' function from the extensions */ - jerryx_handler_register_global ((const jerry_char_t *) "print", - jerryx_handler_print); + /* Add the "print" method for the JavaScript global object */ + { + /* Get the "global" object */ + jerry_value_t global_object = jerry_get_global_object (); + /* Create a "print" JS string */ + jerry_value_t property_name_print = jerry_create_string ((const jerry_char_t *) "print"); + /* Create a function from a native C method (this function will be called from JS) */ + jerry_value_t property_value_func = jerry_create_external_function (print_handler); + /* Add the "print" property with the function value to the "global" object */ + jerry_value_t set_result = jerry_set_property (global_object, property_name_print, property_value_func); - jerry_value_t eval_ret; + /* Check if there was no error when adding the property (in this case it should never happen) */ + if (jerry_value_is_error (set_result)) { + printf ("Failed to add the 'print' property\n"); + } - /* Evaluate script1 */ - eval_ret = jerry_eval (script_1, - sizeof (script_1) - 1, - JERRY_PARSE_NO_OPTS); + /* Release all jerry_value_t-s */ + jerry_release_value (set_result); + jerry_release_value (property_value_func); + jerry_release_value (property_name_print); + jerry_release_value (global_object); + } - /* Free JavaScript value, returned by eval */ - jerry_release_value (eval_ret); + /* Setup Global scope code */ + jerry_value_t parsed_code = jerry_parse (NULL, 0, script, script_size, JERRY_PARSE_NO_OPTS); - /* Evaluate script2 */ - eval_ret = jerry_eval (script_2, - sizeof (script_2) - 1, - JERRY_PARSE_NO_OPTS); + if (!jerry_value_is_error (parsed_code)) + { + /* Execute the parsed source code in the Global scope */ + jerry_value_t ret_value = jerry_run (parsed_code); - /* Free JavaScript value, returned by eval */ - jerry_release_value (eval_ret); + /* Returned value must be freed */ + jerry_release_value (ret_value); + } + + /* Parsed source code must be freed */ + jerry_release_value (parsed_code); /* Cleanup engine */ jerry_cleanup (); @@ -120,9 +401,93 @@ main (void) } ``` -This way, we execute two independent script parts in one execution environment. The first part initializes string variable, and the second outputs the variable. -## Step 4. Interaction with JavaScript environment +To compile it one can use the following command: + +```sh +$ gcc api-example-5.c -o api-example-5 $(pkg-config --cflags --libs libjerry-core libjerry-port-default libjerry-libm) +``` + +If everything is correct the application should print out the string passed for the `print` method in the JS code: + +``` +$ ./api-example-5 +``` + + +## Example 6. Using JerryScript Extensions + +Some of the previous examples used a "print" method to write data out to the standard output. +For convenience JerryScript provides an extension to add a simple "print" handler which +can be used by other applications. + +In this example the following extension methods are used: + +- `jerryx_handler_register_global` +- `jerryx_handler_print` + +In further examples this "print" handler will be used. + +```c +#include "jerryscript.h" +#include "jerryscript-ext/handler.h" + +int +main (void) +{ + const jerry_char_t script[] = "print ('Hello from JS with ext!');"; + const jerry_length_t script_size = sizeof (script) - 1; + + /* Initialize engine */ + jerry_init (JERRY_INIT_EMPTY); + + /* Register 'print' function from the extensions to the global object */ + jerryx_handler_register_global ((const jerry_char_t *) "print", + jerryx_handler_print); + + /* Setup Global scope code */ + jerry_value_t parsed_code = jerry_parse (NULL, 0, script, script_size, JERRY_PARSE_NO_OPTS); + + if (!jerry_value_is_error (parsed_code)) + { + /* Execute the parsed source code in the Global scope */ + jerry_value_t ret_value = jerry_run (parsed_code); + + /* Returned value must be freed */ + jerry_release_value (ret_value); + } + + /* Parsed source code must be freed */ + jerry_release_value (parsed_code); + + /* Cleanup engine */ + jerry_cleanup (); + + return 0; +} +``` + + +To compile it one can use the following command: + +(**Note** that the `libjerry-ext` was added **before** the `libjerry-port-default` entry for the `pkg-config` call. + +```sh +$ gcc api-example-6.c -o api-example-6 $(pkg-config --cflags --libs libjerry-core libjerry-ext libjerry-port-default libjerry-libm) +``` + +If everything is correct the application should print out the string passed for the `print` method in the JS code: + +``` +$ ./api-example-6 +``` + +## Example 7. Interaction with JavaScript environment - adding a string property + +Previously a C method was registered for the global object, now this examples show how one can add a string +property. + +Use the following code as the `api-example-7.c` file: [doctest]: # () @@ -133,8 +498,7 @@ This way, we execute two independent script parts in one execution environment. int main (void) { - const jerry_char_t str[] = "Hello, World!"; - const jerry_char_t script[] = "print (s);"; + const jerry_char_t script[] = "print (my_var);"; /* Initializing JavaScript environment */ jerry_init (JERRY_INIT_EMPTY); @@ -147,11 +511,16 @@ main (void) jerry_value_t global_object = jerry_get_global_object (); /* Constructing strings */ - jerry_value_t prop_name = jerry_create_string ((const jerry_char_t *) "s"); - jerry_value_t prop_value = jerry_create_string (str); + jerry_value_t prop_name = jerry_create_string ((const jerry_char_t *) "my_var"); + jerry_value_t prop_value = jerry_create_string ((const jerry_char_t *) "Hello from C!"); /* Setting the string value as a property of the Global object */ - jerry_release_value (jerry_set_property (global_object, prop_name, prop_value)); + jerry_value_t set_result = jerry_set_property (global_object, prop_name, prop_value); + /* The 'set_result' should be checked if there was any error */ + if (jerry_value_is_error (set_result)) { + printf ("Failed to add the 'my_var' property\n"); + } + jerry_release_value (set_result); /* Releasing string values, as it is no longer necessary outside of engine */ jerry_release_value (prop_name); @@ -175,16 +544,46 @@ main (void) } ``` -The sample will also output 'Hello, World!'. However, now it is not just a part of the source script, but the value, dynamically supplied to the engine. +To compile it one can use the following command: -## Step 5. Description of JerryScript value descriptors +(**Note** that the `libjerry-ext` was added **before** the `libjerry-port-default` entry for the `pkg-config` call. -JerryScript value can be a boolean, number, null, object, string or undefined. The value has an error flag, -that indicates whether is an error or not. Every type has an error flag not only objects. The error flag should -be cleared before the value is passed as an argument, otherwise it can lead to a type error. The error objects -created by API functions has the error flag set. +```sh +$ gcc api-example-7.c -o api-example-7 $(pkg-config --cflags --libs libjerry-core libjerry-ext libjerry-port-default libjerry-libm) +``` -The following example function will output a JavaScript value: +The sample will output 'Hello from C!'. However, now it is not just a part of the source script, but the value, dynamically supplied to the engine: + +``` +$ ./api-example-7 +``` + +## Example 8. Description of JerryScript value descriptors + +JerryScript value can be a boolean, number, null, object, string, undefined or some special type of objects (arraybuffer, symbols, etc). + +There is a special "error" value which wraps another value. This "error" can be created by throwing a JavaScript value from JS code +or via API method(s). It is advised to check for this error with the `jerry_value_is_error` method as not all API methods +can process error values. To extract the value from the "error" the API method `jerry_get_value_from_error` should be used. +If an error object is created via API method (for example with `jerry_create_error`) the "error" value is automatically created. + +Notice the difference between error value and error object: +- The error object is a object which was constructed via one of the `Error` objects (available from the global object or from API). + For example in JS such object be created with the following code example: + +```js +var error_object = new Error ("error message"); +``` + +- The error value is not an object on its own. This is the exception raised/thrown either via API methods or from JS. + For example, creating such error value in JS would look like this: + +```js +throw "message"; +``` + +To check what type a given `jerry_value_t` is the `jerry_value_is_*` methods or the `jerry_value_get_type` could be used. +For example the following code snippet could print out a few types (not all types are checked): [doctest]: # (test="compile") @@ -194,8 +593,20 @@ The following example function will output a JavaScript value: #include "jerryscript.h" static void -print_value (const jerry_value_t value) +print_value (const jerry_value_t jsvalue) { + jerry_value_t value; + /* If there is an error extract the object from it */ + if (jerry_value_is_error (jsvalue)) + { + printf ("Error value detected: "); + value = jerry_get_value_from_error (jsvalue, false); + } + else + { + value = jerry_acquire_value (jsvalue); + } + if (jerry_value_is_undefined (value)) { printf ("undefined"); @@ -218,7 +629,7 @@ print_value (const jerry_value_t value) /* Float value */ else if (jerry_value_is_number (value)) { - printf ("number"); + printf ("number: %lf", jerry_get_number_value (value)); } /* String value */ else if (jerry_value_is_string (value)) @@ -239,10 +650,11 @@ print_value (const jerry_value_t value) } printf ("\n"); + jerry_release_value (value); } ``` -## Simple JavaScript shell +## Example 8: Simple JavaScript shell Now all building blocks, necessary to construct JavaScript shell, are ready. @@ -256,7 +668,9 @@ Shell operation can be described with the following loop: - print result of eval; - loop. -[doctest]: # (test="compile") +See the following `api-example-8-shell.c` file: + +[doctest]: # (test="link") ```c #include @@ -265,7 +679,67 @@ Shell operation can be described with the following loop: #include "jerryscript.h" #include "jerryscript-ext/handler.h" -void print_value (const jerry_value_t); +static void +print_value (const jerry_value_t jsvalue) +{ + jerry_value_t value; + /* If there is an error extract the object from it */ + if (jerry_value_is_error (jsvalue)) + { + printf ("Error value detected: "); + value = jerry_get_value_from_error (jsvalue, false); + } + else + { + value = jerry_acquire_value (jsvalue); + } + + if (jerry_value_is_undefined (value)) + { + printf ("undefined"); + } + else if (jerry_value_is_null (value)) + { + printf ("null"); + } + else if (jerry_value_is_boolean (value)) + { + if (jerry_get_boolean_value (value)) + { + printf ("true"); + } + else + { + printf ("false"); + } + } + /* Float value */ + else if (jerry_value_is_number (value)) + { + printf ("number: %lf", jerry_get_number_value (value)); + } + /* String value */ + else if (jerry_value_is_string (value)) + { + /* Determining required buffer size */ + jerry_size_t req_sz = jerry_get_string_size (value); + jerry_char_t str_buf_p[req_sz + 1]; + + jerry_string_to_char_buffer (value, str_buf_p, req_sz); + str_buf_p[req_sz] = '\0'; + + printf ("%s", (const char *) str_buf_p); + } + /* Object reference */ + else if (jerry_value_is_object (value)) + { + printf ("[JS object]"); + } + + printf ("\n"); + + jerry_release_value (value); +} int main (void) @@ -317,15 +791,9 @@ main (void) len, JERRY_PARSE_NO_OPTS); - /* If command evaluated successfully, print value, returned by eval */ - if (jerry_value_is_error (ret_val)) - { - /* Evaluated JS code thrown an exception - * and didn't handle it with try-catch-finally */ - printf ("Unhandled JS exception occurred: "); - } - + /* Print out the value */ print_value (ret_val); + jerry_release_value (ret_val); } @@ -336,11 +804,24 @@ main (void) } ``` -The application inputs commands and evaluates them, one after another. +To compile it one can use the following command: -## Step 6. Creating JS object in global context +(**Note** that the `libjerry-ext` was added **before** the `libjerry-port-default` entry for the `pkg-config` call. -In this example we demonstrate how to use native function and structures in JavaScript. +```sh +$ gcc api-example-8-shell.c -o api-example-8-shell $(pkg-config --cflags --libs libjerry-core libjerry-ext libjerry-port-default libjerry-libm) +``` + +The application reads lines from standard input and evaluates them, one after another. To try out run: + +``` +$ ./api-example-8-shell +``` + + +## Example 9. Creating JS object in global context + +In this example (`api-example-9.c`) an object with a native function is added to the global object. [doctest]: # () @@ -423,15 +904,33 @@ main (void) } ``` +To compile it one can use the following command: + +(**Note** that the `libjerry-ext` was added **before** the `libjerry-port-default` entry for the `pkg-config` call. + +```sh +$ gcc api-example-9.c -o api-example-9 $(pkg-config --cflags --libs libjerry-core libjerry-ext libjerry-port-default libjerry-libm) +``` + +Execute the example with: + +``` +$ ./api-example-9 +``` + The application will generate the following output: ```bash -Hello World +Hello, World ``` -## Step 7. Extending JS Objects with native functions +## Example 10. Extending JS Objects with native functions -Here we create a JS Object with `jerry_eval`, then extend it with a native function. This function shows how to get a property value from the object and how to manipulate it. +The example creates a JS Object with `jerry_eval`, then it is extended from C with a native function. +In addition this native function shows how to get a property value from the object and how to manipulate it. + + +Use the following code for `api-example-10.c`: [doctest]: # () @@ -445,9 +944,12 @@ Here we create a JS Object with `jerry_eval`, then extend it with a native funct static jerry_value_t add_handler (const jerry_value_t func_value, /**< function object */ const jerry_value_t this_val, /**< this arg */ - const jerry_value_t *args_p, /**< function arguments */ + const jerry_value_t args_p[], /**< function arguments */ const jerry_length_t args_cnt) /**< number of function arguments */ { + /* The the 'this_val' is the 'MyObject' from the JS code below */ + /* Note: that the argument count check is ignored for the example's case */ + /* Get 'this.x' */ jerry_value_t prop_name = jerry_create_string ((const jerry_char_t *) "x"); jerry_value_t x_val = jerry_get_property (this_val, prop_name); @@ -456,7 +958,7 @@ add_handler (const jerry_value_t func_value, /**< function object */ { /* Convert Jerry API values to double */ double x = jerry_get_number_value (x_val); - double d = jerry_get_number_value (*args_p); + double d = jerry_get_number_value (args_p[0]); /* Add the parameter to 'x' */ jerry_value_t res_val = jerry_create_number (x + d); @@ -533,14 +1035,26 @@ main (void) } ``` -The application will generate the following output: +To compile it one can use the following command: + +(**Note** that the `libjerry-ext` was added **before** the `libjerry-port-default` entry for the `pkg-config` call. + +```sh +$ gcc api-example-10.c -o api-example-10 $(pkg-config --cflags --libs libjerry-core libjerry-ext libjerry-port-default libjerry-libm) +``` + +Execute the example with: + +``` +$ ./api-example-10 +``` ```bash Value of x is 12 Value of x is 17 ``` -## Step 8. Changing the seed of pseudorandom generated numbers +## Example 11. Changing the seed of pseudorandom generated numbers If you want to change the seed of `Math.random()` generated numbers, you have to initialize the seed value with `srand`. A recommended method is using `jerry_port_get_current_time()` or something based on a constantly changing value, therefore every run produces truly random numbers.