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 /* 29 * Provides accessors to configuration properties. 30 * 31 * slp_readConfig: attempts to locate slp.conf, and reads in all 32 * properties specified therein. 33 * slp_get_mtu: returns the MTU 34 * slp_get_next_onlist: parses a comma separated list of integers (in 35 * string form), returning one at a time. 36 * slp_parse_static_das: parses the list of DAs given in the DAAddresses 37 * property. 38 * 39 * Also see the config wrapper macros in slp-internal.h. 40 */ 41 42 #include <stdio.h> 43 #include <syslog.h> 44 #include <string.h> 45 #include <stdlib.h> 46 #include <ctype.h> 47 #include <slp-internal.h> 48 49 /* 50 * Reads from fp and dynamically reallocates the buffer if necessary. 51 * Returns 1 on success, 0 on read completion, and -1 on failure. 52 */ 53 static int super_fgets(char **buf, size_t *bufsize, FILE *fp) { 54 char *r, *p; 55 size_t real_bufsize, readlen = 0; 56 57 p = *buf; 58 real_bufsize = *bufsize; 59 for (;;) { 60 r = fgets(p, (int)real_bufsize, fp); 61 if (feof(fp) && !r) 62 return (0); 63 if (!r) 64 return (-1); 65 readlen += strlen(r); 66 if ((*buf)[readlen - 1] == '\n') 67 return (1); 68 69 /* else buf is too small */ 70 *bufsize *= 2; 71 if (!(*buf = realloc(*buf, *bufsize))) { 72 slp_err(LOG_CRIT, 0, "super_fgets", "out of memory"); 73 return (-1); 74 } 75 p = *buf + readlen; 76 real_bufsize = *bufsize - readlen; 77 } 78 } 79 80 static void skip_space(char **p) { 81 while (*p && **p != '\n' && isspace(**p)) 82 (*p)++; 83 } 84 85 static void null_space(char *p) { 86 for (; *p; p++) 87 if (isspace(*p)) 88 *p = 0; 89 } 90 91 /* 92 * Reads into the local property store all properties defined in 93 * the config file. 94 */ 95 void slp_readConfig() { 96 char *cfile, *buf; 97 FILE *fp; 98 size_t buflen = 512; 99 100 /* check env for alternate config file */ 101 fp = NULL; 102 if (cfile = getenv("SLP_CONF_FILE")) 103 fp = fopen(cfile, "rF"); 104 if (!fp) 105 if (!(fp = fopen(SLP_DEFAULT_CONFIG_FILE, "rF"))) { 106 slp_err(LOG_INFO, 0, "readConfig", 107 "cannot open config file"); 108 return; 109 } 110 111 if (!(buf = malloc(buflen))) { 112 slp_err(LOG_CRIT, 0, "readConfig", "out of memory"); 113 (void) fclose(fp); 114 return; 115 } 116 117 while (!feof(fp)) { 118 char *val, *p; 119 int err; 120 121 /* read a line */ 122 err = super_fgets(&buf, &buflen, fp); 123 if (err == 0) continue; 124 if (err == -1) { 125 slp_err(LOG_INFO, 0, "readConfig", 126 "error reading file: %d", 127 ferror(fp)); 128 (void) fclose(fp); 129 free(buf); 130 return; 131 } 132 133 /* skip comments and newlines */ 134 p = buf; 135 skip_space(&p); 136 if (*p == '#' || *p == ';' || *p == '\n') 137 continue; 138 139 /* get property and value */ 140 if (val = strchr(p, '=')) { 141 *val++ = 0; 142 skip_space(&val); 143 /* remove the trailing newline */ 144 val[strlen(val) - 1] = 0; 145 } 146 null_space(p); 147 148 SLPSetProperty(p, val ? val : ""); 149 } 150 151 (void) fclose(fp); 152 free(buf); 153 } 154 155 /* 156 * Config convenience wrappers 157 */ 158 size_t slp_get_mtu() { 159 size_t size; 160 size = atoi(SLPGetProperty(SLP_CONFIG_MTU)); 161 size = size ? size : SLP_DEFAULT_SENDMTU; 162 163 return (size); 164 } 165 166 /* 167 * On the first invocation, *state should == the value of the property 168 * to parse. 169 * If there are no more timeouts, returns -1, otherwise the timeout. 170 * If the value in the property is invalid, returns the default 2000. 171 */ 172 int slp_get_next_onlist(char **state) { 173 char *p, buf[33]; 174 size_t l; 175 int answer; 176 177 if (!*state) 178 return (-1); 179 180 if (**state == ',') { 181 (*state)++; /* skip the ',' */ 182 } 183 p = *state; 184 *state = slp_utf_strchr(*state, ','); 185 if (!*state) 186 l = strlen(p); 187 else { 188 l = *state - p; 189 l = (l > 32 ? 32 : l); 190 } 191 (void) strncpy(buf, p, l); 192 buf[l] = 0; 193 answer = atoi(buf); 194 195 return (answer != 0 ? answer : 2000); 196 } 197 198 int slp_get_maxResults() { 199 int num = atoi(SLPGetProperty(SLP_CONFIG_MAXRESULTS)); 200 201 return (num <= 0 ? -1 : num); 202 } 203