]>
Dogcows Code - chaz/openbox/blob - tools/obxprop/obxprop.c
071ae3f45ddbe492ee37adf477f796abb8f8fff8
2 #include <X11/cursorfont.h>
9 gint
fail(const gchar
*s
) {
11 fprintf(stderr
, "%s\n", s
);
15 "Usage: obxprop [OPTIONS] [--] [PROPERTIES ...]\n\n"
17 " --help Display this help and exit\n"
18 " --display DISPLAY Connect to this X display\n"
19 " --id ID Show the properties for this window\n"
20 " --root Show the properties for the root window\n");
24 gint
parse_hex(gchar
*s
) {
28 if (*s
>= '0' && *s
<='9')
30 else if (*s
>= 'A' && *s
<='F')
32 else if (*s
>= 'a' && *s
<='f')
44 Window
find_client(Display
*d
, Window win
)
48 Atom state
= XInternAtom(d
, "WM_STATE", True
);
51 gulong ret_items
, ret_bytesleft
, *xdata
;
53 XQueryTree(d
, win
, &r
, &r
, &children
, &n
);
54 for (i
= 0; i
< n
; ++i
) {
55 Window w
= find_client(d
, children
[i
]);
60 res
= XGetWindowProperty(d
, win
, state
, 0, 1,
61 False
, state
, &ret_type
, &ret_format
,
62 &ret_items
, &ret_bytesleft
,
63 (unsigned char**) &xdata
);
65 if (res
!= Success
|| ret_type
== None
|| ret_items
< 1)
67 return win
; // found it!
70 static gboolean
get_all(Display
*d
, Window win
, Atom prop
,
71 Atom
*type
, gint
*size
,
72 guchar
**data
, guint
*num
)
77 gulong ret_items
, bytes_left
;
79 res
= XGetWindowProperty(d
, win
, prop
, 0l, G_MAXLONG
,
80 FALSE
, AnyPropertyType
, type
, size
,
81 &ret_items
, &bytes_left
, &xdata
);
86 *data
= g_malloc(ret_items
* (*size
/ 8));
87 for (i
= 0; i
< ret_items
; ++i
)
90 (*data
)[i
] = xdata
[i
];
93 ((guint16
*)*data
)[i
] = ((gushort
*)xdata
)[i
];
96 ((guint32
*)*data
)[i
] = ((gulong
*)xdata
)[i
];
99 g_assert_not_reached(); /* unhandled size */
109 gchar
*append_string(gchar
*before
, gchar
*after
, gboolean quote
)
112 const gchar
*q
= quote
? "\"" : "";
114 tmp
= g_strdup_printf("%s, %s%s%s", before
, q
, after
, q
);
116 tmp
= g_strdup_printf("%s%s%s", q
, after
, q
);
121 gchar
*append_int(gchar
*before
, guint after
)
125 tmp
= g_strdup_printf("%s, %u", before
, after
);
127 tmp
= g_strdup_printf("%u", after
);
132 gchar
* read_strings(gchar
*val
, guint n
, gboolean utf8
)
134 GSList
*strs
= NULL
, *it
;
139 while (p
< val
+ n
) {
140 strs
= g_slist_append(strs
, g_strndup(p
, n
- (p
- val
)));
141 p
+= strlen(p
) + 1; /* next string */
145 for (i
= 0, it
= strs
; it
; ++i
, it
= g_slist_next(it
)) {
149 if (g_utf8_validate(it
->data
, -1, NULL
))
150 data
= g_strdup(it
->data
);
155 data
= g_locale_to_utf8(it
->data
, -1, NULL
, NULL
, NULL
);
157 ret
= append_string(ret
, data
, TRUE
);
163 strs
= g_slist_delete_link(strs
, strs
);
168 gchar
* read_atoms(Display
*d
, guchar
*val
, guint n
)
174 for (i
= 0; i
< n
; ++i
)
175 ret
= append_string(ret
, XGetAtomName(d
, ((guint32
*)val
)[i
]), FALSE
);
179 gchar
* read_numbers(guchar
*val
, guint n
, guint size
)
185 for (i
= 0; i
< n
; ++i
)
188 ret
= append_int(ret
, ((guint8
*)val
)[i
]);
191 ret
= append_int(ret
, ((guint16
*)val
)[i
]);
194 ret
= append_int(ret
, ((guint32
*)val
)[i
]);
197 g_assert_not_reached(); /* unhandled size */
203 gboolean
read_prop(Display
*d
, Window w
, Atom prop
, const gchar
**type
, gchar
**val
)
211 if (get_all(d
, w
, prop
, &ret_type
, &size
, &ret
, &nret
)) {
212 *type
= XGetAtomName(d
, ret_type
);
214 if (strcmp(*type
, "STRING") == 0)
215 *val
= read_strings((gchar
*)ret
, nret
, FALSE
);
216 else if (strcmp(*type
, "UTF8_STRING") == 0)
217 *val
= read_strings((gchar
*)ret
, nret
, TRUE
);
218 else if (strcmp(*type
, "ATOM") == 0) {
219 g_assert(size
== 32);
220 *val
= read_atoms(d
, ret
, nret
);
223 *val
= read_numbers(ret
, nret
, size
);
231 void show_properties(Display
*d
, Window w
, int argc
, char **argv
)
236 props
= XListProperties(d
, w
, &n
);
238 for (i
= 0; i
< n
; ++i
) {
242 name
= XGetAtomName(d
, props
[i
]);
244 if (read_prop(d
, w
, props
[i
], &type
, &val
)) {
250 for (i
= 0; i
< argc
; i
++)
251 if (!strcmp(name
, argv
[i
])) {
257 g_print("%s(%s) = %s\n", name
, type
, val
);
267 int main(int argc
, char **argv
)
270 Window id
, userid
= None
;
273 gboolean root
= FALSE
;
275 for (i
= 1; i
< argc
; ++i
) {
276 if (!strcmp(argv
[i
], "--help")) {
279 else if (!strcmp(argv
[i
], "--root"))
281 else if (!strcmp(argv
[i
], "--id")) {
284 if (argv
[i
][0] == '0' && argv
[i
][1] == 'x') {
286 userid
= parse_hex(argv
[i
]+2);
290 userid
= atoi(argv
[i
]);
293 return fail("Unable to parse argument to --id.");
295 else if (!strcmp(argv
[i
], "--display")) {
300 else if (*argv
[i
] != '-')
302 else if (!strcmp(argv
[i
], "--")) {
310 d
= XOpenDisplay(dname
);
312 return fail("Unable to find an X display. "
313 "Ensure you have permission to connect to the display.");
317 userid
= RootWindow(d
, DefaultScreen(d
));
319 if (userid
== None
) {
321 j
= XGrabPointer(d
, RootWindow(d
, DefaultScreen(d
)),
322 False
, ButtonPressMask
,
323 GrabModeAsync
, GrabModeAsync
,
324 None
, XCreateFontCursor(d
, XC_crosshair
),
326 if (j
!= GrabSuccess
)
327 return fail("Unable to grab the pointer device");
332 if (ev
.type
== ButtonPress
) {
333 XUngrabPointer(d
, CurrentTime
);
334 userid
= ev
.xbutton
.subwindow
;
338 id
= find_client(d
, userid
);
341 id
= userid
; /* they picked this one */
344 return fail("Unable to find window with the requested ID");
346 show_properties(d
, id
, argc
- i
, &argv
[i
]);
This page took 0.055115 seconds and 4 git commands to generate.