Files
ft_ping/srcs/parsing.c
2025-08-20 16:43:54 +02:00

167 lines
3.6 KiB
C

/* ************************************************************************** */
/* */
/* ::: :::::::: */
/* parsing.c :+: :+: :+: */
/* +:+ +:+ +:+ */
/* By: tomoron <tomoron@student.42angouleme.fr> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2025/04/26 17:01:53 by tomoron #+# #+# */
/* Updated: 2025/08/20 16:42:02 by tomoron ### ########.fr */
/* */
/* ************************************************************************** */
#include "includes/ft_ping.h"
int get_set_int(char *arg, t_settings *set)
{
char *tmp;
tmp = arg;
while(*tmp)
{
if(!isdigit(*tmp))
{
fprintf(stderr, "%s: invalid value (`%s' near `%s')\n", set->name, arg, tmp);
set->err = 1;
return(0);
}
tmp++;
}
return(atoi(arg));
}
double get_set_float(char *arg, t_settings *set)
{
char *tmp;
int point;
tmp = arg;
while(*tmp)
{
if((!isdigit(*tmp) && *tmp != '.') || (*tmp == '.' && point))
{
fprintf(stderr, "%s: invalid value (`%s' near `%s')\n", set->name, arg, tmp);
set->err = 1;
return(0);
}
if(*tmp == '.')
point = 1;
tmp++;
}
return(atof(arg));
}
int check_values(t_settings *set, char *name)
{
if (set->setTtl)
{
if (set->ttl == 0)
{
fprintf(stderr, "%s: option value too small: %d\n", name, set->ttl);
return(0);
}
else if (set->ttl >= 256)
{
fprintf(stderr, "%s: option value too big: %d\n", name, set->ttl);
return(0);
}
}
if (set->interval < 0.2)
{
fprintf(stderr, "%s: option value is too small: %g\n", name, set->interval);
return(0);
}
return (1);
}
void init_settings(t_settings *set)
{
char *tmp;
tmp = set->name;
bzero(set, sizeof(t_settings));
set->name = tmp;
set->timeout = -1;
set->interval = 1;
set->socket = -1;
set->linger = 10;
}
int parse_args(int argc, char **argv, t_settings *set)
{
int arg;
struct option opts[] =
{
{"count", required_argument, 0, 'c'},
{"interval", required_argument, 0, 'i'},
{"timeout", required_argument, 0, 'w'},
{"linger", required_argument, 0, 'W'},
{"ttl", required_argument , 0, 1000},
{"verbose", no_argument, &set->verbose, 1},
{"help", no_argument, 0, 'h'},
{0, 0, 0, 0}
};
for(int i = 1; i < argc; i++)
{
if(!strcmp(argv[i], "-?"))
{
show_help(set);
return (1);
}
}
unsetenv("POSIXLY_CORRECT");
init_settings(set);
arg = 0;
while (arg != -1)
{
arg = getopt_long(argc, argv, "c:i:w:W:vh", opts, NULL);
switch (arg) {
case 'c':
set->count = get_set_int(optarg, set);
break;
case 'i':
set->interval = get_set_float(optarg, set);
break;
case 'w':
set->timeout = get_set_int(optarg, set);
break;
case 'W':
set->linger = get_set_int(optarg, set);
break;
case 1000:
set->ttl = get_set_int(optarg, set);
set->setTtl = 1;
break;
case 'v':
set->verbose = 1;
break;
case 'h':
case '?':
show_help(set);
return (1);
default :
break ;
}
}
while (optind < argc)
{
if (!add_host(set, argv[optind]))
{
set->err = 1;
return (0);
}
optind++;
}
if (!set->hosts)
{
fprintf(stderr, "%s: missing host operand\n", set->name);
set->err = 1;
return (1);
}
if (!set->err)
set->err = !check_values(set, argv[0]);
return (0);
}