From: scs0 on
Why is this functionality so difficult to do and find described
online?

If you know the exact steps - I mean the EXACT code - for deleting a
folder (and yes that means it can have files and folders within it
please let me know how it's done EXACTLY. My code isn't working


If you're just going to do the usual newsgroup thing where you give me
a riddle, a tip that leads nowhere, or a fragment of an answer please
hit the back button now. I need an actual answer that actually works.


BTW: Here's what I did and it fails:

// Delete the contents of the driver's backup folder
SHFILEOPSTRUCTW info;
memset(&info, 0, sizeof(info));
info.wFunc = FO_DELETE;
info.fFlags = FOF_NOCONFIRMATION | FOF_SILENT;

TCHAR szBuffer[2048];
memset(szBuffer, 0, sizeof(szBuffer));
_tcscpy(szBuffer, _T("\\\\?\\"));
_tcscat(szBuffer, (LPCTSTR)strFolderToDelete);

info.pFrom = szBuffer;
if (0 != SHFileOperationW(&info))
From: Sheng Jiang[MVP] on
If you just want something works, search for delete folder SHFileOperation
and you will find plenty of code that actually work.

If you want to correct your error check the return value of SHFileOperation
and compare it to the possible return values listed in SHFileOperation's
documentation in MSDN

In addition, memset(szBuffer, 0, sizeof(szBuffer)); may not empty the whole
buffer if your program is compiled in a Unicode configuration. TCHAR is 2
bytes in a Unicode configuration

I am not sure why you add "\\\\?\\" to the front of the folder path. Use
PathFileExists to check if you are deleting a nonexistent folder.

--
Sheng Jiang
Microsoft MVP in VC++

"scs0" <scs0(a)vol.com> wrote in message
news:5422b4d0-3336-4e7b-970f-5568d62f259f(a)t12g2000prg.googlegroups.com...
> Why is this functionality so difficult to do and find described
> online?
>
> If you know the exact steps - I mean the EXACT code - for deleting a
> folder (and yes that means it can have files and folders within it
> please let me know how it's done EXACTLY. My code isn't working
>
>
> If you're just going to do the usual newsgroup thing where you give me
> a riddle, a tip that leads nowhere, or a fragment of an answer please
> hit the back button now. I need an actual answer that actually works.
>
>
> BTW: Here's what I did and it fails:
>
> // Delete the contents of the driver's backup folder
> SHFILEOPSTRUCTW info;
> memset(&info, 0, sizeof(info));
> info.wFunc = FO_DELETE;
> info.fFlags = FOF_NOCONFIRMATION | FOF_SILENT;
>
> TCHAR szBuffer[2048];
> memset(szBuffer, 0, sizeof(szBuffer));
> _tcscpy(szBuffer, _T("\\\\?\\"));
> _tcscat(szBuffer, (LPCTSTR)strFolderToDelete);
>
> info.pFrom = szBuffer;
> if (0 != SHFileOperationW(&info))


From: Alf P. Steinbach on
* scs0:
> Why is this functionality so difficult to do and find described
> online?

Try MSDN Library.


> If you know the exact steps - I mean the EXACT code - for deleting a
> folder (and yes that means it can have files and folders within it
> please let me know how it's done EXACTLY. My code isn't working
>
> If you're just going to do the usual newsgroup thing where you give me
> a riddle, a tip that leads nowhere, or a fragment of an answer please
> hit the back button now. I need an actual answer that actually works.

In that case you should try to provide the actual code you have problems with.

We're not telepathic.



> BTW: Here's what I did and it fails:
>
> // Delete the contents of the driver's backup folder
> SHFILEOPSTRUCTW info;
> memset(&info, 0, sizeof(info));

Why use dangerous and inefficient memset when you can just do (assuming C++)

SHFILEOPSTRUCTW info = {};


> info.wFunc = FO_DELETE;
> info.fFlags = FOF_NOCONFIRMATION | FOF_SILENT;
>
> TCHAR szBuffer[2048];

Why on Earth are you using Hungarian prefixes?


> memset(szBuffer, 0, sizeof(szBuffer));

See earlier comment about memset.


> _tcscpy(szBuffer, _T("\\\\?\\"));

I'm not sure, but I think this prefix works only for Unicode. You're using
silly "_T" functionality which indicates you believe it works also for ANSI strings?


> _tcscat(szBuffer, (LPCTSTR)strFolderToDelete);

This is very dangerous: you can easily exceed the buffer size.

Anyway, have you checked that te resulting string makes sense as a path?


>
> info.pFrom = szBuffer;
> if (0 != SHFileOperationW(&info))

And... What's the actual code? So far you've only set up some buffers.

Assuming this is all the code you're using to delete folder, that's the reason
it's not deleted. You need to isse some function call that deletes the folder.
For example, a call to SHFileOperation().


Cheers, & hth.,

- Alf


--
A: Because it messes up the order in which people normally read text.
Q: Why is it such a bad thing?
A: Top-posting.
Q: What is the most annoying thing on usenet and in e-mail?
From: Giovanni Dicanio on

"Alf P. Steinbach" <alfps(a)start.no> ha scritto nel messaggio
news:VLmdnXgo7NqZk7_VnZ2dnUVZ_uednZ2d(a)comnet...

>> info.wFunc = FO_DELETE;
>> info.fFlags = FOF_NOCONFIRMATION | FOF_SILENT;
>>
>> TCHAR szBuffer[2048];
>
> Why on Earth are you using Hungarian prefixes?

Windows Platform SDK is full of Hungarian prefixes, and several programmers
(including Microsoft quality programmers, I believe) like that notation:
they think that code is more readable and easier to mantain, and they are
not wrong, IMHO.
I think that if the OP (or a programmer, in general) likes Hungarian
prefixes there is no problem: what is important IMHO is coherence (e.g.
avoid to do things like that: 'int szName' or 'float pRadius' ... in that
case the prefixes are clearly wrong and the code is confused.)

Frankly speaking, I like using 'm_' prefix for member variables, or 'g_' for
globals (used rarely), or 'p' for pointers (useful for example in cases when
there are double indirection pointers, like 'void ** ppv...'; so if I write
or read

*ppv ...

in code, I know that I'm handling a simple pointer 'void *', not the
original double pointer 'void**' - it's kind of '*' and 'p' cancel each
other.)

There are also other programmers, I think especially .NET ones, who do not
use prefixes at all.

I do respect both attitudes.

As Tom wrote about top-post and bottom-post techniques: "long life to both"
:)


>> _tcscpy(szBuffer, _T("\\\\?\\"));
>
> I'm not sure, but I think this prefix works only for Unicode. You're
> using silly "_T" functionality which indicates you believe it works also
> for ANSI strings?

I think that the OP is correct about considering _tcscpy Unicode aware.
It will expand to wcscpy in Unicode builds, and to strcpy in ANSI builds.

http://msdn.microsoft.com/en-us/library/kk6xf663(VS.80).aspx

The problem is IMHO the fact that raw TCHAR buffers are a bad solution
today. I do prefer robust string classes, like CString.


>> _tcscat(szBuffer, (LPCTSTR)strFolderToDelete);
>
> This is very dangerous: you can easily exceed the buffer size.

I agree with you.

I think that the OP should use _tcscat_s (the _s = safe version),

http://msdn.microsoft.com/en-us/library/d45bbxx4(VS.80).aspx

or StringCbCat function... or better CString class.


My 2 cents.
Giovanni


From: Alf P. Steinbach on
* Alf P. Steinbach:
>> if (0 != SHFileOperationW(&info))
>
> And... What's the actual code? So far you've only set up some buffers.

Oh I didn't see that: you've hidden the function call in an expression inside an
if, and use "W" at the end.

Well, that "W" won't work with your "_T" stuff if you compile for ANSI. Decide
on one or the other. Best is to avoid "_T".

Code that works (as per request):

<code>
#include <string>
#include <cassert>

#define STRICT
#define NOMINMAX
#define UNICODE
#define _UNICODE
#include <windows.h>

bool deleteDirectory( std::wstring const path )
{
std::wstring const paths = path + L'\0' + L'\0';
assert( paths.length() == path.length() + 2 );

SHFILEOPSTRUCT params = {};
params.wFunc = FO_DELETE;
params.fFlags = FOF_NOCONFIRMATION | FOF_SILENT;
params.pFrom = path.data();
return !SHFileOperation( &params );
}

int main()
{
deleteDirectory( L"v:\\test\\bah" );
}
</code>


Cheers, & hth.,

- Alf


--
A: Because it messes up the order in which people normally read text.
Q: Why is it such a bad thing?
A: Top-posting.
Q: What is the most annoying thing on usenet and in e-mail?