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 /* 22 * Copyright 2009 Sun Microsystems, Inc. All rights reserved. 23 * Use is subject to license terms. 24 */ 25 26 27 #include <sys/audio.h> 28 #include <sys/conf.h> 29 #include <sys/debug.h> 30 #include <sys/disp.h> 31 #include <sys/ddi.h> 32 #include <sys/file.h> 33 #include <sys/id_space.h> 34 #include <sys/kmem.h> 35 #include <sys/lx_audio.h> 36 #include <sys/mixer.h> 37 #include <sys/modhash.h> 38 #include <sys/stat.h> 39 #include <sys/sunddi.h> 40 #include <sys/sunldi.h> 41 #include <sys/sysmacros.h> 42 #include <sys/stropts.h> 43 #include <sys/types.h> 44 #include <sys/zone.h> 45 46 /* Properties used by the lx_audio driver */ 47 #define LXA_PROP_INPUTDEV "inputdev" 48 #define LXA_PROP_OUTPUTDEV "outputdev" 49 50 /* default device paths used by this driver */ 51 #define LXA_DEV_DEFAULT "/dev/audio" 52 #define LXA_DEV_CUSTOM_DIR "/dev/sound/" 53 54 /* maximum possible number of concurrent opens of this driver */ 55 #define LX_AUDIO_MAX_OPENS 1024 56 57 /* 58 * these are default fragment size and fragment count values. 59 * these values were chosen to make quake work well on my 60 * laptop: 2Ghz Pentium M + NVIDIA GeForce Go 6400. 61 * 62 * for reference: 63 * - 1 sec of stereo output at 44Khz is about 171 Kb of data 64 * - 1 sec of mono output at 8Khz is about 8Kb of data 65 */ 66 #define LXA_OSS_FRAG_SIZE (1024) /* 1/8 sec at 8Khz mono */ 67 #define LXA_OSS_FRAG_CNT (1024 * 2) 68 69 /* maximum ammount of fragment memory we'll allow a process to mmap */ 70 #define LXA_OSS_FRAG_MEM (1024 * 1024 * 2) /* 2Mb */ 71 72 /* forward declarations */ 73 typedef struct lxa_state lxa_state_t; 74 typedef struct lxa_zstate lxa_zstate_t; 75 76 /* 77 * Structure and enum declarations 78 */ 79 typedef enum { 80 LXA_TYPE_INVALID = 0, 81 LXA_TYPE_AUDIO = 1, /* audio device */ 82 LXA_TYPE_AUDIOCTL = 2 /* audio control/mixer device */ 83 } lxa_dev_type_t; 84 85 struct lxa_zstate { 86 char *lxa_zs_zonename; 87 88 /* 89 * we could store the input/output audio device setting here, 90 * but instead we're keeing them as device node properties 91 * so that a user can easily see the audio configuration for 92 * a zone via prtconf. 93 */ 94 95 /* 96 * OSS doesn't support multiple opens of the audio device. 97 * (multiple opens of the mixer device are supported.) 98 * so here we'll keep a pointer to any open input/output 99 * streams. (OSS does support two opens if one is for input 100 * and the other is for output.) 101 */ 102 lxa_state_t *lxa_zs_istate; 103 lxa_state_t *lxa_zs_ostate; 104 105 /* 106 * we need to cache channel gain and balance. channel gain and 107 * balance map to PCM volume in OSS, which are supposedly a property 108 * of the underlying hardware. but in solaris, channels are 109 * implemented in software and only exist when an audio device 110 * is actually open. (each open returns a unique channel.) OSS 111 * apps will expect consistent PCM volume set/get operations to 112 * work even if no audio device is open. hence, if no underlying 113 * device is open we need to cache the gain and balance setting. 114 */ 115 lxa_mixer_levels_t lxa_zs_pcm_levels; 116 }; 117 118 struct lxa_state { 119 lxa_zstate_t *lxas_zs; /* zone state pointer */ 120 121 dev_t lxas_dev_old; /* dev_t used to open the device */ 122 dev_t lxas_dev_new; /* new dev_t assigned to an open */ 123 int lxas_flags; /* original flags passed to open */ 124 lxa_dev_type_t lxas_type; /* type of device that was opened */ 125 126 int lxas_devs_same; /* input and output device the same? */ 127 128 /* input device variables */ 129 ldi_handle_t lxas_idev_lh; /* ldi handle for access */ 130 int lxas_idev_flags; /* flags used for open */ 131 132 /* output device variables */ 133 ldi_handle_t lxas_odev_lh; /* ldi handle for access */ 134 int lxas_odev_flags; /* flags used for open */ 135 136 /* 137 * since we support multiplexing of devices we need to remember 138 * certain parameters about the devices 139 */ 140 uint_t lxas_hw_features; 141 uint_t lxas_sw_features; 142 143 uint_t lxas_frag_size; 144 uint_t lxas_frag_cnt; 145 146 /* 147 * members needed to support mmap device access. note that to 148 * simplifly things we only support one mmap access per open. 149 */ 150 ddi_umem_cookie_t lxas_umem_cookie; 151 char *lxas_umem_ptr; 152 size_t lxas_umem_len; 153 kthread_t *lxas_mmap_thread; 154 int lxas_mmap_thread_running; 155 int lxas_mmap_thread_exit; 156 int lxas_mmap_thread_frag; 157 }; 158 159 /* 160 * Global variables 161 */ 162 dev_info_t *lxa_dip = NULL; 163 kmutex_t lxa_lock; 164 id_space_t *lxa_minor_id = NULL; 165 mod_hash_t *lxa_state_hash = NULL; 166 mod_hash_t *lxa_zstate_hash = NULL; 167 size_t lxa_state_hash_size = 15; 168 size_t lxa_zstate_hash_size = 15; 169 size_t lxa_registered_zones = 0; 170 171 /* 172 * function declarations 173 */ 174 static void lxa_mmap_output_disable(lxa_state_t *); 175 176 /* 177 * functions 178 */ 179 static void 180 lxa_state_close(lxa_state_t *lxa_state) 181 { 182 lxa_zstate_t *lxa_zs = lxa_state->lxas_zs; 183 minor_t minor = getminor(lxa_state->lxas_dev_new); 184 185 /* disable any mmap output that might still be going on */ 186 lxa_mmap_output_disable(lxa_state); 187 188 /* 189 * if this was the active input/output device, unlink it from 190 * the global zone state so that other opens of the audio device 191 * can now succeed. 192 */ 193 mutex_enter(&lxa_lock); 194 if (lxa_zs->lxa_zs_istate == lxa_state) 195 lxa_zs->lxa_zs_istate = NULL; 196 if (lxa_zs->lxa_zs_ostate == lxa_state) { 197 lxa_zs->lxa_zs_ostate = NULL; 198 } 199 mutex_exit(&lxa_lock); 200 201 /* remove this state structure from the hash (if it's there) */ 202 (void) mod_hash_remove(lxa_state_hash, 203 (mod_hash_key_t)(uintptr_t)minor, (mod_hash_val_t *)&lxa_state); 204 205 /* close any audio device that we have open */ 206 if (lxa_state->lxas_idev_lh != NULL) 207 (void) ldi_close(lxa_state->lxas_idev_lh, 208 lxa_state->lxas_idev_flags, kcred); 209 if (lxa_state->lxas_odev_lh != NULL) 210 (void) ldi_close(lxa_state->lxas_odev_lh, 211 lxa_state->lxas_odev_flags, kcred); 212 213 /* free up any memory allocated by mmaps */ 214 if (lxa_state->lxas_umem_cookie != NULL) 215 ddi_umem_free(lxa_state->lxas_umem_cookie); 216 217 /* release the id associated with this state structure */ 218 id_free(lxa_minor_id, minor); 219 220 kmem_free(lxa_state, sizeof (*lxa_state)); 221 } 222 223 static char * 224 getzonename(void) 225 { 226 return (curproc->p_zone->zone_name); 227 } 228 229 static char * 230 lxa_devprop_name(char *zname, char *pname) 231 { 232 char *zpname; 233 int n; 234 235 ASSERT((pname != NULL) && (zname != NULL)); 236 237 /* prepend the zone name to the property name */ 238 n = snprintf(NULL, 0, "%s_%s", zname, pname) + 1; 239 zpname = kmem_alloc(n, KM_SLEEP); 240 (void) snprintf(zpname, n, "%s_%s", zname, pname); 241 242 return (zpname); 243 } 244 245 static int 246 lxa_devprop_verify(char *pval) 247 { 248 int n; 249 250 ASSERT(pval != NULL); 251 252 if (strcmp(pval, "default") == 0) 253 return (0); 254 255 /* make sure the value is an integer */ 256 for (n = 0; pval[n] != '\0'; n++) { 257 if ((pval[n] < '0') && (pval[n] > '9')) { 258 return (-1); 259 } 260 } 261 262 return (0); 263 } 264 265 static char * 266 lxa_devprop_lookup(char *zname, char *pname, lxa_dev_type_t lxa_type) 267 { 268 char *zprop_name, *pval; 269 char *dev_path; 270 int n, rv; 271 272 ASSERT((pname != NULL) && (zname != NULL)); 273 ASSERT((lxa_type == LXA_TYPE_AUDIO) || (lxa_type == LXA_TYPE_AUDIOCTL)); 274 275 zprop_name = lxa_devprop_name(zname, pname); 276 277 /* attempt to lookup the property */ 278 rv = ddi_prop_lookup_string(DDI_DEV_T_ANY, lxa_dip, 279 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, zprop_name, &pval); 280 strfree(zprop_name); 281 282 if (rv != DDI_PROP_SUCCESS) 283 return (NULL); 284 285 if (lxa_devprop_verify(pval) != 0) { 286 ddi_prop_free(pval); 287 return (NULL); 288 } 289 290 if (strcmp(pval, "none") == 0) { 291 /* there is no audio device specified */ 292 return (NULL); 293 } else if (strcmp(pval, "default") == 0) { 294 /* use the default audio device on the system */ 295 dev_path = strdup(LXA_DEV_DEFAULT); 296 } else { 297 /* a custom audio device was specified, generate a path */ 298 n = snprintf(NULL, 0, "%s%s", LXA_DEV_CUSTOM_DIR, pval) + 1; 299 dev_path = kmem_alloc(n, KM_SLEEP); 300 (void) snprintf(dev_path, n, "%s%s", LXA_DEV_CUSTOM_DIR, pval); 301 } 302 ddi_prop_free(pval); 303 304 /* 305 * if this is an audio control device so we need to append 306 * "ctl" to the path 307 */ 308 if (lxa_type == LXA_TYPE_AUDIOCTL) { 309 char *tmp; 310 n = snprintf(NULL, 0, "%s%s", dev_path, "ctl") + 1; 311 tmp = kmem_alloc(n, KM_SLEEP); 312 (void) snprintf(tmp, n, "%s%s", dev_path, "ctl"); 313 strfree(dev_path); 314 dev_path = tmp; 315 } 316 317 return (dev_path); 318 } 319 320 static int 321 lxa_dev_getfeatures(lxa_state_t *lxa_state) 322 { 323 audio_info_t ai_idev, ai_odev; 324 int n, rv; 325 326 /* set a default fragment size */ 327 lxa_state->lxas_frag_size = LXA_OSS_FRAG_SIZE; 328 lxa_state->lxas_frag_cnt = LXA_OSS_FRAG_CNT; 329 330 /* get info for the currently open audio devices */ 331 if ((lxa_state->lxas_idev_lh != NULL) && 332 ((rv = ldi_ioctl(lxa_state->lxas_idev_lh, 333 AUDIO_GETINFO, (intptr_t)&ai_idev, FKIOCTL, kcred, &n)) != 0)) 334 return (rv); 335 if ((lxa_state->lxas_odev_lh != NULL) && 336 ((rv = ldi_ioctl(lxa_state->lxas_odev_lh, 337 AUDIO_GETINFO, (intptr_t)&ai_odev, FKIOCTL, kcred, &n)) != 0)) 338 return (rv); 339 340 /* if we're only open for reading or writing then it's easy */ 341 if (lxa_state->lxas_idev_lh == NULL) { 342 lxa_state->lxas_sw_features = ai_odev.sw_features; 343 lxa_state->lxas_hw_features = ai_odev.hw_features; 344 return (0); 345 } else if (lxa_state->lxas_odev_lh == NULL) { 346 lxa_state->lxas_sw_features = ai_idev.sw_features; 347 lxa_state->lxas_hw_features = ai_idev.hw_features; 348 return (0); 349 } 350 351 /* 352 * well if we're open for reading and writing but the underlying 353 * device is the same then it's also pretty easy 354 */ 355 if (lxa_state->lxas_devs_same) { 356 if ((ai_odev.sw_features != ai_idev.sw_features) || 357 (ai_odev.hw_features != ai_idev.hw_features)) { 358 zcmn_err(getzoneid(), CE_WARN, "lx_audio error: " 359 "audio device reported inconsistent features"); 360 return (EIO); 361 } 362 lxa_state->lxas_sw_features = ai_odev.sw_features; 363 lxa_state->lxas_hw_features = ai_odev.hw_features; 364 return (0); 365 } 366 367 /* 368 * figure out which software features we're going to support. 369 * we will report a feature as supported if both the input 370 * and output device support it. 371 */ 372 lxa_state->lxas_sw_features = 0; 373 n = ai_idev.sw_features & ai_odev.sw_features; 374 if (n & AUDIO_SWFEATURE_MIXER) 375 lxa_state->lxas_sw_features |= AUDIO_SWFEATURE_MIXER; 376 377 /* 378 * figure out which hardware features we're going to support. 379 * for a first pass we will report a feature as supported if 380 * both the input and output device support it. 381 */ 382 lxa_state->lxas_hw_features = 0; 383 n = ai_idev.hw_features & ai_odev.hw_features; 384 if (n & AUDIO_HWFEATURE_MSCODEC) 385 lxa_state->lxas_hw_features |= AUDIO_HWFEATURE_MSCODEC; 386 387 /* 388 * if we made it here then we have different audio input and output 389 * devices. this will allow us to report support for additional 390 * hardware features that may not supported by just the input or 391 * output device alone. 392 */ 393 394 /* always report tha we support both playback and recording */ 395 lxa_state->lxas_hw_features = 396 AUDIO_HWFEATURE_PLAY | AUDIO_HWFEATURE_RECORD; 397 398 /* always report full duplex support */ 399 lxa_state->lxas_hw_features = AUDIO_HWFEATURE_DUPLEX; 400 401 /* never report that we have input to output loopback support */ 402 ASSERT((lxa_state->lxas_hw_features & AUDIO_HWFEATURE_IN2OUT) == 0); 403 return (0); 404 } 405 406 static int 407 lxa_dev_open(lxa_state_t *lxa_state) 408 { 409 char *idev, *odev; 410 int flags, rv; 411 ldi_handle_t lh; 412 ldi_ident_t li = NULL; 413 414 ASSERT((lxa_state->lxas_type == LXA_TYPE_AUDIO) || 415 (lxa_state->lxas_type == LXA_TYPE_AUDIOCTL)); 416 417 /* 418 * check if we have configuration properties for this zone. 419 * if we don't then audio isn't supported in this zone. 420 */ 421 idev = lxa_devprop_lookup(getzonename(), LXA_PROP_INPUTDEV, 422 lxa_state->lxas_type); 423 odev = lxa_devprop_lookup(getzonename(), LXA_PROP_OUTPUTDEV, 424 lxa_state->lxas_type); 425 426 /* make sure there is at least one device to read from or write to */ 427 if ((idev == NULL) && (odev == NULL)) 428 return (ENODEV); 429 430 /* see if the input and output devices are actually the same device */ 431 if (((idev != NULL) && (odev != NULL)) && 432 (strcmp(idev, odev) == 0)) 433 lxa_state->lxas_devs_same = 1; 434 435 /* we don't respect FEXCL */ 436 flags = lxa_state->lxas_flags & ~FEXCL; 437 if (lxa_state->lxas_type == LXA_TYPE_AUDIO) { 438 /* 439 * if we're opening audio devices then we need to muck 440 * with the FREAD/FWRITE flags. 441 * 442 * certain audio device may only support input or output 443 * (but not both.) so if we're multiplexing input/output 444 * to different devices we need to make sure we don't try 445 * and open the output device for reading and the input 446 * device for writing. 447 * 448 * if we're using the same device for input/output we still 449 * need to do this because some audio devices won't let 450 * themselves be opened multiple times for read access. 451 */ 452 lxa_state->lxas_idev_flags = flags & ~FWRITE; 453 lxa_state->lxas_odev_flags = flags & ~FREAD; 454 455 /* make sure we have devices to read from and write to */ 456 if (((flags & FREAD) && (idev == NULL)) || 457 ((flags & FWRITE) && (odev == NULL))) { 458 rv = ENODEV; 459 goto out; 460 } 461 } else { 462 lxa_state->lxas_idev_flags = lxa_state->lxas_odev_flags = flags; 463 } 464 465 /* get an ident to open the devices */ 466 if (ldi_ident_from_dev(lxa_state->lxas_dev_new, &li) != 0) { 467 rv = ENODEV; 468 goto out; 469 } 470 471 /* open the input device */ 472 lxa_state->lxas_idev_lh = NULL; 473 if (((lxa_state->lxas_type == LXA_TYPE_AUDIOCTL) || 474 (lxa_state->lxas_idev_flags & FREAD)) && 475 (idev != NULL)) { 476 rv = ldi_open_by_name(idev, lxa_state->lxas_idev_flags, 477 kcred, &lh, li); 478 if (rv != 0) { 479 zcmn_err(getzoneid(), CE_WARN, "lxa_open_dev: " 480 "unable to open audio device: %s", idev); 481 zcmn_err(getzoneid(), CE_WARN, "lxa_open_dev: " 482 "possible zone audio configuration error"); 483 goto out; 484 } 485 lxa_state->lxas_idev_lh = lh; 486 } 487 488 /* open the output device */ 489 lxa_state->lxas_odev_lh = NULL; 490 if (((lxa_state->lxas_type == LXA_TYPE_AUDIOCTL) || 491 (lxa_state->lxas_odev_flags & FWRITE)) && 492 (odev != NULL)) { 493 rv = ldi_open_by_name(odev, lxa_state->lxas_odev_flags, 494 kcred, &lh, li); 495 if (rv != 0) { 496 /* 497 * If this open failed and we previously opened an 498 * input device, it is the responsibility of the 499 * caller to close that device after we return 500 * failure here. 501 */ 502 zcmn_err(getzoneid(), CE_WARN, "lxa_open_dev: " 503 "unable to open audio device: %s", odev); 504 zcmn_err(getzoneid(), CE_WARN, "lxa_open_dev: " 505 "possible zone audio configuration error"); 506 goto out; 507 } 508 lxa_state->lxas_odev_lh = lh; 509 } 510 511 /* free up stuff */ 512 out: 513 if (li != NULL) 514 ldi_ident_release(li); 515 if (idev != NULL) 516 strfree(idev); 517 if (odev != NULL) 518 strfree(odev); 519 520 return (rv); 521 } 522 523 void 524 lxa_mmap_thread_exit(lxa_state_t *lxa_state) 525 { 526 mutex_enter(&lxa_lock); 527 lxa_state->lxas_mmap_thread = NULL; 528 lxa_state->lxas_mmap_thread_frag = 0; 529 lxa_state->lxas_mmap_thread_running = 0; 530 lxa_state->lxas_mmap_thread_exit = 0; 531 mutex_exit(&lxa_lock); 532 thread_exit(); 533 /*NOTREACHED*/ 534 } 535 536 void 537 lxa_mmap_thread(lxa_state_t *lxa_state) 538 { 539 struct uio uio, uio_null; 540 iovec_t iovec, iovec_null; 541 uint_t bytes_per_sec, usec_per_frag, ticks_per_frag; 542 int rv, junk, eof, retry; 543 audio_info_t ai; 544 545 /* we better be setup for writing to the output device */ 546 ASSERT((lxa_state->lxas_flags & FWRITE) != 0); 547 ASSERT(lxa_state->lxas_odev_lh != NULL); 548 549 /* setup a uio to output one fragment */ 550 uio.uio_iov = &iovec; 551 uio.uio_iovcnt = 1; 552 uio.uio_offset = 0; 553 uio.uio_segflg = UIO_SYSSPACE; 554 uio.uio_fmode = 0; 555 uio.uio_extflg = 0; 556 uio.uio_llimit = MAXOFFSET_T; 557 558 /* setup a uio to output a eof (a fragment with a length of 0) */ 559 uio_null.uio_iov = &iovec_null; 560 uio_null.uio_iov->iov_len = 0; 561 uio_null.uio_iov->iov_base = NULL; 562 uio_null.uio_iovcnt = 1; 563 uio_null.uio_offset = 0; 564 uio_null.uio_segflg = UIO_SYSSPACE; 565 uio_null.uio_fmode = 0; 566 uio_null.uio_extflg = 0; 567 uio_null.uio_llimit = MAXOFFSET_T; 568 uio_null.uio_resid = 0; 569 570 lxa_mmap_thread_top: 571 ASSERT(!MUTEX_HELD(&lxa_lock)); 572 573 /* first drain any pending audio output */ 574 if ((rv = ldi_ioctl(lxa_state->lxas_odev_lh, 575 AUDIO_DRAIN, NULL, FKIOCTL, kcred, &junk)) != 0) { 576 cmn_err(CE_WARN, "lxa_mmap_thread: " 577 "AUDIO_DRAIN failed, aborting audio output"); 578 lxa_mmap_thread_exit(lxa_state); 579 /*NOTREACHED*/ 580 } 581 582 /* 583 * we depend on the ai.play.eof value to keep track of 584 * audio output progress so reset it here. 585 */ 586 AUDIO_INITINFO(&ai); 587 ai.play.eof = 0; 588 if ((rv = ldi_ioctl(lxa_state->lxas_odev_lh, 589 AUDIO_SETINFO, (intptr_t)&ai, FKIOCTL, kcred, &junk)) != 0) { 590 cmn_err(CE_WARN, "lxa_mmap_thread: " 591 "AUDIO_SETINFO failed, aborting audio output"); 592 lxa_mmap_thread_exit(lxa_state); 593 /*NOTREACHED*/ 594 } 595 596 /* 597 * we're going to need to know the sampling rate and number 598 * of output channels to estimate how long we can sleep between 599 * requests. 600 */ 601 if ((rv = ldi_ioctl(lxa_state->lxas_odev_lh, AUDIO_GETINFO, 602 (intptr_t)&ai, FKIOCTL, kcred, &junk)) != 0) { 603 cmn_err(CE_WARN, "lxa_mmap_thread: " 604 "AUDIO_GETINFO failed, aborting audio output"); 605 lxa_mmap_thread_exit(lxa_state); 606 /*NOTREACHED*/ 607 } 608 609 /* estimate how many ticks it takes to output a fragment of data */ 610 bytes_per_sec = (ai.play.sample_rate * ai.play.channels * 611 ai.play.precision) / 8; 612 usec_per_frag = MICROSEC * lxa_state->lxas_frag_size / bytes_per_sec; 613 ticks_per_frag = drv_usectohz(usec_per_frag); 614 615 /* queue up three fragments of of data into the output stream */ 616 eof = 3; 617 618 /* sanity check the eof value */ 619 ASSERT(ai.play.eof == 0); 620 ai.play.eof = 0; 621 622 /* we always start audio output at fragment 0 */ 623 mutex_enter(&lxa_lock); 624 lxa_state->lxas_mmap_thread_frag = 0; 625 626 /* 627 * we shouldn't have allowed the mapping if it isn't a multiple 628 * of the fragment size 629 */ 630 ASSERT((lxa_state->lxas_umem_len % lxa_state->lxas_frag_size) == 0); 631 632 while (!lxa_state->lxas_mmap_thread_exit) { 633 size_t start, end; 634 635 /* 636 * calculate the start and ending offsets of the next 637 * fragment to output 638 */ 639 start = lxa_state->lxas_mmap_thread_frag * 640 lxa_state->lxas_frag_size; 641 end = start + lxa_state->lxas_frag_size; 642 643 ASSERT(start < lxa_state->lxas_umem_len); 644 ASSERT(end <= lxa_state->lxas_umem_len); 645 646 /* setup the uio to output one fragment of audio */ 647 uio.uio_resid = end - start; 648 uio.uio_iov->iov_len = end - start; 649 uio.uio_iov->iov_base = &lxa_state->lxas_umem_ptr[start]; 650 651 /* increment the current fragment index */ 652 lxa_state->lxas_mmap_thread_frag = 653 (lxa_state->lxas_mmap_thread_frag + 1) % 654 (lxa_state->lxas_umem_len / lxa_state->lxas_frag_size); 655 656 /* drop the audio lock before actually outputting data */ 657 mutex_exit(&lxa_lock); 658 659 /* 660 * write the fragment of audio data to the device stream 661 * then write a eof to the stream to tell the device to 662 * increment ai.play.eof when it's done processing the 663 * fragment we just wrote 664 */ 665 if ((rv = ldi_write(lxa_state->lxas_odev_lh, 666 &uio, kcred)) != 0) { 667 cmn_err(CE_WARN, "lxa_mmap_thread: " 668 "ldi_write() failed (%d), " 669 "resetting audio output", rv); 670 goto lxa_mmap_thread_top; 671 } 672 if ((rv = ldi_write(lxa_state->lxas_odev_lh, 673 &uio_null, kcred)) != 0) { 674 cmn_err(CE_WARN, "lxa_mmap_thread: " 675 "ldi_write(eof) failed (%d), " 676 "resetting audio output", rv); 677 goto lxa_mmap_thread_top; 678 } 679 680 /* 681 * we want to avoid buffer underrun so ensure that 682 * there is always at least one fragment of data in the 683 * output stream. 684 */ 685 mutex_enter(&lxa_lock); 686 if (--eof > 0) { 687 continue; 688 } 689 690 /* 691 * now we wait until the audio device has finished outputting 692 * at least one fragment of data. 693 */ 694 retry = 0; 695 while (!lxa_state->lxas_mmap_thread_exit && (eof == 0)) { 696 uint_t ai_eof_old = ai.play.eof; 697 698 mutex_exit(&lxa_lock); 699 700 /* 701 * delay for the number of ticks it takes 702 * to output one fragment of data 703 */ 704 if (ticks_per_frag > 0) 705 delay(ticks_per_frag); 706 707 /* check if we've managed to output any fragments */ 708 if ((rv = ldi_ioctl(lxa_state->lxas_odev_lh, 709 AUDIO_GETINFO, (intptr_t)&ai, 710 FKIOCTL, kcred, &junk)) != 0) { 711 cmn_err(CE_WARN, "lxa_mmap_thread: " 712 "AUDIO_GETINFO failed (%d), " 713 "resetting audio output", rv); 714 /* re-start mmap audio output */ 715 goto lxa_mmap_thread_top; 716 } 717 718 if (ai_eof_old == ai.play.eof) { 719 /* institute a random retry limit */ 720 if (retry++ < 100) { 721 mutex_enter(&lxa_lock); 722 continue; 723 } 724 cmn_err(CE_WARN, "lxa_mmap_thread: " 725 "output stalled, " 726 "resetting audio output"); 727 /* re-start mmap audio output */ 728 goto lxa_mmap_thread_top; 729 } 730 731 if (ai.play.eof > ai_eof_old) { 732 eof = ai.play.eof - ai_eof_old; 733 } else { 734 /* eof counter wrapped around */ 735 ASSERT(ai_eof_old < ai.play.eof); 736 eof = ai.play.eof + (ai_eof_old - UINTMAX_MAX); 737 } 738 /* we're done with this loop so re-aquire the lock */ 739 ASSERT(eof != 0); 740 mutex_enter(&lxa_lock); 741 } 742 } 743 mutex_exit(&lxa_lock); 744 lxa_mmap_thread_exit(lxa_state); 745 /*NOTREACHED*/ 746 } 747 748 static void 749 lxa_mmap_output_disable(lxa_state_t *lxa_state) 750 { 751 kt_did_t tid; 752 753 mutex_enter(&lxa_lock); 754 755 /* if the output thread isn't running there's nothing to do */ 756 if (lxa_state->lxas_mmap_thread_running == 0) { 757 mutex_exit(&lxa_lock); 758 return; 759 } 760 761 /* tell the pcm mmap output thread to exit */ 762 lxa_state->lxas_mmap_thread_exit = 1; 763 764 /* wait for the mmap output thread to exit */ 765 tid = lxa_state->lxas_mmap_thread->t_did; 766 mutex_exit(&lxa_lock); 767 thread_join(tid); 768 } 769 770 static void 771 lxa_mmap_output_enable(lxa_state_t *lxa_state) 772 { 773 mutex_enter(&lxa_lock); 774 775 /* if the output thread is already running there's nothing to do */ 776 if (lxa_state->lxas_mmap_thread_running != 0) { 777 mutex_exit(&lxa_lock); 778 return; 779 } 780 781 /* setup output state */ 782 lxa_state->lxas_mmap_thread_running = 1; 783 lxa_state->lxas_mmap_thread_exit = 0; 784 lxa_state->lxas_mmap_thread_frag = 0; 785 786 /* kick off a thread to do the mmap pcm output */ 787 lxa_state->lxas_mmap_thread = thread_create(NULL, 0, 788 (void (*)())lxa_mmap_thread, lxa_state, 789 0, &p0, TS_RUN, minclsyspri); 790 ASSERT(lxa_state->lxas_mmap_thread != NULL); 791 792 mutex_exit(&lxa_lock); 793 } 794 795 static int 796 lxa_ioc_mmap_output(lxa_state_t *lxa_state, intptr_t arg, int mode) 797 { 798 uint_t trigger; 799 800 /* we only support output via mmap */ 801 if ((lxa_state->lxas_flags & FWRITE) == 0) 802 return (EINVAL); 803 804 /* if the user hasn't mmap the device then there's nothing to do */ 805 if (lxa_state->lxas_umem_cookie == NULL) 806 return (EINVAL); 807 808 /* copy in the request */ 809 if (ddi_copyin((void *)arg, &trigger, sizeof (trigger), mode) != 0) 810 return (EFAULT); 811 812 /* a zero value disables output */ 813 if (trigger == 0) { 814 lxa_mmap_output_disable(lxa_state); 815 return (0); 816 } 817 818 /* a non-zero value enables output */ 819 lxa_mmap_output_enable(lxa_state); 820 return (0); 821 } 822 823 static int 824 lxa_ioc_mmap_ptr(lxa_state_t *lxa_state, intptr_t arg, int mode) 825 { 826 int ptr; 827 828 /* we only support output via mmap */ 829 if ((lxa_state->lxas_flags & FWRITE) == 0) 830 return (EINVAL); 831 832 /* if the user hasn't mmap the device then there's nothing to do */ 833 if (lxa_state->lxas_umem_cookie == NULL) 834 return (EINVAL); 835 836 /* if the output thread isn't running then there's nothing to do */ 837 if (lxa_state->lxas_mmap_thread_running == 0) 838 return (EINVAL); 839 840 mutex_enter(&lxa_lock); 841 ptr = lxa_state->lxas_mmap_thread_frag * lxa_state->lxas_frag_size; 842 mutex_exit(&lxa_lock); 843 844 if (ddi_copyout(&ptr, (void *)arg, sizeof (ptr), mode) != 0) 845 return (EFAULT); 846 847 return (0); 848 } 849 850 static int 851 lxa_ioc_get_frag_info(lxa_state_t *lxa_state, intptr_t arg, int mode) 852 { 853 lxa_frag_info_t fi; 854 855 fi.lxa_fi_size = lxa_state->lxas_frag_size; 856 fi.lxa_fi_cnt = lxa_state->lxas_frag_cnt; 857 858 if (ddi_copyout(&fi, (void *)arg, sizeof (fi), mode) != 0) 859 return (EFAULT); 860 861 return (0); 862 } 863 864 static int 865 lxa_ioc_set_frag_info(lxa_state_t *lxa_state, intptr_t arg, int mode) 866 { 867 lxa_frag_info_t fi; 868 869 /* if the device is mmaped we can't change the fragment settings */ 870 if (lxa_state->lxas_umem_cookie != NULL) 871 return (EINVAL); 872 873 /* copy in the request */ 874 if (ddi_copyin((void *)arg, &fi, sizeof (fi), mode) != 0) 875 return (EFAULT); 876 877 /* do basic bounds checking */ 878 if ((fi.lxa_fi_cnt == 0) || (fi.lxa_fi_size < 16)) 879 return (EINVAL); 880 881 /* don't accept size values less than 16 */ 882 883 lxa_state->lxas_frag_size = fi.lxa_fi_size; 884 lxa_state->lxas_frag_cnt = fi.lxa_fi_cnt; 885 886 return (0); 887 } 888 889 static int 890 lxa_audio_drain(lxa_state_t *lxa_state) 891 { 892 int junk; 893 894 /* only applies to output buffers */ 895 if (lxa_state->lxas_odev_lh == NULL) 896 return (EINVAL); 897 898 /* can't fail so ignore the return value */ 899 (void) ldi_ioctl(lxa_state->lxas_odev_lh, AUDIO_DRAIN, NULL, 900 FKIOCTL, kcred, &junk); 901 return (0); 902 } 903 904 /* 905 * lxa_audio_info_merge() usage notes: 906 * 907 * - it's important to make sure NOT to get the ai_idev and ai_odev 908 * parameters mixed up when calling lxa_audio_info_merge(). 909 * 910 * - it's important for the caller to make sure that AUDIO_GETINFO 911 * was called for the input device BEFORE the output device. (see 912 * the comments for merging the monitor_gain setting to see why.) 913 */ 914 static void 915 lxa_audio_info_merge(lxa_state_t *lxa_state, 916 audio_info_t *ai_idev, audio_info_t *ai_odev, audio_info_t *ai_merged) 917 { 918 /* if we're not setup for output return the intput device info */ 919 if (lxa_state->lxas_odev_lh == NULL) { 920 *ai_merged = *ai_idev; 921 return; 922 } 923 924 /* if we're not setup for input return the output device info */ 925 if (lxa_state->lxas_idev_lh == NULL) { 926 *ai_merged = *ai_odev; 927 return; 928 } 929 930 /* get record values from the input device */ 931 ai_merged->record = ai_idev->record; 932 933 /* get play values from the output device */ 934 ai_merged->play = ai_odev->play; 935 936 /* muting status only matters for the output device */ 937 ai_merged->output_muted = ai_odev->output_muted; 938 939 /* we don't support device reference counts, always return 1 */ 940 ai_merged->ref_cnt = 1; 941 942 /* 943 * for supported hw/sw features report the combined feature 944 * set we calcuated out earlier. 945 */ 946 ai_merged->hw_features = lxa_state->lxas_hw_features; 947 ai_merged->sw_features = lxa_state->lxas_sw_features; 948 949 if (!lxa_state->lxas_devs_same) { 950 /* 951 * if the input and output devices are different 952 * physical devices then we don't support input to 953 * output loopback so we always report the input 954 * to output loopback gain to be zero. 955 */ 956 ai_merged->monitor_gain = 0; 957 } else { 958 /* 959 * the intput and output devices are actually the 960 * same physical device. hence it probably supports 961 * intput to output loopback. regardless we should 962 * pass back the intput to output gain reported by 963 * the device. when we pick a value to passback we 964 * use the output device value since that was 965 * the most recently queried. (we base this 966 * decision on the assumption that io gain is 967 * actually hardware setting in the device and 968 * hence if it is changed on one open instance of 969 * the device the change will be visable to all 970 * other instances of the device.) 971 */ 972 ai_merged->monitor_gain = ai_odev->monitor_gain; 973 } 974 975 /* 976 * for currently enabled software features always return the 977 * merger of the two. (of course the enabled software features 978 * for the input and output devices should alway be the same, 979 * so if it isn't complain.) 980 */ 981 if (ai_idev->sw_features_enabled != ai_odev->sw_features_enabled) 982 zcmn_err(getzoneid(), CE_WARN, "lx_audio: " 983 "unexpected sofware feature state"); 984 ai_merged->sw_features_enabled = 985 ai_idev->sw_features_enabled & ai_odev->sw_features_enabled; 986 } 987 988 static int 989 lxa_audio_setinfo(lxa_state_t *lxa_state, int cmd, intptr_t arg, 990 int mode) 991 { 992 audio_info_t ai, ai_null, ai_idev, ai_odev; 993 int rv, junk; 994 995 /* copy in the request */ 996 if (ddi_copyin((void *)arg, &ai, sizeof (ai), mode) != 0) 997 return (EFAULT); 998 999 /* 1000 * if the caller is attempting to enable a software feature that 1001 * we didn't report as supported the return an error 1002 */ 1003 if ((ai.sw_features_enabled != -1) && 1004 (ai.sw_features_enabled & ~lxa_state->lxas_sw_features)) 1005 return (EINVAL); 1006 1007 /* 1008 * if a process has mmaped this device then we don't allow 1009 * changes to the play.eof field (since mmap output depends 1010 * on this field. 1011 */ 1012 if ((lxa_state->lxas_umem_cookie != NULL) && 1013 (ai.play.eof != -1)) 1014 return (EIO); 1015 1016 /* initialize the new requests */ 1017 AUDIO_INITINFO(&ai_null); 1018 ai_idev = ai_odev = ai; 1019 1020 /* remove audio input settings from the output device request */ 1021 ai_odev.record = ai_null.record; 1022 1023 /* remove audio output settings from the input device request */ 1024 ai_idev.play = ai_null.play; 1025 ai_idev.output_muted = ai_null.output_muted; 1026 1027 /* apply settings to the intput device */ 1028 if ((lxa_state->lxas_idev_lh != NULL) && 1029 ((rv = ldi_ioctl(lxa_state->lxas_idev_lh, cmd, 1030 (intptr_t)&ai_idev, FKIOCTL, kcred, &junk)) != 0)) 1031 return (rv); 1032 1033 /* apply settings to the output device */ 1034 if ((lxa_state->lxas_odev_lh != NULL) && 1035 ((rv = ldi_ioctl(lxa_state->lxas_odev_lh, cmd, 1036 (intptr_t)&ai_odev, FKIOCTL, kcred, &junk)) != 0)) 1037 return (rv); 1038 1039 /* 1040 * a AUDIO_SETINFO call performs an implicit AUDIO_GETINFO to 1041 * return values (see the coments in audioio.h.) so we need 1042 * to combine the values returned from the input and output 1043 * device back into the users buffer. 1044 */ 1045 lxa_audio_info_merge(lxa_state, &ai_idev, &ai_odev, &ai); 1046 1047 /* copyout the results */ 1048 if (ddi_copyout(&ai, (void *)arg, sizeof (ai), mode) != 0) { 1049 return (EFAULT); 1050 } 1051 1052 return (0); 1053 } 1054 1055 static int 1056 lxa_audio_getinfo(lxa_state_t *lxa_state, intptr_t arg, int mode) 1057 { 1058 audio_info_t ai, ai_idev, ai_odev; 1059 int rv, junk; 1060 1061 /* get the settings from the input device */ 1062 if ((lxa_state->lxas_idev_lh != NULL) && 1063 ((rv = ldi_ioctl(lxa_state->lxas_idev_lh, AUDIO_GETINFO, 1064 (intptr_t)&ai_idev, FKIOCTL, kcred, &junk)) != 0)) 1065 return (rv); 1066 1067 /* get the settings from the output device */ 1068 if ((lxa_state->lxas_odev_lh != NULL) && 1069 ((rv = ldi_ioctl(lxa_state->lxas_odev_lh, AUDIO_GETINFO, 1070 (intptr_t)&ai_odev, FKIOCTL, kcred, &junk)) != 0)) 1071 return (rv); 1072 1073 /* 1074 * we need to combine the values returned from the input 1075 * and output device back into a single user buffer. 1076 */ 1077 lxa_audio_info_merge(lxa_state, &ai_idev, &ai_odev, &ai); 1078 1079 /* copyout the results */ 1080 if (ddi_copyout(&ai, (void *)arg, sizeof (ai), mode) != 0) 1081 return (EFAULT); 1082 1083 return (0); 1084 } 1085 1086 static int 1087 lxa_mixer_ai_from_lh(ldi_handle_t lh, audio_info_t *ai) 1088 { 1089 int rv, junk; 1090 1091 ASSERT((lh != NULL) && (ai != NULL)); 1092 1093 /* get the device state and channel state */ 1094 rv = ldi_ioctl(lh, AUDIO_GETINFO, (intptr_t)ai, FKIOCTL, kcred, &junk); 1095 1096 return (rv); 1097 } 1098 1099 static int 1100 lxa_mixer_get_ai(lxa_state_t *lxa_state, audio_info_t *ai) 1101 { 1102 audio_info_t ai_idev, ai_odev; 1103 int rv; 1104 1105 /* if there is no input device, query the output device */ 1106 if (lxa_state->lxas_idev_lh == NULL) 1107 return (lxa_mixer_ai_from_lh(lxa_state->lxas_odev_lh, ai)); 1108 1109 /* if there is no ouput device, query the intput device */ 1110 if (lxa_state->lxas_odev_lh == NULL) 1111 return (lxa_mixer_ai_from_lh(lxa_state->lxas_idev_lh, ai)); 1112 1113 /* 1114 * now get the audio_info and channel information for the 1115 * underlying output device. 1116 */ 1117 if ((rv = lxa_mixer_ai_from_lh(lxa_state->lxas_idev_lh, 1118 &ai_idev)) != 0) 1119 return (rv); 1120 if ((rv = lxa_mixer_ai_from_lh(lxa_state->lxas_odev_lh, 1121 &ai_odev)) != 0) 1122 return (rv); 1123 1124 /* now merge the audio_info structures */ 1125 lxa_audio_info_merge(lxa_state, &ai_idev, &ai_odev, ai); 1126 return (0); 1127 } 1128 1129 static int 1130 lxa_mixer_get_common(lxa_state_t *lxa_state, int cmd, intptr_t arg, int mode) 1131 { 1132 lxa_mixer_levels_t lxa_ml; 1133 audio_info_t ai; 1134 int rv; 1135 1136 ASSERT(lxa_state->lxas_type == LXA_TYPE_AUDIOCTL); 1137 1138 if ((rv = lxa_mixer_get_ai(lxa_state, &ai)) != 0) 1139 return (rv); 1140 1141 switch (cmd) { 1142 case LXA_IOC_MIXER_GET_VOL: 1143 lxa_ml.lxa_ml_gain = ai.play.gain; 1144 lxa_ml.lxa_ml_balance = ai.play.balance; 1145 break; 1146 case LXA_IOC_MIXER_GET_MIC: 1147 lxa_ml.lxa_ml_gain = ai.record.gain; 1148 lxa_ml.lxa_ml_balance = ai.record.balance; 1149 break; 1150 } 1151 1152 if (ddi_copyout(&lxa_ml, (void *)arg, sizeof (lxa_ml), mode) != 0) 1153 return (EFAULT); 1154 return (0); 1155 } 1156 1157 static int 1158 lxa_mixer_set_common(lxa_state_t *lxa_state, int cmd, intptr_t arg, int mode) 1159 { 1160 lxa_mixer_levels_t lxa_ml; 1161 audio_info_t ai; 1162 1163 ASSERT(lxa_state->lxas_type == LXA_TYPE_AUDIOCTL); 1164 1165 /* get the new mixer settings */ 1166 if (ddi_copyin((void *)arg, &lxa_ml, sizeof (lxa_ml), mode) != 0) 1167 return (EFAULT); 1168 1169 /* sanity check the mixer settings */ 1170 if (!LXA_MIXER_LEVELS_OK(&lxa_ml)) 1171 return (EINVAL); 1172 1173 /* initialize an audio_info struct with the new settings */ 1174 AUDIO_INITINFO(&ai); 1175 switch (cmd) { 1176 case LXA_IOC_MIXER_SET_VOL: 1177 ai.play.gain = lxa_ml.lxa_ml_gain; 1178 ai.play.balance = lxa_ml.lxa_ml_balance; 1179 break; 1180 case LXA_IOC_MIXER_SET_MIC: 1181 ai.record.gain = lxa_ml.lxa_ml_gain; 1182 ai.record.balance = lxa_ml.lxa_ml_balance; 1183 break; 1184 } 1185 1186 return (lxa_audio_setinfo(lxa_state, AUDIO_SETINFO, (intptr_t)&ai, 1187 FKIOCTL)); 1188 } 1189 1190 static int 1191 lxa_mixer_get_pcm(lxa_state_t *lxa_state, intptr_t arg, int mode) 1192 { 1193 ASSERT(lxa_state->lxas_type == LXA_TYPE_AUDIOCTL); 1194 1195 /* simply return the cached pcm mixer settings */ 1196 mutex_enter(&lxa_lock); 1197 if (ddi_copyout(&lxa_state->lxas_zs->lxa_zs_pcm_levels, (void *)arg, 1198 sizeof (lxa_state->lxas_zs->lxa_zs_pcm_levels), mode) != 0) { 1199 mutex_exit(&lxa_lock); 1200 return (EFAULT); 1201 } 1202 mutex_exit(&lxa_lock); 1203 return (0); 1204 } 1205 1206 static int 1207 lxa_mixer_set_pcm(lxa_state_t *lxa_state, intptr_t arg, int mode) 1208 { 1209 lxa_mixer_levels_t lxa_ml; 1210 int rv; 1211 1212 ASSERT(lxa_state->lxas_type == LXA_TYPE_AUDIOCTL); 1213 1214 /* get the new mixer settings */ 1215 if (ddi_copyin((void *)arg, &lxa_ml, sizeof (lxa_ml), mode) != 0) 1216 return (EFAULT); 1217 1218 /* sanity check the mixer settings */ 1219 if (!LXA_MIXER_LEVELS_OK(&lxa_ml)) 1220 return (EINVAL); 1221 1222 mutex_enter(&lxa_lock); 1223 1224 /* if there is an active output channel, update it */ 1225 if (lxa_state->lxas_zs->lxa_zs_ostate != NULL) { 1226 audio_info_t ai; 1227 1228 /* initialize an audio_info struct with the new settings */ 1229 AUDIO_INITINFO(&ai); 1230 ai.play.gain = lxa_ml.lxa_ml_gain; 1231 ai.play.balance = lxa_ml.lxa_ml_balance; 1232 1233 if ((rv = lxa_audio_setinfo(lxa_state->lxas_zs->lxa_zs_ostate, 1234 AUDIO_SETINFO, (intptr_t)&ai, FKIOCTL)) != 0) { 1235 mutex_exit(&lxa_lock); 1236 return (rv); 1237 } 1238 } 1239 1240 /* update the cached mixer settings */ 1241 lxa_state->lxas_zs->lxa_zs_pcm_levels = lxa_ml; 1242 1243 mutex_exit(&lxa_lock); 1244 return (0); 1245 } 1246 1247 static int 1248 lxa_zone_reg(intptr_t arg, int mode) 1249 { 1250 lxa_zone_reg_t lxa_zr; 1251 lxa_zstate_t *lxa_zs = NULL; 1252 char *idev_name = NULL, *odev_name = NULL, *pval = NULL; 1253 int i, junk; 1254 1255 if (ddi_copyin((void *)arg, &lxa_zr, sizeof (lxa_zr), mode) != 0) 1256 return (EFAULT); 1257 1258 /* make sure that zone_name is a valid string */ 1259 for (i = 0; i < sizeof (lxa_zr.lxa_zr_zone_name); i++) 1260 if (lxa_zr.lxa_zr_zone_name[i] == '\0') 1261 break; 1262 if (i == sizeof (lxa_zr.lxa_zr_zone_name)) 1263 return (EINVAL); 1264 1265 /* make sure that inputdev is a valid string */ 1266 for (i = 0; i < sizeof (lxa_zr.lxa_zr_inputdev); i++) 1267 if (lxa_zr.lxa_zr_inputdev[i] == '\0') 1268 break; 1269 if (i == sizeof (lxa_zr.lxa_zr_inputdev)) 1270 return (EINVAL); 1271 1272 /* make sure it's a valid inputdev property value */ 1273 if (lxa_devprop_verify(lxa_zr.lxa_zr_inputdev) != 0) 1274 return (EINVAL); 1275 1276 /* make sure that outputdev is a valid string */ 1277 for (i = 0; i < sizeof (lxa_zr.lxa_zr_outputdev); i++) 1278 if (lxa_zr.lxa_zr_outputdev[i] == '\0') 1279 break; 1280 if (i == sizeof (lxa_zr.lxa_zr_outputdev)) 1281 return (EINVAL); 1282 1283 /* make sure it's a valid outputdev property value */ 1284 if (lxa_devprop_verify(lxa_zr.lxa_zr_outputdev) != 0) 1285 return (EINVAL); 1286 1287 /* get the property names */ 1288 idev_name = lxa_devprop_name(lxa_zr.lxa_zr_zone_name, 1289 LXA_PROP_INPUTDEV); 1290 odev_name = lxa_devprop_name(lxa_zr.lxa_zr_zone_name, 1291 LXA_PROP_OUTPUTDEV); 1292 1293 /* 1294 * allocate and initialize a zone state structure 1295 * since the audio device can't possibly be opened yet 1296 * (since we're setting it up now and the zone isn't booted 1297 * yet) assign some some resonable default pcm channel settings. 1298 * also, default to one mixer channel. 1299 */ 1300 lxa_zs = kmem_zalloc(sizeof (*lxa_zs), KM_SLEEP); 1301 lxa_zs->lxa_zs_zonename = strdup(lxa_zr.lxa_zr_zone_name); 1302 lxa_zs->lxa_zs_pcm_levels.lxa_ml_gain = AUDIO_MID_GAIN; 1303 lxa_zs->lxa_zs_pcm_levels.lxa_ml_balance = AUDIO_MID_BALANCE; 1304 1305 mutex_enter(&lxa_lock); 1306 1307 /* 1308 * make sure this zone isn't already registered 1309 * a zone is registered with properties for that zone exist 1310 * or there is a zone state structure for that zone 1311 */ 1312 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, lxa_dip, 1313 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 1314 idev_name, &pval) == DDI_PROP_SUCCESS) { 1315 goto err_unlock; 1316 } 1317 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, lxa_dip, 1318 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 1319 odev_name, &pval) == DDI_PROP_SUCCESS) { 1320 goto err_unlock; 1321 } 1322 if (mod_hash_find(lxa_zstate_hash, 1323 (mod_hash_key_t)lxa_zs->lxa_zs_zonename, 1324 (mod_hash_val_t *)&junk) == 0) 1325 goto err_unlock; 1326 1327 /* 1328 * create the new properties and insert the zone state structure 1329 * into the global hash 1330 */ 1331 if (ddi_prop_update_string(DDI_DEV_T_NONE, lxa_dip, 1332 idev_name, lxa_zr.lxa_zr_inputdev) != DDI_PROP_SUCCESS) 1333 goto err_prop_remove; 1334 if (ddi_prop_update_string(DDI_DEV_T_NONE, lxa_dip, 1335 odev_name, lxa_zr.lxa_zr_outputdev) != DDI_PROP_SUCCESS) 1336 goto err_prop_remove; 1337 if (mod_hash_insert(lxa_zstate_hash, 1338 (mod_hash_key_t)lxa_zs->lxa_zs_zonename, 1339 (mod_hash_val_t)lxa_zs) != 0) 1340 goto err_prop_remove; 1341 1342 /* success! */ 1343 lxa_registered_zones++; 1344 mutex_exit(&lxa_lock); 1345 1346 /* cleanup */ 1347 strfree(idev_name); 1348 strfree(odev_name); 1349 return (0); 1350 1351 err_prop_remove: 1352 (void) ddi_prop_remove(DDI_DEV_T_NONE, lxa_dip, idev_name); 1353 (void) ddi_prop_remove(DDI_DEV_T_NONE, lxa_dip, odev_name); 1354 1355 err_unlock: 1356 mutex_exit(&lxa_lock); 1357 1358 if (lxa_zs != NULL) { 1359 strfree(lxa_zs->lxa_zs_zonename); 1360 kmem_free(lxa_zs, sizeof (*lxa_zs)); 1361 } 1362 if (pval != NULL) 1363 ddi_prop_free(pval); 1364 if (idev_name != NULL) 1365 strfree(idev_name); 1366 if (odev_name != NULL) 1367 strfree(odev_name); 1368 return (EIO); 1369 } 1370 1371 static int 1372 lxa_zone_unreg(intptr_t arg, int mode) 1373 { 1374 lxa_zone_reg_t lxa_zr; 1375 lxa_zstate_t *lxa_zs = NULL; 1376 char *idev_name = NULL, *odev_name = NULL, *pval = NULL; 1377 int rv, i; 1378 1379 if (ddi_copyin((void *)arg, &lxa_zr, sizeof (lxa_zr), mode) != 0) 1380 return (EFAULT); 1381 1382 /* make sure that zone_name is a valid string */ 1383 for (i = 0; i < sizeof (lxa_zr.lxa_zr_zone_name); i++) 1384 if (lxa_zr.lxa_zr_zone_name[i] == '\0') 1385 break; 1386 if (i == sizeof (lxa_zr.lxa_zr_zone_name)) 1387 return (EINVAL); 1388 1389 /* get the property names */ 1390 idev_name = lxa_devprop_name(lxa_zr.lxa_zr_zone_name, 1391 LXA_PROP_INPUTDEV); 1392 odev_name = lxa_devprop_name(lxa_zr.lxa_zr_zone_name, 1393 LXA_PROP_OUTPUTDEV); 1394 1395 mutex_enter(&lxa_lock); 1396 1397 if (lxa_registered_zones <= 0) { 1398 rv = ENOENT; 1399 goto err_unlock; 1400 } 1401 1402 /* make sure this zone is actually registered */ 1403 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, lxa_dip, 1404 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 1405 idev_name, &pval) != DDI_PROP_SUCCESS) { 1406 rv = ENOENT; 1407 goto err_unlock; 1408 } 1409 ddi_prop_free(pval); 1410 pval = NULL; 1411 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, lxa_dip, 1412 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 1413 odev_name, &pval) != DDI_PROP_SUCCESS) { 1414 rv = ENOENT; 1415 goto err_unlock; 1416 } 1417 ddi_prop_free(pval); 1418 pval = NULL; 1419 if (mod_hash_find(lxa_zstate_hash, 1420 (mod_hash_key_t)lxa_zr.lxa_zr_zone_name, 1421 (mod_hash_val_t *)&lxa_zs) != 0) { 1422 rv = ENOENT; 1423 goto err_unlock; 1424 } 1425 ASSERT(strcmp(lxa_zr.lxa_zr_zone_name, lxa_zs->lxa_zs_zonename) == 0); 1426 1427 /* 1428 * if the audio device is currently in use then refuse to 1429 * unregister the zone 1430 */ 1431 if ((lxa_zs->lxa_zs_ostate != NULL) || 1432 (lxa_zs->lxa_zs_ostate != NULL)) { 1433 rv = EBUSY; 1434 goto err_unlock; 1435 } 1436 1437 /* success! cleanup zone config state */ 1438 (void) ddi_prop_remove(DDI_DEV_T_NONE, lxa_dip, idev_name); 1439 (void) ddi_prop_remove(DDI_DEV_T_NONE, lxa_dip, odev_name); 1440 1441 /* 1442 * note, the action of removing the zone state structure from the 1443 * hash will automatically free lxa_zs->lxa_zs_zonename. 1444 * 1445 * the reason for this is that we used lxa_zs->lxa_zs_zonename 1446 * as the hash key and by default mod_hash_create_strhash() uses 1447 * mod_hash_strkey_dtor() as a the hash key destructor. (which 1448 * free's the key for us. 1449 */ 1450 (void) mod_hash_remove(lxa_zstate_hash, 1451 (mod_hash_key_t)lxa_zr.lxa_zr_zone_name, 1452 (mod_hash_val_t *)&lxa_zs); 1453 lxa_registered_zones--; 1454 mutex_exit(&lxa_lock); 1455 1456 /* cleanup */ 1457 kmem_free(lxa_zs, sizeof (*lxa_zs)); 1458 strfree(idev_name); 1459 strfree(odev_name); 1460 return (0); 1461 1462 err_unlock: 1463 mutex_exit(&lxa_lock); 1464 1465 if (pval != NULL) 1466 ddi_prop_free(pval); 1467 if (idev_name != NULL) 1468 strfree(idev_name); 1469 if (odev_name != NULL) 1470 strfree(odev_name); 1471 return (rv); 1472 } 1473 1474 static int 1475 lxa_ioctl_devctl(int cmd, intptr_t arg, int mode) 1476 { 1477 /* devctl ioctls are only allowed from the global zone */ 1478 ASSERT(getzoneid() == 0); 1479 if (getzoneid() != 0) 1480 return (EINVAL); 1481 1482 switch (cmd) { 1483 case LXA_IOC_ZONE_REG: 1484 return (lxa_zone_reg(arg, mode)); 1485 case LXA_IOC_ZONE_UNREG: 1486 return (lxa_zone_unreg(arg, mode)); 1487 } 1488 1489 return (EINVAL); 1490 } 1491 1492 static int 1493 /*ARGSUSED*/ 1494 lxa_open(dev_t *devp, int flags, int otyp, cred_t *credp) 1495 { 1496 lxa_dev_type_t open_type = LXA_TYPE_INVALID; 1497 lxa_zstate_t *lxa_zs; 1498 lxa_state_t *lxa_state; 1499 minor_t minor; 1500 int rv; 1501 1502 if (getminor(*devp) == LXA_MINORNUM_DEVCTL) { 1503 /* 1504 * this is a devctl node, it exists to administer this 1505 * pseudo driver so it doesn't actually need access to 1506 * any underlying audio devices. hence there is nothing 1507 * really to do here. course, this driver should 1508 * only be administered from the global zone. 1509 */ 1510 ASSERT(getzoneid() == 0); 1511 if (getzoneid() != 0) 1512 return (EINVAL); 1513 return (0); 1514 } 1515 1516 /* lookup the zone state structure */ 1517 if (mod_hash_find(lxa_zstate_hash, (mod_hash_key_t)getzonename(), 1518 (mod_hash_val_t *)&lxa_zs) != 0) { 1519 return (EIO); 1520 } 1521 1522 /* determine what type of device was opened */ 1523 switch (getminor(*devp)) { 1524 case LXA_MINORNUM_DSP: 1525 open_type = LXA_TYPE_AUDIO; 1526 break; 1527 case LXA_MINORNUM_MIXER: 1528 open_type = LXA_TYPE_AUDIOCTL; 1529 break; 1530 default: 1531 return (EINVAL); 1532 } 1533 ASSERT(open_type != LXA_TYPE_INVALID); 1534 1535 /* all other opens are clone opens so get a new minor node */ 1536 minor = id_alloc(lxa_minor_id); 1537 1538 /* allocate and initialize the new lxa_state structure */ 1539 lxa_state = kmem_zalloc(sizeof (*lxa_state), KM_SLEEP); 1540 lxa_state->lxas_zs = lxa_zs; 1541 lxa_state->lxas_dev_old = *devp; 1542 lxa_state->lxas_dev_new = makedevice(getmajor(*devp), minor); 1543 lxa_state->lxas_flags = flags; 1544 lxa_state->lxas_type = open_type; 1545 1546 /* initialize the input and output device */ 1547 if (((rv = lxa_dev_open(lxa_state)) != 0) || 1548 ((rv = lxa_dev_getfeatures(lxa_state)) != 0)) { 1549 lxa_state_close(lxa_state); 1550 return (rv); 1551 } 1552 1553 /* 1554 * save this audio statue structure into a hash indexed 1555 * by it's minor device number. (this will provide a convient 1556 * way to lookup the state structure on future operations.) 1557 */ 1558 if (mod_hash_insert(lxa_state_hash, (mod_hash_key_t)(uintptr_t)minor, 1559 (mod_hash_val_t)lxa_state) != 0) { 1560 lxa_state_close(lxa_state); 1561 return (EIO); 1562 } 1563 1564 mutex_enter(&lxa_lock); 1565 1566 /* apply the currently cached zone PCM mixer levels */ 1567 if ((lxa_state->lxas_type == LXA_TYPE_AUDIO) && 1568 (lxa_state->lxas_odev_lh != NULL)) { 1569 audio_info_t ai; 1570 1571 AUDIO_INITINFO(&ai); 1572 ai.play.gain = lxa_zs->lxa_zs_pcm_levels.lxa_ml_gain; 1573 ai.play.balance = lxa_zs->lxa_zs_pcm_levels.lxa_ml_balance; 1574 1575 if ((rv = lxa_audio_setinfo(lxa_state, 1576 AUDIO_SETINFO, (intptr_t)&ai, FKIOCTL)) != 0) { 1577 mutex_exit(&lxa_lock); 1578 lxa_state_close(lxa_state); 1579 return (rv); 1580 } 1581 } 1582 1583 /* 1584 * we only allow one active open of the input or output device. 1585 * check here for duplicate opens 1586 */ 1587 if (lxa_state->lxas_type == LXA_TYPE_AUDIO) { 1588 if ((lxa_state->lxas_idev_lh != NULL) && 1589 (lxa_zs->lxa_zs_istate != NULL)) { 1590 mutex_exit(&lxa_lock); 1591 lxa_state_close(lxa_state); 1592 return (EBUSY); 1593 } 1594 if ((lxa_state->lxas_odev_lh != NULL) && 1595 (lxa_zs->lxa_zs_ostate != NULL)) { 1596 mutex_exit(&lxa_lock); 1597 lxa_state_close(lxa_state); 1598 return (EBUSY); 1599 } 1600 1601 /* not a duplicate open, update the global zone state */ 1602 if (lxa_state->lxas_idev_lh != NULL) 1603 lxa_zs->lxa_zs_istate = lxa_state; 1604 if (lxa_state->lxas_odev_lh != NULL) 1605 lxa_zs->lxa_zs_ostate = lxa_state; 1606 } 1607 mutex_exit(&lxa_lock); 1608 1609 /* make sure to return our newly allocated dev_t */ 1610 *devp = lxa_state->lxas_dev_new; 1611 return (0); 1612 } 1613 1614 static int 1615 /*ARGSUSED*/ 1616 lxa_close(dev_t dev, int flags, int otyp, cred_t *credp) 1617 { 1618 lxa_state_t *lxa_state; 1619 minor_t minor = getminor(dev); 1620 1621 /* handle devctl minor nodes (these nodes don't have a handle */ 1622 if (getminor(dev) == LXA_MINORNUM_DEVCTL) 1623 return (0); 1624 1625 /* get the handle for this device */ 1626 if (mod_hash_find(lxa_state_hash, (mod_hash_key_t)(uintptr_t)minor, 1627 (mod_hash_val_t *)&lxa_state) != 0) 1628 return (EINVAL); 1629 1630 lxa_state_close(lxa_state); 1631 return (0); 1632 } 1633 1634 static int 1635 /*ARGSUSED*/ 1636 lxa_read(dev_t dev, struct uio *uiop, cred_t *credp) 1637 { 1638 lxa_state_t *lxa_state; 1639 minor_t minor = getminor(dev); 1640 int rv; 1641 1642 /* get the handle for this device */ 1643 if (mod_hash_find(lxa_state_hash, (mod_hash_key_t)(uintptr_t)minor, 1644 (mod_hash_val_t *)&lxa_state) != 0) 1645 return (EINVAL); 1646 1647 /* 1648 * if a process has mmaped this device then we don't allow 1649 * any more reads or writes to the device 1650 */ 1651 if (lxa_state->lxas_umem_cookie != NULL) 1652 return (EIO); 1653 1654 /* we can't do a read if there is no input device */ 1655 if (lxa_state->lxas_idev_lh == NULL) 1656 return (EBADF); 1657 1658 /* pass the request on */ 1659 while (uiop->uio_resid != 0) { 1660 rv = ldi_read(lxa_state->lxas_idev_lh, uiop, kcred); 1661 if ((rv != 0) || (uiop->uio_fmode & (FNONBLOCK|FNDELAY))) { 1662 break; 1663 } 1664 } 1665 return (rv); 1666 } 1667 1668 static int 1669 /*ARGSUSED*/ 1670 lxa_write(dev_t dev, struct uio *uiop, cred_t *credp) 1671 { 1672 lxa_state_t *lxa_state; 1673 minor_t minor = getminor(dev); 1674 int rv; 1675 1676 /* get the handle for this device */ 1677 if (mod_hash_find(lxa_state_hash, (mod_hash_key_t)(uintptr_t)minor, 1678 (mod_hash_val_t *)&lxa_state) != 0) 1679 return (EINVAL); 1680 1681 /* 1682 * if a process has mmaped this device then we don't allow 1683 * any more reads or writes to the device 1684 */ 1685 if (lxa_state->lxas_umem_cookie != NULL) 1686 return (EIO); 1687 1688 /* we can't do a write if there is no output device */ 1689 if (lxa_state->lxas_odev_lh == NULL) 1690 return (EBADF); 1691 1692 /* pass the request on */ 1693 while (uiop->uio_resid != 0) { 1694 rv = ldi_write(lxa_state->lxas_odev_lh, uiop, kcred); 1695 if ((rv != 0) || (uiop->uio_fmode & (FNONBLOCK|FNDELAY))) { 1696 break; 1697 } 1698 } 1699 return (rv); 1700 } 1701 1702 static int 1703 /*ARGSUSED*/ 1704 lxa_ioctl(dev_t dev, int cmd, intptr_t arg, int mode, cred_t *credp, 1705 int *rvalp) 1706 { 1707 lxa_state_t *lxa_state; 1708 minor_t minor = getminor(dev); 1709 1710 /* handle devctl minor nodes (these nodes don't have a handle */ 1711 if (getminor(dev) == LXA_MINORNUM_DEVCTL) 1712 return (lxa_ioctl_devctl(cmd, arg, mode)); 1713 1714 /* get the handle for this device */ 1715 if (mod_hash_find(lxa_state_hash, (mod_hash_key_t)(uintptr_t)minor, 1716 (mod_hash_val_t *)&lxa_state) != 0) 1717 return (EINVAL); 1718 1719 ASSERT((lxa_state->lxas_type == LXA_TYPE_AUDIO) || 1720 (lxa_state->lxas_type == LXA_TYPE_AUDIOCTL)); 1721 1722 switch (cmd) { 1723 case LXA_IOC_GETMINORNUM: 1724 { 1725 int minornum = getminor(lxa_state->lxas_dev_old); 1726 if (ddi_copyout(&minornum, (void *)arg, 1727 sizeof (minornum), mode) != 0) 1728 return (EFAULT); 1729 } 1730 return (0); 1731 } 1732 1733 if (lxa_state->lxas_type == LXA_TYPE_AUDIO) { 1734 /* deal with native ioctl */ 1735 switch (cmd) { 1736 case LXA_IOC_MMAP_OUTPUT: 1737 return (lxa_ioc_mmap_output(lxa_state, arg, mode)); 1738 case LXA_IOC_MMAP_PTR: 1739 return (lxa_ioc_mmap_ptr(lxa_state, arg, mode)); 1740 case LXA_IOC_GET_FRAG_INFO: 1741 return (lxa_ioc_get_frag_info(lxa_state, arg, mode)); 1742 case LXA_IOC_SET_FRAG_INFO: 1743 return (lxa_ioc_set_frag_info(lxa_state, arg, mode)); 1744 } 1745 1746 /* deal with layered ioctls */ 1747 switch (cmd) { 1748 case AUDIO_DRAIN: 1749 return (lxa_audio_drain(lxa_state)); 1750 case AUDIO_SETINFO: 1751 return (lxa_audio_setinfo(lxa_state, 1752 AUDIO_SETINFO, arg, mode)); 1753 case AUDIO_GETINFO: 1754 return (lxa_audio_getinfo(lxa_state, arg, mode)); 1755 } 1756 } 1757 1758 if (lxa_state->lxas_type == LXA_TYPE_AUDIOCTL) { 1759 /* deal with native ioctl */ 1760 switch (cmd) { 1761 case LXA_IOC_MIXER_GET_VOL: 1762 return (lxa_mixer_get_common(lxa_state, 1763 cmd, arg, mode)); 1764 case LXA_IOC_MIXER_SET_VOL: 1765 return (lxa_mixer_set_common(lxa_state, 1766 cmd, arg, mode)); 1767 case LXA_IOC_MIXER_GET_MIC: 1768 return (lxa_mixer_get_common(lxa_state, 1769 cmd, arg, mode)); 1770 case LXA_IOC_MIXER_SET_MIC: 1771 return (lxa_mixer_set_common(lxa_state, 1772 cmd, arg, mode)); 1773 case LXA_IOC_MIXER_GET_PCM: 1774 return (lxa_mixer_get_pcm(lxa_state, arg, mode)); 1775 case LXA_IOC_MIXER_SET_PCM: 1776 return (lxa_mixer_set_pcm(lxa_state, arg, mode)); 1777 } 1778 1779 } 1780 1781 return (EINVAL); 1782 } 1783 1784 static int 1785 /*ARGSUSED*/ 1786 lxa_devmap(dev_t dev, devmap_cookie_t dhp, 1787 offset_t off, size_t len, size_t *maplen, uint_t model) 1788 { 1789 lxa_state_t *lxa_state; 1790 minor_t minor = getminor(dev); 1791 ddi_umem_cookie_t umem_cookie; 1792 void *umem_ptr; 1793 int rv; 1794 1795 /* get the handle for this device */ 1796 if (mod_hash_find(lxa_state_hash, (mod_hash_key_t)(uintptr_t)minor, 1797 (mod_hash_val_t *)&lxa_state) != 0) 1798 return (EINVAL); 1799 1800 /* we only support mmaping of audio devices */ 1801 if (lxa_state->lxas_type != LXA_TYPE_AUDIO) 1802 return (EINVAL); 1803 1804 /* we only support output via mmap */ 1805 if ((lxa_state->lxas_flags & FWRITE) == 0) 1806 return (EINVAL); 1807 1808 /* sanity check the amount of memory the user is allocating */ 1809 if ((len == 0) || 1810 (len > LXA_OSS_FRAG_MEM) || 1811 ((len % lxa_state->lxas_frag_size) != 0)) 1812 return (EINVAL); 1813 1814 /* allocate and clear memory to mmap */ 1815 umem_ptr = ddi_umem_alloc(len, DDI_UMEM_NOSLEEP, &umem_cookie); 1816 if (umem_ptr == NULL) 1817 return (ENOMEM); 1818 bzero(umem_ptr, len); 1819 1820 /* setup the memory mappings */ 1821 rv = devmap_umem_setup(dhp, lxa_dip, NULL, umem_cookie, 0, len, 1822 PROT_USER | PROT_READ | PROT_WRITE, 0, NULL); 1823 if (rv != 0) { 1824 ddi_umem_free(umem_cookie); 1825 return (EIO); 1826 } 1827 1828 mutex_enter(&lxa_lock); 1829 1830 /* we only support one mmap per open */ 1831 if (lxa_state->lxas_umem_cookie != NULL) { 1832 ASSERT(lxa_state->lxas_umem_ptr != NULL); 1833 mutex_exit(&lxa_lock); 1834 ddi_umem_free(umem_cookie); 1835 return (EBUSY); 1836 } 1837 ASSERT(lxa_state->lxas_umem_ptr == NULL); 1838 1839 *maplen = len; 1840 lxa_state->lxas_umem_len = len; 1841 lxa_state->lxas_umem_ptr = umem_ptr; 1842 lxa_state->lxas_umem_cookie = umem_cookie; 1843 mutex_exit(&lxa_lock); 1844 return (0); 1845 } 1846 1847 static int 1848 /*ARGSUSED*/ 1849 lxa_attach(dev_info_t *dip, ddi_attach_cmd_t cmd) 1850 { 1851 int instance = ddi_get_instance(dip); 1852 1853 if (cmd != DDI_ATTACH) 1854 return (DDI_FAILURE); 1855 1856 ASSERT(instance == 0); 1857 if (instance != 0) 1858 return (DDI_FAILURE); 1859 1860 lxa_dip = dip; 1861 mutex_init(&lxa_lock, NULL, MUTEX_DEFAULT, NULL); 1862 1863 /* create our minor nodes */ 1864 if (ddi_create_minor_node(dip, LXA_MINORNAME_DEVCTL, S_IFCHR, 1865 LXA_MINORNUM_DEVCTL, DDI_PSEUDO, 0) != DDI_SUCCESS) 1866 return (DDI_FAILURE); 1867 1868 if (ddi_create_minor_node(dip, LXA_MINORNAME_DSP, S_IFCHR, 1869 LXA_MINORNUM_DSP, DDI_PSEUDO, 0) != DDI_SUCCESS) 1870 return (DDI_FAILURE); 1871 1872 if (ddi_create_minor_node(dip, LXA_MINORNAME_MIXER, S_IFCHR, 1873 LXA_MINORNUM_MIXER, DDI_PSEUDO, 0) != DDI_SUCCESS) 1874 return (DDI_FAILURE); 1875 1876 /* allocate our data structures */ 1877 lxa_minor_id = id_space_create("lxa_minor_id", 1878 LXA_MINORNUM_COUNT, LX_AUDIO_MAX_OPENS); 1879 lxa_state_hash = mod_hash_create_idhash("lxa_state_hash", 1880 lxa_state_hash_size, mod_hash_null_valdtor); 1881 lxa_zstate_hash = mod_hash_create_strhash("lxa_zstate_hash", 1882 lxa_zstate_hash_size, mod_hash_null_valdtor); 1883 1884 return (DDI_SUCCESS); 1885 } 1886 1887 static int 1888 /*ARGSUSED*/ 1889 lxa_detach(dev_info_t *dip, ddi_detach_cmd_t cmd) 1890 { 1891 if (cmd != DDI_DETACH) 1892 return (DDI_FAILURE); 1893 1894 ASSERT(!MUTEX_HELD(&lxa_lock)); 1895 if (lxa_registered_zones > 0) 1896 return (DDI_FAILURE); 1897 1898 mod_hash_destroy_idhash(lxa_state_hash); 1899 mod_hash_destroy_idhash(lxa_zstate_hash); 1900 id_space_destroy(lxa_minor_id); 1901 lxa_state_hash = NULL; 1902 lxa_dip = NULL; 1903 1904 return (DDI_SUCCESS); 1905 } 1906 1907 static int 1908 /*ARGSUSED*/ 1909 lxa_getinfo(dev_info_t *dip, ddi_info_cmd_t infocmd, void *arg, void **resultp) 1910 { 1911 switch (infocmd) { 1912 case DDI_INFO_DEVT2DEVINFO: 1913 *resultp = lxa_dip; 1914 return (DDI_SUCCESS); 1915 1916 case DDI_INFO_DEVT2INSTANCE: 1917 *resultp = (void *)0; 1918 return (DDI_SUCCESS); 1919 } 1920 return (DDI_FAILURE); 1921 } 1922 1923 /* 1924 * Driver flags 1925 */ 1926 static struct cb_ops lxa_cb_ops = { 1927 lxa_open, /* open */ 1928 lxa_close, /* close */ 1929 nodev, /* strategy */ 1930 nodev, /* print */ 1931 nodev, /* dump */ 1932 lxa_read, /* read */ 1933 lxa_write, /* write */ 1934 lxa_ioctl, /* ioctl */ 1935 lxa_devmap, /* devmap */ 1936 nodev, /* mmap */ 1937 ddi_devmap_segmap, /* segmap */ 1938 nochpoll, /* chpoll */ 1939 ddi_prop_op, /* prop_op */ 1940 NULL, /* cb_str */ 1941 D_NEW | D_MP | D_DEVMAP, 1942 CB_REV, 1943 NULL, 1944 NULL 1945 }; 1946 1947 static struct dev_ops lxa_ops = { 1948 DEVO_REV, 1949 0, 1950 lxa_getinfo, 1951 nulldev, 1952 nulldev, 1953 lxa_attach, 1954 lxa_detach, 1955 nodev, 1956 &lxa_cb_ops, 1957 NULL, 1958 NULL, 1959 ddi_quiesce_not_needed, /* quiesce */ 1960 }; 1961 1962 /* 1963 * Module linkage information for the kernel. 1964 */ 1965 static struct modldrv modldrv = { 1966 &mod_driverops, /* type of module */ 1967 "linux audio driver", /* description of module */ 1968 &lxa_ops /* driver ops */ 1969 }; 1970 1971 static struct modlinkage modlinkage = { 1972 MODREV_1, 1973 &modldrv, 1974 NULL 1975 }; 1976 1977 /* 1978 * standard module entry points 1979 */ 1980 int 1981 _init(void) 1982 { 1983 return (mod_install(&modlinkage)); 1984 } 1985 1986 int 1987 _fini(void) 1988 { 1989 return (mod_remove(&modlinkage)); 1990 } 1991 1992 int 1993 _info(struct modinfo *modinfop) 1994 { 1995 return (mod_info(&modlinkage, modinfop)); 1996 }