Profile support added.

This commit is contained in:
marqs 2016-12-30 00:14:12 +02:00
parent 79f215d41e
commit 0f8439abf3
14 changed files with 298 additions and 138 deletions

View File

@ -523,7 +523,7 @@ BOOL EnableAudioOutput(ULONG VideoPixelClock,BYTE bAudioSampleFreq,BYTE ChannelN
return TRUE ;
}
BOOL EnableAudioOutput4OSSC(ULONG VideoPixelClock,BYTE bExtMCLK,BYTE bAudioDwSampl,BYTE bAudioSwapLR)
BOOL EnableAudioOutput4OSSC(ULONG VideoPixelClock,BYTE bAudioDwSampl,BYTE bAudioSwapLR)
{
// set N and CTS
ULONG n = 12288;
@ -553,7 +553,7 @@ BOOL EnableAudioOutput4OSSC(ULONG VideoPixelClock,BYTE bExtMCLK,BYTE bAudioDwSam
#endif
// define internal/external MCLK and audio down-sampling
HDMITX_SetREG_Byte(REG_TX_CLK_CTRL0,~(M_EXT_MCLK_SEL|B_EXT_MCLK_SAMP|B_EXT_MCLK4CTS),((bExtMCLK&0x1)<<O_MCLK_SAMP) | B_EXT_256FS | ((bExtMCLK&0x1)<<O_MCLK4CTS));
HDMITX_SetREG_Byte(REG_TX_CLK_CTRL0,~(M_EXT_MCLK_SEL|B_EXT_MCLK_SAMP|B_EXT_MCLK4CTS),B_EXT_256FS);
//HDMITX_AndREG_Byte(REG_TX_SW_RST,~M_AUD_DIV);
if (bAudioDwSampl == 0x1)
HDMITX_OrREG_Byte(REG_TX_CLK_CTRL1,B_AUD_DIV2);

View File

@ -821,7 +821,7 @@ BOOL ProgramDEGenModeByID(MODE_ID id,BYTE bInputSignalType) ;
BOOL ProgramSyncEmbeddedVideoMode(BYTE VIC,BYTE bInputType) ;
#endif
BOOL EnableAudioOutput(unsigned long VideoPixelClock,BYTE bAudioSampleFreq,BYTE ChannelNumber,BYTE bAudSWL,BYTE bSPDIF) ;
BOOL EnableAudioOutput4OSSC(ULONG VideoPixelClock,BYTE bExtMCLK,BYTE bAudioDwSampl,BYTE bAudioSwapLR) ;
BOOL EnableAudioOutput4OSSC(ULONG VideoPixelClock,BYTE bAudioDwSampl,BYTE bAudioSwapLR) ;
void DisableIT6613() ;
void DisableVideoOutput() ;
void DisableAudioOutput() ;

View File

@ -27,9 +27,10 @@
// EPCS16 pagesize is 256 bytes
// Flash is split 50-50 to FW and userdata, 1MB each
#define PAGESIZE 256
#define PAGES_PER_SECTOR 256
#define PAGES_PER_SECTOR 256 //EPCS "sector" corresponds to "block" on Spansion flash
#define SECTORSIZE (PAGESIZE*PAGES_PER_SECTOR)
#define USERDATA_OFFSET 0x100000
#define USERDATA_MAX_SIZE 0x1000 //4KB should be enough
#define MAX_USERDATA_ENTRY 15 // 16 sectors for userdata
int check_flash();

View File

@ -56,18 +56,18 @@ avmode_t cm;
extern mode_data_t video_modes[];
extern ypbpr_to_rgb_csc_t csc_coeffs[];
extern alt_u16 rc_keymap[REMOTE_MAX_KEYS];
extern alt_u16 rc_keymap_default[REMOTE_MAX_KEYS];
extern alt_u32 remote_code;
extern alt_u32 btn_code, btn_code_prev;
extern alt_u8 remote_rpt, remote_rpt_prev;
extern avconfig_t tc;
extern alt_u8 video_mode_cnt;
alt_u8 target_typemask;
alt_u8 target_type;
alt_u8 stable_frames;
alt_u8 update_cur_vm;
alt_u8 vm_sel, vm_edit;
alt_u8 vm_sel, vm_edit, profile_sel;
alt_u16 tc_h_samplerate, tc_h_synclen, tc_h_active, tc_v_active, tc_h_bporch, tc_v_bporch;
char row1[LCD_ROW_LEN+1], row2[LCD_ROW_LEN+1], menu_row1[LCD_ROW_LEN+1], menu_row2[LCD_ROW_LEN+1];
@ -100,7 +100,7 @@ inline void SetupAudio(tx_mode_t mode)
pclk_out *= 3;
printf("PCLK_out: %luHz\n", pclk_out);
EnableAudioOutput4OSSC(pclk_out,tc.audio_ext_mclk,tc.audio_dw_sampl,tc.audio_swap_lr);
EnableAudioOutput4OSSC(pclk_out, tc.audio_dw_sampl, tc.audio_swap_lr);
HDMITX_SetAudioInfoFrame((BYTE)tc.audio_dw_sampl);
#ifdef DEBUG
Switch_HDMITX_Bank(1);
@ -327,13 +327,12 @@ status_t get_status(tvp_input_t input, video_format format)
#ifdef DIY_AUDIO
if ((tc.audio_dw_sampl != cm.cc.audio_dw_sampl) ||
(tc.audio_swap_lr != cm.cc.audio_swap_lr) ||
#ifdef MANUAL_CTS
(tc.edtv_l2x != cm.cc.edtv_l2x) ||
(tc.interlace_pt != cm.cc.interlace_pt) ||
update_cur_vm ||
#endif
(tc.audio_ext_mclk != cm.cc.audio_ext_mclk))
(tc.audio_swap_lr != cm.cc.audio_swap_lr))
SetupAudio(tc.tx_mode);
#endif
@ -447,13 +446,59 @@ void program_mode()
#endif
}
void load_profile_disp(alt_u8 code) {
int retval;
switch ((menucode_id)code) {
case VAL_MINUS:
profile_sel = (profile_sel > 0) ? profile_sel-1 : profile_sel;
break;
case VAL_PLUS:
profile_sel = (profile_sel < MAX_PROFILE) ? profile_sel+1 : profile_sel;
break;
case OPT_SELECT:
retval = read_userdata(profile_sel);
sniprintf(menu_row2, LCD_ROW_LEN+1, "%s", (retval==0) ? "Loaded" : "Load failed");
lcd_write_menu();
usleep(500000);
break;
case NO_ACTION:
default:
sniprintf(menu_row2, LCD_ROW_LEN+1, "Slot %u", profile_sel);
break;
}
}
void save_profile_disp(alt_u8 code) {
int retval;
switch ((menucode_id)code) {
case VAL_MINUS:
profile_sel = (profile_sel > 0) ? profile_sel-1 : profile_sel;
break;
case VAL_PLUS:
profile_sel = (profile_sel < MAX_PROFILE) ? profile_sel+1 : profile_sel;
break;
case OPT_SELECT:
retval = write_userdata(profile_sel);
sniprintf(menu_row2, LCD_ROW_LEN+1, "%s", (retval==0) ? "Saved" : "Save failed");
lcd_write_menu();
usleep(500000);
break;
case NO_ACTION:
default:
sniprintf(menu_row2, LCD_ROW_LEN+1, "Slot %u", profile_sel);
break;
}
}
void vm_display(alt_u8 code) {
switch ((menucode_id)code) {
case VAL_MINUS:
vm_sel = (vm_sel > 0) ? vm_sel-1 : vm_sel;
break;
case VAL_PLUS:
vm_sel = (vm_sel < video_mode_cnt-1) ? vm_sel+1 : vm_sel;
vm_sel = (vm_sel < VIDEO_MODES_CNT-1) ? vm_sel+1 : vm_sel;
break;
case OPT_SELECT:
vm_edit = vm_sel;
@ -550,11 +595,15 @@ int init_hw()
set_default_avconfig();
// safe?
read_userdata();
// Load default profile
read_userdata(0);
// Load / setup remote keymap
memcpy(rc_keymap, rc_keymap_default, sizeof(rc_keymap));
if (!(IORD_ALTERA_AVALON_PIO_DATA(PIO_1_BASE) & PB1_BIT))
setup_rc();
else
read_userdata(RC_CONFIG_SLOT);
// init always in HDMI mode (fixes yellow screen bug)
TX_enable(TX_HDMI);

View File

@ -81,5 +81,7 @@ inline void lcd_write_status();
void vm_display(alt_u8 code);
void vm_tweak(alt_u16 v);
void load_profile_disp(alt_u8 code);
void save_profile_disp(alt_u8 code);
#endif

View File

@ -33,8 +33,7 @@
#define DEFAULT_FINE_GAIN 26
#define DEFAULT_FINE_OFFSET 0x80
extern mode_data_t video_modes[], video_modes_def[];
extern alt_u8 video_mode_cnt;
extern mode_data_t video_modes[], video_modes_default[];
extern alt_u8 update_cur_vm;
// Target configuration
@ -70,7 +69,7 @@ int set_default_avconfig()
tc.tx_mode = !!(IORD_ALTERA_AVALON_PIO_DATA(PIO_1_BASE) & HDMITX_MODE_MASK);
#endif
memcpy(video_modes, video_modes_def, video_mode_cnt*sizeof(mode_data_t));
memcpy(video_modes, video_modes_default, VIDEO_MODES_SIZE);
update_cur_vm = 1;
return 0;

View File

@ -60,7 +60,6 @@ typedef struct {
#ifdef DIY_AUDIO
alt_u8 audio_dw_sampl;
alt_u8 audio_swap_lr;
alt_u8 audio_ext_mclk;
#endif
alt_u8 edtv_l2x;
alt_u8 interlace_pt;

View File

@ -24,11 +24,17 @@
#include "menu.h"
#include "av_controller.h"
#include "video_modes.h"
#include "userdata.h"
#include "lcd.h"
#include "altera_avalon_pio_regs.h"
static const char *rc_keydesc[] = { "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "MENU", "OK", "BACK", "UP", "DOWN", "LEFT", "RIGHT", "INFO", "LCD_BACKLIGHT", "SCANLINE_MODE", "SCANLINE_TYPE", "SCANLINE_INT+", "SCANLINE_INT-", "LINEMULT_MODE"};
alt_u16 rc_keymap[REMOTE_MAX_KEYS] = {0x3E29, 0x3EA9, 0x3E69, 0x3EE9, 0x3E19, 0x3E99, 0x3E59, 0x3ED9, 0x3E39, 0x3EC9, 0x3E4D, 0x3E1D, 0x3EED, 0x3E2D, 0x3ECD, 0x3EAD, 0x3E6D, 0x3E65, 0x3E01, 0x1C48, 0x1C18, 0x1C50, 0x1CD0, 0x1CC8};
static const char *rc_keydesc[REMOTE_MAX_KEYS] = { "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", \
"MENU", "OK", "BACK", "UP", "DOWN", "LEFT", "RIGHT", "INFO", "LCD_BACKLIGHT", "SCANLINE_MODE", \
"SCANLINE_TYPE", "SCANLINE_INT+", "SCANLINE_INT-", "LINEMULT_MODE", "PHASE+", "PHASE-", "PROFILE_HOTKEY"};
const alt_u16 rc_keymap_default[REMOTE_MAX_KEYS] = {0x3E29, 0x3EA9, 0x3E69, 0x3EE9, 0x3E19, 0x3E99, 0x3E59, 0x3ED9, 0x3E39, 0x3EC9, \
0x3E4D, 0x3E1D, 0x3EED, 0x3E2D, 0x3ECD, 0x3EAD, 0x3E6D, 0x3E65, 0x3E01, 0x1C48, \
0x1C18, 0x1C50, 0x1CD0, 0x1CC8, 0x5E58, 0x5ED8, 0x3EB9};
alt_u16 rc_keymap[REMOTE_MAX_KEYS];
extern char menu_row1[LCD_ROW_LEN+1], menu_row2[LCD_ROW_LEN+1];
extern const mode_data_t video_modes[];
@ -37,6 +43,7 @@ extern avconfig_t tc;
extern avinput_t target_mode;
extern alt_u8 menu_active;
extern alt_u8 sys_ctrl;
extern alt_u8 profile_sel;
alt_u32 remote_code;
alt_u8 remote_rpt, remote_rpt_prev;
@ -55,6 +62,7 @@ void setup_rc()
while (1) {
remote_code = IORD_ALTERA_AVALON_PIO_DATA(PIO_1_BASE) & RC_MASK;
btn_code = ~IORD_ALTERA_AVALON_PIO_DATA(PIO_1_BASE) & PB_MASK;
if (remote_code && (remote_code != remote_code_prev)) {
if (confirm == 0) {
@ -73,7 +81,18 @@ void setup_rc()
}
}
if ((btn_code_prev == 0) && (btn_code == PB0_BIT)) {
if (i == 0) {
memcpy(rc_keymap, rc_keymap_default, sizeof(rc_keymap));
i=REMOTE_MAX_KEYS;
} else {
i-=2;
}
confirm = 2;
}
remote_code_prev = remote_code;
btn_code_prev = btn_code;
if (confirm == 2)
break;
@ -81,11 +100,13 @@ void setup_rc()
usleep(WAITLOOP_SLEEP_US);
}
}
write_userdata(RC_CONFIG_SLOT);
}
void parse_control()
{
int i;
alt_u32 btn_vec;
if (remote_code)
printf("RCODE: 0x%.4lx, %d\n", remote_code, remote_rpt);
@ -135,6 +156,33 @@ void parse_control()
case RC_SL_MINUS: tc.sl_str = tc.sl_str ? (tc.sl_str - 1) : 0; break;
case RC_SL_PLUS: tc.sl_str = (tc.sl_str < SCANLINESTR_MAX) ? (tc.sl_str + 1) : SCANLINESTR_MAX; break;
case RC_LM_MODE: tc.linemult_target = (tc.linemult_target < LM_MODE_MAX) ? (tc.linemult_target + 1) : 0; break;
case RC_PHASE_PLUS: tc.sampler_phase = (tc.sampler_phase < SAMPLER_PHASE_MAX) ? (tc.sampler_phase + 1) : SAMPLER_PHASE_MAX; break;
case RC_PHASE_MINUS: tc.sampler_phase = tc.sampler_phase ? (tc.sampler_phase - 1) : 0; break;
case RC_PROF_HOTKEY:
strncpy(menu_row1, "Profile load:", LCD_ROW_LEN+1);
strncpy(menu_row2, "press 0-9", LCD_ROW_LEN+1);
lcd_write_menu();
while (1) {
btn_vec = IORD_ALTERA_AVALON_PIO_DATA(PIO_1_BASE) & RC_MASK;
for (i = RC_BTN1; i < REMOTE_MAX_KEYS; i++) {
if (btn_vec == rc_keymap[i])
break;
}
if (i <= RC_BTN0) {
profile_sel = (i+1)%10;
load_profile_disp(OPT_SELECT);
break;
} else if (i == rc_keymap[RC_BACK]) {
break;
}
usleep(WAITLOOP_SLEEP_US);
}
lcd_write_status();
menu_active = 0;
break;
default: break;
}

View File

@ -52,9 +52,12 @@ typedef enum {
RC_SL_PLUS,
RC_SL_MINUS,
RC_LM_MODE,
RC_PHASE_PLUS,
RC_PHASE_MINUS,
RC_PROF_HOTKEY,
} rc_code_t;
#define REMOTE_MAX_KEYS RC_LM_MODE-RC_BTN1+1
#define REMOTE_MAX_KEYS (RC_PROF_HOTKEY-RC_BTN1+1)
void setup_rc();
void parse_control();

View File

@ -122,7 +122,6 @@ MENU(menu_postproc, P99_PROTECT({ \
MENU(menu_audio, P99_PROTECT({ \
{ "Down-sampling", OPT_AVCONFIG_SELECTION, { .sel = { &tc.audio_dw_sampl, OPT_WRAP, SETTING_ITEM(audio_dw_sampl_desc) } } },
{ "Swap left/right", OPT_AVCONFIG_SELECTION, { .sel = { &tc.audio_swap_lr, OPT_WRAP, SETTING_ITEM(off_on_desc) } } },
{ "Use ext. MCLK", OPT_AVCONFIG_SELECTION, { .sel = { &tc.audio_ext_mclk, OPT_WRAP, SETTING_ITEM(off_on_desc) } } },
}))
#define AUDIO_MENU { "Audio options >", OPT_SUBMENU, { .sub = { &menu_audio, NULL } } },
#else
@ -137,9 +136,10 @@ MENU(menu_main, P99_PROTECT({ \
{ LNG("Output opt. >","シュツリョクオプション >"), OPT_SUBMENU, { .sub = { &menu_output, NULL } } },
{ LNG("Post-proc. >","アトショリ >"), OPT_SUBMENU, { .sub = { &menu_postproc, NULL } } },
AUDIO_MENU
{ LNG("<Fw. update >","<ファームウェアアップ >"), OPT_FUNC_CALL, { .fun = { fw_update, LNG("OK - pls restart","OK - サイキドウシテクダサイ"), LNG("failed","シッパイ") } } },
{ "<Load profile >", OPT_SUBMENU, { .sub = { NULL, load_profile_disp } } },
{ LNG("<Save profile >","<セッテイオホゾン >"), OPT_SUBMENU, { .sub = { NULL, save_profile_disp } } },
{ LNG("<Reset settings>","<セッテイオショキカ >"), OPT_FUNC_CALL, { .fun = { set_default_avconfig, LNG("Reset done","ショキカスミ"), "" } } },
{ LNG("<Save settings >","<セッテイオホゾン >"), OPT_FUNC_CALL, { .fun = { write_userdata, LNG("Saved","ホゾンスミ"), LNG("failed","シッパイ") } } },
{ LNG("<Fw. update >","<ファームウェアアップ >"), OPT_FUNC_CALL, { .fun = { fw_update, LNG("OK - pls restart","OK - サイキドウシテクダサイ"), LNG("failed","シッパイ") } } },
}))
// Max 3 levels currently
@ -187,12 +187,14 @@ void display_menu(alt_u8 forcedisp)
case OPT_SELECT:
switch (navi[navlvl].m->items[navi[navlvl].mp].type) {
case OPT_SUBMENU:
if (navi[navlvl+1].m != navi[navlvl].m->items[navi[navlvl].mp].sub.menu)
navi[navlvl+1].mp = 0;
navi[navlvl+1].m = navi[navlvl].m->items[navi[navlvl].mp].sub.menu;
if (navi[navlvl].m->items[navi[navlvl].mp].sub.arg_f)
navi[navlvl].m->items[navi[navlvl].mp].sub.arg_f(code);
navlvl++;
if (navi[navlvl].m->items[navi[navlvl].mp].sub.menu) {
if (navi[navlvl+1].m != navi[navlvl].m->items[navi[navlvl].mp].sub.menu)
navi[navlvl+1].mp = 0;
navi[navlvl+1].m = navi[navlvl].m->items[navi[navlvl].mp].sub.menu;
navlvl++;
}
break;
case OPT_FUNC_CALL:
retval = navi[navlvl].m->items[navi[navlvl].mp].fun.f();

View File

@ -26,104 +26,146 @@
extern alt_u16 rc_keymap[REMOTE_MAX_KEYS];
extern avconfig_t tc;
extern mode_data_t video_modes[];
extern alt_u8 update_cur_vm;
int write_userdata()
int write_userdata(alt_u8 entry)
{
alt_u8 databuf[PAGESIZE];
alt_u16 vm_to_write;
alt_u16 pageoffset, srcoffset;
alt_u8 pageno;
int retval;
strncpy((char*)databuf, "USRDATA", 8);
databuf[8] = FW_VER_MAJOR;
databuf[9] = FW_VER_MINOR;
databuf[10] = 2;
retval = write_flash_page(databuf, USERDATA_HDR_SIZE, (USERDATA_OFFSET/PAGESIZE));
if (retval != 0) {
if (entry > MAX_USERDATA_ENTRY) {
printf("invalid entry\n");
return -1;
}
databuf[0] = UDE_REMOTE_MAP;
databuf[1] = 4+sizeof(rc_keymap);
databuf[2] = databuf[3] = 0; //padding
memcpy(databuf+4, rc_keymap, sizeof(rc_keymap));
strncpy(((ude_hdr*)databuf)->userdata_key, "USRDATA", 8);
((ude_hdr*)databuf)->version_major = FW_VER_MAJOR;
((ude_hdr*)databuf)->version_minor = FW_VER_MINOR;
((ude_hdr*)databuf)->type = (entry > MAX_PROFILE) ? UDE_REMOTE_MAP : UDE_PROFILE;
retval = write_flash_page(databuf, databuf[1], (USERDATA_OFFSET/PAGESIZE)+1);
if (retval != 0) {
return -1;
}
switch (((ude_hdr*)databuf)->type) {
case UDE_REMOTE_MAP:
((ude_remote_map*)databuf)->data_len = sizeof(rc_keymap);
memcpy(((ude_remote_map*)databuf)->keys, rc_keymap, sizeof(rc_keymap));
retval = write_flash_page(databuf, sizeof(ude_remote_map), (USERDATA_OFFSET+entry*SECTORSIZE)/PAGESIZE);
if (retval != 0) {
return -1;
}
break;
case UDE_PROFILE:
vm_to_write = VIDEO_MODES_SIZE;
((ude_profile*)databuf)->avc_data_len = sizeof(avconfig_t);
((ude_profile*)databuf)->vm_data_len = vm_to_write;
databuf[0] = UDE_AVCONFIG;
databuf[1] = 4+sizeof(avconfig_t);
databuf[2] = databuf[3] = 0; //padding
memcpy(databuf+4, &tc, sizeof(avconfig_t));
pageno = 0;
pageoffset = offsetof(ude_profile, avc);
retval = write_flash_page(databuf, databuf[1], (USERDATA_OFFSET/PAGESIZE)+2);
if (retval != 0) {
return -1;
// assume that sizeof(avconfig_t) << PAGESIZE
memcpy(databuf+pageoffset, &tc, sizeof(avconfig_t));
pageoffset += sizeof(avconfig_t);
srcoffset = 0;
while (vm_to_write > 0) {
if (vm_to_write >= PAGESIZE-pageoffset) {
memcpy(databuf+pageoffset, (char*)video_modes+srcoffset, PAGESIZE-pageoffset);
srcoffset += PAGESIZE-pageoffset;
pageoffset = 0;
vm_to_write -= PAGESIZE-pageoffset;
// check
write_flash_page(databuf, PAGESIZE, ((USERDATA_OFFSET+entry*SECTORSIZE)/PAGESIZE) + pageno);
pageno++;
} else {
memcpy(databuf+pageoffset, (char*)video_modes+srcoffset, vm_to_write);
pageoffset += vm_to_write;
vm_to_write = 0;
// check
write_flash_page(databuf, PAGESIZE, ((USERDATA_OFFSET+entry*SECTORSIZE)/PAGESIZE) + pageno);
}
}
printf("Profile %u data written (%u bytes)\n", entry, sizeof(avconfig_t)+VIDEO_MODES_SIZE);
break;
default:
break;
}
return 0;
}
int read_userdata()
int read_userdata(alt_u8 entry)
{
int retval, i;
alt_u8 databuf[PAGESIZE];
userdata_hdr udhdr;
userdata_entry udentry;
alt_u16 vm_to_read;
alt_u16 pageoffset, dstoffset;
alt_u8 pageno;
retval = read_flash(USERDATA_OFFSET, USERDATA_HDR_SIZE, databuf);
if (entry > MAX_USERDATA_ENTRY) {
printf("invalid entry\n");
return -1;
}
retval = read_flash(USERDATA_OFFSET+(entry*SECTORSIZE), PAGESIZE, databuf);
if (retval != 0) {
printf("Flash read error\n");
return -1;
}
strncpy(udhdr.userdata_key, (char*)databuf, 8);
if (strncmp(udhdr.userdata_key, "USRDATA", 8)) {
printf("No userdata found on flash\n");
if (strncmp(((ude_hdr*)databuf)->userdata_key, "USRDATA", 8)) {
printf("No userdata found on entry %u\n", entry);
return 1;
}
udhdr.version_major = databuf[8];
udhdr.version_minor = databuf[9];
udhdr.num_entries = databuf[10];
if ((((ude_hdr*)databuf)->version_major != FW_VER_MAJOR) || (((ude_hdr*)databuf)->version_minor != FW_VER_MINOR)) {
printf("Data version %u.%u does not match fw\n", ((ude_hdr*)databuf)->version_major, ((ude_hdr*)databuf)->version_minor);
return 2;
}
//TODO: check version compatibility
printf("Userdata: v%u.%.2u, %u entries\n", udhdr.version_major, udhdr.version_minor, udhdr.num_entries);
for (i=0; i<udhdr.num_entries; i++) {
retval = read_flash(USERDATA_OFFSET+((i+1)*PAGESIZE), USERDATA_ENTRY_HDR_SIZE, databuf);
if (retval != 0) {
printf("Flash read error\n");
return -1;
switch (((ude_hdr*)databuf)->type) {
case UDE_REMOTE_MAP:
if (((ude_remote_map*)databuf)->data_len == sizeof(rc_keymap)) {
memcpy(rc_keymap, ((ude_remote_map*)databuf)->keys, sizeof(rc_keymap));
printf("RC data read (%u bytes)\n", sizeof(rc_keymap));
}
break;
case UDE_PROFILE:
if ((((ude_profile*)databuf)->avc_data_len == sizeof(avconfig_t)) && (((ude_profile*)databuf)->vm_data_len == VIDEO_MODES_SIZE)) {
vm_to_read = ((ude_profile*)databuf)->vm_data_len;
udentry.type = databuf[0];
udentry.entry_len = databuf[1];
pageno = 0;
pageoffset = offsetof(ude_profile, avc);
retval = read_flash(USERDATA_OFFSET+((i+1)*PAGESIZE), udentry.entry_len, databuf);
if (retval != 0) {
printf("Flash read error\n");
return -1;
}
// assume that sizeof(avconfig_t) << PAGESIZE
memcpy(&tc, databuf+pageoffset, sizeof(avconfig_t));
pageoffset += sizeof(avconfig_t);
switch (udentry.type) {
case UDE_REMOTE_MAP:
if ((udentry.entry_len-4) == sizeof(rc_keymap)) {
memcpy(rc_keymap, databuf+4, sizeof(rc_keymap));
printf("RC data read (%u bytes)\n", sizeof(rc_keymap));
dstoffset = 0;
while (vm_to_read > 0) {
if (vm_to_read >= PAGESIZE-pageoffset) {
memcpy((char*)video_modes+dstoffset, databuf+pageoffset, PAGESIZE-pageoffset);
dstoffset += PAGESIZE-pageoffset;
pageoffset = 0;
vm_to_read -= PAGESIZE-pageoffset;
pageno++;
// check
read_flash(USERDATA_OFFSET+(entry*SECTORSIZE)+pageno*PAGESIZE, PAGESIZE, databuf);
} else {
memcpy((char*)video_modes+dstoffset, databuf+pageoffset, vm_to_read);
pageoffset += vm_to_read;
vm_to_read = 0;
}
}
break;
case UDE_AVCONFIG:
if ((udentry.entry_len-4) == sizeof(avconfig_t)) {
memcpy(&tc, databuf+4, sizeof(avconfig_t));
printf("Avconfig data read (%u bytes)\n", sizeof(avconfig_t));
}
break;
default:
printf("Unknown userdata entry\n");
break;
update_cur_vm = 1;
printf("Profile %u data read (%u bytes)\n", entry, sizeof(avconfig_t)+VIDEO_MODES_SIZE);
}
break;
default:
printf("Unknown userdata entry\n");
break;
}
return 0;

View File

@ -22,27 +22,41 @@
#include "alt_types.h"
#include "sysconfig.h"
#include "controls.h"
#include "avconfig.h"
#include "video_modes.h"
#include "flash.h"
#define MAX_PROFILE 9
#define RC_CONFIG_SLOT MAX_USERDATA_ENTRY
typedef enum {
UDE_REMOTE_MAP = 0,
UDE_PROFILE,
} ude_type;
#define USERDATA_HDR_SIZE 11
typedef struct {
char userdata_key[8];
alt_u8 version_major;
alt_u8 version_minor;
alt_u8 num_entries;
} userdata_hdr;
ude_type type;
} __attribute__((packed, __may_alias__)) ude_hdr;
#define USERDATA_ENTRY_HDR_SIZE 2
typedef struct {
alt_u8 type;
alt_u8 entry_len;
} userdata_entry;
ude_hdr hdr;
alt_u16 data_len;
alt_u16 keys[REMOTE_MAX_KEYS];
} __attribute__((packed, __may_alias__)) ude_remote_map;
typedef enum {
UDE_REMOTE_MAP = 0,
UDE_AVCONFIG,
} userdata_entry_type;
typedef struct {
ude_hdr hdr;
alt_u16 avc_data_len;
alt_u16 vm_data_len;
avconfig_t avc;
mode_data_t vm[VIDEO_MODES_CNT];
} __attribute__((packed, __may_alias__)) ude_profile;
int write_userdata(alt_u8 entry);
int read_userdata(alt_u8 entry);
#endif
int write_userdata();
int read_userdata();

View File

@ -24,40 +24,8 @@
#define LINECNT_MAX_TOLERANCE 30
const mode_data_t video_modes_def[] = {
{ "240p_L3M0", 1280, 240, 6000, 1560, 262, 170, 16, 72, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L3_MODE0|MODE_PLLDIVBY2) },
{ "240p_L3M1", 960, 240, 6000, 1170, 262, 128, 16, 54, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L3_MODE1|MODE_PLLDIVBY2) },
//{ "240p_L3M2", 384, 240, 6000, 512, 262, 66, 16, 31, 3, (VIDEO_LDTV|VIDEO_PC), (MODE_L3_MODE2|MODE_PLLDIVBY2) }, //CPS2
{ "240p_L3M2", 320, 240, 6000, 426, 262, 49, 16, 31, 3, (VIDEO_LDTV|VIDEO_PC), (MODE_L3_MODE2|MODE_PLLDIVBY2) },
{ "240p_L3M3", 256, 240, 6000, 341, 262, 39, 16, 25, 3, (VIDEO_LDTV|VIDEO_PC), (MODE_L3_MODE3|MODE_PLLDIVBY2) },
{ "240p", 720, 240, 6000, 858, 262, 65, 16, 60, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L2ENABLE|MODE_PLLDIVBY2) },
{ "288p_L3M0", 1280, 288, 5000, 1560, 312, 170, 16, 72, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L3_MODE0|MODE_PLLDIVBY2) },
{ "288p_L3M1", 960, 288, 5000, 1170, 312, 128, 16, 54, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L3_MODE1|MODE_PLLDIVBY2) },
{ "288p_L3M2", 320, 240, 5000, 426, 312, 49, 41, 31, 3, (VIDEO_LDTV|VIDEO_PC), (MODE_L3_MODE2|MODE_PLLDIVBY2) },
{ "288p_L3M3", 256, 240, 5000, 341, 312, 39, 41, 25, 3, (VIDEO_LDTV|VIDEO_PC), (MODE_L3_MODE3|MODE_PLLDIVBY2) },
{ "288p", 720, 288, 5000, 864, 312, 65, 16, 60, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L2ENABLE|MODE_PLLDIVBY2) },
{ "384p", 496, 384, 5766, 640, 423, 50, 29, 62, 3, VIDEO_EDTV, (MODE_L2ENABLE|MODE_PLLDIVBY2) }, //Sega Model 2
{ "640x384", 640, 384, 5500, 800, 492, 48, 63, 96, 2, VIDEO_PC, (MODE_L2ENABLE) }, //X68k @ 24kHz
{ "480i", 720, 240, 5994, 858, 525, 65, 16, 60, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L2ENABLE|MODE_PLLDIVBY2|MODE_INTERLACED) },
{ "480p", 720, 480, 5994, 858, 525, 60, 30, 62, 6, (VIDEO_EDTV|VIDEO_PC), (MODE_DTV480P) },
{ "640x480", 640, 480, 6000, 800, 525, 48, 33, 96, 2, (VIDEO_PC|VIDEO_EDTV), (MODE_VGA480P) },
{ "640x512", 640, 512, 6000, 800, 568, 48, 28, 96, 2, VIDEO_PC, 0 }, //X68k @ 31kHz
{ "576i", 720, 288, 5000, 864, 625, 65, 16, 60, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L2ENABLE|MODE_PLLDIVBY2|MODE_INTERLACED) },
{ "576p", 720, 576, 5000, 864, 625, 65, 32, 60, 6, VIDEO_EDTV, 0 },
{ "800x600", 800, 600, 6000, 1056, 628, 88, 23, 128, 4, VIDEO_PC, 0 },
{ "720p", 1280, 720, 5994, 1650, 750, 255, 20, 40, 5, VIDEO_HDTV, 0 },
{ "1280x720", 1280, 720, 6000, 1650, 750, 220, 20, 40, 5, VIDEO_PC, 0 },
{ "1024x768", 1024, 768, 6000, 1344, 806, 160, 29, 136, 6, VIDEO_PC, 0 },
{ "1280x1024", 1280, 1024, 6000, 1688, 1066, 248, 38, 112, 3, VIDEO_PC, 0 },
{ "1080i", 1920, 1080, 5994, 2200, 1125, 148, 16, 44, 5, VIDEO_HDTV, (MODE_INTERLACED) }, //Too high freq for L2 PLL
{ "1080p", 1920, 1080, 5994, 2200, 1125, 188, 36, 44, 5, VIDEO_HDTV, 0 },
{ "1920x1080", 1920, 1080, 6000, 2200, 1125, 148, 36, 44, 5, VIDEO_PC, 0 },
};
mode_data_t video_modes[sizeof(video_modes_def)/sizeof(mode_data_t)];
const alt_u8 video_mode_cnt = sizeof(video_modes_def)/sizeof(mode_data_t);
const mode_data_t video_modes_default[] = VIDEO_MODES_DEF;
mode_data_t video_modes[VIDEO_MODES_CNT];
/* TODO: rewrite, check hz etc. */
alt_8 get_mode_id(alt_u32 totlines, alt_u8 progressive, alt_u32 hz, video_type typemask, alt_u8 linemult_target, alt_u8 l3_mode, alt_u8 s480p_mode)

View File

@ -80,6 +80,39 @@ typedef struct {
mode_flags flags;
} mode_data_t;
#define VIDEO_MODES_DEF { \
{ "240p_L3M0", 1280, 240, 6000, 1560, 262, 170, 16, 72, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L3_MODE0|MODE_PLLDIVBY2) }, \
{ "240p_L3M1", 960, 240, 6000, 1170, 262, 128, 16, 54, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L3_MODE1|MODE_PLLDIVBY2) }, \
/*{ "240p_L3M2", 384, 240, 6000, 512, 262, 66, 16, 31, 3, (VIDEO_LDTV|VIDEO_PC), (MODE_L3_MODE2|MODE_PLLDIVBY2) }, //CPS2*/ \
{ "240p_L3M2", 320, 240, 6000, 426, 262, 49, 16, 31, 3, (VIDEO_LDTV|VIDEO_PC), (MODE_L3_MODE2|MODE_PLLDIVBY2) }, \
{ "240p_L3M3", 256, 240, 6000, 341, 262, 39, 16, 25, 3, (VIDEO_LDTV|VIDEO_PC), (MODE_L3_MODE3|MODE_PLLDIVBY2) }, \
{ "240p", 720, 240, 6000, 858, 262, 65, 16, 60, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L2ENABLE|MODE_PLLDIVBY2) }, \
{ "288p_L3M0", 1280, 288, 5000, 1560, 312, 170, 16, 72, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L3_MODE0|MODE_PLLDIVBY2) }, \
{ "288p_L3M1", 960, 288, 5000, 1170, 312, 128, 16, 54, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L3_MODE1|MODE_PLLDIVBY2) }, \
{ "288p_L3M2", 320, 240, 5000, 426, 312, 49, 41, 31, 3, (VIDEO_LDTV|VIDEO_PC), (MODE_L3_MODE2|MODE_PLLDIVBY2) }, \
{ "288p_L3M3", 256, 240, 5000, 341, 312, 39, 41, 25, 3, (VIDEO_LDTV|VIDEO_PC), (MODE_L3_MODE3|MODE_PLLDIVBY2) }, \
{ "288p", 720, 288, 5000, 864, 312, 65, 16, 60, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L2ENABLE|MODE_PLLDIVBY2) }, \
{ "384p", 496, 384, 5766, 640, 423, 50, 29, 62, 3, VIDEO_EDTV, (MODE_L2ENABLE|MODE_PLLDIVBY2) }, /* Sega Model 2 */ \
{ "640x384", 640, 384, 5500, 800, 492, 48, 63, 96, 2, VIDEO_PC, (MODE_L2ENABLE) }, /* X68k @ 24kHz */ \
{ "480i", 720, 240, 5994, 858, 525, 65, 16, 60, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L2ENABLE|MODE_PLLDIVBY2|MODE_INTERLACED) }, \
{ "480p", 720, 480, 5994, 858, 525, 60, 30, 62, 6, (VIDEO_EDTV|VIDEO_PC), (MODE_DTV480P) }, \
{ "640x480", 640, 480, 6000, 800, 525, 48, 33, 96, 2, (VIDEO_PC|VIDEO_EDTV), (MODE_VGA480P) }, \
{ "640x512", 640, 512, 6000, 800, 568, 48, 28, 96, 2, VIDEO_PC, 0 }, /* X68k @ 31kHz */ \
{ "576i", 720, 288, 5000, 864, 625, 65, 16, 60, 3, (VIDEO_SDTV|VIDEO_PC), (MODE_L2ENABLE|MODE_PLLDIVBY2|MODE_INTERLACED) }, \
{ "576p", 720, 576, 5000, 864, 625, 65, 32, 60, 6, VIDEO_EDTV, 0 }, \
{ "800x600", 800, 600, 6000, 1056, 628, 88, 23, 128, 4, VIDEO_PC, 0 }, \
{ "720p", 1280, 720, 5994, 1650, 750, 255, 20, 40, 5, VIDEO_HDTV, 0 }, \
{ "1280x720", 1280, 720, 6000, 1650, 750, 220, 20, 40, 5, VIDEO_PC, 0 }, \
{ "1024x768", 1024, 768, 6000, 1344, 806, 160, 29, 136, 6, VIDEO_PC, 0 }, \
{ "1280x1024", 1280, 1024, 6000, 1688, 1066, 248, 38, 112, 3, VIDEO_PC, 0 }, \
{ "1080i", 1920, 1080, 5994, 2200, 1125, 148, 16, 44, 5, VIDEO_HDTV, (MODE_INTERLACED) }, /* Too high freq for L2 PLL */ \
{ "1080p", 1920, 1080, 5994, 2200, 1125, 188, 36, 44, 5, VIDEO_HDTV, 0 }, \
{ "1920x1080", 1920, 1080, 6000, 2200, 1125, 148, 36, 44, 5, VIDEO_PC, 0 }, \
}
#define VIDEO_MODES_SIZE (sizeof((mode_data_t[])VIDEO_MODES_DEF))
#define VIDEO_MODES_CNT (sizeof((mode_data_t[])VIDEO_MODES_DEF)/sizeof(mode_data_t))
alt_8 get_mode_id(alt_u32 totlines, alt_u8 progressive, alt_u32 hz, video_type typemask, alt_u8 linemult_target, alt_u8 l3_mode, alt_u8 s480p_mode);
#endif /* VIDEO_MODES_H_ */