Home | History | Annotate | Download | only in agent
      1 /*
      2  * CDDL HEADER START
      3  *
      4  * The contents of this file are subject to the terms of the
      5  * Common Development and Distribution License, Version 1.0 only
      6  * (the "License").  You may not use this file except in compliance
      7  * with the License.
      8  *
      9  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
     10  * or http://www.opensolaris.org/os/licensing.
     11  * See the License for the specific language governing permissions
     12  * and limitations under the License.
     13  *
     14  * When distributing Covered Code, include this CDDL HEADER in each
     15  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
     16  * If applicable, add the following below this CDDL HEADER, with the
     17  * fields enclosed by brackets "[]" replaced with your own identifying
     18  * information: Portions Copyright [yyyy] [name of copyright owner]
     19  *
     20  * CDDL HEADER END
     21  */
     22 /*
     23  * Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
     24  * Use is subject to license terms.
     25  */
     26 
     27 #pragma ident	"%Z%%M%	%I%	%E% SMI"
     28 
     29 #include <stdlib.h>
     30 #include <stdio.h>
     31 #include <string.h>
     32 #include <sys/types.h>
     33 #include <sys/socket.h>
     34 #include <netinet/in.h>
     35 #include <arpa/inet.h>
     36 
     37 #include "impl.h"
     38 #include "error.h"
     39 #include "trace.h"
     40 #include "asn1.h"
     41 #include "snmp.h"
     42 #include "trap.h"
     43 
     44 #include "agent_msg.h"
     45 #include "access.h"
     46 
     47 #define WILD_CARD_HOST_NAME	"*"
     48 #define WILD_CARD_ADDRESS 0
     49 
     50 #define MAX_BUF_SIZE 256
     51 
     52 /***** STATIC VARIABLES *****/
     53 
     54 static Manager *first_manager = NULL;
     55 static Community *first_community = NULL;
     56 
     57 static EFilter *first_efilter = NULL;
     58 
     59 static NameOidPair *first_name_oid_pair = NULL;
     60 
     61 
     62 void init_manager_set ()
     63 {
     64 	first_community = NULL;	/* TODO: check this out */
     65 	first_manager = NULL;
     66 }
     67 
     68 void set_first_manager (Manager *mgr)
     69 {
     70 	first_manager = mgr;
     71 }
     72 
     73 Manager * get_curr_manager_set ()
     74 {
     75 	return first_manager;
     76 }
     77 
     78 /***********************************************************/
     79 
     80 /*
     81  *	returns	0 if OK
     82  *		1 if error
     83  *		-1 if fatal error
     84  */
     85 
     86 Manager* manager_add(char *name, char *error_label)
     87 {
     88 	IPAddress ip_address;
     89 	Manager *new;
     90 	Manager *m;
     91 
     92 
     93 	error_label[0] = '\0';
     94 
     95 
     96 	if(name == NULL)
     97 	{
     98 		(void)sprintf(error_label, "BUG: manager_add(): name is NULL");
     99 		return NULL;
    100 	}
    101 
    102 
    103 	/* skip the ip adx for wild-card host */
    104 
    105 	if(strcmp(name,WILD_CARD_HOST_NAME)){
    106 		/* try to find the IP address from the name */
    107 		if(name_to_ip_address(name, &ip_address, error_label))
    108 		{
    109 			return NULL;
    110 		}
    111 	}
    112 
    113 
    114 	/* checking for dup is on the wild-card host name */
    115 
    116 
    117 	/* check if this manager does not already exist */
    118 	if(strcmp(name,WILD_CARD_HOST_NAME)){
    119 		for(m = first_manager; m; m = m->next_manager)
    120 		{
    121 			if(ip_address.s_addr == m->ip_address.s_addr)
    122 			{
    123 				(void)sprintf(error_label, ERR_MSG_MANAGER_DUP, name);
    124 				return m;
    125 			}
    126 		}
    127 	}else{
    128 		for(m = first_manager; m; m = m->next_manager)
    129 		{
    130 			if(!strcmp(m->name,name))
    131 			{
    132 				return m;
    133 			}
    134 		}
    135 	}
    136 
    137 
    138 	/* allocate, initialize and link the new manager */
    139 	new = (Manager *) calloc(1,sizeof(Manager));
    140 	if(new == NULL)
    141 	{
    142 		(void)sprintf(error_label, ERR_MSG_ALLOC);
    143 		return NULL;
    144 	}
    145 	new->next_manager = NULL;
    146 	new->name = NULL;
    147 
    148 	new->name = strdup(name);
    149 	if(new->name == NULL)
    150 	{
    151 		(void)sprintf(error_label, ERR_MSG_ALLOC);
    152 		free(new);
    153 		return NULL;
    154 	}
    155 
    156 	/* ip adx for wild-card host should be zero */
    157 
    158 	if(strcmp(name,WILD_CARD_HOST_NAME)){
    159 		new->ip_address.s_addr = ip_address.s_addr;
    160 	}else{
    161 		new->ip_address.s_addr = WILD_CARD_ADDRESS;
    162 
    163 	}
    164 
    165 	new->next_manager = first_manager;
    166 	first_manager = new;
    167 
    168 
    169 	return new;
    170 }
    171 
    172 /***********************************************************/
    173 
    174 /*
    175  * returns a pointer to the manager if the request succeeds,
    176  * otherwise returns NULL
    177  */
    178 
    179 Manager *is_valid_manager(Address *address, Manager **mngr)
    180 {
    181         Manager *m;
    182 
    183         *mngr = NULL;
    184 
    185         if(address == NULL)
    186         {
    187                 error("BUG: is_valid_manager(): address is NULL");
    188                 return NULL;
    189         }
    190 
    191         if(first_manager == NULL)
    192         {
    193                 return NULL;
    194         }
    195 
    196         for(m = first_manager; m; m = m->next_manager)
    197         {
    198                 if(address->sin_addr.s_addr == m->ip_address.s_addr)
    199                 {
    200                         *mngr = m;
    201                         return m;
    202                 }
    203         }
    204 
    205         /* check for wild-card host */
    206         for(m = first_manager; m; m = m->next_manager)
    207         {
    208                 if(!strcmp(m->name,WILD_CARD_HOST_NAME)){
    209                         *mngr = m;
    210                         return m;
    211                 }
    212         }
    213 
    214         return m;
    215 }
    216 
    217 /***********************************************************/
    218 
    219 void delete_manager_list()
    220 {
    221 	Manager *next;
    222 
    223 
    224 	while(first_manager)
    225 	{
    226 		next = first_manager->next_manager;
    227 
    228 		if(first_manager->name)
    229 		{
    230 			free(first_manager->name);
    231 		}
    232 
    233 		free(first_manager);
    234 
    235 		first_manager = next;
    236 	}
    237 
    238 	first_manager = NULL;
    239 }
    240 
    241 void manager_list_free(Manager *mngr)
    242 {
    243 	Manager *next;
    244 
    245 
    246 	while(mngr)
    247 	{
    248 		next = mngr->next_manager;
    249 
    250 		if(mngr->name)
    251 		{
    252 			free(mngr->name);
    253 		}
    254 
    255 		free(mngr);
    256 
    257 		mngr = next;
    258 	}
    259 
    260 	mngr = NULL;
    261 }
    262 
    263 void sub_member_free(SubMember *mem)
    264 {
    265   Manager *mngr;
    266 
    267   if(mem==NULL) return;
    268   mem->count--;
    269   if(mem->count<0){
    270   	mngr = mem->first_manager;
    271   	manager_list_free(mngr);
    272   	if(mem->community_string != NULL) free(mem->community_string);
    273   	free(mem);
    274   }
    275 }
    276 
    277 void sub_group_list_free(SubGroup *group)
    278 {
    279 	SubGroup *next;
    280 
    281 
    282 	while(group)
    283 	{
    284 		next = group->next_sub_group;
    285 
    286 		if(group->first_sub_member != NULL)
    287 		{
    288 			sub_member_free(group->first_sub_member);
    289 		}
    290 
    291 		free(group);
    292 
    293 		group = next;
    294 	}
    295 
    296 }
    297 
    298 void trap_slot_list_free(TrapSlot *slot)
    299 {
    300 	TrapSlot *next;
    301 
    302 
    303 	while(slot)
    304 	{
    305 		next = slot->next_trap_slot;
    306 		if(slot->first_sub_group != NULL)
    307 		{
    308 			sub_group_list_free(slot->first_sub_group);
    309 		}
    310 
    311 		free(slot);
    312 
    313 		slot = next;
    314 	}
    315 
    316 }
    317 
    318 
    319 void delete_efilter_list()
    320 {
    321 	EFilter *next;
    322 
    323 
    324 	while(first_efilter)
    325 	{
    326 		next = first_efilter->next_efilter;
    327 
    328 		if(first_efilter->name)
    329 		{
    330 			free(first_efilter->name);
    331 		}
    332 
    333 		free(first_efilter);
    334 
    335 		first_efilter = next;
    336 	}
    337 
    338 	first_efilter = NULL;
    339 }
    340 
    341 /***********************************************************/
    342 
    343 void trace_managers()
    344 {
    345 	Manager *m;
    346 	AccessServer *as;
    347 
    348 	trace("MANAGERS:\n");
    349 	trace("---------\n");
    350 	for(m = first_manager; m; m = m->next_manager)
    351 	{
    352 		trace("%-30s %-20s\n",
    353 			m->name,
    354 			!strcmp(m->name,WILD_CARD_HOST_NAME)?
    355 			"0":inet_ntoa(m->ip_address)   );
    356 		for(as=m->first_acc_server;as;as=as->next_acc_server)
    357 			trace_access_server(as);
    358 
    359 	}
    360 	trace("\n");
    361 }
    362 
    363 
    364 /***********************************************************/
    365 
    366 /*
    367  *	returns	0 if OK
    368  *		1 if error
    369  *		-1 if fatal error
    370  */
    371 
    372 int community_add(char *name, int type, char *error_label)
    373 {
    374 	int ret;
    375 	Community *new;
    376 	Community *c;
    377 	Community *last = NULL;
    378 
    379 
    380 	error_label[0] = '\0';
    381 
    382 	if(name == NULL)
    383 	{
    384 		(void)sprintf(error_label, "BUG: community_add(): name is NULL");
    385 		return -1;
    386 	}
    387 
    388 	if(name[0] == '\0')
    389 	{
    390 		(void)sprintf(error_label, "BUG: community_add(): name is empty");
    391 		return -1;
    392 	}
    393 
    394 	if( (type != READ_ONLY) && (type != READ_WRITE) )
    395 	{
    396 		(void)sprintf(error_label, "BUG: community_add(): bad type (%d)", type);
    397 		return -1;
    398 	}
    399 
    400 	for(c = first_community; c; c = c->next_community)
    401 	{
    402 		ret = strcmp(name, c->name);
    403 		if(ret > 0)
    404 		{
    405 			break;
    406 		}
    407 		else
    408 		if(ret == 0)
    409 		{
    410 			(void)sprintf(error_label, ERR_MSG_COMMUNITY_DUP, name);
    411 			return 1;
    412 		}
    413 
    414 		last = c;
    415 	}
    416 
    417 	new = (Community *) calloc(1,sizeof(Community));
    418 	if(new == NULL)
    419 	{
    420 		(void)sprintf(error_label, ERR_MSG_ALLOC);
    421 		return -1;
    422 	}
    423 	new->next_community = NULL;
    424 	new->name = NULL;
    425 
    426 	new->name = strdup(name);
    427 	if(new->name == NULL)
    428 	{
    429 		(void)sprintf(error_label, ERR_MSG_ALLOC);
    430 		free(new);
    431 		return -1;
    432 	}
    433 
    434 	new->type = type;
    435 
    436 	if(last)
    437 	{
    438 		last->next_community = new;
    439 	}
    440 	else
    441 	{
    442 		first_community = new;
    443 	}
    444 	new->next_community = c;
    445 
    446 
    447 	return 0;
    448 }
    449 
    450 int get_access_type(Manager *mngr,char *name)
    451 {
    452   AccessServer *as;
    453   AccessPolicy *ap;
    454   Community *comm;
    455 
    456   if(name==NULL || mngr==NULL) return NULL;
    457   for(as=mngr->first_acc_server;as;as=as->next_acc_server)
    458   {
    459     if((ap=as->first_acc_policy)!=NULL)
    460 	for(comm=ap->first_community;comm;comm=comm->next_community)
    461 		if(comm->name!=NULL && !strcmp(name,comm->name))
    462 			return ap->access_type;
    463   }
    464   return -1;
    465 }
    466 
    467 
    468 /***********************************************************/
    469 
    470 /* returns True or False        */
    471 
    472 int is_valid_community(char *name, int type, Manager *mngr)
    473 {
    474 	int access_type;
    475 
    476 
    477 	if(name == NULL)
    478 	{
    479 		error("BUG: is_valid_community(): name is NULL");
    480 		return False;
    481 	}
    482 
    483 	if( (type != GETNEXT_REQ_MSG )
    484 		&& (type != GET_REQ_MSG)
    485 		&& (type != SET_REQ_MSG) )
    486 	{
    487 		error("BUG: is_valid_community(): bad type(0x%x)", type);
    488 		return False;
    489 	}
    490 
    491   	if(mngr==NULL)  return True; /* accept reqs from any hosts */
    492 
    493 	if(mngr->first_acc_server!=NULL){
    494 		if( (access_type = get_access_type(mngr,name)) == -1)
    495 			return False;
    496 	}
    497 
    498 	if(type != SET_REQ_MSG)
    499 	{
    500 		return True;
    501 	}
    502 	else
    503 	{
    504 		if(access_type == READ_WRITE)
    505 		{
    506 			return True;
    507 		}
    508 		else
    509 		{
    510 			return False;
    511 		}
    512 	}
    513 
    514 }
    515 
    516 
    517 /***********************************************************/
    518 
    519 void delete_community_list()
    520 {
    521 	Community *next;
    522 
    523 
    524 	while(first_community)
    525 	{
    526 		next = first_community->next_community;
    527 
    528 		if(first_community->name)
    529 		{
    530 			free(first_community->name);
    531 		}
    532 
    533 		free(first_community);
    534 
    535 		first_community = next;
    536 	}
    537 
    538 	first_community = NULL;
    539 }
    540 
    541 
    542 /***********************************************************/
    543 
    544 void trace_access_server(AccessServer *as)
    545 {
    546   AccessPolicy *ap;
    547 
    548   if(as==NULL) return;
    549   if( (ap=as->first_acc_policy)!=NULL )
    550 	trace_access_policy(ap);
    551 }
    552 
    553 void trace_access_policy(AccessPolicy *ap)
    554 {
    555   Community *c;
    556 
    557   if(ap==NULL) return;
    558   trace("\tCOMMUNITIES(");
    559   switch(ap->access_type)
    560   {
    561 	case READ_ONLY:
    562 		trace("%s", "READ_ONLY");
    563 		break;
    564 	case READ_WRITE:
    565 		trace("%s", "READ_WRITE");
    566 		break;
    567   }
    568   trace("): ");
    569   for(c=ap->first_community;c;c=c->next_community)
    570 	trace_communities(c);
    571   trace("\n");
    572 }
    573 
    574 void trace_communities(Community *c)
    575 {
    576 
    577 
    578 	trace(" %s", c->name);
    579 }
    580 
    581 
    582 /***********************************************************/
    583 void community_list_free(Community *comm)
    584 {
    585 	Community *next;
    586 
    587 
    588 	while(comm)
    589 	{
    590 		next = comm->next_community;
    591 
    592 		if(comm->name)
    593 		{
    594 			free(comm->name);
    595 		}
    596 
    597 		free(comm);
    598 
    599 		comm = next;
    600 	}
    601 
    602 	comm = NULL;
    603 }
    604 
    605 void access_policy_list_delete(AccessPolicy *ap)
    606 {
    607   if(ap==NULL) return;
    608   ap->count--;
    609   if(ap->count<=0){
    610   	free(ap);
    611   }
    612 }
    613 
    614 void access_policy_list_free(AccessPolicy *ap)
    615 {
    616   if(ap==NULL) return;
    617   ap->count--;
    618   if(ap->count<=0){
    619   	community_list_free(ap->first_community);
    620   	free(ap);
    621   }
    622 }
    623 
    624 void access_server_delete(AccessServer *as)
    625 {
    626   if(as==NULL) return;
    627   access_policy_list_delete(as->first_acc_policy);
    628   free(as);
    629 }
    630 
    631 void access_server_free(AccessServer *as)
    632 {
    633   if(as==NULL) return;
    634   access_policy_list_free(as->first_acc_policy);
    635   free(as);
    636 }
    637 
    638 void agent_manager_list_free(Manager *mgr)
    639 {
    640 	Manager *nextmgr;
    641 	AccessServer *as, *last=NULL;
    642 
    643 	if (mgr == NULL)
    644 		return;
    645 
    646 	while(mgr)
    647 	{
    648 		nextmgr = mgr->next_manager;
    649 
    650 		as = mgr->first_acc_server;
    651 		while (as) {
    652 			last = as->next_acc_server;
    653 			access_server_delete(as);
    654 			as = last;
    655 		}
    656 
    657 		if(mgr->name)
    658 			free(mgr->name);
    659 
    660 		free(mgr);
    661 
    662 		mgr = nextmgr;
    663 	}
    664 
    665 	mgr = NULL;
    666 }
    667 
    668 void access_server_add_tail(Manager* mngr, AccessServer *acc_server)
    669 {
    670   AccessServer *as, *last=NULL;
    671 
    672   if(mngr==NULL || acc_server==NULL) return;
    673   for(as=mngr->first_acc_server;as;as=as->next_acc_server)
    674 	last = as;
    675 
    676   if(last==NULL){
    677 	mngr->first_acc_server = acc_server;
    678   }else{
    679 	last->next_acc_server = acc_server;
    680   }
    681   acc_server->next_acc_server = NULL;
    682   acc_server->attached = TRUE;
    683 }
    684 
    685 void community_attach(AccessPolicy *ap, Community *comm)
    686 {
    687   if(ap==NULL || comm==NULL) return;
    688   if(ap->first_community==NULL)
    689 	ap->first_community = comm;
    690   else{
    691 	comm->next_community = ap->first_community;
    692 	ap->first_community = comm;
    693   }
    694 }
    695 
    696 
    697 EFilter* efilter_add(char *name, char *error_label)
    698 {
    699 	EFilter *new;
    700 	EFilter *m;
    701 
    702 
    703 	error_label[0] = '\0';
    704 
    705 
    706 	if(name == NULL)
    707 	{
    708 		(void)sprintf(error_label, "BUG: efilter_add(): name is NULL");
    709 		return NULL;
    710 	}
    711 
    712 
    713 	for(m = first_efilter; m; m = m->next_efilter)
    714 	{
    715 		if(!strcmp(m->name,name))
    716 		{
    717 			return m;
    718 		}
    719 	}
    720 
    721 
    722 	/* allocate, initialize and link the new efilter */
    723 	new = (EFilter *) calloc(1,sizeof(EFilter));
    724 	if(new == NULL)
    725 	{
    726 		(void)sprintf(error_label, ERR_MSG_ALLOC);
    727 		return NULL;
    728 	}
    729 	new->next_efilter = NULL;
    730 	new->name = NULL;
    731 
    732 	new->name = strdup(name);
    733 	if(new->name == NULL)
    734 	{
    735 		(void)sprintf(error_label, ERR_MSG_ALLOC);
    736 		free(new);
    737 		return NULL;
    738 	}
    739 
    740 	new->enterprise = enterprise_name_to_oid(new->name);
    741 
    742 	new->next_efilter = first_efilter;
    743 	first_efilter = new;
    744 
    745 	return new;
    746 }
    747 
    748 TrapSlot* trap_slot_add(int num,EFilter *efilter,char *error_label)
    749 {
    750 	TrapSlot *new;
    751 	TrapSlot *m;
    752 
    753 
    754 	if(efilter==NULL) return NULL;
    755 	if(num < 0)
    756 	{
    757 		(void)sprintf(error_label, "BUG: trap_slot_add(): name is NULL");
    758 		return NULL;
    759 	}
    760 
    761 
    762 	for(m = efilter->first_trap_slot; m; m = m->next_trap_slot)
    763 	{
    764 		if(m->num == num)
    765 		{
    766 			return m;
    767 		}
    768 	}
    769 
    770 
    771 	/* allocate, initialize and link the new efilter */
    772 	new = (TrapSlot *) calloc(1,sizeof(TrapSlot));
    773 	if(new == NULL)
    774 	{
    775 		(void)sprintf(error_label, ERR_MSG_ALLOC);
    776 		return NULL;
    777 	}
    778 	new->num = num;
    779 	new->next_trap_slot = efilter->first_trap_slot;
    780 	efilter->first_trap_slot = new;
    781 
    782 	return new;
    783 }
    784 
    785 void sub_group_add_tail(TrapSlot *slot, SubGroup *group)
    786 {
    787   SubGroup *sg, *last =NULL;
    788 
    789   if(slot==NULL || group==NULL) return;
    790   for(sg=slot->first_sub_group;sg;sg=sg->next_sub_group)
    791 	last = sg;
    792 
    793   if(last==NULL){
    794 	slot->first_sub_group = group;
    795   }else{
    796 	last->next_sub_group = group;
    797   }
    798   group->next_sub_group = NULL;
    799 }
    800 
    801 void mem_filter_join(int low, int high,SubMember *mem,EFilter *filter)
    802 {
    803   /* find the trap slot in the filter */
    804   /* create subgroup, attach submember to subgroup */
    805   /* insert subgroup into the trap slot */
    806 
    807   int idx;
    808   TrapSlot *slot;
    809   SubGroup *group;
    810 
    811   if(low<0 || high<0 || filter==NULL || mem==NULL) return;
    812   for(idx=low;idx<=high;idx++){
    813 	slot = trap_slot_add(idx,filter,error_label);
    814 	if(slot==NULL) continue;
    815 	group = calloc(1,sizeof(SubGroup));
    816 	if(group==NULL){
    817 		error("malloc() failed");
    818 	}
    819         /* The efilter list may contain duplicate entries because
    820            the agent ACL file may be read several times. This seems
    821            to be necessary to mantain other functionality in the ACL
    822            such as specifying managers. The following hack makes sure
    823            the trap is sent to each host only by not allowing duplicate
    824            members in an efilter.
    825         */
    826         if (slot->first_sub_group == NULL) {	/* always add initial first_sub_group */
    827 		sub_group_add_tail(slot,group);
    828 		group->first_sub_member = mem;
    829 		mem->count++;
    830         }else {                                 /* at least one sub_group exists  */
    831                 if (strcmp(slot->first_sub_group->first_sub_member->first_manager->name,
    832                            mem->first_manager->name)) {  /* check for duplicate member */
    833                                   sub_group_add_tail(slot,group);
    834                                   group->first_sub_member = mem;
    835                                   mem->count++;
    836                 } else    /* don't add duplicate  */
    837                       free(group);
    838         }
    839   }
    840 }
    841 
    842 static void trace_hosts(Manager *mngr)
    843 {
    844    Manager *m;
    845 
    846    for(m=mngr;m;m=m->next_manager){
    847 	trace("\t\t%s %s\n",
    848 			m->name,
    849 			inet_ntoa(m->ip_address));
    850    }
    851 }
    852 
    853 static void trace_sub_member(SubMember *mem)
    854 {
    855   if(mem==NULL) return;
    856   if(mem->community_string != NULL)
    857   	trace("\tcommunity-string: %s\n",mem->community_string);
    858   trace_hosts(mem->first_manager);
    859 }
    860 
    861 static void trace_sub_group(SubGroup *group)
    862 {
    863   if(group==NULL) return;
    864   trace_sub_member(group->first_sub_member);
    865 }
    866 
    867 static void trace_trap_slot(TrapSlot *slot)
    868 {
    869   SubGroup *group;
    870 
    871   if(slot==NULL) return;
    872   trace("\ttrap-num=%d",slot->num);
    873   for(group=slot->first_sub_group;group;group=group->next_sub_group)
    874   	trace_sub_group(group);
    875 }
    876 
    877 void trace_filter()
    878 {
    879   EFilter *filter;
    880   TrapSlot *slot;
    881 
    882   trace("#EFILTER:\n");
    883   for(filter=first_efilter;filter;filter=filter->next_efilter)
    884   {
    885 	trace("enterprise=\"%s\"\n",filter->name);
    886 	for(slot=filter->first_trap_slot;slot;slot=slot->next_trap_slot)
    887 		trace_trap_slot(slot);
    888   }
    889   trace("\n");
    890 }
    891 
    892 /**** Enterprise related functions *****/
    893 
    894 void trace_name_oid_pair()
    895 {
    896   NameOidPair *np;
    897 
    898   trace("NAME_OID_PAIR:\n");
    899   for(np=first_name_oid_pair;np;np=np->next)
    900         trace("name: %s oid: %s\n",np->name,SSAOidString(np->oid));
    901   trace("\n");
    902 }
    903 
    904 Oid *enterprise_name_to_oid(char *name)
    905 {
    906   NameOidPair *np;
    907 
    908   if(name == NULL) return NULL;
    909   for(np=first_name_oid_pair;np;np=np->next){
    910         if(np->name!=NULL && !strcmp(name,np->name))
    911                 return np->oid;
    912   }
    913   return NULL;
    914 }
    915 
    916 static NameOidPair* set_name_and_oid_pair(char *inbuf)
    917 {
    918         char *str;
    919         char *name_str, *oid_str;
    920         Oid  *oid = NULL;
    921 	NameOidPair *np;
    922 
    923         if ((inbuf== NULL) || (inbuf[0]== '#')) return NULL;
    924 
    925         /* first "  for name */
    926         if ((str = strchr(inbuf, '"')) == NULL) return NULL;
    927         str++;
    928         name_str = str;
    929 
    930                 /* second " for name */
    931         if ((str = strchr(str, '"')) == NULL) return NULL;
    932         *str = '\0';
    933 
    934         str++;
    935         /* first " for oid_str*/
    936         if ((str = strchr(str, '"')) == NULL)  return NULL;
    937         str++;
    938         oid_str = str;
    939 
    940         /* second " for oid_str*/
    941         if ((str = strchr(str, '"')) == NULL) return NULL;
    942         *str = '\0';
    943         oid = SSAOidStrToOid(oid_str,error_label);
    944 
    945 	np = calloc(1,sizeof(NameOidPair));
    946 	if(np==NULL){
    947 	  error("calloc failed");
    948 	  return NULL;
    949 	}
    950 	np->oid = oid;
    951 	np->name = strdup(name_str);
    952 
    953 	if (np->name == NULL) {
    954 		free(np);
    955 		return(NULL);
    956 	}
    957 
    958 	return np;
    959 }
    960 
    961 static void insert_name_oid_pair(char *name_str,char* oid_str)
    962 {
    963   char inbuf[MAX_BUF_SIZE];
    964   NameOidPair *np;
    965 
    966    (void)sprintf(inbuf,"\"%s\"   \"%s\"\n",name_str,oid_str);
    967    if( (np=set_name_and_oid_pair(inbuf)) != NULL){
    968 		np->next = first_name_oid_pair;
    969 		first_name_oid_pair = np;
    970    }
    971 }
    972 
    973 void load_enterprise_oid(char* filename)
    974 {
    975   FILE *fd;
    976   char inbuf[MAX_BUF_SIZE];
    977   NameOidPair *np;
    978 
    979   if(filename==NULL) return;
    980   fd = fopen(filename,"r");
    981   if(fd==NULL){
    982 	error("can open the file %s",filename);
    983 	return;
    984   }
    985   while(fgets(inbuf,MAX_BUF_SIZE,fd)){
    986 	if( (np=set_name_and_oid_pair(inbuf)) != NULL){
    987 	/* insert np */
    988 		np->next = first_name_oid_pair;
    989 		first_name_oid_pair = np;
    990 	}
    991   }
    992   /* insert a couple of extra name-oid pairs:
    993 	sun, snmp
    994    */
    995 	insert_name_oid_pair("snmp", "1.3.6.1.2.1.11");
    996 	insert_name_oid_pair("sun", "1.3.6.1.4.1.42.2.1.1");
    997 
    998   (void)fclose(fd);
    999 }
   1000 
   1001 static EFilter* find_efilter(Oid* oid)
   1002 {
   1003   EFilter *filter;
   1004 
   1005   for(filter=first_efilter;filter;filter=filter->next_efilter)
   1006   {
   1007 	if(SSAOidCmp(filter->enterprise,oid)==0) return filter;
   1008   }
   1009   return NULL;
   1010 }
   1011 
   1012 static TrapSlot* find_trap_slot(int num,EFilter *filter)
   1013 {
   1014   TrapSlot *slot;
   1015 
   1016   for(slot=filter->first_trap_slot;slot;slot=slot->next_trap_slot)
   1017 	if(slot->num==num) return slot;
   1018   return NULL;
   1019 }
   1020 
   1021 void trap_filter_action(Oid *oid,int generic,int specific,
   1022         uint32_t time_stamp,SNMP_variable *variables)
   1023 {
   1024   EFilter *filter;
   1025   TrapSlot *slot;
   1026   SubGroup *group;
   1027   Manager *manager;
   1028   static Subid snmp_subids[] = {1,3,6,1,2,1,11};
   1029   static Oid snmp_oid = {snmp_subids, 7};
   1030   int trap_num;
   1031   IPAddress my_ip_address;
   1032 
   1033   (void)memset(&my_ip_address, 0, sizeof(IPAddress));
   1034 
   1035   if(oid==NULL) return;
   1036   if( (filter=find_efilter(oid))==NULL ) return;
   1037   if(SSAOidCmp(oid,&snmp_oid)==0)
   1038 	trap_num = generic;
   1039   else
   1040 	trap_num = specific;
   1041   if( (slot=find_trap_slot(trap_num,filter))==NULL ) return;
   1042   for(group=slot->first_sub_group;group;group=group->next_sub_group){
   1043 	if(group->first_sub_member!=NULL){
   1044 	  for(manager=group->first_sub_member->first_manager;manager;
   1045 		manager=manager->next_manager){
   1046 		trap_send_raw(&(manager->ip_address),my_ip_address,
   1047 			group->first_sub_member->community_string,0,
   1048 			oid,generic,specific, SNMP_TRAP_PORT,time_stamp,
   1049 			variables,error_label);
   1050 	  }
   1051 	}
   1052   }
   1053 }
   1054 
   1055