/* ECMA-262 3rd Edition 9.8 */ HRESULT to_string(script_ctx_t *ctx, VARIANT *v, jsexcept_t *ei, BSTR *str) { const WCHAR undefinedW[] = {'u','n','d','e','f','i','n','e','d',0}; const WCHAR nullW[] = {'n','u','l','l',0}; const WCHAR trueW[] = {'t','r','u','e',0}; const WCHAR falseW[] = {'f','a','l','s','e',0}; switch(V_VT(v)) { case VT_EMPTY: *str = SysAllocString(undefinedW); break; case VT_NULL: *str = SysAllocString(nullW); break; case VT_I4: *str = int_to_bstr(V_I4(v)); break; case VT_R8: { VARIANT strv; HRESULT hres; V_VT(&strv) = VT_EMPTY; hres = VariantChangeTypeEx(&strv, v, MAKELCID(MAKELANGID(LANG_ENGLISH,SUBLANG_ENGLISH_US),SORT_DEFAULT), 0, VT_BSTR); if(FAILED(hres)) return hres; *str = V_BSTR(&strv); return S_OK; } case VT_BSTR: *str = SysAllocString(V_BSTR(v)); break; case VT_DISPATCH: { VARIANT prim; HRESULT hres; hres = to_primitive(ctx, v, ei, &prim); if(FAILED(hres)) return hres; hres = to_string(ctx, &prim, ei, str); VariantClear(&prim); return hres; } case VT_BOOL: *str = SysAllocString(V_BOOL(v) ? trueW : falseW); break; default: FIXME("unsupported vt %d\n", V_VT(v)); return E_NOTIMPL; } return *str ? S_OK : E_OUTOFMEMORY; }
/* ECMA-262 3rd Edition 9.8 */ HRESULT to_string(script_ctx_t *ctx, jsval_t val, jsstr_t **str) { const WCHAR undefinedW[] = {'u','n','d','e','f','i','n','e','d',0}; const WCHAR nullW[] = {'n','u','l','l',0}; const WCHAR trueW[] = {'t','r','u','e',0}; const WCHAR falseW[] = {'f','a','l','s','e',0}; switch(jsval_type(val)) { case JSV_UNDEFINED: *str = jsstr_alloc(undefinedW); break; case JSV_NULL: *str = jsstr_alloc(nullW); break; case JSV_NUMBER: return double_to_string(get_number(val), str); case JSV_STRING: *str = jsstr_addref(get_string(val)); break; case JSV_OBJECT: { jsval_t prim; HRESULT hres; hres = to_primitive(ctx, val, &prim, HINT_STRING); if(FAILED(hres)) return hres; hres = to_string(ctx, prim, str); jsval_release(prim); return hres; } case JSV_BOOL: *str = jsstr_alloc(get_bool(val) ? trueW : falseW); break; default: FIXME("unsupported %s\n", debugstr_jsval(val)); return E_NOTIMPL; } return *str ? S_OK : E_OUTOFMEMORY; }
/* ECMA-262 3rd Edition 9.3 */ HRESULT to_number(script_ctx_t *ctx, VARIANT *v, jsexcept_t *ei, VARIANT *ret) { switch(V_VT(v)) { case VT_EMPTY: num_set_nan(ret); break; case VT_NULL: V_VT(ret) = VT_I4; V_I4(ret) = 0; break; case VT_I4: case VT_R8: *ret = *v; break; case VT_BSTR: return str_to_number(V_BSTR(v), ret); case VT_DISPATCH: { VARIANT prim; HRESULT hres; hres = to_primitive(ctx, v, ei, &prim); if(FAILED(hres)) return hres; hres = to_number(ctx, &prim, ei, ret); VariantClear(&prim); return hres; } case VT_BOOL: V_VT(ret) = VT_I4; V_I4(ret) = V_BOOL(v) ? 1 : 0; break; default: FIXME("unimplemented for vt %d\n", V_VT(v)); return E_NOTIMPL; } return S_OK; }
/* ECMA-262 3rd Edition 9.3 */ HRESULT to_number(script_ctx_t *ctx, jsval_t val, double *ret) { switch(jsval_type(val)) { case JSV_UNDEFINED: *ret = NAN; return S_OK; case JSV_NULL: *ret = 0; return S_OK; case JSV_NUMBER: *ret = get_number(val); return S_OK; case JSV_STRING: return str_to_number(get_string(val), ret); case JSV_OBJECT: { jsval_t prim; HRESULT hres; hres = to_primitive(ctx, val, &prim, HINT_NUMBER); if(FAILED(hres)) return hres; hres = to_number(ctx, prim, ret); jsval_release(prim); return hres; } case JSV_BOOL: *ret = get_bool(val) ? 1 : 0; return S_OK; case JSV_VARIANT: FIXME("unimplemented for variant %s\n", debugstr_variant(get_variant(val))); return E_NOTIMPL; }; assert(0); return E_FAIL; }