nscd_init.c revision 2830:5228d1267a01
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 2006 Sun Microsystems, Inc.  All rights reserved.
23 * Use is subject to license terms.
24 */
25
26#pragma ident	"%Z%%M%	%I%	%E% SMI"
27
28#include <locale.h>
29#include <unistd.h>
30#include <string.h>
31#include "nscd_common.h"
32#include "nscd_config.h"
33#include "nscd_log.h"
34#include "nscd_switch.h"
35#include "nscd_frontend.h"
36
37static char	*cfgfile_save = NULL;
38
39nscd_rc_t
40_nscd_init(
41	char			*cfgfile)
42{
43	char			*me = "nscd_init";
44	nscd_rc_t		rc;
45	nscd_cfg_error_t	*err;
46
47	/*
48	 * allocate the space for tables
49	 */
50	rc = _nscd_alloc_nsw_config();
51	rc = _nscd_alloc_service_state_table();
52	rc = _nscd_alloc_nsw_state_base();
53	rc = _nscd_alloc_nsw_be_info_db();
54	rc = _nscd_alloc_getent_ctx_base();
55	if (rc != NSCD_SUCCESS)
56		return (rc);
57
58	/*
59	 * allocate the space for local configuration
60	 * and statistics
61	 */
62	rc = _nscd_alloc_switch_cfg();
63	rc = _nscd_alloc_frontend_cfg();
64	rc = _nscd_alloc_switch_stats();
65	if (rc != NSCD_SUCCESS)
66		return (rc);
67
68	/*
69	 * Create and init the internal address database to keep
70	 * track of the memory allocated by _nscd_alloc
71	 */
72	if (_nscd_create_int_addrDB() == NULL) {
73		_NSCD_LOG(NSCD_LOG_INT_ADDR, NSCD_LOG_LEVEL_ERROR)
74		(me, "_nscd_create_int_addrDB failed\n");
75		return (NSCD_NO_MEMORY);
76	}
77
78	/*
79	 * Create and init the internal context database to keep
80	 * track of the getent context currently being used
81	 */
82	if (_nscd_create_getent_ctxDB() == NULL) {
83		_NSCD_LOG(NSCD_LOG_GETENT_CTX, NSCD_LOG_LEVEL_ERROR)
84		(me, "_nscd_create_getent_ctx_addrDB failed\n");
85		return (NSCD_NO_MEMORY);
86	}
87
88	/*
89	 * Create the backend info database for each possible source
90	 */
91	if ((rc = _nscd_init_all_nsw_be_info_db()) != NSCD_SUCCESS) {
92		_NSCD_LOG(NSCD_LOG_NSW_STATE, NSCD_LOG_LEVEL_ERROR)
93		(me, "_nscd_init_all_nsw_be_info_db failed (rc = %d)\n",
94			rc);
95		return (rc);
96	}
97
98	/*
99	 * Create the nscd_nsw_config_t for each possible nss database
100	 */
101	if ((rc = _nscd_init_all_nsw_config()) != NSCD_SUCCESS) {
102		_NSCD_LOG(NSCD_LOG_NSW_STATE, NSCD_LOG_LEVEL_ERROR)
103		(me, "_nscd_init_all_nsw_config failed (rc = %d)\n", rc);
104		return (rc);
105	}
106
107	/*
108	 * populate the backend info databases
109	 */
110	if ((rc = _nscd_populate_nsw_backend_info()) != NSCD_SUCCESS) {
111		_NSCD_LOG(NSCD_LOG_NSW_STATE, NSCD_LOG_LEVEL_ERROR)
112		(me, "_nscd_init_all_nsw_be_info_db failed (rc = %d)\n", rc);
113		return (rc);
114	}
115
116	/*
117	 * initialize config/stats management
118	 */
119	rc = _nscd_cfg_init(&err);
120	if (rc != NSCD_SUCCESS) {
121		if (err != NULL)
122			_nscd_cfg_free_error(err);
123		return (rc);
124	}
125
126	/*
127	 * read in the nsswitch configuration
128	 */
129	rc = _nscd_cfg_read_nsswitch_file("/etc/nsswitch.conf", &err);
130	if (rc != NSCD_SUCCESS) {
131		(void) printf(
132		gettext("reading config file %s failed with rc = %d, %s\n"),
133			"/etc/nsswitch.conf", rc, NSCD_ERR2MSG(err));
134		if (err != NULL)
135			_nscd_cfg_free_error(err);
136
137		_NSCD_LOG(NSCD_LOG_FRONT_END, NSCD_LOG_LEVEL_ERROR)
138	(me, "unable to read /etc/nsswitch.conf (rc = %d)\n", rc);
139		return (rc);
140	}
141
142	/*
143	 * read in the nscd configuration
144	 */
145	if (cfgfile == NULL) {
146		cfgfile = "/etc/nscd.conf";
147		if (access(cfgfile, R_OK) != 0) {
148			_NSCD_LOG(NSCD_LOG_FRONT_END, NSCD_LOG_LEVEL_ERROR)
149		(me, "unable to read /etc/nscd.conf (rc = %d)\n", rc);
150
151			return (NSCD_CFG_FILE_ACCESS_ERROR);
152		}
153	}
154	rc = _nscd_cfg_read_file(cfgfile, &err);
155	if (rc != NSCD_SUCCESS) {
156		(void) printf(
157		gettext("reading config file %s failed with rc = %d, %s\n"),
158			cfgfile, rc, NSCD_ERR2MSG(err));
159		if (err != NULL)
160			_nscd_cfg_free_error(err);
161
162		_NSCD_LOG(NSCD_LOG_FRONT_END, NSCD_LOG_LEVEL_ERROR)
163	(me, "unable to read configuration from %s (rc = %d)\n",
164			cfgfile, rc);
165
166		return (rc);
167	}
168	/*
169	 * remember the name of the config file
170	 * in case refresh is requested later
171	 */
172	if (cfgfile != NULL) {
173		cfgfile_save = strdup(cfgfile);
174		if (cfgfile == NULL)
175			return (NSCD_NO_MEMORY);
176	}
177
178	return (NSCD_SUCCESS);
179}
180
181nscd_rc_t
182_nscd_refresh()
183{
184	char			*me = "nscd_refresh";
185	char			*cfgfile;
186	nscd_rc_t		rc;
187	nscd_cfg_error_t	*err;
188	char			errmsg[1024];
189
190	/*
191	 * re-read the nsswitch configuration
192	 */
193	rc = _nscd_cfg_read_nsswitch_file("/etc/nsswitch.conf", &err);
194	if (rc != NSCD_SUCCESS) {
195		(void) snprintf(errmsg, sizeof (errmsg),
196		"unable to parse the config file %s (rc = %d), %s\n",
197		"/etc/nsswitch.conf", rc, NSCD_ERR2MSG(err));
198		goto error_exit;
199	}
200
201	/*
202	 * re-read the nscd configuration
203	 */
204	if (cfgfile_save == NULL)
205		cfgfile = "/etc/nscd.conf";
206	else
207		cfgfile = cfgfile_save;
208
209	if (access(cfgfile, R_OK) != 0) {
210		(void) snprintf(errmsg, sizeof (errmsg),
211		"unable to read the config file %s (rc = %d), %s\n",
212			cfgfile, NSCD_CFG_FILE_ACCESS_ERROR,
213			strerror(errno));
214
215		goto error_exit;
216	}
217
218	rc = _nscd_cfg_read_file(cfgfile, &err);
219	if (rc != NSCD_SUCCESS) {
220		(void) snprintf(errmsg, sizeof (errmsg),
221		"unable to parse the config file %s (rc = %d), %s\n",
222		cfgfile, rc, NSCD_ERR2MSG(err));
223
224		goto error_exit;
225	}
226
227	_NSCD_LOG(NSCD_LOG_CONFIG, NSCD_LOG_LEVEL_ALL)
228	(me, "nsswitch/nscd configuration refreshed successfully\n");
229
230	return (NSCD_SUCCESS);
231
232	error_exit:
233
234	if (err != NULL)
235		_nscd_cfg_free_error(err);
236
237	_NSCD_LOG(NSCD_LOG_CONFIG, NSCD_LOG_LEVEL_ERROR)
238	(me, "%s\n", errmsg);
239
240	return (rc);
241}
242