text: /*
    +----------------------------------------------------------------------+
    | Zan                                                                  |
    +----------------------------------------------------------------------+
    | Copyright (c) 2016-2017 Zan Group <https://github.com/youzan/zan>    |
    | Copyright (c) 2012-2016 Swoole Team <http://github.com/swoole>       |
    +----------------------------------------------------------------------+
    | This source file is subject to version 2.0 of the Apache license,    |
    | that is bundled with this package in the file LICENSE, and is        |
    | available through the world-wide-web at the following url:           |
    | http://www.apache.org/licenses/LICENSE-2.0.html                      |
    | If you did not receive a copy of the Apache2.0 license and are unable|
    | to obtain it through the world-wide-web, please send a note to       |
    | zan@zanphp.io so we can mail you a copy immediately.                 |
    +----------------------------------------------------------------------+
    | Author: Tianfeng Han  <mikan.tenny@gmail.com>                        |
    |         Zan Group   <zan@zanphp.io>                                  |
    +----------------------------------------------------------------------+
  */
  
  
  #ifndef SW_CONNECTION_H_
  #define SW_CONNECTION_H_
  
  #include "swoole.h"
  #include "swSocket.h"
  #include "swAtomic.h"
  #include "swBaseData.h"
  #include "zanMemory/buffer.h"
  
  #ifdef __cplusplus
  extern "C"
  {
  #endif
  
  #ifdef SW_USE_OPENSSL
  #include <openssl/bio.h>
  #include <openssl/ssl.h>
  #include <openssl/err.h>
  #endif
  
  typedef struct _swConnection
  {
      /**
       * file descript
       */
      int fd;
  
      /**
       * session id
       */
      uint32_t session_id;
  
      /**
       * socket type, SW_SOCK_TCP or SW_SOCK_UDP
       */
      uint8_t socket_type;
  
      /**
       * fd type, SW_FD_TCP or SW_FD_PIPE or SW_FD_TIMERFD
       */
      uint8_t fdtype;
  
      int events;
  
      /**
       * is active
       * system fd must be 0. en: timerfd, signalfd, listen socket
       */
      uint8_t active;
  
      uint8_t connect_notify;
  
      /**
       * for SWOOLE_BASE mode.
       */
      uint8_t close_notify;
  
      uint8_t recv_wait;
      uint8_t send_wait;
  
      uint8_t direct_send;
      uint8_t ssl_send;
  
      /**
       * protected connection, cannot be closed by heartbeat thread.
       */
      uint8_t protect;
  
      uint8_t close_wait;
      uint8_t closed;
      uint8_t closing;
      uint8_t close_force;
      uint8_t close_reset;
      uint8_t event_trigger;
      uint8_t removed;            //// 是否从reactor 中移除
      uint8_t overflow;
  
      uint8_t tcp_nopush;
      uint8_t tcp_nodelay;
  
      uint8_t ssl_want_read;
      uint8_t ssl_want_write;
  
      uint8_t http_upgrade;
      uint8_t http2_stream;
  
      /**
       * ReactorThread id
       */
      uint8_t from_id;
  
      /**
       * from which socket fd, 由哪个监听套接字accepte 出来
       */
      uint8_t from_fd;
  
      uint8_t networker_id;  //networker_id
  
      /**
       * socket address
       */
      swSocketAddress info;
  
      /**
       * link any thing, for kernel, do not use with application.
       */
      void *object;
  
      /*
       * used for user context data
       */
      void *user_data;
  
  
      /**
       * input buffer
       */
      struct _swBuffer *in_buffer;
  
      /**
       * output buffer
       */
      struct _swBuffer *out_buffer;
  
      /**
       * connect time(seconds)
       */
      time_t connect_time;
  
      /**
       * received time with last data，可以用于检测连接空闲
       */
      time_t last_time;
  
      /**
       * bind uid
       */
      long uid;
  
      /**
       * memory buffer size;
       */
      int buffer_size;
  
      /**
       *  upgarde websocket
       */
      uint8_t websocket_status;
  
  #ifdef SW_USE_OPENSSL
      SSL *ssl;
      uint32_t ssl_state;
      swString ssl_client_cert;
  #endif
      sw_atomic_t lock;
  }swConnection;
  
  int swConnection_buffer_send(swConnection *conn);
  
  swBuffer_trunk* swConnection_get_out_buffer(swConnection *conn, uint32_t type);
  
  int swConnection_sendfile_async(swConnection *conn, char *filename);
  int swConnection_onSendfile(swConnection *conn, swBuffer_trunk *chunk);
  void swConnection_sendfile_destructor(swBuffer_trunk *chunk);
  int swConnection_get_ip(swConnection *conn,char* addip,int len);
  int swConnection_get_port(swConnection *conn);
  
  /// Receive data from connection
  ssize_t swConnection_recv(swConnection *conn, void *__buf, size_t __n, int __flags);
  
  /// Send data to connection
  int swConnection_send(swConnection *conn, void *__buf, size_t __n, int __flags);
  
  int swConnection_error(int err);
  
  int zanNetworker_dispatch(swConnection *conn, char *data, uint32_t length);
  
  #ifdef __cplusplus
  }
  #endif
  
  #endif /* SW_CONNECTION_H_ */
  