Exemple #1
0
//---------------------------------------------------------------------------
// Decode RB_RELEASE_IND message from RRC
void nas_mesh_DC_decode_rb_release_ind(struct cx_entity *cx, struct nas_ue_dc_element *p){
  //---------------------------------------------------------------------------
  struct rb_entity *rb;
  // Start debug information
#ifdef NAS_DEBUG_DC
  printk("NAS_MESH_DC_DECODE_RB_RELEASE_IND - begin \n");
#endif
  if (cx==NULL){
#ifdef NAS_DEBUG_DC
    printk("NAS_MESH_DC_DECODE_RB_RELEASE_IND - input parameter cx is NULL \n");
#endif
    return;
  }
  if (p==NULL){
#ifdef NAS_DEBUG_DC
    printk("NAS_MESH_DC_DECODE_RB_RELEASE_IND - input parameter p is NULL \n");
#endif
    return;
  }
  // End debug information
  rb=nas_COMMON_search_rb(cx, p->nasUEDCPrimitive.rb_release_ind.rbId);
  if (rb!=NULL){
    rb->state=NAS_IDLE;
    //needs also to flush corresponding control block to be coherent with add_rb
#ifdef NAS_DEBUG_DC
    printk("NAS_MESH_DC_DECODE_RB_RELEASE_IND: RB_RELEASE_IND reception\n");
    printk("Local Connection reference %u\n",p->nasUEDCPrimitive.rb_release_ind.localConnectionRef);
    printk("Radio Bearer Identity %u\n",p->nasUEDCPrimitive.rb_release_ind.rbId);
    print_TOOL_state(cx->state);
#endif
  }else
    printk("NAS_DC_RG_RECEIVE: RB_RELEASE_IND reception, No corresponding radio bearer\n");

}
Exemple #2
0
//---------------------------------------------------------------------------
// Decode RB_ESTABLISH_IND message from RRC
void nas_mesh_DC_decode_rb_establish_ind(struct cx_entity *cx, struct nas_ue_dc_element *p,struct nas_priv *gpriv)
{
  //---------------------------------------------------------------------------
  struct rb_entity *rb;

  // Start debug information
#ifdef NAS_DEBUG_DC
  printk("NAS_MESH_DC_DECODE_RB_ESTABLISH_IND - begin \n");
#endif

  if (cx==NULL) {
#ifdef NAS_DEBUG_DC
    printk("NAS_MESH_DC_DECODE_RB_ESTABLISH_IND - input parameter cx is NULL \n");
#endif
    return;
  }

  if (p==NULL) {
#ifdef NAS_DEBUG_DC
    printk("NAS_MESH_DC_DECODE_RB_ESTABLISH_IND - input parameter p is NULL \n");
#endif
    return;
  }

  // End debug information
  rb=nas_COMMON_search_rb(cx, p->nasUEDCPrimitive.rb_release_ind.rbId);

  if (rb==NULL) {
    rb=nas_COMMON_add_rb(cx, p->nasUEDCPrimitive.rb_establish_ind.rbId, p->nasUEDCPrimitive.rb_establish_ind.QoSclass);
    rb->state=NAS_RB_DCH;
    cx->state=NAS_CX_DCH;
    //For demo, add automatically a classifier
#ifdef DEMO_3GSM
    rb->countimer=gpriv->timer_establishment+10;
#endif
#ifdef NAS_DEBUG_DC
    printk("NAS_MESH_DC_DECODE_RB_ESTABLISH_IND: RB_ESTABLISH_IND reception\n");
    printk(" Local Connection reference %u\n",p->nasUEDCPrimitive.rb_establish_ind.localConnectionRef);
    printk(" Radio Bearer Identity %u \n",p->nasUEDCPrimitive.rb_establish_ind.rbId);
    printk(" QoS Traffic Class %u\n",p->nasUEDCPrimitive.rb_establish_ind.QoSclass);
    printk(" DSCP Code %u\n",p->nasUEDCPrimitive.rb_establish_ind.dscp);
    printk(" SAP Id %u\n",p->nasUEDCPrimitive.rb_establish_ind.sapId);
    print_TOOL_state(cx->state);
    nas_print_rb_entity(rb);
#endif
  } else
    printk("NAS_MESH_DC_DECODE_RB_ESTABLISH_IND: RB_ESTABLISH_IND reception, Radio bearer already opened\n");
}
Exemple #3
0
//---------------------------------------------------------------------------
struct rb_entity *nas_COMMON_add_rb(struct cx_entity *cx, nasRadioBearerId_t rab_id, nasQoSTrafficClass_t qos)
{
  //--------------------------------------------------------------------------
  struct rb_entity *rb;
#ifdef NAS_DEBUG_CLASS
  printk("NAS_COMMON_ADD_RB - begin for rab_id %d , qos %d\n", rab_id, qos );
#endif

  if (cx==NULL) {
#ifdef NAS_DEBUG_CLASS
    printk("NAS_COMMON_ADD_RB - input parameter cx is NULL \n");
#endif
    return NULL;
  }

  rb=nas_COMMON_search_rb(cx, rab_id);

  if (rb==NULL) {
    rb=(struct rb_entity *)kmalloc(sizeof(struct rb_entity), GFP_KERNEL);

    if (rb!=NULL) {
      rb->retry=0;
      rb->countimer=NAS_TIMER_IDLE;
      rb->rab_id=rab_id;
      //      rb->rab_id=rab_id+(32*cx->lcr);
#ifdef NAS_DEBUG_DC
      printk("NAS_COMMON_ADD_RB: rab_id=%u, mt_id=%u\n",rb->rab_id, cx->lcr);
#endif
      rb->qos=qos;
      rb->sapi=NAS_RAB_INPUT_SAPI;
      rb->state=NAS_IDLE;
      rb->next=cx->rb;
      cx->rb=rb;
      ++cx->num_rb;
    } else
      printk("NAS_ADD_CTL_RB: no memory\n");
  }

#ifdef NAS_DEBUG_CLASS
  printk("NAS_COMMON_ADD_RB - end \n" );
#endif
  return rb;
}
///////////////////////////////////////////////////////////////////////////////
// Radio Bearer Release
//---------------------------------------------------------------------------
void nas_set_msg_rb_release_reply(struct nas_msg_rb_release_reply *msgrep,
                                  struct nas_msg_rb_release_request *msgreq,
                                  struct nas_priv *priv)
{
  //---------------------------------------------------------------------------
  if (msgreq->lcr<NAS_CX_MAX) {
    struct rb_entity *rb;
    struct cx_entity *cx;
    cx=nas_COMMON_search_cx(msgreq->lcr,priv);
    rb=nas_COMMON_search_rb(cx, msgreq->rab_id);

    if (rb!=NULL) {
      //msgrep->status=nas_rg_DC_send_rb_release_request(cx, rb);
    } else
      msgrep->status=-NAS_ERROR_NOTCONNECTED;

    //      msgrep->cnxid  = msgreq->cnxid;
  } else
    msgrep->status=-NAS_ERROR_NOTCORRECTLCR;
}
///////////////////////////////////////////////////////////////////////////////
// Request the addition of a classifier rule
//---------------------------------------------------------------------------
void nas_set_msg_class_add_reply(
  struct nas_msg_class_add_reply   *msgrep,
  struct nas_msg_class_add_request *msgreq,
  struct nas_priv                  *priv)
{
  //---------------------------------------------------------------------------
  struct classifier_entity *gc,*gc2;
  unsigned char *saddr,*daddr;
  unsigned int *saddr32,*daddr32;

  printk("[NAS][CLASS] nas_set_msg_class_add_reply\n");


  if (msgreq->dscp>NAS_DSCP_MAX) {
    printk("NAS_SET_MSG_CLASS_ADD_REPLY: Incoherent parameter value\n");
    msgrep->status=-NAS_ERROR_NOTCORRECTDSCP;
    return;
  }

  if (msgreq->dir==NAS_DIRECTION_SEND) {


    struct cx_entity *cx;
    cx=nas_COMMON_search_cx(msgreq->lcr,priv);

    if (cx!=NULL) {
      printk("NAS_SET_MSG_CLASS_ADD_REPLY: DSCP/EXP %d, Classref %d, RB %u\n", msgreq->dscp, msgreq->classref,msgreq->rab_id );
      gc=nas_CLASS_add_sclassifier(cx, msgreq->dscp, msgreq->classref);

      printk("NAS_SET_MSG_CLASS_ADD_REPLY: %p %p\n" , msgreq, gc);

      if (gc==NULL) {
        msgrep->status=-NAS_ERROR_NOMEMORY;
        return;
      }
    } else {
      msgrep->status=-NAS_ERROR_NOTCORRECTLCR;
      return;
    }

    gc->rab_id=msgreq->rab_id;

    gc->rb=nas_COMMON_search_rb(cx, gc->rab_id);
    printk("NAS_SET_MSG_CLASS_ADD_REPLY: gc_rb %p %u \n", gc->rb, gc->rab_id);
  } else {
    if (msgreq->dir==NAS_DIRECTION_RECEIVE) {
      gc=nas_CLASS_add_rclassifier(msgreq->dscp,
                                   msgreq->classref,
                                   priv);

      if (gc==NULL) {
        msgrep->status=-NAS_ERROR_NOMEMORY;
        return;
      }

      gc->rab_id=msgreq->rab_id;

    } else {
      msgrep->status=-NAS_ERROR_NOTCORRECTDIR;
      return;
    }

    for (gc2 = priv->rclassifier[msgreq->dscp]; gc2!=NULL ; gc2 = gc2->next)
      printk("[NAS][CLASS] Add Receive Classifier dscp %d: rab_id %d (%p,next %p)\n",msgreq->dscp,gc2->rab_id,gc2,gc2->next);
  }

  printk("[NAS][CLASS] Getting addresses ...\n");

  nas_TOOL_fct(gc, msgreq->fct);
  gc->version=msgreq->version;

  switch(gc->version) {
  case 4:
    gc->saddr.ipv4=msgreq->saddr.ipv4;
    gc->daddr.ipv4=msgreq->daddr.ipv4;



    // #ifdef NAS_CLASS_DEBUG
    saddr = (unsigned char *)&gc->saddr.ipv4;
    daddr = (unsigned char *)&gc->daddr.ipv4;

    printk("[NAS][CLASS] Adding IPv4 %d.%d.%d.%d -> %d.%d.%d.%d\n",
           saddr[0],saddr[1],saddr[2],saddr[3],
           daddr[0],daddr[1],daddr[2],daddr[3]);



    //#endif
    gc->splen=msgreq->splen;
    gc->dplen=msgreq->dplen;
    break;

  case 6:
    memcpy(&gc->saddr.ipv6,&msgreq->saddr.ipv6,16);
    memcpy(&gc->daddr.ipv6,&msgreq->daddr.ipv6,16);

    saddr32 = (unsigned int *)&gc->saddr.ipv6;
    daddr32 = (unsigned int *)&gc->daddr.ipv6;

    printk("[NAS][CLASS] Adding IPv6 %X:%X:%X:%X -> %X.%X.%X.%X\n",
           saddr32[0],saddr32[1],saddr32[2],saddr32[3],
           daddr32[0],daddr32[1],daddr32[2],daddr32[3]);
    gc->splen=msgreq->splen;
    gc->dplen=msgreq->dplen;
    break;

  case NAS_MPLS_VERSION_CODE:

    printk("[NAS][CLASS] Adding MPLS label %d with exp %d\n",
           msgreq->daddr.mpls_label,msgreq->dscp);
    gc->daddr.mpls_label = msgreq->daddr.mpls_label;

    break;

  case 0:
    gc->saddr.ipv6.s6_addr32[0]=0;
    gc->daddr.ipv6.s6_addr32[1]=0;
    gc->saddr.ipv6.s6_addr32[2]=0;
    gc->daddr.ipv6.s6_addr32[3]=0;
    gc->splen=0;
    gc->dplen=0;
    break;

  default:
    msgrep->status=-NAS_ERROR_NOTCORRECTVERSION;
    kfree(gc);
    return;
  }

  gc->protocol=msgreq->protocol;
  gc->protocol_message_type=msgreq->protocol_message_type;
  gc->sport=htons(msgreq->sport);
  gc->dport=htons(msgreq->dport);
  msgrep->status=0;
}
Exemple #6
0
void nas_COMMON_QOS_send(struct sk_buff *skb, struct cx_entity *cx, struct classifier_entity *gc,int inst, struct nas_priv *gpriv)
{
  //---------------------------------------------------------------------------
  struct pdcp_data_req_header_s     pdcph;
  struct nas_priv *priv=netdev_priv(nasdev[inst]);
#ifdef LOOPBACK_TEST
  int i;
#endif
  unsigned int bytes_wrote;
  //unsigned char j;
  // Start debug information
#ifdef NAS_DEBUG_SEND
  printk("NAS_COMMON_QOS_SEND - inst %d begin \n",inst);
#endif

  //  if (cx->state!=NAS_STATE_CONNECTED) // <--- A REVOIR
  //  {
  //    priv->stats.tx_dropped ++;
  //    printk("NAS_QOS_SEND: No connected, so message are dropped \n");
  //    return;
  //  }
  if (skb==NULL) {
#ifdef NAS_DEBUG_SEND
    printk("NAS_COMMON_QOS_SEND - input parameter skb is NULL \n");
#endif
    return;
  }

  if (gc==NULL) {
#ifdef NAS_DEBUG_SEND
    printk("NAS_COMMON_QOS_SEND - input parameter gc is NULL \n");
#endif
    return;
  }

  if (cx==NULL) {
#ifdef NAS_DEBUG_SEND
    printk("NAS_COMMON_QOS_SEND - input parameter cx is NULL \n");
#endif
    return;
  }

  // End debug information
  if (gc->rb==NULL) {
    gc->rb=nas_COMMON_search_rb(cx, gc->rab_id);

    if (gc->rb==NULL) {
      ++priv->stats.tx_dropped;
      printk("NAS_COMMON_QOS_SEND: No corresponding Radio Bearer, so message are dropped, rab_id=%u \n", gc->rab_id);
      return;
    }
  }

#ifdef NAS_DEBUG_SEND
  printk("NAS_COMMON_QOS_SEND #1 :");
  printk("lcr %u, rab_id %u, rab_id %u, skb_len %d\n", cx->lcr, (gc->rb)->rab_id, gc->rab_id,skb->len);
  nas_print_classifier(gc);
#endif
  pdcph.data_size  = skb->len;
  pdcph.rb_id      = (gc->rb)->rab_id;
  pdcph.inst       = inst;


#ifdef PDCP_USE_NETLINK
  bytes_wrote = nas_netlink_send((char *)&pdcph,NAS_PDCPH_SIZE);
#ifdef NAS_DEBUG_SEND
  printk("[NAS] Wrote %d bytes (header for %d byte skb) to PDCP via netlink\n",
         bytes_wrote,skb->len);
#endif
#else
  bytes_wrote = rtf_put(NAS2PDCP_FIFO, &pdcph, NAS_PDCPH_SIZE);
#ifdef NAS_DEBUG_SEND
  printk("[NAS] Wrote %d bytes (header for %d byte skb) to PDCP fifo\n",
         bytes_wrote,skb->len);
#endif
#endif //PDCP_USE_NETLINK

  if (bytes_wrote != NAS_PDCPH_SIZE) {
    printk("NAS_COMMON_QOS_SEND: problem while writing PDCP's header (bytes wrote = %d )\n",bytes_wrote);
    printk("rb_id %d, Wrote %d, Header Size %lu\n", pdcph.rb_id , bytes_wrote, NAS_PDCPH_SIZE);
#ifndef PDCP_USE_NETLINK
    rtf_reset(NAS2PDCP_FIFO);
#endif //PDCP_USE_NETLINK
    return;
  }

#ifdef  PDCP_USE_NETLINK
  bytes_wrote += nas_netlink_send((char *)skb->data,skb->len);
#else
  bytes_wrote += rtf_put(NAS2PDCP_FIFO, skb->data, skb->len);
#endif //PDCP_USE_NETLINK

  if (bytes_wrote != skb->len+NAS_PDCPH_SIZE) {
    printk("NAS_COMMON_QOS_SEND: Inst %d, RB_ID %d: problem while writing PDCP's data, bytes_wrote = %d, Data_len %d, PDCPH_SIZE %lu\n",
           inst,
           pdcph.rb_id,
           bytes_wrote,
           skb->len,
           NAS_PDCPH_SIZE); // congestion
#ifndef PDCP_USE_NETLINK
    rtf_reset(NAS2PDCP_FIFO);
#endif //PDCP_USE_NETLINK
    return;
  }

#ifdef NAS_DEBUG_SEND
  printk("NAS_SEND: Sending packet of size %d to PDCP \n",skb->len);

  for (j=0; j<skb->len; j++)
    printk("%2x ",((unsigned char *)(skb->data))[j]);

  printk("\n");
#endif

  priv->stats.tx_bytes   += skb->len;
  priv->stats.tx_packets ++;
#ifdef NAS_DEBUG_SEND
  printk("NAS_COMMON_QOS_SEND - end \n");
#endif
}