8354 sync regcomp(3C) with upstream (fix make catalog)
[unleashed/tickless.git] / usr / src / cmd / svr4pkg / libinst / depchk.c
blob736cda857a536218761538c1564366395360e732
1 /*
2 * CDDL HEADER START
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.
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.
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]
19 * CDDL HEADER END
23 * Copyright 2004 Sun Microsystems, Inc. All rights reserved.
24 * Use is subject to license terms.
29 * System includes
32 #include <stdio.h>
33 #include <limits.h>
34 #include <string.h>
35 #include <stdlib.h>
36 #include <unistd.h>
37 #include <errno.h>
38 #include <sys/types.h>
39 #include <locale.h>
40 #include <libintl.h>
41 #include <assert.h>
44 * local pkg command library includes
47 #include "libinst.h"
48 #include "messages.h"
51 * forward declarations
54 static int
55 collectError(int *r_numZones, char **r_zoneNames, char *a_packageName,
56 depckl_t *a_dck, int a_depIndex, depckErrorRecord_t *a_eir,
57 int a_errIndex);
60 * *****************************************************************************
61 * global external (public) functions
62 * *****************************************************************************
65 int
66 depchkReportErrors(depckl_t *a_dck)
68 char *packageName;
69 char *zonenames;
70 char msgbuf[4096];
71 int err;
72 int i;
73 int numzones = 0;
75 /* entry assertions */
77 assert(a_dck != (depckl_t *)NULL);
79 /* entry debugging info */
81 echoDebug(DBG_DEPCHK_ENTRY);
83 zonenames = (char *)NULL;
85 /* go through dependency table, collect, collapse, report errors */
87 for (i = 0; a_dck[i].name != (char *)NULL; i++) {
88 int j;
89 depckError_t *erc;
91 if (zonenames != (char *)NULL) {
92 free(zonenames);
93 zonenames = (char *)NULL;
96 erc = a_dck[i].record;
97 if (erc->er_numEntries == 0) {
98 continue;
101 for (j = 0; j < erc->er_numEntries; j++) {
102 int k;
103 depckErrorRecord_t *eir;
105 if (zonenames != (char *)NULL) {
106 free(zonenames);
107 zonenames = (char *)NULL;
110 eir = &erc->er_theEntries[j];
111 packageName = eir->ier_packageName;
112 for (k = 0; k < eir->ier_numZones; k++) {
113 int err;
115 err = collectError(&numzones, &zonenames,
116 packageName, a_dck, i, eir, k);
117 if (err != 0) {
118 if (zonenames != (char *)NULL) {
119 free(zonenames);
120 zonenames = (char *)NULL;
122 return (err);
126 if (a_dck[i].ignore_values == (char *)NULL) {
127 continue;
130 if (a_dck[i].err_msg == (char **)NULL) {
131 (void) snprintf(msgbuf, sizeof (msgbuf),
132 ERR_DEPENDENCY_IGNORED, a_dck[i].name,
133 packageName,
134 numzones == 1 ? "zone" : "zones",
135 zonenames ? zonenames : "?");
136 } else {
137 /* LINTED variable format specifier to ... */
138 (void) snprintf(msgbuf, sizeof (msgbuf),
139 *a_dck[i].err_msg, "package",
140 packageName,
141 numzones == 1 ? "zone" : "zones",
142 zonenames ? zonenames : "??");
145 if (a_dck[i].depcklFunc != NULL) {
146 /* call check function */
147 err = (a_dck[i].depcklFunc)(msgbuf,
148 packageName);
149 echoDebug(DBG_DEPCHK_REPORT_ERROR,
150 a_dck[i].ignore_values, err,
151 packageName, msgbuf);
152 if (err != 0) {
153 if (zonenames != (char *)NULL) {
154 free(zonenames);
155 zonenames = (char *)NULL;
157 return (err);
159 } else {
160 /* no check function - just report message */
161 echoDebug(DBG_DEPCHK_IGNORE_ERROR,
162 a_dck[i].ignore_values, packageName,
163 msgbuf);
164 ptext(stderr, "\\n%s", msgbuf);
169 if (zonenames != (char *)NULL) {
170 free(zonenames);
171 zonenames = (char *)NULL;
174 return (0);
177 void
178 depchkRecordError(depckError_t *a_erc, char *a_pkginst,
179 char *a_zoneName, char *a_value)
181 depckErrorRecord_t *erc;
182 int i;
185 * create new error record and entry if first entry
186 * record will look like this:
187 * err->er_#entry=1
188 * err->entry[0]->record->ier_numZones=1
189 * err->entry[0]->record->ier_packageName=a_pkginst
190 * err->entry[0]->record->ier_zones[0]=a_zoneName
191 * err->entry[0]->record->ier_values[0]=a_value
194 if (a_erc->er_numEntries == 0) {
195 depckErrorRecord_t *eir;
197 eir = (depckErrorRecord_t *)calloc(1,
198 sizeof (depckErrorRecord_t));
199 eir->ier_packageName = strdup(a_pkginst);
200 eir->ier_numZones = 1;
201 eir->ier_zones = (char **)calloc(1, sizeof (char **));
202 (eir->ier_zones)[eir->ier_numZones-1] = strdup(a_zoneName);
203 eir->ier_values = (char **)calloc(1, sizeof (char *));
204 (eir->ier_values)[eir->ier_numZones-1] = strdup(a_value);
206 a_erc->er_numEntries = 1;
207 a_erc->er_theEntries = eir;
209 echoDebug(DBG_DEPCHK_RECORD_ERROR, (long)a_erc, a_pkginst,
210 a_zoneName, a_value);
212 return;
215 /* see if this package already has an entry if so add zone to list */
217 for (i = 0; i < a_erc->er_numEntries; i++) {
218 erc = &a_erc->er_theEntries[i];
220 if (strcmp(erc->ier_packageName, a_pkginst) != 0) {
221 continue;
224 echoDebug(DBG_DEPCHK_RECORD_ZERROR, (long)a_erc, a_zoneName,
225 a_value, erc->ier_packageName, erc->ier_numZones,
226 erc->ier_zones[0]);
229 * this package already has an entry - add zone to
230 * existing package entry the modified records will
231 * look like this:
232 * err->er_#entry++;
233 * err->entry[0]->...
234 * err->entry[i]->
235 * -------------->record->
236 * ---------------------->ier_numZones++;
237 * ---------------------->ier_packageName=a_pkginst
238 * ---------------------->ier_zones[0]=...
239 * ---------------------->ier_zones[...]=...
240 * ---------------------->ier_zones[ier_numZones-1]=a_zoneName
241 * ---------------------->ier_values[0]=...
242 * ---------------------->ier_values[...]=...
243 * ---------------------->ier_values[ier_numZones-1]=a_value
244 * err->entry[i+1]->...
246 erc->ier_numZones++;
247 erc->ier_zones = (char **)realloc(erc->ier_zones,
248 sizeof (char **)*erc->ier_numZones);
249 (erc->ier_zones)[erc->ier_numZones-1] = strdup(a_zoneName);
250 erc->ier_values = (char **)realloc(erc->ier_values,
251 sizeof (char **)*erc->ier_numZones);
252 (erc->ier_values)[erc->ier_numZones-1] = strdup(a_value);
253 return;
257 * this packages does not have an entry - add new package
258 * entry for this zone the modified records will look like this:
259 * err->er_#entry++;
260 * err->entry[0]->record->ier_numZones=...
261 * err->entry[0]->record->ier_packageName=...
262 * err->entry[0]->record->ier_zones[0]=...
263 * err->entry[0]->record->ier_values[0]=...
264 * err->entry[er_#entry-1]->record->ier_numZones=1
265 * err->entry[er_#entry-1]->record->ier_packageName=a_pkginst
266 * err->entry[er_#entry-1]->record->ier_zones[0]=a_zoneName
267 * err->entry[er_#entry-1]->record->ier_values[0]=a_value
270 echoDebug(DBG_DEPCHK_RECORD_PERROR, (long)a_erc,
271 a_erc->er_numEntries, a_pkginst, a_zoneName, a_value);
273 a_erc->er_numEntries++;
275 a_erc->er_theEntries = realloc(a_erc->er_theEntries,
276 sizeof (depckErrorRecord_t)*a_erc->er_numEntries);
278 erc = &a_erc->er_theEntries[a_erc->er_numEntries-1];
280 erc->ier_packageName = strdup(a_pkginst);
281 erc->ier_numZones = 1;
282 erc->ier_zones = (char **)calloc(1, sizeof (char *));
283 (erc->ier_zones)[erc->ier_numZones-1] = strdup(a_zoneName);
284 erc->ier_values = (char **)calloc(1, sizeof (char *));
285 (erc->ier_values)[erc->ier_numZones-1] = strdup(a_value);
289 * *****************************************************************************
290 * static internal (private) functions
291 * *****************************************************************************
294 static int
295 collectError(int *r_numZones, char **r_zoneNames, char *a_packageName,
296 depckl_t *a_dck, int a_depIndex, depckErrorRecord_t *a_eir,
297 int a_errIndex)
299 char msgbuf[4096];
300 char *zn = *r_zoneNames;
302 if (a_dck[a_depIndex].ignore_values == (char *)NULL) {
303 if (a_dck[a_depIndex].err_msg == (char **)NULL) {
304 (void) snprintf(msgbuf, sizeof (msgbuf),
305 ERR_DEPENDENCY_REPORT, a_eir->ier_values[a_errIndex],
306 "package", a_packageName,
307 "zone", a_eir->ier_zones[a_errIndex]);
308 } else {
309 /* LINTED variable format specifier to snprintf(); */
310 (void) snprintf(msgbuf, sizeof (msgbuf),
311 *a_dck[a_depIndex].err_msg,
312 a_eir->ier_values[a_errIndex],
313 "package", a_packageName,
314 "zone", a_eir->ier_zones[a_errIndex]);
316 if (a_dck[a_depIndex].depcklFunc != NULL) {
317 int err;
319 err = (a_dck[a_depIndex].depcklFunc)(msgbuf,
320 a_packageName);
321 echoDebug(DBG_DEPCHK_COLLECT_ERROR, err, a_packageName,
322 msgbuf);
323 if (err != 0) {
324 return (err);
326 } else {
327 echoDebug(DBG_DEPCHK_COLLECT_IGNORE, a_packageName,
328 msgbuf);
329 ptext(stderr, "\\n%s", msgbuf);
331 return (0);
334 *r_numZones = (*r_numZones)+1;
335 if (zn == (char *)NULL) {
336 zn = strdup(a_eir->ier_zones[a_errIndex]);
337 } else {
338 char *p;
339 int len = strlen(zn)+strlen(a_eir->ier_zones[a_errIndex])+3;
340 p = calloc(1, len);
341 (void) snprintf(p, len, "%s, %s", zn,
342 a_eir->ier_zones[a_errIndex]);
343 free(zn);
344 zn = p;
347 *r_zoneNames = zn;
348 return (0);