JavascriptBoolean.cpp 8.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217
  1. //-------------------------------------------------------------------------------------------------------
  2. // Copyright (C) Microsoft. All rights reserved.
  3. // Licensed under the MIT license. See LICENSE.txt file in the project root for full license information.
  4. //-------------------------------------------------------------------------------------------------------
  5. #include "RuntimeLibraryPch.h"
  6. namespace Js
  7. {
  8. Var JavascriptBoolean::OP_LdTrue(ScriptContext*scriptContext)
  9. {
  10. return scriptContext->GetLibrary()->GetTrue();
  11. }
  12. Var JavascriptBoolean::OP_LdFalse(ScriptContext* scriptContext)
  13. {
  14. return scriptContext->GetLibrary()->GetFalse();
  15. }
  16. Js::Var JavascriptBoolean::ToVar(BOOL fValue, ScriptContext* scriptContext)
  17. {
  18. return
  19. fValue ?
  20. scriptContext->GetLibrary()->GetTrue() :
  21. scriptContext->GetLibrary()->GetFalse();
  22. }
  23. Var JavascriptBoolean::NewInstance(RecyclableObject* function, CallInfo callInfo, ...)
  24. {
  25. PROBE_STACK(function->GetScriptContext(), Js::Constants::MinStackDefault);
  26. ARGUMENTS(args, callInfo);
  27. ScriptContext* scriptContext = function->GetScriptContext();
  28. AssertMsg(args.HasArg(), "Should always have implicit 'this'");
  29. // SkipDefaultNewObject function flag should have prevented the default object from
  30. // being created, except when call true a host dispatch.
  31. Var newTarget = args.GetNewTarget();
  32. bool isCtorSuperCall = JavascriptOperators::GetAndAssertIsConstructorSuperCall(args);
  33. BOOL value;
  34. if (args.Info.Count > 1)
  35. {
  36. value = JavascriptConversion::ToBoolean(args[1], scriptContext) ? true : false;
  37. }
  38. else
  39. {
  40. value = false;
  41. }
  42. if (callInfo.Flags & CallFlags_New)
  43. {
  44. RecyclableObject* pNew = scriptContext->GetLibrary()->CreateBooleanObject(value);
  45. return isCtorSuperCall ?
  46. JavascriptOperators::OrdinaryCreateFromConstructor(VarTo<RecyclableObject>(newTarget), pNew, nullptr, scriptContext) :
  47. pNew;
  48. }
  49. return scriptContext->GetLibrary()->CreateBoolean(value);
  50. }
  51. // Boolean.prototype.valueOf as described in ES6 spec (draft 24) 19.3.3.3
  52. Var JavascriptBoolean::EntryValueOf(RecyclableObject* function, CallInfo callInfo, ...)
  53. {
  54. PROBE_STACK(function->GetScriptContext(), Js::Constants::MinStackDefault);
  55. ARGUMENTS(args, callInfo);
  56. ScriptContext* scriptContext = function->GetScriptContext();
  57. Assert(!(callInfo.Flags & CallFlags_New));
  58. if(VarIs<JavascriptBoolean>(args[0]))
  59. {
  60. return args[0];
  61. }
  62. else if (VarIs<JavascriptBooleanObject>(args[0]))
  63. {
  64. JavascriptBooleanObject* booleanObject = VarTo<JavascriptBooleanObject>(args[0]);
  65. return scriptContext->GetLibrary()->CreateBoolean(booleanObject->GetValue());
  66. }
  67. else
  68. {
  69. return TryInvokeRemotelyOrThrow(EntryValueOf, scriptContext, args, JSERR_This_NeedBoolean, _u("Boolean.prototype.valueOf"));
  70. }
  71. }
  72. // Boolean.prototype.toString as described in ES6 spec (draft 24) 19.3.3.2
  73. Var JavascriptBoolean::EntryToString(RecyclableObject* function, CallInfo callInfo, ...)
  74. {
  75. PROBE_STACK(function->GetScriptContext(), Js::Constants::MinStackDefault);
  76. ARGUMENTS(args, callInfo);
  77. AssertMsg(args.Info.Count, "Should always have implicit 'this'.");
  78. ScriptContext* scriptContext = function->GetScriptContext();
  79. Assert(!(callInfo.Flags & CallFlags_New));
  80. BOOL bval;
  81. Var aValue = args[0];
  82. if(VarIs<JavascriptBoolean>(aValue))
  83. {
  84. bval = VarTo<JavascriptBoolean>(aValue)->GetValue();
  85. }
  86. else if (VarIs<JavascriptBooleanObject>(aValue))
  87. {
  88. JavascriptBooleanObject* booleanObject = VarTo<JavascriptBooleanObject>(aValue);
  89. bval = booleanObject->GetValue();
  90. }
  91. else
  92. {
  93. return TryInvokeRemotelyOrThrow(EntryToString, scriptContext, args, JSERR_This_NeedBoolean, _u("Boolean.prototype.toString"));
  94. }
  95. return bval ? scriptContext->GetLibrary()->GetTrueDisplayString() : scriptContext->GetLibrary()->GetFalseDisplayString();
  96. }
  97. RecyclableObject * JavascriptBoolean::CloneToScriptContext(ScriptContext* requestContext)
  98. {
  99. if (this->GetValue())
  100. {
  101. return requestContext->GetLibrary()->GetTrue();
  102. }
  103. return requestContext->GetLibrary()->GetFalse();
  104. }
  105. Var JavascriptBoolean::TryInvokeRemotelyOrThrow(JavascriptMethod entryPoint, ScriptContext * scriptContext, Arguments & args, int32 errorCode, PCWSTR varName)
  106. {
  107. if (JavascriptOperators::GetTypeId(args[0]) == TypeIds_HostDispatch)
  108. {
  109. Var result;
  110. if (VarTo<RecyclableObject>(args[0])->InvokeBuiltInOperationRemotely(entryPoint, args, &result))
  111. {
  112. return result;
  113. }
  114. }
  115. // Don't error if we disabled implicit calls
  116. if(scriptContext->GetThreadContext()->RecordImplicitException())
  117. {
  118. JavascriptError::ThrowTypeError(scriptContext, errorCode, varName);
  119. }
  120. else
  121. {
  122. return scriptContext->GetLibrary()->GetUndefined();
  123. }
  124. }
  125. BOOL JavascriptBoolean::Equals(Var other, BOOL* value, ScriptContext * requestContext)
  126. {
  127. return JavascriptBoolean::Equals(this, other, value, requestContext);
  128. }
  129. BOOL JavascriptBoolean::Equals(JavascriptBoolean* left, Var right, BOOL* value, ScriptContext * requestContext)
  130. {
  131. switch (JavascriptOperators::GetTypeId(right))
  132. {
  133. case TypeIds_Integer:
  134. *value = left->GetValue() ? TaggedInt::ToInt32(right) == 1 : TaggedInt::ToInt32(right) == 0;
  135. break;
  136. case TypeIds_Number:
  137. *value = left->GetValue() ? JavascriptNumber::GetValue(right) == 1.0 : JavascriptNumber::GetValue(right) == 0.0;
  138. break;
  139. case TypeIds_Int64Number:
  140. *value = left->GetValue() ? VarTo<JavascriptInt64Number>(right)->GetValue() == 1 : VarTo<JavascriptInt64Number>(right)->GetValue() == 0;
  141. break;
  142. case TypeIds_UInt64Number:
  143. *value = left->GetValue() ? VarTo<JavascriptUInt64Number>(right)->GetValue() == 1 : VarTo<JavascriptUInt64Number>(right)->GetValue() == 0;
  144. break;
  145. case TypeIds_Boolean:
  146. *value = left->GetValue() == VarTo<JavascriptBoolean>(right)->GetValue();
  147. break;
  148. case TypeIds_String:
  149. *value = left->GetValue() ? JavascriptConversion::ToNumber(right, requestContext) == 1.0 : JavascriptConversion::ToNumber(right, requestContext) == 0.0;
  150. break;
  151. case TypeIds_Symbol:
  152. *value = FALSE;
  153. break;
  154. case TypeIds_Undefined:
  155. case TypeIds_Null:
  156. default:
  157. *value = JavascriptOperators::Equal_Full(left->GetValue() ? TaggedInt::ToVarUnchecked(1) : TaggedInt::ToVarUnchecked(0), right, requestContext);
  158. break;
  159. }
  160. return true;
  161. }
  162. BOOL JavascriptBoolean::GetDiagValueString(StringBuilder<ArenaAllocator>* stringBuilder, ScriptContext* requestContext)
  163. {
  164. if (this->GetValue())
  165. {
  166. JavascriptString* trueDisplayString = GetLibrary()->GetTrueDisplayString();
  167. stringBuilder->Append(trueDisplayString->GetString(), trueDisplayString->GetLength());
  168. }
  169. else
  170. {
  171. JavascriptString* falseDisplayString = GetLibrary()->GetFalseDisplayString();
  172. stringBuilder->Append(falseDisplayString->GetString(), falseDisplayString->GetLength());
  173. }
  174. return TRUE;
  175. }
  176. BOOL JavascriptBoolean::GetDiagTypeString(StringBuilder<ArenaAllocator>* stringBuilder, ScriptContext* requestContext)
  177. {
  178. stringBuilder->AppendCppLiteral(_u("Boolean"));
  179. return TRUE;
  180. }
  181. RecyclableObject* JavascriptBoolean::ToObject(ScriptContext * requestContext)
  182. {
  183. return requestContext->GetLibrary()->CreateBooleanObject(this->GetValue() ? true : false);
  184. }
  185. Var JavascriptBoolean::GetTypeOfString(ScriptContext * requestContext)
  186. {
  187. return requestContext->GetLibrary()->GetBooleanTypeDisplayString();
  188. }
  189. } // namespace Js