os

An operating system
git clone https://erai.gay/code/os/
Log | Files | Refs | README | LICENSE

commit 9af7199750e539d4bd0fbe9464c7cd38e09c1706
parent d5f4cba15457120d1a87029ff1a05d47a98226fd
Author: erai <erai@omiltem.net>
Date:   Mon, 27 May 2024 13:00:42 -0400

add xxd command

Diffstat:
Mbootstrap.sh | 2+-
Mbuild.sh | 6++++--
Acat.c | 59+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Mlib.c | 74++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Axxd.c | 56++++++++++++++++++++++++++++++++++++++++++++++++++++++++
5 files changed, 194 insertions(+), 3 deletions(-)

diff --git a/bootstrap.sh b/bootstrap.sh @@ -11,4 +11,4 @@ gcc -Wall -Wextra -Wno-unused -pedantic -std=c99 ./cc0.c -o cc0 cmp cc1 cc2 || echo mismatch -sh ./build.sh +sh -e ./build.sh diff --git a/build.sh b/build.sh @@ -6,8 +6,8 @@ GENLEX="genlex.c" BOOT="pxe.asm" SSHD="chacha20.c poly1305.c sha256.c sha512.c ed25519.c sshd.c" KERNEL="kernel.c" -SHELL="echo.c cmp.c rm.c ls.c mv.c mkdir.c cpio.c vi.c sh.c" -BIN="echo cmp rm ls mv mkdir cpio sh vi sshd init cc1 cc2" +SHELL="echo.c cmp.c rm.c ls.c cat.c xxd.c mv.c mkdir.c cpio.c vi.c sh.c" +BIN="echo cmp rm ls cat xxd mv mkdir cpio sh vi sshd init cc1 cc2 build.sh cc3.l" ALL="${LIBS} ${CC} ${GENLEX} ${BOOT} ${SSHD} ${KERNEL} ${SHELL} ${BIN}" ./cc1 ${LIBS} ${CC} -o cc2 @@ -21,6 +21,8 @@ ALL="${LIBS} ${CC} ${GENLEX} ${BOOT} ${SSHD} ${KERNEL} ${SHELL} ${BIN}" ./cc2 ${LIBS} mv.c -o mv ./cc2 ${LIBS} mkdir.c -o mkdir ./cc2 ${LIBS} ls.c -o ls +./cc2 ${LIBS} cat.c -o cat +./cc2 ${LIBS} xxd.c -o xxd ./cc2 ${LIBS} cpio.c -o cpio ./cc2 ${LIBS} sh.c -o sh ./cc2 ${LIBS} sshd.c -o sshd diff --git a/cat.c b/cat.c @@ -0,0 +1,59 @@ +docat(fd: int, buf: *byte) { + var n: int; + var m: int; + var k: int; + loop { + n = read(fd, buf, 4096); + if n == 0 { + return; + } + + if n < 0 { + die("read failed"); + } + + m = 0; + loop { + if m == n { + break; + } + + k = write(1, &buf[m], n - m); + if k < 0 { + die("write failed"); + } + + m = m + k; + } + } +} + +main(argc: int, argv: **byte, envp: **byte) { + var fd: int; + var i: int; + var a: alloc; + var buf: *byte; + + setup_alloc(&a); + + buf = alloc(&a, 4096); + + if argc == 1 { + docat(0, buf); + } else { + i = 1; + loop { + if i >= argc { + break; + } + + fd = open(argv[i], 0, 0); + + docat(fd, buf); + + close(fd); + + i = i + 1; + } + } +} diff --git a/lib.c b/lib.c @@ -155,6 +155,80 @@ fdputd(fd: int, n: int) { fdputc(fd, '0' + a); } +xxd_line(line: *byte, offset: int, data: *byte, len: int) { + var i: int; + var j: int; + var d: *byte; + d = "0123456789abcdef"; + + i = 0; + + line[i] = d[(offset >> 28) & 15]; + line[i + 1] = d[(offset >> 24) & 15]; + line[i + 2] = d[(offset >> 20) & 15]; + line[i + 3] = d[(offset >> 16) & 15]; + line[i + 4] = d[(offset >> 12) & 15]; + line[i + 5] = d[(offset >> 8) & 15]; + line[i + 6] = d[(offset >> 4) & 15]; + line[i + 7] = d[offset & 15]; + line[i + 8] = ':':byte; + line[i + 9] = ' ':byte; + + i = i + 10; + + j = 0; + loop { + if j == 16 { + break; + } + + if j < len { + line[i] = d[(data[j]:int >> 4) & 15]; + line[i + 1] = d[data[j]:int & 15]; + } else { + line[i] = ' ':byte; + line[i + 1] = ' ':byte; + } + + if j + 1 < len { + line[i + 2] = d[(data[j]:int >> 4) & 15]; + line[i + 3] = d[data[j]:int & 15]; + } else { + line[i + 2] = ' ':byte; + line[i + 3] = ' ':byte; + } + + line[i + 4] = ' ':byte; + + j = j + 2; + i = i + 5; + } + + line[i] = ' ':byte; + i = i + 1; + + j = 0; + loop { + if j == 16 || j >= len { + break; + } + + if data[j]:int >= 0x20 && data[j]:int < 0x80 { + line[i] = data[j]; + } else { + line[i] = '.':byte; + } + + j = j + 1; + i = i + 1; + } + + line[i] = '\n':byte; + i = i + 1; + + line[i] = 0:byte; +} + fdxxd(fd: int, data: *byte, len: int) { var i: int; var j: int; diff --git a/xxd.c b/xxd.c @@ -0,0 +1,56 @@ +doxxd(fd: int, buf: *byte) { + var n: int; + var m: int; + var ret: int; + + m = 0; + loop { + n = 0; + loop { + ret = read(fd, buf, 16 - n); + if ret == 0 { + break; + } + + if ret < 0 { + die("read failed"); + } + + n = n + ret; + + if n == 16 { + break; + } + } + + xxd_line(&buf[16], m, buf, n); + fdputs(1, &buf[16]); + + if n < 16 { + break; + } + + m = m + n; + } +} + +main(argc: int, argv: **byte, envp: **byte) { + var fd: int; + var i: int; + var a: alloc; + var buf: *byte; + + setup_alloc(&a); + + buf = alloc(&a, 4096); + + if argc == 1 { + doxxd(0, buf); + } else if argc == 2 { + fd = open(argv[1], 0, 0); + doxxd(fd, buf); + close(fd); + } else { + die("usage: xxd [file]"); + } +}