Skip to content

Commit

Permalink
text: drop special handling of \r\n line endings
Browse files Browse the repository at this point in the history
  • Loading branch information
martanne committed Apr 9, 2017
1 parent d2004b1 commit 6a6bc5b
Show file tree
Hide file tree
Showing 5 changed files with 36 additions and 109 deletions.
74 changes: 20 additions & 54 deletions text-motions.c
Original file line number Diff line number Diff line change
Expand Up @@ -113,34 +113,14 @@ size_t text_line_find_prev(Text *txt, size_t pos, const char *s) {
}

size_t text_line_prev(Text *txt, size_t pos) {
char c;
Iterator it = text_iterator_get(txt, pos);
if (!text_iterator_char_get(&it, &c))
return pos;
if (c == '\n')
text_iterator_char_prev(&it, &c);
while (text_iterator_byte_get(&it, &c) && c != '\n')
text_iterator_byte_prev(&it, NULL);
if (text_iterator_byte_prev(&it, &c) && c != '\r')
text_iterator_byte_next(&it, &c);
text_iterator_byte_find_prev(&it, '\n');
return it.pos;
}

size_t text_line_begin(Text *txt, size_t pos) {
char c;
Iterator it = text_iterator_get(txt, pos);
if (!text_iterator_char_get(&it, &c))
return pos;
if (c == '\n')
text_iterator_char_prev(&it, &c);
while (text_iterator_byte_get(&it, &c)) {
if (c == '\n') {
it.pos++;
break;
}
text_iterator_byte_prev(&it, NULL);
}
return it.pos;
return text_iterator_byte_find_prev(&it, '\n') ? it.pos+1 : it.pos;
}

size_t text_line_start(Text *txt, size_t pos) {
Expand All @@ -162,27 +142,23 @@ size_t text_line_finish(Text *txt, size_t pos) {
}

size_t text_line_end(Text *txt, size_t pos) {
char c;
Iterator it = text_iterator_get(txt, pos);
if (text_iterator_char_get(&it, &c) && c != '\n')
while (text_iterator_char_next(&it, &c) && c != '\n');
text_iterator_byte_find_next(&it, '\n');
return it.pos;
}

size_t text_line_next(Text *txt, size_t pos) {
char c;
Iterator it = text_iterator_get(txt, pos);
while (text_iterator_byte_get(&it, &c) && c != '\n')
if (text_iterator_byte_find_next(&it, '\n'))
text_iterator_byte_next(&it, NULL);
text_iterator_byte_next(&it, NULL);
return it.pos;
}

size_t text_line_offset(Text *txt, size_t pos, size_t off) {
char c;
size_t bol = text_line_begin(txt, pos);
Iterator it = text_iterator_get(txt, bol);
while (off-- > 0 && text_iterator_char_get(&it, &c) && c != '\n')
while (off-- > 0 && text_iterator_byte_get(&it, &c) && c != '\n')
text_iterator_byte_next(&it, NULL);
return it.pos;
}
Expand All @@ -191,7 +167,7 @@ size_t text_line_char_set(Text *txt, size_t pos, int count) {
char c;
size_t bol = text_line_begin(txt, pos);
Iterator it = text_iterator_get(txt, bol);
if (text_iterator_char_get(&it, &c) && c != '\n')
if (text_iterator_byte_get(&it, &c) && c != '\n')
while (count-- > 0 && text_iterator_char_next(&it, &c) && c != '\n');
return it.pos;
}
Expand All @@ -201,7 +177,7 @@ int text_line_char_get(Text *txt, size_t pos) {
int count = 0;
size_t bol = text_line_begin(txt, pos);
Iterator it = text_iterator_get(txt, bol);
if (text_iterator_char_get(&it, &c) && c != '\n') {
if (text_iterator_byte_get(&it, &c) && c != '\n') {
while (it.pos < pos && c != '\n' && text_iterator_char_next(&it, &c))
count++;
}
Expand All @@ -217,7 +193,7 @@ int text_line_width_get(Text *txt, size_t pos) {
while (it.pos < pos) {
char buf[MB_CUR_MAX];
size_t len = text_bytes_get(txt, it.pos, sizeof buf, buf);
if (len == 0 || buf[0] == '\r' || buf[0] == '\n')
if (len == 0 || buf[0] == '\n')
break;
wchar_t wc;
size_t wclen = mbrtowc(&wc, buf, len, &ps);
Expand Down Expand Up @@ -254,7 +230,7 @@ size_t text_line_width_set(Text *txt, size_t pos, int width) {
for (;;) {
char buf[MB_CUR_MAX];
size_t len = text_bytes_get(txt, it.pos, sizeof buf, buf);
if (len == 0 || buf[0] == '\r' || buf[0] == '\n')
if (len == 0 || buf[0] == '\n')
break;
wchar_t wc;
size_t wclen = mbrtowc(&wc, buf, len, &ps);
Expand Down Expand Up @@ -285,7 +261,7 @@ size_t text_line_width_set(Text *txt, size_t pos, int width) {
size_t text_line_char_next(Text *txt, size_t pos) {
char c;
Iterator it = text_iterator_get(txt, pos);
if (!text_iterator_char_get(&it, &c) || c == '\n')
if (!text_iterator_byte_get(&it, &c) || c == '\n')
return pos;
text_iterator_char_next(&it, NULL);
return it.pos;
Expand Down Expand Up @@ -425,7 +401,7 @@ size_t text_word_start_prev(Text *txt, size_t pos) {

size_t text_sentence_next(Text *txt, size_t pos) {
char c, prev = 'X';
Iterator it = text_iterator_get(txt, pos), rev = text_iterator_get(txt, pos);
Iterator it = text_iterator_get(txt, pos), rev = it;

if (!text_iterator_byte_get(&it, &c))
return pos;
Expand Down Expand Up @@ -469,7 +445,7 @@ size_t text_paragraph_next(Text *txt, size_t pos) {
char c;
Iterator it = text_iterator_get(txt, pos);

while (text_iterator_char_get(&it, &c) && c == '\n')
while (text_iterator_byte_get(&it, &c) && c == '\n')
text_iterator_char_next(&it, NULL);
return text_line_empty_next(txt, it.pos);
}
Expand All @@ -479,37 +455,27 @@ size_t text_paragraph_prev(Text *txt, size_t pos) {
Iterator it = text_iterator_get(txt, pos);

/* c == \0 catches starting the search at EOF */
while (text_iterator_char_get(&it, &c) && (c == '\n' || c == '\0'))
text_iterator_char_prev(&it, NULL);
while (text_iterator_byte_get(&it, &c) && (c == '\n' || c == '\0'))
text_iterator_byte_prev(&it, NULL);
return text_line_empty_prev(txt, it.pos);
}

size_t text_line_empty_next(Text *txt, size_t pos) {
char c;
Iterator it = text_iterator_get(txt, pos);
while (text_iterator_byte_get(&it, &c)) {
if (c == '\n' && text_iterator_byte_next(&it, &c)) {
size_t match = it.pos;
if (c == '\r')
text_iterator_byte_next(&it, &c);
if (c == '\n')
return match;
}
text_iterator_byte_next(&it, NULL);
while (text_iterator_byte_find_next(&it, '\n')) {
if (text_iterator_byte_next(&it, &c) && c == '\n')
return it.pos;
}
return it.pos;
}

size_t text_line_empty_prev(Text *txt, size_t pos) {
char c;
Iterator it = text_iterator_get(txt, pos);
while (text_iterator_byte_prev(&it, &c)) {
if (c == '\n' && text_iterator_byte_prev(&it, &c)) {
if (c == '\r')
text_iterator_byte_prev(&it, &c);
if (c == '\n')
return it.pos + 1;
}
while (text_iterator_byte_find_prev(&it, '\n')) {
if (text_iterator_byte_prev(&it, &c) && c == '\n')
return it.pos + 1;
}
return it.pos;
}
Expand Down
10 changes: 5 additions & 5 deletions text-motions.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,11 +28,11 @@ size_t text_find_prev(Text*, size_t pos, const char *s);
size_t text_line_find_next(Text*, size_t pos, const char *s);
size_t text_line_find_prev(Text*, size_t pos, const char *s);

/* begin finish end next
* v v v v
* [\r]\n I am a line! [\r]\n
* ^ ^
* prev start
/* begin finish next
* v v v
* \n I am a line! \n
* ^ ^ ^
* prev start end
*/
size_t text_line_prev(Text*, size_t pos);
size_t text_line_begin(Text*, size_t pos);
Expand Down
10 changes: 5 additions & 5 deletions text-objects.c
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,8 @@ Filerange text_object_entire_inner(Text *txt, size_t pos) {
char c;
Filerange r = text_object_entire(txt, pos);
Iterator it = text_iterator_get(txt, r.start);
if (text_iterator_char_get(&it, &c) && c == '\n')
while (text_iterator_char_next(&it, &c) && c == '\n');
if (text_iterator_byte_get(&it, &c) && c == '\n')
while (text_iterator_byte_next(&it, &c) && c == '\n');
r.start = it.pos;
it = text_iterator_get(txt, r.end);
while (text_iterator_char_prev(&it, &c) && c == '\n');
Expand Down Expand Up @@ -282,7 +282,7 @@ Filerange text_object_indentation(Text *txt, size_t pos) {
size_t start = bol;
size_t end = text_line_next(txt, bol);
size_t line_indent = sol - bol;
bool line_empty = text_char_get(txt, bol, &c) && c == '\n';
bool line_empty = text_byte_get(txt, bol, &c) && c == '\n';

char *buf = text_bytes_alloc0(txt, bol, line_indent);
char *tmp = malloc(line_indent);
Expand All @@ -298,7 +298,7 @@ Filerange text_object_indentation(Text *txt, size_t pos) {
size_t indent = sol - bol;
if (indent < line_indent)
break;
bool empty = text_char_get(txt, bol, &c) && c == '\n';
bool empty = text_byte_get(txt, bol, &c) && c == '\n';
if (line_empty && !empty)
break;
if (line_indent == 0 && empty)
Expand All @@ -315,7 +315,7 @@ Filerange text_object_indentation(Text *txt, size_t pos) {
size_t indent = sol - bol;
if (indent < line_indent)
break;
bool empty = text_char_get(txt, bol, &c) && c == '\n';
bool empty = text_byte_get(txt, bol, &c) && c == '\n';
if (line_empty && !empty)
break;
if (line_indent == 0 && empty)
Expand Down
45 changes: 6 additions & 39 deletions text.c
Original file line number Diff line number Diff line change
Expand Up @@ -1380,17 +1380,6 @@ bool text_iterator_byte_get(Iterator *it, char *b) {
return false;
}

bool text_iterator_char_get(Iterator *it, char *c) {
bool ret = text_iterator_byte_get(it, c);
if (ret && *c == '\r') {
char d;
if (text_iterator_byte_next(it, &d) && d == '\n')
*c = '\n';
return text_iterator_byte_prev(it, NULL);
}
return ret;
}

bool text_iterator_next(Iterator *it) {
size_t rem = it->end - it->text;
return text_iterator_init(it, it->pos+rem, it->piece ? it->piece->next : NULL, 0);
Expand Down Expand Up @@ -1506,15 +1495,9 @@ bool text_iterator_codepoint_prev(Iterator *it, char *c) {
return false;
}

bool text_iterator_char_next(Iterator *it, char *ret) {
char c;
if (!ret)
ret = &c;
bool cr = text_iterator_byte_get(it, &c) && c == '\r';
if (!text_iterator_codepoint_next(it, ret))
bool text_iterator_char_next(Iterator *it, char *c) {
if (!text_iterator_codepoint_next(it, c))
return false;
if (cr && *ret == '\n')
return text_iterator_byte_next(it, ret) && text_iterator_char_get(it, ret);
mbstate_t ps = { 0 };
for (;;) {
char buf[MB_CUR_MAX];
Expand All @@ -1527,31 +1510,20 @@ bool text_iterator_char_next(Iterator *it, char *ret) {
return false;
} else if (wclen == 0) {
return true;
} else if (wc == L'\r') {
return text_iterator_char_get(it, ret);
} else {
int width = wcwidth(wc);
if (width != 0)
return true;
if (!text_iterator_codepoint_next(it, ret))
if (!text_iterator_codepoint_next(it, c))
return false;
}
}
return true;
}

bool text_iterator_char_prev(Iterator *it, char *ret) {
char c;
if (!ret)
ret = &c;
if (!text_iterator_codepoint_prev(it, ret))
bool text_iterator_char_prev(Iterator *it, char *c) {
if (!text_iterator_codepoint_prev(it, c))
return false;
if (*ret == '\n') {
if (!text_iterator_byte_prev(it, &c) || c != '\r')
text_iterator_byte_next(it, NULL);
return true;
}

for (;;) {
char buf[MB_CUR_MAX];
size_t len = text_bytes_get(it->piece->text, it->pos, sizeof buf, buf);
Expand All @@ -1568,7 +1540,7 @@ bool text_iterator_char_prev(Iterator *it, char *ret) {
int width = wcwidth(wc);
if (width != 0)
return true;
if (!text_iterator_codepoint_prev(it, ret))
if (!text_iterator_codepoint_prev(it, c))
return false;
}
}
Expand All @@ -1579,11 +1551,6 @@ bool text_byte_get(Text *txt, size_t pos, char *buf) {
return text_bytes_get(txt, pos, 1, buf);
}

bool text_char_get(Text *txt, size_t pos, char *buf) {
Iterator it = text_iterator_get(txt, pos);
return text_iterator_char_get(&it, buf);
}

size_t text_bytes_get(Text *txt, size_t pos, size_t len, char *buf) {
if (!buf)
return 0;
Expand Down
6 changes: 0 additions & 6 deletions text.h
Original file line number Diff line number Diff line change
Expand Up @@ -70,9 +70,6 @@ size_t text_lineno_by_pos(Text*, size_t pos);
/* set `buf' to the byte found at `pos' and return true, if `pos' is invalid
* false is returned and `buf' is left unmodified */
bool text_byte_get(Text*, size_t pos, char *buf);
/* same as byte get, but if a sequence of '\r\n' is read at `pos',
* `buf` is set to \n instead of \r. */
bool text_char_get(Text*, size_t pos, char *buf);
/* store at most `len' bytes starting from `pos' into `buf', the return value
* indicates how many bytes were copied into `buf'. WARNING buf will not be
* NUL terminated. */
Expand All @@ -89,9 +86,6 @@ bool text_iterator_prev(Iterator*);
/* get byte at current iterator position, if this is at EOF a NUL
* byte (which is not actually part of the file) is read. */
bool text_iterator_byte_get(Iterator*, char *b);
/* same as byte get, but if a sequence of '\r\n' is read at the
* iterator position, *c is set to \n instead of \r. */
bool text_iterator_char_get(Iterator*, char *c);
/* advance iterator by one byte and get byte at new position. */
bool text_iterator_byte_prev(Iterator*, char *b);
/* if the new position is at EOF a NUL byte (which is not actually
Expand Down

0 comments on commit 6a6bc5b

Please sign in to comment.