Skip to content

Commit

Permalink
Split resolution and refresh rate into two settings
Browse files Browse the repository at this point in the history
  • Loading branch information
IanSB committed Jan 14, 2021
1 parent 275fba7 commit eea95a1
Show file tree
Hide file tree
Showing 7 changed files with 144 additions and 42 deletions.
5 changes: 3 additions & 2 deletions src/defs.h
Expand Up @@ -285,8 +285,9 @@ typedef struct {
#define FILTERING_NEAREST_NEIGHBOUR 8
#define FILTERING_SOFT 2
#define FILTERING_VERY_SOFT 6
#define DEFAULT_RESOLUTION "Auto@EDID"
#define AUTO_RESOLUTION "Auto@50Hz-60Hz"
#define DEFAULT_RESOLUTION "Auto"
#define DEFAULT_REFRESH 1
#define AUTO_REFRESH 2
#define DEFAULT_SCALING 0
#define DEFAULT_FILTERING 8
#define DEFAULT_HDMI_MODE 0
Expand Down
28 changes: 22 additions & 6 deletions src/filesystem.c
Expand Up @@ -498,7 +498,6 @@ static int string_compare (const void * s1, const void * s2) {
return strcmp (s1, s2);
}


void scan_cpld_filenames(char cpld_filenames[MAX_CPLD_FILENAMES][MAX_FILENAME_WIDTH], char *path, int *count) {
FRESULT res;
DIR dir;
Expand Down Expand Up @@ -603,7 +602,7 @@ void scan_sub_profiles(char sub_profile_names[MAX_SUB_PROFILES][MAX_PROFILE_WIDT
close_filesystem();
}

void scan_names(char names[MAX_NAMES][MAX_NAMES_WIDTH], char *path, char *type, size_t *count) {
void scan_rnames(char names[MAX_NAMES][MAX_NAMES_WIDTH], char *path, char *type, size_t *count) {
FRESULT res;
DIR dir;
static FILINFO fno;
Expand All @@ -615,16 +614,26 @@ void scan_names(char names[MAX_NAMES][MAX_NAMES_WIDTH], char *path, char *type,
if (res != FR_OK || fno.fname[0] == 0 || *count == MAX_NAMES) break;
if (!(fno.fattrib & AM_DIR)) {
if (fno.fname[0] != '.' && strlen(fno.fname) > 4) {
char* filetype = fno.fname + strlen(fno.fname)-4;
char* filetype = fno.fname + strlen(fno.fname) - 4;
if (strcmp(filetype, type) == 0) {
strncpy(names[*count], fno.fname, MAX_NAMES_WIDTH);
names[(*count)++][strlen(fno.fname) - 4] = 0;
//mask out bit so numbers starting >5 sort before other numbers so 640, 720 & 800 appear before 1024 1280 etc
if (names[*count][0] > '5' && names[*count][0] <= '9') {
names[*count][0] &= 0xef;
}
names[(*count)++][strlen(fno.fname) - 9] = 0;
}
}
}
}
f_closedir(&dir);
qsort(names, *count, sizeof *names, string_compare);
//restore masked bit
for (int i = 0; i < *count; i++) {
if (names[i][0] > ('5' & 0xef) && names[i][0] <= ('9' & 0xef)) {
names[i][0] |= 0x10;
}
}
}
close_filesystem();
}
Expand Down Expand Up @@ -877,7 +886,7 @@ int file_restore(char *dirpath, char *name) {
return 1;
}

int file_save_config(char *resolution_name, int scaling, int filtering, int current_frontend, int current_hdmi_mode) {
int file_save_config(char *resolution_name, int refresh, int scaling, int filtering, int current_frontend, int current_hdmi_mode) {
FRESULT result;
char path[256];
char buffer [16384];
Expand Down Expand Up @@ -935,9 +944,16 @@ int file_save_config(char *resolution_name, int scaling, int filtering, int curr
}
bytes_read += strlen((char*) (buffer + bytes_read));

sprintf((char*)(buffer + bytes_read), "\r\n#refresh=%d\r\n", refresh);
bytes_read += strlen((char*) (buffer + bytes_read));

sprintf((char*)(buffer + bytes_read), "\r\n#resolution=%s\r\n", resolution_name);
bytes_read += strlen((char*) (buffer + bytes_read));
sprintf(path, "/Resolutions/%s.txt", resolution_name);
if (refresh == REFRESH_50) {
sprintf(path, "/Resolutions/50Hz/%s@50Hz.txt", resolution_name);
} else {
sprintf(path, "/Resolutions/60Hz/%s@60Hz.txt", resolution_name);
}
log_info("Loading file: %s", path);

result = f_open(&file, path, FA_READ);
Expand Down
4 changes: 2 additions & 2 deletions src/filesystem.h
Expand Up @@ -14,8 +14,8 @@ void scan_profiles(char profile_names[MAX_PROFILES][MAX_PROFILE_WIDTH], int has_
void scan_sub_profiles(char sub_profile_names[MAX_SUB_PROFILES][MAX_PROFILE_WIDTH], char *sub_path, size_t *count);

unsigned int file_read_profile(char *profile_name, char *sub_profile_name, int updatecmd, char *command_string, unsigned int buffer_size);
void scan_names(char names[MAX_NAMES][MAX_NAMES_WIDTH], char *path, char *type, size_t *count);
int file_save_config(char *resolution_name, int scaling, int filtering, int current_frontend, int current_hdmi_mode);
void scan_rnames(char names[MAX_NAMES][MAX_NAMES_WIDTH], char *path, char *type, size_t *count);
int file_save_config(char *resolution_name, int refresh, int scaling, int filtering, int current_frontend, int current_hdmi_mode);
int file_load(char *path, char *buffer, unsigned int buffer_size);
int file_save(char *dirpath, char *name, char *buffer, unsigned int buffer_size);
int file_restore(char *dirpath, char *name);
Expand Down
90 changes: 70 additions & 20 deletions src/osd.c
Expand Up @@ -284,13 +284,21 @@ static const char *hdmi_names[] = {
"HDMI (YUV full)"
};

static const char *refresh_names[] = {
"60Hz",
"EDID 50Hz-60Hz",
"Force 50Hz-60Hz",
"Force 50Hz-Any",
"50Hz"
};
// =============================================================
// Feature definitions
// =============================================================

enum {
F_AUTOSWITCH,
F_RESOLUTION,
F_REFRESH,
F_HDMI,
F_SCALING,
F_FRONTEND,
Expand Down Expand Up @@ -338,6 +346,7 @@ enum {
static param_t features[] = {
{ F_AUTOSWITCH, "Auto Switch", "auto_switch", 0, NUM_AUTOSWITCHES - 1, 1 },
{ F_RESOLUTION, "Resolution", "resolution", 0, 0, 1 },
{ F_REFRESH, "Refresh", "refresh", 0, NUM_REFRESH - 1, 1 },
{ F_HDMI, "HDMI Mode", "hdmi_mode", 0, NUM_HDMIS - 1, 1 },
{ F_SCALING, "Scaling", "scaling", 0, NUM_SCALING - 1, 1 },
{ F_FRONTEND, "Interface", "interface", 0, NUM_FRONTENDS - 1, 1 },
Expand Down Expand Up @@ -527,6 +536,7 @@ static menu_t info_menu = {
static param_menu_item_t profile_ref = { I_FEATURE, &features[F_PROFILE] };
static param_menu_item_t subprofile_ref = { I_FEATURE, &features[F_SUBPROFILE] };
static param_menu_item_t resolution_ref = { I_FEATURE, &features[F_RESOLUTION] };
static param_menu_item_t refresh_ref = { I_FEATURE, &features[F_REFRESH] };
static param_menu_item_t hdmi_ref = { I_FEATURE, &features[F_HDMI] };
static param_menu_item_t scaling_ref = { I_FEATURE, &features[F_SCALING] };
static param_menu_item_t frontend_ref = { I_FEATURE, &features[F_FRONTEND] };
Expand Down Expand Up @@ -766,6 +776,7 @@ static menu_t main_menu = {
(base_menu_item_t *) &test_50hz_ref,
(base_menu_item_t *) &hdmi_ref,
(base_menu_item_t *) &resolution_ref,
(base_menu_item_t *) &refresh_ref,
(base_menu_item_t *) &scaling_ref,
(base_menu_item_t *) &frontend_ref,
(base_menu_item_t *) &profile_ref,
Expand All @@ -776,7 +787,7 @@ static menu_t main_menu = {
}
};

#define DIRECTION_INDEX 19
#define DIRECTION_INDEX 20

// =============================================================
// Static local variables
Expand Down Expand Up @@ -970,6 +981,8 @@ static int get_feature(int num) {
return get_subprofile();
case F_RESOLUTION:
return get_resolution();
case F_REFRESH:
return get_refresh();
case F_HDMI:
return get_hdmi();
case F_SCALING:
Expand Down Expand Up @@ -1076,6 +1089,9 @@ static void set_feature(int num, int value) {
case F_RESOLUTION:
set_resolution(value, resolution_names[value], 1);
break;
case F_REFRESH:
set_refresh(value, 1);
break;
case F_HDMI:
set_hdmi(value, 1);
break;
Expand Down Expand Up @@ -1304,6 +1320,8 @@ static const char *get_param_string(param_menu_item_t *param_item) {
return sub_profile_names[value];
case F_RESOLUTION:
return resolution_names[value];
case F_REFRESH:
return refresh_names[value];
case F_HDMI:
return hdmi_names[value];
case F_SCALING:
Expand Down Expand Up @@ -1458,16 +1476,16 @@ int current_50hz_state = get_50hz_state();
osd_set(line++, 0, "50Hz support is already enabled");
osd_set(line++, 0, "");
osd_set(line++, 0, "If menu text is unstable, change the");
osd_set(line++, 0, "Resolution menu option to Auto@60Hz");
osd_set(line++, 0, "to permanently disable 50Hz support.");
osd_set(line++, 0, "Refresh menu option to 60Hz to");
osd_set(line++, 0, "permanently disable 50Hz support.");
break;
case 1:
set_force_genlock_range(GENLOCK_RANGE_FORCE_LOW);
set_status_message(" ");
osd_set(line++, 0, "50Hz support enabled until reset");
osd_set(line++, 0, "");
osd_set(line++, 0, "If you can see this message, change the");
osd_set(line++, 0, "Resolution menu option to Auto@50Hz-60Hz");
osd_set(line++, 0, "Refresh menu option to Force 50Hz-60Hz");
osd_set(line++, 0, "to permanently enable 50Hz support.");
break;
default:
Expand All @@ -1481,7 +1499,7 @@ int current_50hz_state = get_50hz_state();
osd_set(line++, 0, "If the current resolution doesn't match");
osd_set(line++, 0, "the physical resolution of your lcd panel,");
osd_set(line++, 0, "change the Resolution menu option to");
osd_set(line++, 0, "the correct resolution and refresh rate.");
osd_set(line++, 0, "the correct resolution.");
}

static void info_reboot(int line) {
Expand Down Expand Up @@ -4653,17 +4671,21 @@ int osd_key(int key) {
first_time_press = 1;
osd_set(0, ATTR_DOUBLE_SIZE, test_50hz_ref.name);
int line = 3;
osd_set(line++, 0, "Press menu again to start 50Hz test");
osd_set(line++, 0, "or any other button to abort");
osd_set(line++, 0, "Your monitor's EDID data indicates");
osd_set(line++, 0, "it doesn't support 50Hz, however many");
osd_set(line++, 0, "such monitors will actually work if the");
osd_set(line++, 0, "output is forced to 50Hz ignoring the EDID.");
line++;
osd_set(line++, 0, "Press menu again to start the 50Hz test");
osd_set(line++, 0, "or any other button to abort.");
line++;
osd_set(line++, 0, "If there is a blank screen after pressing");
osd_set(line++, 0, "menu then Auto@50Hz-60Hz will not work.");
osd_set(line++, 0, "menu then forcing 50Hz will not work.");
line++;
osd_set(line++, 0, "However you can still try manually");
osd_set(line++, 0, "selecting 50Hz resolutions, such as the");
osd_set(line++, 0, "physical monitor resolution plus these");
osd_set(line++, 0, "standard 50Hz modes: 720x576@50Hz");
osd_set(line++, 0, "1280x720@50Hz or 1920x1080@50Hz");
osd_set(line++, 0, "changing the refresh rate to 50Hz and");
osd_set(line++, 0, "selecting standard 50Hz resolutions such");
osd_set(line++, 0, "as 720x576, 1280x720 or 1920x1080");
line++;
osd_set(line++, 0, "Use menu-reset to recover from no output");
} else {
Expand Down Expand Up @@ -5162,7 +5184,7 @@ void osd_init() {
features[F_RESOLUTION].max = 0;
strcpy(resolution_names[0], NOT_FOUND_STRING);
size_t rcount = 0;
scan_names(resolution_names, "/Resolutions", ".txt", &rcount);
scan_rnames(resolution_names, "/Resolutions/60Hz", ".txt", &rcount);
if (rcount !=0) {
features[F_RESOLUTION].max = rcount - 1;
for (int i = 0; i < rcount; i++) {
Expand Down Expand Up @@ -5319,30 +5341,58 @@ void osd_init() {
set_hdmi(val, 0);

if (cbytes) {
prop = get_prop_no_space(config_buffer, "#force_genlock_range");
prop = get_prop_no_space(config_buffer, "#refresh");
}
if (!prop || !cbytes) {
prop = "0";
}
log_info("Read force_genlock_range: %s", prop);
log_info("Read refresh: %s", prop);
val = atoi(prop);

if (val == GENLOCK_RANGE_EDID && Vrefresh_lo > 50) {
val = GENLOCK_RANGE_NORMAL;
set_refresh(val, 0);

int force_genlock_range = GENLOCK_RANGE_NORMAL;

switch (val) {
default:
case REFRESH_60:
case REFRESH_50:
break;
case REFRESH_EDID:
if (Vrefresh_lo > 50) {
force_genlock_range = GENLOCK_RANGE_NORMAL;
} else {
force_genlock_range = GENLOCK_RANGE_EDID;
}
break;
case REFRESH_50_60:
force_genlock_range = GENLOCK_RANGE_FORCE_LOW;
break;
case REFRESH_50_ANY:
force_genlock_range = GENLOCK_RANGE_FORCE_ALL;
break;
}
set_force_genlock_range(val);

if (cbytes) {
prop = get_prop_no_space(config_buffer, "#resolution");
}
if (!prop || !cbytes) {
log_info("New install detected");
prop = "Auto@60Hz";
set_force_genlock_range(GENLOCK_RANGE_SET_DEFAULT);
prop = "Auto";
force_genlock_range = GENLOCK_RANGE_SET_DEFAULT;
}

log_info("Read resolution: %s", prop);

if (strcmp(prop, DEFAULT_RESOLUTION) == 0 && get_refresh() == REFRESH_50) {
force_genlock_range = REFRESH_50_60;
log_info("Auto 50Hz detected");
}

set_force_genlock_range(force_genlock_range);



for (int i=0; i< rcount; i++) {
if (strcmp(resolution_names[i], prop) == 0) {
log_info("Match resolution: %d %s", i, prop);
Expand Down
8 changes: 8 additions & 0 deletions src/osd.h
Expand Up @@ -208,6 +208,14 @@ enum {
NUM_HDMIS
};

enum {
REFRESH_60,
REFRESH_EDID,
REFRESH_50_60,
REFRESH_50_ANY,
REFRESH_50,
NUM_REFRESH
};

void osd_init();
void osd_clear();
Expand Down

0 comments on commit eea95a1

Please sign in to comment.