static JSBool convert_regexp_to_js(JohnsonRuntime* runtime, VALUE regexp, jsval* retval) { JSContext * context = johnson_get_current_context(runtime); PREPARE_JROOTS(context, 0); VALUE source = rb_funcall(regexp, rb_intern("source"), 0); jsint options = (jsint)(NUM2INT(rb_funcall(regexp, rb_intern("options"), 0))); JSObject* obj = JS_NewRegExpObject(context, StringValuePtr(source), (size_t) StringValueLen(source), (unsigned) options); JCHECK(obj); *retval = OBJECT_TO_JSVAL(obj); JRETURN; }
/* * call-seq: * native_compile(script, filename, linenum) * * Compile +script+ with +filename+ using +linenum+ */ static VALUE native_compile(VALUE self, VALUE script, VALUE filename, VALUE linenum) { JohnsonRuntime* runtime; Data_Get_Struct(self, JohnsonRuntime, runtime); JSContext * context = johnson_get_current_context(runtime); JohnsonContext * johnson_context = OUR_CONTEXT(context); JSScript * compiled_js = JS_CompileScript( context, runtime->global, StringValuePtr(script), (size_t)StringValueLen(script), StringValueCStr(filename), (unsigned)NUM2INT(linenum) ); if(compiled_js == NULL) { if (JS_IsExceptionPending(context)) { // If there's an exception pending here, it's a syntax error. JS_GetPendingException(context, &johnson_context->ex); JS_ClearPendingException(context); } if (johnson_context->ex) { RAISE_JS_ERROR(self, johnson_context->ex); return Qnil; } } JSObject * script_object = JS_NewScriptObject(context, compiled_js); PREPARE_RUBY_JROOTS(context, 1); JROOT(script_object); JRETURN_RUBY(make_ruby_land_proxy(runtime, OBJECT_TO_JSVAL(script_object), "JSScriptProxy")); }
JSBool convert_to_js(JohnsonRuntime* runtime, VALUE ruby, jsval* retval) { JSContext * context = johnson_get_current_context(runtime); PREPARE_JROOTS(context, 0); switch(TYPE(ruby)) { case T_NONE: JERROR("I don't know how to handle T_NONE."); JRETURN; case T_ICLASS: JERROR("I don't know how to handle T_ICLASS."); JRETURN; case T_MATCH: JERROR("I don't know how to handle T_MATCH."); JRETURN; case T_BLKTAG: JERROR("I don't know how to handle T_BLKTAG."); JRETURN; case T_NODE: JERROR("I don't know how to handle T_NODE | T_MASK."); JRETURN; case T_UNDEF: JERROR("I don't know how to handle T_UNDEF."); JRETURN; case T_VARMAP: JERROR("I don't know how to handle T_VARMAP."); JRETURN; case T_NIL: *retval = JSVAL_NULL; JRETURN; case T_TRUE: *retval = JSVAL_TRUE; JRETURN; case T_FALSE: *retval = JSVAL_FALSE; JRETURN; case T_STRING: { JSString* str = JS_NewStringCopyN(context, StringValuePtr(ruby), (size_t) StringValueLen(ruby)); JCHECK(str); *retval = STRING_TO_JSVAL(str); JRETURN; } case T_FIXNUM: { long val = NUM2LONG(ruby); if (val >= JSVAL_INT_MIN && val <= JSVAL_INT_MAX) { *retval = INT_TO_JSVAL((jsint)val); JRETURN; } } case T_FLOAT: case T_BIGNUM: JCHECK(convert_float_or_bignum_to_js(runtime, ruby, retval)); JRETURN; case T_SYMBOL: JCHECK(convert_symbol_to_js(runtime, ruby, retval)); JRETURN; case T_CLASS: case T_ARRAY: case T_HASH: case T_MODULE: case T_FILE: case T_STRUCT: case T_OBJECT: JCHECK(make_js_land_proxy(runtime, ruby, retval)); JRETURN; case T_REGEXP: JCHECK(convert_regexp_to_js(runtime, ruby, retval)); JRETURN; case T_DATA: // HEY! keep T_DATA last for fall-through if (ruby_value_is_proxy(ruby)) JCHECK(unwrap_ruby_land_proxy(runtime, ruby, retval)); else // If we can't identify the object, just wrap it JCHECK(make_js_land_proxy(runtime, ruby, retval)); JRETURN; default: JERROR("unknown ruby type in switch"); } *retval = JSVAL_NULL; JRETURN; }
static JSBool convert_symbol_to_js(JohnsonRuntime* runtime, VALUE symbol, jsval* retval) { JSContext * context = johnson_get_current_context(runtime); PREPARE_JROOTS(context, 2); VALUE to_s = CALL_RUBY_WRAPPER(rb_funcall_0, symbol, rb_intern("to_s"), 0); jsval name = STRING_TO_JSVAL(JS_NewStringCopyN(context, StringValuePtr(to_s), (size_t) StringValueLen(to_s))); JROOT(name); // calls Johnson.symbolize(name) in JS-land. See lib/prelude.js jsval nsJohnson; JCHECK(JS_GetProperty(context, runtime->global, "Johnson", &nsJohnson)); JROOT(nsJohnson); JCHECK(JS_CallFunctionName(context, JSVAL_TO_OBJECT(nsJohnson), "symbolize", 1, &name, retval)); JRETURN; }