From owner-freebsd-bugs Sun Jun 21 14:11:41 1998 Return-Path: Received: (from majordom@localhost) by hub.freebsd.org (8.8.8/8.8.8) id OAA00291 for freebsd-bugs-outgoing; Sun, 21 Jun 1998 14:11:41 -0700 (PDT) (envelope-from owner-freebsd-bugs@FreeBSD.ORG) Received: from freefall.freebsd.org (freefall.FreeBSD.ORG [204.216.27.21]) by hub.freebsd.org (8.8.8/8.8.8) with ESMTP id OAA00274 for ; Sun, 21 Jun 1998 14:11:36 -0700 (PDT) (envelope-from gnats@FreeBSD.org) Received: (from gnats@localhost) by freefall.freebsd.org (8.8.8/8.8.5) id OAA26936; Sun, 21 Jun 1998 14:10:01 -0700 (PDT) Received: from mail.camalott.com (root@[208.203.140.2]) by hub.freebsd.org (8.8.8/8.8.8) with ESMTP id OAA00178 for ; Sun, 21 Jun 1998 14:10:38 -0700 (PDT) (envelope-from joelh@gnu.org) Received: from detlev.UUCP (tex-148.camalott.com [208.229.74.148] (may be forged)) by mail.camalott.com (8.8.7/8.8.5) with ESMTP id QAA16696 for ; Sun, 21 Jun 1998 16:10:11 -0500 Received: (from joelh@localhost) by detlev.UUCP (8.8.8/8.8.8) id QAA25952; Sun, 21 Jun 1998 16:07:59 -0500 (CDT) (envelope-from joelh) Message-Id: <199806212107.QAA25952@detlev.UUCP> Date: Sun, 21 Jun 1998 16:07:59 -0500 (CDT) From: Joel Ray Holveck Reply-To: joelh@gnu.org To: FreeBSD-gnats-submit@FreeBSD.ORG X-Send-Pr-Version: 3.2 Subject: bin/7011: Improvements to ls to help Emacs users; patch included Sender: owner-freebsd-bugs@FreeBSD.ORG Precedence: bulk X-Loop: FreeBSD.org >Number: 7011 >Category: bin >Synopsis: Improvements to ls to help Emacs users; patch included >Confidential: no >Severity: non-critical >Priority: low >Responsible: freebsd-bugs >State: open >Quarter: >Keywords: >Date-Required: >Class: change-request >Submitter-Id: current-users >Arrival-Date: Sun Jun 21 14:10:01 PDT 1998 >Last-Modified: >Originator: Joel Ray Holveck >Organization: None >Release: FreeBSD 3.0-CURRENT i386 >Environment: FreeBSD-current, cvsup'd late 20Jun98. GNU Emacs 20.2.2. >Description: Emacs's editing mode, dired, will ls individual files when it creates changes. However, our current implementation of ls may use different column widths for different sets of files being ls'd. This means that if a single dired directory listing includes data from multiple invocations of ls, the columns may not align properly. This problem should also exist under any other directory utility which directly displays the output of ls, and will display data obtained from multiple invocations with different filesets at the same time. >How-To-Repeat: Launch Emacs. Press: C-x C-f ~ RET Dired will launch and displays a directory listing of the home directory. A portion of a sample follows: -rwxr-xr-x 1 joelh joelh 3863 May 11 23:20 .bashrc -rw-r--r-- 1 joelh joelh 32126 Jun 21 14:10 .emacs -rw-r--r-- 1 joelh joelh 209 Jan 8 12:34 .emacs.bmk -rw-r--r-- 1 joelh joelh 0 Mar 4 02:45 .emacs_args -rw------- 1 joelh joelh 4217 Jun 17 00:24 .fetchmailrc Using C-n and C-p, navigate to an item that uses less than the maximum width of any column (eg, has a size an order of magnitude smaller than another). (I am using .emacs.bmk as an example.) Press M (dired-do-chmod). Press u+r (which is probably a nop in chmod, but will cause the file selected to refresh by itself). The directory will now have skewed columns: -rwxr-xr-x 1 joelh joelh 3863 May 11 23:20 .bashrc -rw-r--r-- 1 joelh joelh 32126 Jun 21 14:10 .emacs -rw-r--r-- 1 joelh joelh 209 Jan 8 12:34 .emacs.bmk -rw-r--r-- 1 joelh joelh 0 Mar 4 02:45 .emacs_args -rw------- 1 joelh joelh 4217 Jun 17 00:24 .fetchmailrc >Fix: I propose a change to ls which will allow minimum column widths to be set in the environment. A runtime environment variable, LS_COLWIDTHS is added. This is a colon-delimited list of minimum column widths for each variable-width column, in order of display by 'ls -lois'. For example, by default, 'ls -l' may display: total 321 -rw-r--r-- 1 joelh bin 7435 Jun 21 13:45 cmp.o -rwxr-xr-x 1 joelh bin 238385 Jun 21 14:42 ls -rw-r--r-- 1 joelh bin 4352 Jun 21 14:42 ls.1.gz -rw-r--r-- 1 joelh bin 21182 Jun 21 14:42 ls.o -rw-r--r-- 1 joelh bin 16457 Jun 21 13:45 print.o -rw-r--r-- 1 joelh bin 9814 Jun 21 13:45 stat_flags.o -rw-r--r-- 1 joelh bin 11508 Jun 21 13:45 util.o However, with LS_COLWIDTHS set to 6:4:2:8:8:1:7:0 (the affected fields for a simple -l listing are block count, user, group, and size), 'ls -l' in the same directory will display: total 321 -rw-r--r-- 1 joelh bin 7435 Jun 21 13:45 cmp.o -rwxr-xr-x 1 joelh bin 238385 Jun 21 14:42 ls -rw-r--r-- 1 joelh bin 4352 Jun 21 14:42 ls.1.gz -rw-r--r-- 1 joelh bin 21182 Jun 21 14:42 ls.o -rw-r--r-- 1 joelh bin 16457 Jun 21 13:45 print.o -rw-r--r-- 1 joelh bin 9814 Jun 21 13:45 stat_flags.o -rw-r--r-- 1 joelh bin 11508 Jun 21 13:45 util.o By setting LS_COLWIDTHS to a reasonable value, all invocations of ls will use the same column widths, thereby effectively allowing a repeatable output format under normal conditions. (The problem will still manifest as before if the column widths specified in LS_COLWIDTHS are insufficient to display the requested listing, since the columns output will still expand to meet the needs of the listing.) If additional output columns are added in the future, it is recommended to append column width specifiers to LS_COLWIDTHS rather than adding them in display order, to maintain backward compatibility. Attached are the diffs to ls.c and ls.1 to implement the recommended change. Happy hacking, joelh *** ls.c-orig Sun Jun 21 13:54:31 1998 --- ls.c Sun Jun 21 14:42:40 1998 *************** *** 69,74 **** --- 69,75 ---- static void display __P((FTSENT *, FTSENT *)); static int mastercmp __P((const FTSENT **, const FTSENT **)); static void traverse __P((int, char **, int)); + static u_quad_t makenines __P((u_long)); static void (*printfcn) __P((DISPLAY *)); static int (*sortfcn) __P((const FTSENT *, const FTSENT *)); *************** *** 396,401 **** --- 397,403 ---- u_quad_t maxsize; u_long btotal, maxblock, maxinode, maxlen, maxnlink; int bcfile, flen, glen, ulen, maxflags, maxgroup, maxuser; + char* initmax; int entries, needstats; char *user, *group, *flags, buf[20]; /* 32 bits == 10 digits */ *************** *** 411,421 **** needstats = f_inode || f_longform || f_size; flen = 0; ! btotal = maxblock = maxinode = maxlen = maxnlink = 0; bcfile = 0; - maxuser = maxgroup = maxflags = 0; flags = NULL; - maxsize = 0; for (cur = list, entries = 0; cur; cur = cur->fts_link) { if (cur->fts_info == FTS_ERR || cur->fts_info == FTS_NS) { warnx("%s: %s", --- 413,441 ---- needstats = f_inode || f_longform || f_size; flen = 0; ! btotal = 0; ! initmax = getenv("LS_COLWIDTHS"); ! /* This sscanf matches the order of ls -lios. */ ! if (initmax != NULL) { ! if (sscanf(initmax, ! " %lu : %lu : %lu : %i : %i : %i : %qu : %lu ", ! &maxinode, &maxblock, &maxnlink, &maxuser, ! &maxgroup, &maxflags, &maxsize, &maxlen) ! == 8) { ! maxinode = makenines(maxinode); ! maxblock = makenines(maxblock); ! maxnlink = makenines(maxnlink); ! maxsize = makenines(maxsize); ! } else { ! fputs("ls: bad LS_COLWIDTHS\n", stderr); ! initmax = NULL; ! } ! } ! if (initmax == NULL) ! maxblock = maxinode = maxlen = maxnlink = ! maxuser = maxgroup = maxflags = maxsize = 0; bcfile = 0; flags = NULL; for (cur = list, entries = 0; cur; cur = cur->fts_link) { if (cur->fts_info == FTS_ERR || cur->fts_info == FTS_NS) { warnx("%s: %s", *************** *** 560,563 **** --- 580,603 ---- return (-1); } return (sortfcn(*a, *b)); + } + + /* + * Makenines() returns (10**n)-1. This is useful for converting a width + * into a number that wide in decimal. + */ + static u_quad_t + makenines(n) + u_long n; + { + u_long i; + u_quad_t reg; + + reg = 1; + /* Use a loop instead of pow(), since all values of n are small. */ + for (i = 0; i < n; i++) + reg *= 10; + reg--; + + return reg; } *** ls.1-orig Sun Jun 21 14:35:08 1998 --- ls.1 Sun Jun 21 14:41:42 1998 *************** *** 373,378 **** --- 373,385 ---- See .Xr environ 7 for more information. + .It Ev LS_COLWIDTHS + If this variable is set, it is considered to be a + colon-delimited list of minimum column widths (possibly + zero). The columns are, in order: inode, block count, + number of links, user name, group name, flags, file size, + file name. (This corresponds to the order of the relevant + columns in output.) .El .Sh COMPATIBILITY The group field is now automatically included in the long listing for >Audit-Trail: >Unformatted: To Unsubscribe: send mail to majordomo@FreeBSD.org with "unsubscribe freebsd-bugs" in the body of the message