feature: parsing with getopt pretty much done (some checks tbd)

This commit is contained in:
0x35c 2025-05-29 00:10:41 +02:00
parent 60f23e9250
commit 6538a085b9
5 changed files with 123 additions and 16 deletions

20
include/parsing.h Normal file
View File

@ -0,0 +1,20 @@
#pragma once
#define NB_OPTIONS 5
typedef enum {
FL_HELP,
FL_PORTS,
FL_IP,
FL_SPEEDUP,
FL_SCAN,
} e_flag;
struct option_lst {
e_flag flag;
char *arg;
struct option_lst *next;
};
struct option_lst *parse_options(int ac, char *const *av);
char *get_option_arg(struct option_lst *options, e_flag flag);

View File

@ -10,7 +10,8 @@ int dns_lookup(char *ip_addr, char *hostname, struct sockaddr_in *addr_con)
{
struct hostent *host = gethostbyname2(hostname, AF_INET);
if (!host) {
dprintf(2, "Hostname %s doesn't exist or has invalid format.\n",
dprintf(2,
"Hostname '%s' doesn't exist or has invalid format.\n",
hostname);
return -1;
}

View File

@ -1,3 +1,4 @@
#include <getopt.h>
#include <netinet/in.h>
#include <netinet/tcp.h>
#include <pcap.h>
@ -7,6 +8,7 @@
#include "dns.h"
#include "interface.h"
#include "parsing.h"
#include "print.h"
#include "scan.h"
#include "thread.h"
@ -19,14 +21,22 @@ int main(int ac, char **av)
print_usage();
return 0;
}
// TODO parse arguments
(void)av;
struct option_lst *options = parse_options(ac, av);
if (options == NULL)
return 1;
char ip_addr[INET_ADDRSTRLEN];
struct sockaddr_in addr_con;
if (dns_lookup(ip_addr, av[1], &addr_con)) {
dprintf(2, "ft_nmap: failed to retrieve ip address from %s\n",
av[1]);
char *host = get_option_arg(options, FL_IP);
if (!host) {
dprintf(2, "ft_nmap: address/hostname required\n");
return 1;
}
if (dns_lookup(ip_addr, host, &addr_con)) {
dprintf(2, "ft_nmap: failed to retrieve ip address from '%s'\n",
host);
return 1;
}
@ -45,5 +55,9 @@ int main(int ac, char **av)
return 1;
}
int threads_running = 0;
while (threads_running)
;
return 0;
}

71
src/parsing.c Normal file
View File

@ -0,0 +1,71 @@
#include <getopt.h>
#include <stddef.h>
#include <stdio.h>
#include <stdlib.h>
#include "parsing.h"
char *get_option_arg(struct option_lst *options, e_flag flag)
{
if (!options)
return 0;
for (struct option_lst *it = options; it; it = it->next)
if (it->flag == flag)
return it->arg;
return 0;
}
static int add_option(struct option_lst **head, e_flag flag, char *arg)
{
struct option_lst *new_option = malloc(sizeof(struct option_lst));
if (!new_option) {
dprintf(2, "ft_ping: allocation of option failed\n");
for (struct option_lst *it = *head; it;) {
struct option_lst *tmp = it;
it = it->next;
free(tmp);
}
return -1;
}
new_option->flag = flag;
new_option->arg = arg;
new_option->next = NULL;
if (*head == NULL) {
*head = new_option;
return 0;
}
for (struct option_lst *it = *head; it; it = it->next) {
if (it->next == NULL) {
it->next = new_option;
break;
}
}
return 0;
}
struct option_lst *parse_options(int ac, char *const *av)
{
struct option_lst *head = NULL;
const struct option options[NB_OPTIONS] = {
{"help", no_argument, 0, 0},
{"ports", required_argument, 0, 0},
{"ip", required_argument, 0, 0},
{"speedup", required_argument, 0, 0},
{"scan", required_argument, 0, 0},
};
int c;
while (1) {
int option_index = 0;
c = getopt_long(ac, av, "", options, &option_index);
if (c == -1)
break;
else if (c)
return NULL;
if (add_option(&head, option_index, optarg) < 0)
return NULL;
}
return head;
}

View File

@ -19,20 +19,21 @@ static void dispatch_callback(u_char *user, const struct pcap_pkthdr *h,
const struct scan *data = (struct scan *)user;
const struct iphdr *iphdr =
(struct iphdr *)(bytes + sizeof(struct ether_header));
const void *packet = bytes + sizeof(struct ether_header) + sizeof(struct iphdr);
const void *packet =
bytes + sizeof(struct ether_header) + sizeof(struct iphdr);
if (iphdr->protocol == IPPROTO_TCP &&
h->caplen >= sizeof(struct ether_header) + sizeof(struct iphdr) +
sizeof(struct tcphdr)) {
tcp_response(packet, data);
}
else if (iphdr->protocol == IPPROTO_UDP &&
h->caplen >= sizeof(struct ether_header) + sizeof(struct iphdr) +
} else if (iphdr->protocol == IPPROTO_UDP &&
h->caplen >= sizeof(struct ether_header) +
sizeof(struct iphdr) +
sizeof(struct udphdr)) {
udp_response(packet, data);
}
else if (iphdr->protocol == IPPROTO_ICMP &&
h->caplen >= sizeof(struct ether_header) + sizeof(struct iphdr) +
} else if (iphdr->protocol == IPPROTO_ICMP &&
h->caplen >= sizeof(struct ether_header) +
sizeof(struct iphdr) +
sizeof(struct icmphdr)) {
icmp_response(packet, data);
}
@ -43,7 +44,7 @@ int scan(const struct scan *data)
int sockfd = socket(AF_INET, SOCK_RAW,
data->type == SCAN_UDP ? IPPROTO_UDP : IPPROTO_TCP);
if (sockfd < 0) {
dprintf(2, "ft_nmap: failed to create socket");
dprintf(2, "ft_nmap: failed to create socket\n");
return -1;
}