Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Make php_fgetcsv() return a HashTale instead of in-out zval param #8936

Merged
merged 2 commits into from Jul 8, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
6 changes: 5 additions & 1 deletion ext/spl/spl_directory.c
Expand Up @@ -1958,7 +1958,11 @@ static zend_result spl_filesystem_file_read_csv(spl_filesystem_object *intern, c
ZVAL_UNDEF(&intern->u.file.current_zval);
}

php_fgetcsv(intern->u.file.stream, delimiter, enclosure, escape, buf_len, buf, &intern->u.file.current_zval);
HashTable *values = php_fgetcsv(intern->u.file.stream, delimiter, enclosure, escape, buf_len, buf);
if (values == NULL) {
values = php_bc_fgetcsv_empty_line();
}
ZVAL_ARR(&intern->u.file.current_zval, values);
if (return_value) {
ZVAL_COPY(return_value, &intern->u.file.current_zval);
}
Expand Down
34 changes: 26 additions & 8 deletions ext/standard/file.c
Expand Up @@ -2050,11 +2050,24 @@ PHP_FUNCTION(fgetcsv)
}
}

php_fgetcsv(stream, delimiter, enclosure, escape, buf_len, buf, return_value);
HashTable *values = php_fgetcsv(stream, delimiter, enclosure, escape, buf_len, buf);
if (values == NULL) {
values = php_bc_fgetcsv_empty_line();
}
RETURN_ARR(values);
}
/* }}} */

PHPAPI void php_fgetcsv(php_stream *stream, char delimiter, char enclosure, int escape_char, size_t buf_len, char *buf, zval *return_value) /* {{{ */
PHPAPI HashTable *php_bc_fgetcsv_empty_line(void)
{
HashTable *values = zend_new_array(1);
zval tmp;
ZVAL_NULL(&tmp);
zend_hash_next_index_insert(values, &tmp);
return values;
}

PHPAPI HashTable *php_fgetcsv(php_stream *stream, char delimiter, char enclosure, int escape_char, size_t buf_len, char *buf) /* {{{ */
{
char *temp, *bptr, *line_end, *limit;
size_t temp_len, line_end_len;
Expand All @@ -2078,12 +2091,11 @@ PHPAPI void php_fgetcsv(php_stream *stream, char delimiter, char enclosure, int
temp_len = buf_len;
temp = emalloc(temp_len + line_end_len + 1);

/* Initialize return array */
array_init(return_value);
/* Initialize values HashTable */
HashTable *values = zend_new_array(0);

/* Main loop to read CSV fields */
/* NB this routine will return a single null entry for a blank line */

/* NB this routine will return NULL for a blank line */
do {
char *comp_end, *hunk_begin;
char *tptr = temp;
Expand All @@ -2100,7 +2112,8 @@ PHPAPI void php_fgetcsv(php_stream *stream, char delimiter, char enclosure, int
}

if (first_field && bptr == line_end) {
add_next_index_null(return_value);
zend_array_destroy(values);
values = NULL;
break;
}
first_field = false;
Expand Down Expand Up @@ -2298,13 +2311,18 @@ PHPAPI void php_fgetcsv(php_stream *stream, char delimiter, char enclosure, int

/* 3. Now pass our field back to php */
*comp_end = '\0';
add_next_index_stringl(return_value, temp, comp_end - temp);

zval z_tmp;
ZVAL_STRINGL(&z_tmp, temp, comp_end - temp);
zend_hash_next_index_insert(values, &z_tmp);
} while (inc_len > 0);

efree(temp);
if (stream) {
efree(buf);
}

return values;
}
/* }}} */

Expand Down
3 changes: 2 additions & 1 deletion ext/standard/file.h
Expand Up @@ -48,7 +48,8 @@ PHPAPI void php_flock_common(php_stream *stream, zend_long operation, uint32_t o
zval *wouldblock, zval *return_value);

#define PHP_CSV_NO_ESCAPE EOF
PHPAPI void php_fgetcsv(php_stream *stream, char delimiter, char enclosure, int escape_char, size_t buf_len, char *buf, zval *return_value);
PHPAPI HashTable *php_bc_fgetcsv_empty_line(void);
PHPAPI HashTable *php_fgetcsv(php_stream *stream, char delimiter, char enclosure, int escape_char, size_t buf_len, char *buf);
PHPAPI ssize_t php_fputcsv(php_stream *stream, zval *fields, char delimiter, char enclosure, int escape_char, zend_string *eol_str);

#define META_DEF_BUFSIZE 8192
Expand Down
6 changes: 5 additions & 1 deletion ext/standard/string.c
Expand Up @@ -5253,7 +5253,11 @@ PHP_FUNCTION(str_getcsv)
esc = esc_len ? (unsigned char) esc_str[0] : PHP_CSV_NO_ESCAPE;
}

php_fgetcsv(NULL, delim, enc, esc, ZSTR_LEN(str), ZSTR_VAL(str), return_value);
HashTable *values = php_fgetcsv(NULL, delim, enc, esc, ZSTR_LEN(str), ZSTR_VAL(str));
if (values == NULL) {
values = php_bc_fgetcsv_empty_line();
}
RETURN_ARR(values);
}
/* }}} */

Expand Down