0

I have tried both strcat and strcat_s, but they both crash. Does anyone know why this happens? I can't find the problem.

Crash: "Unhandled exception at 0x58636D2A (msvcr110d.dll)"
_Dst        0x00ea6b30  "C:\\Users\\Ruben\\Documents\\School\\" char *
_SizeInBytes    260                         unsigned int
_Src        0x0032ef64  "CKV"                   const char *
available       228                         unsigned int
p           0x00ea6b50  ""                  char *

Code:

#include <Windows.h>
#include <strsafe.h>

extern "C"
{
    char* GetFilesInFolders(LPCWSTR filedir, char* path)
    {
        char* files = "";

        char DefChar = ' ';
        char* Streepje = "-";
        bool LastPoint = false;

        WIN32_FIND_DATA ffd;
        TCHAR szDir[MAX_PATH];
        HANDLE hFind = INVALID_HANDLE_VALUE;
        DWORD dwError = 0;

        StringCchCopy(szDir, MAX_PATH, filedir);
        hFind = FindFirstFile(szDir, &ffd);

        if (INVALID_HANDLE_VALUE == hFind) 
            return "";

        do
        {
            DWORD attributes = ffd.dwFileAttributes;
            LPCWSTR nm = ffd.cFileName;
            char name[260];
            WideCharToMultiByte(CP_ACP,0,ffd.cFileName,-1, name,260,&DefChar, NULL);

            for (int i = 0; i <= 260; i++)
            {
                if (name[i] == '.')
                    LastPoint = true;
                else if (name[i] == ' ')
                    break;
            }

            if (LastPoint == true)
            {
                LastPoint = false;
                continue;
            }

            if (attributes & FILE_ATTRIBUTE_HIDDEN)
            {
                continue;
            }
            else if (attributes & FILE_ATTRIBUTE_DIRECTORY)
            {
                char* newfiledir = "";
                char* newpath = path;
                char* add = "\\";
                char* extra = "*";
                strcat_s(newpath, sizeof(name), name);
                strcat_s(newpath, sizeof(add), add);
                puts(newpath);
                strcpy_s(newfiledir, sizeof(newpath) + 1, newpath);
                strcat_s(newfiledir, sizeof(extra) + 1, extra);
                puts(newfiledir);

                size_t origsize = strlen(newfiledir) + 1;
                const size_t newsize = 100;
                size_t convertedChars = 0;
                wchar_t wcstring[newsize];
                mbstowcs_s(&convertedChars, wcstring, origsize, newfiledir, _TRUNCATE);
                LPCWSTR dir = wcstring;
                GetFilesInFolders(dir, newpath);
            }
            else
            {
                char* file = path;
                strcat_s(file, sizeof(name), name);
                puts(file);
                strcat_s(files, sizeof(file), file);
                strcat_s(files, sizeof(Streepje), Streepje);
                puts(files);
            }
        }
        while (FindNextFile(hFind, &ffd) != 0);

        FindClose(hFind);
        return files;
    }
}

int _tmain(int argc, _TCHAR* argv[])
{
    char* path = "C:\\Users\\Ruben\\Documents\\School\\";
    char* filedir = "C:\\Users\\Ruben\\Documents\\School\\*";
    size_t origsize = strlen(filedir) + 1;
    const size_t newsize = 100;
    size_t convertedChars = 0;
    wchar_t wcstring[newsize];
    mbstowcs_s(&convertedChars, wcstring, origsize, filedir, _TRUNCATE);
    LPCWSTR dir = wcstring;
    char* files = GetFilesInFolders(dir, path);
    return 0;
}

Extra info: I don't want to use boost or strings and I want to keep this in unicode (default).

  • is name empty??? Did you try valgrind yet? –  Sep 25 '12 at 16:23
  • 1
    Since `add` is a `char *`, `sizeof(add)` is the same as `sizeof(char *)` which is definitely not what you want. Bluntly, it seems like you simply don't understand how to use C-style strings at all. – David Schwartz Sep 25 '12 at 16:51

2 Answers2

2

You assign a const char* to files, then attempt to append to it.

char* files = "";
// ... 
strcat_s(files, sizeof(file), file);

You cannot modify a constant string literal.

I would recommend that you turn on compiler warnings and make sure to look at them. This would warn you about assigning a const char* to a char*. To fix it, you might have changed files to be const, which would then cause your strcpy_s to no longer compile.

Dark Falcon
  • 43,592
  • 5
  • 83
  • 98
  • Good catch that the destination is in read-only memory. The insufficient size of the destination buffer is also a serious problem. – Ben Voigt Sep 25 '12 at 16:36
  • I have compiler warnings turned on AFAIK, and I don't get any error messages. Also both "files" and "file" are char*. –  Sep 25 '12 at 16:37
0

It looks like you don't understand how variables are stored in memory or how pointers work. In your _tmain() you have char * path pointing to a constant string literal, which you pass into GetFilesInFolders(), where it gets modified. Compilers tend to allow char *s to point at constant strings for backward compatibility with old C programs. You cannot modify these. You cannot append to them. The compiler (generally) puts these in a read-only segment. That's one reason why you're getting an exception.

Your whole GetFilesInFolders() is wrong. And as DarkFalcon pointed out, you haven't allocated any space anywhere for files, you have it pointing to a constant string literal.

Get "The C++ Programming Language" and read chapter 5.

Rob K
  • 8,757
  • 2
  • 32
  • 36