/* * Copyright (c) 1998 Regents of The University of Michigan. * All Rights Reserved. See COPYRIGHT. */ /********** machine.c **********/ #include #include #include #include #include #include #include #include #include #include #include #include #include #include "nefu.h" #include "ll.h" char *machine_errstr[] = { "machine_errstr: no error!", "can't be in the stb twice", #define MACHINE_INSERT 1 NULL }; char * machine_create( char *m_name ) { struct machine *m_node; struct hostent *hp; char *e; if (( m_node = (struct machine*)malloc( sizeof( struct machine ))) == NULL ) { perror( "malloc" ); exit( 1 ); } memset( m_node, 0, sizeof( struct machine )); if (( m_node->m_name = strdup( m_name )) == NULL ) { perror( "strdup" ); exit( 1 ); } /* workaround for bugs in the gethostbyname() routine */ if (( m_node->m_sin.sin_addr.s_addr = inet_addr( m_name )) == -1 ) { /* do internet data for this machine */ if (( hp = gethostbyname( m_node->m_name )) == NULL ) { m_node->m_dns_status = MACHINE_NO_DNS; m_node->m_next_dns = machines_no_dns; machines_no_dns = m_node; } else if ( hp->h_addr_list[ 1 ] != NULL ) { m_node->m_dns_status = MACHINE_MULT_IPS; m_node->m_next_dns = machines_no_dns; machines_no_dns = m_node; } else { memcpy( &(m_node->m_sin.sin_addr.s_addr), hp->h_addr_list[ 0 ], (unsigned int)hp->h_length ); } } /* give machine implicit dependancy */ if (( e = test( m_node, NULL, T_DEFAULT, 0, NULL )) != NULL ) { return( e ); } /* place new machine node in to stab table */ if ( ll_insert( &machine_stab, m_node->m_name, m_node ) != 0 ) { return( machine_errstr[ MACHINE_INSERT ]); } return( 0 ); } struct machine* machine_lookup( char *m_name ) { return((struct machine*)ll_lookup( machine_stab, m_name )); } int machine_errors( void ) { struct stab_entry *st; int err = 0; struct machine *m; struct test *m_test, *t_path; for ( st = machine_stab; st != NULL; st = st->st_next ) { m = (struct machine*)st->st_data; m_test = m->m_test; if (( m_test == NULL ) || ( m->m_defined == 0 )) { /* something horribly wrong with this machine */ fprintf( stderr, "machine %s not defined %d\n", m->m_name, m->m_defined); err++; continue; } t_path = m_test->t_parent; m_test->t_loop = m_test; /* loop if comes back to self */ for ( ;; ) { if ( t_path == NULL ) { /* at the root */ break; } if ( t_path->t_loop == m_test ) { /* loop detected */ fprintf( stderr, "Loop detected:\n" ); fprintf( stderr, "\t%s -> ", m->m_name ); t_path = m_test->t_parent; do { fprintf( stderr, "%s -> ", t_path->t_machine->m_name ); t_path = t_path->t_parent; } while ( t_path->t_loop != m_test ); fprintf( stderr, "%s\n\n", t_path->t_machine->m_name ); err++; break; } else { /* no resolution yet */ t_path->t_loop = m_test; t_path = t_path->t_parent; } } } return( err ); } void machine_rcode_assign( struct machine *m, struct rcode *r ) { int len; for ( ; r != NULL; r = r->r_next ) { if ( ll_lookup( m->m_rcodes, r->r_code ) == NULL ) { ll_insert( &m->m_rcodes, r->r_code, r ); ll_insert( &r->r_machines, m->m_name, m ); /* does the default test need to inherit our rcode? */ if ( m->m_ping == 0 ) { m->m_test->t_rcodes = m->m_rcodes; if ( m->m_test->t_rlist == NULL ) { if (( m->m_test->t_rlist = strdup( r->r_code )) == NULL ) { perror( "strdup" ); exit( 1 ); } } else { len = strlen( m->m_test->t_rlist ) + strlen( r->r_code ) + 3; if (( m->m_test->t_rlist = (char*) realloc( m->m_test->t_rlist, len )) == NULL ) { perror( "realloc" ); exit( 1 ); } sprintf( m->m_test->t_rlist, "%s, %s", m->m_test->t_rlist, r->r_code ); } } } } }