• R/O
  • SSH
  • HTTPS

nos: Commit


Commit MetaInfo

Révision358 (tree)
l'heure2009-10-22 18:19:19
Auteuruchan_nos

Message de Log

コンソールに文字入力・改行・削除ができるようになった
コマンド解釈機構をつけた

Change Summary

Modification

--- bitnos5/trunk/kernel/console.cpp (revision 357)
+++ bitnos5/trunk/kernel/console.cpp (revision 358)
@@ -9,20 +9,308 @@
99 #include <bitnos/mtask.h>
1010 #include <bitnos/sheet.h>
1111 #include <bitnos/window.h>
12+#include <string.h>
1213
13-void TaskConsoleFunc()
14+namespace TaskConsole
1415 {
15- Task* task = taskman->GetCurrentTask();
16+
17+struct Valiables
18+{
1619 Console cons;
20+ Image* img;
21+ Sheet* sht;
1722
18- Image* img = new Image(8 + 8 * 29, 25 + 8 + 16 * 10);
19- Window::Make(img);
20- img->DrawRectangleFill(0x0000, Point(0, 25), Point(239, 192));
21- Sheet* sht = shtman->Alloc();
22- sht->Init(img, Sheet::NoInvColor, Point(200, 50));
23- shtman->SetHeight(sht, 0, Sheet::Normal);
23+ char cmdline[128];
24+ int cmdlineBegin;
25+};
2426
25- while (!0) {
26- taskman->Sleep(task);
27+// コマンド実行機能なし
28+void PutChar0(Valiables* o, char ch);
29+
30+// PutChar0 + コマンド実行
31+void PutChar(Valiables* o, char ch);
32+
33+void PutString0(Valiables* o, const char* str);
34+
35+void ConsoleRefreshScreen(Valiables* o, int begin);
36+
37+void RunCommand(Valiables* o);
38+
39+void Init(void* obj)
40+{
41+ Valiables* o = (Valiables*)obj;
42+
43+ Task* task = taskman->GetCurrentTask();
44+
45+ Debug::WriteLine("Console Init");
46+
47+ o->cons.height = 10;
48+ o->cons.width = 29;
49+ o->cons.bufHeight = 100;
50+ o->cons.bufWidth = 29;
51+ o->cons.buf = new char[o->cons.bufHeight * o->cons.bufWidth];
52+ o->cons.startLine = o->cons.endLine = 0;
53+ o->cons.xPos = 0;
54+ o->cons.backColor = ConvRGB16(0, 0, 0);
55+ o->cons.textColor = ConvRGB16(255, 255, 255);
56+ o->cmdlineBegin = 0;
57+
58+ o->img = new Image(
59+ 8 + fontHankaku->GetWidth() * o->cons.width,
60+ 25 + 8 + fontHankaku->GetHeight() * o->cons.height);
61+ Window::Make(o->img);
62+ o->img->DrawRectangleFill(
63+ o->cons.backColor, Point(0, 25), Point(o->img->width - 1, o->img->height - 1));
64+ o->sht = shtman->Alloc();
65+ o->sht->Init(o->img, Sheet::NoInvColor, Point(200, 50));
66+ o->sht->SetParentTask(task);
67+ shtman->SetHeight(o->sht, 0, Sheet::Normal);
68+
69+ PutChar(o, '>');
70+}
71+
72+void Proc(void* obj, Message* msg)
73+{
74+ Valiables* o = (Valiables*)obj;
75+
76+ if (msg->from == Message::From::Keyboard) {
77+ if (msg->arg1 != 0) {
78+ PutChar(o, msg->arg1);
79+ }
2780 }
2881 }
82+
83+void PutChar0(Valiables* o, char ch)
84+{
85+ // バッファに格納
86+ if (0x20 <= ch && ch < 0x80) {
87+ o->cons.buf[o->cons.bufWidth * o->cons.endLine + o->cons.xPos] = ch;
88+ o->cons.xPos++;
89+ }
90+ if (ch == '\b') {
91+ if (o->cons.xPos > 0) {
92+ o->cons.xPos--;
93+ }
94+ o->cons.buf[o->cons.bufWidth * o->cons.endLine + o->cons.xPos] = '\0';
95+ // 1文字だけ消去する
96+ int end = o->cons.endLine;
97+ if (end >= o->cons.height) {
98+ end = o->cons.height - 1;
99+ }
100+ o->sht->DrawRectangleFill(
101+ o->cons.backColor,
102+ Point(
103+ 4 + fontHankaku->GetWidth() * o->cons.xPos,
104+ 25 + 4 + fontHankaku->GetHeight() * end),
105+ Point(
106+ 4 + fontHankaku->GetWidth() * (o->cons.xPos + 1) - 1,
107+ 25 + 4 + fontHankaku->GetHeight() * (end + 1) - 1)
108+ );
109+ } else if (o->cons.bufWidth <= o->cons.xPos || ch == '\n') {
110+ // バッファの右端まで行った、またはエンターキーが押されたから改行
111+ if (o->cons.xPos < o->cons.bufWidth - 1) {
112+ o->cons.buf[o->cons.bufWidth * o->cons.endLine + o->cons.xPos] = '\0';
113+ }
114+ o->cons.xPos = 0;
115+ o->cons.endLine++;
116+ if (o->cons.endLine == o->cons.startLine) {
117+ o->cons.startLine++;
118+ }
119+ // 画面全体を描画しなおす
120+ ConsoleRefreshScreen(o, o->cons.endLine - o->cons.height + 1);
121+ } else {
122+ // 改行しなかった
123+ int end = o->cons.endLine;
124+ if (end >= o->cons.height) {
125+ end = o->cons.height - 1;
126+ }
127+ // 1文字だけ描画する
128+ o->sht->DrawChar(
129+ o->cons.textColor,
130+ ch,
131+ Point(
132+ 4 + fontHankaku->GetWidth() * (o->cons.xPos - 1),
133+ 25 + 4 + fontHankaku->GetHeight() * end),
134+ fontHankaku);
135+ }
136+}
137+
138+void PutChar(Valiables* o, char ch)
139+{
140+#if 0
141+ // バッファに格納
142+ if (0x20 <= ch && ch < 0x80) {
143+ o->cons.buf[o->cons.bufWidth * o->cons.endLine + o->cons.xPos] = ch;
144+ o->cons.xPos++;
145+ }
146+ if (ch == '\b') {
147+ if (o->cons.xPos > 0) {
148+ o->cons.xPos--;
149+ }
150+ o->cons.buf[o->cons.bufWidth * o->cons.endLine + o->cons.xPos] = '\0';
151+ // 1文字だけ消去する
152+ int end = o->cons.endLine;
153+ if (end >= o->cons.height) {
154+ end = o->cons.height - 1;
155+ }
156+ o->sht->DrawRectangleFill(
157+ o->cons.backColor,
158+ Point(
159+ 4 + fontHankaku->GetWidth() * o->cons.xPos,
160+ 25 + 4 + fontHankaku->GetHeight() * end),
161+ Point(
162+ 4 + fontHankaku->GetWidth() * (o->cons.xPos + 1) - 1,
163+ 25 + 4 + fontHankaku->GetHeight() * (end + 1) - 1)
164+ );
165+ } else if (o->cons.bufWidth <= o->cons.xPos || ch == '\n') {
166+ // バッファの右端まで行った、またはエンターキーが押されたから改行
167+ if (o->cons.xPos < o->cons.bufWidth - 1) {
168+ o->cons.buf[o->cons.bufWidth * o->cons.endLine + o->cons.xPos] = '\0';
169+ }
170+ o->cons.xPos = 0;
171+ o->cons.endLine++;
172+ if (o->cons.endLine == o->cons.startLine) {
173+ o->cons.startLine++;
174+ }
175+ if (ch == '\n') {
176+ // コマンドラインを取得
177+ int i = 0;
178+ char c;
179+ for (int line = o->cmdlineBegin, x = 1; line != o->cons.endLine; line++) {
180+ if (line == o->cons.bufHeight) {
181+ line = 0;
182+ }
183+ for (; x < o->cons.bufWidth && (c = o->cons.buf[o->cons.bufWidth * line + x]) != '\0'; x++) {
184+ o->cmdline[i++] = c;
185+ }
186+ x = 0;
187+ }
188+ o->cmdline[i] = '\0';
189+ o->cmdlineBegin = o->cons.endLine;
190+ RunCommand(o);
191+ o->cons.buf[o->cons.bufWidth * o->cons.endLine + o->cons.xPos] = '>';
192+ o->cons.xPos++;
193+ }
194+ // 画面全体を描画しなおす
195+ ConsoleRefreshScreen(o, o->cons.endLine - o->cons.height + 1);
196+ } else {
197+ // 改行しなかった
198+ int end = o->cons.endLine;
199+ if (end >= o->cons.height) {
200+ end = o->cons.height - 1;
201+ }
202+ // 1文字だけ描画する
203+ o->sht->DrawChar(
204+ o->cons.textColor,
205+ ch,
206+ Point(
207+ 4 + fontHankaku->GetWidth() * (o->cons.xPos - 1),
208+ 25 + 4 + fontHankaku->GetHeight() * end),
209+ fontHankaku);
210+ }
211+#endif
212+ PutChar0(o, ch);
213+ if (ch == '\n') {
214+ // コマンドラインを取得
215+ int i = 0;
216+ char c;
217+ for (int line = o->cmdlineBegin, x = 1; line != o->cons.endLine; line++) {
218+ if (line == o->cons.bufHeight) {
219+ line = 0;
220+ }
221+ for (; x < o->cons.bufWidth && (c = o->cons.buf[o->cons.bufWidth * line + x]) != '\0'; x++) {
222+ o->cmdline[i++] = c;
223+ }
224+ x = 0;
225+ }
226+ o->cmdline[i] = '\0';
227+
228+ Debug::WriteLine(o->cmdline);
229+ RunCommand(o);
230+
231+ o->cmdlineBegin = o->cons.endLine;
232+ PutChar0(o, '>');
233+ }
234+
235+}
236+
237+void PutString0(Valiables* o, const char* str)
238+{
239+ while (*str != '\0') {
240+ PutChar0(o, *str++);
241+ }
242+}
243+
244+void ConsoleRefreshScreen(Valiables* o, int begin)
245+{
246+ int lines = o->cons.height;
247+ if (begin < 0) {
248+ // 自動計算モード
249+ lines = o->cons.endLine - o->cons.startLine + 1;
250+ if (lines <= 0) {
251+ /*
252+ * bufの状態が
253+ * ...
254+ * endLine
255+ * ...
256+ * startLine
257+ * ...
258+ * のようになっているとき
259+ */
260+ lines += o->cons.bufHeight;
261+ }
262+ if (lines <= o->cons.height) {
263+ begin = o->cons.startLine;
264+ } else {
265+ lines = o->cons.height;
266+ begin = o->cons.endLine - o->cons.height;
267+ if (begin < 0) {
268+ begin += o->cons.bufHeight;
269+ }
270+ }
271+ }
272+ o->img->DrawRectangleFill(
273+ o->cons.backColor, Point(0, 25), Point(o->img->width - 1, o->img->height - 1));
274+ int line = begin;
275+ for (int y = 0; y < lines; y++) {
276+ for (int x = 0; x < o->cons.width; x++) {
277+ char ch = o->cons.buf[line * o->cons.bufWidth + x];
278+ if (ch == '\0') {
279+ break;
280+ }
281+ o->img->DrawChar(
282+ o->cons.textColor,
283+ ch,
284+ Point(4 + x * fontHankaku->GetWidth(), 25 + 4 + y * fontHankaku->GetHeight()),
285+ fontHankaku);
286+ }
287+ line++;
288+ if (line == o->cons.bufHeight) {
289+ line = 0;
290+ }
291+ if (line == o->cons.startLine) {
292+ break;
293+ }
294+ }
295+ o->sht->Refresh();
296+}
297+
298+void RunCommand(Valiables* o)
299+{
300+ if (strncmp(o->cmdline, "mem", 4) == 0) {
301+ PutString0(o, "can't calculate memory size\n");
302+ } else if (strncmp(o->cmdline, "opencons", 9) == 0) {
303+ Task* consTask = taskman->Alloc();
304+ uintptr_t stackTop;
305+ uint32_t stackSize;
306+ stackTop = (uintptr_t)(new uint8_t[stackSize = 1024*4]);
307+ consTask->SetFuncs(stackTop, stackSize,
308+ TaskConsole::Init, DummyFunc, TaskConsole::Proc);
309+ consTask->InitQueue(128);
310+ taskman->Run(consTask, 1, 2);
311+ } else {
312+ PutString0(o, "unknown command\n");
313+ }
314+}
315+
316+}
--- bitnos5/trunk/include/bitnos/console.h (revision 357)
+++ bitnos5/trunk/include/bitnos/console.h (revision 358)
@@ -8,12 +8,31 @@
88 #ifndef CONSOLE_H_
99 #define CONSOLE_H_
1010
11-void TaskConsoleFunc();
11+#include <stdint.h>
1212
13-class Console
13+struct Console
1414 {
1515 int width; // 横の文字数
1616 int height; // 縦の文字数
17+ int bufWidth; // バッファの横の文字数
18+ int bufHeight; // バッファの縦の文字数
19+ char* buf; // バッファ
20+
21+ int startLine; // バッファの開始行
22+ int endLine; // バッファの終了行(書き込み行)
23+ int xPos; // 書き込みの横位置
24+
25+ uint16_t backColor; // 背景色
26+ uint16_t textColor; // 前景色
1727 };
1828
29+class Message;
30+
31+namespace TaskConsole
32+{
33+void Init(void* obj);
34+void Proc(void* obj, Message* msg);
35+}
36+
37+
1938 #endif /* CONSOLE_H_ */
Afficher sur ancien navigateur de dépôt.