From ae1daab3dfc262d6aa7c77b085301bc5eab977fc Mon Sep 17 00:00:00 2001 From: William Bell Date: Sat, 4 May 2024 01:11:52 +0100 Subject: [PATCH] fix buffer overflow --- Makefile | 2 +- openFile.c | 11 +- render.c | 4 +- test | 423 ----------------------------------------------------- 4 files changed, 9 insertions(+), 431 deletions(-) delete mode 100644 test diff --git a/Makefile b/Makefile index 2963e06..bed43af 100644 --- a/Makefile +++ b/Makefile @@ -4,7 +4,7 @@ full: build: mkdir -p bin - gcc -o bin/mte *.c -lncurses -Wall -Wextra -Werror -pedantic -std=c99 + gcc -o bin/mte *.c -lncurses -Wall -Wextra -pedantic -std=c99 -Wimplicit-fallthrough=0 clean: rm -rf bin \ No newline at end of file diff --git a/openFile.c b/openFile.c index ea57260..72cfcf0 100644 --- a/openFile.c +++ b/openFile.c @@ -41,6 +41,8 @@ int openFile(char *Path) { char *myMessage = "New File"; message = realloc(message, strlen(myMessage) + 1); + strcpy(message, myMessage); + showMessage = 1; } char *content_COPY = malloc(strlen(content) + 1); strcpy(content_COPY, content); @@ -102,14 +104,14 @@ int openFile(char *Path) { case 10: lineIndent = indent(content, fileData.cursor_y, fileData.cursor_x); - newContent = malloc(strlen(content) + lineIndent + 1); + newContent = malloc(strlen(content) + lineIndent+2); int cursorPos = cursorToCharPos(content, fileData.cursor_x, fileData.cursor_y); strncpy(newContent, content, cursorPos); newContent[cursorPos] = '\n'; for (int i = 0; i < lineIndent; i++) newContent[cursorPos + i + 1] = ' '; strncpy(newContent + cursorPos + lineIndent + 1, content + cursorPos, strlen(content) - cursorPos); - newContent[strlen(content) + cursorPos + lineIndent + 1] = '\0'; + newContent[strlen(content) + lineIndent + 1] = '\0'; free(content); content = newContent; fileData.cursor_y++; @@ -151,7 +153,7 @@ int openFile(char *Path) break; } int length = lineLength(content, fileData.cursor_y - toRemove); - newContent = malloc(strlen(content)); + newContent = malloc(strlen(content)-toRemove + 1); strncpy(newContent, content, cursorPos - toRemove); strncpy(newContent + cursorPos - toRemove, content + cursorPos, strlen(content) - cursorPos); newContent[strlen(content) - toRemove] = '\0'; @@ -167,7 +169,7 @@ int openFile(char *Path) } break; case 9: - newContent = malloc(strlen(content) + tabSize); + newContent = malloc(strlen(content) + tabSize+1); strncpy(newContent, content, cursorToCharPos(content, fileData.cursor_x, fileData.cursor_y)); for (int i = 0; i < tabSize; i++) newContent[cursorToCharPos(content, fileData.cursor_x, fileData.cursor_y) + i] = ' '; @@ -231,7 +233,6 @@ int openFile(char *Path) } break; case '\n': - switch (command[0]) { case 'w': diff --git a/render.c b/render.c index c054d79..a62f996 100644 --- a/render.c +++ b/render.c @@ -23,7 +23,7 @@ void render(struct FileData fileData) mvprintw(0, 0, "%s - %s\n", programName, *fileData.path); // Display content - char *line = malloc(1); + char *line = malloc(12); sprintf(line, "%d", fileData.numLines); int widthOfLineNumText = strlen(line) + 1; if (widthOfLineNumText < 4) @@ -68,7 +68,7 @@ void render(struct FileData fileData) { move(contentBeginY + LineNum - fileData.scroll - 1, 0); } - char *line = malloc(1); + char *line = malloc(12); lineLength = 0; sprintf(line, "%d", LineNum); int linelen = strlen(line); diff --git a/test b/test deleted file mode 100644 index ea57260..0000000 --- a/test +++ /dev/null @@ -1,423 +0,0 @@ -#include "openFile.h" -#include "config.h" -#include "render.h" -#include "cursorMovement.h" -#include "lengths.h" - -#include -#include -#include -#include -#include -#include - -int openFile(char *Path) -{ - char *path = malloc((sizeof(Path) / sizeof(char *)) + 1); - char *message = malloc(1); - message[0] = '\0'; - int showMessage = 0; - strcpy(path, Path); - ESCDELAY = 0; - char *content = malloc(1); - content[0] = '\0'; - - if (strlen(path) != 0) - { - FILE *fptr = fopen(path, "r"); - if (fptr != NULL) - { - // Read the contents of the file into the content variable - fseek(fptr, 0, SEEK_END); - long fsize = ftell(fptr); - fseek(fptr, 0, SEEK_SET); - content = realloc(content, fsize + 1); - fread(content, 1, fsize, fptr); - content[fsize] = 0; - fclose(fptr); - } - } - else - { - char *myMessage = "New File"; - message = realloc(message, strlen(myMessage) + 1); - } - char *content_COPY = malloc(strlen(content) + 1); - strcpy(content_COPY, content); - // path = malloc(100); - int mode = 0; - char *command = malloc(1); - command[0] = '\0'; - - struct FileData fileData = {&path, &content, &command, &mode, &message, &showMessage, 0, 0, 0, 0, 0}; - - setlocale(LC_ALL, ""); - initscr(); - cbreak(); - keypad(stdscr, TRUE); - - struct lineAndCharNum lineAndCharNum = getLineAndCharNum(content); - fileData.numLines = lineAndCharNum.lineNum; - fileData.numChars = lineAndCharNum.charNum; - render(fileData); - - int across = 0; - - int choice; - char *newContent; - char *myMessage; - int lineIndent; - int running = 1; - while (1) - { - choice = getch(); // Get user input - int isPrintable = isprint(choice); - if (isPrintable) - showMessage = 0; - // sprintf(path, "%s, %02X", path, choice); - int stop = 0; - if (mode != 2) - { - cursorMovement(choice, &fileData, &content, &across, &stop); - } - if (!stop) - { - switch (mode) - { - case 0: - switch (choice) - { - case ':': - mode = 2; - break; - case 'i': - mode = 1; - break; - default: - break; - } - break; - case 1: - switch (choice) - { - case 10: - lineIndent = indent(content, fileData.cursor_y, fileData.cursor_x); - newContent = malloc(strlen(content) + lineIndent + 1); - int cursorPos = cursorToCharPos(content, fileData.cursor_x, fileData.cursor_y); - strncpy(newContent, content, cursorPos); - newContent[cursorPos] = '\n'; - for (int i = 0; i < lineIndent; i++) - newContent[cursorPos + i + 1] = ' '; - strncpy(newContent + cursorPos + lineIndent + 1, content + cursorPos, strlen(content) - cursorPos); - newContent[strlen(content) + cursorPos + lineIndent + 1] = '\0'; - free(content); - content = newContent; - fileData.cursor_y++; - fileData.cursor_x = lineIndent; - across = 0; - break; - case 27: - mode = 0; - break; - case KEY_BACKSPACE: - case 0x7F: - if (strlen(content) > 0) - { - int toRemove = 1; - - int lineIndent = indent(content, fileData.cursor_y, fileData.cursor_x); - if (lineIndent == fileData.cursor_x) - { - int inTab = lineIndent % tabSize; - if (inTab == 0) - { - toRemove = tabSize; - } - else - { - toRemove = inTab; - } - } - - if (fileData.cursor_x < toRemove) - toRemove = fileData.cursor_x; - - if (toRemove < 1) - toRemove = 1; - - int cursorPos = cursorToCharPos(content, fileData.cursor_x, fileData.cursor_y); - if (cursorPos == 0) - { - break; - } - int length = lineLength(content, fileData.cursor_y - toRemove); - newContent = malloc(strlen(content)); - strncpy(newContent, content, cursorPos - toRemove); - strncpy(newContent + cursorPos - toRemove, content + cursorPos, strlen(content) - cursorPos); - newContent[strlen(content) - toRemove] = '\0'; - free(content); - content = newContent; - fileData.cursor_x -= toRemove; - if (fileData.cursor_x < 0 && fileData.cursor_y > 0) - { - fileData.cursor_y--; - fileData.cursor_x = length; - } - across = fileData.cursor_x; - } - break; - case 9: - newContent = malloc(strlen(content) + tabSize); - strncpy(newContent, content, cursorToCharPos(content, fileData.cursor_x, fileData.cursor_y)); - for (int i = 0; i < tabSize; i++) - newContent[cursorToCharPos(content, fileData.cursor_x, fileData.cursor_y) + i] = ' '; - strncpy(newContent + cursorToCharPos(content, fileData.cursor_x, fileData.cursor_y) + tabSize, content + cursorToCharPos(content, fileData.cursor_x, fileData.cursor_y), strlen(content) - cursorToCharPos(content, fileData.cursor_x, fileData.cursor_y)); - newContent[strlen(content) + tabSize] = '\0'; - free(content); - content = newContent; - fileData.cursor_x += tabSize; - across = fileData.cursor_x; - break; - case 0x17: - case KEY_DC: - if (strlen(content) > 0) - { - int cursorPos = cursorToCharPos(content, fileData.cursor_x, fileData.cursor_y); - if (cursorPos == (int)strlen(content)) - { - break; - } - newContent = malloc(strlen(content)); - strncpy(newContent, content, cursorPos); - strncpy(newContent + cursorPos, content + cursorPos + 1, strlen(content) - cursorPos); - newContent[strlen(content) - 1] = '\0'; - free(content); - content = newContent; - across = fileData.cursor_x; - } - break; - default: - if (isPrintable) - { - int cursorPos = cursorToCharPos(content, fileData.cursor_x, fileData.cursor_y); - newContent = malloc(strlen(content) + 2); - strncpy(newContent, content, cursorPos); - newContent[cursorPos] = choice; - strncpy(newContent + cursorPos + 1, content + cursorPos, strlen(content) - cursorPos); - newContent[strlen(content) + 1] = '\0'; - free(content); - content = newContent; - fileData.cursor_x++; - across = fileData.cursor_x; - } - break; - } - break; - case 2: - switch (choice) - { - case 27: - mode = 0; - break; - case KEY_BACKSPACE: - case 0x7F: - if (strlen(command) > 0) - { - char *newCommand = malloc(strlen(command)); - strncpy(newCommand, command, strlen(command) - 1); - newCommand[strlen(command) - 1] = '\0'; - free(command); - command = newCommand; - } - break; - case '\n': - - switch (command[0]) - { - case 'w': - if (strlen(path) != 0) - { - FILE *fptr; - fptr = fopen(path, "w"); - if (fptr != NULL) - { - fwrite(content, 1, strlen(content), fptr); - fclose(fptr); - content_COPY = realloc(content_COPY, strlen(content) + 1); - strcpy(content_COPY, content); - } - } - if (strlen(command) == 1 || command[1] != 'q') - break; - case 'q': - if ((strlen(content) != 0 && strcmp(content, content_COPY) != 0) && (strlen(command) == 1 || command[1] != '!')) - { - char *myMessage = "No write since last change (add ! to override)"; - message = realloc(message, strlen(myMessage) + 1); - strcpy(message, myMessage); - showMessage = 1; - break; - } - running = 0; - break; - case 's': - if (strlen(command) > 2) - { - path = realloc(path, strlen(command) - 2); - strncpy(path, command + 2, strlen(command) - 2); - path[strlen(command) - 2] = '\0'; - FILE *fptr; - fptr = fopen(path, "w"); - if (fptr != NULL) - { - fwrite(content, 1, strlen(content), fptr); - fclose(fptr); - content_COPY = realloc(content_COPY, strlen(content) + 1); - strcpy(content_COPY, content); - } - } - else - { - char *myMessage = "No path specified"; - message = realloc(message, strlen(myMessage) + 1); - strcpy(message, myMessage); - showMessage = 1; - } - break; - case 'o': - if (strlen(command) > 2) - { - char *newPath = malloc(strlen(command) - 2); - strncpy(newPath, command + 2, strlen(command) - 2); - newPath[strlen(command) - 2] = '\0'; - FILE *fptr; - fptr = fopen(newPath, "r"); - if (fptr != NULL) - { - // Read the contents of the file into the content variable - fseek(fptr, 0, SEEK_END); - long fsize = ftell(fptr); - fseek(fptr, 0, SEEK_SET); - content = realloc(content, fsize + 1); - fread(content, 1, fsize, fptr); - content[fsize] = 0; - fclose(fptr); - free(path); - path = newPath; - } - else - { - content = realloc(content, 1); - content[0] = '\0'; - } - fileData = (struct FileData){&path, &content, &command, &mode, &message, &showMessage, 0, 0, 0, 0, 0}; - } - else - { - char *myMessage = "No path specified"; - message = realloc(message, strlen(myMessage) + 1); - strcpy(message, myMessage); - showMessage = 1; - } - break; - case 'l': - if (strlen(command) > 2) - { - char *line = malloc(strlen(command) - 2); - strncpy(line, command + 2, strlen(command) - 2); - line[strlen(command) - 2] = '\0'; - int lineNum = atoi(line); - if (lineNum < 0) - { - if (fileData.numLines + lineNum < 0) - { - lineNum = 0; - } - else - { - lineNum = fileData.numLines + lineNum; - } - } - int numLines = 0; - int numChars = strlen(content); - int i; - for (i = 0; i < numChars; i++) - { - if (content[i] == '\n') - { - numLines++; - if (numLines == lineNum) - { - break; - } - } - } - fileData.cursor_y = numLines; - fileData.cursor_x = 0; - } - else - { - char *myMessage = "No line specified"; - message = realloc(message, strlen(myMessage) + 1); - strcpy(message, myMessage); - showMessage = 1; - } - break; - default: - myMessage = "Invalid command"; - message = realloc(message, strlen(myMessage) + 1); - strcpy(message, myMessage); - showMessage = 1; - break; - } - - command = realloc(command, 1); - command[0] = '\0'; - mode = 0; - break; - default: - if (isPrintable) - { - int length = strlen(command); - char *newCommand = malloc(length + 2); - strncpy(newCommand, command, length); - newCommand[length] = choice; - newCommand[length + 1] = '\0'; - free(command); - command = newCommand; - } - break; - } - break; - default: - break; - } - } - if (!running) - { - break; - } - if (fileData.cursor_y < fileData.scroll) - { - fileData.scroll = fileData.cursor_y; - } - if (fileData.cursor_y - (LINES - 4) >= fileData.scroll) - { - fileData.scroll = fileData.cursor_y - (LINES - 4) + 1; - } - lineAndCharNum = getLineAndCharNum(content); - fileData.numLines = lineAndCharNum.lineNum; - fileData.numChars = lineAndCharNum.charNum; - render(fileData); // Re-render the menu - } - - free(content); - free(command); - free(content_COPY); - free(path); - free(message); - // Clean up and exit ncurses - endwin(); - - return 0; -}