C++ c_str of std::string returns empty

So, I’m running into an issue with the following code whereby the result of std::cout << cstr << std::endl is the single character

PyObject * CKKSwrapper::SerializeContext() {
    std::string s;                                      // 1
    std::ostringstream os(s);                           // 2
    Serial::Serialize(m_cc, os, SerType::BINARY);   // 3
    const std::string string_repr = os.str();                   // 4
    std::cout << string_repr << std::endl;                      // 5

    char *cstr = new char[string_repr.length() + 1];            // 6
    std::strcpy(cstr, string_repr.c_str());                     // 7
    std::cout << "******************************************************" << std::endl; // 8

    std::cout << string_repr << std::endl;                      // 9
    std::cout << "******************************************************" << std::endl; // 10
    std::cout <<  cstr << std::endl;                    // 11

    auto resp = PyBytes_FromString(cstr);               // 12
    return resp;

Checking the std::cout result on line 5 looks good and is non-empty.

@ � �4 lbcrypto::LPCryptoParametersCKKSlbcrypto::DCRTPoly � @ �

^ the first few characters (not sure if that helps)

Later, I create a char array and copy over the c_str to it which (I think) avoids the issue of a temporary result as was discussed https://stackoverflow.com/a/39006531/3532564

Don’t attempt to store the pointer returned by c_str(). If you need that string as a C-string for an extended period of time, allocate memory buffer for it yourself and copy the result of c_str() to that buffer.

I also found https://stackoverflow.com/a/35981001/3532564 which made me wonder if my string_repr object was being destroyed so I did a std::cout on line 9 and it looks good also.

Can anyone help me? I’m really not sure where the issue stems from. Unfortunately, I need to pass a char * [] to PyBytes_FromString despite what the name might make one think


Presumably the string contains one or more nul characters, resulting in strcpy() not copying all of the bytes. You also have a memory leak from not freeing cstr before you return from the function.

You can avoid both problems by bypassing the unnecessary string array and calling PyBytes_FromStringAndSize:

return PyBytes_FromStringAndSize(string_repr.c_str(), string_repr.size());