diff options
| author | Richard Qin <richard.qin.x@gmail.com> | 2026-01-04 14:12:24 +0800 |
|---|---|---|
| committer | Richard Qin <richard.qin.x@gmail.com> | 2026-01-04 14:12:24 +0800 |
| commit | a64d25c07b31d57f8706073e11cd774d0880d6dd (patch) | |
| tree | a4bbae6cff94fa69eea30db865267b211eb4c86b /src/user/ls.cc | |
| parent | 210025560c80b48af4875af199f183ad709e3bf0 (diff) | |
| parent | d3cf3f08d1343d6b265516d5a79ce2d197b59d26 (diff) | |
| download | lume-a64d25c07b31d57f8706073e11cd774d0880d6dd.tar.gz lume-a64d25c07b31d57f8706073e11cd774d0880d6dd.tar.xz | |
Merge pull request #5 from Richard-Qin-001/dev/file-system
feat(file-system): implement read and write FAT32 File System and basic shell
Diffstat (limited to 'src/user/ls.cc')
| -rw-r--r-- | src/user/ls.cc | 112 |
1 files changed, 112 insertions, 0 deletions
diff --git a/src/user/ls.cc b/src/user/ls.cc new file mode 100644 index 0000000..e472578 --- /dev/null +++ b/src/user/ls.cc @@ -0,0 +1,112 @@ +#include "ulib/stdio.h" +#include "ulib/stdlib.h" +#include "ulib/string.h" +#include "user/user.h" +#include "common/fcntl.h" + + +struct FAT32_DirEnt +{ + char name[11]; + uint8 attr; + uint8 lcase; + uint8 ctime_cs; + uint16 ctime; + uint16 cdate; + uint16 adate; + uint16 fstClusHI; + uint16 wtime; + uint16 wdate; + uint16 fstClusLO; + uint32 fileSize; +} __attribute__((packed)); + +#define ATTR_DIRECTORY 0x10 +#define ATTR_LONG_NAME 0x0F + +void fmt_name(char *dst, const char *src) +{ + int i; + char *d = dst; + + for (i = 0; i < 8; i++) + { + if (src[i] == ' ') + break; + *d++ = src[i]; + } + + if (src[8] != ' ') + { + *d++ = '.'; + for (i = 8; i < 11; i++) + { + if (src[i] == ' ') + break; + *d++ = src[i]; + } + } + *d = 0; + + for (d = dst; *d; d++) + { + if (*d >= 'A' && *d <= 'Z') + *d += 32; + } +} + +void ls(const char *path) +{ + int fd; + struct FAT32_DirEnt de; + char name_buf[16]; + + if ((fd = open(path, O_RDONLY)) < 0) + { + printf("ls: cannot open %s\n", path); + return; + } + + while (read(fd, &de, sizeof(de)) == sizeof(de)) + { + if (de.name[0] == 0) + { + break; + } + + if ((unsigned char)de.name[0] == 0xE5) + { + continue; + } + + if ((de.attr & ATTR_LONG_NAME) == ATTR_LONG_NAME) + { + continue; + } + + fmt_name(name_buf, de.name); + + printf("%s %d\t%s\n", + (de.attr & ATTR_DIRECTORY) ? "<DIR>" : " ", + de.fileSize, + name_buf); + } + + close(fd); +} + +int main(int argc, char *argv[]) +{ + if (argc < 2) + { + ls("."); + } + else + { + for (int i = 1; i < argc; i++) + { + ls(argv[i]); + } + } + exit(0); +}
\ No newline at end of file |
