Skip to content
Snippets Groups Projects
Commit 5e55cfd4 authored by Richard Linden's avatar Richard Linden
Browse files

SH-4653 FIX Interesting: Viewer crashes while reading chat history

fixed code that was causing abnormal thread termination in the first place
parent 1522c1b3
No related branches found
No related tags found
No related merge requests found
...@@ -845,115 +845,115 @@ bool LLChatLogParser::parse(std::string& raw, LLSD& im, const LLSD& parse_params ...@@ -845,115 +845,115 @@ bool LLChatLogParser::parse(std::string& raw, LLSD& im, const LLSD& parse_params
return true; //parsed name and message text, maybe have a timestamp too return true; //parsed name and message text, maybe have a timestamp too
} }
LLLoadHistoryThread::LLLoadHistoryThread() : LLThread("load chat history")
{
mNewLoad = false;
}
void LLLoadHistoryThread::run()
LLLoadHistoryThread::LLLoadHistoryThread() : LLThread("load chat history") {
{ while (!LLApp::isQuitting())
mNewLoad = false;
}
void LLLoadHistoryThread::run()
{
while (!LLApp::isQuitting())
{
if(mNewLoad)
{
loadHistory(mFileName,mMessages,mLoadParams);
shutdown();
}
}
}
void LLLoadHistoryThread::setHistoryParams(const std::string& file_name, const LLSD& load_params)
{ {
mFileName = file_name; if(mNewLoad)
mLoadParams = load_params; {
mNewLoad = true; loadHistory(mFileName,mMessages,mLoadParams);
break;
}
} }
void LLLoadHistoryThread::loadHistory(const std::string& file_name, std::list<LLSD>& messages, const LLSD& load_params) }
{
if (file_name.empty())
{
LL_WARNS("LLLogChat::loadHistory") << "Session name is Empty!" << LL_ENDL;
return ;
}
bool load_all_history = load_params.has("load_all_history") ? load_params["load_all_history"].asBoolean() : false;
LLFILE* fptr = LLFile::fopen(LLLogChat::makeLogFileName(file_name), "r");/*Flawfinder: ignore*/ void LLLoadHistoryThread::setHistoryParams(const std::string& file_name, const LLSD& load_params)
if (!fptr) {
{ mFileName = file_name;
fptr = LLFile::fopen(LLLogChat::oldLogFileName(file_name), "r");/*Flawfinder: ignore*/ mLoadParams = load_params;
if (!fptr) mNewLoad = true;
{ }
mNewLoad = false;
(*mLoadEndSignal)(messages, file_name);
return; //No previous conversation with this name.
}
}
char buffer[LOG_RECALL_SIZE]; /*Flawfinder: ignore*/ void LLLoadHistoryThread::loadHistory(const std::string& file_name, std::list<LLSD>& messages, const LLSD& load_params)
char *bptr; {
S32 len; if (file_name.empty())
bool firstline = TRUE; {
LL_WARNS("LLLogChat::loadHistory") << "Session name is Empty!" << LL_ENDL;
return ;
}
if (load_all_history || fseek(fptr, (LOG_RECALL_SIZE - 1) * -1 , SEEK_END)) bool load_all_history = load_params.has("load_all_history") ? load_params["load_all_history"].asBoolean() : false;
{ //We need to load the whole historyFile or it's smaller than recall size, so get it all.
firstline = FALSE;
if (fseek(fptr, 0, SEEK_SET))
{
fclose(fptr);
mNewLoad = false;
(*mLoadEndSignal)(messages, file_name);
return;
}
}
while (fgets(buffer, LOG_RECALL_SIZE, fptr) && !feof(fptr))
{
len = strlen(buffer) - 1; /*Flawfinder: ignore*/
for (bptr = (buffer + len); (*bptr == '\n' || *bptr == '\r') && bptr>buffer; bptr--) *bptr='\0';
if (firstline) LLFILE* fptr = LLFile::fopen(LLLogChat::makeLogFileName(file_name), "r");/*Flawfinder: ignore*/
{ if (!fptr)
firstline = FALSE; {
continue; fptr = LLFile::fopen(LLLogChat::oldLogFileName(file_name), "r");/*Flawfinder: ignore*/
} if (!fptr)
{
mNewLoad = false;
(*mLoadEndSignal)(messages, file_name);
return; //No previous conversation with this name.
}
}
std::string line(buffer); char buffer[LOG_RECALL_SIZE]; /*Flawfinder: ignore*/
char *bptr;
S32 len;
bool firstline = TRUE;
//updated 1.23 plaint text log format requires a space added before subsequent lines in a multilined message if (load_all_history || fseek(fptr, (LOG_RECALL_SIZE - 1) * -1 , SEEK_END))
if (' ' == line[0]) { //We need to load the whole historyFile or it's smaller than recall size, so get it all.
{ firstline = FALSE;
line.erase(0, MULTI_LINE_PREFIX.length()); if (fseek(fptr, 0, SEEK_SET))
append_to_last_message(messages, '\n' + line); {
}
else if (0 == len && ('\n' == line[0] || '\r' == line[0]))
{
//to support old format's multilined messages with new lines used to divide paragraphs
append_to_last_message(messages, line);
}
else
{
LLSD item;
if (!LLChatLogParser::parse(line, item, load_params))
{
item[LL_IM_TEXT] = line;
}
messages.push_back(item);
}
}
fclose(fptr); fclose(fptr);
mNewLoad = false; mNewLoad = false;
(*mLoadEndSignal)(messages, file_name); (*mLoadEndSignal)(messages, file_name);
return;
}
} }
//static while (fgets(buffer, LOG_RECALL_SIZE, fptr) && !feof(fptr))
boost::signals2::connection LLLoadHistoryThread::setLoadEndSignal(const load_end_signal_t::slot_type& cb)
{ {
if (NULL == mLoadEndSignal) len = strlen(buffer) - 1; /*Flawfinder: ignore*/
for (bptr = (buffer + len); (*bptr == '\n' || *bptr == '\r') && bptr>buffer; bptr--) *bptr='\0';
if (firstline)
{ {
mLoadEndSignal = new load_end_signal_t(); firstline = FALSE;
continue;
} }
return mLoadEndSignal->connect(cb); std::string line(buffer);
//updated 1.23 plaint text log format requires a space added before subsequent lines in a multilined message
if (' ' == line[0])
{
line.erase(0, MULTI_LINE_PREFIX.length());
append_to_last_message(messages, '\n' + line);
}
else if (0 == len && ('\n' == line[0] || '\r' == line[0]))
{
//to support old format's multilined messages with new lines used to divide paragraphs
append_to_last_message(messages, line);
}
else
{
LLSD item;
if (!LLChatLogParser::parse(line, item, load_params))
{
item[LL_IM_TEXT] = line;
}
messages.push_back(item);
}
} }
fclose(fptr);
mNewLoad = false;
(*mLoadEndSignal)(messages, file_name);
}
//static
boost::signals2::connection LLLoadHistoryThread::setLoadEndSignal(const load_end_signal_t::slot_type& cb)
{
if (NULL == mLoadEndSignal)
{
mLoadEndSignal = new load_end_signal_t();
}
return mLoadEndSignal->connect(cb);
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment