summaryrefslogtreecommitdiff
path: root/editors
diff options
context:
space:
mode:
Diffstat (limited to 'editors')
-rw-r--r--editors/vi.c552
1 files changed, 276 insertions, 276 deletions
diff --git a/editors/vi.c b/editors/vi.c
index e960afc..9db763c 100644
--- a/editors/vi.c
+++ b/editors/vi.c
@@ -693,6 +693,282 @@ static ALWAYS_INLINE int query_screen_dimensions(void)
}
#endif
+// sleep for 'h' 1/100 seconds, return 1/0 if stdin is (ready for read)/(not ready)
+static int mysleep(int hund)
+{
+ struct pollfd pfd[1];
+
+ if (hund != 0)
+ fflush_all();
+
+ pfd[0].fd = STDIN_FILENO;
+ pfd[0].events = POLLIN;
+ return safe_poll(pfd, 1, hund*10) > 0;
+}
+
+//----- Set terminal attributes --------------------------------
+static void rawmode(void)
+{
+ // no TERMIOS_CLEAR_ISIG: leave ISIG on - allow signals
+ set_termios_to_raw(STDIN_FILENO, &term_orig, TERMIOS_RAW_CRNL);
+ erase_char = term_orig.c_cc[VERASE];
+}
+
+static void cookmode(void)
+{
+ fflush_all();
+ tcsetattr_stdin_TCSANOW(&term_orig);
+}
+
+//----- Terminal Drawing ---------------------------------------
+// The terminal is made up of 'rows' line of 'columns' columns.
+// classically this would be 24 x 80.
+// screen coordinates
+// 0,0 ... 0,79
+// 1,0 ... 1,79
+// . ... .
+// . ... .
+// 22,0 ... 22,79
+// 23,0 ... 23,79 <- status line
+
+//----- Move the cursor to row x col (count from 0, not 1) -------
+static void place_cursor(int row, int col)
+{
+ char cm1[sizeof(ESC_SET_CURSOR_POS) + sizeof(int)*3 * 2];
+
+ if (row < 0) row = 0;
+ if (row >= rows) row = rows - 1;
+ if (col < 0) col = 0;
+ if (col >= columns) col = columns - 1;
+
+ sprintf(cm1, ESC_SET_CURSOR_POS, row + 1, col + 1);
+ write1(cm1);
+}
+
+//----- Erase from cursor to end of line -----------------------
+static void clear_to_eol(void)
+{
+ write1(ESC_CLEAR2EOL);
+}
+
+static void go_bottom_and_clear_to_eol(void)
+{
+ place_cursor(rows - 1, 0);
+ clear_to_eol();
+}
+
+//----- Start standout mode ------------------------------------
+static void standout_start(void)
+{
+ write1(ESC_BOLD_TEXT);
+}
+
+//----- End standout mode --------------------------------------
+static void standout_end(void)
+{
+ write1(ESC_NORM_TEXT);
+}
+
+//----- Text Movement Routines ---------------------------------
+static char *begin_line(char *p) // return pointer to first char cur line
+{
+ if (p > text) {
+ p = memrchr(text, '\n', p - text);
+ if (!p)
+ return text;
+ return p + 1;
+ }
+ return p;
+}
+
+static char *end_line(char *p) // return pointer to NL of cur line
+{
+ if (p < end - 1) {
+ p = memchr(p, '\n', end - p - 1);
+ if (!p)
+ return end - 1;
+ }
+ return p;
+}
+
+static char *dollar_line(char *p) // return pointer to just before NL line
+{
+ p = end_line(p);
+ // Try to stay off of the Newline
+ if (*p == '\n' && (p - begin_line(p)) > 0)
+ p--;
+ return p;
+}
+
+static char *prev_line(char *p) // return pointer first char prev line
+{
+ p = begin_line(p); // goto beginning of cur line
+ if (p > text && p[-1] == '\n')
+ p--; // step to prev line
+ p = begin_line(p); // goto beginning of prev line
+ return p;
+}
+
+static char *next_line(char *p) // return pointer first char next line
+{
+ p = end_line(p);
+ if (p < end - 1 && *p == '\n')
+ p++; // step to next line
+ return p;
+}
+
+//----- Text Information Routines ------------------------------
+static char *end_screen(void)
+{
+ char *q;
+ int cnt;
+
+ // find new bottom line
+ q = screenbegin;
+ for (cnt = 0; cnt < rows - 2; cnt++)
+ q = next_line(q);
+ q = end_line(q);
+ return q;
+}
+
+// count line from start to stop
+static int count_lines(char *start, char *stop)
+{
+ char *q;
+ int cnt;
+
+ if (stop < start) { // start and stop are backwards- reverse them
+ q = start;
+ start = stop;
+ stop = q;
+ }
+ cnt = 0;
+ stop = end_line(stop);
+ while (start <= stop && start <= end - 1) {
+ start = end_line(start);
+ if (*start == '\n')
+ cnt++;
+ start++;
+ }
+ return cnt;
+}
+
+static char *find_line(int li) // find beginning of line #li
+{
+ char *q;
+
+ for (q = text; li > 1; li--) {
+ q = next_line(q);
+ }
+ return q;
+}
+
+static int next_tabstop(int col)
+{
+ return col + ((tabstop - 1) - (col % tabstop));
+}
+
+//----- Erase the Screen[] memory ------------------------------
+static void screen_erase(void)
+{
+ memset(screen, ' ', screensize); // clear new screen
+}
+
+//----- Synchronize the cursor to Dot --------------------------
+static NOINLINE void sync_cursor(char *d, int *row, int *col)
+{
+ char *beg_cur; // begin and end of "d" line
+ char *tp;
+ int cnt, ro, co;
+
+ beg_cur = begin_line(d); // first char of cur line
+
+ if (beg_cur < screenbegin) {
+ // "d" is before top line on screen
+ // how many lines do we have to move
+ cnt = count_lines(beg_cur, screenbegin);
+ sc1:
+ screenbegin = beg_cur;
+ if (cnt > (rows - 1) / 2) {
+ // we moved too many lines. put "dot" in middle of screen
+ for (cnt = 0; cnt < (rows - 1) / 2; cnt++) {
+ screenbegin = prev_line(screenbegin);
+ }
+ }
+ } else {
+ char *end_scr; // begin and end of screen
+ end_scr = end_screen(); // last char of screen
+ if (beg_cur > end_scr) {
+ // "d" is after bottom line on screen
+ // how many lines do we have to move
+ cnt = count_lines(end_scr, beg_cur);
+ if (cnt > (rows - 1) / 2)
+ goto sc1; // too many lines
+ for (ro = 0; ro < cnt - 1; ro++) {
+ // move screen begin the same amount
+ screenbegin = next_line(screenbegin);
+ // now, move the end of screen
+ end_scr = next_line(end_scr);
+ end_scr = end_line(end_scr);
+ }
+ }
+ }
+ // "d" is on screen- find out which row
+ tp = screenbegin;
+ for (ro = 0; ro < rows - 1; ro++) { // drive "ro" to correct row
+ if (tp == beg_cur)
+ break;
+ tp = next_line(tp);
+ }
+
+ // find out what col "d" is on
+ co = 0;
+ while (tp < d) { // drive "co" to correct column
+ if (*tp == '\n') //vda || *tp == '\0')
+ break;
+ if (*tp == '\t') {
+ // handle tabs like real vi
+ if (d == tp && cmd_mode) {
+ break;
+ }
+ co = next_tabstop(co);
+ } else if ((unsigned char)*tp < ' ' || *tp == 0x7f) {
+ co++; // display as ^X, use 2 columns
+ }
+ co++;
+ tp++;
+ }
+
+ // "co" is the column where "dot" is.
+ // The screen has "columns" columns.
+ // The currently displayed columns are 0+offset -- columns+ofset
+ // |-------------------------------------------------------------|
+ // ^ ^ ^
+ // offset | |------- columns ----------------|
+ //
+ // If "co" is already in this range then we do not have to adjust offset
+ // but, we do have to subtract the "offset" bias from "co".
+ // If "co" is outside this range then we have to change "offset".
+ // If the first char of a line is a tab the cursor will try to stay
+ // in column 7, but we have to set offset to 0.
+
+ if (co < 0 + offset) {
+ offset = co;
+ }
+ if (co >= columns + offset) {
+ offset = co - columns + 1;
+ }
+ // if the first char of the line is a tab, and "dot" is sitting on it
+ // force offset to 0.
+ if (d == beg_cur && *d == '\t') {
+ offset = 0;
+ }
+ co -= offset;
+
+ *row = ro;
+ *col = co;
+}
+
//----- The Colon commands -------------------------------------
#if ENABLE_FEATURE_VI_COLON
static char *get_one_address(char *p, int *addr) // get colon addr, if present
@@ -1355,200 +1631,6 @@ static void Hit_Return(void)
redraw(TRUE); // force redraw all
}
-static int next_tabstop(int col)
-{
- return col + ((tabstop - 1) - (col % tabstop));
-}
-
-//----- Synchronize the cursor to Dot --------------------------
-static NOINLINE void sync_cursor(char *d, int *row, int *col)
-{
- char *beg_cur; // begin and end of "d" line
- char *tp;
- int cnt, ro, co;
-
- beg_cur = begin_line(d); // first char of cur line
-
- if (beg_cur < screenbegin) {
- // "d" is before top line on screen
- // how many lines do we have to move
- cnt = count_lines(beg_cur, screenbegin);
- sc1:
- screenbegin = beg_cur;
- if (cnt > (rows - 1) / 2) {
- // we moved too many lines. put "dot" in middle of screen
- for (cnt = 0; cnt < (rows - 1) / 2; cnt++) {
- screenbegin = prev_line(screenbegin);
- }
- }
- } else {
- char *end_scr; // begin and end of screen
- end_scr = end_screen(); // last char of screen
- if (beg_cur > end_scr) {
- // "d" is after bottom line on screen
- // how many lines do we have to move
- cnt = count_lines(end_scr, beg_cur);
- if (cnt > (rows - 1) / 2)
- goto sc1; // too many lines
- for (ro = 0; ro < cnt - 1; ro++) {
- // move screen begin the same amount
- screenbegin = next_line(screenbegin);
- // now, move the end of screen
- end_scr = next_line(end_scr);
- end_scr = end_line(end_scr);
- }
- }
- }
- // "d" is on screen- find out which row
- tp = screenbegin;
- for (ro = 0; ro < rows - 1; ro++) { // drive "ro" to correct row
- if (tp == beg_cur)
- break;
- tp = next_line(tp);
- }
-
- // find out what col "d" is on
- co = 0;
- while (tp < d) { // drive "co" to correct column
- if (*tp == '\n') //vda || *tp == '\0')
- break;
- if (*tp == '\t') {
- // handle tabs like real vi
- if (d == tp && cmd_mode) {
- break;
- }
- co = next_tabstop(co);
- } else if ((unsigned char)*tp < ' ' || *tp == 0x7f) {
- co++; // display as ^X, use 2 columns
- }
- co++;
- tp++;
- }
-
- // "co" is the column where "dot" is.
- // The screen has "columns" columns.
- // The currently displayed columns are 0+offset -- columns+ofset
- // |-------------------------------------------------------------|
- // ^ ^ ^
- // offset | |------- columns ----------------|
- //
- // If "co" is already in this range then we do not have to adjust offset
- // but, we do have to subtract the "offset" bias from "co".
- // If "co" is outside this range then we have to change "offset".
- // If the first char of a line is a tab the cursor will try to stay
- // in column 7, but we have to set offset to 0.
-
- if (co < 0 + offset) {
- offset = co;
- }
- if (co >= columns + offset) {
- offset = co - columns + 1;
- }
- // if the first char of the line is a tab, and "dot" is sitting on it
- // force offset to 0.
- if (d == beg_cur && *d == '\t') {
- offset = 0;
- }
- co -= offset;
-
- *row = ro;
- *col = co;
-}
-
-//----- Text Movement Routines ---------------------------------
-static char *begin_line(char *p) // return pointer to first char cur line
-{
- if (p > text) {
- p = memrchr(text, '\n', p - text);
- if (!p)
- return text;
- return p + 1;
- }
- return p;
-}
-
-static char *end_line(char *p) // return pointer to NL of cur line
-{
- if (p < end - 1) {
- p = memchr(p, '\n', end - p - 1);
- if (!p)
- return end - 1;
- }
- return p;
-}
-
-static char *dollar_line(char *p) // return pointer to just before NL line
-{
- p = end_line(p);
- // Try to stay off of the Newline
- if (*p == '\n' && (p - begin_line(p)) > 0)
- p--;
- return p;
-}
-
-static char *prev_line(char *p) // return pointer first char prev line
-{
- p = begin_line(p); // goto beginning of cur line
- if (p > text && p[-1] == '\n')
- p--; // step to prev line
- p = begin_line(p); // goto beginning of prev line
- return p;
-}
-
-static char *next_line(char *p) // return pointer first char next line
-{
- p = end_line(p);
- if (p < end - 1 && *p == '\n')
- p++; // step to next line
- return p;
-}
-
-//----- Text Information Routines ------------------------------
-static char *end_screen(void)
-{
- char *q;
- int cnt;
-
- // find new bottom line
- q = screenbegin;
- for (cnt = 0; cnt < rows - 2; cnt++)
- q = next_line(q);
- q = end_line(q);
- return q;
-}
-
-// count line from start to stop
-static int count_lines(char *start, char *stop)
-{
- char *q;
- int cnt;
-
- if (stop < start) { // start and stop are backwards- reverse them
- q = start;
- start = stop;
- stop = q;
- }
- cnt = 0;
- stop = end_line(stop);
- while (start <= stop && start <= end - 1) {
- start = end_line(start);
- if (*start == '\n')
- cnt++;
- start++;
- }
- return cnt;
-}
-
-static char *find_line(int li) // find beginning of line #li
-{
- char *q;
-
- for (q = text; li > 1; li--) {
- q = next_line(q);
- }
- return q;
-}
-
//----- Dot Movement Routines ----------------------------------
static void dot_left(void)
{
@@ -2430,32 +2512,6 @@ static char *swap_context(char *p) // goto new context for '' command make this
}
#endif /* FEATURE_VI_YANKMARK */
-//----- Set terminal attributes --------------------------------
-static void rawmode(void)
-{
- // no TERMIOS_CLEAR_ISIG: leave ISIG on - allow signals
- set_termios_to_raw(STDIN_FILENO, &term_orig, TERMIOS_RAW_CRNL);
- erase_char = term_orig.c_cc[VERASE];
-}
-
-static void cookmode(void)
-{
- fflush_all();
- tcsetattr_stdin_TCSANOW(&term_orig);
-}
-
-static int mysleep(int hund) // sleep for 'hund' 1/100 seconds or stdin ready
-{
- struct pollfd pfd[1];
-
- if (hund != 0)
- fflush_all();
-
- pfd[0].fd = STDIN_FILENO;
- pfd[0].events = POLLIN;
- return safe_poll(pfd, 1, hund*10) > 0;
-}
-
//----- IO Routines --------------------------------------------
static int readit(void) // read (maybe cursor) key from stdin
{
@@ -2637,55 +2693,6 @@ static int file_write(char *fn, char *first, char *last)
return charcnt;
}
-//----- Terminal Drawing ---------------------------------------
-// The terminal is made up of 'rows' line of 'columns' columns.
-// classically this would be 24 x 80.
-// screen coordinates
-// 0,0 ... 0,79
-// 1,0 ... 1,79
-// . ... .
-// . ... .
-// 22,0 ... 22,79
-// 23,0 ... 23,79 <- status line
-
-//----- Move the cursor to row x col (count from 0, not 1) -------
-static void place_cursor(int row, int col)
-{
- char cm1[sizeof(ESC_SET_CURSOR_POS) + sizeof(int)*3 * 2];
-
- if (row < 0) row = 0;
- if (row >= rows) row = rows - 1;
- if (col < 0) col = 0;
- if (col >= columns) col = columns - 1;
-
- sprintf(cm1, ESC_SET_CURSOR_POS, row + 1, col + 1);
- write1(cm1);
-}
-
-//----- Erase from cursor to end of line -----------------------
-static void clear_to_eol(void)
-{
- write1(ESC_CLEAR2EOL);
-}
-
-static void go_bottom_and_clear_to_eol(void)
-{
- place_cursor(rows - 1, 0);
- clear_to_eol();
-}
-
-//----- Start standout mode ------------------------------------
-static void standout_start(void)
-{
- write1(ESC_BOLD_TEXT);
-}
-
-//----- End standout mode --------------------------------------
-static void standout_end(void)
-{
- write1(ESC_NORM_TEXT);
-}
-
//----- Flash the screen --------------------------------------
static void flash(int h)
{
@@ -2709,13 +2716,6 @@ static void indicate_error(void)
}
}
-//----- Screen[] Routines --------------------------------------
-//----- Erase the Screen[] memory ------------------------------
-static void screen_erase(void)
-{
- memset(screen, ' ', screensize); // clear new screen
-}
-
static int bufsum(char *buf, int count)
{
int sum = 0;