【问题标题】:libuv - free write bufferlibuv - 空闲的写缓冲区
【发布时间】:2019-10-19 06:43:38
【问题描述】:

uv_write 的文档指出 [1]:

注意缓冲区指向的内存必须保持有效,直到回调被调用。这也适用于 uv_write2()。

因此,缓冲区的基础可能需要动态分配。调用函数可能如下所示:

void write_to_stream(uv_stream_t* stream) {   
    uv_write_t* write_req = new uv_write_t;
    uv_buf_t buf{};
    buf.base = new char[1024];
    buf.len = 1024;
    // fill the buffer
    uv_write(write_req, stream, buf, 1, on_write);
}

在这种情况下,new char[1024] 分配的内存需要在触发on_write 回调之前有效。

查看回调void on_write(uv_write_t* req, int status) 的签名,不清楚如何释放此内存,因为似乎无法从回调中访问此指针。

void on_write(uv_write_t* req, int status) {
    // how to find the memory allocated for req's buffer?
    delete[] ???;
}

一旦不再需要该内存,释放该内存的预期方法是什么?

【问题讨论】:

    标签: c++ node.js libuv


    【解决方案1】:

    由于libuv 是一个c 库,它的结构应该是标准布局类型。因此,您可以将uv_write_tuv_buf_t 包装在上下文结构中,然后再转换回上下文结构。请参阅以下示例:

    struct write_context_t {
        uv_write_t write_req;
        uv_buf_t buf;
        ~write_context_t() {
            delete[] buf.base;
        }
    }
    
    void on_write(uv_write_t* req, int status) {
        write_context_t* context = reinterpret_cast<write_context_t*>(req);
        /* Do stuff ... */
        delete context;
    }
    
    void write_to_stream(uv_stream_t* stream) {   
        write_context_t* write_req = new write_context_t;
    
        /* fill your write_req and buf info here ... */
    
        // initiate write
        uv_write(&write_req.write_req, stream, write_req.buf, 1, on_write);
    }
    

    这是因为指向标准布局对象的第一个非静态数据成员的指针可以与指向该对象的指针相互转换。

    【讨论】:

      【解决方案2】:

      另一种方法是使用data。请注意,所有 uv-handles 都包含一个 data 字段,可以根据自己的需要使用。

      void write_to_stream(uv_stream_t* stream) {   
          uv_write_t* write_req = new uv_write_t;
          write_req.data = new char[1024];
      
          uv_buf_t buf{};
          buf.base = write_req.data;
          buf.len = 1024;
      
          // fill the buffer
          uv_write(write_req, stream, buf, 1, on_write);
      }
      
      void on_write(uv_write_t* req, int status) {
      
          delete[] req.data;
          delete req;
      }
      
      

      【讨论】:

      • 请注意,通过 void 指针删除是 C++ 中未定义的行为。
      猜你喜欢
      • 2011-08-02
      • 1970-01-01
      • 2015-04-15
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多