run.c 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331
  1. #include "__run.h"
  2. /**
  3. * 运行单个statement
  4. * @param st
  5. * @param inter
  6. * @param var_list
  7. * @return
  8. */
  9. ResultType runStatement(INTER_FUNCTIONSIG) {
  10. setResultCore(result);
  11. ResultType type = not_return;
  12. switch (st->type) {
  13. case base_value:
  14. type = getBaseValue(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  15. break;
  16. case base_var:
  17. type = getVar(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong), getBaseVarInfo);
  18. break;
  19. case base_svar:
  20. type = getVar(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong), getBaseSVarInfo);
  21. break;
  22. case base_list:
  23. type = getList(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  24. break;
  25. case base_dict:
  26. type = getDict(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  27. break;
  28. case base_lambda:
  29. type = setLambda(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  30. break;
  31. case operation:
  32. type = operationStatement(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  33. break;
  34. case set_class:
  35. type = setClass(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  36. break;
  37. case set_function:
  38. type = setFunction(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  39. break;
  40. case slice_:
  41. type = elementSlice(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  42. break;
  43. case call_function:
  44. type = callBack(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  45. break;
  46. case if_branch:
  47. type = ifBranch(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  48. break;
  49. case while_branch:
  50. type = whileBranch(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  51. break;
  52. case for_branch:
  53. type = forBranch(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  54. break;
  55. case with_branch:
  56. type = withBranch(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  57. break;
  58. case try_branch:
  59. type = tryBranch(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  60. break;
  61. case break_cycle:
  62. type = breakCycle(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  63. break;
  64. case continue_cycle:
  65. type = continueCycle(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  66. break;
  67. case rego_if:
  68. type = regoIf(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  69. break;
  70. case restart:
  71. type = restartCode(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  72. break;
  73. case return_code:
  74. type = returnCode(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  75. break;
  76. case yield_code:
  77. type = yieldCode(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  78. break;
  79. case raise_code:
  80. type = raiseCode(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  81. break;
  82. case include_file:
  83. type = includeFile(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  84. break;
  85. case import_file:
  86. type = importFile(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  87. break;
  88. case from_import_file:
  89. type = fromImportFile(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  90. break;
  91. case default_var:
  92. type = setDefault(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  93. break;
  94. case assert:
  95. type = assertCode(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  96. break;
  97. case goto_:
  98. type = gotoLabel(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  99. break;
  100. case del_:
  101. type = delOperation(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  102. break;
  103. default:
  104. setResult(result, inter, belong);
  105. break;
  106. }
  107. if (RUN_TYPE(type) && result->value->aut == auto_aut)
  108. result->value->aut = st->aut;
  109. result->node = st;
  110. #if START_GC
  111. gc_run(inter, var_list, 1, 0, 0, var_list);
  112. #endif
  113. return type;
  114. }
  115. bool checkSignal(ResultType *type, fline line, char *file, INTER_FUNCTIONSIG_NOT_ST) {
  116. if (is_KeyInterrupt == signal_appear){
  117. is_KeyInterrupt = signal_reset;
  118. if (type != NULL)
  119. *type = error_return;
  120. setResultError(E_KeyInterrupt, KEY_INTERRUPT, line, file, true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  121. return true;
  122. }
  123. return false;
  124. }
  125. /**
  126. * 局部程序运行statement
  127. * @param st
  128. * @param inter
  129. * @param var_list
  130. * @return
  131. */
  132. ResultType iterStatement(INTER_FUNCTIONSIG) {
  133. Statement *base;
  134. ResultType type;
  135. void *bak = NULL;
  136. setResultCore(result);
  137. if (st == NULL){
  138. setResult(result, inter, belong);
  139. return result->type;
  140. }
  141. is_KeyInterrupt = signal_reset;
  142. bak = signal(SIGINT, signalStopInter);
  143. do {
  144. base = st;
  145. if (checkSignal(&type, base->line, base->code_file, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong)))
  146. break;
  147. while (base != NULL) {
  148. freeResult(result);
  149. type = runStatement(CALL_INTER_FUNCTIONSIG(base, var_list, result, belong));
  150. if (checkSignal(&type, base->line, base->code_file, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong)))
  151. break;
  152. if (type == goto_return && result->times == 0){
  153. Statement *label_st = checkLabel(st, result->label);
  154. if (label_st == NULL){
  155. setResultErrorSt(E_GotoException, "Don't find label", true, st, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  156. type = error_return;
  157. break;
  158. }
  159. type = runLabel(CALL_INTER_FUNCTIONSIG(label_st, var_list, result, belong));
  160. if (!RUN_TYPE(type))
  161. break;
  162. base = label_st->next;
  163. }
  164. else if (!RUN_TYPE(type))
  165. break;
  166. else
  167. base = base->next;
  168. }
  169. } while (type == restart_return && result->times == 0);
  170. if (type == not_return || type == restart_return)
  171. setResultOperationNone(result, inter, belong);
  172. result->node = base;
  173. #if START_GC
  174. gc_run(inter, var_list, 1, 0, 0, var_list);
  175. #endif
  176. signal(SIGINT, bak);
  177. return result->type;
  178. }
  179. /**
  180. * 全局程序运行statement
  181. * @param inter
  182. * @return
  183. */
  184. ResultType globalIterStatement(Result *result, Inter *inter, Statement *st) {
  185. ResultType type;
  186. VarList *var_list = NULL;
  187. Statement *base;
  188. LinkValue *belong = inter->base_father;
  189. void *bak = NULL;
  190. if (st == NULL){
  191. setResult(result, inter, belong);
  192. return result->type;
  193. }
  194. is_KeyInterrupt = signal_reset;
  195. bak = signal(SIGINT, signalStopInter);
  196. gc_addTmpLink(&belong->gc_status);
  197. do {
  198. base = st;
  199. var_list = inter->var_list;
  200. if (checkSignal(&type, base->line, base->code_file, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong)))
  201. break;
  202. while (base != NULL) {
  203. freeResult(result);
  204. type = runStatement(CALL_INTER_FUNCTIONSIG(base, var_list, result, belong));
  205. if (checkSignal(&type, base->line, base->code_file, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong)))
  206. break;
  207. if (type == goto_return){
  208. Statement *label_st = checkLabel(st, result->label);
  209. if (label_st == NULL){
  210. setResultErrorSt(E_GotoException, "Don't find label", true, st, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  211. type = error_return;
  212. break;
  213. }
  214. type = runLabel(CALL_INTER_FUNCTIONSIG(label_st, var_list, result, belong));
  215. if (!RUN_TYPE(type))
  216. break;
  217. base = label_st->next;
  218. }
  219. else if (!RUN_TYPE(type))
  220. break;
  221. else
  222. base = base->next;
  223. }
  224. } while (type == restart_return && result->times == 0);
  225. if (type != error_return && type != function_return)
  226. setResultOperationNone(result, inter, belong);
  227. result->node = base;
  228. #if START_GC
  229. gc_freeTmpLink(&belong->gc_status);
  230. gc_run(inter, var_list, 1, 0, 0, var_list);
  231. #endif
  232. signal(SIGINT, bak);
  233. return result->type;
  234. }
  235. // 若需要中断执行, 则返回true
  236. bool operationSafeInterStatement(INTER_FUNCTIONSIG){
  237. ResultType type;
  238. type = iterStatement(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  239. if (RUN_TYPE(type))
  240. return false;
  241. else if (type != return_code && type != error_return)
  242. setResultErrorSt(E_ResultException, "Operation get not support result type", true, st, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
  243. return true;
  244. }
  245. bool ifBranchSafeInterStatement(INTER_FUNCTIONSIG){
  246. ResultType type;
  247. type = iterStatement(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  248. if (RUN_TYPE(type))
  249. return false;
  250. if (type == rego_return){
  251. result->times--;
  252. if (result->times < 0)
  253. return false;
  254. }
  255. if (type == restart_return || type == goto_return)
  256. result->times--;
  257. return true;
  258. }
  259. bool cycleBranchSafeInterStatement(INTER_FUNCTIONSIG){
  260. ResultType type;
  261. type = iterStatement(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  262. if (RUN_TYPE(type))
  263. return false;
  264. if (type == break_return || type == continue_return){
  265. result->times--;
  266. if (result->times < 0)
  267. return false;
  268. }
  269. if (type == restart_return || type == goto_return)
  270. result->times--;
  271. return true;
  272. }
  273. bool tryBranchSafeInterStatement(INTER_FUNCTIONSIG){
  274. ResultType type;
  275. type = iterStatement(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  276. if (RUN_TYPE(type))
  277. return false;
  278. if (type == restart_return || type == goto_return)
  279. result->times--;
  280. return true;
  281. }
  282. bool functionSafeInterStatement(INTER_FUNCTIONSIG){
  283. ResultType type;
  284. type = iterStatement(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  285. if (type == error_return || result->type == yield_return)
  286. return true;
  287. else if (type == function_return)
  288. result->type = operation_return;
  289. else
  290. result->type = not_return;
  291. return false;
  292. }
  293. bool blockSafeInterStatement(INTER_FUNCTIONSIG){
  294. ResultType type;
  295. type = iterStatement(CALL_INTER_FUNCTIONSIG(st, var_list, result, belong));
  296. if (type == error_return || type == yield_return)
  297. return true;
  298. result->type = operation_return;
  299. return false;
  300. }
  301. Statement *checkLabel(Statement *base, char *label){
  302. for (PASS; base != NULL; base = base->next)
  303. if (base->type == label_ && eqString(base->u.label_.label, label))
  304. return base;
  305. return NULL;
  306. }
  307. bool is_quitExc(LinkValue *value, Inter *inter) {
  308. return value->value == inter->data.quit_exc->value || checkAttribution(value->value, inter->data.quit_exc->value);
  309. }