nwasmutil.pas 5.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157
  1. {
  2. Copyright (c) 2021 by Nikolay Nikolov
  3. WebAssembly version of some node tree helper routines
  4. This program is free software; you can redistribute it and/or modify
  5. it under the terms of the GNU General Public License as published by
  6. the Free Software Foundation; either version 2 of the License, or
  7. (at your option) any later version.
  8. This program is distributed in the hope that it will be useful,
  9. but WITHOUT ANY WARRANTY; without even the implied warranty of
  10. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  11. GNU General Public License for more details.
  12. You should have received a copy of the GNU General Public License
  13. along with this program; if not, write to the Free Software
  14. Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  15. ****************************************************************************
  16. }
  17. unit nwasmutil;
  18. {$i fpcdefs.inc}
  19. interface
  20. uses
  21. ngenutil,
  22. symsym;
  23. type
  24. { twasmnodeutils }
  25. twasmnodeutils = class(tnodeutils)
  26. public
  27. class procedure insertbssdata(sym : tstaticvarsym); override;
  28. class procedure InsertObjectInfo; override;
  29. end;
  30. implementation
  31. uses
  32. globtype,globals,
  33. cpubase,
  34. aasmbase,aasmdata,aasmtai,aasmcpu,
  35. hlcgobj,hlcgcpu,
  36. symdef,symtype,symconst,symcpu,
  37. fmodule;
  38. { twasmnodeutils }
  39. class procedure twasmnodeutils.insertbssdata(sym: tstaticvarsym);
  40. var
  41. symcpu: tcpustaticvarsym;
  42. begin
  43. symcpu:=tcpustaticvarsym(sym);
  44. if symcpu.is_wasm_global then
  45. // don't reserve bss data for wasm global vars
  46. else
  47. inherited;
  48. end;
  49. class procedure twasmnodeutils.InsertObjectInfo;
  50. procedure WriteImportDll(list: TAsmList; proc: tprocdef);
  51. begin
  52. thlcgwasm(hlcg).g_procdef(list,proc);
  53. list.Concat(tai_import_module.create(proc.mangledname,proc.import_dll^));
  54. list.Concat(tai_import_name.create(proc.mangledname,proc.import_name^));
  55. end;
  56. procedure InsertUnitInfo(list : TAsmList;cur_unit: tused_unit);
  57. var
  58. i: Integer;
  59. def : tdef;
  60. proc : tprocdef;
  61. begin
  62. if (cur_unit.u.moduleflags * [mf_init,mf_finalize])<>[] then
  63. begin
  64. if mf_init in cur_unit.u.moduleflags then
  65. list.Concat(tai_functype.create(make_mangledname('INIT$',cur_unit.u.globalsymtable,''),TWasmFuncType.Create([],[])));
  66. if mf_finalize in cur_unit.u.moduleflags then
  67. list.Concat(tai_functype.create(make_mangledname('FINALIZE$',cur_unit.u.globalsymtable,''),TWasmFuncType.Create([],[])));
  68. end;
  69. for i:=0 to cur_unit.u.deflist.Count-1 do
  70. begin
  71. def:=tdef(cur_unit.u.deflist[i]);
  72. if assigned(def) and (tdef(def).typ = procdef) then
  73. begin
  74. proc := tprocdef(def);
  75. if (po_external in proc.procoptions) and (po_has_importdll in proc.procoptions) then
  76. WriteImportDll(list,proc)
  77. else if not proc.owner.iscurrentunit or (po_external in proc.procoptions) then
  78. thlcgwasm(hlcg).g_procdef(list,proc);
  79. end;
  80. end;
  81. end;
  82. var
  83. i : integer;
  84. def : tdef;
  85. proc : tprocdef;
  86. list : TAsmList;
  87. cur_unit: tused_unit;
  88. begin
  89. inherited;
  90. list:=current_asmdata.asmlists[al_start];
  91. list.Concat(tai_globaltype.create(STACK_POINTER_SYM,wbt_i32,false));
  92. if ts_wasm_threads in current_settings.targetswitches then
  93. begin
  94. list.Concat(tai_globaltype.create(TLS_SIZE_SYM,wbt_i32,true));
  95. list.Concat(tai_globaltype.create(TLS_ALIGN_SYM,wbt_i32,true));
  96. list.Concat(tai_globaltype.create(TLS_BASE_SYM,wbt_i32,false));
  97. end;
  98. if ts_wasm_native_exceptions in current_settings.targetswitches then
  99. begin
  100. list.Concat(tai_tagtype.create(FPC_EXCEPTION_TAG_SYM, []));
  101. list.Concat(tai_symbol.Create_Weak(current_asmdata.WeakRefAsmSymbol(FPC_EXCEPTION_TAG_SYM,AT_WASM_EXCEPTION_TAG),0));
  102. end;
  103. for i:=0 to current_module.deflist.Count-1 do
  104. begin
  105. def:=tdef(current_module.deflist[i]);
  106. { since commit 48986 deflist might have NIL entries }
  107. if assigned(def) and (def.typ=procdef) then
  108. begin
  109. proc := tprocdef(def);
  110. if po_external in proc.procoptions then
  111. if po_has_importdll in proc.procoptions then
  112. WriteImportDll(list,proc)
  113. else
  114. thlcgwasm(hlcg).g_procdef(list,proc);
  115. end;
  116. end;
  117. cur_unit:=tused_unit(usedunits.First);
  118. while assigned(cur_unit) do
  119. begin
  120. InsertUnitInfo(list,cur_unit);
  121. cur_unit:=tused_unit(cur_unit.Next);
  122. end;
  123. cur_unit:=tused_unit(current_module.used_units.First);
  124. while assigned(cur_unit) do
  125. begin
  126. InsertUnitInfo(list,cur_unit);
  127. cur_unit:=tused_unit(cur_unit.Next);
  128. end;
  129. end;
  130. begin
  131. cnodeutils:=twasmnodeutils;
  132. end.