1 static void client_sigwinch_handler(int sig
) {
2 client
.need_resize
= true;
5 static bool client_send_packet(Packet
*pkt
) {
6 print_packet("client-send:", pkt
);
7 if (send_packet(server
.socket
, pkt
))
10 server
.running
= false;
14 static bool client_recv_packet(Packet
*pkt
) {
15 if (recv_packet(server
.socket
, pkt
)) {
16 print_packet("client-recv:", pkt
);
19 debug("client-recv: FAILED\n");
20 server
.running
= false;
24 static void client_restore_terminal(void) {
26 tcsetattr(STDIN_FILENO
, TCSADRAIN
, &orig_term
);
27 if (alternate_buffer
) {
28 printf("\033[?1049l");
30 alternate_buffer
= false;
34 static void client_setup_terminal(void) {
35 atexit(client_restore_terminal
);
38 cur_term
.c_iflag
&= ~(IGNBRK
|BRKINT
|PARMRK
|ISTRIP
|INLCR
|IGNCR
|ICRNL
|IXON
|IXOFF
);
39 cur_term
.c_oflag
&= ~(OPOST
);
40 cur_term
.c_lflag
&= ~(ECHO
|ECHONL
|ICANON
|ISIG
|IEXTEN
);
41 cur_term
.c_cflag
&= ~(CSIZE
|PARENB
);
42 cur_term
.c_cflag
|= CS8
;
43 cur_term
.c_cc
[VLNEXT
] = _POSIX_VDISABLE
;
44 cur_term
.c_cc
[VMIN
] = 1;
45 cur_term
.c_cc
[VTIME
] = 0;
46 tcsetattr(STDIN_FILENO
, TCSADRAIN
, &cur_term
);
48 if (!alternate_buffer
) {
49 printf("\033[?1049h\033[H");
51 alternate_buffer
= true;
55 static int client_mainloop(void) {
56 sigset_t emptyset
, blockset
;
57 sigemptyset(&emptyset
);
58 sigemptyset(&blockset
);
59 sigaddset(&blockset
, SIGWINCH
);
60 sigprocmask(SIG_BLOCK
, &blockset
, NULL
);
62 client
.need_resize
= true;
65 .u
= { .b
= client
.readonly
},
66 .len
= sizeof(pkt
.u
.b
),
68 client_send_packet(&pkt
);
70 while (server
.running
) {
73 FD_SET(STDIN_FILENO
, &fds
);
74 FD_SET(server
.socket
, &fds
);
76 if (client
.need_resize
) {
78 if (ioctl(STDIN_FILENO
, TIOCGWINSZ
, &ws
) != -1) {
84 if (client_send_packet(&pkt
))
85 client
.need_resize
= false;
89 if (pselect(server
.socket
+1, &fds
, NULL
, NULL
, NULL
, &emptyset
) == -1) {
92 die("client-mainloop");
95 if (FD_ISSET(server
.socket
, &fds
)) {
97 if (client_recv_packet(&pkt
)) {
100 write_all(STDOUT_FILENO
, pkt
.u
.msg
, pkt
.len
);
103 client
.need_resize
= true;
106 client_send_packet(&pkt
);
107 close(server
.socket
);
113 if (FD_ISSET(STDIN_FILENO
, &fds
)) {
114 Packet pkt
= { .type
= MSG_CONTENT
};
115 ssize_t len
= read(STDIN_FILENO
, pkt
.u
.msg
, sizeof(pkt
.u
.msg
));
116 if (len
== -1 && errno
!= EAGAIN
&& errno
!= EINTR
)
119 debug("client-stdin: %c\n", pkt
.u
.msg
[0]);
121 if (pkt
.u
.msg
[0] == KEY_REDRAW
) {
122 client
.need_resize
= true;
123 } else if (pkt
.u
.msg
[0] == KEY_DETACH
) {
124 pkt
.type
= MSG_DETACH
;
126 client_send_packet(&pkt
);
127 close(server
.socket
);
129 } else if (!client
.readonly
) {
130 client_send_packet(&pkt
);