Hi,
I am attaching a patch to refactor the (hopefully the last one) qf_init_ext()
function. This moves the code that parses a line to get the quickfix fields
to a separate function.
I have also added another quickfix test.
- Yegappan
--
--
You received this message from the "vim_dev" maillist.
Do not top-post! Type your reply below the text you are replying to.
For more information, visit http://www.vim.org/maillist.php
---
You received this message because you are subscribed to the Google Groups
"vim_dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to vim_dev+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.
diff --git a/src/quickfix.c b/src/quickfix.c
index 1145896..ec516a1 100644
--- a/src/quickfix.c
+++ b/src/quickfix.c
@@ -411,6 +411,11 @@ parse_efm_option(char_u *efm)
goto parse_efm_end;
/*
+ * Each part of the format string is copied and modified from errorformat
+ * to regex prog. Only a few % characters are allowed.
+ */
+
+/*
* Get some space to modify the format string into.
*/
i = (FMT_PATTERNS * 3) + ((int)STRLEN(efm) << 2);
@@ -474,7 +479,8 @@ enum {
QF_FAIL = 0,
QF_OK = 1,
QF_END_OF_INPUT = 2,
-QF_NOMEM = 3
+QF_NOMEM = 3,
+QF_IGNORE_LINE = 4
};
typedef struct {
@@ -764,6 +770,324 @@ qf_get_nextline(qfstate_T *state)
return QF_OK;
}
+typedef struct {
+char_u *namebuf;
+char_u *errmsg;
+interrmsglen;
+long lnum;
+intcol;
+char_u use_viscol;
+char_u *pattern;
+intenr;
+inttype;
+intvalid;
+} qffields_T;
+
+/* Parse a line and get the quickfix fields */
+static int
+qf_parse_line(
+ qf_info_T *qi,
+ char_u *linebuf,
+ int linelen,
+ efm_T *fmt_first,
+ qffields_T *fields
+ )
+{
+efm_T *fmt_ptr;
+static efm_T *fmt_start = NULL; /* cached across calls */
+char_u *ptr;
+intlen;
+inti;
+intidx = 0;
+char_u *tail = NULL;
+regmatch_T regmatch;
+
+/* Always ignore case when looking for a matching error. */
+regmatch.rm_ic = TRUE;
+
+/* If there was no %> item start at the first pattern */
+if (fmt_start == NULL)
+ fmt_ptr = fmt_first;
+else
+{
+ fmt_ptr = fmt_start;
+ fmt_start = NULL;
+}
+
+/*
+ * Try to match each part of 'errorformat' until we find a complete
+ * match or no match.
+ */
+fields->valid = TRUE;
+restofline:
+for ( ; fmt_ptr != NULL; fmt_ptr = fmt_ptr->next)
+{
+ int r;
+
+ idx = fmt_ptr->prefix;
+ if (qi->qf_multiscan && vim_strchr((char_u *)"OPQ", idx) == NULL)
+ continue;
+ fields->namebuf[0] = NUL;
+ fields->pattern[0] = NUL;
+ if (!qi->qf_multiscan)
+ fields->errmsg[0] = NUL;
+ fields->lnum = 0;
+ fields->col = 0;
+ fields->use_viscol = FALSE;
+ fields->enr = -1;
+ fields->type = 0;
+ tail = NULL;
+
+ regmatch.regprog = fmt_ptr->prog;
+ r = vim_regexec(®match, linebuf, (colnr_T)0);
+ fmt_ptr->prog = regmatch.regprog;
+ if (r)
+ {
+ if ((idx == 'C' || idx == 'Z') && !qi->qf_multiline)
+ continue;
+ if (vim_strchr((char_u *)"EWI", idx) != NULL)
+ fields->type = idx;
+ else
+ fields->type = 0;
+ /*
+* Extract error message data from matched line.
+* We check for an actual submatch, because "\[" and "\]" in
+* the 'errorformat' may cause the wrong submatch to be used.
+*/
+ if ((i = (int)fmt_ptr->addr[0]) > 0)/* %f */
+ {
+ int c;
+
+ if (regmatch.startp[i] == NULL || regmatch.endp[i] == NULL)
+ continue;
+
+ /* Expand ~/file and $HOME/file to full path. */
+ c = *regmatch.endp[i];
+ *regmatch.endp[i] = NUL;
+ expand_env(regmatch.startp[i], fields->namebuf, CMDBUFFSIZE);
+ *regmatch.endp[i] = c;
+
+ if (vim_strchr((char_u *)"OPQ", idx) != NULL
+ && mch_getperm(fields->namebuf) == -1)
+ continue;
+ }
+ if ((i = (int)fmt_ptr->addr[1]) > 0)/* %n */
+ {
+ if (regmatch.startp[i] == NULL)
+ continue;
+ fields->enr = (int)atol((char *)regmatch.startp[i]);
+ }
+ if ((i = (int)fmt_ptr->addr[2]) > 0)/* %l */
+ {
+ if (regmatch.startp[i] == NULL)
+ continue;