This commit was manufactured by cvs2svn to create tag 'FreeBSD-release/1.0'.
[unix-history] / bin / ls / print.c
CommitLineData
15637ed4
RG
1/*
2 * Copyright (c) 1989 The Regents of the University of California.
3 * All rights reserved.
4 *
5 * This code is derived from software contributed to Berkeley by
6 * Michael Fischbein.
7 *
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
10 * are met:
11 * 1. Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
16 * 3. All advertising materials mentioning features or use of this software
17 * must display the following acknowledgement:
18 * This product includes software developed by the University of
19 * California, Berkeley and its contributors.
20 * 4. Neither the name of the University nor the names of its contributors
21 * may be used to endorse or promote products derived from this software
22 * without specific prior written permission.
23 *
24 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
25 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
26 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
27 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
28 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
29 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
30 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
31 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
32 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
33 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
34 * SUCH DAMAGE.
35 */
36
37#ifndef lint
38static char sccsid[] = "@(#)print.c 5.24 (Berkeley) 10/19/90";
78ed81a3 39static char rcsid[] = "$Header: /a/cvs/386BSD/src/bin/ls/print.c,v 1.2 1993/06/29 02:59:33 nate Exp $";
15637ed4
RG
40#endif /* not lint */
41
42#include <sys/param.h>
43#include <sys/stat.h>
44#include <stdio.h>
45#include <grp.h>
46#include <pwd.h>
47#include <utmp.h>
48#include <tzfile.h>
49#include "ls.h"
50
51printscol(stats, num)
52 register LS *stats;
53 register int num;
54{
55 for (; num--; ++stats) {
56 (void)printaname(stats);
57 (void)putchar('\n');
58 }
59}
60
61printlong(stats, num)
62 LS *stats;
63 register int num;
64{
65 extern int errno;
66 char modep[15], *user_from_uid(), *group_from_gid(), *strerror();
67
68 if (f_total)
69 (void)printf("total %lu\n", f_kblocks ?
70 howmany(stats[0].lstat.st_btotal, 2) :
71 stats[0].lstat.st_btotal);
72 for (; num--; ++stats) {
73 if (f_inode)
74 (void)printf("%6lu ", stats->lstat.st_ino);
75 if (f_size)
76 (void)printf("%4ld ", f_kblocks ?
77 howmany(stats->lstat.st_blocks, 2) :
78 stats->lstat.st_blocks);
79 (void)strmode(stats->lstat.st_mode, modep);
80 (void)printf("%s %3u %-*s ", modep, stats->lstat.st_nlink,
81 UT_NAMESIZE, user_from_uid(stats->lstat.st_uid, 0));
82 if (f_group)
83 (void)printf("%-*s ", UT_NAMESIZE,
84 group_from_gid(stats->lstat.st_gid, 0));
85 if (S_ISCHR(stats->lstat.st_mode) ||
86 S_ISBLK(stats->lstat.st_mode))
87 (void)printf("%3d, %3d ", major(stats->lstat.st_rdev),
88 minor(stats->lstat.st_rdev));
89 else
90 (void)printf("%8ld ", stats->lstat.st_size);
91 if (f_accesstime)
92 printtime(stats->lstat.st_atime);
93 else if (f_statustime)
94 printtime(stats->lstat.st_ctime);
95 else
96 printtime(stats->lstat.st_mtime);
97 (void)printf("%s", stats->name);
98 if (f_type)
99 (void)printtype(stats->lstat.st_mode);
100 if (S_ISLNK(stats->lstat.st_mode))
101 printlink(stats->name);
102 (void)putchar('\n');
103 }
104}
105
106#define TAB 8
107
108printcol(stats, num)
109 LS *stats;
110 int num;
111{
112 extern int termwidth;
113 register int base, chcnt, cnt, col, colwidth;
114 int endcol, numcols, numrows, row;
115
116 colwidth = stats[0].lstat.st_maxlen;
117 if (f_inode)
118 colwidth += 6;
119 if (f_size)
120 colwidth += 5;
121 if (f_type)
122 colwidth += 1;
123
124 colwidth = (colwidth + TAB) & ~(TAB - 1);
125 if (termwidth < 2 * colwidth) {
126 printscol(stats, num);
127 return;
128 }
129
130 numcols = termwidth / colwidth;
131 numrows = num / numcols;
132 if (num % numcols)
133 ++numrows;
134
135 if (f_size && f_total)
136 (void)printf("total %lu\n", f_kblocks ?
137 howmany(stats[0].lstat.st_btotal, 2) :
138 stats[0].lstat.st_btotal);
139 for (row = 0; row < numrows; ++row) {
140 endcol = colwidth;
141 for (base = row, chcnt = col = 0; col < numcols; ++col) {
142 chcnt += printaname(stats + base);
143 if ((base += numrows) >= num)
144 break;
145 while ((cnt = (chcnt + TAB & ~(TAB - 1))) <= endcol) {
146 (void)putchar('\t');
147 chcnt = cnt;
148 }
149 endcol += colwidth;
150 }
151 putchar('\n');
152 }
153}
154
155/*
156 * print [inode] [size] name
157 * return # of characters printed, no trailing characters
158 */
159printaname(lp)
160 LS *lp;
161{
162 int chcnt;
163
164 chcnt = 0;
165 if (f_inode)
166 chcnt += printf("%5lu ", lp->lstat.st_ino);
167 if (f_size)
168 chcnt += printf("%4ld ", f_kblocks ?
169 howmany(lp->lstat.st_blocks, 2) : lp->lstat.st_blocks);
170 chcnt += printf("%s", lp->name);
171 if (f_type)
172 chcnt += printtype(lp->lstat.st_mode);
173 return(chcnt);
174}
175
176printtime(ftime)
177 time_t ftime;
178{
179 int i;
180 char *longstring, *ctime();
181 time_t time();
182
183 longstring = ctime((long *)&ftime);
184 for (i = 4; i < 11; ++i)
185 (void)putchar(longstring[i]);
186
187#define SIXMONTHS ((DAYSPERNYEAR / 2) * SECSPERDAY)
188 if (f_sectime)
189 for (i = 11; i < 24; i++)
190 (void)putchar(longstring[i]);
191 else if (ftime + SIXMONTHS > time((time_t *)NULL))
192 for (i = 11; i < 16; ++i)
193 (void)putchar(longstring[i]);
194 else {
195 (void)putchar(' ');
196 for (i = 20; i < 24; ++i)
197 (void)putchar(longstring[i]);
198 }
199 (void)putchar(' ');
200}
201
202printtype(mode)
203 mode_t mode;
204{
205 switch(mode & S_IFMT) {
206 case S_IFDIR:
207 (void)putchar('/');
208 return(1);
209 case S_IFLNK:
210 (void)putchar('@');
211 return(1);
212 case S_IFSOCK:
213 (void)putchar('=');
214 return(1);
78ed81a3 215 case S_IFIFO:
216 (void)putchar('|');
217 return(1);
15637ed4
RG
218 }
219 if (mode & (S_IXUSR | S_IXGRP | S_IXOTH)) {
220 (void)putchar('*');
221 return(1);
222 }
223 return(0);
224}
225
226printlink(name)
227 char *name;
228{
229 int lnklen;
230 char path[MAXPATHLEN + 1], *strerror();
231
232 if ((lnklen = readlink(name, path, MAXPATHLEN)) == -1) {
233 (void)fprintf(stderr, "\nls: %s: %s\n", name, strerror(errno));
234 return;
235 }
236 path[lnklen] = '\0';
237 (void)printf(" -> %s", path);
238}