xv6-riscv-kernel/user/ls.c

86 lines
1.6 KiB
C
Raw Normal View History

#include "kernel/types.h"
#include "kernel/stat.h"
#include "user/user.h"
#include "kernel/fs.h"
2006-08-12 06:33:50 +02:00
2024-06-15 16:55:06 +02:00
char *
fmtname(char *path)
{
2024-06-15 16:55:06 +02:00
static char buf[DIRSIZ + 1];
char *p;
// Find first character after last slash.
2024-08-07 16:07:20 +02:00
for(p = path + strlen(path); p >= path && *p != '/'; p--) {}
p++;
// Return blank-padded name.
if(strlen(p) >= DIRSIZ)
return p;
memmove(buf, p, strlen(p));
2024-06-15 16:55:06 +02:00
memset(buf + strlen(p), ' ', DIRSIZ - strlen(p));
return buf;
}
void
ls(char *path)
2006-08-12 06:33:50 +02:00
{
2024-06-15 16:55:06 +02:00
char buf[512], *p;
int fd;
2007-08-22 07:57:39 +02:00
struct dirent de;
2024-06-15 16:55:06 +02:00
struct stat st;
2024-06-15 16:55:06 +02:00
if((fd = open(path, 0)) < 0) {
2019-08-27 19:13:03 +02:00
fprintf(2, "ls: cannot open %s\n", path);
return;
2006-08-12 06:33:50 +02:00
}
2024-06-15 16:55:06 +02:00
if(fstat(fd, &st) < 0) {
2019-08-27 19:13:03 +02:00
fprintf(2, "ls: cannot stat %s\n", path);
close(fd);
return;
2006-08-12 06:33:50 +02:00
}
2024-06-15 16:55:06 +02:00
switch(st.type) {
case T_DEVICE:
case T_FILE:
2019-08-27 19:13:03 +02:00
printf("%s %d %d %l\n", fmtname(path), st.type, st.ino, st.size);
break;
case T_DIR:
2024-06-15 16:55:06 +02:00
if(strlen(path) + 1 + DIRSIZ + 1 > sizeof buf) {
2019-08-27 19:13:03 +02:00
printf("ls: path too long\n");
break;
}
strcpy(buf, path);
2024-06-15 16:55:06 +02:00
p = buf + strlen(buf);
*p++ = '/';
2024-06-15 16:55:06 +02:00
while(read(fd, &de, sizeof(de)) == sizeof(de)) {
if(de.inum == 0)
continue;
memmove(p, de.name, DIRSIZ);
p[DIRSIZ] = 0;
2024-06-15 16:55:06 +02:00
if(stat(buf, &st) < 0) {
2019-08-27 19:13:03 +02:00
printf("ls: cannot stat %s\n", buf);
continue;
}
2019-08-27 19:13:03 +02:00
printf("%s %d %d %d\n", fmtname(buf), st.type, st.ino, st.size);
2006-08-14 05:00:13 +02:00
}
break;
2006-08-12 06:33:50 +02:00
}
close(fd);
}
int
main(int argc, char *argv[])
{
int i;
2024-06-15 16:55:06 +02:00
if(argc < 2) {
ls(".");
exit(0);
}
2024-06-15 16:55:06 +02:00
for(i = 1; i < argc; i++)
ls(argv[i]);
exit(0);
2006-08-12 06:33:50 +02:00
}