Skip to content

Commit

Permalink
term: support Solaris console
Browse files Browse the repository at this point in the history
  • Loading branch information
akinomyoga committed Feb 22, 2021
1 parent 37363be commit 6ca0b8c
Show file tree
Hide file tree
Showing 8 changed files with 370 additions and 162 deletions.
25 changes: 24 additions & 1 deletion lib/init-cmap.sh
Expand Up @@ -133,7 +133,7 @@ function ble/init:cmap/initialize {
ble-bind --csi '7~' home
ble-bind --csi '8~' end
local kdch1; ble/util/assign kdch1 'tput kD 2>/dev/null || tput kdch1 2>/dev/null'
[[ $kdch1 == $'\x7F' ]] && ble-bind -k 'DEL' delete
[[ $kdch1 == $'\x7F' || $TERM == sun* ]] && ble-bind -k 'DEL' delete

# vt220, xterm, rxvt
ble-bind --csi '11~' f1
Expand Down Expand Up @@ -240,6 +240,29 @@ function ble/init:cmap/initialize {
ble/init:cmap/bind-single-csi '[ D' f4
ble/init:cmap/bind-single-csi '[ E' f5

# sun specific (Solaris)
ble/init:cmap/bind-single-csi '2 4 7 z' insert
ble/init:cmap/bind-single-csi '2 1 4 z' home
ble/init:cmap/bind-single-csi '2 2 0 z' end
ble/init:cmap/bind-single-csi '2 2 2 z' prior
ble/init:cmap/bind-single-csi '2 1 6 z' next
ble/init:cmap/bind-single-csi '2 2 4 z' f1
ble/init:cmap/bind-single-csi '2 2 5 z' f2
ble/init:cmap/bind-single-csi '2 2 6 z' f3
ble/init:cmap/bind-single-csi '2 2 7 z' f4
ble/init:cmap/bind-single-csi '2 2 8 z' f5
ble/init:cmap/bind-single-csi '2 2 9 z' f6
ble/init:cmap/bind-single-csi '2 3 0 z' f7
ble/init:cmap/bind-single-csi '2 3 1 z' f8
ble/init:cmap/bind-single-csi '2 3 2 z' f9
ble/init:cmap/bind-single-csi '2 3 3 z' f10
ble/init:cmap/bind-single-csi '2 3 4 z' f11
ble/init:cmap/bind-single-csi '2 3 5 z' f12
# ble/init:cmap/bind-single-csi '2 z' insert # terminfo
# ble/init:cmap/bind-single-csi '3 z' delete # terminfo
# ble/init:cmap/bind-single-csi '1 9 2 z' f11
# ble/init:cmap/bind-single-csi '1 9 3 z' f12

# 修飾キー 'CAN @ ?'
#
# 取り敢えず CAN で始まる修飾キーは無効にしておく。何故なら、
Expand Down
17 changes: 11 additions & 6 deletions lib/init-term.sh
Expand Up @@ -77,7 +77,8 @@ function ble/init:term/initialize {
_ble_term_xenl=1
[[ $_ble_term_tput ]] &&
! ble/init:term/tput xenl:xn &>/dev/null &&
_ble_term_xenl=0
_ble_term_xenl=
[[ $TERM == sun* ]] && _ble_term_xenl=
ble/init:term/register-varname _ble_term_xenl

# bce (background color erase)
Expand All @@ -96,9 +97,9 @@ function ble/init:term/initialize {
ble/init:term/register-varname _ble_term_it

# IND/RI, CR, LF, FS
ble/init:term/define-cap.2 _ble_term_ind $'\eD' ind:sf
ble/init:term/define-cap _ble_term_ri $'\eM' ri:sr
ble/init:term/define-cap _ble_term_cr $'\r' cr:cr
ble/init:term/define-cap.2 _ble_term_ind $'\n' ind:sf # $'\eD'
ble/init:term/define-cap _ble_term_ri '' ri:sr # $'\eM'
ble/init:term/define-cap _ble_term_cr $'\r' cr:cr
if [[ $OSTYPE == msys && ! $_ble_term_CR ]]; then # msys-1.0
[[ $_ble_term_cr ]] || _ble_term_cr=$'\e[G'
if [[ $TERM == cygwin ]]; then
Expand All @@ -118,6 +119,9 @@ function ble/init:term/initialize {
_ble_term_cub=${_ble_term_cub//123/%d}
# ※もし 122 だとか 124 だとかになると上記では駄目

_ble_term_ri_or_cuu1=${_ble_term_ri:-${_ble_term_cuu//'%d'/1}}
ble/init:term/register-varname _ble_term_ri_or_cuu1

# CUP
ble/init:term/define-cap _ble_term_cup $'\e[13;35H' cup:cm 12 34
_ble_term_cup=${_ble_term_cup//13/%l}
Expand Down Expand Up @@ -165,9 +169,10 @@ function ble/init:term/initialize {
_ble_term_ech=${_ble_term_ech//123/%d}

# DECSC/DECRC or SCOSC/SCORC
ble/init:term/define-cap _ble_term_sc $'\e[s' sc:sc
ble/init:term/define-cap _ble_term_rc $'\e[u' rc:rc
ble/init:term/define-cap _ble_term_sc $'\e7' sc:sc # \e[s
ble/init:term/define-cap _ble_term_rc $'\e8' rc:rc # \e[u
[[ $TERM == minix ]] && _ble_term_sc= _ble_term_rc=
# Note: TERM=sun{,-color}: terminfo にはないが \e7 \e8 が使える。

# Cursors
ble/init:term/define-cap _ble_term_Ss '' Ss:Ss 123 # DECSCUSR
Expand Down
5 changes: 5 additions & 0 deletions memo/ChangeLog.md
Expand Up @@ -56,6 +56,11 @@
- mandb: improve extraction and cache for each locale `#D1480` 3588158
- decode (rlfunc): work around incomplete bytes in keyseq (reported by onelittlehope) `#D1483` 3559658 beb0383 0000000

## Compatibility

- term: work around quirks of Solaris xpg4 awk `#D1481` 0000000
- term: support key sequences and control sequences of Solaris console `#D1481` 0000000

## Internal changes and fixes

- main: include hostname in local runtime directory `#D1444` 6494836
Expand Down
127 changes: 127 additions & 0 deletions note.txt
Expand Up @@ -3811,6 +3811,133 @@ bash_tips

2021-02-20

* term: sum (Solaris console) IND/RI が使えない。他色々動いていない [#D1481]

* RI が使えない時にどの様にすれば良いか。

* 使っている箇所の一つは vbell である。

例えば prompt の上の行に一行 IL するという方針だと…。vbell を表示する度
にずれてしまう。今ここで欲しいのは "上に一行も余裕がない時限定で一行確保
する" という機能である。

* ble/canvas/put-ri.draw

これは2箇所から使われている。両方とも
ble/canvas/panel/ensure-tmargin.draw という関数の中から使われていて、この
関数は vbell から使う為の物である。

* ble/canvas/panel#clear-after.draw
これは単に cuu に置き換えれば良い気がする→置き換えた。

結局 vbell が問題になる。_ble_term_ri が空の時に別の手法で vbell を表示す
る?

a 例えば xterm_title を使って表示するか。

元から設定されている値を保存・復元したりするのが面倒である。push/pop の
エスケープシーケンスも存在するかもしれないが、それに対応しているかどう
かの判定も面倒である。というより RI を対応していない端末が xterm title
等に対応しているとは思えない。この手法は追求しても余り意味がない。

b 或いは、一番下の行に表示するというのは可能だろうか。

この方法を取る場合には現在の canvas の tmargin の取り扱いを工夫しなけれ
ばならない。というか RI が使えない場合には canvas の tmargin も振る舞い
が微妙な気がする。

c もしくは _ble_term_ri を使わずに被っても良いので先頭行を使う。

然し、やはり内容が上書きされてしまうというのは都合が悪い様に思われる。

d もしくは毎回一番上に行を挿入する。

この方法だと bell が表示される度に行がどんどん下の方に移動してしまって
余り嬉しい事にはならない。一応 IND を使って下に行きすぎない様に調整する
事はできる。top/bottom dock に分かれている場合には制御が面倒である。

現在の ble/canvas/panel/ensure-tmargin.draw の実装について確認する。
DECSTBM が存在する場合には、スクロール領域を設定して bottom dock を固定する。
その上で RI を実行して canvas 原点の上に tmargin 行だけスペースを確保する。

それ以外の場合には即座に RI で canvas 原点の上にスペースを確保する。
bottom に関しては破壊されてしまうのは我慢して invalidate する。

さて、RI が使えない場合にどの様に内容をシフトするのか。場合分けして考え
る。DECSTBM が使える場合にはやはり bottom dock を固定して於いて、その上
で、top_height+tmargin だけ IND を実行する。これで少なくとも top dock
の下に tmargin だけのスペースができる。その後で IL を一番上で実行すれば
良い。

うーん。完全ではないが d の方針で何とか誤魔化す事にした。

* done: modifyOtherkeys がそのまま出力される。

これは linux や minix と同様に出力しない様に変更。

* done: home csi 214 z / end csi 210 z

これは contra の escseq.html にまとめてある物に一致する気がするので確認する。

* done: OSC がそのまま出力されている

面倒なので xterm_title の所で直接 term の判定を行って切り替える。
OSC を無視できるかどうかを各 OS のコンソールで確認する。
freebsd, linux, haiku ではちゃんと無視できている。
minix 及び sun は失敗している。

* prompt_eol_mark 関連のカーソル移動に使われているシーケンスにも問題のある
物がある。_ble_term_sc, _ble_term_rc の既定値が \e[s, \e[u になっていたが、
これらは寧ろ少数派なので \e7, \e8 に切り替える事にした。Solaris では
terminfo に \e7, \e8 は載っていないが実際には使える。

また _ble_term_xenl に関しても terminfo になかった事から既定で 1 になって
いたが、Solaris では 0 にする必要がある。修正した。序でに xenl がない時に
は 0 ではなくて空文字列にする事にする。

x ok: RI がない時の vbell の振る舞いが駄目。再度実装を確認する。
うーん。幾らか修正して、更に必要な時にだけ高さを確保する様に変更した。

そもそも sun console は下から出ていくと上に戻るという変な振る舞いをするの
でまともに対応するのが難しい。適当な所で良しとするのが良い。

* done: delete キーで ^? (DEL) が送信される。これについては TERM=sun* の時
に ^? を delete に変換して対策する事にした。実は既に infocmp kdch1 が ^?
の時にはこの対策が実施されていたが、sun* の terminfo に kdch1 が登録され
ていなかったのが原因だった。

x 文字 x が入力できない。emacs にするとちゃんと入力できる。.blerc を別名に
すると入力できる。と思ったがこれは set -o vi が実行されなくなるからだった。
更に時々 segfault もする。またランダムな文字列を実行しようともする。

これは恐らく "x?" で bind が形成されてその後でそれが削除される事により、
x 単体の入力に対して出鱈目な文字列が実行されているという事なのだろう。
では誰が x に bind しているのだろうか。。不思議である。

うーん。inputrc は存在していないし、bind は特に直接呼び出されてはいない様
だし、という事を考えると ble.sh で呼び出している builtin bind が問題を起
こしているという事なのだろうか。

generate-source-to-unbind-default の出力を保存してそれを読ませてみたら
問題が発生するという事が分かった。特に問題のある行もない…と思いきや、

builtin bind -r 'x1c' (bash-4.1)

という変な行が混入している。これは一体何処から出てきた物だろうか。普通に
動いている環境で実行してみると

builtin bind -r '\x1c' (bash-4.4)

という結果になっている。つまり、これは bash-4.1 特有の処置ではなくて一般
に行われている処置である。

問題の箇所を確認してみると awk で sub(/.../, "\"\\x1c\"") としている。
つまり Solaris awk はこの \\ を消してしまうという事。と思っていたら、
既にその問題点についてコメントに書かれていた。'\'' に対しては対策されていたが、
直接 \ が現れる場合については対策されていなかったのが原因。
特に \x の組み合わせが x に変換されてしまうという問題の様である。
\x についても対応すると共にコードの整理を行った。

* complete/mabdb: man awk の内容を抽出しきれていない [#D1480]

先ず .PD という行が挿入されている事が原因の様である。
Expand Down
40 changes: 33 additions & 7 deletions src/canvas.sh
Expand Up @@ -368,12 +368,12 @@ function ble/canvas/put.draw {
}
function ble/canvas/put-ind.draw {
local count=${1-1}
local ret; ble/string#repeat "${_ble_term_ind}" "$count"
local ret; ble/string#repeat "$_ble_term_ind" "$count"
DRAW_BUFF[${#DRAW_BUFF[*]}]=$ret
}
function ble/canvas/put-ri.draw {
local count=${1-1}
local ret; ble/string#repeat "${_ble_term_ri}" "$count"
local ret; ble/string#repeat "$_ble_term_ri" "$count"
DRAW_BUFF[${#DRAW_BUFF[*]}]=$ret
}
function ble/canvas/put-il.draw {
Expand Down Expand Up @@ -2119,7 +2119,7 @@ function ble/canvas/panel#clear-after.draw {
ble/canvas/put.draw "$_ble_term_ind"
ble/canvas/put-dl.draw "$rest_lines"
ble/canvas/put-il.draw "$rest_lines"
ble/canvas/put.draw "$_ble_term_ri"
ble/canvas/put-cuu.draw 1
fi
}

Expand Down Expand Up @@ -2180,8 +2180,18 @@ function ble/canvas/panel/ensure-tmargin.draw {
ble/canvas/put.draw $'\e[1;'$((LINES-bottom_height))'r'
ble/canvas/excursion-end.draw
ble/canvas/goto.draw 0 0
ble/canvas/put-ri.draw "$tmargin"
ble/canvas/put-cud.draw "$tmargin"
if [[ $_ble_term_ri ]]; then
ble/canvas/put-ri.draw "$tmargin"
ble/canvas/put-cud.draw "$tmargin"
else
# RI がない時
ble/canvas/put-ind.draw $((top_height-1+tmargin))
ble/canvas/put-cuu.draw $((top_height-1+tmargin))
ble/canvas/excursion-start.draw
ble/canvas/put-cup.draw 1 1
ble/canvas/put-il.draw "$tmargin"
ble/canvas/excursion-end.draw
fi
ble/canvas/excursion-start.draw
ble/canvas/put.draw $'\e[;r'
ble/canvas/excursion-end.draw
Expand All @@ -2193,7 +2203,23 @@ function ble/canvas/panel/ensure-tmargin.draw {
fi

ble/canvas/goto.draw 0 0
ble/canvas/put-ri.draw "$tmargin"
ble/canvas/put-cud.draw "$tmargin"
if [[ $_ble_term_ri ]]; then
ble/canvas/put-ri.draw "$tmargin"
ble/canvas/put-cud.draw "$tmargin"
else
# RI がない時
local total_height=$((top_height+bottom_height))
ble/canvas/put-ind.draw $((total_height-1+tmargin))
ble/canvas/put-cuu.draw $((total_height-1+tmargin))
if [[ $_ble_term_rc ]]; then
ble/canvas/excursion-start.draw
ble/canvas/put-cup.draw 1 1
ble/canvas/put-il.draw "$tmargin"
ble/canvas/excursion-end.draw
else
ble/canvas/put-il.draw "$tmargin"
fi
ble/canvas/put-cud.draw "$tmargin"
fi
ble/canvas/panel/load-position.draw "$pos"
}
24 changes: 15 additions & 9 deletions src/decode.sh
Expand Up @@ -2638,18 +2638,24 @@ function ble/decode/bind/.generate-source-to-unbind-default {
} 2>/dev/null
function ble/decode/bind/.generate-source-to-unbind-default/.process {
# Note: #D1355 LC_ALL 切り替えに伴うエラーメッセージは呼び出し元で /dev/null に繋いでいる。
local q=\' b=\\ Q="'\''"
local q=\' Q="'\''" is_xpg4=0
# Note: Solaris xpg4 awk では gsub の置換後のエスケープシーケンスも処理される
[[ $_ble_bin_awk_solaris_xpg4 == yes ]] && Q="'$b$b''"
local QUOT_Q=\"${Q//"$b"/$b$b}\"
LC_ALL=C ble/bin/awk -v q="$q" '
[[ $_ble_bin_awk_solaris_xpg4 == yes ]] && is_xpg4=1
LC_ALL=C ble/bin/awk -v q="$q" -v is_xpg4="$is_xpg4" '
function str2rep(str) {
if (is_xpg4) sub(/\\/, "\\\\\\\\", str);
return str;
}
BEGIN {
Q = '"$QUOT_Q"';
rep_Q = str2rep(q "\\" q q);
rep_bslash = str2rep("\\");
rep_kseq_1c5c = str2rep("\"\\x1c\\x5c\"");
rep_kseq_1c = str2rep("\"\\x1c\"");
mode = 1;
}
function quote(text) {
gsub(q, Q, text);
gsub(q, rep_Q, text);
return q text q;
}
Expand All @@ -2673,7 +2679,7 @@ function ble/decode/bind/.generate-source-to-unbind-default/.process {
str = unescape_control_modifier(str);
gsub(/\\e/, sprintf("%c", 27), str);
gsub(/\\"/, "\"", str);
gsub(/\\\\/, "\\", str);
gsub(/\\\\/, rep_bslash, str);
return str;
}
Expand All @@ -2694,8 +2700,8 @@ function ble/decode/bind/.generate-source-to-unbind-default/.process {
mode == 1 && $0 ~ /^"/ {
# Workaround Bash-5.0 bug (cf #D1078)
sub(/^"\\C-\\\\\\"/, "\"\\x1c\\x5c\"");
sub(/^"\\C-\\\\?"/, "\"\\x1c\"");
sub(/^"\\C-\\\\\\"/, rep_kseq_1c5c);
sub(/^"\\C-\\\\?"/, rep_kseq_1c);
output_bindr($0);
Expand Down
12 changes: 8 additions & 4 deletions src/edit.sh
Expand Up @@ -1061,10 +1061,14 @@ function ble/prompt/update {
fi

# bleopt prompt_xterm_title
local ret
ble/prompt/.instantiate-control-string _ble_prompt_xterm_title "$bleopt_prompt_xterm_title"
[[ $ret ]] && ret=$'\e]0;'$ret$'\a'
_ble_prompt_xterm_title[6]=$ret
case ${_ble_term_TERM:-$TERM} in
(sun*|minix) ;; # black list
(*)
local ret
ble/prompt/.instantiate-control-string _ble_prompt_xterm_title "$bleopt_prompt_xterm_title"
[[ $ret ]] && ret=$'\e]0;'$ret$'\a'
_ble_prompt_xterm_title[6]=$ret ;;
esac

# bleopt prompt_screen_title
case ${_ble_term_TERM:-$TERM} in
Expand Down

0 comments on commit 6ca0b8c

Please sign in to comment.