src/csvparser.c
/*
    Public API
    Main parsing state-machine
*/
Public API
Main parsing state-machine
Public API Main parsing state - machine
enum csvError csvParserProcessByte(
    struct csvParser* lpParser,
    char bByte
) {
    enum csvError e;
    if(lpParser == NULL) {
        return csvE_InvalidParam;
    }
    if((lpParser->dwFlags & CSVPARSER_FLAGS__QUIRKS_ALLOW_NONASCII) == 0) {
        if((bByte & 0x80) != 0) {
            return csvE_EncodingError;
        }
    }
    if(lpParser->parserState == csvParserState_IDLE) {
        if(bByte == lpParser->sepChar) {
            e = csvParser_Collector_EventNextField(lpParser); if(e != csvE_Ok) { return e; }
            lpParser->parserState = csvParserState_IDLE;
            return csvE_Ok;
        } else if(bByte == 0x0D) {
            lpParser->parserState = csvParserState_CR1;
            return csvE_Ok;
        } else if(bByte == 0x22) {
            lpParser->parserState = csvParserState_EscapedField;
            return csvE_Ok;
        } else if((bByte == 0x20) || (bByte == 0x21) || ((bByte >= 0x23) && (bByte <= 0x2B)) || ((bByte >= 0x2D) && (bByte <= 0x7E))) {
            e = csvParser_Collector_Push(lpParser, bByte);
            if(e != csvE_Ok) { return e; }
            lpParser->parserState = csvParserState_Field;
            return csvE_Ok;
        }
		if(lpParser->callbacks.callbackError != NULL) {
			lpParser->callbacks.callbackError(lpParser, lpParser->callbacks.lpFreeParam_Error, csvE_ParserError, lpParser->dwLineNumber);
		}
        return csvE_ParserError;
    } else if(lpParser->parserState == csvParserState_CR1) {
        if(bByte == 0x0A) {
            lpParser->parserState = csvParserState_IDLE;
            lpParser->dwLineNumber = lpParser->dwLineNumber + 1;
            e = csvParser_Event_FinishedRecord(lpParser);
            return e;
        }
		if(lpParser->callbacks.callbackError != NULL) {
			lpParser->callbacks.callbackError(lpParser, lpParser->callbacks.lpFreeParam_Error, csvE_ParserError, lpParser->dwLineNumber);
		}
        return csvE_ParserError;
    } else if(lpParser->parserState == csvParserState_EscapedField) {
        if(bByte == 0x22) {
            lpParser->parserState = csvParserState_Quote;
            return csvE_Ok;
        } else if((bByte == 0x20) || (bByte == 0x21) || ((bByte >= 0x23) && (bByte <= 0x2B)) || ((bByte >= 0x2D) && (bByte <= 0x7E)) || (bByte == ',') || (bByte == 0x0A) || (bByte == 0x0D)) {
            e = csvParser_Collector_Push(lpParser, bByte);
            if(e != csvE_Ok) { return e; }
            lpParser->parserState = csvParserState_EscapedField;
            return csvE_Ok;
        }
		if(lpParser->callbacks.callbackError != NULL) {
			lpParser->callbacks.callbackError(lpParser, lpParser->callbacks.lpFreeParam_Error, csvE_ParserError, lpParser->dwLineNumber);
		}
        return csvE_ParserError;
    } else if(lpParser->parserState == csvParserState_Quote) {
        if(bByte == 0x22) {
            e = csvParser_Collector_Push(lpParser, bByte);
            if(e != csvE_Ok) { return e; }
            lpParser->parserState = csvParserState_EscapedField;
            return csvE_Ok;
        } else if(bByte == lpParser->sepChar) {
            e = csvParser_Collector_EventNextField(lpParser); if(e != csvE_Ok) { return e; }
            lpParser->parserState = csvParserState_IDLE;
            return csvE_Ok;
        } else if(bByte == 0x0D) {
            lpParser->parserState = csvParserState_CR3;
            return csvE_Ok;
        }
		if(lpParser->callbacks.callbackError != NULL) {
			lpParser->callbacks.callbackError(lpParser, lpParser->callbacks.lpFreeParam_Error, csvE_ParserError, lpParser->dwLineNumber);
		}
        return csvE_ParserError;
    } else if(lpParser->parserState == csvParserState_CR3) {
        if(bByte == 0x0A) {
            lpParser->parserState = csvParserState_IDLE;
            e = csvParser_Event_FinishedRecord(lpParser);
            return e;
        }
		if(lpParser->callbacks.callbackError != NULL) {
			lpParser->callbacks.callbackError(lpParser, lpParser->callbacks.lpFreeParam_Error, csvE_ParserError, lpParser->dwLineNumber);
		}
        return csvE_ParserError;
    } else if(lpParser->parserState == csvParserState_Field) {
        if((bByte == 0x20) || (bByte == 0x21) || ((bByte >= 0x23) && (bByte <= 0x2B)) || ((bByte >= 0x2D) && (bByte <= 0x7E))) {
            e = csvParser_Collector_Push(lpParser, bByte);
            if(e != csvE_Ok) { return e; }
            lpParser->parserState = csvParserState_Field;
            return csvE_Ok;
        } else if(bByte == 0x0D) {
            lpParser->parserState = csvParserState_CR2;
            return csvE_Ok;
        } else if(bByte == lpParser->sepChar) {
            e = csvParser_Collector_EventNextField(lpParser); if(e != csvE_Ok) { return e; }
            lpParser->parserState = csvParserState_IDLE;
            return csvE_Ok;
        } else if(bByte == 0x0a) {
          lpParser->dwLineNumber = lpParser->dwLineNumber + 1;
          e = csvParser_Event_FinishedRecord(lpParser);
					lpParser->parserState = csvParserState_IDLE;
					return csvE_Ok;
				}
		if(lpParser->callbacks.callbackError != NULL) {
			lpParser->callbacks.callbackError(lpParser, lpParser->callbacks.lpFreeParam_Error, csvE_ParserError, lpParser->dwLineNumber);
		}
        return csvE_ParserError;
    } else if(lpParser->parserState == csvParserState_CR2) {
        if(bByte == 0x0A) {
            lpParser->parserState = csvParserState_IDLE;
            e = csvParser_Event_FinishedRecord(lpParser);
            return e;
        }
		if(lpParser->callbacks.callbackError != NULL) {
			lpParser->callbacks.callbackError(lpParser, lpParser->callbacks.lpFreeParam_Error, csvE_ParserError, lpParser->dwLineNumber);
		}
        return csvE_ParserError;
    } else {
        return csvE_ImplementationError; 
    }
}
enum csvError csvParserProcessByte ( struct csvParser * lpParser , char bByte ) { enum csvError e ; if ( lpParser == NULL ) { return csvE_InvalidParam ; } if ( ( lpParser -> dwFlags & CSVPARSER_FLAGS__QUIRKS_ALLOW_NONASCII ) == 0 ) { if ( ( bByte & 0x80 ) != 0 ) { return csvE_EncodingError ; } } if ( lpParser -> parserState == csvParserState_IDLE ) { if ( bByte == lpParser -> sepChar ) { e = csvParser_Collector_EventNextField ( lpParser ) ; if ( e != csvE_Ok ) { return e ; } lpParser -> parserState = csvParserState_IDLE ; return csvE_Ok ; } else if ( bByte == 0x0D ) { lpParser -> parserState = csvParserState_CR1 ; return csvE_Ok ; } else if ( bByte == 0x22 ) { lpParser -> parserState = csvParserState_EscapedField ; return csvE_Ok ; } else if ( ( bByte == 0x20 ) || ( bByte == 0x21 ) || ( ( bByte >= 0x23 ) && ( bByte <= 0x2B ) ) || ( ( bByte >= 0x2D ) && ( bByte <= 0x7E ) ) ) { e = csvParser_Collector_Push ( lpParser , bByte ) ; if ( e != csvE_Ok ) { return e ; } lpParser -> parserState = csvParserState_Field ; return csvE_Ok ; } if ( lpParser -> callbacks . callbackError != NULL ) { lpParser -> callbacks . callbackError ( lpParser , lpParser -> callbacks . lpFreeParam_Error , csvE_ParserError , lpParser -> dwLineNumber ) ; } return csvE_ParserError ; } else if ( lpParser -> parserState == csvParserState_CR1 ) { if ( bByte == 0x0A ) { lpParser -> parserState = csvParserState_IDLE ; lpParser -> dwLineNumber = lpParser -> dwLineNumber + 1 ; e = csvParser_Event_FinishedRecord ( lpParser ) ; return e ; } if ( lpParser -> callbacks . callbackError != NULL ) { lpParser -> callbacks . callbackError ( lpParser , lpParser -> callbacks . lpFreeParam_Error , csvE_ParserError , lpParser -> dwLineNumber ) ; } return csvE_ParserError ; } else if ( lpParser -> parserState == csvParserState_EscapedField ) { if ( bByte == 0x22 ) { lpParser -> parserState = csvParserState_Quote ; return csvE_Ok ; } else if ( ( bByte == 0x20 ) || ( bByte == 0x21 ) || ( ( bByte >= 0x23 ) && ( bByte <= 0x2B ) ) || ( ( bByte >= 0x2D ) && ( bByte <= 0x7E ) ) || ( bByte == ' ' ) || ( bByte == 0x0A ) || ( bByte == 0x0D ) ) { e = csvParser_Collector_Push ( lpParser , bByte ) ; if ( e != csvE_Ok ) { return e ; } lpParser -> parserState = csvParserState_EscapedField ; return csvE_Ok ; } if ( lpParser -> callbacks . callbackError != NULL ) { lpParser -> callbacks . callbackError ( lpParser , lpParser -> callbacks . lpFreeParam_Error , csvE_ParserError , lpParser -> dwLineNumber ) ; } return csvE_ParserError ; } else if ( lpParser -> parserState == csvParserState_Quote ) { if ( bByte == 0x22 ) { e = csvParser_Collector_Push ( lpParser , bByte ) ; if ( e != csvE_Ok ) { return e ; } lpParser -> parserState = csvParserState_EscapedField ; return csvE_Ok ; } else if ( bByte == lpParser -> sepChar ) { e = csvParser_Collector_EventNextField ( lpParser ) ; if ( e != csvE_Ok ) { return e ; } lpParser -> parserState = csvParserState_IDLE ; return csvE_Ok ; } else if ( bByte == 0x0D ) { lpParser -> parserState = csvParserState_CR3 ; return csvE_Ok ; } if ( lpParser -> callbacks . callbackError != NULL ) { lpParser -> callbacks . callbackError ( lpParser , lpParser -> callbacks . lpFreeParam_Error , csvE_ParserError , lpParser -> dwLineNumber ) ; } return csvE_ParserError ; } else if ( lpParser -> parserState == csvParserState_CR3 ) { if ( bByte == 0x0A ) { lpParser -> parserState = csvParserState_IDLE ; e = csvParser_Event_FinishedRecord ( lpParser ) ; return e ; } if ( lpParser -> callbacks . callbackError != NULL ) { lpParser -> callbacks . callbackError ( lpParser , lpParser -> callbacks . lpFreeParam_Error , csvE_ParserError , lpParser -> dwLineNumber ) ; } return csvE_ParserError ; } else if ( lpParser -> parserState == csvParserState_Field ) { if ( ( bByte == 0x20 ) || ( bByte == 0x21 ) || ( ( bByte >= 0x23 ) && ( bByte <= 0x2B ) ) || ( ( bByte >= 0x2D ) && ( bByte <= 0x7E ) ) ) { e = csvParser_Collector_Push ( lpParser , bByte ) ; if ( e != csvE_Ok ) { return e ; } lpParser -> parserState = csvParserState_Field ; return csvE_Ok ; } else if ( bByte == 0x0D ) { lpParser -> parserState = csvParserState_CR2 ; return csvE_Ok ; } else if ( bByte == lpParser -> sepChar ) { e = csvParser_Collector_EventNextField ( lpParser ) ; if ( e != csvE_Ok ) { return e ; } lpParser -> parserState = csvParserState_IDLE ; return csvE_Ok ; } else if ( bByte == 0x0a ) { lpParser -> dwLineNumber = lpParser -> dwLineNumber + 1 ; e = csvParser_Event_FinishedRecord ( lpParser ) ; lpParser -> parserState = csvParserState_IDLE ; return csvE_Ok ; } if ( lpParser -> callbacks . callbackError != NULL ) { lpParser -> callbacks . callbackError ( lpParser , lpParser -> callbacks . lpFreeParam_Error , csvE_ParserError , lpParser -> dwLineNumber ) ; } return csvE_ParserError ; } else if ( lpParser -> parserState == csvParserState_CR2 ) { if ( bByte == 0x0A ) { lpParser -> parserState = csvParserState_IDLE ; e = csvParser_Event_FinishedRecord ( lpParser ) ; return e ; } if ( lpParser -> callbacks . callbackError != NULL ) { lpParser -> callbacks . callbackError ( lpParser , lpParser -> callbacks . lpFreeParam_Error , csvE_ParserError , lpParser -> dwLineNumber ) ; } return csvE_ParserError ; } else { return csvE_ImplementationError ; } }
Public API
Main parsing state-machine
Public API Main parsing state - machine
/* Separation character */ /* CR */ /* DQUOTE */ /* TEXTDATA */ /* LF */ /* DQUOTE */ /* EV: Done Record TODO */ /* Separation character */ /* TEXTDATA */ /* Separation character */ //					e = csvParser_Collector_EventNextField(lpParser); if(e != csvE_Ok) { return e; }
 /* Undefined state ... should never happen */