summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/user/app/shell.c27
-rw-r--r--src/user/driver/termcook.c8
-rw-r--r--src/user/lib/stdlib.c17
-rw-r--r--src/user/lib/stdlib.h1
4 files changed, 39 insertions, 14 deletions
diff --git a/src/user/app/shell.c b/src/user/app/shell.c
index 3a08af4..952b9b7 100644
--- a/src/user/app/shell.c
+++ b/src/user/app/shell.c
@@ -46,21 +46,24 @@ static void cmd_cat_ls(const char *args, bool ls) {
static char buf[512];
int len; // first used for strlen(args), then length of buffer
- if (!args) args = "/";
- len = strlen(args);
- memcpy(buf, args, len + 1); // no overflow check - the shell is just a PoC
-
- if (ls) { // paths to directories always have a trailing slash
- char *p = buf;
- while (*p) p++;
- if (p[-1] != '/') {
- p[0] = '/';
- p[1] = '\0';
- len++;
+ if (args) {
+ len = strlen(args);
+ memcpy(buf, args, len + 1); // no overflow check - the shell is just a PoC
+
+ if (ls) { // paths to directories always have a trailing slash
+ if (buf[len-1] != '/') {
+ buf[len] = '/';
+ buf[len+1] = '\0';
+ }
}
+
+ file = file_open(buf, 0);
+ } else if (ls) { /* ls default argument */
+ file = file_open("/", 0);
+ } else { /* cat default argument */
+ file = file_clone(stdin);
}
- file = file_open(buf, 0);
if (!file) {
printf("couldn't open.\n");
return;
diff --git a/src/user/driver/termcook.c b/src/user/driver/termcook.c
index 6ed8223..56ac77c 100644
--- a/src/user/driver/termcook.c
+++ b/src/user/driver/termcook.c
@@ -28,8 +28,12 @@ static void line_editor(handle_t input, handle_t output) {
}
break;
case 4: /* EOT, C-d */
- w_output(output, linebuf, linepos);
- linepos = 0;
+ if (linepos > 0) {
+ w_output(output, linebuf, linepos);
+ linepos = 0;
+ } else {
+ _syscall_write(output, NULL, 0, 0); // eof
+ }
break;
case '\n':
case '\r':
diff --git a/src/user/lib/stdlib.c b/src/user/lib/stdlib.c
index 32b4f06..56b8bb4 100644
--- a/src/user/lib/stdlib.c
+++ b/src/user/lib/stdlib.c
@@ -94,6 +94,23 @@ fail:
return NULL;
}
+libc_file *file_clone(const libc_file *f) {
+ handle_t h = _syscall_dup(f->fd, -1, 0);
+ libc_file *f2;
+ if (h < 0) return NULL;
+
+ // TODO file_wrapfd
+ f2 = malloc(sizeof *f2);
+ if (!f2) {
+ close(h);
+ return NULL;
+ }
+ f2->pos = f->pos;
+ f2->eof = f->eof;
+ f2->fd = h;
+ return f2;
+}
+
int file_read(libc_file *f, char *buf, size_t len) {
if (f->fd < 0) return -1;
diff --git a/src/user/lib/stdlib.h b/src/user/lib/stdlib.h
index 22227e3..1982e85 100644
--- a/src/user/lib/stdlib.h
+++ b/src/user/lib/stdlib.h
@@ -17,6 +17,7 @@ typedef struct {
} libc_file;
libc_file *file_open(const char *path, int flags);
libc_file *file_reopen(libc_file*, const char *path, int flags);
+libc_file *file_clone(const libc_file*);
int file_read(libc_file*, char *buf, size_t len);
int file_write(libc_file*, const char *buf, size_t len);
void file_close(libc_file*);