optimized pipe writing/reading and `ErrorMessage` serialization a bit (#5279)
This commit is contained in:
parent
d4d77edeae
commit
5371455606
|
@ -90,32 +90,35 @@ public:
|
|||
|
||||
private:
|
||||
// TODO: how to log file name in error?
|
||||
void writeToPipe(PipeSignal type, const std::string &data) const
|
||||
void writeToPipeInternal(PipeSignal type, const void* data, std::size_t to_write) const
|
||||
{
|
||||
unsigned int len = static_cast<unsigned int>(data.length() + 1);
|
||||
char *out = new char[len + 1 + sizeof(len)];
|
||||
out[0] = static_cast<char>(type);
|
||||
std::memcpy(&(out[1]), &len, sizeof(len));
|
||||
std::memcpy(&(out[1+sizeof(len)]), data.c_str(), len);
|
||||
|
||||
std::size_t bytes_to_write = len + 1 + sizeof(len);
|
||||
ssize_t bytes_written = write(mWpipe, out, len + 1 + sizeof(len));
|
||||
const ssize_t bytes_written = write(mWpipe, data, to_write);
|
||||
if (bytes_written <= 0) {
|
||||
const int err = errno;
|
||||
delete[] out;
|
||||
out = nullptr;
|
||||
std::cerr << "#### ThreadExecutor::writeToPipe() error for type " << type << ": " << std::strerror(err) << std::endl;
|
||||
std::cerr << "#### ThreadExecutor::writeToPipeInternal() error for type " << type << ": " << std::strerror(err) << std::endl;
|
||||
std::exit(EXIT_FAILURE);
|
||||
}
|
||||
// TODO: write until everything is written
|
||||
if (bytes_written != bytes_to_write) {
|
||||
delete[] out;
|
||||
out = nullptr;
|
||||
std::cerr << "#### ThreadExecutor::writeToPipe() error for type " << type << ": insufficient data written (expected: " << bytes_to_write << " / got: " << bytes_written << ")" << std::endl;
|
||||
if (bytes_written != to_write) {
|
||||
std::cerr << "#### ThreadExecutor::writeToPipeInternal() error for type " << type << ": insufficient data written (expected: " << to_write << " / got: " << bytes_written << ")" << std::endl;
|
||||
std::exit(EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
|
||||
delete[] out;
|
||||
void writeToPipe(PipeSignal type, const std::string &data) const
|
||||
{
|
||||
{
|
||||
const char t = static_cast<char>(type);
|
||||
writeToPipeInternal(type, &t, 1);
|
||||
}
|
||||
|
||||
const unsigned int len = static_cast<unsigned int>(data.length() + 1);
|
||||
{
|
||||
static constexpr std::size_t l_size = sizeof(unsigned int);
|
||||
writeToPipeInternal(type, &len, l_size);
|
||||
}
|
||||
|
||||
writeToPipeInternal(type, data.c_str(), len);
|
||||
}
|
||||
|
||||
const int mWpipe;
|
||||
|
@ -164,8 +167,8 @@ bool ProcessExecutor::handleRead(int rpipe, unsigned int &result, const std::str
|
|||
|
||||
// Don't rely on incoming data being null-terminated.
|
||||
// Allocate +1 element and null-terminate the buffer.
|
||||
char *buf = new char[len + 1];
|
||||
char *data_start = buf;
|
||||
std::string buf(len + 1, '\0');
|
||||
char *data_start = &buf[0];
|
||||
bytes_to_read = len;
|
||||
do {
|
||||
bytes_read = read(rpipe, data_start, bytes_to_read);
|
||||
|
@ -177,13 +180,14 @@ bool ProcessExecutor::handleRead(int rpipe, unsigned int &result, const std::str
|
|||
bytes_to_read -= bytes_read;
|
||||
data_start += bytes_read;
|
||||
} while (bytes_to_read != 0);
|
||||
buf[len] = 0;
|
||||
buf[len] = '\0';
|
||||
|
||||
bool res = true;
|
||||
if (type == PipeWriter::REPORT_OUT) {
|
||||
// the first character is the color
|
||||
const Color c = static_cast<Color>(buf[0]);
|
||||
mErrorLogger.reportOut(buf + 1, c);
|
||||
// TODO: avoid string copy
|
||||
mErrorLogger.reportOut(buf.substr(1), c);
|
||||
} else if (type == PipeWriter::REPORT_ERROR) {
|
||||
ErrorMessage msg;
|
||||
try {
|
||||
|
@ -200,7 +204,6 @@ bool ProcessExecutor::handleRead(int rpipe, unsigned int &result, const std::str
|
|||
res = false;
|
||||
}
|
||||
|
||||
delete[] buf;
|
||||
return res;
|
||||
}
|
||||
|
||||
|
|
|
@ -227,35 +227,50 @@ Suppressions::ErrorMessage ErrorMessage::toSuppressionsErrorMessage() const
|
|||
return ret;
|
||||
}
|
||||
|
||||
static void serializeString(std::string &oss, const std::string & str)
|
||||
{
|
||||
oss += std::to_string(str.length());
|
||||
oss += " ";
|
||||
oss += str;
|
||||
}
|
||||
|
||||
std::string ErrorMessage::serialize() const
|
||||
{
|
||||
// Serialize this message into a simple string
|
||||
std::ostringstream oss;
|
||||
oss << id.length() << " " << id;
|
||||
oss << Severity::toString(severity).length() << " " << Severity::toString(severity);
|
||||
oss << MathLib::toString(cwe.id).length() << " " << MathLib::toString(cwe.id);
|
||||
oss << MathLib::toString(hash).length() << " " << MathLib::toString(hash);
|
||||
oss << file0.size() << " " << file0;
|
||||
std::string oss;
|
||||
serializeString(oss, id);
|
||||
serializeString(oss, Severity::toString(severity));
|
||||
serializeString(oss, MathLib::toString(cwe.id));
|
||||
serializeString(oss, MathLib::toString(hash));
|
||||
serializeString(oss, file0);
|
||||
if (certainty == Certainty::inconclusive) {
|
||||
const std::string text("inconclusive");
|
||||
oss << text.length() << " " << text;
|
||||
serializeString(oss, text);
|
||||
}
|
||||
|
||||
const std::string saneShortMessage = fixInvalidChars(mShortMessage);
|
||||
const std::string saneVerboseMessage = fixInvalidChars(mVerboseMessage);
|
||||
|
||||
oss << saneShortMessage.length() << " " << saneShortMessage;
|
||||
oss << saneVerboseMessage.length() << " " << saneVerboseMessage;
|
||||
oss << callStack.size() << " ";
|
||||
serializeString(oss, saneShortMessage);
|
||||
serializeString(oss, saneVerboseMessage);
|
||||
oss += std::to_string(callStack.size());
|
||||
oss += " ";
|
||||
|
||||
for (std::list<ErrorMessage::FileLocation>::const_iterator loc = callStack.cbegin(); loc != callStack.cend(); ++loc) {
|
||||
std::ostringstream smallStream;
|
||||
smallStream << (*loc).line << '\t' << (*loc).column << '\t' << (*loc).getfile(false) << '\t' << loc->getOrigFile(false) << '\t' << loc->getinfo();
|
||||
oss << smallStream.str().length() << " " << smallStream.str();
|
||||
std::string frame;
|
||||
frame += std::to_string((*loc).line);
|
||||
frame += '\t';
|
||||
frame += std::to_string((*loc).column);
|
||||
frame += '\t';
|
||||
frame += (*loc).getfile(false);
|
||||
frame += '\t';
|
||||
frame += loc->getOrigFile(false);
|
||||
frame += '\t';
|
||||
frame += loc->getinfo();
|
||||
serializeString(oss, frame);
|
||||
}
|
||||
|
||||
return oss.str();
|
||||
return oss;
|
||||
}
|
||||
|
||||
void ErrorMessage::deserialize(const std::string &data)
|
||||
|
|
Loading…
Reference in New Issue