1 /* 2 * Copyright (c) 1988 Regents of the University of California. 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms are permitted 6 * provided that the above copyright notice and this paragraph are 7 * duplicated in all such forms and that any documentation, 8 * advertising materials, and other materials related to such 9 * distribution and use acknowledge that the software was developed 10 * by the University of California, Berkeley. The name of the 11 * University may not be used to endorse or promote products derived 12 * from this software without specific prior written permission. 13 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR 14 * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED 15 * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. 16 */ 17 18 #ifndef lint 19 static char sccsid[] = "@(#)apilib.c 4.1 (Berkeley) 12/04/88"; 20 #endif /* not lint */ 21 22 #include "../ctlr/api.h" 23 24 #include "apilib.h" 25 26 int 27 api_sup_errno = 0, /* Supervisor error number */ 28 api_sup_fcn_id = 0, /* Supervisor function id (0x12) */ 29 api_fcn_errno = 0, /* Function error number */ 30 api_fcn_fcn_id = 0; /* Function ID (0x6b, etc.) */ 31 32 static int 33 gate_sessmgr = 0, 34 gate_keyboard = 0, 35 gate_copy = 0, 36 gate_oiam = 0; 37 38 /* 39 * Issue an API request, with reg structures supplied by the caller. 40 * 41 * Only certain routines need this (supervisor services come to mind). 42 */ 43 44 static int 45 api_issue_regs(ah, al, bh, bl, cx, dx, parms, length, regs, sregs) 46 int ah, al, bh, bl, cx, dx; 47 char *parms; 48 int length; 49 union REGS *regs; 50 struct SREGS *sregs; 51 { 52 char far *ourseg = parms; 53 54 regs->h.ah = ah; 55 regs->h.al = al; 56 regs->h.bh = bh; 57 regs->h.bl = bl; 58 regs->x.cx = cx; 59 regs->x.dx = dx; 60 sregs->es = FP_SEG(ourseg); 61 regs->x.di = FP_OFF(ourseg); 62 63 #if defined(MSDOS) 64 int86x(API_INTERRUPT_NUMBER, regs, regs, sregs); 65 #endif /* defined(MSDOS) */ 66 #if defined(unix) 67 api_exch_api(regs, sregs, parms, length); 68 #endif /* defined(unix) */ 69 70 if (regs->h.cl != 0) { 71 api_sup_errno = regs->h.cl; 72 return -1; 73 } else { 74 return 0; 75 } 76 } 77 78 79 /* 80 * Issue an API request without requiring caller to supply 81 * registers. Most routines use this. 82 */ 83 84 static int 85 api_issue(ah, al, bh, bl, cx, dx, parms, length) 86 int 87 ah, 88 al, 89 bh, 90 bl, 91 cx, 92 dx; 93 char *parms; 94 int length; /* Length of parms */ 95 { 96 union REGS regs; 97 struct SREGS sregs; 98 99 return api_issue_regs(ah, al, bh, bl, cx, dx, parms, length, ®s, &sregs); 100 } 101 102 /* 103 * Supervisor Services 104 */ 105 106 int 107 api_name_resolve(name) 108 char *name; 109 { 110 NameResolveParms parms; 111 int i; 112 union REGS regs; 113 struct SREGS sregs; 114 115 for (i = 0; i < sizeof parms.gate_name; i++) { 116 if (*name) { 117 parms.gate_name[i] = *name++; 118 } else { 119 parms.gate_name[i] = ' '; 120 } 121 } 122 123 if (api_issue_regs(NAME_RESOLUTION, 0, 0, 0, 0, 0, (char *) &parms, 124 sizeof parms, ®s, &sregs) == -1) { 125 return -1; 126 } else { 127 return regs.x.dx; 128 } 129 } 130 131 #if defined(unix) 132 /* 133 * Block until the oia or ps is modified. 134 */ 135 136 int 137 api_ps_or_oia_modified() 138 { 139 union REGS regs; 140 struct SREGS sregs; 141 142 if (api_issue_regs(PS_OR_OIA_MODIFIED, 0, 0, 0, 0, 0, (char *) 0, 143 0, ®s, &sregs) == -1) { 144 return -1; 145 } else { 146 return 0; 147 } 148 } 149 #endif /* defined(unix) */ 150 151 /* 152 * Session Information Services 153 */ 154 155 api_query_session_id(parms) 156 QuerySessionIdParms *parms; 157 { 158 if (api_issue(0x09, QUERY_SESSION_ID, 0x80, 0x20, 0, 159 gate_sessmgr, (char *)parms, sizeof *parms) == -1) { 160 api_fcn_errno = 0; 161 api_fcn_fcn_id = 0; 162 return -1; 163 } else if (parms->rc == 0) { 164 return 0; 165 } else { 166 api_fcn_errno = parms->rc; 167 api_fcn_fcn_id = parms->function_id; 168 return -1; 169 } 170 } 171 172 173 api_query_session_parameters(parms) 174 QuerySessionParametersParms *parms; 175 { 176 if (api_issue(0x09, QUERY_SESSION_PARAMETERS, 0x80, 0x20, 0, 177 gate_sessmgr, (char *)parms, sizeof *parms) == -1) { 178 api_fcn_errno = 0; 179 api_fcn_fcn_id = 0; 180 return -1; 181 } else if (parms->rc == 0) { 182 return 0; 183 } else { 184 api_fcn_errno = parms->rc; 185 api_fcn_fcn_id = parms->function_id; 186 return -1; 187 } 188 } 189 190 api_query_session_cursor(parms) 191 QuerySessionCursorParms *parms; 192 { 193 if (api_issue(0x09, QUERY_SESSION_CURSOR, 0x80, 0x20, 0xff, 194 gate_sessmgr, (char *)parms, sizeof *parms) == -1) { 195 api_fcn_errno = 0; 196 api_fcn_fcn_id = 0; 197 return -1; 198 } else if (parms->rc == 0) { 199 return 0; 200 } else { 201 api_fcn_errno = parms->rc; 202 api_fcn_fcn_id = parms->function_id; 203 return -1; 204 } 205 } 206 207 /* 208 * Keyboard Services 209 */ 210 211 api_connect_to_keyboard(parms) 212 ConnectToKeyboardParms *parms; 213 { 214 if (api_issue(0x09, CONNECT_TO_KEYBOARD, 0x80, 0x20, 0, 215 gate_keyboard, (char *)parms, sizeof *parms) == -1) { 216 api_fcn_errno = 0; 217 api_fcn_fcn_id = 0; 218 return -1; 219 } else if (parms->rc == 0) { 220 return 0; 221 } else { 222 api_fcn_errno = parms->rc; 223 api_fcn_fcn_id = parms->function_id; 224 return -1; 225 } 226 } 227 228 229 api_disconnect_from_keyboard(parms) 230 DisconnectFromKeyboardParms *parms; 231 { 232 if (api_issue(0x09, DISCONNECT_FROM_KEYBOARD, 0x80, 0x20, 0, 233 gate_keyboard, (char *)parms, sizeof *parms) == -1) { 234 api_fcn_errno = 0; 235 api_fcn_fcn_id = 0; 236 return -1; 237 } else if (parms->rc == 0) { 238 return 0; 239 } else { 240 api_fcn_errno = parms->rc; 241 api_fcn_fcn_id = parms->function_id; 242 return -1; 243 } 244 } 245 246 247 api_write_keystroke(parms) 248 WriteKeystrokeParms *parms; 249 { 250 if (api_issue(0x09, WRITE_KEYSTROKE, 0x80, 0x20, 0, 251 gate_keyboard, (char *)parms, sizeof *parms) == -1) { 252 api_fcn_errno = 0; 253 api_fcn_fcn_id = 0; 254 return -1; 255 } else if (parms->rc == 0) { 256 return 0; 257 } else { 258 api_fcn_errno = parms->rc; 259 api_fcn_fcn_id = parms->function_id; 260 return -1; 261 } 262 } 263 264 265 api_disable_input(parms) 266 DisableInputParms *parms; 267 { 268 if (api_issue(0x09, DISABLE_INPUT, 0x80, 0x20, 0, 269 gate_keyboard, (char *)parms, sizeof *parms) == -1) { 270 api_fcn_errno = 0; 271 api_fcn_fcn_id = 0; 272 return -1; 273 } else if (parms->rc == 0) { 274 return 0; 275 } else { 276 api_fcn_errno = parms->rc; 277 api_fcn_fcn_id = parms->function_id; 278 return -1; 279 } 280 } 281 282 api_enable_input(parms) 283 EnableInputParms *parms; 284 { 285 if (api_issue(0x09, ENABLE_INPUT, 0x80, 0x20, 0, 286 gate_keyboard, (char *)parms, sizeof *parms) == -1) { 287 api_fcn_errno = 0; 288 api_fcn_fcn_id = 0; 289 return -1; 290 } else if (parms->rc == 0) { 291 return 0; 292 } else { 293 api_fcn_errno = parms->rc; 294 api_fcn_fcn_id = parms->function_id; 295 return -1; 296 } 297 } 298 299 /* 300 * Copy Services 301 */ 302 303 api_copy_string(parms) 304 CopyStringParms *parms; 305 { 306 if (api_issue(0x09, COPY_STRING, 0x80, 0x20, 0xff, 307 gate_copy, (char *)parms, sizeof *parms) == -1) { 308 api_fcn_errno = 0; 309 api_fcn_fcn_id = 0; 310 return -1; 311 } else if (parms->rc == 0) { 312 return 0; 313 } else { 314 api_fcn_errno = parms->rc; 315 api_fcn_fcn_id = parms->function_id; 316 return -1; 317 } 318 } 319 320 /* 321 * Operator Information Area Services 322 */ 323 324 api_read_oia_group(parms) 325 ReadOiaGroupParms *parms; 326 { 327 if (api_issue(0x09, READ_OIA_GROUP, 0x80, 0x20, 0xff, 328 gate_oiam, (char *)parms, sizeof *parms) == -1) { 329 api_fcn_errno = 0; 330 api_fcn_fcn_id = 0; 331 return -1; 332 } else if (parms->rc == 0) { 333 return 0; 334 } else { 335 api_fcn_errno = parms->rc; 336 api_fcn_fcn_id = parms->function_id; 337 return -1; 338 } 339 } 340 341 /* 342 * The "we are done" routine. This gets called last. 343 */ 344 345 api_finish() 346 { 347 #if defined(unix) 348 if (api_close_api() == -1) { 349 return -1; 350 } else { 351 return 0; 352 } 353 #endif /* defined(unix) */ 354 } 355 356 357 /* 358 * The initialization routine. Be sure to call this first. 359 */ 360 361 api_init() 362 { 363 #if defined(MSDOS) 364 union REGS regs; 365 struct SREGS sregs; 366 367 regs.h.ah = 0x35; 368 regs.h.al = API_INTERRUPT_NUMBER; 369 intdosx(®s, ®s, &sregs); 370 371 if ((regs.x.bx == 0) && (sregs.es == 0)) { 372 return 0; /* Interrupt not being handled */ 373 } 374 #endif /* defined(MSDOS) */ 375 #if defined(unix) 376 if (api_open_api((char *)0) == -1) { 377 return 0; 378 } 379 #endif /* defined(unix) */ 380 381 gate_sessmgr = api_name_resolve("SESSMGR"); 382 gate_keyboard = api_name_resolve("KEYBOARD"); 383 gate_copy = api_name_resolve("COPY"); 384 gate_oiam = api_name_resolve("OIAM"); 385 386 if ((gate_sessmgr == gate_keyboard) || 387 (gate_sessmgr == gate_copy) || 388 (gate_sessmgr == gate_oiam) || 389 (gate_keyboard == gate_copy) || 390 (gate_keyboard == gate_oiam) || 391 (gate_copy == gate_oiam)) { 392 return 0; /* Interrupt doesn't seem correct */ 393 } 394 return 1; 395 } 396