|
8 | 8 | *
|
9 | 9 | *
|
10 | 10 | * IDENTIFICATION
|
11 |
| - * $Header: /cvsroot/pgsql/src/interfaces/libpq/fe-connect.c,v 1.138 2000/10/14 23:56:59 momjian Exp $ |
| 11 | + * $Header: /cvsroot/pgsql/src/interfaces/libpq/fe-connect.c,v 1.139 2000/10/17 01:00:58 momjian Exp $ |
12 | 12 | *
|
13 | 13 | *-------------------------------------------------------------------------
|
14 | 14 | */
|
@@ -111,6 +111,9 @@ static const PQconninfoOption PQconninfoOptions[] = {
|
111 | 111 | {"authtype","PGAUTHTYPE",DefaultAuthtype,NULL,
|
112 | 112 | "Database-Authtype","D",20},
|
113 | 113 |
|
| 114 | +{"service","PGSERVICE",NULL,NULL, |
| 115 | +"Database-Service","",20}, |
| 116 | + |
114 | 117 | {"user","PGUSER",NULL,NULL,
|
115 | 118 | "Database-User","",20},
|
116 | 119 |
|
@@ -187,6 +190,8 @@ static PQconninfoOption *conninfo_parse(const char *conninfo,
|
187 | 190 | staticchar*conninfo_getval(PQconninfoOption*connOptions,
|
188 | 191 | constchar*keyword);
|
189 | 192 | staticvoiddefaultNoticeProcessor(void*arg,constchar*message);
|
| 193 | +staticintparseServiceInfo(PQconninfoOption*options, |
| 194 | +PQExpBuffererrorMessage); |
190 | 195 |
|
191 | 196 |
|
192 | 197 | /* ----------------
|
@@ -2090,6 +2095,114 @@ pqPacketSend(PGconn *conn, const char *buf, size_t len)
|
2090 | 2095 | returnSTATUS_OK;
|
2091 | 2096 | }
|
2092 | 2097 |
|
| 2098 | +intparseServiceInfo(PQconninfoOption*options,PQExpBuffererrorMessage) { |
| 2099 | +char*service=conninfo_getval(options,"service"); |
| 2100 | +char*serviceFile="/etc/pg_service.conf"; |
| 2101 | +intMAXBUFSIZE=256; |
| 2102 | +intgroup_found=0; |
| 2103 | +intlinenr=0,i; |
| 2104 | + |
| 2105 | +if(service!=NULL) { |
| 2106 | +FILE*f; |
| 2107 | +charbuf[MAXBUFSIZE],*line; |
| 2108 | + |
| 2109 | +f=fopen(serviceFile,"r"); |
| 2110 | +if(f==NULL) { |
| 2111 | +printfPQExpBuffer(errorMessage,"ERROR: Service file '%s' not found\n", |
| 2112 | +serviceFile); |
| 2113 | +return1; |
| 2114 | + } |
| 2115 | + |
| 2116 | +/* As default, set the database name to the name of the service */ |
| 2117 | +for(i=0;options[i].keyword;i++) |
| 2118 | +if(strcmp(options[i].keyword,"dbname")==0) { |
| 2119 | +if(options[i].val!=NULL) |
| 2120 | +free(options[i].val); |
| 2121 | +options[i].val=strdup(service); |
| 2122 | + } |
| 2123 | + |
| 2124 | +while((line=fgets(buf,MAXBUFSIZE-1,f))!=NULL) { |
| 2125 | +linenr++; |
| 2126 | + |
| 2127 | +if(strlen(line) >=MAXBUFSIZE-2) { |
| 2128 | +fclose(f); |
| 2129 | +printfPQExpBuffer(errorMessage, |
| 2130 | +"ERROR: line %d too long in service file '%s'\n", |
| 2131 | +linenr, |
| 2132 | +serviceFile); |
| 2133 | +return2; |
| 2134 | + } |
| 2135 | + |
| 2136 | +/* ignore EOL at end of line */ |
| 2137 | +if(strlen(line)&&line[strlen(line)-1]=='\n') |
| 2138 | +line[strlen(line)-1]=0; |
| 2139 | + |
| 2140 | +/* ignore leading blanks */ |
| 2141 | +while(*line&&isspace(line[0])) |
| 2142 | +line++; |
| 2143 | + |
| 2144 | +/* ignore comments and empty lines */ |
| 2145 | +if(strlen(line)==0||line[0]=='#') |
| 2146 | +continue; |
| 2147 | + |
| 2148 | +/* Check for right groupname */ |
| 2149 | +if(line[0]=='[') { |
| 2150 | +if(group_found) { |
| 2151 | +/* group info already read */ |
| 2152 | +fclose(f); |
| 2153 | +return0; |
| 2154 | +} |
| 2155 | + |
| 2156 | +if(strncmp(line+1,service,strlen(service))==0&& |
| 2157 | +line[strlen(service)+1]==']') |
| 2158 | +group_found=1; |
| 2159 | +else |
| 2160 | +group_found=0; |
| 2161 | + }else { |
| 2162 | +if(group_found) { |
| 2163 | +/* Finally, we are in the right group and can parse the line */ |
| 2164 | +char*key,*val; |
| 2165 | +intfound_keyword; |
| 2166 | + |
| 2167 | +key=strtok(line,"="); |
| 2168 | +if(key==NULL) { |
| 2169 | +printfPQExpBuffer(errorMessage, |
| 2170 | +"ERROR: syntax error in service file '%s', line %d\n", |
| 2171 | +serviceFile, |
| 2172 | +linenr); |
| 2173 | +fclose(f); |
| 2174 | +return3; |
| 2175 | + } |
| 2176 | +val=line+strlen(line)+1; |
| 2177 | + |
| 2178 | +found_keyword=0; |
| 2179 | +for(i=0;options[i].keyword;i++) { |
| 2180 | +if(strcmp(options[i].keyword,key)==0) { |
| 2181 | +if(options[i].val!=NULL) |
| 2182 | +free(options[i].val); |
| 2183 | +options[i].val=strdup(val); |
| 2184 | +found_keyword=1; |
| 2185 | + } |
| 2186 | + } |
| 2187 | + |
| 2188 | +if(!found_keyword) { |
| 2189 | +printfPQExpBuffer(errorMessage, |
| 2190 | +"ERROR: syntax error in service file '%s', line %d\n", |
| 2191 | +serviceFile, |
| 2192 | +linenr); |
| 2193 | +fclose(f); |
| 2194 | +return3; |
| 2195 | + } |
| 2196 | +} |
| 2197 | + } |
| 2198 | + } |
| 2199 | + |
| 2200 | +fclose(f); |
| 2201 | + } |
| 2202 | + |
| 2203 | +return0; |
| 2204 | +} |
| 2205 | + |
2093 | 2206 |
|
2094 | 2207 | /* ----------------
|
2095 | 2208 | * Conninfo parser routine
|
@@ -2263,6 +2376,14 @@ conninfo_parse(const char *conninfo, PQExpBuffer errorMessage)
|
2263 | 2376 | if (option->val)
|
2264 | 2377 | free(option->val);
|
2265 | 2378 | option->val=strdup(pval);
|
| 2379 | + |
| 2380 | +} |
| 2381 | + |
| 2382 | +/* Now check for service info */ |
| 2383 | +if(parseServiceInfo(options,errorMessage)) { |
| 2384 | +PQconninfoFree(options); |
| 2385 | +free(buf); |
| 2386 | +returnNULL; |
2266 | 2387 | }
|
2267 | 2388 |
|
2268 | 2389 | /* Done with the modifiable input string */
|
|