2006-12-06 17:25:32 -06:00
|
|
|
/* setterm.c, set terminal attributes.
|
|
|
|
*
|
|
|
|
* Copyright (C) 1990 Gordon Irlam (gordoni@cs.ua.oz.au). Conditions of use,
|
|
|
|
* modification, and redistribution are contained in the file COPYRIGHT that
|
|
|
|
* forms part of this distribution.
|
|
|
|
*
|
|
|
|
* Adaption to Linux by Peter MacDonald.
|
|
|
|
*
|
|
|
|
* Enhancements by Mika Liljeberg (liljeber@cs.Helsinki.FI)
|
|
|
|
*
|
2006-12-06 17:25:34 -06:00
|
|
|
* Beep modifications by Christophe Jolif (cjolif@storm.gatelink.fr.net)
|
|
|
|
*
|
|
|
|
* Sanity increases by Cafeine Addict [sic].
|
|
|
|
*
|
2006-12-06 17:25:41 -06:00
|
|
|
* Powersave features by todd j. derr <tjd@wordsmith.org>
|
2006-12-06 17:25:34 -06:00
|
|
|
*
|
|
|
|
* Converted to terminfo by Kars de Jong (jongk@cs.utwente.nl)
|
2006-12-06 17:25:32 -06:00
|
|
|
*
|
2013-01-26 10:07:51 -06:00
|
|
|
* 1999-02-22 Arkadiusz Miśkiewicz <misiek@pld.ORG.PL>
|
2006-12-06 17:25:39 -06:00
|
|
|
* - added Native Language Support
|
|
|
|
*
|
2006-12-06 17:25:32 -06:00
|
|
|
* Semantics:
|
|
|
|
*
|
2006-12-06 17:25:34 -06:00
|
|
|
* Setterm writes to standard output a character string that will
|
2012-05-29 12:06:50 -05:00
|
|
|
* invoke the specified terminal capabilities. Where possible
|
2006-12-06 17:25:34 -06:00
|
|
|
* terminfo is consulted to find the string to use. Some options
|
|
|
|
* however do not correspond to a terminfo capability. In this case if
|
|
|
|
* the terminal type is "con*", or "linux*" the string that invokes
|
|
|
|
* the specified capabilities on the PC Linux virtual console driver
|
|
|
|
* is output. Options that are not implemented by the terminal are
|
|
|
|
* ignored.
|
2006-12-06 17:25:32 -06:00
|
|
|
*
|
|
|
|
* The following options are non-obvious.
|
|
|
|
*
|
|
|
|
* -term can be used to override the TERM environment variable.
|
|
|
|
*
|
|
|
|
* -reset displays the terminal reset string, which typically resets the
|
|
|
|
* terminal to its power on state.
|
|
|
|
*
|
|
|
|
* -initialize displays the terminal initialization string, which typically
|
|
|
|
* sets the terminal's rendering options, and other attributes to the
|
|
|
|
* default values.
|
|
|
|
*
|
|
|
|
* -default sets the terminal's rendering options to the default values.
|
|
|
|
*
|
|
|
|
* -store stores the terminal's current rendering options as the default
|
2006-12-06 17:25:34 -06:00
|
|
|
* values. */
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2014-05-11 16:52:09 -05:00
|
|
|
#include <ctype.h>
|
|
|
|
#include <errno.h>
|
|
|
|
#include <fcntl.h>
|
2014-05-17 12:52:01 -05:00
|
|
|
#include <getopt.h>
|
2006-12-06 17:25:32 -06:00
|
|
|
#include <stdio.h>
|
2006-12-06 17:25:43 -06:00
|
|
|
#include <stdlib.h>
|
2006-12-06 17:25:32 -06:00
|
|
|
#include <string.h>
|
2014-05-11 16:52:09 -05:00
|
|
|
#include <sys/ioctl.h>
|
|
|
|
#include <sys/klog.h>
|
|
|
|
#include <sys/param.h> /* for MAXPATHLEN */
|
|
|
|
#include <sys/time.h>
|
|
|
|
#include <termios.h>
|
|
|
|
#include <unistd.h>
|
2013-09-28 23:44:36 -05:00
|
|
|
|
2006-12-06 17:25:37 -06:00
|
|
|
#ifndef NCURSES_CONST
|
2014-05-11 16:52:09 -05:00
|
|
|
# define NCURSES_CONST const /* define before including term.h */
|
2006-12-06 17:25:37 -06:00
|
|
|
#endif
|
2006-12-06 17:26:54 -06:00
|
|
|
#ifdef HAVE_NCURSES_H
|
2014-05-11 16:52:09 -05:00
|
|
|
# include <ncurses.h>
|
2009-10-15 18:40:58 -05:00
|
|
|
#elif defined(HAVE_NCURSES_NCURSES_H)
|
2014-05-11 16:52:09 -05:00
|
|
|
# include <ncurses/ncurses.h>
|
2006-12-06 17:25:34 -06:00
|
|
|
#endif
|
2013-09-28 23:44:36 -05:00
|
|
|
/* must include after ncurses.h */
|
|
|
|
#include <term.h>
|
2006-12-06 17:26:54 -06:00
|
|
|
|
2007-11-27 16:54:35 -06:00
|
|
|
#ifdef HAVE_LINUX_TIOCL_H
|
2014-05-11 16:52:09 -05:00
|
|
|
# include <linux/tiocl.h>
|
2007-11-27 16:54:35 -06:00
|
|
|
#endif
|
2009-10-15 18:40:58 -05:00
|
|
|
|
|
|
|
#include "c.h"
|
2012-04-04 12:44:04 -05:00
|
|
|
#include "closestream.h"
|
2014-05-11 16:52:09 -05:00
|
|
|
#include "nls.h"
|
2014-05-17 13:21:34 -05:00
|
|
|
#include "strutils.h"
|
2014-05-11 16:52:09 -05:00
|
|
|
#include "xalloc.h"
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:34 -06:00
|
|
|
/* Constants. */
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2011-04-02 15:56:52 -05:00
|
|
|
/* Non-standard return values. */
|
|
|
|
#define EXIT_DUMPFILE -1
|
|
|
|
|
2006-12-06 17:25:32 -06:00
|
|
|
/* Colors. */
|
2014-05-11 14:26:48 -05:00
|
|
|
enum {
|
|
|
|
BLACK = 0,
|
|
|
|
RED,
|
|
|
|
GREEN,
|
|
|
|
YELLOW,
|
|
|
|
BLUE,
|
|
|
|
MAGENTA,
|
|
|
|
CYAN,
|
|
|
|
WHITE,
|
|
|
|
GREY,
|
|
|
|
DEFAULT
|
|
|
|
};
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2007-11-27 16:54:35 -06:00
|
|
|
/* Blank commands */
|
2014-05-11 14:26:48 -05:00
|
|
|
enum {
|
|
|
|
BLANKSCREEN = -1,
|
|
|
|
UNBLANKSCREEN = -2,
|
|
|
|
BLANKEDSCREEN = -3
|
|
|
|
};
|
2007-11-27 16:54:35 -06:00
|
|
|
|
|
|
|
/* <linux/tiocl.h> fallback */
|
|
|
|
#ifndef TIOCL_BLANKSCREEN
|
2014-05-11 14:26:48 -05:00
|
|
|
enum {
|
|
|
|
TIOCL_UNBLANKSCREEN = 4, /* unblank screen */
|
|
|
|
TIOCL_SETVESABLANK = 10, /* set vesa blanking mode */
|
|
|
|
TIOCL_BLANKSCREEN = 14, /* keep screen blank even if a key is pressed */
|
|
|
|
TIOCL_BLANKEDSCREEN = 15 /* return which vt was blanked */
|
|
|
|
};
|
2007-11-27 16:54:35 -06:00
|
|
|
#endif
|
|
|
|
|
2014-05-11 14:26:49 -05:00
|
|
|
/* Powersave modes */
|
|
|
|
enum {
|
|
|
|
VESA_BLANK_MODE_OFF = 0,
|
|
|
|
VESA_BLANK_MODE_SUSPENDV,
|
|
|
|
VESA_BLANK_MODE_SUSPENDH,
|
|
|
|
VESA_BLANK_MODE_POWERDOWN
|
|
|
|
};
|
|
|
|
|
|
|
|
/* klogctl() actions */
|
|
|
|
enum {
|
|
|
|
SYSLOG_ACTION_CONSOLE_OFF = 6,
|
|
|
|
SYSLOG_ACTION_CONSOLE_ON = 7,
|
|
|
|
SYSLOG_ACTION_CONSOLE_LEVEL = 8
|
|
|
|
};
|
|
|
|
|
|
|
|
/* Console log levels */
|
|
|
|
enum {
|
|
|
|
CONSOLE_LEVEL_MIN = 1,
|
|
|
|
CONSOLE_LEVEL_MAX = 8
|
|
|
|
};
|
|
|
|
|
|
|
|
/* Various numbers */
|
|
|
|
#define DEFAULT_TAB_LEN 8
|
|
|
|
#define BLANK_MAX 60
|
|
|
|
#define TABS_MAX 160
|
|
|
|
#define BLENGTH_MAX 2000
|
|
|
|
|
2006-12-06 17:25:32 -06:00
|
|
|
/* Option flags. Set if the option is to be invoked. */
|
2006-12-06 17:25:41 -06:00
|
|
|
int opt_term, opt_reset, opt_initialize, opt_cursor;
|
2014-05-11 14:26:46 -05:00
|
|
|
int opt_linewrap, opt_default, opt_foreground;
|
2006-12-06 17:25:32 -06:00
|
|
|
int opt_background, opt_bold, opt_blink, opt_reverse, opt_underline;
|
2014-05-11 14:26:46 -05:00
|
|
|
int opt_store, opt_clear, opt_blank, opt_snap, opt_snapfile;
|
2006-12-06 17:25:32 -06:00
|
|
|
int opt_append, opt_ulcolor, opt_hbcolor, opt_halfbright, opt_repeat;
|
|
|
|
int opt_tabs, opt_clrtabs, opt_regtabs, opt_appcursorkeys, opt_inversescreen;
|
2006-12-06 17:25:34 -06:00
|
|
|
int opt_msg, opt_msglevel, opt_powersave, opt_powerdown;
|
|
|
|
int opt_blength, opt_bfreq;
|
2006-12-06 17:25:32 -06:00
|
|
|
|
|
|
|
/* Option controls. The variable names have been contracted to ensure
|
|
|
|
* uniqueness.
|
|
|
|
*/
|
|
|
|
char *opt_te_terminal_name; /* Terminal name. */
|
2014-05-11 14:26:46 -05:00
|
|
|
int opt_cu_on, opt_li_on, opt_bo_on, opt_hb_on, opt_bl_on;
|
2006-12-06 17:25:32 -06:00
|
|
|
int opt_re_on, opt_un_on, opt_rep_on, opt_appck_on, opt_invsc_on;
|
2006-12-06 17:25:34 -06:00
|
|
|
int opt_msg_on; /* Boolean switches. */
|
2006-12-06 17:25:32 -06:00
|
|
|
int opt_fo_color, opt_ba_color; /* Colors. */
|
|
|
|
int opt_ul_color, opt_hb_color;
|
|
|
|
int opt_cl_all; /* Clear all or rest. */
|
|
|
|
int opt_bl_min; /* Blank screen. */
|
2006-12-06 17:25:34 -06:00
|
|
|
int opt_blength_l;
|
|
|
|
int opt_bfreq_f;
|
2006-12-06 17:26:08 -06:00
|
|
|
int opt_sn_num; /* Snap screen. */
|
2006-12-06 17:25:32 -06:00
|
|
|
int opt_rt_len; /* regular tab length */
|
2014-05-11 14:26:49 -05:00
|
|
|
int opt_tb_array[TABS_MAX + 1]; /* Array for tab list */
|
2006-12-06 17:25:32 -06:00
|
|
|
int opt_msglevel_num;
|
2006-12-06 17:25:34 -06:00
|
|
|
int opt_ps_mode, opt_pd_min; /* powersave mode/powerdown time */
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
char opt_sn_name[PATH_MAX] = "screen.dump";
|
2006-12-06 17:25:32 -06:00
|
|
|
|
|
|
|
/* Command line parsing routines.
|
|
|
|
*
|
|
|
|
* Note that it is an error for a given option to be invoked more than once.
|
|
|
|
*/
|
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
static int parse_switch(const char *arg, const char *t, const char *f)
|
|
|
|
{
|
|
|
|
if (strcmp(arg, t) == 0)
|
|
|
|
return 1;
|
|
|
|
else if (strcmp(arg, f) == 0)
|
|
|
|
return 0;
|
|
|
|
errx(EXIT_FAILURE, _("argument error: %s"), arg);
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
static int parse_febg_color(const char *arg)
|
|
|
|
{
|
2014-05-17 13:21:34 -05:00
|
|
|
int color;
|
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
if (strcmp(arg, "black") == 0)
|
|
|
|
return BLACK;
|
|
|
|
else if (strcmp(arg, "red") == 0)
|
|
|
|
return RED;
|
|
|
|
else if (strcmp(arg, "green") == 0)
|
|
|
|
return GREEN;
|
|
|
|
else if (strcmp(arg, "yellow") == 0)
|
|
|
|
return YELLOW;
|
|
|
|
else if (strcmp(arg, "blue") == 0)
|
|
|
|
return BLUE;
|
|
|
|
else if (strcmp(arg, "magenta") == 0)
|
|
|
|
return MAGENTA;
|
|
|
|
else if (strcmp(arg, "cyan") == 0)
|
|
|
|
return CYAN;
|
|
|
|
else if (strcmp(arg, "white") == 0)
|
|
|
|
return WHITE;
|
|
|
|
else if (strcmp(arg, "default") == 0)
|
|
|
|
return DEFAULT;
|
2014-05-17 13:21:34 -05:00
|
|
|
else
|
|
|
|
color = strtos32_or_err(arg, _("argument error"));
|
|
|
|
if (color < BLACK || DEFAULT < color || color == GREY)
|
|
|
|
errx(EXIT_FAILURE, _("argument error: %s"), arg);
|
|
|
|
return color;
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
static int parse_ulhb_color(char **argv, int *optind)
|
|
|
|
{
|
|
|
|
char *color_name;
|
|
|
|
int bright = 0;
|
|
|
|
int color = -1;
|
|
|
|
|
|
|
|
if (argv[*optind] && strcmp(argv[*optind - 1], "bright") == 0) {
|
|
|
|
bright = 1;
|
|
|
|
color_name = argv[*optind];
|
|
|
|
(*optind)++;
|
|
|
|
} else
|
|
|
|
color_name = argv[*optind - 1];
|
|
|
|
|
|
|
|
if (strcmp(color_name, "black") == 0)
|
|
|
|
color = BLACK;
|
|
|
|
else if (strcmp(color_name, "grey") == 0)
|
|
|
|
color = GREY;
|
|
|
|
else if (strcmp(color_name, "red") == 0)
|
|
|
|
color = RED;
|
|
|
|
else if (strcmp(color_name, "green") == 0)
|
|
|
|
color = GREEN;
|
|
|
|
else if (strcmp(color_name, "yellow") == 0)
|
|
|
|
color = YELLOW;
|
|
|
|
else if (strcmp(color_name, "blue") == 0)
|
|
|
|
color = BLUE;
|
|
|
|
else if (strcmp(color_name, "magenta") == 0)
|
|
|
|
color = MAGENTA;
|
|
|
|
else if (strcmp(color_name, "cyan") == 0)
|
|
|
|
color = CYAN;
|
|
|
|
else if (strcmp(color_name, "white") == 0)
|
|
|
|
color = WHITE;
|
2014-05-17 13:21:34 -05:00
|
|
|
else {
|
|
|
|
color = strtos32_or_err(color_name, _("argument error"));
|
|
|
|
if (color < BLACK || DEFAULT < color)
|
|
|
|
errx(EXIT_FAILURE, _("argument error"));
|
|
|
|
}
|
2014-05-17 12:52:01 -05:00
|
|
|
if (bright && (color == BLACK || color == GREY))
|
|
|
|
errx(EXIT_FAILURE, _("argument error: bright %s is not supported"), color_name);
|
|
|
|
|
|
|
|
return color;
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
static char *find_optional_arg(char **argv, char *optarg, int *optind)
|
|
|
|
{
|
|
|
|
char *arg;
|
|
|
|
if (optarg)
|
|
|
|
return optarg;
|
|
|
|
else {
|
|
|
|
arg = argv[*optind];
|
|
|
|
if (!arg || arg[0] == '-')
|
|
|
|
return NULL;
|
2006-12-06 17:25:43 -06:00
|
|
|
}
|
2014-05-17 12:52:01 -05:00
|
|
|
(*optind)++;
|
|
|
|
return arg;
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
static int parse_blank(char **argv, char *optarg, int *optind)
|
|
|
|
{
|
|
|
|
char *arg;
|
|
|
|
|
|
|
|
arg = find_optional_arg(argv, optarg, optind);
|
|
|
|
if (!arg)
|
|
|
|
return BLANKEDSCREEN;
|
|
|
|
if (!strcmp(arg, "force"))
|
|
|
|
return BLANKSCREEN;
|
|
|
|
else if (!strcmp(arg, "poke"))
|
|
|
|
return UNBLANKSCREEN;
|
|
|
|
else {
|
2014-05-17 13:21:34 -05:00
|
|
|
int ret;
|
2014-05-17 12:52:01 -05:00
|
|
|
|
2014-05-17 13:21:34 -05:00
|
|
|
ret = strtos32_or_err(arg, _("argument error"));
|
2014-05-17 12:52:01 -05:00
|
|
|
if (ret < 0 || BLANK_MAX < ret)
|
|
|
|
errx(EXIT_FAILURE, _("argument error: %s"), arg);
|
|
|
|
return ret;
|
2006-12-06 17:25:43 -06:00
|
|
|
}
|
2014-05-17 12:52:01 -05:00
|
|
|
/* should be impossible to reach */
|
|
|
|
abort();
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
static int parse_powersave(const char *arg)
|
|
|
|
{
|
|
|
|
if (strcmp(arg, "on") == 0)
|
|
|
|
return VESA_BLANK_MODE_SUSPENDV;
|
|
|
|
else if (strcmp(arg, "vsync") == 0)
|
|
|
|
return VESA_BLANK_MODE_SUSPENDV;
|
|
|
|
else if (strcmp(arg, "hsync") == 0)
|
|
|
|
return VESA_BLANK_MODE_SUSPENDH;
|
|
|
|
else if (strcmp(arg, "powerdown") == 0)
|
|
|
|
return VESA_BLANK_MODE_POWERDOWN;
|
|
|
|
else if (strcmp(arg, "off") == 0)
|
|
|
|
return VESA_BLANK_MODE_OFF;
|
|
|
|
errx(EXIT_FAILURE, _("argument error: %s"), arg);
|
2006-12-06 17:25:34 -06:00
|
|
|
}
|
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
static int parse_msglevel(const char *arg)
|
|
|
|
{
|
2014-05-17 13:21:34 -05:00
|
|
|
int ret;
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2014-05-17 13:21:34 -05:00
|
|
|
ret = strtos32_or_err(arg, _("argument error"));
|
2014-05-17 12:52:01 -05:00
|
|
|
if (ret < CONSOLE_LEVEL_MIN || CONSOLE_LEVEL_MAX < ret)
|
|
|
|
errx(EXIT_FAILURE, _("argument error: %s"), arg);
|
|
|
|
return ret;
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
static int parse_snap(char **argv, char *optarg, int *optind)
|
|
|
|
{
|
2014-05-17 13:21:34 -05:00
|
|
|
int ret;
|
2014-05-17 12:52:01 -05:00
|
|
|
char *arg;
|
|
|
|
|
|
|
|
arg = find_optional_arg(argv, optarg, optind);
|
|
|
|
if (!arg)
|
|
|
|
return 0;
|
2014-05-17 13:21:34 -05:00
|
|
|
ret = strtos32_or_err(arg, _("argument error"));
|
2014-05-17 12:52:01 -05:00
|
|
|
if (ret < 1)
|
|
|
|
errx(EXIT_FAILURE, _("argument error: %s"), arg);
|
|
|
|
return ret;
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
static void parse_tabs(char **argv, char *optarg, int *optind, int *tab_array)
|
|
|
|
{
|
|
|
|
int i = 0;
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
if (optarg) {
|
2014-05-17 13:21:34 -05:00
|
|
|
tab_array[i] = strtos32_or_err(optarg, _("argument error"));
|
2014-05-17 12:52:01 -05:00
|
|
|
i++;
|
2006-12-06 17:25:43 -06:00
|
|
|
}
|
2014-05-17 12:52:01 -05:00
|
|
|
while (argv[*optind]) {
|
|
|
|
if (TABS_MAX < i)
|
|
|
|
errx(EXIT_FAILURE, _("too many tabs"));
|
|
|
|
if (argv[*optind][0] == '-')
|
|
|
|
break;
|
2014-05-17 13:21:34 -05:00
|
|
|
tab_array[i] = strtos32_or_err(argv[*optind], _("argument error"));
|
2014-05-17 12:52:01 -05:00
|
|
|
(*optind)++;
|
|
|
|
i++;
|
2006-12-06 17:25:43 -06:00
|
|
|
}
|
2014-05-17 12:52:01 -05:00
|
|
|
tab_array[i] = -1;
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
static int parse_regtabs(char **argv, char *optarg, int *optind)
|
|
|
|
{
|
|
|
|
int ret;
|
|
|
|
char *arg;
|
|
|
|
|
|
|
|
arg = find_optional_arg(argv, optarg, optind);
|
|
|
|
if (!arg)
|
|
|
|
return DEFAULT_TAB_LEN;
|
2014-05-17 13:21:34 -05:00
|
|
|
ret = strtos32_or_err(arg, _("argument error"));
|
2014-05-17 12:52:01 -05:00
|
|
|
if (ret < 1 || TABS_MAX < ret)
|
|
|
|
errx(EXIT_FAILURE, _("argument error: %s"), arg);
|
|
|
|
return ret;
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
static int parse_blength(char **argv, char *optarg, int *optind)
|
|
|
|
{
|
|
|
|
int ret = -1;
|
|
|
|
char *arg;
|
|
|
|
|
|
|
|
arg = find_optional_arg(argv, optarg, optind);
|
|
|
|
if (!arg)
|
|
|
|
return 0;
|
2014-05-17 13:21:34 -05:00
|
|
|
ret = strtos32_or_err(arg, _("argument error"));
|
2014-05-17 12:52:01 -05:00
|
|
|
if (ret < 0 || BLENGTH_MAX < ret)
|
|
|
|
errx(EXIT_FAILURE, _("argument error: %s"), arg);
|
|
|
|
return ret;
|
2006-12-06 17:25:34 -06:00
|
|
|
}
|
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
static int parse_bfreq(char **argv, char *optarg, int *optind)
|
|
|
|
{
|
|
|
|
char *arg;
|
|
|
|
|
|
|
|
arg = find_optional_arg(argv, optarg, optind);
|
|
|
|
if (!arg)
|
|
|
|
return 0;
|
2014-05-17 13:21:34 -05:00
|
|
|
return strtos32_or_err(arg, _("argument error"));
|
2006-12-06 17:25:34 -06:00
|
|
|
}
|
|
|
|
|
2011-04-02 15:56:51 -05:00
|
|
|
static void __attribute__ ((__noreturn__))
|
|
|
|
usage(FILE *out) {
|
|
|
|
/* Print error message about arguments, and the command's syntax. */
|
|
|
|
|
|
|
|
if (out == stderr)
|
|
|
|
warnx(_("Argument error."));
|
|
|
|
|
2011-08-16 06:50:29 -05:00
|
|
|
fputs(_("\nUsage:\n"), out);
|
|
|
|
fprintf(out,
|
|
|
|
_(" %s [options]\n"), program_invocation_short_name);
|
|
|
|
|
|
|
|
fputs(_("\nOptions:\n"), out);
|
2014-05-19 16:21:14 -05:00
|
|
|
fputs(_(" --term <terminal_name>\n"), out);
|
|
|
|
fputs(_(" --reset\n"), out);
|
|
|
|
fputs(_(" --initialize\n"), out);
|
|
|
|
fputs(_(" --cursor <on|off>\n"), out);
|
|
|
|
fputs(_(" --repeat <on|off>\n"), out);
|
|
|
|
fputs(_(" --appcursorkeys <on|off>\n"), out);
|
|
|
|
fputs(_(" --linewrap <on|off>\n"), out);
|
|
|
|
fputs(_(" --default\n"), out);
|
|
|
|
fputs(_(" --foreground <default|black|blue|cyan|green|magenta|red|white|yellow>\n"), out);
|
|
|
|
fputs(_(" --background <default|black|blue|cyan|green|magenta|red|white|yellow>\n"), out);
|
|
|
|
fputs(_(" --ulcolor <black|blue|bright|cyan|green|grey|magenta|red|white|yellow>\n"), out);
|
|
|
|
fputs(_(" --ulcolor <black|blue|bright|cyan|green|grey|magenta|red|white|yellow>\n"), out);
|
|
|
|
fputs(_(" --hbcolor <black|blue|bright|cyan|green|grey|magenta|red|white|yellow>\n"), out);
|
|
|
|
fputs(_(" --hbcolor <black|blue|bright|cyan|green|grey|magenta|red|white|yellow>\n"), out);
|
|
|
|
fputs(_(" --inversescreen <on|off>\n"), out);
|
|
|
|
fputs(_(" --bold <on|off>\n"), out);
|
|
|
|
fputs(_(" --half-bright <on|off>\n"), out);
|
|
|
|
fputs(_(" --blink <on|off>\n"), out);
|
|
|
|
fputs(_(" --reverse <on|off>\n"), out);
|
|
|
|
fputs(_(" --underline <on|off>\n"), out);
|
|
|
|
fputs(_(" --store\n"), out);
|
|
|
|
fputs(_(" --clear <all|rest>\n"), out);
|
|
|
|
fputs(_(" --tabs <tab1 tab2 tab3 ...> (tabn = 1-160)\n"), out);
|
|
|
|
fputs(_(" --clrtabs <tab1 tab2 tab3 ...> (tabn = 1-160)\n"), out);
|
|
|
|
fputs(_(" --regtabs <1-160>\n"), out);
|
|
|
|
fputs(_(" --blank <0-60|force|poke>\n"), out);
|
|
|
|
fputs(_(" --dump <1-NR_CONSOLES>\n"), out);
|
|
|
|
fputs(_(" --append <1-NR_CONSOLES>\n"), out);
|
|
|
|
fputs(_(" --file dumpfilename\n"), out);
|
|
|
|
fputs(_(" --msg <on|off>\n"), out);
|
|
|
|
fputs(_(" --msglevel <0-8>\n"), out); /* FIXME: klogctl console_log range is 1-8 */
|
|
|
|
fputs(_(" --powersave <on|vsync|hsync|powerdown|off>\n"), out);
|
|
|
|
fputs(_(" --powerdown <0-60>\n"), out);
|
|
|
|
fputs(_(" --blength <0-2000>\n"), out);
|
|
|
|
fputs(_(" --bfreq freqnumber\n"), out);
|
|
|
|
fputs(_(" --version\n"), out);
|
|
|
|
fputs(_(" --help\n"), out);
|
2011-04-02 15:56:51 -05:00
|
|
|
|
2012-03-15 17:06:39 -05:00
|
|
|
fprintf(out, USAGE_MAN_TAIL("setterm(1)"));
|
2011-04-02 15:56:51 -05:00
|
|
|
|
|
|
|
exit(out == stderr ? EXIT_FAILURE : EXIT_SUCCESS);
|
|
|
|
}
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
static void set_opt_flag(int *opt)
|
|
|
|
{
|
|
|
|
if (*opt)
|
|
|
|
errx(EXIT_FAILURE, _("duplicate use of an option"));
|
|
|
|
*opt = 1;
|
|
|
|
}
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2014-05-17 12:52:01 -05:00
|
|
|
static void parse_option(int argc, char **argv)
|
|
|
|
{
|
|
|
|
int c;
|
|
|
|
enum {
|
|
|
|
OPT_TERM = CHAR_MAX + 1,
|
|
|
|
OPT_RESET,
|
|
|
|
OPT_INITIALIZE,
|
|
|
|
OPT_CURSOR,
|
|
|
|
OPT_REPEAT,
|
|
|
|
OPT_APPCURSORKEYS,
|
|
|
|
OPT_LINEWRAP,
|
|
|
|
OPT_DEFAULT,
|
|
|
|
OPT_FOREGROUND,
|
|
|
|
OPT_BACKGROUND,
|
|
|
|
OPT_ULCOLOR,
|
|
|
|
OPT_HBCOLOR,
|
|
|
|
OPT_INVERSESCREEN,
|
|
|
|
OPT_BOLD,
|
|
|
|
OPT_HALF_BRIGHT,
|
|
|
|
OPT_BLINK,
|
|
|
|
OPT_REVERSE,
|
|
|
|
OPT_UNDERLINE,
|
|
|
|
OPT_STORE,
|
|
|
|
OPT_CLEAR,
|
|
|
|
OPT_TABS,
|
|
|
|
OPT_CLRTABS,
|
|
|
|
OPT_REGTABS,
|
|
|
|
OPT_BLANK,
|
|
|
|
OPT_DUMP,
|
|
|
|
OPT_APPEND,
|
|
|
|
OPT_FILE,
|
|
|
|
OPT_MSG,
|
|
|
|
OPT_MSGLEVEL,
|
|
|
|
OPT_POWERSAVE,
|
|
|
|
OPT_POWERDOWN,
|
|
|
|
OPT_BLENGTH,
|
|
|
|
OPT_BFREQ,
|
|
|
|
OPT_VERSION,
|
|
|
|
OPT_HELP
|
|
|
|
};
|
|
|
|
static const struct option longopts[] = {
|
|
|
|
{"term", required_argument, NULL, OPT_TERM},
|
|
|
|
{"reset", no_argument, NULL, OPT_RESET},
|
|
|
|
{"initialize", no_argument, NULL, OPT_INITIALIZE},
|
|
|
|
{"cursor", required_argument, NULL, OPT_CURSOR},
|
|
|
|
{"repeat", required_argument, NULL, OPT_REPEAT},
|
|
|
|
{"appcursorkeys", required_argument, NULL, OPT_APPCURSORKEYS},
|
|
|
|
{"linewrap", required_argument, NULL, OPT_LINEWRAP},
|
|
|
|
{"default", no_argument, NULL, OPT_DEFAULT},
|
|
|
|
{"foreground", required_argument, NULL, OPT_FOREGROUND},
|
|
|
|
{"background", required_argument, NULL, OPT_BACKGROUND},
|
|
|
|
{"ulcolor", required_argument, NULL, OPT_ULCOLOR},
|
|
|
|
{"ulcolor", required_argument, NULL, OPT_ULCOLOR},
|
|
|
|
{"hbcolor", required_argument, NULL, OPT_HBCOLOR},
|
|
|
|
{"hbcolor", required_argument, NULL, OPT_HBCOLOR},
|
|
|
|
{"inversescreen", required_argument, NULL, OPT_INVERSESCREEN},
|
|
|
|
{"bold", required_argument, NULL, OPT_BOLD},
|
|
|
|
{"half-bright", required_argument, NULL, OPT_HALF_BRIGHT},
|
|
|
|
{"blink", required_argument, NULL, OPT_BLINK},
|
|
|
|
{"reverse", required_argument, NULL, OPT_REVERSE},
|
|
|
|
{"underline", required_argument, NULL, OPT_UNDERLINE},
|
|
|
|
{"store", no_argument, NULL, OPT_STORE},
|
|
|
|
{"clear", required_argument, NULL, OPT_CLEAR},
|
|
|
|
{"tabs", optional_argument, NULL, OPT_TABS},
|
|
|
|
{"clrtabs", optional_argument, NULL, OPT_CLRTABS},
|
|
|
|
{"regtabs", optional_argument, NULL, OPT_REGTABS},
|
|
|
|
{"blank", optional_argument, NULL, OPT_BLANK},
|
|
|
|
{"dump", optional_argument, NULL, OPT_DUMP},
|
|
|
|
{"append", required_argument, NULL, OPT_APPEND},
|
|
|
|
{"file", required_argument, NULL, OPT_FILE},
|
|
|
|
{"msg", required_argument, NULL, OPT_MSG},
|
|
|
|
{"msglevel", required_argument, NULL, OPT_MSGLEVEL},
|
|
|
|
{"powersave", required_argument, NULL, OPT_POWERSAVE},
|
|
|
|
{"powerdown", optional_argument, NULL, OPT_POWERDOWN},
|
|
|
|
{"blength", optional_argument, NULL, OPT_BLENGTH},
|
|
|
|
{"bfreq", optional_argument, NULL, OPT_BFREQ},
|
|
|
|
{"version", no_argument, NULL, OPT_VERSION},
|
|
|
|
{"help", no_argument, NULL, OPT_HELP},
|
|
|
|
{NULL, 0, NULL, 0}
|
|
|
|
};
|
|
|
|
|
|
|
|
while ((c = getopt_long_only(argc, argv, "", longopts, NULL)) != -1) {
|
|
|
|
switch (c) {
|
|
|
|
case OPT_TERM:
|
|
|
|
set_opt_flag(&opt_term);
|
|
|
|
opt_te_terminal_name = optarg;
|
|
|
|
break;
|
|
|
|
case OPT_RESET:
|
|
|
|
set_opt_flag(&opt_reset);
|
|
|
|
break;
|
|
|
|
case OPT_INITIALIZE:
|
|
|
|
set_opt_flag(&opt_initialize);
|
|
|
|
break;
|
|
|
|
case OPT_CURSOR:
|
|
|
|
set_opt_flag(&opt_cursor);
|
|
|
|
opt_cu_on = parse_switch(optarg, "on", "off");
|
|
|
|
break;
|
|
|
|
case OPT_REPEAT:
|
|
|
|
set_opt_flag(&opt_repeat);
|
|
|
|
opt_rep_on = parse_switch(optarg, "on", "off");
|
|
|
|
break;
|
|
|
|
case OPT_APPCURSORKEYS:
|
|
|
|
set_opt_flag(&opt_appcursorkeys);
|
|
|
|
opt_appck_on = parse_switch(optarg, "on", "off");
|
|
|
|
break;
|
|
|
|
case OPT_LINEWRAP:
|
|
|
|
set_opt_flag(&opt_linewrap);
|
|
|
|
opt_li_on = parse_switch(optarg, "on", "off");
|
|
|
|
break;
|
|
|
|
case OPT_DEFAULT:
|
|
|
|
set_opt_flag(&opt_default);
|
|
|
|
break;
|
|
|
|
case OPT_FOREGROUND:
|
|
|
|
set_opt_flag(&opt_foreground);
|
|
|
|
opt_fo_color = parse_febg_color(optarg);
|
|
|
|
break;
|
|
|
|
case OPT_BACKGROUND:
|
|
|
|
set_opt_flag(&opt_background);
|
|
|
|
opt_ba_color = parse_febg_color(optarg);
|
|
|
|
break;
|
|
|
|
case OPT_ULCOLOR:
|
|
|
|
set_opt_flag(&opt_ulcolor);
|
|
|
|
opt_ul_color = parse_ulhb_color(argv, &optind);
|
|
|
|
break;
|
|
|
|
case OPT_HBCOLOR:
|
|
|
|
set_opt_flag(&opt_hbcolor);
|
|
|
|
opt_hb_color = parse_ulhb_color(argv, &optind);
|
|
|
|
break;
|
|
|
|
case OPT_INVERSESCREEN:
|
|
|
|
set_opt_flag(&opt_inversescreen);
|
|
|
|
opt_invsc_on = parse_switch(optarg, "on", "off");
|
|
|
|
break;
|
|
|
|
case OPT_BOLD:
|
|
|
|
set_opt_flag(&opt_bold);
|
|
|
|
opt_bo_on = parse_switch(optarg, "on", "off");
|
|
|
|
break;
|
|
|
|
case OPT_HALF_BRIGHT:
|
|
|
|
set_opt_flag(&opt_halfbright);
|
|
|
|
opt_hb_on = parse_switch(optarg, "on", "off");
|
|
|
|
break;
|
|
|
|
case OPT_BLINK:
|
|
|
|
set_opt_flag(&opt_blink);
|
|
|
|
opt_bl_on = parse_switch(optarg, "on", "off");
|
|
|
|
break;
|
|
|
|
case OPT_REVERSE:
|
|
|
|
set_opt_flag(&opt_reverse);
|
|
|
|
opt_re_on = parse_switch(optarg, "on", "off");
|
|
|
|
break;
|
|
|
|
case OPT_UNDERLINE:
|
|
|
|
set_opt_flag(&opt_underline);
|
|
|
|
opt_un_on = parse_switch(optarg, "on", "off");
|
|
|
|
break;
|
|
|
|
case OPT_STORE:
|
|
|
|
set_opt_flag(&opt_store);
|
|
|
|
break;
|
|
|
|
case OPT_CLEAR:
|
|
|
|
set_opt_flag(&opt_clear);
|
|
|
|
opt_cl_all = parse_switch(optarg, "all", "reset");
|
|
|
|
break;
|
|
|
|
case OPT_TABS:
|
|
|
|
set_opt_flag(&opt_tabs);
|
|
|
|
parse_tabs(argv, optarg, &optind, opt_tb_array);
|
|
|
|
break;
|
|
|
|
case OPT_CLRTABS:
|
|
|
|
set_opt_flag(&opt_clrtabs);
|
|
|
|
parse_tabs(argv, optarg, &optind, opt_tb_array);
|
|
|
|
break;
|
|
|
|
case OPT_REGTABS:
|
|
|
|
set_opt_flag(&opt_regtabs);
|
|
|
|
opt_rt_len = parse_regtabs(argv, optarg, &optind);
|
|
|
|
break;
|
|
|
|
case OPT_BLANK:
|
|
|
|
set_opt_flag(&opt_blank);
|
|
|
|
opt_bl_min = parse_blank(argv, optarg, &optind);
|
|
|
|
break;
|
|
|
|
case OPT_DUMP:
|
|
|
|
set_opt_flag(&opt_snap);
|
|
|
|
opt_sn_num = parse_snap(argv, optarg, &optind);
|
|
|
|
break;
|
|
|
|
case OPT_APPEND:
|
|
|
|
set_opt_flag(&opt_append);
|
|
|
|
opt_sn_num = parse_snap(argv, optarg, &optind);
|
|
|
|
break;
|
|
|
|
case OPT_FILE:
|
|
|
|
set_opt_flag(&opt_snapfile);
|
2014-05-17 13:21:34 -05:00
|
|
|
xstrncpy(opt_sn_name, optarg, PATH_MAX);
|
2014-05-17 12:52:01 -05:00
|
|
|
break;
|
|
|
|
case OPT_MSG:
|
|
|
|
set_opt_flag(&opt_msg);
|
|
|
|
opt_msg_on = parse_switch(optarg, "on", "off");
|
|
|
|
break;
|
|
|
|
case OPT_MSGLEVEL:
|
|
|
|
set_opt_flag(&opt_msglevel);
|
|
|
|
opt_msglevel_num = parse_msglevel(optarg);
|
|
|
|
break;
|
|
|
|
case OPT_POWERSAVE:
|
|
|
|
set_opt_flag(&opt_powersave);
|
|
|
|
opt_ps_mode = parse_powersave(optarg);
|
|
|
|
break;
|
|
|
|
case OPT_POWERDOWN:
|
|
|
|
set_opt_flag(&opt_powerdown);
|
|
|
|
opt_pd_min = parse_blank(argv, optarg, &optind);
|
|
|
|
break;
|
|
|
|
case OPT_BLENGTH:
|
|
|
|
set_opt_flag(&opt_blength);
|
|
|
|
opt_blength_l = parse_blength(argv, optarg, &optind);
|
|
|
|
break;
|
|
|
|
case OPT_BFREQ:
|
|
|
|
set_opt_flag(&opt_bfreq);
|
|
|
|
opt_bfreq_f = parse_bfreq(argv, optarg, &optind);
|
|
|
|
break;
|
|
|
|
case OPT_VERSION:
|
|
|
|
printf(UTIL_LINUX_VERSION);
|
|
|
|
exit(EXIT_SUCCESS);
|
|
|
|
case OPT_HELP:
|
|
|
|
usage(stdout);
|
|
|
|
default:
|
|
|
|
usage(stderr);
|
|
|
|
}
|
|
|
|
}
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
|
|
|
|
|
|
|
/* End of command line parsing routines. */
|
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
static char *ti_entry(const char *name) {
|
|
|
|
/* name: Terminfo capability string to lookup. */
|
|
|
|
|
2006-12-06 17:25:34 -06:00
|
|
|
/* Return the specified terminfo string, or an empty string if no such terminfo
|
2006-12-06 17:25:32 -06:00
|
|
|
* capability exists.
|
|
|
|
*/
|
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
char *buf_ptr;
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:53 -06:00
|
|
|
if ((buf_ptr = tigetstr((char *)name)) == (char *)-1)
|
|
|
|
buf_ptr = NULL;
|
2006-12-06 17:25:43 -06:00
|
|
|
return buf_ptr;
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
|
|
|
|
2014-05-17 14:12:23 -05:00
|
|
|
static void show_tabs(void)
|
|
|
|
{
|
|
|
|
int i, co = tigetnum("cols");
|
|
|
|
|
|
|
|
if (co > 0) {
|
|
|
|
printf("\r ");
|
|
|
|
for (i = 10; i < co - 2; i += 10)
|
|
|
|
printf("%-10d", i);
|
|
|
|
putchar('\n');
|
|
|
|
for (i = 1; i <= co; i++)
|
|
|
|
putchar(i % 10 + '0');
|
|
|
|
putchar('\n');
|
|
|
|
for (i = 1; i < co; i++)
|
|
|
|
printf("\tT\b");
|
|
|
|
putchar('\n');
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
static void screendump(int vcnum, FILE *F)
|
|
|
|
{
|
|
|
|
char infile[MAXPATHLEN];
|
|
|
|
unsigned char header[4];
|
|
|
|
unsigned int rows, cols;
|
|
|
|
int fd;
|
|
|
|
size_t i, j;
|
|
|
|
ssize_t rc;
|
|
|
|
char *inbuf = NULL, *outbuf = NULL, *p, *q;
|
|
|
|
|
|
|
|
sprintf(infile, "/dev/vcsa%d", vcnum);
|
|
|
|
fd = open(infile, O_RDONLY);
|
|
|
|
if (fd < 0 && vcnum == 0) {
|
|
|
|
/* vcsa0 is often called vcsa */
|
|
|
|
sprintf(infile, "/dev/vcsa");
|
|
|
|
fd = open(infile, O_RDONLY);
|
|
|
|
}
|
|
|
|
if (fd < 0) {
|
|
|
|
/* try devfs name - for zero vcnum just /dev/vcc/a */
|
|
|
|
/* some gcc's warn for %.u - add 0 */
|
|
|
|
sprintf(infile, "/dev/vcc/a%.0u", vcnum);
|
|
|
|
fd = open(infile, O_RDONLY);
|
|
|
|
}
|
|
|
|
if (fd < 0) {
|
|
|
|
sprintf(infile, "/dev/vcsa%d", vcnum);
|
|
|
|
goto read_error;
|
|
|
|
}
|
|
|
|
if (read(fd, header, 4) != 4)
|
|
|
|
goto read_error;
|
|
|
|
rows = header[0];
|
|
|
|
cols = header[1];
|
|
|
|
if (rows * cols == 0)
|
|
|
|
goto read_error;
|
|
|
|
|
|
|
|
inbuf = xmalloc(rows * cols * 2);
|
|
|
|
outbuf = xmalloc(rows * (cols + 1));
|
|
|
|
|
|
|
|
rc = read(fd, inbuf, rows * cols * 2);
|
|
|
|
if (rc < 0 || (size_t)rc != rows * cols * 2)
|
|
|
|
goto read_error;
|
|
|
|
p = inbuf;
|
|
|
|
q = outbuf;
|
|
|
|
for (i = 0; i < rows; i++) {
|
|
|
|
for (j = 0; j < cols; j++) {
|
|
|
|
*q++ = *p;
|
|
|
|
p += 2;
|
|
|
|
}
|
|
|
|
while (j-- > 0 && q[-1] == ' ')
|
|
|
|
q--;
|
|
|
|
*q++ = '\n';
|
|
|
|
}
|
|
|
|
if (fwrite(outbuf, 1, q - outbuf, F) != (size_t)(q - outbuf)) {
|
|
|
|
warnx(_("Error writing screendump"));
|
|
|
|
goto error;
|
|
|
|
}
|
|
|
|
close(fd);
|
|
|
|
free(inbuf);
|
|
|
|
free(outbuf);
|
|
|
|
return;
|
|
|
|
|
|
|
|
read_error:
|
|
|
|
if (vcnum != 0)
|
|
|
|
warnx(_("Couldn't read %s"), infile);
|
|
|
|
else
|
|
|
|
warnx(_("Couldn't read neither /dev/vcsa0 nor /dev/vcsa"));
|
|
|
|
|
|
|
|
error:
|
|
|
|
if (fd >= 0)
|
|
|
|
close(fd);
|
|
|
|
free(inbuf);
|
|
|
|
free(outbuf);
|
|
|
|
exit(EXIT_FAILURE);
|
|
|
|
}
|
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
static void
|
|
|
|
perform_sequence(int vcterm) {
|
|
|
|
/* vcterm: Set if terminal is a virtual console. */
|
|
|
|
|
|
|
|
int result;
|
2006-12-06 17:25:32 -06:00
|
|
|
/* Perform the selected options. */
|
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* -reset. */
|
|
|
|
if (opt_reset) {
|
|
|
|
putp(ti_entry("rs1"));
|
|
|
|
}
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* -initialize. */
|
|
|
|
if (opt_initialize) {
|
|
|
|
putp(ti_entry("is2"));
|
|
|
|
}
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* -cursor [on|off]. */
|
|
|
|
if (opt_cursor) {
|
|
|
|
if (opt_cu_on)
|
|
|
|
putp(ti_entry("cnorm"));
|
|
|
|
else
|
|
|
|
putp(ti_entry("civis"));
|
|
|
|
}
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* -linewrap [on|off]. Vc only (vt102) */
|
2014-05-12 06:53:10 -05:00
|
|
|
if (opt_linewrap && vcterm)
|
|
|
|
fputs(opt_li_on ? "\033[?7h" : "\033[?7l", stdout);
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* -repeat [on|off]. Vc only (vt102) */
|
2014-05-12 06:53:10 -05:00
|
|
|
if (opt_repeat && vcterm)
|
|
|
|
fputs(opt_rep_on ? "\033[?8h" : "\033[?8l", stdout);
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* -appcursorkeys [on|off]. Vc only (vt102) */
|
2014-05-12 06:53:10 -05:00
|
|
|
if (opt_appcursorkeys && vcterm)
|
|
|
|
fputs(opt_appck_on ? "\033[?1h" : "\033[?1l", stdout);
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* -default. Vc sets default rendition, otherwise clears all
|
|
|
|
* attributes.
|
|
|
|
*/
|
|
|
|
if (opt_default) {
|
2006-12-06 17:25:32 -06:00
|
|
|
if (vcterm)
|
2006-12-06 17:25:43 -06:00
|
|
|
printf("\033[0m");
|
2006-12-06 17:25:32 -06:00
|
|
|
else
|
2006-12-06 17:25:34 -06:00
|
|
|
putp(ti_entry("sgr0"));
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
2006-12-06 17:25:43 -06:00
|
|
|
|
|
|
|
/* -foreground black|red|green|yellow|blue|magenta|cyan|white|default.
|
|
|
|
* Vc only (ANSI).
|
|
|
|
*/
|
2014-05-12 06:53:10 -05:00
|
|
|
if (opt_foreground && vcterm)
|
|
|
|
printf("\033[3%c%s", '0' + opt_fo_color, "m");
|
2006-12-06 17:25:43 -06:00
|
|
|
|
|
|
|
/* -background black|red|green|yellow|blue|magenta|cyan|white|default.
|
|
|
|
* Vc only (ANSI).
|
|
|
|
*/
|
2014-05-12 06:53:10 -05:00
|
|
|
if (opt_background && vcterm)
|
|
|
|
printf("\033[4%c%s", '0' + opt_ba_color, "m");
|
2006-12-06 17:25:43 -06:00
|
|
|
|
|
|
|
/* -ulcolor black|red|green|yellow|blue|magenta|cyan|white|default.
|
|
|
|
* Vc only.
|
|
|
|
*/
|
|
|
|
if (opt_ulcolor && vcterm) {
|
|
|
|
printf("\033[1;%d]", opt_ul_color);
|
|
|
|
}
|
|
|
|
|
|
|
|
/* -hbcolor black|red|green|yellow|blue|magenta|cyan|white|default.
|
|
|
|
* Vc only.
|
|
|
|
*/
|
|
|
|
if (opt_hbcolor && vcterm) {
|
|
|
|
printf("\033[2;%d]", opt_hb_color);
|
|
|
|
}
|
|
|
|
|
|
|
|
/* -inversescreen [on|off]. Vc only (vt102).
|
|
|
|
*/
|
2014-05-12 06:53:10 -05:00
|
|
|
if (opt_inversescreen && vcterm)
|
|
|
|
fputs(opt_invsc_on ? "\033[?5h" : "\033[?5l", stdout);
|
2006-12-06 17:25:43 -06:00
|
|
|
|
|
|
|
/* -bold [on|off]. Vc behaves as expected, otherwise off turns off
|
|
|
|
* all attributes.
|
|
|
|
*/
|
|
|
|
if (opt_bold) {
|
|
|
|
if (opt_bo_on)
|
|
|
|
putp(ti_entry("bold"));
|
|
|
|
else {
|
|
|
|
if (vcterm)
|
2014-05-12 06:53:10 -05:00
|
|
|
fputs("\033[22m", stdout);
|
2006-12-06 17:25:43 -06:00
|
|
|
else
|
|
|
|
putp(ti_entry("sgr0"));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* -half-bright [on|off]. Vc behaves as expected, otherwise off turns off
|
|
|
|
* all attributes.
|
|
|
|
*/
|
|
|
|
if (opt_halfbright) {
|
|
|
|
if (opt_hb_on)
|
|
|
|
putp(ti_entry("dim"));
|
|
|
|
else {
|
|
|
|
if (vcterm)
|
2014-05-12 06:53:10 -05:00
|
|
|
fputs("\033[22m", stdout);
|
2006-12-06 17:25:43 -06:00
|
|
|
else
|
|
|
|
putp(ti_entry("sgr0"));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* -blink [on|off]. Vc behaves as expected, otherwise off turns off
|
|
|
|
* all attributes.
|
|
|
|
*/
|
|
|
|
if (opt_blink) {
|
|
|
|
if (opt_bl_on)
|
|
|
|
putp(ti_entry("blink"));
|
|
|
|
else {
|
|
|
|
if (vcterm)
|
2014-05-12 06:53:10 -05:00
|
|
|
fputs("\033[25m", stdout);
|
2006-12-06 17:25:43 -06:00
|
|
|
else
|
|
|
|
putp(ti_entry("sgr0"));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* -reverse [on|off]. Vc behaves as expected, otherwise off turns
|
|
|
|
* off all attributes.
|
|
|
|
*/
|
|
|
|
if (opt_reverse) {
|
|
|
|
if (opt_re_on)
|
|
|
|
putp(ti_entry("rev"));
|
|
|
|
else {
|
|
|
|
if (vcterm)
|
2014-05-12 06:53:10 -05:00
|
|
|
fputs("\033[27m", stdout);
|
2006-12-06 17:25:43 -06:00
|
|
|
else
|
|
|
|
putp(ti_entry("sgr0"));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* -underline [on|off]. */
|
2014-05-12 06:53:10 -05:00
|
|
|
if (opt_underline)
|
|
|
|
putp(ti_entry(opt_un_on ? "smul" : "rmul"));
|
2006-12-06 17:25:43 -06:00
|
|
|
|
|
|
|
/* -store. Vc only. */
|
2014-05-12 06:53:10 -05:00
|
|
|
if (opt_store && vcterm)
|
|
|
|
fputs("\033[8]", stdout);
|
2006-12-06 17:25:43 -06:00
|
|
|
|
|
|
|
/* -clear [all|rest]. */
|
2014-05-12 06:53:10 -05:00
|
|
|
if (opt_clear)
|
|
|
|
putp(ti_entry(opt_cl_all ? "clear" : "ed"));
|
2006-12-06 17:25:43 -06:00
|
|
|
|
|
|
|
/* -tabs Vc only. */
|
|
|
|
if (opt_tabs && vcterm) {
|
|
|
|
int i;
|
|
|
|
|
|
|
|
if (opt_tb_array[0] == -1)
|
|
|
|
show_tabs();
|
|
|
|
else {
|
|
|
|
for(i=0; opt_tb_array[i] > 0; i++)
|
|
|
|
printf("\033[%dG\033H", opt_tb_array[i]);
|
|
|
|
putchar('\r');
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* -clrtabs Vc only. */
|
|
|
|
if (opt_clrtabs && vcterm) {
|
|
|
|
int i;
|
|
|
|
|
|
|
|
if (opt_tb_array[0] == -1)
|
2014-05-12 06:53:10 -05:00
|
|
|
fputs("\033[3g", stdout);
|
2006-12-06 17:25:32 -06:00
|
|
|
else
|
2006-12-06 17:25:43 -06:00
|
|
|
for(i=0; opt_tb_array[i] > 0; i++)
|
|
|
|
printf("\033[%dG\033[g", opt_tb_array[i]);
|
|
|
|
putchar('\r');
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* -regtabs Vc only. */
|
|
|
|
if (opt_regtabs && vcterm) {
|
|
|
|
int i;
|
|
|
|
|
2014-05-12 06:53:10 -05:00
|
|
|
fputs("\033[3g\r", stdout);
|
2014-05-11 14:26:49 -05:00
|
|
|
for(i=opt_rt_len+1; i<=TABS_MAX; i+=opt_rt_len)
|
2006-12-06 17:25:43 -06:00
|
|
|
printf("\033[%dC\033H",opt_rt_len);
|
|
|
|
putchar('\r');
|
|
|
|
}
|
|
|
|
|
|
|
|
/* -blank [0-60]. */
|
2007-11-27 16:54:35 -06:00
|
|
|
if (opt_blank && vcterm) {
|
|
|
|
if (opt_bl_min >= 0)
|
|
|
|
printf("\033[9;%d]", opt_bl_min);
|
|
|
|
else if (opt_bl_min == BLANKSCREEN) {
|
|
|
|
char ioctlarg = TIOCL_BLANKSCREEN;
|
|
|
|
if (ioctl(0,TIOCLINUX,&ioctlarg))
|
2011-04-02 15:56:52 -05:00
|
|
|
warn(_("cannot force blank"));
|
2007-11-27 16:54:35 -06:00
|
|
|
} else if (opt_bl_min == UNBLANKSCREEN) {
|
|
|
|
char ioctlarg = TIOCL_UNBLANKSCREEN;
|
|
|
|
if (ioctl(0,TIOCLINUX,&ioctlarg))
|
2011-04-02 15:56:52 -05:00
|
|
|
warn(_("cannot force unblank"));
|
2007-11-27 16:54:35 -06:00
|
|
|
} else if (opt_bl_min == BLANKEDSCREEN) {
|
|
|
|
char ioctlarg = TIOCL_BLANKEDSCREEN;
|
|
|
|
int ret;
|
|
|
|
ret = ioctl(0,TIOCLINUX,&ioctlarg);
|
|
|
|
if (ret < 0)
|
2011-04-02 15:56:52 -05:00
|
|
|
warn(_("cannot get blank status"));
|
2007-11-27 16:54:35 -06:00
|
|
|
else
|
|
|
|
printf("%d\n",ret);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* -powersave [on|vsync|hsync|powerdown|off] (console) */
|
|
|
|
if (opt_powersave) {
|
|
|
|
char ioctlarg[2];
|
2007-11-27 16:54:35 -06:00
|
|
|
ioctlarg[0] = TIOCL_SETVESABLANK;
|
2006-12-06 17:25:43 -06:00
|
|
|
ioctlarg[1] = opt_ps_mode;
|
|
|
|
if (ioctl(0,TIOCLINUX,ioctlarg))
|
2011-04-02 15:56:52 -05:00
|
|
|
warn(_("cannot (un)set powersave mode"));
|
2006-12-06 17:25:43 -06:00
|
|
|
}
|
|
|
|
|
|
|
|
/* -powerdown [0-60]. */
|
|
|
|
if (opt_powerdown) {
|
|
|
|
printf("\033[14;%d]", opt_pd_min);
|
|
|
|
}
|
2006-12-06 17:25:34 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* -snap [1-NR_CONS]. */
|
|
|
|
if (opt_snap || opt_append) {
|
|
|
|
FILE *F;
|
|
|
|
|
|
|
|
F = fopen(opt_sn_name, opt_snap ? "w" : "a");
|
2011-04-02 15:56:52 -05:00
|
|
|
if (!F)
|
|
|
|
err(EXIT_DUMPFILE, _("can not open dump file %s for output"),
|
2006-12-06 17:25:43 -06:00
|
|
|
opt_sn_name);
|
|
|
|
screendump(opt_sn_num, F);
|
2012-04-04 12:44:04 -05:00
|
|
|
if (close_stream(F) != 0)
|
|
|
|
errx(EXIT_FAILURE, _("write error"));
|
2006-12-06 17:25:43 -06:00
|
|
|
}
|
|
|
|
|
|
|
|
/* -msg [on|off]. */
|
|
|
|
if (opt_msg && vcterm) {
|
|
|
|
if (opt_msg_on)
|
|
|
|
/* 7 -- Enable printk's to console */
|
2014-05-11 14:26:49 -05:00
|
|
|
result = klogctl(SYSLOG_ACTION_CONSOLE_ON, NULL, 0);
|
2006-12-06 17:25:43 -06:00
|
|
|
else
|
|
|
|
/* 6 -- Disable printk's to console */
|
2014-05-11 14:26:49 -05:00
|
|
|
result = klogctl(SYSLOG_ACTION_CONSOLE_OFF, NULL, 0);
|
2006-12-06 17:25:43 -06:00
|
|
|
|
|
|
|
if (result != 0)
|
2011-04-02 15:56:52 -05:00
|
|
|
warn(_("klogctl error"));
|
2006-12-06 17:25:43 -06:00
|
|
|
}
|
|
|
|
|
|
|
|
/* -msglevel [0-8] */
|
|
|
|
if (opt_msglevel && vcterm) {
|
|
|
|
/* 8 -- Set level of messages printed to console */
|
2014-05-11 14:26:49 -05:00
|
|
|
result = klogctl(SYSLOG_ACTION_CONSOLE_LEVEL, NULL, opt_msglevel_num);
|
2006-12-06 17:25:43 -06:00
|
|
|
if (result != 0)
|
2011-04-02 15:56:52 -05:00
|
|
|
warn(_("klogctl error"));
|
2006-12-06 17:25:43 -06:00
|
|
|
}
|
|
|
|
|
|
|
|
/* -blength [0-2000] */
|
|
|
|
if (opt_blength && vcterm) {
|
|
|
|
printf("\033[11;%d]", opt_blength_l);
|
|
|
|
}
|
2009-10-15 18:40:58 -05:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* -bfreq freqnumber */
|
|
|
|
if (opt_bfreq && vcterm) {
|
|
|
|
printf("\033[10;%d]", opt_bfreq_f);
|
|
|
|
}
|
2006-12-06 17:25:34 -06:00
|
|
|
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
int
|
|
|
|
main(int argc, char **argv) {
|
|
|
|
char *term; /* Terminal type. */
|
|
|
|
int vcterm; /* Set if terminal is a virtual console. */
|
2011-04-02 15:56:52 -05:00
|
|
|
int errret;
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
setlocale(LC_ALL, "");
|
|
|
|
bindtextdomain(PACKAGE, LOCALEDIR);
|
|
|
|
textdomain(PACKAGE);
|
2012-04-04 12:44:04 -05:00
|
|
|
atexit(close_stdout);
|
2009-10-15 18:40:58 -05:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
if (argc < 2)
|
2014-05-17 12:52:01 -05:00
|
|
|
usage(stderr);
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* Parse arguments. */
|
2014-05-17 12:52:01 -05:00
|
|
|
parse_option(argc, argv);
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* Find out terminal name. */
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
if (opt_term) {
|
|
|
|
term = opt_te_terminal_name;
|
|
|
|
} else {
|
|
|
|
term = getenv("TERM");
|
2011-04-02 15:56:52 -05:00
|
|
|
if (term == NULL)
|
|
|
|
errx(EXIT_FAILURE, _("$TERM is not defined."));
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* Find terminfo entry. */
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2011-04-02 15:56:52 -05:00
|
|
|
if (setupterm(term, 1, &errret))
|
|
|
|
switch(errret) {
|
|
|
|
case -1:
|
|
|
|
errx(EXIT_FAILURE, _("terminfo database cannot be found"));
|
|
|
|
case 0:
|
|
|
|
errx(EXIT_FAILURE, _("%s: unknown terminal type"), term);
|
|
|
|
case 1:
|
|
|
|
errx(EXIT_FAILURE, _("terminal is hardcopy"));
|
|
|
|
}
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* See if the terminal is a virtual console terminal. */
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
vcterm = (!strncmp(term, "con", 3) || !strncmp(term, "linux", 5));
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
/* Perform the selected options. */
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2006-12-06 17:25:43 -06:00
|
|
|
perform_sequence(vcterm);
|
2006-12-06 17:25:32 -06:00
|
|
|
|
2011-04-02 15:56:52 -05:00
|
|
|
return EXIT_SUCCESS;
|
2006-12-06 17:25:32 -06:00
|
|
|
}
|