78
CheckHostPort(const char *host, const char *port)
80
emit_sockaddr(struct tokenlist *tl, void *sa, unsigned sal)
80
struct addrinfo *res, hint;
83
memset(&hint, 0, sizeof hint);
84
hint.ai_family = PF_UNSPEC;
85
hint.ai_socktype = SOCK_STREAM;
86
error = getaddrinfo(host, port, &hint, &res);
88
return (gai_strerror(error));
88
Fh(tl, 0, "\nstatic const unsigned char sockaddr%u[%d] = {\n",
89
tl->nsockaddr, sal + 1);
90
Fh(tl, 0, " %3u, /* Length */\n", sal);
92
for (len = 0; len <sal; len++) {
95
Fh(tl, 0, " %3u", u[len]);
102
return (tl->nsockaddr++);
93
105
/*--------------------------------------------------------------------
96
108
* and put it in an official sockaddr when we load the VCL.
100
114
Emit_Sockaddr(struct tokenlist *tl, const struct token *t_host,
101
115
const char *port)
103
118
struct addrinfo *res, *res0, *res1, hint;
104
int n4, n6, len, error, retval;
119
int n4, n6, error, retval, x;
105
120
const char *emit, *multiple;
107
121
char hbuf[NI_MAXHOST];
111
126
memset(&hint, 0, sizeof hint);
112
127
hint.ai_family = PF_UNSPEC;
113
128
hint.ai_socktype = SOCK_STREAM;
114
error = getaddrinfo(t_host->dec, port, &hint, &res0);
130
if (VSS_parse(t_host->dec, &hop, &pop)) {
132
"Backend host '%.*s': wrong syntax (unbalanced [...] ?)\n",
134
vcc_ErrWhere(tl, t_host);
138
error = getaddrinfo(hop, pop, &hint, &res0);
140
error = getaddrinfo(t_host->dec, port, &hint, &res0);
145
"Backend host '%.*s'"
146
" could not be resolved to an IP address:\n", PF(t_host));
149
"(Sorry if that error message is gibberish.)\n",
150
gai_strerror(error));
151
vcc_ErrWhere(tl, t_host);
118
158
for (res = res0; res; res = res->ai_next) {
120
160
if (res->ai_family == PF_INET) {
122
emit = "ipv4_sockaddr";
124
164
multiple = "IPv4";
125
165
} else if (res->ai_family == PF_INET6) {
127
emit = "ipv6_sockaddr";
129
169
multiple = "IPv6";
154
assert(res->ai_addrlen < 256);
155
Fh(tl, 0, "\nstatic const unsigned char sockaddr%u[%d] = {\n",
156
tl->nsockaddr, res->ai_addrlen + 1);
157
Fh(tl, 0, " %3u, /* Length */\n", res->ai_addrlen);
158
u = (void*)res->ai_addr;
159
for (len = 0; len < res->ai_addrlen; len++) {
162
Fh(tl, 0, " %3u", u[len]);
163
if (len + 1 < res->ai_addrlen)
169
Fb(tl, 0, "\t.%s = sockaddr%u,\n", emit, tl->nsockaddr++);
192
x = emit_sockaddr(tl, res->ai_addr, res->ai_addrlen);
193
Fb(tl, 0, "\t.%s_sockaddr = sockaddr%u,\n", emit, x);
194
error = getnameinfo(res->ai_addr,
195
res->ai_addrlen, hbuf, sizeof hbuf,
196
NULL, 0, NI_NUMERICHOST);
198
Fb(tl, 0, "\t.%s_addr = \"%s\",\n", emit, hbuf);
202
error = getnameinfo(res0->ai_addr,
203
res0->ai_addrlen, NULL, 0, hbuf, sizeof hbuf,
206
Fb(tl, 0, "\t.port = \"%s\",\n", hbuf);
172
208
freeaddrinfo(res0);
173
209
if (retval == 0) {
174
210
vsb_printf(tl->sb,
512
547
/* Check that the hostname makes sense */
513
548
assert(t_host != NULL);
514
ep = CheckHostPort(t_host->dec, "80");
516
vsb_printf(tl->sb, "Backend host '%.*s': %s\n", PF(t_host), ep);
517
vcc_ErrWhere(tl, t_host);
521
/* Check that the portname makes sense */
522
if (t_port != NULL) {
523
ep = CheckHostPort("127.0.0.1", t_port->dec);
526
"Backend port '%.*s': %s\n", PF(t_port), ep);
527
vcc_ErrWhere(tl, t_port);
530
550
Emit_Sockaddr(tl, t_host, t_port->dec);
532
552
Emit_Sockaddr(tl, t_host, "80");
536
555
ExpectErr(tl, '}');
662
681
{ "random", vcc_ParseRandomDirector },
663
682
{ "client", vcc_ParseRandomDirector },
664
683
{ "round-robin", vcc_ParseRoundRobinDirector },
684
{ "dns", vcc_ParseDnsDirector },