freebsd-dev/sys/netatm/sigpvc/sigpvc_subr.c
Poul-Henning Kamp 1820df7a2d Add new files for HARP3
Host ATM Research Platform (HARP), Network Computing Services, Inc.
This software was developed with the support of the Defense Advanced
Research Projects Agency (DARPA).
1998-09-15 08:23:17 +00:00

182 lines
3.9 KiB
C

/*
*
* ===================================
* HARP | Host ATM Research Platform
* ===================================
*
*
* This Host ATM Research Platform ("HARP") file (the "Software") is
* made available by Network Computing Services, Inc. ("NetworkCS")
* "AS IS". NetworkCS does not provide maintenance, improvements or
* support of any kind.
*
* NETWORKCS MAKES NO WARRANTIES OR REPRESENTATIONS, EXPRESS OR IMPLIED,
* INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE, AS TO ANY ELEMENT OF THE
* SOFTWARE OR ANY SUPPORT PROVIDED IN CONNECTION WITH THIS SOFTWARE.
* In no event shall NetworkCS be responsible for any damages, including
* but not limited to consequential damages, arising from or relating to
* any use of the Software or related support.
*
* Copyright 1994-1998 Network Computing Services, Inc.
*
* Copies of this Software may be made, however, the above copyright
* notice must be reproduced on all copies.
*
* @(#) $Id: sigpvc_subr.c,v 1.7 1998/06/29 21:52:25 mks Exp $
*
*/
/*
* PVC-only Signalling Manager
* ---------------------------
*
* Subroutines
*
*/
#ifndef lint
static char *RCSid = "@(#) $Id: sigpvc_subr.c,v 1.7 1998/06/29 21:52:25 mks Exp $";
#endif
#include <netatm/kern_include.h>
#include <netatm/sigpvc/sigpvc.h>
#include <netatm/sigpvc/sigpvc_var.h>
extern struct sp_info sigpvc_vcpool;
/*
* Create a SigPVC Permanent Virtual Channel
*
* This function will construct a vccb for a "sigpvc-controlled" PVC
* and create the service stack requested by the user.
*
* Must be called at splnet.
*
* Arguments:
* pvp pointer to sigpvc protocol instance
* cvp pointer to CM's connection VCC
* errp location to store an error code if CALL_FAILED is returned
*
* Returns:
* CALL_FAILED - pvc creation failed
* CALL_CONNECTED - pvc has been successfully created
*
*/
int
sigpvc_create_pvc(pvp, cvp, errp)
struct sigpvc *pvp;
Atm_connvc *cvp;
int *errp;
{
Atm_addr_pvc *pp;
struct vccb *vcp;
u_int vpi, vci;
pp = (Atm_addr_pvc *)cvp->cvc_attr.called.addr.address;
vpi = ATM_PVC_GET_VPI(pp);
vci = ATM_PVC_GET_VCI(pp);
/*
* Verify requested VPI,VCI
*/
if ((vpi > pvp->pv_pif->pif_maxvpi) ||
(vci == 0) || (vci > pvp->pv_pif->pif_maxvci)) {
*errp = ERANGE;
return (CALL_FAILED);
}
for (vcp = Q_HEAD(pvp->pv_vccq, struct vccb); vcp;
vcp = Q_NEXT(vcp, struct vccb, vc_sigelem)) {
if ((vcp->vc_vpi == vpi) &&
(vcp->vc_vci == vci)) {
*errp = EADDRINUSE;
return (CALL_FAILED);
}
}
/*
* Verify network interface
*/
if (cvp->cvc_attr.nif) {
if (cvp->cvc_attr.nif->nif_pif != pvp->pv_pif) {
*errp = EINVAL;
return (CALL_FAILED);
}
}
/*
* Allocate control block for PVC
*/
vcp = (struct vccb *)atm_allocate(&sigpvc_vcpool);
if (vcp == NULL) {
*errp = ENOMEM;
return (CALL_FAILED);
}
/*
* Fill in VCCB
*/
vcp->vc_type = VCC_PVC | VCC_IN | VCC_OUT;
vcp->vc_proto = ATM_SIG_PVC;
vcp->vc_sstate = VCCS_ACTIVE;
vcp->vc_ustate = VCCU_OPEN;
vcp->vc_pif = pvp->pv_pif;
vcp->vc_nif = cvp->cvc_attr.nif;
vcp->vc_vpi = vpi;
vcp->vc_vci = vci;
vcp->vc_connvc = cvp;
/*
* Put VCCB on sigpvc queue
*/
ENQUEUE(vcp, struct vccb, vc_sigelem, pvp->pv_vccq);
/*
* Pass back VCCB to connection manager
*/
cvp->cvc_vcc = vcp;
/*
* PVC is ready to go!
*/
return (CALL_CONNECTED);
}
/*
* Close a SigPVC VCC
*
* Clean up vccb, note that it's closing and wait for its freeing.
*
* Arguments:
* vcp pointer to connection's VCC control block
*
* Returns:
* none
*
*/
void
sigpvc_close_vcc(vcp)
struct vccb *vcp;
{
/*
* Sanity check (actually design-flaw check)
*/
if (vcp->vc_connvc->cvc_upcnt || vcp->vc_connvc->cvc_downcnt)
panic("sigpvc_close_vcc: stack call");
/*
* Set state variables
*/
vcp->vc_ustate = VCCU_CLOSED;
vcp->vc_sstate = VCCS_FREE;
/*
* Wait for user to free resources
*/
}