⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 parse.c

📁 This is the first ever open source implementation of Dynamic Host Configuration Protocol for IPv6 (D
💻 C
字号:
#include "stdhead.h"#include "lib.h"#include "parse.h"char *config_buff = 0, *curr_ptr = 0, *token = 0;// Read the entire configuration file into config_buffvoid read_config_file (char *file_name){    int fd, n, size = 0;        if ((fd = open (file_name, O_RDONLY)) == -1)    {	printf ("Error opening file %s.\n", file_name);	exit (0);    }        config_buff = (char *) realloc (config_buff, 1);    size = 1;    while (read (fd, &config_buff[size - 1], 1) > 0)    {	size++;	config_buff = (char *) realloc (config_buff, size);    }    config_buff[size - 1] = '\0';    close (fd);}    // skip all whitespacevoid skip_whitespace (void){    while ((*curr_ptr == ' ') || (*curr_ptr == '\t') || (*curr_ptr == '\r') || (*curr_ptr == '\n'))	curr_ptr++;}// move across substring return success/failureint move_across_substring (char *substring){    curr_ptr = strstr (curr_ptr, substring);    if (curr_ptr)	curr_ptr += strlen (substring);    else	return 0;    return 1;}// Move across the substring. If not found exitint Move_across_substring (char *substring){    curr_ptr = strstr (curr_ptr, substring);    if (curr_ptr)	curr_ptr += strlen (substring);    else    {	printf ("Configuration file not correct.\n");	exit (1);    }    return 1;}// Read the next tokenvoid read_token (void){    char *p;    int n = 0;        if (token)	token = (char *) realloc (token, 0);        while ((*curr_ptr != ' ') && (*curr_ptr != '\t') && (*curr_ptr != '\r') && (*curr_ptr != '\n'))    {	n++;	token = (char *) realloc (token, n);	p = token + (n - 1);	*p = *curr_ptr;	curr_ptr++;    }    n++;    token = (char *) realloc (token, n);    p = token + (n - 1);    *p = '\0';}// Find if substring s1 occurs before s2int find_if_s1_before_s2 (char *s1, char *s2){    char *search_s1 = 0, *search_s2 = 0;    search_s1 = strstr (curr_ptr, s1);    search_s2 = strstr (curr_ptr, s2);    if (!search_s1 && !search_s2)	return 0;    else if ((search_s2 && (search_s2 > search_s1)) || !search_s2)    {        curr_ptr = search_s1;        curr_ptr += strlen (s1);        return 1;    }    else        return 0;}// Return an array of link list of possible range and user nodestruct config_head ** parse_and_assign (char *file_name, int *subnet_count, int relay_agent_flag){    extern struct DUID *server_duid;    struct DUID1 *server_duid1;    struct DUID2 *server_duid2;    struct DUID3 *server_duid3;        char *bkup_curr_ptr = 0, *start = 0;    struct config_range *range_node, *prev_range_ptr = 0;    struct config_user *user_node, *prev_user_ptr = 0;    int node_count = 0, i, count = 0;    struct config_head **head;    u_int8_t temp[2];    *(subnet_count) = 0;            if (relay_agent_flag)	// Multiple subnets configuration	return;        // One server subnet only    if (file_name)	read_config_file (file_name);    else	read_config_file (DEFAULT_CONFIG_FILE);    // assign current pointer to configuration buffer    curr_ptr = config_buff;    Move_across_substring ("duid_type");    skip_whitespace();    read_token();        server_duid = (struct DUID *) malloc (sizeof (struct DUID));    server_duid -> u_duid_type.duid_type = atoi (token);    server_duid -> opt = 0;    Move_across_substring ("{");        switch (server_duid -> u_duid_type.duid_type)    {	case 1 :	    start = curr_ptr;    	    server_duid1 = (struct DUID1 *) malloc (sizeof (struct DUID1));    	    server_duid -> duid_type = server_duid1;	                Move_across_substring ("time");	    skip_whitespace();	    read_token();    	    server_duid1 -> u_time.time = atoi (token);	    	    curr_ptr = start;            Move_across_substring ("hardware_type");	    skip_whitespace();	    read_token();	    server_duid1 -> u_haddr_type.haddr_type = atoi (token);    	    curr_ptr = start;	    Move_across_substring ("hardware_len");	    skip_whitespace();	    read_token();	    server_duid1 -> haddr_len = atoi (token);	    	    curr_ptr = start;	    Move_across_substring ("hardware_addr");	    skip_whitespace();	    read_token();	    server_duid1 -> link_layer_address = (u_int8_t *) malloc (sizeof (u_int8_t) * server_duid1 -> haddr_len);	    for (i = 0; i < 3 * server_duid1 -> haddr_len - 1; i += 3)	    {		temp[0] = convert_character_to_hex (token[i]);		temp[1] = convert_character_to_hex (token[i + 1]);		server_duid1 -> link_layer_address[count++] = (temp[0] << 4) | temp[1];	    }	    break;	    	case 2 :	    start = curr_ptr;    	    server_duid2 = (struct DUID2 *) malloc (sizeof (struct DUID2));    	    server_duid -> duid_type = server_duid2;	    	    curr_ptr = start;	    Move_across_substring ("ident_len");	    skip_whitespace();	    read_token();	    server_duid2 -> u_identifier_length.identifier_length = atoi (token);	    	    curr_ptr = start;	    Move_across_substring ("identifier");	    skip_whitespace();	    read_token();	    server_duid2 -> identifier = (u_int8_t *) malloc (sizeof (u_int8_t) * server_duid2 -> u_identifier_length.identifier_length);	    for (i = 0; i < server_duid2 -> u_identifier_length.identifier_length; i++)		server_duid2 -> identifier[i] = token[i];			    curr_ptr = start;	    Move_across_substring ("domain_name");	    skip_whitespace();	    read_token();	    server_duid2 -> domain_name_len = sizeof (token);	    server_duid2 -> domain_name = (char *) malloc (sizeof (char) * server_duid2 -> domain_name_len);	    for (i = 0; i < server_duid2 -> domain_name_len; i++)		server_duid2 -> domain_name[i] = token[i];	    break;	    	case 3 :	    start = curr_ptr;    	    server_duid3 = (struct DUID3 *) malloc (sizeof (struct DUID3));    	    server_duid -> duid_type = server_duid3;	                Move_across_substring ("hardware_type");	    skip_whitespace();	    read_token();	    server_duid3 -> u_haddr_type.haddr_type = atoi (token);    	    curr_ptr = start;	    Move_across_substring ("hardware_len");	    skip_whitespace();	    read_token();	    server_duid3 -> haddr_len = atoi (token);	    	    curr_ptr = start;	    Move_across_substring ("hardware_addr");	    skip_whitespace();	    read_token();	    server_duid3 -> link_layer_address = (u_int8_t *) malloc (sizeof (u_int8_t) * server_duid3 -> haddr_len);	    for (i = 0; i < 3 * server_duid3 -> haddr_len - 1; i += 3)	    {		temp[0] = convert_character_to_hex (token[i]);		temp[1] = convert_character_to_hex (token[i + 1]);		server_duid3 -> link_layer_address[count++] = (temp[0] << 4) | temp[1];	    }	    break;	    	default :	    printf ("Unrecognized DUID type\n");	    exit (1);    }    Move_across_substring ("}");    head = (struct config_head **) malloc (sizeof (struct config_head *));    head[(*subnet_count)++] = (struct config_head *) malloc (sizeof (struct config_head));    Move_across_substring ("subnet");        Move_across_substring ("t1");    skip_whitespace();    read_token();    head[*(subnet_count) - 1] -> t1 = atoi (token);            Move_across_substring ("t2");    skip_whitespace();    read_token();    head[*(subnet_count) - 1] -> t2 = atoi (token);        // Build all user nodes    bkup_curr_ptr = curr_ptr;    while (find_if_s1_before_s2 ("user", "subnet"))//if user is before subnet.    {	user_node = (struct config_user *) malloc (sizeof (struct config_user));	if (!node_count)	{	    head[*(subnet_count) - 1]->first_node_type = USER_NODE;	    head[*(subnet_count) - 1]->next = user_node;	}	else	{    	    prev_user_ptr->next = user_node;	    prev_user_ptr->next_node_type = USER_NODE;	}	node_count++;	prev_user_ptr = user_node;		move_across_substring ("{");	start = curr_ptr;		move_across_substring ("link_local_address");	skip_whitespace();	read_token();	user_node -> link_local_addr = (struct in6_addr *) malloc (sizeof (struct in6_addr));	inet_pton (AF_INET6, token, user_node -> link_local_addr);			curr_ptr = start;	move_across_substring ("IPv6_address");	skip_whitespace();	read_token();	user_node -> ipv6_addr = (struct in6_addr *) malloc (sizeof (struct in6_addr));	inet_pton (AF_INET6, token, user_node -> ipv6_addr);		curr_ptr = start;	move_across_substring ("preferred_lifetime");	skip_whitespace();	read_token();	user_node -> pref_life = atoi (token);		curr_ptr = start;	move_across_substring ("valid_lifetime");	skip_whitespace();	read_token();	user_node -> valid_life = atoi (token);			curr_ptr = start;	move_across_substring ("max_renew_count");	skip_whitespace();	read_token();	user_node -> max_renew_count = atoi (token);		curr_ptr = start;	move_across_substring ("preference_val");	skip_whitespace();	read_token();	user_node -> pref_val = atoi (token);		move_across_substring ("}");    }    // Build all range nodes    curr_ptr = bkup_curr_ptr;        while (find_if_s1_before_s2 ("range", "subnet"))    {	range_node = (struct config_range *) malloc (sizeof (struct config_range));	if (!node_count)	{	    head[*(subnet_count) - 1]->first_node_type = RANGE_NODE;	    head[*(subnet_count) - 1]->next = range_node;	}	else	{	    if (prev_user_ptr)	    {	        prev_user_ptr->next = range_node;		prev_user_ptr->next_node_type = RANGE_NODE;		prev_user_ptr = 0;	    }	    else	    {		prev_range_ptr->next = range_node;		prev_range_ptr->next_node_type = RANGE_NODE;	    }	}	node_count++;	prev_range_ptr = range_node;		skip_whitespace();	read_token();	range_node -> st_addr = (struct in6_addr *) malloc (sizeof (struct in6_addr));	inet_pton (AF_INET6, token, range_node -> st_addr);			skip_whitespace();	read_token();	range_node -> end_addr = (struct in6_addr *) malloc (sizeof (struct in6_addr));	inet_pton (AF_INET6, token, range_node -> end_addr);		move_across_substring ("{");	start = curr_ptr;		move_across_substring ("preferred_lifetime");	skip_whitespace();	read_token();	range_node -> pref_life = atoi (token);		curr_ptr = start;	move_across_substring ("valid_lifetime");	skip_whitespace();	read_token();	range_node -> valid_life = atoi (token);			curr_ptr = start;	move_across_substring ("max_renew_count");	skip_whitespace();	read_token();	range_node -> max_renew_count = atoi (token);		curr_ptr = start;	move_across_substring ("preference_val");	skip_whitespace();	read_token();	range_node -> pref_val = atoi (token);		move_across_substring ("}");    }        Move_across_substring ("}");    if (prev_user_ptr)    {	prev_user_ptr -> next_node_type = NO_NODE;	prev_user_ptr -> next = 0;    }    else if (prev_range_ptr)    {	prev_range_ptr -> next_node_type = NO_NODE;	prev_range_ptr -> next = 0;    }    else    {	head[*(subnet_count) - 1] -> first_node_type = NO_NODE;	head[*(subnet_count) - 1] -> next = 0;    }        return head;}// Print the contents of the linked list.void print_config_list_contents (struct config_head *head){    struct config_range *range_node = 0;    struct config_user *user_node = 0;    char name[64];        printf ("Subnet options\n");    printf ("T1 = %d\n", head -> t1);    printf ("T2 = %d\n", head -> t2);        if (head -> first_node_type == RANGE_NODE)	range_node = (struct config_range *) head -> next;    else if (head -> first_node_type == USER_NODE)	user_node = (struct config_user *) head -> next;    else if (head -> first_node_type == NO_NODE)	return;	    while (user_node)    {	printf ("\nLink local address of user = %s\n", inet_ntop (AF_INET6, (char *) user_node -> link_local_addr, name, 64));	printf ("IPv6 address of user = %s\n", inet_ntop (AF_INET6, (char *) user_node -> ipv6_addr, name, 64));	printf ("Preferred lifetime = %d\n", user_node -> pref_life);	printf ("Valid lifetime = %d\n", user_node -> valid_life);	printf ("Maximum renewal count = %d\n", user_node -> max_renew_count);		printf ("Preference value = %d\n", user_node -> pref_val);		if (user_node -> next_node_type == RANGE_NODE)	{	    range_node = (struct config_range *) user_node -> next;	    break;	}	else if (user_node -> next_node_type == USER_NODE)	    user_node = (struct config_user *) user_node -> next;	else if (user_node -> next_node_type == NO_NODE)	    return;    }    while (range_node)    {	printf ("\nStarting address of range = %s\n", inet_ntop (AF_INET6, (char *) range_node -> st_addr, name, 64));	printf ("Ending address of range = %s\n", inet_ntop (AF_INET6, (char *) range_node -> end_addr, name, 64));	printf ("Preferred lifetime = %d\n", range_node -> pref_life);	printf ("Valid lifetime = %d\n", range_node -> valid_life);	printf ("Maximum renewal count = %d\n", range_node -> max_renew_count);		printf ("Preference value = %d\n", range_node -> pref_val);		if (range_node -> next_node_type == RANGE_NODE)	    range_node = (struct config_range *) range_node -> next;	else if (range_node -> next_node_type == NO_NODE)	    return;    }}void print_server_duid (void){    extern struct DUID *server_duid;    struct DUID1 *d1;    struct DUID2 *d2;    struct DUID3 *d3;    int i;        printf ("\nServer DUID\n");    printf ("DUID type = %d\n", server_duid -> u_duid_type.duid_type);        switch (server_duid -> u_duid_type.duid_type)    {	case 1 :	    d1 = server_duid -> duid_type;            printf ("Time = %d\n", d1 -> u_time.time);            printf ("Hardware type = %d\nHardware address = ", d1 -> u_haddr_type.haddr_type);            for (i = 0; i < 6; i++)            {                printf ("%x", d1 -> link_layer_address[i]);                if (i != 5)                    printf (":");            }            break;	        	case 2 :            d2 = server_duid -> duid_type;            printf ("Identifier length = %d\nIdentifier = ", d2 -> u_identifier_length.identifier_length);            for (i = 0; i < d2 -> u_identifier_length.identifier_length; i++)                printf ("%d", d2 -> identifier[i]);            printf ("\nDomain name = ");            for (i = 0; i < d2 -> domain_name_len; i++)                printf ("%c", d2 -> domain_name[i]);            break;        case 3 :            d3 = server_duid -> duid_type;            printf ("Hardware type = %d\nHardware address = ", d3 -> u_haddr_type.haddr_type);            for (i = 0; i < 6; i++)            {                printf ("%x", d3 -> link_layer_address[i]);                if (i != 5)                    printf (":");            }	    break;    }        printf ("\n\n");}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -