-2

note: the title may not be relevant to the issue, because I can't understand where the issue comes from.

The isuue: I have a piece of code which gets a filename from a dir and appends it to a vector < char* >. It works ok, but if I wrap it in a function, it gives weird behavior, the resulting vector element prints single random character in console instead of the filename. I have checked and re-checked everything but can't see why it is happening.

Below is complete runnable code, I compiled it on Windows with cl.exe namely just cl.exe "a.cpp" /EHsc. x64 native environment and target.

I put together both pieces, for easier testing.

#include <windows.h>
#include <iostream>
#include <vector>

using namespace  std;

void  getimglist ( const char*  mask,  vector < char* > & flist )
{
WIN32_FIND_DATA         data;
HANDLE              hFind;

hFind = FindFirstFile ( mask, & data );
cout << "-fname: " << data.cFileName << "\n";
flist.push_back ( data.cFileName ); 
FindClose ( hFind );
}

int main  (int argc,  char* argv[]) 
{
vector < char* >    L ;
vector < char* >    L2 ;
const char*     mask = ".\\input-cam0\\*.jpg";
const char*     mask2 = ".\\input-cam0\\*.jpg";

//  this code works 
WIN32_FIND_DATA         data;
HANDLE              hFind;

hFind = FindFirstFile ( mask, & data );
cout << " first file: " << data.cFileName << "\n";
L.push_back ( data.cFileName ); 
FindClose (hFind);
// ***

cout << " size:" << L.size() << "\n";
cout << " first file L:" << L[0] << "\n";


// this works weird, output is different and wrong
cout << " ** function call **\n";
getimglist ( mask2, L2 );
cout << " size:" << L2.size() << "\n";
cout << " first file: " << L2[0] << "\n";

return 0;

} // end main

Output:

 first file: 000-001.jpg
 size:1
 first file L:000-001.jpg
 ** function call **
-fname: 000-001.jpg
 size:1
 first file: R 

See the last line ^, here it is R, and if I run multiple times the exe file, it prints single random character. And the result from main block gives correct results. Where is the problem?

Mikhail V
  • 1,416
  • 1
  • 14
  • 23
  • 1
    Why is `vector` used? Is `std::string` known to You? – Robert Andrzejuk Nov 19 '18 at 16:51
  • 1
    You are pushing dangling pointers into that vector, they point to complete garbage once the function returns. The lifetime of &data.cFileName ends when the function ends. You must use `vector`. – Hans Passant Nov 19 '18 at 16:54

1 Answers1

1

WIN32_FIND_DATA data is allocated on the stack, stack memory is destroyed when your variable goes out of scope (in this case at the end of the function). This means that the pointer you have stored in your vector doesn't point to a valid address any more. When you print it the application happily prints whatever is now in the specified memory segment.

The simple fix is to copy the string into a new variable, the preferred way to do this would be to change your vectors into vector<std::string>. You can still call flist.push_back ( data.cFileName ) and the compiler will copy the character array into a std::string for you.

Alan Birtles
  • 32,622
  • 4
  • 31
  • 60
  • ha, it worked! thanks. I blame here silly error messages from cl.exe - not myself :) I have tried it before with vector < string > but it just floods the console with non-intuitive error descriptions. In reality I just needed to write `include ` to make it work with `vector `. – Mikhail V Nov 19 '18 at 21:24