xcopy: Make displayed names mirror windows.

This commit is contained in:
Jason Edmeades 2007-03-31 21:24:17 +01:00 committed by Alexandre Julliard
parent a8914b9494
commit da977e5579
1 changed files with 79 additions and 50 deletions

View File

@ -48,7 +48,8 @@
WINE_DEFAULT_DEBUG_CHANNEL(xcopy); WINE_DEFAULT_DEBUG_CHANNEL(xcopy);
/* Prototypes */ /* Prototypes */
static int XCOPY_ProcessSourceParm(WCHAR *suppliedsource, WCHAR *stem, WCHAR *spec); static int XCOPY_ProcessSourceParm(WCHAR *suppliedsource, WCHAR *stem,
WCHAR *spec, DWORD flags);
static int XCOPY_ProcessDestParm(WCHAR *supplieddestination, WCHAR *stem, static int XCOPY_ProcessDestParm(WCHAR *supplieddestination, WCHAR *stem,
WCHAR *spec, WCHAR *srcspec, DWORD flags); WCHAR *spec, WCHAR *srcspec, DWORD flags);
static int XCOPY_DoCopy(WCHAR *srcstem, WCHAR *srcspec, static int XCOPY_DoCopy(WCHAR *srcstem, WCHAR *srcspec,
@ -255,7 +256,7 @@ int main (int argc, char *argv[])
WINE_TRACE("Destination : '%s'\n", wine_dbgstr_w(supplieddestination)); WINE_TRACE("Destination : '%s'\n", wine_dbgstr_w(supplieddestination));
/* Extract required information from source specification */ /* Extract required information from source specification */
rc = XCOPY_ProcessSourceParm(suppliedsource, sourcestem, sourcespec); rc = XCOPY_ProcessSourceParm(suppliedsource, sourcestem, sourcespec, flags);
/* Extract required information from destination specification */ /* Extract required information from destination specification */
rc = XCOPY_ProcessDestParm(supplieddestination, destinationstem, rc = XCOPY_ProcessDestParm(supplieddestination, destinationstem,
@ -307,11 +308,13 @@ int main (int argc, char *argv[])
XCOPY_ProcessSourceParm - Takes the supplied source parameter, and XCOPY_ProcessSourceParm - Takes the supplied source parameter, and
converts it into a stem and a filespec converts it into a stem and a filespec
========================================================================= */ ========================================================================= */
static int XCOPY_ProcessSourceParm(WCHAR *suppliedsource, WCHAR *stem, WCHAR *spec) static int XCOPY_ProcessSourceParm(WCHAR *suppliedsource, WCHAR *stem,
WCHAR *spec, DWORD flags)
{ {
WCHAR actualsource[MAX_PATH]; WCHAR actualsource[MAX_PATH];
WCHAR *starPos; WCHAR *starPos;
WCHAR *questPos; WCHAR *questPos;
DWORD attribs;
/* /*
* Validate the source, expanding to full path ensuring it exists * Validate the source, expanding to full path ensuring it exists
@ -321,56 +324,79 @@ static int XCOPY_ProcessSourceParm(WCHAR *suppliedsource, WCHAR *stem, WCHAR *sp
return RC_INITERROR; return RC_INITERROR;
} }
/* If full names required, convert to using the full path */
if (flags & OPT_FULL) {
lstrcpyW(suppliedsource, actualsource);
}
/* /*
* Work out the stem of the source * Work out the stem of the source
*/ */
/* If no wildcard were supplied then the source is either a single /* If a directory is supplied, use that as-is (either fully or
file or a directory - in which case thats the stem of the search, partially qualified)
otherwise split off the wildcards and use the higher level as the If a filename is supplied + a directory or drive path, use that
stem */ as-is
lstrcpyW(stem, actualsource); Otherwise
starPos = wcschr(stem, '*'); If no directory or path specified, add eg. C:
questPos = wcschr(stem, '?'); stem is Drive/Directory is bit up to last \ (or first :)
spec is bit after that */
starPos = wcschr(suppliedsource, '*');
questPos = wcschr(suppliedsource, '?');
if (starPos || questPos) { if (starPos || questPos) {
attribs = 0x00; /* Ensures skips invalid or directory check below */
} else {
attribs = GetFileAttributes(actualsource);
}
if (attribs == INVALID_FILE_ATTRIBUTES) {
XCOPY_FailMessage(GetLastError());
return RC_INITERROR;
/* Directory:
stem should be exactly as supplied plus a '\', unless it was
eg. C: in which case no slash required */
} else if (attribs & FILE_ATTRIBUTE_DIRECTORY) {
WCHAR lastChar;
WINE_TRACE("Directory supplied\n");
lstrcpyW(stem, suppliedsource);
lastChar = stem[lstrlenW(stem)-1];
if (lastChar != '\\' && lastChar != ':') {
lstrcatW(stem, wchr_slash);
}
lstrcpyW(spec, wchr_star);
/* File or wildcard search:
stem should be:
Up to and including last slash if directory path supplied
If c:filename supplied, just the c:
Otherwise stem should be the current drive letter + ':' */
} else {
WCHAR *lastDir; WCHAR *lastDir;
if (starPos) *starPos = 0x00; WINE_TRACE("Filename supplied\n");
if (questPos) *questPos = 0x00; lastDir = wcsrchr(suppliedsource, '\\');
lastDir = wcsrchr(stem, '\\'); if (lastDir) {
if (lastDir) *(lastDir+1) = 0x00; lstrcpyW(stem, suppliedsource);
else { stem[(lastDir-suppliedsource) + 1] = 0x00;
WINE_FIXME("Unexpected syntax error in source parameter\n"); lstrcpyW(spec, (lastDir+1));
return RC_INITERROR; } else if (suppliedsource[1] == ':') {
} lstrcpyW(stem, suppliedsource);
lstrcpyW(spec, actualsource + (lastDir - stem)+1); stem[2] = 0x00;
} else { lstrcpyW(spec, suppliedsource+2);
DWORD attribs = GetFileAttributes(actualsource);
if (attribs == INVALID_FILE_ATTRIBUTES) {
XCOPY_FailMessage(GetLastError());
return RC_INITERROR;
/* Directory: */
} else if (attribs & FILE_ATTRIBUTE_DIRECTORY) {
lstrcatW(stem, wchr_slash);
lstrcpyW(spec, wchr_star);
/* File: */
} else { } else {
WCHAR drive[MAX_PATH]; WCHAR curdir[MAXSTRING];
WCHAR dir[MAX_PATH]; GetCurrentDirectory (sizeof(curdir), curdir);
WCHAR fname[MAX_PATH]; stem[0] = curdir[0];
WCHAR ext[MAX_PATH]; stem[1] = curdir[1];
_wsplitpath(actualsource, drive, dir, fname, ext); stem[2] = 0x00;
lstrcpyW(stem, drive); lstrcpyW(spec, suppliedsource);
lstrcatW(stem, dir);
lstrcpyW(spec, fname);
lstrcatW(spec, ext);
} }
} }
return RC_OK; return RC_OK;
} }
@ -868,14 +894,17 @@ static BOOL XCOPY_ProcessExcludeFile(WCHAR* filename, WCHAR* endOfName) {
/* Strip CRLF */ /* Strip CRLF */
buffer[length-1] = 0x00; buffer[length-1] = 0x00;
thisEntry = HeapAlloc(GetProcessHeap(), 0, sizeof(EXCLUDELIST)); /* If more than CRLF */
thisEntry->next = excludeList; if (length > 1) {
excludeList = thisEntry; thisEntry = HeapAlloc(GetProcessHeap(), 0, sizeof(EXCLUDELIST));
thisEntry->name = HeapAlloc(GetProcessHeap(), 0, thisEntry->next = excludeList;
(length * sizeof(WCHAR))+1); excludeList = thisEntry;
lstrcpyW(thisEntry->name, buffer); thisEntry->name = HeapAlloc(GetProcessHeap(), 0,
CharUpperBuff(thisEntry->name, length); (length * sizeof(WCHAR))+1);
WINE_TRACE("Read line : '%s'\n", wine_dbgstr_w(thisEntry->name)); lstrcpyW(thisEntry->name, buffer);
CharUpperBuff(thisEntry->name, length);
WINE_TRACE("Read line : '%s'\n", wine_dbgstr_w(thisEntry->name));
}
} }
/* See if EOF or error occurred */ /* See if EOF or error occurred */