annotate i8255.c @ 2688:b42f00a3a937 default tip

Fix default target. Ensure m68k.h and z80.h are built before anything else when no dep info is available
author Michael Pavone <pavone@retrodev.com>
date Mon, 31 Mar 2025 21:06:18 -0700
parents 8cf7cadc17ee
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
2521
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
1 #include "i8255.h"
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
2
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
3 #include <string.h>
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
4
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
5 #define BIT_OBFA 0x80
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
6 #define BIT_ACKA 0x40
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
7 #define BIT_IBFA 0x20
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
8 #define BIT_STBA 0x10
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
9 #define BIT_INTRA 0x08
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
10 #define BIT_STB_ACKB 0x04
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
11 #define BIT_IBF_OBFB 0x02
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
12 #define BIT_INTRB 0x01
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
13
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
14 #define BIT_INTE1 BIT_ACKA
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
15 #define BIT_INTE2 BIT_STBA
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
16 #define BIT_INTEB BIT_STB_ACKB
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
17
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
18 void i8255_init(i8255 *ppi, i8255_out_update out, i8255_in_sample in)
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
19 {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
20 memset(ppi->latches, 0, sizeof(ppi->latches));
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
21 ppi->control = 0x1B; //all ports start as input
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
22 ppi->portc_write_mask = 0xFF;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
23 ppi->portc_out_mask = 0;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
24 ppi->out_handler = out;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
25 ppi->in_handler = in;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
26 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
27
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
28 static uint8_t porta_out_enabled(i8255 *ppi)
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
29 {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
30 return (ppi->control & 0x40) || !(ppi->control & 0x10);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
31 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
32
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
33 void i8255_write(uint32_t address, i8255 *ppi, uint8_t value, uint32_t cycle)
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
34 {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
35 switch(address)
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
36 {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
37 case 0:
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
38 ppi->latches[0] = value;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
39 if (porta_out_enabled(ppi)) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
40 if (ppi->control & 0x60) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
41 //Mode 1 or 2
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
42 ppi->latches[2] &= ~BIT_OBFA;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
43 if ((ppi->control & 0x60) == 0x20 || !(ppi->latches[2] & BIT_IBFA)) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
44 ppi->latches[2] &= ~BIT_INTRA;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
45 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
46 if (ppi->out_handler) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
47 ppi->out_handler(ppi, cycle, 2, ppi->latches[2] & ppi->portc_out_mask);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
48 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
49 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
50 if (ppi->out_handler && !(ppi->control & 0x40)) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
51 ppi->out_handler(ppi, cycle, address, value);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
52 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
53 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
54 break;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
55 case 1:
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
56 if (!(ppi->control & 0x02)) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
57 ppi->latches[1] = value;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
58 if (ppi->control & 0x04) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
59 //Mode 1
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
60 ppi->latches[2] &= ~(BIT_IBF_OBFB|BIT_INTRB);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
61 if (ppi->out_handler) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
62 ppi->out_handler(ppi, cycle, 2, ppi->latches[2] & ppi->portc_out_mask);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
63 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
64 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
65 if (ppi->out_handler) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
66 ppi->out_handler(ppi, cycle, address, value);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
67 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
68 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
69 break;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
70 case 2:
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
71 ppi->latches[2] &= ~ppi->portc_write_mask;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
72 ppi->latches[2] |= value & ppi->portc_write_mask;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
73 if (ppi->out_handler && ppi->portc_out_mask) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
74 ppi->out_handler(ppi, cycle, address, ppi->latches[2] & ppi->portc_out_mask);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
75 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
76 break;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
77 case 3:
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
78 if (value & 0x80) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
79 uint8_t changed = ppi->control ^ value;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
80 //datasheet says "output" state is cleared on mode changes
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
81 if (changed & 0x60) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
82 //group A mode changed
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
83 ppi->latches[0] = 0;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
84 ppi->latches[2] &= 0x0F;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
85 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
86 if (changed & 4) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
87 //group B mode changed
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
88 ppi->latches[1] = 0;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
89 if (value & 0x60) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
90 //PC4 is INTRa
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
91 ppi->latches[2] &= 0xF8;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
92 } else {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
93 ppi->latches[2] &= 0xF0;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
94 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
95 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
96 ppi->control = value;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
97 ppi->portc_write_mask = ppi->portc_out_mask = 0;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
98 if (value & 0x40) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
99 //Port A Mode 2
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
100 ppi->portc_out_mask |= BIT_OBFA | BIT_IBFA | BIT_INTRA;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
101 ppi->portc_write_mask |= BIT_INTE1 | BIT_INTE2;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
102 } else if (value & 0x20) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
103 //Port A Mode 1
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
104 ppi->portc_out_mask |= BIT_INTRA;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
105 if (value & 0x10) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
106 //Input
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
107 ppi->portc_out_mask |= BIT_IBFA;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
108 ppi->portc_write_mask |= BIT_INTE2 | 0xC0;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
109 if (!(value & 0x08)) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
110 //Port C upper Output
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
111 ppi->portc_out_mask |= 0xC0;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
112 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
113 } else {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
114 //Output
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
115 ppi->portc_out_mask |= BIT_OBFA;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
116 ppi->portc_out_mask |= BIT_INTE1 | 0x30;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
117 if (!(value & 0x08)) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
118 //Port C upper Output
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
119 ppi->portc_out_mask |= 0x30;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
120 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
121 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
122 } else {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
123 ppi->portc_write_mask |= 0xF0;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
124 if (!(value & 0x08)) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
125 //Port C upper Output
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
126 ppi->portc_out_mask |= 0xF0;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
127 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
128 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
129 if (value & 0x04) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
130 //Port B Mode 1
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
131 ppi->portc_out_mask |= BIT_IBF_OBFB | BIT_INTRB;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
132 ppi->portc_write_mask |= BIT_INTEB;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
133 if (!(ppi->portc_out_mask & BIT_INTRA) && !(value & 1)) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
134 //Port C lower Output
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
135 ppi->portc_out_mask |= 0x08;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
136 ppi->portc_write_mask |= 0x08;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
137 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
138 } else {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
139 if (!(value & 1)) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
140 //Port C lower Output
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
141 ppi->portc_out_mask |= 0x07;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
142 ppi->portc_write_mask |= 0x07;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
143 if (!(ppi->portc_out_mask & BIT_INTRA)) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
144 ppi->portc_out_mask |= 0x08;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
145 ppi->portc_write_mask |= 0x08;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
146 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
147 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
148 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
149 } else {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
150 uint8_t bit = 1 << ((value >> 1) & 7);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
151 if (ppi->portc_write_mask & bit) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
152 if (value & 1) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
153 ppi->latches[2] |= bit;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
154 } else {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
155 ppi->latches[2] &= bit;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
156 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
157 if (ppi->out_handler && ppi->portc_out_mask) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
158 ppi->out_handler(ppi, cycle, 2, ppi->latches[2] & ppi->portc_out_mask);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
159 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
160 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
161 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
162
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
163 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
164 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
165
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
166 uint8_t i8255_read(uint32_t address, i8255 *ppi, uint32_t cycle)
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
167 {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
168 switch(address)
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
169 {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
170 case 0:
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
171 if (ppi->control & 0x60) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
172 //Mode 1 or 2
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
173 if (ppi->control & 0x50) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
174 //Mode 2 or Mode 1 input
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
175 ppi->latches[2] &= ~BIT_IBFA;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
176 if (!(ppi->control & 0x40) || (ppi->latches[2] & BIT_OBFA)) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
177 ppi->latches[2] &= ~BIT_INTRA;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
178 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
179 if (ppi->out_handler) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
180 ppi->out_handler(ppi, cycle, 2, ppi->latches[2] & ppi->portc_out_mask);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
181 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
182 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
183 return ppi->latches[3];
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
184 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
185 if (ppi->control & 0x10) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
186 if (ppi->in_handler) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
187 return ppi->in_handler(ppi, cycle, address);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
188 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
189 return 0xFF;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
190 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
191 return ppi->latches[0];
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
192 case 1:
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
193 if (ppi->control & 0x40) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
194 //Mode 1
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
195 if (ppi->control & 0x2) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
196 //input
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
197 ppi->latches[2] &= ~(BIT_IBF_OBFB|BIT_INTRB);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
198 if (ppi->out_handler) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
199 ppi->out_handler(ppi, cycle, 2, ppi->latches[2] & ppi->portc_out_mask);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
200 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
201 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
202 return ppi->latches[1];
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
203 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
204 if (ppi->control & 0x2) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
205 //input
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
206 if (ppi->in_handler) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
207 return ppi->in_handler(ppi, cycle, address);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
208 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
209 return 0xFF;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
210 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
211 return ppi->latches[1];
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
212 case 2:
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
213 return ppi->latches[2];
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
214 case 3:
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
215 default:
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
216 return 0xFF;//described as illegal in datasheet
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
217 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
218 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
219
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
220 void i8255_input_strobe_a(i8255 *ppi, uint8_t value, uint32_t cycle)
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
221 {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
222 if ((ppi->control & 0x70) == 0x30 || (ppi->control & 0x40)) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
223 //Mode 2 or Mode 1 input
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
224 ppi->latches[3] = value;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
225 ppi->latches[2] |= BIT_IBFA;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
226 if (ppi->latches[2] & BIT_INTE2) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
227 ppi->latches[2] |= BIT_INTRA;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
228 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
229 if (ppi->out_handler) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
230 ppi->out_handler(ppi, cycle, 2, ppi->latches[2] & ppi->portc_out_mask);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
231 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
232 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
233 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
234
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
235 void i8255_input_strobe_b(i8255 *ppi, uint8_t value, uint32_t cycle)
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
236 {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
237 if ((ppi->control & 6) == 6) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
238 //Mode 1 input
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
239 ppi->latches[1] = value;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
240 ppi->latches[2] |= BIT_IBF_OBFB;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
241 if (ppi->latches[2] & BIT_INTEB) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
242 ppi->latches[2] |= BIT_INTRB;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
243 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
244 if (ppi->out_handler) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
245 ppi->out_handler(ppi, cycle, 2, ppi->latches[2] & ppi->portc_out_mask);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
246 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
247 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
248 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
249
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
250 uint8_t i8255_output_ack_a(i8255 *ppi, uint32_t cycle)
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
251 {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
252 if ((ppi->control & 0x70) == 0x20 || (ppi->control & 0x40)) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
253 //Mode 2 or Mode 1 output
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
254 ppi->latches[2] |= BIT_OBFA;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
255 if (ppi->latches[2] & BIT_INTE1) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
256 ppi->latches[2] |= BIT_INTRA;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
257 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
258 if (ppi->out_handler) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
259 ppi->out_handler(ppi, cycle, 2, ppi->latches[2] & ppi->portc_out_mask);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
260 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
261 return ppi->latches[0];
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
262 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
263 if (ppi->control & 0x10) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
264 //input mode
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
265 return 0xFF;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
266 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
267 //Mode 0 output
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
268 return ppi->latches[0];
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
269 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
270
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
271 uint8_t i8255_output_ack_b(i8255 *ppi, uint32_t cycle)
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
272 {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
273 if ((ppi->control & 0x06) == 0x04) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
274 //Mode 1 output
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
275 ppi->latches[2] |= BIT_IBF_OBFB;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
276 if (ppi->latches[2] & BIT_INTEB) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
277 ppi->latches[2] |= BIT_INTRB;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
278 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
279 if (ppi->out_handler) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
280 ppi->out_handler(ppi, cycle, 2, ppi->latches[2] & ppi->portc_out_mask);
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
281 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
282 return ppi->latches[1];
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
283 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
284 if (ppi->control & 2) {
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
285 //input mode
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
286 return 0xFF;
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
287 }
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
288 //Mode 0 output
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
289 return ppi->latches[1];
8cf7cadc17ee Initial SC-3000 support
Michael Pavone <pavone@retrodev.com>
parents:
diff changeset
290 }