Commit 4f7bdeea authored by Poul-Henning Kamp's avatar Poul-Henning Kamp

Add minimal facility for dealing with TELNET option negotiation

in a way that telnet clients don't get confused about:

Return WONT on to all DO or DONT and ignore everything else.



git-svn-id: http://www.varnish-cache.org/svn/trunk/varnish-cache@3866 d4fa192b-c00b-0410-8231-f00ffab90ce4
parent 8679b351
......@@ -501,6 +501,10 @@ mgt_cli_setup(int fdi, int fdo, int verbose, const char *ident)
XXXAN(cp->cli->sb);
cp->cli->priv = cp;
/* Deal with TELNET options */
if (cp->fdi != 0)
VLU_SetTelnet(cp->vlu, cp->fdo);
/*
* If we have a secret file authenticate all CLI connections
* except the stdin/stdout debug port.
......
......@@ -38,5 +38,6 @@ int VLU_Fd(int fd, struct vlu *l);
int VLU_File(FILE *f, struct vlu *l);
int VLU_Data(const void *ptr, int len, struct vlu *l);
void VLU_Destroy(struct vlu *l);
void VLU_SetTelnet(struct vlu *l, int fd);
#endif
......@@ -46,6 +46,7 @@ struct vlu {
unsigned bufl;
unsigned bufp;
void *priv;
int telnet;
vlu_f *func;
};
......@@ -66,10 +67,19 @@ VLU_New(void *priv, vlu_f *func, unsigned bufsize)
FREE_OBJ(l);
l = NULL;
}
l->telnet = -1;
}
return (l);
}
void
VLU_SetTelnet(struct vlu *l, int fd)
{
CHECK_OBJ_NOTNULL(l, LINEUP_MAGIC);
assert(fd >= 0);
l->telnet = fd;
}
void
VLU_Destroy(struct vlu *l)
{
......@@ -79,6 +89,51 @@ VLU_Destroy(struct vlu *l)
FREE_OBJ(l);
}
static int
vlu_dotelnet(struct vlu *l, char *p)
{
char *e;
char tno[3];
int i;
e = l->buf + l->bufp;
assert(p >= l->buf && p < e);
assert(*p == (char)255);
/* We need at least two characters */
if (p == e - 1)
return (1);
/* And three for will/wont/do/dont */
if (p[1] >= (char)251 && p[1] <= (char)254 && p == e - 2)
return (1);
switch (p[1]) {
case (char)251: /* WILL */
case (char)252: /* WONT */
/* Ignore these */
i = 3;
break;
case (char)253: /* DO */
case (char)254: /* DONT */
/* Return WONT for these */
memcpy(tno, p, 3);
tno[1] = (char)252;
write(l->telnet, tno, 3);
i = 3;
break;
default:
/* Ignore the rest */
/* XXX: only p[1] >= 240 ? */
i = 2;
}
/* Remove telnet sequence from buffer */
memmove(p, p + i, 1 + e - (p + i));
l->bufp -= i;
return (0);
}
static int
LineUpProcess(struct vlu *l)
{
......@@ -88,9 +143,13 @@ LineUpProcess(struct vlu *l)
l->buf[l->bufp] = '\0';
for (p = l->buf; *p != '\0'; p = q) {
/* Find first CR or NL */
for (q = p; *q != '\0'; q++)
for (q = p; *q != '\0'; q++) {
while (l->telnet >= 0 && *q == (char)255)
if (vlu_dotelnet(l, q))
return (0);
if (*q == '\n' || *q == '\r')
break;
}
if (*q == '\0')
break;
*q++ = '\0';
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment