* CopyReadLineText - inner loop of CopyReadLine for text mode */
| 839 | * CopyReadLineText - inner loop of CopyReadLine for text mode |
| 840 | */ |
| 841 | bool |
| 842 | CopyReadLineText(CopyFromState cstate) |
| 843 | { |
| 844 | char *copy_input_buf; |
| 845 | int input_buf_ptr; |
| 846 | int copy_buf_len; |
| 847 | bool need_data = false; |
| 848 | bool hit_eof = false; |
| 849 | bool result = false; |
| 850 | |
| 851 | /* CSV variables */ |
| 852 | bool first_char_in_line = true; |
| 853 | bool in_quote = false, |
| 854 | last_was_esc = false; |
| 855 | char quotec = '\0'; |
| 856 | char escapec = '\0'; |
| 857 | |
| 858 | if (cstate->opts.csv_mode) |
| 859 | { |
| 860 | quotec = cstate->opts.quote[0]; |
| 861 | escapec = cstate->opts.escape[0]; |
| 862 | /* ignore special escape processing if it's the same as quotec */ |
| 863 | if (quotec == escapec) |
| 864 | escapec = '\0'; |
| 865 | } |
| 866 | |
| 867 | /* |
| 868 | * The objective of this loop is to transfer the entire next input line |
| 869 | * into line_buf. Hence, we only care for detecting newlines (\r and/or |
| 870 | * \n) and the end-of-copy marker (\.). |
| 871 | * |
| 872 | * In CSV mode, \r and \n inside a quoted field are just part of the data |
| 873 | * value and are put in line_buf. We keep just enough state to know if we |
| 874 | * are currently in a quoted field or not. |
| 875 | * |
| 876 | * These four characters, and the CSV escape and quote characters, are |
| 877 | * assumed the same in frontend and backend encodings. |
| 878 | * |
| 879 | * For speed, we try to move data from raw_buf to line_buf in chunks |
| 880 | * rather than one character at a time. input_buf_ptr points to the next |
| 881 | * character to examine; any characters from raw_buf_index to input_buf_ptr |
| 882 | * have been determined to be part of the line, but not yet transferred to |
| 883 | * line_buf. |
| 884 | * |
| 885 | * For a little extra speed within the loop, we copy raw_buf and |
| 886 | * raw_buf_len into local variables. |
| 887 | */ |
| 888 | copy_input_buf = cstate->input_buf; |
| 889 | input_buf_ptr = cstate->input_buf_index; |
| 890 | copy_buf_len = cstate->input_buf_len; |
| 891 | |
| 892 | for (;;) |
| 893 | { |
| 894 | int prev_raw_ptr; |
| 895 | char c; |
| 896 | |
| 897 | /* |
| 898 | * Load more data if needed. Ideally we would just force four bytes |
no test coverage detected