diff options
Diffstat (limited to 'swaybar/status_line.c')
-rw-r--r-- | swaybar/status_line.c | 64 |
1 files changed, 33 insertions, 31 deletions
diff --git a/swaybar/status_line.c b/swaybar/status_line.c index 54a68b40..fcc0cb93 100644 --- a/swaybar/status_line.c +++ b/swaybar/status_line.c | |||
@@ -31,7 +31,6 @@ void status_error(struct status_line *status, const char *text) { | |||
31 | 31 | ||
32 | bool status_handle_readable(struct status_line *status) { | 32 | bool status_handle_readable(struct status_line *status) { |
33 | ssize_t read_bytes = 1; | 33 | ssize_t read_bytes = 1; |
34 | char *line; | ||
35 | switch (status->protocol) { | 34 | switch (status->protocol) { |
36 | case PROTOCOL_I3BAR: | 35 | case PROTOCOL_I3BAR: |
37 | if (i3bar_handle_readable(status) > 0) { | 36 | if (i3bar_handle_readable(status) > 0) { |
@@ -39,36 +38,37 @@ bool status_handle_readable(struct status_line *status) { | |||
39 | } | 38 | } |
40 | break; | 39 | break; |
41 | case PROTOCOL_UNDEF: | 40 | case PROTOCOL_UNDEF: |
42 | line = read_line_buffer(status->read, | 41 | errno = 0; |
43 | status->buffer, status->buffer_size); | 42 | read_bytes = getline(&status->buffer, |
44 | if (!line) { | 43 | &status->buffer_size, status->read); |
44 | if (errno == EAGAIN) { | ||
45 | clearerr(status->read); | ||
46 | } else if (errno) { | ||
45 | status_error(status, "[error reading from status command]"); | 47 | status_error(status, "[error reading from status command]"); |
46 | return false; | 48 | return true; |
47 | } | 49 | } |
48 | if (line[0] == '{') { | 50 | |
49 | json_object *proto = json_tokener_parse(line); | 51 | // the header must be sent completely the first time round |
50 | if (proto) { | 52 | json_object *header, *version; |
51 | json_object *version; | 53 | if (status->buffer[read_bytes - 1] == '\n' |
52 | if (json_object_object_get_ex(proto, "version", &version) | 54 | && (header = json_tokener_parse(status->buffer)) |
53 | && json_object_get_int(version) == 1) { | 55 | && json_object_object_get_ex(header, "version", &version) |
54 | wlr_log(WLR_DEBUG, "Switched to i3bar protocol."); | 56 | && json_object_get_int(version) == 1) { |
55 | status->protocol = PROTOCOL_I3BAR; | 57 | wlr_log(WLR_DEBUG, "Using i3bar protocol."); |
56 | } | 58 | status->protocol = PROTOCOL_I3BAR; |
57 | json_object *click_events; | 59 | |
58 | if (json_object_object_get_ex( | 60 | json_object *click_events; |
59 | proto, "click_events", &click_events) | 61 | if (json_object_object_get_ex(header, "click_events", &click_events) |
60 | && json_object_get_boolean(click_events)) { | 62 | && json_object_get_boolean(click_events)) { |
61 | wlr_log(WLR_DEBUG, "Enabled click events."); | 63 | wlr_log(WLR_DEBUG, "Enabling click events."); |
62 | status->i3bar_state.click_events = true; | 64 | status->i3bar_state.click_events = true; |
63 | const char *events_array = "[\n"; | 65 | if (write(status->write_fd, "[\n", 2) != 2) { |
64 | ssize_t len = strlen(events_array); | 66 | status_error(status, "[failed to write to status command]"); |
65 | if (write(status->write_fd, events_array, len) != len) { | 67 | json_object_put(header); |
66 | status_error(status, | 68 | return true; |
67 | "[failed to write to status command]"); | ||
68 | } | ||
69 | } | 69 | } |
70 | json_object_put(proto); | ||
71 | } | 70 | } |
71 | json_object_put(header); | ||
72 | 72 | ||
73 | status->protocol = PROTOCOL_I3BAR; | 73 | status->protocol = PROTOCOL_I3BAR; |
74 | free(status->buffer); | 74 | free(status->buffer); |
@@ -76,11 +76,13 @@ bool status_handle_readable(struct status_line *status) { | |||
76 | status->i3bar_state.buffer_size = 4096; | 76 | status->i3bar_state.buffer_size = 4096; |
77 | status->i3bar_state.buffer = | 77 | status->i3bar_state.buffer = |
78 | malloc(status->i3bar_state.buffer_size); | 78 | malloc(status->i3bar_state.buffer_size); |
79 | } else { | 79 | return false; |
80 | status->protocol = PROTOCOL_TEXT; | ||
81 | status->text = line; | ||
82 | } | 80 | } |
83 | return true; | 81 | |
82 | wlr_log(WLR_DEBUG, "Using text protocol."); | ||
83 | status->protocol = PROTOCOL_TEXT; | ||
84 | status->text = status->buffer; | ||
85 | // intentional fall-through | ||
84 | case PROTOCOL_TEXT: | 86 | case PROTOCOL_TEXT: |
85 | errno = 0; | 87 | errno = 0; |
86 | while (true) { | 88 | while (true) { |