2 * Copyright (C) 1984-2012 Mark Nudelman
3 * Modified for use with illumos by Garrett D'Amore.
4 * Copyright 2014 Garrett D'Amore <garrett@damore.org>
6 * You may distribute under the terms of either the GNU General Public
7 * License or the Less License, as specified in the README file.
9 * For more information, see the README file.
13 * Routines to manipulate the "line buffer".
14 * The line buffer holds a line of output as it is being built
15 * in preparation for output to the screen.
21 static char *linebuf
= NULL
; /* Buffer which holds the current output line */
22 static char *attr
= NULL
; /* Extension of linebuf to hold attributes */
23 int size_linebuf
= 0; /* Size of line buffer (and attr buffer) */
25 static int cshift
; /* Current left-shift of output line buffer */
26 int hshift
; /* Desired left-shift of output line buffer */
27 int tabstops
[TABSTOP_MAX
] = { 0 }; /* Custom tabstops */
28 int ntabstops
= 1; /* Number of tabstops */
29 int tabdefault
= 8; /* Default repeated tabstops */
30 off_t highest_hilite
; /* Pos of last hilite in file found so far */
32 static int curr
; /* Index into linebuf */
33 static int column
; /* Printable length, accounting for backspaces, etc. */
34 static int overstrike
; /* Next char should overstrike previous char */
35 static int is_null_line
; /* There is no current line */
36 static int lmargin
; /* Left margin */
39 static char *end_ansi_chars
;
40 static char *mid_ansi_chars
;
42 static int attr_swidth(int);
43 static int attr_ewidth(int);
44 static int do_append(LWCHAR
, char *, off_t
);
46 extern volatile sig_atomic_t sigs
;
52 extern int status_col
;
53 extern int auto_wrap
, ignaw
;
54 extern int bo_s_width
, bo_e_width
;
55 extern int ul_s_width
, ul_e_width
;
56 extern int bl_s_width
, bl_e_width
;
57 extern int so_s_width
, so_e_width
;
58 extern int sc_width
, sc_height
;
60 extern off_t start_attnpos
;
61 extern off_t end_attnpos
;
63 static char mbc_buf
[MAX_UTF_CHAR_LEN
];
64 static int mbc_buf_len
= 0;
65 static int mbc_buf_index
= 0;
69 * Initialize from environment variables.
74 end_ansi_chars
= lgetenv("LESSANSIENDCHARS");
75 if (end_ansi_chars
== NULL
|| *end_ansi_chars
== '\0')
78 mid_ansi_chars
= lgetenv("LESSANSIMIDCHARS");
79 if (mid_ansi_chars
== NULL
|| *mid_ansi_chars
== '\0')
80 mid_ansi_chars
= "0123456789;[?!\"'#%()*+ ";
82 linebuf
= ecalloc(LINEBUF_SIZE
, sizeof (char));
83 attr
= ecalloc(LINEBUF_SIZE
, sizeof (char));
84 size_linebuf
= LINEBUF_SIZE
;
88 * Expand the line buffer.
93 /* Double the size of the line buffer. */
94 int new_size
= size_linebuf
* 2;
96 /* Just realloc to expand the buffer, if we can. */
97 char *new_buf
= recallocarray(linebuf
, size_linebuf
, new_size
, 1);
98 char *new_attr
= recallocarray(attr
, size_linebuf
, new_size
, 1);
99 if (new_buf
== NULL
|| new_attr
== NULL
) {
106 size_linebuf
= new_size
;
111 * Is a character ASCII?
114 is_ascii_char(LWCHAR ch
)
120 * Rewind the line buffer.
138 * Insert the line number (of the given position) into the line buffer.
146 if (linenums
== OPT_ONPLUS
) {
148 * Get the line number and put it in the current line.
149 * {{ Note: since find_linenum calls forw_raw_line,
150 * it may seek in the input file, requiring the caller
151 * of plinenum to re-seek if necessary. }}
152 * {{ Since forw_raw_line modifies linebuf, we must
153 * do this first, before storing anything in linebuf. }}
155 linenum
= find_linenum(pos
);
159 * Display a status column if the -J option is set.
163 if (start_attnpos
!= -1 &&
164 pos
>= start_attnpos
&& pos
< end_attnpos
)
165 attr
[curr
] = AT_NORMAL
|AT_HILITE
;
167 attr
[curr
] = AT_NORMAL
;
172 * Display the line number at the start of each line
173 * if the -N option is set.
175 if (linenums
== OPT_ONPLUS
) {
179 postoa(linenum
, buf
, sizeof(buf
));
181 if (n
< MIN_LINENUM_WIDTH
)
182 n
= MIN_LINENUM_WIDTH
;
183 snprintf(linebuf
+curr
, size_linebuf
-curr
, "%*s ", n
, buf
);
184 n
++; /* One space after the line number. */
185 for (i
= 0; i
< n
; i
++)
186 attr
[curr
+i
] = AT_NORMAL
;
193 * Append enough spaces to bring us to the lmargin.
195 while (column
< lmargin
) {
197 attr
[curr
++] = AT_NORMAL
;
203 * Shift the input line left.
204 * This means discarding N printable chars at the start of the buffer.
219 if (shift
> column
- lmargin
)
220 shift
= column
- lmargin
;
221 if (shift
> curr
- lmargin
)
222 shift
= curr
- lmargin
;
226 * We keep on going when shifted == shift
227 * to get all combining chars.
229 while (shifted
<= shift
&& from
< curr
) {
231 if (ctldisp
== OPT_ONPLUS
&& IS_CSI_START(c
)) {
232 /* Keep cumulative effect. */
234 attr
[to
++] = attr
[from
++];
235 while (from
< curr
&& linebuf
[from
]) {
236 linebuf
[to
] = linebuf
[from
];
237 attr
[to
++] = attr
[from
];
238 if (!is_ansi_middle(linebuf
[from
++]))
246 if (!IS_ASCII_OCTET(c
) && utf_mode
) {
247 /* Assumes well-formedness validation already done. */
251 if (from
+ len
> curr
)
253 ch
= get_wchar(linebuf
+ from
);
254 if (!is_composing_char(ch
) &&
255 !is_combining_char(prev_ch
, ch
))
256 width
= is_wide_char(ch
) ? 2 : 1;
261 /* XXX - Incorrect if several '\b' in a row. */
262 width
= (utf_mode
&& is_wide_char(prev_ch
)) ?
264 else if (!control_char(c
))
269 if (width
== 2 && shift
- shifted
== 1) {
270 /* Should never happen when called by pshift_all(). */
271 attr
[to
] = attr
[from
];
273 * Assume a wide_char will never be the first half of a
274 * combining_char pair, so reset prev_ch in case we're
275 * followed by a '\b'.
277 prev_ch
= linebuf
[to
++] = ' ';
283 /* Adjust width for magic cookies. */
284 prev_attr
= (to
> 0) ? attr
[to
-1] : AT_NORMAL
;
285 next_attr
= (from
+ len
< curr
) ? attr
[from
+ len
] : prev_attr
;
286 if (!is_at_equiv(attr
[from
], prev_attr
) &&
287 !is_at_equiv(attr
[from
], next_attr
)) {
288 width
+= attr_swidth(attr
[from
]);
289 if (from
+ len
< curr
)
290 width
+= attr_ewidth(attr
[from
]);
291 if (is_at_equiv(prev_attr
, next_attr
)) {
292 width
+= attr_ewidth(prev_attr
);
293 if (from
+ len
< curr
)
294 width
+= attr_swidth(next_attr
);
298 if (shift
- shifted
< width
)
305 while (from
< curr
) {
306 linebuf
[to
] = linebuf
[from
];
307 attr
[to
++] = attr
[from
++];
324 * Return the printing width of the start (enter) sequence
325 * for a given character attribute.
332 a
= apply_at_specials(a
);
334 if (a
& AT_UNDERLINE
)
347 * Return the printing width of the end (exit) sequence
348 * for a given character attribute.
355 a
= apply_at_specials(a
);
357 if (a
& AT_UNDERLINE
)
370 * Return the printing width of a given character and attribute,
371 * if the character were added to the current position in the line buffer.
372 * Adding a character with a given attribute may cause an enter or exit
373 * attribute sequence to be inserted, so this must be taken into account.
376 pwidth(LWCHAR ch
, int a
, LWCHAR prev_ch
)
382 * Backspace moves backwards one or two positions.
383 * XXX - Incorrect if several '\b' in a row.
385 return ((utf_mode
&& is_wide_char(prev_ch
)) ? -2 : -1);
387 if (!utf_mode
|| is_ascii_char(ch
)) {
388 if (control_char((char)ch
)) {
390 * Control characters do unpredictable things,
391 * so we don't even try to guess; say it doesn't move.
392 * This can only happen if the -r flag is in effect.
397 if (is_composing_char(ch
) || is_combining_char(prev_ch
, ch
)) {
399 * Composing and combining chars take up no space.
401 * Some terminals, upon failure to compose a
402 * composing character with the character(s) that
403 * precede(s) it will actually take up one column
404 * for the composing character; there isn't much
405 * we could do short of testing the (complex)
406 * composition process ourselves and printing
407 * a binary representation when it fails.
414 * Other characters take one or two columns,
415 * plus the width of any attribute enter/exit sequence.
418 if (is_wide_char(ch
))
420 if (curr
> 0 && !is_at_equiv(attr
[curr
-1], a
))
421 w
+= attr_ewidth(attr
[curr
-1]);
422 if ((apply_at_specials(a
) != AT_NORMAL
) &&
423 (curr
== 0 || !is_at_equiv(attr
[curr
-1], a
)))
429 * Delete to the previous base character in the line buffer.
430 * Return 1 if one is found.
436 char *p
= linebuf
+ curr
;
437 LWCHAR ch
= step_char(&p
, -1, linebuf
+ lmargin
);
440 /* This assumes that there is no '\b' in linebuf. */
441 while (curr
> lmargin
&& column
> lmargin
&&
442 (!(attr
[curr
- 1] & (AT_ANSI
|AT_BINARY
)))) {
444 prev_ch
= step_char(&p
, -1, linebuf
+ lmargin
);
445 width
= pwidth(ch
, attr
[curr
], prev_ch
);
456 * Are we currently within a recognized ANSI escape sequence?
459 in_ansi_esc_seq(void)
464 * Search backwards for either an ESC (which means we ARE in a seq);
465 * or an end char (which means we're NOT in a seq).
467 for (p
= &linebuf
[curr
]; p
> linebuf
; ) {
468 LWCHAR ch
= step_char(&p
, -1, linebuf
);
469 if (IS_CSI_START(ch
))
471 if (!is_ansi_middle(ch
))
478 * Is a character the end of an ANSI escape sequence?
481 is_ansi_end(LWCHAR ch
)
483 if (!is_ascii_char(ch
))
485 return (strchr(end_ansi_chars
, (char)ch
) != NULL
);
492 is_ansi_middle(LWCHAR ch
)
494 if (!is_ascii_char(ch
))
498 return (strchr(mid_ansi_chars
, (char)ch
) != NULL
);
502 * Append a character and attribute to the line buffer.
504 #define STORE_CHAR(ch, a, rep, pos) \
505 if (store_char((ch), (a), (rep), (pos))) \
509 store_char(LWCHAR ch
, char a
, char *rep
, off_t pos
)
516 if (is_hilited(pos
, pos
+1, 0, &matches
)) {
518 * This character should be highlighted.
519 * Override the attribute passed in.
522 if (highest_hilite
!= -1 && pos
> highest_hilite
)
523 highest_hilite
= pos
;
528 if (ctldisp
== OPT_ONPLUS
&& in_ansi_esc_seq()) {
529 if (!is_ansi_end(ch
) && !is_ansi_middle(ch
)) {
530 /* Remove whole unrecognized sequence. */
531 char *p
= &linebuf
[curr
];
534 bch
= step_char(&p
, -1, linebuf
);
535 } while (p
> linebuf
&& !IS_CSI_START(bch
));
539 a
= AT_ANSI
; /* Will force re-AT_'ing around it. */
541 } else if (ctldisp
== OPT_ONPLUS
&& IS_CSI_START(ch
)) {
542 a
= AT_ANSI
; /* Will force re-AT_'ing around it. */
545 char *p
= &linebuf
[curr
];
546 LWCHAR prev_ch
= step_char(&p
, -1, linebuf
);
547 w
= pwidth(ch
, a
, prev_ch
);
550 if (ctldisp
!= OPT_ON
&& column
+ w
+ attr_ewidth(a
) > sc_width
)
552 * Won't fit on screen.
561 replen
= utf_len(rep
[0]);
563 if (curr
+ replen
>= size_linebuf
-6) {
565 * Won't fit in line buffer.
568 if (expand_linebuf())
572 while (replen
-- > 0) {
573 linebuf
[curr
] = *rep
++;
582 * Append a tab to the line buffer.
583 * Store spaces to represent the tab.
585 #define STORE_TAB(a, pos) \
586 if (store_tab((a), (pos))) \
590 store_tab(int attr
, off_t pos
)
592 int to_tab
= column
+ cshift
- lmargin
;
595 if (ntabstops
< 2 || to_tab
>= tabstops
[ntabstops
-1])
596 to_tab
= tabdefault
-
597 ((to_tab
- tabstops
[ntabstops
-1]) % tabdefault
);
599 for (i
= ntabstops
- 2; i
>= 0; i
--)
600 if (to_tab
>= tabstops
[i
])
602 to_tab
= tabstops
[i
+1] - to_tab
;
605 if (column
+ to_tab
- 1 + pwidth(' ', attr
, 0) +
606 attr_ewidth(attr
) > sc_width
)
610 STORE_CHAR(' ', attr
, " ", pos
);
611 } while (--to_tab
> 0);
615 #define STORE_PRCHAR(c, pos) \
616 if (store_prchar((c), (pos))) \
620 store_prchar(char c
, off_t pos
)
625 * Convert to printable representation.
630 * Make sure we can get the entire representation
631 * of the character on this line.
633 if (column
+ (int)strlen(s
) - 1 +
634 pwidth(' ', binattr
, 0) + attr_ewidth(binattr
) > sc_width
)
637 for (; *s
!= 0; s
++) {
638 STORE_CHAR(*s
, AT_BINARY
, NULL
, pos
);
644 flush_mbc_buf(off_t pos
)
648 for (i
= 0; i
< mbc_buf_index
; i
++)
649 if (store_prchar(mbc_buf
[i
], pos
))
650 return (mbc_buf_index
- i
);
656 * Append a character to the line buffer.
657 * Expand tabs into spaces, handle underlining, boldfacing, etc.
658 * Returns 0 if ok, 1 if couldn't fit in buffer.
661 pappend(char c
, off_t pos
)
666 if (do_append(pendc
, NULL
, pendpos
))
668 * Oops. We've probably lost the char which
669 * was in pendc, since caller won't back up.
675 if (c
== '\r' && bs_mode
== BS_SPECIAL
) {
676 if (mbc_buf_len
> 0) /* utf_mode must be on. */ {
677 /* Flush incomplete (truncated) sequence. */
678 r
= flush_mbc_buf(mbc_pos
);
679 mbc_buf_index
= r
+ 1;
682 return (mbc_buf_index
);
686 * Don't put the CR into the buffer until we see
687 * the next char. If the next char is a newline,
696 r
= do_append((LWCHAR
) c
, NULL
, pos
);
698 /* Perform strict validation in all possible cases. */
699 if (mbc_buf_len
== 0) {
703 if (IS_ASCII_OCTET(c
)) {
704 r
= do_append((LWCHAR
) c
, NULL
, pos
);
705 } else if (IS_UTF8_LEAD(c
)) {
706 mbc_buf_len
= utf_len(c
);
710 /* UTF8_INVALID or stray UTF8_TRAIL */
711 r
= flush_mbc_buf(pos
);
713 } else if (IS_UTF8_TRAIL(c
)) {
714 mbc_buf
[mbc_buf_index
++] = c
;
715 if (mbc_buf_index
< mbc_buf_len
)
717 if (is_utf8_well_formed(mbc_buf
))
718 r
= do_append(get_wchar(mbc_buf
), mbc_buf
,
721 /* Complete, but not shortest form, sequence. */
722 mbc_buf_index
= r
= flush_mbc_buf(mbc_pos
);
725 /* Flush incomplete (truncated) sequence. */
726 r
= flush_mbc_buf(mbc_pos
);
727 mbc_buf_index
= r
+ 1;
729 /* Handle new char. */
736 * If we need to shift the line, do it.
737 * But wait until we get to at least the middle of the screen,
738 * so shifting it doesn't affect the chars we're currently
739 * pappending. (Bold & underline can get messed up otherwise.)
741 if (cshift
< hshift
&& column
> sc_width
/ 2) {
742 linebuf
[curr
] = '\0';
743 pshift(hshift
- cshift
);
746 /* How many chars should caller back up? */
747 r
= (!utf_mode
) ? 1 : mbc_buf_index
;
753 do_append(LWCHAR ch
, char *rep
, off_t pos
)
761 if (bs_mode
== BS_CONTROL
)
762 goto do_control_char
;
765 * A better test is needed here so we don't
766 * backspace over part of the printed
767 * representation of a binary character.
769 if (curr
<= lmargin
||
771 (attr
[curr
- 1] & (AT_ANSI
|AT_BINARY
))) {
772 STORE_PRCHAR('\b', pos
);
773 } else if (bs_mode
== BS_NORMAL
) {
774 STORE_CHAR(ch
, AT_NORMAL
, NULL
, pos
);
775 } else if (bs_mode
== BS_SPECIAL
) {
776 overstrike
= backc();
782 if (overstrike
> 0) {
784 * Overstrike the character at the current position
785 * in the line buffer. This will cause either
786 * underline (if a "_" is overstruck),
787 * bold (if an identical character is overstruck),
788 * or just deletion of the character in the buffer.
790 overstrike
= utf_mode
? -1 : 0;
791 /* To be correct, this must be a base character. */
792 prev_ch
= get_wchar(linebuf
+ curr
);
796 * Overstriking a char with itself means make it bold.
797 * But overstriking an underscore with itself is
798 * ambiguous. It could mean make it bold, or
799 * it could mean make it underlined.
800 * Use the previous overstrike to resolve it.
803 if ((a
& (AT_BOLD
|AT_UNDERLINE
)) != AT_NORMAL
)
804 a
|= (AT_BOLD
|AT_UNDERLINE
);
805 else if (curr
> 0 && attr
[curr
- 1] & AT_UNDERLINE
)
807 else if (curr
> 0 && attr
[curr
- 1] & AT_BOLD
)
814 } else if (ch
== '_') {
817 rep
= linebuf
+ curr
;
818 } else if (prev_ch
== '_') {
821 /* Else we replace prev_ch, but we keep its attributes. */
822 } else if (overstrike
< 0) {
823 if (is_composing_char(ch
) ||
824 is_combining_char(get_wchar(linebuf
+ curr
), ch
)) {
825 /* Continuation of the same overstrike. */
827 a
= attr
[curr
- 1] & (AT_UNDERLINE
| AT_BOLD
);
836 * Expand a tab into spaces.
840 goto do_control_char
;
846 } else if ((!utf_mode
|| is_ascii_char(ch
)) && control_char((char)ch
)) {
848 if (ctldisp
== OPT_ON
||
849 (ctldisp
== OPT_ONPLUS
&& IS_CSI_START(ch
))) {
851 * Output as a normal character.
853 STORE_CHAR(ch
, AT_NORMAL
, rep
, pos
);
855 STORE_PRCHAR((char)ch
, pos
);
857 } else if (utf_mode
&& ctldisp
!= OPT_ON
&& is_ubin_char(ch
)) {
862 if (column
+ (int)strlen(s
) - 1 +
863 pwidth(' ', binattr
, 0) + attr_ewidth(binattr
) > sc_width
)
867 STORE_CHAR(*s
, AT_BINARY
, NULL
, pos
);
869 STORE_CHAR(ch
, a
, rep
, pos
);
882 if (mbc_buf_len
> 0) {
883 /* Flush incomplete (truncated) sequence. */
884 r
= flush_mbc_buf(mbc_pos
);
891 * Terminate the line in the line buffer.
894 pdone(int endline
, int forw
)
900 if (pendc
&& (pendc
!= '\r' || !endline
))
902 * If we had a pending character, put it in the buffer.
903 * But discard a pending CR if we are at end of line
904 * (that is, discard the CR in a CR/LF sequence).
906 (void) do_append(pendc
, NULL
, pendpos
);
908 for (i
= curr
- 1; i
>= 0; i
--) {
909 if (attr
[i
] & AT_INDET
) {
910 attr
[i
] &= ~AT_INDET
;
911 if (i
< curr
- 1 && attr
[i
+ 1] & AT_BOLD
)
914 attr
[i
] |= AT_UNDERLINE
;
919 * Make sure we've shifted the line, if we need to.
922 pshift(hshift
- cshift
);
924 if (ctldisp
== OPT_ONPLUS
&& is_ansi_end('m')) {
925 /* Switch to normal attribute at end of line. */
927 for (; *p
!= '\0'; p
++) {
929 attr
[curr
++] = AT_ANSI
;
934 * Add a newline if necessary,
935 * and append a '\0' to the end of the line.
936 * We output a newline if we're not at the right edge of the screen,
937 * or if the terminal doesn't auto wrap,
938 * or if this is really the end of the line AND the terminal ignores
939 * a newline at the right edge.
940 * (In the last case we don't want to output a newline if the terminal
941 * doesn't ignore it since that would produce an extra blank line.
942 * But we do want to output a newline if the terminal ignores it in case
943 * the next line is blank. In that case the single newline output for
944 * that blank line would be ignored!)
946 if (column
< sc_width
|| !auto_wrap
|| (endline
&& ignaw
) ||
948 linebuf
[curr
] = '\n';
949 attr
[curr
] = AT_NORMAL
;
951 } else if (ignaw
&& column
>= sc_width
&& forw
) {
953 * Terminals with "ignaw" don't wrap until they *really* need
954 * to, i.e. when the character *after* the last one to fit on a
955 * line is output. But they are too hard to deal with when they
956 * get in the state where a full screen width of characters
957 * have been output but the cursor is sitting on the right edge
958 * instead of at the start of the next line.
959 * So we nudge them into wrapping by outputting a space
960 * character plus a backspace. But do this only if moving
961 * forward; if we're moving backward and drawing this line at
962 * the top of the screen, the space would overwrite the first
963 * char on the next line. We don't need to do this "nudge"
964 * at the top of the screen anyway.
967 attr
[curr
++] = AT_NORMAL
;
968 linebuf
[curr
] = '\b';
969 attr
[curr
++] = AT_NORMAL
;
971 linebuf
[curr
] = '\0';
972 attr
[curr
] = AT_NORMAL
;
979 set_status_col(char c
)
982 attr
[0] = AT_NORMAL
|AT_HILITE
;
986 * Get a character from the current line.
987 * Return the character as the function return value,
988 * and the character attribute in *ap.
991 gline(int i
, int *ap
)
995 * If there is no current line, we pretend the line is
996 * either "~" or "", depending on the "twiddle" flag.
1005 /* Make sure we're back to AT_NORMAL before the '\n'. */
1007 return (i
? '\0' : '\n');
1011 return (linebuf
[i
] & 0xFF);
1015 * Indicate that there is no current line.
1025 * Analogous to forw_line(), but deals with "raw lines":
1026 * lines which are not split for screen width.
1027 * {{ This is supposed to be more efficient than forw_line(). }}
1030 forw_raw_line(off_t curr_pos
, char **linep
, int *line_lenp
)
1036 if (curr_pos
== -1 || ch_seek(curr_pos
) ||
1037 (c
= ch_forw_get()) == EOI
)
1042 if (c
== '\n' || c
== EOI
|| ABORT_SIGS()) {
1043 new_pos
= ch_tell();
1046 if (n
>= size_linebuf
-1) {
1047 if (expand_linebuf()) {
1049 * Overflowed the input buffer.
1050 * Pretend the line ended here.
1052 new_pos
= ch_tell() - 1;
1056 linebuf
[n
++] = (char)c
;
1062 if (line_lenp
!= NULL
)
1068 * Analogous to back_line(), but deals with "raw lines".
1069 * {{ This is supposed to be more efficient than back_line(). }}
1072 back_raw_line(off_t curr_pos
, char **linep
, int *line_lenp
)
1078 if (curr_pos
== -1 || curr_pos
<= ch_zero() || ch_seek(curr_pos
- 1))
1082 linebuf
[--n
] = '\0';
1085 if (c
== '\n' || ABORT_SIGS()) {
1087 * This is the newline ending the previous line.
1088 * We have hit the beginning of the line.
1090 new_pos
= ch_tell() + 1;
1095 * We have hit the beginning of the file.
1096 * This must be the first line in the file.
1097 * This must, of course, be the beginning of the line.
1099 new_pos
= ch_zero();
1103 int old_size_linebuf
= size_linebuf
;
1104 if (expand_linebuf()) {
1106 * Overflowed the input buffer.
1107 * Pretend the line ended here.
1109 new_pos
= ch_tell() + 1;
1113 * Shift the data to the end of the new linebuf.
1115 n
= size_linebuf
- old_size_linebuf
;
1116 memmove(linebuf
+ n
, linebuf
, old_size_linebuf
);
1121 *linep
= &linebuf
[n
];
1122 if (line_lenp
!= NULL
)
1123 *line_lenp
= size_linebuf
- 1 - n
;