[Contents] [Prev. Chapter] [Next Section] [Index] [Help]

B    Connection Programming Examples

This appendix contains programming code fragments for the following connection-related tasks:


[Contents] [Prev. Chapter] [Next Section] [Index] [Help]

B.1    Making a Call

Example B-1 shows one way to make a call for point-to-point connections and to make the first call for a point-to-multipoint connection.

Example B-1:  Making a Call Code Fragment

make_call(unsigned char *called_party)
{
    register atm_uni_call_ie_p iep, ie;
    register union atm_cmi_addr ra;
    register atm_vc_services_p vcs;
    atm_error_t retval;
    int rv = ESUCCESS;
    extern atm_cvg_handle_t my_handle;
    extern atm_bind_handle_t my_bind;
 
    /* Get memory for setup IEs */
    iep = ie = atm_cmm_alloc_ie(3);
    if(ie == NULL)
    {
        rv =  ENOMEM;
        goto bad;
    }
 
    /* Get memory for services structure */
    vcs = atm_cmm_alloc_services();
    if(vcs == NULL)
    {
        atm_cmm_free_ie(iep);
        rv =  ENOMEM;
        goto bad;
    }
 
    /* Get the storage for the endpoint address */
    ra.addr = atm_cmm_alloc_addr();
    if(ra.addr == NULL)
    {
        atm_cmm_free_ie(iep);
        atm_cmm_free_services(vcs);
        rv = ENOMEM;
        goto bad;
    }
 
    /* Set cell rate information for ABR traffic.
     * Cell rates - cells/sec. 1 cell = 53 bytes.
     */
     vcs->fpeakcr[ATM_CLP_1] = 0x800;
     vcs->bpeakcr[ATM_CLP_1] = 0x800;
 
     vcs->valid_rates =  ATM_VCRV_FPEAK1 |
			 ATM_VCRV_BPEAK1;
 
     /* Best effort service class and enable tagging */
     vcs->flags = ATM_SERVICES_BEI;
 
    /* Set the Qos */
    vcs->fqos = ATM_QOS_CLASSA;
    vcs->bqos = ATM_QOS_CLASSA;
 
    /* Set the MTU in the services structure */
    vcs->fmtu = 1500;
    vcs->bmtu = 1500;
 
    /* Set the BB bearer class in the services structure */
    vcs->bearer_class = ATM_BBEARER_BCOB_X;
 
    /* Fill out the AAL 5 IE */
    ie->ie_type = ATM_IET_AAL5;
    ATM_IE_SETVAL(ie->ie.aal_params.aal5.fsdu,1500);
    ATM_IE_SETVAL(ie->ie.aal_params.aal5.bsdu,1500);
    ATM_IE_SETVAL(ie->ie.aal_params.aal5.mode,
			ATM_AAL_MESG_MODE);
    ATM_IE_SETVAL(ie->ie.aal_params.aal5.sscs,
			ATM_AAL_SSCS_NULL);
 
    /* Fill out the BLLI IE */
    ie++;
    ie->last = 1;
    ie->ie_type = ATM_IET_BBLOW;
    ATM_IE_SETVAL(ie->ie.bb_low_layer.layer2proto,
			ATM_BLLI_UIL2_LAN_LLC_8022);
 
 
    bcopy(called_party,ra.addr->address,ATMADDR_LEN);
    ra.addr->ton = 0;
    ra.addr->anpi = 2;
 
 
    if((retval = atm_cmm_connect(my_handle,ATM_CT_PTP,  [1]
	my_bind,ra,iep,ATM_AGE_FOREVER,vcs)) !=
		ATM_CAUSE_GOOD)
    {
        atm_cmm_free_ie(iep);
        atm_cmm_free_services(vcs);
        atm_cmm_free_addr(ra.addr);
        ATM_FREE(ivc);
        rv =  EIO;
        goto bad;
    }
 
    /* The VC is valid if the call is proceeding! */
    ra.addr->vc->conv_pp1 =
    ra.addr->conv_p1 =
    ra.addr->conv_p2 =
 
    return rv;
}

  1. For point-to-multipoint connections, use the ATM_CT_PTM argument in place of the ATM_CT_PTP argument. [Return to example]


[Contents] [Prev. Chapter] [Prev. Section] [Next Section] [Index] [Help]

B.2    Adding More Parties to a Point-to-Multipoint Connection

Example B-2 shows one way to add more parties to the VC associated with the first call in a point-to-multipoint connection.

Example B-2:  Adding Parties to a Point-to-Multipoint Connection Code Fragment

add_leaf(atm_vc_p vc, unsigned char *new_leaf)
{
    register atm_uni_call_ie_p iep, ie;
    register struct atm_addr_p leaf;
    atm_error_t retval;
    int rv = ESUCCESS;
    extern atm_cvg_handle_t my_handle;
    extern atm_bind_handle_t my_bind;
 
    /* Get memory for setup IEs */
    iep = ie = atm_cmm_alloc_ie(3);
    if(ie == NULL)
    {
        rv =  ENOMEM;
        goto bad;
    }
 
    /* Get the storage for the endpoint address */
    leaf = atm_cmm_alloc_addr();
    if(leaf == NULL)
    {
        atm_cmm_free_ie(iep);
        atm_cmm_free_services(vcs);
        rv = ENOMEM;
        goto bad;
    }
 
    /* Fill out the AAL 5 IE */
    ie->ie_type = ATM_IET_AAL5;
    ATM_IE_SETVAL(ie->ie.aal_params.aal5.fsdu,1500);
    ATM_IE_SETVAL(ie->ie.aal_params.aal5.bsdu,1500);
    ATM_IE_SETVAL(ie->ie.aal_params.aal5.mode,
			ATM_AAL_MESG_MODE);
    ATM_IE_SETVAL(ie->ie.aal_params.aal5.sscs,
			ATM_AAL_SSCS_NULL);
 
    /* Fill out the BLLI IE */
    ie++;
    ie->last = 1;
    ie->ie_type = ATM_IET_BBLOW;
    ATM_IE_SETVAL(ie->ie.bb_low_layer.layer2proto,
			ATM_BLLI_UIL2_LAN_LLC_8022);
 
 
    bcopy(new_leaf,leaf->address,ATMADDR_LEN);
    leaf->ton = 0;
    leaf->anpi = 2;
 
 
    if((retval = atm_cmm_add(my_handle,leaf,ie,vc)) !=
ATM_CAUSE_GOOD)
    {
        atm_cmm_free_ie(iep);
        atm_cmm_free_addr(leaf);
        ATM_FREE(ivc);
        rv =  EIO;
        goto bad;
    }
 
    /* The VC is valid if the call is proceeding! */
    ra.addr->conv_p1 =
    ra.addr->conv_p2 =
 
    return rv;
}


[Contents] [Prev. Chapter] [Prev. Section] [Index] [Help]

B.3    Processing an Incoming Call

Example B-3 shows how a convergence module processes an incoming call.

Example B-3:  Incoming Call Processing Code Fragment

atm_error_t
new_connect(void *bind_handle,
        atm_addr_p           addr,
        atm_bind_handle_t    bind,
        atm_vc_p             vc,
        atm_uni_call_ie_p    *reply,
        atm_vc_services_p    requested,
        atm_vc_services_p    *avail)
{
    register atm_uni_call_ie_p iep = NULL;
    atm_uni_call_ie_p rblli = NULL, raal = NULL;
    atm_uni_call_ie_p nblli;
 
    /* Verify IEs to make sure they are valid for our service */
    if(addr != NULL && (iep = addr->setup))
    {
        for(;; iep++)
        {
            switch(iep->ie_type)
            {
            /* Things we do not want to see */
            case ATM_IET_AAL1:
            case ATM_IET_AAL2:
            case ATM_IET_AAL3:
            case ATM_IET_AALU:
                return ATM_CAUSE_APNS;
 
            /* Do not need to look at these */
            case ATM_IET_BBBC:
            case ATM_IET_BBHI:
                break;
 
            case ATM_IET_REPEAT:
                break;
 
            case ATM_IET_AAL5:
                /* Make sure the MTU is supported.  Accept
                 * an MTU greater than 1500 and then
                 * negotiate it down until larger MTUs are
                 * supported.
                 */
                if(ATM_IE_ISVALID(iep->ie.aal_params.aal5.fsdu))
                {
                    if(ATM_IE_GETVAL(iep->ie.aal_params.aal5.fsdu)
				< 1500)
                        	return ATM_CAUSE_APNS;
                }
                if(ATM_IE_ISVALID(iep->ie.aal_params.aal5.bsdu))
                {
                    if(ATM_IE_GETVAL(iep->ie.aal_params.aal5.bsdu)
				< 1500)
                        	return ATM_CAUSE_APNS;
                }
                raal = iep;
                break;
 
            case ATM_IET_BBLOW:
                /* Check for LLC encapsulation */
                if(ATM_IE_ISVALID(iep->ie.bb_low_layer.layer2proto))
                {
                    if(ATM_IE_GETVAL(iep->ie.bb_low_layer.layer2proto)
				!= 0x0C)
                        	return ATM_CAUSE_BCNI;
                    rblli = iep;
                    break;
                }
                break;
            }
            if(iep->last)
                break;
        }
 
        /* Make sure the required info is present */
        if(rblli == NULL)    /* No required BLLI */
        {
            addr->diag_length = 2;
            addr->diagnostic[0] = 0x5;
            addr->diagnostic[1] = 0x5e;
            return ATM_CAUSE_CR;
        }
        if(raal == NULL)    /* No required AAL parameters */
        {
            addr->diag_length = 2;
            addr->diagnostic[0] = 0x5;
            addr->diagnostic[1] = 0x58;
            return ATM_CAUSE_CR;
        }
 
        /* Set up reply values */
        iep = atm_cmm_alloc_ie(2);
        if(!iep)
            return ATM_CAUSE_RUU;
        bcopy(raal,iep,sizeof(atm_uni_call_ie_t));
        ATM_IE_SETVAL(iep->ie.aal_params.aal5.fsdu,1500);
        ATM_IE_SETVAL(iep->ie.aal_params.aal5.bsdu,1500);
        nblli = iep+1;
        bcopy(rblli,nblli,sizeof(atm_uni_call_ie_t));
        nblli->last = 1;
        *reply = iep;
 
        /* Now take care of the services stuff */
        if ( (avail) && (*avail) ) {
                (*avail)->fmtu = (*avail)->bmtu = 1500;
        }
 
    }
 
    vc->conv_pp1 =
    vc->conv_pp2 =
 
    /* If there is no signalling protocol, then this is a PVC */
    if(vc->ppa->sig != NULL)
    {
        addr->conv_p1 =
        addr->conv_p2 =
    }
 
    return ATM_CAUSE_GOOD;
}


[Contents] [Prev. Chapter] [Prev. Section] [Index] [Help]