#include "rules.h"
#include "objects.h"
#include "services.h"
void dump_resolv(int verbose)
{
/* pointers to current object */
rulenum *ruleptr;
objlist *objptr;
services *svcptr;
/* indicates what we have processed on this iteration */
int srcflag=0;
int dstflag=0;
int svcflag=0;
/* indicates if object is a group of subobjects */
int srcgroup=0;
int dstgroup=0;
int svcgroup=0;
/* number of objects currently processed */
int src_group_count=0;
int dst_group_count=0;
int svc_group_count=0;
/* current object number */
int srcrule=0;
int dstrule=0;
int svcrule=0;
/* buffer used to send current service to resolv_svc() */
char *resolv_rule;
/* contains install and action strings */
char install[LNSIZE];
char action[LNSIZE];
/* current loop number */
int loopcount=0;
/* start at the head of the list */
ruleptr = head->count_link;
objptr = ohead->nodelink;
svcptr = shead->nodelink;
/* allocate space for current line */
if((resolv_rule = malloc(LNSIZE)) == NULL) {
fprintf(stderr,"dump_resolv: malloc failed\n");
exit(1);
}
/* header at top of page */
printf("%10cSource Address%13cSource IP%5cSource Netmask",' ',' ',' ');
printf("%6cDestination Address%5cDestination IP%5cDest Netmask",' ',' ',' ');
printf("%7cService%7cPort%4cType%2cInstall%1cAct\n",' ',' ',' ',' ',' ');
/*
* This is the main loop. It increments after all of source, destination and
* services have been processed and ruleptr rules are NULL
*/
while(ruleptr->count_link != NULL) {
printf("%2d ",ruleptr->rulecount);
/* copy install and action to be printed at the end */
sprintf(install,"%s",ruleptr->install);
sprintf(action,"%s",ruleptr->action);
srcgroup=dstgroup=svcgroup=0;
loopcount=0;
srcrule=0;
dstrule=0;
svcrule=0;
src_group_count=0;
dst_group_count=0;
svc_group_count=0;
/*
* This is the other major loop. It determines whether we are dealing with a main
* or subrule for each object, and stops when all of the targets are NULL
*/
do {
srcflag=dstflag=svcflag=0;
loopcount++;
srctop:
/* Process Source Groups */
if(srcgroup > 0) {
objptr = ohead->nodelink;
while((objptr->nodelink != NULL) && (ruleptr->src[srcrule] != NULL)) {
/* does the current object match the rule we're working on? */
if(strcmp(ruleptr->src[srcrule],objptr->objname) == 0) {
/* now that we found the group, see if there's any entries left
* to be printed */
if(objptr->group[src_group_count] != NULL) {
printf("%2c%3c%-28s",' ',' ',objptr->group[src_group_count]);
find_group(objptr->group[src_group_count]);
src_group_count++;
srcflag=1;
} else {
/* Doing three things here:
* 1.On the loop around where the object is now NULL, the
* next ruleptr->src[srcrule] is not printed
* 2.Indicate a record has been printed with srcflag=1
* 3.Increment srcrule, as we just printed one
*/
if(objptr->group[src_group_count] == NULL) {
srcrule++;
srcgroup=0;
/* can't just set src_group_count=0 and reprocess. Would involve
* too much manipulation of srcgroup and srcrule. Same for dst and
* svc
*/
if(ruleptr->src[srcrule] != NULL) {
srcflag=1;
goto srctop;
}
}
}
}
objptr = objptr->nodelink;
}
} else {
/* Process Source services. These may be group elements, but
* never will it be before we determine if its a group or not */
if(srcgroup == 0) {
if(ruleptr->src[srcrule] != NULL) {
if(srcrule > 0)
printf("%3c",' ');
srcflag=1;
/* resolv_src() takes the current rule, and just finds the
* object we're looking for, and prints it */
if((resolv_src(ruleptr->src[srcrule]) == 1)) {
srcgroup=1;
src_group_count=0;
} else {
srcgroup=0;
srcrule++;
}
}
}
}
/* Begin of processing destination hostname and destination IP address */
dsttop:
if(dstgroup > 0) {
objptr = ohead->nodelink;
while((objptr->nodelink != NULL) && (ruleptr->dst[dstrule] != NULL)) {
if(strcmp(ruleptr->dst[dstrule],objptr->objname) == 0) {
if(objptr->group[dst_group_count] != NULL) {
dstflag=1;
if(srcflag == 0)
printf("%5c%28c%16c%16c ",' ',' ',' ',' ');
printf("%2c%-28s",' ',objptr->group[dst_group_count]);
find_group(objptr->group[dst_group_count]);
dst_group_count++;
} else
if(objptr->group[dst_group_count] == NULL) {
dstgroup=0;
dstrule++;
if(ruleptr->dst[dstrule] != NULL) {
dstflag=1;
goto dsttop;
}
}
}
objptr = objptr->nodelink;
}
} else {
/* Process Destination Groups */
if(dstgroup == 0) {
/* Process Destination Services */
if(ruleptr->dst[dstrule] != NULL) {
dstflag=1;
if(srcflag == 0)
printf("%6c%28c%16c%16c",' ',' ',' ',' ');
if((resolv_dst(ruleptr->dst[dstrule]) == 1)) {
dstgroup=1;
dst_group_count=0;
} else {
dstgroup=0;
dstrule++;
}
}
}
}
/* Begin of processing services and service types */
svctop:
/* Process Group Services */
if(svcgroup > 0) {
svcptr = shead->nodelink;
/* truncate those long ICMP service listings on groups only */
if((svc_group_count > 3) && (verbose == 0)) {
svcgroup=0;
sprintf(ruleptr->svc[svcrule]," More...");
goto svctop;
}
while((svcptr->nodelink != NULL) && (ruleptr->svc[svcrule] != NULL)) {
if(strcmp(ruleptr->svc[svcrule],svcptr->svcname) == 0) {
if(svcptr->group[svc_group_count] != NULL) {
svcflag=1;
printf("%2c",' ');
if((srcflag == 0) && (dstflag == 0)) {
printf(" %5c%28c%16c%16c",' ',' ',' ',' ');
printf("%28c%16c%16c",' ',' ',' ');
} else {
if(dstflag == 0)
printf(" %28c%16c%16c",' ',' ',' ');
}
find_services(svcptr->group[svc_group_count]);
svc_group_count++;
} else
if(svcptr->group[svc_group_count] == NULL) {
svcgroup=0;
svcrule++;
if(ruleptr->svc[svcrule] != NULL) {
svcflag=1;
goto svctop;
}
}
}
svcptr = svcptr->nodelink;
}
} else {
if(svcgroup == 0) {
/* Process Services */
if(ruleptr->svc[svcrule] != NULL) {
svcflag=1;
if((srcflag == 0) && (dstflag == 0)) {
printf(" %5c%28c%16c%16c",' ',' ',' ',' ');
printf("%28c%16c%16c",' ',' ',' ');
} else {
if(dstflag == 0)
printf(" %28c%16c%16c",' ',' ',' ');
}
if((resolv_svc(ruleptr->svc[svcrule]) == 1)) {
svcgroup=1;
svc_group_count=0;
} else {
svcgroup=0;
svcrule++;
}
}
}
}
/* If anything was printed on this line, print a carriage return */
if((srcflag == 1) || (dstflag == 1) || (svcflag == 1)) {
if(loopcount == 1)
printf(" %s %s",install,action);
printf("\n");
}
/* continue while at least some data is being printed */
} while((ruleptr->src[srcrule] != NULL) || (srcflag == 1) ||
(ruleptr->dst[dstrule] != NULL) || (dstflag == 1) ||
(ruleptr->svc[svcrule] != NULL) || (svcflag == 1));
/* print a carriage return seperating rules */
printf("\n");
/* advance pointer to next rule */
ruleptr = ruleptr->count_link;
}
}
/* Description:
* Find current source, and print out associated information
*/
int resolv_src(char *rule_src)
{
objlist *objptr;
objptr = ohead->nodelink;
while(objptr->nodelink != NULL) {
if(strcmp(rule_src,objptr->objname) == 0) {
if(strcmp(objptr->type,"group") == 0) {
printf("%-28s%16s%16s ",rule_src,objptr->ipaddr,objptr->netmask);
return 1;
} else
printf("%-28s%16s%16s ",objptr->objname,objptr->ipaddr,objptr->netmask);
return 0;
}
objptr = objptr->nodelink;
}
/* Can't find a match for source */
if(rule_src != NULL)
printf("%-28s%16c%16c ",rule_src,' ',' ');
return 0;
}
/* Description:
* Find current destination, and print out associated information
*/
int resolv_dst(char *rule_dst)
{
objlist *objptr;
objptr = ohead->nodelink;
while(objptr->nodelink != NULL) {
if(strcmp(rule_dst,objptr->objname) == 0) {
if(strcmp(objptr->type,"group") == 0) {
printf("%-28s%16s%16s ",rule_dst,objptr->ipaddr,objptr->netmask);
return 1;
}
printf("%-28s%16s%16s ",objptr->objname,objptr->ipaddr,objptr->netmask);
return 0;
}
objptr = objptr->nodelink;
}
/* Can't find a match for destination */
if(rule_dst != NULL)
printf("%-28s%16c%16c ",rule_dst,' ',' ');
return 0;
}
/* Description:
* This one is somewhat more involved, because there seems to be quite a few
* screwed up cases. Find the current service, and make sure it is the
* correct length and content for what we're looking for
*/
int resolv_svc(char *rule_serv)
{
services *svcptr;
int i=0;
/* used to store service before printing,
* so its length and content can be modified */
char port[LNSIZE];
char svcname[LNSIZE];
char type[LNSIZE];
svcptr = shead->nodelink;
while(svcptr->nodelink != NULL) {
if(strcmp(rule_serv,svcptr->svcname) == 0) {
/* make a copy to not corrupt real data */
sprintf(svcname,"%s",svcptr->svcname);
/* simple hack to cut down the length if not a character */
for(i=0;i 10)) {
svcname[i] = '\0';
}
}
sprintf(port,"%s",svcptr->port);
/* get rid of some of those ports with weird names */
/* also make sure there is at least one char written */
for(i=0;iport);i++) {
if((port[i] == ',') && (i > 1)) {
port[i] = '\0';
}
}
if(strcmp(svcptr->type,"group") == 0) {
printf("%-11s%18c",svcname,' ');
return 1;
} else {
sprintf(type,"%s",svcptr->type);
if(strlen(type) > 10)
type[11] = '\0';
printf("%-13s:%-9s %5s",svcname,port,type);
return 0;
}
}
svcptr = svcptr->nodelink;
}
/* looked thru whole list, and didn't find any matches */
/* I think if we make it here, something really went wrong... */
/*if((svcflag == 0) && (rule_serv != NULL)) {*/
if(rule_serv != NULL) {
/* not resolution was found -- just print it out */
if(strlen(rule_serv) > 10)
rule_serv[11] = '\0';
printf("%-11s%18c",rule_serv,' ');
}
/* we know at this point the current object is not a group */
return 0;
}