mirror of
https://github.com/reactos/reactos.git
synced 2025-02-20 15:35:04 +00:00
Simplify and fix code by using GetFullPathName and GetVolumePathName instead of re-inventing the wheel once again.
See issue #2041 for more details. svn path=/trunk/; revision=28074
This commit is contained in:
parent
e42a8d41ff
commit
1f6dec06f4
1 changed files with 69 additions and 251 deletions
|
@ -621,189 +621,6 @@ DirReadParam(LPTSTR Line, /* [IN] The line with the parameters & switches */
|
|||
}
|
||||
|
||||
|
||||
/*
|
||||
* ExtendFilespec
|
||||
*
|
||||
* extend the filespec, possibly adding wildcards
|
||||
*/
|
||||
static VOID
|
||||
ExtendFilespec (LPTSTR file)
|
||||
{
|
||||
INT len = 0;
|
||||
|
||||
if (!file)
|
||||
return;
|
||||
|
||||
|
||||
/* if no file spec, change to "*.*" */
|
||||
if (*file == _T('\0'))
|
||||
{
|
||||
_tcscpy (file, _T("*.*"));
|
||||
return;
|
||||
}
|
||||
|
||||
// add support for *.
|
||||
if ((file[0] == _T('*')) && (file[1] == _T('.') ))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
/* if starts with . add * in front */
|
||||
if (*file == _T('.'))
|
||||
{
|
||||
memmove (&file[1], &file[0], (_tcslen (file) + 1) * sizeof(TCHAR));
|
||||
file[0] = _T('*');
|
||||
}
|
||||
|
||||
/* if no . add .* */
|
||||
if (!_tcschr (file, _T('.')))
|
||||
{
|
||||
_tcscat (file, _T(".*"));
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* if last character is '.' add '*' */
|
||||
len = _tcslen (file);
|
||||
if (file[len - 1] == _T('.'))
|
||||
{
|
||||
_tcscat (file, _T("*"));
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* dir_parse_pathspec
|
||||
*
|
||||
* split the pathspec into drive, directory, and filespec
|
||||
*/
|
||||
static INT
|
||||
DirParsePathspec (LPTSTR szPathspec, LPTSTR szPath, LPTSTR szFilespec)
|
||||
{
|
||||
TCHAR szOrigPath[MAX_PATH];
|
||||
LPTSTR start;
|
||||
LPTSTR tmp;
|
||||
INT i;
|
||||
BOOL bWildcards = FALSE;
|
||||
|
||||
GetCurrentDirectory (MAX_PATH, szOrigPath);
|
||||
|
||||
/* get the drive and change to it */
|
||||
if (szPathspec[1] == _T(':'))
|
||||
{
|
||||
TCHAR szRootPath[] = _T("A:");
|
||||
|
||||
szRootPath[0] = szPathspec[0];
|
||||
start = szPathspec + 2;
|
||||
if (!SetCurrentDirectory (szRootPath))
|
||||
{
|
||||
ErrorMessage (GetLastError(), NULL);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
start = szPathspec;
|
||||
}
|
||||
|
||||
|
||||
/* check for wildcards */
|
||||
for (i = 0; szPathspec[i]; i++)
|
||||
{
|
||||
if (szPathspec[i] == _T('*') || szPathspec[i] == _T('?'))
|
||||
bWildcards = TRUE;
|
||||
}
|
||||
|
||||
/* check if this spec is a directory */
|
||||
if (!bWildcards)
|
||||
{
|
||||
if (SetCurrentDirectory (szPathspec))
|
||||
{
|
||||
_tcscpy (szFilespec, _T("*.*"));
|
||||
|
||||
if (!GetCurrentDirectory (MAX_PATH, szPath))
|
||||
{
|
||||
szFilespec[0] = _T('\0');
|
||||
SetCurrentDirectory (szOrigPath);
|
||||
error_out_of_memory();
|
||||
return 1;
|
||||
}
|
||||
|
||||
SetCurrentDirectory (szOrigPath);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
/* find the file spec */
|
||||
tmp = _tcsrchr (start, _T('\\'));
|
||||
|
||||
/* if no path is specified */
|
||||
if (!tmp)
|
||||
{
|
||||
_tcscpy (szFilespec, start);
|
||||
ExtendFilespec (szFilespec);
|
||||
if (!GetCurrentDirectory (MAX_PATH, szPath))
|
||||
{
|
||||
szFilespec[0] = _T('\0');
|
||||
SetCurrentDirectory (szOrigPath);
|
||||
error_out_of_memory();
|
||||
return 1;
|
||||
}
|
||||
|
||||
SetCurrentDirectory (szOrigPath);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* get the filename */
|
||||
_tcscpy (szFilespec, tmp+1);
|
||||
ExtendFilespec (szFilespec);
|
||||
|
||||
if (tmp == start)
|
||||
{
|
||||
/* change to the root directory */
|
||||
if (!SetCurrentDirectory (_T("\\")))
|
||||
{
|
||||
szFilespec[0] = _T('\0');
|
||||
SetCurrentDirectory (szOrigPath);
|
||||
error_path_not_found ();
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
*tmp = _T('\0');
|
||||
|
||||
/* change to this directory */
|
||||
if (!SetCurrentDirectory (start))
|
||||
{
|
||||
*tmp = _T('\\');
|
||||
szFilespec[0] = _T('\0');
|
||||
SetCurrentDirectory (szOrigPath);
|
||||
error_path_not_found ();
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
/* get the full name of the directory */
|
||||
if (!GetCurrentDirectory (MAX_PATH, szPath))
|
||||
{
|
||||
*tmp = _T('\\');
|
||||
szFilespec[0] = _T('\0');
|
||||
SetCurrentDirectory (szOrigPath);
|
||||
error_out_of_memory ();
|
||||
return 1;
|
||||
}
|
||||
|
||||
*tmp = _T('\\');
|
||||
|
||||
SetCurrentDirectory (szOrigPath);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* PrintDirectoryHeader
|
||||
*
|
||||
|
@ -813,58 +630,30 @@ static BOOL
|
|||
PrintDirectoryHeader(LPTSTR szPath, LPDIRSWITCHFLAGS lpFlags)
|
||||
{
|
||||
TCHAR szMsg[RC_STRING_MAX_SIZE];
|
||||
TCHAR szFullDir[MAX_PATH];
|
||||
TCHAR szRootName[MAX_PATH];
|
||||
TCHAR szVolName[80];
|
||||
LPTSTR pszFilePart;
|
||||
DWORD dwSerialNr;
|
||||
LPTSTR p;
|
||||
|
||||
if (lpFlags->bBareFormat)
|
||||
return TRUE;
|
||||
|
||||
/* build usable root path */
|
||||
if (szPath[1] == _T(':') && szPath[2] == _T('\\'))
|
||||
if (GetFullPathName(szPath, sizeof(szFullDir) / sizeof(TCHAR), szFullDir, &pszFilePart) == 0)
|
||||
{
|
||||
/* normal path */
|
||||
szRootName[0] = szPath[0];
|
||||
szRootName[1] = _T(':');
|
||||
szRootName[2] = _T('\\');
|
||||
szRootName[3] = 0;
|
||||
}
|
||||
else if (szPath[0] == _T('\\') && szPath[1] == _T('\\'))
|
||||
{
|
||||
/* UNC path */
|
||||
p = _tcschr(&szPath[2], _T('\\'));
|
||||
if (p == NULL)
|
||||
{
|
||||
error_invalid_drive();
|
||||
return(FALSE);
|
||||
}
|
||||
p = _tcschr(p+1, _T('\\'));
|
||||
if (p == NULL)
|
||||
{
|
||||
_tcscpy(szRootName, szPath);
|
||||
_tcscat(szRootName, _T("\\"));
|
||||
}
|
||||
else
|
||||
{
|
||||
*p = 0;
|
||||
_tcscpy(szRootName, szPath);
|
||||
_tcscat(szRootName, _T("\\"));
|
||||
*p = _T('\\');
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
error_invalid_drive();
|
||||
return(FALSE);
|
||||
ErrorMessage(GetLastError(), _T("Failed to build full directory path"));
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (pszFilePart != NULL)
|
||||
*pszFilePart = _T('\0');
|
||||
|
||||
/* get the media ID of the drive */
|
||||
if (!GetVolumeInformation(szRootName, szVolName, 80, &dwSerialNr,
|
||||
if (!GetVolumePathName(szFullDir, szRootName, sizeof(szRootName) / sizeof(TCHAR)) ||
|
||||
!GetVolumeInformation(szRootName, szVolName, 80, &dwSerialNr,
|
||||
NULL, NULL, NULL, 0))
|
||||
{
|
||||
error_invalid_drive();
|
||||
return(FALSE);
|
||||
return(TRUE);
|
||||
}
|
||||
|
||||
/* print drive info */
|
||||
|
@ -1522,12 +1311,18 @@ DirPrintFiles(LPWIN32_FIND_DATA ptrFiles[], /* [IN] Files' Info */
|
|||
{
|
||||
TCHAR szMsg[RC_STRING_MAX_SIZE];
|
||||
TCHAR szTemp[MAX_PATH]; /* A buffer to format the directory header */
|
||||
LPTSTR pszFilePart;
|
||||
SIZE_T len;
|
||||
|
||||
/* Print directory header */
|
||||
_tcscpy(szTemp, szCurPath);
|
||||
|
||||
/* We cut the trailing \ of the full path, unless the path is a drive */
|
||||
if (GetFullPathName(szCurPath, sizeof(szTemp) / sizeof(TCHAR), szTemp, &pszFilePart) == 0)
|
||||
{
|
||||
pszFilePart = NULL;
|
||||
_tcscpy(szTemp, szCurPath);
|
||||
}
|
||||
else if (pszFilePart != NULL)
|
||||
*pszFilePart = _T('\0');
|
||||
|
||||
len = _tcslen(szTemp);
|
||||
if ((len != 3 || szTemp[len - 2] != _T(':')) && szTemp[len - 1] == _T('\\'))
|
||||
szTemp[len-1] = _T('\0');
|
||||
|
@ -1736,7 +1531,6 @@ QsortFiles(LPWIN32_FIND_DATA ptrArray[], /* [IN/OUT] The array with file info po
|
|||
*/
|
||||
static INT
|
||||
DirList(LPTSTR szPath, /* [IN] The path that dir starts */
|
||||
LPTSTR szFilespec, /* [IN] The type of file that we are looking for */
|
||||
LPDIRSWITCHFLAGS lpFlags) /* [IN] The flags of the listing */
|
||||
{
|
||||
HANDLE hSearch; /* The handle of the search */
|
||||
|
@ -1746,7 +1540,8 @@ DirList(LPTSTR szPath, /* [IN] The path that dir starts */
|
|||
PDIRFINDLISTNODE ptrStartNode; /* The pointer to the first node */
|
||||
PDIRFINDLISTNODE ptrNextNode; /* A pointer used for relatives refernces */
|
||||
TCHAR szFullPath[MAX_PATH]; /* The full path that we are listing with trailing \ */
|
||||
TCHAR szFullFileSpec[MAX_PATH]; /* The full path with file specs that we ll request\ */
|
||||
TCHAR szSubPath[MAX_PATH];
|
||||
LPTSTR pszFilePart;
|
||||
DWORD dwCount; /* A counter of files found in directory */
|
||||
DWORD dwCountFiles; /* Counter for files */
|
||||
DWORD dwCountDirs; /* Counter for directories */
|
||||
|
@ -1761,12 +1556,14 @@ ULARGE_INTEGER u64Temp; /* A temporary counter */
|
|||
dwCountDirs = 0;
|
||||
u64CountBytes.QuadPart = 0;
|
||||
|
||||
/* Create szFullPath and szFullFileSpec */
|
||||
_tcscpy (szFullPath, szPath);
|
||||
if (szFullPath[_tcslen(szFullPath) - 1] != _T('\\'))
|
||||
_tcscat (szFullPath, _T("\\"));
|
||||
_tcscpy (szFullFileSpec, szFullPath);
|
||||
_tcscat (szFullFileSpec, szFilespec);
|
||||
/* Create szFullPath */
|
||||
if (GetFullPathName(szPath, sizeof(szFullPath) / sizeof(TCHAR), szFullPath, &pszFilePart) == 0)
|
||||
{
|
||||
_tcscpy (szFullPath, szPath);
|
||||
if (szFullPath[_tcslen(szFullPath) - 1] != _T('\\'))
|
||||
_tcscat (szFullPath, _T("\\"));
|
||||
pszFilePart = NULL;
|
||||
}
|
||||
|
||||
/* Prepare the linked list, first node is allocated */
|
||||
ptrStartNode = cmd_alloc(sizeof(DIRFINDLISTNODE));
|
||||
|
@ -1780,7 +1577,7 @@ ULARGE_INTEGER u64Temp; /* A temporary counter */
|
|||
ptrNextNode = ptrStartNode;
|
||||
|
||||
/* Collect the results for the current folder */
|
||||
hSearch = FindFirstFile(szFullFileSpec, &wfdFileInfo);
|
||||
hSearch = FindFirstFile(szFullPath, &wfdFileInfo);
|
||||
do
|
||||
{
|
||||
if (hSearch != INVALID_HANDLE_VALUE)
|
||||
|
@ -1902,9 +1699,17 @@ ULARGE_INTEGER u64Temp; /* A temporary counter */
|
|||
if (lpFlags->bRecursive)
|
||||
{
|
||||
/* The new search is involving any *.* file */
|
||||
_tcscpy(szFullFileSpec, szFullPath);
|
||||
_tcscat(szFullFileSpec, _T("*.*"));
|
||||
hRecSearch = FindFirstFile (szFullFileSpec, &wfdFileInfo);
|
||||
if (pszFilePart != NULL)
|
||||
{
|
||||
memcpy(szSubPath, szFullPath, (pszFilePart - szFullPath) * sizeof(TCHAR));
|
||||
szSubPath[pszFilePart - szFullPath] = _T('\0');
|
||||
}
|
||||
else
|
||||
_tcscpy(szSubPath, szFullPath);
|
||||
|
||||
_tcscat(szSubPath, _T("*.*"));
|
||||
|
||||
hRecSearch = FindFirstFile (szSubPath, &wfdFileInfo);
|
||||
do
|
||||
{
|
||||
if (hRecSearch != INVALID_HANDLE_VALUE)
|
||||
|
@ -1915,10 +1720,21 @@ ULARGE_INTEGER u64Temp; /* A temporary counter */
|
|||
(wfdFileInfo.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY))
|
||||
{
|
||||
/* Concat the path and the directory to do recursive */
|
||||
_tcscpy(szFullFileSpec, szFullPath);
|
||||
_tcscat(szFullFileSpec, wfdFileInfo.cFileName);
|
||||
/* We do the same for tha folder */
|
||||
if (DirList(szFullFileSpec, szFilespec, lpFlags) != 0)
|
||||
if (pszFilePart != NULL)
|
||||
{
|
||||
memcpy(szSubPath, szFullPath, (pszFilePart - szFullPath) * sizeof(TCHAR));
|
||||
szSubPath[pszFilePart - szFullPath] = _T('\0');
|
||||
}
|
||||
else
|
||||
_tcscpy(szSubPath, szFullPath);
|
||||
|
||||
_tcscat(szSubPath, wfdFileInfo.cFileName);
|
||||
_tcscat(szSubPath, _T("\\"));
|
||||
if (pszFilePart != NULL)
|
||||
_tcscat(szSubPath, pszFilePart);
|
||||
|
||||
/* We do the same for the folder */
|
||||
if (DirList(szSubPath, lpFlags) != 0)
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
@ -1953,7 +1769,6 @@ CommandDir(LPTSTR first, LPTSTR rest)
|
|||
TCHAR dircmd[256]; /* A variable to store the DIRCMD enviroment variable */
|
||||
TCHAR cDrive;
|
||||
TCHAR szPath[MAX_PATH];
|
||||
TCHAR szFilespec[MAX_PATH];
|
||||
LPTSTR* params = NULL;
|
||||
INT entries = 0;
|
||||
UINT loop = 0;
|
||||
|
@ -1987,7 +1802,7 @@ CommandDir(LPTSTR first, LPTSTR rest)
|
|||
stFlags.stOrderBy.bUnSet = FALSE;
|
||||
|
||||
nErrorLevel = 0;
|
||||
|
||||
|
||||
/* read the parameters from the DIRCMD environment variable */
|
||||
if (GetEnvironmentVariable (_T("DIRCMD"), dircmd, 256))
|
||||
if (!DirReadParam(dircmd, ¶ms, &entries, &stFlags))
|
||||
|
@ -2005,21 +1820,23 @@ CommandDir(LPTSTR first, LPTSTR rest)
|
|||
|
||||
/* default to current directory */
|
||||
if(entries == 0) {
|
||||
if(!add_entry(&entries, ¶ms, _T("."))) {
|
||||
if(!add_entry(&entries, ¶ms, _T("*"))) {
|
||||
nErrorLevel = 1;
|
||||
goto cleanup;
|
||||
}
|
||||
}
|
||||
szPath[0] = _T('\0');
|
||||
|
||||
for(loop = 0; loop < entries; loop++)
|
||||
{
|
||||
/* parse the directory info */
|
||||
if (DirParsePathspec (params[loop], szPath, szFilespec) || CheckCtrlBreak(BREAK_INPUT))
|
||||
if (CheckCtrlBreak(BREAK_INPUT))
|
||||
{
|
||||
nErrorLevel = 1;
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
_tcscpy(szPath, params[loop]);
|
||||
|
||||
/* <Debug :>
|
||||
Uncomment this to show the final state of switch flags*/
|
||||
#ifdef _DEBUG
|
||||
|
@ -2045,26 +1862,27 @@ CommandDir(LPTSTR first, LPTSTR rest)
|
|||
#endif
|
||||
|
||||
/* Print the drive header if the drive changed */
|
||||
if(cDrive != szPath[0] && !stFlags.bBareFormat) {
|
||||
if (!PrintDirectoryHeader (szPath, &stFlags)) {
|
||||
if(cDrive != params[loop][0] && !stFlags.bBareFormat) {
|
||||
if (!PrintDirectoryHeader (params[loop], &stFlags)) {
|
||||
nErrorLevel = 1;
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
cDrive = szPath[0];
|
||||
cDrive = params[loop][0];
|
||||
}
|
||||
|
||||
|
||||
/* do the actual dir */
|
||||
if (DirList (szPath, szFilespec, &stFlags))
|
||||
if (DirList (params[loop], &stFlags))
|
||||
{
|
||||
nErrorLevel = 1;
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/* print the footer */
|
||||
PrintSummary(szPath,
|
||||
PrintSummary(szPath, // FIXME: root of initial dir?
|
||||
recurse_file_cnt,
|
||||
recurse_dir_cnt,
|
||||
recurse_bytes,
|
||||
|
|
Loading…
Reference in a new issue