2 var BindingSupportLib = {
3 $BINDING__postset: 'BINDING.export_functions (Module);',
5 BINDING_ASM: "[binding_tests]WebAssembly.Runtime",
6 mono_wasm_object_registry: [],
7 mono_wasm_ref_counter: 0,
8 mono_wasm_free_list: [],
9 mono_bindings_init: function (binding_asm) {
10 this.BINDING_ASM = binding_asm;
13 export_functions: function (module) {
14 module ["mono_bindings_init"] = BINDING.mono_bindings_init.bind(BINDING);
15 module ["mono_method_invoke"] = BINDING.call_method.bind(BINDING);
16 module ["mono_method_get_call_signature"] = BINDING.mono_method_get_call_signature.bind(BINDING);
17 module ["mono_method_resolve"] = BINDING.resolve_method_fqn.bind(BINDING);
18 module ["mono_bind_static_method"] = BINDING.bind_static_method.bind(BINDING);
19 module ["mono_call_static_method"] = BINDING.call_static_method.bind(BINDING);
22 bindings_lazy_init: function () {
26 this.assembly_load = Module.cwrap ('mono_wasm_assembly_load', 'number', ['string']);
27 this.find_class = Module.cwrap ('mono_wasm_assembly_find_class', 'number', ['number', 'string', 'string']);
28 this.find_method = Module.cwrap ('mono_wasm_assembly_find_method', 'number', ['number', 'string', 'number']);
29 this.invoke_method = Module.cwrap ('mono_wasm_invoke_method', 'number', ['number', 'number', 'number', 'number']);
30 this.mono_string_get_utf8 = Module.cwrap ('mono_wasm_string_get_utf8', 'number', ['number']);
31 this.js_string_to_mono_string = Module.cwrap ('mono_wasm_string_from_js', 'number', ['string']);
32 this.mono_get_obj_type = Module.cwrap ('mono_wasm_get_obj_type', 'number', ['number']);
33 this.mono_unbox_int = Module.cwrap ('mono_unbox_int', 'number', ['number']);
34 this.mono_unbox_float = Module.cwrap ('mono_wasm_unbox_float', 'number', ['number']);
35 this.mono_array_length = Module.cwrap ('mono_wasm_array_length', 'number', ['number']);
36 this.mono_array_get = Module.cwrap ('mono_wasm_array_get', 'number', ['number', 'number']);
37 this.mono_obj_array_new = Module.cwrap ('mono_wasm_obj_array_new', 'number', ['number']);
38 this.mono_obj_array_set = Module.cwrap ('mono_wasm_obj_array_set', 'void', ['number', 'number', 'number']);
40 // receives a byteoffset into allocated Heap with a size.
41 this.mono_typed_array_new = Module.cwrap ('mono_wasm_typed_array_new', 'number', ['number','number','number','number']);
42 this.mono_array_to_heap = Module.cwrap ('mono_wasm_array_to_heap', 'void', ['number','number']);
44 var binding_fqn_asm = this.BINDING_ASM.substring(this.BINDING_ASM.indexOf ("[") + 1, this.BINDING_ASM.indexOf ("]")).trim();
45 var binding_fqn_class = this.BINDING_ASM.substring (this.BINDING_ASM.indexOf ("]") + 1).trim();
47 this.binding_module = this.assembly_load (binding_fqn_asm);
48 if (!this.binding_module)
49 throw "Can't find bindings module assembly: " + binding_fqn_asm;
51 if (binding_fqn_class !== null && typeof binding_fqn_class !== "undefined")
53 var namespace = "WebAssembly";
54 var classname = binding_fqn_class.length > 0 ? binding_fqn_class : "Runtime";
55 if (binding_fqn_class.indexOf(".") != -1) {
56 var idx = binding_fqn_class.lastIndexOf(".");
57 namespace = binding_fqn_class.substring (0, idx);
58 classname = binding_fqn_class.substring (idx + 1);
62 var wasm_runtime_class = this.find_class (this.binding_module, namespace, classname)
63 if (!wasm_runtime_class)
64 throw "Can't find " + binding_fqn_class + " class";
66 var get_method = function(method_name) {
67 var res = BINDING.find_method (wasm_runtime_class, method_name, -1)
69 throw "Can't find method " + namespace + "." + classname + ":" + method_name;
72 this.bind_js_obj = get_method ("BindJSObject");
73 this.bind_existing_obj = get_method ("BindExistingObject");
74 this.unbind_js_obj = get_method ("UnBindJSObject");
75 this.unbind_js_obj_and_fee = get_method ("UnBindJSObjectAndFree");
76 this.get_js_id = get_method ("GetJSObjectId");
77 this.get_raw_mono_obj = get_method ("GetMonoObject");
79 this.box_js_int = get_method ("BoxInt");
80 this.box_js_double = get_method ("BoxDouble");
81 this.box_js_bool = get_method ("BoxBool");
82 this.setup_js_cont = get_method ("SetupJSContinuation");
84 this.create_tcs = get_method ("CreateTaskSource");
85 this.set_tcs_result = get_method ("SetTaskSourceResult");
86 this.set_tcs_failure = get_method ("SetTaskSourceFailure");
87 this.tcs_get_task_and_bind = get_method ("GetTaskAndBind");
88 this.get_call_sig = get_method ("GetCallSignature");
93 get_js_obj: function (js_handle) {
95 return this.mono_wasm_require_handle(js_handle);
99 //FIXME this is wastefull, we could remove the temp malloc by going the UTF16 route
100 //FIXME this is unsafe, cuz raw objects could be GC'd.
101 conv_string: function (mono_obj) {
104 var raw = this.mono_string_get_utf8 (mono_obj);
105 var res = Module.UTF8ToString (raw);
111 mono_array_to_js_array: function (mono_array) {
116 var len = this.mono_array_length (mono_array);
117 for (var i = 0; i < len; ++i)
118 res.push (this.unbox_mono_obj (this.mono_array_get (mono_array, i)));
123 js_array_to_mono_array: function (js_array) {
124 var mono_array = this.mono_obj_array_new (js_array.length);
125 for (var i = 0; i < js_array.length; ++i) {
126 this.mono_obj_array_set (mono_array, i, this.js_to_mono_obj (js_array [i]));
131 unbox_mono_obj: function (mono_obj) {
134 var type = this.mono_get_obj_type (mono_obj);
135 //See MARSHAL_TYPE_ defines in driver.c
138 return this.mono_unbox_int (mono_obj);
140 return this.mono_unbox_float (mono_obj);
142 return this.conv_string (mono_obj);
144 throw new Error ("no idea on how to unbox value types");
145 case 5: { // delegate
146 var obj = this.extract_js_obj (mono_obj);
148 return BINDING.invoke_delegate (obj, arguments);
153 if (typeof Promise === "undefined" || typeof Promise.resolve === "undefined")
154 throw new Error ("Promises are not supported thus C# Tasks can not work in this context.");
156 var obj = this.extract_js_obj (mono_obj);
158 var promise = new Promise (function (resolve, reject) {
165 this.call_method (this.setup_js_cont, null, "mo", [ mono_obj, cont_obj ]);
170 return this.extract_js_obj (mono_obj);
173 return this.mono_unbox_int (mono_obj) != 0;
184 var res = this.mono_array_to_js_typedarray(type, mono_obj);
189 throw new Error ("no idea on how to unbox object kind " + type);
193 create_task_completion_source: function () {
194 return this.call_method (this.create_tcs, null, "i", [ -1 ]);
197 set_task_result: function (tcs, result) {
198 this.call_method (this.set_tcs_result, null, "oo", [ tcs, result ]);
201 set_task_failure: function (tcs, reason) {
202 this.call_method (this.set_tcs_failure, null, "os", [ tcs, reason.toString () ]);
205 // https://github.com/Planeshifter/emscripten-examples/blob/master/01_PassingArrays/sum_post.js
206 js_typedarray_to_heap: function(typedArray){
207 var numBytes = typedArray.length * typedArray.BYTES_PER_ELEMENT;
208 var ptr = Module._malloc(numBytes);
209 var heapBytes = new Uint8Array(Module.HEAPU8.buffer, ptr, numBytes);
210 heapBytes.set(new Uint8Array(typedArray.buffer));
213 mono_array_to_js_typedarray: function(type, mono_array){
215 // length of our array
216 var szLength = this.mono_array_length(mono_array);
218 // The element size that will need to be allocated
219 var bytes_per_element = 0;
224 bytes_per_element = Int8Array.BYTES_PER_ELEMENT;
227 bytes_per_element = Uint8Array.BYTES_PER_ELEMENT;
230 bytes_per_element = Int16Array.BYTES_PER_ELEMENT;
233 bytes_per_element = Uint16Array.BYTES_PER_ELEMENT;
236 bytes_per_element = Int32Array.BYTES_PER_ELEMENT;
239 bytes_per_element = Uint32Array.BYTES_PER_ELEMENT;
242 bytes_per_element = Float32Array.BYTES_PER_ELEMENT;
245 bytes_per_element = Float64Array.BYTES_PER_ELEMENT;
249 // Allocate bytes needed for the array of bytes
250 var bufferSize = szLength * bytes_per_element;
251 var bufferPtr = Module._malloc(bufferSize);
253 // blit the mono array to the heap
254 this.mono_array_to_heap(mono_array, bufferPtr);
256 // result to be returned
259 // We now need to create a new typed array based off the heap view
263 res = Module.HEAP8.slice(bufferPtr / bytes_per_element, bufferPtr / bytes_per_element + szLength);
266 res = Module.HEAPU8.slice(bufferPtr / bytes_per_element, bufferPtr / bytes_per_element + szLength);
269 res = Module.HEAP16.slice(bufferPtr / bytes_per_element, bufferPtr / bytes_per_element + szLength);
272 res = Module.HEAPU16.slice(bufferPtr / bytes_per_element, bufferPtr / bytes_per_element + szLength);
275 res = Module.HEAP32.slice(bufferPtr / bytes_per_element, bufferPtr / bytes_per_element + szLength);
278 res = Module.HEAPU32.slice(bufferPtr / bytes_per_element, bufferPtr / bytes_per_element + szLength);
281 res = Module.HEAPF32.slice(bufferPtr / bytes_per_element, bufferPtr / bytes_per_element + szLength);
284 res = Module.HEAPF64.slice(bufferPtr / bytes_per_element, bufferPtr / bytes_per_element + szLength);
288 // free the allocated memory
289 Module._free(bufferPtr);
290 // return new typed array
294 js_to_mono_obj: function (js_obj) {
295 this.bindings_lazy_init ();
297 if (js_obj == null || js_obj == undefined)
299 if (typeof js_obj == 'number') {
300 if (parseInt(js_obj) == js_obj)
301 return this.call_method (this.box_js_int, null, "im", [ js_obj ]);
302 return this.call_method (this.box_js_double, null, "dm", [ js_obj ]);
304 if (typeof js_obj == 'string')
305 return this.js_string_to_mono_string (js_obj);
307 if (typeof js_obj == 'boolean')
308 return this.call_method (this.box_js_bool, null, "im", [ js_obj ]);
310 if (Promise.resolve(js_obj) === js_obj) {
311 var the_task = this.try_extract_mono_obj (js_obj);
314 var tcs = this.create_task_completion_source ();
315 //FIXME dispose the TCS once the promise completes
316 js_obj.then (function (result) {
317 BINDING.set_task_result (tcs, result);
318 }, function (reason) {
319 BINDING.set_task_failure (tcs, reason);
322 return this.get_task_and_bind (tcs, js_obj);
326 // JavaScript typed arrays are array-like objects and provide a mechanism for accessing
327 // raw binary data. (...) To achieve maximum flexibility and efficiency, JavaScript typed arrays
328 // split the implementation into buffers and views. A buffer (implemented by the ArrayBuffer object)
329 // is an object representing a chunk of data; it has no format to speak of, and offers no
330 // mechanism for accessing its contents. In order to access the memory contained in a buffer,
331 // you need to use a view. A view provides a context — that is, a data type, starting offset,
332 // and number of elements — that turns the data into an actual typed array.
333 // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Typed_arrays
334 if (!!(js_obj.buffer instanceof ArrayBuffer && js_obj.BYTES_PER_ELEMENT))
337 if (js_obj instanceof Int8Array)
339 if (js_obj instanceof Uint8Array)
341 if (js_obj instanceof Uint8ClampedArray)
343 if (js_obj instanceof Int16Array)
345 if (js_obj instanceof Uint16Array)
347 if (js_obj instanceof Int32Array)
349 if (js_obj instanceof Uint32Array)
351 if (js_obj instanceof Float32Array)
353 if (js_obj instanceof Float64Array)
356 var heapBytes = this.js_typedarray_to_heap(js_obj);
357 var bufferArray = this.mono_typed_array_new(heapBytes.byteOffset, js_obj.length, js_obj.BYTES_PER_ELEMENT, arrayType);
358 Module._free(heapBytes.byteOffset);
361 // The ArrayBuffer object is used to represent a generic, fixed-length raw binary data buffer.
362 // You cannot directly manipulate the contents of an ArrayBuffer; instead, you create one of the
363 // typed array objects or a DataView object which represents the buffer in a specific format, and
364 // use that to read and write the contents of the buffer.
365 // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Typed_arrays#ArrayBuffer
366 if (ArrayBuffer.isView(js_obj) || js_obj instanceof ArrayBuffer)
368 var heapBytes = this.js_typedarray_to_heap(new Uint8Array(js_obj));
370 var bufferArray = this.mono_typed_array_new(heapBytes.byteOffset, heapBytes.length, heapBytes.BYTES_PER_ELEMENT, 2);
371 Module._free(heapBytes.byteOffset);
375 return this.extract_mono_obj (js_obj);
378 wasm_binding_obj_new: function (js_obj_id)
380 return this.call_method (this.bind_js_obj, null, "i", [js_obj_id]);
383 wasm_bind_existing: function (mono_obj, js_id)
385 return this.call_method (this.bind_existing_obj, null, "mi", [mono_obj, js_id]);
388 wasm_unbind_js_obj: function (js_obj_id)
390 return this.call_method (this.unbind_js_obj, null, "i", [js_obj_id]);
393 wasm_unbind_js_obj_and_free: function (js_obj_id)
395 return this.call_method (this.unbind_js_obj_and_fee, null, "i", [js_obj_id]);
398 wasm_get_js_id: function (mono_obj)
400 return this.call_method (this.get_js_id, null, "m", [mono_obj]);
403 wasm_get_raw_obj: function (gchandle)
405 return this.call_method (this.get_raw_mono_obj, null, "im", [gchandle]);
408 try_extract_mono_obj:function (js_obj) {
409 if (js_obj === null || typeof js_obj === "undefined" || typeof js_obj.__mono_gchandle__ === "undefined")
411 return this.wasm_get_raw_obj (js_obj.__mono_gchandle__);
414 mono_method_get_call_signature: function(method) {
415 this.bindings_lazy_init ();
417 return this.call_method (this.get_call_sig, null, "i", [ method ]);
420 get_task_and_bind: function (tcs, js_obj) {
421 var gc_handle = this.mono_wasm_free_list.length ? this.mono_wasm_free_list.pop() : this.mono_wasm_ref_counter++;
422 var task_gchandle = this.call_method (this.tcs_get_task_and_bind, null, "oi", [ tcs, gc_handle + 1 ]);
423 js_obj.__mono_gchandle__ = task_gchandle;
424 this.mono_wasm_object_registry[gc_handle] = js_obj;
425 return this.wasm_get_raw_obj (js_obj.__mono_gchandle__);
428 extract_mono_obj: function (js_obj) {
429 //help JS ppl, is this enough?
430 if (js_obj === null || typeof js_obj === "undefined")
433 if (!js_obj.__mono_gchandle__) {
434 this.mono_wasm_register_obj(js_obj);
437 return this.wasm_get_raw_obj (js_obj.__mono_gchandle__);
440 extract_js_obj: function (mono_obj) {
444 var js_id = this.wasm_get_js_id (mono_obj);
446 return this.mono_wasm_require_handle(js_id);
448 var gcHandle = this.mono_wasm_free_list.length ? this.mono_wasm_free_list.pop() : this.mono_wasm_ref_counter++;
450 __mono_gchandle__: this.wasm_bind_existing(mono_obj, gcHandle + 1),
451 is_mono_bridged_obj: true
454 this.mono_wasm_object_registry[gcHandle] = js_obj;
459 args_marshal is a string with one character per parameter that tells how to marshal it, here are the valid values:
466 o: js object will be converted to a C# object (this will box numbers/bool/promises)
467 m: raw mono object. Don't use it unless you know what you're doing
469 additionally you can append 'm' to args_marshal beyond `args.length` if you don't want the return value marshaled
471 call_method: function (method, this_arg, args_marshal, args) {
472 this.bindings_lazy_init ();
474 var extra_args_mem = 0;
475 for (var i = 0; i < args.length; ++i) {
476 //long/double memory must be 8 bytes aligned and I'm being lazy here
477 if (args_marshal[i] == 'i' || args_marshal[i] == 'f' || args_marshal[i] == 'l' || args_marshal[i] == 'd')
481 var extra_args_mem = extra_args_mem ? Module._malloc (extra_args_mem) : 0;
482 var extra_arg_idx = 0;
483 var args_mem = Module._malloc (args.length * 4);
484 var eh_throw = Module._malloc (4);
485 for (var i = 0; i < args.length; ++i) {
486 if (args_marshal[i] == 's') {
487 Module.setValue (args_mem + i * 4, this.js_string_to_mono_string (args [i]), "i32");
488 } else if (args_marshal[i] == 'm') {
489 Module.setValue (args_mem + i * 4, args [i], "i32");
490 } else if (args_marshal[i] == 'o') {
491 Module.setValue (args_mem + i * 4, this.js_to_mono_obj (args [i]), "i32");
492 } else if (args_marshal[i] == 'i' || args_marshal[i] == 'f' || args_marshal[i] == 'l' || args_marshal[i] == 'd') {
493 var extra_cell = extra_args_mem + extra_arg_idx;
496 if (args_marshal[i] == 'i')
497 Module.setValue (extra_cell, args [i], "i32");
498 else if (args_marshal[i] == 'l')
499 Module.setValue (extra_cell, args [i], "i64");
500 else if (args_marshal[i] == 'f')
501 Module.setValue (extra_cell, args [i], "float");
503 Module.setValue (extra_cell, args [i], "double");
505 Module.setValue (args_mem + i * 4, extra_cell, "i32");
508 Module.setValue (eh_throw, 0, "i32");
510 var res = this.invoke_method (method, this_arg, args_mem, eh_throw);
512 var eh_res = Module.getValue (eh_throw, "i32");
515 Module._free (extra_args_mem);
516 Module._free (args_mem);
517 Module._free (eh_throw);
520 var msg = this.conv_string (res);
521 throw new Error (msg); //the convention is that invoke_method ToString () any outgoing exception
524 if (args_marshal.length >= args.length && args_marshal [args.length] == 'm')
526 return this.unbox_mono_obj (res);
529 invoke_delegate: function (delegate_obj, js_args) {
530 this.bindings_lazy_init ();
532 if (!this.delegate_dynamic_invoke) {
534 this.corlib = this.assembly_load ("mscorlib");
535 if (!this.delegate_class)
536 this.delegate_class = this.find_class (this.corlib, "System", "Delegate");
537 this.delegate_dynamic_invoke = this.find_method (this.delegate_class, "DynamicInvoke", -1);
539 var mono_args = this.js_array_to_mono_array (js_args);
540 return this.call_method (this.delegate_dynamic_invoke, this.extract_mono_obj (delegate_obj), "m", [ mono_args ]);
543 resolve_method_fqn: function (fqn) {
544 var assembly = fqn.substring(fqn.indexOf ("[") + 1, fqn.indexOf ("]")).trim();
545 fqn = fqn.substring (fqn.indexOf ("]") + 1).trim();
547 var methodname = fqn.substring(fqn.indexOf (":") + 1);
548 fqn = fqn.substring (0, fqn.indexOf (":")).trim ();
552 if (fqn.indexOf(".") != -1) {
553 var idx = fqn.lastIndexOf(".");
554 namespace = fqn.substring (0, idx);
555 classname = fqn.substring (idx + 1);
558 var asm = this.assembly_load (assembly);
560 throw new Error ("Could not find assembly: " + assembly);
562 var klass = this.find_class(asm, namespace, classname);
564 throw new Error ("Could not find class: " + namespace + ":" +classname);
566 var method = this.find_method (klass, methodname, -1);
568 throw new Error ("Could not find method: " + methodname);
572 call_static_method: function (fqn, args, signature) {
573 this.bindings_lazy_init ();
575 var method = this.resolve_method_fqn (fqn);
577 if (typeof signature === "undefined")
578 signature = Module.mono_method_get_call_signature (method);
580 return this.call_method (method, null, signature, args);
583 bind_static_method: function (fqn, signature) {
584 this.bindings_lazy_init ();
586 var method = this.resolve_method_fqn (fqn);
588 if (typeof signature === "undefined")
589 signature = Module.mono_method_get_call_signature (method);
592 return BINDING.call_method (method, null, signature, arguments);
595 // Object wrapping helper functions to handle reference handles that will
596 // be used in managed code.
597 mono_wasm_register_obj: function(obj) {
599 var gc_handle = undefined;
600 if (obj !== null && typeof obj !== "undefined") {
601 gc_handle = obj.__mono_gchandle__;
602 if (typeof gc_handle === "undefined") {
603 var handle = this.mono_wasm_free_list.length ?
604 this.mono_wasm_free_list.pop() : this.mono_wasm_ref_counter++;
605 gc_handle = handle + 1;
606 obj.__mono_gchandle__ = this.wasm_binding_obj_new(gc_handle);
609 this.mono_wasm_object_registry[handle] = obj;
613 mono_wasm_require_handle: function(handle) {
615 return this.mono_wasm_object_registry[handle - 1];
618 mono_wasm_unregister_obj: function(js_id) {
619 var obj = this.mono_wasm_object_registry[js_id - 1]
620 if (typeof obj !== "undefined" && obj !== null) {
621 var gc_handle = obj.__mono_gchandle__;
622 if (typeof gc_handle !== "undefined") {
623 this.wasm_unbind_js_obj_and_free(js_id);
624 delete obj.__mono_gchandle__;
625 this.mono_wasm_free_list.push(js_id - 1);
631 mono_wasm_free_handle: function(handle) {
632 this.mono_wasm_unregister_obj(handle);
636 mono_wasm_invoke_js_with_args: function(js_handle, method_name, args, is_exception) {
637 BINDING.bindings_lazy_init ();
639 var obj = BINDING.get_js_obj (js_handle);
641 setValue (is_exception, 1, "i32");
642 return BINDING.js_string_to_mono_string ("Invalid JS object handle '" + js_handle + "'");
645 var js_name = BINDING.conv_string (method_name);
647 setValue (is_exception, 1, "i32");
648 return BINDING.js_string_to_mono_string ("Invalid method name object '" + method_name + "'");
651 var js_args = BINDING.mono_array_to_js_array(args);
655 var m = obj [js_name];
656 var res = m.apply (obj, js_args);
657 return BINDING.js_to_mono_obj (res);
659 var res = e.toString ();
660 setValue (is_exception, 1, "i32");
661 if (res === null || res === undefined)
662 res = "unknown exception";
663 return BINDING.js_string_to_mono_string (res);
666 mono_wasm_get_object_property: function(js_handle, property_name, is_exception) {
667 BINDING.bindings_lazy_init ();
669 var obj = BINDING.mono_wasm_require_handle (js_handle);
671 setValue (is_exception, 1, "i32");
672 return BINDING.js_string_to_mono_string ("Invalid JS object handle '" + js_handle + "'");
675 var js_name = BINDING.conv_string (property_name);
677 setValue (is_exception, 1, "i32");
678 return BINDING.js_string_to_mono_string ("Invalid property name object '" + js_name + "'");
683 var m = obj [js_name];
684 if (m === Object(m) && obj.__is_mono_proxied__)
685 m.__is_mono_proxied__ = true;
687 return BINDING.js_to_mono_obj (m);
689 var res = e.toString ();
690 setValue (is_exception, 1, "i32");
691 if (res === null || typeof res === "undefined")
692 res = "unknown exception";
693 return BINDING.js_string_to_mono_string (res);
696 mono_wasm_set_object_property: function (js_handle, property_name, value, createIfNotExist, hasOwnProperty, is_exception) {
698 BINDING.bindings_lazy_init ();
700 var requireObject = BINDING.mono_wasm_require_handle (js_handle);
701 if (!requireObject) {
702 setValue (is_exception, 1, "i32");
703 return BINDING.js_string_to_mono_string ("Invalid JS object handle '" + js_handle + "'");
706 var property = BINDING.conv_string (property_name);
708 setValue (is_exception, 1, "i32");
709 return BINDING.js_string_to_mono_string ("Invalid property name object '" + property_name + "'");
714 var js_value = BINDING.unbox_mono_obj(value);
716 if (createIfNotExist) {
717 requireObject[property] = js_value;
722 if (!createIfNotExist)
724 if (!requireObject.hasOwnProperty(property))
727 if (hasOwnProperty === true) {
728 if (requireObject.hasOwnProperty(property)) {
729 requireObject[property] = js_value;
734 requireObject[property] = js_value;
739 return BINDING.call_method (BINDING.box_js_bool, null, "im", [ result ]);
744 autoAddDeps(BindingSupportLib, '$BINDING')
745 mergeInto(LibraryManager.library, BindingSupportLib)