Skip to main content
GameDev.net gamedev.net
🔒 Locked

Variable corrupting when a function finishes

Started by Nauraushaun Dec 15, 2010 at 3:00 PM 15 replies 2.9k views
Original Post
Nauraushaun
Nauraushaun
Forgive me if this is beneath the people on this forum, but I've been having a problem with a certain variable. My program has an "update" and "render" function, and in the "update" function I set a const char pointer to some text. But as soon as the function exits, the pointer starts pointing to jibberish. The pointer belongs to an object that doesn't get deleted or anything, so I assumed the pointer and whatever it's pointing to would be safe (that is, wouldn't get deleted once the function finished).
In case it was a matter of the char getting out of scope, I tried creating the char on the heap (using the new keyword), but the same thing happened.
The problem seems to be that the program is deciding my char is out of scope, and deleting it, even though it's not, and there's a pointer pointing to it.

Have I made some mistake?
Sneftel
Sneftel
Post your actual code.
Nauraushaun
Nauraushaun
Never mind, I'm having all sorts of other problems now instead.
Basically, I've got this:
char* cCurrentFunctionName = "Quit";
char cMenuHeaderBuffer[100] = "Please enter a key for the ";

strcat_s(cMenuHeaderBuffer, sizeof(cMenuHeaderBuffer), cCurrentFunctionName);

m_szMenuHeader = cMenuHeaderBuffer;

Where m_szMenuHeader is a const char*.
I need to create a char array, concatenate it with another char array, then assign it to a const char*.
The problem is that everything has to be in an exact form, or some function won't accept it. The cMenuHeaderBuffer has to take the form of an array like it is, or strcat flips out. The m_szMenuHeader has to be a const char*, or a later method flips out.
What I've got here works, except that the program is inexplicably deciding to erase the contents of m_szMenuHeader as soon as the function ends.

I've also found that if I set m_szMenuHeader to "sometext", it works fine. It only forgets it when there's a variable assigned to it.

[Edited by - Nauraushaun on December 15, 2010 7:55:25 PM]
no such user
no such user
Just use std::string and don't worry about manually juggling the char pointers.
Palidine
Palidine
Quote:
Original post by Nauraushaun
What I've got here works, except that the program is inexplicably deciding to erase the contents of m_szMenuHeader as soon as the function ends.


Which is why Sneftel asked you to post your actual code. Just post the entire function exactly as you've written it. Not "basically" what you have, but what you have.

However from what you've posted, it looks like you're trying to return a pointer to a local stack array which is not going to work because the memory to which it points goes out of scope as soon as the function ends.

-me
Nauraushaun
Nauraushaun
I considered that, but getting my array to work on the heap requires a different syntax and a whole new set of problems.

I've heard that std::string is often impractical to use in games development.

I realize that I should've posted my code to begin with, but it was a mess of confusing stuff that's irrelevant to the problem. Took some cleaning up.
silvermace
silvermace
what is m_szMenuHeader's type, is it "char* m_szMenuHeader" or "char m_szMenuHeader[100]" ?

this is your problem line:
m_szMenuHeader = cMenuHeaderBuffer

if m_szMenuHeader is infact a char array and not a char pointer, then you can fix it by using:

strcpy(m_szMenuHeader, cMenuHeaderBuffer);

While this may fix your current problem, you are heading for a world of hurt if you dont use the right tools for the job.

C++ version
struct foo {  std::string m_sMenuHeader;  void bar() {     std::string s("Please enter a key for the ");     s += std::string("Quit");     m_sMenuHeader = s;  }};
SiCrane
SiCrane
std::string isn't the perfect string class for all uses. It's a generic string class and so there will always be problem domains where a different string implementation would be better. However, it's a "good enough" solution for most situations, including game development, and it's certainly more practical than debugging manual memory allocations. If you want to do better than std::string, the solution is a different string class not no string class.
Nauraushaun
Nauraushaun
It's type is char* m_szMenuHeader, so I can't use strcpy.
That's just the problem, converting those two. And it works fine except that it's getting corrupted. I never knew it was so hard to convert char to char :\
Chris_F
Chris_F
I can't think of any situation in which managing your own dynamic character arrays would be a good idea. Using the STL containers is the right thing to do 99% of the time. I've noticed a lot of people on this forum in particular who think it's better to reinvent the wheel, which is surprising because that's usually frowned on most other places.
silvermace
silvermace
you may not want to hear this, but it sounds like you don't have a good grasp of C++ and how it all works yet. If you want to get stuff explained to you, you're probably going to have provide a more complete picture of your code. It sounds like you're trying different things and just hoping, and that's not the best way to go about this particular issue.
Nauraushaun
Nauraushaun
I've been taught that most game consoles can't use C++ strings, and that I should learn to use c-strings as a substitute.

I'm willing to admit I don't know the language that well, it's all part of the learning process ;)
rip-off
rip-off
Quote:
Original post by Nauraushaun
I've been taught that most game consoles can't use C++ strings, and that I should learn to use c-strings as a substitute.

Are you writing for a console?

I'm pretty sure that consoles can use C++ strings, they just don't for a variety of reasons (memory budgets, avoiding dynamic allocation). These restrictions don't apply to you unless your game will max out a modern console.

You can learn C strings later when you have a better understanding of the basics. std::string can be considered a thin wrapper over C strings anyway.
Nauraushaun
Nauraushaun
You're right, but I would still like to understand them. What's more, what happens in circumstances such as this, when I need different types of c-strings to pass in to different functions? For example, I'm using Direct3D, and the function to render my font insists that I pass it a value created as:
char* cVariable;
rip-off
rip-off
std::string::c_str() returns a const char * that can be passed directly to functions expecting a C string.

The problem you are having is that "m_szMenuHeader" appears to be some kind of character pointer, which is pointed at the local array "cMenuHeaderBuffer". This buffer goes out of scope once the function completes. If you made "m_szMenuHeader" a character array, and strcat() the necessary data to it directly, then you shouldn't have this problem.

If you keep it as a pointer you'll have to use dynamic allocation, which is in every way worse than simply changing the data type. When working with C strings, use char arrays, not pointers, for storing the strings. Only use pointers for reading or writing to them, or passing them temporarily to functions. Unless you are 110% sure of what you are doing, avoid using character pointers as members.

This is what Palidine and silvermace were saying.
Nauraushaun
Nauraushaun
I see. Okay. That's very useful advice, eliminating the char pointers. I'm doing some fiddling and I believe it to be working, though we won't know until it compiles. But it's bedtime.

Thanks everyone for your help so far. See you tomorrow :P
Nauraushaun
Nauraushaun
Oh, it works perfectly. It's actually a bit weird, using a certain function in my program and not having it output jibberish. I didn't realize those char pointers were do dangerous. In the end I cut them out and started just using char arrays.

Thanks everyone for all the advice.

Topic Locked

This topic has been locked by a moderator. New replies are not allowed.

Sign in to reply to this topic.