File: rl-callbacktest

package info (click to toggle)
libterm-readline-gnu-perl 1.47-1
  • links: PTS, VCS
  • area: main
  • in suites: sid
  • size: 1,148 kB
  • sloc: perl: 2,191; makefile: 10
file content (84 lines) | stat: -rwxr-xr-x 2,283 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
#!/usr/bin/env perl
#
# rl-callbacktest: 2.4.14 Alternate Interface Example
#
#   Copyright (C) 2024 Hiroo Hayashi
#
# Derived from: examples/rl-callbacktest.c in the GNU Readline Library

use strict;
use warnings;
use Term::ReadLine;

my $t = new Term::ReadLine 'rl-callbacktest';
my $a = $t->Attribs;

my $sigwinch_received = 0;
my $running           = 0;
my $prompt            = 'rltest$ ';

# Handle window size changes when readline is not active and reading
# characters.
sub sigwinch_handler {
    my $sig = shift;
    $sigwinch_received = 1;
}

# Callback function called for each line when accept-line executed, EOF
# seen, or EOF character read.  This sets a flag and returns; it could
# also call exit(3).
sub cb_linehandler {
    my $line = shift;

    # Can use ^D (stty eof) or `exit' to exit.
    if (!$line || $line eq "exit") {
        print "\n" unless $line;
        print "exit\n";

        # This function needs to be called to reset the terminal settings,
        # and calling it from the line handler keeps one extra prompt from
        # being displayed.
        $t->callback_handler_remove();

        $running = 0;
    } else {
        $t->add_history($line) if $line;
        print "input line: $line\n";
    }
}

# Handle SIGWINCH
$SIG{WINCH} = \&sigwinch_handler;

# Install the line handler.
$t->callback_handler_install($prompt, \&cb_linehandler);

# Enter a simple event loop.  This waits until something is available
# to read on readline's input stream (defaults to standard input) and
# calls the builtin character read callback to read it.  It does not
# have to modify the user's terminal settings.
$running = 1;
while ($running) {
    my $fds = '';
    vec($fds, fileno($a->{instream}), 1) = 1;

    my $r = select($fds, undef, undef, undef);
    if ($r < 0 && $! && !$!{EINTR}) {   # EINTR is not an error
        warn "$0: select: $!\n";
        $t->callback_handler_remove();
        last;
    }
    if ($sigwinch_received) {
        warn "$0: SIGWINCH received\n";
        $t->resize_terminal();
        $sigwinch_received = 0;
    }
    next if $r < 0; # select returns EINTR (interrupted system call)

    if (vec($fds, fileno($a->{instream}), 1)) {
        $t->callback_read_char();
    }
}

print "$0: Event loop has exited\n";
exit 0;