comparison src/search.c @ 6971:e859731ea1cd v7.4.803

patch 7.4.803 Problem: C indent does not support C11 raw strings. (Mark Lodato) Solution: Do not change indent inside the raw string.
author Bram Moolenaar <bram@vim.org>
date Tue, 28 Jul 2015 21:17:36 +0200
parents 1e621b31948b
children 814f1f569e4a
comparison
equal deleted inserted replaced
6970:589a962ecc16 6971:e859731ea1cd
1723 if (prevcol) 1723 if (prevcol)
1724 *prevcol = col; 1724 *prevcol = col;
1725 return (col >= 0 && linep[col] == ch) ? TRUE : FALSE; 1725 return (col >= 0 && linep[col] == ch) ? TRUE : FALSE;
1726 } 1726 }
1727 1727
1728 static int find_rawstring_end __ARGS((char_u *linep, pos_T *startpos, pos_T *endpos));
1729
1730 /*
1731 * Raw string start is found at linep[startpos.col - 1].
1732 * Return TRUE if the matching end can be found between startpos and endpos.
1733 */
1734 static int
1735 find_rawstring_end(linep, startpos, endpos)
1736 char_u *linep;
1737 pos_T *startpos;
1738 pos_T *endpos;
1739 {
1740 char_u *p;
1741 char_u *delim_copy;
1742 size_t delim_len;
1743 linenr_T lnum;
1744 int found = FALSE;
1745
1746 for (p = linep + startpos->col + 1; *p && *p != '('; ++p)
1747 ;
1748 delim_len = (p - linep) - startpos->col - 1;
1749 delim_copy = vim_strnsave(linep + startpos->col + 1, delim_len);
1750 if (delim_copy == NULL)
1751 return FALSE;
1752 for (lnum = startpos->lnum; lnum <= endpos->lnum; ++lnum)
1753 {
1754 char_u *line = ml_get(lnum);
1755
1756 for (p = line + (lnum == startpos->lnum
1757 ? startpos->col + 1 : 0); *p; ++p)
1758 {
1759 if (lnum == endpos->lnum && (colnr_T)(p - line) >= endpos->col)
1760 break;
1761 if (*p == ')' && p[delim_len + 1] == '"'
1762 && STRNCMP(delim_copy, p + 1, delim_len) == 0)
1763 {
1764 found = TRUE;
1765 break;
1766 }
1767 }
1768 if (found)
1769 break;
1770 }
1771 vim_free(delim_copy);
1772 return found;
1773 }
1774
1728 /* 1775 /*
1729 * findmatchlimit -- find the matching paren or brace, if it exists within 1776 * findmatchlimit -- find the matching paren or brace, if it exists within
1730 * maxtravel lines of here. A maxtravel of 0 means search until falling off 1777 * maxtravel lines of the cursor. A maxtravel of 0 means search until falling
1731 * the edge of the file. 1778 * off the edge of the file.
1732 * 1779 *
1733 * "initc" is the character to find a match for. NUL means to find the 1780 * "initc" is the character to find a match for. NUL means to find the
1734 * character at or after the cursor. 1781 * character at or after the cursor. Special values:
1782 * '*' look for C-style comment / *
1783 * '/' look for C-style comment / *, ignoring comment-end
1784 * '#' look for preprocessor directives
1785 * 'R' look for raw string start: R"delim(text)delim" (only backwards)
1735 * 1786 *
1736 * flags: FM_BACKWARD search backwards (when initc is '/', '*' or '#') 1787 * flags: FM_BACKWARD search backwards (when initc is '/', '*' or '#')
1737 * FM_FORWARD search forwards (when initc is '/', '*' or '#') 1788 * FM_FORWARD search forwards (when initc is '/', '*' or '#')
1738 * FM_BLOCKSTOP stop at start/end of block ({ or } in column 0) 1789 * FM_BLOCKSTOP stop at start/end of block ({ or } in column 0)
1739 * FM_SKIPCOMM skip comments (not implemented yet!) 1790 * FM_SKIPCOMM skip comments (not implemented yet!)
1740 * 1791 *
1741 * "oap" is only used to set oap->motion_type for a linewise motion, it be 1792 * "oap" is only used to set oap->motion_type for a linewise motion, it can be
1742 * NULL 1793 * NULL
1743 */ 1794 */
1744 1795
1745 pos_T * 1796 pos_T *
1746 findmatchlimit(oap, initc, flags, maxtravel) 1797 findmatchlimit(oap, initc, flags, maxtravel)
1752 static pos_T pos; /* current search position */ 1803 static pos_T pos; /* current search position */
1753 int findc = 0; /* matching brace */ 1804 int findc = 0; /* matching brace */
1754 int c; 1805 int c;
1755 int count = 0; /* cumulative number of braces */ 1806 int count = 0; /* cumulative number of braces */
1756 int backwards = FALSE; /* init for gcc */ 1807 int backwards = FALSE; /* init for gcc */
1808 int raw_string = FALSE; /* search for raw string */
1757 int inquote = FALSE; /* TRUE when inside quotes */ 1809 int inquote = FALSE; /* TRUE when inside quotes */
1758 char_u *linep; /* pointer to current line */ 1810 char_u *linep; /* pointer to current line */
1759 char_u *ptr; 1811 char_u *ptr;
1760 int do_quotes; /* check for quotes in current line */ 1812 int do_quotes; /* check for quotes in current line */
1761 int at_start; /* do_quotes value at start position */ 1813 int at_start; /* do_quotes value at start position */
1796 * if initc given, look in the table for the matching character 1848 * if initc given, look in the table for the matching character
1797 * '/' and '*' are special cases: look for start or end of comment. 1849 * '/' and '*' are special cases: look for start or end of comment.
1798 * When '/' is used, we ignore running backwards into an star-slash, for 1850 * When '/' is used, we ignore running backwards into an star-slash, for
1799 * "[*" command, we just want to find any comment. 1851 * "[*" command, we just want to find any comment.
1800 */ 1852 */
1801 if (initc == '/' || initc == '*') 1853 if (initc == '/' || initc == '*' || initc == 'R')
1802 { 1854 {
1803 comment_dir = dir; 1855 comment_dir = dir;
1804 if (initc == '/') 1856 if (initc == '/')
1805 ignore_cend = TRUE; 1857 ignore_cend = TRUE;
1806 backwards = (dir == FORWARD) ? FALSE : TRUE; 1858 backwards = (dir == FORWARD) ? FALSE : TRUE;
1859 raw_string = (initc == 'R');
1807 initc = NUL; 1860 initc = NUL;
1808 } 1861 }
1809 else if (initc != '#' && initc != NUL) 1862 else if (initc != '#' && initc != NUL)
1810 { 1863 {
1811 find_mps_values(&initc, &findc, &backwards, TRUE); 1864 find_mps_values(&initc, &findc, &backwards, TRUE);
1812 if (findc == NUL) 1865 if (findc == NUL)
1813 return NULL; 1866 return NULL;
1814 } 1867 }
1815 /*
1816 * Either initc is '#', or no initc was given and we need to look under the
1817 * cursor.
1818 */
1819 else 1868 else
1820 { 1869 {
1870 /*
1871 * Either initc is '#', or no initc was given and we need to look
1872 * under the cursor.
1873 */
1821 if (initc == '#') 1874 if (initc == '#')
1822 { 1875 {
1823 hash_dir = dir; 1876 hash_dir = dir;
1824 } 1877 }
1825 else 1878 else
2133 * A comment may contain / * or / /, it may also start or end 2186 * A comment may contain / * or / /, it may also start or end
2134 * with / * /. Ignore a / * after / /. 2187 * with / * /. Ignore a / * after / /.
2135 */ 2188 */
2136 if (pos.col == 0) 2189 if (pos.col == 0)
2137 continue; 2190 continue;
2191 else if (raw_string)
2192 {
2193 if (linep[pos.col - 1] == 'R'
2194 && linep[pos.col] == '"'
2195 && vim_strchr(linep + pos.col + 1, '(') != NULL)
2196 {
2197 /* Possible start of raw string. Now that we have the
2198 * delimiter we can check if it ends before where we
2199 * started searching, or before the previously found
2200 * raw string start. */
2201 if (!find_rawstring_end(linep, &pos,
2202 count > 0 ? &match_pos : &curwin->w_cursor))
2203 {
2204 count++;
2205 match_pos = pos;
2206 match_pos.col--;
2207 }
2208 linep = ml_get(pos.lnum); /* may have been released */
2209 }
2210 }
2138 else if ( linep[pos.col - 1] == '/' 2211 else if ( linep[pos.col - 1] == '/'
2139 && linep[pos.col] == '*' 2212 && linep[pos.col] == '*'
2140 && (int)pos.col < comment_col) 2213 && (int)pos.col < comment_col)
2141 { 2214 {
2142 count++; 2215 count++;