1 /***************************************************************************
2 
3   inptport.c
4 
5   Input ports handling
6 
7 TODO:	remove the 1 analog device per port limitation
8 		support for inputports producing interrupts
9 		support for extra "real" hardware (PC throttle's, spinners etc)
10 
11 ***************************************************************************/
12 
13 #include "driver.h"
14 #include <math.h>
15 
16 #ifdef MAME_NET
17 #include "network.h"
18 
19 static unsigned short input_port_defaults[MAX_INPUT_PORTS];
20 static int default_player;
21 static int analog_player_port[MAX_INPUT_PORTS];
22 #endif /* MAME_NET */
23 
24 /* Use the MRU code for 4way joysticks */
25 #define MRU_JOYSTICK
26 
27 /* header identifying the version of the game.cfg file */
28 /* mame 0.36b11 */
29 #define MAMECFGSTRING_V5 "MAMECFG\5"
30 #define MAMEDEFSTRING_V5 "MAMEDEF\4"
31 
32 /* mame 0.36b12 with multi key/joy extension */
33 #define MAMECFGSTRING_V6 "MAMECFG\6"
34 #define MAMEDEFSTRING_V6 "MAMEDEF\5"
35 
36 /* mame 0.36b13 with and/or/not combination */
37 #define MAMECFGSTRING_V7 "MAMECFG\7"
38 #define MAMEDEFSTRING_V7 "MAMEDEF\6"
39 
40 /* mame 0.36b16 with key/joy merge */
41 #define MAMECFGSTRING_V8 "MAMECFG\x8"
42 #define MAMEDEFSTRING_V8 "MAMEDEF\7"
43 
44 extern void *record;
45 extern void *playback;
46 
47 extern unsigned int dispensed_tickets;
48 extern unsigned int coins[COIN_COUNTERS];
49 extern unsigned int lastcoin[COIN_COUNTERS];
50 extern unsigned int coinlockedout[COIN_COUNTERS];
51 
52 static unsigned short input_port_value[MAX_INPUT_PORTS];
53 static unsigned short input_vblank[MAX_INPUT_PORTS];
54 
55 /* Assuming a maxium of one analog input device per port BW 101297 */
56 static struct InputPort *input_analog[MAX_INPUT_PORTS];
57 static int input_analog_current_value[MAX_INPUT_PORTS],input_analog_previous_value[MAX_INPUT_PORTS];
58 static int input_analog_init[MAX_INPUT_PORTS];
59 
60 static int mouse_delta_x[OSD_MAX_JOY_ANALOG], mouse_delta_y[OSD_MAX_JOY_ANALOG];
61 static int analog_current_x[OSD_MAX_JOY_ANALOG], analog_current_y[OSD_MAX_JOY_ANALOG];
62 static int analog_previous_x[OSD_MAX_JOY_ANALOG], analog_previous_y[OSD_MAX_JOY_ANALOG];
63 
64 #ifdef ENABLE_AUTOFIRE
65 int seq_pressed_with_autofire(struct InputPort *in, InputSeq *code);
66 #endif
67 
68 
69 /***************************************************************************
70 
71   Configuration load/save
72 
73 ***************************************************************************/
74 
75 /* this must match the enum in inptport.h */
76 char ipdn_defaultstrings[][MAX_DEFSTR_LEN] =
77 {
78 	"Off",
79 	"On",
80 	"No",
81 	"Yes",
82 	"Lives",
83 	"Bonus Life",
84 	"Difficulty",
85 	"Demo Sounds",
86 	"Coinage",
87 	"Coin A",
88 	"Coin B",
89 	"9 Coins/1 Credit",
90 	"8 Coins/1 Credit",
91 	"7 Coins/1 Credit",
92 	"6 Coins/1 Credit",
93 	"5 Coins/1 Credit",
94 	"4 Coins/1 Credit",
95 	"3 Coins/1 Credit",
96 	"8 Coins/3 Credits",
97 	"4 Coins/2 Credits",
98 	"2 Coins/1 Credit",
99 	"5 Coins/3 Credits",
100 	"3 Coins/2 Credits",
101 	"4 Coins/3 Credits",
102 	"4 Coins/4 Credits",
103 	"3 Coins/3 Credits",
104 	"2 Coins/2 Credits",
105 	"1 Coin/1 Credit",
106 	"4 Coins/5 Credits",
107 	"3 Coins/4 Credits",
108 	"2 Coins/3 Credits",
109 	"4 Coins/7 Credits",
110 	"2 Coins/4 Credits",
111 	"1 Coin/2 Credits",
112 	"2 Coins/5 Credits",
113 	"2 Coins/6 Credits",
114 	"1 Coin/3 Credits",
115 	"2 Coins/7 Credits",
116 	"2 Coins/8 Credits",
117 	"1 Coin/4 Credits",
118 	"1 Coin/5 Credits",
119 	"1 Coin/6 Credits",
120 	"1 Coin/7 Credits",
121 	"1 Coin/8 Credits",
122 	"1 Coin/9 Credits",
123 	"Free Play",
124 	"Cabinet",
125 	"Upright",
126 	"Cocktail",
127 	"Flip Screen",
128 	"Service Mode",
129 	"Unused",
130 	"Unknown"
131 };
132 
133 struct ipd inputport_defaults[] =
134 {
135 	{ IPT_UI_CONFIGURE,         "Config Menu",       SEQ_DEF_1(KEYCODE_TAB) },
136 	{ IPT_UI_ON_SCREEN_DISPLAY, "On Screen Display", SEQ_DEF_1(KEYCODE_TILDE) },
137 	{ IPT_UI_PAUSE,             "Pause",             SEQ_DEF_1(KEYCODE_P) },
138 	{ IPT_UI_RESET_MACHINE,     "Reset Game",        SEQ_DEF_1(KEYCODE_F3) },
139 	{ IPT_UI_SHOW_GFX,          "Show Gfx",          SEQ_DEF_1(KEYCODE_F4) },
140 	{ IPT_UI_FRAMESKIP_DEC,     "Frameskip Dec",     SEQ_DEF_1(KEYCODE_F8) },
141 	{ IPT_UI_FRAMESKIP_INC,     "Frameskip Inc",     SEQ_DEF_1(KEYCODE_F9) },
142 	{ IPT_UI_THROTTLE,          "Throttle",          SEQ_DEF_1(KEYCODE_F10) },
143 	{ IPT_UI_SHOW_FPS,          "Show FPS",          SEQ_DEF_5(KEYCODE_F11, CODE_NOT, KEYCODE_LCONTROL, CODE_NOT, KEYCODE_LSHIFT) },
144 	{ IPT_UI_SHOW_PROFILER,     "Show Profiler",     SEQ_DEF_2(KEYCODE_F11, KEYCODE_LSHIFT) },
145 #ifdef MESS
146 	{ IPT_UI_TOGGLE_UI,         "UI Toggle",         SEQ_DEF_1(KEYCODE_SCRLOCK) },
147 #endif
148 	{ IPT_UI_SNAPSHOT,          "Save Snapshot",     SEQ_DEF_1(KEYCODE_F12) },
149 	{ IPT_UI_TOGGLE_CHEAT,      "Toggle Cheat",      SEQ_DEF_1(KEYCODE_F5) },
150 	{ IPT_UI_UP,                "UI Up",             SEQ_DEF_3(KEYCODE_UP, CODE_OR, JOYCODE_1_UP) },
151 	{ IPT_UI_DOWN,              "UI Down",           SEQ_DEF_3(KEYCODE_DOWN, CODE_OR, JOYCODE_1_DOWN) },
152 	{ IPT_UI_LEFT,              "UI Left",           SEQ_DEF_3(KEYCODE_LEFT, CODE_OR, JOYCODE_1_LEFT) },
153 	{ IPT_UI_RIGHT,             "UI Right",          SEQ_DEF_3(KEYCODE_RIGHT, CODE_OR, JOYCODE_1_RIGHT) },
154 	{ IPT_UI_SELECT,            "UI Select",         SEQ_DEF_3(KEYCODE_ENTER, CODE_OR, JOYCODE_1_BUTTON1) },
155 	{ IPT_UI_CANCEL,            "UI Cancel",         SEQ_DEF_1(KEYCODE_ESC) },
156 	{ IPT_UI_PAN_UP,            "Pan Up",            SEQ_DEF_3(KEYCODE_PGUP, CODE_NOT, KEYCODE_LSHIFT) },
157 	{ IPT_UI_PAN_DOWN,          "Pan Down",          SEQ_DEF_3(KEYCODE_PGDN, CODE_NOT, KEYCODE_LSHIFT) },
158 	{ IPT_UI_PAN_LEFT,          "Pan Left",          SEQ_DEF_2(KEYCODE_PGUP, KEYCODE_LSHIFT) },
159 	{ IPT_UI_PAN_RIGHT,         "Pan Right",         SEQ_DEF_2(KEYCODE_PGDN, KEYCODE_LSHIFT) },
160 	{ IPT_START1, "1 Player Start",  SEQ_DEF_1(KEYCODE_1) },
161 	{ IPT_START2, "2 Players Start", SEQ_DEF_1(KEYCODE_2) },
162 	{ IPT_START3, "3 Players Start", SEQ_DEF_1(KEYCODE_3) },
163 	{ IPT_START4, "4 Players Start", SEQ_DEF_1(KEYCODE_4) },
164 	{ IPT_COIN1,  "Coin 1",          SEQ_DEF_1(KEYCODE_5) },
165 	{ IPT_COIN2,  "Coin 2",          SEQ_DEF_1(KEYCODE_6) },
166 	{ IPT_COIN3,  "Coin 3",          SEQ_DEF_1(KEYCODE_7) },
167 	{ IPT_COIN4,  "Coin 4",          SEQ_DEF_1(KEYCODE_8) },
168 	{ IPT_SERVICE1, "Service 1",     SEQ_DEF_1(KEYCODE_9) },
169 	{ IPT_SERVICE2, "Service 2",     SEQ_DEF_1(KEYCODE_0) },
170 	{ IPT_SERVICE3, "Service 3",     SEQ_DEF_1(KEYCODE_MINUS) },
171 	{ IPT_SERVICE4, "Service 4",     SEQ_DEF_1(KEYCODE_EQUALS) },
172 #ifndef MESS
173 	{ IPT_TILT,   "Tilt",            SEQ_DEF_1(KEYCODE_T) },
174 #else
175 	{ IPT_TILT,   "Tilt",            SEQ_DEF_0 },
176 #endif
177 
178 	{ IPT_JOYSTICK_UP         | IPF_PLAYER1, "P1 Up",          SEQ_DEF_3(KEYCODE_UP, CODE_OR, JOYCODE_1_UP)    },
179 	{ IPT_JOYSTICK_DOWN       | IPF_PLAYER1, "P1 Down",        SEQ_DEF_3(KEYCODE_DOWN, CODE_OR, JOYCODE_1_DOWN)  },
180 	{ IPT_JOYSTICK_LEFT       | IPF_PLAYER1, "P1 Left",        SEQ_DEF_3(KEYCODE_LEFT, CODE_OR, JOYCODE_1_LEFT)  },
181 	{ IPT_JOYSTICK_RIGHT      | IPF_PLAYER1, "P1 Right",       SEQ_DEF_3(KEYCODE_RIGHT, CODE_OR, JOYCODE_1_RIGHT) },
182 	{ IPT_BUTTON1             | IPF_PLAYER1, "P1 Button 1",    SEQ_DEF_3(KEYCODE_LCONTROL, CODE_OR, JOYCODE_1_BUTTON1) },
183 	{ IPT_BUTTON2             | IPF_PLAYER1, "P1 Button 2",    SEQ_DEF_3(KEYCODE_LALT, CODE_OR, JOYCODE_1_BUTTON2) },
184 	{ IPT_BUTTON3             | IPF_PLAYER1, "P1 Button 3",    SEQ_DEF_3(KEYCODE_SPACE, CODE_OR, JOYCODE_1_BUTTON3) },
185 	{ IPT_BUTTON4             | IPF_PLAYER1, "P1 Button 4",    SEQ_DEF_3(KEYCODE_LSHIFT, CODE_OR, JOYCODE_1_BUTTON4) },
186 	{ IPT_BUTTON5             | IPF_PLAYER1, "P1 Button 5",    SEQ_DEF_3(KEYCODE_Z, CODE_OR, JOYCODE_1_BUTTON5) },
187 	{ IPT_BUTTON6             | IPF_PLAYER1, "P1 Button 6",    SEQ_DEF_3(KEYCODE_X, CODE_OR, JOYCODE_1_BUTTON6) },
188 	{ IPT_BUTTON7             | IPF_PLAYER1, "P1 Button 7",    SEQ_DEF_1(KEYCODE_C) },
189 	{ IPT_BUTTON8             | IPF_PLAYER1, "P1 Button 8",    SEQ_DEF_1(KEYCODE_V) },
190 	{ IPT_BUTTON9             | IPF_PLAYER1, "P1 Button 9",    SEQ_DEF_1(KEYCODE_B) },
191 	{ IPT_BUTTON10            | IPF_PLAYER1, "P1 Button 10",   SEQ_DEF_1(KEYCODE_N) },
192 	{ IPT_JOYSTICKRIGHT_UP    | IPF_PLAYER1, "P1 Right/Up",    SEQ_DEF_3(KEYCODE_I, CODE_OR, JOYCODE_1_BUTTON4) },
193 	{ IPT_JOYSTICKRIGHT_DOWN  | IPF_PLAYER1, "P1 Right/Down",  SEQ_DEF_3(KEYCODE_K, CODE_OR, JOYCODE_1_BUTTON2) },
194 	{ IPT_JOYSTICKRIGHT_LEFT  | IPF_PLAYER1, "P1 Right/Left",  SEQ_DEF_3(KEYCODE_J, CODE_OR, JOYCODE_1_BUTTON3) },
195 	{ IPT_JOYSTICKRIGHT_RIGHT | IPF_PLAYER1, "P1 Right/Right", SEQ_DEF_3(KEYCODE_L, CODE_OR, JOYCODE_1_BUTTON1) },
196 	{ IPT_JOYSTICKLEFT_UP     | IPF_PLAYER1, "P1 Left/Up",     SEQ_DEF_3(KEYCODE_E, CODE_OR, JOYCODE_1_UP) },
197 	{ IPT_JOYSTICKLEFT_DOWN   | IPF_PLAYER1, "P1 Left/Down",   SEQ_DEF_3(KEYCODE_D, CODE_OR, JOYCODE_1_DOWN) },
198 	{ IPT_JOYSTICKLEFT_LEFT   | IPF_PLAYER1, "P1 Left/Left",   SEQ_DEF_3(KEYCODE_S, CODE_OR, JOYCODE_1_LEFT) },
199 	{ IPT_JOYSTICKLEFT_RIGHT  | IPF_PLAYER1, "P1 Left/Right",  SEQ_DEF_3(KEYCODE_F, CODE_OR, JOYCODE_1_RIGHT) },
200 
201 	{ IPT_JOYSTICK_UP         | IPF_PLAYER2, "P2 Up",          SEQ_DEF_3(KEYCODE_R, CODE_OR, JOYCODE_2_UP)    },
202 	{ IPT_JOYSTICK_DOWN       | IPF_PLAYER2, "P2 Down",        SEQ_DEF_3(KEYCODE_F, CODE_OR, JOYCODE_2_DOWN)  },
203 	{ IPT_JOYSTICK_LEFT       | IPF_PLAYER2, "P2 Left",        SEQ_DEF_3(KEYCODE_D, CODE_OR, JOYCODE_2_LEFT)  },
204 	{ IPT_JOYSTICK_RIGHT      | IPF_PLAYER2, "P2 Right",       SEQ_DEF_3(KEYCODE_G, CODE_OR, JOYCODE_2_RIGHT) },
205 	{ IPT_BUTTON1             | IPF_PLAYER2, "P2 Button 1",    SEQ_DEF_3(KEYCODE_A, CODE_OR, JOYCODE_2_BUTTON1) },
206 	{ IPT_BUTTON2             | IPF_PLAYER2, "P2 Button 2",    SEQ_DEF_3(KEYCODE_S, CODE_OR, JOYCODE_2_BUTTON2) },
207 	{ IPT_BUTTON3             | IPF_PLAYER2, "P2 Button 3",    SEQ_DEF_3(KEYCODE_Q, CODE_OR, JOYCODE_2_BUTTON3) },
208 	{ IPT_BUTTON4             | IPF_PLAYER2, "P2 Button 4",    SEQ_DEF_3(KEYCODE_W, CODE_OR, JOYCODE_2_BUTTON4) },
209 	{ IPT_BUTTON5             | IPF_PLAYER2, "P2 Button 5",    SEQ_DEF_1(JOYCODE_2_BUTTON5) },
210 	{ IPT_BUTTON6             | IPF_PLAYER2, "P2 Button 6",    SEQ_DEF_1(JOYCODE_2_BUTTON6) },
211 	{ IPT_BUTTON7             | IPF_PLAYER2, "P2 Button 7",    SEQ_DEF_0 },
212 	{ IPT_BUTTON8             | IPF_PLAYER2, "P2 Button 8",    SEQ_DEF_0 },
213 	{ IPT_BUTTON9             | IPF_PLAYER2, "P2 Button 9",    SEQ_DEF_0 },
214 	{ IPT_BUTTON10            | IPF_PLAYER2, "P2 Button 10",   SEQ_DEF_0 },
215 	{ IPT_JOYSTICKRIGHT_UP    | IPF_PLAYER2, "P2 Right/Up",    SEQ_DEF_0 },
216 	{ IPT_JOYSTICKRIGHT_DOWN  | IPF_PLAYER2, "P2 Right/Down",  SEQ_DEF_0 },
217 	{ IPT_JOYSTICKRIGHT_LEFT  | IPF_PLAYER2, "P2 Right/Left",  SEQ_DEF_0 },
218 	{ IPT_JOYSTICKRIGHT_RIGHT | IPF_PLAYER2, "P2 Right/Right", SEQ_DEF_0 },
219 	{ IPT_JOYSTICKLEFT_UP     | IPF_PLAYER2, "P2 Left/Up",     SEQ_DEF_0 },
220 	{ IPT_JOYSTICKLEFT_DOWN   | IPF_PLAYER2, "P2 Left/Down",   SEQ_DEF_0 },
221 	{ IPT_JOYSTICKLEFT_LEFT   | IPF_PLAYER2, "P2 Left/Left",   SEQ_DEF_0 },
222 	{ IPT_JOYSTICKLEFT_RIGHT  | IPF_PLAYER2, "P2 Left/Right",  SEQ_DEF_0 },
223 
224 	{ IPT_JOYSTICK_UP         | IPF_PLAYER3, "P3 Up",          SEQ_DEF_3(KEYCODE_I, CODE_OR, JOYCODE_3_UP)    },
225 	{ IPT_JOYSTICK_DOWN       | IPF_PLAYER3, "P3 Down",        SEQ_DEF_3(KEYCODE_K, CODE_OR, JOYCODE_3_DOWN)  },
226 	{ IPT_JOYSTICK_LEFT       | IPF_PLAYER3, "P3 Left",        SEQ_DEF_3(KEYCODE_J, CODE_OR, JOYCODE_3_LEFT)  },
227 	{ IPT_JOYSTICK_RIGHT      | IPF_PLAYER3, "P3 Right",       SEQ_DEF_3(KEYCODE_L, CODE_OR, JOYCODE_3_RIGHT) },
228 	{ IPT_BUTTON1             | IPF_PLAYER3, "P3 Button 1",    SEQ_DEF_3(KEYCODE_RCONTROL, CODE_OR, JOYCODE_3_BUTTON1) },
229 	{ IPT_BUTTON2             | IPF_PLAYER3, "P3 Button 2",    SEQ_DEF_3(KEYCODE_RSHIFT, CODE_OR, JOYCODE_3_BUTTON2) },
230 	{ IPT_BUTTON3             | IPF_PLAYER3, "P3 Button 3",    SEQ_DEF_3(KEYCODE_ENTER, CODE_OR, JOYCODE_3_BUTTON3) },
231 	{ IPT_BUTTON4             | IPF_PLAYER3, "P3 Button 4",    SEQ_DEF_1(JOYCODE_3_BUTTON4) },
232 
233 	{ IPT_JOYSTICK_UP         | IPF_PLAYER4, "P4 Up",          SEQ_DEF_1(JOYCODE_4_UP) },
234 	{ IPT_JOYSTICK_DOWN       | IPF_PLAYER4, "P4 Down",        SEQ_DEF_1(JOYCODE_4_DOWN) },
235 	{ IPT_JOYSTICK_LEFT       | IPF_PLAYER4, "P4 Left",        SEQ_DEF_1(JOYCODE_4_LEFT) },
236 	{ IPT_JOYSTICK_RIGHT      | IPF_PLAYER4, "P4 Right",       SEQ_DEF_1(JOYCODE_4_RIGHT) },
237 	{ IPT_BUTTON1             | IPF_PLAYER4, "P4 Button 1",    SEQ_DEF_1(JOYCODE_4_BUTTON1) },
238 	{ IPT_BUTTON2             | IPF_PLAYER4, "P4 Button 2",    SEQ_DEF_1(JOYCODE_4_BUTTON2) },
239 	{ IPT_BUTTON3             | IPF_PLAYER4, "P4 Button 3",    SEQ_DEF_1(JOYCODE_4_BUTTON3) },
240 	{ IPT_BUTTON4             | IPF_PLAYER4, "P4 Button 4",    SEQ_DEF_1(JOYCODE_4_BUTTON4) },
241 
242 	{ IPT_PEDAL	                | IPF_PLAYER1, "Pedal 1",        SEQ_DEF_3(KEYCODE_LCONTROL, CODE_OR, JOYCODE_1_BUTTON1) },
243 	{ (IPT_PEDAL+IPT_EXTENSION) | IPF_PLAYER1, "P1 Auto Release <Y/N>", SEQ_DEF_1(KEYCODE_Y) },
244 	{ IPT_PEDAL                 | IPF_PLAYER2, "Pedal 2",        SEQ_DEF_3(KEYCODE_A, CODE_OR, JOYCODE_2_BUTTON1) },
245 	{ (IPT_PEDAL+IPT_EXTENSION) | IPF_PLAYER2, "P2 Auto Release <Y/N>", SEQ_DEF_1(KEYCODE_Y) },
246 	{ IPT_PEDAL                 | IPF_PLAYER3, "Pedal 3",        SEQ_DEF_3(KEYCODE_RCONTROL, CODE_OR, JOYCODE_3_BUTTON1) },
247 	{ (IPT_PEDAL+IPT_EXTENSION) | IPF_PLAYER3, "P3 Auto Release <Y/N>", SEQ_DEF_1(KEYCODE_Y) },
248 	{ IPT_PEDAL                 | IPF_PLAYER4, "Pedal 4",        SEQ_DEF_1(JOYCODE_4_BUTTON1) },
249 	{ (IPT_PEDAL+IPT_EXTENSION) | IPF_PLAYER4, "P4 Auto Release <Y/N>", SEQ_DEF_1(KEYCODE_Y) },
250 
251 	{ IPT_PADDLE | IPF_PLAYER1,  "Paddle",        SEQ_DEF_3(KEYCODE_LEFT, CODE_OR, JOYCODE_1_LEFT) },
252 	{ (IPT_PADDLE | IPF_PLAYER1)+IPT_EXTENSION,             "Paddle",        SEQ_DEF_3(KEYCODE_RIGHT, CODE_OR, JOYCODE_1_RIGHT)  },
253 	{ IPT_PADDLE | IPF_PLAYER2,  "Paddle 2",      SEQ_DEF_3(KEYCODE_D, CODE_OR, JOYCODE_2_LEFT) },
254 	{ (IPT_PADDLE | IPF_PLAYER2)+IPT_EXTENSION,             "Paddle 2",      SEQ_DEF_3(KEYCODE_G, CODE_OR, JOYCODE_2_RIGHT) },
255 	{ IPT_PADDLE | IPF_PLAYER3,  "Paddle 3",      SEQ_DEF_3(KEYCODE_J, CODE_OR, JOYCODE_3_LEFT) },
256 	{ (IPT_PADDLE | IPF_PLAYER3)+IPT_EXTENSION,             "Paddle 3",      SEQ_DEF_3(KEYCODE_L, CODE_OR, JOYCODE_3_RIGHT) },
257 	{ IPT_PADDLE | IPF_PLAYER4,  "Paddle 4",      SEQ_DEF_1(JOYCODE_4_LEFT) },
258 	{ (IPT_PADDLE | IPF_PLAYER4)+IPT_EXTENSION,             "Paddle 4",      SEQ_DEF_1(JOYCODE_4_RIGHT) },
259 	{ IPT_PADDLE_V | IPF_PLAYER1,  "Paddle V",          SEQ_DEF_3(KEYCODE_UP, CODE_OR, JOYCODE_1_UP) },
260 	{ (IPT_PADDLE_V | IPF_PLAYER1)+IPT_EXTENSION,             "Paddle V",          SEQ_DEF_3(KEYCODE_DOWN, CODE_OR, JOYCODE_1_DOWN) },
261 	{ IPT_PADDLE_V | IPF_PLAYER2,  "Paddle V 2",        SEQ_DEF_3(KEYCODE_R, CODE_OR, JOYCODE_2_UP) },
262 	{ (IPT_PADDLE_V | IPF_PLAYER2)+IPT_EXTENSION,             "Paddle V 2",      SEQ_DEF_3(KEYCODE_F, CODE_OR, JOYCODE_2_DOWN) },
263 	{ IPT_PADDLE_V | IPF_PLAYER3,  "Paddle V 3",        SEQ_DEF_3(KEYCODE_I, CODE_OR, JOYCODE_3_UP) },
264 	{ (IPT_PADDLE_V | IPF_PLAYER3)+IPT_EXTENSION,             "Paddle V 3",      SEQ_DEF_3(KEYCODE_K, CODE_OR, JOYCODE_3_DOWN) },
265 	{ IPT_PADDLE_V | IPF_PLAYER4,  "Paddle V 4",        SEQ_DEF_1(JOYCODE_4_UP) },
266 	{ (IPT_PADDLE_V | IPF_PLAYER4)+IPT_EXTENSION,             "Paddle V 4",      SEQ_DEF_1(JOYCODE_4_DOWN) },
267 	{ IPT_DIAL | IPF_PLAYER1,    "Dial",          SEQ_DEF_3(KEYCODE_LEFT, CODE_OR, JOYCODE_1_LEFT) },
268 	{ (IPT_DIAL | IPF_PLAYER1)+IPT_EXTENSION,               "Dial",          SEQ_DEF_3(KEYCODE_RIGHT, CODE_OR, JOYCODE_1_RIGHT) },
269 	{ IPT_DIAL | IPF_PLAYER2,    "Dial 2",        SEQ_DEF_3(KEYCODE_D, CODE_OR, JOYCODE_2_LEFT) },
270 	{ (IPT_DIAL | IPF_PLAYER2)+IPT_EXTENSION,               "Dial 2",      SEQ_DEF_3(KEYCODE_G, CODE_OR, JOYCODE_2_RIGHT) },
271 	{ IPT_DIAL | IPF_PLAYER3,    "Dial 3",        SEQ_DEF_3(KEYCODE_J, CODE_OR, JOYCODE_3_LEFT) },
272 	{ (IPT_DIAL | IPF_PLAYER3)+IPT_EXTENSION,               "Dial 3",      SEQ_DEF_3(KEYCODE_L, CODE_OR, JOYCODE_3_RIGHT) },
273 	{ IPT_DIAL | IPF_PLAYER4,    "Dial 4",        SEQ_DEF_1(JOYCODE_4_LEFT) },
274 	{ (IPT_DIAL | IPF_PLAYER4)+IPT_EXTENSION,               "Dial 4",      SEQ_DEF_1(JOYCODE_4_RIGHT) },
275 	{ IPT_DIAL_V | IPF_PLAYER1,  "Dial V",          SEQ_DEF_3(KEYCODE_UP, CODE_OR, JOYCODE_1_UP) },
276 	{ (IPT_DIAL_V | IPF_PLAYER1)+IPT_EXTENSION,             "Dial V",          SEQ_DEF_3(KEYCODE_DOWN, CODE_OR, JOYCODE_1_DOWN) },
277 	{ IPT_DIAL_V | IPF_PLAYER2,  "Dial V 2",        SEQ_DEF_3(KEYCODE_R, CODE_OR, JOYCODE_2_UP) },
278 	{ (IPT_DIAL_V | IPF_PLAYER2)+IPT_EXTENSION,             "Dial V 2",      SEQ_DEF_3(KEYCODE_F, CODE_OR, JOYCODE_2_DOWN) },
279 	{ IPT_DIAL_V | IPF_PLAYER3,  "Dial V 3",        SEQ_DEF_3(KEYCODE_I, CODE_OR, JOYCODE_3_UP) },
280 	{ (IPT_DIAL_V | IPF_PLAYER3)+IPT_EXTENSION,             "Dial V 3",      SEQ_DEF_3(KEYCODE_K, CODE_OR, JOYCODE_3_DOWN) },
281 	{ IPT_DIAL_V | IPF_PLAYER4,  "Dial V 4",        SEQ_DEF_1(JOYCODE_4_UP) },
282 	{ (IPT_DIAL_V | IPF_PLAYER4)+IPT_EXTENSION,             "Dial V 4",      SEQ_DEF_1(JOYCODE_4_DOWN) },
283 
284 	{ IPT_TRACKBALL_X | IPF_PLAYER1, "Track X",   SEQ_DEF_3(KEYCODE_LEFT, CODE_OR, JOYCODE_1_LEFT) },
285 	{ (IPT_TRACKBALL_X | IPF_PLAYER1)+IPT_EXTENSION,                 "Track X",   SEQ_DEF_3(KEYCODE_RIGHT, CODE_OR, JOYCODE_1_RIGHT) },
286 	{ IPT_TRACKBALL_X | IPF_PLAYER2, "Track X 2", SEQ_DEF_3(KEYCODE_D, CODE_OR, JOYCODE_2_LEFT) },
287 	{ (IPT_TRACKBALL_X | IPF_PLAYER2)+IPT_EXTENSION,                 "Track X 2", SEQ_DEF_3(KEYCODE_G, CODE_OR, JOYCODE_2_RIGHT) },
288 	{ IPT_TRACKBALL_X | IPF_PLAYER3, "Track X 3", SEQ_DEF_3(KEYCODE_J, CODE_OR, JOYCODE_3_LEFT) },
289 	{ (IPT_TRACKBALL_X | IPF_PLAYER3)+IPT_EXTENSION,                 "Track X 3", SEQ_DEF_3(KEYCODE_L, CODE_OR, JOYCODE_3_RIGHT) },
290 	{ IPT_TRACKBALL_X | IPF_PLAYER4, "Track X 4", SEQ_DEF_1(JOYCODE_4_LEFT) },
291 	{ (IPT_TRACKBALL_X | IPF_PLAYER4)+IPT_EXTENSION,                 "Track X 4", SEQ_DEF_1(JOYCODE_4_RIGHT) },
292 
293 	{ IPT_TRACKBALL_Y | IPF_PLAYER1, "Track Y",   SEQ_DEF_3(KEYCODE_UP, CODE_OR, JOYCODE_1_UP) },
294 	{ (IPT_TRACKBALL_Y | IPF_PLAYER1)+IPT_EXTENSION,                 "Track Y",   SEQ_DEF_3(KEYCODE_DOWN, CODE_OR, JOYCODE_1_DOWN) },
295 	{ IPT_TRACKBALL_Y | IPF_PLAYER2, "Track Y 2", SEQ_DEF_3(KEYCODE_R, CODE_OR, JOYCODE_2_UP) },
296 	{ (IPT_TRACKBALL_Y | IPF_PLAYER2)+IPT_EXTENSION,                 "Track Y 2", SEQ_DEF_3(KEYCODE_F, CODE_OR, JOYCODE_2_DOWN) },
297 	{ IPT_TRACKBALL_Y | IPF_PLAYER3, "Track Y 3", SEQ_DEF_3(KEYCODE_I, CODE_OR, JOYCODE_3_UP) },
298 	{ (IPT_TRACKBALL_Y | IPF_PLAYER3)+IPT_EXTENSION,                 "Track Y 3", SEQ_DEF_3(KEYCODE_K, CODE_OR, JOYCODE_3_DOWN) },
299 	{ IPT_TRACKBALL_Y | IPF_PLAYER4, "Track Y 4", SEQ_DEF_1(JOYCODE_4_UP) },
300 	{ (IPT_TRACKBALL_Y | IPF_PLAYER4)+IPT_EXTENSION,                 "Track Y 4", SEQ_DEF_1(JOYCODE_4_DOWN) },
301 
302 	{ IPT_AD_STICK_X | IPF_PLAYER1, "AD Stick X",   SEQ_DEF_3(KEYCODE_LEFT, CODE_OR, JOYCODE_1_LEFT) },
303 	{ (IPT_AD_STICK_X | IPF_PLAYER1)+IPT_EXTENSION,                "AD Stick X",   SEQ_DEF_3(KEYCODE_RIGHT, CODE_OR, JOYCODE_1_RIGHT) },
304 	{ IPT_AD_STICK_X | IPF_PLAYER2, "AD Stick X 2", SEQ_DEF_3(KEYCODE_D, CODE_OR, JOYCODE_2_LEFT) },
305 	{ (IPT_AD_STICK_X | IPF_PLAYER2)+IPT_EXTENSION,                "AD Stick X 2", SEQ_DEF_3(KEYCODE_G, CODE_OR, JOYCODE_2_RIGHT) },
306 	{ IPT_AD_STICK_X | IPF_PLAYER3, "AD Stick X 3", SEQ_DEF_3(KEYCODE_J, CODE_OR, JOYCODE_3_LEFT) },
307 	{ (IPT_AD_STICK_X | IPF_PLAYER3)+IPT_EXTENSION,                "AD Stick X 3", SEQ_DEF_3(KEYCODE_L, CODE_OR, JOYCODE_3_RIGHT) },
308 	{ IPT_AD_STICK_X | IPF_PLAYER4, "AD Stick X 4", SEQ_DEF_1(JOYCODE_4_LEFT) },
309 	{ (IPT_AD_STICK_X | IPF_PLAYER4)+IPT_EXTENSION,                "AD Stick X 4", SEQ_DEF_1(JOYCODE_4_RIGHT) },
310 
311 	{ IPT_AD_STICK_Y | IPF_PLAYER1, "AD Stick Y",   SEQ_DEF_3(KEYCODE_UP, CODE_OR, JOYCODE_1_UP) },
312 	{ (IPT_AD_STICK_Y | IPF_PLAYER1)+IPT_EXTENSION,                "AD Stick Y",   SEQ_DEF_3(KEYCODE_DOWN, CODE_OR, JOYCODE_1_DOWN) },
313 	{ IPT_AD_STICK_Y | IPF_PLAYER2, "AD Stick Y 2", SEQ_DEF_3(KEYCODE_R, CODE_OR, JOYCODE_2_UP) },
314 	{ (IPT_AD_STICK_Y | IPF_PLAYER2)+IPT_EXTENSION,                "AD Stick Y 2", SEQ_DEF_3(KEYCODE_F, CODE_OR, JOYCODE_2_DOWN) },
315 	{ IPT_AD_STICK_Y | IPF_PLAYER3, "AD Stick Y 3", SEQ_DEF_3(KEYCODE_I, CODE_OR, JOYCODE_3_UP) },
316 	{ (IPT_AD_STICK_Y | IPF_PLAYER3)+IPT_EXTENSION,                "AD Stick Y 3", SEQ_DEF_3(KEYCODE_K, CODE_OR, JOYCODE_3_DOWN) },
317 	{ IPT_AD_STICK_Y | IPF_PLAYER4, "AD Stick Y 4", SEQ_DEF_1(JOYCODE_4_UP) },
318 	{ (IPT_AD_STICK_Y | IPF_PLAYER4)+IPT_EXTENSION,                "AD Stick Y 4", SEQ_DEF_1(JOYCODE_4_DOWN) },
319 
320 	{ IPT_UNKNOWN,             "UNKNOWN",         SEQ_DEF_0 },
321 	{ IPT_END,                 0,                 SEQ_DEF_0 }	/* returned when there is no match */
322 };
323 
324 struct ipd inputport_defaults_backup[sizeof(inputport_defaults)/sizeof(struct ipd)];
325 
326 /***************************************************************************/
327 /* Generic IO */
328 
readint(void * f,UINT32 * num)329 static int readint(void *f,UINT32 *num)
330 {
331 	unsigned i;
332 
333 	*num = 0;
334 	for (i = 0;i < sizeof(UINT32);i++)
335 	{
336 		unsigned char c;
337 
338 
339 		*num <<= 8;
340 		if (osd_fread(f,&c,1) != 1)
341 			return -1;
342 		*num |= c;
343 	}
344 
345 	return 0;
346 }
347 
writeint(void * f,UINT32 num)348 static void writeint(void *f,UINT32 num)
349 {
350 	unsigned i;
351 
352 	for (i = 0;i < sizeof(UINT32);i++)
353 	{
354 		unsigned char c;
355 
356 
357 		c = (num >> 8 * (sizeof(UINT32)-1)) & 0xff;
358 		osd_fwrite(f,&c,1);
359 		num <<= 8;
360 	}
361 }
362 
readword(void * f,UINT16 * num)363 static int readword(void *f,UINT16 *num)
364 {
365 	unsigned i;
366 	int res;
367 
368 	res = 0;
369 	for (i = 0;i < sizeof(UINT16);i++)
370 	{
371 		unsigned char c;
372 
373 
374 		res <<= 8;
375 		if (osd_fread(f,&c,1) != 1)
376 			return -1;
377 		res |= c;
378 	}
379 
380 	*num = res;
381 	return 0;
382 }
383 
writeword(void * f,UINT16 num)384 static void writeword(void *f,UINT16 num)
385 {
386 	unsigned i;
387 
388 	for (i = 0;i < sizeof(UINT16);i++)
389 	{
390 		unsigned char c;
391 
392 
393 		c = (num >> 8 * (sizeof(UINT16)-1)) & 0xff;
394 		osd_fwrite(f,&c,1);
395 		num <<= 8;
396 	}
397 }
398 
399 #ifndef NOLEGACY
400 #include "legacy.h"
401 #endif
402 
seq_read_ver_8(void * f,InputSeq * seq)403 static int seq_read_ver_8(void* f, InputSeq* seq)
404 {
405 	int j,len;
406 	UINT32 i;
407 	UINT16 w;
408 
409 	if (readword(f,&w) != 0)
410 		return -1;
411 
412 	len = w;
413 	seq_set_0(seq);
414 	for(j=0;j<len;++j)
415 	{
416 		if (readint(f,&i) != 0)
417  			return -1;
418 		(*seq)[j] = savecode_to_code(i);
419  	}
420 
421  	return 0;
422   }
423 
seq_read(void * f,InputSeq * seq,int ver)424 static int seq_read(void* f, InputSeq* seq, int ver)
425   {
426 #ifdef NOLEGACY
427 	if (ver==8)
428 		return seq_read_ver_8(f,seq);
429 #else
430 	switch (ver) {
431 		case 5 : return seq_read_ver_5(f,seq);
432 		case 6 : return seq_read_ver_6(f,seq);
433 		case 7 : return seq_read_ver_7(f,seq);
434 		case 8 : return seq_read_ver_8(f,seq);
435 	}
436 #endif
437 	return -1;
438   }
439 
seq_write(void * f,InputSeq * seq)440 static void seq_write(void* f, InputSeq* seq)
441   {
442 	int j,len;
443         for(len=0;len<SEQ_MAX;++len)
444 		if ((*seq)[len] == CODE_NONE)
445 			break;
446 	writeword(f,len);
447 	for(j=0;j<len;++j)
448 		writeint(f, code_to_savecode( (*seq)[j] ));
449   }
450 
451 /***************************************************************************/
452 /* Load */
453 
load_default_keys(void)454 static void load_default_keys(void)
455 {
456 	void *f;
457 
458 
459 	osd_customize_inputport_defaults(inputport_defaults);
460 	memcpy(inputport_defaults_backup,inputport_defaults,sizeof(inputport_defaults));
461 
462 	if ((f = osd_fopen("default",0,OSD_FILETYPE_CONFIG,0)) != 0)
463 	{
464 		char buf[8];
465 		int version;
466 
467 		/* read header */
468 		if (osd_fread(f,buf,8) != 8)
469 			goto getout;
470 
471 		if (memcmp(buf,MAMEDEFSTRING_V5,8) == 0)
472 			version = 5;
473 		else if (memcmp(buf,MAMEDEFSTRING_V6,8) == 0)
474 			version = 6;
475 		else if (memcmp(buf,MAMEDEFSTRING_V7,8) == 0)
476 			version = 7;
477 		else if (memcmp(buf,MAMEDEFSTRING_V8,8) == 0)
478 			version = 8;
479 		else
480 			goto getout;	/* header invalid */
481 
482 		for (;;)
483 		{
484 			UINT32 type;
485 			InputSeq def_seq;
486 			InputSeq seq;
487 			int i;
488 
489 			if (readint(f,&type) != 0)
490 				goto getout;
491 
492 			if (seq_read(f,&def_seq,version)!=0)
493 				goto getout;
494 			if (seq_read(f,&seq,version)!=0)
495 				goto getout;
496 
497 			i = 0;
498 			while (inputport_defaults[i].type != IPT_END)
499 			{
500 				if (inputport_defaults[i].type == type)
501 				{
502 					/* load stored settings only if the default hasn't changed */
503 					if (seq_cmp(&inputport_defaults[i].seq,&def_seq)==0)
504 						seq_copy(&inputport_defaults[i].seq,&seq);
505 				}
506 
507 				i++;
508 			}
509 		}
510 
511 getout:
512 		osd_fclose(f);
513 	}
514 }
515 
save_default_keys(void)516 static void save_default_keys(void)
517 {
518 	void *f;
519 
520 
521 	if ((f = osd_fopen("default",0,OSD_FILETYPE_CONFIG,1)) != 0)
522 	{
523 		int i;
524 
525 
526 		/* write header */
527 		osd_fwrite(f,MAMEDEFSTRING_V8,8);
528 
529 		i = 0;
530 		while (inputport_defaults[i].type != IPT_END)
531 		{
532 			writeint(f,inputport_defaults[i].type);
533 
534 			seq_write(f,&inputport_defaults_backup[i].seq);
535 			seq_write(f,&inputport_defaults[i].seq);
536 
537 			i++;
538 		}
539 
540 		osd_fclose(f);
541 	}
542 	memcpy(inputport_defaults,inputport_defaults_backup,sizeof(inputport_defaults_backup));
543 }
544 
input_port_read_ver_8(void * f,struct InputPort * in)545 static int input_port_read_ver_8(void *f,struct InputPort *in)
546 {
547 	UINT32 i;
548 	UINT16 w;
549 	if (readint(f,&i) != 0)
550 		return -1;
551 	in->type = i;
552 
553 	if (readword(f,&w) != 0)
554 		return -1;
555 	in->mask = w;
556 
557 	if (readword(f,&w) != 0)
558 		return -1;
559 	in->default_value = w;
560 
561 	if (seq_read_ver_8(f,&in->seq) != 0)
562 		return -1;
563 
564 	return 0;
565 }
566 
input_port_read(void * f,struct InputPort * in,int ver)567 static int input_port_read(void *f,struct InputPort *in, int ver)
568 {
569 #ifdef NOLEGACY
570 	if (ver==8)
571 		return input_port_read_ver_8(f,in);
572 #else
573 	switch (ver) {
574 		case 5 : return	input_port_read_ver_5(f,in);
575 		case 6 : return	input_port_read_ver_6(f,in);
576 		case 7 : return	input_port_read_ver_7(f,in);
577 		case 8 : return	input_port_read_ver_8(f,in);
578 	}
579 #endif
580 	return -1;
581 }
582 
input_port_write(void * f,struct InputPort * in)583 static void input_port_write(void *f,struct InputPort *in)
584 {
585 	writeint(f,in->type);
586 	writeword(f,in->mask);
587 	writeword(f,in->default_value);
588 	seq_write(f,&in->seq);
589 }
590 
591 
load_input_port_settings(void)592 int load_input_port_settings(void)
593 {
594 	void *f;
595 #ifdef MAME_NET
596     struct InputPort *in;
597     int port, player;
598 #endif /* MAME_NET */
599 
600 
601 	load_default_keys();
602 
603 	if ((f = osd_fopen(Machine->gamedrv->name,0,OSD_FILETYPE_CONFIG,0)) != 0)
604 	{
605 #ifndef MAME_NET
606 		struct InputPort *in;
607 #endif
608 		unsigned int total,savedtotal;
609 		char buf[8];
610 		int i;
611 		int version;
612 
613 		in = Machine->input_ports_default;
614 
615 		/* calculate the size of the array */
616 		total = 0;
617 		while (in->type != IPT_END)
618 		{
619 			total++;
620 			in++;
621 		}
622 
623 		/* read header */
624 		if (osd_fread(f,buf,8) != 8)
625 			goto getout;
626 
627 		if (memcmp(buf,MAMECFGSTRING_V5,8) == 0)
628 			version = 5;
629 		else if (memcmp(buf,MAMECFGSTRING_V6,8) == 0)
630 			version = 6;
631 		else if (memcmp(buf,MAMECFGSTRING_V7,8) == 0)
632 			version = 7;
633 		else if (memcmp(buf,MAMECFGSTRING_V8,8) == 0)
634 			version = 8;
635 		else
636 			goto getout;	/* header invalid */
637 
638 		/* read array size */
639 		if (readint(f,&savedtotal) != 0)
640 			goto getout;
641 		if (total != savedtotal)
642 			goto getout;	/* different size */
643 
644 		/* read the original settings and compare them with the ones defined in the driver */
645 		in = Machine->input_ports_default;
646 		while (in->type != IPT_END)
647 		{
648 			struct InputPort saved;
649 
650 			if (input_port_read(f,&saved,version) != 0)
651 				goto getout;
652 
653 			if (in->mask != saved.mask ||
654 				in->default_value != saved.default_value ||
655 				in->type != saved.type ||
656 				seq_cmp(&in->seq,&saved.seq) !=0 )
657 			goto getout;	/* the default values are different */
658 
659 			in++;
660 		}
661 
662 		/* read the current settings */
663 		in = Machine->input_ports;
664 		while (in->type != IPT_END)
665 		{
666 			if (input_port_read(f,in,version) != 0)
667 				goto getout;
668 			in++;
669 		}
670 
671 		/* Clear the coin & ticket counters/flags - LBO 042898 */
672 		for (i = 0; i < COIN_COUNTERS; i ++)
673 			coins[i] = lastcoin[i] = coinlockedout[i] = 0;
674 		dispensed_tickets = 0;
675 
676 		/* read in the coin/ticket counters */
677 		for (i = 0; i < COIN_COUNTERS; i ++)
678 		{
679 			if (readint(f,&coins[i]) != 0)
680 				goto getout;
681 		}
682 		if (readint(f,&dispensed_tickets) != 0)
683 			goto getout;
684 
685 		mixer_read_config(f);
686 
687 getout:
688 		osd_fclose(f);
689 	}
690 
691 	/* All analog ports need initialization */
692 	{
693 		int i;
694 		for (i = 0; i < MAX_INPUT_PORTS; i++)
695 			input_analog_init[i] = 1;
696 	}
697 #ifdef MAME_NET
698 	/* Find out what port is used by what player and swap regular inputs */
699 	in = Machine->input_ports;
700 
701 //	if (in->type == IPT_END) return; 	/* nothing to do */
702 
703 	/* make sure the InputPort definition is correct */
704 //	if (in->type != IPT_PORT)
705 //	{
706 //		logerror("Error in InputPort definition: expecting PORT_START\n");
707 //		return;
708 //	}
709 //	else in++;
710 	in++;
711 
712 	/* scan all the input ports */
713 	port = 0;
714 	while (in->type != IPT_END && port < MAX_INPUT_PORTS)
715 	{
716 		/* now check the input bits. */
717 		while (in->type != IPT_END && in->type != IPT_PORT)
718 		{
719 			if ((in->type & ~IPF_MASK) != IPT_DIPSWITCH_SETTING &&	/* skip dipswitch definitions */
720 				(in->type & ~IPF_MASK) != IPT_EXTENSION &&			/* skip analog extension fields */
721 				(in->type & IPF_UNUSED) == 0 &&						/* skip unused bits */
722 				!(!options.cheat && (in->type & IPF_CHEAT)) &&				/* skip cheats if cheats disabled */
723 				(in->type & ~IPF_MASK) != IPT_VBLANK &&				/* skip vblank stuff */
724 				((in->type & ~IPF_MASK) >= IPT_COIN1 &&				/* skip if coin input and it's locked out */
725 				(in->type & ~IPF_MASK) <= IPT_COIN4 &&
726                  coinlockedout[(in->type & ~IPF_MASK) - IPT_COIN1]))
727 			{
728 				player = 0;
729 				if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER2) player = 1;
730 				else if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER3) player = 2;
731 				else if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER4) player = 3;
732 
733 				if (((in->type & ~IPF_MASK) > IPT_ANALOG_START)
734 					&& ((in->type & ~IPF_MASK) < IPT_ANALOG_END))
735 				{
736 					analog_player_port[port] = player;
737 				}
738 				if (((in->type & ~IPF_MASK) == IPT_BUTTON1) ||
739 					((in->type & ~IPF_MASK) == IPT_BUTTON2) ||
740 					((in->type & ~IPF_MASK) == IPT_BUTTON3) ||
741 					((in->type & ~IPF_MASK) == IPT_BUTTON4) ||
742 					((in->type & ~IPF_MASK) == IPT_JOYSTICK_UP) ||
743 					((in->type & ~IPF_MASK) == IPT_JOYSTICK_DOWN) ||
744 					((in->type & ~IPF_MASK) == IPT_JOYSTICK_LEFT) ||
745 					((in->type & ~IPF_MASK) == IPT_JOYSTICK_RIGHT) ||
746 					((in->type & ~IPF_MASK) == IPT_JOYSTICKRIGHT_UP) ||
747 					((in->type & ~IPF_MASK) == IPT_JOYSTICKRIGHT_DOWN) ||
748  					((in->type & ~IPF_MASK) == IPT_JOYSTICKRIGHT_LEFT) ||
749 					((in->type & ~IPF_MASK) == IPT_JOYSTICKRIGHT_RIGHT) ||
750 					((in->type & ~IPF_MASK) == IPT_JOYSTICKLEFT_UP) ||
751 					((in->type & ~IPF_MASK) == IPT_JOYSTICKLEFT_DOWN) ||
752 					((in->type & ~IPF_MASK) == IPT_JOYSTICKLEFT_LEFT) ||
753 					((in->type & ~IPF_MASK) == IPT_JOYSTICKLEFT_RIGHT) ||
754 					((in->type & ~IPF_MASK) == IPT_PADDLE) ||
755 					((in->type & ~IPF_MASK) == IPT_DIAL) ||
756 					((in->type & ~IPF_MASK) == IPT_TRACKBALL_X) ||
757 					((in->type & ~IPF_MASK) == IPT_TRACKBALL_Y) ||
758 					((in->type & ~IPF_MASK) == IPT_AD_STICK_X) ||
759 					((in->type & ~IPF_MASK) == IPT_AD_STICK_Y))
760 				{
761 					switch (default_player)
762 					{
763 						case 0:
764 							/* do nothing */
765 							break;
766 						case 1:
767 							if (player == 0)
768 							{
769 								in->type &= ~IPF_PLAYER1;
770 								in->type |= IPF_PLAYER2;
771 							}
772 							else if (player == 1)
773 							{
774 								in->type &= ~IPF_PLAYER2;
775 								in->type |= IPF_PLAYER1;
776 							}
777 							break;
778 						case 2:
779 							if (player == 0)
780 							{
781 								in->type &= ~IPF_PLAYER1;
782 								in->type |= IPF_PLAYER3;
783 							}
784 							else if (player == 2)
785 							{
786 								in->type &= ~IPF_PLAYER3;
787 								in->type |= IPF_PLAYER1;
788 							}
789 							break;
790 						case 3:
791 							if (player == 0)
792 							{
793 								in->type &= ~IPF_PLAYER1;
794 								in->type |= IPF_PLAYER4;
795 							}
796 							else if (player == 3)
797 							{
798 								in->type &= ~IPF_PLAYER4;
799 								in->type |= IPF_PLAYER1;
800 							}
801 							break;
802 					}
803 				}
804 			}
805 			in++;
806 		}
807 		port++;
808 		if (in->type == IPT_PORT) in++;
809 	}
810 
811 	/* TODO: at this point the games should initialize peers to same as server */
812 
813 #endif /* MAME_NET */
814 
815 	update_input_ports();
816 
817 	/* if we didn't find a saved config, return 0 so the main core knows that it */
818 	/* is the first time the game is run and it should diplay the disclaimer. */
819 	if (f) return 1;
820 	else return 0;
821 }
822 
823 /***************************************************************************/
824 /* Save */
825 
save_input_port_settings(void)826 void save_input_port_settings(void)
827 {
828 	void *f;
829 #ifdef MAME_NET
830 	struct InputPort *in;
831 	int port, player;
832 
833 	/* Swap input port definitions back to defaults */
834 	in = Machine->input_ports;
835 
836 	if (in->type == IPT_END) return; 	/* nothing to do */
837 
838 	/* make sure the InputPort definition is correct */
839 	if (in->type != IPT_PORT)
840 	{
841 		logerror("Error in InputPort definition: expecting PORT_START\n");
842 		return;
843 	}
844 	else in++;
845 
846 	/* scan all the input ports */
847 	port = 0;
848 	while (in->type != IPT_END && port < MAX_INPUT_PORTS)
849 	{
850 		/* now check the input bits. */
851 		while (in->type != IPT_END && in->type != IPT_PORT)
852 		{
853 			if ((in->type & ~IPF_MASK) != IPT_DIPSWITCH_SETTING &&	/* skip dipswitch definitions */
854 				(in->type & ~IPF_MASK) != IPT_EXTENSION &&			/* skip analog extension fields */
855 				(in->type & IPF_UNUSED) == 0 &&						/* skip unused bits */
856 				!(!options.cheat && (in->type & IPF_CHEAT)) &&				/* skip cheats if cheats disabled */
857 				(in->type & ~IPF_MASK) != IPT_VBLANK &&				/* skip vblank stuff */
858 				((in->type & ~IPF_MASK) >= IPT_COIN1 &&				/* skip if coin input and it's locked out */
859 				(in->type & ~IPF_MASK) <= IPT_COIN4 &&
860                  coinlockedout[(in->type & ~IPF_MASK) - IPT_COIN1]))
861 			{
862 				player = 0;
863 				if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER2) player = 1;
864 				else if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER3) player = 2;
865 				else if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER4) player = 3;
866 
867 				if (((in->type & ~IPF_MASK) == IPT_BUTTON1) ||
868 					((in->type & ~IPF_MASK) == IPT_BUTTON2) ||
869 					((in->type & ~IPF_MASK) == IPT_BUTTON3) ||
870 					((in->type & ~IPF_MASK) == IPT_BUTTON4) ||
871 					((in->type & ~IPF_MASK) == IPT_JOYSTICK_UP) ||
872 					((in->type & ~IPF_MASK) == IPT_JOYSTICK_DOWN) ||
873 					((in->type & ~IPF_MASK) == IPT_JOYSTICK_LEFT) ||
874 					((in->type & ~IPF_MASK) == IPT_JOYSTICK_RIGHT) ||
875 					((in->type & ~IPF_MASK) == IPT_JOYSTICKRIGHT_UP) ||
876 					((in->type & ~IPF_MASK) == IPT_JOYSTICKRIGHT_DOWN) ||
877 					((in->type & ~IPF_MASK) == IPT_JOYSTICKRIGHT_LEFT) ||
878 					((in->type & ~IPF_MASK) == IPT_JOYSTICKRIGHT_RIGHT) ||
879 					((in->type & ~IPF_MASK) == IPT_JOYSTICKLEFT_UP) ||
880 					((in->type & ~IPF_MASK) == IPT_JOYSTICKLEFT_DOWN) ||
881 					((in->type & ~IPF_MASK) == IPT_JOYSTICKLEFT_LEFT) ||
882 					((in->type & ~IPF_MASK) == IPT_JOYSTICKLEFT_RIGHT) ||
883 					((in->type & ~IPF_MASK) == IPT_PADDLE) ||
884 					((in->type & ~IPF_MASK) == IPT_DIAL) ||
885 					((in->type & ~IPF_MASK) == IPT_TRACKBALL_X) ||
886 					((in->type & ~IPF_MASK) == IPT_TRACKBALL_Y) ||
887 					((in->type & ~IPF_MASK) == IPT_AD_STICK_X) ||
888 					((in->type & ~IPF_MASK) == IPT_AD_STICK_Y))
889 				{
890 					switch (default_player)
891 					{
892 						case 0:
893 							/* do nothing */
894 							analog_player_port[port] = player;
895 							break;
896 						case 1:
897 							if (player == 0)
898 							{
899 								in->type &= ~IPF_PLAYER1;
900 								in->type |= IPF_PLAYER2;
901 								analog_player_port[port] = 1;
902 							}
903 							else if (player == 1)
904 							{
905 								in->type &= ~IPF_PLAYER2;
906 								in->type |= IPF_PLAYER1;
907 								analog_player_port[port] = 0;
908 							}
909 							break;
910 						case 2:
911 							if (player == 0)
912 							{
913 								in->type &= ~IPF_PLAYER1;
914 								in->type |= IPF_PLAYER3;
915 								analog_player_port[port] = 2;
916 							}
917 							else if (player == 2)
918 							{
919 								in->type &= ~IPF_PLAYER3;
920 								in->type |= IPF_PLAYER1;
921 								analog_player_port[port] = 0;
922 							}
923 							break;
924 						case 3:
925 							if (player == 0)
926 							{
927 								in->type &= ~IPF_PLAYER1;
928 								in->type |= IPF_PLAYER4;
929 								analog_player_port[port] = 3;
930 							}
931 							else if (player == 3)
932 							{
933 								in->type &= ~IPF_PLAYER4;
934 								in->type |= IPF_PLAYER1;
935 								analog_player_port[port] = 0;
936 							}
937 							break;
938 					}
939 				}
940 			}
941 			in++;
942 		}
943 		port++;
944 		if (in->type == IPT_PORT) in++;
945 	}
946 #endif /* MAME_NET */
947 
948 	save_default_keys();
949 
950 	if ((f = osd_fopen(Machine->gamedrv->name,0,OSD_FILETYPE_CONFIG,1)) != 0)
951 	{
952 #ifndef MAME_NET
953 		struct InputPort *in;
954 #endif /* MAME_NET */
955 		int total;
956 		int i;
957 
958 
959 		in = Machine->input_ports_default;
960 
961 		/* calculate the size of the array */
962 		total = 0;
963 		while (in->type != IPT_END)
964 		{
965 			total++;
966 			in++;
967 		}
968 
969 		/* write header */
970 		osd_fwrite(f,MAMECFGSTRING_V8,8);
971 		/* write array size */
972 		writeint(f,total);
973 		/* write the original settings as defined in the driver */
974 		in = Machine->input_ports_default;
975 		while (in->type != IPT_END)
976 		{
977 			input_port_write(f,in);
978 			in++;
979 		}
980 		/* write the current settings */
981 		in = Machine->input_ports;
982 		while (in->type != IPT_END)
983 		{
984 			input_port_write(f,in);
985 			in++;
986 		}
987 
988 		/* write out the coin/ticket counters for this machine - LBO 042898 */
989 		for (i = 0; i < COIN_COUNTERS; i ++)
990 			writeint(f,coins[i]);
991 		writeint(f,dispensed_tickets);
992 
993 		mixer_write_config(f);
994 
995 		osd_fclose(f);
996 	}
997 }
998 
999 
1000 
1001 /* Note that the following 3 routines have slightly different meanings with analog ports */
input_port_name(const struct InputPort * in)1002 const char *input_port_name(const struct InputPort *in)
1003 {
1004 	int i;
1005 	unsigned type;
1006 
1007 	if (in->name != IP_NAME_DEFAULT) return in->name;
1008 
1009 	i = 0;
1010 
1011 	if ((in->type & ~IPF_MASK) == IPT_EXTENSION)
1012 		type = (in-1)->type & (~IPF_MASK | IPF_PLAYERMASK);
1013 	else
1014 		type = in->type & (~IPF_MASK | IPF_PLAYERMASK);
1015 
1016 	while (inputport_defaults[i].type != IPT_END &&
1017 			inputport_defaults[i].type != type)
1018 		i++;
1019 
1020 	if ((in->type & ~IPF_MASK) == IPT_EXTENSION)
1021 		return inputport_defaults[i+1].name;
1022 	else
1023 		return inputport_defaults[i].name;
1024 }
1025 
input_port_type_seq(int type)1026 InputSeq* input_port_type_seq(int type)
1027 {
1028 	unsigned i;
1029 
1030 	i = 0;
1031 
1032 	while (inputport_defaults[i].type != IPT_END &&
1033 			inputport_defaults[i].type != type)
1034 		i++;
1035 
1036 	return &inputport_defaults[i].seq;
1037 }
1038 
input_port_seq(const struct InputPort * in)1039 InputSeq* input_port_seq(const struct InputPort *in)
1040 {
1041 	int i,type;
1042 
1043 	static InputSeq ip_none = SEQ_DEF_1(CODE_NONE);
1044 
1045 	while (seq_get_1((InputSeq*)&in->seq) == CODE_PREVIOUS) in--;
1046 
1047 	if ((in->type & ~IPF_MASK) == IPT_EXTENSION)
1048 	{
1049 		type = (in-1)->type & (~IPF_MASK | IPF_PLAYERMASK);
1050 		/* if port is disabled, or cheat with cheats disabled, return no key */
1051 		if (((in-1)->type & IPF_UNUSED) || (!options.cheat && ((in-1)->type & IPF_CHEAT)))
1052 			return &ip_none;
1053 	}
1054 	else
1055 	{
1056 		type = in->type & (~IPF_MASK | IPF_PLAYERMASK);
1057 		/* if port is disabled, or cheat with cheats disabled, return no key */
1058 		if ((in->type & IPF_UNUSED) || (!options.cheat && (in->type & IPF_CHEAT)))
1059 			return &ip_none;
1060 	}
1061 
1062 	if (seq_get_1((InputSeq*)&in->seq) != CODE_DEFAULT)
1063 		return (InputSeq*)&in->seq;
1064 
1065 	i = 0;
1066 
1067 	while (inputport_defaults[i].type != IPT_END &&
1068 			inputport_defaults[i].type != type)
1069 		i++;
1070 
1071 	if ((in->type & ~IPF_MASK) == IPT_EXTENSION)
1072 		return &inputport_defaults[i+1].seq;
1073 	else
1074 		return &inputport_defaults[i].seq;
1075 }
1076 
1077 
1078 extern int analog_read[4];
1079 
update_analog_port(int port)1080 void update_analog_port(int port)
1081 {
1082 	struct InputPort *in;
1083 	int current, delta, type, sensitivity, min, max, default_value;
1084 	int axis, is_stick, check_bounds;
1085 	InputSeq* incseq;
1086 	InputSeq* decseq;
1087 	int keydelta;
1088 	int player;
1089 
1090 	/* get input definition */
1091 	in = input_analog[port];
1092 
1093 	switch (in->type & IPF_PLAYERMASK)
1094 	{
1095 		case IPF_PLAYER2:          player = 1; break;
1096 		case IPF_PLAYER3:          player = 2; break;
1097 		case IPF_PLAYER4:          player = 3; break;
1098 		case IPF_PLAYER1: default: player = 0; break;
1099 	}
1100 
1101 	/* if we're not cheating and this is a cheat-only port, bail */
1102 	if (!options.cheat && (in->type & IPF_CHEAT)) return;
1103 	type=(in->type & ~IPF_MASK);
1104 
1105 	decseq = input_port_seq(in);
1106 	incseq = input_port_seq(in+1);
1107 
1108 	keydelta = IP_GET_DELTA(in);
1109 
1110 	if(analog_read[player])keydelta=0;
1111 
1112 	switch (type)
1113 	{
1114 		case IPT_PADDLE:
1115 			axis = X_AXIS; is_stick = 0; check_bounds = 1; break;
1116 		case IPT_PADDLE_V:
1117 			axis = Y_AXIS; is_stick = 0; check_bounds = 1; break;
1118 		case IPT_DIAL:
1119 			axis = X_AXIS; is_stick = 0; check_bounds = 0; break;
1120 		case IPT_DIAL_V:
1121 			axis = Y_AXIS; is_stick = 0; check_bounds = 0; break;
1122 		case IPT_TRACKBALL_X:
1123 			axis = X_AXIS; is_stick = 0; check_bounds = 0; break;
1124 		case IPT_TRACKBALL_Y:
1125 			axis = Y_AXIS; is_stick = 0; check_bounds = 0; break;
1126 		case IPT_AD_STICK_X:
1127 			axis = X_AXIS; is_stick = 1; check_bounds = 1; break;
1128 		case IPT_AD_STICK_Y:
1129 			axis = Y_AXIS; is_stick = 1; check_bounds = 1; break;
1130 		case IPT_PEDAL:
1131 			axis = Y_AXIS; is_stick = 0; check_bounds = 1; break;
1132 		default:
1133 			/* Use some defaults to prevent crash */
1134 			axis = X_AXIS; is_stick = 0; check_bounds = 0;
1135 			logerror("Oops, polling non analog device in update_analog_port()????\n");
1136 	}
1137 
1138 
1139 	sensitivity = IP_GET_SENSITIVITY(in);
1140 
1141 	//if(analog_read[player])sensitivity=(sensitivity/4);
1142 
1143 	min = IP_GET_MIN(in);
1144 	max = IP_GET_MAX(in);
1145 	default_value = in->default_value * 100 / sensitivity;
1146 	/* extremes can be either signed or unsigned */
1147 	if (min > max)
1148 	{
1149 		if (in->mask > 0xff) min = min - 0x10000;
1150 		else min = min - 0x100;
1151 	}
1152 
1153 	input_analog_previous_value[port] = input_analog_current_value[port];
1154 
1155 	/* if IPF_CENTER go back to the default position */
1156 	/* sticks are handled later... */
1157 	if ((in->type & IPF_CENTER) && (!is_stick))
1158 		input_analog_current_value[port] = in->default_value * 100 / sensitivity;
1159 
1160 	current = input_analog_current_value[port];
1161 
1162 	delta = 0;
1163 
1164 	if (!is_stick)
1165 	{
1166 		if (axis == X_AXIS)
1167 			delta = mouse_delta_x[player];
1168 		else
1169 			delta = mouse_delta_y[player];
1170 	}
1171 
1172 	if (seq_pressed(decseq)) delta -= keydelta;
1173 
1174 	if (type != IPT_PEDAL)
1175 	{
1176 		if (seq_pressed(incseq)) delta += keydelta;
1177 	}
1178 	else
1179 	{
1180 		/* is this cheesy or what? */
1181 		if (!delta && seq_get_1(incseq) == KEYCODE_Y) delta += keydelta;
1182 		delta = -delta;
1183 	}
1184 
1185 	if (in->type & IPF_REVERSE) delta = -delta;
1186 
1187 	if (is_stick)
1188 	{
1189 		int _new, prev;
1190 
1191 		/* center stick */
1192 		if ((delta == 0) && (in->type & IPF_CENTER))
1193 		{
1194 			if (current > default_value)
1195 			delta = -100 / sensitivity;
1196 			if (current < default_value)
1197 			delta = 100 / sensitivity;
1198 		}
1199 
1200 		/* An analog joystick which is not at zero position (or has just */
1201 		/* moved there) takes precedence over all other computations */
1202 		/* analog_x/y holds values from -128 to 128 (yes, 128, not 127) */
1203 
1204 		if (axis == X_AXIS)
1205 		{
1206 			_new  = analog_current_x[player];
1207 			prev = analog_previous_x[player];
1208 		}
1209 		else
1210 		{
1211 			_new  = analog_current_y[player];
1212 			prev = analog_previous_y[player];
1213 		}
1214 
1215 		if ((_new != 0) || (_new-prev != 0))
1216 		{
1217 			delta=0;
1218 
1219 			if (in->type & IPF_REVERSE)
1220 			{
1221 				_new  = -_new;
1222 				prev = -prev;
1223 			}
1224 
1225 			/* apply sensitivity using a logarithmic scale */
1226 			if (in->mask > 0xff)
1227 			{
1228 				if (_new > 0)
1229 				{
1230 					current = (pow(_new / 32768.0, 100.0 / sensitivity) * (max-in->default_value)
1231 							+ in->default_value) * 100 / sensitivity;
1232 				}
1233 				else
1234 				{
1235 					current = (pow(-_new / 32768.0, 100.0 / sensitivity) * (min-in->default_value)
1236 							+ in->default_value) * 100 / sensitivity;
1237 				}
1238 			}
1239 			else
1240 			{
1241 				if (_new > 0)
1242 				{
1243 					current = (pow(_new / 128.0, 100.0 / sensitivity) * (max-in->default_value)
1244 							+ in->default_value) * 100 / sensitivity;
1245 				}
1246 				else
1247 				{
1248 					current = (pow(-_new / 128.0, 100.0 / sensitivity) * (min-in->default_value)
1249 							+ in->default_value) * 100 / sensitivity;
1250 				}
1251 			}
1252 		}
1253 	}
1254 
1255 	current += delta;
1256 
1257 	if (check_bounds)
1258 	{
1259 		if ((current * sensitivity + 50) / 100 < min)
1260 			current = (min * 100 + sensitivity/2) / sensitivity;
1261 		if ((current * sensitivity + 50) / 100 > max)
1262 			current = (max * 100 + sensitivity/2) / sensitivity;
1263 	}
1264 
1265 	input_analog_current_value[port] = current;
1266     //printf("input_analog_current_value %d %d %d %d ",port,current,sensitivity,keydelta);
1267 }
1268 
scale_analog_port(int port)1269 static void scale_analog_port(int port)
1270 {
1271 	struct InputPort *in;
1272 	int delta,current,sensitivity;
1273 
1274 profiler_mark(PROFILER_INPUT);
1275 	in = input_analog[port];
1276 	sensitivity = IP_GET_SENSITIVITY(in);
1277 
1278 	delta = cpu_scalebyfcount(input_analog_current_value[port] - input_analog_previous_value[port]);
1279 
1280 	current = input_analog_previous_value[port] + delta;
1281 
1282 	input_port_value[port] &= ~in->mask;
1283 	input_port_value[port] |= ((current * sensitivity + 50) / 100) & in->mask;
1284 
1285 	if (playback)
1286 		readword(playback,&input_port_value[port]);
1287 	if (record)
1288 		writeword(record,input_port_value[port]);
1289 #ifdef MAME_NET
1290 	if ( net_active() && (default_player != NET_SPECTATOR) )
1291 		net_analog_sync((unsigned char *) input_port_value, port, analog_player_port, default_player);
1292 #endif /* MAME_NET */
1293 profiler_mark(PROFILER_END);
1294 }
1295 
1296 
update_input_ports(void)1297 void update_input_ports(void)
1298 {
1299 	int port,ib;
1300 	struct InputPort *in;
1301 #define MAX_INPUT_BITS 1024
1302 static int impulsecount[MAX_INPUT_BITS];
1303 static int waspressed[MAX_INPUT_BITS];
1304 #define MAX_JOYSTICKS 3
1305 #define MAX_PLAYERS 4
1306 #ifdef MRU_JOYSTICK
1307 static int update_serial_number = 1;
1308 static int joyserial[MAX_JOYSTICKS*MAX_PLAYERS][4];
1309 #else
1310 int joystick[MAX_JOYSTICKS*MAX_PLAYERS][4];
1311 #endif
1312 
1313 #ifdef MAME_NET
1314 int player;
1315 #endif /* MAME_NET */
1316 
1317 
1318 profiler_mark(PROFILER_INPUT);
1319 
1320 	/* clear all the values before proceeding */
1321 	for (port = 0;port < MAX_INPUT_PORTS;port++)
1322 	{
1323 		input_port_value[port] = 0;
1324 		input_vblank[port] = 0;
1325 		input_analog[port] = 0;
1326 	}
1327 
1328 #ifndef MRU_JOYSTICK
1329 	for (i = 0;i < 4*MAX_JOYSTICKS*MAX_PLAYERS;i++)
1330 		joystick[i/4][i%4] = 0;
1331 #endif
1332 
1333 	in = Machine->input_ports;
1334 
1335 	if (in->type == IPT_END) return; 	/* nothing to do */
1336 
1337 	/* make sure the InputPort definition is correct */
1338 	if (in->type != IPT_PORT)
1339 	{
1340 		logerror("Error in InputPort definition: expecting PORT_START\n");
1341 		return;
1342 	}
1343 	else in++;
1344 
1345 #ifdef MRU_JOYSTICK
1346 	/* scan all the joystick ports */
1347 	port = 0;
1348 	while (in->type != IPT_END && port < MAX_INPUT_PORTS)
1349 	{
1350 		while (in->type != IPT_END && in->type != IPT_PORT)
1351 		{
1352 			if ((in->type & ~IPF_MASK) >= IPT_JOYSTICK_UP &&
1353 				(in->type & ~IPF_MASK) <= IPT_JOYSTICKLEFT_RIGHT)
1354 			{
1355 				InputSeq* seq;
1356 
1357 				seq = input_port_seq(in);
1358 
1359 				if (seq_get_1(seq) != 0 && seq_get_1(seq) != CODE_NONE)
1360 				{
1361 					int joynum,joydir,player;
1362 
1363 					player = 0;
1364 					if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER2)
1365 						player = 1;
1366 					else if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER3)
1367 						player = 2;
1368 					else if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER4)
1369 						player = 3;
1370 
1371 					joynum = player * MAX_JOYSTICKS +
1372 							 ((in->type & ~IPF_MASK) - IPT_JOYSTICK_UP) / 4;
1373 					joydir = ((in->type & ~IPF_MASK) - IPT_JOYSTICK_UP) % 4;
1374 
1375 #ifdef ENABLE_AUTOFIRE
1376 					if (seq_pressed_with_autofire(in, seq))
1377 #else
1378 					if (seq_pressed(seq))
1379 #endif
1380 					{
1381 						if (joyserial[joynum][joydir] == 0)
1382 							joyserial[joynum][joydir] = update_serial_number;
1383 					}
1384 					else
1385 						joyserial[joynum][joydir] = 0;
1386 				}
1387 			}
1388 			in++;
1389 		}
1390 
1391 		port++;
1392 		if (in->type == IPT_PORT) in++;
1393 	}
1394 	update_serial_number += 1;
1395 
1396 	in = Machine->input_ports;
1397 
1398 	/* already made sure the InputPort definition is correct */
1399 	in++;
1400 #endif
1401 
1402 
1403 	/* scan all the input ports */
1404 	port = 0;
1405 	ib = 0;
1406 	while (in->type != IPT_END && port < MAX_INPUT_PORTS)
1407 	{
1408 		struct InputPort *start;
1409 
1410 
1411 		/* first of all, scan the whole input port definition and build the */
1412 		/* default value. I must do it before checking for input because otherwise */
1413 		/* multiple keys associated with the same input bit wouldn't work (the bit */
1414 		/* would be reset to its default value by the second entry, regardless if */
1415 		/* the key associated with the first entry was pressed) */
1416 		start = in;
1417 		while (in->type != IPT_END && in->type != IPT_PORT)
1418 		{
1419 			if ((in->type & ~IPF_MASK) != IPT_DIPSWITCH_SETTING &&	/* skip dipswitch definitions */
1420 				(in->type & ~IPF_MASK) != IPT_EXTENSION)			/* skip analog extension fields */
1421 			{
1422 				input_port_value[port] =
1423 						(input_port_value[port] & ~in->mask) | (in->default_value & in->mask);
1424 #ifdef MAME_NET
1425 				if ( net_active() )
1426 					input_port_defaults[port] = input_port_value[port];
1427 #endif /* MAME_NET */
1428 			}
1429 
1430 			in++;
1431 		}
1432 
1433 		/* now get back to the beginning of the input port and check the input bits. */
1434 		for (in = start;
1435 			 in->type != IPT_END && in->type != IPT_PORT;
1436 			 in++, ib++)
1437 		{
1438 #ifdef MAME_NET
1439 			player = 0;
1440 			if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER2) player = 1;
1441 			else if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER3) player = 2;
1442 			else if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER4) player = 3;
1443 #endif /* MAME_NET */
1444 			if ((in->type & ~IPF_MASK) != IPT_DIPSWITCH_SETTING &&	/* skip dipswitch definitions */
1445 					(in->type & ~IPF_MASK) != IPT_EXTENSION)		/* skip analog extension fields */
1446 			{
1447 				if ((in->type & ~IPF_MASK) == IPT_VBLANK)
1448 				{
1449 					input_vblank[port] ^= in->mask;
1450 					input_port_value[port] ^= in->mask;
1451 if (Machine->drv->vblank_duration == 0)
1452 	logerror("Warning: you are using IPT_VBLANK with vblank_duration = 0. You need to increase vblank_duration for IPT_VBLANK to work.\n");
1453 				}
1454 				/* If it's an analog control, handle it appropriately */
1455 				else if (((in->type & ~IPF_MASK) > IPT_ANALOG_START)
1456 					  && ((in->type & ~IPF_MASK) < IPT_ANALOG_END  )) /* LBO 120897 */
1457 				{
1458 					input_analog[port]=in;
1459 					/* reset the analog port on first access */
1460 					if (input_analog_init[port])
1461 					{
1462 						input_analog_init[port] = 0;
1463 						input_analog_current_value[port] = input_analog_previous_value[port]
1464 							= in->default_value * 100 / IP_GET_SENSITIVITY(in);
1465 					}
1466 				}
1467 				else
1468 				{
1469 					InputSeq* seq;
1470 
1471 					seq = input_port_seq(in);
1472 
1473 #ifdef ENABLE_AUTOFIRE
1474 					if (seq_pressed_with_autofire(in, seq))
1475 #else
1476 					if (seq_pressed(seq))
1477 #endif
1478 					{
1479 						/* skip if coin input and it's locked out */
1480 						if ((in->type & ~IPF_MASK) >= IPT_COIN1 &&
1481 							(in->type & ~IPF_MASK) <= IPT_COIN4 &&
1482                             coinlockedout[(in->type & ~IPF_MASK) - IPT_COIN1])
1483 						{
1484 							continue;
1485 						}
1486 
1487 						/* if IPF_RESET set, reset the first CPU */
1488 						if ((in->type & IPF_RESETCPU) && waspressed[ib] == 0)
1489 							cpu_set_reset_line(0,PULSE_LINE);
1490 
1491 						if (in->type & IPF_IMPULSE)
1492 						{
1493 if (IP_GET_IMPULSE(in) == 0)
1494 	logerror("error in input port definition: IPF_IMPULSE with length = 0\n");
1495 							if (waspressed[ib] == 0)
1496 								impulsecount[ib] = IP_GET_IMPULSE(in);
1497 								/* the input bit will be toggled later */
1498 						}
1499 						else if (in->type & IPF_TOGGLE)
1500 						{
1501 							if (waspressed[ib] == 0)
1502 							{
1503 								in->default_value ^= in->mask;
1504 								input_port_value[port] ^= in->mask;
1505 							}
1506 						}
1507 						else if ((in->type & ~IPF_MASK) >= IPT_JOYSTICK_UP &&
1508 								(in->type & ~IPF_MASK) <= IPT_JOYSTICKLEFT_RIGHT)
1509 						{
1510 #ifndef MAME_NET
1511 							int joynum,joydir,mask,player;
1512 
1513 
1514 							player = 0;
1515 							if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER2) player = 1;
1516 							else if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER3) player = 2;
1517 							else if ((in->type & IPF_PLAYERMASK) == IPF_PLAYER4) player = 3;
1518 #else
1519 							int joynum,joydir,mask;
1520 #endif /* !MAME_NET */
1521 							joynum = player * MAX_JOYSTICKS +
1522 									((in->type & ~IPF_MASK) - IPT_JOYSTICK_UP) / 4;
1523 							joydir = ((in->type & ~IPF_MASK) - IPT_JOYSTICK_UP) % 4;
1524 
1525 							mask = in->mask;
1526 
1527 #ifndef MRU_JOYSTICK
1528 							/* avoid movement in two opposite directions */
1529 							if (joystick[joynum][joydir ^ 1] != 0)
1530 								mask = 0;
1531 							else if (in->type & IPF_4WAY)
1532 							{
1533 								int dir;
1534 
1535 
1536 								/* avoid diagonal movements */
1537 								for (dir = 0;dir < 4;dir++)
1538 								{
1539 									if (joystick[joynum][dir] != 0)
1540 										mask = 0;
1541 								}
1542 							}
1543 
1544 							joystick[joynum][joydir] = 1;
1545 #else
1546 							/* avoid movement in two opposite directions */
1547 							if (joyserial[joynum][joydir ^ 1] != 0)
1548 								mask = 0;
1549 							else if (in->type & IPF_4WAY)
1550 							{
1551 								int mru_dir = joydir;
1552 								int mru_serial = 0;
1553 								int dir;
1554 
1555 
1556 								/* avoid diagonal movements, use mru button */
1557 								for (dir = 0;dir < 4;dir++)
1558 								{
1559 									if (joyserial[joynum][dir] > mru_serial)
1560 									{
1561 										mru_serial = joyserial[joynum][dir];
1562 										mru_dir = dir;
1563 									}
1564 								}
1565 
1566 								if (mru_dir != joydir)
1567 									mask = 0;
1568 							}
1569 #endif
1570 
1571 							input_port_value[port] ^= mask;
1572 						}
1573 						else
1574 							input_port_value[port] ^= in->mask;
1575 
1576 						waspressed[ib] = 1;
1577 					}
1578 					else
1579 						waspressed[ib] = 0;
1580 
1581 					if ((in->type & IPF_IMPULSE) && impulsecount[ib] > 0)
1582 					{
1583 						impulsecount[ib]--;
1584 						waspressed[ib] = 1;
1585 						input_port_value[port] ^= in->mask;
1586 					}
1587 				}
1588 			}
1589 		}
1590 
1591 		port++;
1592 		if (in->type == IPT_PORT) in++;
1593 	}
1594 
1595 	if (playback)
1596 	{
1597 		int i;
1598 
1599 		for (i = 0; i < MAX_INPUT_PORTS; i ++)
1600 			readword(playback,&input_port_value[i]);
1601 	}
1602 	if (record)
1603 	{
1604 		int i;
1605 
1606 		for (i = 0; i < MAX_INPUT_PORTS; i ++)
1607 			writeword(record,input_port_value[i]);
1608 	}
1609 #ifdef MAME_NET
1610 	if ( net_active() && (default_player != NET_SPECTATOR) )
1611 		net_input_sync((unsigned char *) input_port_value, (unsigned char *) input_port_defaults, MAX_INPUT_PORTS);
1612 #endif /* MAME_NET */
1613 
1614 profiler_mark(PROFILER_END);
1615 }
1616 
1617 
1618 
1619 /* used the the CPU interface to notify that VBlank has ended, so we can update */
1620 /* IPT_VBLANK input ports. */
inputport_vblank_end(void)1621 void inputport_vblank_end(void)
1622 {
1623 	int port;
1624 	int i;
1625 
1626 
1627 profiler_mark(PROFILER_INPUT);
1628 	for (port = 0;port < MAX_INPUT_PORTS;port++)
1629 	{
1630 		if (input_vblank[port])
1631 		{
1632 			input_port_value[port] ^= input_vblank[port];
1633 			input_vblank[port] = 0;
1634 		}
1635 	}
1636 
1637 	/* poll all the analog joysticks */
1638 	osd_poll_joysticks();
1639 
1640 	/* update the analog devices */
1641 	for (i = 0;i < OSD_MAX_JOY_ANALOG;i++)
1642 	{
1643 		/* update the analog joystick position */
1644 		analog_previous_x[i] = analog_current_x[i];
1645 		analog_previous_y[i] = analog_current_y[i];
1646 		osd_analogjoy_read (i, &(analog_current_x[i]), &(analog_current_y[i]));
1647 
1648 		/* update mouse/trackball position */
1649 		osd_trak_read (i, &mouse_delta_x[i], &mouse_delta_y[i]);
1650 	}
1651 
1652 	for (i = 0;i < MAX_INPUT_PORTS;i++)
1653 	{
1654 		struct InputPort *in;
1655 
1656 		in=input_analog[i];
1657 		if (in)
1658 		{
1659 			update_analog_port(i);
1660 		}
1661 	}
1662 profiler_mark(PROFILER_END);
1663 }
1664 
1665 
1666 
readinputport(int port)1667 int readinputport(int port)
1668 {
1669 	struct InputPort *in;
1670 
1671 	/* Update analog ports on demand */
1672 	in=input_analog[port];
1673 	if (in)
1674 	{
1675 		scale_analog_port(port);
1676 	}
1677 
1678 	return input_port_value[port];
1679 }
1680 
READ_HANDLER(input_port_0_r)1681 READ_HANDLER( input_port_0_r ) { return readinputport(0); }
READ_HANDLER(input_port_1_r)1682 READ_HANDLER( input_port_1_r ) { return readinputport(1); }
READ_HANDLER(input_port_2_r)1683 READ_HANDLER( input_port_2_r ) { return readinputport(2); }
READ_HANDLER(input_port_3_r)1684 READ_HANDLER( input_port_3_r ) { return readinputport(3); }
READ_HANDLER(input_port_4_r)1685 READ_HANDLER( input_port_4_r ) { return readinputport(4); }
READ_HANDLER(input_port_5_r)1686 READ_HANDLER( input_port_5_r ) { return readinputport(5); }
READ_HANDLER(input_port_6_r)1687 READ_HANDLER( input_port_6_r ) { return readinputport(6); }
READ_HANDLER(input_port_7_r)1688 READ_HANDLER( input_port_7_r ) { return readinputport(7); }
READ_HANDLER(input_port_8_r)1689 READ_HANDLER( input_port_8_r ) { return readinputport(8); }
READ_HANDLER(input_port_9_r)1690 READ_HANDLER( input_port_9_r ) { return readinputport(9); }
READ_HANDLER(input_port_10_r)1691 READ_HANDLER( input_port_10_r ) { return readinputport(10); }
READ_HANDLER(input_port_11_r)1692 READ_HANDLER( input_port_11_r ) { return readinputport(11); }
READ_HANDLER(input_port_12_r)1693 READ_HANDLER( input_port_12_r ) { return readinputport(12); }
READ_HANDLER(input_port_13_r)1694 READ_HANDLER( input_port_13_r ) { return readinputport(13); }
READ_HANDLER(input_port_14_r)1695 READ_HANDLER( input_port_14_r ) { return readinputport(14); }
READ_HANDLER(input_port_15_r)1696 READ_HANDLER( input_port_15_r ) { return readinputport(15); }
READ_HANDLER(input_port_16_r)1697 READ_HANDLER( input_port_16_r ) { return readinputport(16); }
READ_HANDLER(input_port_17_r)1698 READ_HANDLER( input_port_17_r ) { return readinputport(17); }
READ_HANDLER(input_port_18_r)1699 READ_HANDLER( input_port_18_r ) { return readinputport(18); }
READ_HANDLER(input_port_19_r)1700 READ_HANDLER( input_port_19_r ) { return readinputport(19); }
1701 
1702 
1703 #ifdef MAME_NET
set_default_player_controls(int player)1704 void set_default_player_controls(int player)
1705 {
1706 	if (player == NET_SPECTATOR)
1707 		default_player = NET_SPECTATOR;
1708 	else
1709 		default_player = player - 1;
1710 }
1711 #endif /* MAME_NET */
1712 
1713 /***************************************************************************/
1714 /* InputPort conversion */
1715 
input_port_count(const struct InputPortTiny * src)1716 static unsigned input_port_count(const struct InputPortTiny *src)
1717 {
1718 	unsigned total;
1719 
1720 	total = 0;
1721 	while (src->type != IPT_END)
1722 	{
1723 		int type = src->type & ~IPF_MASK;
1724 		if (type > IPT_ANALOG_START && type < IPT_ANALOG_END)
1725 			total += 2;
1726 		else if (type != IPT_EXTENSION)
1727 			++total;
1728 		++src;
1729 	}
1730 
1731 	++total; /* for IPT_END */
1732 
1733 	return total;
1734 }
1735 
input_port_allocate(const struct InputPortTiny * src)1736 struct InputPort* input_port_allocate(const struct InputPortTiny *src)
1737 {
1738 	struct InputPort* dst;
1739 	struct InputPort* base;
1740 	unsigned total;
1741 
1742 	total = input_port_count(src);
1743 
1744 	base = (struct InputPort*)malloc(total * sizeof(struct InputPort));
1745 	dst = base;
1746 
1747 	while (src->type != IPT_END)
1748 	{
1749 		int type = src->type & ~IPF_MASK;
1750 		const struct InputPortTiny *ext;
1751 		const struct InputPortTiny *src_end;
1752 		InputCode seq_default;
1753 
1754 		if (type > IPT_ANALOG_START && type < IPT_ANALOG_END)
1755 			src_end = src + 2;
1756 		else
1757 			src_end = src + 1;
1758 
1759 		switch (type)
1760 		{
1761 			case IPT_END :
1762 			case IPT_PORT :
1763 			case IPT_DIPSWITCH_NAME :
1764 			case IPT_DIPSWITCH_SETTING :
1765 				seq_default = CODE_NONE;
1766 			break;
1767 			default:
1768 				seq_default = CODE_DEFAULT;
1769 		}
1770 
1771 		ext = src_end;
1772 		while (src != src_end)
1773 		{
1774 			dst->type = src->type;
1775 			dst->mask = src->mask;
1776 			dst->default_value = src->default_value;
1777 			dst->name = src->name;
1778 
1779   			if (ext->type == IPT_EXTENSION)
1780   			{
1781 				InputCode or1 =	IP_GET_CODE_OR1(ext);
1782 				InputCode or2 =	IP_GET_CODE_OR2(ext);
1783 
1784 				if (or1 < __code_max)
1785 				{
1786 					if (or2 < __code_max)
1787 						seq_set_3(&dst->seq, or1, CODE_OR, or2);
1788 					else
1789 						seq_set_1(&dst->seq, or1);
1790 				} else {
1791 					if (or1 == CODE_NONE)
1792 						seq_set_1(&dst->seq, or2);
1793 					else
1794 						seq_set_1(&dst->seq, or1);
1795 				}
1796 
1797   				++ext;
1798   			} else {
1799 				seq_set_1(&dst->seq,seq_default);
1800   			}
1801 
1802 			++src;
1803 			++dst;
1804 		}
1805 
1806 		src = ext;
1807 	}
1808 
1809 	dst->type = IPT_END;
1810 
1811 	return base;
1812 }
1813 
input_port_free(struct InputPort * dst)1814 void input_port_free(struct InputPort* dst)
1815 {
1816 	free(dst);
1817 }
1818 
1819 /*
1820  * added for autofire
1821  */
1822 #ifdef ENABLE_AUTOFIRE
1823 
1824 extern void ui_displaymenu(struct osd_bitmap *bitmap, const char **items, const char **subitems, char *flag, int selected, int arrowize_subitem);
1825 extern int need_to_clear_bitmap;	/* used to tell updatescreen() to clear the bitmap */
1826 
1827 #define MAX_AUTOFIRE_BUTTON 6
1828 
1829 static int af_ipt_button[] = {
1830     IPT_BUTTON1,IPT_BUTTON2,IPT_BUTTON3,IPT_BUTTON4,
1831     IPT_BUTTON5,IPT_BUTTON6,IPT_BUTTON7,IPT_BUTTON8
1832 };
1833 
1834 InputSeq af_fire_on = { KEYCODE_INSERT, CODE_NONE };
1835 InputSeq af_fire_off= { KEYCODE_DEL, CODE_NONE };
1836 
1837 static char af_autofire[MAX_AUTOFIRE_BUTTON];
1838 static char af_noautofire[MAX_AUTOFIRE_BUTTON];
1839 static char af_autopressed[MAX_AUTOFIRE_BUTTON];
1840 //static int af_record_first_insert = 1;
1841 
autofire_menu(struct osd_bitmap * bitmap,int selected)1842 int autofire_menu(struct osd_bitmap *bitmap, int selected)
1843 {
1844     const char *menu_item[100];
1845     const char *menu_subitem[100];
1846     char menu_item_sub[100][256];
1847     char menu_subitem_sub[100][256];
1848     char flag[100];
1849     int sel,sel_af_on,sel_af_off,sel_return;
1850     int total;
1851     int arrowize;
1852 
1853     sel = selected - 1;
1854     arrowize = 0;
1855 
1856     /* auto-fire button menu */
1857     for (total = 0; total < MAX_AUTOFIRE_BUTTON; total ++) {
1858         flag[total] = 0;
1859         sprintf(menu_item_sub[total] , "Auto-Fire on Button %d", total + 1);
1860         sprintf(menu_subitem_sub[total], "Delay %02d", af_autofire[total]);
1861         menu_item[total] = menu_item_sub[total];
1862         if (af_autofire[total] > 0)
1863             menu_subitem[total] = menu_subitem_sub[total];
1864         else
1865             menu_subitem[total] = "      No";
1866 
1867 	if (sel == total) {
1868             if (af_autofire[sel] == 0)
1869                 arrowize = 2;
1870             else if (af_autofire[sel] == 99)
1871                 arrowize = 1;
1872             else
1873                 arrowize = 3;
1874 	}
1875     }
1876 
1877     /* auto-fire on menu */
1878     sel_af_on = total;
1879     flag[total] = 0;
1880     menu_subitem[total] = code_name(af_fire_on[0]);
1881     menu_item[total ++] = "Auto-Fire On  ";
1882 
1883     /* auto-fire off menu */
1884     sel_af_off = total;
1885     flag[total] = 0;
1886     menu_subitem[total] = code_name(af_fire_off[0]);
1887     menu_item[total ++] = "Auto-Fire Off ";
1888 
1889     /* Return to Main Menu */
1890     sel_return = total;
1891     flag[total] =0;
1892     menu_subitem[total] = "";
1893     menu_item[total ++] = "Return to Main Menu";
1894 
1895     menu_item[total] = 0;	/* End of array */
1896 
1897     if (sel > SEL_MASK) {
1898         int ret;
1899         InputSeq seq;
1900 
1901         menu_subitem[sel & SEL_MASK] = "    ";
1902         ui_displaymenu(bitmap, menu_item, menu_subitem,
1903                        flag, sel & SEL_MASK, 3);
1904 
1905         seq_set_1(&seq, CODE_NONE);
1906         ret = seq_read_async(&seq, 0);
1907 
1908         if (ret >= 0) {
1909             sel &= 0xff;
1910             schedule_full_refresh();
1911             if (seq_get_1(&seq) != CODE_NONE) {
1912                 if (sel == sel_af_on)
1913                     af_fire_on[0] = seq_get_1(&seq);
1914                 else if (sel==sel_af_off)
1915                     af_fire_off[0] = seq_get_1(&seq);
1916             }
1917         }
1918         return sel + 1;
1919     }
1920 
1921     ui_displaymenu(bitmap, menu_item, menu_subitem, flag, sel, arrowize);
1922 
1923     if (input_ui_pressed_repeat(IPT_UI_DOWN, 8)) {
1924         if (sel < sel_return)
1925             sel++;
1926         else
1927             sel = 0;
1928     }
1929 
1930     if (input_ui_pressed_repeat(IPT_UI_UP, 8)) {
1931         if (sel > 0)
1932             sel--;
1933         else
1934             sel = sel_return;
1935     }
1936 
1937     if (input_ui_pressed_repeat(IPT_UI_RIGHT, 8)) {
1938         if ((sel >= 0) && (sel < MAX_AUTOFIRE_BUTTON))
1939             if (af_autofire[sel] ++ > 98)
1940                 af_autofire[sel] = 99;
1941         schedule_full_refresh();
1942     }
1943 
1944     if (input_ui_pressed_repeat(IPT_UI_LEFT, 8)) {
1945         if ((sel >= 0) && (sel < MAX_AUTOFIRE_BUTTON))
1946             if (af_autofire[sel] -- < 1)
1947                 af_autofire[sel] = 0;
1948         schedule_full_refresh();
1949     }
1950 
1951     if (input_ui_pressed(IPT_UI_SELECT)) {
1952         if (sel == sel_return)
1953             sel = -1;
1954         else if ((sel == sel_af_on) || (sel == sel_af_off)) {
1955             seq_read_async_start();
1956             sel |= 1 << SEL_BITS;	/* we'll ask for a key */
1957 /*			sel |= 0x100;	   we'll ask for a key */
1958             schedule_full_refresh();
1959         }
1960     }
1961 
1962     if (input_ui_pressed(IPT_UI_CANCEL))
1963         sel = -1;
1964 
1965     if (input_ui_pressed(IPT_UI_CONFIGURE))
1966         sel = -2;
1967 
1968     if (sel == -1 || sel == -2)
1969         schedule_full_refresh();
1970 
1971     return sel + 1;
1972 }
1973 
AfButton(int impport)1974 void AfButton(int impport)
1975 {
1976     int no;
1977 #if 0
1978     int i;
1979     char msg[100];
1980     char tmp[10];
1981 #endif
1982 
1983     switch (impport) {
1984     case IPT_BUTTON1:
1985         no = 0;
1986         break;
1987     case IPT_BUTTON2:
1988         no = 1;
1989         break;
1990     case IPT_BUTTON3:
1991         no = 2;
1992         break;
1993     case IPT_BUTTON4:
1994         no = 3;
1995         break;
1996     case IPT_BUTTON5:
1997         no = 4;
1998         break;
1999     case IPT_BUTTON6:
2000         no = 5;
2001         break;
2002     case IPT_BUTTON7:
2003         no = 6;
2004         break;
2005     case IPT_BUTTON8:
2006         no = 7;
2007         break;
2008     default:
2009         return;
2010     }
2011     if (no >= MAX_AUTOFIRE_BUTTON)
2012         return;
2013 
2014     if (seq_pressed(&af_fire_on))
2015         af_noautofire[no] = 0;
2016     else if (seq_pressed(&af_fire_off))
2017         af_noautofire[no] = 1;
2018     else
2019         return;
2020 
2021 #if 0
2022     strcpy(msg, "Autofire ");
2023     for (i = 0; i < MAX_AUTOFIRE_BUTTON; i ++) {
2024         if (!af_noautofire[i]) {
2025             if (af_autofire[i])
2026                 sprintf(tmp, "%d=%02d  ", i + 1, af_autofire[i]);
2027             else
2028                 sprintf(tmp, "%d=NO  ", i + 1);
2029         } else
2030             sprintf(tmp, "%d=OFF ", i + 1);
2031         strcat(msg, tmp);
2032     }
2033     usrintf_showmessage(msg);
2034 #endif
2035 }
2036 
seq_pressed_with_autofire(struct InputPort * in,InputSeq * code)2037 int seq_pressed_with_autofire(struct InputPort *in,InputSeq* code)
2038 {
2039     int i, impport, ret;
2040 
2041     impport = in->type & ~IPF_MASK;
2042 
2043     ret = seq_pressed(code);
2044     if (ret != 0) {
2045         for (i = 0; i < MAX_AUTOFIRE_BUTTON; i ++)
2046             if (impport == af_ipt_button[i]) {
2047                 if (!af_noautofire[i] && (af_autofire[i] > 0)
2048                     && (af_autopressed[i] >= af_autofire[i])) {
2049                     ret = 0;
2050                     af_autopressed[i] = 0;
2051                 }
2052                 else
2053                     af_autopressed[i] ++;
2054             }
2055 
2056         AfButton(impport);
2057     }
2058 
2059     return ret;
2060 }
2061 
2062 #endif
2063