vobject.c 8.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208
  1. #include "__ofunc.h"
  2. typedef void (*base_opt)(LinkValue *, Result *, struct Inter *, VarList *var_list, Value *, Value *);
  3. void vobject_add_base(LinkValue *belong, Result *result, struct Inter *inter, VarList *var_list, Value *left, Value *right) {
  4. setResultCore(result);
  5. if (left->type == number && right->type == number)
  6. makeNumberValue(left->data.num.num + right->data.num.num, 0, "vobject.add", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  7. else if(left->type == string && right->type == string){
  8. char *new_string = memStrcat(left->data.str.str, right->data.str.str, false, false);
  9. makeStringValue(new_string, 0, "vobject.add", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  10. memFree(new_string);
  11. }
  12. else
  13. setResultError(E_TypeException, CUL_ERROR(Add), 0, "vobject.add", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  14. }
  15. void vobject_sub_base(LinkValue *belong, Result *result, struct Inter *inter, VarList *var_list, Value *left, Value *right) {
  16. setResultCore(result);
  17. if (left->type == number && right->type == number)
  18. makeNumberValue(left->data.num.num - right->data.num.num, 0, "vobject.sub", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  19. else
  20. setResultError(E_TypeException, CUL_ERROR(Sub), 0, "vobject.sub", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  21. }
  22. void vobject_mul_base(LinkValue *belong, Result *result, struct Inter *inter, VarList *var_list, Value *left, Value *right) {
  23. setResultCore(result);
  24. if (left->type == number && right->type == number)
  25. makeNumberValue(left->data.num.num * right->data.num.num, 0, "vobject.mul", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  26. else if(left->type == number && right->type == string) {
  27. Value *tmp = left;
  28. left = right;
  29. right = tmp;
  30. goto mul_str;
  31. }
  32. else if(left->type == string && right->type == number) mul_str: {
  33. char *new_string = memStrcpySelf(left->data.str.str, right->data.num.num);
  34. makeStringValue(new_string, 0, "vobject.mul", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  35. memFree(new_string);
  36. }
  37. else
  38. setResultError(E_TypeException, CUL_ERROR(Mul), 0, "vobject.mul", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  39. }
  40. void vobject_div_base(LinkValue *belong, Result *result, struct Inter *inter, VarList *var_list, Value *left, Value *right) {
  41. setResultCore(result);
  42. if (left->type == number && right->type == number) {
  43. lldiv_t div_result = lldiv(left->data.num.num, right->data.num.num);
  44. makeNumberValue(div_result.quot, 0, "vobject.div", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  45. }
  46. else
  47. setResultError(E_TypeException, CUL_ERROR(Div), 0, "vobject.div", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  48. }
  49. ResultType vobject_opt_core(OFFICAL_FUNCTIONSIG, base_opt func){
  50. Value *left = NULL;
  51. Value *right = NULL;
  52. ArgumentParser ap[] = {{.type=only_value, .must=1, .long_arg=false},
  53. {.type=name_value, .name="right", .must=1, .long_arg=false},
  54. {.must=-1}};
  55. setResultCore(result);
  56. {
  57. parserArgumentUnion(ap, arg, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  58. if (!CHECK_RESULT(result))
  59. return result->type;
  60. freeResult(result);
  61. }
  62. left = ap[0].value->value;
  63. right = ap[1].value->value;
  64. func(belong, result, inter, var_list, left, right);
  65. return result->type;
  66. }
  67. ResultType vobject_add(OFFICAL_FUNCTIONSIG){
  68. return vobject_opt_core(CALL_OFFICAL_FUNCTION(arg, var_list, result, belong), vobject_add_base);
  69. }
  70. ResultType vobject_sub(OFFICAL_FUNCTIONSIG){
  71. return vobject_opt_core(CALL_OFFICAL_FUNCTION(arg, var_list, result, belong), vobject_sub_base);
  72. }
  73. ResultType vobject_mul(OFFICAL_FUNCTIONSIG){
  74. return vobject_opt_core(CALL_OFFICAL_FUNCTION(arg, var_list, result, belong), vobject_mul_base);
  75. }
  76. ResultType vobject_div(OFFICAL_FUNCTIONSIG){
  77. return vobject_opt_core(CALL_OFFICAL_FUNCTION(arg, var_list, result, belong), vobject_div_base);
  78. }
  79. ResultType vobject_bool(OFFICAL_FUNCTIONSIG){
  80. ArgumentParser ap[] = {{.type=only_value, .must=1, .long_arg=false},
  81. {.must=-1}};
  82. bool result_ = false;
  83. Value *value = NULL;
  84. setResultCore(result);
  85. {
  86. parserArgumentUnion(ap, arg, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  87. if (!CHECK_RESULT(result))
  88. return result->type;
  89. freeResult(result);
  90. }
  91. value = ap[0].value->value;
  92. switch (value->type) {
  93. case number:
  94. result_ = value->data.num.num != 0;
  95. break;
  96. case string:
  97. result_ = memStrlen(value->data.str.str) > 0;
  98. break;
  99. case bool_:
  100. result_ = value->data.bool_.bool_;
  101. break;
  102. case pass_:
  103. case none:
  104. result_ = false;
  105. break;
  106. case list:
  107. result_ = value->data.list.size > 0;
  108. break;
  109. case dict:
  110. result_ = value->data.dict.size > 0;
  111. break;
  112. default:
  113. setResultError(E_TypeException, CUL_ERROR(bool), 0, "vobject", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  114. return error_return;
  115. }
  116. makeBoolValue(result_, 0, "vobject.bool", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  117. return result->type;
  118. }
  119. ResultType vobject_repo(OFFICAL_FUNCTIONSIG){
  120. ArgumentParser ap[] = {{.type=only_value, .must=1, .long_arg=false},
  121. {.must=-1}};
  122. char *repo = NULL;
  123. Value *value = NULL;
  124. setResultCore(result);
  125. parserArgumentUnion(ap, arg, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  126. if (!CHECK_RESULT(result))
  127. return result->type;
  128. freeResult(result);
  129. value = ap[0].value->value;
  130. switch (value->type){
  131. case number: {
  132. char str[30] = {};
  133. snprintf(str, 30, "%lld", value->data.num.num);
  134. repo = memStrcpy(str);
  135. break;
  136. }
  137. case string:
  138. repo = memStrcpy(value->data.str.str);
  139. break;
  140. case function: {
  141. char str[30] = {};
  142. snprintf(str, 30, "(function on %p)", value);
  143. repo = memStrcpy(str);
  144. break;
  145. }
  146. case none:
  147. repo = memStrcpy("(null)");
  148. break;
  149. case class: {
  150. char str[30] = {};
  151. snprintf(str, 30, "(class on %p)", value);
  152. repo = memStrcpy(str);
  153. break;
  154. }
  155. case bool_:
  156. if (value->data.bool_.bool_)
  157. repo = memStrcpy("true");
  158. else
  159. repo = memStrcpy("false");
  160. break;
  161. case pass_:
  162. repo = memStrcpy("...");
  163. break;
  164. default:
  165. setResultError(E_TypeException, CUL_ERROR(repo/str), 0, "vobject", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  166. return error_return;
  167. }
  168. makeStringValue(repo, 0, "vobject.repo", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  169. memFree(repo);
  170. return result->type;
  171. }
  172. void registeredVObject(REGISTERED_FUNCTIONSIG){
  173. LinkValue *object = makeLinkValue(inter->data.vobject, inter->base_father, inter);
  174. NameFunc tmp[] = {{inter->data.object_add, vobject_add, object_free_},
  175. {inter->data.object_sub, vobject_sub, object_free_},
  176. {inter->data.object_mul, vobject_mul, object_free_},
  177. {inter->data.object_div, vobject_div, object_free_},
  178. {inter->data.object_bool, vobject_bool, object_free_},
  179. {inter->data.object_repo, vobject_repo, object_free_},
  180. {inter->data.object_str, vobject_repo, object_free_},
  181. {NULL, NULL}};
  182. gc_addTmpLink(&object->gc_status);
  183. addBaseClassVar("vobject", object, belong, inter);
  184. iterBaseClassFunc(tmp, object, CALL_INTER_FUNCTIONSIG_CORE(inter->var_list));
  185. gc_freeTmpLink(&object->gc_status);
  186. }
  187. void makeBaseVObject(Inter *inter){
  188. Value *vobject = makeClassValue(copyVarList(inter->var_list, false, inter), inter, NULL);
  189. gc_addStatementLink(&vobject->gc_status);
  190. inter->data.vobject = vobject;
  191. }