aboutsummaryrefslogtreecommitdiffstats
path: root/swaybar/status_line.c
diff options
context:
space:
mode:
authorLibravatar Ian Fan <ianfan0@gmail.com>2018-09-17 13:43:27 +0100
committerLibravatar Ian Fan <ianfan0@gmail.com>2018-09-18 11:36:33 +0100
commit70245c2cd5c34586fa91eb784e58471869ba66bd (patch)
treec1a0f34b5b8815ab0fee61c37aff707e756f60b3 /swaybar/status_line.c
parentswaybar: only create i3bar block hotspot if click events are enabled (diff)
downloadsway-70245c2cd5c34586fa91eb784e58471869ba66bd.tar.gz
sway-70245c2cd5c34586fa91eb784e58471869ba66bd.tar.zst
sway-70245c2cd5c34586fa91eb784e58471869ba66bd.zip
swaybar: rewrite text protocol handling
This now uses getline to correctly handle multiple or long statuses. It also removes the struct text_protocol_state and moves its members into the status_line struct.
Diffstat (limited to 'swaybar/status_line.c')
-rw-r--r--swaybar/status_line.c40
1 files changed, 24 insertions, 16 deletions
diff --git a/swaybar/status_line.c b/swaybar/status_line.c
index 09ed2375..54a68b40 100644
--- a/swaybar/status_line.c
+++ b/swaybar/status_line.c
@@ -30,27 +30,17 @@ void status_error(struct status_line *status, const char *text) {
30} 30}
31 31
32bool status_handle_readable(struct status_line *status) { 32bool status_handle_readable(struct status_line *status) {
33 ssize_t read_bytes = 1;
33 char *line; 34 char *line;
34 switch (status->protocol) { 35 switch (status->protocol) {
35 case PROTOCOL_ERROR:
36 return false;
37 case PROTOCOL_I3BAR: 36 case PROTOCOL_I3BAR:
38 if (i3bar_handle_readable(status) > 0) { 37 if (i3bar_handle_readable(status) > 0) {
39 return true; 38 return true;
40 } 39 }
41 break; 40 break;
42 case PROTOCOL_TEXT:
43 line = read_line_buffer(status->read,
44 status->text_state.buffer, status->text_state.buffer_size);
45 if (!line) {
46 status_error(status, "[error reading from status command]");
47 } else {
48 status->text = line;
49 }
50 return true;
51 case PROTOCOL_UNDEF: 41 case PROTOCOL_UNDEF:
52 line = read_line_buffer(status->read, 42 line = read_line_buffer(status->read,
53 status->text_state.buffer, status->text_state.buffer_size); 43 status->buffer, status->buffer_size);
54 if (!line) { 44 if (!line) {
55 status_error(status, "[error reading from status command]"); 45 status_error(status, "[error reading from status command]");
56 return false; 46 return false;
@@ -81,7 +71,7 @@ bool status_handle_readable(struct status_line *status) {
81 } 71 }
82 72
83 status->protocol = PROTOCOL_I3BAR; 73 status->protocol = PROTOCOL_I3BAR;
84 free(status->text_state.buffer); 74 free(status->buffer);
85 wl_list_init(&status->blocks); 75 wl_list_init(&status->blocks);
86 status->i3bar_state.buffer_size = 4096; 76 status->i3bar_state.buffer_size = 4096;
87 status->i3bar_state.buffer = 77 status->i3bar_state.buffer =
@@ -91,14 +81,32 @@ bool status_handle_readable(struct status_line *status) {
91 status->text = line; 81 status->text = line;
92 } 82 }
93 return true; 83 return true;
84 case PROTOCOL_TEXT:
85 errno = 0;
86 while (true) {
87 if (status->buffer[read_bytes - 1] == '\n') {
88 status->buffer[read_bytes - 1] = '\0';
89 }
90 read_bytes = getline(&status->buffer,
91 &status->buffer_size, status->read);
92 if (errno == EAGAIN) {
93 clearerr(status->read);
94 return true;
95 } else if (errno) {
96 status_error(status, "[error reading from status command]");
97 return true;
98 }
99 }
100 default:
101 return false;
94 } 102 }
95 return false; 103 return false;
96} 104}
97 105
98struct status_line *status_line_init(char *cmd) { 106struct status_line *status_line_init(char *cmd) {
99 struct status_line *status = calloc(1, sizeof(struct status_line)); 107 struct status_line *status = calloc(1, sizeof(struct status_line));
100 status->text_state.buffer_size = 8192; 108 status->buffer_size = 8192;
101 status->text_state.buffer = malloc(status->text_state.buffer_size); 109 status->buffer = malloc(status->buffer_size);
102 110
103 int pipe_read_fd[2]; 111 int pipe_read_fd[2];
104 int pipe_write_fd[2]; 112 int pipe_write_fd[2];
@@ -148,7 +156,7 @@ void status_line_free(struct status_line *status) {
148 break; 156 break;
149 } 157 }
150 default: 158 default:
151 free(status->text_state.buffer); 159 free(status->buffer);
152 break; 160 break;
153 } 161 }
154 free(status); 162 free(status);