fix: leaks shouldnt happen anymore

This commit is contained in:
lisk77 2025-11-24 23:52:51 +01:00
parent bb1e99406f
commit 136fac9243
3 changed files with 115 additions and 151 deletions

View file

@ -76,50 +76,70 @@ int diff(char* file1_path, char* file2_path) {
if (!file2) exit(1); if (!file2) exit(1);
ActionList* actions = myers_diff(file1, file2, 0, 0); ActionList* actions = myers_diff(file1, file2, 0, 0);
if (!actions) printf("ERROR: something went wrong while taking the diff!"); if (!actions) {
else visualize_diff(file1, file2, actions); printf("ERROR: something went wrong while taking the diff!");
free_file(file1);
free_file(file2);
return 1;
} else {
visualize_diff(file1, file2, actions);
}
free_action_list(actions);
free_file(file1);
free_file(file2);
return 1; return 1;
} }
int status() { int status() {
FileInfoBuffer* files = file_info_buffer_new(); int ret = 1;
FileInfoBuffer* files = NULL;
char* root = NULL;
char* branch = NULL;
CommitLog* log = NULL;
BaseFileBuffer* tracked_list = NULL;
StringBuffer* modified_files = NULL;
StringBuffer* deleted_files = NULL;
StringBuffer* untracked_files = NULL;
Changes* changes = NULL;
files = file_info_buffer_new();
if (!files) goto cleanup;
char relative[PATH_MAX] = ""; char relative[PATH_MAX] = "";
char* root = find_root(relative); root = find_root(relative);
if (!root) { if (!root) goto cleanup;
list_free(files);
return 1;
}
walk(root, relative, relative, files, 0, root); walk(root, relative, relative, files, 0, root);
file_info_buffer_sort(files); file_info_buffer_sort(files);
char branch_path[PATH_MAX]; char branch_path[PATH_MAX];
snprintf(branch_path, sizeof(branch_path), "%s/.merk/BRANCH", root); snprintf(branch_path, sizeof(branch_path), "%s/.merk/BRANCH", root);
char* branch = get_file_content(branch_path); branch = get_file_content(branch_path);
if (!branch) goto cleanup;
char info_path[PATH_MAX]; char info_path[PATH_MAX];
snprintf(info_path, sizeof(info_path), "%s/.merk/info/%s", root, branch); snprintf(info_path, sizeof(info_path), "%s/.merk/info/%s", root, branch);
char log_path[PATH_MAX]; char log_path[PATH_MAX];
snprintf(log_path, sizeof(log_path), "%s/.merk/logs/branches/%s", root, branch); snprintf(log_path, sizeof(log_path), "%s/.merk/logs/branches/%s", root, branch);
CommitLog* log = commit_log_new(); log = commit_log_new();
if (!log) goto cleanup;
read_commit_log(log, log_path); read_commit_log(log, log_path);
char* last_tree_hash = NULL;
if (log->len != 0) {
last_tree_hash = ((Commit*)log->items + (log->len))->tree_hash;
}
BaseFileBuffer* tracked_list = base_file_buffer_new(); tracked_list = base_file_buffer_new();
if (!tracked_list) goto cleanup;
read_base_file_list(tracked_list, info_path); read_base_file_list(tracked_list, info_path);
StringBuffer* modified_files = string_buffer_new(); modified_files = string_buffer_new();
StringBuffer* deleted_files = string_buffer_new(); deleted_files = string_buffer_new();
StringBuffer* untracked_files = string_buffer_new(); untracked_files = string_buffer_new();
if (!modified_files || !deleted_files || !untracked_files) goto cleanup;
Changes* changes = calloc(1, sizeof(Changes)); changes = calloc(1, sizeof(Changes));
if (!changes) { if (!changes) {
printf("ERROR: unable to allocate memory for changes!\n"); printf("ERROR: unable to allocate memory for changes!\n");
return 1; goto cleanup;
} }
changes->insertions = 0; changes->insertions = 0;
@ -142,13 +162,14 @@ int status() {
File* basefile = parse_object(base_file_hash, BaseFileObject, NULL, NULL); File* basefile = parse_object(base_file_hash, BaseFileObject, NULL, NULL);
if (!basefile) { if (!basefile) {
printf("ERROR: unable to parse base file %s!\n", file_name); printf("ERROR: unable to parse base file %s!\n", file_name);
return 1; goto cleanup;
} }
File* modified_file = new_file(file_name); File* modified_file = new_file(file_name);
if (!modified_file) { if (!modified_file) {
printf("ERROR: unable to read modified file %s!\n", file_name); printf("ERROR: unable to read modified file %s!\n", file_name);
return 1; free_file(basefile);
goto cleanup;
} }
File* comparison_file = basefile; File* comparison_file = basefile;
@ -173,7 +194,10 @@ int status() {
ActionList* diff = myers_diff(comparison_file, modified_file, 0, 0); ActionList* diff = myers_diff(comparison_file, modified_file, 0, 0);
if (!diff) { if (!diff) {
printf("ERROR: unable to compute diff for file %s!\n", file_name); printf("ERROR: unable to compute diff for file %s!\n", file_name);
return 1; free_file(modified_file);
if (comparison_file != basefile) free_file(comparison_file);
free_file(basefile);
goto cleanup;
} }
if (diff->len != 0) { if (diff->len != 0) {
@ -219,9 +243,19 @@ int status() {
printf("\n\x1b[32;1m%d+\x1b[0m \x1b[31;1m%d-\x1b[0m on branch \x1b[39;1;4m%s\x1b[0m with %lu commits\n", changes->insertions, changes->deletions, branch, log->len); printf("\n\x1b[32;1m%d+\x1b[0m \x1b[31;1m%d-\x1b[0m on branch \x1b[39;1;4m%s\x1b[0m with %lu commits\n", changes->insertions, changes->deletions, branch, log->len);
ret = 1;
cleanup:
if (modified_files) list_free(modified_files);
if (deleted_files) list_free(deleted_files);
if (untracked_files) list_free(untracked_files);
if (tracked_list) base_file_buffer_free(tracked_list);
if (log) commit_log_free(log);
file_info_buffer_free(files); file_info_buffer_free(files);
free(branch);
free(root); free(root);
return 1; free(changes);
return ret;
} }
int commit(int argc, char** argv) { int commit(int argc, char** argv) {
@ -385,6 +419,15 @@ int commit(int argc, char** argv) {
} }
FlatMap* file_hash_map = flat_map_new(); FlatMap* file_hash_map = flat_map_new();
if (!file_hash_map) {
free(commit_message);
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
return 1;
}
Changes* changes = calloc(1, sizeof(Changes)); Changes* changes = calloc(1, sizeof(Changes));
if (!changes) { if (!changes) {
free(commit_message); free(commit_message);
@ -393,6 +436,7 @@ int commit(int argc, char** argv) {
free(branch); free(branch);
free(root); free(root);
free_config(&config); free_config(&config);
flat_map_free(file_hash_map);
return 1; return 1;
} }
@ -408,16 +452,10 @@ int commit(int argc, char** argv) {
// Compress the files content and put it into the object database // Compress the files content and put it into the object database
File* modified_file = new_file(files->items[idx]); File* modified_file = new_file(files->items[idx]);
if (!modified_file) { if (!modified_file) {
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
free(changes);
return 1;
} }
changes->insertions += modified_file->lines; changes->insertions += modified_file->lines;
free_file(modified_file);
char file_hash[41]; char file_hash[41];
snapshot_file(files->items[idx], root, 0, branch, file_hash); snapshot_file(files->items[idx], root, 0, branch, file_hash);
@ -431,41 +469,20 @@ int commit(int argc, char** argv) {
object_hash(BaseFileObject, id, base_file_hash); object_hash(BaseFileObject, id, base_file_hash);
File* basefile = parse_object(base_file_hash, BaseFileObject, NULL, NULL); File* basefile = parse_object(base_file_hash, BaseFileObject, NULL, NULL);
if (!basefile) { if (!basefile) {
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
free(changes);
return 1;
} }
File* modified_file = new_file(files->items[idx]); File* modified_file = new_file(files->items[idx]);
if (!modified_file) { if (!modified_file) {
free_file(basefile); free_file(basefile);
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
free(changes);
return 1;
} }
ActionList* diff = myers_diff(basefile, modified_file, 0, 0); ActionList* diff = myers_diff(basefile, modified_file, 0, 0);
if (!diff) { if (!diff) {
free_file(basefile); free_file(basefile);
free_file(modified_file); free_file(modified_file);
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
free(changes);
return 1;
} }
if (base_file->diff_num == 0) { if (base_file->diff_num == 0) {
@ -491,14 +508,7 @@ int commit(int argc, char** argv) {
free_action_list(diff); free_action_list(diff);
free_file(modified_file); free_file(modified_file);
free_file(basefile); free_file(basefile);
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
free(changes);
return 1;
} }
File* last_version = apply_diff(basefile, last_diff); File* last_version = apply_diff(basefile, last_diff);
@ -507,14 +517,7 @@ int commit(int argc, char** argv) {
free_action_list(diff); free_action_list(diff);
free_file(modified_file); free_file(modified_file);
free_file(basefile); free_file(basefile);
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
free(changes);
return 1;
} }
ActionList* modified_diff = myers_diff(last_version, modified_file, 0, 0); ActionList* modified_diff = myers_diff(last_version, modified_file, 0, 0);
@ -523,14 +526,7 @@ int commit(int argc, char** argv) {
free_action_list(diff); free_action_list(diff);
free_file(modified_file); free_file(modified_file);
free_file(basefile); free_file(basefile);
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
free(changes);
return 1;
} }
for (size_t idx = 0; idx < modified_diff->len; idx++) { for (size_t idx = 0; idx < modified_diff->len; idx++) {
@ -568,14 +564,7 @@ int commit(int argc, char** argv) {
free_action_list(diff); free_action_list(diff);
free_file(modified_file); free_file(modified_file);
free_file(basefile); free_file(basefile);
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
free(changes);
return 1;
} }
snprintf(id, id_len, "%s %zu %s", (char*)files->items[idx], base_file->diff_num, branch); snprintf(id, id_len, "%s %zu %s", (char*)files->items[idx], base_file->diff_num, branch);
@ -598,13 +587,7 @@ int commit(int argc, char** argv) {
write_base_file_list(base_files, info_path); write_base_file_list(base_files, info_path);
FileInfoBuffer* tree = basefilebuffer_to_fileinfobuffer(base_files); FileInfoBuffer* tree = basefilebuffer_to_fileinfobuffer(base_files);
if (!tree) { if (!tree) {
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
return 1;
} }
for (size_t idx = 0; idx < tree->len; idx++) { for (size_t idx = 0; idx < tree->len; idx++) {
@ -622,13 +605,7 @@ int commit(int argc, char** argv) {
if (!log) { if (!log) {
file_info_buffer_free(tree); file_info_buffer_free(tree);
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
return 1;
} }
read_commit_log(log, log_path); read_commit_log(log, log_path);
@ -662,13 +639,7 @@ int commit(int argc, char** argv) {
free(authors[0].timestamp); free(authors[0].timestamp);
free(authors); free(authors);
file_info_buffer_free(tree); file_info_buffer_free(tree);
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
return 1;
} }
char commit_hash_content[4096]; char commit_hash_content[4096];
@ -683,13 +654,7 @@ int commit(int argc, char** argv) {
free(authors[0].email); free(authors[0].email);
free(authors[0].timestamp); free(authors[0].timestamp);
free(authors); free(authors);
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
return 1;
} }
offset += written; offset += written;
@ -702,13 +667,7 @@ int commit(int argc, char** argv) {
free(authors[0].email); free(authors[0].email);
free(authors[0].timestamp); free(authors[0].timestamp);
free(authors); free(authors);
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
return 1;
} }
offset += written; offset += written;
} }
@ -721,13 +680,7 @@ int commit(int argc, char** argv) {
free(authors[0].email); free(authors[0].email);
free(authors[0].timestamp); free(authors[0].timestamp);
free(authors); free(authors);
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
return 1;
} }
offset += written; offset += written;
@ -739,13 +692,7 @@ int commit(int argc, char** argv) {
free(authors[0].email); free(authors[0].email);
free(authors[0].timestamp); free(authors[0].timestamp);
free(authors); free(authors);
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
return 1;
} }
offset += written; offset += written;
@ -757,13 +704,7 @@ int commit(int argc, char** argv) {
free(authors[0].email); free(authors[0].email);
free(authors[0].timestamp); free(authors[0].timestamp);
free(authors); free(authors);
free(commit_message); goto commit_cleanup;
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
return 1;
} }
offset += written; offset += written;
@ -783,13 +724,11 @@ int commit(int argc, char** argv) {
if (!write_commit_log(log, log_path)) { if (!write_commit_log(log, log_path)) {
commit_log_free(log); commit_log_free(log);
file_info_buffer_free(tree); file_info_buffer_free(tree);
free(commit_message); free(authors[0].name);
list_free(files); free(authors[0].email);
base_file_buffer_free(base_files); free(authors[0].timestamp);
free(branch); free(authors);
free(root); goto commit_cleanup;
free_config(&config);
return 1;
} }
commit_log_free(log); commit_log_free(log);
@ -814,8 +753,21 @@ int commit(int argc, char** argv) {
free(branch); free(branch);
free(root); free(root);
free_config(&config); free_config(&config);
flat_map_free(file_hash_map);
free(commit_message); free(commit_message);
free(changes);
return 1; return 1;
commit_cleanup:
free(commit_message);
list_free(files);
base_file_buffer_free(base_files);
free(branch);
free(root);
free_config(&config);
flat_map_free(file_hash_map);
free(changes);
return 1;
} }
int commit_log() { int commit_log() {

View file

@ -305,6 +305,11 @@ int file_info_buffer_push(FileInfoBuffer* buffer, FileInfo info) {
void file_info_buffer_free(List* buffer) { void file_info_buffer_free(List* buffer) {
if (buffer) { if (buffer) {
for (size_t i = 0; i < buffer->len; i++) {
FileInfo* info = (FileInfo*)buffer->items + i;
free(info->name);
free(info->hash);
}
free(buffer->items); free(buffer->items);
free(buffer); free(buffer);
} }

View file

@ -15,6 +15,7 @@ char* get_object(char* hash, size_t* size_out) {
unsigned char* compressed_data = (unsigned char*)get_file_content_with_size(file_path, &compressed_size); unsigned char* compressed_data = (unsigned char*)get_file_content_with_size(file_path, &compressed_size);
if (!compressed_data || compressed_size == 0) { if (!compressed_data || compressed_size == 0) {
free(compressed_data); free(compressed_data);
free(root);
return NULL; return NULL;
} }
@ -27,12 +28,14 @@ char* get_object(char* hash, size_t* size_out) {
if (idx == 0) { if (idx == 0) {
perror("ERROR: no length found at start of object!"); perror("ERROR: no length found at start of object!");
free(compressed_data); free(compressed_data);
free(root);
return NULL; return NULL;
} }
char* size_str = calloc(idx + 1, sizeof(char)); char* size_str = calloc(idx + 1, sizeof(char));
if (!size_str) { if (!size_str) {
free(compressed_data); free(compressed_data);
free(root);
return NULL; return NULL;
} }
@ -45,6 +48,7 @@ char* get_object(char* hash, size_t* size_out) {
perror("ERROR: invalid length in get_object!"); perror("ERROR: invalid length in get_object!");
free(size_str); free(size_str);
free(compressed_data); free(compressed_data);
free(root);
return NULL; return NULL;
} }
free(size_str); free(size_str);
@ -56,6 +60,7 @@ char* get_object(char* hash, size_t* size_out) {
char* decompressed = malloc(original_size + 1); char* decompressed = malloc(original_size + 1);
if (!decompressed) { if (!decompressed) {
free(compressed_data); free(compressed_data);
free(root);
return NULL; return NULL;
} }
uLongf decompressed_size = original_size; uLongf decompressed_size = original_size;
@ -64,10 +69,12 @@ char* get_object(char* hash, size_t* size_out) {
perror("ERROR: decompression failed in get_object!"); perror("ERROR: decompression failed in get_object!");
free(decompressed); free(decompressed);
free(compressed_data); free(compressed_data);
free(root);
return NULL; return NULL;
} }
free(compressed_data); free(compressed_data);
free(root);
decompressed[decompressed_size] = '\0'; decompressed[decompressed_size] = '\0';
if (size_out) { if (size_out) {