4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License, Version 1.0 only
6 * (the "License"). You may not use this file except in compliance
9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10 * or http://www.opensolaris.org/os/licensing.
11 * See the License for the specific language governing permissions
12 * and limitations under the License.
14 * When distributing Covered Code, include this CDDL HEADER in each
15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16 * If applicable, add the following below this CDDL HEADER, with the
17 * fields enclosed by brackets "[]" replaced with your own identifying
18 * information: Portions Copyright [yyyy] [name of copyright owner]
23 * Copyright 2004 Sun Microsystems, Inc. All rights reserved.
24 * Use is subject to license terms.
29 * This file contains generic SCSI related functions for scsi plug-in
34 #include <sys/types.h>
36 #include <sys/ioctl.h>
40 #include <sys/smedia.h>
41 #include "../../../library/inc/rmedia.h"
45 #include <sys/scsi/scsi.h>
47 #include "../../../library/common/l_defines.h"
50 static int32_t remap_shared_buf(rmedia_handle_t
*, size_t, char *);
53 #define BUF_SIZE_MULTIPLE 0x2000
56 _m_get_media_info(rmedia_handle_t
*handle
, void *ip
)
58 smmedium_prop_t
*medinfo
= ip
;
60 smedia_reqget_medium_property_t reqget_medium_property
;
61 smedia_retget_medium_property_t
*retget_medium_property
;
62 smedia_reterror_t
*reterror
;
64 char rbuf
[sizeof (smedia_services_t
) + sizeof (door_desc_t
)];
66 DPRINTF("get_media_info called.\n");
67 /* Check for valid handle */
69 DPRINTF("Null Handle\n");
73 if (handle
->sm_signature
!= (int32_t)LIBSMEDIA_SIGNATURE
) {
74 DPRINTF("Invalid signature in handle.\n");
75 DPRINTF2("Signature expected=0x%x, found=0x%x\n",
76 LIBSMEDIA_SIGNATURE
, handle
->sm_signature
);
77 DPRINTF1("fd=%d\n", handle
->sm_fd
);
81 (void) memset(medinfo
, 0, sizeof (smmedium_prop_t
));
83 reqget_medium_property
.cnum
= SMEDIA_CNUM_GET_MEDIUM_PROPERTY
;
84 door_args
.data_ptr
= (char *)&reqget_medium_property
;
85 door_args
.data_size
= sizeof (smedia_services_t
);
86 door_args
.desc_ptr
= NULL
;
87 door_args
.desc_num
= 0;
88 door_args
.rbuf
= rbuf
;
89 door_args
.rsize
= sizeof (rbuf
);
91 ret_val
= door_call(handle
->sm_door
, &door_args
);
96 retget_medium_property
=
97 (smedia_retget_medium_property_t
*)((void *)door_args
.data_ptr
);
98 reterror
= (smedia_reterror_t
*)((void *)door_args
.data_ptr
);
99 if (reterror
->cnum
== SMEDIA_CNUM_ERROR
) {
101 "Error in get_medium_property. errnum = 0x%x \n", reterror
->errnum
);
102 errno
= reterror
->errnum
;
106 *medinfo
= retget_medium_property
->smprop
;
112 _m_get_device_info(rmedia_handle_t
*handle
, void *ip
)
114 struct smdevice_info
*dev_info
= ip
;
116 smedia_reqget_device_info_t reqget_device_info
;
117 smedia_retget_device_info_t
*retget_device_info
;
118 smedia_reterror_t
*reterror
;
119 door_arg_t door_args
;
120 char rbuf
[sizeof (smedia_services_t
) + sizeof (door_desc_t
)];
121 char *vendor_name
, *product_name
, *fw_version
;
123 /* Check for valid handle */
124 if (handle
== NULL
) {
125 DPRINTF("Null Handle\n");
129 if (handle
->sm_signature
!= LIBSMEDIA_SIGNATURE
) {
130 DPRINTF("Invalid signature in handle.\n");
135 vendor_name
= (char *)malloc(9);
136 if (vendor_name
== NULL
) {
141 product_name
= (char *)malloc(17);
142 if (product_name
== NULL
) {
149 fw_version
= (char *)malloc(18);
150 if (fw_version
== NULL
) {
157 reqget_device_info
.cnum
= SMEDIA_CNUM_GET_DEVICE_INFO
;
158 door_args
.data_ptr
= (char *)&reqget_device_info
;
159 door_args
.data_size
= sizeof (smedia_services_t
);
160 door_args
.desc_ptr
= NULL
;
161 door_args
.desc_num
= 0;
162 door_args
.rbuf
= rbuf
;
163 door_args
.rsize
= sizeof (rbuf
);
165 ret_val
= door_call(handle
->sm_door
, &door_args
);
173 retget_device_info
= (smedia_retget_device_info_t
*)
174 ((void *)door_args
.data_ptr
);
175 reterror
= (smedia_reterror_t
*)((void *)door_args
.data_ptr
);
176 if (reterror
->cnum
== SMEDIA_CNUM_ERROR
) {
177 DPRINTF1("Error in get_device_info. errnum = 0x%x \n",
179 errno
= reterror
->errnum
;
186 dev_info
->sm_vendor_name
= vendor_name
;
187 dev_info
->sm_product_name
= product_name
;
188 dev_info
->sm_firmware_version
= fw_version
;
191 (void) strlcpy(dev_info
->sm_vendor_name
,
192 retget_device_info
->sm_vendor_name
, 8);
193 dev_info
->sm_vendor_name
[8] = 0;
194 (void) strlcpy(dev_info
->sm_product_name
,
195 retget_device_info
->sm_product_name
, 16);
196 dev_info
->sm_product_name
[16] = 0;
197 (void) strlcpy(dev_info
->sm_firmware_version
,
198 retget_device_info
->sm_firmware_version
, 17);
199 dev_info
->sm_firmware_version
[17] = 0;
201 dev_info
->sm_interface_type
= retget_device_info
->sm_interface_type
;
204 DPRINTF1("Vendor name = %s\n", dev_info
->sm_vendor_name
);
205 DPRINTF1("product name = %s\n", dev_info
->sm_product_name
);
206 DPRINTF1("Firmware revision = %s\n", dev_info
->sm_firmware_version
);
213 _m_free_device_info(rmedia_handle_t
*handle
, void *ip
)
215 struct smdevice_info
*dev_info
= ip
;
217 /* Check for valid handle */
218 if (handle
== NULL
) {
219 DPRINTF("Null Handle\n");
223 if (handle
->sm_signature
!= LIBSMEDIA_SIGNATURE
) {
224 DPRINTF("Invalid signature in handle.\n");
229 free(dev_info
->sm_vendor_name
);
230 free(dev_info
->sm_product_name
);
231 free(dev_info
->sm_firmware_version
);
236 _m_raw_write(rmedia_handle_t
*handle
, void *i_p
)
239 struct raw_params
*r_p
= (struct raw_params
*)i_p
;
240 smedia_reqraw_write_t reqraw_write
;
241 smedia_retraw_write_t
*retraw_write
;
242 smedia_reterror_t
*reterror
;
243 door_arg_t door_args
;
244 char rbuf
[sizeof (smedia_services_t
) + sizeof (door_desc_t
)];
246 /* Check for valid handle */
247 if (handle
== NULL
) {
248 DPRINTF("Null Handle\n");
252 if (handle
->sm_signature
!= LIBSMEDIA_SIGNATURE
) {
253 DPRINTF("Invalid signature in handle.\n");
257 (void) mutex_lock(&handle
->sm_bufmutex
);
258 ret_val
= remap_shared_buf(handle
, r_p
->size
, r_p
->buffer
);
259 if (ret_val
!= 0) goto error
;
260 reqraw_write
.cnum
= SMEDIA_CNUM_RAW_WRITE
;
261 reqraw_write
.blockno
= r_p
->offset
;
262 reqraw_write
.nbytes
= r_p
->size
;
263 bcopy(r_p
->buffer
, handle
->sm_buf
, r_p
->size
);
264 door_args
.data_ptr
= (char *)&reqraw_write
;
265 door_args
.data_size
= sizeof (reqraw_write
);
266 door_args
.desc_ptr
= NULL
;
267 door_args
.desc_num
= 0;
268 door_args
.rbuf
= rbuf
;
269 door_args
.rsize
= sizeof (rbuf
);
271 ret_val
= door_call(handle
->sm_door
, &door_args
);
276 retraw_write
= (smedia_retraw_write_t
*)((void *)door_args
.data_ptr
);
277 reterror
= (smedia_reterror_t
*)((void *)door_args
.data_ptr
);
278 if (reterror
->cnum
== SMEDIA_CNUM_ERROR
) {
279 DPRINTF3("Error in raw write. errnum = 0x%x "
280 "blk_num = 0x%x(%d)\n", reterror
->errnum
, r_p
->offset
,
282 errno
= reterror
->errnum
;
285 (void) mutex_unlock(&handle
->sm_bufmutex
);
286 return (retraw_write
->nbytes
);
289 (void) mutex_unlock(&handle
->sm_bufmutex
);
294 _m_raw_read(rmedia_handle_t
*handle
, void *i_p
)
296 struct raw_params
*r_p
= (struct raw_params
*)i_p
;
297 int32_t ret_val
, bytes_read
;
298 smedia_reqraw_read_t reqraw_read
;
299 smedia_retraw_read_t
*retraw_read
;
300 smedia_reterror_t
*reterror
;
301 door_arg_t door_args
;
302 char rbuf
[sizeof (smedia_services_t
) + sizeof (door_desc_t
)];
304 /* Check for valid handle */
305 if (handle
== NULL
) {
306 DPRINTF("Null Handle\n");
310 if (handle
->sm_signature
!= LIBSMEDIA_SIGNATURE
) {
311 DPRINTF("Invalid signature in handle.\n");
315 * Check if another thread is doing an IO with same handle.
316 * In that case ww block here.
318 (void) mutex_lock(&handle
->sm_bufmutex
);
319 ret_val
= remap_shared_buf(handle
, r_p
->size
, r_p
->buffer
);
320 if (ret_val
!= 0) goto error
;
322 reqraw_read
.cnum
= SMEDIA_CNUM_RAW_READ
;
323 reqraw_read
.blockno
= r_p
->offset
;
324 reqraw_read
.nbytes
= r_p
->size
;
325 door_args
.data_ptr
= (char *)&reqraw_read
;
326 door_args
.data_size
= sizeof (smedia_services_t
);
327 door_args
.desc_ptr
= NULL
;
328 door_args
.desc_num
= 0;
329 door_args
.rbuf
= rbuf
;
330 door_args
.rsize
= sizeof (rbuf
);
332 ret_val
= door_call(handle
->sm_door
, &door_args
);
337 retraw_read
= (smedia_retraw_read_t
*)((void *)door_args
.data_ptr
);
338 reterror
= (smedia_reterror_t
*)((void *)door_args
.data_ptr
);
339 if (reterror
->cnum
== SMEDIA_CNUM_ERROR
) {
343 DPRINTF3("Error in raw read. errnum = 0x%x "
344 "blk_num = 0x%x(%d)\n", reterror
->errnum
, r_p
->offset
,
346 errno
= reterror
->errnum
;
349 (void) memcpy(r_p
->buffer
, handle
->sm_buf
, retraw_read
->nbytes
);
350 bytes_read
= retraw_read
->nbytes
;
351 (void) mutex_unlock(&handle
->sm_bufmutex
);
355 (void) mutex_unlock(&handle
->sm_bufmutex
);
361 _m_media_format(rmedia_handle_t
*handle
, void *ip
)
364 struct format_flags
*ffl
= (struct format_flags
*)ip
;
365 smedia_reqformat_t reqformat
;
366 smedia_reterror_t
*reterror
;
367 door_arg_t door_args
;
368 char rbuf
[sizeof (smedia_services_t
) + sizeof (door_desc_t
)];
370 /* Check for valid handle */
371 if (handle
== NULL
) {
372 DPRINTF("Null Handle\n");
376 if (handle
->sm_signature
!= LIBSMEDIA_SIGNATURE
) {
377 DPRINTF("Invalid signature in handle.\n");
381 reqformat
.cnum
= SMEDIA_CNUM_FORMAT
;
382 reqformat
.flavor
= ffl
->flavor
;
383 reqformat
.mode
= ffl
->mode
;
384 door_args
.data_ptr
= (char *)&reqformat
;
385 door_args
.data_size
= sizeof (smedia_services_t
);
386 door_args
.desc_ptr
= NULL
;
387 door_args
.desc_num
= 0;
388 door_args
.rbuf
= rbuf
;
389 door_args
.rsize
= sizeof (rbuf
);
391 ret_val
= door_call(handle
->sm_door
, &door_args
);
396 reterror
= (smedia_reterror_t
*)((void *)door_args
.data_ptr
);
397 if (reterror
->cnum
== SMEDIA_CNUM_ERROR
) {
398 DPRINTF1("Error in format. errnum = 0x%x \n", reterror
->errnum
);
399 errno
= reterror
->errnum
;
406 _m_get_media_status(rmedia_handle_t
*handle
, void *ip
)
408 smwp_state_t
*wp
= ip
;
410 smedia_reqget_protection_status_t reqget_protection_status
;
411 smedia_retget_protection_status_t
*retget_protection_status
;
412 smedia_reterror_t
*reterror
;
413 door_arg_t door_args
;
414 char rbuf
[sizeof (smedia_services_t
) + sizeof (door_desc_t
)];
416 /* Check for valid handle */
417 if (handle
== NULL
) {
418 DPRINTF("Null Handle\n");
422 if (handle
->sm_signature
!= LIBSMEDIA_SIGNATURE
) {
423 DPRINTF("Invalid signature in handle.\n");
427 reqget_protection_status
.cnum
= SMEDIA_CNUM_GET_PROTECTION_STATUS
;
428 door_args
.data_ptr
= (char *)&reqget_protection_status
;
429 door_args
.data_size
= sizeof (smedia_services_t
);
430 door_args
.desc_ptr
= NULL
;
431 door_args
.desc_num
= 0;
432 door_args
.rbuf
= rbuf
;
433 door_args
.rsize
= sizeof (rbuf
);
435 ret_val
= door_call(handle
->sm_door
, &door_args
);
440 retget_protection_status
= (smedia_retget_protection_status_t
*)
441 ((void *)door_args
.data_ptr
);
442 reterror
= (smedia_reterror_t
*)((void *)door_args
.data_ptr
);
443 if (reterror
->cnum
== SMEDIA_CNUM_ERROR
) {
444 DPRINTF1("Error in get_protection-status. errnum = 0x%x \n",
446 errno
= reterror
->errnum
;
449 (void) memcpy((char *)wp
, (char *)&retget_protection_status
->prot_state
,
450 sizeof (smwp_state_t
));
455 _m_set_media_status(rmedia_handle_t
*handle
, void *ip
)
458 smwp_state_t
*wp
= ip
;
460 smedia_reqset_protection_status_t reqset_protection_status
;
461 smedia_reterror_t
*reterror
;
462 door_arg_t door_args
;
463 char rbuf
[sizeof (smedia_services_t
) + sizeof (door_desc_t
)];
465 /* Check for valid handle */
466 if (handle
== NULL
) {
467 DPRINTF("Null Handle\n");
471 if (handle
->sm_signature
!= LIBSMEDIA_SIGNATURE
) {
472 DPRINTF("Invalid signature in handle.\n");
476 reqset_protection_status
.cnum
= SMEDIA_CNUM_SET_PROTECTION_STATUS
;
477 reqset_protection_status
.prot_state
= *wp
;
478 door_args
.data_ptr
= (char *)&reqset_protection_status
;
479 door_args
.data_size
= sizeof (smedia_services_t
);
480 door_args
.desc_ptr
= NULL
;
481 door_args
.desc_num
= 0;
482 door_args
.rbuf
= rbuf
;
483 door_args
.rsize
= sizeof (rbuf
);
485 ret_val
= door_call(handle
->sm_door
, &door_args
);
490 reterror
= (smedia_reterror_t
*)((void *)door_args
.data_ptr
);
491 if (reterror
->cnum
== SMEDIA_CNUM_ERROR
) {
493 "Error in set_protection-status. errnum = 0x%x \n", reterror
->errnum
);
494 errno
= reterror
->errnum
;
501 _m_reassign_block(rmedia_handle_t
*handle
, void *ip
)
504 diskaddr_t
*blockp
= (diskaddr_t
*)ip
;
506 smedia_reqreassign_block_t reqreassign_block
;
507 smedia_reterror_t
*reterror
;
508 door_arg_t door_args
;
509 char rbuf
[sizeof (smedia_services_t
) + sizeof (door_desc_t
)];
511 /* Check for valid handle */
512 if (handle
== NULL
) {
513 DPRINTF("Null Handle\n");
517 if (handle
->sm_signature
!= LIBSMEDIA_SIGNATURE
) {
518 DPRINTF("Invalid signature in handle.\n");
523 DPRINTF1("reassign block %d\n", block
);
524 reqreassign_block
.cnum
= SMEDIA_CNUM_REASSIGN_BLOCK
;
525 reqreassign_block
.blockno
= block
;
526 door_args
.data_ptr
= (char *)&reqreassign_block
;
527 door_args
.data_size
= sizeof (smedia_services_t
);
528 door_args
.desc_ptr
= NULL
;
529 door_args
.desc_num
= 0;
530 door_args
.rbuf
= rbuf
;
531 door_args
.rsize
= sizeof (rbuf
);
533 ret_val
= door_call(handle
->sm_door
, &door_args
);
538 reterror
= (smedia_reterror_t
*)((void *)door_args
.data_ptr
);
539 if (reterror
->cnum
== SMEDIA_CNUM_ERROR
) {
540 DPRINTF2("Error in reassign_block. block = 0x%x "
541 "errnum = 0x%x \n", block
, reterror
->errnum
);
542 errno
= reterror
->errnum
;
550 _m_eject(rmedia_handle_t
*handle
, void *ip
)
554 /* Check for valid handle */
555 if (handle
== NULL
) {
556 DPRINTF("Null Handle\n");
560 if (handle
->sm_signature
!= LIBSMEDIA_SIGNATURE
) {
561 DPRINTF("Invalid signature in handle.\n");
566 return (ioctl(fd
, DKIOCEJECT
));
570 _m_device_type(ushort_t ctype
, ushort_t mtype
)
572 if ((ctype
== DKC_SCSI_CCS
) ||
573 (ctype
== DKC_MD21
) ||
574 (ctype
== DKC_CDROM
)) {
584 return (SM_SCSI_VERSION_1
);
588 _m_check_format_status(rmedia_handle_t
*handle
, void *ip
)
591 smedia_reqcheck_format_status_t reqcheck_format_status
;
592 smedia_retcheck_format_status_t
*retcheck_format_status
;
593 smedia_reterror_t
*reterror
;
594 door_arg_t door_args
;
595 char rbuf
[sizeof (smedia_services_t
) + sizeof (door_desc_t
)];
597 /* Check for valid handle */
598 if (handle
== NULL
) {
599 DPRINTF("Null Handle\n");
603 if (handle
->sm_signature
!= LIBSMEDIA_SIGNATURE
) {
604 DPRINTF("Invalid signature in handle.\n");
608 reqcheck_format_status
.cnum
= SMEDIA_CNUM_CHECK_FORMAT_STATUS
;
609 door_args
.data_ptr
= (char *)&reqcheck_format_status
;
610 door_args
.data_size
= sizeof (smedia_services_t
);
611 door_args
.desc_ptr
= NULL
;
612 door_args
.desc_num
= 0;
613 door_args
.rbuf
= rbuf
;
614 door_args
.rsize
= sizeof (rbuf
);
616 ret_val
= door_call(handle
->sm_door
, &door_args
);
621 retcheck_format_status
=
622 (smedia_retcheck_format_status_t
*)((void *)door_args
.data_ptr
);
623 reterror
= (smedia_reterror_t
*)((void *)door_args
.data_ptr
);
624 if (reterror
->cnum
== SMEDIA_CNUM_ERROR
) {
625 DPRINTF1("Error in check_format_status. errnum = 0x%x \n",
627 errno
= reterror
->errnum
;
630 return (retcheck_format_status
->percent_complete
);
634 _m_uscsi_cmd(rmedia_handle_t
*handle
, struct uscsi_cmd
*ucmd
)
637 smedia_requscsi_cmd_t requscsi_cmd
;
638 smedia_retuscsi_cmd_t
*retuscsi_cmd
;
639 smedia_reterror_t
*reterror
;
640 door_arg_t door_args
;
641 char rbuf
[sizeof (smedia_services_t
) + sizeof (door_desc_t
)];
643 /* Check for valid handle */
644 if (handle
== NULL
) {
645 DPRINTF("Null Handle\n");
649 if (handle
->sm_signature
!= LIBSMEDIA_SIGNATURE
) {
650 DPRINTF("Invalid signature in handle.\n");
655 * We will be validating the user supplied buffer lengths and
658 if (ucmd
->uscsi_cdblen
> MAX_CDB_LEN
) {
659 DPRINTF("Invalid cdblen specified.\n");
663 if ((ucmd
->uscsi_flags
& USCSI_RQENABLE
) &&
664 (ucmd
->uscsi_rqlen
> MAX_RQ_LEN
)) {
665 DPRINTF("Invalid rqlen specified.\n");
669 if (ucmd
->uscsi_cdb
== NULL
) {
670 DPRINTF("cdb buffer is NULL.\n");
674 if ((ucmd
->uscsi_buflen
) && (ucmd
->uscsi_bufaddr
== NULL
)) {
675 DPRINTF("bufaddr is NULL.\n");
679 if ((ucmd
->uscsi_flags
& USCSI_RQENABLE
) &&
680 (ucmd
->uscsi_rqbuf
== NULL
)) {
681 DPRINTF("rqbuf is NULL.\n");
686 * Check if another thread is doing an IO with same handle.
687 * In that case we block here.
689 (void) mutex_lock(&handle
->sm_bufmutex
);
690 ret_val
= remap_shared_buf(handle
, ucmd
->uscsi_buflen
,
691 ucmd
->uscsi_bufaddr
);
693 DPRINTF("remap of shared buf failed.\n");
697 requscsi_cmd
.cnum
= SMEDIA_CNUM_USCSI_CMD
;
698 requscsi_cmd
.uscsi_flags
= ucmd
->uscsi_flags
;
699 requscsi_cmd
.uscsi_timeout
= ucmd
->uscsi_timeout
;
700 requscsi_cmd
.uscsi_buflen
= ucmd
->uscsi_buflen
;
701 requscsi_cmd
.uscsi_cdblen
= ucmd
->uscsi_cdblen
;
702 requscsi_cmd
.uscsi_rqlen
= ucmd
->uscsi_rqlen
;
705 * The uscsi_buflen has been validated in the call to
706 * remap_shared_buf() done earlier.
708 /* Check for write */
709 if (!(ucmd
->uscsi_flags
& USCSI_READ
)) {
710 bcopy(ucmd
->uscsi_bufaddr
, handle
->sm_buf
, ucmd
->uscsi_buflen
);
713 bcopy(ucmd
->uscsi_cdb
, requscsi_cmd
.uscsi_cdb
, ucmd
->uscsi_cdblen
);
715 door_args
.data_ptr
= (char *)&requscsi_cmd
;
716 door_args
.data_size
= sizeof (smedia_services_t
);
717 door_args
.desc_ptr
= NULL
;
718 door_args
.desc_num
= 0;
719 door_args
.rbuf
= rbuf
;
720 door_args
.rsize
= sizeof (rbuf
);
722 ret_val
= door_call(handle
->sm_door
, &door_args
);
727 retuscsi_cmd
= (smedia_retuscsi_cmd_t
*)((void *)door_args
.data_ptr
);
728 reterror
= (smedia_reterror_t
*)((void *)door_args
.data_ptr
);
729 if (reterror
->cnum
== SMEDIA_CNUM_ERROR
) {
731 "Error in uscsi cmd. errnum = 0x%x\n", reterror
->errnum
);
732 errno
= reterror
->errnum
;
735 ucmd
->uscsi_status
= retuscsi_cmd
->uscsi_status
;
736 ucmd
->uscsi_resid
= retuscsi_cmd
->uscsi_resid
;
737 ucmd
->uscsi_rqstatus
= retuscsi_cmd
->uscsi_rqstatus
;
738 ucmd
->uscsi_rqresid
= retuscsi_cmd
->uscsi_rqresid
;
739 if ((ucmd
->uscsi_flags
& USCSI_RQENABLE
) &&
740 (ucmd
->uscsi_rqbuf
!= NULL
)) {
741 bcopy(retuscsi_cmd
->uscsi_rqbuf
, ucmd
->uscsi_rqbuf
,
744 errno
= retuscsi_cmd
->uscsi_errno
;
749 if (ucmd
->uscsi_resid
> ucmd
->uscsi_buflen
) {
751 * Invalid resid value. return error.
756 if (ucmd
->uscsi_flags
& USCSI_READ
) {
757 (void) memcpy(ucmd
->uscsi_bufaddr
,
758 handle
->sm_buf
, ucmd
->uscsi_buflen
- ucmd
->uscsi_resid
);
760 (void) mutex_unlock(&handle
->sm_bufmutex
);
762 if (retuscsi_cmd
->uscsi_retval
|| ucmd
->uscsi_status
)
763 DPRINTF2("Error in uscsi_cmd: retval=0x%x uscsi_status=0x%x\n",
764 retuscsi_cmd
->uscsi_retval
, ucmd
->uscsi_status
);
766 return (retuscsi_cmd
->uscsi_retval
);
768 (void) mutex_unlock(&handle
->sm_bufmutex
);
773 remap_shared_buf(rmedia_handle_t
*handle
, size_t buf_size
, char *buffer
)
775 char rbuf
[sizeof (smedia_services_t
) + sizeof (door_desc_t
)];
777 smedia_reqset_shfd_t reqset_shfd
;
778 smedia_reterror_t
*reterror
;
780 door_arg_t door_args
;
781 door_desc_t ddesc
[2];
783 size_t shared_bufsize
;
784 off_t file_size
, ret
;
786 if (handle
->sm_bufsize
>= buf_size
)
788 shared_bufsize
= ((buf_size
+ BUF_SIZE_MULTIPLE
- 1)/BUF_SIZE_MULTIPLE
)
790 if (handle
->sm_buffd
!= -1) {
791 /* extend the file and re-map */
792 fd
= handle
->sm_buffd
;
793 ret_val
= munmap(handle
->sm_buf
, handle
->sm_bufsize
);
795 DPRINTF1("remap:munmap failed. errno = 0x%x\n", errno
);
797 handle
->sm_buf
= NULL
;
798 handle
->sm_bufsize
= 0;
799 handle
->sm_buffd
= -1;
802 file_size
= lseek(fd
, 0, SEEK_END
);
803 if (file_size
== -1) {
804 DPRINTF1("remap:lseek failed. errno = 0x%x\n", errno
);
807 handle
->sm_buf
= NULL
;
808 handle
->sm_bufsize
= 0;
809 handle
->sm_buffd
= -1;
811 /* create a new file and mapping */
812 (void) sprintf(fname
, "/tmp/libsmedia_mmaped_file_XXXXXX");
815 DPRINTF1("remap:mktemp failed. errno = 0x%x\n", errno
);
818 ret_val
= unlink(fname
);
820 DPRINTF1("remap:unlink failed. errno = 0x%x\n", errno
);
826 /* Need to start at the beginning of the file when enlarging */
827 ret
= lseek(fd
, 0, SEEK_SET
);
829 DPRINTF1("remap:lseek failed. errno = 0x%x\n", errno
);
832 while (file_size
< shared_bufsize
) {
833 ret_val
= write(fd
, buffer
, buf_size
);
834 if (ret_val
!= buf_size
) {
835 DPRINTF1("remap:write failed. errno = 0x%x\n", errno
);
839 file_size
+= buf_size
;
841 fbuf
= mmap(NULL
, shared_bufsize
, PROT_READ
| PROT_WRITE
,
843 if (fbuf
== (char *)-1) {
844 perror("mmap failed");
849 reqset_shfd
.cnum
= SMEDIA_CNUM_SET_SHFD
;
850 reqset_shfd
.fdbuf_len
= shared_bufsize
;
851 ddesc
[0].d_data
.d_desc
.d_descriptor
= fd
;
852 ddesc
[0].d_attributes
= DOOR_DESCRIPTOR
;
853 door_args
.data_ptr
= (char *)&reqset_shfd
;
854 door_args
.data_size
= sizeof (reqset_shfd
);
855 door_args
.desc_ptr
= &ddesc
[0];
856 door_args
.desc_num
= 1;
857 door_args
.rbuf
= rbuf
;
858 door_args
.rsize
= sizeof (rbuf
);
860 ret_val
= door_call(handle
->sm_door
, &door_args
);
866 reterror
= (smedia_reterror_t
*)((void *)door_args
.data_ptr
);
867 if (reterror
->cnum
== SMEDIA_CNUM_ERROR
) {
868 DPRINTF1("Error in set shfd. errnum = 0x%x\n",
870 errno
= reterror
->errnum
;
874 handle
->sm_buffd
= fd
;
875 handle
->sm_buf
= fbuf
;
876 handle
->sm_bufsize
= shared_bufsize
;
877 DPRINTF("Returned successful from remap shared buf routine.\n");