1 /*
   2  * CDDL HEADER START
   3  *
   4  * The contents of this file are subject to the terms of the
   5  * Common Development and Distribution License (the "License").
   6  * You may not use this file except in compliance with the License.
   7  *
   8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
   9  * or http://www.opensolaris.org/os/licensing.
  10  * See the License for the specific language governing permissions
  11  * and limitations under the License.
  12  *
  13  * When distributing Covered Code, include this CDDL HEADER in each
  14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15  * If applicable, add the following below this CDDL HEADER, with the
  16  * fields enclosed by brackets "[]" replaced with your own identifying
  17  * information: Portions Copyright [yyyy] [name of copyright owner]
  18  *
  19  * CDDL HEADER END
  20  */
  21 /*      Copyright (c) 1990, 1991 UNIX System Laboratories, Inc. */
  22 /*      Copyright (c) 1984, 1986, 1987, 1988, 1989, 1990 AT&T       */
  23 /*        All Rights Reserved   */
  24 
  25 /*
  26  * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
  27  * Use is subject to license terms.
  28  */
  29 
  30 #define KEYMAP_SIZE_VARIABLE
  31 
  32 #include <sys/types.h>
  33 #include <sys/errno.h>
  34 #include <sys/inline.h>
  35 #include <sys/termio.h>
  36 #include <sys/stropts.h>
  37 #include <sys/termios.h>
  38 #include <sys/stream.h>
  39 #include <sys/strtty.h>
  40 #include <sys/strsubr.h>
  41 #include <sys/strsun.h>
  42 #include <sys/ddi.h>
  43 #include <sys/sunddi.h>
  44 #include <sys/note.h>
  45 #include "sys/consdev.h"
  46 #include <sys/kbd.h>
  47 #include <sys/kbtrans.h>
  48 #include "kb8042.h"
  49 
  50 #include <sys/i8042.h>
  51 
  52 #include "sys/kbio.h"           /* for KIOCSLAYOUT */
  53 #include "sys/stat.h"
  54 #include "sys/reboot.h"
  55 #include <sys/promif.h>
  56 #include <sys/beep.h>
  57 #include <sys/inttypes.h>
  58 #include <sys/policy.h>
  59 
  60 /*
  61  * For any keyboard, there is a unique code describing the position
  62  * of the key on a keyboard. We refer to the code as "station number".
  63  * The following table is used to map the station numbers from ps2
  64  * AT/XT keyboards to that of a USB one.
  65  *
  66  * A mapping was added for entry K8042_STOP, to map to USB key code 120 (which
  67  * maps to the STOP key) when in KB_USB mode, and maps to a HOLE entry
  68  * when in KB_PC mode.  Note that this does not need to be made conditional
  69  * on the architecture for which this module is complied because there are no
  70  * keys that map to K8042_STOP on non-SPARC platforms.
  71  */
  72 static kbtrans_key_t keytab_pc2usb[KBTRANS_KEYNUMS_MAX] = {
  73 /*  0 */        0,      53,     30,     31,     32,     33,     34,     35,
  74 /*  8 */        36,     37,     38,     39,     45,     46,     137,    42,
  75 /* 16 */        43,     20,     26,     8,      21,     23,     28,     24,
  76 /* 24 */        12,     18,     19,     47,     48,     49,     57,     4,
  77 /* 32 */        22,     7,      9,      10,     11,     13,     14,     15,
  78 /* 40 */        51,     52,     50,     40,     225,    100,    29,     27,
  79 /* 48 */        6,      25,     5,      17,     16,     54,     55,     56,
  80 /* 56 */        135,    229,    224,    227,    226,    44,     230,    231,
  81 /* 64 */        228,    101,    0,      0,      0,      0,      0,      0,
  82 /* 72 */        0,      0,      0,      73,     76,     0,      0,      80,
  83 /* 80 */        74,     77,     0,      82,     81,     75,     78,     0,
  84 /* 88 */        0,      79,     83,     95,     92,     89,     0,      84,
  85 /* 96 */        96,     93,     90,     98,     85,     97,     94,     91,
  86 /* 104 */       99,     86,     87,     133,    88,     0,      41,     0,
  87 /* 112 */       58,     59,     60,     61,     62,     63,     64,     65,
  88 /* 120 */       66,     67,     68,     69,     70,     71,     72,     0,
  89 /* 128 */       0,      0,      0,      139,    138,    136,    0,      0,
  90 /* 136 */       0,      0,      0,      0,      0,      0,      0,      0,
  91 /* 144 */       0,      0,      0,      0,      0,      0,      0,      0,
  92 /* 152 */       0,      0,      0,      0,      0,      0,      0,      0,
  93 /* 160 */       120,    0,      0,      0,      0,      0,      0,      0,
  94 /* 168 */       0,      0,      0,      0,      0,      0,      0,      0,
  95 /* 176 */       0,      0,      0,      0,      0,      0,      0,      0,
  96 /* 184 */       0,      0,      0,      0,      0,      0,      0,      0,
  97 /* 192 */       0,      0,      0,      0,      0,      0,      0,      0,
  98 /* 200 */       0,      0,      0,      0,      0,      0,      0,      0,
  99 /* 208 */       0,      0,      0,      0,      0,      0,      0,      0,
 100 /* 216 */       0,      0,      0,      0,      0,      0,      0,      0,
 101 /* 224 */       0,      0,      0,      0,      0,      0,      0,      0,
 102 /* 232 */       0,      128,    129,    127,    0,      0,      0,      0,
 103 /* 240 */       0,      0,      0,      0,      0,      0,      0,      0,
 104 /* 248 */       0,      0,      0,      0
 105 };
 106 
 107 #ifdef __sparc
 108 #define USECS_PER_WAIT 100
 109 #define MAX_WAIT_USECS 100000 /* in usecs = 100 ms */
 110 #define MIN_DELAY_USECS USECS_PER_WAIT
 111 
 112 boolean_t kb8042_warn_unknown_scanset = B_TRUE;
 113 int kb8042_default_scanset = 2;
 114 
 115 #endif
 116 
 117 #define MAX_KB8042_WAIT_MAX_MS  500             /* 500ms total */
 118 #define MAX_KB8042_RETRIES      5
 119 
 120 enum state_return { STATE_NORMAL, STATE_INTERNAL };
 121 
 122 static void kb8042_init(struct kb8042 *kb8042, boolean_t from_resume);
 123 static uint_t kb8042_intr(caddr_t arg);
 124 static void kb8042_wait_poweron(struct kb8042 *kb8042);
 125 static void kb8042_send_to_keyboard(struct kb8042 *, int, boolean_t);
 126 static int kb8042_xlate_leds(int);
 127 static void kb8042_setled(struct kb8042 *, int led_state, boolean_t polled);
 128 static void kb8042_streams_setled(struct kbtrans_hardware *hw, int led_state);
 129 static void kb8042_polled_setled(struct kbtrans_hardware *hw, int led_state);
 130 static boolean_t kb8042_polled_keycheck(
 131                         struct kbtrans_hardware *hw, int *key,
 132                         enum keystate *state);
 133 static void kb8042_get_initial_leds(struct kb8042 *, int *, int *);
 134 static boolean_t kb8042_autorepeat_detect(struct kb8042 *kb8042, int key_pos,
 135                         enum keystate state);
 136 static void kb8042_type4_cmd(struct kb8042 *kb8042, int cmd);
 137 static void kb8042_ioctlmsg(struct kb8042 *kb8042, queue_t *, mblk_t *);
 138 static void kb8042_iocdatamsg(queue_t *, mblk_t *);
 139 static void kb8042_process_key(struct kb8042 *, kbtrans_key_t, enum keystate);
 140 static int kb8042_polled_ischar(cons_polledio_arg_t arg);
 141 static int kb8042_polled_getchar(cons_polledio_arg_t arg);
 142 static void kb8042_cleanup(struct kb8042 *kb8042);
 143 
 144 static struct kbtrans_callbacks kb8042_callbacks = {
 145         kb8042_streams_setled,
 146         kb8042_polled_setled,
 147         kb8042_polled_keycheck,
 148 };
 149 
 150 extern struct keyboard keyindex_pc;
 151 
 152 #define DRIVER_NAME(dip) ddi_driver_name(dip)
 153 
 154 static  char    module_name[] = "kb8042";
 155 
 156 static int kb8042_open(queue_t *qp, dev_t *devp, int flag, int sflag,
 157                         cred_t *credp);
 158 static int kb8042_close(queue_t *qp, int flag, cred_t *credp);
 159 static int kb8042_wsrv();
 160 
 161 struct module_info kb8042_sinfo = {
 162         .mi_idnum = 42,                 /* Module ID */
 163         .mi_idname = module_name,       /* Module name */
 164         .mi_minpsz = 0,                 /* Minimum packet size */
 165         .mi_maxpsz = 32,                /* Maximum packet size */
 166         .mi_hiwat = 256,                /* High water mark */
 167         .mi_lowat = 128                 /* Low water mark */
 168 };
 169 
 170 static struct qinit kb8042_rinit = {
 171         .qi_putp = NULL,
 172         .qi_srvp = NULL,
 173         .qi_qopen = kb8042_open,
 174         .qi_qclose = kb8042_close,
 175         .qi_qadmin = NULL,
 176         .qi_minfo = &kb8042_sinfo,
 177         .qi_mstat = NULL,
 178         .qi_rwp = NULL,
 179         .qi_infop = NULL,
 180         .qi_struiot = 0
 181 };
 182 
 183 static struct qinit kb8042_winit = {
 184         .qi_putp = putq,
 185         .qi_srvp = kb8042_wsrv,
 186         .qi_qopen = kb8042_open,
 187         .qi_qclose = kb8042_close,
 188         .qi_qadmin = NULL,
 189         .qi_minfo = &kb8042_sinfo,
 190         .qi_mstat = NULL,
 191         .qi_rwp = NULL,
 192         .qi_infop = NULL,
 193         .qi_struiot = 0
 194 };
 195 
 196 struct streamtab kb8042_str_info = {
 197         .st_rdinit = &kb8042_rinit,
 198         .st_wrinit = &kb8042_winit,
 199         .st_muxrinit = NULL,
 200         .st_muxwinit = NULL
 201 };
 202 
 203 struct kb8042   Kdws = {0};
 204 static dev_info_t *kb8042_dip = NULL;
 205 
 206 static int kb8042_getinfo(dev_info_t *dip, ddi_info_cmd_t infocmd, void *arg,
 207                 void **result);
 208 static int kb8042_attach(dev_info_t *, ddi_attach_cmd_t);
 209 static int kb8042_detach(dev_info_t *, ddi_detach_cmd_t);
 210 
 211 static  struct cb_ops cb_kb8042_ops = {
 212         .cb_open = nulldev,
 213         .cb_close = nulldev,
 214         .cb_strategy = nodev,
 215         .cb_print = nodev,
 216         .cb_dump = nodev,
 217         .cb_read = nodev,
 218         .cb_write = nodev,
 219         .cb_ioctl = nodev,
 220         .cb_devmap = nodev,
 221         .cb_mmap = nodev,
 222         .cb_segmap = nodev,
 223         .cb_chpoll = nochpoll,
 224         .cb_prop_op = ddi_prop_op,
 225         .cb_str = &kb8042_str_info,
 226         .cb_flag = D_MP,
 227         .cb_rev = CB_REV,
 228         .cb_aread = nodev,
 229         .cb_awrite = nodev
 230 };
 231 
 232 struct dev_ops kb8042_ops = {
 233         .devo_rev = DEVO_REV,
 234         .devo_refcnt = 0,
 235         .devo_getinfo = kb8042_getinfo,
 236         .devo_identify = nulldev,
 237         .devo_probe = nulldev,
 238         .devo_attach = kb8042_attach,
 239         .devo_detach = kb8042_detach,
 240         .devo_reset = nodev,
 241         .devo_cb_ops = &cb_kb8042_ops,
 242         .devo_bus_ops = NULL,
 243         .devo_power = NULL,
 244         .devo_quiesce = ddi_quiesce_not_needed
 245 };
 246 
 247 
 248 /*
 249  * This is the loadable module wrapper.
 250  */
 251 #include <sys/modctl.h>
 252 
 253 /*
 254  * Module linkage information for the kernel.
 255  */
 256 static struct modldrv modldrv = {
 257         .drv_modops = &mod_driverops,       /* Type of module. */
 258         .drv_linkinfo = "PS/2 keyboard driver",
 259         .drv_dev_ops = &kb8042_ops, /* driver ops */
 260 };
 261 
 262 static struct modlinkage modlinkage = {
 263         .ml_rev = MODREV_1,
 264         .ml_linkage = { &modldrv, NULL }
 265 };
 266 
 267 int
 268 _init(void)
 269 {
 270         int     rv;
 271 
 272         rv = mod_install(&modlinkage);
 273         return (rv);
 274 }
 275 
 276 
 277 int
 278 _fini(void)
 279 {
 280         return (mod_remove(&modlinkage));
 281 }
 282 
 283 int
 284 _info(struct modinfo *modinfop)
 285 {
 286         return (mod_info(&modlinkage, modinfop));
 287 }
 288 
 289 #ifdef __sparc
 290 static boolean_t
 291 kb8042_is_input_avail(struct kb8042 *kb8042, int timeout_usec, boolean_t polled)
 292 {
 293         int i;
 294         int port = (polled == B_TRUE) ? I8042_POLL_INPUT_AVAIL :
 295             I8042_INT_INPUT_AVAIL;
 296         int reps = timeout_usec / USECS_PER_WAIT;
 297 
 298         for (i = 0; i < reps; i++) {
 299                 if (ddi_get8(kb8042->handle, kb8042->addr + port) != 0)
 300                         return (B_TRUE);
 301 
 302                 if (i < (reps - 1))
 303                         drv_usecwait(USECS_PER_WAIT);
 304         }
 305         return (B_FALSE);
 306 }
 307 
 308 static void
 309 kb8042_clear_input_buffer(struct kb8042 *kb8042, boolean_t polled)
 310 {
 311         int port = (polled == B_TRUE) ? I8042_POLL_INPUT_DATA :
 312             I8042_INT_INPUT_DATA;
 313 
 314         while (kb8042_is_input_avail(kb8042, MIN_DELAY_USECS, polled)) {
 315                 (void) ddi_get8(kb8042->handle, kb8042->addr + port);
 316         }
 317 }
 318 
 319 /*
 320  * kb8042_send_and_expect does all its I/O via polling interfaces
 321  */
 322 static boolean_t
 323 kb8042_send_and_expect(struct kb8042 *kb8042, uint8_t send, uint8_t expect,
 324     int timeout, int *error, uint8_t *got)
 325 {
 326         uint8_t datab;
 327         int err;
 328         boolean_t rval;
 329 
 330         ddi_put8(kb8042->handle,
 331             kb8042->addr + I8042_POLL_OUTPUT_DATA, send);
 332 
 333         if (kb8042_is_input_avail(kb8042, timeout, B_TRUE)) {
 334                 err = 0;
 335                 datab = ddi_get8(kb8042->handle,
 336                     kb8042->addr + I8042_POLL_INPUT_DATA);
 337                 rval = ((datab == expect) ? B_TRUE : B_FALSE);
 338         } else {
 339                 err = EAGAIN;
 340                 rval = B_FALSE;
 341         }
 342 
 343         if (error != NULL)
 344                 *error = err;
 345         if (got != NULL)
 346                 *got = datab;
 347         return (rval);
 348 }
 349 
 350 static const char *
 351 kb8042_error_string(int errcode)
 352 {
 353         switch (errcode) {
 354         case EAGAIN:
 355                 return ("Timed out");
 356         default:
 357                 return ("Unknown error");
 358         }
 359 }
 360 
 361 /*
 362  * kb8042_read_scanset works properly because it is called before ddi_add_intr
 363  * (if it is called after ddi_add_intr, i8042_intr would call kb8042_intr
 364  * instead of just storing the data that comes in from the keyboard, which
 365  * would prevent the code here from getting it.)
 366  */
 367 static int
 368 kb8042_read_scanset(struct kb8042 *kb8042)
 369 {
 370         int scanset = -1;
 371         int err;
 372         uint8_t got;
 373 
 374         kb8042_clear_input_buffer(kb8042, B_TRUE);
 375 
 376         /*
 377          * Send a "change scan code set" command to the keyboard.
 378          * It should respond with an ACK.
 379          */
 380         if (kb8042_send_and_expect(kb8042, KB_SET_SCAN, KB_ACK, MAX_WAIT_USECS,
 381             &err, &got) != B_TRUE) {
 382                 goto fail_read_scanset;
 383         }
 384 
 385         /*
 386          * Send a 0.  The keyboard should ACK the 0, then it should send the
 387          * scan code set in use.
 388          */
 389         if (kb8042_send_and_expect(kb8042, 0, KB_ACK, MAX_WAIT_USECS, &err,
 390             &got) != B_TRUE) {
 391                 goto fail_read_scanset;
 392         }
 393 
 394         /*
 395          * The next input byte from the keyboard should be the scan code
 396          * set in use, though some keyboards like to send a few more acks
 397          * just for fun, so blow past those to get the keyboard scan code.
 398          */
 399         while (kb8042_is_input_avail(kb8042, MAX_WAIT_USECS, B_TRUE) &&
 400             (scanset = ddi_get8(kb8042->handle,
 401             kb8042->addr + I8042_POLL_INPUT_DATA)) == KB_ACK)
 402                 ;
 403 
 404 #ifdef DEBUG
 405         cmn_err(CE_NOTE, "!Scan code set from keyboard is `%d'.",
 406             scanset);
 407 #endif
 408 
 409         return (scanset);
 410 
 411 fail_read_scanset:
 412 #ifdef DEBUG
 413         if (err == 0)
 414                 cmn_err(CE_NOTE, "Could not read current scan set from "
 415                     "keyboard: %s. (Expected 0x%x, but got 0x%x).",
 416                     kb8042_error_string(err), KB_ACK, got);
 417         else
 418                 cmn_err(CE_NOTE, "Could not read current scan set from "
 419                     "keyboard: %s.", kb8042_error_string(err));
 420 #endif
 421         return (-1);
 422 }
 423 #endif
 424 
 425 static int
 426 kb8042_attach(dev_info_t *devi, ddi_attach_cmd_t cmd)
 427 {
 428         int     rc;
 429         int     scanset;
 430         int     leds;
 431 
 432         struct kb8042   *kb8042 = &Kdws;
 433         static ddi_device_acc_attr_t attr = {
 434                 DDI_DEVICE_ATTR_V0,
 435                 DDI_NEVERSWAP_ACC,
 436                 DDI_STRICTORDER_ACC,
 437         };
 438 
 439         switch (cmd) {
 440         case DDI_RESUME:
 441                 leds = kb8042->leds.commanded;
 442                 kb8042->w_init = 0;
 443                 kb8042_init(kb8042, B_TRUE);
 444                 kb8042_setled(kb8042, leds, B_FALSE);
 445                 mutex_enter(&kb8042->w_hw_mutex);
 446                 kb8042->suspended = B_FALSE;
 447                 if (kb8042->w_qp != NULL) {
 448                         enableok(WR(kb8042->w_qp));
 449                         qenable(WR(kb8042->w_qp));
 450                 }
 451                 cv_broadcast(&kb8042->suspend_cv);
 452                 mutex_exit(&kb8042->w_hw_mutex);
 453                 return (DDI_SUCCESS);
 454 
 455         case DDI_ATTACH:
 456                 if (kb8042_dip != NULL)
 457                         return (DDI_FAILURE);
 458                 /* The rest of the function is for attach */
 459                 break;
 460 
 461         default:
 462                 return (DDI_FAILURE);
 463         }
 464 
 465         kb8042->debugger.mod1 = 58;  /* Left Ctrl */
 466         kb8042->debugger.mod2 = 60;  /* Left Alt */
 467         kb8042->debugger.trigger = 33;       /* D */
 468         kb8042->debugger.mod1_down = B_FALSE;
 469         kb8042->debugger.mod2_down = B_FALSE;
 470         kb8042->debugger.enabled = B_FALSE;
 471 
 472         kb8042_dip = devi;
 473         kb8042->init_state = KB8042_UNINITIALIZED;
 474 
 475         kb8042->polled_synthetic_release_pending = B_FALSE;
 476 
 477         if (ddi_create_minor_node(devi, module_name, S_IFCHR, 0,
 478             DDI_NT_KEYBOARD, 0) == DDI_FAILURE) {
 479                 goto failure;
 480         }
 481 
 482         kb8042->init_state |= KB8042_MINOR_NODE_CREATED;
 483 
 484         rc = ddi_regs_map_setup(devi, 0, (caddr_t *)&kb8042->addr,
 485             (offset_t)0, (offset_t)0, &attr, &kb8042->handle);
 486         if (rc != DDI_SUCCESS) {
 487 #ifdef DEBUG
 488                 cmn_err(CE_WARN, "kb8042_attach:  can't map registers");
 489 #endif
 490                 goto failure;
 491         }
 492 
 493         kb8042->init_state |= KB8042_REGS_MAPPED;
 494 
 495         if (ddi_get_iblock_cookie(devi, 0, &kb8042->w_iblock) !=
 496             DDI_SUCCESS) {
 497                 cmn_err(CE_WARN, "kb8042_attach:  Can't get iblock cookie");
 498                 goto failure;
 499         }
 500 
 501         mutex_init(&kb8042->w_hw_mutex, NULL, MUTEX_DRIVER, kb8042->w_iblock);
 502         cv_init(&kb8042->ops_cv, NULL, CV_DRIVER, NULL);
 503         cv_init(&kb8042->suspend_cv, NULL, CV_DRIVER, NULL);
 504         cv_init(&kb8042->cmd_cv, NULL, CV_DRIVER, NULL);
 505         kb8042->init_state |= KB8042_HW_MUTEX_INITTED;
 506 
 507         kb8042_init(kb8042, B_FALSE);
 508 
 509 #ifdef __sparc
 510         /* Detect the scan code set currently in use */
 511         scanset = kb8042_read_scanset(kb8042);
 512 
 513         if (scanset < 0 && kb8042_warn_unknown_scanset) {
 514 
 515                 cmn_err(CE_WARN, "Cannot determine keyboard scan code set ");
 516                 cmn_err(CE_CONT, "(is the keyboard plugged in?). ");
 517                 cmn_err(CE_CONT, "Defaulting to scan code set %d.  If the "
 518                     "keyboard does not ", kb8042_default_scanset);
 519                 cmn_err(CE_CONT, "work properly, add "
 520                     "`set kb8042:kb8042_default_scanset=%d' to /etc/system ",
 521                     (kb8042_default_scanset == 1) ? 2 : 1);
 522                 cmn_err(CE_CONT, "(via network or with a USB keyboard) and "
 523                     "restart the system.  If you ");
 524                 cmn_err(CE_CONT, "do not want to see this message in the "
 525                     "future, add ");
 526                 cmn_err(CE_CONT, "`set kb8042:kb8042_warn_unknown_scanset=0' "
 527                     "to /etc/system.\n");
 528 
 529                 /* Use the default scan code set. */
 530                 scanset = kb8042_default_scanset;
 531         }
 532 #else
 533         /* x86 systems use scan code set 1 -- no detection required */
 534         scanset = 1;
 535 #endif
 536         if (KeyboardConvertScan_init(kb8042, scanset) != DDI_SUCCESS) {
 537                 cmn_err(CE_WARN, "Cannot initialize keyboard scan converter: "
 538                     "Unknown scan code set `%d'.", scanset);
 539                 /* Scan code set is not supported */
 540                 goto failure;
 541         }
 542 
 543         /*
 544          * Turn on interrupts...
 545          */
 546         if (ddi_add_intr(devi, 0,
 547             &kb8042->w_iblock, (ddi_idevice_cookie_t *)NULL,
 548             kb8042_intr, (caddr_t)kb8042) != DDI_SUCCESS) {
 549                 cmn_err(CE_WARN, "kb8042_attach: cannot add interrupt");
 550                 goto failure;
 551         }
 552 
 553         kb8042->init_state |= KB8042_INTR_ADDED;
 554 
 555         ddi_report_dev(devi);
 556 
 557 #ifdef DEBUG
 558         cmn_err(CE_CONT, "?%s instance #%d READY\n",
 559             DRIVER_NAME(devi), ddi_get_instance(devi));
 560 #endif
 561 
 562         return (DDI_SUCCESS);
 563 
 564 failure:
 565         kb8042_cleanup(kb8042);
 566         return (DDI_FAILURE);
 567 }
 568 
 569 static int
 570 kb8042_detach(dev_info_t *dip, ddi_detach_cmd_t cmd)
 571 {
 572         struct kb8042 *kb8042 = &Kdws;
 573 
 574         switch (cmd) {
 575         case DDI_SUSPEND:
 576                 mutex_enter(&kb8042->w_hw_mutex);
 577                 ASSERT(kb8042->ops >= 0);
 578                 while (kb8042->ops > 0)
 579                         cv_wait(&kb8042->ops_cv, &kb8042->w_hw_mutex);
 580                 kb8042->suspended = B_TRUE;
 581                 mutex_exit(&kb8042->w_hw_mutex);
 582                 return (DDI_SUCCESS);
 583 
 584         case DDI_DETACH:
 585                 /* If someone has a stream open, fail to detach */
 586                 if (kb8042->w_qp != NULL)
 587                         return (DDI_FAILURE);
 588 
 589                 ASSERT(kb8042_dip == dip);
 590 
 591                 kb8042_cleanup(kb8042);
 592 
 593                 return (DDI_SUCCESS);
 594 
 595         default:
 596                 return (DDI_FAILURE);
 597         }
 598 }
 599 
 600 /*ARGSUSED*/
 601 static int
 602 kb8042_getinfo(
 603     dev_info_t *dip,
 604     ddi_info_cmd_t infocmd,
 605     void *arg,
 606     void **result)
 607 {
 608         register int error;
 609 
 610         switch (infocmd) {
 611         case DDI_INFO_DEVT2DEVINFO:
 612                 if (kb8042_dip == NULL) {
 613                         error = DDI_FAILURE;
 614                 } else {
 615                         *result = (void *) kb8042_dip;
 616                         error = DDI_SUCCESS;
 617                 }
 618                 break;
 619         case DDI_INFO_DEVT2INSTANCE:
 620                 *result = (void *)0;
 621                 error = DDI_SUCCESS;
 622                 break;
 623         default:
 624                 error = DDI_FAILURE;
 625                 break;
 626         }
 627         return (error);
 628 }
 629 
 630 static void
 631 kb8042_cleanup(struct kb8042 *kb8042)
 632 {
 633         ASSERT(kb8042_dip != NULL);
 634 
 635         if (kb8042->init_state & KB8042_INTR_ADDED)
 636                 ddi_remove_intr(kb8042_dip, 0, kb8042->w_iblock);
 637 
 638         if (kb8042->init_state & KB8042_HW_MUTEX_INITTED) {
 639                 cv_destroy(&kb8042->cmd_cv);
 640                 cv_destroy(&kb8042->suspend_cv);
 641                 cv_destroy(&kb8042->ops_cv);
 642                 mutex_destroy(&kb8042->w_hw_mutex);
 643         }
 644 
 645         if (kb8042->init_state & KB8042_REGS_MAPPED)
 646                 ddi_regs_map_free(&kb8042->handle);
 647 
 648         if (kb8042->init_state & KB8042_MINOR_NODE_CREATED)
 649                 ddi_remove_minor_node(kb8042_dip, NULL);
 650 
 651         kb8042->init_state = KB8042_UNINITIALIZED;
 652         kb8042_dip = NULL;
 653 }
 654 
 655 static void
 656 kb8042_init(struct kb8042 *kb8042, boolean_t from_resume)
 657 {
 658         if (kb8042->w_init)
 659                 return;
 660 
 661         if (!from_resume) {
 662                 kb8042->w_kblayout = 0;      /* Default to US */
 663                 kb8042->w_qp = (queue_t *)NULL;
 664                 kb8042->simulated_kbd_type = KB_PC;
 665                 kb8042->leds.commanded = -1; /* Unknown initial state */
 666                 kb8042->leds.desired = -1;   /* Unknown initial state */
 667         }
 668 
 669         kb8042_wait_poweron(kb8042);
 670 
 671         kb8042->kb_old_key_pos = 0;
 672 
 673         /*
 674          * Explicitly grab and release the 8042 lock outside of
 675          * kb8042_send_to_keyboard, because this is the only situation
 676          * where a polling interface is used with locking required.
 677          */
 678         (void) ddi_get8(kb8042->handle, kb8042->addr + I8042_LOCK);
 679         /* Set up the command state machine and start it running. */
 680         kb8042_send_to_keyboard(kb8042, KB_ENABLE, B_TRUE);
 681         (void) ddi_get8(kb8042->handle, kb8042->addr + I8042_UNLOCK);
 682 
 683         kb8042->w_init++;
 684 
 685         (void) drv_setparm(SYSRINT, 1); /* reset keyboard interrupts */
 686 }
 687 
 688 /*ARGSUSED2*/
 689 static int
 690 kb8042_open(queue_t *qp, dev_t *devp, int flag, int sflag, cred_t *credp)
 691 {
 692         struct kb8042   *kb8042;
 693         int err = 0;
 694         int initial_leds;
 695         int initial_led_mask;
 696 
 697         kb8042 = &Kdws;
 698 
 699         mutex_enter(&kb8042->w_hw_mutex);
 700         if (qp->q_ptr) {
 701                 kb8042->w_dev = *devp;
 702                 mutex_exit(&kb8042->w_hw_mutex);
 703                 return (0);
 704         }
 705 
 706         if (secpolicy_console(credp) != 0) {
 707                 mutex_exit(&kb8042->w_hw_mutex);
 708                 return (EPERM);
 709         }
 710 
 711         while (kb8042->suspended) {
 712                 if (cv_wait_sig(&kb8042->suspend_cv, &kb8042->w_hw_mutex) ==
 713                     0) {
 714                         mutex_exit(&kb8042->w_hw_mutex);
 715                         return (EINTR);
 716                 }
 717         }
 718 
 719         kb8042->w_dev = *devp;
 720         qp->q_ptr = (caddr_t)kb8042;
 721         WR(qp)->q_ptr = qp->q_ptr;
 722         if (!kb8042->w_qp)
 723                 kb8042->w_qp = qp;
 724 
 725         ASSERT(kb8042->ops >= 0);
 726         kb8042->ops++;
 727         mutex_exit(&kb8042->w_hw_mutex);
 728 
 729         kb8042_get_initial_leds(kb8042, &initial_leds, &initial_led_mask);
 730         err = kbtrans_streams_init(qp, sflag,
 731             (struct kbtrans_hardware *)kb8042, &kb8042_callbacks,
 732             &kb8042->hw_kbtrans,
 733             initial_leds, initial_led_mask);
 734         if (err != 0)
 735                 goto out;
 736 
 737         kbtrans_streams_set_keyboard(kb8042->hw_kbtrans, KB_PC, &keyindex_pc);
 738 
 739         kb8042->polledio.cons_polledio_version = CONSPOLLEDIO_V1;
 740         kb8042->polledio.cons_polledio_argument =
 741             (cons_polledio_arg_t)kb8042;
 742         kb8042->polledio.cons_polledio_putchar = NULL;
 743         kb8042->polledio.cons_polledio_getchar =
 744             (int (*)(cons_polledio_arg_t))kb8042_polled_getchar;
 745         kb8042->polledio.cons_polledio_ischar =
 746             (boolean_t (*)(cons_polledio_arg_t))kb8042_polled_ischar;
 747         kb8042->polledio.cons_polledio_enter = NULL;
 748         kb8042->polledio.cons_polledio_exit = NULL;
 749         kb8042->polledio.cons_polledio_setled =
 750             (void (*)(cons_polledio_arg_t, int))kb8042_polled_setled;
 751         kb8042->polledio.cons_polledio_keycheck =
 752             (boolean_t (*)(cons_polledio_arg_t, int *,
 753             enum keystate *))kb8042_polled_keycheck;
 754 
 755         qprocson(qp);
 756 
 757         kbtrans_streams_enable(kb8042->hw_kbtrans);
 758 
 759 out:
 760         mutex_enter(&kb8042->w_hw_mutex);
 761         ASSERT(kb8042->ops > 0);
 762         kb8042->ops--;
 763         if (kb8042->ops == 0)
 764                 cv_broadcast(&kb8042->ops_cv);
 765         mutex_exit(&kb8042->w_hw_mutex);
 766 
 767         return (err);
 768 }
 769 
 770 /*ARGSUSED1*/
 771 static int
 772 kb8042_close(queue_t *qp, int flag, cred_t *credp)
 773 {
 774         struct kb8042   *kb8042;
 775 
 776         /* If a beep is in progress, stop that */
 777         (void) beeper_off();
 778 
 779         kb8042 = (struct kb8042 *)qp->q_ptr;
 780 
 781         mutex_enter(&kb8042->w_hw_mutex);
 782         while (kb8042->suspended) {
 783                 if (cv_wait_sig(&kb8042->suspend_cv, &kb8042->w_hw_mutex) ==
 784                     0) {
 785                         mutex_exit(&kb8042->w_hw_mutex);
 786                         return (EINTR);
 787                 }
 788         }
 789 
 790         ASSERT(kb8042->ops >= 0);
 791         kb8042->ops++;
 792         mutex_exit(&kb8042->w_hw_mutex);
 793 
 794         (void) kbtrans_streams_fini(kb8042->hw_kbtrans);
 795 
 796         kb8042->w_qp = (queue_t *)NULL;
 797         qprocsoff(qp);
 798 
 799         mutex_enter(&kb8042->w_hw_mutex);
 800         ASSERT(kb8042->ops > 0);
 801         kb8042->ops--;
 802         if (kb8042->ops == 0)
 803                 cv_broadcast(&kb8042->ops_cv);
 804         mutex_exit(&kb8042->w_hw_mutex);
 805 
 806         return (0);
 807 }
 808 
 809 static int
 810 kb8042_wsrv(queue_t *qp)
 811 {
 812         struct kb8042 *kb8042;
 813 
 814         mblk_t  *mp;
 815         boolean_t suspended;
 816 
 817         kb8042 = (struct kb8042 *)qp->q_ptr;
 818 
 819         mutex_enter(&kb8042->w_hw_mutex);
 820         suspended = kb8042->suspended;
 821         ASSERT(kb8042->ops >= 0);
 822         if (!suspended)
 823                 kb8042->ops++;
 824         mutex_exit(&kb8042->w_hw_mutex);
 825 
 826 #ifdef NO_KB_DEBUG
 827         while (!suspended && (mp = getq(qp)) != NULL) {
 828 #else
 829         /*
 830          * Not taking keyboard input while suspending can make debugging
 831          * difficult.  However, we still do the ops counting so that we
 832          * don't suspend at a bad time.
 833          */
 834         while ((mp = getq(qp))) {
 835 #endif
 836                 switch (kbtrans_streams_message(kb8042->hw_kbtrans, mp)) {
 837                 case KBTRANS_MESSAGE_HANDLED:
 838                         continue;
 839                 case KBTRANS_MESSAGE_NOT_HANDLED:
 840                         break;
 841                 }
 842                 switch (mp->b_datap->db_type) {
 843                 case M_IOCTL:
 844                         kb8042_ioctlmsg(kb8042, qp, mp);
 845                         continue;
 846                 case M_IOCDATA:
 847                         kb8042_iocdatamsg(qp, mp);
 848                         continue;
 849                 case M_DELAY:
 850                 case M_STARTI:
 851                 case M_STOPI:
 852                 case M_READ:    /* ignore, no buffered data */
 853                         freemsg(mp);
 854                         continue;
 855                 case M_FLUSH:
 856                         *mp->b_rptr &= ~FLUSHW;
 857                         if (*mp->b_rptr & FLUSHR)
 858                                 qreply(qp, mp);
 859                         else
 860                                 freemsg(mp);
 861                         continue;
 862                 default:
 863                         cmn_err(CE_NOTE, "kb8042_wsrv: bad msg %x",
 864                             mp->b_datap->db_type);
 865                         freemsg(mp);
 866                         continue;
 867                 }
 868         }
 869 
 870         mutex_enter(&kb8042->w_hw_mutex);
 871         if (!suspended) {
 872                 ASSERT(kb8042->ops > 0);
 873                 kb8042->ops--;
 874                 if (kb8042->ops == 0)
 875                         cv_broadcast(&kb8042->ops_cv);
 876         }
 877         mutex_exit(&kb8042->w_hw_mutex);
 878 
 879         return (0);
 880 }
 881 
 882 static void
 883 kb8042_ioctlmsg(struct kb8042 *kb8042, queue_t *qp, mblk_t *mp)
 884 {
 885         struct iocblk   *iocp;
 886         mblk_t          *datap;
 887         int             error;
 888         int             tmp;
 889         int             cycles;
 890         int             frequency;
 891         int             msecs;
 892 
 893         iocp = (struct iocblk *)mp->b_rptr;
 894 
 895         switch (iocp->ioc_cmd) {
 896 
 897         case CONSOPENPOLLEDIO:
 898                 error = miocpullup(mp, sizeof (struct cons_polledio *));
 899                 if (error != 0) {
 900                         miocnak(qp, mp, 0, error);
 901                         return;
 902                 }
 903 
 904                 /*
 905                  * We are given an appropriate-sized data block,
 906                  * and return a pointer to our structure in it.
 907                  */
 908                 *(struct cons_polledio **)mp->b_cont->b_rptr =
 909                     &kb8042->polledio;
 910                 mp->b_datap->db_type = M_IOCACK;
 911                 iocp->ioc_error = 0;
 912                 qreply(qp, mp);
 913                 break;
 914 
 915         case CONSCLOSEPOLLEDIO:
 916                 miocack(qp, mp, 0, 0);
 917                 break;
 918 
 919         case CONSSETABORTENABLE:
 920                 if (iocp->ioc_count != TRANSPARENT) {
 921                         miocnak(qp, mp, 0, EINVAL);
 922                         return;
 923                 }
 924 
 925                 kb8042->debugger.enabled = *(intptr_t *)mp->b_cont->b_rptr;
 926                 miocack(qp, mp, 0, 0);
 927                 break;
 928 
 929         /*
 930          * Valid only in TR_UNTRANS_MODE mode.
 931          */
 932         case CONSSETKBDTYPE:
 933                 error = miocpullup(mp, sizeof (int));
 934                 if (error != 0) {
 935                         miocnak(qp, mp, 0, error);
 936                         return;
 937                 }
 938                 tmp =  *(int *)mp->b_cont->b_rptr;
 939                 if (tmp != KB_PC && tmp != KB_USB) {
 940                         miocnak(qp, mp, 0, EINVAL);
 941                         break;
 942                 }
 943                 kb8042->simulated_kbd_type = tmp;
 944                 miocack(qp, mp, 0, 0);
 945                 break;
 946 
 947         case KIOCLAYOUT:
 948                 if (kb8042->w_kblayout == -1) {
 949                         miocnak(qp, mp, 0, EINVAL);
 950                         return;
 951                 }
 952 
 953                 if ((datap = allocb(sizeof (int), BPRI_HI)) == NULL) {
 954                         miocnak(qp, mp, 0, ENOMEM);
 955                         return;
 956                 }
 957 
 958                 if (kb8042->simulated_kbd_type == KB_USB)
 959                         *(int *)datap->b_wptr = KBTRANS_USBKB_DEFAULT_LAYOUT;
 960                 else
 961                         *(int *)datap->b_wptr = kb8042->w_kblayout;
 962 
 963                 datap->b_wptr += sizeof (int);
 964                 if (mp->b_cont)
 965                         freemsg(mp->b_cont);
 966                 mp->b_cont = datap;
 967                 iocp->ioc_count = sizeof (int);
 968                 mp->b_datap->db_type = M_IOCACK;
 969                 iocp->ioc_error = 0;
 970                 qreply(qp, mp);
 971                 break;
 972 
 973         case KIOCSLAYOUT:
 974                 if (iocp->ioc_count != TRANSPARENT) {
 975                         miocnak(qp, mp, 0, EINVAL);
 976                         return;
 977                 }
 978 
 979                 kb8042->w_kblayout = *(intptr_t *)mp->b_cont->b_rptr;
 980                 miocack(qp, mp, 0, 0);
 981                 break;
 982 
 983         case KIOCCMD:
 984                 error = miocpullup(mp, sizeof (int));
 985                 if (error != 0) {
 986                         miocnak(qp, mp, 0, error);
 987                         return;
 988                 }
 989 
 990                 kb8042_type4_cmd(kb8042, *(int *)mp->b_cont->b_rptr);
 991                 miocack(qp, mp, 0, 0);
 992                 break;
 993 
 994         case KIOCMKTONE:
 995                 if (iocp->ioc_count != TRANSPARENT) {
 996                         miocnak(qp, mp, 0, EINVAL);
 997                         return;
 998                 }
 999 
1000                 tmp = (int)(*(intptr_t *)mp->b_cont->b_rptr);
1001                 cycles = tmp & 0xffff;
1002                 msecs = (tmp >> 16) & 0xffff;
1003 
1004                 if (cycles == 0)
1005                         frequency = UINT16_MAX;
1006                 else if (cycles == UINT16_MAX)
1007                         frequency = 0;
1008                 else {
1009                         frequency = (PIT_HZ + cycles / 2) / cycles;
1010                         if (frequency > UINT16_MAX)
1011                                 frequency = UINT16_MAX;
1012                 }
1013 
1014                 error = beep_mktone(frequency, msecs);
1015                 if (error != 0)
1016                         miocnak(qp, mp, 0, error);
1017                 else
1018                         miocack(qp, mp, 0, 0);
1019                 break;
1020 
1021         default:
1022 #ifdef DEBUG1
1023                 cmn_err(CE_NOTE, "!kb8042_ioctlmsg %x", iocp->ioc_cmd);
1024 #endif
1025                 miocnak(qp, mp, 0, EINVAL);
1026                 return;
1027         }
1028 }
1029 
1030 /*
1031  * Process a byte received from the keyboard
1032  */
1033 static void
1034 kb8042_received_byte(
1035         struct kb8042   *kb8042,
1036         int             scancode)       /* raw scan code */
1037 {
1038         boolean_t       legit;          /* is this a legit key pos'n? */
1039         int             key_pos = -1;
1040         enum keystate   state;
1041         boolean_t       synthetic_release_needed;
1042 
1043         /*
1044          * Intercept ACK and RESEND and signal the condition that
1045          * kb8042_send_and_wait is waiting for.
1046          */
1047         if (scancode == KB_ACK) {
1048                 mutex_enter(&kb8042->w_hw_mutex);
1049                 kb8042->acked = 1;
1050                 cv_signal(&kb8042->cmd_cv);
1051                 mutex_exit(&kb8042->w_hw_mutex);
1052                 return;
1053         } else if (scancode == KB_RESEND) {
1054                 mutex_enter(&kb8042->w_hw_mutex);
1055                 kb8042->need_retry = 1;
1056                 cv_signal(&kb8042->cmd_cv);
1057                 mutex_exit(&kb8042->w_hw_mutex);
1058                 return;
1059         }
1060 
1061         if (!kb8042->w_init) /* can't do anything anyway */
1062                 return;
1063 
1064         legit = KeyboardConvertScan(kb8042, scancode, &key_pos, &state,
1065             &synthetic_release_needed);
1066 
1067         if (legit == 0) {
1068                 /* Eaten by translation */
1069                 return;
1070         }
1071 
1072         /*
1073          * Don't know if we want this permanently, but it seems interesting
1074          * for the moment.
1075          */
1076         if (key_pos == kb8042->debugger.mod1) {
1077                 kb8042->debugger.mod1_down = (state == KEY_PRESSED);
1078         }
1079         if (key_pos == kb8042->debugger.mod2) {
1080                 kb8042->debugger.mod2_down = (state == KEY_PRESSED);
1081         }
1082         if (kb8042->debugger.enabled &&
1083             key_pos == kb8042->debugger.trigger &&
1084             kb8042->debugger.mod1_down &&
1085             kb8042->debugger.mod2_down) {
1086                 /*
1087                  * Require new presses of the modifiers.
1088                  */
1089                 kb8042->debugger.mod1_down = B_FALSE;
1090                 kb8042->debugger.mod2_down = B_FALSE;
1091                 abort_sequence_enter(NULL);
1092                 return;
1093         }
1094 
1095         /*
1096          * If there's no queue above us - as can happen if we've been
1097          * attached but not opened - drop the keystroke.
1098          * Note that we do this here instead of above so that
1099          * Ctrl-Alt-D still works.
1100          */
1101         if (kb8042->w_qp == NULL) {
1102                 return;
1103         }
1104 
1105         /*
1106          * This is to filter out auto repeat since it can't be
1107          * turned off at the hardware.  (Yeah, yeah, PS/2 keyboards
1108          * can.  Don't know whether they've taken over the world.
1109          * Don't think so.)
1110          */
1111         if (kb8042_autorepeat_detect(kb8042, key_pos, state)) {
1112                 return;
1113         }
1114 
1115 
1116         kb8042_process_key(kb8042, key_pos, state);
1117 
1118         /*
1119          * This is a total hack.  For some stupid reason, the two additional
1120          * keys on Korean keyboards (Hangul and Hangul/Hanja) report press
1121          * only.  We synthesize a release immediately.
1122          */
1123         if (synthetic_release_needed) {
1124                 (void) kb8042_autorepeat_detect(kb8042, key_pos, KEY_RELEASED);
1125                 kb8042_process_key(kb8042, key_pos, state);
1126         }
1127 }
1128 
1129 
1130 static void
1131 kb8042_process_key(struct kb8042 *kb8042, kbtrans_key_t key_pos,
1132     enum keystate state)
1133 {
1134         kbtrans_key_t key;
1135 
1136         ASSERT(key_pos >= 0 && key_pos <= 255);
1137         if (kb8042->simulated_kbd_type == KB_PC) {
1138                 kbtrans_streams_key(kb8042->hw_kbtrans, key_pos, state);
1139         } else if (kb8042->simulated_kbd_type == KB_USB) {
1140                 key = keytab_pc2usb[key_pos];
1141                 if (key != 0) {
1142                         kbtrans_streams_key(kb8042->hw_kbtrans, key, state);
1143                 }
1144         }
1145 }
1146 
1147 /*
1148  * Called from interrupt handler when keyboard interrupt occurs.
1149  */
1150 static uint_t
1151 kb8042_intr(caddr_t arg)
1152 {
1153         uchar_t scancode;       /* raw scan code */
1154         int rc;
1155         struct kb8042 *kb8042 = (struct kb8042 *)arg;
1156 
1157         rc = DDI_INTR_UNCLAIMED;
1158 
1159         if (kb8042->init_state == KB8042_UNINITIALIZED)
1160                 return (DDI_INTR_UNCLAIMED);
1161 
1162         /* don't care if drv_setparm succeeds */
1163         (void) drv_setparm(SYSRINT, 1);
1164 
1165         while (ddi_get8(kb8042->handle, kb8042->addr + I8042_INT_INPUT_AVAIL)
1166             != 0) {
1167                 rc = DDI_INTR_CLAIMED;
1168 
1169                 scancode = ddi_get8(kb8042->handle,
1170                     kb8042->addr + I8042_INT_INPUT_DATA);
1171 
1172                 kb8042_received_byte(kb8042, scancode);
1173         }
1174 
1175         return (rc);
1176 }
1177 
1178 static void
1179 kb8042_iocdatamsg(queue_t *qp, mblk_t *mp)
1180 {
1181         struct copyresp *csp;
1182 
1183         csp = (struct copyresp *)mp->b_rptr;
1184         if (csp->cp_rval) {
1185                 freemsg(mp);
1186                 return;
1187         }
1188 
1189         switch (csp->cp_cmd) {
1190         default:
1191                 miocack(qp, mp, 0, 0);
1192                 break;
1193         }
1194 }
1195 
1196 static boolean_t
1197 kb8042_polled_keycheck(
1198     struct kbtrans_hardware *hw,
1199     int *key,
1200     enum keystate *state)
1201 {
1202         struct kb8042 *kb8042 = (struct kb8042 *)hw;
1203         int     scancode;
1204         boolean_t       legit;
1205         boolean_t       synthetic_release_needed;
1206 
1207         if (kb8042->polled_synthetic_release_pending) {
1208                 *key = kb8042->polled_synthetic_release_key;
1209                 *state = KEY_RELEASED;
1210                 kb8042->polled_synthetic_release_pending = B_FALSE;
1211                 (void) kb8042_autorepeat_detect(kb8042, *key, *state);
1212                 return (B_TRUE);
1213         }
1214 
1215         for (;;) {
1216                 if (ddi_get8(kb8042->handle,
1217                     kb8042->addr + I8042_POLL_INPUT_AVAIL) == 0) {
1218                         return (B_FALSE);
1219                 }
1220 
1221                 scancode = ddi_get8(kb8042->handle,
1222                     kb8042->addr + I8042_POLL_INPUT_DATA);
1223 
1224                 legit = KeyboardConvertScan(kb8042, scancode, key, state,
1225                     &synthetic_release_needed);
1226                 if (!legit) {
1227                         continue;
1228                 }
1229                 /*
1230                  * For the moment at least, we rely on hardware autorepeat
1231                  * for polled I/O autorepeat.  However, for coordination
1232                  * with the interrupt-driven code, maintain the last key
1233                  * pressed.
1234                  */
1235                 (void) kb8042_autorepeat_detect(kb8042, *key, *state);
1236 
1237                 /*
1238                  * This is a total hack to support two additional keys
1239                  * on Korean keyboards.  They report only on press, and
1240                  * so we synthesize a release.  Most likely this will
1241                  * never be important to polled  I/O, but if I do it
1242                  * "right" the first time it _won't_ be an issue.
1243                  */
1244                 if (synthetic_release_needed) {
1245                         kb8042->polled_synthetic_release_pending = B_TRUE;
1246                         kb8042->polled_synthetic_release_key = *key;
1247                 }
1248 
1249                 if (kb8042->simulated_kbd_type == KB_USB) {
1250                         *key = keytab_pc2usb[*key];
1251                 }
1252                 return (B_TRUE);
1253         }
1254 }
1255 
1256 static void
1257 kb8042_setled(struct kb8042 *kb8042, int led_state, boolean_t polled)
1258 {
1259         kb8042->leds.desired = led_state;
1260 
1261         if (!polled)
1262                 mutex_enter(&kb8042->w_hw_mutex);
1263 
1264         if (kb8042->leds.desired != kb8042->leds.commanded) {
1265                 kb8042_send_to_keyboard(kb8042, KB_SET_LED, polled);
1266         }
1267 
1268         if (!polled)
1269                 mutex_exit(&kb8042->w_hw_mutex);
1270 }
1271 
1272 static void
1273 kb8042_polled_setled(struct kbtrans_hardware *hw, int led_state)
1274 {
1275         struct kb8042 *kb8042 = (struct kb8042 *)hw;
1276         kb8042_setled(kb8042, led_state, B_TRUE);
1277 }
1278 
1279 static void
1280 kb8042_streams_setled(struct kbtrans_hardware *hw, int led_state)
1281 {
1282         struct kb8042 *kb8042 = (struct kb8042 *)hw;
1283         kb8042_setled(kb8042, led_state, B_FALSE);
1284 }
1285 
1286 
1287 static int
1288 kb8042_send_and_wait(struct kb8042 *kb8042, uint8_t u8, boolean_t polled)
1289 {
1290         uint8_t *outp = kb8042->addr +
1291             (polled ? I8042_POLL_OUTPUT_DATA : I8042_INT_OUTPUT_DATA);
1292         uint8_t *inavp = kb8042->addr +
1293             (polled ? I8042_POLL_INPUT_AVAIL : I8042_INT_INPUT_AVAIL);
1294         uint8_t *inp = kb8042->addr +
1295             (polled ? I8042_POLL_INPUT_DATA : I8042_INT_INPUT_DATA);
1296         uint8_t b;
1297         int ms_waited;
1298         int timedout;
1299         int expire;
1300         int retries = 0;
1301 
1302         do {
1303                 kb8042->acked = 0;
1304                 kb8042->need_retry = 0;
1305                 ms_waited = 0;          /* Zero it whether polled or not */
1306                 timedout = 0;
1307 
1308                 ddi_put8(kb8042->handle, outp, u8);
1309 
1310                 while (!kb8042->acked && !kb8042->need_retry && !timedout) {
1311 
1312                         if (polled) {
1313                                 if (ddi_get8(kb8042->handle, inavp)) {
1314                                         b = ddi_get8(kb8042->handle, inp);
1315                                         switch (b) {
1316                                         case KB_ACK:
1317                                                 kb8042->acked = 1;
1318                                                 break;
1319                                         case KB_RESEND:
1320                                                 kb8042->need_retry = 1;
1321                                                 break;
1322                                         default:
1323                                                 /*
1324                                                  * drop it: We should never
1325                                                  * get scancodes while
1326                                                  * we're in the middle of a
1327                                                  * command anyway.
1328                                                  */
1329 #ifdef DEBUG
1330                                                 cmn_err(CE_WARN, "!Unexpected "
1331                                                     " byte 0x%x", b);
1332 #endif
1333                                                 break;
1334                                         }
1335                                 }
1336 
1337                                 /*
1338                                  * Wait 1ms if an ACK wasn't received yet
1339                                  */
1340                                 if (!kb8042->acked) {
1341                                         drv_usecwait(1000);
1342                                         ms_waited++;
1343                                         if (ms_waited >= MAX_KB8042_WAIT_MAX_MS)
1344                                                 timedout = B_TRUE;
1345                                 }
1346                         } else {
1347                                 /* Interrupt-driven */
1348                                 expire = ddi_get_lbolt() +
1349                                     drv_usectohz(MAX_KB8042_WAIT_MAX_MS * 1000);
1350 
1351                                 /*
1352                                  * If cv_timedwait returned -1 and we neither
1353                                  * received an ACK nor a RETRY response, then
1354                                  * we timed out.
1355                                  */
1356                                 if (cv_timedwait(&kb8042->cmd_cv,
1357                                     &kb8042->w_hw_mutex, expire) == -1 &&
1358                                     !kb8042->acked && !kb8042->need_retry) {
1359                                         timedout = B_TRUE;
1360                                 }
1361                         }
1362 
1363                 }
1364         } while ((kb8042->need_retry || timedout) &&
1365             ++retries < MAX_KB8042_RETRIES);
1366 
1367         return (kb8042->acked);
1368 }
1369 
1370 /*
1371  * kb8042_send_to_keyboard should be called with w_hw_mutex held if
1372  * polled is FALSE.
1373  */
1374 static void
1375 kb8042_send_to_keyboard(struct kb8042 *kb8042, int byte, boolean_t polled)
1376 {
1377 
1378         /*
1379          * KB_SET_LED and KB_ENABLE are special commands which require blocking
1380          * other 8042 consumers while executing.
1381          *
1382          * Other commands/data are sent using the single put8 I/O access
1383          * function.
1384          */
1385         if (byte == KB_SET_LED) {
1386 
1387                 if (!polled) {
1388                         (void) ddi_get8(kb8042->handle, kb8042->addr +
1389                             I8042_LOCK);
1390                 }
1391 
1392                 if (kb8042_send_and_wait(kb8042, KB_SET_LED, polled)) {
1393                         /*
1394                          * Ignore return value, as there's nothing we can
1395                          * do about it if the SET LED command fails.
1396                          */
1397                         (void) kb8042_send_and_wait(kb8042,
1398                             kb8042_xlate_leds(kb8042->leds.desired), polled);
1399                 }
1400 
1401                 if (!polled) {
1402                         (void) ddi_get8(kb8042->handle, kb8042->addr +
1403                             I8042_UNLOCK);
1404                 }
1405                 kb8042->leds.commanded = kb8042->leds.desired;
1406 
1407         } else if (byte == KB_ENABLE) {
1408 
1409                 if (!polled) {
1410                         (void) ddi_get8(kb8042->handle, kb8042->addr +
1411                             I8042_LOCK);
1412                 }
1413 
1414                 (void) kb8042_send_and_wait(kb8042, KB_ENABLE, polled);
1415 
1416                 if (!polled) {
1417                         (void) ddi_get8(kb8042->handle, kb8042->addr +
1418                             I8042_UNLOCK);
1419                 }
1420 
1421         } else {
1422                 /* All other commands use the "normal" virtual output port */
1423                 if (polled) {
1424                         ddi_put8(kb8042->handle,
1425                             kb8042->addr + I8042_POLL_OUTPUT_DATA, byte);
1426                 } else {
1427                         ddi_put8(kb8042->handle,
1428                             kb8042->addr + I8042_INT_OUTPUT_DATA, byte);
1429                 }
1430         }
1431 }
1432 
1433 /*
1434  * Wait until the keyboard is fully up, maybe.
1435  * We may be the first person to talk to the keyboard, in which case
1436  * it's patiently waiting to say "AA" to us to tell us it's up.
1437  * In theory it sends the AA in 300ms < n < 9s, but it's a pretty
1438  * good bet that we've already spent that long getting to that point,
1439  * so we'll only wait long enough for the communications electronics to
1440  * run.
1441  */
1442 static void
1443 kb8042_wait_poweron(struct kb8042 *kb8042)
1444 {
1445         int cnt;
1446         int ready;
1447 
1448         /* wait for up to 250 ms for a response */
1449         for (cnt = 0; cnt < 250; cnt++) {
1450                 ready = ddi_get8(kb8042->handle,
1451                     kb8042->addr + I8042_INT_INPUT_AVAIL);
1452                 if (ready != 0)
1453                         break;
1454                 drv_usecwait(1000);
1455         }
1456 
1457         /*
1458          * If there's something pending, read and discard it.  If not,
1459          * assume things are OK anyway - maybe somebody else ate it
1460          * already.  (On a PC, the BIOS almost certainly did.)
1461          */
1462         if (ready != 0) {
1463                 (void) ddi_get8(kb8042->handle,
1464                     kb8042->addr + I8042_INT_INPUT_DATA);
1465         }
1466 }
1467 
1468 static int
1469 kb8042_xlate_leds(int led)
1470 {
1471         int res;
1472 
1473         res = 0;
1474 
1475         if (led & LED_NUM_LOCK)
1476                 res |= LED_NUM;
1477         if (led & LED_SCROLL_LOCK)
1478                 res |= LED_SCR;
1479         if (led & LED_CAPS_LOCK)
1480                 res |= LED_CAP;
1481 
1482         return (res);
1483 }
1484 
1485 /*ARGSUSED*/
1486 static void
1487 kb8042_get_initial_leds(
1488     struct kb8042 *kb8042,
1489     int *initial_leds,
1490     int *initial_led_mask)
1491 {
1492 #if defined(__i386) || defined(__amd64)
1493         extern caddr_t  p0_va;
1494         uint8_t         bios_kb_flag;
1495 
1496         bios_kb_flag = p0_va[BIOS_KB_FLAG];
1497 
1498         *initial_led_mask = LED_CAPS_LOCK | LED_NUM_LOCK | LED_SCROLL_LOCK;
1499         *initial_leds = 0;
1500         if (bios_kb_flag & BIOS_CAPS_STATE)
1501                 *initial_leds |= LED_CAPS_LOCK;
1502         if (bios_kb_flag & BIOS_NUM_STATE)
1503                 *initial_leds |= LED_NUM_LOCK;
1504         if (bios_kb_flag & BIOS_SCROLL_STATE)
1505                 *initial_leds |= LED_SCROLL_LOCK;
1506 #else
1507         *initial_leds = 0;
1508         *initial_led_mask = 0;
1509 #endif
1510 }
1511 
1512 static boolean_t
1513 kb8042_autorepeat_detect(
1514     struct kb8042 *kb8042,
1515     int key_pos,
1516     enum keystate state)
1517 {
1518         if (state == KEY_RELEASED) {
1519                 if (kb8042->kb_old_key_pos == key_pos)
1520                         kb8042->kb_old_key_pos = 0;
1521         } else {
1522                 if (kb8042->kb_old_key_pos == key_pos) {
1523                         return (B_TRUE);
1524                 }
1525                 kb8042->kb_old_key_pos = key_pos;
1526         }
1527         return (B_FALSE);
1528 }
1529 
1530 /* ARGSUSED */
1531 static void
1532 kb8042_type4_cmd(struct kb8042 *kb8042, int cmd)
1533 {
1534         switch (cmd) {
1535         case KBD_CMD_BELL:
1536                 (void) beeper_on(BEEP_TYPE4);
1537                 break;
1538         case KBD_CMD_NOBELL:
1539                 (void) beeper_off();
1540                 break;
1541         }
1542 }
1543 
1544 
1545 /*
1546  * This is a pass-thru routine to get a character at poll time.
1547  */
1548 static int
1549 kb8042_polled_getchar(cons_polledio_arg_t arg)
1550 {
1551         struct kb8042   *kb8042;
1552 
1553         kb8042 = (struct kb8042 *)arg;
1554 
1555         return (kbtrans_getchar(kb8042->hw_kbtrans));
1556 }
1557 
1558 /*
1559  * This is a pass-thru routine to get a character at poll time.
1560  */
1561 static int
1562 kb8042_polled_ischar(cons_polledio_arg_t arg)
1563 {
1564         struct kb8042   *kb8042;
1565 
1566         kb8042 = (struct kb8042 *)arg;
1567 
1568         return (kbtrans_ischar(kb8042->hw_kbtrans));
1569 }