741f82fa54f9befc60d2cd84e84ddd67683755da hiram Fri Jan 24 15:34:00 2014 -0800 move common lav reading business into the library and fixup more lavToPsl bugs and add to lav testing refs #12502 diff --git src/hg/lib/lav.c src/hg/lib/lav.c new file mode 100644 index 0000000..8ec6cfe --- /dev/null +++ src/hg/lib/lav.c @@ -0,0 +1,156 @@ +/* lav.c - common lav file reading routines */ +#include "lav.h" + +static void unexpectedEof(struct lineFile *lf) +/* Squawk about unexpected end of file. */ +{ +errAbort("Unexpected end of file in %s", lf->fileName); +} + +static void seekEndOfStanza(struct lineFile *lf) +/* find end of stanza */ +{ +char *line; +for (;;) + { + if (!lineFileNext(lf, &line, NULL)) + unexpectedEof(lf); + if (line[0] == '}') + break; + } +} + +static char *needNextWord(struct lineFile *lf, char **pLine) +/* Get next word from line or die trying. */ +{ +char *word = nextWord(pLine); +if (word == NULL) + errAbort("Short line %d of %s\n", lf->lineIx, lf->fileName); +return word; +} + +static char *justChrom(char *s) +/* Simplify mongo nib file thing in axt. */ +{ +char *e = stringIn(".nib:", s); +if (e == NULL) + return s; +*e = 0; +e = strrchr(s, '/'); +if (e == NULL) + return s; +else + return e+1; +} + +void parseS(struct lineFile *lf, int *tSize, int *qSize) +/* Parse s stanza and return tSize and qSize */ +{ +char *words[3]; +if (!lineFileRow(lf, words)) + unexpectedEof(lf); +*tSize = lineFileNeedNum(lf, words, 2); +if (!lineFileRow(lf, words)) + unexpectedEof(lf); +*qSize = lineFileNeedNum(lf, words, 2); +seekEndOfStanza(lf); +} + +void parseH(struct lineFile *lf, char **tName, char **qName, boolean *isRc) +/* Parse out H stanza */ +{ +char *line, *word, *e; +int i; + + +/* Set return variables to default values. */ +freez(qName); +freez(tName); +*isRc = FALSE; + +for (i=0; ; ++i) + { + if (!lineFileNext(lf, &line, NULL)) + unexpectedEof(lf); + if (line[0] == '#') + continue; + if (line[0] == '}') + { + if (i < 2) + errAbort("Short H stanza line %d of %s", lf->lineIx, lf->fileName); + break; + } + word = needNextWord(lf, &line); + word += 2; /* Skip over "> */ + e = strchr(word, '"'); + if (e != NULL) + { + *e = 0; + if (line != NULL) + ++line; + } + if (i == 0) + *tName = cloneString(justChrom(word)); + else if (i == 1) + *qName = cloneString(justChrom(word)); + if ((line != NULL) && (stringIn("(reverse", line) != NULL)) + *isRc = TRUE; + } +} + +void parseD(struct lineFile *lf, char **matrix, char **command, FILE *f) +/* Parse d stanza and return matrix and blastz command line */ +{ +char *line, *words[64]; +int i, size, wordCount = 0; +struct axtScoreScheme *ss = NULL; +freez(matrix); +freez(command); +if (!lineFileNext(lf, &line, &size)) + unexpectedEof(lf); +if (stringIn("lastz",line)) + { + stripChar(line,'"'); + wordCount = chopLine(line, words); + fprintf(f, "##aligner=%s",words[0]); + for (i = 3 ; i <wordCount ; i++) + fprintf(f, " %s ",words[i]); + fprintf(f,"\n"); + ss = axtScoreSchemeReadLf(lf); + axtScoreSchemeDnaWrite(ss, f, words[0]); + } +seekEndOfStanza(lf); +} + +struct block *removeFrayedEnds(struct block *blockList) +/* Remove zero length blocks at start and/or end to + * work around blastz bug. */ +{ +struct block *block = blockList; +struct block *lastBlock = NULL; +if (block != NULL && block->qStart == block->qEnd) + { +verbose(2,"removeFrayedEnds: first block: %d == %d\n", + block->qStart, block->qEnd); + blockList = blockList->next; + freeMem(block); + } +for (block = blockList; block != NULL; block = block->next) + { + if (block->next == NULL) /* Last block in list */ + { + if (block->qStart == block->qEnd) + { +verbose(2,"removeFrayedEnds:\n"); + if (lastBlock == NULL) /* Only block on list. */ + blockList = NULL; + else + lastBlock->next = NULL; + } + } + lastBlock = block; + } +if (lastBlock != NULL && lastBlock->qStart == lastBlock->qEnd) + freeMem(lastBlock); +return blockList; +}