Merge branch 'master' of https://github.com/linappleii/linapple
T. Joseph Carter
4 years ago
0 | Linapple - crossplatfom emulator of Apple ][ (Apple2, Apple 2e) series computer for Linux or other OSes with SDL support. | |
1 | ||
2 | [INSTALL] | |
3 | ||
4 | You need SDL, cURL, zlib and libzip libraries development versions with -dev or -devel suffixes. | |
5 | ||
6 | For Debian/Ubuntu their names are: | |
7 | libsdl1.2-dev - Simple Direct Media crossplatform library for video,audio, events etc. | |
8 | libcurl4 - openssl-dev - cURL net functions | |
9 | zlib1g-dev - access .gz files | |
10 | libzip-dev - access .zip files | |
11 | ||
12 | All these libraries are available for free around the world. | |
13 | ||
14 | For example for Debian/Ubuntu to install: | |
15 | $ sudo apt-get install libsdl1.2-dev libcurl4-openssl-dev zlib1g-dev libzip-dev | |
16 | ||
17 | After being SDL, zlib, cURL and libzip installed you will be able to compile linapple from sources: | |
18 | ||
19 | Untar the package (in .bz2 format): | |
20 | $ tar xjf linapple_src-2b.tar.bz2 | |
21 | ||
22 | Then go to src directory and compile. | |
23 | $ cd linapple_src-2b/src | |
24 | $ make | |
25 | ||
26 | If there are no errors, you may install it if you wish: | |
27 | $ sudo make install | |
28 | ||
29 | It will be installed in /usr/local/linapple folder, whre you can find linapple.conf file for changing some linapple settings, | |
30 | and empty `images` and `ftp` folders, where Apple 2 images files and downloaded through FTP cached images are meant to be in. | |
31 | ||
32 | Of course you are free to choose any directories of your choice changing it in Makefile in src directory. | |
33 | Note: you should read/write permissions for these folders, or linapple could not work properly. | |
34 | ||
35 | For linaaple ability to unpack .zip and .gz files on the fly (either from local disks or from FTP) you also need read/write access for linapple working folder (which by default is /usr/local/linapple), for linapple unpacks these files as drive0.dsk and drive1.dsk for drive 1 and 2 respectively. | |
36 | ||
37 | OK. If you installed it, you are able to run emulator from any place, just run it like this: | |
38 | $ linapple | |
39 | ||
40 | If you have chosen not to install it, go to the upper directory then and run the beast: | |
41 | $ cd .. | |
42 | $ ./linapple | |
43 | ||
44 | If all files are on their places, you should see an X-Window with splash screen. | |
45 | Press F2 (or F3 before to choose some disk image in drive 1), and go to work. | |
46 | ||
47 | Note: linapple needs some files in its current working directory for proper working. | |
48 | ||
49 | These files are: | |
50 | splash.bmp - splash screen | |
51 | charset40.bmp - charset for Apple][ (Apple 2e, etc.) text modes. | |
52 | font.bmp - font for Help screen and Disk Select screens. | |
53 | icon.bmp - nice icon, logo of Apple][ computer. | |
54 | linapple.conf - configuration file. | |
55 | Master.dsk - disk image with Applesoft(tm) DOS 3.3 inside. See Apple license (on apple.com) for details. | |
56 | ||
57 | Essential are font.bmp and charset40.bmp, others can be omitted peacefully. | |
58 | ||
59 | P.S. You may play with some options in Makefile in src directory, if you know what you want to do. | |
60 | ||
61 | Note: See README file for more detailed instructions on using linapple. | |
62 | ||
63 | [UNINSTALL] | |
64 | ||
65 | To uninstall previously installed linapple (by `sudo make install` command) you may write this: | |
66 | $ sudo make uninstall | |
67 | ||
68 | This will remove by default entire `/usr/local/linapple` folder and `/usr/local/bin/linapple` script. | |
69 | ||
70 | Also there is possible command for cleaning compiled binaries in src directory: | |
71 | $ make clean | |
72 | ||
73 | Note: `linapple` executable in upper directory will remain intact. | |
74 | ||
75 | [CONTACT] | |
76 | ||
77 | I will be glad to see your comments, suggestions and so on on my email beotiger@gmail.com | |
78 | ||
79 | Sincerely Yours, | |
80 | beotiger, December 2007 AD - March 2012 AD - June 2015 | |
81 | http://beotiger.com beotiger@gmail.com | |
82 | ||
83 | Let Apple 2 live forever! |
0 | 0 | # Installation |
1 | # Build modernization by Greg Hedger, November 2017 | |
2 | # Ubuntu 16.04 | |
1 | ||
2 | ||
3 | ## Ubuntu 16.04 | |
3 | 4 | |
4 | 5 | make |
5 | 6 | cd bin |
6 | 7 | ./linapple |
7 | 8 | |
8 | # Prerequisites | |
9 | sudo apt-get install libzip-dev libzip4 libcurl3 libcurl-ocaml-dev | |
9 | ### Prerequisites | |
10 | 10 | |
11 | ```bash | |
12 | sudo apt-get git libzip-dev libsdl1.2-dev libcurl4-openssl-dev zlib1g-dev | |
13 | ``` | |
11 | 14 | |
12 | # Historical INSTALL | |
15 | ### Clone | |
16 | ||
17 | ```bash | |
18 | git clone git@github.com:linappleii/linapple.git | |
19 | ``` | |
13 | 20 | Linapple - crossplatfom emulator of Apple][ (Apple2, Apple 2) series computer for Linux or other OSes with SDL support. |
14 | 21 | |
15 | 22 | |
16 | [INSTALL] | |
23 | ### Compile | |
17 | 24 | |
18 | You need SDL, cURL, zlib and libzip: | |
25 | ```bash | |
26 | cd linapple | |
27 | make | |
28 | ``` | |
19 | 29 | |
20 | For Debian/Ubuntu their names are: | |
30 | ### Global Install | |
31 | ```shell | |
32 | make install | |
33 | ``` | |
21 | 34 | |
22 | libsdl1.2-dev - Simple Direct Media crossplatform library for video,audio, events etc. | |
23 | libcurl4 - openssl-dev - cURL net functions | |
24 | zlib1g-dev - access .gz files | |
25 | libzip-dev - access .zip files | |
35 | ### Run | |
26 | 36 | |
27 | All these libraries are available for free around the world. | |
37 | ```bash | |
38 | bin/linapple | |
39 | ``` | |
28 | 40 | |
29 | For example for Debian/Ubuntu to install: | |
41 | Or if you did a global install. | |
30 | 42 | |
31 | $sudo apt-get install libsdl1.2-dev libcurl4-openssl-dev zlib1g-dev libzip-dev | |
43 | ```bash | |
44 | linapple | |
45 | ``` | |
32 | 46 | |
47 | ### Configure | |
33 | 48 | |
34 | After being SDL, zlib, cURL and libzip installed you will be able to compile linapple from sources: | |
49 | A directory name `linapple` can be found in your home directory. Edit the `linapple.conf` file. | |
35 | 50 | |
36 | Untar the package (in .bz2 format): | |
37 | ||
38 | $ tar xjf linapple-src_2a.tar.bz2 | |
39 | ||
40 | ||
41 | Then go to src directory and compile. | |
42 | ||
43 | $ make | |
44 | ||
45 | If there was no errors, you may install it if you wish: | |
46 | ||
47 | $ cd bin | |
48 | $ ./linapple | |
49 | ||
50 | It will be install in /usr/local/linapple folder, whre you can find linapple.conf file for changing some linapple settings, | |
51 | and empty `images` and `ftp` folders, where Apple 2 images files and downloaded through FTP images are meant to be in. | |
52 | ||
53 | But of course you are free to choose any directories of your choice. | |
54 | Note: you should read/write permissions of these folders, or linapple could not work properly. | |
55 | ||
56 | For linaaple ability to unpack .zip and .gz files on the fly (either from local disks or from FTP) you also need read/write access for linapple working | |
57 | folder (which by default is /usr/local/linapple), for linapple unpacks these files as drive0.dsk and drive1.dsk for drive 1 and 2 respectively. | |
58 | ||
59 | ||
60 | OK. | |
61 | If you installed it, you are able to run emulator from any place, just run it like this: | |
62 | ||
63 | $ linapple | |
64 | ||
65 | ||
66 | If you have chosen not to install it, go to the upper directory then and run the beast: | |
67 | ||
68 | $ cd .. | |
69 | ||
70 | $ ./linapple | |
71 | ||
72 | ||
73 | If all files are on their places, you should see an X-Window with splash screen. | |
74 | Press F2 (or F3 before to choose some disk image in drive 1), and go to work. | |
75 | ||
76 | Note: linapple needs some files in its current working directory for proper working. | |
77 | ||
78 | These files are: | |
79 | ||
80 | splash.bmp - splash screen | |
81 | charset40.bmp - charset for Apple][ (Apple 2e, etc.) text modes. | |
82 | font.bmp - font for Help screen and Disk Select screens. | |
83 | icon.bmp - nice icon, logo of Apple][ computer. | |
84 | linapple.conf - configuration file. | |
85 | Master.dsk - disk image with Applesoft(tm) DOS 3.3 inside. See Apple license (on apple.com) for details. | |
86 | ||
87 | Essentials are font.bmp and charset40.bmp, others can be omitted peacefully. | |
88 | ||
89 | P.S. You may play with some options in Makefile in src directory, if you know what you are to do. :) | |
90 | ||
91 | Note: See README file for more detailed instructions on using linapple. | |
92 | ||
93 | ||
94 | [UNINSTALL] | |
95 | ||
96 | To uninstall previously installed linapple (by `sudo make install` command) you may write this: | |
97 | ||
98 | $ sudo make uninstall | |
99 | ||
100 | This will remove by default entire `/usr/local/linapple` folder and `/usr/local/bin/linapple` script. | |
101 | ||
102 | ||
103 | Also there is possible command for cleaning compiled binaries in src directory: | |
104 | ||
105 | $ make clean | |
106 | ||
107 | Note: `linapple` executable in upper directory will remain intact. | |
108 | ||
109 | ||
110 | ||
111 | [CONTACT] | |
112 | ||
113 | I will be glad to see your comments, suggestions and so on on my email: beotiger@gmail.com | |
114 | ||
115 | Sincerely Yours, | |
116 | Krez beom beotiger, December 2007 AD - March 2012 AD | |
117 | ||
118 | beotiger@mail.ru | |
119 | beotiger@gmail.com | |
120 | ||
121 | Let Apple 2 live forever! | |
122 |
12 | 12 | extern regsrec regs; |
13 | 13 | extern unsigned __int64 g_nCumulativeCycles; |
14 | 14 | |
15 | void CpuDestroy (); | |
16 | void CpuCalcCycles(ULONG nExecutedCycles); | |
17 | DWORD CpuExecute (DWORD); | |
18 | ULONG CpuGetCyclesThisFrame(ULONG nExecutedCycles); | |
19 | void CpuInitialize (); | |
20 | void CpuSetupBenchmark (); | |
15 | void CpuDestroy (); | |
16 | void CpuCalcCycles(ULONG nExecutedCycles); | |
17 | DWORD CpuExecute (DWORD); | |
18 | ULONG CpuGetCyclesThisFrame(ULONG nExecutedCycles); | |
19 | void CpuInitialize (); | |
20 | void CpuSetupBenchmark (); | |
21 | 21 | void CpuIrqReset(); |
22 | 22 | void CpuIrqAssert(eIRQSRC Device); |
23 | 23 | void CpuIrqDeassert(eIRQSRC Device); |
24 | 24 | void CpuNmiReset(); |
25 | 25 | void CpuNmiAssert(eIRQSRC Device); |
26 | 26 | void CpuNmiDeassert(eIRQSRC Device); |
27 | void CpuReset (); | |
28 | DWORD CpuGetSnapshot(SS_CPU6502* pSS); | |
29 | DWORD CpuSetSnapshot(SS_CPU6502* pSS); | |
27 | void CpuReset (); | |
28 | DWORD CpuGetSnapshot(SS_CPU6502* pSS); | |
29 | DWORD CpuSetSnapshot(SS_CPU6502* pSS); |
37 | 37 | bit5 C2_INPUT C2_OUTPUT |
38 | 38 | */ |
39 | 39 | #define PIA_IRQ1 0x80 |
40 | #define PIA_IRQ2 0x40 | |
40 | #define PIA_IRQ2 0x40 | |
41 | 41 | #define SET_IRQ1(c) c |= PIA_IRQ1; |
42 | 42 | #define SET_IRQ2(c) c |= PIA_IRQ2; |
43 | 43 | #define CLEAR_IRQ1(c) c &= ~PIA_IRQ1; |
119 | 119 | { |
120 | 120 | BYTE retval = 0; |
121 | 121 | byRS &= 3; |
122 | switch ( byRS ) | |
123 | { | |
122 | switch (byRS) { | |
124 | 123 | /******************* port A output/DDR read *******************/ |
125 | case PIA_DDRA: | |
126 | // read output register | |
127 | if ( OUTPUT_SELECTED(m_byCTLA) ) | |
128 | { | |
129 | // combine input and output values | |
130 | retval = ( m_byOA & m_byDDRA ) | ( m_byIA & ~m_byDDRA ); | |
131 | // IRQ flags implicitly cleared by a read | |
132 | CLEAR_IRQ1( m_byCTLA ); | |
133 | CLEAR_IRQ1( m_byCTLB ); | |
124 | case PIA_DDRA: | |
125 | // read output register | |
126 | if (OUTPUT_SELECTED(m_byCTLA)) { | |
127 | // combine input and output values | |
128 | retval = (m_byOA & m_byDDRA) | (m_byIA & ~m_byDDRA); | |
129 | // IRQ flags implicitly cleared by a read | |
130 | CLEAR_IRQ1(m_byCTLA); | |
131 | CLEAR_IRQ1(m_byCTLB); | |
132 | UpdateInterrupts(); | |
133 | // CA2 is configured as output and in read strobe mode | |
134 | if (C2_OUTPUT(m_byCTLA) && C2_STROBE_MODE(m_byCTLA)) { | |
135 | // this will cause a transition low; call the output function if we're currently high | |
136 | if (m_byOCA2) | |
137 | PIA_W_CALLBACK(m_stOutCA2, 0); | |
138 | m_byOCA2 = 0; | |
139 | ||
140 | // if the CA2 strobe is cleared by the E, reset it right away | |
141 | if (STROBE_E_RESET(m_byCTLA)) { | |
142 | PIA_W_CALLBACK(m_stOutCA2, 1); | |
143 | m_byOCA2 = 1; | |
144 | } | |
145 | } | |
146 | } | |
147 | // read DDR register | |
148 | else { | |
149 | retval = m_byDDRA; | |
150 | } | |
151 | break; | |
152 | ||
153 | /******************* port B output/DDR read *******************/ | |
154 | case PIA_DDRB: | |
155 | ||
156 | // read output register | |
157 | if (OUTPUT_SELECTED(m_byCTLB)) { | |
158 | // combine input and output values | |
159 | retval = (m_byOB & m_byDDRB) + (m_byIB & ~m_byDDRB); | |
160 | ||
161 | // IRQ flags implicitly cleared by a read | |
162 | CLEAR_IRQ2(m_byCTLA); | |
163 | CLEAR_IRQ2(m_byCTLB); | |
164 | UpdateInterrupts(); | |
165 | } | |
166 | /* read DDR register */ | |
167 | else { | |
168 | retval = m_byDDRB; | |
169 | } | |
170 | break; | |
171 | ||
172 | /******************* port A control read *******************/ | |
173 | case PIA_CTLA: | |
174 | // read control register | |
175 | retval = m_byCTLA; | |
176 | // when CA2 is an output, IRQA2 = 0, and is not affected by CA2 transitions. | |
177 | if (C2_OUTPUT(m_byCTLA)) | |
178 | retval &= ~PIA_IRQ2; | |
179 | break; | |
180 | ||
181 | /******************* port B control read *******************/ | |
182 | case PIA_CTLB: | |
183 | retval = m_byCTLB; | |
184 | // when CB2 is an output, IRQB2 = 0, and is not affected by CB2 transitions. | |
185 | if (C2_OUTPUT(m_byCTLB)) | |
186 | retval &= ~PIA_IRQ2; | |
187 | break; | |
188 | ||
189 | } | |
190 | ||
191 | return retval; | |
192 | } | |
193 | ||
194 | void C6821::Write(BYTE byRS, BYTE byData) | |
195 | { | |
196 | byRS &= 3; | |
197 | ||
198 | switch( byRS ) { | |
199 | /******************* port A output/DDR write *******************/ | |
200 | case PIA_DDRA: | |
201 | ||
202 | // write output register | |
203 | if (OUTPUT_SELECTED(m_byCTLA)) { | |
204 | // update the output value | |
205 | m_byOA = byData; | |
206 | ||
207 | // send it to the output function | |
208 | if (m_byDDRA) | |
209 | PIA_W_CALLBACK(m_stOutA, m_byOA & m_byDDRA); | |
210 | } | |
211 | ||
212 | // write DDR register | |
213 | else { | |
214 | if (m_byDDRA != byData) { | |
215 | m_byDDRA = byData; | |
216 | ||
217 | // send it to the output function | |
218 | if (m_byDDRA) | |
219 | PIA_W_CALLBACK(m_stOutA, m_byOA & m_byDDRA); | |
220 | } | |
221 | } | |
222 | break; | |
223 | ||
224 | /******************* port B output/DDR write *******************/ | |
225 | case PIA_DDRB: | |
226 | ||
227 | // write output register | |
228 | if (OUTPUT_SELECTED(m_byCTLB)) { | |
229 | // update the output value | |
230 | m_byOB = byData; | |
231 | ||
232 | // send it to the output function | |
233 | if (m_byDDRB) | |
234 | PIA_W_CALLBACK(m_stOutB, m_byOB & m_byDDRB); | |
235 | ||
236 | // CB2 is configured as output and in write strobe mode | |
237 | if (C2_OUTPUT(m_byCTLB) && C2_STROBE_MODE(m_byCTLB)) { | |
238 | // this will cause a transition low; call the output function if we're currently high | |
239 | if (m_byOCB2) | |
240 | PIA_W_CALLBACK(m_stOutCB2, 0); | |
241 | m_byOCB2 = 0; | |
242 | ||
243 | // if the CB2 strobe is cleared by the E, reset it right away | |
244 | if (STROBE_E_RESET(m_byCTLB)) { | |
245 | PIA_W_CALLBACK(m_stOutCB2, 1); | |
246 | m_byOCB2 = 1; | |
247 | } | |
248 | } | |
249 | } | |
250 | // write DDR register | |
251 | else { | |
252 | if (m_byDDRB != byData) { | |
253 | m_byDDRB = byData; | |
254 | ||
255 | // send it to the output function | |
256 | if (m_byDDRB) | |
257 | PIA_W_CALLBACK(m_stOutB, m_byOB & m_byDDRB); | |
258 | } | |
259 | } | |
260 | break; | |
261 | ||
262 | /******************* port A control write *******************/ | |
263 | case PIA_CTLA: | |
264 | // Bit 7 and 6 read only | |
265 | byData &= 0x3f; | |
266 | ||
267 | // CA2 is configured as output and in set/reset mode | |
268 | if (C2_OUTPUT(byData)) { | |
269 | // determine the new value | |
270 | int temp = SET_C2(byData) ? 1 : 0; | |
271 | ||
272 | // if this creates a transition, call the CA2 output function | |
273 | if (m_byOCA2 ^ temp) | |
274 | PIA_W_CALLBACK(m_stOutCA2, temp); | |
275 | ||
276 | // set the new value | |
277 | m_byOCA2 = temp; | |
278 | } | |
279 | ||
280 | // update the control register | |
281 | m_byCTLA = (m_byCTLA & ~0x3F) | byData; | |
282 | ||
283 | // update externals | |
134 | 284 | UpdateInterrupts(); |
135 | // CA2 is configured as output and in read strobe mode | |
136 | if ( C2_OUTPUT(m_byCTLA) && C2_STROBE_MODE(m_byCTLA) ) | |
137 | { | |
138 | // this will cause a transition low; call the output function if we're currently high | |
139 | if ( m_byOCA2 ) | |
140 | PIA_W_CALLBACK( m_stOutCA2, 0 ); | |
141 | m_byOCA2 = 0; | |
142 | ||
143 | // if the CA2 strobe is cleared by the E, reset it right away | |
144 | if ( STROBE_E_RESET( m_byCTLA ) ) | |
145 | { | |
146 | PIA_W_CALLBACK( m_stOutCA2, 1 ); | |
147 | m_byOCA2 = 1; | |
148 | } | |
149 | } | |
150 | } | |
151 | // read DDR register | |
152 | else | |
153 | { | |
154 | retval = m_byDDRA; | |
155 | } | |
156 | break; | |
157 | ||
158 | /******************* port B output/DDR read *******************/ | |
159 | case PIA_DDRB: | |
160 | ||
161 | // read output register | |
162 | if ( OUTPUT_SELECTED( m_byCTLB ) ) | |
163 | { | |
164 | // combine input and output values | |
165 | retval = ( m_byOB & m_byDDRB ) + ( m_byIB & ~m_byDDRB ); | |
166 | ||
167 | // IRQ flags implicitly cleared by a read | |
168 | CLEAR_IRQ2( m_byCTLA ); | |
169 | CLEAR_IRQ2( m_byCTLB ); | |
285 | break; | |
286 | ||
287 | /******************* port B control write *******************/ | |
288 | case PIA_CTLB: | |
289 | ||
290 | /* Bit 7 and 6 read only - PD 16/01/00 */ | |
291 | ||
292 | byData &= 0x3f; | |
293 | ||
294 | // CB2 is configured as output and in set/reset mode | |
295 | if (C2_OUTPUT(byData)) { | |
296 | // determine the new value | |
297 | int temp = SET_C2(byData) ? 1 : 0; | |
298 | ||
299 | // if this creates a transition, call the CA2 output function | |
300 | if (m_byOCB2 ^ temp) | |
301 | PIA_W_CALLBACK(m_stOutCB2, temp); | |
302 | ||
303 | // set the new value | |
304 | m_byOCB2 = temp; | |
305 | } | |
306 | ||
307 | // update the control register | |
308 | m_byCTLB = (m_byCTLB & ~0x3F) | byData; | |
309 | ||
310 | // update externals | |
170 | 311 | UpdateInterrupts(); |
171 | } | |
172 | /* read DDR register */ | |
173 | else | |
174 | { | |
175 | retval = m_byDDRB; | |
176 | } | |
177 | break; | |
178 | ||
179 | /******************* port A control read *******************/ | |
180 | case PIA_CTLA: | |
181 | // read control register | |
182 | retval = m_byCTLA; | |
183 | // when CA2 is an output, IRQA2 = 0, and is not affected by CA2 transitions. | |
184 | if ( C2_OUTPUT( m_byCTLA ) ) | |
185 | retval &= ~PIA_IRQ2; | |
186 | break; | |
187 | ||
188 | /******************* port B control read *******************/ | |
189 | case PIA_CTLB: | |
190 | retval = m_byCTLB; | |
191 | // when CB2 is an output, IRQB2 = 0, and is not affected by CB2 transitions. | |
192 | if ( C2_OUTPUT( m_byCTLB ) ) | |
193 | retval &= ~PIA_IRQ2; | |
194 | break; | |
195 | ||
196 | } | |
197 | ||
198 | return retval; | |
199 | } | |
200 | ||
201 | void C6821::Write(BYTE byRS, BYTE byData) | |
202 | { | |
203 | byRS &= 3; | |
204 | ||
205 | switch( byRS ) | |
206 | { | |
207 | /******************* port A output/DDR write *******************/ | |
208 | case PIA_DDRA: | |
209 | ||
210 | // write output register | |
211 | if ( OUTPUT_SELECTED( m_byCTLA ) ) | |
212 | { | |
213 | // update the output value | |
214 | m_byOA = byData; | |
215 | ||
216 | // send it to the output function | |
217 | if ( m_byDDRA ) | |
218 | PIA_W_CALLBACK( m_stOutA, m_byOA & m_byDDRA ); | |
219 | } | |
220 | ||
221 | // write DDR register | |
222 | else | |
223 | { | |
224 | if ( m_byDDRA != byData ) | |
225 | { | |
226 | m_byDDRA = byData; | |
227 | ||
228 | // send it to the output function | |
229 | if ( m_byDDRA ) | |
230 | PIA_W_CALLBACK( m_stOutA, m_byOA & m_byDDRA ); | |
231 | } | |
232 | } | |
233 | break; | |
234 | ||
235 | /******************* port B output/DDR write *******************/ | |
236 | case PIA_DDRB: | |
237 | ||
238 | // write output register | |
239 | if ( OUTPUT_SELECTED( m_byCTLB ) ) | |
240 | { | |
241 | // update the output value | |
242 | m_byOB = byData; | |
243 | ||
244 | // send it to the output function | |
245 | if ( m_byDDRB ) | |
246 | PIA_W_CALLBACK( m_stOutB, m_byOB & m_byDDRB ); | |
247 | ||
248 | // CB2 is configured as output and in write strobe mode | |
249 | if ( C2_OUTPUT( m_byCTLB ) && C2_STROBE_MODE( m_byCTLB ) ) | |
250 | { | |
251 | // this will cause a transition low; call the output function if we're currently high | |
252 | if ( m_byOCB2 ) | |
253 | PIA_W_CALLBACK( m_stOutCB2, 0 ); | |
254 | m_byOCB2 = 0; | |
255 | ||
256 | // if the CB2 strobe is cleared by the E, reset it right away | |
257 | if ( STROBE_E_RESET( m_byCTLB ) ) | |
258 | { | |
259 | PIA_W_CALLBACK( m_stOutCB2, 1 ); | |
260 | m_byOCB2 = 1; | |
261 | } | |
262 | } | |
263 | } | |
264 | // write DDR register | |
265 | else | |
266 | { | |
267 | if ( m_byDDRB != byData ) | |
268 | { | |
269 | m_byDDRB = byData; | |
270 | ||
271 | // send it to the output function | |
272 | if ( m_byDDRB ) | |
273 | PIA_W_CALLBACK( m_stOutB, m_byOB & m_byDDRB ); | |
274 | } | |
275 | } | |
276 | break; | |
277 | ||
278 | /******************* port A control write *******************/ | |
279 | case PIA_CTLA: | |
280 | // Bit 7 and 6 read only | |
281 | byData &= 0x3f; | |
282 | ||
283 | // CA2 is configured as output and in set/reset mode | |
284 | if ( C2_OUTPUT( byData ) ) | |
285 | { | |
286 | // determine the new value | |
287 | int temp = SET_C2( byData ) ? 1 : 0; | |
288 | ||
289 | // if this creates a transition, call the CA2 output function | |
290 | if ( m_byOCA2 ^ temp) | |
291 | PIA_W_CALLBACK( m_stOutCA2, temp ); | |
292 | ||
293 | // set the new value | |
294 | m_byOCA2 = temp; | |
295 | } | |
296 | ||
297 | // update the control register | |
298 | m_byCTLA = ( m_byCTLA & ~0x3F ) | byData; | |
299 | ||
300 | // update externals | |
301 | UpdateInterrupts(); | |
302 | break; | |
303 | ||
304 | /******************* port B control write *******************/ | |
305 | case PIA_CTLB: | |
306 | ||
307 | /* Bit 7 and 6 read only - PD 16/01/00 */ | |
308 | ||
309 | byData &= 0x3f; | |
310 | ||
311 | // CB2 is configured as output and in set/reset mode | |
312 | if ( C2_OUTPUT( byData ) ) | |
313 | { | |
314 | // determine the new value | |
315 | int temp = SET_C2( byData ) ? 1 : 0; | |
316 | ||
317 | // if this creates a transition, call the CA2 output function | |
318 | if ( m_byOCB2 ^ temp) | |
319 | PIA_W_CALLBACK( m_stOutCB2, temp ); | |
320 | ||
321 | // set the new value | |
322 | m_byOCB2 = temp; | |
323 | } | |
324 | ||
325 | // update the control register | |
326 | m_byCTLB = ( m_byCTLB & ~0x3F ) | byData; | |
327 | ||
328 | // update externals | |
329 | UpdateInterrupts(); | |
330 | break; | |
312 | break; | |
331 | 313 | } |
332 | 314 | |
333 | 315 | } |
427 | 409 | if ( m_byICA2 ^ byData ) |
428 | 410 | { |
429 | 411 | // handle the active transition |
430 | if ( ( byData && C2_LOW_TO_HIGH( m_byCTLA ) ) || | |
431 | ( !byData && C2_HIGH_TO_LOW( m_byCTLA ) ) ) | |
432 | { | |
412 | if ((byData && C2_LOW_TO_HIGH(m_byCTLA)) || | |
413 | (!byData && C2_HIGH_TO_LOW(m_byCTLA))) { | |
433 | 414 | // mark the IRQ |
434 | SET_IRQ2( m_byCTLA ); | |
415 | SET_IRQ2(m_byCTLA); | |
435 | 416 | |
436 | 417 | // update externals |
437 | 418 | UpdateInterrupts(); |
26 | 26 | // information, if you find new information we would appreciate if you made it |
27 | 27 | // freely available as well. |
28 | 28 | // |
29 | ||
30 | 29 | |
31 | 30 | #include "wincompat.h" |
32 | 31 | #include <stdio.h> |
63 | 63 | |
64 | 64 | eApple2Type g_Apple2Type = A2TYPE_APPLE2EEHANCED; |
65 | 65 | |
66 | BOOL behind = 0; // Redundant | |
67 | DWORD cumulativecycles = 0; // Wraps after ~1hr 9mins | |
68 | DWORD cyclenum = 0; // Used by SpkrToggle() for non-wave sound | |
69 | DWORD emulmsec = 0; | |
70 | static DWORD emulmsec_frac = 0; | |
71 | bool g_bFullSpeed = false; | |
66 | BOOL behind = 0; // Redundant | |
67 | DWORD cumulativecycles = 0; // Wraps after ~1hr 9mins | |
68 | DWORD cyclenum = 0; // Used by SpkrToggle() for non-wave sound | |
69 | DWORD emulmsec = 0; | |
70 | static DWORD emulmsec_frac = 0; | |
71 | bool g_bFullSpeed = false; | |
72 | 72 | bool hddenabled = false; |
73 | 73 | static bool g_uMouseInSlot4 = false; // not any mouse in slot4??--bb |
74 | 74 | // Win32 |
520 | 520 | MB_SetSoundcardType((eSOUNDCARDTYPE)dwTmp); |
521 | 521 | |
522 | 522 | if(LOAD(TEXT(REGVALUE_SAVE_STATE_ON_EXIT), &dwTmp)) |
523 | g_bSaveStateOnExit = dwTmp ? true : false; | |
523 | g_bSaveStateOnExit = dwTmp != NULL || false; | |
524 | 524 | |
525 | 525 | if(LOAD(TEXT(REGVALUE_HDD_ENABLED), &dwTmp)) hddenabled = (bool) dwTmp;// after MemInitialize |
526 | 526 | // HD_SetEnabled(dwTmp ? true : false); |
864 | 864 | else if (g_uMaxExPages < 1) |
865 | 865 | g_uMaxExPages = 1; |
866 | 866 | } |
867 | ||
868 | else if(strcmp(lpNextArg, "-autoboot") == 0) | |
869 | { | |
870 | bBoot = true; | |
871 | } | |
867 | else if(strcmp(lpNextArg, "-autoboot") == 0) | |
868 | { | |
869 | bBoot = true; | |
870 | } | |
872 | 871 | #endif |
873 | 872 | |
874 | 873 | //*lpCmdLine = lpNextArg; |
1000 | 999 | DebugInitialize(); |
1001 | 1000 | JoyInitialize(); |
1002 | 1001 | MemInitialize(); |
1003 | HD_SetEnabled(hddenabled ? true : false); | |
1002 | HD_SetEnabled(hddenabled); | |
1004 | 1003 | //printf("g_bHD_Enabled = %d\n", g_bHD_Enabled); |
1005 | 1004 | |
1006 | 1005 | VideoInitialize(); |
1024 | 1023 | // bSetFullScreen = false; |
1025 | 1024 | // } |
1026 | 1025 | // |
1027 | //Automatically boot from disk if specified on the command line | |
1026 | //Automatically boot from disk if specified on the command line | |
1028 | 1027 | if(bBoot) |
1029 | 1028 | { |
1030 | // autostart | |
1031 | setAutoBoot(); | |
1029 | // autostart | |
1030 | setAutoBoot(); | |
1032 | 1031 | } |
1033 | 1032 | |
1034 | 1033 | JoyReset(); |
628 | 628 | } else { |
629 | 629 | result = *(fptr->trackimage+fptr->byte); |
630 | 630 | } |
631 | } | |
632 | if (0) | |
633 | { | |
634 | LOG_DISK("nib %4X = %2X\r", fptr->byte, result); | |
635 | 631 | } |
636 | 632 | if (++fptr->byte >= fptr->nibbles) |
637 | 633 | fptr->byte = 0; |
904 | 904 | } |
905 | 905 | |
906 | 906 | CloseHandle(file); |
907 | if (!(size > 0)) | |
907 | if (size <= 0) | |
908 | 908 | DeleteFile(imagefilename); |
909 | 909 | |
910 | 910 | return IMAGE_ERROR_BAD_SIZE; // HACK: MAGIC # 2 |
844 | 844 | |
845 | 845 | bool MemCheckSLOTCXROM() |
846 | 846 | { |
847 | return SW_SLOTCXROM ? true : false; | |
847 | return SW_SLOTCXROM != NULL || false; | |
848 | 848 | } |
849 | 849 | |
850 | 850 | //=========================================================================== |
2163 | 2163 | |
2164 | 2164 | bool VideoGetSW80COL() |
2165 | 2165 | { |
2166 | return SW_80COL ? true : false; | |
2166 | return SW_80COL != NULL || false; | |
2167 | 2167 | } |
2168 | 2168 | |
2169 | 2169 | //=========================================================================== |
2170 | 2170 | |
2171 | 2171 | DWORD VideoGetSnapshot(SS_IO_Video* pSS) |
2172 | 2172 | { |
2173 | pSS->bAltCharSet = !(g_nAltCharSetOffset == 0); | |
2173 | pSS->bAltCharSet = g_nAltCharSetOffset != 0; | |
2174 | 2174 | pSS->dwVidMode = vidmode; |
2175 | 2175 | return 0; |
2176 | 2176 | } |
224 | 224 | ret = [lalerte runModal] ; |
225 | 225 | [lalerte release] ; |
226 | 226 | switch (ret) { |
227 | case NSAlertFirstButtonReturn : return NSAlertDefaultReturn ; | |
228 | break ; | |
229 | case NSAlertSecondButtonReturn: return NSAlertAlternateReturn ; | |
230 | break ; | |
231 | default : return NSAlertOtherReturn ; | |
232 | } ; | |
227 | case NSAlertFirstButtonReturn: | |
228 | return NSAlertDefaultReturn; | |
229 | case NSAlertSecondButtonReturn: | |
230 | return NSAlertAlternateReturn; | |
231 | }; | |
232 | return NSAlertOtherReturn; | |
233 | 233 | } |
234 | 234 | |
235 | 235 | @end |