summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKarel Zak2014-05-20 11:44:26 +0200
committerKarel Zak2014-05-20 11:44:26 +0200
commit10bd07cad86923b89fc2d2a61fe34c35cb258772 (patch)
treed372dae12be68c725acf6d5fca5bcb041094d536
parentfsck.cramfs: cleanup usage() and warning messages (diff)
parentsetterm: remove ulcolor and hbcolor duplicates (diff)
downloadkernel-qcow2-util-linux-10bd07cad86923b89fc2d2a61fe34c35cb258772.tar.gz
kernel-qcow2-util-linux-10bd07cad86923b89fc2d2a61fe34c35cb258772.tar.xz
kernel-qcow2-util-linux-10bd07cad86923b89fc2d2a61fe34c35cb258772.zip
Merge branch '2014wk19' of git://github.com/kerolasa/lelux-utiliteetit
* '2014wk19' of git://github.com/kerolasa/lelux-utiliteetit: setterm: remove ulcolor and hbcolor duplicates setterm: add set_blanking() action setterm: mark some options to be exclusive with each other setterm: various visual terminal effects are not console specific setterm: improve error messages setterm: tell user when options does not effect setterm: improve perform_sequence() coding style setterm: correct usage() bright color argument setterm: make -msglevel 0 to work as is did earlier setterm: remove devfs and /dev/vcsa0 support setterm: clean up screendump() setterm: add init_terminal() to make main() shorter setterm: add option control structure setterm: remove usage comment segment setterm: move show_tabs() and screendump() functions setterm: use string utils to numeric parsing setterm: recommend long options with double hyphen setterm: use getopt_long_only() for option parsing setterm: clean up includes
-rw-r--r--bash-completion/setterm121
-rw-r--r--term-utils/Makemodule.am2
-rw-r--r--term-utils/setterm.194
-rw-r--r--term-utils/setterm.c1665
4 files changed, 872 insertions, 1010 deletions
diff --git a/bash-completion/setterm b/bash-completion/setterm
index a7ef6ebed..dd46472de 100644
--- a/bash-completion/setterm
+++ b/bash-completion/setterm
@@ -1,11 +1,11 @@
_setterm_module()
{
- local cur prev OPTS
+ local bright cur prev OPTS
COMPREPLY=()
cur="${COMP_WORDS[COMP_CWORD]}"
prev="${COMP_WORDS[COMP_CWORD-1]}"
case $prev in
- '-term')
+ '--term')
local TERM_LIST I
TERM_LIST=''
for I in /usr/share/terminfo/?/*; do
@@ -14,103 +14,112 @@ _setterm_module()
COMPREPLY=( $(compgen -W "$TERM_LIST" -- $cur) )
return 0
;;
- '-foreground'|'-background'|'-ulcolor'|'-hbcolor')
- COMPREPLY=( $(compgen -W "default black blue cyan green magenta red white yellow" -- $cur) )
+ '--foreground'|'--background')
+ COMPREPLY=( $(compgen -W "black blue cyan default green magenta red white yellow" -- $cur) )
return 0
;;
- '-cursor'|'-repeat'|'-appcursorkeys'|'-linewrap'|'-inversescreen'|'-bold'|'-half-bright'|'-blink'|'-reverse'|'-underline'|'-msg')
+ '--ulcolor'|'--hbcolor'|'bright')
+ if [ $prev != 'bright' ]; then
+ bright='bright black grey'
+ else
+ bright=''
+ fi
+ COMPREPLY=( $(compgen -W "$bright blue cyan green magenta red white yellow" -- $cur) )
+ return 0
+ ;;
+ '--cursor'|'--repeat'|'--appcursorkeys'|'--linewrap'|'--inversescreen'|'--bold'|'--half-bright'|'--blink'|'--reverse'|'--underline'|'--msg')
COMPREPLY=( $(compgen -W "off on" -- $cur) )
return 0
;;
- '-clear')
+ '--clear')
COMPREPLY=( $(compgen -W "all rest" -- $cur) )
return 0
;;
- '-tabs'|'-clrtabs')
+ '--tabs'|'--clrtabs')
COMPREPLY=( $(compgen -W "tab1 tab2 tab3 tab160" -- $cur) )
return 0
;;
- '-regtabs')
+ '--regtabs')
COMPREPLY=( $(compgen -W "{1..160}" -- $cur) )
return 0
;;
- '-blank')
+ '--blank')
COMPREPLY=( $(compgen -W "{0..60} force poke" -- $cur) )
return 0
;;
- '-dump'|'-append')
+ '--dump'|'--append')
local NUM_CONS
- NUM_CONS=(/sys/class/tty/*)
+ NUM_CONS=(/dev/vcsa?*)
COMPREPLY=( $(compgen -W "{1..${#NUM_CONS[*]}}" -- $cur) )
return 0
;;
- '-file')
+ '--file')
local IFS=$'\n'
compopt -o filenames
COMPREPLY=( $(compgen -f -- $cur) )
return 0
;;
- '-msglevel')
- COMPREPLY=( $(compgen -W "{1..8}" -- $cur) )
+ '--msglevel')
+ COMPREPLY=( $(compgen -W "{0..8}" -- $cur) )
return 0
;;
- '-powersave')
+ '--powersave')
COMPREPLY=( $(compgen -W "on vsync hsync powerdown off" -- $cur) )
return 0
;;
- '-powerdown')
+ '--powerdown')
COMPREPLY=( $(compgen -W "{0..60}" -- $cur) )
return 0
;;
- '-blength')
+ '--blength')
COMPREPLY=( $(compgen -W "0-2000" -- $cur) )
return 0
;;
- '-bfreq')
+ '--bfreq')
COMPREPLY=( $(compgen -W "freqnumber" -- $cur) )
return 0
;;
- '-help'|'-version')
+ '--help'|'--version')
return 0
;;
esac
- OPTS=" -term
- -reset
- -initialize
- -cursor
- -repeat
- -appcursorkeys
- -linewrap
- -default
- -foreground
- -background
- -ulcolor
- -hbcolor
- -ulcolor
- -hbcolor
- -inversescreen
- -bold
- -half-bright
- -blink
- -reverse
- -underline
- -store
- -clear
- -tabs
- -clrtabs
- -regtabs
- -blank
- -dump
- -append
- -file
- -msg
- -msglevel
- -powersave
- -powerdown
- -blength
- -bfreq
- -version
- -help"
+ OPTS=" --term
+ --reset
+ --initialize
+ --cursor
+ --repeat
+ --appcursorkeys
+ --linewrap
+ --default
+ --foreground
+ --background
+ --ulcolor
+ --hbcolor
+ --ulcolor
+ --hbcolor
+ --inversescreen
+ --bold
+ --half-bright
+ --blink
+ --reverse
+ --underline
+ --store
+ --clear
+ --tabs
+ --clrtabs
+ --regtabs
+ --blank
+ --dump
+ --append
+ --file
+ --msg
+ --msglevel
+ --powersave
+ --powerdown
+ --blength
+ --bfreq
+ --version
+ --help"
COMPREPLY=( $(compgen -W "${OPTS[*]}" -- $cur) )
return 0
}
diff --git a/term-utils/Makemodule.am b/term-utils/Makemodule.am
index e53471f23..39fddc9a0 100644
--- a/term-utils/Makemodule.am
+++ b/term-utils/Makemodule.am
@@ -29,7 +29,7 @@ usrbin_exec_PROGRAMS += setterm
dist_man_MANS += term-utils/setterm.1
setterm_SOURCES = term-utils/setterm.c
setterm_CFLAGS = $(AM_CFLAGS)
-setterm_LDADD = $(LDADD)
+setterm_LDADD = $(LDADD) libcommon.la
if HAVE_TINFO
setterm_LDADD += $(TINFO_LIBS)
setterm_CFLAGS += $(TINFO_CFLAGS)
diff --git a/term-utils/setterm.1 b/term-utils/setterm.1
index 9f5b2292d..d15fd40e7 100644
--- a/term-utils/setterm.1
+++ b/term-utils/setterm.1
@@ -39,23 +39,23 @@ by \fBred\fP, \fBgreen\fP, \fByellow\fP, \fBblue\fP, \fBmagenta\fP,
.P
The various color options may be set independently, at least at virtual
consoles, though the results of setting multiple modes (for example,
-.BR \-underline " and " \-half-bright )
+.BR \-\-underline " and " \-\-half-bright )
are hardware-dependent.
.TP
-.BR \-appcursorkeys " [" on | off "] (virtual consoles only)"
+.BR \-\-appcursorkeys " [" on | off "] (virtual consoles only)"
Sets Cursor Key Application Mode on or off. When on, ESC O A, ESC O B, etc.
will be sent for the cursor keys instead of ESC [ A, ESC [ B, etc. See the
"vi and Cursor-Keys" section of the Text-Terminal-HOWTO for how this can
cause problems for vi users.
.TP
-.BR \-append " [\fI1-NR_CONS\fP]"
-Like \fB\-dump\fP, but appends to the snapshot file instead of overwriting
-it. Only works if no \fB\-dump\fP options are given.
+.BR \-\-append " [\fI1-NR_CONS\fP]"
+Like \fB\-\-dump\fP, but appends to the snapshot file instead of overwriting
+it. Only works if no \fB\-\-dump\fP options are given.
.TP
-\fB\-background\fP \fI8-color\fP|\fBdefault\fP (virtual consoles only)
+\fB\-\-background\fP \fI8-color\fP|\fBdefault\fP (virtual consoles only)
Sets the background text color.
.TP
-.BR \-blank " [\fI0-60\fP|\fBforce\fP|\fBpoke\fP] (virtual consoles only)"
+.BR \-\-blank " [\fI0-60\fP|\fBforce\fP|\fBpoke\fP] (virtual consoles only)"
Sets the interval of inactivity, in minutes, after which the screen will be
automatically blanked (using APM if available). Without an argument, gets the
blank status (returns which vt was blanked or zero for unblanked vt).
@@ -68,121 +68,121 @@ The
.B poke
option unblank the screen.
.TP
-.BR \-bfreq " [\fIfreqnumber\fP]"
+.BR \-\-bfreq " [\fIfreqnumber\fP]"
Sets the bell frequency in Hz. Without an argument, defaults to 0.
.TP
-.BR \-blength " [\fI0-2000\fP]"
+.BR \-\-blength " [\fI0-2000\fP]"
Sets the bell duration in milliseconds. Without an argument, defaults to 0.
.TP
-.BR \-blink " [" on | off ]
-Turns blink mode on or off. Except at a virtual console, \fB\-blink off\fP
+.BR \-\-blink " [" on | off ]
+Turns blink mode on or off. Except at a virtual console, \fB\-\-blink off\fP
turns off all attributes (bold, half-brightness, blink, reverse).
.TP
-.BR \-bold " [" on | off ]
+.BR \-\-bold " [" on | off ]
Turns bold (extra bright) mode on or off. Except at a virtual console,
-\fB\-bold off\fP turns off all attributes (bold, half-brightness, blink,
+\fB\-\-bold off\fP turns off all attributes (bold, half-brightness, blink,
reverse).
.TP
-.BR \-clear " [" all ]
+.BR \-\-clear " [" all ]
Clears the screen and "homes" the cursor, as
.BR clear (1).
.TP
-.B \-clear rest
+.B \-\-clear rest
Clears from the current cursor position to the end of the screen.
.TP
-.BR \-clrtabs " [\fItab1 tab2 tab3\fP ...] (virtual consoles only)"
+.BR \-\-clrtabs " [\fItab1 tab2 tab3\fP ...] (virtual consoles only)"
Clears tab stops from the given horizontal cursor positions, in the range
1-160. Without arguments, clears all tab stops.
.TP
-.BR \-cursor " [" on | off ]
+.BR \-\-cursor " [" on | off ]
Turns the terminal's cursor on or off.
.TP
-.B \-default
+.B \-\-default
Sets the terminal's rendering options to the default values.
.TP
-.BR \-dump " [\fI1-NR_CONS\fP]"
+.BR \-\-dump " [\fI1-NR_CONS\fP]"
Writes a snapshot of the given virtual console to the file
-specified in the \fB\-file\fP option, overwriting its contents; the default
+specified in the \fB\-\-file\fP option, overwriting its contents; the default
is screen.dump. Without an argument, dumps the current virtual console.
-Overrides \fB\-append\fP.
+Overrides \fB\-\-append\fP.
.TP
-.BR \-append " [\fI1-NR_CONS\fP]"
-Like \fB\-dump\fP, but appends to the snapshot file instead of overwriting
-it. Only works if no \fB\-dump\fP options are given.
+.BR \-\-append " [\fI1-NR_CONS\fP]"
+Like \fB\-\-dump\fP, but appends to the snapshot file instead of overwriting
+it. Only works if no \fB\-\-dump\fP options are given.
.TP
-.BI \-file " dumpfilename"
-Sets the snapshot file name for any \fB\-dump\fP or \fB\-append\fP options
+.BI \-\-file " dumpfilename"
+Sets the snapshot file name for any \fB\-\-dump\fP or \fB\-\-append\fP options
on the same command line. If this option is not present, the default is
screen.dump in the current directory. A path name that exceeds system
maximum will be truncated, see PATH_MAX from linux/limits.h for the value.
.TP
-.BR \-msg " [" on | off "] (virtual consoles only)"
+.BR \-\-msg " [" on | off "] (virtual consoles only)"
Enables or disables the sending of kernel \fBprintk()\fP messages to the
console.
.TP
-.BR \-msglevel " \fI1-8\fP (virtual consoles only)"
+.BR \-\-msglevel " \fI1-8\fP (virtual consoles only)"
Sets the console logging level for kernel \fBprintk()\fP messages. All
messages strictly more important than this will be printed, so a logging
-level of 0 has the same effect as \fB\-msg on\fP and a logging level of 8
+level of 0 has the same effect as \fB\-\-msg on\fP and a logging level of 8
will print all kernel messages.
.BR klogd (8)
may be a more convenient interface to the logging of kernel messages.
.TP
-.BR \-powerdown " [\fI0-60\fP]"
+.BR \-\-powerdown " [\fI0-60\fP]"
Sets the VESA powerdown interval in minutes. Without an argument, defaults
to 0 (disable powerdown). If the console is blanked or the monitor is in
suspend mode, then the monitor will go into vsync suspend mode or powerdown
mode respectively after this period of time has elapsed.
.TP
-.BR \-underline " [" on | off ]
-Turns underline mode on or off (see \fB\-ulcolor\fP).
+.BR \-\-underline " [" on | off ]
+Turns underline mode on or off (see \fB\-\-ulcolor\fP).
.TP
-.BR \-powersave " [" off "]"
+.BR \-\-powersave " [" off "]"
Turns off monitor VESA powersaving features.
.TP
-.BR "\-powersave on" | vsync
+.BR "\-\-powersave on" | vsync
Puts the monitor into VESA vsync suspend mode.
.TP
-.B \-powersave powerdown
+.B \-\-powersave powerdown
Puts the monitor into VESA powerdown mode.
.TP
-.B \-powersave hsync
+.B \-\-powersave hsync
Puts the monitor into VESA hsync suspend mode.
.TP
-.BR \-regtabs " [\fI1-160\fP] (virtual consoles only)"
+.BR \-\-regtabs " [\fI1-160\fP] (virtual consoles only)"
Clears all tab stops, then sets a regular tab stop pattern, with one tab
every specified number of positions. Without an argument, defaults to 8.
.TP
-.BR \-repeat " [" on | off "] (virtual consoles only)"
+.BR \-\-repeat " [" on | off "] (virtual consoles only)"
Turns keyboard repeat on or off.
.TP
-.B \-reset
+.B \-\-reset
Displays the terminal reset string, which typically resets the terminal to
its power on state.
.TP
-.BR \-reverse " [" on | off ]
+.BR \-\-reverse " [" on | off ]
Turns reverse video mode on or off. Except at a virtual console,
-\fB\-reverse off\fP turns off all attributes (bold, half-brightness, blink,
+\fB\-\-reverse off\fP turns off all attributes (bold, half-brightness, blink,
reverse).
.TP
-.BR \-store " (virtual consoles only)"
+.BR \-\-store " (virtual consoles only)"
Stores the terminal's current rendering options (foreground and
background colors) as the values to be used at reset-to-default.
.TP
-.BR \-tabs " [\fItab1 tab2 tab3\fP ...] (virtual consoles only)"
+.BR \-\-tabs " [\fItab1 tab2 tab3\fP ...] (virtual consoles only)"
Sets tab stops at the given horizontal cursor positions, in the range 1-160.
Without arguments, shows the current tab stop settings.
.TP
-.BR \-term " terminal_name"
+.BR \-\-term " terminal_name"
Overrides the TERM environment variable.
.TP
-\fB\-ulcolor\fP \fI16-color\fP (virtual consoles only)
+\fB\-\-ulcolor\fP \fI16-color\fP (virtual consoles only)
Sets the color for underlined characters.
.TP
-.BR \-version
+.BR \-\-version
Display version information and exit.
.TP
-.BR \-help
+.BR \-\-help
Display help text and exit.
.SH "SEE ALSO"
.BR tput (1),
diff --git a/term-utils/setterm.c b/term-utils/setterm.c
index 7a3131f5f..edaf6b85d 100644
--- a/term-utils/setterm.c
+++ b/term-utils/setterm.c
@@ -19,52 +19,6 @@
* 1999-02-22 Arkadiusz Miƛkiewicz <misiek@pld.ORG.PL>
* - added Native Language Support
*
- *
- * Syntax:
- *
- * setterm
- * [ -term terminal_name ]
- * [ -reset ]
- * [ -initialize ]
- * [ -cursor [on|off] ]
- * [ -repeat [on|off] ]
- * [ -appcursorkeys [on|off] ]
- * [ -linewrap [on|off] ]
- * [ -snow [on|off] ]
- * [ -softscroll [on|off] ]
- * [ -defaults ]
- * [ -foreground black|red|green|yellow|blue|magenta|cyan|white|default ]
- * [ -background black|red|green|yellow|blue|magenta|cyan|white|default ]
- * [ -ulcolor black|grey|red|green|yellow|blue|magenta|cyan|white ]
- * [ -ulcolor bright red|green|yellow|blue|magenta|cyan|white ]
- * [ -hbcolor black|grey|red|green|yellow|blue|magenta|cyan|white ]
- * [ -hbcolor bright red|green|yellow|blue|magenta|cyan|white ]
- * [ -inversescreen [on|off] ]
- * [ -bold [on|off] ]
- * [ -half-bright [on|off] ]
- * [ -blink [on|off] ]
- * [ -reverse [on|off] ]
- * [ -underline [on|off] ]
- * [ -store ]
- * [ -clear [ all|rest ] ]
- * [ -tabs [tab1 tab2 tab3 ... ] ] (tabn = 1-160)
- * [ -clrtabs [ tab1 tab2 tab3 ... ] (tabn = 1-160)
- * [ -regtabs [1-160] ]
- * [ -blank [0-60|force|poke|] ]
- * [ -dump [1-NR_CONS ] ]
- * [ -append [1-NR_CONS ] ]
- * [ -file dumpfilename ]
- * [ -standout [attr] ]
- * [ -msg [on|off] ]
- * [ -msglevel [0-8] ]
- * [ -powersave [on|vsync|hsync|powerdown|off] ]
- * [ -powerdown [0-60] ]
- * [ -blength [0-2000] ]
- * [ -bfreq freq ]
- * [ -version ]
- * [ -help ]
- *
- *
* Semantics:
*
* Setterm writes to standard output a character string that will
@@ -92,48 +46,41 @@
* -store stores the terminal's current rendering options as the default
* values. */
+#include <ctype.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <getopt.h>
#include <stdio.h>
#include <stdlib.h>
-#include <errno.h>
-#include <ctype.h>
-#include <unistd.h>
-#include <termios.h>
#include <string.h>
-#include <fcntl.h>
+#include <sys/ioctl.h>
+#include <sys/klog.h>
+#include <sys/param.h> /* for MAXPATHLEN */
+#include <sys/time.h>
+#include <termios.h>
+#include <unistd.h>
#ifndef NCURSES_CONST
-#define NCURSES_CONST const /* define before including term.h */
+# define NCURSES_CONST const /* define before including term.h */
#endif
#ifdef HAVE_NCURSES_H
-#include <ncurses.h>
+# include <ncurses.h>
#elif defined(HAVE_NCURSES_NCURSES_H)
-#include <ncurses/ncurses.h>
+# include <ncurses/ncurses.h>
#endif
/* must include after ncurses.h */
#include <term.h>
-#include <sys/param.h> /* for MAXPATHLEN */
-#include <sys/ioctl.h>
-#include <sys/time.h>
#ifdef HAVE_LINUX_TIOCL_H
-#include <linux/tiocl.h>
+# include <linux/tiocl.h>
#endif
#include "c.h"
-#include "xalloc.h"
-#include "nls.h"
#include "closestream.h"
-
-#if defined(__GNU_LIBRARY__) && __GNU_LIBRARY__ < 5
-#ifndef __alpha__
-# include <linux/unistd.h>
-#define __NR_klogctl __NR_syslog
-_syscall3(int, klogctl, int, type, char*, buf, int, len);
-#else /* __alpha__ */
-#define klogctl syslog
-#endif
-#endif
-extern int klogctl(int type, char *buf, int len);
+#include "nls.h"
+#include "optutils.h"
+#include "strutils.h"
+#include "xalloc.h"
/* Constants. */
@@ -188,7 +135,7 @@ enum {
/* Console log levels */
enum {
- CONSOLE_LEVEL_MIN = 1,
+ CONSOLE_LEVEL_MIN = 0,
CONSOLE_LEVEL_MAX = 8
};
@@ -198,730 +145,771 @@ enum {
#define TABS_MAX 160
#define BLENGTH_MAX 2000
-/* Option flags. Set if the option is to be invoked. */
-int opt_term, opt_reset, opt_initialize, opt_cursor;
-int opt_linewrap, opt_default, opt_foreground;
-int opt_background, opt_bold, opt_blink, opt_reverse, opt_underline;
-int opt_store, opt_clear, opt_blank, opt_snap, opt_snapfile;
-int opt_append, opt_ulcolor, opt_hbcolor, opt_halfbright, opt_repeat;
-int opt_tabs, opt_clrtabs, opt_regtabs, opt_appcursorkeys, opt_inversescreen;
-int opt_msg, opt_msglevel, opt_powersave, opt_powerdown;
-int opt_blength, opt_bfreq;
-
-/* Option controls. The variable names have been contracted to ensure
- * uniqueness.
- */
-char *opt_te_terminal_name; /* Terminal name. */
-int opt_cu_on, opt_li_on, opt_bo_on, opt_hb_on, opt_bl_on;
-int opt_re_on, opt_un_on, opt_rep_on, opt_appck_on, opt_invsc_on;
-int opt_msg_on; /* Boolean switches. */
-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. */
-int opt_blength_l;
-int opt_bfreq_f;
-int opt_sn_num; /* Snap screen. */
-int opt_rt_len; /* regular tab length */
-int opt_tb_array[TABS_MAX + 1]; /* Array for tab list */
-int opt_msglevel_num;
-int opt_ps_mode, opt_pd_min; /* powersave mode/powerdown time */
-
-char opt_sn_name[PATH_MAX + 1] = "screen.dump";
-
-static void screendump(int vcnum, FILE *F);
+/* Command controls. */
+struct setterm_control {
+ char *opt_te_terminal_name; /* terminal name */
+ int opt_bl_min; /* blank screen */
+ int opt_blength_l; /* bell duration in milliseconds */
+ int opt_bfreq_f; /* bell frequency in Hz */
+ int opt_sn_num; /* console number to be snapshoted */
+ char *opt_sn_name; /* path to write snap */
+ char *in_device; /* device to snapshot */
+ int opt_msglevel_num; /* printk() loging level */
+ int opt_ps_mode; /* powersave mode */
+ int opt_pd_min; /* powerdown time */
+ int opt_rt_len; /* regular tab length */
+ int opt_tb_array[TABS_MAX + 1]; /* array for tab list */
+ /* colors */
+ int opt_fo_color:4, opt_ba_color:4, opt_ul_color:4, opt_hb_color:4;
+ /* boolean options */
+ int opt_cu_on:1, opt_li_on:1, opt_bo_on:1, opt_hb_on:1, opt_bl_on:1,
+ opt_re_on:1, opt_un_on:1, opt_rep_on:1, opt_appck_on:1,
+ opt_invsc_on:1, opt_msg_on:1, opt_cl_all:1, vcterm:1;
+ /* Option flags. Set when an option is invoked. */
+ uint64_t opt_term:1, opt_reset:1, opt_initialize:1, opt_cursor:1,
+ opt_linewrap:1, opt_default:1, opt_foreground:1,
+ opt_background:1, opt_bold:1, opt_blink:1, opt_reverse:1,
+ opt_underline:1, opt_store:1, opt_clear:1, opt_blank:1,
+ opt_snap:1, opt_snapfile:1, opt_append:1, opt_ulcolor:1,
+ opt_hbcolor:1, opt_halfbright:1, opt_repeat:1, opt_tabs:1,
+ opt_clrtabs:1, opt_regtabs:1, opt_appcursorkeys:1,
+ opt_inversescreen:1, opt_msg:1, opt_msglevel:1, opt_powersave:1,
+ opt_powerdown:1, opt_blength:1, opt_bfreq:1;
+};
/* Command line parsing routines.
*
* Note that it is an error for a given option to be invoked more than once.
*/
-static void
-parse_term(int argc, char **argv, int *option, char **ttyname, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Term flag to set. */
- /* ttyname: Terminal name to set. */
- /* bad_arg: Set to true if an error is detected. */
-
-/* Parse a -term specification. */
-
- if (argc != 1 || *option)
- *bad_arg = TRUE;
- *option = TRUE;
- if (argc == 1)
- *ttyname = argv[0];
+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);
}
-static void
-parse_none(int argc, char **argv __attribute__ ((__unused__)), int *option, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Term flag to set. */
- /* bad_arg: Set to true if an error is detected. */
+static int parse_febg_color(const char *arg)
+{
+ int color;
+
+ 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;
+ else
+ color = strtos32_or_err(arg, _("argument error"));
+ if (color < BLACK || DEFAULT < color || color == GREY)
+ errx(EXIT_FAILURE, _("argument error: %s"), arg);
+ return color;
+}
-/* Parse a parameterless specification. */
+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;
+ else {
+ color = strtos32_or_err(color_name, _("argument error"));
+ if (color < BLACK || DEFAULT < color)
+ errx(EXIT_FAILURE, _("argument error: %s"), color_name);
+ }
+ if (bright && (color == BLACK || color == GREY))
+ errx(EXIT_FAILURE, _("argument error: bright %s is not supported"), color_name);
- if (argc != 0 || *option)
- *bad_arg = TRUE;
- *option = TRUE;
+ return color;
}
-static void
-parse_switch(int argc, char **argv, int *option, int *opt_on, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Option flag to set. */
- /* opt_on: Boolean option switch to set or reset. */
- /* bad_arg: Set to true if an error is detected. */
-
-/* Parse a boolean (on/off) specification. */
-
- if (argc > 1 || *option)
- *bad_arg = TRUE;
- *option = TRUE;
- if (argc == 1) {
- if (strcmp(argv[0], "on") == 0)
- *opt_on = TRUE;
- else if (strcmp(argv[0], "off") == 0)
- *opt_on = FALSE;
- else
- *bad_arg = TRUE;
- } else {
- *opt_on = TRUE;
+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;
}
+ (*optind)++;
+ return arg;
}
-static void
-par_color(int argc, char **argv, int *option, int *opt_color, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Color flag to set. */
- /* opt_color: Color to set. */
- /* bad_arg: Set to true if an error is detected. */
-
-/* Parse a -foreground or -background specification. */
-
- if (argc != 1 || *option)
- *bad_arg = TRUE;
- *option = TRUE;
- if (argc == 1) {
- if (strcmp(argv[0], "black") == 0)
- *opt_color = BLACK;
- else if (strcmp(argv[0], "red") == 0)
- *opt_color = RED;
- else if (strcmp(argv[0], "green") == 0)
- *opt_color = GREEN;
- else if (strcmp(argv[0], "yellow") == 0)
- *opt_color = YELLOW;
- else if (strcmp(argv[0], "blue") == 0)
- *opt_color = BLUE;
- else if (strcmp(argv[0], "magenta") == 0)
- *opt_color = MAGENTA;
- else if (strcmp(argv[0], "cyan") == 0)
- *opt_color = CYAN;
- else if (strcmp(argv[0], "white") == 0)
- *opt_color = WHITE;
- else if (strcmp(argv[0], "default") == 0)
- *opt_color = DEFAULT;
- else if (isdigit(argv[0][0]))
- *opt_color = atoi(argv[0]);
- else
- *bad_arg = TRUE;
-
- if(*opt_color < BLACK || DEFAULT < *opt_color || *opt_color == GREY)
- *bad_arg = TRUE;
+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 {
+ int ret;
+
+ ret = strtos32_or_err(arg, _("argument error"));
+ if (ret < 0 || BLANK_MAX < ret)
+ errx(EXIT_FAILURE, _("argument error: %s"), arg);
+ return ret;
}
+ /* should be impossible to reach */
+ abort();
}
-static void
-par_color2(int argc, char **argv, int *option, int *opt_color, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Color flag to set. */
- /* opt_color: Color to set. */
- /* bad_arg: Set to true if an error is detected. */
-
-/* Parse a -ulcolor or -hbcolor specification. */
-
- if (!argc || argc > 2 || *option)
- *bad_arg = TRUE;
- *option = TRUE;
- *opt_color = 0;
- if (argc == 2) {
- if (strcmp(argv[0], "bright") == 0)
- *opt_color = GREY;
- else {
- *bad_arg = TRUE;
- return;
- }
- }
- if (argc) {
- if (strcmp(argv[argc-1], "black") == 0) {
- if(*opt_color)
- *bad_arg = TRUE;
- else
- *opt_color = BLACK;
- } else if (strcmp(argv[argc-1], "grey") == 0) {
- if(*opt_color)
- *bad_arg = TRUE;
- else
- *opt_color = GREY;
- } else if (strcmp(argv[argc-1], "red") == 0)
- *opt_color |= RED;
- else if (strcmp(argv[argc-1], "green") == 0)
- *opt_color |= GREEN;
- else if (strcmp(argv[argc-1], "yellow") == 0)
- *opt_color |= YELLOW;
- else if (strcmp(argv[argc-1], "blue") == 0)
- *opt_color |= BLUE;
- else if (strcmp(argv[argc-1], "magenta") == 0)
- *opt_color |= MAGENTA;
- else if (strcmp(argv[argc-1], "cyan") == 0)
- *opt_color |= CYAN;
- else if (strcmp(argv[argc-1], "white") == 0)
- *opt_color |= WHITE;
- else if (isdigit(argv[argc-1][0]))
- *opt_color = atoi(argv[argc-1]);
- else
- *bad_arg = TRUE;
- if(*opt_color < BLACK || DEFAULT < *opt_color )
- *bad_arg = TRUE;
- }
+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);
}
-static void
-parse_clear(int argc, char **argv, int *option, int *opt_all, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Clear flag to set. */
- /* opt_all: Clear all switch to set or reset. */
- /* bad_arg: Set to true if an error is detected. */
-
-/* Parse a -clear specification. */
-
- if (argc > 1 || *option)
- *bad_arg = TRUE;
- *option = TRUE;
- if (argc == 1) {
- if (strcmp(argv[0], "all") == 0)
- *opt_all = TRUE;
- else if (strcmp(argv[0], "rest") == 0)
- *opt_all = FALSE;
- else
- *bad_arg = TRUE;
- } else {
- *opt_all = TRUE;
- }
+static int parse_msglevel(const char *arg)
+{
+ int ret;
+
+ ret = strtos32_or_err(arg, _("argument error"));
+ if (ret < CONSOLE_LEVEL_MIN || CONSOLE_LEVEL_MAX < ret)
+ errx(EXIT_FAILURE, _("argument error: %s"), arg);
+ return ret;
}
-static void
-parse_blank(int argc, char **argv, int *option, int *opt_all, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Clear flag to set. */
- /* opt_all: Clear all switch to set or reset. */
- /* bad_arg: Set to true if an error is detected. */
-
-/* Parse a -blank specification. */
-
- if (argc > 1 || *option)
- *bad_arg = TRUE;
- *option = TRUE;
- if (argc == 1) {
- if (!strcmp(argv[0], "force"))
- *opt_all = BLANKSCREEN;
- else if (!strcmp(argv[0], "poke"))
- *opt_all = UNBLANKSCREEN;
- else {
- *opt_all = atoi(argv[0]);
- if (*opt_all < 0 || BLANK_MAX < *opt_all)
- *bad_arg = TRUE;
- }
- } else {
- *opt_all = BLANKEDSCREEN;
- }
+static int parse_snap(char **argv, char *optarg, int *optind)
+{
+ int ret;
+ char *arg;
+
+ arg = find_optional_arg(argv, optarg, optind);
+ if (!arg)
+ return 0;
+ ret = strtos32_or_err(arg, _("argument error"));
+ if (ret < 1)
+ errx(EXIT_FAILURE, _("argument error: %s"), arg);
+ return ret;
}
-static void
-parse_powersave(int argc, char **argv, int *option, int *opt_mode, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: powersave flag to set. */
- /* opt_mode: Powersaving mode, defined in vesa_blank.c */
- /* bad_arg: Set to true if an error is detected. */
-
-/* Parse a -powersave mode specification. */
-
- if (argc > 1 || *option)
- *bad_arg = TRUE;
- *option = TRUE;
- if (argc == 1) {
- if (strcmp(argv[0], "on") == 0)
- *opt_mode = VESA_BLANK_MODE_SUSPENDV;
- else if (strcmp(argv[0], "vsync") == 0)
- *opt_mode = VESA_BLANK_MODE_SUSPENDV;
- else if (strcmp(argv[0], "hsync") == 0)
- *opt_mode = VESA_BLANK_MODE_SUSPENDH;
- else if (strcmp(argv[0], "powerdown") == 0)
- *opt_mode = VESA_BLANK_MODE_POWERDOWN;
- else if (strcmp(argv[0], "off") == 0)
- *opt_mode = VESA_BLANK_MODE_OFF;
- else
- *bad_arg = TRUE;
- } else {
- *opt_mode = VESA_BLANK_MODE_OFF;
+static void parse_tabs(char **argv, char *optarg, int *optind, int *tab_array)
+{
+ int i = 0;
+
+ if (optarg) {
+ tab_array[i] = strtos32_or_err(optarg, _("argument error"));
+ i++;
+ }
+ while (argv[*optind]) {
+ if (TABS_MAX < i)
+ errx(EXIT_FAILURE, _("too many tabs"));
+ if (argv[*optind][0] == '-')
+ break;
+ tab_array[i] = strtos32_or_err(argv[*optind], _("argument error"));
+ (*optind)++;
+ i++;
}
+ tab_array[i] = -1;
}
-static void
-parse_msglevel(int argc, char **argv, int *option, int *opt_all, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Clear flag to set. */
- /* opt_all: Clear all switch to set or reset. */
- /* bad_arg: Set to true if an error is detected. */
-
- if (argc > 1 || *option)
- *bad_arg = TRUE;
- *option = TRUE;
- if (argc == 1) {
- *opt_all = atoi(argv[0]);
- if (*opt_all < CONSOLE_LEVEL_MIN || CONSOLE_LEVEL_MAX < *opt_all)
- *bad_arg = TRUE;
- } else {
- *opt_all = -1;
- }
+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;
+ ret = strtos32_or_err(arg, _("argument error"));
+ if (ret < 1 || TABS_MAX < ret)
+ errx(EXIT_FAILURE, _("argument error: %s"), arg);
+ return ret;
}
-static void
-parse_snap(int argc, char **argv, int *option, int *opt_all, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Clear flag to set. */
- /* opt_all: Clear all switch to set or reset. */
- /* bad_arg: Set to true if an error is detected. */
-
-/* Parse a -dump or -append specification. */
-
- if (argc > 1 || *option)
- *bad_arg = TRUE;
- *option = TRUE;
- if (argc == 1) {
- *opt_all = atoi(argv[0]);
- if ((*opt_all <= 0))
- *bad_arg = TRUE;
- } else {
- *opt_all = 0;
- }
+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;
+ ret = strtos32_or_err(arg, _("argument error"));
+ if (ret < 0 || BLENGTH_MAX < ret)
+ errx(EXIT_FAILURE, _("argument error: %s"), arg);
+ return ret;
}
-static void
-parse_snapfile(int argc, char **argv, int *option, int *opt_all, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Clear flag to set. */
- /* opt_all: Clear all switch to set or reset. */
- /* bad_arg: Set to true if an error is detected. */
-
-/* Parse a -file specification. */
-
- if (argc != 1 || *option)
- *bad_arg = TRUE;
- *option = TRUE;
- memset(opt_all, 0, PATH_MAX + 1);
- if (argc == 1)
- strncpy((char *)opt_all, argv[0], PATH_MAX);
+static int parse_bfreq(char **argv, char *optarg, int *optind)
+{
+ char *arg;
+
+ arg = find_optional_arg(argv, optarg, optind);
+ if (!arg)
+ return 0;
+ return strtos32_or_err(arg, _("argument error"));
}
-static void
-parse_tabs(int argc, char **argv, int *option, int *tab_array, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Clear flag to set. */
- /* tab_array: Array of tabs */
- /* bad_arg: Set to true if an error is detected. */
-
- if (*option || TABS_MAX < argc)
- *bad_arg = TRUE;
- *option = TRUE;
- tab_array[argc] = -1;
- while(argc--) {
- tab_array[argc] = atoi(argv[argc]);
- if (tab_array[argc] < 1 || TABS_MAX < tab_array[argc]) {
- *bad_arg = TRUE;
- return;
- }
- }
+static void __attribute__((__noreturn__)) usage(FILE *out)
+{
+ if (out == stderr)
+ warnx(_("argument error"));
+
+ fputs(USAGE_HEADER, out);
+ fprintf(out,
+ _(" %s [options]\n"), program_invocation_short_name);
+ fputs(USAGE_OPTIONS, out);
+ 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|color>\n"), out);
+ fputs(_(" --background <default|color>\n"), out);
+ fputs(_(" --ulcolor <bright> <color>\n"), out);
+ fputs(_(" --hbcolor <bright> <color>\n"), out);
+ fputs(_(" <color>: black blue 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);
+ 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);
+ fprintf(out, USAGE_MAN_TAIL("setterm(1)"));
+ exit(out == stderr ? EXIT_FAILURE : EXIT_SUCCESS);
}
-static void
-parse_clrtabs(int argc, char **argv, int *option, int *tab_array, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Clear flag to set. */
- /* tab_array: Array of tabs */
- /* bad_arg: Set to true if an error is detected. */
-
- if (*option || TABS_MAX < argc)
- *bad_arg = TRUE;
- *option = TRUE;
- if(argc == 0) {
- tab_array[0] = -1;
- return;
- }
- tab_array[argc] = -1;
- while(argc--) {
- tab_array[argc] = atoi(argv[argc]);
- if(tab_array[argc] < 1 || TABS_MAX < tab_array[argc]) {
- *bad_arg = TRUE;
- return;
- }
- }
+static int __attribute__((__pure__)) set_opt_flag(int opt)
+{
+ if (opt)
+ errx(EXIT_FAILURE, _("duplicate use of an option"));
+ return 1;
}
-static void
-parse_regtabs(int argc, char **argv, int *option, int *opt_len, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Clear flag to set. */
- /* opt_len: Regular tab length. */
- /* bad_arg: Set to true if an error is detected. */
-
- if (*option || argc > 1)
- *bad_arg = TRUE;
- *option = TRUE;
- if(argc == 0) {
- *opt_len = DEFAULT_TAB_LEN;
- return;
- }
- *opt_len = atoi(argv[0]);
- if(*opt_len < 1 || TABS_MAX < *opt_len) {
- *bad_arg = TRUE;
- return;
+static void parse_option(struct setterm_control *ctl, 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},
+ {"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}
+ };
+ static const ul_excl_t excl[] = {
+ { OPT_DEFAULT, OPT_STORE },
+ { OPT_TABS, OPT_CLRTABS, OPT_REGTABS },
+ { OPT_MSG, OPT_MSGLEVEL },
+ { 0 }
+ };
+ int excl_st[ARRAY_SIZE(excl)] = UL_EXCL_STATUS_INIT;
+
+ while ((c = getopt_long_only(argc, argv, "", longopts, NULL)) != -1) {
+ err_exclusive_options(c, longopts, excl, excl_st);
+ switch (c) {
+ case OPT_TERM:
+ ctl->opt_term = set_opt_flag(ctl->opt_term);
+ ctl->opt_te_terminal_name = optarg;
+ break;
+ case OPT_RESET:
+ ctl->opt_reset = set_opt_flag(ctl->opt_reset);
+ break;
+ case OPT_INITIALIZE:
+ ctl->opt_initialize = set_opt_flag(ctl->opt_initialize);
+ break;
+ case OPT_CURSOR:
+ ctl->opt_cursor = set_opt_flag(ctl->opt_cursor);
+ ctl->opt_cu_on = parse_switch(optarg, "on", "off");
+ break;
+ case OPT_REPEAT:
+ ctl->opt_repeat = set_opt_flag(ctl->opt_repeat);
+ ctl->opt_rep_on = parse_switch(optarg, "on", "off");
+ break;
+ case OPT_APPCURSORKEYS:
+ ctl->opt_appcursorkeys = set_opt_flag(ctl->opt_appcursorkeys);
+ ctl->opt_appck_on = parse_switch(optarg, "on", "off");
+ break;
+ case OPT_LINEWRAP:
+ ctl->opt_linewrap = set_opt_flag(ctl->opt_linewrap);
+ ctl->opt_li_on = parse_switch(optarg, "on", "off");
+ break;
+ case OPT_DEFAULT:
+ ctl->opt_default = set_opt_flag(ctl->opt_default);
+ break;
+ case OPT_FOREGROUND:
+ ctl->opt_foreground = set_opt_flag(ctl->opt_foreground);
+ ctl->opt_fo_color = parse_febg_color(optarg);
+ break;
+ case OPT_BACKGROUND:
+ ctl->opt_background = set_opt_flag(ctl->opt_background);
+ ctl->opt_ba_color = parse_febg_color(optarg);
+ break;
+ case OPT_ULCOLOR:
+ ctl->opt_ulcolor = set_opt_flag(ctl->opt_ulcolor);
+ ctl->opt_ul_color = parse_ulhb_color(argv, &optind);
+ break;
+ case OPT_HBCOLOR:
+ ctl->opt_hbcolor = set_opt_flag(ctl->opt_hbcolor);
+ ctl->opt_hb_color = parse_ulhb_color(argv, &optind);
+ break;
+ case OPT_INVERSESCREEN:
+ ctl->opt_inversescreen = set_opt_flag(ctl->opt_inversescreen);
+ ctl->opt_invsc_on = parse_switch(optarg, "on", "off");
+ break;
+ case OPT_BOLD:
+ ctl->opt_bold = set_opt_flag(ctl->opt_bold);
+ ctl->opt_bo_on = parse_switch(optarg, "on", "off");
+ break;
+ case OPT_HALF_BRIGHT:
+ ctl->opt_halfbright = set_opt_flag(ctl->opt_halfbright);
+ ctl->opt_hb_on = parse_switch(optarg, "on", "off");
+ break;
+ case OPT_BLINK:
+ ctl->opt_blink = set_opt_flag(ctl->opt_blink);
+ ctl->opt_bl_on = parse_switch(optarg, "on", "off");
+ break;
+ case OPT_REVERSE:
+ ctl->opt_reverse = set_opt_flag(ctl->opt_reverse);
+ ctl->opt_re_on = parse_switch(optarg, "on", "off");
+ break;
+ case OPT_UNDERLINE:
+ ctl->opt_underline = set_opt_flag(ctl->opt_underline);
+ ctl->opt_un_on = parse_switch(optarg, "on", "off");
+ break;
+ case OPT_STORE:
+ ctl->opt_store = set_opt_flag(ctl->opt_store);
+ break;
+ case OPT_CLEAR:
+ ctl->opt_clear = set_opt_flag(ctl->opt_clear);
+ ctl->opt_cl_all = parse_switch(optarg, "all", "reset");
+ break;
+ case OPT_TABS:
+ ctl->opt_tabs = set_opt_flag(ctl->opt_tabs);
+ parse_tabs(argv, optarg, &optind, ctl->opt_tb_array);
+ break;
+ case OPT_CLRTABS:
+ ctl->opt_clrtabs = set_opt_flag(ctl->opt_clrtabs);
+ parse_tabs(argv, optarg, &optind, ctl->opt_tb_array);
+ break;
+ case OPT_REGTABS:
+ ctl->opt_regtabs = set_opt_flag(ctl->opt_regtabs);
+ ctl->opt_rt_len = parse_regtabs(argv, optarg, &optind);
+ break;
+ case OPT_BLANK:
+ ctl->opt_blank = set_opt_flag(ctl->opt_blank);
+ ctl->opt_bl_min = parse_blank(argv, optarg, &optind);
+ break;
+ case OPT_DUMP:
+ ctl->opt_snap = set_opt_flag(ctl->opt_snap);
+ ctl->opt_sn_num = parse_snap(argv, optarg, &optind);
+ break;
+ case OPT_APPEND:
+ ctl->opt_append = set_opt_flag(ctl->opt_append);
+ ctl->opt_sn_num = parse_snap(argv, optarg, &optind);
+ break;
+ case OPT_FILE:
+ ctl->opt_snapfile = set_opt_flag(ctl->opt_snapfile);
+ ctl->opt_sn_name = optarg;
+ break;
+ case OPT_MSG:
+ ctl->opt_msg = set_opt_flag(ctl->opt_msg);
+ ctl->opt_msg_on = parse_switch(optarg, "on", "off");
+ break;
+ case OPT_MSGLEVEL:
+ ctl->opt_msglevel = set_opt_flag(ctl->opt_msglevel);
+ ctl->opt_msglevel_num = parse_msglevel(optarg);
+ if (ctl->opt_msglevel_num == 0) {
+ ctl->opt_msg = set_opt_flag(ctl->opt_msg);
+ ctl->opt_msg_on |= 1;
+ }
+ break;
+ case OPT_POWERSAVE:
+ ctl->opt_powersave = set_opt_flag(ctl->opt_powersave);
+ ctl->opt_ps_mode = parse_powersave(optarg);
+ break;
+ case OPT_POWERDOWN:
+ ctl->opt_powerdown = set_opt_flag(ctl->opt_powerdown);
+ ctl->opt_pd_min = parse_blank(argv, optarg, &optind);
+ break;
+ case OPT_BLENGTH:
+ ctl->opt_blength = set_opt_flag(ctl->opt_blength);
+ ctl->opt_blength_l = parse_blength(argv, optarg, &optind);
+ break;
+ case OPT_BFREQ:
+ ctl->opt_bfreq = set_opt_flag(ctl->opt_bfreq);
+ ctl->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);
+ }
}
}
+/* End of command line parsing routines. */
-static void
-parse_blength(int argc, char **argv, int *option, int *opt_all, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Clear flag to set. */
- /* opt_all */
- /* bad_arg: Set to true if an error is detected. */
-
-/* Parse -blength specification. */
-
- if (argc > 1 || *option)
- *bad_arg = TRUE;
- *option = TRUE;
- if (argc == 1) {
- *opt_all = atoi(argv[0]);
- if (BLENGTH_MAX < *opt_all)
- *bad_arg = TRUE;
- } else {
- *opt_all = 0;
- }
-}
+/* Return the specified terminfo string, or an empty string if no such
+ * terminfo capability exists. */
+static char *ti_entry(const char *name)
+{
+ char *buf_ptr;
-static void
-parse_bfreq(int argc, char **argv, int *option, int *opt_all, int *bad_arg) {
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* option: Clear flag to set. */
- /* opt_all */
- /* bad_arg: Set to true if an error is detected. */
-
-/* Parse -bfreq specification. */
-
- if (argc > 1 || *option)
- *bad_arg = TRUE;
- *option = TRUE;
- if (argc == 1) {
- *opt_all = atoi(argv[0]);
- } else {
- *opt_all = 0;
- }
+ if ((buf_ptr = tigetstr((char *)name)) == (char *)-1)
+ buf_ptr = NULL;
+ return buf_ptr;
}
-
-static void
-show_tabs(void) {
+static void show_tabs(void)
+{
int i, co = tigetnum("cols");
- if(co > 0) {
+ if (co > 0) {
printf("\r ");
- for(i = 10; i < co-2; i+=10)
+ for (i = 10; i < co - 2; i += 10)
printf("%-10d", i);
putchar('\n');
- for(i = 1; i <= co; i++)
- putchar(i%10+'0');
+ for (i = 1; i <= co; i++)
+ putchar(i % 10 + '0');
putchar('\n');
- for(i = 1; i < co; i++)
+ for (i = 1; i < co; i++)
printf("\tT\b");
putchar('\n');
}
}
-static void __attribute__ ((__noreturn__))
-usage(FILE *out) {
-/* Print error message about arguments, and the command's syntax. */
-
- if (out == stderr)
- warnx(_("Argument error."));
-
- fputs(_("\nUsage:\n"), out);
- fprintf(out,
- _(" %s [options]\n"), program_invocation_short_name);
-
- fputs(_("\nOptions:\n"), out);
- 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);
- 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);
-
- fprintf(out, USAGE_MAN_TAIL("setterm(1)"));
-
- exit(out == stderr ? EXIT_FAILURE : EXIT_SUCCESS);
-}
+static int open_snapshot_device(struct setterm_control *ctl)
+{
+ int fd;
-#define STRCMP(str1,str2) strncmp(str1,str2,strlen(str1))
-
-static void
-parse_option(char *option, int argc, char **argv, int *bad_arg) {
- /* option: Option with leading '-' removed. */
- /* argc: Number of arguments for this option. */
- /* argv: Arguments for this option. */
- /* bad_arg: Set to true if an error is detected. */
-
-/* Parse a single specification. */
-
- if (STRCMP(option, "term") == 0)
- parse_term(argc, argv, &opt_term, &opt_te_terminal_name, bad_arg);
- else if (STRCMP(option, "reset") == 0)
- parse_none(argc, argv, &opt_reset, bad_arg);
- else if (STRCMP(option, "initialize") == 0)
- parse_none(argc, argv, &opt_initialize, bad_arg);
- else if (STRCMP(option, "cursor") == 0)
- parse_switch(argc, argv, &opt_cursor, &opt_cu_on, bad_arg);
- else if (STRCMP(option, "repeat") == 0)
- parse_switch(argc, argv, &opt_repeat, &opt_rep_on, bad_arg);
- else if (STRCMP(option, "appcursorkeys") == 0)
- parse_switch(argc, argv, &opt_appcursorkeys, &opt_appck_on, bad_arg);
- else if (STRCMP(option, "linewrap") == 0)
- parse_switch(argc, argv, &opt_linewrap, &opt_li_on, bad_arg);
- else if (STRCMP(option, "default") == 0)
- parse_none(argc, argv, &opt_default, bad_arg);
- else if (STRCMP(option, "foreground") == 0)
- par_color(argc, argv, &opt_foreground, &opt_fo_color, bad_arg);
- else if (STRCMP(option, "background") == 0)
- par_color(argc, argv, &opt_background, &opt_ba_color, bad_arg);
- else if (STRCMP(option, "ulcolor") == 0)
- par_color2(argc, argv, &opt_ulcolor, &opt_ul_color, bad_arg);
- else if (STRCMP(option, "hbcolor") == 0)
- par_color2(argc, argv, &opt_hbcolor, &opt_hb_color, bad_arg);
- else if (STRCMP(option, "inversescreen") == 0)
- parse_switch(argc, argv, &opt_inversescreen, &opt_invsc_on, bad_arg);
- else if (STRCMP(option, "bold") == 0)
- parse_switch(argc, argv, &opt_bold, &opt_bo_on, bad_arg);
- else if (STRCMP(option, "half-bright") == 0)
- parse_switch(argc, argv, &opt_halfbright, &opt_hb_on, bad_arg);
- else if (STRCMP(option, "blink") == 0)
- parse_switch(argc, argv, &opt_blink, &opt_bl_on, bad_arg);
- else if (STRCMP(option, "reverse") == 0)
- parse_switch(argc, argv, &opt_reverse, &opt_re_on, bad_arg);
- else if (STRCMP(option, "underline") == 0)
- parse_switch(argc, argv, &opt_underline, &opt_un_on, bad_arg);
- else if (STRCMP(option, "store") == 0)
- parse_none(argc, argv, &opt_store, bad_arg);
- else if (STRCMP(option, "clear") == 0)
- parse_clear(argc, argv, &opt_clear, &opt_cl_all, bad_arg);
- else if (STRCMP(option, "tabs") == 0)
- parse_tabs(argc, argv, &opt_tabs, opt_tb_array, bad_arg);
- else if (STRCMP(option, "clrtabs") == 0)
- parse_clrtabs(argc, argv, &opt_clrtabs, opt_tb_array, bad_arg);
- else if (STRCMP(option, "regtabs") == 0)
- parse_regtabs(argc, argv, &opt_regtabs, &opt_rt_len, bad_arg);
- else if (STRCMP(option, "blank") == 0)
- parse_blank(argc, argv, &opt_blank, &opt_bl_min, bad_arg);
- else if (STRCMP(option, "dump") == 0)
- parse_snap(argc, argv, &opt_snap, &opt_sn_num, bad_arg);
- else if (STRCMP(option, "append") == 0)
- parse_snap(argc, argv, &opt_append, &opt_sn_num, bad_arg);
- else if (STRCMP(option, "file") == 0)
- parse_snapfile(argc, argv, &opt_snapfile, (int *)opt_sn_name, bad_arg);
- else if (STRCMP(option, "msg") == 0)
- parse_switch(argc, argv, &opt_msg, &opt_msg_on, bad_arg);
- else if (STRCMP(option, "msglevel") == 0)
- parse_msglevel(argc, argv, &opt_msglevel, &opt_msglevel_num, bad_arg);
- else if (STRCMP(option, "powersave") == 0)
- parse_powersave(argc, argv, &opt_powersave, &opt_ps_mode, bad_arg);
- else if (STRCMP(option, "powerdown") == 0)
- parse_blank(argc, argv, &opt_powerdown, &opt_pd_min, bad_arg);
- else if (STRCMP(option, "blength") == 0)
- parse_blength(argc, argv, &opt_blength, &opt_blength_l, bad_arg);
- else if (STRCMP(option, "bfreq") == 0)
- parse_bfreq(argc, argv, &opt_bfreq, &opt_bfreq_f, bad_arg);
- else if (STRCMP(option, "version") == 0) {
- printf(_("%s from %s\n"), program_invocation_short_name,
- PACKAGE_STRING);
- exit(EXIT_SUCCESS);
- } else if (STRCMP(option, "help") == 0)
- usage(stdout);
+ if (ctl->opt_sn_num)
+ xasprintf(&ctl->in_device, "/dev/vcsa%d", ctl->opt_sn_num);
else
- *bad_arg = TRUE;
+ xasprintf(&ctl->in_device, "/dev/vcsa");
+ fd = open(ctl->in_device, O_RDONLY);
+ if (fd < 0)
+ err(EXIT_DUMPFILE, _("cannot read %s"), ctl->in_device);
+ return fd;
}
-/* End of command line parsing routines. */
-
-static char *ti_entry(const char *name) {
- /* name: Terminfo capability string to lookup. */
-
-/* Return the specified terminfo string, or an empty string if no such terminfo
- * capability exists.
- */
+static void set_blanking(struct setterm_control *ctl)
+{
+ char ioctlarg;
+ int ret;
- char *buf_ptr;
+ if (0 <= ctl->opt_bl_min) {
+ printf("\033[9;%d]", ctl->opt_bl_min);
+ return;
+ }
+ switch (ctl->opt_bl_min) {
+ case BLANKSCREEN:
+ ioctlarg = TIOCL_BLANKSCREEN;
+ if (ioctl(STDIN_FILENO, TIOCLINUX, &ioctlarg))
+ warn(_("cannot force blank"));
+ break;
+ case UNBLANKSCREEN:
+ ioctlarg = TIOCL_UNBLANKSCREEN;
+ if (ioctl(STDIN_FILENO, TIOCLINUX, &ioctlarg))
+ warn(_("cannot force unblank"));
+ break;
+ case BLANKEDSCREEN:
+ ioctlarg = TIOCL_BLANKEDSCREEN;
+ ret = ioctl(STDIN_FILENO, TIOCLINUX, &ioctlarg);
+ if (ret < 0)
+ warn(_("cannot get blank status"));
+ else
+ printf("%d\n", ret);
+ break;
+ default: /* should be impossible to reach */
+ abort();
+ }
+ return;
+}
- if ((buf_ptr = tigetstr((char *)name)) == (char *)-1)
- buf_ptr = NULL;
- return buf_ptr;
+static void screendump(struct setterm_control *ctl)
+{
+ unsigned char header[4];
+ unsigned int rows, cols;
+ int fd;
+ FILE *out;
+ size_t i, j;
+ ssize_t rc;
+ char *inbuf, *outbuf, *p, *q;
+ char dump_default[] = "screen.dump";
+
+ /* open source and destination files */
+ fd = open_snapshot_device(ctl);
+ if (!ctl->opt_sn_name)
+ ctl->opt_sn_name = dump_default;
+ out = fopen(ctl->opt_sn_name, ctl->opt_snap ? "w" : "a");
+ if (!out)
+ err(EXIT_DUMPFILE, _("can not open dump file %s for output"), ctl->opt_sn_name);
+ /* determine snapshot size */
+ if (read(fd, header, 4) != 4)
+ err(EXIT_DUMPFILE, _("cannot read %s"), ctl->in_device);
+ rows = header[0];
+ cols = header[1];
+ if (rows * cols == 0)
+ err(EXIT_DUMPFILE, _("cannot read %s"), ctl->in_device);
+ /* allocate buffers */
+ inbuf = xmalloc(rows * cols * 2);
+ outbuf = xmalloc(rows * (cols + 1));
+ /* read input */
+ rc = read(fd, inbuf, rows * cols * 2);
+ if (rc < 0 || (size_t)rc != rows * cols * 2)
+ err(EXIT_DUMPFILE, _("cannot read %s"), ctl->in_device);
+ p = inbuf;
+ q = outbuf;
+ /* copy inbuf to 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';
+ }
+ fwrite(outbuf, 1, q - outbuf, out);
+ /* clean up allocations */
+ close(fd);
+ free(inbuf);
+ free(outbuf);
+ free(ctl->in_device);
+ if (close_stream(out) != 0)
+ errx(EXIT_FAILURE, _("write error"));
+ return;
}
-static void
-perform_sequence(int vcterm) {
- /* vcterm: Set if terminal is a virtual console. */
+/* Some options are applicable when terminal is virtual console. */
+static int vc_only(struct setterm_control *ctl, const char *err)
+{
+ if (!ctl->vcterm) {
+ if (err)
+ warnx(_("terminal %s does not support %s"),
+ ctl->opt_te_terminal_name, err);
+ }
+ return ctl->vcterm;
+}
+static void perform_sequence(struct setterm_control *ctl)
+{
int result;
-/* Perform the selected options. */
/* -reset. */
- if (opt_reset) {
+ if (ctl->opt_reset)
putp(ti_entry("rs1"));
- }
/* -initialize. */
- if (opt_initialize) {
+ if (ctl->opt_initialize)
putp(ti_entry("is2"));
- }
/* -cursor [on|off]. */
- if (opt_cursor) {
- if (opt_cu_on)
+ if (ctl->opt_cursor) {
+ if (ctl->opt_cu_on)
putp(ti_entry("cnorm"));
else
putp(ti_entry("civis"));
}
- /* -linewrap [on|off]. Vc only (vt102) */
- if (opt_linewrap && vcterm)
- fputs(opt_li_on ? "\033[?7h" : "\033[?7l", stdout);
+ /* -linewrap [on|off]. */
+ if (ctl->opt_linewrap)
+ fputs(ctl->opt_li_on ? "\033[?7h" : "\033[?7l", stdout);
- /* -repeat [on|off]. Vc only (vt102) */
- if (opt_repeat && vcterm)
- fputs(opt_rep_on ? "\033[?8h" : "\033[?8l", stdout);
+ /* -repeat [on|off]. */
+ if (ctl->opt_repeat && vc_only(ctl, "--repeat"))
+ fputs(ctl->opt_rep_on ? "\033[?8h" : "\033[?8l", stdout);
- /* -appcursorkeys [on|off]. Vc only (vt102) */
- if (opt_appcursorkeys && vcterm)
- fputs(opt_appck_on ? "\033[?1h" : "\033[?1l", stdout);
+ /* -appcursorkeys [on|off]. */
+ if (ctl->opt_appcursorkeys && vc_only(ctl, "--appcursorkeys"))
+ fputs(ctl->opt_appck_on ? "\033[?1h" : "\033[?1l", stdout);
/* -default. Vc sets default rendition, otherwise clears all
- * attributes.
- */
- if (opt_default) {
- if (vcterm)
+ * attributes. */
+ if (ctl->opt_default) {
+ if (vc_only(ctl, NULL))
printf("\033[0m");
else
putp(ti_entry("sgr0"));
}
- /* -foreground black|red|green|yellow|blue|magenta|cyan|white|default.
- * Vc only (ANSI).
- */
- if (opt_foreground && vcterm)
- printf("\033[3%c%s", '0' + opt_fo_color, "m");
-
- /* -background black|red|green|yellow|blue|magenta|cyan|white|default.
- * Vc only (ANSI).
- */
- if (opt_background && vcterm)
- printf("\033[4%c%s", '0' + opt_ba_color, "m");
-
- /* -ulcolor black|red|green|yellow|blue|magenta|cyan|white|default.
- * Vc only.
- */
- if (opt_ulcolor && vcterm) {
- printf("\033[1;%d]", opt_ul_color);
- }
+ /* -foreground black|red|green|yellow|blue|magenta|cyan|white|default. */
+ if (ctl->opt_foreground)
+ printf("\033[3%c%s", '0' + ctl->opt_fo_color, "m");
- /* -hbcolor black|red|green|yellow|blue|magenta|cyan|white|default.
- * Vc only.
- */
- if (opt_hbcolor && vcterm) {
- printf("\033[2;%d]", opt_hb_color);
- }
+ /* -background black|red|green|yellow|blue|magenta|cyan|white|default. */
+ if (ctl->opt_background)
+ printf("\033[4%c%s", '0' + ctl->opt_ba_color, "m");
+
+ /* -ulcolor black|red|green|yellow|blue|magenta|cyan|white|default. */
+ if (ctl->opt_ulcolor && vc_only(ctl, "--ulcolor"))
+ printf("\033[1;%d]", ctl->opt_ul_color);
+
+ /* -hbcolor black|red|green|yellow|blue|magenta|cyan|white|default. */
+ if (ctl->opt_hbcolor)
+ printf("\033[2;%d]", ctl->opt_hb_color);
- /* -inversescreen [on|off]. Vc only (vt102).
- */
- if (opt_inversescreen && vcterm)
- fputs(opt_invsc_on ? "\033[?5h" : "\033[?5l", stdout);
+ /* -inversescreen [on|off]. */
+ if (ctl->opt_inversescreen)
+ fputs(ctl->opt_invsc_on ? "\033[?5h" : "\033[?5l", stdout);
/* -bold [on|off]. Vc behaves as expected, otherwise off turns off
- * all attributes.
- */
- if (opt_bold) {
- if (opt_bo_on)
+ * all attributes. */
+ if (ctl->opt_bold) {
+ if (ctl->opt_bo_on)
putp(ti_entry("bold"));
else {
- if (vcterm)
+ if (vc_only(ctl, NULL))
fputs("\033[22m", stdout);
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)
+ /* -half-bright [on|off]. Vc behaves as expected, otherwise off
+ * turns off all attributes. */
+ if (ctl->opt_halfbright) {
+ if (ctl->opt_hb_on)
putp(ti_entry("dim"));
else {
- if (vcterm)
+ if (vc_only(ctl, NULL))
fputs("\033[22m", stdout);
else
putp(ti_entry("sgr0"));
@@ -929,13 +917,12 @@ perform_sequence(int vcterm) {
}
/* -blink [on|off]. Vc behaves as expected, otherwise off turns off
- * all attributes.
- */
- if (opt_blink) {
- if (opt_bl_on)
+ * all attributes. */
+ if (ctl->opt_blink) {
+ if (ctl->opt_bl_on)
putp(ti_entry("blink"));
else {
- if (vcterm)
+ if (vc_only(ctl, NULL))
fputs("\033[25m", stdout);
else
putp(ti_entry("sgr0"));
@@ -943,13 +930,12 @@ perform_sequence(int vcterm) {
}
/* -reverse [on|off]. Vc behaves as expected, otherwise off turns
- * off all attributes.
- */
- if (opt_reverse) {
- if (opt_re_on)
+ * off all attributes. */
+ if (ctl->opt_reverse) {
+ if (ctl->opt_re_on)
putp(ti_entry("rev"));
else {
- if (vcterm)
+ if (vc_only(ctl, NULL))
fputs("\033[27m", stdout);
else
putp(ti_entry("sgr0"));
@@ -957,279 +943,146 @@ perform_sequence(int vcterm) {
}
/* -underline [on|off]. */
- if (opt_underline)
- putp(ti_entry(opt_un_on ? "smul" : "rmul"));
+ if (ctl->opt_underline)
+ putp(ti_entry(ctl->opt_un_on ? "smul" : "rmul"));
- /* -store. Vc only. */
- if (opt_store && vcterm)
+ /* -store. */
+ if (ctl->opt_store && vc_only(ctl, "--store"))
fputs("\033[8]", stdout);
/* -clear [all|rest]. */
- if (opt_clear)
- putp(ti_entry(opt_cl_all ? "clear" : "ed"));
+ if (ctl->opt_clear)
+ putp(ti_entry(ctl->opt_cl_all ? "clear" : "ed"));
- /* -tabs Vc only. */
- if (opt_tabs && vcterm) {
- int i;
-
- if (opt_tb_array[0] == -1)
+ /* -tabs. */
+ if (ctl->opt_tabs) {
+ if (ctl->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]);
+ int i;
+
+ for (i = 0; ctl->opt_tb_array[i] > 0; i++)
+ printf("\033[%dG\033H", ctl->opt_tb_array[i]);
putchar('\r');
}
}
- /* -clrtabs Vc only. */
- if (opt_clrtabs && vcterm) {
+ /* -clrtabs. */
+ if (ctl->opt_clrtabs && vc_only(ctl, "--clrtabs")) {
int i;
- if (opt_tb_array[0] == -1)
+ if (ctl->opt_tb_array[0] == -1)
fputs("\033[3g", stdout);
else
- for(i=0; opt_tb_array[i] > 0; i++)
- printf("\033[%dG\033[g", opt_tb_array[i]);
+ for (i = 0; ctl->opt_tb_array[i] > 0; i++)
+ printf("\033[%dG\033[g", ctl->opt_tb_array[i]);
putchar('\r');
}
- /* -regtabs Vc only. */
- if (opt_regtabs && vcterm) {
+ /* -regtabs. */
+ if (ctl->opt_regtabs && vc_only(ctl, "--regtabs")) {
int i;
fputs("\033[3g\r", stdout);
- for(i=opt_rt_len+1; i<=TABS_MAX; i+=opt_rt_len)
- printf("\033[%dC\033H",opt_rt_len);
+ for (i = ctl->opt_rt_len + 1; i <= TABS_MAX; i += ctl->opt_rt_len)
+ printf("\033[%dC\033H", ctl->opt_rt_len);
putchar('\r');
}
/* -blank [0-60]. */
- 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))
- warn(_("cannot force blank"));
- } else if (opt_bl_min == UNBLANKSCREEN) {
- char ioctlarg = TIOCL_UNBLANKSCREEN;
- if (ioctl(0,TIOCLINUX,&ioctlarg))
- warn(_("cannot force unblank"));
- } else if (opt_bl_min == BLANKEDSCREEN) {
- char ioctlarg = TIOCL_BLANKEDSCREEN;
- int ret;
- ret = ioctl(0,TIOCLINUX,&ioctlarg);
- if (ret < 0)
- warn(_("cannot get blank status"));
- else
- printf("%d\n",ret);
- }
- }
+ if (ctl->opt_blank && vc_only(ctl, "--blank"))
+ set_blanking(ctl);
/* -powersave [on|vsync|hsync|powerdown|off] (console) */
- if (opt_powersave) {
+ if (ctl->opt_powersave) {
char ioctlarg[2];
ioctlarg[0] = TIOCL_SETVESABLANK;
- ioctlarg[1] = opt_ps_mode;
- if (ioctl(0,TIOCLINUX,ioctlarg))
+ ioctlarg[1] = ctl->opt_ps_mode;
+ if (ioctl(STDIN_FILENO, TIOCLINUX, ioctlarg))
warn(_("cannot (un)set powersave mode"));
}
/* -powerdown [0-60]. */
- if (opt_powerdown) {
- printf("\033[14;%d]", opt_pd_min);
- }
+ if (ctl->opt_powerdown)
+ printf("\033[14;%d]", ctl->opt_pd_min);
/* -snap [1-NR_CONS]. */
- if (opt_snap || opt_append) {
- FILE *F;
-
- F = fopen(opt_sn_name, opt_snap ? "w" : "a");
- if (!F)
- err(EXIT_DUMPFILE, _("can not open dump file %s for output"),
- opt_sn_name);
- screendump(opt_sn_num, F);
- if (close_stream(F) != 0)
- errx(EXIT_FAILURE, _("write error"));
- }
+ if (ctl->opt_snap || ctl->opt_append)
+ screendump(ctl);
- /* -msg [on|off]. */
- if (opt_msg && vcterm) {
- if (opt_msg_on)
- /* 7 -- Enable printk's to console */
+ /* -msg [on|off]. Controls printk's to console. */
+ if (ctl->opt_msg && vc_only(ctl, "--msg")) {
+ if (ctl->opt_msg_on)
result = klogctl(SYSLOG_ACTION_CONSOLE_ON, NULL, 0);
else
- /* 6 -- Disable printk's to console */
result = klogctl(SYSLOG_ACTION_CONSOLE_OFF, NULL, 0);
if (result != 0)
warn(_("klogctl error"));
}
- /* -msglevel [0-8] */
- if (opt_msglevel && vcterm) {
- /* 8 -- Set level of messages printed to console */
- result = klogctl(SYSLOG_ACTION_CONSOLE_LEVEL, NULL, opt_msglevel_num);
+ /* -msglevel [0-8]. Console printk message level. */
+ if (ctl->opt_msglevel_num && vc_only(ctl, "--msglevel")) {
+ result =
+ klogctl(SYSLOG_ACTION_CONSOLE_LEVEL, NULL,
+ ctl->opt_msglevel_num);
if (result != 0)
warn(_("klogctl error"));
}
/* -blength [0-2000] */
- if (opt_blength && vcterm) {
- printf("\033[11;%d]", opt_blength_l);
+ if (ctl->opt_blength && vc_only(ctl, "--blength")) {
+ printf("\033[11;%d]", ctl->opt_blength_l);
}
/* -bfreq freqnumber */
- if (opt_bfreq && vcterm) {
- printf("\033[10;%d]", opt_bfreq_f);
+ if (ctl->opt_bfreq && vc_only(ctl, "--bfreq")) {
+ printf("\033[10;%d]", ctl->opt_bfreq_f);
}
-
}
-static void
-screendump(int vcnum, FILE * F)
+static void init_terminal(struct setterm_control *ctl)
{
- 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);
-}
+ int term_errno;
-int
-main(int argc, char **argv) {
- int bad_arg = FALSE; /* Set if error in arguments. */
- int arg, modifier;
- char *term; /* Terminal type. */
- int vcterm; /* Set if terminal is a virtual console. */
- int errret;
-
- setlocale(LC_ALL, "");
- bindtextdomain(PACKAGE, LOCALEDIR);
- textdomain(PACKAGE);
- atexit(close_stdout);
-
- if (argc < 2)
- bad_arg = TRUE;
-
- /* Parse arguments. */
-
- for (arg = 1; arg < argc;) {
- if (*argv[arg] == '-') {
-
- /* Parse a single option. */
-
- for (modifier = arg + 1; modifier < argc; modifier++) {
- if (*argv[modifier] == '-') break;
- }
- parse_option(argv[arg] + 1, modifier - arg - 1,
- &argv[arg + 1], &bad_arg);
- arg = modifier;
- } else {
- bad_arg = TRUE;
- arg++;
- }
- }
-
- /* Display syntax message if error in arguments. */
-
- if (bad_arg)
- usage(stderr);
-
- /* Find out terminal name. */
-
- if (opt_term) {
- term = opt_te_terminal_name;
- } else {
- term = getenv("TERM");
- if (term == NULL)
+ if (!ctl->opt_te_terminal_name) {
+ ctl->opt_te_terminal_name = getenv("TERM");
+ if (ctl->opt_te_terminal_name == NULL)
errx(EXIT_FAILURE, _("$TERM is not defined."));
}
/* Find terminfo entry. */
-
- if (setupterm(term, 1, &errret))
- switch(errret) {
+ if (setupterm(ctl->opt_te_terminal_name, STDOUT_FILENO, &term_errno))
+ switch (term_errno) {
case -1:
errx(EXIT_FAILURE, _("terminfo database cannot be found"));
case 0:
- errx(EXIT_FAILURE, _("%s: unknown terminal type"), term);
+ errx(EXIT_FAILURE, _("%s: unknown terminal type"), ctl->opt_te_terminal_name);
case 1:
errx(EXIT_FAILURE, _("terminal is hardcopy"));
}
/* See if the terminal is a virtual console terminal. */
+ ctl->vcterm = (!strncmp(ctl->opt_te_terminal_name, "con", 3) ||
+ !strncmp(ctl->opt_te_terminal_name, "linux", 5));
+}
- vcterm = (!strncmp(term, "con", 3) || !strncmp(term, "linux", 5));
- /* Perform the selected options. */
+int main(int argc, char **argv)
+{
+ struct setterm_control ctl = { 0 };
+
+ setlocale(LC_ALL, "");
+ bindtextdomain(PACKAGE, LOCALEDIR);
+ textdomain(PACKAGE);
+ atexit(close_stdout);
+
+ if (argc < 2)
+ usage(stderr);
- perform_sequence(vcterm);
+ parse_option(&ctl, argc, argv);
+ init_terminal(&ctl);
+ perform_sequence(&ctl);
return EXIT_SUCCESS;
}