diff --git a/ubb-vga/ubb-vga.c b/ubb-vga/ubb-vga.c index 8e16d47..e753c2d 100644 --- a/ubb-vga/ubb-vga.c +++ b/ubb-vga/ubb-vga.c @@ -49,16 +49,19 @@ static int bad; static const struct mode mode_db[] = { - { "640x480", 640, 480, 11, US(29.7), US(0.79+3.77-0.3) }, - { "800x600", 800, 600, 8, US(28.7), US(2.0+3.3+0.3) }, - /* the next one may work after adjusting the timing in "frame" */ - { "800x600", 800, 600, 8, US(28.2), US(2.0+3.3+0.3-0.3) }, - /* the 1024x768 below is not great but has good parameter tolerance */ - { "1024x768", 1024, 768, 8, US(36.0), US(2.0+3.3) }, - /* illustrate underruns */ - { "1024x768ur", 1024, 768, 7, US(33.5), US(0.4+2.1+0.5) }, - { "1024x768/53", 1024, 768, 5, US(23.1), US(0.4+2.1-0.4) }, - { NULL } +/* name xres yres clkdiv vfront hsync hback htotal */ +/* vsync vback */ +{ "640x480", 640, 480, 11, 2, 32, 14, US(3.47), US(0.79), US(29.7) }, +{ "800x600", 800, 600, 8, 2, 32, 14, US(4.81), US(0.79), US(28.7) }, +/* the next one may work after adjusting the timing in "frame" */ +{ "800x600", 800, 600, 8, 2, 32, 14, US(4.51), US(0.79), US(28.2) }, + +/* the 1024x768 below is not great but has good parameter tolerance */ +{ "1024x768", 1024, 768, 8, 2, 32, 14, US(4.51), US(0.79), US(36.0) }, +/* illustrate underruns */ +{ "1024x768ur", 1024, 768, 7, 2, 32, 14, US(2.21), US(0.79), US(33.5) }, +{ "1024x768/53",1024, 768, 5, 2, 32, 14, US(1.31), US(0.79), US(23.1) }, +{ NULL } }; /* @@ -274,7 +277,7 @@ static void line(unsigned long line) DTA(DMA) = REG_PADDR(MSC_TXFIFO); /* MUST set this each time */ DTC(DMA) = mode->xres >> 6; - until(US(0.79)); + until(mode->hback_cycles); /* HSYNC */ @@ -295,7 +298,7 @@ static void line(unsigned long line) (1 << 31) | /* no descriptor */ 1; - until(mode->hsync_end); + until(mode->hback_cycles+mode->hsync_cycles); // MSC_TXFIFO = 0xffffffff; @@ -316,7 +319,7 @@ static void hdelay(int cycles) while (cycles--) { TCNT(TIMER) = 0; PDDATC = HSYNC; - until(US(3.77)); + until(mode->hsync_cycles); PDDATS = HSYNC; until(mode->line_cycles); } @@ -329,12 +332,12 @@ static void frame(const unsigned long *f) /* VSYNC */ PDDATC = VSYNC; - hdelay(2); + hdelay(mode->vsync_lines); PDDATS = VSYNC; /* Front porch */ - hdelay(31); + hdelay(mode->vfront_lines-1); /* * The horizontal back porch of the previous line is handled inside @@ -342,9 +345,9 @@ static void frame(const unsigned long *f) */ TCNT(TIMER) = 0; PDDATC = HSYNC; - until(US(3.77)); + until(mode->hsync_cycles); PDDATS = HSYNC; - until(mode->line_cycles-US(0.79)); + until(mode->line_cycles-mode->hback_cycles); /* * Note: resetting the timer just before calling "line" isn't enough. @@ -358,7 +361,7 @@ static void frame(const unsigned long *f) } /* Back porch */ - hdelay(14); + hdelay(mode->vback_lines); } @@ -448,6 +451,14 @@ int main(int argc, char *const *argv) usage(*argv); } +#if 0 +#define CYCLES(cy) ((cy)/112.0+0.5) + +printf("V: %d+%d+%d+%d\n", mode->vsync_lines, mode->vfront_lines, + mode->yres, mode->vback_lines); +printf("H: %4.1f+?+?+%4.1f (%4.1f)\n", CYCLES(mode->hsync_cycles), + CYCLES(mode->hback_cycles), CYCLES(mode->line_cycles)); +#endif setup(); session(gen, frames); cleanup(); diff --git a/ubb-vga/ubb-vga.h b/ubb-vga/ubb-vga.h index 3fb37b5..78d2174 100644 --- a/ubb-vga/ubb-vga.h +++ b/ubb-vga/ubb-vga.h @@ -27,8 +27,12 @@ struct mode { const char *name; /* NULL for end of table */ int xres, yres; int clkdiv; /* pixel clock = 336 MHz/(clkdiv+1) */ - int line_cycles; /* 31.77 us for official VGA */ - int hsync_end; /* 0.79+3.77 us for official VGA */ + int vsync_lines; /* 2 lines, for official VGA */ + int vfront_lines; /* 32 lines */ + int vback_lines; /* 14 lines */ + uint16_t hsync_cycles; /* 3.77 us */ + uint16_t hback_cycles; /* 0.79 us */ + uint16_t line_cycles; /* 31.77 us */ }; extern const struct mode *mode;