ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/root-tail/root-tail.c
(Generate patch)

Comparing root-tail/root-tail.c (file contents):
Revision 1.63 by chris_moore, Thu Apr 15 00:38:13 2004 UTC vs.
Revision 1.65 by root, Sun Jun 16 01:24:29 2019 UTC

39#include <ctype.h> 39#include <ctype.h>
40#include <stdarg.h> 40#include <stdarg.h>
41#include <X11/Xlib.h> 41#include <X11/Xlib.h>
42#include <X11/Xatom.h> 42#include <X11/Xatom.h>
43#include <X11/Xutil.h> 43#include <X11/Xutil.h>
44#include <X11/extensions/shape.h>
45#include <X11/extensions/Xfixes.h>
44 46
45#if HAS_REGEX 47#if HAS_REGEX
46#include <regex.h> 48#include <regex.h>
47#endif 49#endif
48 50
105 int buffer_size; 107 int buffer_size;
106 unsigned long color; 108 unsigned long color;
107}; 109};
108 110
109/* global variables */ 111/* global variables */
110struct line_node *linelist = NULL, *linelist_tail = NULL; 112static struct line_node *linelist = NULL, *linelist_tail = NULL;
111struct displaymatrix *display; 113static struct displaymatrix *display;
112int continuation_width = -1; 114static int continuation_width = -1;
113int continuation_color; 115static int continuation_color;
114int continuation_length; 116static int continuation_length;
115 117
116/* HACK - ideally listlen will start at however many '~'s will fit on 118/* HACK - ideally listlen will start at however many '~'s will fit on
117 * the screen */ 119 * the screen */
118int width = STD_WIDTH, height = STD_HEIGHT, listlen = 50; 120static unsigned int width = STD_WIDTH, height = STD_HEIGHT;
121static int listlen = 50;
119int win_x = LOC_X, win_y = LOC_Y; 122static int win_x = LOC_X, win_y = LOC_Y;
120int effect_x_space, effect_y_space; /* how much space does shading / outlining take up */ 123static int effect_x_space, effect_y_space; /* how much space does shading / outlining take up */
121int effect_x_offset, effect_y_offset; /* and how does it offset the usable space */ 124static int effect_x_offset, effect_y_offset; /* and how does it offset the usable space */
122int do_reopen; 125static int do_reopen;
123struct timeval interval = { 2, 400000 }; 126static struct timeval interval = { 2, 400000 };
124 127
125/* command line options */ 128/* command line options */
126int opt_noinitial, opt_shade, opt_frame, opt_reverse, opt_nofilename, 129static int opt_noinitial, opt_shade, opt_frame, opt_reverse, opt_nofilename,
127 opt_outline, opt_noflicker, opt_whole, opt_update, opt_wordwrap, 130 opt_outline, opt_noflicker, opt_whole, opt_update, opt_wordwrap,
128 opt_justify, geom_mask, opt_minspace, reload; 131 opt_justify, geom_mask, opt_minspace, opt_windowed, reload;
129const char *command = NULL, 132static const char *command = NULL,
130 *fontname = USE_FONT, *dispname = NULL, *def_color = DEF_COLOR, 133 *fontname = USE_FONT, *dispname = NULL, *def_color = DEF_COLOR,
131 *continuation = "|| ", *cont_color = DEF_CONT_COLOR; 134 *continuation = "|| ", *cont_color = DEF_CONT_COLOR;
132 135
133struct logfile_entry *loglist = NULL, *loglist_tail = NULL; 136struct logfile_entry *loglist = NULL, *loglist_tail = NULL;
134 137
135Display *disp; 138static Display *disp;
136Window root; 139static Window root;
137GC WinGC; 140static GC WinGC;
138 141
139#if HAS_REGEX 142#if HAS_REGEX
140struct re_list 143struct re_list
141{ 144{
142 regex_t from; 145 regex_t from;
143 const char *to; 146 const char *to;
144 struct re_list *next; 147 struct re_list *next;
145}; 148};
146struct re_list *re_head, *re_tail; 149static struct re_list *re_head, *re_tail;
147char *transform_to = NULL; 150static char *transform_to = NULL;
148regex_t *transformre; 151static regex_t *transformre;
149#endif 152#endif
150 153
151 154
152/* prototypes */ 155/* prototypes */
153void list_files (int); 156static void list_files (int);
154void force_reopen (int); 157static void force_reopen (int);
155void force_refresh (int); 158static void force_refresh (int);
156void blank_window (int); 159static void blank_window (int);
157#ifdef USE_TOON_GET_ROOT_WINDOW 160#ifdef USE_TOON_GET_ROOT_WINDOW
158Window ToonGetRootWindow(Display *, int, Window *); 161static Window ToonGetRootWindow(Display *, int, Window *);
159#endif /* USE_TOON_GET_ROOT_WINDOW */ 162#endif /* USE_TOON_GET_ROOT_WINDOW */
160 163
161void InitWindow (void); 164static void InitWindow (void);
162unsigned long GetColor (const char *); 165static unsigned long GetColor (const char *);
163void redraw (int); 166static void redraw (int);
164void refresh (int, int, int, int); 167static void refresh (int, int, int, int);
165 168
166void transform_line (char *s);
167int lineinput (struct logfile_entry *); 169static int lineinput (struct logfile_entry *);
168void reopen (void); 170static void reopen (void);
169void check_open_files (void); 171static void check_open_files (void);
170FILE *openlog (struct logfile_entry *); 172static FILE *openlog (struct logfile_entry *);
171static void main_loop (void); 173static void main_loop (void);
172 174
173void display_version (void); 175static void display_version (void);
174void display_help (char *); 176static void display_help (char *);
175void install_signal (int, void (*)(int)); 177static void install_signal (int, void (*)(int));
176void *xstrdup (const char *); 178static void *xstrdup (const char *);
177void *xmalloc (size_t); 179static void *xmalloc (size_t);
178void *xrealloc (void *, size_t); 180static void *xrealloc (void *, size_t);
179int daemonize (void); 181static int daemonize (void);
180 182
181/* signal handlers */ 183/* signal handlers */
182void 184static void
183list_files (int dummy) 185list_files (int dummy)
184{ 186{
185 struct logfile_entry *e; 187 struct logfile_entry *e;
186 188
187 fprintf (stderr, "Files opened:\n"); 189 fprintf (stderr, "Files opened:\n");
188 for (e = loglist; e; e = e->next) 190 for (e = loglist; e; e = e->next)
189 fprintf (stderr, "\t%s (%s)\n", e->fname, e->desc); 191 fprintf (stderr, "\t%s (%s)\n", e->fname, e->desc);
190} 192}
191 193
192void 194static void
193force_reopen (int dummy) 195force_reopen (int dummy)
194{ 196{
195 do_reopen = 1; 197 do_reopen = 1;
196} 198}
197 199
198void 200static void
199force_refresh (int dummy) 201force_refresh (int dummy)
200{ 202{
201 redraw (1); 203 redraw (1);
202} 204}
203 205
204void 206static void
205blank_window (int dummy) 207blank_window (int dummy)
206{ 208{
207 XClearArea (disp, root, win_x, win_y, width + MARGIN_OF_ERROR, height, False); 209 XClearArea (disp, root, win_x, win_y, width + MARGIN_OF_ERROR, height, False);
208 XFlush (disp); 210 XFlush (disp);
209 exit (0); 211 exit (0);
210} 212}
211 213
212/* X related functions */ 214/* X related functions */
213unsigned long 215static unsigned long
214GetColor (const char *ColorName) 216GetColor (const char *ColorName)
215{ 217{
216 XColor Color; 218 XColor Color;
217 XWindowAttributes Attributes; 219 XWindowAttributes Attributes;
218 220
233{ 235{
234 if (!root) 236 if (!root)
235 { 237 {
236 Atom SWM_VROOT = XInternAtom (display, "__SWM_VROOT", False); 238 Atom SWM_VROOT = XInternAtom (display, "__SWM_VROOT", False);
237 Atom NAUTILUS_DESKTOP_WINDOW_ID = XInternAtom (display, "NAUTILUS_DESKTOP_WINDOW_ID", False); 239 Atom NAUTILUS_DESKTOP_WINDOW_ID = XInternAtom (display, "NAUTILUS_DESKTOP_WINDOW_ID", False);
238 root = RootWindow (display, screen_number);
239 240
240 Window unused, *windows = 0; 241 Window unused, *windows = 0;
241 unsigned int count; 242 unsigned int count;
242 243
243 Atom type; 244 Atom type;
244 int format; 245 int format;
245 unsigned long nitems, bytes_after_return; 246 unsigned long nitems, bytes_after_return;
246 unsigned char *virtual_root_window; 247 unsigned char *virtual_root_window;
248
249 root = RootWindow (display, screen_number);
247 250
248 if (XGetWindowProperty (display, root, NAUTILUS_DESKTOP_WINDOW_ID, 251 if (XGetWindowProperty (display, root, NAUTILUS_DESKTOP_WINDOW_ID,
249 0, 1, False, XA_WINDOW, &type, &format, 252 0, 1, False, XA_WINDOW, &type, &format,
250 &nitems, &bytes_after_return, 253 &nitems, &bytes_after_return,
251 &virtual_root_window) == Success 254 &virtual_root_window) == Success
280 fprintf (stderr, "Can't query tree on root window 0x%lx", root); 283 fprintf (stderr, "Can't query tree on root window 0x%lx", root);
281 } 284 }
282} 285}
283#endif /* USE_TOON_GET_ROOT_WINDOW */ 286#endif /* USE_TOON_GET_ROOT_WINDOW */
284 287
285void 288static void
286InitWindow (void) 289InitWindow (void)
287{ 290{
288 XGCValues gcv; 291 XGCValues gcv;
289 unsigned long gcm; 292 unsigned long gcm;
290 int screen, ScreenWidth, ScreenHeight; 293 int screen, ScreenWidth, ScreenHeight;
298 301
299 screen = DefaultScreen (disp); 302 screen = DefaultScreen (disp);
300 ScreenHeight = DisplayHeight (disp, screen); 303 ScreenHeight = DisplayHeight (disp, screen);
301 ScreenWidth = DisplayWidth (disp, screen); 304 ScreenWidth = DisplayWidth (disp, screen);
302 305
306 if (opt_windowed)
307 {
308 XRectangle rect = { };
309 XSetWindowAttributes attr;
310
311 attr.background_pixmap = ParentRelative;
312 attr.override_redirect = True;
313
314 root = XCreateWindow (
315 disp, DefaultRootWindow (disp), 0, 0, DisplayWidth (disp, screen), DisplayHeight (disp, screen),
316 0, CopyFromParent, InputOutput, CopyFromParent,
317 CWOverrideRedirect | CWBackPixmap, &attr);
318
319 XMapWindow (disp, root);
320 XLowerWindow (disp, root);
321
322 XserverRegion region = XFixesCreateRegion (disp, &rect, 1);
323 XFixesSetWindowShapeRegion (disp, root, ShapeInput, 0, 0, region);
324 XFixesDestroyRegion (disp, region);
325 }
326 else
303 find_root_window (disp, screen); 327 find_root_window (disp, screen);
304 328
305 gcm = GCBackground; 329 gcm = GCBackground;
306 gcv.graphics_exposures = True; 330 gcv.graphics_exposures = True;
307 WinGC = XCreateGC (disp, root, gcm, &gcv); 331 WinGC = XCreateGC (disp, root, gcm, &gcv);
308 XMapWindow (disp, root); 332 XMapWindow (disp, root);
316 char *def_string; 340 char *def_string;
317 341
318 e->fontset = XCreateFontSet (disp, e->fontname, 342 e->fontset = XCreateFontSet (disp, e->fontname,
319 &missing_charset_list, &missing_charset_count, 343 &missing_charset_list, &missing_charset_count,
320 &def_string); 344 &def_string);
321
322 if (missing_charset_count) 345 if (missing_charset_count)
323 { 346 {
347#if 0
324 fprintf (stderr, 348 fprintf (stderr,
325 "Missing charsets in String to FontSet conversion (%s)\n", 349 "Missing charsets in String to FontSet conversion (%s)\n",
326 missing_charset_list[0]); 350 missing_charset_list[0]);
351#endif
327 XFreeStringList (missing_charset_list); 352 XFreeStringList (missing_charset_list);
328 } 353 }
329 354
330 if (!e->fontset) 355 if (!e->fontset)
331 { 356 {
375 * -noflicker is in effect) then only the lines which have changed 400 * -noflicker is in effect) then only the lines which have changed
376 * since the last draw are redrawn. 401 * since the last draw are redrawn.
377 * 402 *
378 * the rest is handled by regular refresh ()'es 403 * the rest is handled by regular refresh ()'es
379 */ 404 */
380void 405static void
381redraw (int redraw_all) 406redraw (int redraw_all)
382{ 407{
383 XSetClipMask (disp, WinGC, None); 408 XSetClipMask (disp, WinGC, None);
384 refresh (0, 32768, 1, redraw_all); 409 refresh (0, 32768, 1, redraw_all);
385} 410}
386 411
412static void
387void draw_text (Display *disp, Window root, GC WinGC, int x, int y, struct line_node *line, int foreground) 413draw_text (Display *disp, Window root, GC WinGC, int x, int y, struct line_node *line, int foreground)
388{ 414{
389 if (line->wrapped_right && opt_justify && line->breaks) 415 if (line->wrapped_right && opt_justify && line->breaks)
390 { 416 {
391 int i; 417 int i;
392 for (i = 0; i < line->num_words; i++) 418 for (i = 0; i < line->num_words; i++)
414 } 440 }
415 } 441 }
416} 442}
417 443
418/* Just redraw everything without clearing (i.e. after an EXPOSE event) */ 444/* Just redraw everything without clearing (i.e. after an EXPOSE event) */
419void 445static void
420refresh (int miny, int maxy, int clear, int refresh_all) 446refresh (int miny, int maxy, int clear, int refresh_all)
421{ 447{
422 int lin = 0; 448 int lin = 0;
423 int space = height; 449 int space = height;
424 int offset; 450 int offset;
592 XDrawRectangle (disp, root, WinGC, win_x - 0, win_y - 0, width - 1, height - 1); 618 XDrawRectangle (disp, root, WinGC, win_x - 0, win_y - 0, width - 1, height - 1);
593 } 619 }
594} 620}
595 621
596#if HAS_REGEX 622#if HAS_REGEX
597void 623void void
598transform_line (char *s) 624transform_line (char *s)
599{ 625{
600#ifdef I_AM_Md 626#ifdef I_AM_Md
601 int i; 627 int i;
602 if (1) 628 if (1)
647 673
648/* 674/*
649 * appends p2 to the end of p1, if p1 is not null 675 * appends p2 to the end of p1, if p1 is not null
650 * otherwise allocates a new string and copies p2 to it 676 * otherwise allocates a new string and copies p2 to it
651 */ 677 */
652char * 678static char *
653concat_line (char *p1, const char *p2) 679concat_line (char *p1, const char *p2)
654{ 680{
655 int l1 = p1 ? strlen (p1) : 0; 681 int l1 = p1 ? strlen (p1) : 0;
656 int l2 = strlen (p2); 682 int l2 = strlen (p2);
657 char *r; 683 char *r;
670} 696}
671 697
672/* 698/*
673 * This routine can read a line of any length if it is called enough times. 699 * This routine can read a line of any length if it is called enough times.
674 */ 700 */
675int 701static int
676lineinput (struct logfile_entry *logfile) 702lineinput (struct logfile_entry *logfile)
677{ 703{
678 char buff[1024], *p; 704 char buff[1024], *p;
679 int ch; 705 int ch;
680 /* HACK-2: add on the length of any partial line which we will be appending to */ 706 /* HACK-2: add on the length of any partial line which we will be appending to */
739/* input: reads file->fname 765/* input: reads file->fname
740 * output: fills file->fp, file->inode 766 * output: fills file->fp, file->inode
741 * returns file->fp 767 * returns file->fp
742 * in case of error, file->fp is NULL 768 * in case of error, file->fp is NULL
743 */ 769 */
744FILE * 770static FILE *
745openlog (struct logfile_entry * file) 771openlog (struct logfile_entry *file)
746{ 772{
747 struct stat stats; 773 struct stat stats;
748 774
749 if ((file->fp = fopen (file->fname, "r")) == NULL) 775 if ((file->fp = fopen (file->fname, "r")) == NULL)
750 { 776 {
771 797
772 file->last_size = stats.st_size; 798 file->last_size = stats.st_size;
773 return file->fp; 799 return file->fp;
774} 800}
775 801
776void 802static void
777reopen (void) 803reopen (void)
778{ 804{
779 struct logfile_entry *e; 805 struct logfile_entry *e;
780 806
781 for (e = loglist; e; e = e->next) 807 for (e = loglist; e; e = e->next)
790 } 816 }
791 817
792 do_reopen = 0; 818 do_reopen = 0;
793} 819}
794 820
795void 821static void
796check_open_files (void) 822check_open_files (void)
797{ 823{
798 struct logfile_entry *e; 824 struct logfile_entry *e;
799 struct stat stats; 825 struct stat stats;
800 826
1270 region = XCreateRegion (); 1296 region = XCreateRegion ();
1271 } 1297 }
1272 } 1298 }
1273} 1299}
1274 1300
1275
1276int 1301int
1277main (int argc, char *argv[]) 1302main (int argc, char *argv[])
1278{ 1303{
1279 int i; 1304 int i;
1280 int opt_daemonize = 0; 1305 int opt_daemonize = 0;
1323 else if (!strcmp (arg, "-reload")) 1348 else if (!strcmp (arg, "-reload"))
1324 { 1349 {
1325 reload = atoi (argv[++i]); 1350 reload = atoi (argv[++i]);
1326 command = argv[++i]; 1351 command = argv[++i];
1327 } 1352 }
1353 else if (!strcmp (arg, "-windowed"))
1354 opt_windowed = 1;
1328 else if (!strcmp (arg, "-shade")) 1355 else if (!strcmp (arg, "-shade"))
1329 opt_shade = 1; 1356 opt_shade = 1;
1330 else if (!strcmp (arg, "-outline")) 1357 else if (!strcmp (arg, "-outline"))
1331 opt_outline = 1; 1358 opt_outline = 1;
1332 else if (!strcmp (arg, "-minspace")) 1359 else if (!strcmp (arg, "-minspace"))
1536 main_loop (); 1563 main_loop ();
1537 1564
1538 exit (1); /* to make gcc -Wall stop complaining */ 1565 exit (1); /* to make gcc -Wall stop complaining */
1539} 1566}
1540 1567
1541void 1568static void
1542install_signal (int sig, void (*handler) (int)) 1569install_signal (int sig, void (*handler) (int))
1543{ 1570{
1544 struct sigaction action; 1571 struct sigaction action;
1545 1572
1546 action.sa_handler = handler; 1573 action.sa_handler = handler;
1549 1576
1550 if (sigaction (sig, &action, NULL) < 0) 1577 if (sigaction (sig, &action, NULL) < 0)
1551 fprintf (stderr, "sigaction (%d): %s\n", sig, strerror (errno)), exit (1); 1578 fprintf (stderr, "sigaction (%d): %s\n", sig, strerror (errno)), exit (1);
1552} 1579}
1553 1580
1554void * 1581static void *
1555xstrdup (const char *string) 1582xstrdup (const char *string)
1556{ 1583{
1557 void *p; 1584 void *p;
1558 1585
1559 while ((p = strdup (string)) == NULL) 1586 while ((p = strdup (string)) == NULL)
1563 } 1590 }
1564 1591
1565 return p; 1592 return p;
1566} 1593}
1567 1594
1568void * 1595static void *
1569xmalloc (size_t size) 1596xmalloc (size_t size)
1570{ 1597{
1571 void *p; 1598 void *p;
1572 1599
1573 while ((p = malloc (size)) == NULL) 1600 while ((p = malloc (size)) == NULL)
1577 } 1604 }
1578 1605
1579 return p; 1606 return p;
1580} 1607}
1581 1608
1582void * 1609static void *
1583xrealloc (void *ptr, size_t size) 1610xrealloc (void *ptr, size_t size)
1584{ 1611{
1585 void *p; 1612 void *p;
1586 1613
1587 while ((p = realloc (ptr, size)) == NULL) 1614 while ((p = realloc (ptr, size)) == NULL)
1591 } 1618 }
1592 1619
1593 return p; 1620 return p;
1594} 1621}
1595 1622
1596void 1623static void
1597display_help (char *myname) 1624display_help (char *myname)
1598{ 1625{
1599 printf ("Usage: %s [options] file1[,color[,desc]]" 1626 printf ("Usage: %s [options] file1[,color[,desc]]"
1600 "[options] [file2[,color[,desc]] ...]\n", myname); 1627 "[options] [file2[,color[,desc]] ...]\n", myname);
1601 printf (" -g | -geometry geometry -g WIDTHxHEIGHT+X+Y\n" 1628 printf (" -g | -geometry geometry -g WIDTHxHEIGHT+X+Y\n"
1602 " -color color use color $color as default\n" 1629 " -color color use color $color as default\n"
1603 " -reload sec command reload after $sec and run command\n" 1630 " -reload sec command reload after $sec and run command\n"
1604 " -id id window id to use instead of the root window\n" 1631 " -id id window id to use instead of the root window\n"
1632 " -windowed create a window instead of writing to the root\n"
1605 " -font FONTSPEC (-fn) font to use\n" 1633 " -font FONTSPEC (-fn) font to use\n"
1606 " -f | -fork fork into background\n" 1634 " -f | -fork fork into background\n"
1607 " -reverse print new lines at the top\n" 1635 " -reverse print new lines at the top\n"
1608 " -whole wait for \\n before showing a line\n" 1636 " -whole wait for \\n before showing a line\n"
1609 " -partial show lines even if they don't end with a \\n\n" 1637 " -partial show lines even if they don't end with a \\n\n"
1623 printf ("Example:\n%s -g 800x250+100+50 -font fixed /var/log/messages,green " 1651 printf ("Example:\n%s -g 800x250+100+50 -font fixed /var/log/messages,green "
1624 "/var/log/secure,red,'ALERT'\n", myname); 1652 "/var/log/secure,red,'ALERT'\n", myname);
1625 exit (0); 1653 exit (0);
1626} 1654}
1627 1655
1628void 1656static void
1629display_version (void) 1657display_version (void)
1630{ 1658{
1631 printf ("root-tail version " VERSION "\n"); 1659 printf ("root-tail version " VERSION "\n");
1632 exit (0); 1660 exit (0);
1633} 1661}
1634 1662
1635int 1663static int
1636daemonize (void) 1664daemonize (void)
1637{ 1665{
1638 pid_t pid; 1666 pid_t pid;
1639 1667
1640 switch (pid = fork ()) 1668 switch (pid = fork ())
1651 if (setsid () == -1) 1679 if (setsid () == -1)
1652 return -1; 1680 return -1;
1653 1681
1654 return 0; 1682 return 0;
1655} 1683}
1684

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines