tags 556522 patch thanks Hi :) I incorporated some code from util-linuxs getty to make hurds getty ask for a login name and pass that name to login. This way the login shell is no longer needed. I also turned on logins --paranoid flag to prevent it leaking whether a user exists or not. Cheers, Justus
--- hurd-20100926/daemons/getty.c 2010-09-26 22:10:52.000000000 +0000
+++ hurd-20100926-mine/daemons/getty.c 2011-01-09 23:35:27.000000000 +0000
@@ -4,6 +4,9 @@
Written by Michael I. Bushnell, p/BSG.
+ This file contains parts of the get_logname function from
+ util-linux/getty.c.
+
This file is part of the GNU Hurd.
The GNU Hurd is free software; you can redistribute it and/or
@@ -34,11 +37,21 @@
#include <utmp.h>
#include <sys/ioctl.h>
#include <termios.h>
+#include <ctype.h>
/* XXX */
extern char *localhost ();
#define _PATH_LOGIN "/bin/login"
+#define LOGIN " login: " /* login prompt */
+
+/* Some shorthands for control characters. */
+
+#define CTL(x) (x ^ 0100) /* Assumes ASCII dialect */
+#define CR CTL('M') /* carriage return */
+#define NL CTL('J') /* line feed */
+#define BS CTL('H') /* back space */
+#define DEL CTL('?') /* delete */
/* Parse the terminal speed. */
static void
@@ -77,6 +90,89 @@
write (fd, s, cc);
}
+char *
+get_login_name(int fd)
+{
+ size_t max_pw_size;
+ char *result;
+ char *ptr;
+ char c;
+ char done;
+ char *prompt;
+ int prompt_size;
+ char *hostname;
+
+ max_pw_size = sysconf (_SC_GETPW_R_SIZE_MAX);
+
+ if (!(result = malloc (max_pw_size + 1)))
+ {
+ syslog (LOG_ERR, "Failed to allocate memory for login name");
+ exit (EXIT_FAILURE);
+ }
+
+ hostname = localhost ();
+ prompt_size = asprintf (&prompt, "%s%s", hostname, LOGIN);
+ free (hostname);
+ write (fd, prompt, prompt_size);
+ free (prompt);
+
+ /* flush pending input */
+ sleep (1);
+ tcflush (fd, TCIFLUSH);
+
+ for (ptr = result, done = 0; !done; /* void */)
+ {
+ if (read (fd, &c, 1) < 1)
+ {
+ if (errno == EINTR || errno == EIO)
+ exit (EXIT_FAILURE);
+ }
+
+ switch (c)
+ {
+ case CR:
+ case NL:
+ *ptr = 0; /* terminate logname */
+ done = 1;
+ break;
+ case BS:
+ case DEL:
+ case '#':
+ if (ptr > result)
+ {
+ write (fd, "\b", 1);
+ ptr--;
+ }
+ break;
+ case CTL('U'):
+ case '@':
+ while (ptr > result)
+ {
+ write (fd, "\b", 1);
+ ptr--;
+ }
+ break;
+ case CTL('D'):
+ exit (EXIT_SUCCESS);
+ default:
+ if (!isascii (c) || !isprint (c))
+ {
+ /* ignore garbage characters */
+ }
+ else if (ptr - result > max_pw_size)
+ {
+ /* input overrun, dropping character */
+ }
+ else
+ {
+ *ptr++ = c; /* and store it */
+ }
+ break;
+ }
+ }
+ return result;
+}
+
int
main (int argc, char **argv)
{
@@ -84,6 +180,7 @@
int tty;
struct ttyent *tt;
char *arg;
+ char *login_name;
openlog ("getty", LOG_ODELAY|LOG_CONS|LOG_PID, LOG_AUTH);
@@ -121,6 +218,7 @@
set_speed (tty, linespec);
print_banner (tty, ttyname);
+ login_name = get_login_name(tty);
if (login_tty (tty) == -1)
syslog (LOG_ERR, "cannot set controlling terminal to %s: %m", ttyname);
@@ -129,10 +227,12 @@
if (tt && strcmp (tt->ty_type, "dialup") == 0)
/* Dialup lines time out (which is login's default). */
- execl (_PATH_LOGIN, "login", "-e", arg, NULL);
+ execl (_PATH_LOGIN, "login", "--paranoid", "-e", arg,
+ login_name, NULL);
else
/* Hardwired lines don't. */
- execl (_PATH_LOGIN, "login", "-e", arg, "-aNOAUTH_TIMEOUT", NULL);
+ execl (_PATH_LOGIN, "login", "--paranoid", "-e", arg,
+ "-aNOAUTH_TIMEOUT", login_name, NULL);
syslog (LOG_ERR, "%s: %m", _PATH_LOGIN);
Attachment:
signature.asc
Description: PGP signature