-
Notifications
You must be signed in to change notification settings - Fork 0
/
teletype.inc
597 lines (571 loc) · 17.5 KB
/
teletype.inc
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
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
enum & _SET_FONT_FORCE
_teletype_set_font:
; in:
; ebx - teletype object pointer
; ecx - flags (force change font even if it's the same)
; esi - fonts object pointer
; out: cf - set when width/height are not power of two
; preserves: ebx, edi, esi, ebp
push edi
cmp ecx, (_SET_FONT_FORCE + 1H)
cmc
jc _teletype_set_font_exit
test cl, _SET_FONT_FORCE
jnz _teletype_set_font_force
cmp dword [ebx+_teletype.fonts], esi
jz _teletype_set_font_exit
_teletype_set_font_force:
mov eax, esi
lea edi, [ebx+_teletype.fonts]
mov ecx, _fonts.sizeof
call _copy_string
mov esi, eax
movzx eax, byte [esi+_fonts.width]
call _is_power_two
jc _teletype_set_font_exit
movzx eax, byte [esi+_fonts.height]
call _is_power_two
jc _teletype_set_font_exit
movzx eax, byte [esi+_fonts.width]
movzx edx, byte [esi+_fonts.height]
bsf eax, eax
bsf edx, edx
mov byte [esi+_fonts.btposw], al
mov byte [esi+_fonts.btposh], dl
mov cl, al
mov ax, word [_current_modeinfo.x_resolution]
shr ax, cl
stc
jz _teletype_set_font_exit
mov word [ebx+_teletype.xgrid], ax
mov cl, dl
mov dx, word [_current_modeinfo.y_resolution]
shr dx, cl
stc
jz _teletype_set_font_exit
mov word [ebx+_teletype.ygrid], dx
movzx eax, word [_current_modeinfo.bytes_scanline]
shl eax, cl
mov dword [ebx+_teletype.scroll], eax
call _teletype_clear
_teletype_set_font_exit:
pop edi
ret
_teletype_remap_frame_buffer:
; in: ebx - teletype object pointer
; preserves: eax, ebx, edx, edi, ebp
push eax ebx edx edi
cmp ebx, dword [_current_teletype]
jnz _teletype_remap_frame_buffer_exit
mov esi, dword [_current]
cmp byte [esi+_process.refresh], 0H
mov byte [esi+_process.refresh], 0H
jz _teletype_remap_frame_buffer_exit
xor ecx, ecx
mov cl, _REGEN_4MB_PAGE
test byte [_singleton.pae], 1H
jz _teletype_remap_frame_buffer_remap
shl ecx, ((_PAGE_DIRECTORY_SHIFT - _PAGE_TABLE_SHIFT) - (_PAE_PAGE_DIRECTORY_SHIFT - _PAE_PAGE_TABLE_SHIFT))
_teletype_remap_frame_buffer_remap:
xor eax, eax
mov al, (_DEALLOCATION_VIRTUAL or _DEALLOCATION_PSE or _DEALLOCATION_SHARING)
mov ebx, dword [ebx+_teletype.video]
and ebx, (not _PSE_OFFSET_MASK)
call _unmap_virtual_address
jc _teletype_remap_frame_buffer_exit
xor eax, eax
mov al, (_ALLOCATION_VIRTUAL or _ALLOCATION_PSE)
call _allocate_kernel_frame
_teletype_remap_frame_buffer_exit:
pop edi edx ebx eax
ret
_teletype_buffer_target:
; in: ebx - teletype object pointer
; out:
; edi - target buffer (regen or video)
; zf - set when the video video ram is selected
; preserves: eax, ebx, ecx, edx, esi, ebp
mov edi, dword [ebx+_teletype.video]
cmp ebx, dword [_current_teletype]
jz _teletype_buffer_target_exit
mov edi, dword [ebx+_teletype.regen]
_teletype_buffer_target_exit:
ret
_teletype_clear:
; in: ebx - teletype object pointer
; out: cf - set on error
; preserves: ebx, ecx, esi, edi, ebp
push ecx esi edi
xor eax, eax
mov byte [ebx+_teletype.cursor], al
mov word [ebx+_teletype.xlinear], ax
mov word [ebx+_teletype.ylinear], ax
mov word [ebx+_teletype.xsaved], ax
mov word [ebx+_teletype.ysaved], ax
call _teletype_buffer_target
jnz _teletype_clear_perform
mov eax, dword [_current]
cmp byte [eax+_process.refresh], 0H ; if the cursor is already set jump for set the cursor
jz _teletype_clear_perform
call _teletype_remap_frame_buffer
_teletype_clear_perform:
mov ecx, dword [_vbe_frame_amount]
call _clear_string
mov byte [ebx+_teletype.cursor], (not 0H) ; and set the cursor to the top left
call _teletype_redraw_cursor
pop edi esi ecx
ret
_teletype_erase_character:
; in:
; ebx - teletype object pointer
; ecx - count of position to move backward
; preserves: ebx, esi, ebp
jecxz _teletype_erase_character_exit
_teletype_erase_character_loop:
mov al, _TELETYPE_BACKSPACE
xor edx, edx
call _teletype_write_character
jc _teletype_erase_character_exit
mov al, 020H
xor edi, edi
call _teletype_write_character
jc _teletype_erase_character_exit
loop _teletype_erase_character_loop
_teletype_erase_character_exit:
ret
_teletype_set_color:
; in:
; eax - forground color
; ebx - teletype object pointer
; edx - background color
mov dword [ebx+_teletype.foregnd], eax
mov dword [ebx+_teletype.backgnd], edx
ret
_teletype_redraw_cursor:
; in: ebx - teletype object pointer
; out: cf - set on error
; preserves: ebx, ebp
cmp byte [ebx+_teletype.cursor], 0H
jz _teletype_redraw_cursor_exit
xor eax, eax
mov edx, _teletype_write_character_cursor
call _teletype_write_character_foreach
_teletype_redraw_cursor_exit:
ret
_teletype_update_cursor:
; in:
; ebx - teletype object pointer
; ebp - predicate direction pointer
; out:
; preserves: ebx, ecx, esi, edi, ebp
push ecx esi edi
call _teletype_redraw_cursor
jc _teletype_update_cursor_exit
call ebp
call _teletype_redraw_cursor
_teletype_update_cursor_exit:
pop edi esi ecx
ret
_teletype_internal_buffer_full:
; in: ebx - teletype object pointer
; out: cf - set if overflow
cmp word [ebx+_teletype.index], _PAGE_FRAME_SIZE
jmp _convert_zero_carry
_teletype_reset_canonical:
mov word [ebx+_teletype.ceidx], 0H
mov byte [ebx+_teletype.eoi], 0H
ret
_teletype_switch:
; in: ebx - target teletype object pointer
; preserves: eax, ebx, ebp
push ebp
mov ebp, dword [_current_teletype]
cmp ebx, ebp
jz _teletype_switch_exit
mov esi, dword [ebp+_teletype.video]
mov edi, dword [ebp+_teletype.regen]
mov ecx, dword [_vbe_frame_amount]
call _copy_string
mov esi, dword [ebx+_teletype.regen]
mov edi, dword [ebx+_teletype.video]
mov ecx, dword [_vbe_frame_amount]
call _copy_string
mov dword [_current_teletype], ebx
_teletype_switch_exit:
pop ebp
ret
enum & _TELETYPE_UPDATE_CURSOR
_teletype_write_character:
; in:
; al - target character
; ebx - teletype object pointer
; edx - control character mask (only useful when al is a control character)
; edi - flags
; out:
; cf - set on error
; preserves: eax, ebx, ecx, esi, edi, ebp
push eax ecx esi ebp
push edi ; flags
push 0H ; is printable ?
call _teletype_remap_frame_buffer
jc _teletype_write_character_exit
cmp edi, (_TELETYPE_UPDATE_CURSOR + 1H)
cmc
jc _teletype_write_character_exit
mov ebp, _teletype_write_character_forward
cmp al, 07FH
jae _teletype_write_character_special
cmp al, 020H
jae _teletype_write_character_printable
_teletype_write_character_special:
mov edi, _TELETYPE_UPDATE_CURSOR
mov dword [esp+4H], edi
cmp al, 07FH
jae _teletype_write_character_escape
mov cl, al
mov ebp, 1H
shl ebp, cl
and ebp, edx
jz _teletype_write_character_control
_teletype_write_character_escape:
lea esi, [eax+040H]
and esi, 07FH
mov al, 05EH
call _teletype_write_character
jc _teletype_write_character_exit
mov eax, esi
call _teletype_write_character
jmp _teletype_write_character_exit
_teletype_write_character_control:
mov byte [esp], (not 0H)
cmp al, _TELETYPE_BACKSPACE
mov ebp, _teletype_direction_backward
jz _teletype_write_character_printable
cmp al, _TELETYPE_TABULATION
jz _teletype_write_character_tabulation
cmp al, _TELETYPE_NEWLINE
mov ebp, _teletype_write_character_newline
jz _teletype_write_character_printable
cmp al, _TELETYPE_CARRIAGE
mov ebp, _teletype_write_character_carriage
clc
jnz _teletype_write_character_exit
_teletype_write_character_printable:
mov esi, dword [ebx+_teletype.fonts.source]
sub al, 020H
movzx eax, al
mov cl, byte [ebx+_teletype.fonts.btposh]
shl eax, cl
add esi, eax
call _teletype_redraw_cursor
jc _teletype_write_character_exit
_teletype_write_character_display:
cmp byte [esp], 0H
jnz _teletype_write_character_invoke
xor eax, eax
mov al, (_TELETYPE_WRITE_TEMPLATE or _TELETYPE_SAVE_ALL)
mov edx, _teletype_write_character_glyph
call _teletype_write_character_foreach
jc _teletype_write_character_exit
_teletype_write_character_invoke:
test byte [esp+4H], _TELETYPE_UPDATE_CURSOR
jz _teletype_write_character_redraw
call ebp
jc _teletype_write_character_exit
_teletype_write_character_redraw:
call _teletype_redraw_cursor
jmp _teletype_write_character_exit
_teletype_write_character_tabulation:
movzx ecx, byte [ebx+_teletype.tabulation]
mov al, 020H
mov edi, _TELETYPE_UPDATE_CURSOR
test ecx, ecx
jnz _teletype_write_character_tabulation_loop
inc cl
_teletype_write_character_tabulation_loop:
call _teletype_write_character
jc _teletype_write_character_exit
loop _teletype_write_character_tabulation_loop
_teletype_write_character_exit:
lea esp, [esp+4H]
pop edi ebp esi ecx eax
ret
_teletype_write_character_forward:
; preserves: ebx, esi, edi, ebp
call _teletype_direction_forward
jnc _teletype_write_character_forward_exit+3H ; skip all pop
mov word [ebx+_teletype.xlinear], 0H
_teletype_write_character_forward_nextline:
push esi edi ebp
call _teletype_direction_downward
jnc _teletype_write_character_forward_exit
xor eax, eax
xor edx, edx
call _teletype_write_character_position
jc _teletype_write_character_forward_exit
mov esi, edi
xor eax, eax
movzx edx, word [ebx+_teletype.ylinear]
call _teletype_write_character_position
jc _teletype_write_character_forward_exit
mov ebp, edi
sub edi, esi
mov ecx, edi
xor eax, eax
xor edx, edx
inc dl
call _teletype_write_character_position
jc _teletype_write_character_forward_exit
xchg esi, edi
call _copy_string
mov edi, ebp
mov ecx, dword [ebx+_teletype.scroll]
call _clear_string
_teletype_write_character_forward_exit:
pop ebp edi esi
ret
_teletype_write_character_newline:
call _teletype_write_character_forward_nextline
test byte [ebx+_teletype.termios.oflag], OPOST
jnz _teletype_write_character_carriage
ret
_teletype_write_character_carriage:
mov word [ebx+_teletype.xlinear], 0H
ret
_teletype_write_character_position:
; in:
; eax - x linear in the framebuffer
; ebx - teletype object pointer
; edx - y linear in the framebuffer
; out: edi - framebuffer location
; preserves: ebx, ecx, esi, ebp
push ecx
mov cl, byte [ebx+_teletype.fonts.btposh]
shl edx, cl
movzx ecx, word [_current_modeinfo.bytes_scanline]
imul edx, ecx
jc _teletype_write_character_position_exit
mov cl, byte [ebx+_teletype.fonts.btposw]
shl eax, cl
call _bsf_bits_pixel
shl eax, cl
add eax, edx
call _teletype_buffer_target
add edi, eax
_teletype_write_character_position_exit:
pop ecx
ret
enum & _TELETYPE_WRITE_TEMPLATE, _TELETYPE_SAVE_ALL
_teletype_write_character_foreach:
; in:
; eax - write foreach flags
; ebx - teletype object pointer
; edx - predicate to call on each character scanline (functor must preserve all register except edi)
; out: cf - set on error
; preserves: eax, ebx, edx, ebp
; note:
; on predicate call all register must be preserved except eax when _TELETYPE_WRITE_TEMPLATE is specified
; cf is set also to indicate if a match occurs character '@' in fonts.inc
push eax ebp edx
cmp eax, ((_TELETYPE_WRITE_TEMPLATE or _TELETYPE_SAVE_ALL) + 1H)
cmc
jc _teletype_write_character_foreach_exit
movzx eax, word [ebx+_teletype.xlinear]
movzx edx, word [ebx+_teletype.ylinear]
call _teletype_write_character_position
jc _teletype_write_character_foreach_exit
movzx ecx, byte [ebx+_teletype.fonts.width]
movzx ebp, byte [ebx+_teletype.fonts.height]
_teletype_write_character_foreach_loop:
xor eax, eax
lea edx, [ecx-1H]
test byte [esp+8H], _TELETYPE_WRITE_TEMPLATE
jz _teletype_write_character_foreach_btst
lodsb
_teletype_write_character_foreach_btst:
test byte [esp+8H], _TELETYPE_SAVE_ALL
jnz _teletype_write_character_foreach_save_all
bt ax, dx
call dword [esp]
jmp _teletype_write_character_foreach_decrement
_teletype_write_character_foreach_save_all:
bt ax, dx
pusha
call dword [esp+_PUSHA_TOTAL]
mov dword [esp+_PUSHA_EDI], edi
popa
_teletype_write_character_foreach_decrement:
dec edx
test byte [esp+8H], _TELETYPE_WRITE_TEMPLATE
test edx, edx
jns _teletype_write_character_foreach_btst
dec ebp
jz _teletype_write_character_foreach_exit
movzx eax, word [_current_modeinfo.bytes_scanline]
lea edi, [edi+eax]
mov edx, ecx
call _bsf_bits_pixel
mov eax, edx
shl eax, cl
mov ecx, edx
sub edi, eax
jmp _teletype_write_character_foreach_loop
_teletype_write_character_foreach_exit:
pop edx ebp eax
ret
_teletype_write_character_glyph:
mov eax, dword [ebx+_teletype.backgnd]
jnc _teletype_write_character_glyph_store
mov eax, dword [ebx+_teletype.foregnd]
_teletype_write_character_glyph_store:
cmp byte [ebx+_teletype.legacy], 0H
jz $+5H
stosb
jmp $+3H
stosd
ret
_CURSOR_COLOR_RGB = _RGB_WHITE
_CURSOR_COLOR_VGA = _VGA_WHITE
_teletype_write_character_cursor:
mov eax, dword [ebx+_teletype.foregnd]
cmp byte [edi], al
jnz _teletype_write_character_cursor_color
cmp byte [ebx+_teletype.legacy], 0H
jnz _teletype_write_character_cursor_exit
cmp dword [edi], eax
jz _teletype_write_character_cursor_exit
_teletype_write_character_cursor_color:
mov eax, dword [ebx+_teletype.backgnd]
cmp byte [ebx+_teletype.legacy], 0H
jz _teletype_write_character_cursor_vbe
cmp byte [edi], _CURSOR_COLOR_VGA
jz _teletype_write_character_cursor_exit
xor eax, eax
mov al, _CURSOR_COLOR_VGA
jmp _teletype_write_character_cursor_exit
_teletype_write_character_cursor_vbe:
cmp dword [edi], _CURSOR_COLOR_RGB
jz _teletype_write_character_cursor_exit
mov eax, _CURSOR_COLOR_RGB
_teletype_write_character_cursor_exit:
jmp _teletype_write_character_glyph_store
_teletype_direction_downward:
; out: cf - set when overflow
mov ax, word [ebx+_teletype.ygrid]
dec ax
cmp word [ebx+_teletype.ylinear], ax
cmc
jc _teletype_direction_downward_exit
inc word [ebx+_teletype.ylinear]
_teletype_direction_downward_exit:
ret
_teletype_direction_forward:
; out: cf - set when overflow
mov ax, word [ebx+_teletype.xgrid]
dec ax
cmp word [ebx+_teletype.xlinear], ax
cmc
jc _teletype_direction_forward_exit
inc word [ebx+_teletype.xlinear]
_teletype_direction_forward_exit:
ret
_teletype_direction_upward:
cmp word [ebx+_teletype.ylinear], 0H
jz _teletype_direction_upward_exit
dec word [ebx+_teletype.ylinear]
_teletype_direction_upward_exit:
ret
_teletype_direction_backward:
cmp word [ebx+_teletype.xlinear], 0H
jz _teletype_direction_backward_exit
dec word [ebx+_teletype.xlinear]
_teletype_direction_backward_exit:
ret
_teletype_direction_reset:
mov word [ebx+_teletype.xlinear], 0H
mov word [ebx+_teletype.ylinear], 0H
ret
_teletype_erase_internal:
; in:
; ebx - teletype object pointer
; ecx - count of byte to delete
; out: cf - set on error
; preserves: ebx
jecxz _teletype_erase_internal_exit
cmp word [ebx+_teletype.index], 0H
jz _teletype_erase_internal_exit
movzx esi, word [ebx+_teletype.index]
cmp ecx, esi
cmova ecx, esi
dec esi
add esi, dword [ebx+_teletype.input]
_teletype_erase_internal_loop:
std
lodsb
cld
mov ebp, ecx
xor ecx, ecx
cmp al, _TELETYPE_TABULATION
mov cl, 4H
jz _teletype_erase_internal_backspace
cmp al, 020H
jb _teletype_erase_internal_special
cmp al, 07FH
jae _teletype_erase_internal_special
mov cl, 1H
jnz _teletype_erase_internal_backspace
_teletype_erase_internal_special:
xor cl, cl
test dword [ebx+_teletype.termios.lflag], ECHOCTL
jz _teletype_erase_internal_backspace
mov cl, 2H
_teletype_erase_internal_backspace:
test dword [ebx+_teletype.termios.lflag], ECHO
jz teletype_erase_internal_update
call _teletype_erase_character
jc _teletype_erase_internal_exit
teletype_erase_internal_update:
dec word [ebx+_teletype.index]
mov ecx, ebp
loop _teletype_erase_internal_loop
_teletype_erase_internal_exit:
ret
_teletype_insert_character:
; in:
; al - byte wanted to be inserted
; ebx - teletype object pointer
; preserves: eax, ebx, ecx, edx, esi, ebp
call _teletype_internal_buffer_full
jc _teletype_insert_character_exit
movzx edi, word [ebx+_teletype.index]
add edi, dword [ebx+_teletype.input]
stosb
inc word [ebx+_teletype.index]
clc
_teletype_insert_character_exit:
ret
_teletype_send_signal:
; in:
; eax - signal kind
; ebx - teletype object pointer
; out: cf - set if bad signal or teletype not a controling terminal and not have a foreground group
; preserves: ebx, esi, edi, ebp
; note: send the signal to all the process in the "foreground" group
push ebx esi ebp
cmp byte [ebx+_teletype.control], 0H
jz _teletype_send_signal_exit
cmp byte [ebx+_teletype.fground], 0H
jz _teletype_send_signal_exit
mov ebp, eax
mov eax, dword [ebx+_teletype.grpdesc]
lea eax, [eax+_process_group_descriptor.prclist]
xor ecx, ecx
mov cl, _process.pgroup
xor edx, edx
mov dl, (_LIST_FORWARD or _LIST_SAVE_ALL)
mov esi, _send_signal_process_group_iterate
call _find_list
_teletype_send_signal_exit:
cmc
pop ebp esi ebx
ret