Skip to content

Commit

Permalink
Merge pull request #7 from kurrrru/6-gnlを追加する
Browse files Browse the repository at this point in the history
gnlwo
  • Loading branch information
mmiyahar1205 authored Dec 11, 2024
2 parents 32e6afb + 6da9794 commit 43d0eac
Show file tree
Hide file tree
Showing 5 changed files with 210 additions and 1 deletion.
3 changes: 2 additions & 1 deletion libft/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,8 @@ SRCS = ft_atoi.c ft_memchr.c ft_split.c ft_strncmp.c \
ft_isascii.c ft_putchar_fd.c ft_strlcat.c ft_tolower.c \
ft_isdigit.c ft_putendl_fd.c ft_strlcpy.c ft_toupper.c \
ft_isprint.c ft_putnbr_fd.c ft_strlen.c \
ft_itoa.c ft_putstr_fd.c ft_strmapi.c
ft_itoa.c ft_putstr_fd.c ft_strmapi.c \
get_next_line.c get_next_line_utils.c
BONUS_SRCS = ft_lstadd_back_bonus.c ft_lstlast_bonus.c \
ft_lstadd_front_bonus.c ft_lstmap_bonus.c \
ft_lstclear_bonus.c ft_lstnew_bonus.c \
Expand Down
47 changes: 47 additions & 0 deletions libft/get_next_line.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
/* ************************************************************************** */
/* */
/* ::: :::::::: */
/* get_next_line.c :+: :+: :+: */
/* +:+ +:+ +:+ */
/* By: nkawaguc <[email protected]> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2024/05/03 20:02:39 by nkawaguc #+# #+# */
/* Updated: 2024/06/28 00:35:41 by nkawaguc ### ########.fr */
/* */
/* ************************************************************************** */

#include "get_next_line.h"

// get_next_line: read a line from a file descriptor
// If fd is invalid or BUFFER_SIZE is invalid, return NULL.
// If buf is not initialized, initialize it with buf_init.
// Allocate a line buffer and initialize it with '\0'.
// Read until a newline character is found or EOF is reached with gnl_read.
// return: a line read from the file descriptor
char *get_next_line(int fd)
{
static char *buf = NULL;
char *line;
int line_size;
int flag;

if (fd < 0 || BUFFER_SIZE <= 0 || buf_init(&buf) == -1)
return (NULL);
line_size = BUFFER_SIZE + 1;
line = (char *)malloc(line_size * sizeof(char));
if (!line)
return (free(buf), gnl_bzero(&buf, sizeof(char *)), NULL);
gnl_bzero(line, line_size);
flag = gnl_read(fd, &line, &line_size, buf);
if (flag == -1 || flag == 0)
{
free(buf);
gnl_bzero(&buf, sizeof(char *));
if (flag == -1 || line[0] == '\0')
return (free(line), NULL);
}
line = gnl_realloc(line, 0, line_size);
if (line == NULL)
return (free(buf), gnl_bzero(&buf, sizeof(char *)), NULL);
return (line);
}
33 changes: 33 additions & 0 deletions libft/get_next_line.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
/* ************************************************************************** */
/* */
/* ::: :::::::: */
/* get_next_line.h :+: :+: :+: */
/* +:+ +:+ +:+ */
/* By: nkawaguc <[email protected]> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2024/05/03 20:02:43 by nkawaguc #+# #+# */
/* Updated: 2024/06/28 00:35:31 by nkawaguc ### ########.fr */
/* */
/* ************************************************************************** */

#ifndef GET_NEXT_LINE_H
# define GET_NEXT_LINE_H

# include <unistd.h>
# include <stdlib.h>
# include <limits.h>

# ifndef BUFFER_SIZE
# define BUFFER_SIZE 1024
# endif

// # define DEBUG

char *get_next_line(int fd);
int buf_init(char **buf);
void *gnl_realloc(void *ptr, size_t new_size, size_t old_size);
int gnl_strncat(char **dst, const char *src, int *line_size, int *cat_size);
int gnl_read(int fd, char **line, int *line_size, char *buf);
void gnl_bzero(void *buf, size_t size);

#endif
127 changes: 127 additions & 0 deletions libft/get_next_line_utils.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,127 @@
/* ************************************************************************** */
/* */
/* ::: :::::::: */
/* get_next_line_utils.c :+: :+: :+: */
/* +:+ +:+ +:+ */
/* By: nkawaguc <[email protected]> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2024/05/03 20:02:34 by nkawaguc #+# #+# */
/* Updated: 2024/06/28 00:25:18 by nkawaguc ### ########.fr */
/* */
/* ************************************************************************** */

#include "get_next_line.h"

// buf_init: Initialize buf if it is not initialized.
// After memory allocation, initialize the memory with '\0'.
// Return: whether the initialization is successful. (1: success, -1: error)
int buf_init(char **buf)
{
if (*buf)
return (1);
*buf = (char *)malloc((BUFFER_SIZE + 1) * sizeof(char));
if (*buf == NULL)
return (-1);
gnl_bzero(*buf, BUFFER_SIZE + 1);
return (1);
}

// gnl_realloc: Reallocate memory with new_size.
// If the reallocation fails, free the original pointer and return NULL.
// If the reallocation succeeds, copy the original data to the new pointer.
// Return: the new pointer.
void *gnl_realloc(void *ptr, size_t new_size, size_t old_size)
{
void *new_ptr;
size_t i;

if (new_size == 0)
while (new_size == 0 || ((char *)ptr)[new_size - 1])
new_size++;
new_ptr = malloc(new_size);
if (new_ptr == NULL)
return (free(ptr), NULL);
i = 0;
while (i < old_size && i < new_size)
{
((char *)new_ptr)[i] = ((char *)ptr)[i];
i++;
}
free(ptr);
return (new_ptr);
}

// gnl_strncat: Concatenate src to dst.
// If the new_size of dst is not enough, it is reallocated in gnl_realloc.
// The size of the concatenated string of src is stored in cat_size.
// Return: the size of the concatenated string of src.
int gnl_strncat(char **dst, const char *src, int *line_size, int *cat_size)
{
int i;
int j;

i = -1;
while ((*dst)[++i])
;
j = 0;
while (src[j] && (j == 0 || src[j - 1] != '\n'))
{
if (i + j + 1 >= *line_size)
{
*dst = gnl_realloc(*dst, *line_size * 2, *line_size);
if (*dst == NULL)
{
*cat_size = -1;
return (-1);
}
*line_size *= 2;
}
(*dst)[i + j] = src[j];
j++;
}
(*dst)[i + j] = '\0';
*cat_size = j;
return (j);
}

// gnl_bzero: Initialize buf with '\0'.
// Return: None
void gnl_bzero(void *buf, size_t size)
{
while (size)
((char *)buf)[--size] = '\0';
}

// gnl_read: Read from fd to buf and concatenate buf to line.
// If line is not empty, concatenate buf to line.
// If '\n' is not found in buf, read until '\n' is found or EOF is reached.
// Move the characters after first '\n' to the beginning of buf.
// Return: whether the reading is successful. (1: success, 0: EOF, -1: error)
int gnl_read(int fd, char **line, int *line_size, char *buf)
{
int read_size;
int cat_size;
int i;

cat_size = 0;
if (line[0] && gnl_strncat(line, buf, line_size, &cat_size) == -1)
return (-1);
if (!buf[cat_size] && (cat_size == 0 || buf[cat_size - 1] != '\n'))
{
while (1)
{
read_size = read(fd, buf, BUFFER_SIZE);
if (read_size == -1 || read_size == 0)
return (read_size);
buf[read_size] = '\0';
if (gnl_strncat(line, buf, line_size, &cat_size) <= 0)
return (cat_size);
if (buf[cat_size - 1] == '\n')
break ;
}
}
i = -1;
while (++i <= BUFFER_SIZE - cat_size)
buf[i] = buf[cat_size + i];
return (1);
}
1 change: 1 addition & 0 deletions libft/libft.h
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
# include <unistd.h>
# include <limits.h>
# include <stdint.h>
# include "get_next_line.h"

// libc functions
int ft_atoi(const char *str);
Expand Down

0 comments on commit 43d0eac

Please sign in to comment.