3 This file is part of the HandBrake source code.
4 Homepage: <http://handbrake.m0k.org/>.
5 It may be used under the terms of the GNU General Public License. */
11 /* Internal declarations */
12 #define is_newline(_x) ( (_x) == 13 || \
16 #define is_white(_x) ( (_x) == '\t' || \
20 #define is_sep(_x) ( (_x) == ',' )
22 #define is_esc(_x) ( (_x) == '\\' )
24 #define CSV_CHAR_ERROR 0x8000
25 #define CSV_CHAR_EOF 0x4000
26 #define CSV_CHAR_ROWSEP 0x2000
27 #define CSV_CHAR_COLSEP 0x1000
29 #define CSV_PARSE_NORMAL 0x0000
30 #define CSV_PARSE_SEEK 0x0001
31 #define CSV_PARSE_ESC 0x0002
33 static uint16_t hb_parse_character( hb_csv_file_t
* file
);
34 static void hb_trim_end( char *text
);
37 hb_csv_file_t
*hb_open_csv_file( const char *filepath
)
39 hb_csv_file_t
*file
= NULL
;
42 if( filepath
== NULL
)
47 fileref
= fopen( filepath
, "r" );
53 file
= malloc( sizeof( hb_csv_file_t
) );
54 file
->fileref
= fileref
;
56 file
->parse_state
= CSV_PARSE_SEEK
;
62 void hb_close_csv_file( hb_csv_file_t
*file
)
69 fclose( file
->fileref
);
74 hb_csv_cell_t
*hb_read_next_cell( hb_csv_file_t
*file
)
76 hb_csv_cell_t
*cell
= NULL
;
90 cell
= malloc( sizeof( hb_csv_cell_t
) );
91 cell
->cell_row
= file
->curr_row
;
92 cell
->cell_col
= file
->curr_col
;
94 while( CSV_CHAR_EOF
!= (c
= hb_parse_character( file
) ) )
96 if( c
== CSV_CHAR_ROWSEP
)
102 else if( c
== CSV_CHAR_COLSEP
)
111 cell
->cell_text
[index
] = (char)c
;
117 if( c
== CSV_CHAR_EOF
)
122 /* Terminate the cell text */
123 cell
->cell_text
[index
] = '\0';
124 hb_trim_end( cell
->cell_text
);
128 void hb_dispose_cell( hb_csv_cell_t
*cell
)
139 static uint16_t hb_parse_character( hb_csv_file_t
* file
)
147 return CSV_CHAR_ERROR
;
152 byte
= fgetc( file
->fileref
);
153 if( feof( file
->fileref
) )
157 if( ferror( file
->fileref
) )
159 return CSV_CHAR_ERROR
;
162 if( file
->parse_state
== CSV_PARSE_SEEK
&& is_white(byte
) )
166 else if( file
->parse_state
!= CSV_PARSE_ESC
&& is_esc(byte
) )
168 file
->parse_state
= CSV_PARSE_ESC
;
171 else if( file
->parse_state
!= CSV_PARSE_ESC
&& is_sep(byte
) )
173 file
->parse_state
= CSV_PARSE_SEEK
;
177 else if( file
->parse_state
== CSV_PARSE_ESC
)
179 file
->parse_state
= CSV_PARSE_NORMAL
;
183 else if( is_newline(byte
) )
185 file
->parse_state
= CSV_PARSE_SEEK
;
191 file
->parse_state
= CSV_PARSE_NORMAL
;
200 static void hb_trim_end( char *text
)
207 int i
= strlen(text
) - 1;
209 for( i
= strlen(text
) - 1; i
>= 0 && is_white(text
[i
]) ; i
-- )