#include "get_cmd.h"

USING_YOSYS_NAMESPACE

void GetCmd::help() {
    //   |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|
    log("\n");
    log("   get_%ss [-quiet] [-filter filter_expression] "
        "<%s_selection> \n",
        TypeName().c_str(), TypeName().c_str());
    log("\n");
    log("Get matching %ss\n", TypeName().c_str());
    log("\n");
    log("Print the output to stdout too. This is useful when all Yosys "
        "is "
        "executed.\n");
    log("\n");
    log("    -filter\n");
    log("        Name and value of attribute to be taken into "
        "account.\n");
    log("        e.g. -filter { attr == \"true\" }\n");
    log("\n");
    log("    -quiet\n");
    log("        Don't print the result of the execution to stdout.\n");
    log("\n");
    log("    <selection_pattern>\n");
    log("        Selection of %s names. Default are all %ss in the "
        "design.\n",
        TypeName().c_str(), TypeName().c_str());
    log("\n");
}

void GetCmd::ExecuteSelection(RTLIL::Design* design, const CommandArgs& args) {
    std::vector<std::string> selection_args;
    // Add name of top module to selection string
    std::transform(args.selection_objects.begin(), args.selection_objects.end(),
                   std::back_inserter(selection_args),
                   [&](const std::string& obj) {
	               return RTLIL::unescape_id(design->top_module()->name) +
	                      "/" + SelectionType() + ":" + obj;
                   });
    extra_args(selection_args, 0, design);
    if (design->selected_modules().empty()) {
	if (!args.is_quiet) {
	    log_warning("Specified %s not found in design\n",
	                TypeName().c_str());
	}
    }
}

void GetCmd::PackToTcl(const SelectionObjects& objects) {
    Tcl_Obj* tcl_result;
    if (objects.size() == 1) {
	tcl_result = Tcl_NewStringObj(objects.at(0).c_str(), -1);
    } else {
	tcl_result = Tcl_NewListObj(0, NULL);
	for (const auto& object : objects) {
	    Tcl_Obj* value_obj = Tcl_NewStringObj(object.c_str(), -1);
	    Tcl_ListObjAppendElement(yosys_get_tcl_interp(), tcl_result,
	                             value_obj);
	}
    }
    Tcl_SetObjResult(yosys_get_tcl_interp(), tcl_result);
}

GetCmd::CommandArgs GetCmd::ParseCommand(const std::vector<std::string>& args) {
    CommandArgs parsed_args{.filters = Filters(),
                            .is_quiet = false,
                            .selection_objects = SelectionObjects()};
    size_t argidx(0);
    for (argidx = 1; argidx < args.size(); argidx++) {
	std::string arg = args[argidx];
	if (arg == "-quiet") {
	    parsed_args.is_quiet = true;
	    continue;
	}

	if (arg == "-filter" and argidx + 1 < args.size()) {
	    std::string filter_arg = args[++argidx];

	    // Remove spaces
	    filter_arg.erase(
	        std::remove_if(filter_arg.begin(), filter_arg.end(), isspace),
	        filter_arg.end());

	    // Parse filters
	    std::regex filter_attr_regex("(\\w+\\s?==\\s?\\w+)([(||)(&&)]*)");
	    std::regex_token_iterator<std::string::iterator> regex_end;
	    std::regex_token_iterator<std::string::iterator> matches(
	        filter_arg.begin(), filter_arg.end(), filter_attr_regex, 1);
	    if (matches == regex_end) {
		log_warning(
		    "Currently -filter switch supports only a single "
		    "'equal(==)' condition expression, the rest will be "
		    "ignored\n");
	    }

	    while (matches != regex_end) {
		std::string filter(*matches++);
		auto separator = filter.find("==");
		if (separator == std::string::npos) {
		    log_cmd_error("Incorrect filter expression: %s\n",
		                  args[argidx].c_str());
		}
		parsed_args.filters.emplace_back(filter.substr(0, separator),
		                                 filter.substr(separator + 2));
	    }
	    if (parsed_args.filters.size() > 1) {
		log_warning(
		    "Currently -filter switch supports only a single "
		    "'equal(==)' condition expression, the rest will be "
		    "ignored\n");
	    }
	    continue;
	}

	if (arg.size() > 0 and arg[0] == '-') {
	    log_cmd_error("Unknown option %s.\n", arg.c_str());
	}

	break;
    }
    std::copy(args.begin() + argidx, args.end(),
              std::back_inserter(parsed_args.selection_objects));
    return parsed_args;
}

void GetCmd::execute(std::vector<std::string> args, RTLIL::Design* design) {
    if (design->top_module() == nullptr) {
	log_cmd_error("No top module detected\n");
    }

    CommandArgs parsed_args(ParseCommand(args));
    ExecuteSelection(design, parsed_args);
    PackToTcl(ExtractSelection(design, parsed_args));
}
