root/tools/perf/ui/tui/setup.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. ui__refresh_dimensions
  2. ui__sigwinch
  3. ui__setup_sigwinch
  4. ui__getch
  5. ui__signal_backtrace
  6. ui__signal
  7. ui__init
  8. ui__exit

   1 #include <errno.h>
   2 #include <signal.h>
   3 #include <stdbool.h>
   4 #include <stdlib.h>
   5 #include <unistd.h>
   6 #include <linux/kernel.h>
   7 #ifdef HAVE_BACKTRACE_SUPPORT
   8 #include <execinfo.h>
   9 #endif
  10 
  11 #include "../../util/debug.h"
  12 #include "../../perf.h"
  13 #include "../browser.h"
  14 #include "../helpline.h"
  15 #include "../ui.h"
  16 #include "../util.h"
  17 #include "../libslang.h"
  18 #include "../keysyms.h"
  19 #include "tui.h"
  20 
  21 static volatile int ui__need_resize;
  22 
  23 extern struct perf_error_ops perf_tui_eops;
  24 extern bool tui_helpline__set;
  25 
  26 extern void hist_browser__init_hpp(void);
  27 
  28 void ui__refresh_dimensions(bool force)
  29 {
  30         if (force || ui__need_resize) {
  31                 ui__need_resize = 0;
  32                 pthread_mutex_lock(&ui__lock);
  33                 SLtt_get_screen_size();
  34                 SLsmg_reinit_smg();
  35                 pthread_mutex_unlock(&ui__lock);
  36         }
  37 }
  38 
  39 static void ui__sigwinch(int sig __maybe_unused)
  40 {
  41         ui__need_resize = 1;
  42 }
  43 
  44 static void ui__setup_sigwinch(void)
  45 {
  46         static bool done;
  47 
  48         if (done)
  49                 return;
  50 
  51         done = true;
  52         pthread__unblock_sigwinch();
  53         signal(SIGWINCH, ui__sigwinch);
  54 }
  55 
  56 int ui__getch(int delay_secs)
  57 {
  58         struct timeval timeout, *ptimeout = delay_secs ? &timeout : NULL;
  59         fd_set read_set;
  60         int err, key;
  61 
  62         ui__setup_sigwinch();
  63 
  64         FD_ZERO(&read_set);
  65         FD_SET(0, &read_set);
  66 
  67         if (delay_secs) {
  68                 timeout.tv_sec = delay_secs;
  69                 timeout.tv_usec = 0;
  70         }
  71 
  72         err = select(1, &read_set, NULL, NULL, ptimeout);
  73 
  74         if (err == 0)
  75                 return K_TIMER;
  76 
  77         if (err == -1) {
  78                 if (errno == EINTR)
  79                         return K_RESIZE;
  80                 return K_ERROR;
  81         }
  82 
  83         key = SLang_getkey();
  84         if (key != K_ESC)
  85                 return key;
  86 
  87         FD_ZERO(&read_set);
  88         FD_SET(0, &read_set);
  89         timeout.tv_sec = 0;
  90         timeout.tv_usec = 20;
  91         err = select(1, &read_set, NULL, NULL, &timeout);
  92         if (err == 0)
  93                 return K_ESC;
  94 
  95         SLang_ungetkey(key);
  96         return SLkp_getkey();
  97 }
  98 
  99 #ifdef HAVE_BACKTRACE_SUPPORT
 100 static void ui__signal_backtrace(int sig)
 101 {
 102         void *stackdump[32];
 103         size_t size;
 104 
 105         ui__exit(false);
 106         psignal(sig, "perf");
 107 
 108         printf("-------- backtrace --------\n");
 109         size = backtrace(stackdump, ARRAY_SIZE(stackdump));
 110         backtrace_symbols_fd(stackdump, size, STDOUT_FILENO);
 111 
 112         exit(0);
 113 }
 114 #else
 115 # define ui__signal_backtrace  ui__signal
 116 #endif
 117 
 118 static void ui__signal(int sig)
 119 {
 120         ui__exit(false);
 121         psignal(sig, "perf");
 122         exit(0);
 123 }
 124 
 125 int ui__init(void)
 126 {
 127         int err;
 128 
 129         SLutf8_enable(-1);
 130         SLtt_get_terminfo();
 131         SLtt_get_screen_size();
 132 
 133         err = SLsmg_init_smg();
 134         if (err < 0)
 135                 goto out;
 136         err = SLang_init_tty(-1, 0, 0);
 137         if (err < 0)
 138                 goto out;
 139 
 140         err = SLkp_init();
 141         if (err < 0) {
 142                 pr_err("TUI initialization failed.\n");
 143                 goto out;
 144         }
 145 
 146         SLkp_define_keysym((char *)"^(kB)", SL_KEY_UNTAB);
 147 
 148         signal(SIGSEGV, ui__signal_backtrace);
 149         signal(SIGFPE, ui__signal_backtrace);
 150         signal(SIGINT, ui__signal);
 151         signal(SIGQUIT, ui__signal);
 152         signal(SIGTERM, ui__signal);
 153 
 154         perf_error__register(&perf_tui_eops);
 155 
 156         ui_helpline__init();
 157         ui_browser__init();
 158         tui_progress__init();
 159 
 160         hist_browser__init_hpp();
 161 out:
 162         return err;
 163 }
 164 
 165 void ui__exit(bool wait_for_ok)
 166 {
 167         if (wait_for_ok && tui_helpline__set)
 168                 ui__question_window("Fatal Error",
 169                                     ui_helpline__last_msg,
 170                                     "Press any key...", 0);
 171 
 172         SLtt_set_cursor_visibility(1);
 173         SLsmg_refresh();
 174         SLsmg_reset_smg();
 175         SLang_reset_tty();
 176 
 177         perf_error__unregister(&perf_tui_eops);
 178 }

/* [<][>][^][v][top][bottom][index][help] */