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 (c) 2010, Oracle and/or its affiliates. All rights reserved.
23  */
24 
25 #include <stdio.h>
26 #include <libintl.h>
27 #include <errno.h>
28 #include <assert.h>
29 #include <unistd.h>
30 #include "bblk_einfo.h"
31 #include "boot_utils.h"
32 
33 boolean_t boot_debug = B_FALSE;
34 boolean_t nowrite = B_FALSE;
35 
36 void
boot_gdebug(const char * funcname,char * format,...)37 boot_gdebug(const char *funcname, char *format, ...)
38 {
39 	va_list ap;
40 
41 	if (boot_debug == B_FALSE)
42 		return;
43 
44 	(void) fprintf(stdout, "%s(): ", funcname);
45 
46 	va_start(ap, format);
47 	/* LINTED: E_SEC_PRINTF_VAR_FMT */
48 	(void) vfprintf(stdout, format, ap);
49 	va_end(ap);
50 }
51 
52 /*
53  * Common functions to write out and read in block-sized data to a file
54  * descriptor.
55  */
56 int
write_out(int fd,void * buffer,size_t size,off_t off)57 write_out(int fd, void *buffer, size_t size, off_t off)
58 {
59 	int		ret;
60 	char		*buf = buffer;
61 
62 	if (size % SECTOR_SIZE != 0)
63 		BOOT_DEBUG("Expected block-sized data, got: %d\n", size);
64 
65 	/* Dry run. */
66 	if (nowrite)
67 		return (BC_SUCCESS);
68 
69 	for (;;) {
70 	again:
71 		ret = pwrite(fd, buf, size, off);
72 		if (ret == -1) {
73 			if (errno == EAGAIN)
74 				goto again;
75 			else
76 				return (BC_ERROR);
77 			}
78 		if (ret < size) {
79 			size -= ret;
80 			off += ret;
81 			buf += ret;
82 		} else {
83 			break;
84 		}
85 	}
86 	return (BC_SUCCESS);
87 }
88 
89 int
read_in(int fd,void * buffer,size_t size,off_t off)90 read_in(int fd, void *buffer, size_t size, off_t off)
91 {
92 	int		ret;
93 	char		*buf = buffer;
94 
95 	if (size % SECTOR_SIZE != 0)
96 		BOOT_DEBUG("Expected block-sized data, got: %d\n", size);
97 
98 	for (;;) {
99 	again:
100 		ret = pread(fd, buf, size, off);
101 		if (ret == -1) {
102 			if (errno == EAGAIN)
103 				goto again;
104 			else
105 				return (BC_ERROR);
106 			}
107 		if (ret < size) {
108 			size -= ret;
109 			off += ret;
110 			buf += ret;
111 		} else {
112 			break;
113 		}
114 	}
115 	return (BC_SUCCESS);
116 }
117