include: one folder per subsystem, and includes that name it
Sixty-five headers sat side by side in include/, so `#include "irq.h"` said nothing about where irq.h was or what it belonged to, and errno.h, stat.h and fcntl.h at the top shadowed the system's for any host tool built with -I./include. They are in folders now -- arch/ core/ fs/ dev/ gfx/ net/ uapi/ (and ldls/ for the Linux driver layer) -- and every include names the folder, as Linux's do: "core/proc.h". Done mechanically and checked the hard way: the kernel built from this tree disassembles identically to the one built from the tree before it. The full image boots, and userland is the same set of programs. Paths in docs and comments follow; docs/guides/layout.md has a table of what is where, and tools/fix-includes.py rewrites old-style includes from the folders in the tree, for code written before this. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01S1giNvrHTrPMPw7V6x1kQ4
This commit is contained in:
parent
0e39e711f1
commit
a1c965da1e
267 changed files with 1560 additions and 1440 deletions
164
include/dev/vt.h
Normal file
164
include/dev/vt.h
Normal file
|
|
@ -0,0 +1,164 @@
|
|||
// SPDX-License-Identifier: GPL-2.0-or-later
|
||||
//
|
||||
// Virtual terminals.
|
||||
//
|
||||
// Until this existed there was one console. `/dev/tty` was an alias for
|
||||
// `/dev/console` with the same major and minor, `tty_fg_pgrp` was a single
|
||||
// global int, and TIOCSCTTY was `return 0`. One screen, one foreground
|
||||
// process group, one line discipline, no way to have a second shell.
|
||||
//
|
||||
// The thing that makes switching possible is a backing store. The console
|
||||
// drew straight into the framebuffer and scrolled by moving pixels, which
|
||||
// works exactly as long as nothing else ever wants the screen: there was
|
||||
// nowhere to put terminal 2 while terminal 1 was visible, and nothing to
|
||||
// repaint terminal 1 from when it came back. So each VT owns a grid of cells
|
||||
// and the framebuffer shows whichever grid is active.
|
||||
//
|
||||
// A VT that is not active is not a special case. Writes to it land in its
|
||||
// grid, its cursor moves, it scrolls; the only thing it does not do is draw.
|
||||
// That is the whole switching mechanism: vt_switch repaints, and everything
|
||||
// else is written as though it were always on screen.
|
||||
|
||||
#ifndef VT_H
|
||||
#define VT_H
|
||||
|
||||
#include "core/types.h"
|
||||
#include "core/param.h"
|
||||
#include "uapi/posix.h"
|
||||
|
||||
// Six, and Linux's numbering: /dev/tty1 through /dev/tty6, reached with
|
||||
// Alt+1..Alt+6. A seventh is deliberately not bound -- that is where a
|
||||
// display server goes, and Schcom will want it.
|
||||
#define NVT 6
|
||||
|
||||
// A cell.
|
||||
//
|
||||
// `ch` is the glyph the font draws, not a codepoint: the console maps UTF-8
|
||||
// to CP437 before it gets here, because that is what include/gfx/font.h contains.
|
||||
// Storing the codepoint would mean re-running that mapping on every repaint
|
||||
// and getting a different answer for anything the font cannot draw.
|
||||
//
|
||||
// The colours are palette indices rather than RGB. Sixteen ANSI colours plus
|
||||
// the two theme defaults fit in a byte each and make a cell four bytes; the
|
||||
// same cell holding two 32-bit colours would be twelve, and the grids are
|
||||
// static.
|
||||
struct vtcell {
|
||||
// A Unicode codepoint, not a byte.
|
||||
//
|
||||
// This was a uint8, which is to say the grid could hold 256 distinct glyphs
|
||||
// and every terminal was a CP437 terminal. A codepoint outside that was not
|
||||
// stored wrongly, it was *converted* -- `glyph_for()` mapped what it could
|
||||
// and turned the rest into `?`. Ą, Ę, Ś, Ω, Œ, Ə, ∞ and every other
|
||||
// character anybody actually types were question marks before they reached
|
||||
// the font, so no font could have fixed it.
|
||||
//
|
||||
// Four bytes a cell instead of one. A 1920x1080 screen at 9x18 is 12,720
|
||||
// cells, so the grid costs 100 KB instead of 50 KB per terminal.
|
||||
uint32 ch;
|
||||
uint8 fg;
|
||||
uint8 bg;
|
||||
uint8 attr; // reserved: bold/underline/reverse, which do not change
|
||||
uint8 pad; // the glyph and so can be added without touching a grid
|
||||
};
|
||||
|
||||
#define VT_FG_DEFAULT 16 // SCH_FG from include/gfx/theme.h
|
||||
#define VT_BG_DEFAULT 17 // SCH_BG
|
||||
#define VT_NCOLOUR 18
|
||||
|
||||
// Cell attributes that do not change which glyph is drawn, only how.
|
||||
#define VT_ATTR_REVERSE 0x01
|
||||
|
||||
// The largest console a grid can hold, which is 1920x1200 with the 8x16 font.
|
||||
// A framebuffer wider or taller than this still works -- vt_init clamps the
|
||||
// grid and the rest of the screen stays background -- but it is worth raising
|
||||
// rather than living with, because the clamp is invisible until someone
|
||||
// notices the bottom of their screen never has text on it.
|
||||
#define VT_MAXCOLS 240
|
||||
#define VT_MAXROWS 75
|
||||
|
||||
#define VT_INPUT_BUF 256
|
||||
#define VT_MAXPARM 8
|
||||
|
||||
// Escape parser states. E_OSC and E_OSC_ESC exist for hyperlinks: a terminal
|
||||
// that does not follow OSC 8 must still consume it, or the URL is printed as
|
||||
// text. See the comment in kernel/core/console.c that this came from.
|
||||
enum { VE_NORMAL, VE_ESC, VE_CSI, VE_OSC, VE_OSC_ESC };
|
||||
|
||||
struct vt {
|
||||
int index; // 0-based; /dev/tty<index+1>
|
||||
int cols, rows;
|
||||
|
||||
struct vtcell *cells; // cols*rows, row-major, into vt_storage
|
||||
|
||||
int cx, cy; // cursor, in cells
|
||||
// Deferred wrap, the rule every real terminal follows and none of them
|
||||
// document well: a glyph printed in the last column does NOT move the
|
||||
// cursor to the next line. It sets this instead, and the wrap happens when
|
||||
// the *next* glyph arrives. Anything that moves the cursor deliberately --
|
||||
// CR, LF, backspace, an escape sequence -- clears it.
|
||||
int wrap_pending;
|
||||
int saved_cx, saved_cy; // DECSC/DECRC
|
||||
|
||||
uint8 fg, bg; // current SGR colours
|
||||
int bold;
|
||||
int attr; // VT_ATTR_* applied to new cells
|
||||
|
||||
// Escape parser.
|
||||
int esc_state;
|
||||
int esc_parm[VT_MAXPARM];
|
||||
int esc_nparm;
|
||||
int esc_private;
|
||||
|
||||
// UTF-8 decoder.
|
||||
uint32 u8_cp;
|
||||
int u8_need;
|
||||
|
||||
// Line discipline. One per terminal, because ICANON and ECHO are properties
|
||||
// of a terminal and not of the machine.
|
||||
struct termios tio;
|
||||
|
||||
struct {
|
||||
char buf[VT_INPUT_BUF];
|
||||
uint r, w, e;
|
||||
uint abort_read;
|
||||
uint eof;
|
||||
} in;
|
||||
|
||||
// Job control. This was one global for the whole system; a terminal each
|
||||
// is the entire point of having more than one.
|
||||
int fg_pgrp;
|
||||
int sid; // session that owns this terminal, 0 = none
|
||||
|
||||
int opened; // times it has been opened, for /dev/tty
|
||||
|
||||
// VT_AUTO or VT_PROCESS. In VT_PROCESS a program has claimed switching and
|
||||
// the kernel stops acting on the chord -- see vt_kernel_switches().
|
||||
int mode;
|
||||
};
|
||||
|
||||
// The active terminal, and the one the framebuffer is showing.
|
||||
extern int vt_active;
|
||||
|
||||
void vt_init(void);
|
||||
void vt_resize(void); // a scanout arrived; re-measure
|
||||
struct vt *vt_get(int i); // 0-based, clamped, never null
|
||||
struct vt *vt_current(void);
|
||||
int vt_switch(int i); // 0-based; repaints. -1 if out of range
|
||||
int vt_cycle(int dir); // -1 previous, +1 next, in-use only
|
||||
|
||||
// Output, per terminal. Drawing happens only if `v` is the active one.
|
||||
void vt_feed(struct vt *v, int c); // one output byte, through the parser
|
||||
void vt_putc(struct vt *v, int glyph); // one glyph, already mapped
|
||||
void vt_cursor_set(struct vt *v, int col, int row);
|
||||
void vt_cursor_get(struct vt *v, int *col, int *row);
|
||||
void vt_erase_display(struct vt *v, int mode);
|
||||
void vt_erase_line(struct vt *v, int mode);
|
||||
void vt_clear(struct vt *v);
|
||||
void vt_scroll(struct vt *v);
|
||||
void vt_repaint(struct vt *v); // grid -> framebuffer, if active
|
||||
|
||||
uint32 vt_rgb(uint8 idx); // palette index -> RGB
|
||||
int vt_index(struct vt *v); // 0-based number of a terminal
|
||||
int vt_kernel_switches(void); // 0 if a program owns switching
|
||||
|
||||
#endif // VT_H
|
||||
Loading…
Reference in a new issue