Print this page
make: remove SCCS ident stuff
Split |
Close |
Expand all |
Collapse all |
--- old/usr/src/cmd/make/lib/vroot/src/lock.cc
+++ new/usr/src/cmd/make/lib/vroot/src/lock.cc
1 1 /*
2 2 * CDDL HEADER START
3 3 *
4 4 * The contents of this file are subject to the terms of the
5 5 * Common Development and Distribution License (the "License").
6 6 * You may not use this file except in compliance with the License.
7 7 *
8 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 9 * or http://www.opensolaris.org/os/licensing.
10 10 * See the License for the specific language governing permissions
11 11 * and limitations under the License.
12 12 *
13 13 * When distributing Covered Code, include this CDDL HEADER in each
14 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
↓ open down ↓ |
14 lines elided |
↑ open up ↑ |
15 15 * If applicable, add the following below this CDDL HEADER, with the
16 16 * fields enclosed by brackets "[]" replaced with your own identifying
17 17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 18 *
19 19 * CDDL HEADER END
20 20 */
21 21 /*
22 22 * Copyright 2004 Sun Microsystems, Inc. All rights reserved.
23 23 * Use is subject to license terms.
24 24 */
25 -/*
26 - * @(#)lock.cc 1.17 06/12/12
27 - */
28 -
29 -#pragma ident "@(#)lock.cc 1.17 06/12/12"
30 25
31 26 #include <avo/intl.h> /* for NOCATGETS */
32 27 #include <stdio.h>
33 28 #include <stdlib.h>
34 29 #include <string.h>
35 30 #include <sys/errno.h>
36 31 #include <sys/param.h>
37 32 #include <sys/stat.h>
38 33 #include <sys/types.h>
39 34 #include <unistd.h>
40 35 #include <vroot/vroot.h>
41 36 #include <mksdmsi18n/mksdmsi18n.h>
42 37 #include <signal.h>
43 38 #include <errno.h> /* errno */
44 39
45 40 #if !defined(linux)
46 41 extern char *sys_errlist[];
47 42 extern int sys_nerr;
48 43 #endif
49 44
50 45 static void file_lock_error(char *msg, char *file, char *str, int arg1, int arg2);
51 46
52 47 #define BLOCK_INTERUPTS sigfillset(&newset) ; \
53 48 sigprocmask(SIG_SETMASK, &newset, &oldset)
54 49
55 50 #define UNBLOCK_INTERUPTS \
56 51 sigprocmask(SIG_SETMASK, &oldset, &newset)
57 52
58 53 /*
59 54 * This code stolen from the NSE library and changed to not depend
60 55 * upon any NSE routines or header files.
61 56 *
62 57 * Simple file locking.
63 58 * Create a symlink to a file. The "test and set" will be
64 59 * atomic as creating the symlink provides both functions.
65 60 *
66 61 * The timeout value specifies how long to wait for stale locks
67 62 * to disappear. If the lock is more than 'timeout' seconds old
68 63 * then it is ok to blow it away. This part has a small window
69 64 * of vunerability as the operations of testing the time,
70 65 * removing the lock and creating a new one are not atomic.
71 66 * It would be possible for two processes to both decide to blow
72 67 * away the lock and then have process A remove the lock and establish
73 68 * its own, and then then have process B remove the lock which accidentily
74 69 * removes A's lock rather than the stale one.
75 70 *
76 71 * A further complication is with the NFS. If the file in question is
77 72 * being served by an NFS server, then its time is set by that server.
78 73 * We can not use the time on the client machine to check for a stale
79 74 * lock. Therefore, a temp file on the server is created to get
80 75 * the servers current time.
81 76 *
82 77 * Returns an error message. NULL return means the lock was obtained.
83 78 *
84 79 * 12/6/91 Added the parameter "file_locked". Before this parameter
85 80 * was added, the calling procedure would have to wait for file_lock()
86 81 * to return before it sets the flag. If the user interrupted "make"
87 82 * between the time the lock was acquired and the time file_lock()
88 83 * returns, make wouldn't know that the file has been locked, and therefore
89 84 * it wouldn' remove the lock. Setting the flag right after locking the file
90 85 * makes this window much smaller.
91 86 */
92 87
93 88 int
94 89 file_lock(char *name, char *lockname, int *file_locked, int timeout)
95 90 {
96 91 int counter = 0;
97 92 static char msg[MAXPATHLEN+1];
98 93 int printed_warning = 0;
99 94 int r;
100 95 struct stat statb;
101 96 sigset_t newset;
102 97 sigset_t oldset;
103 98
104 99 *file_locked = 0;
105 100 if (timeout <= 0) {
106 101 timeout = 120;
107 102 }
108 103 for (;;) {
109 104 BLOCK_INTERUPTS;
110 105 r = symlink(name, lockname);
111 106 if (r == 0) {
112 107 *file_locked = 1;
113 108 UNBLOCK_INTERUPTS;
114 109 return 0; /* success */
115 110 }
116 111 UNBLOCK_INTERUPTS;
117 112
118 113 if (errno != EEXIST) {
119 114 file_lock_error(msg, name, NOCATGETS("symlink(%s, %s)"),
120 115 (int) name, (int) lockname);
121 116 fprintf(stderr, "%s", msg);
122 117 return errno;
123 118 }
124 119
125 120 counter = 0;
126 121 for (;;) {
127 122 sleep(1);
128 123 r = lstat(lockname, &statb);
129 124 if (r == -1) {
130 125 /*
131 126 * The lock must have just gone away - try
132 127 * again.
133 128 */
134 129 break;
135 130 }
136 131
137 132 if ((counter > 5) && (!printed_warning)) {
138 133 /* Print waiting message after 5 secs */
139 134 #if defined(SUN5_0) || defined(HP_UX) || defined(linux)
140 135 (void) getcwd(msg, MAXPATHLEN);
141 136 #else
142 137 (void) getwd(msg);
143 138 #endif
144 139 fprintf(stderr,
145 140 catgets(libmksdmsi18n_catd, 1, 162, "file_lock: file %s is already locked.\n"),
146 141 name);
147 142 fprintf(stderr,
148 143 catgets(libmksdmsi18n_catd, 1, 163, "file_lock: will periodically check the lockfile %s for two minutes.\n"),
149 144 lockname);
150 145 fprintf(stderr,
151 146 catgets(libmksdmsi18n_catd, 1, 144, "Current working directory %s\n"),
152 147 msg);
153 148
154 149 printed_warning = 1;
155 150 }
156 151
157 152 if (++counter > timeout ) {
158 153 /*
159 154 * Waited enough - return an error..
160 155 */
161 156 return EEXIST;
162 157 }
163 158 }
164 159 }
165 160 /* NOTREACHED */
166 161 }
167 162
168 163 /*
169 164 * Format a message telling why the lock could not be created.
170 165 */
171 166 static void
172 167 file_lock_error(char *msg, char *file, char *str, int arg1, int arg2)
173 168 {
174 169 int len;
175 170
176 171 sprintf(msg, catgets(libmksdmsi18n_catd, 1, 145, "Could not lock file `%s'; "), file);
177 172 len = strlen(msg);
178 173 sprintf(&msg[len], str, arg1, arg2);
179 174 strcat(msg, catgets(libmksdmsi18n_catd, 1, 146, " failed - "));
180 175 #if !defined(linux)
181 176 if (errno < sys_nerr) {
182 177 #ifdef SUN4_x
183 178 strcat(msg, sys_errlist[errno]);
184 179 #endif
185 180 #ifdef SUN5_0
186 181 strcat(msg, strerror(errno));
187 182 #endif
188 183 } else {
189 184 len = strlen(msg);
190 185 sprintf(&msg[len], NOCATGETS("errno %d"), errno);
191 186 }
192 187 #else
193 188 strcat(msg, strerror(errno));
194 189 #endif
195 190 }
196 191
↓ open down ↓ |
157 lines elided |
↑ open up ↑ |
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX