void network_be_end ( epdata_t *epd ) // for lua function die { if ( epd->process_timeout == 1 && epd->keepalive != -1 ) { epd->process_timeout = 0; free_epd ( epd ); return; } //printf ( "network_be_end %d\n" , ((se_ptr_t*)epd->se_ptr)->fd ); update_timeout ( epd->timeout_ptr, STEP_SEND_TIMEOUT ); se_be_write ( epd->se_ptr, network_be_write ); serv_status.success_counts++; epd->status = STEP_SEND; serv_status.sending_counts++; if ( epd->iov[0].iov_base == NULL && epd->iov[1].iov_base == NULL && epd->response_sendfile_fd == -1 ) { serv_status.sending_counts--; network_send_error ( epd, 417, "" ); } else if ( epd->response_sendfile_fd == -2 ) { epd->response_sendfile_fd = -1; serv_status.sending_counts--; network_send_error ( epd, 404, "File Not Found!" ); } else { int gzip_data = 0; //printf("%d %s\n", epd->response_content_length, epd->iov[1].iov_base); if ( epd->response_content_length > 1024 && epd->iov[1].iov_base && !is_binary ( epd->iov[1].iov_base, epd->iov[1].iov_len ) ) { char *p = NULL; if ( epd->headers ) { p = stristr ( epd->headers, "Accept-Encoding", epd->header_len ); } if ( p ) { p += 16; int i = 0, m = strlen ( p ); for ( ; i < 20 && i < m; i++ ) { if ( p[i] == '\n' ) { break; } } p[i] = '\0'; if ( strstr ( p, "deflate" ) ) { gzip_data = 2; } else if ( strstr ( p, "gzip" ) ) { gzip_data = 1; } p[i] = '\n'; } } if ( gzip_data > 0 ) epd->response_content_length = gzip_iov ( gzip_data, ( struct iovec * ) &epd->iov, epd->iov_buf_count, &epd->iov_buf_count ); int len = 0; if ( epd->iov[0].iov_base == NULL ) { len = sprintf ( temp_buf, "HTTP/1.1 200 OK\r\nServer: aLiLua/%s (%s)\r\nContent-Type: text/html; charset=UTF-8\r\nConnection: %s\r\n%sContent-Length: %d\r\n\r\n", version, hostname, ( epd->keepalive == 1 ? "keep-alive" : "close" ), ( gzip_data == 1 ? "Content-Encoding: gzip\r\n" : ( gzip_data == 2 ? "Content-Encoding: deflate\r\n" : "" ) ), epd->response_content_length + ( gzip_data == 1 ? 10 : 0 ) ); epd->response_header_length = len; } else { //( ( char * ) ( epd->iov[0].iov_base ) ) [epd->response_header_length] = '\0'; memcpy ( temp_buf, epd->iov[0].iov_base, epd->response_header_length ); len = epd->response_header_length + sprintf ( temp_buf + epd->response_header_length, "Server: aLiLua/%s (%s)\r\nConnection: %s\r\nDate: %s\r\n%sContent-Length: %d\r\n\r\n", version, hostname, ( epd->keepalive == 1 ? "keep-alive" : "close" ), now_date, ( gzip_data == 1 ? "Content-Encoding: gzip\r\n" : ( gzip_data == 2 ? "Content-Encoding: deflate\r\n" : "" ) ), epd->response_content_length + ( gzip_data == 1 ? 10 : 0 ) ); epd->response_header_length += len; } if ( len < 4086 && epd->response_sendfile_fd <= -1 && epd->iov[1].iov_base && epd->iov[1].iov_len > 0 ) { if ( epd->iov[0].iov_base == NULL ) { epd->iov[0].iov_base = malloc ( EP_D_BUF_SIZE ); } if ( epd->iov[0].iov_base == NULL ) { epd->keepalive = 0; network_end_process ( epd ); serv_status.sending_counts--; return; } memcpy ( epd->iov[0].iov_base, temp_buf, len ); epd->iov[0].iov_len = len; epd->response_content_length += len; if ( gzip_data == 1 ) { memcpy ( epd->iov[0].iov_base + len, gzip_header, 10 ); epd->iov[0].iov_len += 10; epd->response_content_length += 10; } epd->iov_buf_count += 1; } else { network_raw_send ( epd->fd, temp_buf, len ); if ( gzip_data == 1 ) { network_raw_send ( epd->fd, gzip_header, 10 ); } free ( epd->iov[0].iov_base ); epd->iov[0].iov_base = NULL; int i = 0; for ( i = 0; i < epd->iov_buf_count; i++ ) { epd->iov[i] = epd->iov[i + 1]; epd->iov[i + 1].iov_base = NULL; epd->iov[i + 1].iov_len = 0; } } //epd->response_header_length = 0; //printf("%d\n", epd->response_header_length); if ( epd->response_content_length == 0 ) { network_end_process ( epd ); serv_status.sending_counts--; } else { epd->response_buf_sended = 0; } } }
static int lua_co_send(lua_State *L) { cosocket_t *c*k = NULL; { if(lua_gettop(L) < 2) { return 0; } int t = lua_type(L, 2); if(!lua_isuserdata(L, 1) || (t != LUA_TSTRING && t != LUA_TTABLE)) { lua_pushboolean(L, 0); lua_pushstring(L, "Error params!"); return 2; } c*k = (cosocket_t *) lua_touserdata(L, 1); if(c*k->status != 2 || c*k->fd == -1 || !c*k->ptr) { lua_pushboolean(L, 0); lua_pushstring(L, "Not connected!"); return 2; } if(c*k->inuse == 1) { lua_pushnil(L); lua_pushstring(L, "socket busy!"); return 2; } c*k->L = L; c*k->send_buf_ed = 0; if(t == LUA_TTABLE) { c*k->send_buf_len = lua_calc_strlen_in_table(L, 2, 2, 1 /* strict */); if(c*k->send_buf_len > 0) { if(c*k->send_buf_len < _SENDBUF_SIZE) { c*k->send_buf_need_free = NULL; lua_copy_str_in_table(L, 2, c*k->_send_buf); c*k->send_buf = c*k->_send_buf; } else { c*k->send_buf_need_free = large_malloc(c*k->send_buf_len); if(!c*k->send_buf_need_free) { LOGF(ERR, "malloc error @%s:%d\n", __FILE__, __LINE__); exit(1); } lua_copy_str_in_table(L, 2, c*k->send_buf_need_free); c*k->send_buf = c*k->send_buf_need_free; } } } else { const char *p = lua_tolstring(L, 2, &c*k->send_buf_len); c*k->send_buf_need_free = NULL; if(c*k->send_buf_len < _SENDBUF_SIZE) { memcpy(c*k->_send_buf, p, c*k->send_buf_len); c*k->send_buf = c*k->_send_buf; } else { c*k->send_buf_need_free = large_malloc(c*k->send_buf_len); if(!c*k->send_buf_need_free) { LOGF(ERR, "malloc error @%s:%d\n", __FILE__, __LINE__); exit(1); } memcpy(c*k->send_buf_need_free, p, c*k->send_buf_len); c*k->send_buf = c*k->send_buf_need_free; } } if(c*k->send_buf_len < 1) { lua_pushboolean(L, 0); lua_pushstring(L, "content empty!"); return 2; } c*k->inuse = 0; int ret = cosocket_be_write(c*k->ptr); if(ret > 0) { se_be_write(c*k->ptr, cosocket_be_write); c*k->timeout_ptr = add_timeout(c*k, c*k->timeout, timeout_handle); c*k->inuse = 1; return lua_yield(L, 0); } else { return 0 - ret; } } }