LUALIB_API int luaL_loadfilex (lua_State *L, const char *filename, const char *mode) { LoadF lf; int status, readstatus; int c; int fnameindex = lua_gettop(L) + 1; /* index of filename on the stack */ if (filename == NULL) { lua_pushliteral(L, "=stdin"); lf.f = stdin; } else { lua_pushfstring(L, "@%s", filename); lf.f = fopen(filename, "r"); if (lf.f == NULL) return errfile(L, "open", fnameindex); } if (skipcomment(&lf, &c)) /* read initial portion */ lf.buff[lf.n++] = '\n'; /* add line to correct line numbers */ if (c == LUA_SIGNATURE[0] && filename) { /* binary file? */ lf.f = freopen(filename, "rb", lf.f); /* reopen in binary mode */ if (lf.f == NULL) return errfile(L, "reopen", fnameindex); skipcomment(&lf, &c); /* re-read initial portion */ } if (c != EOF) lf.buff[lf.n++] = c; /* 'c' is the first character of the stream */ status = lua_load(L, getF, &lf, lua_tostring(L, -1), mode); readstatus = ferror(lf.f); if (filename) fclose(lf.f); /* close file (even in case of errors) */ if (readstatus) { lua_settop(L, fnameindex); /* ignore results from `lua_load' */ return errfile(L, "read", fnameindex); } lua_remove(L, fnameindex); return status; }
/* * Function for evaluating the innermost parts of expressions, * viz. !expr (expr) number defined(symbol) symbol * We reset the constexpr flag in the last two cases. */ static Linetype eval_unary(const struct ops *ops, int *valp, const char **cpp) { const char *cp; char *ep; int sym; bool defparen; Linetype lt; cp = skipcomment(*cpp); if (*cp == '!') { debug("eval%d !", prec(ops)); cp++; lt = eval_unary(ops, valp, &cp); if (lt == LT_ERROR) return (LT_ERROR); if (lt != LT_IF) { *valp = !*valp; lt = *valp ? LT_TRUE : LT_FALSE; } } else if (*cp == '(') { cp++; debug("eval%d (", prec(ops)); lt = eval_table(eval_ops, valp, &cp); if (lt == LT_ERROR) return (LT_ERROR); cp = skipcomment(cp); if (*cp++ != ')') return (LT_ERROR); } else if (isdigit((unsigned char)*cp)) { debug("eval%d number", prec(ops)); *valp = strtol(cp, &ep, 0); if (ep == cp) return (LT_ERROR); lt = *valp ? LT_TRUE : LT_FALSE; cp = skipsym(cp); } else if (strncmp(cp, "defined", 7) == 0 && endsym(cp[7])) { cp = skipcomment(cp+7); debug("eval%d defined", prec(ops)); if (*cp == '(') { cp = skipcomment(cp+1); defparen = true; } else { defparen = false; } sym = findsym(cp); if (sym < 0) { lt = LT_IF; } else { *valp = (value[sym] != NULL); lt = *valp ? LT_TRUE : LT_FALSE; } cp = skipsym(cp); cp = skipcomment(cp); if (defparen && *cp++ != ')') return (LT_ERROR); constexpr = false; } else if (!endsym(*cp)) {
/* * Table-driven evaluation of binary operators. */ static Linetype eval_table(const struct ops *ops, int *valp, const char **cpp) { const struct op *op; const char *cp; int val; debug("eval%d", ops - eval_ops); cp = *cpp; if (ops->inner(ops+1, valp, &cp) == LT_IF) return (LT_IF); for (;;) { cp = skipcomment(cp); for (op = ops->op; op->str != NULL; op++) if (strncmp(cp, op->str, strlen(op->str)) == 0) break; if (op->str == NULL) break; cp += strlen(op->str); debug("eval%d %s", ops - eval_ops, op->str); if (ops->inner(ops+1, &val, &cp) == LT_IF) return (LT_IF); *valp = op->fn(*valp, val); } *cpp = cp; debug("eval%d = %d", ops - eval_ops, *valp); return (*valp ? LT_TRUE : LT_FALSE); }
int read_pgm_hdr(FILE *fp, int *w, int *h) { char filetype[4]; int maxval; if(skipcomment(fp) == EOF || fscanf(fp, "%2s\n", filetype) != 1 || strcmp(filetype, "P5") || skipcomment(fp) == EOF || fscanf(fp, "%d", w) != 1 || skipcomment(fp) == EOF || fscanf(fp, "%d", h) != 1 || skipcomment(fp) == EOF || fscanf(fp, "%d%*c", &maxval) != 1 || maxval > 255) { return(-1); } else { return(0); } }
/* * Table-driven evaluation of binary operators. */ static Linetype eval_table(const struct ops *ops, int *valp, const char **cpp) { const struct op *op; const char *cp; int val; Linetype lhs, rhs; debug("eval%d", ops - eval_ops); cp = *cpp; lhs = ops->inner(ops+1, valp, &cp); for (;;) { cp = skipcomment(cp); for (op = ops->op; op->str != NULL; op++) if (strncmp(cp, op->str, strlen(op->str)) == 0) break; if (op->str == NULL) break; cp += strlen(op->str); debug("eval%d %s", ops - eval_ops, op->str); rhs = ops->inner(ops+1, &val, &cp); if (op->fn == op_and && (lhs == LT_FALSE || rhs == LT_FALSE)) { debug("eval%d: and always false", ops - eval_ops); if (lhs == LT_IF) *valp = val; lhs = LT_FALSE; continue; } if (op->fn == op_or && (lhs == LT_TRUE || rhs == LT_TRUE)) { debug("eval%d: or always true", ops - eval_ops); if (lhs == LT_IF) *valp = val; lhs = LT_TRUE; continue; } if (rhs == LT_IF) lhs = LT_IF; if (lhs != LT_IF) *valp = op->fn(*valp, val); } *cpp = cp; debug("eval%d = %d", ops - eval_ops, *valp); if (lhs != LT_IF) lhs = (*valp ? LT_TRUE : LT_FALSE); return lhs; }
void fill_config(void) { FILE *prconf; char buf[MAX_LINE_SIZE]; char *delim; char hombconf[BUFSIZE], *home; struct stat bufstat; char line[MAX_LINE_SIZE]; int linenum = 0; home = getenv("HOME"); sprintf(hombconf, "%s%s", home, FICHIERCONFHOME); if (NULL == (configHash = g_hash_table_new(g_str_hash, g_str_equal))) { perror("g_hash_table_new"); exit(1); } if (-1 == stat(hombconf, &bufstat)) { perror("stat"); exit(1); } if ((prconf = fopen(hombconf, "r")) == NULL) { perror("open"); exit(1); } linenum = 1; while (fgets(buf, MAX_LINE_SIZE, prconf)) { skipcomment(buf); skipspace(buf); if (strlen(buf) >= 1) { delim = strchr(buf, '='); if (!delim) { printf("Error, malformed line[%d]: %s\n", linenum, line); exit(1); } *delim = '\0'; /*line a une forme maintenant clée\0valeur, strdup(line) nous donne la première partie */ g_hash_table_insert(configHash, strdup(buf), strdup(delim + 1)); linenum++; } } }
// Parse a one- or two-char operator like >, >=, >>, ... void parseop(void) { sym = inchar; // think horse not zebra fetchc(); // inchar has second char of token or ?? const prog_char *tk = twochartokens; byte index = 0; for (;;) { byte c1 = pgm_read_byte(tk++); if (!c1) return; byte c2 = pgm_read_byte(tk++); if ((sym == c1) && (inchar == c2)) { sym = (byte) pgm_read_byte(twocharsyms + index); fetchc(); if (sym == s_comment) skipcomment(); return; } index++; } }
// extracts a text block contained within a pair of braces // (may contain nested braces) WCHAR *CTeXFilter::ExtractBracedBlock() { m_iDepth++; WCHAR *result = m_pBuffer + (m_pPtr - m_pData); WCHAR *rptr = result; int currDepth = m_iDepth; while (*m_pPtr && m_iDepth >= currDepth) { switch (*m_pPtr++) { case '\\': // skip all LaTeX/TeX commands if (iscmdchar(*m_pPtr)) { // ignore the content of \begin{...} and \end{...} if (str::StartsWith(m_pPtr, L"begin{") || str::StartsWith(m_pPtr, L"end{")) { m_pPtr = wcschr(m_pPtr, '{') + 1; ExtractBracedBlock(); addsingleNL(result, &rptr); break; } // convert \item to a single dash if (str::StartsWith(m_pPtr, L"item") && !iscmdchar(*(m_pPtr + 4))) { m_pPtr += 4; addsingleNL(result, &rptr); *rptr++ = '-'; addsinglespace(result, &rptr); } for (; iscmdchar(*m_pPtr); m_pPtr++); skipspace(m_pPtr); // ignore command parameters in brackets if (*m_pPtr == '[' && wcschr(m_pPtr, ']')) { m_pPtr = wcschr(m_pPtr, ']') + 1; } break; } // handle newlines newlines, spaces, etc. if (*m_pPtr == '\\') { addsingleNL(result, &rptr); m_pPtr++; break; } if (*m_pPtr == ',') { addsinglespace(result, &rptr); m_pPtr++; break; } if (*m_pPtr == '>') { *rptr++ = '\t'; m_pPtr++; break; } if (*m_pPtr == '%') { *rptr++ = '%'; m_pPtr++; break; } // TODO: handle more international characters if (str::StartsWith(m_pPtr, L"'e")) { *rptr++ = L'é'; m_pPtr += 2; break; } if (str::StartsWith(m_pPtr, L"`e")) { *rptr++ = L'è'; m_pPtr += 2; break; } if (str::StartsWith(m_pPtr, L"`a")) { *rptr++ = L'à'; m_pPtr += 2; break; } if (*m_pPtr != '"') break; m_pPtr++; /* fall through */ case '"': // TODO: handle more international characters switch (*m_pPtr++) { case 'a': *rptr++ = L'ä'; break; case 'A': *rptr++ = L'Ä'; break; case 'o': *rptr++ = L'ö'; break; case 'O': *rptr++ = L'Ö'; break; case 'u': *rptr++ = L'ü'; break; case 'U': *rptr++ = L'Ü'; break; case '`': case '\'': *rptr++ = '"'; break; default: *rptr++ = *(m_pPtr - 1); break; } break; case '{': m_iDepth++; break; case '}': m_iDepth--; if (*m_pPtr == '{') addsinglespace(result, &rptr); break; case '[': // ignore command parameters in brackets if (wcschr(m_pPtr, ']') && wcschr(m_pPtr, ']') < wcschr(m_pPtr, '\n')) m_pPtr = wcschr(m_pPtr, ']') + 1; break; case '%': skipcomment(m_pPtr); break; case '&': *rptr++ = '\t'; break; case '~': addsinglespace(result, &rptr); break; case '\n': // treat single newlines as spaces if (*m_pPtr == '\n' || *m_pPtr == '\r') { addsingleNL(result, &rptr); m_pPtr++; break; } default: m_pPtr--; if (str::IsWs(*m_pPtr)) { addsinglespace(result, &rptr); m_pPtr++; break; } *rptr++ = *m_pPtr++; break; } } if (*m_pPtr == '}') m_pPtr++; *rptr = '\0'; return result; }
HRESULT CTeXFilter::GetNextChunkValue(CChunkValue &chunkValue) { WCHAR *start, *end; ContinueParsing: if (!*m_pPtr && m_state == STATE_TEX_PREAMBLE) { // if there was no preamble, treat the whole document as content m_pPtr = m_pData; m_iDepth = 0; m_state = STATE_TEX_CONTENT; } else if (!*m_pPtr) { m_state = STATE_TEX_END; } switch (m_state) { case STATE_TEX_START: m_state = STATE_TEX_PREAMBLE; chunkValue.SetTextValue(PKEY_PerceivedType, L"document"); return S_OK; case STATE_TEX_PREAMBLE: // the preamble (i.e. everything before \begin{document}) may contain // \author{...} and \title{...} commands start = end = NULL; while (*m_pPtr && !start) { switch (*m_pPtr++){ case '\\': if (iscmdchar(*m_pPtr)) { start = m_pPtr; for (end = start; iscmdchar(*m_pPtr); m_pPtr++, end++); break; } if (*m_pPtr) m_pPtr++; break; case '{': ExtractBracedBlock(); break; case '%': skipcomment(m_pPtr); break; } } if (!start) goto ContinueParsing; skipspace(m_pPtr); if (*m_pPtr != '{') goto ContinueParsing; m_pPtr++; if (!wcsncmp(start, L"author", end - start) || !wcsncmp(start, L"title", end - start)) { chunkValue.SetTextValue(*start == 'a' ? PKEY_Author : PKEY_Title, ExtractBracedBlock()); return S_OK; } if (!wcsncmp(start, L"begin", end - start) && str::Eq(ExtractBracedBlock(), L"document")) m_state = STATE_TEX_CONTENT; goto ContinueParsing; case STATE_TEX_CONTENT: chunkValue.SetTextValue(PKEY_Search_Contents, ExtractBracedBlock(), CHUNK_TEXT); return S_OK; default: return FILTER_E_END_OF_CHUNKS; } }
void create_config (void ) { FILE *pconf, *prconf; char *home; char buf[BUFSIZE]; int linenum; char homeconf[BUFSIZE]; char bufconf[BUFSIZE]; char line[BUFSIZE]; struct stat bufstat; char *delim; home = getenv ("HOME"); snprintf (homeconf,BUFSIZE, "%s%s", home, FICHIERCONFHOME); if (NULL == (configHash = g_hash_table_new (g_str_hash, g_str_equal))) { perror ("g_hash_table_new"); exit (1); } if (-1 == stat (homeconf, &bufstat)) { printf ("%s n'existe pas on va le créer!\n", homeconf); snprintf(bufconf,BUFSIZE,"%s/config/%s",DATADIR,FICHIERCONF); if (-1 == stat (bufconf, &bufstat)) { perror ("stat"); exit (1); } if ((pconf = fopen (homeconf, "w")) == NULL) { perror ("fopen"); exit (1); } if ((prconf = fopen (bufconf, "r")) == NULL) { perror ("open"); exit (1); } while (fgets (line, BUFSIZE, prconf)) { if (fputs (line, pconf) == -1) { perror ("fputs"); exit (1); } } fclose (prconf); fclose (pconf); printf ("Validate the values n %s et restart", homeconf); exit (0); } else { if ((pconf = fopen (homeconf, "r")) == NULL) { perror ("open"); exit (1); } linenum = 1; while (fgets (buf, MAX_LINE_SIZE, pconf)) { skipcomment (buf); skipspace (buf); if (strlen (buf) >= 1) { delim = strchr (buf, '='); if (!delim) { printf ("Error, malformed line[%d]: %s\n", linenum, line); exit (1); } *delim = '\0'; /*line a une forme maintenant clée\0valeur, strdup(line) nous donne la première partie */ g_hash_table_insert (configHash, strdup(buf), strdup(delim + 1)); linenum++; } } fclose(pconf); } }
void untex(FILE *inf) { int c, c1; while ( (c=getc(inf)) != EOF ) { switch (c) { case '\\': GET(c); switch (c) { /*****************************************/ /* following code treats chars preceeded by a backslash */ case '|': /* print escaped special chars */ case '$': case '&': case '%': case '#': case '_': case '{': case '}': putchar(c); break; case ' ': /* print space instead of these */ case '`': case '\'': case '+': case '/': case ':': case ';': case ',': case '<': case '>': case '@': putchar(' '); break; case '-': /* ignore these */ case '=': case '!': case '^': case '~': case '.': break; case '(': /* if -m is set, ignore math */ case '[': c1 = (c == '(') ? ')' : ']'; if (!nomath) putchar(c); while (nomath && c != c1) { while ( (c=getc(inf)) != EOF && skipcomment(inf, &c) && c != '\\' ); GET(c); } break; case '3': if (germ) fputs(umlaut('s'), stdout); break; case '\"': GET(c); if (uml) fputs(umlaut(c), stdout); break; case '\\':putchar('\n'); GET(c); if (c == '[') while ((c=getc(inf)) != EOF && skipcomment(inf, &c) && c != ']'); else ungetc(c, inf); break; default: ungetc(c, inf); if ((c=parsecmd(inf)) == EOF) return; if (c=='\n') putchar(c); else putchar(' '); break; } break; /*****************************************/ case '%':while ((c=getc(inf)) != EOF && c != '\n'); break; case '{': case '}': case '~': case '_': putchar(' '); break; case '\"': if (germ) { GET(c); fputs(umlaut(c), stdout); } else putchar(c); break; case '$': GET(c); if (c != '$') ungetc(c, inf); if (nomath) { int bs = (c == '\\'); while ((c=getc(inf)) != EOF && skipcomment(inf, &c) && !(c == '$' && !bs)) bs = (c == '\\'); if (c == EOF) return; GET(c); if (c != '$') ungetc(c, inf); } break; case '&': if (inarray) putchar(' '); else putchar('&'); break; default:putchar(c); break; } if (c == EOF) return; } return; }
/* * Parse a line and determine its type. We keep the preprocessor line * parser state between calls in the global variable linestate, with * help from skipcomment(). */ static Linetype get_line(void) { const char *cp; int cursym; int kwlen; Linetype retval; Comment_state wascomment; if (fgets(tline, MAXLINE, input) == NULL) return (LT_EOF); retval = LT_PLAIN; wascomment = incomment; cp = skipcomment(tline); if (linestate == LS_START) { if (*cp == '#') { linestate = LS_HASH; cp = skipcomment(cp + 1); } else if (*cp != '\0') linestate = LS_DIRTY; } if (!incomment && linestate == LS_HASH) { keyword = tline + (cp - tline); cp = skipsym(cp); kwlen = cp - keyword; /* no way can we deal with a continuation inside a keyword */ if (strncmp(cp, "\\\n", 2) == 0) Eioccc(); if (strlcmp("ifdef", keyword, kwlen) == 0 || strlcmp("ifndef", keyword, kwlen) == 0) { cp = skipcomment(cp); if ((cursym = findsym(cp)) < 0) retval = LT_IF; else { retval = (keyword[2] == 'n') ? LT_FALSE : LT_TRUE; if (value[cursym] == NULL) retval = (retval == LT_TRUE) ? LT_FALSE : LT_TRUE; if (ignore[cursym]) retval = (retval == LT_TRUE) ? LT_TRUEI : LT_FALSEI; } cp = skipsym(cp); } else if (strlcmp("if", keyword, kwlen) == 0) retval = ifeval(&cp); else if (strlcmp("elif", keyword, kwlen) == 0) retval = ifeval(&cp) - LT_IF + LT_ELIF; else if (strlcmp("else", keyword, kwlen) == 0) retval = LT_ELSE; else if (strlcmp("endif", keyword, kwlen) == 0) retval = LT_ENDIF; else { linestate = LS_DIRTY; retval = LT_PLAIN; } cp = skipcomment(cp); if (*cp != '\0') { linestate = LS_DIRTY; if (retval == LT_TRUE || retval == LT_FALSE || retval == LT_TRUEI || retval == LT_FALSEI) retval = LT_IF; if (retval == LT_ELTRUE || retval == LT_ELFALSE) retval = LT_ELIF; } if (retval != LT_PLAIN && (wascomment || incomment)) { retval += LT_DODGY; if (incomment) linestate = LS_DIRTY; } /* skipcomment should have changed the state */ if (linestate == LS_HASH) abort(); /* bug */ } if (linestate == LS_DIRTY) { while (*cp != '\0') cp = skipcomment(cp + 1); } debug("parser %s comment %s line", comment_name[incomment], linestate_name[linestate]); return (retval); }
/* * Parse a line and determine its type. We keep the preprocessor line * parser state between calls in the global variable linestate, with * help from skipcomment(). */ static Linetype parseline(void) { const char *cp; int cursym; Linetype retval; Comment_state wascomment; wascomment = incomment; cp = skiphash(); if (cp == NULL) return (LT_EOF); if (newline == NULL) { if (strrchr(tline, '\n') == strrchr(tline, '\r') + 1) newline = newline_crlf; else newline = newline_unix; } if (*cp == '\0') { retval = LT_PLAIN; goto done; } keyword = tline + (cp - tline); if ((cp = matchsym("ifdef", keyword)) != NULL || (cp = matchsym("ifndef", keyword)) != NULL) { cp = skipcomment(cp); if ((cursym = findsym(&cp)) < 0) retval = LT_IF; else { retval = (keyword[2] == 'n') ? LT_FALSE : LT_TRUE; if (value[cursym] == NULL) retval = (retval == LT_TRUE) ? LT_FALSE : LT_TRUE; if (ignore[cursym]) retval = (retval == LT_TRUE) ? LT_TRUEI : LT_FALSEI; } } else if ((cp = matchsym("if", keyword)) != NULL) retval = ifeval(&cp); else if ((cp = matchsym("elif", keyword)) != NULL) retval = linetype_if2elif(ifeval(&cp)); else if ((cp = matchsym("else", keyword)) != NULL) retval = LT_ELSE; else if ((cp = matchsym("endif", keyword)) != NULL) retval = LT_ENDIF; else { cp = skipsym(keyword); /* no way can we deal with a continuation inside a keyword */ if (strncmp(cp, "\\\r\n", 3) == 0 || strncmp(cp, "\\\n", 2) == 0) Eioccc(); cp = skipline(cp); retval = LT_PLAIN; goto done; } cp = skipcomment(cp); if (*cp != '\0') { cp = skipline(cp); if (retval == LT_TRUE || retval == LT_FALSE || retval == LT_TRUEI || retval == LT_FALSEI) retval = LT_IF; if (retval == LT_ELTRUE || retval == LT_ELFALSE) retval = LT_ELIF; } /* the following can happen if the last line of the file lacks a newline or if there is too much whitespace in a directive */ if (linestate == LS_HASH) { long len = cp - tline; if (fgets(tline + len, MAXLINE - len, input) == NULL) { if (ferror(input)) err(2, "can't read %s", filename); /* append the missing newline at eof */ strcpy(tline + len, newline); cp += strlen(newline); linestate = LS_START; } else { linestate = LS_DIRTY; } } if (retval != LT_PLAIN && (wascomment || linestate != LS_START)) { retval = linetype_2dodgy(retval); linestate = LS_DIRTY; } done: debug("parser line %d state %s comment %s line", linenum, comment_name[incomment], linestate_name[linestate]); return (retval); }
/* * Function for evaluating the innermost parts of expressions, * viz. !expr (expr) number defined(symbol) symbol * We reset the constexpr flag in the last two cases. */ static Linetype eval_unary(const struct ops *ops, long *valp, const char **cpp) { const char *cp; char *ep; int sym; bool defparen; Linetype lt; cp = skipcomment(*cpp); if (*cp == '!') { debug("eval%d !", prec(ops)); cp++; lt = eval_unary(ops, valp, &cp); if (lt == LT_ERROR) return (LT_ERROR); if (lt != LT_IF) { *valp = !*valp; lt = *valp ? LT_TRUE : LT_FALSE; } } else if (*cp == '~') { debug("eval%d ~", prec(ops)); cp++; lt = eval_unary(ops, valp, &cp); if (lt == LT_ERROR) return (LT_ERROR); if (lt != LT_IF) { *valp = ~(*valp); lt = *valp ? LT_TRUE : LT_FALSE; } } else if (*cp == '-') { debug("eval%d -", prec(ops)); cp++; lt = eval_unary(ops, valp, &cp); if (lt == LT_ERROR) return (LT_ERROR); if (lt != LT_IF) { *valp = -(*valp); lt = *valp ? LT_TRUE : LT_FALSE; } } else if (*cp == '(') { cp++; debug("eval%d (", prec(ops)); lt = eval_table(eval_ops, valp, &cp); if (lt == LT_ERROR) return (LT_ERROR); cp = skipcomment(cp); if (*cp++ != ')') return (LT_ERROR); } else if (isdigit((unsigned char)*cp)) { debug("eval%d number", prec(ops)); *valp = strtol(cp, &ep, 0); if (ep == cp) return (LT_ERROR); lt = *valp ? LT_TRUE : LT_FALSE; cp = ep; } else if (matchsym("defined", cp) != NULL) { cp = skipcomment(cp+7); if (*cp == '(') { cp = skipcomment(cp+1); defparen = true; } else { defparen = false; } sym = findsym(&cp); cp = skipcomment(cp); if (defparen && *cp++ != ')') { debug("eval%d defined missing ')'", prec(ops)); return (LT_ERROR); } if (sym < 0) { debug("eval%d defined unknown", prec(ops)); lt = LT_IF; } else { debug("eval%d defined %s", prec(ops), symname[sym]); *valp = (value[sym] != NULL); lt = *valp ? LT_TRUE : LT_FALSE; } constexpr = false; } else if (!endsym(*cp)) {
/* * Parse a line and determine its type. We keep the preprocessor line * parser state between calls in the global variable linestate, with * help from skipcomment(). */ static Linetype parseline(void) { const char *cp; int cursym; int kwlen; Linetype retval; Comment_state wascomment; linenum++; if (fgets(tline, MAXLINE, input) == NULL) { if (ferror(input)) err(2, "can't read %s", filename); else return (LT_EOF); } if (newline == NULL) { if (strrchr(tline, '\n') == strrchr(tline, '\r') + 1) newline = newline_crlf; else newline = newline_unix; } retval = LT_PLAIN; wascomment = incomment; cp = skipcomment(tline); if (linestate == LS_START) { if (*cp == '#') { linestate = LS_HASH; firstsym = true; cp = skipcomment(cp + 1); } else if (*cp != '\0') linestate = LS_DIRTY; } if (!incomment && linestate == LS_HASH) { keyword = tline + (cp - tline); cp = skipsym(cp); kwlen = cp - keyword; /* no way can we deal with a continuation inside a keyword */ if (strncmp(cp, "\\\r\n", 3) == 0 || strncmp(cp, "\\\n", 2) == 0) Eioccc(); if (strlcmp("ifdef", keyword, kwlen) == 0 || strlcmp("ifndef", keyword, kwlen) == 0) { cp = skipcomment(cp); if ((cursym = findsym(cp)) < 0) retval = LT_IF; else { retval = (keyword[2] == 'n') ? LT_FALSE : LT_TRUE; if (value[cursym] == NULL) retval = (retval == LT_TRUE) ? LT_FALSE : LT_TRUE; if (ignore[cursym]) retval = (retval == LT_TRUE) ? LT_TRUEI : LT_FALSEI; } cp = skipsym(cp); } else if (strlcmp("if", keyword, kwlen) == 0) retval = ifeval(&cp); else if (strlcmp("elif", keyword, kwlen) == 0) retval = linetype_if2elif(ifeval(&cp)); else if (strlcmp("else", keyword, kwlen) == 0) retval = LT_ELSE; else if (strlcmp("endif", keyword, kwlen) == 0) retval = LT_ENDIF; else { linestate = LS_DIRTY; retval = LT_PLAIN; } cp = skipcomment(cp); if (*cp != '\0') { linestate = LS_DIRTY; if (retval == LT_TRUE || retval == LT_FALSE || retval == LT_TRUEI || retval == LT_FALSEI) retval = LT_IF; if (retval == LT_ELTRUE || retval == LT_ELFALSE) retval = LT_ELIF; } if (retval != LT_PLAIN && (wascomment || incomment)) { retval = linetype_2dodgy(retval); if (incomment) linestate = LS_DIRTY; } /* skipcomment normally changes the state, except if the last line of the file lacks a newline, or if there is too much whitespace in a directive */ if (linestate == LS_HASH) { size_t len = cp - tline; if (fgets(tline + len, MAXLINE - len, input) == NULL) { if (ferror(input)) err(2, "can't read %s", filename); /* append the missing newline at eof */ strcpy(tline + len, newline); cp += strlen(newline); linestate = LS_START; } else { linestate = LS_DIRTY; } } } if (linestate == LS_DIRTY) { while (*cp != '\0') cp = skipcomment(cp + 1); } debug("parser line %d state %s comment %s line", linenum, comment_name[incomment], linestate_name[linestate]); return (retval); }
int parsecmd(FILE *inf) { int c, ce; char cmd[MAXCMDLEN], env[MAXCMDLEN], envtst[MAXCMDLEN]; int fnc, cmdc, envc, i, openb, closeb; int proceed; char fname[MAXFILENAMELEN]; fnc = envc = cmdc = 0; c = getc(inf); while (c != EOF && (isalnum(c) || c == '@' || c == '*' )) { cmd[cmdc++] = c; if (cmdc >= MAXCMDLEN - 1) cmdc--; c = getc(inf); } cmd[cmdc] = 0; if (c == EOF) return(c); if (noopt && c == '[') { while ((c=getc(inf)) != EOF && c != ']'); if ((c = getc(inf)) == EOF) return(c); } if (noarg && c == '{' && strcmp(cmd,"begin") && strcmp(cmd,"end") && ((strcmp(cmd,"include") && strcmp(cmd,"input"))||!inputs) ) { openb = 1; closeb = 0; while ((c = getc(inf)) != EOF && skipcomment(inf, &c) && closeb != openb) if (c =='{') openb++; else if (c == '}') closeb++; ungetc(c, inf); return(c); } if (inputs && (!strcmp(cmd, "input") || !strcmp(cmd,"include"))) { FILE *incfile; if (!(c == '{' || ( c == ' ' && !strcmp(cmd,"input"))) || c == EOF) { ungetc(c, inf); return(c); } fnc = 0; if (c == '{') ce = '}'; else { c = '{'; ce = '\n'; } while (c != EOF && c != ce && !isspace(c)) { c = getc(inf); fname[fnc++] = c; if (fnc >= MAXFILENAMELEN - 4) fnc--; } fname[fnc-1] = 0; if (strncmp(fname+fnc-5, ".tex", 4)) strcat(fname,".tex"); if ((incfile = fopen(fname,"r"))==NULL) perror(fname); else untex(incfile); fclose(incfile); return(c); } if (!strcmp(cmd,"begin") || !strcmp(cmd,"end")) { if ((c != '{' || c == EOF)) { ungetc(c, inf); return(c); } envc = 0; while (c != EOF && c != '}') { c = getc(inf); env[envc++] = c; if (envc >= MAXCMDLEN - 1) envc--; } env[envc-1] = 0; if (!noenv) printf(env); envtst[0] = 0; /* special treatment of some environments */ /* thebibiliography */ if (noenv && !strcmp(cmd, "begin") && !strcmp(env,"thebibliography")) skip(inf, '{'); /* table, figure */ if (noenv && !strcmp(cmd, "begin") && (!strcmp(env, "table") || !strcmp(env, "table*") || !strcmp(env, "figure") || !strcmp(env, "figure*") )) skip(inf, '['); /* documentstyle, minipage */ if (noenv && !strcmp(cmd, "begin") && !strcmp(env, "minipage")) { skip(inf, '['); skip(inf, '{'); } /* tabular, array, eqnarray */ if (!strcmp(cmd, "begin") && (!strcmp(env, "tabular") || !strcmp(env, "eqnarray") || !strcmp(env, "eqnarray*") || !strcmp(env, "array") )) { inarray++; if (noenv && env[0] != 'e') { skip(inf, '['); skip(inf, '{'); } } if (!strcmp(cmd, "end") && (!strcmp(env, "tabular") || !strcmp(env, "eqnarray") || !strcmp(env, "eqnarray*") || !strcmp(env, "array") )) if (--inarray < 0) inarray = 0; /* displaymath, equation, eqnarray */ if (nomath && !strcmp(cmd,"begin") && (!strcmp(env,"displaymath") || !strcmp(env,"equation") || !strcmp(env,"eqnarray") || !strcmp(env,"equation*") || !strcmp(env,"eqnarray*") ) ) { putchar('\n'); while (strcmp(envtst, env)) { while ((c=getc(inf)) != EOF && skipcomment(inf, &c) && c != '\\'); if (getc(inf) == 'e' && getc(inf) == 'n' && getc(inf) == 'd' && getc(inf) == '{') { i = 0; while ((c=getc(inf)) != EOF && c != '}') { envtst[i++] = c; if (i >= MAXCMDLEN - 1) i--; } envtst[i] = 0; } } if (!noenv) printf(envtst); } } ungetc(c, inf); return(c); }
/* * Function for evaluating the innermost parts of expressions, * viz. !expr (expr) defined(symbol) symbol number * We reset the keepthis flag when we find a non-constant subexpression. */ static Linetype eval_unary(const struct ops *ops, int *valp, const char **cpp) { const char *cp; char *ep; int sym; cp = skipcomment(*cpp); if (*cp == '!') { debug("eval%d !", ops - eval_ops); cp++; if (eval_unary(ops, valp, &cp) == LT_IF) { *cpp = cp; return (LT_IF); } *valp = !*valp; } else if (*cp == '(') { cp++; debug("eval%d (", ops - eval_ops); if (eval_table(eval_ops, valp, &cp) == LT_IF) return (LT_IF); cp = skipcomment(cp); if (*cp++ != ')') return (LT_IF); } else if (isdigit((unsigned char)*cp)) { debug("eval%d number", ops - eval_ops); *valp = strtol(cp, &ep, 0); cp = skipsym(cp); } else if (strncmp(cp, "defined", 7) == 0 && endsym(cp[7])) { cp = skipcomment(cp+7); debug("eval%d defined", ops - eval_ops); if (*cp++ != '(') return (LT_IF); cp = skipcomment(cp); sym = findsym(cp); cp = skipsym(cp); cp = skipcomment(cp); if (*cp++ != ')') return (LT_IF); if (sym >= 0) *valp = (value[sym] != NULL); else { *cpp = cp; return (LT_IF); } keepthis = false; } else if (!endsym(*cp)) { debug("eval%d symbol", ops - eval_ops); sym = findsym(cp); if (sym < 0) return (LT_IF); if (value[sym] == NULL) *valp = 0; else { *valp = strtol(value[sym], &ep, 0); if (*ep != '\0' || ep == value[sym]) return (LT_IF); } cp = skipsym(cp); keepthis = false; } else { debug("eval%d bad expr", ops - eval_ops); return (LT_IF); } *cpp = cp; debug("eval%d = %d", ops - eval_ops, *valp); return (*valp ? LT_TRUE : LT_FALSE); }
static Linetype parseline(void) { const char *cp; int cursym; int kwlen; Linetype retval; Comment_state wascomment; linenum++; if (fgets(tline, MAXLINE, input) == NULL) return (LT_EOF); if (newline == NULL) { if (strrchr(tline, '\n') == strrchr(tline, '\r') + 1) newline = newline_crlf; else newline = newline_unix; } retval = LT_PLAIN; wascomment = incomment; cp = skipcomment(tline); if (linestate == LS_START) { if (*cp == '#') { linestate = LS_HASH; firstsym = true; cp = skipcomment(cp + 1); } else if (*cp != '\0') linestate = LS_DIRTY; } if (!incomment && linestate == LS_HASH) { keyword = tline + (cp - tline); cp = skipsym(cp); kwlen = cp - keyword; if (strncmp(cp, "\\\r\n", 3) == 0 || strncmp(cp, "\\\n", 2) == 0) Eioccc(); if (strlcmp("ifdef", keyword, kwlen) == 0 || strlcmp("ifndef", keyword, kwlen) == 0) { cp = skipcomment(cp); if ((cursym = findsym(cp)) < 0) retval = LT_IF; else { retval = (keyword[2] == 'n') ? LT_FALSE : LT_TRUE; if (value[cursym] == NULL) retval = (retval == LT_TRUE) ? LT_FALSE : LT_TRUE; if (ignore[cursym]) retval = (retval == LT_TRUE) ? LT_TRUEI : LT_FALSEI; } cp = skipsym(cp); } else if (strlcmp("if", keyword, kwlen) == 0) retval = ifeval(&cp); else if (strlcmp("elif", keyword, kwlen) == 0) retval = ifeval(&cp) - LT_IF + LT_ELIF; else if (strlcmp("else", keyword, kwlen) == 0) retval = LT_ELSE; else if (strlcmp("endif", keyword, kwlen) == 0) retval = LT_ENDIF; else { linestate = LS_DIRTY; retval = LT_PLAIN; } cp = skipcomment(cp); if (*cp != '\0') { linestate = LS_DIRTY; if (retval == LT_TRUE || retval == LT_FALSE || retval == LT_TRUEI || retval == LT_FALSEI) retval = LT_IF; if (retval == LT_ELTRUE || retval == LT_ELFALSE) retval = LT_ELIF; } if (retval != LT_PLAIN && (wascomment || incomment)) { retval += LT_DODGY; if (incomment) linestate = LS_DIRTY; } if (linestate == LS_HASH) { size_t len = cp - tline; if (fgets(tline + len, MAXLINE - len, input) == NULL) { strcpy(tline + len, newline); cp += strlen(newline); linestate = LS_START; } else { linestate = LS_DIRTY; } } } if (linestate == LS_DIRTY) { while (*cp != '\0') cp = skipcomment(cp + 1); } debug("parser line %d state %s comment %s line", linenum, comment_name[incomment], linestate_name[linestate]); return (retval); }