dpkg: free results of read_package_field(), preliminary cleanups in read_package_field()
No binary (build failed)
—
(log yok)
| @@ -531,26 +531,31 @@ static void free_package(common_node_t *node) | |
| } | |
| /* | |
| - | * Gets the next package field from package_buffer, separated into the field name |
| - | * and field value, it returns the int offset to the first character of the next field |
| + | * Gets the next package field from package_buffer: |
| + | * "Name:<whitespace>VALUE{\n|NUL}" |
| + | * "Name:<whitespace>\n |
| + | * " VALUE{\n|NUL}" |
| + | * separated into "NAME" and "VALUE", both strdup()ed. |
| + | * Returns the int offset to the first character of the next field. |
| + | * The package_buffer parameter is NUL-terminated. |
| */ | |
| static int read_package_field(const char *package_buffer, char **field_name, char **field_value) | |
| { | |
| int offset_name_start = 0; | |
| int offset_name_end = 0; | |
| int offset_value_start = 0; | |
| - | int offset_value_end = 0; |
| int offset = 0; | |
| int next_offset; | |
| int name_length; | |
| int value_length; | |
| int exit_flag = FALSE; | |
| + | *field_name = NULL; |
| + | *field_value = NULL; |
| if (package_buffer == NULL) { | |
| - | *field_name = NULL; |
| - | *field_value = NULL; |
| return -1; | |
| } | |
| + | |
| while (1) { | |
| next_offset = offset + 1; | |
| switch (package_buffer[offset]) { | |
| @@ -566,14 +571,14 @@ static int read_package_field(const char *package_buffer, char **field_name, cha | |
| * immediately after name */ | |
| break; | |
| case '\n': | |
| - | /* TODO: The char next_offset may be out of bounds */ |
| if (package_buffer[next_offset] != ' ') { | |
| exit_flag = TRUE; | |
| break; | |
| } | |
| + | /* fall through */ |
| case '\t': | |
| case ' ': | |
| - | /* increment the value start point if its a just filler */ |
| + | /* increment start points if it is just a filler */ |
| if (offset_name_start == offset) { | |
| offset_name_start++; | |
| } | |
| @@ -584,9 +589,8 @@ static int read_package_field(const char *package_buffer, char **field_name, cha | |
| } | |
| if (exit_flag) { | |
| /* Check that the names are valid */ | |
| - | offset_value_end = offset; |
| name_length = offset_name_end - offset_name_start; | |
| - | value_length = offset_value_end - offset_value_start; |
| + | value_length = offset - offset_value_start; |
| if (name_length == 0) { | |
| break; | |
| } | |
| @@ -594,27 +598,26 @@ static int read_package_field(const char *package_buffer, char **field_name, cha | |
| break; | |
| } | |
| - | /* If not valid, start fresh with next field */ |
| + | /* Not valid: start fresh with next field */ |
| exit_flag = FALSE; | |
| offset_name_start = offset + 1; | |
| offset_name_end = 0; | |
| offset_value_start = offset + 1; | |
| - | offset_value_end = offset + 1; |
| offset++; | |
| } | |
| offset++; | |
| - | } |
| - | *field_name = NULL; |
| - | if (name_length) { |
| + | } /* while (1) */ |
| + | |
| + | if (name_length > 0) { |
| *field_name = xstrndup(&package_buffer[offset_name_start], name_length); | |
| } | |
| - | *field_value = NULL; |
| if (value_length > 0) { | |
| *field_value = xstrndup(&package_buffer[offset_value_start], value_length); | |
| } | |
| return next_offset; | |
| } | |
| + | /* The parameter is NUL-terminated */ |
| static unsigned fill_package_struct(char *control_buffer) | |
| { | |
| static const char field_names[] ALIGN1 = | |
| @@ -623,14 +626,14 @@ static unsigned fill_package_struct(char *control_buffer) | |
| "Conflicts\0""Suggests\0""Recommends\0""Enhances\0"; | |
| common_node_t *new_node = xzalloc(sizeof(common_node_t)); | |
| - | char *field_name; |
| - | char *field_value; |
| int field_start = 0; | |
| - | int num = -1; |
| int buffer_length = strlen(control_buffer); | |
| + | int num; |
| new_node->version = search_name_hashtable("unknown"); | |
| while (field_start < buffer_length) { | |
| + | char *field_name; |
| + | char *field_value; |
| unsigned field_num; | |
| field_start += read_package_field(&control_buffer[field_start], | |
| @@ -799,7 +802,7 @@ static void write_buffer_no_status(FILE *new_status_file, const char *control_bu | |
| char *name; | |
| char *value; | |
| int start = 0; | |
| - | while (1) { |
| + | while (control_buffer[start]) { |
| start += read_package_field(&control_buffer[start], &name, &value); | |
| if (name == NULL) { | |
| break; | |
| @@ -807,6 +810,8 @@ static void write_buffer_no_status(FILE *new_status_file, const char *control_bu | |
| if (strcmp(name, "Status") != 0) { | |
| fprintf(new_status_file, "%s: %s\n", name, value); | |
| } | |
| + | free(name); |
| + | free(value); |
| } | |
| } | |
| @@ -815,34 +820,35 @@ static void write_status_file(deb_file_t **deb_file) | |
| { | |
| FILE *old_status_file = xfopen_for_read("/var/lib/dpkg/status"); | |
| FILE *new_status_file = xfopen_for_write("/var/lib/dpkg/status.udeb"); | |
| - | char *package_name; |
| - | char *status_from_file; |
| - | char *control_buffer = NULL; |
| - | char *tmp_string; |
| - | int status_num; |
| + | char *control_buffer; |
| int field_start = 0; | |
| - | int write_flag; |
| - | int i = 0; |
| + | int status_num; |
| + | int i; |
| /* Update previously known packages */ | |
| while ((control_buffer = xmalloc_fgetline_str(old_status_file, "\n\n")) != NULL) { | |
| + | char *package_name; |
| + | char *status_from_file; |
| + | char *tmp_string; |
| + | int write_flag; |
| + | //FIXME: "int field_start = 0;" should be _here_, right? |
| + | |
| tmp_string = strstr(control_buffer, "Package:"); | |
| if (tmp_string == NULL) { | |
| + | free(control_buffer); |
| continue; | |
| } | |
| - | |
| tmp_string += 8; | |
| tmp_string += strspn(tmp_string, " \n\t"); | |
| package_name = xstrndup(tmp_string, strcspn(tmp_string, "\n")); | |
| + | |
| write_flag = FALSE; | |
| + | status_from_file = NULL; |
| tmp_string = strstr(control_buffer, "Status:"); | |
| if (tmp_string != NULL) { | |
| - | /* Separate the status value from the control buffer */ |
| tmp_string += 7; | |
| tmp_string += strspn(tmp_string, " \n\t"); | |
| status_from_file = xstrndup(tmp_string, strcspn(tmp_string, "\n")); | |
| - | } else { |
| - | status_from_file = NULL; |
| } | |
| /* Find this package in the status hashtable */ | |
| @@ -870,7 +876,7 @@ static void write_status_file(deb_file_t **deb_file) | |
| } | |
| i++; | |
| } | |
| - | /* This is temperary, debugging only */ |
| + | /* This is temporary, debugging only */ |
| if (deb_file[i] == NULL) { | |
| bb_error_msg_and_die("ALERT: cannot find a control file, " | |
| "your status file may be broken, status may be " | |
| @@ -882,7 +888,7 @@ static void write_status_file(deb_file_t **deb_file) | |
| fprintf(new_status_file, "Package: %s\n", package_name); | |
| fprintf(new_status_file, "Status: %s\n", status_from_hashtable); | |
| - | while (1) { |
| + | while (control_buffer[field_start]) { |
| char *field_name; | |
| char *field_value; | |
| field_start += read_package_field(&control_buffer[field_start], &field_name, &field_value); | |
| @@ -894,13 +900,15 @@ static void write_status_file(deb_file_t **deb_file) | |
| ) { | |
| fprintf(new_status_file, "%s: %s\n", field_name, field_value); | |
| } | |
| + | free(field_name); |
| + | free(field_value); |
| } | |
| write_flag = TRUE; | |
| fputs("\n", new_status_file); | |
| } | |
| else if (strcmp("config-files", name_hashtable[state_status]) == 0) { | |
| /* only change the status line */ | |
| - | while (1) { |
| + | while (control_buffer[field_start]) { |
| char *field_name; | |
| char *field_value; | |
| field_start += read_package_field(&control_buffer[field_start], &field_name, &field_value); | |
| @@ -913,13 +921,15 @@ static void write_status_file(deb_file_t **deb_file) | |
| } else { | |
| fprintf(new_status_file, "%s: %s\n", field_name, field_value); | |
| } | |
| + | free(field_name); |
| + | free(field_value); |
| } | |
| write_flag = TRUE; | |
| fputs("\n", new_status_file); | |
| } | |
| } | |
| } | |
| - | /* If the package from the status file wasn't handle above, do it now*/ |
| + | /* If the package from the status file wasn't handled above, do it now */ |
| if (!write_flag) { | |
| fprintf(new_status_file, "%s\n\n", control_buffer); | |
| } | |
| @@ -927,7 +937,7 @@ static void write_status_file(deb_file_t **deb_file) | |
| free(status_from_file); | |
| free(package_name); | |
| free(control_buffer); | |
| - | } |
| + | } /* while (control_buffer) */ |
| /* Write any new packages */ | |
| for (i = 0; deb_file[i] != NULL; i++) { | |