Example #1
0
static STATUS
gcn_result( GCN_MBUF *mbout, i4 opcode, i4 count )
{
    char	*msg_out;
    GCN_MBUF	*mbuf;
    STATUS	status = OK;

    mbuf = gcn_add_mbuf( mbout, TRUE, &status );
    if ( status != OK ) return( status );

    mbuf->type = GCN_RESULT;
    msg_out = mbuf->data;
    msg_out += gcu_put_int( msg_out, opcode );
    msg_out += gcu_put_int( msg_out, count );
    mbuf->used = msg_out - mbuf->data;

    return( OK );
}
Example #2
0
STATUS
gcn_get_auth( GCN_RESOLVE_CB *grcb, GCN_MBUF *mbout )
{
    char	passwd[ 20 ];	/* Need size > ((len + 8) * 2) */
    char	*m;
    GCN_MBUF 	*mbuf;
    STATUS	status;
    i4		i;

    /* 
    ** Encrypt the NOUSER password, so the local GCC can decrypt it.
    */
    gcn_login(GCN_VLP_COMSVR, GCN_VLP_V1, TRUE, GCN_NOUSER, GCN_NOPASS, passwd);

    /*
    ** Produce the GCN2_RESOLVED message.
    */
    if ( (status = gcn_connect_info( grcb, mbout, 
    				     GCN_NOUSER, passwd, 0, NULL )) != OK )
	return( status );

    /*
    ** Prepare GCN_NS_AUTHORIZE message.
    */
    mbuf = gcn_add_mbuf( mbout, TRUE, &status );
    if ( status != OK )  return status;

    m = mbuf->data;
    m += gcu_put_int( m, GCN_AUTH_TICKET );
    m += gcu_put_str( m, grcb->username );
    m += gcu_put_str( m, IIGCn_static.lcl_vnode );
    m += gcu_put_str( m, grcb->vnode );
    m += gcu_put_int( m, IIGCn_static.ticket_cache_size );
    mbuf->used = m - mbuf->data;
    mbuf->type = GCN_NS_AUTHORIZE;

    return( OK );
}
Example #3
0
static STATUS
gcn_op_servers
( 
    GCN_MBUF	*mbout, 
    GCN_TUP	*masktup,
    i4		opflags
)
{
    QUEUE		*q;
    GCN_MBUF		*mbuf;
    char		*msg_out = NULL;
    char		*msg_post = NULL;
    char		*row_ptr = NULL;
    i4			row_count = 0;
    STATUS		status = OK;

    /*
    ** User ID is not applicable for registered servers.
    */
    masktup->uid = "";

    for(
	 q = IIGCn_static.name_queues.q_next;
	 q != &IIGCn_static.name_queues;
	 q = q->q_next
       )
    {
	GCN_QUE_NAME	*nq = (GCN_QUE_NAME *)q;
	GCN_TUP		*tupvec[ GCN_SVR_MAX ];
	PTR		scan_cb = NULL;
	i4		i, tupcount;

	/*
	** Skip non-server and registry queues.
	** Also, ignore errors on individual queues.
	*/
        if ( ! nq->gcn_transient )  continue;
	if ( ! STcompare( GCN_NS_REG, nq->gcn_type ) )  continue;
	if ( gcn_nq_lock( nq, FALSE ) != OK )  continue;

	/* 
	** Call gcn_nq_scan in a loop to get a batch at a time. 
	*/
	do
	{
	    /* Load up the next entries */
	    tupcount = gcn_nq_scan( nq, masktup, &scan_cb, 
				    GCN_SVR_MAX, tupvec, NULL );

	    /* Loop through server entries */
	    for( i = 0; i < tupcount; i++ )
	    {
		GCN_TUP	*tup = tupvec[ i ];
		GCN_TUP	newtup;
		char 	buf[ 1024 ];
		char	*p = buf;

		newtup.uid = tup->uid;
		newtup.obj = tup->obj;
		newtup.val = tup->val;
		p += gcu_put_str( p, nq->gcn_type );
		p += gcn_put_tup( p, &newtup );

		if ( msg_out  &&  (p - buf) + msg_out > msg_post )
		{
		    /*
		    ** Update the row count for this message.
		    ** We send individual messages rather than
		    ** continued messages hoping (in vain) that
		    ** the client won't need to piece message
		    ** segments back together.
		    */
		    gcu_put_int( row_ptr, row_count );
		    mbuf->used = msg_out - mbuf->data;
		    row_count = 0;
		    msg_out = NULL;
		}

		if ( ! msg_out )
		{
		    mbuf = gcn_add_mbuf( mbout, TRUE, &status );
		    if ( status != OK )  return( status );

		    mbuf->type = GCN_RESULT;
		    msg_out = mbuf->data;
		    msg_post = mbuf->data + mbuf->len;

		    msg_out += gcu_put_int( msg_out, GCN_RET );
		    row_ptr = msg_out;
		    msg_out += gcu_put_int( msg_out, 0 );
		}
			    
		MEcopy( buf, p - buf, msg_out );
		msg_out += p - buf;
		row_count++;
	    }
	} while( tupcount == GCN_SVR_MAX );

	gcn_nq_unlock( nq );
    }

    if ( ! msg_out )
	status = gcn_result( mbout, GCN_RET, 0 );
    else
    {
	(void)gcu_put_int( row_ptr, row_count );
	mbuf->used = msg_out - mbuf->data;
    } 

    return( status );
}
Example #4
0
static STATUS
gcn_op_get
( 
    GCN_MBUF	*mbout, 
    char	*gcn_type,
    GCN_TUP	*masktup,
    i4		opflags
)
{
    GCN_QUE_NAME	*nq;
    GCN_MBUF		*mbuf;
    char		*msg_out = NULL;
    char		*msg_post = NULL;
    char		*row_ptr = NULL;
    i4			row_count = 0;
    STATUS		status = OK;

    /*
    ** Find desired class
    */
    if ( ! (nq = gcn_nq_find( gcn_type )) )
	if ( opflags & GCN_OPFLAG_SRV )
	    return( gcn_result( mbout, GCN_RET, 0 ) );	/* No servers */
	else
	{
	    /* Can't find class.  */
	    gcn_error( E_GC0100_GCN_SVRCLASS_NOTFOUND, NULL, gcn_type, mbout );
	    return( E_GC0100_GCN_SVRCLASS_NOTFOUND );
	}

    /*
    ** User ID is not applicable for registered servers.
    */
    if ( nq->gcn_transient )  masktup->uid = "";

    if ( gcn_nq_lock( nq, FALSE ) == OK )
    {
	GCN_TUP	*tupvec[ GCN_SVR_MAX ];
	PTR	scan_cb = NULL;
	i4	i, tupcount;

	/* 
	** Call gcn_nq_scan in a loop to get a batch at a time. 
	*/
	do
	{
	    /* Load up the next entries */
	    tupcount = gcn_nq_scan( nq, masktup, &scan_cb, 
				    GCN_SVR_MAX, tupvec, NULL );

	    /* Loop through server entries */
	    for( i = 0; i < tupcount; i++ )
	    {
		GCN_TUP	*tup = tupvec[ i ];
		GCN_TUP	newtup;
		char 	buf[ 1024 ];
		char	*p = buf;
		char	tmpbuf[ 128 ];
		char	*tmp = tmpbuf;

		p += gcu_put_str( p, nq->gcn_type );
		newtup.uid = tup->uid;
		newtup.obj = tup->obj;
		newtup.val = tup->val;

		/*
		** VNODE login passwords are not exposed.
		*/
		if ( opflags & GCN_OPFLAG_LOGIN )
		{
		    char	*pv[2];
		    i4		len = STlength( tup->val ) + 1;

		    if ( len > sizeof( tmpbuf )  &&
		    	 ! (tmp = (char *)MEreqmem(0, len, FALSE, NULL)) )
		    {
			gcn_nq_unlock( nq );
			return( E_GC0121_GCN_NOMEM );
		    }

		    (void)gcu_words( tup->val, tmp, pv, ',', 2 );
		    newtup.val = pv[0];
		}

		p += gcn_put_tup( p, &newtup );
		if ( tmp != tmpbuf )  MEfree( (PTR)tmp );

		if ( msg_out  &&  (p - buf) + msg_out > msg_post )
		{
		    /*
		    ** Update the row count for this message.
		    ** We send individual messages rather than
		    ** continued messages hoping (in vain) that
		    ** the client won't need to piece message
		    ** segments back together.
		    */
		    gcu_put_int( row_ptr, row_count );
		    mbuf->used = msg_out - mbuf->data;
		    row_count = 0;
		    msg_out = NULL;
		}

		if ( ! msg_out )
		{
		    mbuf = gcn_add_mbuf( mbout, TRUE, &status );
		    if ( status != OK )
		    {
			gcn_nq_unlock( nq );
			return( status );
		    }

		    mbuf->type = GCN_RESULT;
		    msg_out = mbuf->data;
		    msg_post = mbuf->data + mbuf->len;

		    msg_out += gcu_put_int( msg_out, GCN_RET );
		    row_ptr = msg_out;
		    msg_out += gcu_put_int( msg_out, 0 );
		}
			    
		MEcopy( buf, p - buf, msg_out );
		msg_out += p - buf;
		row_count++;
	    }
	} while( tupcount == GCN_SVR_MAX );

	if ( ! msg_out )
	    status = gcn_result( mbout, GCN_RET, 0 );
	else
	{
	    (void)gcu_put_int( row_ptr, row_count );
	    mbuf->used = msg_out - mbuf->data;
	} 

	gcn_nq_unlock( nq );
    }
    else
    {
	status = E_GC0134_GCN_INT_NQ_ERROR;
	gcn_error( status, NULL, NULL, mbout );
    }

    return( status );
}
Example #5
0
STATUS
gcn_make_auth( GCN_MBUF *mbin, GCN_MBUF *mbout, i4 prot )
{
    char	*username;
    i4		rq_count;
    i4		auth_type;
    i4		i, userlen;
    STATUS	status;
    GCN_MBUF	*mbuf;
    char	*msg_out;
    char	*m, *end;
    char	rtickvec[ GCN_DFLT_L_TICKVEC ][ GCN_L_TICKET ];

    /* 
    ** Unpack GCN_NS_AUTHORIZE message 
    */
    m = mbin->data;
    end = m + mbin->len;
    m += gcu_get_int( m, &auth_type );

    m += gcu_get_int( m, &userlen );
    username = m;
    userlen = min( userlen, end - m );
    m += userlen;

    m += gcu_get_int( m, &i );		/* Skip */
    m += min( i, end - m );

    m += gcu_get_int( m, &i );		/* Skip */
    m += min( i, end - m );

    m += gcu_get_int( m, &rq_count );
    if ( rq_count > GCN_DFLT_L_TICKVEC )  rq_count = GCN_DFLT_L_TICKVEC;
    if ( rq_count > IIGCn_static.ticket_cache_size )  
        rq_count = IIGCn_static.ticket_cache_size;

    /*
    ** Verify message.
    */
    if ( auth_type != GCN_AUTH_TICKET )  
    {
	gcn_error( E_GC0141_GCN_INPW_NOSUPP, NULL, NULL, mbout );
	return( E_GC0141_GCN_INPW_NOSUPP );
    }

    /* 
    ** Generate tickets 
    */
    username[ userlen ] = EOS;
    status = gcn_make_tickets( username, IIGCn_static.lcl_vnode,
			       &rtickvec[0][0], rq_count, GCN_L_TICKET,
			       prot );
    if ( status != OK )
    {
	gcn_error( status, (CL_ERR_DESC *)0, (char *)0, mbout );
	return( status );
    }

    /* 
    ** Pack GCN_AUTHORIZED message 
    */
    mbuf = gcn_add_mbuf( mbout, TRUE, &status );
    if ( status != OK )  return( status );

    m = mbuf->data;
    m += gcu_put_int( m, auth_type );
    m += gcu_put_int( m, rq_count );

    for( i = 0; i < rq_count; i++ )  m += gcu_put_str( m, rtickvec[ i ] );

    mbuf->used = m - mbuf->data;
    mbuf->type = GCN_AUTHORIZED;

    return( OK );
}