source: mainline/uspace/srv/fb/serial_console.c@ 2d32081

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export
Last change on this file since 2d32081 was 8b97256, checked in by Jiri Svoboda <jirik.svoboda@…>, 17 years ago

Do not duplicate code in serial framebuffer drivers.

  • Property mode set to 100644
File size: 5.0 KB
Line 
1/*
2 * Copyright (c) 2006 Ondrej Palkovsky
3 * Copyright (c) 2008 Martin Decky
4 * Copyright (c) 2008 Pavel Rimsky
5 * All rights reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 *
11 * - Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * - Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
16 * - The name of the author may not be used to endorse or promote products
17 * derived from this software without specific prior written permission.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
20 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
21 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
22 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
23 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
24 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
28 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29 */
30
31/**
32 * @defgroup serial Serial console
33 * @brief Serial console services (putc, puts, clear screen, cursor goto,...)
34 * @{
35 */
36
37/** @file
38 */
39
40#include <stdio.h>
41#include <ipc/ipc.h>
42#include <async.h>
43#include <ipc/fb.h>
44#include <bool.h>
45#include <errno.h>
46
47#include "serial_console.h"
48
49#define MAX_CONTROL 20
50
51static int width;
52static int height;
53static putc_function_t putc_function;
54
55/* Allow only 1 connection */
56static int client_connected = 0;
57
58void serial_puts(char *str)
59{
60 while (*str)
61 putc_function(*(str++));
62}
63
64void serial_goto(const unsigned int row, const unsigned int col)
65{
66 if ((row > height) || (col > width))
67 return;
68
69 char control[20];
70 snprintf(control, 20, "\033[%u;%uf", row + 1, col + 1);
71 serial_puts(control);
72}
73
74void serial_clrscr(void)
75{
76 serial_puts("\033[2J");
77}
78
79void serial_scroll(int i)
80{
81 if (i > 0) {
82 serial_goto(height - 1, 0);
83 while (i--)
84 serial_puts("\033D");
85 } else if (i < 0) {
86 serial_goto(0, 0);
87 while (i++)
88 serial_puts("\033M");
89 }
90}
91
92void serial_set_style(const unsigned int mode)
93{
94 char control[MAX_CONTROL];
95 snprintf(control, MAX_CONTROL, "\033[%um", mode);
96 serial_puts(control);
97}
98
99/** Set scrolling region. */
100void serial_set_scroll_region(unsigned last_row)
101{
102 char control[MAX_CONTROL];
103 snprintf(control, MAX_CONTROL, "\033[0;%ur", last_row);
104 serial_puts(control);
105}
106
107void serial_cursor_disable(void)
108{
109 serial_puts("\033[?25l");
110}
111
112void serial_cursor_enable(void)
113{
114 serial_puts("\033[?25h");
115}
116
117void serial_console_init(putc_function_t putc_fn, uint32_t w, uint32_t h)
118{
119 width = w;
120 height = h;
121 putc_function = putc_fn;
122}
123
124/**
125 * Main function of the thread serving client connections.
126 */
127void serial_client_connection(ipc_callid_t iid, ipc_call_t *icall)
128{
129 int retval;
130 ipc_callid_t callid;
131 ipc_call_t call;
132 char c;
133 int lastcol = 0;
134 int lastrow = 0;
135 int newcol;
136 int newrow;
137 int fgcolor;
138 int bgcolor;
139 int i;
140
141 if (client_connected) {
142 ipc_answer_0(iid, ELIMIT);
143 return;
144 }
145
146 client_connected = 1;
147 ipc_answer_0(iid, EOK);
148
149 /* Clear the terminal, set scrolling region
150 to 0 - height rows. */
151 serial_clrscr();
152 serial_goto(0, 0);
153 serial_set_scroll_region(height);
154
155 while (true) {
156 callid = async_get_call(&call);
157 switch (IPC_GET_METHOD(call)) {
158 case IPC_M_PHONE_HUNGUP:
159 client_connected = 0;
160 ipc_answer_0(callid, EOK);
161 return;
162 case FB_PUTCHAR:
163 c = IPC_GET_ARG1(call);
164 newrow = IPC_GET_ARG2(call);
165 newcol = IPC_GET_ARG3(call);
166 if ((lastcol != newcol) || (lastrow != newrow))
167 serial_goto(newrow, newcol);
168 lastcol = newcol + 1;
169 lastrow = newrow;
170 (*putc_function)(c);
171 retval = 0;
172 break;
173 case FB_CURSOR_GOTO:
174 newrow = IPC_GET_ARG1(call);
175 newcol = IPC_GET_ARG2(call);
176 serial_goto(newrow, newcol);
177 lastrow = newrow;
178 lastcol = newcol;
179 retval = 0;
180 break;
181 case FB_GET_CSIZE:
182 ipc_answer_2(callid, EOK, height, width);
183 continue;
184 case FB_CLEAR:
185 serial_clrscr();
186 retval = 0;
187 break;
188 case FB_SET_STYLE:
189 fgcolor = IPC_GET_ARG1(call);
190 bgcolor = IPC_GET_ARG2(call);
191 if (fgcolor < bgcolor)
192 serial_set_style(0);
193 else
194 serial_set_style(7);
195 retval = 0;
196 break;
197 case FB_SCROLL:
198 i = IPC_GET_ARG1(call);
199 if ((i > height) || (i < -height)) {
200 retval = EINVAL;
201 break;
202 }
203 serial_scroll(i);
204 serial_goto(lastrow, lastcol);
205 retval = 0;
206 break;
207 case FB_CURSOR_VISIBILITY:
208 if(IPC_GET_ARG1(call))
209 serial_cursor_enable();
210 else
211 serial_cursor_disable();
212 retval = 0;
213 break;
214 default:
215 retval = ENOENT;
216 }
217 ipc_answer_0(callid, retval);
218 }
219}
220
221/**
222 * @}
223 */
Note: See TracBrowser for help on using the repository browser.