Ir para o conteúdo

ggets

O gets() é uma função manhosa, devido ao possível buffer overflow. Esta implementação aloca dinamicamente a linha lida, deixando de haver esse problema. Não se esquecam de libertar (free()) a linha depois de a processarem.

ggets.h:

/*
 *  GPL
 *
 *  Written by Diogo Sousa aka orium
 *  Copyright (C) 2006,2007,2008 Diogo Sousa
 *
 *  This program is free software: you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation, either version 3 of the License, or
 *  (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License
 *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */

#ifndef GGETS_H_
#define GGETS_H_

#include <stdio.h>

enum gget_status {
        GGETS_OK,
        GGETS_NOMEM,
        GGETS_EOF=EOF
};

#define ggets(str) fggets(str,stdin)

extern int fggets(char **, FILE *);

#endif

ggets.c:

/*
 *  GPL
 *
 *  Written by Diogo Sousa aka orium
 *  Copyright (C) 2006,2007,2008 Diogo Sousa
 *
 *  This program is free software: you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation, either version 3 of the License, or
 *  (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License
 *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */

#include <stdio.h>
#include <stdlib.h>

#define GGETS_INIT_SIZE 128
#define GGETS_EXPANSION_SIZE 64

#include "ggets.h"

int 
fggets(char **str, FILE *fp)
{
        int ch;
        long i;
        long size;

        *str=NULL;

        if (feof(fp))
                return GGETS_EOF;

        *str=malloc(size=GGETS_INIT_SIZE);
        if (*str == NULL)
                return GGETS_NOMEM;

        for (i=0; (ch=fgetc(fp)) != EOF; i++)
        {
                if (i+1 >= size)
        {
            *str=realloc(*str,size+=GGETS_EXPANSION_SIZE);

                        if (*str == NULL)
                                return GGETS_NOMEM;
        }

                if (ch == 'n')
                        break;

                (*str)[i]=ch;
        }

        (*str)[i]='0';

        return GGETS_OK;
}