commit dcfa54da43d06623c133d973cbc7c375040ecf75
parent 256ff3955e54c488b48a51113f56f9fd507cad85
Author: ssnf <ssnf@ssnf.xyz>
Date: Thu, 10 Jul 2025 16:28:05 -0500
add signal-based window resize support
Diffstat:
M | posix.c | | | 22 | +++++++++++++++------- |
M | sim.c | | | 82 | +++++++++++++++++++++++++++++++++++++++++++------------------------------------ |
M | sim.h | | | 13 | +++++++------ |
3 files changed, 67 insertions(+), 50 deletions(-)
diff --git a/posix.c b/posix.c
@@ -1,23 +1,23 @@
-#include <sys/ioctl.h>
#include <stdio.h>
+
+#include <sys/ioctl.h>
+#include <signal.h>
#include <termios.h>
#include "sim.h"
-void win_end(void);
-void win_init(Window* w);
-void win_query(Window* w);
+static void handle(int);
static struct termios initial_state;
-void
+extern void
win_end(void)
{
printf(ED CSI "H");
tcsetattr(0, TCSAFLUSH, &initial_state);
}
-void
+extern void
win_init(Window* w)
{
struct termios raw_state;
@@ -30,9 +30,10 @@ win_init(Window* w)
printf(CSI "H\t" CSI "6n");
scanf("\x1b[%*d;%huR", &w->t);
--w->t;
+ handle(SIGWINCH);
}
-void
+extern void
win_query(Window* w)
{
struct winsize ws;
@@ -41,3 +42,10 @@ win_query(Window* w)
w->wx = ws.ws_col;
w->wy = ws.ws_row;
}
+
+static void
+handle(int sig)
+{
+ resize();
+ signal(SIGWINCH, handle);
+}
diff --git a/sim.c b/sim.c
@@ -85,9 +85,6 @@ typedef struct {
ushort size;
} Frame;
-void die(char*, ...);
-void* emalloc(ulong);
-void* erealloc(void*, ulong);
static Rune* Strchr(Rune *s, Rune r);
static String Strn(Rune *r, ulong n);
static Rune* Strnstr(Rune *s1, Rune *s2, ulong n);
@@ -107,6 +104,7 @@ static void delete(int arg);
static void dot(int arg);
static void redo(int arg);
static void escape(int c);
+static uchar getc2(void);
static Rune getr(void);
static void init(void);
static void input(String* s, uint line, char* prefix);
@@ -130,7 +128,6 @@ static void msg(uint line, char* fmt, ...);
static void paste(int arg);
static void pline(int arg);
static uchar r2u(char *s, Rune r);
-static void resize(void);
static uint runesiz(Rune c, ulong wx);
static void search(int arg);
static int selection(int arg);
@@ -151,11 +148,11 @@ static void move(int);
static void quit(int);
static void yank(int arg);
-static Frame* fr, frame[FILECOUNT];
-static File* f, file[FILECOUNT];
-static String istr, srch;
-static Window w;
-static uint counter;
+static Frame frame[FILECOUNT], *fr = frame;
+static File file[FILECOUNT], *f = file;
+static String istr, srch;
+static Window w;
+static uint counter;
static char *ctrune[0x20] = {
"nul", "soh", "stx", "etx", "eot", "enq", "ack", "bel",
"bs" , "\\t", "\\n", "vt" , "ff" , "cr" , "so" , "si",
@@ -165,7 +162,7 @@ static char *ctrune[0x20] = {
#include "config.h"
-void
+extern void
die(char* fmt, ...)
{
static char *s;
@@ -192,7 +189,7 @@ die(char* fmt, ...)
abort();
}
-void*
+extern void*
emalloc(ulong n)
{
void* p;
@@ -204,7 +201,7 @@ emalloc(ulong n)
return p;
}
-void*
+extern void*
erealloc(void* p, ulong n)
{
p = realloc(p, n);
@@ -213,6 +210,20 @@ erealloc(void* p, ulong n)
return p;
}
+extern void
+resize(void)
+{
+ Window wt;
+
+ win_query(&wt);
+ if (wt.wx != w.wx || wt.wy != w.wy) {
+ w.wx = wt.wx;
+ w.wy = wt.wy;
+ fr_zero(fr);
+ fr_update();
+ }
+}
+
static Rune*
Strchr(Rune *s, Rune r)
{
@@ -542,7 +553,7 @@ static void
escape(int c)
{
counter = 0;
- c = fgetc(stdin) - 0x30;
+ c = getc2() - 0x30;
if (c > 0 && c <= 8) {
--c;
f = &file[c];
@@ -552,6 +563,21 @@ escape(int c)
ungetc(c + 0x30, stdin);
}
+static uchar
+getc2(void)
+{
+ uchar c;
+
+get:
+ c = getchar();
+ if (c == (uchar)EOF) {
+ if (!feof(stdin))
+ goto get;
+ exit(0);
+ }
+ return c;
+}
+
static Rune
getr(void)
{
@@ -561,7 +587,7 @@ getr(void)
r = 0;
seq = 0;
do {
- c = fgetc(stdin);
+ c = getc2();
if (c2r(&r, c, &seq) == -1) {
seq = 0;
ungetc(c, stdin);
@@ -633,7 +659,6 @@ insert(int arg)
break;
}
for (;;) {
- resize();
fr_update();
switch (c.s[0] = getr()) {
case Esc:
@@ -669,15 +694,13 @@ init(void)
{
uint i;
- win_init(&w);
for (i = 0; i < FILECOUNT; ++i) {
file_init(&file[i]);
fr_init(&frame[i]);
}
- f = &file[0];
- fr = &frame[0];
str_init(&srch);
str_init(&istr);
+ win_init(&w);
}
static void
@@ -718,7 +741,7 @@ static void
file_load(File* f)
{
FILE *disk;
- ulong i, n;
+ ulong n;
char *s;
s = NULL;
@@ -730,9 +753,8 @@ file_load(File* f)
n = 0;
do {
s = erealloc(s, n + 4096);
- i = fread(s + n, 1, 4096, disk);
- n += i;
- } while (i != 0);
+ n += fread(s + n, 1, 4096, disk);
+ } while (!feof(disk));
s[n] = '\0';
u2str(&f->s, s);
free(s);
@@ -1061,7 +1083,7 @@ pline(int arg)
}
curmov(0, h);
printf("%-4lu ", l);
- i = fgetc(stdin);
+ i = getc2();
if (i != Esc)
ungetc(i, stdin);
}
@@ -1104,19 +1126,6 @@ r2u(char *s, Rune r)
return p - s;
}
-static void
-resize(void)
-{
- Window wt;
-
- win_query(&wt);
- if (wt.wx != w.wx || wt.wy != w.wy) {
- w.wx = wt.wx;
- w.wy = wt.wy;
- fr_zero(fr);
- }
-}
-
static uint
runesiz(Rune c, ulong wx)
{
@@ -1409,7 +1418,6 @@ main(int argc, char* argv[])
file_load(f);
}
for (;;) {
- resize();
fr_update();
c = getr();
for (i = 0; i < LENGTH(keys); ++i) {
diff --git a/sim.h b/sim.h
@@ -12,9 +12,10 @@ typedef struct {
ushort t;
} Window;
-void die(char* fmt, ...);
-void* emalloc(ulong n);
-void* erealloc(void* p, ulong n);
-void win_end(void);
-void win_init(Window* w);
-void win_query(Window* w);
+extern void die(char* fmt, ...);
+extern void* emalloc(ulong n);
+extern void* erealloc(void* p, ulong n);
+extern void resize(void);
+extern void win_end(void);
+extern void win_init(Window* w);
+extern void win_query(Window* w);