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 /* 23 * Copyright 2008 Sun Microsystems, Inc. All rights reserved. 24 * Use is subject to license terms. 25 */ 26 27 /* Copyright (c) 1988 AT&T */ 28 /* All Rights Reserved */ 29 30 #pragma ident "%Z%%M% %I% %E% SMI" 31 32 #pragma weak _run_setkey = run_setkey 33 #pragma weak _run_crypt = run_crypt 34 #pragma weak _crypt_close = crypt_close 35 #pragma weak _makekey = makekey 36 37 #include <stdio.h> 38 #include <signal.h> 39 #include <fcntl.h> 40 #include <errno.h> 41 #include <thread.h> 42 #include <sys/types.h> 43 #include <unistd.h> 44 #include <strings.h> 45 #include <crypt.h> 46 #include "des_soft.h" 47 #include "lib_gen.h" 48 49 #define READER 0 50 #define WRITER 1 51 #define KSIZE 8 52 53 /* Global Variables */ 54 static char key[KSIZE+1]; 55 struct header { 56 long offset; 57 unsigned int count; 58 }; 59 60 static mutex_t lock = DEFAULTMUTEX; 61 62 static int cryptopen(); 63 static int writekey(); 64 65 void _exit(); 66 67 int 68 run_setkey(int p[2], const char *keyparam) 69 { 70 (void) mutex_lock(&lock); 71 if (cryptopen(p) == -1) { 72 (void) mutex_unlock(&lock); 73 return (-1); 74 } 75 (void) strncpy(key, keyparam, KSIZE); 76 if (*key == 0) { 77 (void) crypt_close_nolock(p); 78 (void) mutex_unlock(&lock); 79 return (0); 80 } 81 if (writekey(p, key) == -1) { 82 (void) mutex_unlock(&lock); 83 return (-1); 84 } 85 (void) mutex_unlock(&lock); 86 return (1); 87 } 88 89 static char cmd[] = "exec /usr/bin/crypt -p 2>/dev/null"; 90 static int 91 cryptopen(int p[2]) 92 { 93 char c; 94 95 if (__p2open(cmd, p) < 0) 96 return (-1); 97 if (read(p[WRITER], &c, 1) != 1) { /* check that crypt is working on */ 98 /* other end */ 99 (void) crypt_close(p); /* remove defunct process */ 100 return (-1); 101 } 102 return (1); 103 } 104 105 static int 106 writekey(int p[2], char *keyarg) 107 { 108 void (*pstat) (); 109 pstat = signal(SIGPIPE, SIG_IGN); /* don't want pipe errors to cause */ 110 /* death */ 111 if (write(p[READER], keyarg, KSIZE) != KSIZE) { 112 (void) crypt_close(p); /* remove defunct process */ 113 (void) signal(SIGPIPE, pstat); 114 return (-1); 115 } 116 (void) signal(SIGPIPE, pstat); 117 return (1); 118 } 119 120 121 int 122 run_crypt(long offset, char *buffer, unsigned int count, int p[2]) 123 { 124 struct header header; 125 void (*pstat) (); 126 127 (void) mutex_lock(&lock); 128 header.count = count; 129 header.offset = offset; 130 pstat = signal(SIGPIPE, SIG_IGN); 131 if (write(p[READER], (char *)&header, sizeof (header)) 132 != sizeof (header)) { 133 (void) crypt_close_nolock(p); 134 (void) signal(SIGPIPE, pstat); 135 (void) mutex_unlock(&lock); 136 return (-1); 137 } 138 if (write(p[READER], buffer, count) < count) { 139 (void) crypt_close_nolock(p); 140 (void) signal(SIGPIPE, pstat); 141 (void) mutex_unlock(&lock); 142 return (-1); 143 } 144 if (read(p[WRITER], buffer, count) < count) { 145 (void) crypt_close_nolock(p); 146 (void) signal(SIGPIPE, pstat); 147 (void) mutex_unlock(&lock); 148 return (-1); 149 } 150 (void) signal(SIGPIPE, pstat); 151 (void) mutex_unlock(&lock); 152 return (0); 153 } 154 155 int 156 makekey(int b[2]) 157 { 158 int i; 159 long gorp; 160 char tempbuf[KSIZE], *a, *temp; 161 162 (void) mutex_lock(&lock); 163 a = key; 164 temp = tempbuf; 165 for (i = 0; i < KSIZE; i++) 166 temp[i] = *a++; 167 gorp = getuid() + getgid(); 168 169 for (i = 0; i < 4; i++) 170 temp[i] ^= (char)((gorp>>(8*i))&0377); 171 172 if (cryptopen(b) == -1) { 173 (void) mutex_unlock(&lock); 174 return (-1); 175 } 176 if (writekey(b, temp) == -1) { 177 (void) mutex_unlock(&lock); 178 return (-1); 179 } 180 (void) mutex_unlock(&lock); 181 return (0); 182 } 183 184 int 185 crypt_close_nolock(int p[2]) 186 { 187 188 if (p[0] == 0 && p[1] == 0 || p[0] < 0 || p[1] < 0) { 189 return (-1); 190 } 191 192 return (__p2close(p, NULL, SIGKILL)); 193 } 194 195 int 196 crypt_close(int p[2]) 197 { 198 (void) mutex_lock(&lock); 199 (void) crypt_close_nolock(p); 200 (void) mutex_unlock(&lock); 201 return (0); 202 } 203