Browse Source

[linux] Add console

Add linux console using stdin/out. Configure the attached terminal for
readline use.

Signed-off-by: Piotr Jaroszyński <p.jaroszynski@gmail.com>
Signed-off-by: Michael Brown <mcb30@ipxe.org>
tags/v1.20.1
Piotr Jaroszyński 14 years ago
parent
commit
18d3c12b01
4 changed files with 152 additions and 1 deletions
  1. 1
    1
      src/Makefile
  2. 3
    0
      src/config/config.c
  3. 2
    0
      src/config/defaults/linux.h
  4. 146
    0
      src/interface/linux/linux_console.c

+ 1
- 1
src/Makefile View File

@@ -73,7 +73,7 @@ SRCDIRS		+= drivers/block
73 73
 SRCDIRS		+= drivers/nvs
74 74
 SRCDIRS		+= drivers/bitbash
75 75
 SRCDIRS		+= drivers/infiniband
76
-SRCDIRS		+= interface/pxe interface/efi interface/smbios
76
+SRCDIRS		+= interface/pxe interface/efi interface/smbios interface/linux
77 77
 SRCDIRS		+= tests
78 78
 SRCDIRS		+= crypto crypto/axtls crypto/matrixssl
79 79
 SRCDIRS		+= hci hci/commands hci/tui

+ 3
- 0
src/config/config.c View File

@@ -82,6 +82,9 @@ REQUIRE_OBJECT ( syslog );
82 82
 #ifdef CONSOLE_EFI
83 83
 REQUIRE_OBJECT ( efi_console );
84 84
 #endif
85
+#ifdef CONSOLE_LINUX
86
+REQUIRE_OBJECT ( linux_console );
87
+#endif
85 88
 
86 89
 /*
87 90
  * Drag in all requested network protocols

+ 2
- 0
src/config/defaults/linux.h View File

@@ -7,6 +7,8 @@
7 7
  *
8 8
  */
9 9
 
10
+#define CONSOLE_LINUX
11
+
10 12
 #define IMAGE_SCRIPT
11 13
 
12 14
 #endif /* CONFIG_DEFAULTS_LINUX_H */

+ 146
- 0
src/interface/linux/linux_console.c View File

@@ -0,0 +1,146 @@
1
+/*
2
+ * Copyright (C) 2010 Piotr Jaroszyński <p.jaroszynski@gmail.com>
3
+ *
4
+ * This program is free software; you can redistribute it and/or
5
+ * modify it under the terms of the GNU General Public License as
6
+ * published by the Free Software Foundation; either version 2 of the
7
+ * License, or any later version.
8
+ *
9
+ * This program is distributed in the hope that it will be useful, but
10
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
11
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12
+ * General Public License for more details.
13
+ *
14
+ * You should have received a copy of the GNU General Public License
15
+ * along with this program; if not, write to the Free Software
16
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
17
+ */
18
+
19
+FILE_LICENCE(GPL2_OR_LATER);
20
+
21
+/** @file
22
+ *
23
+ * Linux console implementation.
24
+ *
25
+ */
26
+
27
+#include <console.h>
28
+
29
+#include <ipxe/init.h>
30
+#include <ipxe/keys.h>
31
+#include <linux_api.h>
32
+
33
+#include <linux/termios.h>
34
+#include <asm/errno.h>
35
+
36
+static void linux_console_putchar(int c)
37
+{
38
+	/* write to stdout */
39
+	if (linux_write(1, &c, 1) != 1)
40
+		DBG("linux_console write failed (%s)\n", linux_strerror(linux_errno));
41
+}
42
+
43
+static int linux_console_getchar()
44
+{
45
+	char c;
46
+
47
+	/* read from stdin */
48
+	if (linux_read(0, &c, 1) < 0) {
49
+		DBG("linux_console read failed (%s)\n", linux_strerror(linux_errno));
50
+		return 0;
51
+	}
52
+	/* backspace seems to be returned as ascii del, map it here */
53
+	if (c == 0x7f)
54
+		return KEY_BACKSPACE;
55
+	else
56
+		return c;
57
+}
58
+
59
+static int linux_console_iskey()
60
+{
61
+	struct pollfd pfd;
62
+	pfd.fd = 0;
63
+	pfd.events = POLLIN;
64
+
65
+	/* poll for data to be read on stdin */
66
+	if (linux_poll(&pfd, 1, 0) == -1) {
67
+		DBG("linux_console poll failed (%s)\n", linux_strerror(linux_errno));
68
+		return 0;
69
+	}
70
+
71
+	if (pfd.revents & POLLIN)
72
+		return 1;
73
+	else
74
+		return 0;
75
+}
76
+
77
+struct console_driver linux_console __console_driver = {
78
+	.disabled = 0,
79
+	.putchar = linux_console_putchar,
80
+	.getchar = linux_console_getchar,
81
+	.iskey = linux_console_iskey,
82
+};
83
+
84
+static int linux_tcgetattr(int fd, struct termios *termios_p)
85
+{
86
+	return linux_ioctl(fd, TCGETS, termios_p);
87
+}
88
+
89
+static int linux_tcsetattr(int fd, int optional_actions, const struct termios *termios_p)
90
+{
91
+	unsigned long int cmd;
92
+
93
+	switch (optional_actions)
94
+	{
95
+		case TCSANOW:
96
+			cmd = TCSETS;
97
+			break;
98
+		case TCSADRAIN:
99
+			cmd = TCSETSW;
100
+			break;
101
+		case TCSAFLUSH:
102
+			cmd = TCSETSF;
103
+			break;
104
+		default:
105
+			linux_errno = EINVAL;
106
+			return -1;
107
+	}
108
+
109
+	return linux_ioctl(fd, cmd, termios_p);
110
+}
111
+
112
+/** Saved termios attributes */
113
+static struct termios saved_termios;
114
+
115
+/** Setup the terminal for our use */
116
+static void linux_console_startup(void)
117
+{
118
+	struct termios t;
119
+
120
+	if (linux_tcgetattr(0, &t)) {
121
+		DBG("linux_console tcgetattr failed (%s)", linux_strerror(linux_errno));
122
+		return;
123
+	}
124
+
125
+	saved_termios = t;
126
+
127
+	/* Disable canonical mode and echo. Let readline handle that */
128
+	t.c_lflag &= ~(ECHO | ICANON);
129
+	/* stop ^C from sending a signal */
130
+	t.c_cc[VINTR] = 0;
131
+
132
+	if (linux_tcsetattr(0, TCSAFLUSH, &t))
133
+		DBG("linux_console tcsetattr failed (%s)", linux_strerror(linux_errno));
134
+}
135
+
136
+/** Restores original terminal attributes on shutdown */
137
+static void linux_console_shutdown(int flags __unused)
138
+{
139
+	if (linux_tcsetattr(0, TCSAFLUSH, &saved_termios))
140
+		DBG("linux_console tcsetattr failed (%s)", linux_strerror(linux_errno));
141
+}
142
+
143
+struct startup_fn linux_console_startup_fn __startup_fn(STARTUP_EARLY) = {
144
+	.startup = linux_console_startup,
145
+	.shutdown = linux_console_shutdown,
146
+};

Loading…
Cancel
Save