C++;:将指针的指针传递给函数 我是C++的新成员,并尝试将 OpenSSL 集成到我的项目中。这里的一些函数,例如i2d\u RSAPublicKey接收无符号字符**作为第二个参数,并在其中存储一些数据。我在这里也遇到过类似的问题:
但是由于使用C++;:将指针的指针传递给函数 我是C++的新成员,并尝试将 OpenSSL 集成到我的项目中。这里的一些函数,例如i2d\u RSAPublicKey接收无符号字符**作为第二个参数,并在其中存储一些数据。我在这里也遇到过类似的问题:,c++,pointers,openssl,C++,Pointers,Openssl,但是由于使用std::string和std::vector在这里并不方便,我决定问另一个问题 由于std::string::c_str()返回const行指针,而std::vector::data()仅返回行指针,因此它们与此函数不兼容。另外,我不认为操纵行指针将数据存储在std::string或std::vector中是个好主意 所以我的问题是,我应该使用什么样的数据类型来不违反RAII标准,并将指针的指针传递给将在其中存储一些数据的函数 std::unique\u ptr可以接受一个定制的删
std::string
和std::vector
在这里并不方便,我决定问另一个问题
由于std::string::c_str()
返回const
行指针,而std::vector::data()
仅返回行指针,因此它们与此函数不兼容。另外,我不认为操纵行指针将数据存储在std::string
或std::vector
中是个好主意
所以我的问题是,我应该使用什么样的数据类型来不违反
RAII
标准,并将指针的指针传递给将在其中存储一些数据的函数 std::unique\u ptr
可以接受一个定制的删除程序,它可以管理OpenSSL分配的内存。确切地说,它需要调用什么函数来清理东西取决于分配给它的函数,但对于您在示例中使用的i2d\u RSAPublicKey
示例,它需要包装OPENSSL\u free
:
struct OpenSSLFree
{
void operator()(void* ptr)
{
OPENSSL_free(ptr);
}
};
template <typename T>
using OpenSSLPointer = std::unique_ptr<T, OpenSSLFree>;
OpenSSLPointer<unsigned char> EncodeRSAPublicKey(RSA* key)
{
unsigned char* out = nullptr;
int status = i2d_RSAPublicKey(key, &out);
if (status < 0) {
// handle error
}
return OpenSSLPointer<unsigned char>{out};
}
这可能是一个更干净的界面,但它不会在任何地方都工作。带有自定义删除器方法的
std::unique_ptr
广泛适用,但是,删除程序调用的函数将取决于内存的分配方式。您会惊讶地发现,通过一些明智的模板专门化,即std::default\u delete
和std::unique\u ptr
,您的openssl代码是多么整洁,您所询问的函数使用一个基本的原始指针来传达您正在编写的数据块的深度。虽然数据blob可以由RAII管理,但不需要指定特定的指针。简而言之,考虑这个论点在担心把它打包成一个不必要的RAII结构之前所做的事情。我不认为<代码> STD::UnQuyJPTR <代码>可以与<代码> OpenSSL < /代码>经常使用。即使在我的情况下,我也不能使用std::unique\u tr
将指针的指针传递给函数,我不同意这种说法。以std::unique_ptr
的谨慎伪装包装所有这些动态管理结构意味着您永远不必担心其他情况下的大量清理。例如:EVP\u MD\u CTX\u清理
和EVP\u MD\u CYX\u销毁
。只要std::unique_ptr
离开作用域,就会发生这种情况,无论是由于异常还是函数返回等原因。只需要一个合适的删除器就可以实现。不管怎样,在你的例子中,你是在谈论一种特殊的情况,其中unsigned char*p=NULL
然后传递&p
并让libOPENSSL\u malloc
内存用于DER编码?是的,在那里如何使用std::unique\u ptr
?在这种特定情况下,您不能(轻松地)使用它。您必须知道DER的大小(至少最少)才能直接写入由向量管理的缓冲区。如果您使用openssl api为您分配特定的缓冲区,那么在标准库中就没有包含该缓冲区的智能包装器。我从来没有处理过这个问题,因为给定pkey(public或private+public)的DER大小的数学计算非常简单。你确定用.data()检索std::vector
后面的指针吗
并操纵它将一些数据存储在std::vector
中是一个好主意?@Ojs这就是data
方法存在的原因。但由于它不返回指针的引用,如果将某个字符串文本分配给指针怎么办?它不会更改vector right的内容?i2d\u RSAPublicKey
写入**out
并修改*out
。这意味着在本例中,它将写入由outPtr
指向的缓冲区(这是由outVec
管理的缓冲区),并修改指针outPtr
以指向outVec
结束后的元素。调用后,outPtr==&*outVec.end()
将保持为真。@zhanibramidze,因为它想修改您传递给它的指针,使其指向它写入的数据的末尾。在这里,我试图画一个简单的图表。
std::vector<unsigned char> EncodeRSAPublicKey(RSA* key)
{
int len = i2d_RSAPublicKey(key, nullptr);
if (len < 0) {
// handle error
}
std::vector<unsigned char> outVec(len);
unsigned char* outPtr = outVec.data();
len = i2d_RSAPublicKey(key, &outPtr);
if (len < 0) {
// handle error
}
return outVec;
}