将系统信息(内存页大小……)提升为全局初始化对象;调整IO缓冲大小为内存页面大小;IO缓冲采用内存池;增加文件映射功能

This commit is contained in:
gb 2023-12-12 09:36:06 +08:00
parent 1ca053bea6
commit b6884b148e
6 changed files with 112 additions and 12 deletions

View File

@ -10,6 +10,29 @@
#include <sys/mman.h>
#endif
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// sys_info
uint32_t sys_info::page_size = 0;
uint32_t sys_info::page_map_size = 0;
uint32_t sys_info::cluster_size = 0;
sys_info::sys_info()
{
sys_info::page_size = utils::get_page_size(&sys_info::page_map_size);
std::string path(utils::get_local_data_path());
unsigned long long cluster = 0;
utils::get_disk_space(path.c_str(), nullptr, nullptr, &cluster);
sys_info::cluster_size = cluster;
printf("Page size: %u\nMap size: %u\nCluster : %u\n", sys_info::page_size, sys_info::page_map_size, sys_info::cluster_size);
}
sys_info::~sys_info()
{}
static sys_info g_si;
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//
packet_data_base::packet_data_base() : pack_cmd_(0), pack_id_(0)
@ -406,6 +429,12 @@ dyn_mem& dyn_mem::operator+=(dyn_mem& r)
return *this;
}
void dyn_mem::clear_data(void)
{
len_ = 0;
set_packet_param(0, 0);
set_session_id(0);
}
bool dyn_mem::is_memory_block(void)
{
@ -450,6 +479,7 @@ file_reader::~file_reader()
fclose(src_);
if (map_)
map_->release();
notify_progress(len_, len_, 0); // ensure 100%
utils::to_log(LOG_LEVEL_DEBUG, "Read file(%s) over(%ld/%ld).\n", path_.c_str(), consume_, len_);
}

View File

@ -76,6 +76,18 @@ public:
uint8_t* buffer(void);
};
class sys_info
{
public:
sys_info();
~sys_info();
public:
static uint32_t page_size;
static uint32_t page_map_size;
static uint32_t cluster_size;
};
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//
/* data_holder, used when data is also required for a certain packet
@ -220,6 +232,7 @@ public:
size_t used(size_t len); // used len bytes content, move following data to head and set data length, return rest data length
dyn_mem& operator+=(dyn_mem& r);
void clear_data(void);
// data_source
public:
@ -284,7 +297,7 @@ CLS_PTR(file_reader);
//
// when invalid packet, suggest use the entire data
//
// packet_data_base_ptr* - return data_holder or data_source or nullptr £¨The number of bytes required for this packet, 0 is over for this packet£©
// packet_data_base_ptr* - return data_holder or data_source or nullptr <EFBFBD><EFBFBD>The number of bytes required for this packet, 0 is over for this packet<65><74>
//
// data_holder: the packet/command need more data than dyn_mem_ptr provides to complete the business. such as 'write a large file'
//

View File

@ -44,6 +44,7 @@
enum ep0_req
{
USB_REQ_EP0_GET_PROTO_VER = 100, // get protocol version (PROTOCOL_VER), req = me, ind = 0, val = 0, len = 2
USB_REQ_EP0_GET_IO_SIZE, // get bulk size of IO buffer, req = me, ind = 0, val = 0, len = sizeof(uint32_t)
USB_REQ_EP0_GET_STATUS, // 获取各工作线程状态, return EP0REPLYSTATUS. req = me, ind = 0, val = 0, len = sizeof(EP0REPLYSTATUS)
USB_REQ_EP0_RESET_BULK, // 关闭并重新打开BULK端点, return error number (uint32_t). req = me, ind = 0, val = 0, len = sizeof(uint32_t)
USB_REQ_EP0_CANCEL_CMD, // 取消当前指令的继续执行(一般用于中止大数据的传输). req = me, ind = 0, val = 0, len = sizeof(uint32_t) * 2 [(uint32_t)cmd + (uint32_t)pack-id]

View File

@ -1052,8 +1052,6 @@ namespace utils
ret = statfs(path, &fs);
if (ret == 0)
{
utils::to_log(LOG_LEVEL_DEBUG, " Total: %lld, Free: %lld, Avail: %lld, block size: %lld\n",
fs.f_blocks, fs.f_bfree, fs.f_bavail, fs.f_bsize);
if (total)
*total = fs.f_blocks * fs.f_bsize;
if (avail)

View File

@ -18,7 +18,7 @@ async_usb_gadget::async_usb_gadget(std::function<FUNCTION_PROTO_COMMAND_HANDLE>
, std::function<void(bool)> dev_conn)
: handle_cmd_(cmd_handler), dev_connect_(dev_conn)
, enc_head_(ENCRYPT_CMD_NONE), enc_payload_(ENCRYPT_NONE), enc_data_(0)
, cmd_que_("in-queue"), sent_que_("out-queue")
, io_buf_("IO-buf"), cmd_que_("in-queue"), sent_que_("out-queue")
, wait_in_("wait_usb_enable_in"), wait_out_("wait_usb_enable_out")
{
cmd_que_.enable_wait_log(false);
@ -87,7 +87,17 @@ async_usb_gadget::async_usb_gadget(std::function<FUNCTION_PROTO_COMMAND_HANDLE>
};
threads_.set_exception_handler(excep);
unit_in_ = unit_out_ = dev_->get_max_packet();
unit_in_ = unit_out_ = sys_info::page_size; // dev_->get_max_packet();
// allocate 10MB for IO
for(int i = 0; i < SIZE_MB(10) / unit_out_; ++i)
{
dyn_mem_ptr buf = dyn_mem::memory(unit_out_);
if(buf)
io_buf_.save(buf);
}
utils::to_log(LOG_LEVEL_DEBUG, "Prepare %u(%u * %u) for IO.\n", io_buf_.size() * unit_out_, io_buf_.size(), unit_in_);
threads_.start(task, "thread_pump_task", (void*)&async_usb_gadget::thread_pump_task);
threads_.start(bulkw, "thread_write_bulk", (void*)&async_usb_gadget::thread_write_bulk);
threads_.start(bulkr, "thread_read_bulk", (void*)&async_usb_gadget::thread_read_bulk);
@ -97,6 +107,27 @@ async_usb_gadget::async_usb_gadget(std::function<FUNCTION_PROTO_COMMAND_HANDLE>
async_usb_gadget::~async_usb_gadget()
{
stop();
dyn_mem_ptr buf = nullptr;
while(io_buf_.take(buf, false))
{
if(buf)
buf->release();
}
}
dyn_mem_ptr async_usb_gadget::get_io_buffer(void)
{
dyn_mem_ptr buf = nullptr;
io_buf_.take(buf, true);
return buf;
}
void async_usb_gadget::free_io_buffer(dyn_mem_ptr buf)
{
buf->clear_data();
io_buf_.save(buf, true);
}
const char* async_usb_gadget::ep0_status_desc(int ep0_status, char* unk_buf/*>= 20 bytes*/)
@ -233,6 +264,10 @@ dyn_mem_ptr async_usb_gadget::handle_ctrl_setup(dyn_mem_ptr data)
utils::log_mem_info("threads status:", lps, sizeof(*lps), LOG_LEVEL_DEBUG);
}
break;
case USB_REQ_EP0_GET_IO_SIZE:
reply = dyn_mem::memory(sizeof(unit_out_));
reply->put(&unit_out_, sizeof(unit_out_));
break;
case USB_REQ_EP0_RESET_BULK:
reply = dyn_mem::memory(sizeof(uint32_t));
reply->put(&err, sizeof(err));
@ -435,12 +470,12 @@ void async_usb_gadget::thread_read_ep0(void)
}
void async_usb_gadget::thread_read_bulk(int fd)
{
size_t bulk_size = unit_out_ * get_buf_coefficient();
size_t bulk_size = unit_out_; // * get_buf_coefficient();
uint32_t cnt_0 = 0;
while(run_)
{
dyn_mem_ptr buf(dyn_mem::memory(bulk_size));
dyn_mem_ptr buf = get_io_buffer();
int l = 0;
statu_out_ = WORKER_STATUS_BUSY;
@ -449,7 +484,7 @@ void async_usb_gadget::thread_read_bulk(int fd)
statu_out_ = WORKER_STATUS_IDLE;
if(l <= 0)
{
buf->release();
free_io_buffer(buf);
if(errno)
{
utils::to_log(LOG_LEVEL_ALL, "read bulk(%d) failed: %d(%s)\n", l, errno, strerror(errno));
@ -512,6 +547,7 @@ void async_usb_gadget::thread_pump_task(void)
statu_task_ = WORKER_STATUS_IDLE;
if(cmd_que_.take(data, true) && data)
{
bool pool = true;
statu_task_ = WORKER_STATUS_BUSY;
if(max_que < cmd_que_.size())
max_que = cmd_que_.size();
@ -527,8 +563,9 @@ void async_usb_gadget::thread_pump_task(void)
{
utils::to_log(LOG_LEVEL_ALL, "Combine partial packet with length %u and %u ...\n", prev->get_rest(), data->get_rest());
*prev += *data;
data->release();
free_io_buffer(data);
data = prev;
pool = false;
}
prev = nullptr;
}
@ -542,7 +579,10 @@ void async_usb_gadget::thread_pump_task(void)
if (!online_ || data->get_session_id() != session_id_)
{
utils::to_log(LOG_LEVEL_DEBUG, "Discard task for session ID(%u) is not equal now(%u) or is offline.\n", data->get_session_id(), session_id_);
data->release();
if(pool)
free_io_buffer(data);
else
data->release();
continue;
}
@ -653,14 +693,28 @@ void async_usb_gadget::thread_pump_task(void)
}while(used && data->get_rest());
if(data->get_rest())
prev = data;
{
if(pool)
{
prev = dyn_mem::memory(unit_out_);
prev->put(data->ptr(), data->get_rest());
free_io_buffer(data);
}
else
{
prev = data;
}
}
else
{
if(!dh)
{
task_cmd_ = task_packet_id_ = want_bytes_task_ = 0;
}
data->release();
if(pool)
free_io_buffer(data);
else
data->release();
}
}
}

View File

@ -69,6 +69,7 @@ class async_usb_gadget : public refer
uint32_t task_cmd_ = 0;
uint32_t task_packet_id_ = 0;
safe_fifo<dyn_mem_ptr> io_buf_;
safe_fifo<dyn_mem_ptr> cmd_que_;
safe_fifo<data_source_ptr> sent_que_;
@ -83,6 +84,9 @@ class async_usb_gadget : public refer
std::function<FUNCTION_PROTO_COMMAND_HANDLE> handle_cmd_;
std::function<void(bool)> dev_connect_;
dyn_mem_ptr get_io_buffer(void);
void free_io_buffer(dyn_mem_ptr buf);
const char* ep0_status_desc(int ep0_status, char* unk_buf/*>= 40 bytes*/);
int wait_fd_event(int fd, int to_ms = -1);