Annotation of src/usr.bin/tmux/control-notify.c, Revision 1.2
1.2 ! nicm 1: /* $OpenBSD: control-notify.c,v 1.1 2012/09/03 09:32:38 nicm Exp $ */
1.1 nicm 2:
3: /*
4: * Copyright (c) 2012 Nicholas Marriott <nicm@users.sourceforge.net>
5: * Copyright (c) 2012 George Nachman <tmux@georgester.com>
6: *
7: * Permission to use, copy, modify, and distribute this software for any
8: * purpose with or without fee is hereby granted, provided that the above
9: * copyright notice and this permission notice appear in all copies.
10: *
11: * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
12: * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
13: * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
14: * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
15: * WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
16: * IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
17: * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
18: */
19:
20: #include <sys/types.h>
21:
22: #include "tmux.h"
23:
24: #define CONTROL_SHOULD_NOTIFY_CLIENT(c) \
25: ((c) != NULL && ((c)->flags & CLIENT_CONTROL))
1.2 ! nicm 26:
! 27: void
! 28: control_notify_input(struct client *c, struct window_pane *wp,
! 29: struct evbuffer *input)
! 30: {
! 31: u_char *buf;
! 32: size_t len;
! 33: struct evbuffer *message;
! 34: u_int i;
! 35:
! 36: if (c->session == NULL)
! 37: return;
! 38:
! 39: buf = EVBUFFER_DATA(input);
! 40: len = EVBUFFER_LENGTH(input);
! 41:
! 42: /*
! 43: * Only write input if the window pane is linked to a window belonging
! 44: * to the client's session.
! 45: */
! 46: if (winlink_find_by_window(&c->session->windows, wp->window) != NULL) {
! 47: message = evbuffer_new();
! 48: evbuffer_add_printf(message, "%%output %%%u ", wp->id);
! 49: for (i = 0; i < len; i++)
! 50: evbuffer_add_printf(message, "%02hhx", buf[i]);
! 51: control_write_buffer(c, message);
! 52: evbuffer_free(message);
! 53: }
! 54: }
1.1 nicm 55:
56: void
57: control_notify_window_layout_changed(struct window *w)
58: {
59: struct client *c;
60: struct session *s;
61: struct format_tree *ft;
62: struct winlink *wl;
63: u_int i;
64: const char *template;
65:
66: for (i = 0; i < ARRAY_LENGTH(&clients); i++) {
67: c = ARRAY_ITEM(&clients, i);
68: if (!CONTROL_SHOULD_NOTIFY_CLIENT(c) || c->session == NULL)
69: continue;
70: s = c->session;
71:
72: if (winlink_find_by_window_id(&s->windows, w->id) == NULL)
73: continue;
74:
75: /*
76: * When the last pane in a window is closed it won't have a
77: * layout root and we don't need to inform the client about the
78: * layout change because the whole window will go away soon.
79: */
80: if (w->layout_root == NULL)
81: continue;
82: template = "%layout-change #{window_id} #{window_layout}";
83:
84: ft = format_create();
85: wl = winlink_find_by_window(&s->windows, w);
86: if (wl != NULL) {
87: format_winlink(ft, c->session, wl);
88: control_write(c, "%s", format_expand(ft, template));
89: }
90: format_free(ft);
91: }
92: }
93:
94: void
95: control_notify_window_unlinked(unused struct session *s, struct window *w)
96: {
97: struct client *c;
98: struct session *cs;
99: u_int i;
100:
101: for (i = 0; i < ARRAY_LENGTH(&clients); i++) {
102: c = ARRAY_ITEM(&clients, i);
103: if (!CONTROL_SHOULD_NOTIFY_CLIENT(c) || c->session == NULL)
104: continue;
105: cs = c->session;
106:
107: if (winlink_find_by_window_id(&cs->windows, w->id) != NULL)
108: control_write(c, "%%window-close %u", w->id);
109: else
110: control_write(c, "%%unlinked-window-close %u", w->id);
111: }
112: }
113:
114: void
115: control_notify_window_linked(unused struct session *s, struct window *w)
116: {
117: struct client *c;
118: struct session *cs;
119: u_int i;
120:
121: for (i = 0; i < ARRAY_LENGTH(&clients); i++) {
122: c = ARRAY_ITEM(&clients, i);
123: if (!CONTROL_SHOULD_NOTIFY_CLIENT(c) || c->session == NULL)
124: continue;
125: cs = c->session;
126:
127: if (winlink_find_by_window_id(&cs->windows, w->id) != NULL)
128: control_write(c, "%%window-add %u", w->id);
129: else
130: control_write(c, "%%unlinked-window-add %u", w->id);
131: }
132: }
133:
134: void
135: control_notify_window_renamed(struct window *w)
136: {
137: struct client *c;
138: struct session *s;
139: u_int i;
140:
141: for (i = 0; i < ARRAY_LENGTH(&clients); i++) {
142: c = ARRAY_ITEM(&clients, i);
143: if (!CONTROL_SHOULD_NOTIFY_CLIENT(c) || c->session == NULL)
144: continue;
145: s = c->session;
146:
147: if (winlink_find_by_window_id(&s->windows, w->id) != NULL) {
148: control_write(c, "%%window-renamed %u %s",
149: w->id, w->name);
150: } else {
151: control_write(c, "%%unlinked-window-renamed %u %s",
152: w->id, w->name);
153: }
154: }
155: }
156:
157: void
158: control_notify_attached_session_changed(struct client *c)
159: {
160: struct session *s;
161:
162: if (!CONTROL_SHOULD_NOTIFY_CLIENT(c) || c->session == NULL)
163: return;
164: s = c->session;
165:
166: control_write(c, "%%session-changed %d %s", s->idx, s->name);
167: }
168:
169: void
170: control_notify_session_renamed(struct session *s)
171: {
172: struct client *c;
173: u_int i;
174:
175: for (i = 0; i < ARRAY_LENGTH(&clients); i++) {
176: c = ARRAY_ITEM(&clients, i);
177: if (!CONTROL_SHOULD_NOTIFY_CLIENT(c) || c->session != s)
178: continue;
179:
180: control_write(c, "%%session-renamed %s", s->name);
181: }
182: }
183:
184: void
185: control_notify_session_created(unused struct session *s)
186: {
187: struct client *c;
188: u_int i;
189:
190: for (i = 0; i < ARRAY_LENGTH(&clients); i++) {
191: c = ARRAY_ITEM(&clients, i);
192: if (!CONTROL_SHOULD_NOTIFY_CLIENT(c) || c->session == NULL)
193: continue;
194:
195: control_write(c, "%%sessions-changed");
196: }
197: }
198:
199: void
200: control_notify_session_close(unused struct session *s)
201: {
202: struct client *c;
203: u_int i;
204:
205: for (i = 0; i < ARRAY_LENGTH(&clients); i++) {
206: c = ARRAY_ITEM(&clients, i);
207: if (!CONTROL_SHOULD_NOTIFY_CLIENT(c) || c->session == NULL)
208: continue;
209:
210: control_write(c, "%%sessions-changed");
211: }
212: }