shithub: kandr

Download patch

ref: 91fc7321c2b7df934036f7b88ffdd5d6c826e941
parent: eff8fc233ea5bb8d61b5ab53bf66e792eacda7f5
author: henesy <henesy.dev@gmail.com>
date: Fri Feb 25 23:00:22 EST 2022

pt1 content, ex1-[19-20]

--- /dev/null
+++ b/ex/ex1-16.c
@@ -1,0 +1,44 @@
+#include <u.h>
+#include <libc.h>
+#include <bio.h>
+
+/* 
+Print the length of arbitraryily long input lines
+	and as much as possible of the text.
+*/
+void
+main(int, char*[])
+{
+	Biobuf	*in, *out;
+	in = Bfdopen(0, OREAD);
+	out = Bfdopen(1, OWRITE);
+
+	u32int len = 0;
+	while(1){
+		long r;
+		int n;
+
+		// Read
+		r = Bgetrune(in);
+		if(r == Beof)
+			break;
+		if(r < 0)
+			sysfatal("err: could not read rune → %r\n");
+
+		len++;
+		if(r == L'\n'){
+			Bprint(out, "\n» Line length = %uld\n", len);
+			len = 0;
+		}
+
+		// Write
+		n = Bputrune(out, r);
+		if(n < 0)
+			sysfatal("err: could not write rune → %r\n");
+	}
+
+	Bterm(in);
+	Bterm(out);
+
+	exits(nil);
+}
--- /dev/null
+++ b/ex/ex1-17.c
@@ -1,0 +1,43 @@
+#include <u.h>
+#include <libc.h>
+#include <bio.h>
+
+const MIN = 80;
+
+/* 
+Print lines greater than 80 runes. 
+*/
+void
+main(int, char*[])
+{
+	Biobuf	*in, *out;
+	in = Bfdopen(0, OREAD);
+	out = Bfdopen(1, OWRITE);
+
+	u32int len = 0;
+	while(1){
+		char *line;
+		int len, n;
+
+		// Read
+		line = Brdline(in, '\n');
+		len = Blinelen(in);
+		if(line == 0)
+			break;
+		if(len < 0)
+			sysfatal("err: could not read line → %r\n");
+
+		if(len <= 80)
+			continue;
+
+		// Write
+		n = Bwrite(out, line, len);
+		if(n < 0)
+			sysfatal("err: could not write rune → %r\n");
+	}
+
+	Bterm(in);
+	Bterm(out);
+
+	exits(nil);
+}
--- /dev/null
+++ b/ex/ex1-18.c
@@ -1,0 +1,59 @@
+#include <u.h>
+#include <libc.h>
+#include <bio.h>
+
+const MIN = 80;
+
+/* 
+Skip blank lines and trim trailing whitespace. 
+*/
+void
+main(int, char*[])
+{
+	Biobuf	*in, *out;
+	in = Bfdopen(0, OREAD);
+	out = Bfdopen(1, OWRITE);
+
+	u32int len = 0;
+	while(1){
+		char *line;
+		int len, n, i, last;
+
+		// Read
+		line = Brdline(in, '\n');
+		len = Blinelen(in);
+		if(line == 0)
+			break;
+		if(len < 0)
+			sysfatal("err: could not read line → %r\n");
+
+		if(len < 2)
+			continue;
+
+		last = 0;
+		for(i = 0; i < len-1; i++){
+			switch(line[i]){
+			case ' ':
+			case '\t':
+				break;
+			default:
+				last = i;
+			}
+		}
+
+		if(last != len-1){
+			len = last+2;
+			line[last+1] = '\n';
+		}
+
+		// Write
+		n = Bwrite(out, line, len);
+		if(n < 0)
+			sysfatal("err: could not write line → %r\n");
+	}
+
+	Bterm(in);
+	Bterm(out);
+
+	exits(nil);
+}
--- /dev/null
+++ b/ex/ex1-19.c
@@ -1,0 +1,74 @@
+#include <u.h>
+#include <libc.h>
+#include <bio.h>
+
+// Return an allocated buffer containing the reversal of 'in'
+Rune*
+reverse(Rune *in, Rune *out, usize len)
+{
+	if(in == nil || len < 1)
+		return nil;
+
+	int i;
+
+	//fprint(2, "reversing \"%S\" ;; runelen = %d\n", in, len);
+	int to = 0, from = len-1;
+	while(from >= 0){
+		//fprint(2, "out[%d] = in[%d](%C)\n", to, from, in[from]);
+		out[to] = in[from];
+		from--;
+		to++;
+	}
+
+	return out;
+}
+
+/* 
+Reverse lines of input using a reverse function. 
+*/
+void
+main(int, char*[])
+{
+	Biobuf	*in, *out;
+	in = Bfdopen(0, OREAD);
+	out = Bfdopen(1, OWRITE);
+
+	while(1){
+		long rlen = 0;
+		char *line;
+		int len = 0, n, i;
+		Rune *rev, *rstr;
+
+		// Read
+		line = Brdstr(in, '\n', 1);
+		len = Blinelen(in);
+		if(line == 0)
+			break;
+		if(len < 0)
+			sysfatal("err: could not read line → %r\n");
+
+		rstr = runesmprint("%s", line);
+		if(rstr == nil)
+			sysfatal("err: UTF8 conversion failed → %r\n");
+		rlen = runestrlen(rstr);
+		rev = calloc(rlen+1, sizeof (Rune));
+		reverse(rstr, rev, rlen);
+		if(rev == nil)
+			sysfatal("err: reversal failed\n");
+		rev[rlen] = '\0';
+
+		// Write
+		n = Bprint(out, "%S\n", rev);
+		if(n < 0)
+			sysfatal("err: could not write line → %r\n");
+
+		free(line);
+		free(rev);
+		free(rstr);
+	}
+
+	Bterm(in);
+	Bterm(out);
+
+	exits(nil);
+}
--- /dev/null
+++ b/ex/ex1-20.c
@@ -1,0 +1,80 @@
+#include <u.h>
+#include <libc.h>
+#include <bio.h>
+
+void
+usage(void)
+{
+	fprint(2, "usage: %s [-t tabstop]", argv0);
+	exits("usage");
+}
+
+/* 
+Replace tabs with 'tabstop' number of spaces. 
+*/
+void
+main(int argc, char *argv[])
+{
+	int tabstop = 4;
+	Biobuf	*in, *out;
+	char *aux;
+
+	ARGBEGIN{
+	case 't':
+		aux = EARGF(usage());
+		tabstop = atoi(aux);
+		break;
+	default:
+		usage();
+	}ARGEND
+
+	in = Bfdopen(0, OREAD);
+	out = Bfdopen(1, OWRITE);
+
+	while(1){
+		char *line;
+		int len, n, i;
+
+		// Read
+		line = Brdline(in, '\n');
+		len = Blinelen(in);
+		if(line == 0)
+			break;
+		if(len < 0)
+			sysfatal("err: could not read line → %r\n");
+
+		int ind = -1;
+		for(i = 0; i < len-1; i++){
+			if(line[i] != ' ' && line[i] != '	'){
+				ind = i;
+				break;
+			}
+
+			if(line[i] == '	'){
+				int j;
+				for(j = 0; j < tabstop; j++)
+					Bwrite(out, " ", 1);
+			}
+		}
+
+		// Write
+		char *begin = line;
+		int end = len;
+
+		if(ind > 0){
+			ind++;
+			begin = line+ind-1;
+			end = len-ind+1;
+		}
+
+		n = Bwrite(out, begin, end);
+		if(n < 0)
+			sysfatal("err: could not write line → %r\n");
+	}
+
+	Bterm(in);
+	Bterm(out);
+
+	exits(nil);
+}
+