Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-or-later
0002 /******************************************************************************
0003  *
0004  *  (C)Copyright 1998,1999 SysKonnect,
0005  *  a business unit of Schneider & Koch & Co. Datensysteme GmbH.
0006  *
0007  *  See the file "skfddi.c" for further information.
0008  *
0009  *  The information in this file is provided "AS IS" without warranty.
0010  *
0011  ******************************************************************************/
0012 
0013 /*
0014  * *******************************************************************
0015  * This SBA code implements the Synchronous Bandwidth Allocation
0016  * functions described in the "FDDI Synchronous Forum Implementer's
0017  * Agreement" dated December 1th, 1993.
0018  * *******************************************************************
0019  *
0020  *  PURPOSE: The purpose of this function is to control
0021  *       synchronous allocations on a single FDDI segment.
0022  *       Allocations are limited to the primary FDDI ring.
0023  *       The SBM provides recovery mechanisms to recover
0024  *       unused bandwidth also resolves T_Neg and
0025  *       reconfiguration changes. Many of the SBM state
0026  *       machine inputs are sourced by the underlying
0027  *       FDDI sub-system supporting the SBA application.
0028  *
0029  * *******************************************************************
0030  */
0031 
0032 #include "h/types.h"
0033 #include "h/fddi.h"
0034 #include "h/smc.h"
0035 #include "h/smt_p.h"
0036 
0037 
0038 #ifndef SLIM_SMT
0039 
0040 #ifdef ESS
0041 
0042 #ifndef lint
0043 #define LINT_USE(x)
0044 #else
0045 #define LINT_USE(x) (x)=(x)
0046 #endif
0047 #define MS2BCLK(x)  ((x)*12500L)
0048 
0049 /*
0050     -------------------------------------------------------------
0051     LOCAL VARIABLES:
0052     -------------------------------------------------------------
0053 */
0054 
0055 static const u_short plist_raf_alc_res[] = { SMT_P0012, SMT_P320B, SMT_P320F,
0056                     SMT_P3210, SMT_P0019, SMT_P001A,
0057                     SMT_P001D, 0 } ;
0058 
0059 static const u_short plist_raf_chg_req[] = { SMT_P320B, SMT_P320F, SMT_P3210,
0060                     SMT_P001A, 0 } ;
0061 
0062 static const struct fddi_addr smt_sba_da = {{0x80,0x01,0x43,0x00,0x80,0x0C}} ;
0063 static const struct fddi_addr null_addr = {{0,0,0,0,0,0}} ;
0064 
0065 /*
0066     -------------------------------------------------------------
0067     GLOBAL VARIABLES:
0068     -------------------------------------------------------------
0069 */
0070 
0071 
0072 /*
0073     -------------------------------------------------------------
0074     LOCAL FUNCTIONS:
0075     -------------------------------------------------------------
0076 */
0077 
0078 static void ess_send_response(struct s_smc *smc, struct smt_header *sm,
0079                   int sba_cmd);
0080 static void ess_config_fifo(struct s_smc *smc);
0081 static void ess_send_alc_req(struct s_smc *smc);
0082 static void ess_send_frame(struct s_smc *smc, SMbuf *mb);
0083 
0084 /*
0085     -------------------------------------------------------------
0086     EXTERNAL FUNCTIONS:
0087     -------------------------------------------------------------
0088 */
0089 
0090 /*
0091     -------------------------------------------------------------
0092     PUBLIC FUNCTIONS:
0093     -------------------------------------------------------------
0094 */
0095 
0096 void ess_timer_poll(struct s_smc *smc);
0097 void ess_para_change(struct s_smc *smc);
0098 int ess_raf_received_pack(struct s_smc *smc, SMbuf *mb, struct smt_header *sm,
0099               int fs);
0100 static int process_bw_alloc(struct s_smc *smc, long int payload, long int overhead);
0101 
0102 
0103 /*
0104  * --------------------------------------------------------------------------
0105  *  End Station Support (ESS)
0106  * --------------------------------------------------------------------------
0107  */
0108 
0109 /*
0110  * evaluate the RAF frame
0111  */
0112 int ess_raf_received_pack(struct s_smc *smc, SMbuf *mb, struct smt_header *sm,
0113               int fs)
0114 {
0115     void            *p ;        /* universal pointer */
0116     struct smt_p_0016   *cmd ;      /* para: command for the ESS */
0117     SMbuf           *db ;
0118     u_long          msg_res_type ;  /* recource type */
0119     u_long          payload, overhead ;
0120     int         local ;
0121     int         i ;
0122 
0123     /*
0124      * Message Processing Code
0125      */
0126      local = ((fs & L_INDICATOR) != 0) ;
0127 
0128     /*
0129      * get the resource type
0130      */
0131     if (!(p = (void *) sm_to_para(smc,sm,SMT_P0015))) {
0132         DB_ESS("ESS: RAF frame error, parameter type not found");
0133         return fs;
0134     }
0135     msg_res_type = ((struct smt_p_0015 *)p)->res_type ;
0136 
0137     /*
0138      * get the pointer to the ESS command
0139      */
0140     if (!(cmd = (struct smt_p_0016 *) sm_to_para(smc,sm,SMT_P0016))) {
0141         /*
0142          * error in frame: para ESS command was not found
0143          */
0144          DB_ESS("ESS: RAF frame error, parameter command not found");
0145          return fs;
0146     }
0147 
0148     DB_ESSN(2, "fc %x   ft %x", sm->smt_class, sm->smt_type);
0149     DB_ESSN(2, "ver %x  tran %x", sm->smt_version, sm->smt_tid);
0150     DB_ESSN(2, "stn_id %pM", &sm->smt_source);
0151 
0152     DB_ESSN(2, "infolen %x  res %lx", sm->smt_len, msg_res_type);
0153     DB_ESSN(2, "sbacmd %x", cmd->sba_cmd);
0154 
0155     /*
0156      * evaluate the ESS command
0157      */
0158     switch (cmd->sba_cmd) {
0159 
0160     /*
0161      * Process an ESS Allocation Request
0162      */
0163     case REQUEST_ALLOCATION :
0164         /*
0165          * check for an RAF Request (Allocation Request)
0166          */
0167         if (sm->smt_type == SMT_REQUEST) {
0168             /*
0169              * process the Allocation request only if the frame is
0170              * local and no static allocation is used
0171              */
0172             if (!local || smc->mib.fddiESSPayload)
0173                 return fs;
0174             
0175             p = (void *) sm_to_para(smc,sm,SMT_P0019)  ;
0176             for (i = 0; i < 5; i++) {
0177                 if (((struct smt_p_0019 *)p)->alloc_addr.a[i]) {
0178                     return fs;
0179                 }
0180             }
0181 
0182             /*
0183              * Note: The Application should send a LAN_LOC_FRAME.
0184              *   The ESS do not send the Frame to the network!
0185              */
0186             smc->ess.alloc_trans_id = sm->smt_tid ;
0187             DB_ESS("ESS: save Alloc Req Trans ID %x", sm->smt_tid);
0188             p = (void *) sm_to_para(smc,sm,SMT_P320F) ;
0189             ((struct smt_p_320f *)p)->mib_payload =
0190                 smc->mib.a[PATH0].fddiPATHSbaPayload ;
0191             p = (void *) sm_to_para(smc,sm,SMT_P3210) ;
0192             ((struct smt_p_3210 *)p)->mib_overhead =
0193                 smc->mib.a[PATH0].fddiPATHSbaOverhead ;
0194             sm->smt_dest = smt_sba_da ;
0195 
0196             if (smc->ess.local_sba_active)
0197                 return fs | I_INDICATOR;
0198 
0199             if (!(db = smt_get_mbuf(smc)))
0200                 return fs;
0201 
0202             db->sm_len = mb->sm_len ;
0203             db->sm_off = mb->sm_off ;
0204             memcpy(((char *)(db->sm_data+db->sm_off)),(char *)sm,
0205                 (int)db->sm_len) ;
0206             dump_smt(smc,
0207                 (struct smt_header *)(db->sm_data+db->sm_off),
0208                 "RAF") ;
0209             smt_send_frame(smc,db,FC_SMT_INFO,0) ;
0210             return fs;
0211         }
0212 
0213         /*
0214          * The RAF frame is an Allocation Response !
0215          * check the parameters
0216          */
0217         if (smt_check_para(smc,sm,plist_raf_alc_res)) {
0218             DB_ESS("ESS: RAF with para problem, ignoring");
0219             return fs;
0220         }
0221 
0222         /*
0223          * VERIFY THE FRAME IS WELL BUILT:
0224          *
0225          *  1. path index = primary ring only
0226          *  2. resource type = sync bw only
0227          *  3. trans action id = alloc_trans_id
0228          *  4. reason code = success
0229          *
0230          * If any are violated, discard the RAF frame
0231          */
0232         if ((((struct smt_p_320b *)sm_to_para(smc,sm,SMT_P320B))->path_index
0233             != PRIMARY_RING) ||
0234             (msg_res_type != SYNC_BW) ||
0235         (((struct smt_p_reason *)sm_to_para(smc,sm,SMT_P0012))->rdf_reason
0236             != SMT_RDF_SUCCESS) ||
0237             (sm->smt_tid != smc->ess.alloc_trans_id)) {
0238 
0239             DB_ESS("ESS: Allocation Response not accepted");
0240             return fs;
0241         }
0242 
0243         /*
0244          * Extract message parameters
0245          */
0246         p = (void *) sm_to_para(smc,sm,SMT_P320F) ;
0247                 if (!p) {
0248                         printk(KERN_ERR "ESS: sm_to_para failed");
0249                         return fs;
0250                 }       
0251         payload = ((struct smt_p_320f *)p)->mib_payload ;
0252         p = (void *) sm_to_para(smc,sm,SMT_P3210) ;
0253                 if (!p) {
0254                         printk(KERN_ERR "ESS: sm_to_para failed");
0255                         return fs;
0256                 }       
0257         overhead = ((struct smt_p_3210 *)p)->mib_overhead ;
0258 
0259         DB_ESSN(2, "payload= %lx    overhead= %lx",
0260             payload, overhead);
0261 
0262         /*
0263          * process the bandwidth allocation
0264          */
0265         (void)process_bw_alloc(smc,(long)payload,(long)overhead) ;
0266 
0267         return fs;
0268         /* end of Process Allocation Request */
0269 
0270     /*
0271      * Process an ESS Change Request
0272      */
0273     case CHANGE_ALLOCATION :
0274         /*
0275          * except only replies
0276          */
0277         if (sm->smt_type != SMT_REQUEST) {
0278             DB_ESS("ESS: Do not process Change Responses");
0279             return fs;
0280         }
0281 
0282         /*
0283          * check the para for the Change Request
0284          */
0285         if (smt_check_para(smc,sm,plist_raf_chg_req)) {
0286             DB_ESS("ESS: RAF with para problem, ignoring");
0287             return fs;
0288         }
0289 
0290         /*
0291          * Verify the path index and resource
0292          * type are correct. If any of
0293          * these are false, don't process this
0294          * change request frame.
0295          */
0296         if ((((struct smt_p_320b *)sm_to_para(smc,sm,SMT_P320B))->path_index
0297             != PRIMARY_RING) || (msg_res_type != SYNC_BW)) {
0298             DB_ESS("ESS: RAF frame with para problem, ignoring");
0299             return fs;
0300         }
0301 
0302         /*
0303          * Extract message queue parameters
0304          */
0305         p = (void *) sm_to_para(smc,sm,SMT_P320F) ;
0306         payload = ((struct smt_p_320f *)p)->mib_payload ;
0307         p = (void *) sm_to_para(smc,sm,SMT_P3210) ;
0308         overhead = ((struct smt_p_3210 *)p)->mib_overhead ;
0309 
0310         DB_ESSN(2, "ESS: Change Request from %pM",
0311             &sm->smt_source);
0312         DB_ESSN(2, "payload= %lx    overhead= %lx",
0313             payload, overhead);
0314 
0315         /*
0316          * process the bandwidth allocation
0317          */
0318         if(!process_bw_alloc(smc,(long)payload,(long)overhead))
0319             return fs;
0320 
0321         /*
0322          * send an RAF Change Reply
0323          */
0324         ess_send_response(smc,sm,CHANGE_ALLOCATION) ;
0325 
0326         return fs;
0327         /* end of Process Change Request */
0328 
0329     /*
0330      * Process Report Response
0331      */
0332     case REPORT_ALLOCATION :
0333         /*
0334          * except only requests
0335          */
0336         if (sm->smt_type != SMT_REQUEST) {
0337             DB_ESS("ESS: Do not process a Report Reply");
0338             return fs;
0339         }
0340 
0341         DB_ESSN(2, "ESS: Report Request from %pM",
0342             &sm->smt_source);
0343 
0344         /*
0345          * verify that the resource type is sync bw only
0346          */
0347         if (msg_res_type != SYNC_BW) {
0348             DB_ESS("ESS: ignoring RAF with para problem");
0349             return fs;
0350         }
0351 
0352         /*
0353          * send an RAF Change Reply
0354          */
0355         ess_send_response(smc,sm,REPORT_ALLOCATION) ;
0356 
0357         return fs;
0358         /* end of Process Report Request */
0359 
0360     default:
0361         /*
0362          * error in frame
0363          */
0364         DB_ESS("ESS: ignoring RAF with bad sba_cmd");
0365         break ;
0366     }
0367 
0368     return fs;
0369 }
0370 
0371 /*
0372  * determines the synchronous bandwidth, set the TSYNC register and the
0373  * mib variables SBAPayload, SBAOverhead and fddiMACT-NEG.
0374  */
0375 static int process_bw_alloc(struct s_smc *smc, long int payload, long int overhead)
0376 {
0377     /*
0378      * determine the synchronous bandwidth (sync_bw) in bytes per T-NEG,
0379      * if the payload is greater than zero.
0380      * For the SBAPayload and the SBAOverhead we have the following
0381      * unite quations
0382      *            _       _
0383      *           |       bytes |
0384      *  SBAPayload = | 8000 ------ |
0385      *           |      s  |
0386      *            -       -
0387      *             _       _
0388      *            |  bytes  |
0389      *  SBAOverhead = | ------  |
0390      *            |  T-NEG  |
0391      *             -       -
0392      *
0393      * T-NEG is described by the equation:
0394      *
0395      *           (-) fddiMACT-NEG
0396      *  T-NEG =     -------------------
0397      *          12500000 1/s
0398      *
0399      * The number of bytes we are able to send is the payload
0400      * plus the overhead.
0401      *
0402      *            bytes    T-NEG SBAPayload 8000 bytes/s
0403      * sync_bw =  SBAOverhead ------ + -----------------------------
0404      *            T-NEG     T-NEG
0405      *
0406      *
0407      *                   1
0408      * sync_bw =  SBAOverhead + ---- (-)fddiMACT-NEG * SBAPayload
0409      *                  1562
0410      *
0411      */
0412 
0413     /*
0414      * set the mib attributes fddiPATHSbaOverhead, fddiPATHSbaPayload
0415      */
0416 /*  if (smt_set_obj(smc,SMT_P320F,payload,S_SET)) {
0417         DB_ESS("ESS: SMT does not accept the payload value");
0418         return FALSE;
0419     }
0420     if (smt_set_obj(smc,SMT_P3210,overhead,S_SET)) {
0421         DB_ESS("ESS: SMT does not accept the overhead value");
0422         return FALSE;
0423     } */
0424 
0425     /* premliminary */
0426     if (payload > MAX_PAYLOAD || overhead > 5000) {
0427         DB_ESS("ESS: payload / overhead not accepted");
0428         return FALSE;
0429     }
0430 
0431     /*
0432      * start the iterative allocation process if the payload or the overhead
0433      * are smaller than the parsed values
0434      */
0435     if (smc->mib.fddiESSPayload &&
0436         ((u_long)payload != smc->mib.fddiESSPayload ||
0437         (u_long)overhead != smc->mib.fddiESSOverhead)) {
0438         smc->ess.raf_act_timer_poll = TRUE ;
0439         smc->ess.timer_count = 0 ;
0440     }
0441 
0442     /*
0443      * evulate the Payload
0444      */
0445     if (payload) {
0446         DB_ESSN(2, "ESS: turn SMT_ST_SYNC_SERVICE bit on");
0447         smc->ess.sync_bw_available = TRUE ;
0448 
0449         smc->ess.sync_bw = overhead -
0450             (long)smc->mib.m[MAC0].fddiMACT_Neg *
0451             payload / 1562 ;
0452     }
0453     else {
0454         DB_ESSN(2, "ESS: turn SMT_ST_SYNC_SERVICE bit off");
0455         smc->ess.sync_bw_available = FALSE ;
0456         smc->ess.sync_bw = 0 ;
0457         overhead = 0 ;
0458     }
0459 
0460     smc->mib.a[PATH0].fddiPATHSbaPayload = payload ;
0461     smc->mib.a[PATH0].fddiPATHSbaOverhead = overhead ;
0462 
0463 
0464     DB_ESSN(2, "tsync = %lx", smc->ess.sync_bw);
0465 
0466     ess_config_fifo(smc) ;
0467     set_formac_tsync(smc,smc->ess.sync_bw) ;
0468     return TRUE;
0469 }
0470 
0471 static void ess_send_response(struct s_smc *smc, struct smt_header *sm,
0472                   int sba_cmd)
0473 {
0474     struct smt_sba_chg  *chg ;
0475     SMbuf           *mb ;
0476     void            *p ;
0477 
0478     /*
0479      * get and initialize the response frame
0480      */
0481     if (sba_cmd == CHANGE_ALLOCATION) {
0482         if (!(mb=smt_build_frame(smc,SMT_RAF,SMT_REPLY,
0483                 sizeof(struct smt_sba_chg))))
0484                 return ;
0485     }
0486     else {
0487         if (!(mb=smt_build_frame(smc,SMT_RAF,SMT_REPLY,
0488                 sizeof(struct smt_sba_rep_res))))
0489                 return ;
0490     }
0491 
0492     chg = smtod(mb,struct smt_sba_chg *) ;
0493     chg->smt.smt_tid = sm->smt_tid ;
0494     chg->smt.smt_dest = sm->smt_source ;
0495 
0496     /* set P15 */
0497     chg->s_type.para.p_type = SMT_P0015 ;
0498     chg->s_type.para.p_len = sizeof(struct smt_p_0015) - PARA_LEN ;
0499     chg->s_type.res_type = SYNC_BW ;
0500 
0501     /* set P16 */
0502     chg->cmd.para.p_type = SMT_P0016 ;
0503     chg->cmd.para.p_len = sizeof(struct smt_p_0016) - PARA_LEN ;
0504     chg->cmd.sba_cmd = sba_cmd ;
0505 
0506     /* set P320B */
0507     chg->path.para.p_type = SMT_P320B ;
0508     chg->path.para.p_len = sizeof(struct smt_p_320b) - PARA_LEN ;
0509     chg->path.mib_index = SBAPATHINDEX ;
0510     chg->path.path_pad = 0;
0511     chg->path.path_index = PRIMARY_RING ;
0512 
0513     /* set P320F */
0514     chg->payload.para.p_type = SMT_P320F ;
0515     chg->payload.para.p_len = sizeof(struct smt_p_320f) - PARA_LEN ;
0516     chg->payload.mib_index = SBAPATHINDEX ;
0517     chg->payload.mib_payload = smc->mib.a[PATH0].fddiPATHSbaPayload ;
0518 
0519     /* set P3210 */
0520     chg->overhead.para.p_type = SMT_P3210 ;
0521     chg->overhead.para.p_len = sizeof(struct smt_p_3210) - PARA_LEN ;
0522     chg->overhead.mib_index = SBAPATHINDEX ;
0523     chg->overhead.mib_overhead = smc->mib.a[PATH0].fddiPATHSbaOverhead ;
0524 
0525     if (sba_cmd == CHANGE_ALLOCATION) {
0526         /* set P1A */
0527         chg->cat.para.p_type = SMT_P001A ;
0528         chg->cat.para.p_len = sizeof(struct smt_p_001a) - PARA_LEN ;
0529         p = (void *) sm_to_para(smc,sm,SMT_P001A) ;
0530         chg->cat.category = ((struct smt_p_001a *)p)->category ;
0531     }
0532     dump_smt(smc,(struct smt_header *)chg,"RAF") ;
0533     ess_send_frame(smc,mb) ;
0534 }
0535 
0536 void ess_timer_poll(struct s_smc *smc)
0537 {
0538     if (!smc->ess.raf_act_timer_poll)
0539         return ;
0540 
0541     DB_ESSN(2, "ESS: timer_poll");
0542 
0543     smc->ess.timer_count++ ;
0544     if (smc->ess.timer_count == 10) {
0545         smc->ess.timer_count = 0 ;
0546         ess_send_alc_req(smc) ;
0547     }
0548 }
0549 
0550 static void ess_send_alc_req(struct s_smc *smc)
0551 {
0552     struct smt_sba_alc_req *req ;
0553     SMbuf   *mb ;
0554 
0555     /*
0556      * send never allocation request where the requested payload and
0557      * overhead is zero or deallocate bandwidth when no bandwidth is
0558      * parsed
0559      */
0560     if (!smc->mib.fddiESSPayload) {
0561         smc->mib.fddiESSOverhead = 0 ;
0562     }
0563     else {
0564         if (!smc->mib.fddiESSOverhead)
0565             smc->mib.fddiESSOverhead = DEFAULT_OV ;
0566     }
0567 
0568     if (smc->mib.fddiESSOverhead ==
0569         smc->mib.a[PATH0].fddiPATHSbaOverhead &&
0570         smc->mib.fddiESSPayload ==
0571         smc->mib.a[PATH0].fddiPATHSbaPayload){
0572         smc->ess.raf_act_timer_poll = FALSE ;
0573         smc->ess.timer_count = 7 ;  /* next RAF alc req after 3 s */
0574         return ;
0575     }
0576     
0577     /*
0578      * get and initialize the response frame
0579      */
0580     if (!(mb=smt_build_frame(smc,SMT_RAF,SMT_REQUEST,
0581             sizeof(struct smt_sba_alc_req))))
0582             return ;
0583     req = smtod(mb,struct smt_sba_alc_req *) ;
0584     req->smt.smt_tid = smc->ess.alloc_trans_id = smt_get_tid(smc) ;
0585     req->smt.smt_dest = smt_sba_da ;
0586 
0587     /* set P15 */
0588     req->s_type.para.p_type = SMT_P0015 ;
0589     req->s_type.para.p_len = sizeof(struct smt_p_0015) - PARA_LEN ;
0590     req->s_type.res_type = SYNC_BW ;
0591 
0592     /* set P16 */
0593     req->cmd.para.p_type = SMT_P0016 ;
0594     req->cmd.para.p_len = sizeof(struct smt_p_0016) - PARA_LEN ;
0595     req->cmd.sba_cmd = REQUEST_ALLOCATION ;
0596 
0597     /*
0598      * set the parameter type and parameter length of all used
0599      * parameters
0600      */
0601 
0602     /* set P320B */
0603     req->path.para.p_type = SMT_P320B ;
0604     req->path.para.p_len = sizeof(struct smt_p_320b) - PARA_LEN ;
0605     req->path.mib_index = SBAPATHINDEX ;
0606     req->path.path_pad = 0;
0607     req->path.path_index = PRIMARY_RING ;
0608 
0609     /* set P0017 */
0610     req->pl_req.para.p_type = SMT_P0017 ;
0611     req->pl_req.para.p_len = sizeof(struct smt_p_0017) - PARA_LEN ;
0612     req->pl_req.sba_pl_req = smc->mib.fddiESSPayload -
0613         smc->mib.a[PATH0].fddiPATHSbaPayload ;
0614 
0615     /* set P0018 */
0616     req->ov_req.para.p_type = SMT_P0018 ;
0617     req->ov_req.para.p_len = sizeof(struct smt_p_0018) - PARA_LEN ;
0618     req->ov_req.sba_ov_req = smc->mib.fddiESSOverhead -
0619         smc->mib.a[PATH0].fddiPATHSbaOverhead ;
0620 
0621     /* set P320F */
0622     req->payload.para.p_type = SMT_P320F ;
0623     req->payload.para.p_len = sizeof(struct smt_p_320f) - PARA_LEN ;
0624     req->payload.mib_index = SBAPATHINDEX ;
0625     req->payload.mib_payload = smc->mib.a[PATH0].fddiPATHSbaPayload ;
0626 
0627     /* set P3210 */
0628     req->overhead.para.p_type = SMT_P3210 ;
0629     req->overhead.para.p_len = sizeof(struct smt_p_3210) - PARA_LEN ;
0630     req->overhead.mib_index = SBAPATHINDEX ;
0631     req->overhead.mib_overhead = smc->mib.a[PATH0].fddiPATHSbaOverhead ;
0632 
0633     /* set P19 */
0634     req->a_addr.para.p_type = SMT_P0019 ;
0635     req->a_addr.para.p_len = sizeof(struct smt_p_0019) - PARA_LEN ;
0636     req->a_addr.sba_pad = 0;
0637     req->a_addr.alloc_addr = null_addr ;
0638 
0639     /* set P1A */
0640     req->cat.para.p_type = SMT_P001A ;
0641     req->cat.para.p_len = sizeof(struct smt_p_001a) - PARA_LEN ;
0642     req->cat.category = smc->mib.fddiESSCategory ;
0643 
0644     /* set P1B */
0645     req->tneg.para.p_type = SMT_P001B ;
0646     req->tneg.para.p_len = sizeof(struct smt_p_001b) - PARA_LEN ;
0647     req->tneg.max_t_neg = smc->mib.fddiESSMaxTNeg ;
0648 
0649     /* set P1C */
0650     req->segm.para.p_type = SMT_P001C ;
0651     req->segm.para.p_len = sizeof(struct smt_p_001c) - PARA_LEN ;
0652     req->segm.min_seg_siz = smc->mib.fddiESSMinSegmentSize ;
0653 
0654     dump_smt(smc,(struct smt_header *)req,"RAF") ;
0655     ess_send_frame(smc,mb) ;
0656 }
0657 
0658 static void ess_send_frame(struct s_smc *smc, SMbuf *mb)
0659 {
0660     /*
0661      * check if the frame must be send to the own ESS
0662      */
0663     if (smc->ess.local_sba_active) {
0664         /*
0665          * Send the Change Reply to the local SBA
0666          */
0667         DB_ESS("ESS:Send to the local SBA");
0668         if (!smc->ess.sba_reply_pend)
0669             smc->ess.sba_reply_pend = mb ;
0670         else {
0671             DB_ESS("Frame is lost - another frame was pending");
0672             smt_free_mbuf(smc,mb) ;
0673         }
0674     }
0675     else {
0676         /*
0677          * Send the SBA RAF Change Reply to the network
0678          */
0679         DB_ESS("ESS:Send to the network");
0680         smt_send_frame(smc,mb,FC_SMT_INFO,0) ;
0681     }
0682 }
0683 
0684 void ess_para_change(struct s_smc *smc)
0685 {
0686     (void)process_bw_alloc(smc,(long)smc->mib.a[PATH0].fddiPATHSbaPayload,
0687         (long)smc->mib.a[PATH0].fddiPATHSbaOverhead) ;
0688 }
0689 
0690 static void ess_config_fifo(struct s_smc *smc)
0691 {
0692     /*
0693      * if nothing to do exit 
0694      */
0695     if (smc->mib.a[PATH0].fddiPATHSbaPayload) {
0696         if (smc->hw.fp.fifo.fifo_config_mode & SYNC_TRAFFIC_ON &&
0697             (smc->hw.fp.fifo.fifo_config_mode&SEND_ASYNC_AS_SYNC) ==
0698             smc->mib.fddiESSSynchTxMode) {
0699             return ;
0700         }
0701     }
0702     else {
0703         if (!(smc->hw.fp.fifo.fifo_config_mode & SYNC_TRAFFIC_ON)) {
0704             return ;
0705         }
0706     }
0707 
0708     /*
0709      * split up the FIFO and reinitialize the queues
0710      */
0711     formac_reinit_tx(smc) ;
0712 }
0713 
0714 #endif /* ESS */
0715 
0716 #endif  /* no SLIM_SMT */
0717