login bug? Fix?
walter harms
wharms at bfs.de
Fri Nov 7 08:52:35 UTC 2008
i am sorry for my stupid question but ...
according to sources in the internet login should test for /etc/nologin
and die if exists and you are not root.
so i do not understand why someone may want to read it content.
IMHO the line
puts("\r\nSystem closed for routine maintenance\r");
could be printed always. Not only will it save an if()
but also remind root that /etc/nologin is still present.
just my to cents,
wh
Denys Vlasenko schrieb:
> On Friday 07 November 2008 01:39, Cathey, Jim wrote:
>> The /etc/nologin logic of BB 10&11 seems a bit odd, and
>> had problems echoing newlines in our system. Also,
>> as I understand it, if nologin has contents those
>> are all that's echoed, whereas if there but empty
>> a system default message is supplied.
>>
>> $ diff -c loginutils/login.c~ loginutils/login.c
>> *** loginutils/login.c~ 2008-10-15 11:01:16.000000000 -0700
>> --- loginutils/login.c 2008-11-06 15:19:18.000000000 -0800
>> ***************
>> *** 117,123 ****
>> static void die_if_nologin(void)
>> {
>> FILE *fp;
>> ! int c;
>>
>> if (access("/etc/nologin", F_OK))
>> return;
>> --- 117,123 ----
>> static void die_if_nologin(void)
>> {
>> FILE *fp;
>> ! int c, ii = 0;
>>
>> if (access("/etc/nologin", F_OK))
>> return;
>> ***************
>> *** 125,135 ****
>> fp = fopen("/etc/nologin", "r");
>> if (fp) {
>> while ((c = getc(fp)) != EOF)
>> ! bb_putchar((c=='\n') ? '\r' : c);
>> fflush(stdout);
>> fclose(fp);
>> ! } else
>> puts("\r\nSystem closed for routine maintenance\r");
>> exit(EXIT_FAILURE);
>> }
>> #else
>> --- 125,139 ----
>> fp = fopen("/etc/nologin", "r");
>> if (fp) {
>> while ((c = getc(fp)) != EOF)
>> ! ++ii,bb_putchar((c=='\n') ? (bb_putchar('\r'),c) :
>> c);
>
> (1) Linewrapep patch
> (2) Do you hate poor souls who read your code or just try
> to win code obfuscation contest?
>
>> fflush(stdout);
>> fclose(fp);
>> ! }
>> ! if (!ii) {
>> puts("\r\nSystem closed for routine maintenance\r");
>> + fflush(stdout);
>> + }
>> + tcdrain(fileno(stdout));
>
> fflush() can be done once, after if() - smaller code.
> fileno(stdout) is a known constant, it's STDOUT_FILENO.
> Use it directly - smaller code.
>
>> The above change makes for a recursive \r-adder on \n's, and counts
>> emitted characters. The original code wouldn't emit any \n's that were
>> in a standard unix text file, converting them to \r's instead, resulting
>> in lines that overwrote themselves on display. I thought the purpose of
>> this was to be able to deal with output paths that didn't have a tty
>> device driver that could do CRNL mapping itself. In which case you
>> need both, not a conversion.
>>
>> If any characters are emitted due to the nologin file contents, the
>> default message is suppressed. (This was how I understood the original
>> login [big] to work, and allows for supporting non-English
>> installations.)
>>
>> We also had problems with the emitted file contents being truncated
>> due to the exit(), and the race of the close and the write. The
>> tcdrain()
>> call fixed that. (I don't remember if it was telnet or console that
>> exhibited this problem.)
>
> Thanks.
>
> Applying this patch:
>
> diff -d -urpN busybox.8/loginutils/login.c busybox.9/loginutils/login.c
> --- busybox.8/loginutils/login.c 2008-10-30 08:41:37.000000000 +0100
> +++ busybox.9/loginutils/login.c 2008-11-07 02:07:13.000000000 +0100
> @@ -118,18 +118,25 @@ static void die_if_nologin(void)
> {
> FILE *fp;
> int c;
> + int empty = 1;
>
> - if (access("/etc/nologin", F_OK))
> + fp = fopen_for_read("/etc/nologin");
> + if (!fp) /* assuming it does not exist */
> return;
>
> - fp = fopen_for_read("/etc/nologin");
> - if (fp) {
> - while ((c = getc(fp)) != EOF)
> - bb_putchar((c=='\n') ? '\r' : c);
> - fflush(stdout);
> - fclose(fp);
> - } else
> + while ((c = getc(fp)) != EOF) {
> + if (c == '\n')
> + bb_putchar('\r');
> + bb_putchar(c);
> + empty = 0;
> + }
> + if (empty)
> puts("\r\nSystem closed for routine maintenance\r");
> +
> + fclose(fp);
> + fflush(NULL);
> + /* Users say that they do need this prior exit: */
> + tcdrain(STDOUT_FILENO);
> exit(EXIT_FAILURE);
> }
> #else
> _______________________________________________
> busybox mailing list
> busybox at busybox.net
> http://busybox.net/cgi-bin/mailman/listinfo/busybox
>
>
>
More information about the busybox
mailing list