Validator.cpp 99 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355235623572358235923602361236223632364236523662367236823692370237123722373237423752376237723782379238023812382238323842385238623872388238923902391239223932394239523962397239823992400240124022403240424052406240724082409241024112412241324142415241624172418241924202421242224232424242524262427242824292430243124322433243424352436243724382439244024412442244324442445244624472448244924502451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499250025012502250325042505250625072508250925102511251225132514251525162517251825192520252125222523252425252526252725282529253025312532253325342535253625372538253925402541254225432544254525462547254825492550255125522553255425552556255725582559256025612562256325642565256625672568256925702571257225732574257525762577257825792580258125822583258425852586258725882589259025912592259325942595259625972598259926002601260226032604260526062607260826092610261126122613261426152616261726182619262026212622262326242625262626272628262926302631263226332634263526362637263826392640264126422643264426452646264726482649265026512652265326542655265626572658265926602661266226632664266526662667266826692670267126722673267426752676267726782679268026812682268326842685268626872688268926902691269226932694269526962697269826992700270127022703270427052706270727082709271027112712271327142715271627172718271927202721272227232724272527262727272827292730273127322733273427352736273727382739274027412742274327442745274627472748274927502751275227532754275527562757275827592760276127622763276427652766276727682769277027712772277327742775277627772778277927802781278227832784278527862787278827892790279127922793279427952796279727982799280028012802280328042805280628072808280928102811281228132814281528162817281828192820282128222823282428252826282728282829283028312832283328342835283628372838283928402841284228432844284528462847284828492850285128522853285428552856285728582859286028612862286328642865286628672868286928702871287228732874287528762877287828792880288128822883288428852886288728882889289028912892289328942895289628972898289929002901290229032904290529062907290829092910291129122913291429152916291729182919292029212922292329242925292629272928292929302931293229332934293529362937293829392940294129422943294429452946294729482949295029512952295329542955295629572958295929602961296229632964296529662967296829692970297129722973297429752976297729782979298029812982298329842985298629872988298929902991299229932994299529962997299829993000300130023003300430053006300730083009301030113012301330143015301630173018301930203021302230233024302530263027302830293030303130323033303430353036303730383039304030413042304330443045304630473048304930503051305230533054305530563057305830593060306130623063306430653066306730683069307030713072307330743075307630773078307930803081308230833084308530863087308830893090309130923093309430953096309730983099310031013102310331043105310631073108310931103111311231133114311531163117311831193120312131223123312431253126312731283129313031313132313331343135313631373138313931403141314231433144314531463147314831493150315131523153315431553156315731583159316031613162316331643165316631673168316931703171317231733174317531763177317831793180318131823183318431853186318731883189319031913192319331943195319631973198319932003201320232033204320532063207320832093210321132123213321432153216321732183219322032213222322332243225322632273228322932303231323232333234323532363237323832393240324132423243324432453246324732483249325032513252325332543255325632573258325932603261326232633264326532663267326832693270327132723273327432753276327732783279328032813282328332843285328632873288328932903291329232933294329532963297329832993300330133023303330433053306330733083309331033113312331333143315331633173318331933203321332233233324332533263327332833293330333133323333333433353336333733383339334033413342334333443345334633473348334933503351335233533354335533563357335833593360336133623363336433653366336733683369337033713372337333743375337633773378337933803381338233833384338533863387338833893390339133923393339433953396339733983399340034013402340334043405340634073408340934103411341234133414341534163417341834193420342134223423342434253426342734283429343034313432343334343435343634373438343934403441344234433444344534463447344834493450345134523453345434553456345734583459346034613462346334643465346634673468346934703471347234733474347534763477347834793480348134823483348434853486348734883489349034913492349334943495349634973498349935003501350235033504350535063507350835093510351135123513351435153516351735183519352035213522352335243525352635273528352935303531353235333534353535363537353835393540354135423543354435453546354735483549355035513552355335543555355635573558355935603561356235633564356535663567356835693570357135723573357435753576357735783579358035813582358335843585358635873588358935903591359235933594359535963597359835993600360136023603360436053606360736083609361036113612361336143615361636173618361936203621362236233624362536263627362836293630363136323633363436353636363736383639364036413642364336443645364636473648364936503651365236533654365536563657365836593660366136623663366436653666366736683669367036713672367336743675367636773678367936803681368236833684368536863687368836893690369136923693369436953696369736983699370037013702370337043705370637073708370937103711371237133714371537163717371837193720372137223723372437253726372737283729373037313732373337343735373637373738373937403741
  1. /*
  2. * Copyright (c) 2021, Ali Mohammad Pur <mpfard@serenityos.org>
  3. *
  4. * SPDX-License-Identifier: BSD-2-Clause
  5. */
  6. #include <AK/HashTable.h>
  7. #include <AK/SourceLocation.h>
  8. #include <AK/TemporaryChange.h>
  9. #include <AK/Try.h>
  10. #include <LibWasm/AbstractMachine/Validator.h>
  11. #include <LibWasm/Printer/Printer.h>
  12. namespace Wasm {
  13. ErrorOr<void, ValidationError> Validator::validate(Module& module)
  14. {
  15. // Pre-emptively make invalid. The module will be set to `Valid` at the end
  16. // of validation.
  17. module.set_validation_status(Module::ValidationStatus::Invalid, {});
  18. // Note: The spec performs this after populating the context, but there's no real reason to do so,
  19. // as this has no dependency.
  20. HashTable<StringView> seen_export_names;
  21. for (auto& export_ : module.export_section().entries())
  22. if (seen_export_names.try_set(export_.name()).release_value_but_fixme_should_propagate_errors() != AK::HashSetResult::InsertedNewEntry)
  23. return Errors::duplicate_export_name(export_.name());
  24. m_context = {};
  25. m_context.types.extend(module.type_section().types());
  26. m_context.data_count = module.data_count_section().count();
  27. for (auto& import_ : module.import_section().imports()) {
  28. TRY(import_.description().visit(
  29. [&](TypeIndex const& index) -> ErrorOr<void, ValidationError> {
  30. if (m_context.types.size() > index.value())
  31. m_context.functions.append(m_context.types[index.value()]);
  32. else
  33. return Errors::invalid("TypeIndex"sv);
  34. m_context.imported_function_count++;
  35. return {};
  36. },
  37. [&](FunctionType const& type) -> ErrorOr<void, ValidationError> {
  38. m_context.functions.append(type);
  39. m_context.imported_function_count++;
  40. return {};
  41. },
  42. [&](TableType const& type) -> ErrorOr<void, ValidationError> {
  43. m_context.tables.append(type);
  44. return {};
  45. },
  46. [&](MemoryType const& type) -> ErrorOr<void, ValidationError> {
  47. m_context.memories.append(type);
  48. return {};
  49. },
  50. [&](GlobalType const& type) -> ErrorOr<void, ValidationError> {
  51. m_globals_without_internal_globals.append(type);
  52. m_context.globals.append(type);
  53. return {};
  54. }));
  55. }
  56. if (module.code_section().functions().size() != module.function_section().types().size())
  57. return Errors::invalid("FunctionSection"sv);
  58. m_context.functions.ensure_capacity(module.function_section().types().size() + m_context.functions.size());
  59. for (auto& index : module.function_section().types())
  60. if (m_context.types.size() > index.value())
  61. m_context.functions.append(m_context.types[index.value()]);
  62. else
  63. return Errors::invalid("TypeIndex"sv);
  64. m_context.tables.ensure_capacity(m_context.tables.size() + module.table_section().tables().size());
  65. for (auto& table : module.table_section().tables())
  66. m_context.tables.append(table.type());
  67. m_context.memories.ensure_capacity(m_context.memories.size() + module.memory_section().memories().size());
  68. for (auto& memory : module.memory_section().memories())
  69. m_context.memories.append(memory.type());
  70. m_context.globals.ensure_capacity(m_context.globals.size() + module.global_section().entries().size());
  71. for (auto& global : module.global_section().entries())
  72. m_context.globals.append(global.type());
  73. m_context.elements.ensure_capacity(module.element_section().segments().size());
  74. for (auto& segment : module.element_section().segments())
  75. m_context.elements.append(segment.type);
  76. m_context.datas.resize(module.data_section().data().size());
  77. // We need to build the set of declared functions to check that `ref.func` uses a specific set of predetermined functions, found in:
  78. // - Element initializer expressions
  79. // - Global initializer expressions
  80. // - Exports
  81. auto scan_expression_for_function_indices = [&](auto& expression) {
  82. for (auto& instruction : expression.instructions()) {
  83. if (instruction.opcode() == Instructions::ref_func) {
  84. auto index = instruction.arguments().template get<FunctionIndex>();
  85. m_context.references->tree.insert(index.value(), index);
  86. }
  87. }
  88. };
  89. for (auto& export_ : module.export_section().entries()) {
  90. if (!export_.description().has<FunctionIndex>())
  91. continue;
  92. auto index = export_.description().get<FunctionIndex>();
  93. m_context.references->tree.insert(index.value(), index);
  94. }
  95. for (auto& segment : module.element_section().segments()) {
  96. for (auto& expression : segment.init)
  97. scan_expression_for_function_indices(expression);
  98. }
  99. for (auto& segment : module.global_section().entries())
  100. scan_expression_for_function_indices(segment.expression());
  101. TRY(validate(module.import_section()));
  102. TRY(validate(module.export_section()));
  103. TRY(validate(module.start_section()));
  104. TRY(validate(module.data_section()));
  105. TRY(validate(module.element_section()));
  106. TRY(validate(module.global_section()));
  107. TRY(validate(module.memory_section()));
  108. TRY(validate(module.table_section()));
  109. TRY(validate(module.code_section()));
  110. module.set_validation_status(Module::ValidationStatus::Valid, {});
  111. return {};
  112. }
  113. ErrorOr<void, ValidationError> Validator::validate(ImportSection const& section)
  114. {
  115. for (auto& import_ : section.imports())
  116. TRY(import_.description().visit([&](auto& entry) { return validate(entry); }));
  117. return {};
  118. }
  119. ErrorOr<void, ValidationError> Validator::validate(ExportSection const& section)
  120. {
  121. for (auto& export_ : section.entries())
  122. TRY(export_.description().visit([&](auto& entry) { return validate(entry); }));
  123. return {};
  124. }
  125. ErrorOr<void, ValidationError> Validator::validate(StartSection const& section)
  126. {
  127. if (!section.function().has_value())
  128. return {};
  129. TRY(validate(section.function()->index()));
  130. FunctionType const& type = m_context.functions[section.function()->index().value()];
  131. if (!type.parameters().is_empty() || !type.results().is_empty())
  132. return Errors::invalid("start function signature"sv);
  133. return {};
  134. }
  135. ErrorOr<void, ValidationError> Validator::validate(DataSection const& section)
  136. {
  137. if (m_context.data_count.has_value() && section.data().size() != m_context.data_count)
  138. return Errors::invalid("data count does not match segment count"sv);
  139. for (auto& entry : section.data()) {
  140. TRY(entry.value().visit(
  141. [](DataSection::Data::Passive const&) { return ErrorOr<void, ValidationError> {}; },
  142. [&](DataSection::Data::Active const& active) -> ErrorOr<void, ValidationError> {
  143. TRY(validate(active.index));
  144. auto expression_result = TRY(validate(active.offset, { ValueType(ValueType::I32) }));
  145. if (!expression_result.is_constant)
  146. return Errors::invalid("active data initializer"sv);
  147. if (expression_result.result_types.size() != 1 || !expression_result.result_types.first().is_of_kind(ValueType::I32))
  148. return Errors::invalid("active data initializer type"sv, ValueType(ValueType::I32), expression_result.result_types);
  149. return {};
  150. }));
  151. }
  152. return {};
  153. }
  154. ErrorOr<void, ValidationError> Validator::validate(ElementSection const& section)
  155. {
  156. for (auto& segment : section.segments()) {
  157. TRY(segment.mode.visit(
  158. [](ElementSection::Declarative const&) -> ErrorOr<void, ValidationError> { return {}; },
  159. [](ElementSection::Passive const&) -> ErrorOr<void, ValidationError> { return {}; },
  160. [&](ElementSection::Active const& active) -> ErrorOr<void, ValidationError> {
  161. TRY(validate(active.index));
  162. auto table = m_context.tables[active.index.value()];
  163. if (table.element_type() != segment.type)
  164. return Errors::invalid("active element reference type"sv);
  165. auto expression_result = TRY(validate(active.expression, { ValueType(ValueType::I32) }));
  166. if (!expression_result.is_constant)
  167. return Errors::invalid("active element initializer"sv);
  168. if (expression_result.result_types.size() != 1 || !expression_result.result_types.first().is_of_kind(ValueType::I32))
  169. return Errors::invalid("active element initializer type"sv, ValueType(ValueType::I32), expression_result.result_types);
  170. return {};
  171. }));
  172. for (auto& expression : segment.init) {
  173. if (expression.instructions().is_empty())
  174. continue;
  175. auto result = TRY(validate(expression, { segment.type }));
  176. if (!result.is_constant)
  177. return Errors::invalid("element initializer"sv);
  178. }
  179. }
  180. return {};
  181. }
  182. ErrorOr<void, ValidationError> Validator::validate(GlobalSection const& section)
  183. {
  184. TemporaryChange omit_internal_globals { m_context.globals, m_globals_without_internal_globals };
  185. for (auto& entry : section.entries()) {
  186. auto& type = entry.type();
  187. TRY(validate(type));
  188. auto expression_result = TRY(validate(entry.expression(), { type.type() }));
  189. if (!expression_result.is_constant)
  190. return Errors::invalid("global variable initializer"sv);
  191. if (expression_result.result_types.size() != 1 || !expression_result.result_types.first().is_of_kind(type.type().kind()))
  192. return Errors::invalid("global variable initializer type"sv, ValueType(ValueType::I32), expression_result.result_types);
  193. }
  194. return {};
  195. }
  196. ErrorOr<void, ValidationError> Validator::validate(MemorySection const& section)
  197. {
  198. for (auto& entry : section.memories())
  199. TRY(validate(entry.type()));
  200. return {};
  201. }
  202. ErrorOr<void, ValidationError> Validator::validate(TableSection const& section)
  203. {
  204. for (auto& entry : section.tables())
  205. TRY(validate(entry.type()));
  206. return {};
  207. }
  208. ErrorOr<void, ValidationError> Validator::validate(CodeSection const& section)
  209. {
  210. size_t index = m_context.imported_function_count;
  211. for (auto& entry : section.functions()) {
  212. auto function_index = index++;
  213. TRY(validate(FunctionIndex { function_index }));
  214. auto& function_type = m_context.functions[function_index];
  215. auto& function = entry.func();
  216. auto function_validator = fork();
  217. function_validator.m_context.locals = {};
  218. function_validator.m_context.locals.extend(function_type.parameters());
  219. for (auto& local : function.locals()) {
  220. for (size_t i = 0; i < local.n(); ++i)
  221. function_validator.m_context.locals.append(local.type());
  222. }
  223. function_validator.m_frames.empend(function_type, FrameKind::Function, (size_t)0);
  224. auto results = TRY(function_validator.validate(function.body(), function_type.results()));
  225. if (results.result_types.size() != function_type.results().size())
  226. return Errors::invalid("function result"sv, function_type.results(), results.result_types);
  227. }
  228. return {};
  229. }
  230. ErrorOr<void, ValidationError> Validator::validate(TableType const& type)
  231. {
  232. return validate(type.limits(), (1ull << 32) - 1);
  233. }
  234. ErrorOr<void, ValidationError> Validator::validate(MemoryType const& type)
  235. {
  236. return validate(type.limits(), 1 << 16);
  237. }
  238. ErrorOr<FunctionType, ValidationError> Validator::validate(BlockType const& type)
  239. {
  240. if (type.kind() == BlockType::Index) {
  241. TRY(validate(type.type_index()));
  242. return m_context.types[type.type_index().value()];
  243. }
  244. if (type.kind() == BlockType::Type) {
  245. FunctionType function_type { {}, { type.value_type() } };
  246. TRY(validate(function_type));
  247. return function_type;
  248. }
  249. if (type.kind() == BlockType::Empty)
  250. return FunctionType { {}, {} };
  251. return Errors::invalid("BlockType"sv);
  252. }
  253. ErrorOr<void, ValidationError> Validator::validate(Limits const& limits, u64 bound)
  254. {
  255. auto check_bound = [bound](auto value) {
  256. return static_cast<u64>(value) <= bound;
  257. };
  258. if (!check_bound(limits.min()))
  259. return Errors::out_of_bounds("limit minimum"sv, limits.min(), 0, bound);
  260. if (limits.max().has_value() && (limits.max().value() < limits.min() || !check_bound(*limits.max()))) {
  261. return Errors::out_of_bounds("limit maximum"sv, limits.max().value(), limits.min(), bound);
  262. }
  263. return {};
  264. }
  265. template<u64 opcode>
  266. ErrorOr<void, ValidationError> Validator::validate_instruction(Instruction const& instruction, Stack&, bool&)
  267. {
  268. return Errors::invalid(ByteString::formatted("instruction opcode ({:#x}) (missing validation!)", instruction.opcode().value()));
  269. }
  270. #define VALIDATE_INSTRUCTION(name) \
  271. template<> \
  272. ErrorOr<void, ValidationError> Validator::validate_instruction<Instructions::name.value()>([[maybe_unused]] Instruction const& instruction, [[maybe_unused]] Stack& stack, [[maybe_unused]] bool& is_constant)
  273. // https://webassembly.github.io/spec/core/bikeshed/#-tmathsfhrefsyntax-instr-numericmathsfconstc
  274. VALIDATE_INSTRUCTION(i32_const)
  275. {
  276. is_constant = true;
  277. stack.append(ValueType(ValueType::I32));
  278. return {};
  279. }
  280. VALIDATE_INSTRUCTION(i64_const)
  281. {
  282. is_constant = true;
  283. stack.append(ValueType(ValueType::I64));
  284. return {};
  285. }
  286. VALIDATE_INSTRUCTION(f32_const)
  287. {
  288. is_constant = true;
  289. stack.append(ValueType(ValueType::F32));
  290. return {};
  291. }
  292. VALIDATE_INSTRUCTION(f64_const)
  293. {
  294. is_constant = true;
  295. stack.append(ValueType(ValueType::F64));
  296. return {};
  297. }
  298. // https://webassembly.github.io/spec/core/bikeshed/#-tmathsfhrefsyntax-unopmathitunop
  299. VALIDATE_INSTRUCTION(i32_clz)
  300. {
  301. TRY(stack.take_and_put<ValueType::I32>(ValueType::I32));
  302. return {};
  303. }
  304. VALIDATE_INSTRUCTION(i32_ctz)
  305. {
  306. TRY(stack.take_and_put<ValueType::I32>(ValueType::I32));
  307. return {};
  308. }
  309. VALIDATE_INSTRUCTION(i32_popcnt)
  310. {
  311. TRY(stack.take_and_put<ValueType::I32>(ValueType::I32));
  312. return {};
  313. }
  314. VALIDATE_INSTRUCTION(i64_clz)
  315. {
  316. TRY(stack.take_and_put<ValueType::I64>(ValueType::I64));
  317. return {};
  318. }
  319. VALIDATE_INSTRUCTION(i64_ctz)
  320. {
  321. TRY(stack.take_and_put<ValueType::I64>(ValueType::I64));
  322. return {};
  323. }
  324. VALIDATE_INSTRUCTION(i64_popcnt)
  325. {
  326. TRY(stack.take_and_put<ValueType::I64>(ValueType::I64));
  327. return {};
  328. }
  329. VALIDATE_INSTRUCTION(f32_abs)
  330. {
  331. TRY(stack.take_and_put<ValueType::F32>(ValueType::F32));
  332. return {};
  333. }
  334. VALIDATE_INSTRUCTION(f32_neg)
  335. {
  336. TRY(stack.take_and_put<ValueType::F32>(ValueType::F32));
  337. return {};
  338. }
  339. VALIDATE_INSTRUCTION(f32_sqrt)
  340. {
  341. TRY(stack.take_and_put<ValueType::F32>(ValueType::F32));
  342. return {};
  343. }
  344. VALIDATE_INSTRUCTION(f32_ceil)
  345. {
  346. TRY(stack.take_and_put<ValueType::F32>(ValueType::F32));
  347. return {};
  348. }
  349. VALIDATE_INSTRUCTION(f32_floor)
  350. {
  351. TRY(stack.take_and_put<ValueType::F32>(ValueType::F32));
  352. return {};
  353. }
  354. VALIDATE_INSTRUCTION(f32_trunc)
  355. {
  356. TRY(stack.take_and_put<ValueType::F32>(ValueType::F32));
  357. return {};
  358. }
  359. VALIDATE_INSTRUCTION(f32_nearest)
  360. {
  361. TRY(stack.take_and_put<ValueType::F32>(ValueType::F32));
  362. return {};
  363. }
  364. VALIDATE_INSTRUCTION(f64_abs)
  365. {
  366. TRY(stack.take_and_put<ValueType::F64>(ValueType::F64));
  367. return {};
  368. }
  369. VALIDATE_INSTRUCTION(f64_neg)
  370. {
  371. TRY(stack.take_and_put<ValueType::F64>(ValueType::F64));
  372. return {};
  373. }
  374. VALIDATE_INSTRUCTION(f64_sqrt)
  375. {
  376. TRY(stack.take_and_put<ValueType::F64>(ValueType::F64));
  377. return {};
  378. }
  379. VALIDATE_INSTRUCTION(f64_ceil)
  380. {
  381. TRY(stack.take_and_put<ValueType::F64>(ValueType::F64));
  382. return {};
  383. }
  384. VALIDATE_INSTRUCTION(f64_floor)
  385. {
  386. TRY(stack.take_and_put<ValueType::F64>(ValueType::F64));
  387. return {};
  388. }
  389. VALIDATE_INSTRUCTION(f64_trunc)
  390. {
  391. TRY(stack.take_and_put<ValueType::F64>(ValueType::F64));
  392. return {};
  393. }
  394. VALIDATE_INSTRUCTION(f64_nearest)
  395. {
  396. TRY(stack.take_and_put<ValueType::F64>(ValueType::F64));
  397. return {};
  398. }
  399. VALIDATE_INSTRUCTION(i32_extend16_s)
  400. {
  401. TRY(stack.take_and_put<ValueType::I32>(ValueType::I32));
  402. return {};
  403. }
  404. VALIDATE_INSTRUCTION(i32_extend8_s)
  405. {
  406. TRY(stack.take_and_put<ValueType::I32>(ValueType::I32));
  407. return {};
  408. }
  409. VALIDATE_INSTRUCTION(i64_extend32_s)
  410. {
  411. TRY(stack.take_and_put<ValueType::I64>(ValueType::I64));
  412. return {};
  413. }
  414. VALIDATE_INSTRUCTION(i64_extend16_s)
  415. {
  416. TRY(stack.take_and_put<ValueType::I64>(ValueType::I64));
  417. return {};
  418. }
  419. VALIDATE_INSTRUCTION(i64_extend8_s)
  420. {
  421. TRY(stack.take_and_put<ValueType::I64>(ValueType::I64));
  422. return {};
  423. }
  424. // https://webassembly.github.io/spec/core/bikeshed/#-tmathsfhrefsyntax-binopmathitbinop
  425. VALIDATE_INSTRUCTION(i32_add)
  426. {
  427. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  428. stack.append(ValueType(ValueType::I32));
  429. return {};
  430. }
  431. VALIDATE_INSTRUCTION(i32_sub)
  432. {
  433. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  434. stack.append(ValueType(ValueType::I32));
  435. return {};
  436. }
  437. VALIDATE_INSTRUCTION(i32_mul)
  438. {
  439. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  440. stack.append(ValueType(ValueType::I32));
  441. return {};
  442. }
  443. VALIDATE_INSTRUCTION(i32_divs)
  444. {
  445. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  446. stack.append(ValueType(ValueType::I32));
  447. return {};
  448. }
  449. VALIDATE_INSTRUCTION(i32_divu)
  450. {
  451. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  452. stack.append(ValueType(ValueType::I32));
  453. return {};
  454. }
  455. VALIDATE_INSTRUCTION(i32_rems)
  456. {
  457. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  458. stack.append(ValueType(ValueType::I32));
  459. return {};
  460. }
  461. VALIDATE_INSTRUCTION(i32_remu)
  462. {
  463. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  464. stack.append(ValueType(ValueType::I32));
  465. return {};
  466. }
  467. VALIDATE_INSTRUCTION(i32_and)
  468. {
  469. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  470. stack.append(ValueType(ValueType::I32));
  471. return {};
  472. }
  473. VALIDATE_INSTRUCTION(i32_or)
  474. {
  475. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  476. stack.append(ValueType(ValueType::I32));
  477. return {};
  478. }
  479. VALIDATE_INSTRUCTION(i32_xor)
  480. {
  481. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  482. stack.append(ValueType(ValueType::I32));
  483. return {};
  484. }
  485. VALIDATE_INSTRUCTION(i32_shl)
  486. {
  487. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  488. stack.append(ValueType(ValueType::I32));
  489. return {};
  490. }
  491. VALIDATE_INSTRUCTION(i32_shrs)
  492. {
  493. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  494. stack.append(ValueType(ValueType::I32));
  495. return {};
  496. }
  497. VALIDATE_INSTRUCTION(i32_shru)
  498. {
  499. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  500. stack.append(ValueType(ValueType::I32));
  501. return {};
  502. }
  503. VALIDATE_INSTRUCTION(i32_rotl)
  504. {
  505. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  506. stack.append(ValueType(ValueType::I32));
  507. return {};
  508. }
  509. VALIDATE_INSTRUCTION(i32_rotr)
  510. {
  511. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  512. stack.append(ValueType(ValueType::I32));
  513. return {};
  514. }
  515. VALIDATE_INSTRUCTION(i64_add)
  516. {
  517. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  518. stack.append(ValueType(ValueType::I64));
  519. return {};
  520. }
  521. VALIDATE_INSTRUCTION(i64_sub)
  522. {
  523. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  524. stack.append(ValueType(ValueType::I64));
  525. return {};
  526. }
  527. VALIDATE_INSTRUCTION(i64_mul)
  528. {
  529. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  530. stack.append(ValueType(ValueType::I64));
  531. return {};
  532. }
  533. VALIDATE_INSTRUCTION(i64_divs)
  534. {
  535. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  536. stack.append(ValueType(ValueType::I64));
  537. return {};
  538. }
  539. VALIDATE_INSTRUCTION(i64_divu)
  540. {
  541. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  542. stack.append(ValueType(ValueType::I64));
  543. return {};
  544. }
  545. VALIDATE_INSTRUCTION(i64_rems)
  546. {
  547. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  548. stack.append(ValueType(ValueType::I64));
  549. return {};
  550. }
  551. VALIDATE_INSTRUCTION(i64_remu)
  552. {
  553. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  554. stack.append(ValueType(ValueType::I64));
  555. return {};
  556. }
  557. VALIDATE_INSTRUCTION(i64_and)
  558. {
  559. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  560. stack.append(ValueType(ValueType::I64));
  561. return {};
  562. }
  563. VALIDATE_INSTRUCTION(i64_or)
  564. {
  565. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  566. stack.append(ValueType(ValueType::I64));
  567. return {};
  568. }
  569. VALIDATE_INSTRUCTION(i64_xor)
  570. {
  571. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  572. stack.append(ValueType(ValueType::I64));
  573. return {};
  574. }
  575. VALIDATE_INSTRUCTION(i64_shl)
  576. {
  577. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  578. stack.append(ValueType(ValueType::I64));
  579. return {};
  580. }
  581. VALIDATE_INSTRUCTION(i64_shrs)
  582. {
  583. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  584. stack.append(ValueType(ValueType::I64));
  585. return {};
  586. }
  587. VALIDATE_INSTRUCTION(i64_shru)
  588. {
  589. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  590. stack.append(ValueType(ValueType::I64));
  591. return {};
  592. }
  593. VALIDATE_INSTRUCTION(i64_rotl)
  594. {
  595. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  596. stack.append(ValueType(ValueType::I64));
  597. return {};
  598. }
  599. VALIDATE_INSTRUCTION(i64_rotr)
  600. {
  601. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  602. stack.append(ValueType(ValueType::I64));
  603. return {};
  604. }
  605. VALIDATE_INSTRUCTION(f32_add)
  606. {
  607. TRY((stack.take<ValueType::F32, ValueType::F32>()));
  608. stack.append(ValueType(ValueType::F32));
  609. return {};
  610. }
  611. VALIDATE_INSTRUCTION(f32_sub)
  612. {
  613. TRY((stack.take<ValueType::F32, ValueType::F32>()));
  614. stack.append(ValueType(ValueType::F32));
  615. return {};
  616. }
  617. VALIDATE_INSTRUCTION(f32_mul)
  618. {
  619. TRY((stack.take<ValueType::F32, ValueType::F32>()));
  620. stack.append(ValueType(ValueType::F32));
  621. return {};
  622. }
  623. VALIDATE_INSTRUCTION(f32_div)
  624. {
  625. TRY((stack.take<ValueType::F32, ValueType::F32>()));
  626. stack.append(ValueType(ValueType::F32));
  627. return {};
  628. }
  629. VALIDATE_INSTRUCTION(f32_min)
  630. {
  631. TRY((stack.take<ValueType::F32, ValueType::F32>()));
  632. stack.append(ValueType(ValueType::F32));
  633. return {};
  634. }
  635. VALIDATE_INSTRUCTION(f32_max)
  636. {
  637. TRY((stack.take<ValueType::F32, ValueType::F32>()));
  638. stack.append(ValueType(ValueType::F32));
  639. return {};
  640. }
  641. VALIDATE_INSTRUCTION(f32_copysign)
  642. {
  643. TRY((stack.take<ValueType::F32, ValueType::F32>()));
  644. stack.append(ValueType(ValueType::F32));
  645. return {};
  646. }
  647. VALIDATE_INSTRUCTION(f64_add)
  648. {
  649. TRY((stack.take<ValueType::F64, ValueType::F64>()));
  650. stack.append(ValueType(ValueType::F64));
  651. return {};
  652. }
  653. VALIDATE_INSTRUCTION(f64_sub)
  654. {
  655. TRY((stack.take<ValueType::F64, ValueType::F64>()));
  656. stack.append(ValueType(ValueType::F64));
  657. return {};
  658. }
  659. VALIDATE_INSTRUCTION(f64_mul)
  660. {
  661. TRY((stack.take<ValueType::F64, ValueType::F64>()));
  662. stack.append(ValueType(ValueType::F64));
  663. return {};
  664. }
  665. VALIDATE_INSTRUCTION(f64_div)
  666. {
  667. TRY((stack.take<ValueType::F64, ValueType::F64>()));
  668. stack.append(ValueType(ValueType::F64));
  669. return {};
  670. }
  671. VALIDATE_INSTRUCTION(f64_min)
  672. {
  673. TRY((stack.take<ValueType::F64, ValueType::F64>()));
  674. stack.append(ValueType(ValueType::F64));
  675. return {};
  676. }
  677. VALIDATE_INSTRUCTION(f64_max)
  678. {
  679. TRY((stack.take<ValueType::F64, ValueType::F64>()));
  680. stack.append(ValueType(ValueType::F64));
  681. return {};
  682. }
  683. VALIDATE_INSTRUCTION(f64_copysign)
  684. {
  685. TRY((stack.take<ValueType::F64, ValueType::F64>()));
  686. stack.append(ValueType(ValueType::F64));
  687. return {};
  688. }
  689. // https://webassembly.github.io/spec/core/bikeshed/#-tmathsfhrefsyntax-testopmathittestop
  690. VALIDATE_INSTRUCTION(i32_eqz)
  691. {
  692. TRY((stack.take<ValueType::I32>()));
  693. stack.append(ValueType(ValueType::I32));
  694. return {};
  695. }
  696. VALIDATE_INSTRUCTION(i64_eqz)
  697. {
  698. TRY((stack.take<ValueType::I64>()));
  699. stack.append(ValueType(ValueType::I32));
  700. return {};
  701. }
  702. // https://webassembly.github.io/spec/core/bikeshed/#-tmathsfhrefsyntax-relopmathitrelop
  703. VALIDATE_INSTRUCTION(i32_eq)
  704. {
  705. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  706. stack.append(ValueType(ValueType::I32));
  707. return {};
  708. }
  709. VALIDATE_INSTRUCTION(i32_ne)
  710. {
  711. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  712. stack.append(ValueType(ValueType::I32));
  713. return {};
  714. }
  715. VALIDATE_INSTRUCTION(i32_lts)
  716. {
  717. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  718. stack.append(ValueType(ValueType::I32));
  719. return {};
  720. }
  721. VALIDATE_INSTRUCTION(i32_ltu)
  722. {
  723. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  724. stack.append(ValueType(ValueType::I32));
  725. return {};
  726. }
  727. VALIDATE_INSTRUCTION(i32_gts)
  728. {
  729. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  730. stack.append(ValueType(ValueType::I32));
  731. return {};
  732. }
  733. VALIDATE_INSTRUCTION(i32_gtu)
  734. {
  735. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  736. stack.append(ValueType(ValueType::I32));
  737. return {};
  738. }
  739. VALIDATE_INSTRUCTION(i32_les)
  740. {
  741. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  742. stack.append(ValueType(ValueType::I32));
  743. return {};
  744. }
  745. VALIDATE_INSTRUCTION(i32_leu)
  746. {
  747. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  748. stack.append(ValueType(ValueType::I32));
  749. return {};
  750. }
  751. VALIDATE_INSTRUCTION(i32_ges)
  752. {
  753. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  754. stack.append(ValueType(ValueType::I32));
  755. return {};
  756. }
  757. VALIDATE_INSTRUCTION(i32_geu)
  758. {
  759. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  760. stack.append(ValueType(ValueType::I32));
  761. return {};
  762. }
  763. VALIDATE_INSTRUCTION(i64_eq)
  764. {
  765. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  766. stack.append(ValueType(ValueType::I32));
  767. return {};
  768. }
  769. VALIDATE_INSTRUCTION(i64_ne)
  770. {
  771. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  772. stack.append(ValueType(ValueType::I32));
  773. return {};
  774. }
  775. VALIDATE_INSTRUCTION(i64_lts)
  776. {
  777. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  778. stack.append(ValueType(ValueType::I32));
  779. return {};
  780. }
  781. VALIDATE_INSTRUCTION(i64_ltu)
  782. {
  783. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  784. stack.append(ValueType(ValueType::I32));
  785. return {};
  786. }
  787. VALIDATE_INSTRUCTION(i64_gts)
  788. {
  789. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  790. stack.append(ValueType(ValueType::I32));
  791. return {};
  792. }
  793. VALIDATE_INSTRUCTION(i64_gtu)
  794. {
  795. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  796. stack.append(ValueType(ValueType::I32));
  797. return {};
  798. }
  799. VALIDATE_INSTRUCTION(i64_les)
  800. {
  801. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  802. stack.append(ValueType(ValueType::I32));
  803. return {};
  804. }
  805. VALIDATE_INSTRUCTION(i64_leu)
  806. {
  807. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  808. stack.append(ValueType(ValueType::I32));
  809. return {};
  810. }
  811. VALIDATE_INSTRUCTION(i64_ges)
  812. {
  813. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  814. stack.append(ValueType(ValueType::I32));
  815. return {};
  816. }
  817. VALIDATE_INSTRUCTION(i64_geu)
  818. {
  819. TRY((stack.take<ValueType::I64, ValueType::I64>()));
  820. stack.append(ValueType(ValueType::I32));
  821. return {};
  822. }
  823. VALIDATE_INSTRUCTION(f32_eq)
  824. {
  825. TRY((stack.take<ValueType::F32, ValueType::F32>()));
  826. stack.append(ValueType(ValueType::I32));
  827. return {};
  828. }
  829. VALIDATE_INSTRUCTION(f32_ne)
  830. {
  831. TRY((stack.take<ValueType::F32, ValueType::F32>()));
  832. stack.append(ValueType(ValueType::I32));
  833. return {};
  834. }
  835. VALIDATE_INSTRUCTION(f32_lt)
  836. {
  837. TRY((stack.take<ValueType::F32, ValueType::F32>()));
  838. stack.append(ValueType(ValueType::I32));
  839. return {};
  840. }
  841. VALIDATE_INSTRUCTION(f32_le)
  842. {
  843. TRY((stack.take<ValueType::F32, ValueType::F32>()));
  844. stack.append(ValueType(ValueType::I32));
  845. return {};
  846. }
  847. VALIDATE_INSTRUCTION(f32_gt)
  848. {
  849. TRY((stack.take<ValueType::F32, ValueType::F32>()));
  850. stack.append(ValueType(ValueType::I32));
  851. return {};
  852. }
  853. VALIDATE_INSTRUCTION(f32_ge)
  854. {
  855. TRY((stack.take<ValueType::F32, ValueType::F32>()));
  856. stack.append(ValueType(ValueType::I32));
  857. return {};
  858. }
  859. VALIDATE_INSTRUCTION(f64_eq)
  860. {
  861. TRY((stack.take<ValueType::F64, ValueType::F64>()));
  862. stack.append(ValueType(ValueType::I32));
  863. return {};
  864. }
  865. VALIDATE_INSTRUCTION(f64_ne)
  866. {
  867. TRY((stack.take<ValueType::F64, ValueType::F64>()));
  868. stack.append(ValueType(ValueType::I32));
  869. return {};
  870. }
  871. VALIDATE_INSTRUCTION(f64_lt)
  872. {
  873. TRY((stack.take<ValueType::F64, ValueType::F64>()));
  874. stack.append(ValueType(ValueType::I32));
  875. return {};
  876. }
  877. VALIDATE_INSTRUCTION(f64_le)
  878. {
  879. TRY((stack.take<ValueType::F64, ValueType::F64>()));
  880. stack.append(ValueType(ValueType::I32));
  881. return {};
  882. }
  883. VALIDATE_INSTRUCTION(f64_gt)
  884. {
  885. TRY((stack.take<ValueType::F64, ValueType::F64>()));
  886. stack.append(ValueType(ValueType::I32));
  887. return {};
  888. }
  889. VALIDATE_INSTRUCTION(f64_ge)
  890. {
  891. TRY((stack.take<ValueType::F64, ValueType::F64>()));
  892. stack.append(ValueType(ValueType::I32));
  893. return {};
  894. }
  895. // https://webassembly.github.io/spec/core/bikeshed/#-t_2mathsfhrefsyntax-cvtopmathitcvtopmathsf_t_1mathsf_hrefsyntax-sxmathitsx
  896. VALIDATE_INSTRUCTION(i32_wrap_i64)
  897. {
  898. TRY(stack.take_and_put<ValueType::I64>(ValueType::I32));
  899. return {};
  900. }
  901. VALIDATE_INSTRUCTION(i64_extend_si32)
  902. {
  903. TRY(stack.take_and_put<ValueType::I32>(ValueType::I64));
  904. return {};
  905. }
  906. VALIDATE_INSTRUCTION(i64_extend_ui32)
  907. {
  908. TRY(stack.take_and_put<ValueType::I32>(ValueType::I64));
  909. return {};
  910. }
  911. VALIDATE_INSTRUCTION(i32_trunc_sf32)
  912. {
  913. TRY(stack.take_and_put<ValueType::F32>(ValueType::I32));
  914. return {};
  915. }
  916. VALIDATE_INSTRUCTION(i32_trunc_uf32)
  917. {
  918. TRY(stack.take_and_put<ValueType::F32>(ValueType::I32));
  919. return {};
  920. }
  921. VALIDATE_INSTRUCTION(i32_trunc_sf64)
  922. {
  923. TRY(stack.take_and_put<ValueType::F64>(ValueType::I32));
  924. return {};
  925. }
  926. VALIDATE_INSTRUCTION(i32_trunc_uf64)
  927. {
  928. TRY(stack.take_and_put<ValueType::F64>(ValueType::I32));
  929. return {};
  930. }
  931. VALIDATE_INSTRUCTION(i64_trunc_sf32)
  932. {
  933. TRY(stack.take_and_put<ValueType::F32>(ValueType::I64));
  934. return {};
  935. }
  936. VALIDATE_INSTRUCTION(i64_trunc_uf32)
  937. {
  938. TRY(stack.take_and_put<ValueType::F32>(ValueType::I64));
  939. return {};
  940. }
  941. VALIDATE_INSTRUCTION(i64_trunc_sf64)
  942. {
  943. TRY(stack.take_and_put<ValueType::F64>(ValueType::I64));
  944. return {};
  945. }
  946. VALIDATE_INSTRUCTION(i64_trunc_uf64)
  947. {
  948. TRY(stack.take_and_put<ValueType::F64>(ValueType::I64));
  949. return {};
  950. }
  951. VALIDATE_INSTRUCTION(i32_trunc_sat_f32_s)
  952. {
  953. TRY(stack.take_and_put<ValueType::F32>(ValueType::I32));
  954. return {};
  955. }
  956. VALIDATE_INSTRUCTION(i32_trunc_sat_f32_u)
  957. {
  958. TRY(stack.take_and_put<ValueType::F32>(ValueType::I32));
  959. return {};
  960. }
  961. VALIDATE_INSTRUCTION(i32_trunc_sat_f64_s)
  962. {
  963. TRY(stack.take_and_put<ValueType::F64>(ValueType::I32));
  964. return {};
  965. }
  966. VALIDATE_INSTRUCTION(i32_trunc_sat_f64_u)
  967. {
  968. TRY(stack.take_and_put<ValueType::F64>(ValueType::I32));
  969. return {};
  970. }
  971. VALIDATE_INSTRUCTION(i64_trunc_sat_f32_s)
  972. {
  973. TRY(stack.take_and_put<ValueType::F32>(ValueType::I64));
  974. return {};
  975. }
  976. VALIDATE_INSTRUCTION(i64_trunc_sat_f32_u)
  977. {
  978. TRY(stack.take_and_put<ValueType::F32>(ValueType::I64));
  979. return {};
  980. }
  981. VALIDATE_INSTRUCTION(i64_trunc_sat_f64_s)
  982. {
  983. TRY(stack.take_and_put<ValueType::F64>(ValueType::I64));
  984. return {};
  985. }
  986. VALIDATE_INSTRUCTION(i64_trunc_sat_f64_u)
  987. {
  988. TRY(stack.take_and_put<ValueType::F64>(ValueType::I64));
  989. return {};
  990. }
  991. VALIDATE_INSTRUCTION(f32_convert_si32)
  992. {
  993. TRY(stack.take_and_put<ValueType::I32>(ValueType::F32));
  994. return {};
  995. }
  996. VALIDATE_INSTRUCTION(f32_convert_ui32)
  997. {
  998. TRY(stack.take_and_put<ValueType::I32>(ValueType::F32));
  999. return {};
  1000. }
  1001. VALIDATE_INSTRUCTION(f32_convert_si64)
  1002. {
  1003. TRY(stack.take_and_put<ValueType::I64>(ValueType::F32));
  1004. return {};
  1005. }
  1006. VALIDATE_INSTRUCTION(f32_convert_ui64)
  1007. {
  1008. TRY(stack.take_and_put<ValueType::I64>(ValueType::F32));
  1009. return {};
  1010. }
  1011. VALIDATE_INSTRUCTION(f64_convert_si32)
  1012. {
  1013. TRY(stack.take_and_put<ValueType::I32>(ValueType::F64));
  1014. return {};
  1015. }
  1016. VALIDATE_INSTRUCTION(f64_convert_ui32)
  1017. {
  1018. TRY(stack.take_and_put<ValueType::I32>(ValueType::F64));
  1019. return {};
  1020. }
  1021. VALIDATE_INSTRUCTION(f64_convert_si64)
  1022. {
  1023. TRY(stack.take_and_put<ValueType::I64>(ValueType::F64));
  1024. return {};
  1025. }
  1026. VALIDATE_INSTRUCTION(f64_convert_ui64)
  1027. {
  1028. TRY(stack.take_and_put<ValueType::I64>(ValueType::F64));
  1029. return {};
  1030. }
  1031. VALIDATE_INSTRUCTION(f32_demote_f64)
  1032. {
  1033. TRY(stack.take_and_put<ValueType::F64>(ValueType::F32));
  1034. return {};
  1035. }
  1036. VALIDATE_INSTRUCTION(f64_promote_f32)
  1037. {
  1038. TRY(stack.take_and_put<ValueType::F32>(ValueType::F64));
  1039. return {};
  1040. }
  1041. VALIDATE_INSTRUCTION(f32_reinterpret_i32)
  1042. {
  1043. TRY(stack.take_and_put<ValueType::I32>(ValueType::F32));
  1044. return {};
  1045. }
  1046. VALIDATE_INSTRUCTION(f64_reinterpret_i64)
  1047. {
  1048. TRY(stack.take_and_put<ValueType::I64>(ValueType::F64));
  1049. return {};
  1050. }
  1051. VALIDATE_INSTRUCTION(i32_reinterpret_f32)
  1052. {
  1053. TRY(stack.take_and_put<ValueType::F32>(ValueType::I32));
  1054. return {};
  1055. }
  1056. VALIDATE_INSTRUCTION(i64_reinterpret_f64)
  1057. {
  1058. TRY(stack.take_and_put<ValueType::F64>(ValueType::I64));
  1059. return {};
  1060. }
  1061. // https://webassembly.github.io/spec/core/bikeshed/#reference-instructions%E2%91%A2
  1062. VALIDATE_INSTRUCTION(ref_null)
  1063. {
  1064. is_constant = true;
  1065. stack.append(instruction.arguments().get<ValueType>());
  1066. return {};
  1067. }
  1068. VALIDATE_INSTRUCTION(ref_is_null)
  1069. {
  1070. if (stack.is_empty() || !stack.last().is_reference())
  1071. return Errors::invalid_stack_state(stack, Tuple { "reference" });
  1072. TRY(stack.take_last());
  1073. stack.append(ValueType(ValueType::I32));
  1074. return {};
  1075. }
  1076. VALIDATE_INSTRUCTION(ref_func)
  1077. {
  1078. auto index = instruction.arguments().get<FunctionIndex>();
  1079. TRY(validate(index));
  1080. if (m_context.references->tree.find(index.value()) == nullptr)
  1081. return Errors::invalid("function reference"sv);
  1082. is_constant = true;
  1083. stack.append(ValueType(ValueType::FunctionReference));
  1084. return {};
  1085. }
  1086. // https://webassembly.github.io/spec/core/bikeshed/#parametric-instructions%E2%91%A2
  1087. VALIDATE_INSTRUCTION(drop)
  1088. {
  1089. TRY(stack.take_last());
  1090. return {};
  1091. }
  1092. VALIDATE_INSTRUCTION(select)
  1093. {
  1094. TRY(stack.take<ValueType::I32>());
  1095. auto arg0_type = TRY(stack.take_last());
  1096. auto arg1_type = TRY(stack.take_last());
  1097. if (arg0_type != arg1_type || arg0_type.concrete_type.is_reference() || arg1_type.concrete_type.is_reference())
  1098. return Errors::invalid("select argument types"sv, Vector { arg0_type, arg0_type }, Vector { arg0_type, arg1_type });
  1099. stack.append(arg0_type.is_known ? arg0_type : arg1_type);
  1100. return {};
  1101. }
  1102. VALIDATE_INSTRUCTION(select_typed)
  1103. {
  1104. auto& required_types = instruction.arguments().get<Vector<ValueType>>();
  1105. if (required_types.size() != 1)
  1106. return Errors::invalid("select types"sv, "exactly one type"sv, required_types);
  1107. TRY(stack.take<ValueType::I32>());
  1108. auto arg0_type = TRY(stack.take_last());
  1109. auto arg1_type = TRY(stack.take_last());
  1110. if (arg0_type != arg1_type || arg0_type != required_types.first())
  1111. return Errors::invalid("select argument types"sv, Vector { required_types.first(), required_types.first() }, Vector { arg0_type, arg1_type });
  1112. stack.append(arg0_type.is_known ? arg0_type : arg1_type);
  1113. return {};
  1114. }
  1115. // https://webassembly.github.io/spec/core/bikeshed/#variable-instructions%E2%91%A2
  1116. VALIDATE_INSTRUCTION(local_get)
  1117. {
  1118. auto index = instruction.arguments().get<LocalIndex>();
  1119. TRY(validate(index));
  1120. stack.append(m_context.locals[index.value()]);
  1121. return {};
  1122. }
  1123. VALIDATE_INSTRUCTION(local_set)
  1124. {
  1125. auto index = instruction.arguments().get<LocalIndex>();
  1126. TRY(validate(index));
  1127. auto& value_type = m_context.locals[index.value()];
  1128. TRY(stack.take(value_type));
  1129. return {};
  1130. }
  1131. VALIDATE_INSTRUCTION(local_tee)
  1132. {
  1133. auto index = instruction.arguments().get<LocalIndex>();
  1134. TRY(validate(index));
  1135. auto& value_type = m_context.locals[index.value()];
  1136. TRY(stack.take(value_type));
  1137. stack.append(value_type);
  1138. return {};
  1139. }
  1140. VALIDATE_INSTRUCTION(global_get)
  1141. {
  1142. auto index = instruction.arguments().get<GlobalIndex>();
  1143. TRY(validate(index));
  1144. auto& global = m_context.globals[index.value()];
  1145. is_constant = !global.is_mutable();
  1146. stack.append(global.type());
  1147. return {};
  1148. }
  1149. VALIDATE_INSTRUCTION(global_set)
  1150. {
  1151. auto index = instruction.arguments().get<GlobalIndex>();
  1152. TRY(validate(index));
  1153. auto& global = m_context.globals[index.value()];
  1154. if (!global.is_mutable())
  1155. return Errors::invalid("global variable for global.set"sv);
  1156. TRY(stack.take(global.type()));
  1157. return {};
  1158. }
  1159. // https://webassembly.github.io/spec/core/bikeshed/#table-instructions%E2%91%A2
  1160. VALIDATE_INSTRUCTION(table_get)
  1161. {
  1162. auto index = instruction.arguments().get<TableIndex>();
  1163. TRY(validate(index));
  1164. auto& table = m_context.tables[index.value()];
  1165. TRY(stack.take<ValueType::I32>());
  1166. stack.append(table.element_type());
  1167. return {};
  1168. }
  1169. VALIDATE_INSTRUCTION(table_set)
  1170. {
  1171. auto index = instruction.arguments().get<TableIndex>();
  1172. TRY(validate(index));
  1173. auto& table = m_context.tables[index.value()];
  1174. TRY(stack.take(table.element_type()));
  1175. TRY(stack.take<ValueType::I32>());
  1176. return {};
  1177. }
  1178. VALIDATE_INSTRUCTION(table_size)
  1179. {
  1180. auto index = instruction.arguments().get<TableIndex>();
  1181. TRY(validate(index));
  1182. stack.append(ValueType(ValueType::I32));
  1183. return {};
  1184. }
  1185. VALIDATE_INSTRUCTION(table_grow)
  1186. {
  1187. auto index = instruction.arguments().get<TableIndex>();
  1188. TRY(validate(index));
  1189. auto& table = m_context.tables[index.value()];
  1190. TRY(stack.take<ValueType::I32>());
  1191. TRY(stack.take(table.element_type()));
  1192. stack.append(ValueType(ValueType::I32));
  1193. return {};
  1194. }
  1195. VALIDATE_INSTRUCTION(table_fill)
  1196. {
  1197. auto index = instruction.arguments().get<TableIndex>();
  1198. TRY(validate(index));
  1199. auto& table = m_context.tables[index.value()];
  1200. TRY(stack.take<ValueType::I32>());
  1201. TRY(stack.take(table.element_type()));
  1202. TRY(stack.take<ValueType::I32>());
  1203. return {};
  1204. }
  1205. VALIDATE_INSTRUCTION(table_copy)
  1206. {
  1207. auto& args = instruction.arguments().get<Instruction::TableTableArgs>();
  1208. TRY(validate(args.lhs));
  1209. TRY(validate(args.rhs));
  1210. auto& lhs_table = m_context.tables[args.lhs.value()];
  1211. auto& rhs_table = m_context.tables[args.rhs.value()];
  1212. if (lhs_table.element_type() != rhs_table.element_type())
  1213. return Errors::non_conforming_types("table.copy"sv, lhs_table.element_type(), rhs_table.element_type());
  1214. if (!lhs_table.element_type().is_reference())
  1215. return Errors::invalid("table.copy element type"sv, "a reference type"sv, lhs_table.element_type());
  1216. TRY((stack.take<ValueType::I32, ValueType::I32, ValueType::I32>()));
  1217. return {};
  1218. }
  1219. VALIDATE_INSTRUCTION(table_init)
  1220. {
  1221. auto& args = instruction.arguments().get<Instruction::TableElementArgs>();
  1222. TRY(validate(args.table_index));
  1223. TRY(validate(args.element_index));
  1224. auto& table = m_context.tables[args.table_index.value()];
  1225. auto& element_type = m_context.elements[args.element_index.value()];
  1226. if (table.element_type() != element_type)
  1227. return Errors::non_conforming_types("table.init"sv, table.element_type(), element_type);
  1228. TRY((stack.take<ValueType::I32, ValueType::I32, ValueType::I32>()));
  1229. return {};
  1230. }
  1231. VALIDATE_INSTRUCTION(elem_drop)
  1232. {
  1233. auto index = instruction.arguments().get<ElementIndex>();
  1234. TRY(validate(index));
  1235. return {};
  1236. }
  1237. // https://webassembly.github.io/spec/core/bikeshed/#memory-instructions%E2%91%A2
  1238. VALIDATE_INSTRUCTION(i32_load)
  1239. {
  1240. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1241. TRY(validate(arg.memory_index));
  1242. if ((1ull << arg.align) > sizeof(i32))
  1243. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, sizeof(i32));
  1244. TRY((stack.take<ValueType::I32>()));
  1245. stack.append(ValueType(ValueType::I32));
  1246. return {};
  1247. }
  1248. VALIDATE_INSTRUCTION(i64_load)
  1249. {
  1250. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1251. TRY(validate(arg.memory_index));
  1252. if ((1ull << arg.align) > sizeof(i64))
  1253. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, sizeof(i64));
  1254. TRY((stack.take<ValueType::I32>()));
  1255. stack.append(ValueType(ValueType::I64));
  1256. return {};
  1257. }
  1258. VALIDATE_INSTRUCTION(f32_load)
  1259. {
  1260. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1261. TRY(validate(arg.memory_index));
  1262. if ((1ull << arg.align) > sizeof(float))
  1263. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, sizeof(float));
  1264. TRY((stack.take<ValueType::I32>()));
  1265. stack.append(ValueType(ValueType::F32));
  1266. return {};
  1267. }
  1268. VALIDATE_INSTRUCTION(f64_load)
  1269. {
  1270. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1271. TRY(validate(arg.memory_index));
  1272. if ((1ull << arg.align) > sizeof(double))
  1273. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, sizeof(double));
  1274. TRY((stack.take<ValueType::I32>()));
  1275. stack.append(ValueType(ValueType::F64));
  1276. return {};
  1277. }
  1278. VALIDATE_INSTRUCTION(i32_load16_s)
  1279. {
  1280. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1281. TRY(validate(arg.memory_index));
  1282. if ((1ull << arg.align) > 16 / 8)
  1283. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 16 / 8);
  1284. TRY((stack.take<ValueType::I32>()));
  1285. stack.append(ValueType(ValueType::I32));
  1286. return {};
  1287. }
  1288. VALIDATE_INSTRUCTION(i32_load16_u)
  1289. {
  1290. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1291. TRY(validate(arg.memory_index));
  1292. if ((1ull << arg.align) > 16 / 8)
  1293. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 16 / 8);
  1294. TRY((stack.take<ValueType::I32>()));
  1295. stack.append(ValueType(ValueType::I32));
  1296. return {};
  1297. }
  1298. VALIDATE_INSTRUCTION(i32_load8_s)
  1299. {
  1300. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1301. TRY(validate(arg.memory_index));
  1302. if ((1ull << arg.align) > 8 / 8)
  1303. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 8 / 8);
  1304. TRY((stack.take<ValueType::I32>()));
  1305. stack.append(ValueType(ValueType::I32));
  1306. return {};
  1307. }
  1308. VALIDATE_INSTRUCTION(i32_load8_u)
  1309. {
  1310. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1311. TRY(validate(arg.memory_index));
  1312. if ((1ull << arg.align) > 8 / 8)
  1313. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 8 / 8);
  1314. TRY((stack.take<ValueType::I32>()));
  1315. stack.append(ValueType(ValueType::I32));
  1316. return {};
  1317. }
  1318. VALIDATE_INSTRUCTION(i64_load32_s)
  1319. {
  1320. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1321. TRY(validate(arg.memory_index));
  1322. if ((1ull << arg.align) > 32 / 8)
  1323. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 32 / 8);
  1324. TRY((stack.take<ValueType::I32>()));
  1325. stack.append(ValueType(ValueType::I64));
  1326. return {};
  1327. }
  1328. VALIDATE_INSTRUCTION(i64_load32_u)
  1329. {
  1330. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1331. TRY(validate(arg.memory_index));
  1332. if ((1ull << arg.align) > 32 / 8)
  1333. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 32 / 8);
  1334. TRY((stack.take<ValueType::I32>()));
  1335. stack.append(ValueType(ValueType::I64));
  1336. return {};
  1337. }
  1338. VALIDATE_INSTRUCTION(i64_load16_s)
  1339. {
  1340. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1341. TRY(validate(arg.memory_index));
  1342. if ((1ull << arg.align) > 16 / 8)
  1343. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 16 / 8);
  1344. TRY((stack.take<ValueType::I32>()));
  1345. stack.append(ValueType(ValueType::I64));
  1346. return {};
  1347. }
  1348. VALIDATE_INSTRUCTION(i64_load16_u)
  1349. {
  1350. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1351. TRY(validate(arg.memory_index));
  1352. if ((1ull << arg.align) > 16 / 8)
  1353. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 16 / 8);
  1354. TRY((stack.take<ValueType::I32>()));
  1355. stack.append(ValueType(ValueType::I64));
  1356. return {};
  1357. }
  1358. VALIDATE_INSTRUCTION(i64_load8_s)
  1359. {
  1360. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1361. TRY(validate(arg.memory_index));
  1362. if ((1ull << arg.align) > 8 / 8)
  1363. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 8 / 8);
  1364. TRY((stack.take<ValueType::I32>()));
  1365. stack.append(ValueType(ValueType::I64));
  1366. return {};
  1367. }
  1368. VALIDATE_INSTRUCTION(i64_load8_u)
  1369. {
  1370. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1371. TRY(validate(arg.memory_index));
  1372. if ((1ull << arg.align) > 8 / 8)
  1373. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 8 / 8);
  1374. TRY((stack.take<ValueType::I32>()));
  1375. stack.append(ValueType(ValueType::I64));
  1376. return {};
  1377. }
  1378. VALIDATE_INSTRUCTION(i32_store)
  1379. {
  1380. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1381. TRY(validate(arg.memory_index));
  1382. if ((1ull << arg.align) > sizeof(i32))
  1383. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, sizeof(i32));
  1384. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  1385. return {};
  1386. }
  1387. VALIDATE_INSTRUCTION(i64_store)
  1388. {
  1389. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1390. TRY(validate(arg.memory_index));
  1391. if ((1ull << arg.align) > sizeof(i64))
  1392. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, sizeof(i64));
  1393. TRY((stack.take<ValueType::I64, ValueType::I32>()));
  1394. return {};
  1395. }
  1396. VALIDATE_INSTRUCTION(f32_store)
  1397. {
  1398. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1399. TRY(validate(arg.memory_index));
  1400. if ((1ull << arg.align) > sizeof(float))
  1401. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, sizeof(float));
  1402. TRY((stack.take<ValueType::F32, ValueType::I32>()));
  1403. return {};
  1404. }
  1405. VALIDATE_INSTRUCTION(f64_store)
  1406. {
  1407. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1408. TRY(validate(arg.memory_index));
  1409. if ((1ull << arg.align) > sizeof(double))
  1410. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, sizeof(double));
  1411. TRY((stack.take<ValueType::F64, ValueType::I32>()));
  1412. return {};
  1413. }
  1414. VALIDATE_INSTRUCTION(i32_store16)
  1415. {
  1416. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1417. TRY(validate(arg.memory_index));
  1418. if ((1ull << arg.align) > 16 / 8)
  1419. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 16 / 8);
  1420. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  1421. return {};
  1422. }
  1423. VALIDATE_INSTRUCTION(i32_store8)
  1424. {
  1425. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1426. TRY(validate(arg.memory_index));
  1427. if ((1ull << arg.align) > 8 / 8)
  1428. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 8 / 8);
  1429. TRY((stack.take<ValueType::I32, ValueType::I32>()));
  1430. return {};
  1431. }
  1432. VALIDATE_INSTRUCTION(i64_store32)
  1433. {
  1434. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1435. TRY(validate(arg.memory_index));
  1436. if ((1ull << arg.align) > 32 / 8)
  1437. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 32 / 8);
  1438. TRY((stack.take<ValueType::I64, ValueType::I32>()));
  1439. return {};
  1440. }
  1441. VALIDATE_INSTRUCTION(i64_store16)
  1442. {
  1443. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1444. TRY(validate(arg.memory_index));
  1445. if ((1ull << arg.align) > 16 / 8)
  1446. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 16 / 8);
  1447. TRY((stack.take<ValueType::I64, ValueType::I32>()));
  1448. return {};
  1449. }
  1450. VALIDATE_INSTRUCTION(i64_store8)
  1451. {
  1452. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1453. TRY(validate(arg.memory_index));
  1454. if ((1ull << arg.align) > 8 / 8)
  1455. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, 8 / 8);
  1456. TRY((stack.take<ValueType::I64, ValueType::I32>()));
  1457. return {};
  1458. }
  1459. VALIDATE_INSTRUCTION(memory_size)
  1460. {
  1461. TRY(validate(instruction.arguments().get<Instruction::MemoryIndexArgument>().memory_index));
  1462. stack.append(ValueType(ValueType::I32));
  1463. return {};
  1464. }
  1465. VALIDATE_INSTRUCTION(memory_grow)
  1466. {
  1467. TRY(validate(instruction.arguments().get<Instruction::MemoryIndexArgument>().memory_index));
  1468. TRY((stack.take<ValueType::I32>()));
  1469. stack.append(ValueType(ValueType::I32));
  1470. return {};
  1471. }
  1472. VALIDATE_INSTRUCTION(memory_fill)
  1473. {
  1474. TRY(validate(instruction.arguments().get<Instruction::MemoryIndexArgument>().memory_index));
  1475. TRY((stack.take<ValueType::I32, ValueType::I32, ValueType::I32>()));
  1476. return {};
  1477. }
  1478. VALIDATE_INSTRUCTION(memory_copy)
  1479. {
  1480. auto& args = instruction.arguments().get<Instruction::MemoryCopyArgs>();
  1481. TRY(validate(args.src_index));
  1482. TRY(validate(args.dst_index));
  1483. TRY((stack.take<ValueType::I32, ValueType::I32, ValueType::I32>()));
  1484. return {};
  1485. }
  1486. VALIDATE_INSTRUCTION(memory_init)
  1487. {
  1488. if (!m_context.data_count.has_value())
  1489. return Errors::invalid("memory.init, requires data count section"sv);
  1490. auto& args = instruction.arguments().get<Instruction::MemoryInitArgs>();
  1491. TRY(validate(args.memory_index));
  1492. TRY(validate(args.data_index));
  1493. TRY((stack.take<ValueType::I32, ValueType::I32, ValueType::I32>()));
  1494. return {};
  1495. }
  1496. VALIDATE_INSTRUCTION(data_drop)
  1497. {
  1498. if (!m_context.data_count.has_value())
  1499. return Errors::invalid("data.drop, requires data count section"sv);
  1500. auto index = instruction.arguments().get<DataIndex>();
  1501. TRY(validate(index));
  1502. return {};
  1503. }
  1504. // https://webassembly.github.io/spec/core/bikeshed/#control-instructions%E2%91%A2
  1505. VALIDATE_INSTRUCTION(nop)
  1506. {
  1507. return {};
  1508. }
  1509. VALIDATE_INSTRUCTION(unreachable)
  1510. {
  1511. // https://webassembly.github.io/spec/core/bikeshed/#polymorphism
  1512. m_frames.last().unreachable = true;
  1513. stack.resize(m_frames.last().initial_size);
  1514. return {};
  1515. }
  1516. // Note: This is responsible for _all_ structured instructions, and is *not* from the spec.
  1517. VALIDATE_INSTRUCTION(structured_end)
  1518. {
  1519. if (m_frames.is_empty())
  1520. return Errors::invalid("usage of structured end"sv);
  1521. auto& last_frame = m_frames.last();
  1522. // If this is true, then the `if` had no else. In that case, validate that the
  1523. // empty else block produces the correct type.
  1524. if (last_frame.kind == FrameKind::If) {
  1525. bool is_constant = false;
  1526. TRY(validate(Instruction(Instructions::structured_else), stack, is_constant));
  1527. }
  1528. auto& results = last_frame.type.results();
  1529. for (size_t i = 1; i <= results.size(); ++i)
  1530. TRY(stack.take(results[results.size() - i]));
  1531. if (stack.size() != last_frame.initial_size)
  1532. return Errors::stack_height_mismatch(stack, last_frame.initial_size);
  1533. for (auto& result : results)
  1534. stack.append(result);
  1535. m_frames.take_last();
  1536. return {};
  1537. }
  1538. // Note: This is *not* from the spec.
  1539. VALIDATE_INSTRUCTION(structured_else)
  1540. {
  1541. if (m_frames.is_empty())
  1542. return Errors::invalid("usage of structured else"sv);
  1543. if (m_frames.last().kind != FrameKind::If)
  1544. return Errors::invalid("usage of structured else"sv);
  1545. auto& frame = m_frames.last();
  1546. auto& block_type = frame.type;
  1547. auto& results = block_type.results();
  1548. for (size_t i = 1; i <= results.size(); ++i)
  1549. TRY(stack.take(results[results.size() - i]));
  1550. if (stack.size() != frame.initial_size)
  1551. return Errors::stack_height_mismatch(stack, frame.initial_size);
  1552. frame.kind = FrameKind::Else;
  1553. frame.unreachable = false;
  1554. for (auto& parameter : block_type.parameters())
  1555. stack.append(parameter);
  1556. return {};
  1557. }
  1558. VALIDATE_INSTRUCTION(block)
  1559. {
  1560. auto& args = instruction.arguments().get<Instruction::StructuredInstructionArgs>();
  1561. auto block_type = TRY(validate(args.block_type));
  1562. auto& parameters = block_type.parameters();
  1563. for (size_t i = 1; i <= parameters.size(); ++i)
  1564. TRY(stack.take(parameters[parameters.size() - i]));
  1565. m_frames.empend(block_type, FrameKind::Block, stack.size());
  1566. for (auto& parameter : parameters)
  1567. stack.append(parameter);
  1568. return {};
  1569. }
  1570. VALIDATE_INSTRUCTION(loop)
  1571. {
  1572. auto& args = instruction.arguments().get<Instruction::StructuredInstructionArgs>();
  1573. auto block_type = TRY(validate(args.block_type));
  1574. auto& parameters = block_type.parameters();
  1575. for (size_t i = 1; i <= parameters.size(); ++i)
  1576. TRY(stack.take(parameters[parameters.size() - i]));
  1577. m_frames.empend(block_type, FrameKind::Loop, stack.size());
  1578. for (auto& parameter : parameters)
  1579. stack.append(parameter);
  1580. return {};
  1581. }
  1582. VALIDATE_INSTRUCTION(if_)
  1583. {
  1584. auto& args = instruction.arguments().get<Instruction::StructuredInstructionArgs>();
  1585. auto block_type = TRY(validate(args.block_type));
  1586. TRY(stack.take<ValueType::I32>());
  1587. auto stack_snapshot = stack;
  1588. auto& parameters = block_type.parameters();
  1589. for (size_t i = 1; i <= parameters.size(); ++i)
  1590. TRY(stack.take(parameters[parameters.size() - i]));
  1591. m_frames.empend(block_type, FrameKind::If, stack.size());
  1592. for (auto& parameter : parameters)
  1593. stack.append(parameter);
  1594. return {};
  1595. }
  1596. VALIDATE_INSTRUCTION(br)
  1597. {
  1598. auto label = instruction.arguments().get<LabelIndex>();
  1599. TRY(validate(label));
  1600. auto& type = m_frames[(m_frames.size() - 1) - label.value()].labels();
  1601. for (size_t i = 1; i <= type.size(); ++i)
  1602. TRY(stack.take(type[type.size() - i]));
  1603. m_frames.last().unreachable = true;
  1604. stack.resize(m_frames.last().initial_size);
  1605. return {};
  1606. }
  1607. VALIDATE_INSTRUCTION(br_if)
  1608. {
  1609. auto label = instruction.arguments().get<LabelIndex>();
  1610. TRY(validate(label));
  1611. TRY(stack.take<ValueType::I32>());
  1612. auto& type = m_frames[(m_frames.size() - 1) - label.value()].labels();
  1613. Vector<StackEntry> entries;
  1614. entries.ensure_capacity(type.size());
  1615. for (size_t i = 0; i < type.size(); ++i) {
  1616. auto& entry = type[type.size() - i - 1];
  1617. TRY(stack.take(entry));
  1618. entries.append(entry);
  1619. }
  1620. for (size_t i = 0; i < entries.size(); ++i)
  1621. stack.append(entries[entries.size() - i - 1]);
  1622. return {};
  1623. }
  1624. VALIDATE_INSTRUCTION(br_table)
  1625. {
  1626. auto& args = instruction.arguments().get<Instruction::TableBranchArgs>();
  1627. TRY(validate(args.default_));
  1628. for (auto& label : args.labels)
  1629. TRY(validate(label));
  1630. TRY(stack.take<ValueType::I32>());
  1631. auto& default_types = m_frames[(m_frames.size() - 1) - args.default_.value()].labels();
  1632. auto arity = default_types.size();
  1633. for (auto& label : args.labels) {
  1634. auto& label_types = m_frames[(m_frames.size() - 1) - label.value()].labels();
  1635. if (label_types.size() != arity)
  1636. return Errors::invalid("br_table label arity mismatch"sv);
  1637. Vector<StackEntry> popped {};
  1638. for (size_t i = 0; i < arity; ++i) {
  1639. auto stack_entry = TRY(stack.take(label_types[label_types.size() - i - 1]));
  1640. popped.append(stack_entry);
  1641. }
  1642. for (auto popped_type : popped.in_reverse())
  1643. stack.append(popped_type);
  1644. }
  1645. for (size_t i = 0; i < arity; ++i) {
  1646. auto expected = default_types[default_types.size() - i - 1];
  1647. TRY((stack.take(expected)));
  1648. }
  1649. m_frames.last().unreachable = true;
  1650. stack.resize(m_frames.last().initial_size);
  1651. return {};
  1652. }
  1653. VALIDATE_INSTRUCTION(return_)
  1654. {
  1655. auto& return_types = m_frames.first().type.results();
  1656. for (size_t i = 0; i < return_types.size(); ++i)
  1657. TRY((stack.take(return_types[return_types.size() - i - 1])));
  1658. m_frames.last().unreachable = true;
  1659. stack.resize(m_frames.last().initial_size);
  1660. return {};
  1661. }
  1662. VALIDATE_INSTRUCTION(call)
  1663. {
  1664. auto index = instruction.arguments().get<FunctionIndex>();
  1665. TRY(validate(index));
  1666. auto& function_type = m_context.functions[index.value()];
  1667. for (size_t i = 0; i < function_type.parameters().size(); ++i)
  1668. TRY(stack.take(function_type.parameters()[function_type.parameters().size() - i - 1]));
  1669. for (auto& type : function_type.results())
  1670. stack.append(type);
  1671. return {};
  1672. }
  1673. VALIDATE_INSTRUCTION(call_indirect)
  1674. {
  1675. auto& args = instruction.arguments().get<Instruction::IndirectCallArgs>();
  1676. TRY(validate(args.table));
  1677. TRY(validate(args.type));
  1678. auto& table = m_context.tables[args.table.value()];
  1679. if (table.element_type().kind() != ValueType::FunctionReference)
  1680. return Errors::invalid("table element type for call.indirect"sv, "a function reference"sv, table.element_type());
  1681. auto& type = m_context.types[args.type.value()];
  1682. TRY(stack.take<ValueType::I32>());
  1683. for (size_t i = 0; i < type.parameters().size(); ++i)
  1684. TRY(stack.take(type.parameters()[type.parameters().size() - i - 1]));
  1685. for (auto& type : type.results())
  1686. stack.append(type);
  1687. return {};
  1688. }
  1689. VALIDATE_INSTRUCTION(v128_load)
  1690. {
  1691. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1692. TRY(validate(arg.memory_index));
  1693. if ((1ull << arg.align) > sizeof(u128))
  1694. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, sizeof(u128));
  1695. TRY((stack.take_and_put<ValueType::I32>(ValueType::V128)));
  1696. return {};
  1697. }
  1698. VALIDATE_INSTRUCTION(v128_load8x8_s)
  1699. {
  1700. auto const& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1701. constexpr auto N = 8;
  1702. constexpr auto M = 8;
  1703. constexpr auto max_alignment = N * M / 8;
  1704. TRY(validate(arg.memory_index));
  1705. if ((1 << arg.align) > max_alignment)
  1706. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.align, 0u, max_alignment);
  1707. return stack.take_and_put<ValueType::I32>(ValueType::V128);
  1708. }
  1709. VALIDATE_INSTRUCTION(v128_load8x8_u)
  1710. {
  1711. auto const& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1712. constexpr auto N = 8;
  1713. constexpr auto M = 8;
  1714. constexpr auto max_alignment = N * M / 8;
  1715. TRY(validate(arg.memory_index));
  1716. if ((1 << arg.align) > max_alignment)
  1717. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.align, 0u, max_alignment);
  1718. return stack.take_and_put<ValueType::I32>(ValueType::V128);
  1719. }
  1720. VALIDATE_INSTRUCTION(v128_load16x4_s)
  1721. {
  1722. auto const& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1723. constexpr auto N = 16;
  1724. constexpr auto M = 4;
  1725. constexpr auto max_alignment = N * M / 8;
  1726. TRY(validate(arg.memory_index));
  1727. if ((1 << arg.align) > max_alignment)
  1728. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.align, 0u, max_alignment);
  1729. return stack.take_and_put<ValueType::I32>(ValueType::V128);
  1730. }
  1731. VALIDATE_INSTRUCTION(v128_load16x4_u)
  1732. {
  1733. auto const& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1734. constexpr auto N = 16;
  1735. constexpr auto M = 4;
  1736. constexpr auto max_alignment = N * M / 8;
  1737. TRY(validate(arg.memory_index));
  1738. if ((1 << arg.align) > max_alignment)
  1739. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.align, 0u, max_alignment);
  1740. return stack.take_and_put<ValueType::I32>(ValueType::V128);
  1741. }
  1742. VALIDATE_INSTRUCTION(v128_load32x2_s)
  1743. {
  1744. auto const& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1745. constexpr auto N = 32;
  1746. constexpr auto M = 2;
  1747. constexpr auto max_alignment = N * M / 8;
  1748. TRY(validate(arg.memory_index));
  1749. if ((1 << arg.align) > max_alignment)
  1750. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.align, 0u, max_alignment);
  1751. return stack.take_and_put<ValueType::I32>(ValueType::V128);
  1752. }
  1753. VALIDATE_INSTRUCTION(v128_load32x2_u)
  1754. {
  1755. auto const& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1756. constexpr auto N = 32;
  1757. constexpr auto M = 2;
  1758. constexpr auto max_alignment = N * M / 8;
  1759. TRY(validate(arg.memory_index));
  1760. if ((1 << arg.align) > max_alignment)
  1761. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.align, 0u, max_alignment);
  1762. return stack.take_and_put<ValueType::I32>(ValueType::V128);
  1763. }
  1764. VALIDATE_INSTRUCTION(v128_load8_splat)
  1765. {
  1766. auto const& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1767. constexpr auto N = 8;
  1768. constexpr auto max_alignment = N / 8;
  1769. TRY(validate(arg.memory_index));
  1770. if ((1 << arg.align) > max_alignment)
  1771. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.align, 0u, max_alignment);
  1772. return stack.take_and_put<ValueType::I32>(ValueType::V128);
  1773. }
  1774. VALIDATE_INSTRUCTION(v128_load16_splat)
  1775. {
  1776. auto const& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1777. constexpr auto N = 16;
  1778. constexpr auto max_alignment = N / 8;
  1779. TRY(validate(arg.memory_index));
  1780. if ((1 << arg.align) > max_alignment)
  1781. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.align, 0u, max_alignment);
  1782. return stack.take_and_put<ValueType::I32>(ValueType::V128);
  1783. }
  1784. VALIDATE_INSTRUCTION(v128_load32_splat)
  1785. {
  1786. auto const& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1787. constexpr auto N = 32;
  1788. constexpr auto max_alignment = N / 8;
  1789. TRY(validate(arg.memory_index));
  1790. if ((1 << arg.align) > max_alignment)
  1791. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.align, 0u, max_alignment);
  1792. return stack.take_and_put<ValueType::I32>(ValueType::V128);
  1793. }
  1794. VALIDATE_INSTRUCTION(v128_load64_splat)
  1795. {
  1796. auto const& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1797. constexpr auto N = 64;
  1798. constexpr auto max_alignment = N / 8;
  1799. TRY(validate(arg.memory_index));
  1800. if ((1 << arg.align) > max_alignment)
  1801. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.align, 0u, max_alignment);
  1802. return stack.take_and_put<ValueType::I32>(ValueType::V128);
  1803. }
  1804. VALIDATE_INSTRUCTION(v128_store)
  1805. {
  1806. auto& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  1807. TRY(validate(arg.memory_index));
  1808. if ((1ull << arg.align) > sizeof(u128))
  1809. return Errors::out_of_bounds("memory op alignment"sv, 1ull << arg.align, 0, sizeof(u128));
  1810. TRY((stack.take<ValueType::V128, ValueType::I32>()));
  1811. return {};
  1812. }
  1813. VALIDATE_INSTRUCTION(v128_const)
  1814. {
  1815. is_constant = true;
  1816. stack.append(ValueType(ValueType::V128));
  1817. return {};
  1818. }
  1819. VALIDATE_INSTRUCTION(i8x16_shuffle)
  1820. {
  1821. auto const& arg = instruction.arguments().get<Instruction::ShuffleArgument>();
  1822. for (auto lane : arg.lanes) {
  1823. if (lane >= 32)
  1824. return Errors::out_of_bounds("shuffle lane"sv, lane, 0, 32);
  1825. }
  1826. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  1827. }
  1828. VALIDATE_INSTRUCTION(i8x16_swizzle)
  1829. {
  1830. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  1831. }
  1832. enum class Shape {
  1833. I8x16,
  1834. I16x8,
  1835. I32x4,
  1836. I64x2,
  1837. F32x4,
  1838. F64x2,
  1839. };
  1840. template<Shape shape>
  1841. static constexpr Wasm::ValueType::Kind unpacked()
  1842. {
  1843. switch (shape) {
  1844. case Shape::I8x16:
  1845. case Shape::I16x8:
  1846. case Shape::I32x4:
  1847. return Wasm::ValueType::I32;
  1848. case Shape::I64x2:
  1849. return Wasm::ValueType::I64;
  1850. case Shape::F32x4:
  1851. return Wasm::ValueType::F32;
  1852. case Shape::F64x2:
  1853. return Wasm::ValueType::F64;
  1854. }
  1855. }
  1856. template<Shape shape>
  1857. static constexpr size_t dimensions()
  1858. {
  1859. switch (shape) {
  1860. case Shape::I8x16:
  1861. return 16;
  1862. case Shape::I16x8:
  1863. return 8;
  1864. case Shape::I32x4:
  1865. return 4;
  1866. case Shape::I64x2:
  1867. return 2;
  1868. case Shape::F32x4:
  1869. return 4;
  1870. case Shape::F64x2:
  1871. return 2;
  1872. }
  1873. }
  1874. VALIDATE_INSTRUCTION(i8x16_splat)
  1875. {
  1876. constexpr auto unpacked_shape = unpacked<Shape::I8x16>();
  1877. return stack.take_and_put<unpacked_shape>(ValueType::V128);
  1878. }
  1879. VALIDATE_INSTRUCTION(i16x8_splat)
  1880. {
  1881. constexpr auto unpacked_shape = unpacked<Shape::I16x8>();
  1882. return stack.take_and_put<unpacked_shape>(ValueType::V128);
  1883. }
  1884. VALIDATE_INSTRUCTION(i32x4_splat)
  1885. {
  1886. constexpr auto unpacked_shape = unpacked<Shape::I32x4>();
  1887. return stack.take_and_put<unpacked_shape>(ValueType::V128);
  1888. }
  1889. VALIDATE_INSTRUCTION(i64x2_splat)
  1890. {
  1891. constexpr auto unpacked_shape = unpacked<Shape::I64x2>();
  1892. return stack.take_and_put<unpacked_shape>(ValueType::V128);
  1893. }
  1894. VALIDATE_INSTRUCTION(f32x4_splat)
  1895. {
  1896. constexpr auto unpacked_shape = unpacked<Shape::F32x4>();
  1897. return stack.take_and_put<unpacked_shape>(ValueType::V128);
  1898. }
  1899. VALIDATE_INSTRUCTION(f64x2_splat)
  1900. {
  1901. constexpr auto unpacked_shape = unpacked<Shape::F64x2>();
  1902. return stack.take_and_put<unpacked_shape>(ValueType::V128);
  1903. }
  1904. VALIDATE_INSTRUCTION(i8x16_extract_lane_s)
  1905. {
  1906. auto const& arg = instruction.arguments().get<Instruction::LaneIndex>();
  1907. constexpr auto shape = Shape::I8x16;
  1908. constexpr auto max_lane = dimensions<shape>();
  1909. if (arg.lane >= max_lane)
  1910. return Errors::out_of_bounds("extract lane"sv, arg.lane, 0, max_lane);
  1911. return stack.take_and_put<ValueType::V128>(unpacked<shape>());
  1912. }
  1913. VALIDATE_INSTRUCTION(i8x16_extract_lane_u)
  1914. {
  1915. auto const& arg = instruction.arguments().get<Instruction::LaneIndex>();
  1916. constexpr auto shape = Shape::I8x16;
  1917. constexpr auto max_lane = dimensions<shape>();
  1918. if (arg.lane >= max_lane)
  1919. return Errors::out_of_bounds("extract lane"sv, arg.lane, 0, max_lane);
  1920. return stack.take_and_put<ValueType::V128>(unpacked<shape>());
  1921. }
  1922. VALIDATE_INSTRUCTION(i8x16_replace_lane)
  1923. {
  1924. auto const& arg = instruction.arguments().get<Instruction::LaneIndex>();
  1925. constexpr auto shape = Shape::I8x16;
  1926. constexpr auto max_lane = dimensions<shape>();
  1927. if (arg.lane >= max_lane)
  1928. return Errors::out_of_bounds("extract lane"sv, arg.lane, 0, max_lane);
  1929. return stack.take_and_put<unpacked<shape>(), ValueType::V128>(ValueType::V128);
  1930. }
  1931. VALIDATE_INSTRUCTION(i16x8_extract_lane_s)
  1932. {
  1933. auto const& arg = instruction.arguments().get<Instruction::LaneIndex>();
  1934. constexpr auto shape = Shape::I16x8;
  1935. constexpr auto max_lane = dimensions<shape>();
  1936. if (arg.lane >= max_lane)
  1937. return Errors::out_of_bounds("extract lane"sv, arg.lane, 0, max_lane);
  1938. return stack.take_and_put<ValueType::V128>(unpacked<shape>());
  1939. }
  1940. VALIDATE_INSTRUCTION(i16x8_extract_lane_u)
  1941. {
  1942. auto const& arg = instruction.arguments().get<Instruction::LaneIndex>();
  1943. constexpr auto shape = Shape::I16x8;
  1944. constexpr auto max_lane = dimensions<shape>();
  1945. if (arg.lane >= max_lane)
  1946. return Errors::out_of_bounds("extract lane"sv, arg.lane, 0, max_lane);
  1947. return stack.take_and_put<ValueType::V128>(unpacked<shape>());
  1948. }
  1949. VALIDATE_INSTRUCTION(i16x8_replace_lane)
  1950. {
  1951. auto const& arg = instruction.arguments().get<Instruction::LaneIndex>();
  1952. constexpr auto shape = Shape::I16x8;
  1953. constexpr auto max_lane = dimensions<shape>();
  1954. if (arg.lane >= max_lane)
  1955. return Errors::out_of_bounds("extract lane"sv, arg.lane, 0, max_lane);
  1956. return stack.take_and_put<unpacked<shape>(), ValueType::V128>(ValueType::V128);
  1957. }
  1958. VALIDATE_INSTRUCTION(i32x4_extract_lane)
  1959. {
  1960. auto const& arg = instruction.arguments().get<Instruction::LaneIndex>();
  1961. constexpr auto shape = Shape::I32x4;
  1962. constexpr auto max_lane = dimensions<shape>();
  1963. if (arg.lane >= max_lane)
  1964. return Errors::out_of_bounds("extract lane"sv, arg.lane, 0, max_lane);
  1965. return stack.take_and_put<ValueType::V128>(unpacked<shape>());
  1966. }
  1967. VALIDATE_INSTRUCTION(i32x4_replace_lane)
  1968. {
  1969. auto const& arg = instruction.arguments().get<Instruction::LaneIndex>();
  1970. constexpr auto shape = Shape::I32x4;
  1971. constexpr auto max_lane = dimensions<shape>();
  1972. if (arg.lane >= max_lane)
  1973. return Errors::out_of_bounds("extract lane"sv, arg.lane, 0, max_lane);
  1974. return stack.take_and_put<unpacked<shape>(), ValueType::V128>(ValueType::V128);
  1975. }
  1976. VALIDATE_INSTRUCTION(i64x2_extract_lane)
  1977. {
  1978. auto const& arg = instruction.arguments().get<Instruction::LaneIndex>();
  1979. constexpr auto shape = Shape::I64x2;
  1980. constexpr auto max_lane = dimensions<shape>();
  1981. if (arg.lane >= max_lane)
  1982. return Errors::out_of_bounds("extract lane"sv, arg.lane, 0, max_lane);
  1983. return stack.take_and_put<ValueType::V128>(unpacked<shape>());
  1984. }
  1985. VALIDATE_INSTRUCTION(i64x2_replace_lane)
  1986. {
  1987. auto const& arg = instruction.arguments().get<Instruction::LaneIndex>();
  1988. constexpr auto shape = Shape::I64x2;
  1989. constexpr auto max_lane = dimensions<shape>();
  1990. if (arg.lane >= max_lane)
  1991. return Errors::out_of_bounds("extract lane"sv, arg.lane, 0, max_lane);
  1992. return stack.take_and_put<unpacked<shape>(), ValueType::V128>(ValueType::V128);
  1993. }
  1994. VALIDATE_INSTRUCTION(f32x4_extract_lane)
  1995. {
  1996. auto const& arg = instruction.arguments().get<Instruction::LaneIndex>();
  1997. constexpr auto shape = Shape::F32x4;
  1998. constexpr auto max_lane = dimensions<shape>();
  1999. if (arg.lane >= max_lane)
  2000. return Errors::out_of_bounds("extract lane"sv, arg.lane, 0, max_lane);
  2001. return stack.take_and_put<ValueType::V128>(unpacked<shape>());
  2002. }
  2003. VALIDATE_INSTRUCTION(f32x4_replace_lane)
  2004. {
  2005. auto const& arg = instruction.arguments().get<Instruction::LaneIndex>();
  2006. constexpr auto shape = Shape::F32x4;
  2007. constexpr auto max_lane = dimensions<shape>();
  2008. if (arg.lane >= max_lane)
  2009. return Errors::out_of_bounds("extract lane"sv, arg.lane, 0, max_lane);
  2010. return stack.take_and_put<unpacked<shape>(), ValueType::V128>(ValueType::V128);
  2011. }
  2012. VALIDATE_INSTRUCTION(f64x2_extract_lane)
  2013. {
  2014. auto const& arg = instruction.arguments().get<Instruction::LaneIndex>();
  2015. constexpr auto shape = Shape::F64x2;
  2016. constexpr auto max_lane = dimensions<shape>();
  2017. if (arg.lane >= max_lane)
  2018. return Errors::out_of_bounds("extract lane"sv, arg.lane, 0, max_lane);
  2019. return stack.take_and_put<ValueType::V128>(unpacked<shape>());
  2020. }
  2021. VALIDATE_INSTRUCTION(f64x2_replace_lane)
  2022. {
  2023. auto const& arg = instruction.arguments().get<Instruction::LaneIndex>();
  2024. constexpr auto shape = Shape::F64x2;
  2025. constexpr auto max_lane = dimensions<shape>();
  2026. if (arg.lane >= max_lane)
  2027. return Errors::out_of_bounds("extract lane"sv, arg.lane, 0, max_lane);
  2028. return stack.take_and_put<unpacked<shape>(), ValueType::V128>(ValueType::V128);
  2029. }
  2030. VALIDATE_INSTRUCTION(i8x16_eq)
  2031. {
  2032. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2033. }
  2034. VALIDATE_INSTRUCTION(i8x16_ne)
  2035. {
  2036. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2037. }
  2038. VALIDATE_INSTRUCTION(i8x16_lt_s)
  2039. {
  2040. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2041. }
  2042. VALIDATE_INSTRUCTION(i8x16_lt_u)
  2043. {
  2044. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2045. }
  2046. VALIDATE_INSTRUCTION(i8x16_gt_s)
  2047. {
  2048. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2049. }
  2050. VALIDATE_INSTRUCTION(i8x16_gt_u)
  2051. {
  2052. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2053. }
  2054. VALIDATE_INSTRUCTION(i8x16_le_s)
  2055. {
  2056. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2057. }
  2058. VALIDATE_INSTRUCTION(i8x16_le_u)
  2059. {
  2060. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2061. }
  2062. VALIDATE_INSTRUCTION(i8x16_ge_s)
  2063. {
  2064. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2065. }
  2066. VALIDATE_INSTRUCTION(i8x16_ge_u)
  2067. {
  2068. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2069. }
  2070. VALIDATE_INSTRUCTION(i16x8_eq)
  2071. {
  2072. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2073. }
  2074. VALIDATE_INSTRUCTION(i16x8_ne)
  2075. {
  2076. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2077. }
  2078. VALIDATE_INSTRUCTION(i16x8_lt_s)
  2079. {
  2080. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2081. }
  2082. VALIDATE_INSTRUCTION(i16x8_lt_u)
  2083. {
  2084. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2085. }
  2086. VALIDATE_INSTRUCTION(i16x8_gt_s)
  2087. {
  2088. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2089. }
  2090. VALIDATE_INSTRUCTION(i16x8_gt_u)
  2091. {
  2092. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2093. }
  2094. VALIDATE_INSTRUCTION(i16x8_le_s)
  2095. {
  2096. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2097. }
  2098. VALIDATE_INSTRUCTION(i16x8_le_u)
  2099. {
  2100. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2101. }
  2102. VALIDATE_INSTRUCTION(i16x8_ge_s)
  2103. {
  2104. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2105. }
  2106. VALIDATE_INSTRUCTION(i16x8_ge_u)
  2107. {
  2108. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2109. }
  2110. VALIDATE_INSTRUCTION(i32x4_eq)
  2111. {
  2112. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2113. }
  2114. VALIDATE_INSTRUCTION(i32x4_ne)
  2115. {
  2116. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2117. }
  2118. VALIDATE_INSTRUCTION(i32x4_lt_s)
  2119. {
  2120. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2121. }
  2122. VALIDATE_INSTRUCTION(i32x4_lt_u)
  2123. {
  2124. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2125. }
  2126. VALIDATE_INSTRUCTION(i32x4_gt_s)
  2127. {
  2128. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2129. }
  2130. VALIDATE_INSTRUCTION(i32x4_gt_u)
  2131. {
  2132. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2133. }
  2134. VALIDATE_INSTRUCTION(i32x4_le_s)
  2135. {
  2136. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2137. }
  2138. VALIDATE_INSTRUCTION(i32x4_le_u)
  2139. {
  2140. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2141. }
  2142. VALIDATE_INSTRUCTION(i32x4_ge_s)
  2143. {
  2144. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2145. }
  2146. VALIDATE_INSTRUCTION(i32x4_ge_u)
  2147. {
  2148. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2149. }
  2150. VALIDATE_INSTRUCTION(f32x4_eq)
  2151. {
  2152. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2153. }
  2154. VALIDATE_INSTRUCTION(f32x4_ne)
  2155. {
  2156. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2157. }
  2158. VALIDATE_INSTRUCTION(f32x4_lt)
  2159. {
  2160. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2161. }
  2162. VALIDATE_INSTRUCTION(f32x4_gt)
  2163. {
  2164. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2165. }
  2166. VALIDATE_INSTRUCTION(f32x4_le)
  2167. {
  2168. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2169. }
  2170. VALIDATE_INSTRUCTION(f32x4_ge)
  2171. {
  2172. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2173. }
  2174. VALIDATE_INSTRUCTION(f64x2_eq)
  2175. {
  2176. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2177. }
  2178. VALIDATE_INSTRUCTION(f64x2_ne)
  2179. {
  2180. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2181. }
  2182. VALIDATE_INSTRUCTION(f64x2_lt)
  2183. {
  2184. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2185. }
  2186. VALIDATE_INSTRUCTION(f64x2_gt)
  2187. {
  2188. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2189. }
  2190. VALIDATE_INSTRUCTION(f64x2_le)
  2191. {
  2192. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2193. }
  2194. VALIDATE_INSTRUCTION(f64x2_ge)
  2195. {
  2196. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2197. }
  2198. VALIDATE_INSTRUCTION(v128_not)
  2199. {
  2200. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2201. }
  2202. VALIDATE_INSTRUCTION(v128_and)
  2203. {
  2204. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2205. }
  2206. VALIDATE_INSTRUCTION(v128_andnot)
  2207. {
  2208. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2209. }
  2210. VALIDATE_INSTRUCTION(v128_or)
  2211. {
  2212. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2213. }
  2214. VALIDATE_INSTRUCTION(v128_xor)
  2215. {
  2216. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2217. }
  2218. VALIDATE_INSTRUCTION(v128_bitselect)
  2219. {
  2220. return stack.take_and_put<ValueType::V128, ValueType::V128, ValueType::V128>(ValueType::V128);
  2221. }
  2222. VALIDATE_INSTRUCTION(v128_any_true)
  2223. {
  2224. return stack.take_and_put<ValueType::V128>(ValueType::I32);
  2225. }
  2226. VALIDATE_INSTRUCTION(v128_load8_lane)
  2227. {
  2228. auto const& arg = instruction.arguments().get<Instruction::MemoryAndLaneArgument>();
  2229. constexpr auto N = 8;
  2230. constexpr auto max_lane = 128 / N;
  2231. constexpr auto max_alignment = N / 8;
  2232. if (arg.lane >= max_lane)
  2233. return Errors::out_of_bounds("lane index"sv, arg.lane, 0u, max_lane);
  2234. TRY(validate(arg.memory.memory_index));
  2235. if ((1 << arg.memory.align) > max_alignment)
  2236. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.memory.align, 0u, max_alignment);
  2237. return stack.take_and_put<ValueType::V128, ValueType::I32>(ValueType::V128);
  2238. }
  2239. VALIDATE_INSTRUCTION(v128_load16_lane)
  2240. {
  2241. auto const& arg = instruction.arguments().get<Instruction::MemoryAndLaneArgument>();
  2242. constexpr auto N = 16;
  2243. constexpr auto max_lane = 128 / N;
  2244. constexpr auto max_alignment = N / 8;
  2245. if (arg.lane >= max_lane)
  2246. return Errors::out_of_bounds("lane index"sv, arg.lane, 0u, max_lane);
  2247. TRY(validate(arg.memory.memory_index));
  2248. if ((1 << arg.memory.align) > max_alignment)
  2249. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.memory.align, 0u, max_alignment);
  2250. return stack.take_and_put<ValueType::V128, ValueType::I32>(ValueType::V128);
  2251. }
  2252. VALIDATE_INSTRUCTION(v128_load32_lane)
  2253. {
  2254. auto const& arg = instruction.arguments().get<Instruction::MemoryAndLaneArgument>();
  2255. constexpr auto N = 32;
  2256. constexpr auto max_lane = 128 / N;
  2257. constexpr auto max_alignment = N / 8;
  2258. if (arg.lane >= max_lane)
  2259. return Errors::out_of_bounds("lane index"sv, arg.lane, 0u, max_lane);
  2260. TRY(validate(arg.memory.memory_index));
  2261. if ((1 << arg.memory.align) > max_alignment)
  2262. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.memory.align, 0u, max_alignment);
  2263. return stack.take_and_put<ValueType::V128, ValueType::I32>(ValueType::V128);
  2264. }
  2265. VALIDATE_INSTRUCTION(v128_load64_lane)
  2266. {
  2267. auto const& arg = instruction.arguments().get<Instruction::MemoryAndLaneArgument>();
  2268. constexpr auto N = 64;
  2269. constexpr auto max_lane = 128 / N;
  2270. constexpr auto max_alignment = N / 8;
  2271. if (arg.lane >= max_lane)
  2272. return Errors::out_of_bounds("lane index"sv, arg.lane, 0u, max_lane);
  2273. TRY(validate(arg.memory.memory_index));
  2274. if ((1 << arg.memory.align) > max_alignment)
  2275. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.memory.align, 0u, max_alignment);
  2276. return stack.take_and_put<ValueType::V128, ValueType::I32>(ValueType::V128);
  2277. }
  2278. VALIDATE_INSTRUCTION(v128_store8_lane)
  2279. {
  2280. auto const& arg = instruction.arguments().get<Instruction::MemoryAndLaneArgument>();
  2281. constexpr auto N = 8;
  2282. constexpr auto max_lane = 128 / N;
  2283. constexpr auto max_alignment = N / 8;
  2284. if (arg.lane >= max_lane)
  2285. return Errors::out_of_bounds("lane index"sv, arg.lane, 0u, max_lane);
  2286. TRY(validate(arg.memory.memory_index));
  2287. if ((1 << arg.memory.align) > max_alignment)
  2288. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.memory.align, 0u, max_alignment);
  2289. return stack.take<ValueType::V128, ValueType::I32>();
  2290. }
  2291. VALIDATE_INSTRUCTION(v128_store16_lane)
  2292. {
  2293. auto const& arg = instruction.arguments().get<Instruction::MemoryAndLaneArgument>();
  2294. constexpr auto N = 16;
  2295. constexpr auto max_lane = 128 / N;
  2296. constexpr auto max_alignment = N / 8;
  2297. if (arg.lane >= max_lane)
  2298. return Errors::out_of_bounds("lane index"sv, arg.lane, 0u, max_lane);
  2299. TRY(validate(arg.memory.memory_index));
  2300. if ((1 << arg.memory.align) > max_alignment)
  2301. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.memory.align, 0u, max_alignment);
  2302. return stack.take<ValueType::V128, ValueType::I32>();
  2303. }
  2304. VALIDATE_INSTRUCTION(v128_store32_lane)
  2305. {
  2306. auto const& arg = instruction.arguments().get<Instruction::MemoryAndLaneArgument>();
  2307. constexpr auto N = 32;
  2308. constexpr auto max_lane = 128 / N;
  2309. constexpr auto max_alignment = N / 8;
  2310. if (arg.lane >= max_lane)
  2311. return Errors::out_of_bounds("lane index"sv, arg.lane, 0u, max_lane);
  2312. TRY(validate(arg.memory.memory_index));
  2313. if ((1 << arg.memory.align) > max_alignment)
  2314. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.memory.align, 0u, max_alignment);
  2315. return stack.take<ValueType::V128, ValueType::I32>();
  2316. }
  2317. VALIDATE_INSTRUCTION(v128_store64_lane)
  2318. {
  2319. auto const& arg = instruction.arguments().get<Instruction::MemoryAndLaneArgument>();
  2320. constexpr auto N = 64;
  2321. constexpr auto max_lane = 128 / N;
  2322. constexpr auto max_alignment = N / 8;
  2323. if (arg.lane >= max_lane)
  2324. return Errors::out_of_bounds("lane index"sv, arg.lane, 0u, max_lane);
  2325. TRY(validate(arg.memory.memory_index));
  2326. if ((1 << arg.memory.align) > max_alignment)
  2327. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.memory.align, 0u, max_alignment);
  2328. return stack.take<ValueType::V128, ValueType::I32>();
  2329. }
  2330. VALIDATE_INSTRUCTION(v128_load32_zero)
  2331. {
  2332. auto const& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  2333. constexpr auto N = 32;
  2334. constexpr auto max_alignment = N / 8;
  2335. TRY(validate(arg.memory_index));
  2336. if ((1 << arg.align) > max_alignment)
  2337. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.align, 0u, max_alignment);
  2338. return stack.take_and_put<ValueType::I32>(ValueType::V128);
  2339. }
  2340. VALIDATE_INSTRUCTION(v128_load64_zero)
  2341. {
  2342. auto const& arg = instruction.arguments().get<Instruction::MemoryArgument>();
  2343. constexpr auto N = 64;
  2344. constexpr auto max_alignment = N / 8;
  2345. TRY(validate(arg.memory_index));
  2346. if ((1 << arg.align) > max_alignment)
  2347. return Errors::out_of_bounds("memory op alignment"sv, 1 << arg.align, 0u, max_alignment);
  2348. return stack.take_and_put<ValueType::I32>(ValueType::V128);
  2349. }
  2350. VALIDATE_INSTRUCTION(f32x4_demote_f64x2_zero)
  2351. {
  2352. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2353. }
  2354. VALIDATE_INSTRUCTION(f64x2_promote_low_f32x4)
  2355. {
  2356. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2357. }
  2358. VALIDATE_INSTRUCTION(i8x16_abs)
  2359. {
  2360. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2361. }
  2362. VALIDATE_INSTRUCTION(i8x16_neg)
  2363. {
  2364. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2365. }
  2366. VALIDATE_INSTRUCTION(i8x16_popcnt)
  2367. {
  2368. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2369. }
  2370. VALIDATE_INSTRUCTION(i8x16_all_true)
  2371. {
  2372. return stack.take_and_put<ValueType::V128>(ValueType::I32);
  2373. }
  2374. VALIDATE_INSTRUCTION(i8x16_bitmask)
  2375. {
  2376. return stack.take_and_put<ValueType::V128>(ValueType::I32);
  2377. }
  2378. VALIDATE_INSTRUCTION(i8x16_narrow_i16x8_s)
  2379. {
  2380. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2381. }
  2382. VALIDATE_INSTRUCTION(i8x16_narrow_i16x8_u)
  2383. {
  2384. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2385. }
  2386. VALIDATE_INSTRUCTION(f32x4_ceil)
  2387. {
  2388. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2389. }
  2390. VALIDATE_INSTRUCTION(f32x4_floor)
  2391. {
  2392. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2393. }
  2394. VALIDATE_INSTRUCTION(f32x4_trunc)
  2395. {
  2396. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2397. }
  2398. VALIDATE_INSTRUCTION(f32x4_nearest)
  2399. {
  2400. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2401. }
  2402. VALIDATE_INSTRUCTION(i8x16_shl)
  2403. {
  2404. return stack.take_and_put<ValueType::I32, ValueType::V128>(ValueType::V128);
  2405. }
  2406. VALIDATE_INSTRUCTION(i8x16_shr_s)
  2407. {
  2408. return stack.take_and_put<ValueType::I32, ValueType::V128>(ValueType::V128);
  2409. }
  2410. VALIDATE_INSTRUCTION(i8x16_shr_u)
  2411. {
  2412. return stack.take_and_put<ValueType::I32, ValueType::V128>(ValueType::V128);
  2413. }
  2414. VALIDATE_INSTRUCTION(i8x16_add)
  2415. {
  2416. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2417. }
  2418. VALIDATE_INSTRUCTION(i8x16_add_sat_s)
  2419. {
  2420. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2421. }
  2422. VALIDATE_INSTRUCTION(i8x16_add_sat_u)
  2423. {
  2424. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2425. }
  2426. VALIDATE_INSTRUCTION(i8x16_sub)
  2427. {
  2428. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2429. }
  2430. VALIDATE_INSTRUCTION(i8x16_sub_sat_s)
  2431. {
  2432. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2433. }
  2434. VALIDATE_INSTRUCTION(i8x16_sub_sat_u)
  2435. {
  2436. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2437. }
  2438. VALIDATE_INSTRUCTION(f64x2_ceil)
  2439. {
  2440. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2441. }
  2442. VALIDATE_INSTRUCTION(f64x2_floor)
  2443. {
  2444. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2445. }
  2446. VALIDATE_INSTRUCTION(i8x16_min_s)
  2447. {
  2448. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2449. }
  2450. VALIDATE_INSTRUCTION(i8x16_min_u)
  2451. {
  2452. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2453. }
  2454. VALIDATE_INSTRUCTION(i8x16_max_s)
  2455. {
  2456. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2457. }
  2458. VALIDATE_INSTRUCTION(i8x16_max_u)
  2459. {
  2460. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2461. }
  2462. VALIDATE_INSTRUCTION(f64x2_trunc)
  2463. {
  2464. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2465. }
  2466. VALIDATE_INSTRUCTION(i8x16_avgr_u)
  2467. {
  2468. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2469. }
  2470. VALIDATE_INSTRUCTION(i16x8_extadd_pairwise_i8x16_s)
  2471. {
  2472. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2473. }
  2474. VALIDATE_INSTRUCTION(i16x8_extadd_pairwise_i8x16_u)
  2475. {
  2476. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2477. }
  2478. VALIDATE_INSTRUCTION(i32x4_extadd_pairwise_i16x8_s)
  2479. {
  2480. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2481. }
  2482. VALIDATE_INSTRUCTION(i32x4_extadd_pairwise_i16x8_u)
  2483. {
  2484. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2485. }
  2486. VALIDATE_INSTRUCTION(i16x8_abs)
  2487. {
  2488. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2489. }
  2490. VALIDATE_INSTRUCTION(i16x8_neg)
  2491. {
  2492. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2493. }
  2494. VALIDATE_INSTRUCTION(i16x8_q15mulr_sat_s)
  2495. {
  2496. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2497. }
  2498. VALIDATE_INSTRUCTION(i16x8_all_true)
  2499. {
  2500. return stack.take_and_put<ValueType::V128>(ValueType::I32);
  2501. }
  2502. VALIDATE_INSTRUCTION(i16x8_bitmask)
  2503. {
  2504. return stack.take_and_put<ValueType::V128>(ValueType::I32);
  2505. }
  2506. VALIDATE_INSTRUCTION(i16x8_narrow_i32x4_s)
  2507. {
  2508. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2509. }
  2510. VALIDATE_INSTRUCTION(i16x8_narrow_i32x4_u)
  2511. {
  2512. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2513. }
  2514. VALIDATE_INSTRUCTION(i16x8_extend_low_i8x16_s)
  2515. {
  2516. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2517. }
  2518. VALIDATE_INSTRUCTION(i16x8_extend_high_i8x16_s)
  2519. {
  2520. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2521. }
  2522. VALIDATE_INSTRUCTION(i16x8_extend_low_i8x16_u)
  2523. {
  2524. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2525. }
  2526. VALIDATE_INSTRUCTION(i16x8_extend_high_i8x16_u)
  2527. {
  2528. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2529. }
  2530. VALIDATE_INSTRUCTION(i16x8_shl)
  2531. {
  2532. return stack.take_and_put<ValueType::I32, ValueType::V128>(ValueType::V128);
  2533. }
  2534. VALIDATE_INSTRUCTION(i16x8_shr_s)
  2535. {
  2536. return stack.take_and_put<ValueType::I32, ValueType::V128>(ValueType::V128);
  2537. }
  2538. VALIDATE_INSTRUCTION(i16x8_shr_u)
  2539. {
  2540. return stack.take_and_put<ValueType::I32, ValueType::V128>(ValueType::V128);
  2541. }
  2542. VALIDATE_INSTRUCTION(i16x8_add)
  2543. {
  2544. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2545. }
  2546. VALIDATE_INSTRUCTION(i16x8_add_sat_s)
  2547. {
  2548. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2549. }
  2550. VALIDATE_INSTRUCTION(i16x8_add_sat_u)
  2551. {
  2552. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2553. }
  2554. VALIDATE_INSTRUCTION(i16x8_sub)
  2555. {
  2556. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2557. }
  2558. VALIDATE_INSTRUCTION(i16x8_sub_sat_s)
  2559. {
  2560. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2561. }
  2562. VALIDATE_INSTRUCTION(i16x8_sub_sat_u)
  2563. {
  2564. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2565. }
  2566. VALIDATE_INSTRUCTION(f64x2_nearest)
  2567. {
  2568. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2569. }
  2570. VALIDATE_INSTRUCTION(i16x8_mul)
  2571. {
  2572. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2573. }
  2574. VALIDATE_INSTRUCTION(i16x8_min_s)
  2575. {
  2576. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2577. }
  2578. VALIDATE_INSTRUCTION(i16x8_min_u)
  2579. {
  2580. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2581. }
  2582. VALIDATE_INSTRUCTION(i16x8_max_s)
  2583. {
  2584. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2585. }
  2586. VALIDATE_INSTRUCTION(i16x8_max_u)
  2587. {
  2588. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2589. }
  2590. VALIDATE_INSTRUCTION(i16x8_avgr_u)
  2591. {
  2592. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2593. }
  2594. VALIDATE_INSTRUCTION(i16x8_extmul_low_i8x16_s)
  2595. {
  2596. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2597. }
  2598. VALIDATE_INSTRUCTION(i16x8_extmul_high_i8x16_s)
  2599. {
  2600. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2601. }
  2602. VALIDATE_INSTRUCTION(i16x8_extmul_low_i8x16_u)
  2603. {
  2604. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2605. }
  2606. VALIDATE_INSTRUCTION(i16x8_extmul_high_i8x16_u)
  2607. {
  2608. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2609. }
  2610. VALIDATE_INSTRUCTION(i32x4_abs)
  2611. {
  2612. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2613. }
  2614. VALIDATE_INSTRUCTION(i32x4_neg)
  2615. {
  2616. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2617. }
  2618. VALIDATE_INSTRUCTION(i32x4_all_true)
  2619. {
  2620. return stack.take_and_put<ValueType::V128>(ValueType::I32);
  2621. }
  2622. VALIDATE_INSTRUCTION(i32x4_bitmask)
  2623. {
  2624. return stack.take_and_put<ValueType::V128>(ValueType::I32);
  2625. }
  2626. VALIDATE_INSTRUCTION(i32x4_extend_low_i16x8_s)
  2627. {
  2628. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2629. }
  2630. VALIDATE_INSTRUCTION(i32x4_extend_high_i16x8_s)
  2631. {
  2632. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2633. }
  2634. VALIDATE_INSTRUCTION(i32x4_extend_low_i16x8_u)
  2635. {
  2636. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2637. }
  2638. VALIDATE_INSTRUCTION(i32x4_extend_high_i16x8_u)
  2639. {
  2640. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2641. }
  2642. VALIDATE_INSTRUCTION(i32x4_shl)
  2643. {
  2644. return stack.take_and_put<ValueType::I32, ValueType::V128>(ValueType::V128);
  2645. }
  2646. VALIDATE_INSTRUCTION(i32x4_shr_s)
  2647. {
  2648. return stack.take_and_put<ValueType::I32, ValueType::V128>(ValueType::V128);
  2649. }
  2650. VALIDATE_INSTRUCTION(i32x4_shr_u)
  2651. {
  2652. return stack.take_and_put<ValueType::I32, ValueType::V128>(ValueType::V128);
  2653. }
  2654. VALIDATE_INSTRUCTION(i32x4_add)
  2655. {
  2656. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2657. }
  2658. VALIDATE_INSTRUCTION(i32x4_sub)
  2659. {
  2660. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2661. }
  2662. VALIDATE_INSTRUCTION(i32x4_mul)
  2663. {
  2664. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2665. }
  2666. VALIDATE_INSTRUCTION(i32x4_min_s)
  2667. {
  2668. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2669. }
  2670. VALIDATE_INSTRUCTION(i32x4_min_u)
  2671. {
  2672. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2673. }
  2674. VALIDATE_INSTRUCTION(i32x4_max_s)
  2675. {
  2676. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2677. }
  2678. VALIDATE_INSTRUCTION(i32x4_max_u)
  2679. {
  2680. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2681. }
  2682. VALIDATE_INSTRUCTION(i32x4_dot_i16x8_s)
  2683. {
  2684. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2685. }
  2686. VALIDATE_INSTRUCTION(i32x4_extmul_low_i16x8_s)
  2687. {
  2688. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2689. }
  2690. VALIDATE_INSTRUCTION(i32x4_extmul_high_i16x8_s)
  2691. {
  2692. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2693. }
  2694. VALIDATE_INSTRUCTION(i32x4_extmul_low_i16x8_u)
  2695. {
  2696. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2697. }
  2698. VALIDATE_INSTRUCTION(i32x4_extmul_high_i16x8_u)
  2699. {
  2700. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2701. }
  2702. VALIDATE_INSTRUCTION(i64x2_abs)
  2703. {
  2704. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2705. }
  2706. VALIDATE_INSTRUCTION(i64x2_neg)
  2707. {
  2708. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2709. }
  2710. VALIDATE_INSTRUCTION(i64x2_all_true)
  2711. {
  2712. return stack.take_and_put<ValueType::V128>(ValueType::I32);
  2713. }
  2714. VALIDATE_INSTRUCTION(i64x2_bitmask)
  2715. {
  2716. return stack.take_and_put<ValueType::V128>(ValueType::I32);
  2717. }
  2718. VALIDATE_INSTRUCTION(i64x2_extend_low_i32x4_s)
  2719. {
  2720. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2721. }
  2722. VALIDATE_INSTRUCTION(i64x2_extend_high_i32x4_s)
  2723. {
  2724. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2725. }
  2726. VALIDATE_INSTRUCTION(i64x2_extend_low_i32x4_u)
  2727. {
  2728. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2729. }
  2730. VALIDATE_INSTRUCTION(i64x2_extend_high_i32x4_u)
  2731. {
  2732. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2733. }
  2734. VALIDATE_INSTRUCTION(i64x2_shl)
  2735. {
  2736. return stack.take_and_put<ValueType::I32, ValueType::V128>(ValueType::V128);
  2737. }
  2738. VALIDATE_INSTRUCTION(i64x2_shr_s)
  2739. {
  2740. return stack.take_and_put<ValueType::I32, ValueType::V128>(ValueType::V128);
  2741. }
  2742. VALIDATE_INSTRUCTION(i64x2_shr_u)
  2743. {
  2744. return stack.take_and_put<ValueType::I32, ValueType::V128>(ValueType::V128);
  2745. }
  2746. VALIDATE_INSTRUCTION(i64x2_add)
  2747. {
  2748. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2749. }
  2750. VALIDATE_INSTRUCTION(i64x2_sub)
  2751. {
  2752. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2753. }
  2754. VALIDATE_INSTRUCTION(i64x2_mul)
  2755. {
  2756. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2757. }
  2758. VALIDATE_INSTRUCTION(i64x2_eq)
  2759. {
  2760. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2761. }
  2762. VALIDATE_INSTRUCTION(i64x2_ne)
  2763. {
  2764. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2765. }
  2766. VALIDATE_INSTRUCTION(i64x2_lt_s)
  2767. {
  2768. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2769. }
  2770. VALIDATE_INSTRUCTION(i64x2_gt_s)
  2771. {
  2772. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2773. }
  2774. VALIDATE_INSTRUCTION(i64x2_le_s)
  2775. {
  2776. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2777. }
  2778. VALIDATE_INSTRUCTION(i64x2_ge_s)
  2779. {
  2780. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2781. }
  2782. VALIDATE_INSTRUCTION(i64x2_extmul_low_i32x4_s)
  2783. {
  2784. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2785. }
  2786. VALIDATE_INSTRUCTION(i64x2_extmul_high_i32x4_s)
  2787. {
  2788. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2789. }
  2790. VALIDATE_INSTRUCTION(i64x2_extmul_low_i32x4_u)
  2791. {
  2792. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2793. }
  2794. VALIDATE_INSTRUCTION(i64x2_extmul_high_i32x4_u)
  2795. {
  2796. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2797. }
  2798. VALIDATE_INSTRUCTION(f32x4_abs)
  2799. {
  2800. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2801. }
  2802. VALIDATE_INSTRUCTION(f32x4_neg)
  2803. {
  2804. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2805. }
  2806. VALIDATE_INSTRUCTION(f32x4_sqrt)
  2807. {
  2808. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2809. }
  2810. VALIDATE_INSTRUCTION(f32x4_add)
  2811. {
  2812. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2813. }
  2814. VALIDATE_INSTRUCTION(f32x4_sub)
  2815. {
  2816. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2817. }
  2818. VALIDATE_INSTRUCTION(f32x4_mul)
  2819. {
  2820. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2821. }
  2822. VALIDATE_INSTRUCTION(f32x4_div)
  2823. {
  2824. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2825. }
  2826. VALIDATE_INSTRUCTION(f32x4_min)
  2827. {
  2828. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2829. }
  2830. VALIDATE_INSTRUCTION(f32x4_max)
  2831. {
  2832. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2833. }
  2834. VALIDATE_INSTRUCTION(f32x4_pmin)
  2835. {
  2836. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2837. }
  2838. VALIDATE_INSTRUCTION(f32x4_pmax)
  2839. {
  2840. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2841. }
  2842. VALIDATE_INSTRUCTION(f64x2_abs)
  2843. {
  2844. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2845. }
  2846. VALIDATE_INSTRUCTION(f64x2_neg)
  2847. {
  2848. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2849. }
  2850. VALIDATE_INSTRUCTION(f64x2_sqrt)
  2851. {
  2852. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2853. }
  2854. VALIDATE_INSTRUCTION(f64x2_add)
  2855. {
  2856. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2857. }
  2858. VALIDATE_INSTRUCTION(f64x2_sub)
  2859. {
  2860. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2861. }
  2862. VALIDATE_INSTRUCTION(f64x2_mul)
  2863. {
  2864. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2865. }
  2866. VALIDATE_INSTRUCTION(f64x2_div)
  2867. {
  2868. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2869. }
  2870. VALIDATE_INSTRUCTION(f64x2_min)
  2871. {
  2872. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2873. }
  2874. VALIDATE_INSTRUCTION(f64x2_max)
  2875. {
  2876. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2877. }
  2878. VALIDATE_INSTRUCTION(f64x2_pmin)
  2879. {
  2880. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2881. }
  2882. VALIDATE_INSTRUCTION(f64x2_pmax)
  2883. {
  2884. return stack.take_and_put<ValueType::V128, ValueType::V128>(ValueType::V128);
  2885. }
  2886. VALIDATE_INSTRUCTION(i32x4_trunc_sat_f32x4_s)
  2887. {
  2888. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2889. }
  2890. VALIDATE_INSTRUCTION(i32x4_trunc_sat_f32x4_u)
  2891. {
  2892. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2893. }
  2894. VALIDATE_INSTRUCTION(f32x4_convert_i32x4_s)
  2895. {
  2896. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2897. }
  2898. VALIDATE_INSTRUCTION(f32x4_convert_i32x4_u)
  2899. {
  2900. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2901. }
  2902. VALIDATE_INSTRUCTION(i32x4_trunc_sat_f64x2_s_zero)
  2903. {
  2904. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2905. }
  2906. VALIDATE_INSTRUCTION(i32x4_trunc_sat_f64x2_u_zero)
  2907. {
  2908. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2909. }
  2910. VALIDATE_INSTRUCTION(f64x2_convert_low_i32x4_s)
  2911. {
  2912. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2913. }
  2914. VALIDATE_INSTRUCTION(f64x2_convert_low_i32x4_u)
  2915. {
  2916. return stack.take_and_put<ValueType::V128>(ValueType::V128);
  2917. }
  2918. ErrorOr<void, ValidationError> Validator::validate(Instruction const& instruction, Stack& stack, bool& is_constant)
  2919. {
  2920. switch (instruction.opcode().value()) {
  2921. #define M(name, integer_value) \
  2922. case Instructions::name.value(): \
  2923. dbgln_if(WASM_VALIDATOR_DEBUG, "checking {}, stack = {}", #name, stack); \
  2924. return validate_instruction<integer_value>(instruction, stack, is_constant);
  2925. ENUMERATE_WASM_OPCODES(M)
  2926. #undef M
  2927. default:
  2928. is_constant = false;
  2929. return Errors::invalid(ByteString::formatted("instruction opcode ({:#x})", instruction.opcode().value()));
  2930. }
  2931. }
  2932. ErrorOr<Validator::ExpressionTypeResult, ValidationError> Validator::validate(Expression const& expression, Vector<ValueType> const& result_types)
  2933. {
  2934. if (m_frames.is_empty())
  2935. m_frames.empend(FunctionType { {}, result_types }, FrameKind::Function, (size_t)0);
  2936. auto stack = Stack(m_frames);
  2937. bool is_constant_expression = true;
  2938. for (auto& instruction : expression.instructions()) {
  2939. bool is_constant = false;
  2940. TRY(validate(instruction, stack, is_constant));
  2941. is_constant_expression &= is_constant;
  2942. }
  2943. auto expected_result_types = result_types;
  2944. while (!expected_result_types.is_empty())
  2945. TRY(stack.take(expected_result_types.take_last()));
  2946. for (auto& type : result_types)
  2947. stack.append(type);
  2948. m_frames.take_last();
  2949. VERIFY(m_frames.is_empty());
  2950. return ExpressionTypeResult { stack.release_vector(), is_constant_expression };
  2951. }
  2952. ByteString Validator::Errors::find_instruction_name(SourceLocation const& location)
  2953. {
  2954. auto index = location.function_name().find('<');
  2955. auto end_index = location.function_name().find('>');
  2956. if (!index.has_value() || !end_index.has_value())
  2957. return ByteString::formatted("{}", location);
  2958. auto opcode = location.function_name().substring_view(index.value() + 1, end_index.value() - index.value() - 1).to_number<unsigned>();
  2959. if (!opcode.has_value())
  2960. return ByteString::formatted("{}", location);
  2961. return instruction_name(OpCode { *opcode });
  2962. }
  2963. }