gc.c 4.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148
  1. #include "__virtualmath.h"
  2. void gc_iterLinkValue(LinkValue *value){
  3. if (value == NULL)
  4. return;
  5. gc_addLink(&value->gc_status);
  6. if (!gc_IterAlready(&value->gc_status)){
  7. gc_iterLinkValue(value->father);
  8. gc_iterValue(value->value);
  9. }
  10. }
  11. void gc_fatherValue(FatherValue *value){
  12. for (PASS; value != NULL; value = value->next)
  13. gc_iterLinkValue(value->value);
  14. }
  15. void gc_iterValue(Value *value){
  16. if (value == NULL)
  17. return;
  18. gc_addLink(&value->gc_status);
  19. if (gc_IterAlready(&value->gc_status))
  20. return;
  21. gc_varList(value->object.var);
  22. gc_varList(value->object.out_var);
  23. gc_fatherValue(value->object.father);
  24. switch (value->type) {
  25. case list:
  26. for (int i=0;i < value->data.list.size;i++)
  27. gc_iterLinkValue(value->data.list.list[i]);
  28. break;
  29. case dict:
  30. gc_iterHashTable(value->data.dict.dict);
  31. break;
  32. default:
  33. break;
  34. }
  35. }
  36. void gc_varList(VarList *vl){
  37. for (PASS; vl != NULL; vl = vl->next)
  38. gc_iterHashTable(vl->hashtable);
  39. }
  40. void gc_iterHashTable(HashTable *ht){
  41. if (ht == NULL)
  42. return;
  43. gc_addLink(&ht->gc_status);
  44. if (gc_IterAlready(&ht->gc_status))
  45. return;
  46. for (int i=0;i < MAX_SIZE;i++)
  47. gc_iterVar(ht->hashtable[i]);
  48. }
  49. void gc_iterVar(Var *var){
  50. if (var == NULL)
  51. return;
  52. gc_addLink(&var->gc_status);
  53. if (gc_IterAlready(&var->gc_status))
  54. return;
  55. for (PASS; var != NULL; var = var->next){
  56. gc_iterLinkValue(var->name_);
  57. gc_iterLinkValue(var->value);
  58. }
  59. }
  60. void gc_resetBase(Inter *inter){
  61. for (Value *value_base = inter->base; value_base != NULL; value_base = value_base->gc_next)
  62. resetGC(&value_base->gc_status);
  63. for (LinkValue *link_base = inter->link_base; link_base != NULL; link_base = link_base->gc_next)
  64. resetGC(&link_base->gc_status);
  65. for (HashTable *hash_base = inter->hash_base; hash_base != NULL; hash_base = hash_base->gc_next)
  66. resetGC(&hash_base->gc_status);
  67. for (Var *var_base = inter->base_var; var_base != NULL; var_base = var_base->gc_next)
  68. resetGC(&var_base->gc_status);
  69. }
  70. void gc_checkBase(Inter *inter){
  71. for (Value *value_base = inter->base; value_base != NULL; value_base = value_base->gc_next)
  72. if (!gc_needFree(&value_base->gc_status) && !value_base->gc_status.continue_)
  73. gc_iterValue(value_base);
  74. for (LinkValue *link_base = inter->link_base; link_base != NULL; link_base = link_base->gc_next)
  75. if (!gc_needFree(&link_base->gc_status) && !link_base->gc_status.continue_)
  76. gc_iterLinkValue(link_base);
  77. for (HashTable *hash_base = inter->hash_base; hash_base != NULL; hash_base = hash_base->gc_next)
  78. if (!gc_needFree(&hash_base->gc_status) && !hash_base->gc_status.continue_)
  79. gc_iterHashTable(hash_base);
  80. for (Var *var_base = inter->base_var; var_base != NULL; var_base = var_base->gc_next)
  81. if (!gc_needFree(&var_base->gc_status) && !var_base->gc_status.continue_)
  82. gc_iterVar(var_base);
  83. }
  84. void gc_freeBase(Inter *inter){
  85. #if START_GC
  86. for (Value **value_base = &inter->base; *value_base != NULL;)
  87. if (gc_needFree(&(*value_base)->gc_status))
  88. freeValue(value_base);
  89. else
  90. value_base = &(*value_base)->gc_next;
  91. for (LinkValue **link_base = &inter->link_base; *link_base != NULL;)
  92. if (gc_needFree(&(*link_base)->gc_status))
  93. freeLinkValue(link_base);
  94. else
  95. link_base = &(*link_base)->gc_next;
  96. for (HashTable **hash_base = &inter->hash_base; *hash_base != NULL;)
  97. if (gc_needFree(&(*hash_base)->gc_status))
  98. freeHashTable(hash_base);
  99. else
  100. hash_base = &(*hash_base)->gc_next;
  101. for (Var **var_base = &inter->base_var; *var_base != NULL;)
  102. if (gc_needFree(&(*var_base)->gc_status))
  103. freeVar(var_base);
  104. else
  105. var_base = &(*var_base)->gc_next;
  106. #endif
  107. }
  108. void gc_run(Inter *inter, int var_list, int link_value, int value, ...){
  109. #if START_GC
  110. gc_resetBase(inter);
  111. va_list arg;
  112. va_start(arg, value);
  113. for (int i =0;i < var_list;i ++){
  114. VarList *tmp = va_arg(arg, VarList *);
  115. gc_varList(tmp);
  116. }
  117. for (int i =0;i < link_value;i ++){
  118. LinkValue *tmp = va_arg(arg, LinkValue *);
  119. gc_iterLinkValue(tmp);
  120. }
  121. for (int i =0;i < value;i ++){
  122. Value *tmp = va_arg(arg, Value *);
  123. gc_iterValue(tmp);
  124. }
  125. va_end(arg);
  126. gc_checkBase(inter);
  127. gc_freeBase(inter);
  128. #endif
  129. }