Mercurial > repos > blastem
comparison jag_video.c @ 1088:c0a026e974f4
Basic handling of video/object processor register writes
author | Michael Pavone <pavone@retrodev.com> |
---|---|
date | Sat, 08 Oct 2016 23:49:20 -0700 |
parents | 6433d4d05934 |
children | 87597a048d38 |
comparison
equal
deleted
inserted
replaced
1087:6433d4d05934 | 1088:c0a026e974f4 |
---|---|
1 #include <stdint.h> | 1 #include <stdint.h> |
2 #include <stdlib.h> | 2 #include <stdlib.h> |
3 #include <stdio.h> | |
3 #include "jag_video.h" | 4 #include "jag_video.h" |
5 | |
6 enum { | |
7 VMODE_CRY, | |
8 VMODE_RGB24, | |
9 VMODE_DIRECT16, | |
10 VMODE_RGB16, | |
11 VMODE_VARIABLE | |
12 }; | |
13 | |
14 char *vmode_names[] = { | |
15 "CRY", | |
16 "RGB16", | |
17 "DIRECT16", | |
18 "VARIABLE" | |
19 }; | |
4 | 20 |
5 jag_video *jag_video_init(void) | 21 jag_video *jag_video_init(void) |
6 { | 22 { |
7 return calloc(1, sizeof(jag_video)); | 23 return calloc(1, sizeof(jag_video)); |
8 } | 24 } |
9 | 25 |
10 void jag_video_run(jag_video *context, uint32_t target_cycle) | 26 void jag_video_run(jag_video *context, uint32_t target_cycle) |
11 { | 27 { |
12 context->cycles = target_cycle; | 28 context->cycles = target_cycle; |
29 | |
13 } | 30 } |
31 | |
32 static uint8_t is_reg_writeable(uint32_t address) | |
33 { | |
34 return address < VID_HLPEN || address >= VID_OBJLIST1; | |
35 } | |
36 | |
37 void jag_video_reg_write(jag_video *context, uint32_t address, uint16_t value) | |
38 { | |
39 uint32_t reg = (address >> 1 & 0x7F) - 2; | |
40 if (reg < JAG_VIDEO_REGS && is_reg_writeable(reg)) { | |
41 context->regs[reg] = value; | |
42 if (reg == VID_VMODE) { | |
43 context->pclock_div = (value >> 9 & 7) + 1; | |
44 context->pclock_counter = 0; | |
45 if (value & 0x10) { | |
46 context->mode = VMODE_VARIABLE; | |
47 } else { | |
48 context->mode = value >> 1 & 3; | |
49 } | |
50 printf("Mode %s, pixel clock divider: %d, time base generation: %s\n", vmode_names[context->mode], context->pclock_div, value & 1 ? "enabled" : "disabled"); | |
51 } | |
52 switch (reg) | |
53 { | |
54 case VID_OBJLIST1: | |
55 printf("Object List Pointer 1: %X\n", value); | |
56 break; | |
57 case VID_OBJLIST2: | |
58 printf("Object List Pointer 2: %X\n", value); | |
59 break; | |
60 case VID_HPERIOD: | |
61 printf("Horizontal period: %d\n", value & 0x3FF); | |
62 break; | |
63 case VID_HBLANK_BEGIN: | |
64 printf("horizontal blanking begin: %d\n", value & 0x7FF); | |
65 break; | |
66 case VID_HBLANK_END: | |
67 printf("horizontal blanking end: %d\n", value & 0x7FF); | |
68 break; | |
69 case VID_HSYNC: | |
70 printf("horizontal sync start: %d\n", value & 0x7FF); | |
71 break; | |
72 case VID_HDISP_BEGIN1: | |
73 printf("horizontal display begin 1: %d\n", value & 0x7FF); | |
74 break; | |
75 case VID_HDISP_BEGIN2: | |
76 printf("horizontal display begin 2: %d\n", value & 0x7FF); | |
77 break; | |
78 case VID_HDISP_END: | |
79 printf("horizontal display end: %d\n", value & 0x7FF); | |
80 break; | |
81 case VID_VPERIOD: | |
82 printf("Vertical period: %d\n", value & 0x7FF); | |
83 break; | |
84 case VID_VBLANK_BEGIN: | |
85 printf("vertical blanking begin: %d\n", value & 0x7FF); | |
86 break; | |
87 case VID_VBLANK_END: | |
88 printf("vertical blanking end: %d\n", value & 0x7FF); | |
89 break; | |
90 case VID_VSYNC: | |
91 printf("vertical sync start: %d\n", value & 0x7FF); | |
92 break; | |
93 case VID_VDISP_BEGIN: | |
94 printf("vertical display begin: %d\n", value & 0x7FF); | |
95 break; | |
96 case VID_VDISP_END: | |
97 printf("vertical display end: %d\n", value & 0x7FF); | |
98 break; | |
99 } | |
100 } else { | |
101 fprintf(stderr, "Write to invalid video/object processor register %X:%X\n", address, value); | |
102 } | |
103 } |