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, Version 1.0 only 6 * (the "License"). You may not use this file except in compliance 7 * with the License. 8 * 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. 13 * 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] 19 * 20 * CDDL HEADER END 21 */ 22 /* 23 * Copyright 2004 Sun Microsystems, Inc. All rights reserved. 24 * Use is subject to license terms. 25 */ 26 27 #pragma ident "%Z%%M% %I% %E% SMI" 28 29 30 /* 31 * Just in case we're not in a build environment, make sure that 32 * TEXT_DOMAIN gets set to something. 33 */ 34 #if !defined(TEXT_DOMAIN) 35 #define TEXT_DOMAIN "SYS_TEST" 36 #endif 37 38 /* 39 * patch md.cf file 40 */ 41 42 #include <meta.h> 43 44 /* 45 * save metadevice configuration in md.cf 46 */ 47 int 48 meta_update_md_cf( 49 mdsetname_t *sp, 50 md_error_t *ep 51 ) 52 { 53 char *name = METACONF; 54 char *tname = METACONFTMP; 55 FILE *tfp = NULL; 56 FILE *mfp = NULL; 57 mdprtopts_t options = PRINT_SHORT | PRINT_FAST; 58 struct stat sbuf; 59 char line[1000]; 60 61 /* If this is not the local set, no need to do anything */ 62 if (!metaislocalset(sp)) 63 return (0); 64 65 /* open temp file */ 66 if ((tfp = fopen(tname, "w")) == NULL) 67 return (mdsyserror(ep, errno, tname)); 68 if (stat(name, &sbuf) == 0) { 69 (void) fchmod(fileno(tfp), (sbuf.st_mode & 0777)); 70 (void) fchown(fileno(tfp), sbuf.st_uid, sbuf.st_gid); 71 } 72 73 /* dump header */ 74 if (fputs(dgettext(TEXT_DOMAIN, 75 "# metadevice configuration file\n" 76 "# do not hand edit\n"), tfp) == EOF) { 77 (void) mdsyserror(ep, errno, tname); 78 goto errout; 79 } 80 81 /* dump device configuration */ 82 if (meta_print_all(sp, tname, NULL, tfp, options, NULL, ep) != 0) 83 goto errout; 84 85 /* close and rename file */ 86 if (fclose(tfp) != 0) { 87 (void) mdsyserror(ep, errno, tname); 88 goto errout; 89 } 90 tfp = NULL; 91 92 /* 93 * Renames don't work in the miniroot since tmpfiles are 94 * created in /var/tmp. Hence we copy the data out. 95 */ 96 97 if (rename(tname, name) != 0) { 98 if (errno == EROFS) { 99 if ((tfp = fopen(tname, "r")) == NULL) { 100 goto errout; 101 } 102 if ((mfp = fopen(METACONF, "w+")) == NULL) { 103 goto errout; 104 } 105 while (fgets(line, 1000, tfp) != NULL) { 106 if (fputs(line, mfp) == NULL) { 107 (void) mdsyserror(ep, errno, METACONF); 108 goto errout; 109 } 110 } 111 if (fclose(tfp) != 0) { 112 tfp = NULL; 113 goto errout; 114 } 115 tfp = NULL; 116 /* delete the tempfile */ 117 (void) unlink(tname); 118 if (fflush(mfp) != 0) { 119 goto errout; 120 } 121 if (fsync(fileno(mfp)) != 0) { 122 goto errout; 123 } 124 if (fclose(mfp) != 0) { 125 mfp = NULL; 126 goto errout; 127 } 128 mfp = NULL; 129 } else { 130 (void) mdsyserror(ep, errno, name); 131 goto errout; 132 } 133 } 134 135 /* success */ 136 return (0); 137 138 /* cleanup, return error */ 139 errout: 140 if (tfp != NULL) { 141 (void) fclose(tfp); 142 (void) unlink(tname); 143 } 144 if (mfp != NULL) { 145 (void) fclose(mfp); 146 } 147 return (-1); 148 } 149