I keep getting this error and I'm not sure how to correct it as I am given no errors in my code editors. I have looked up similar issues, but I am still having trouble to understand how to apply the solutions here. I've tried altering my code for several hours now, but to no avail. Any help would be appreciated. I have provided my .h and .cpp files below.
ErrorMessage.h
#ifndef SICT_ERRORMESSAGE_H
#define SICT_ERRORMESSAGE_H
#include <iostream>
namespace sict {
class ErrorMessage {
char* message_; //pointer that holds the address of the message stored in current object
public:
explicit ErrorMessage(const char* errorMessage = nullptr); //receive address of a C-style nullterminate string holding an error message
ErrorMessage(const ErrorMessage& em) = delete; //deleted copy constructor that prevents copying of an ErrorMessage object
ErrorMessage& operator=(const ErrorMessage& em) = delete; //deleted assignment operator that prevents assignment of ErrorMessage object to current object
virtual ~ErrorMessage(); //deallocates any memory that has been dynamically allocated by the current object
void clear(); //clears any message stored by current object and initialize object to safe, empty state
bool isClear() const; //return true if object is in a safe, empty state
void message(const char* str); //stores a copy of the C-style string pointed to by str
const char* message() const; //return address of the message stored in current object
};
//helper operator
std::ostream& operator<<(std::ostream& os, const ErrorMessage& err);
}
#endif
ErrorMessage.cpp
#define _CRT_SECURE_NO_WARNINGS
#include <iostream>
#include <cstring>
#include "ErrorMessage.h"
namespace sict {
ErrorMessage::ErrorMessage(const char* errorMessage) {
if(errorMessage == nullptr) {
message_ = nullptr;
}
else {
message(errorMessage);
}
}
ErrorMessage::~ErrorMessage() {
delete [] message_;
}
void ErrorMessage::clear() {
delete [] message_;
message_ = nullptr;
}
bool ErrorMessage::isClear() const {
if(message_ == nullptr) {
return true;
}
else {
return false;
}
}
void ErrorMessage::message(const char* str) {
delete [] message_;
message_ = new char[strlen(str) + 1];
strcpy(message_, str);
}
const char* ErrorMessage::message() const {
return message_;
}
std::ostream& operator<<(std::ostream& os, const ErrorMessage& err) {
if(!err.isClear()) {
os << err.message();
}
return os;
}
}
It's not surprising your code made it through editor syntax checks and compilation - it's valid code. It's just got an incorrect pointer somewhere.
This may mean that your'e accidentally dereferencing something , or perhaps passing a value somewhere you should be passing a pointer. You should get a compile time warning about that kind of stuff.
Another possibility is that you're failing to initialize some pointer, and its value happens to be 0xb75....
Clearly, neither you nor I are not likely to guess from whence this error originates. As Sam Varshavchik pointed out in a comment, you don't even know if the code you posted is the source of the error. Even if you guess your way through this one ( or perhaps keenly observe, Sam ), it's just plain silly to try to write C++ that way.
What you need is a debugger. A debugger is a program you run your program within, and it keeps track of the program's state so that when you have a memory violation, the debugger can produce a backtrace showing where in your source code the error occurred. You also have to compile your program with debugging support, so that the debugger has markers it can use to refer back to the source code.
It's a process far beyond the scope of your question, but one that's easy to learn about once you know what you're going for. Look for one that integrates with your IDE, if possible, as you're leveraging your development environment heavily. It's not unlikely that you already have it set up- you might just need to use it. Search for C++ debugging in the context of your editor first - if it turns up nothing, consider searching under your compiler suite, whatever that may be ( if your'e using open source, you're probably using gcc, and the matching debugger is gdb ).
You're about to gain a far more accurate understanding of what it is to program C / C++. Good luck.
Related
I'd like to use C++ version of SymSpell, which is called SymSpellPlusPlus. In C# version using WordSegmentation looks like this (from the first link):
//word segmentation and correction for multi-word input strings with/without spaces
inputTerm="thequickbrownfoxjumpsoverthelazydog";
maxEditDistance = 0;
suggestion = symSpell.WordSegmentation(input);
//display term and edit distance
Console.WriteLine(suggestion.correctedString + " " + suggestion.distanceSum.ToString("N0"));
In C++ version method WordSegmentation returns shared pointer (from the second link):
...
shared_ptr<WordSegmentationItem> WordSegmentation(const char* input)
{
return WordSegmentation(input, this->maxDictionaryEditDistance, this->maxDictionaryWordLength);
}
shared_ptr<WordSegmentationItem> WordSegmentation(const char* input, size_t maxEditDistance)
{
return WordSegmentation(input, maxEditDistance, this->maxDictionaryWordLength);
}
shared_ptr<WordSegmentationItem> WordSegmentation(const char* input, size_t maxEditDistance, size_t maxSegmentationWordLength)
{
// lines 1039 - 1179 under second link
std::vector<shared_ptr<WordSegmentationItem>> compositions;
...
return compositions[circularIndex];
}
In my code I tried among others the following code:
const char* inputTerm = "whereis th elove hehad dated forImuch of thepast who couqdn'tread in sixtgrade and ins pired him";
auto suggestions = symSpell.WordSegmentation(inputTerm);
But it gives an error:
free() invalid next size (fast)
It is related to memory error, but I don't know how to overcome this problem.
Class WordSegmentationItem looks as follows (lines 292-325 in second link):
class WordSegmentationItem
{
public:
const char* segmentedString{ nullptr };
const char* correctedString{ nullptr };
u_int8_t distanceSum = 0;
double probabilityLogSum = 0;
WordSegmentationItem() { }
WordSegmentationItem(const symspell::WordSegmentationItem & p)
{
this->segmentedString = p.segmentedString;
this->correctedString = p.correctedString;
this->distanceSum = p.distanceSum;
this->probabilityLogSum = p.probabilityLogSum;
}
WordSegmentationItem& operator=(const WordSegmentationItem&) { return *this; }
WordSegmentationItem& operator=(WordSegmentationItem&&) { return *this; }
void set(const char* pSegmentedString, const char* pCorrectedString, u_int8_t pDistanceSum, double pProbabilityLogSum)
{
this->segmentedString = pSegmentedString;
this->correctedString = pCorrectedString;
this->distanceSum = pDistanceSum;
this->probabilityLogSum = pProbabilityLogSum;
}
~WordSegmentationItem()
{
delete[] segmentedString;
delete[] correctedString;
}
};
How should I get the correctedString from the WordSegmentationItem?
The library is buggy and the author needs to make some fixes.
First, compiling gives us a warning about SuggestItem::ShallowCopy, which returns a local variable by reference. Very bad! We can change that to return by value, probably.
This doesn't fix the crash, though.
If we clone the library's repo then run the following testcase in a debugger:
#include "symspell6.h"
int main()
{
const char* inputTerm = "whereis th elove hehad dated forlmuch of thepast who couqdn'tread in sixtgrade and ins pired him";
symspell::SymSpell symSpell;
auto suggestions = symSpell.WordSegmentation(inputTerm);
}
…we see that returning compositions[circularIndex] from the WordSegmentation function is causing an invalid access in the shared_ptr constructor. This suggests that circularIndex is out-of-bounds and giving us a non-existent shared_ptr. Indeed, circularIndex is 95 but compositions.size() is 0!
The function is lacking some serious error checking.
Now, only the author (or at least someone who knows what the library is supposed to do; that's not me!) can fix this properly. But as a quick patch I added the following after line 1055:
if (compositions.empty())
return nullptr;
…and it now at least runs.
It seems that the function assumes the dictionary is non-empty. I don't know whether that's expected behaviour or not (other than the missing error checking as detailed above).
The project is in serious need of some documentation, because no preconditions or postconditions are mentioned for these functions and there is no indication as to how the library is supposed to be used. Again, the author should fix these things.
I'm trying to create a constructor in which the strings are dynamically allocated. I've looked up dynamically allocated memory several times and watched a video about it, but I'm still not 100% sure if I'm understanding the concept. I'm hoping an example specific to what I'm coding will help me out a bit.
These are the private variables I have in my h file:
string* tableID;
int numSeats;
string* serverName;
With that in mind, could someone tell me how I could dynamically allocate memory for the strings in this constructor?
Table::Table(const string& tableID, int numSeats, const string& serverName) {
}
Finally, I would greatly appreciate it if someone could tell me the purpose of dynamically allocated memory. I've see explanations on what dynamically allocate memory is, but I'm not understanding the use of it. Why use dynamically allocated memory? What are the benefits? What are the drawbacks? Thank you!
EDIT: I'm including the rest of the h file. Note that this wasn't created by me, so I can't make changes to it. I can only adhere to it in the cpp file.
#include <string>
#include "party.h"
using std::string;
class Table {
public:
Table();
Table(const string& tableID, int numSeats, const string& serverName);
~Table();
const string* getTableID() const { return tableID; }
int getNumSeats() const { return numSeats; }
const string* getServerName() const { return serverName; }
void decrementTimer() { timer--; }
int getTimer() const { return timer; }
void setTimer(int duration) { timer = duration; }
const Party* getParty() { return party; }
void seatParty(const Party* newParty);
void clearTable() { party = nullptr; timer = 0; }
private:
string* tableID;
int numSeats;
string* serverName;
int timer;
const Party* party;
};
The easiest way to get what you want is to take advantage of the Member Initializer List as this also solves the problem of having the parameters shadow the member variables of the same name.
Table::Table(const string& tableID,
int numSeats,
const string& serverName):
tableID(new string(tableID)),
numSeats(numSeats),
serverName(new string(serverName))
{
}
Allocation is performed with the new operator. Later you will have to release the dynamically allocated memory with the delete operator. Here is documentation on new and the same for delete.
But the use a pointer requirement is bizarre as storing pointers to string makes everything else you with the class do orders of magnitude more difficult. This may be the point of the assignment, but there are better and less-confusing ways to teach this lesson.
The allocated strings must be released. The C++ idiom of Resource Allocation Is Initialization (What is meant by Resource Acquisition is Initialization (RAII)?) suggests you have a destructor to automate clean-up to ensure that it is done. If you need a destructor, you almost always need the other two members of The Big Three (What is The Rule of Three?) and possibly need to take The Rule of Five into account as well.
Whereas because string observes the Rule of Five for you, you should be able to take advantage of the Rule of Zero and implement no special functions.
M.M raises an excellent point in the comments. The above example is too naive. It is probably all you need for the assignment, but it's not good enough for real code. Sooner or later it will fail. Example of how it fails.
First we replace string with something that can expose the error:
class throwsecond
{
static int count;
public:
throwsecond(const string &)
{
if (count ++)
{
count = 0; // reset count so only every second fails
throw runtime_error("Kaboom!");
}
cout << "Constructed\n";
}
~throwsecond()
{
cout << "Destructed\n";
}
};
int throwsecond::count = 0;
Then a simple class that does basically the above with less frills
class bad_example
{
throwsecond * a;
throwsecond * b;
public:
bad_example(): a(nullptr), b(nullptr)
{
}
bad_example (const string& a,
const string& b)
{
this->a = new throwsecond(a);
this->b = new throwsecond(b);
}
~bad_example()
{
delete a;
delete b;
}
};
and a main to exercise it
int main()
{
cout << "Bad example\n";
try
{
bad_example("", "");
}
catch (...)
{
cout << "Caught exception\n";
}
}
Output:
Bad example
Constructed
Caught exception
We have an object constructed and never destroyed.
Since a default constructor has been defined by Table we can, with a compiler that supports the C++11 or a more recent Standard, take advantage of delegated constructors to force destruction of the partially constructed object because it has been fully constructed by the default constructor.
class good_example
{
throwsecond * a;
throwsecond * b;
public:
good_example():
a(nullptr), b(nullptr) //must be nulled or destruction is dicey
{
}
good_example (const string& a,
const string& b) : good_example() // call default constructor
{
this->a = new throwsecond(a);
this->b = new throwsecond(b);
}
~good_example()
{
delete a;
delete b;
}
};
Output:
Good example
Constructed
Destructed
Caught exception
One construct and one destruct. The beauty of this approach is it scales well and adds nothing to the code that you don't already have. The cost is minimal, a and b get initialized and then assigned as opposed to just initialization. Faster code is useless if it doesn't work.
Full example: https://ideone.com/0ckSge
If you can't compile to a modern standard, you wind up doing something like
the next snippet to make sure everything is deleted. It's main sin is it's ugly, but as you add more classes that must be constructed and destroyed it starts getting unwieldy.
Table::Table(const string& tableID,
int numSeats,
const string& serverName):
tableID(NULL),
numSeats(numSeats),
serverName(NULL)
{
try
{
this->tableID(new string(tableID)),
// see all the this->es? don't shadow variables and you won't have this problem
// miss a this-> and you'll have a really bad day of debugging
this->serverName(new string(serverName))
// more here as required
}
catch (...)
{
delete this->tableID;
delete this->serverName;
// more here as required
throw;
}
}
There is probably a way to improve on this and make it more manageable, but I don't know it. I just use newer standards and value semantics (I'd love it if someone can provide a good link that describes this concept) where possible.
One error that I often see is a container being cleared whilst iterating through it. I have attempted to put together a small example program demonstrating this happening. One thing to note is that this can often happen many function calls deep so is quite hard to detect.
Note: This example deliberately shows some poorly designed code. I am trying to find a solution to detect the errors caused by writing code such as this without having to meticulously examine an entire codebase (~500 C++ units)
#include <iostream>
#include <string>
#include <vector>
class Bomb;
std::vector<Bomb> bombs;
class Bomb
{
std::string name;
public:
Bomb(std::string name)
{
this->name = name;
}
void touch()
{
if(rand() % 100 > 30)
{
/* Simulate everything being exploded! */
bombs.clear();
/* An error: "this" is no longer valid */
std::cout << "Crickey! The bomb was set off by " << name << std::endl;
}
}
};
int main()
{
bombs.push_back(Bomb("Freddy"));
bombs.push_back(Bomb("Charlie"));
bombs.push_back(Bomb("Teddy"));
bombs.push_back(Bomb("Trudy"));
for(size_t i = 0; i < bombs.size(); i++)
{
bombs.at(i).touch();
}
return 0;
}
Can anyone suggest a way of guaranteeing this cannot happen?
The only way I can currently detect this kind of thing is replacing the global new and delete with mmap / mprotect and detecting use after free memory accesses. This and Valgrind however sometimes fail to pick it up if the vector does not need to reallocate (i.e only some elements removed or the new size is not yet the reserve size). Ideally I don't want to have to clone much of the STL to make a version of std::vector that always reallocates every insertion/deletion during debug / testing.
One way that almost works is if the std::vector instead contains std::weak_ptr, then the usage of .lock() to create a temporary reference prevents its deletion whilst execution is within the classes method. However this cannot work with std::shared_ptr because you do not need lock() and same with plain objects. Creating a container of weak pointers just for this would be wasteful.
Can anyone else think of a way to protect ourselves from this.
Easiest way is to run your unit tests with Clang MemorySanitizer linked in.
Let some continuous-integration Linux box to do it automatically on each push
into repo.
MemorySanitizer has "Use-after-destruction detection" (flag -fsanitize-memory-use-after-dtor + environment variable MSAN_OPTIONS=poison_in_dtor=1) and so it will blow the test up that executes the code and that turns your continuous-integration red.
If you have neither unit tests nor continuous integration in place then you can also just manually debug your code with MemorySanitizer but that is hard way compared with the easiest. So better start to use continuous integration and write unit tests.
Note that there may be legitimate reasons of memory reads and writes after destructor has been ran but memory hasn't yet been freed. For example std::variant<std::string,double>. It lets us to assign it std::string then double and so its implementation might destroy the string and reuse same storage for double. Filtering such cases out is unfortunately manual work at the moment, but tools evolve.
In your particular example the misery boils down to no less than two design flaws:
Your vector is a global variable. Limit the scope of all of your objects as much as possible and issues like this are less likely to occur.
Having the single responsibility principle in mind, I can hardly imagine how one could come up with a class that needs to have some method that either directly or indirectly (maybe through 100 layers of call stack) deletes objects that could happen to be this.
I am aware that your example is artificial and intentionally bad, so please don't get me wrong here: I'm sure that in your actual case it is not so obvious how sticking to some basic design rules can prevent you from doing this. But as I said, I strongly believe that good design will reduce the likelyhood of such bugs coming up. And in fact, I cannot remember that I was ever facing such an issue, but maybe I am just not experienced enough :)
However, if this really keeps being an issue despite sticking with some design rules, then I have this idea how to detect it:
Create a member int recursionDepth in your class and initialize it with 0
At the beginning of each non-private method increment it.
Use RAII to make sure that at the end of each method it is decremented again
In the destructor check it to be 0, otherwise it means that the destructor is directly or indirectly called by some method of this.
You may want to #ifdef all of this and enable it only in debug build. This would essentially make it a debug assertion, some people like them :)
Note, that this does not work in a multi threaded environment.
In the end I went with a custom iterator that if the owner std::vector resizes whilst the iterator is still in scope, it will log an error or abort (giving me a stacktrace of the program). This example is a bit convoluted but I have tried to simplify it as much as possible and removed unused functionality from the iterator.
This system has flagged up about 50 errors of this nature. Some may be repeats. However Valgrind and ElecricFence at this point came up clean which is disappointing (In total they flagged up around 10 which I have already fixed since the start of the code cleanup).
In this example I use clear() which Valgrind does flag as an error. However in the actual codebase it is random access erases (i.e vec.erase(vec.begin() + 9)) which I need to check and Valgrind unfortunately misses quite a few.
main.cpp
#include "sstd_vector.h"
#include <iostream>
#include <string>
#include <memory>
class Bomb;
sstd::vector<std::shared_ptr<Bomb> > bombs;
class Bomb
{
std::string name;
public:
Bomb(std::string name)
{
this->name = name;
}
void touch()
{
if(rand() % 100 > 30)
{
/* Simulate everything being exploded! */
bombs.clear(); // Causes an ABORT
std::cout << "Crickey! The bomb was set off by " << name << std::endl;
}
}
};
int main()
{
bombs.push_back(std::make_shared<Bomb>("Freddy"));
bombs.push_back(std::make_shared<Bomb>("Charlie"));
bombs.push_back(std::make_shared<Bomb>("Teddy"));
bombs.push_back(std::make_shared<Bomb>("Trudy"));
/* The key part is the lifetime of the iterator. If the vector
* changes during the lifetime of the iterator, even if it did
* not reallocate, an error will be logged */
for(sstd::vector<std::shared_ptr<Bomb> >::iterator it = bombs.begin(); it != bombs.end(); it++)
{
it->get()->touch();
}
return 0;
}
sstd_vector.h
#include <vector>
#include <stdlib.h>
namespace sstd
{
template <typename T>
class vector
{
std::vector<T> data;
size_t refs;
void check_valid()
{
if(refs > 0)
{
/* Report an error or abort */
abort();
}
}
public:
vector() : refs(0) { }
~vector()
{
check_valid();
}
vector& operator=(vector const& other)
{
check_valid();
data = other.data;
return *this;
}
void push_back(T val)
{
check_valid();
data.push_back(val);
}
void clear()
{
check_valid();
data.clear();
}
class iterator
{
friend class vector;
typename std::vector<T>::iterator it;
vector<T>* parent;
iterator() { }
iterator& operator=(iterator const&) { abort(); }
public:
iterator(iterator const& other)
{
it = other.it;
parent = other.parent;
parent->refs++;
}
~iterator()
{
parent->refs--;
}
bool operator !=(iterator const& other)
{
if(it != other.it) return true;
if(parent != other.parent) return true;
return false;
}
iterator operator ++(int val)
{
iterator rtn = *this;
it ++;
return rtn;
}
T* operator ->()
{
return &(*it);
}
T& operator *()
{
return *it;
}
};
iterator begin()
{
iterator rtn;
rtn.it = data.begin();
rtn.parent = this;
refs++;
return rtn;
}
iterator end()
{
iterator rtn;
rtn.it = data.end();
rtn.parent = this;
refs++;
return rtn;
}
};
}
The disadvantages of this system is that I must use an iterator rather than .at(idx) or [idx]. I personally don't mind this one so much. I can still use .begin() + idx if random access is needed.
It is a little bit slower (nothing compared to Valgrind though). When I am done, I can do a search / replace of sstd::vector with std::vector and there should be no performance drop.
I have a C++ structure defined as follows:
typedef struct event{
int id;
string name;
//int arg0;
QByteArray data;
bool operator<(const event& e) const
{
return id < e.id;
}
bool operator==(const event& e) const
{
return id == e.id;
}
}Event;
I also have a map defined as follows:
map<string, set<Event>> mapOfEventsByString;
When I want to see if an Event is associated to a given string I use this line of code:
if(mapOfEventsByString.find(aString)->second.count(event)==1)
{
//do stuff
}
Problem: Sometimes (and I mean that 9/10 times I can run the entire application with the exact same data set without any problems), I get a segmentation fault here:
bool operator<(const event& e) const
{
return id < e.id; <------- GIVES SEGMENTATION FAULT SOMETIMES
}
After many attempts at reproducing the error while debugging, I managed to pinpoint the segfault to that line. In that scenario e.id is filled with data and id says: "no such value".
Help?
Thank you
Without a backtrace we are only guessing, but this is a strong indication that the member id doesn't exist, so you're accessing memory you shouldn't.
If the member id doesn't exist, then your operator< call is broken. Given that it is invoked by the below highlighted part of your code:
if(mapOfEventsByString.find(aString)->second.count(event)==1)
// ^^^^^^^^^^^^^
that suggests to me that the below highlighted expression does not assuredly refer to a valid object:
if(mapOfEventsByString.find(aString)->second.count(event)==1)
// ^^^^^^
The only way that can happen is if the below highlighted dereference operation is invalid:
if(mapOfEventsByString.find(aString)->second.count(event)==1)
// ^^
which occurs when the find fails, returning mapOfEventsByString.end() (which cannot be dereferenced):
if(mapOfEventsByString.find(aString)->second.count(event)==1)
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
I think if you actually check for find success you'll see that, 1 out of 10 times, aString was not found in mapOfEventsByString.
Let's do this, instead:
const auto it = mapOfEventsByString.find(aString);
if (it != mapOfEventsByString.end() && it->second.count(event) == 1) {
// do stuff
}
Now you can put a breakpoint in for when it == mapOfEventsByString.end() and investigate why the find is failing. Good luck!
I've been bragging a friend of mine about C++ (scopes and RAII and static typing ftw) (I'd be embarrassed if this were me and not ask :P) but as I'm looking at it I am puzzled as tp what is going wrong. I hope you guys can help. She's coming from Java hence the CamcelCase
ListIndexOutOfBoundsException.h
#ifndef LISTINDEXOUTOFBOUNDSEXCEPTION_H_
#define LISTINDEXOUTOFBOUNDSEXCEPTION_H_
#include <exception>
namespace Structures {
class ListIndexOutOfBoundsException: public ::std::exception {
public:
ListIndexOutOfBoundsException(int index, int length);
virtual const char* what() const noexcept;
virtual ~ListIndexOutOfBoundsException() noexcept;
private:
const char* errorString;
};
}
#endif /* LISTINDEXOUTOFBOUNDSEXCEPTION_H_ */
ListIndexOutOfBoundsException.cpp
#include "ListIndexOutOfBoundsException.h"
#include <string>
#include <sstream>
namespace Structures {
using ::std::stringstream;
ListIndexOutOfBoundsException::ListIndexOutOfBoundsException(int index,int length) {
stringstream errorText("List index (");
errorText<<index<<") out of bounds! (list length: "<<length<<")";
errorString = errorText.str().c_str();
}
const char* ListIndexOutOfBoundsException::what() const noexcept {
return errorString;
}
ListIndexOutOfBoundsException::~ListIndexOutOfBoundsException() noexcept {
delete errorString;
}
}
When thrown this happens:
terminate called after throwing an instance of
'Structures::ListIndexOutOfBoundsException'
what(): OfBoundsException
I cannot work out where "OfBoundsException" has come from. What is going on!?
When the constructor goes out of scope, errorText no longer points to valid data, so all bets are off when you call what() (it invokes undefined behavior). The easiest fix is to derive from std::runtime_error, as that keeps a std::string (or equivalent) which is valid for the lifetime of the exception.
The problem is this
errorString = errorText.str().c_str();
errorText was a local object to the constructor that went out of scope and freed the memory it was using for it's c_str().
Try replacing errorString with a char errorString[SomeLimit]; and using basic string operations to write to it. Using a stringstream is somewhat overly complex for an exceptionhandler.