mirror of
https://github.com/open-goal/jak-project
synced 2026-08-16 13:17:34 -04:00
add support for non virtual states (#764)
* add support for non virtual states * typecheck go * start on virtual states * more support for virtual states * offline passes * fix tests * use behavior shortcut instead of lambda * final cleanup of virtual go * unused var warnings and fix inconsistent enum decompile order on win vs linux * fix thread safety bug with goal symbol table and vif1 interrupt handler * fix type mistake
This commit is contained in:
@@ -5,25 +5,53 @@
|
||||
#include "decompiler/analysis/final_output.h"
|
||||
|
||||
namespace decompiler {
|
||||
|
||||
namespace {
|
||||
bool try_convert_lambda(const Function& parent_function,
|
||||
FormPool& pool,
|
||||
Form* f,
|
||||
bool defstate_behavior) {
|
||||
auto atom = form_as_atom(f);
|
||||
if (atom && atom->is_static_addr()) {
|
||||
auto lab = parent_function.ir2.env.file->labels.at(atom->label());
|
||||
auto& env = parent_function.ir2.env;
|
||||
auto label_kv = env.label_types().find(lab.name);
|
||||
if (label_kv != env.label_types().end()) {
|
||||
if (label_kv->second.type_name == "_lambda_") {
|
||||
auto& file = env.file;
|
||||
auto other_func = file->try_get_function_at_label(atom->label());
|
||||
if (other_func) {
|
||||
goos::Object result;
|
||||
if (defstate_behavior) {
|
||||
result = final_output_defstate_anonymous_behavior(*other_func);
|
||||
} else {
|
||||
result = final_output_lambda(*other_func);
|
||||
}
|
||||
|
||||
f->clear();
|
||||
f->push_back(pool.alloc_element<LambdaDefinitionElement>(result));
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
} // namespace
|
||||
|
||||
int insert_static_refs(Form* top_level_form,
|
||||
FormPool& pool,
|
||||
const Function& function,
|
||||
const DecompilerTypeSystem&) {
|
||||
int replaced = 0;
|
||||
top_level_form->apply_form([&](Form* f) {
|
||||
auto atom = form_as_atom(f);
|
||||
if (atom && atom->is_static_addr()) {
|
||||
auto lab = function.ir2.env.file->labels.at(atom->label());
|
||||
auto& env = function.ir2.env;
|
||||
auto label_kv = env.label_types().find(lab.name);
|
||||
if (label_kv != env.label_types().end()) {
|
||||
if (label_kv->second.type_name == "_lambda_") {
|
||||
auto& file = env.file;
|
||||
auto other_func = file->try_get_function_at_label(atom->label());
|
||||
if (other_func) {
|
||||
auto result = final_output_lambda(*other_func);
|
||||
f->clear();
|
||||
f->push_back(pool.alloc_element<LambdaDefinitionElement>(result));
|
||||
|
||||
// first, look for defstates and lambdas to behaviors.
|
||||
top_level_form->apply([&](FormElement* fe) {
|
||||
auto as_defstate = dynamic_cast<DefstateElement*>(fe);
|
||||
if (as_defstate) {
|
||||
for (auto& e : as_defstate->entries()) {
|
||||
if (e.is_behavior) {
|
||||
if (try_convert_lambda(function, pool, e.val, true)) {
|
||||
replaced++;
|
||||
}
|
||||
}
|
||||
@@ -31,6 +59,13 @@ int insert_static_refs(Form* top_level_form,
|
||||
}
|
||||
});
|
||||
|
||||
// next, all the rest.
|
||||
top_level_form->apply_form([&](Form* f) {
|
||||
if (try_convert_lambda(function, pool, f, false)) {
|
||||
replaced++;
|
||||
}
|
||||
});
|
||||
|
||||
top_level_form->apply([&](FormElement* fe) {
|
||||
auto as_static_data = dynamic_cast<DecompiledDataElement*>(fe);
|
||||
if (as_static_data) {
|
||||
|
||||
Reference in New Issue
Block a user