⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 api_msg.c

📁 freescale k40/k60 freertos-lwip例程
💻 C
📖 第 1 页 / 共 3 页
字号:
#if LWIP_RAW   case NETCONN_RAW:     msg->conn->pcb.raw = raw_new(msg->msg.n.proto);     if(msg->conn->pcb.raw == NULL) {       msg->conn->err = ERR_MEM;       break;     }     raw_recv(msg->conn->pcb.raw, recv_raw, msg->conn);     break;#endif /* LWIP_RAW */#if LWIP_UDP   case NETCONN_UDP:     msg->conn->pcb.udp = udp_new();     if(msg->conn->pcb.udp == NULL) {       msg->conn->err = ERR_MEM;       break;     }#if LWIP_UDPLITE     if (msg->conn->type==NETCONN_UDPLITE) {       udp_setflags(msg->conn->pcb.udp, UDP_FLAGS_UDPLITE);     }#endif /* LWIP_UDPLITE */     if (msg->conn->type==NETCONN_UDPNOCHKSUM) {       udp_setflags(msg->conn->pcb.udp, UDP_FLAGS_NOCHKSUM);     }     udp_recv(msg->conn->pcb.udp, recv_udp, msg->conn);     break;#endif /* LWIP_UDP */#if LWIP_TCP   case NETCONN_TCP:     msg->conn->pcb.tcp = tcp_new();     if(msg->conn->pcb.tcp == NULL) {       msg->conn->err = ERR_MEM;       break;     }     setup_tcp(msg->conn);     break;#endif /* LWIP_TCP */   default:     /* Unsupported netconn type, e.g. protocol disabled */     msg->conn->err = ERR_VAL;     break;   }  return msg->conn->err;}/** * Create a new pcb of a specific type inside a netconn. * Called from netconn_new_with_proto_and_callback. * * @param msg the api_msg_msg describing the connection type */voiddo_newconn(struct api_msg_msg *msg){   if(msg->conn->pcb.tcp == NULL) {     pcb_new(msg);   }   /* Else? This "new" connection already has a PCB allocated. */   /* Is this an error condition? Should it be deleted? */   /* We currently just are happy and return. */   TCPIP_APIMSG_ACK(msg);}/** * Create a new netconn (of a specific type) that has a callback function. * The corresponding pcb is NOT created! * * @param t the type of 'connection' to create (@see enum netconn_type) * @param proto the IP protocol for RAW IP pcbs * @param callback a function to call on status changes (RX available, TX'ed) * @return a newly allocated struct netconn or *         NULL on memory error */struct netconn*netconn_alloc(enum netconn_type t, netconn_callback callback){  struct netconn *conn;  int size;  conn = memp_malloc(MEMP_NETCONN);  if (conn == NULL) {    return NULL;  }  conn->err = ERR_OK;  conn->type = t;  conn->pcb.tcp = NULL;#if (DEFAULT_RAW_RECVMBOX_SIZE == DEFAULT_UDP_RECVMBOX_SIZE) && \    (DEFAULT_RAW_RECVMBOX_SIZE == DEFAULT_TCP_RECVMBOX_SIZE)  size = DEFAULT_RAW_RECVMBOX_SIZE;#else  switch(NETCONNTYPE_GROUP(t)) {#if LWIP_RAW  case NETCONN_RAW:    size = DEFAULT_RAW_RECVMBOX_SIZE;    break;#endif /* LWIP_RAW */#if LWIP_UDP  case NETCONN_UDP:    size = DEFAULT_UDP_RECVMBOX_SIZE;    break;#endif /* LWIP_UDP */#if LWIP_TCP  case NETCONN_TCP:    size = DEFAULT_TCP_RECVMBOX_SIZE;    break;#endif /* LWIP_TCP */  default:    LWIP_ASSERT("netconn_alloc: undefined netconn_type", 0);    break;  }#endif  if ((conn->op_completed = sys_sem_new(0)) == SYS_SEM_NULL) {    memp_free(MEMP_NETCONN, conn);    return NULL;  }  if ((conn->recvmbox = sys_mbox_new(size)) == SYS_MBOX_NULL) {    sys_sem_free(conn->op_completed);    memp_free(MEMP_NETCONN, conn);    return NULL;  }  conn->acceptmbox   = SYS_MBOX_NULL;  conn->state        = NETCONN_NONE;  /* initialize socket to -1 since 0 is a valid socket */  conn->socket       = -1;  conn->callback     = callback;  conn->recv_avail   = 0;#if LWIP_TCP  conn->write_msg    = NULL;  conn->write_offset = 0;#if LWIP_TCPIP_CORE_LOCKING  conn->write_delayed = 0;#endif /* LWIP_TCPIP_CORE_LOCKING */#endif /* LWIP_TCP */#if LWIP_SO_RCVTIMEO  conn->recv_timeout = 0;#endif /* LWIP_SO_RCVTIMEO */#if LWIP_SO_RCVBUF  conn->recv_bufsize = RECV_BUFSIZE_DEFAULT;#endif /* LWIP_SO_RCVBUF */  return conn;}/** * Delete a netconn and all its resources. * The pcb is NOT freed (since we might not be in the right thread context do this). * * @param conn the netconn to free */voidnetconn_free(struct netconn *conn){  void *mem;  LWIP_ASSERT("PCB must be deallocated outside this function", conn->pcb.tcp == NULL);  /* Drain the recvmbox. */  if (conn->recvmbox != SYS_MBOX_NULL) {    while (sys_mbox_tryfetch(conn->recvmbox, &mem) != SYS_MBOX_EMPTY) {      if (conn->type == NETCONN_TCP) {        if(mem != NULL) {          pbuf_free((struct pbuf *)mem);        }      } else {        netbuf_delete((struct netbuf *)mem);      }    }    sys_mbox_free(conn->recvmbox);    conn->recvmbox = SYS_MBOX_NULL;  }  /* Drain the acceptmbox. */  if (conn->acceptmbox != SYS_MBOX_NULL) {    while (sys_mbox_tryfetch(conn->acceptmbox, &mem) != SYS_MBOX_EMPTY) {      netconn_delete((struct netconn *)mem);    }    sys_mbox_free(conn->acceptmbox);    conn->acceptmbox = SYS_MBOX_NULL;  }  sys_sem_free(conn->op_completed);  conn->op_completed = SYS_SEM_NULL;  memp_free(MEMP_NETCONN, conn);}#if LWIP_TCP/** * Internal helper function to close a TCP netconn: since this sometimes * doesn't work at the first attempt, this function is called from multiple * places. * * @param conn the TCP netconn to close */static voiddo_close_internal(struct netconn *conn){  err_t err;  LWIP_ASSERT("invalid conn", (conn != NULL));  LWIP_ASSERT("this is for tcp netconns only", (conn->type == NETCONN_TCP));  LWIP_ASSERT("conn must be in state NETCONN_CLOSE", (conn->state == NETCONN_CLOSE));  LWIP_ASSERT("pcb already closed", (conn->pcb.tcp != NULL));  /* Set back some callback pointers */  tcp_arg(conn->pcb.tcp, NULL);  if (conn->pcb.tcp->state == LISTEN) {    tcp_accept(conn->pcb.tcp, NULL);  } else {    tcp_recv(conn->pcb.tcp, NULL);    tcp_accept(conn->pcb.tcp, NULL);    /* some callbacks have to be reset if tcp_close is not successful */    tcp_sent(conn->pcb.tcp, NULL);    tcp_poll(conn->pcb.tcp, NULL, 4);    tcp_err(conn->pcb.tcp, NULL);  }  /* Try to close the connection */  err = tcp_close(conn->pcb.tcp);  if (err == ERR_OK) {    /* Closing succeeded */    conn->state = NETCONN_NONE;    /* Set back some callback pointers as conn is going away */    conn->pcb.tcp = NULL;    conn->err = ERR_OK;    /* Trigger select() in socket layer. This send should something else so the       errorfd is set, not the read and write fd! */    API_EVENT(conn, NETCONN_EVT_RCVPLUS, 0);    API_EVENT(conn, NETCONN_EVT_SENDPLUS, 0);    /* wake up the application task */    sys_sem_signal(conn->op_completed);  } else {    /* Closing failed, restore some of the callbacks */    /* Closing of listen pcb will never fail! */    LWIP_ASSERT("Closing a listen pcb may not fail!", (conn->pcb.tcp->state != LISTEN));    tcp_sent(conn->pcb.tcp, sent_tcp);    tcp_poll(conn->pcb.tcp, poll_tcp, 4);    tcp_err(conn->pcb.tcp, err_tcp);    tcp_arg(conn->pcb.tcp, conn);  }  /* If closing didn't succeed, we get called again either     from poll_tcp or from sent_tcp */}#endif /* LWIP_TCP *//** * Delete the pcb inside a netconn. * Called from netconn_delete. * * @param msg the api_msg_msg pointing to the connection */voiddo_delconn(struct api_msg_msg *msg){  if (msg->conn->pcb.tcp != NULL) {    switch (NETCONNTYPE_GROUP(msg->conn->type)) {#if LWIP_RAW    case NETCONN_RAW:      raw_remove(msg->conn->pcb.raw);      break;#endif /* LWIP_RAW */#if LWIP_UDP    case NETCONN_UDP:      msg->conn->pcb.udp->recv_arg = NULL;      udp_remove(msg->conn->pcb.udp);      break;#endif /* LWIP_UDP */#if LWIP_TCP    case NETCONN_TCP:      msg->conn->state = NETCONN_CLOSE;      do_close_internal(msg->conn);      /* API_EVENT is called inside do_close_internal, before releasing         the application thread, so we can return at this point! */      return;#endif /* LWIP_TCP */    default:      break;    }  }  /* tcp netconns don't come here! */  /* Trigger select() in socket layer. This send should something else so the     errorfd is set, not the read and write fd! */  API_EVENT(msg->conn, NETCONN_EVT_RCVPLUS, 0);  API_EVENT(msg->conn, NETCONN_EVT_SENDPLUS, 0);  if (msg->conn->op_completed != SYS_SEM_NULL) {    sys_sem_signal(msg->conn->op_completed);  }}/** * Bind a pcb contained in a netconn * Called from netconn_bind. * * @param msg the api_msg_msg pointing to the connection and containing *            the IP address and port to bind to */voiddo_bind(struct api_msg_msg *msg){  if (!ERR_IS_FATAL(msg->conn->err)) {    if (msg->conn->pcb.tcp != NULL) {      switch (NETCONNTYPE_GROUP(msg->conn->type)) {#if LWIP_RAW      case NETCONN_RAW:        msg->conn->err = raw_bind(msg->conn->pcb.raw, msg->msg.bc.ipaddr);        break;#endif /* LWIP_RAW */#if LWIP_UDP      case NETCONN_UDP:        msg->conn->err = udp_bind(msg->conn->pcb.udp, msg->msg.bc.ipaddr, msg->msg.bc.port);        break;#endif /* LWIP_UDP */#if LWIP_TCP      case NETCONN_TCP:        msg->conn->err = tcp_bind(msg->conn->pcb.tcp, msg->msg.bc.ipaddr, msg->msg.bc.port);        break;#endif /* LWIP_TCP */      default:        break;      }    } else {      /* msg->conn->pcb is NULL */      msg->conn->err = ERR_VAL;    }  }  TCPIP_APIMSG_ACK(msg);}#if LWIP_TCP/** * TCP callback function if a connection (opened by tcp_connect/do_connect) has * been established (or reset by the remote host). * * @see tcp.h (struct tcp_pcb.connected) for parameters and return values */static err_tdo_connected(void *arg, struct tcp_pcb *pcb, err_t err){  struct netconn *conn;  LWIP_UNUSED_ARG(pcb);  conn = arg;  if (conn == NULL) {    return ERR_VAL;  }  conn->err = err;  if ((conn->type == NETCONN_TCP) && (err == ERR_OK)) {    setup_tcp(conn);  }  conn->state = NETCONN_NONE;  sys_sem_signal(conn->op_completed);  return ERR_OK;}#endif /* LWIP_TCP *//** * Connect a pcb contained inside a netconn * Called from netconn_connect. * * @param msg the api_msg_msg pointing to the connection and containing *            the IP address and port to connect to */voiddo_connect(struct api_msg_msg *msg){  if (msg->conn->pcb.tcp == NULL) {    sys_sem_signal(msg->conn->op_completed);    return;  }  switch (NETCONNTYPE_GROUP(msg->conn->type)) {#if LWIP_RAW  case NETCONN_RAW:    msg->conn->err = raw_connect(msg->conn->pcb.raw, msg->msg.bc.ipaddr);    sys_sem_signal(msg->conn->op_completed);    break;#endif /* LWIP_RAW */#if LWIP_UDP  case NETCONN_UDP:    msg->conn->err = udp_connect(msg->conn->pcb.udp, msg->msg.bc.ipaddr, msg->msg.bc.port);    sys_sem_signal(msg->conn->op_completed);    break;#endif /* LWIP_UDP */#if LWIP_TCP  case NETCONN_TCP:    msg->conn->state = NETCONN_CONNECT;    setup_tcp(msg->conn);    msg->conn->err = tcp_connect(msg->conn->pcb.tcp, msg->msg.bc.ipaddr, msg->msg.bc.port,                                 do_connected);    /* sys_sem_signal() is called from do_connected (or err_tcp()),     * when the connection is established! */    break;#endif /* LWIP_TCP */  default:    LWIP_ERROR("Invalid netconn type", 0, do{ msg->conn->err = ERR_VAL;      sys_sem_signal(msg->conn->op_completed); }while(0));    break;  }}/** * Connect a pcb contained inside a netconn * Only used for UDP netconns. * Called from netconn_disconnect. * * @param msg the api_msg_msg pointing to the connection to disconnect

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -