<commit_before>#include <cstdio>
#include <cstring>
#include <algorithm>
#include <regex>
#include <set>
#include <chrono>

#include <sys/select.h>

#include <kms++/kms++.h>
#include <kms++/modedb.h>
#include <kms++/mode_cvt.h>

#include <kms++util/kms++util.h>

using namespace std;
using namespace kms;

struct PlaneInfo
{
	Plane* plane;

	unsigned x;
	unsigned y;
	unsigned w;
	unsigned h;

	vector<DumbFramebuffer*> fbs;
};

struct OutputInfo
{
	Connector* connector;

	Crtc* crtc;
	Plane* primary_plane;
	Videomode mode;
	bool user_set_crtc;
	vector<DumbFramebuffer*> fbs;

	vector<PlaneInfo> planes;
};

static bool s_use_dmt;
static bool s_use_cea;
static unsigned s_num_buffers = 1;
static bool s_flip_mode;
static bool s_flip_sync;
static bool s_cvt;
static bool s_cvt_v2;
static bool s_cvt_vid_opt;

static set<Crtc*> s_used_crtcs;
static set<Plane*> s_used_planes;

__attribute__ ((unused))
static void print_regex_match(smatch sm)
{
	for (unsigned i = 0; i < sm.size(); ++i) {
		string str = sm[i].str();
		printf("%u: %s\n", i, str.c_str());
	}
}

static void get_default_connector(Card& card, OutputInfo& output)
{
	output.connector = card.get_first_connected_connector();
	output.mode = output.connector->get_default_mode();
}

static void parse_connector(Card& card, const string& str, OutputInfo& output)
{
	Connector* conn = resolve_connector(card, str);

	if (!conn)
		EXIT("No connector '%s'", str.c_str());

	if (!conn->connected())
		EXIT("Connector '%s' not connected", conn->fullname().c_str());

	output.connector = conn;
	output.mode = output.connector->get_default_mode();
}

static void get_default_crtc(Card& card, OutputInfo& output)
{
	Crtc* crtc = output.connector->get_current_crtc();

	if (crtc && s_used_crtcs.find(crtc) == s_used_crtcs.end()) {
		s_used_crtcs.insert(crtc);
		output.crtc = crtc;
		return;
	}

	for (const auto& possible : output.connector->get_possible_crtcs()) {
		if (s_used_crtcs.find(possible) == s_used_crtcs.end()) {
			s_used_crtcs.insert(possible);
			output.crtc = possible;
			return;
		}
	}

	EXIT("Could not find available crtc");
}

static void parse_crtc(Card& card, const string& crtc_str, OutputInfo& output)
{
	// @12:1920x1200i@60
	// @12:33000000,800/210/30/16/-,480/22/13/10/-,i

	const regex modename_re("(?:(@?)(\\d+):)?"	// @12:
				"(?:(\\d+)x(\\d+)(i)?)"	// 1920x1200i
				"(?:@([\\d\\.]+))?");	// @60

	const regex modeline_re("(?:(@?)(\\d+):)?"			// @12:
				"(\\d+),"				// 33000000,
				"(\\d+)/(\\d+)/(\\d+)/(\\d+)/([+-]),"	// 800/210/30/16/-,
				"(\\d+)/(\\d+)/(\\d+)/(\\d+)/([+-])"	// 480/22/13/10/-
				"(?:,([i]+))?"				// ,i
				);

	smatch sm;
	if (regex_match(crtc_str, sm, modename_re)) {
		if (sm[2].matched) {
			bool use_id = sm[1].length() == 1;
			unsigned num = stoul(sm[2].str());

			if (use_id) {
				Crtc* c = card.get_crtc(num);
				if (!c)
					EXIT("Bad crtc id '%u'", num);

				output.crtc = c;
			} else {
				auto crtcs = card.get_crtcs();

				if (num >= crtcs.size())
					EXIT("Bad crtc number '%u'", num);

				output.crtc = crtcs[num];
			}
		} else {
			output.crtc = output.connector->get_current_crtc();
		}

		unsigned w = stoul(sm[3]);
		unsigned h = stoul(sm[4]);
		bool ilace = sm[5].matched ? true : false;
		float refresh = sm[6].matched ? stof(sm[6]) : 0;

		bool found_mode = false;

		if (s_cvt) {
			output.mode = videomode_from_cvt(w, h, refresh, ilace, s_cvt_v2, s_cvt_vid_opt);
			found_mode = true;
		}

		if (!found_mode) {
			try {
				output.mode = output.connector->get_mode(w, h, refresh, ilace);
				found_mode = true;
			} catch (exception& e) { }
		}

		if (!found_mode && s_use_dmt) {
			try {
				output.mode = find_dmt(w, h, refresh, ilace);
				found_mode = true;
				printf("Found mode from DMT\n");
			} catch (exception& e) { }
		}

		if (!found_mode && s_use_cea) {
			try {
				output.mode = find_cea(w, h, refresh, ilace);
				found_mode = true;
				printf("Found mode from CEA\n");
			} catch (exception& e) { }
		}

		if (!found_mode)
			throw invalid_argument("Mode not found");
	} else if (regex_match(crtc_str, sm, modeline_re)) {
		if (sm[2].matched) {
			bool use_id = sm[1].length() == 1;
			unsigned num = stoul(sm[2].str());

			if (use_id) {
				Crtc* c = card.get_crtc(num);
				if (!c)
					EXIT("Bad crtc id '%u'", num);

				output.crtc = c;<commit_msg>kmstest: be explicit about mode selection<commit_after>#include <cstdio>
#include <cstring>
#include <algorithm>
#include <regex>
#include <set>
#include <chrono>

#include <sys/select.h>

#include <kms++/kms++.h>
#include <kms++/modedb.h>
#include <kms++/mode_cvt.h>

#include <kms++util/kms++util.h>

using namespace std;
using namespace kms;

struct PlaneInfo
{
	Plane* plane;

	unsigned x;
	unsigned y;
	unsigned w;
	unsigned h;

	vector<DumbFramebuffer*> fbs;
};

struct OutputInfo
{
	Connector* connector;

	Crtc* crtc;
	Plane* primary_plane;
	Videomode mode;
	bool user_set_crtc;
	vector<DumbFramebuffer*> fbs;

	vector<PlaneInfo> planes;
};

static bool s_use_dmt;
static bool s_use_cea;
static unsigned s_num_buffers = 1;
static bool s_flip_mode;
static bool s_flip_sync;
static bool s_cvt;
static bool s_cvt_v2;
static bool s_cvt_vid_opt;

static set<Crtc*> s_used_crtcs;
static set<Plane*> s_used_planes;

__attribute__ ((unused))
static void print_regex_match(smatch sm)
{
	for (unsigned i = 0; i < sm.size(); ++i) {
		string str = sm[i].str();
		printf("%u: %s\n", i, str.c_str());
	}
}

static void get_default_connector(Card& card, OutputInfo& output)
{
	output.connector = card.get_first_connected_connector();
	output.mode = output.connector->get_default_mode();
}

static void parse_connector(Card& card, const string& str, OutputInfo& output)
{
	Connector* conn = resolve_connector(card, str);

	if (!conn)
		EXIT("No connector '%s'", str.c_str());

	if (!conn->connected())
		EXIT("Connector '%s' not connected", conn->fullname().c_str());

	output.connector = conn;
	output.mode = output.connector->get_default_mode();
}

static void get_default_crtc(Card& card, OutputInfo& output)
{
	Crtc* crtc = output.connector->get_current_crtc();

	if (crtc && s_used_crtcs.find(crtc) == s_used_crtcs.end()) {
		s_used_crtcs.insert(crtc);
		output.crtc = crtc;
		return;
	}

	for (const auto& possible : output.connector->get_possible_crtcs()) {
		if (s_used_crtcs.find(possible) == s_used_crtcs.end()) {
			s_used_crtcs.insert(possible);
			output.crtc = possible;
			return;
		}
	}

	EXIT("Could not find available crtc");
}

static void parse_crtc(Card& card, const string& crtc_str, OutputInfo& output)
{
	// @12:1920x1200i@60
	// @12:33000000,800/210/30/16/-,480/22/13/10/-,i

	const regex modename_re("(?:(@?)(\\d+):)?"	// @12:
				"(?:(\\d+)x(\\d+)(i)?)"	// 1920x1200i
				"(?:@([\\d\\.]+))?");	// @60

	const regex modeline_re("(?:(@?)(\\d+):)?"			// @12:
				"(\\d+),"				// 33000000,
				"(\\d+)/(\\d+)/(\\d+)/(\\d+)/([+-]),"	// 800/210/30/16/-,
				"(\\d+)/(\\d+)/(\\d+)/(\\d+)/([+-])"	// 480/22/13/10/-
				"(?:,([i]+))?"				// ,i
				);

	smatch sm;
	if (regex_match(crtc_str, sm, modename_re)) {
		if (sm[2].matched) {
			bool use_id = sm[1].length() == 1;
			unsigned num = stoul(sm[2].str());

			if (use_id) {
				Crtc* c = card.get_crtc(num);
				if (!c)
					EXIT("Bad crtc id '%u'", num);

				output.crtc = c;
			} else {
				auto crtcs = card.get_crtcs();

				if (num >= crtcs.size())
					EXIT("Bad crtc number '%u'", num);

				output.crtc = crtcs[num];
			}
		} else {
			output.crtc = output.connector->get_current_crtc();
		}

		unsigned w = stoul(sm[3]);
		unsigned h = stoul(sm[4]);
		bool ilace = sm[5].matched ? true : false;
		float refresh = sm[6].matched ? stof(sm[6]) : 0;

		if (s_cvt) {
			output.mode = videomode_from_cvt(w, h, refresh, ilace, s_cvt_v2, s_cvt_vid_opt);
		} else if (s_use_dmt) {
			try {
				output.mode = find_dmt(w, h, refresh, ilace);
			} catch (exception& e) {
				EXIT("Mode not found from DMT tables\n");
			}
		} else if (s_use_cea) {
			try {
				output.mode = find_cea(w, h, refresh, ilace);
			} catch (exception& e) {
				EXIT("Mode not found from CEA tables\n");
			}
		} else {
			try {
				output.mode = output.connector->get_mode(w, h, refresh, ilace);
			} catch (exception& e) {
				EXIT("Mode not found from the connector\n");
			}
		}
	} else if (regex_match(crtc_str, sm, modeline_re)) {
		if (sm[2].matched) {
			bool use_id = sm[1].length() == 1;
			unsigned num = stoul(sm[2].str());

			if (use_id) {
				Crtc* c = card.get_crtc(num);
				if (!c)
					EXIT("Bad crtc id '%u'", num);

				output.crtc = c;
{'fraction_non_alphanumeric': 0.19217667097380478, 'fraction_numerical': 0.02349348055914484, 'mean_word_length': 3.5872844827586206, 'pattern_counts': {'":': 0, '<': 37, '<?xml version=': 0, '>': 53, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3259802', 'n_tokens_mistral': 3924, 'n_tokens_neox': 3500, 'n_words': 742}