summaryrefslogtreecommitdiffstats
path: root/private/oleutest/cfmex/cdir.cxx
diff options
context:
space:
mode:
authorAdam <you@example.com>2020-05-17 05:51:50 +0200
committerAdam <you@example.com>2020-05-17 05:51:50 +0200
commite611b132f9b8abe35b362e5870b74bce94a1e58e (patch)
treea5781d2ec0e085eeca33cf350cf878f2efea6fe5 /private/oleutest/cfmex/cdir.cxx
downloadNT4.0-e611b132f9b8abe35b362e5870b74bce94a1e58e.tar
NT4.0-e611b132f9b8abe35b362e5870b74bce94a1e58e.tar.gz
NT4.0-e611b132f9b8abe35b362e5870b74bce94a1e58e.tar.bz2
NT4.0-e611b132f9b8abe35b362e5870b74bce94a1e58e.tar.lz
NT4.0-e611b132f9b8abe35b362e5870b74bce94a1e58e.tar.xz
NT4.0-e611b132f9b8abe35b362e5870b74bce94a1e58e.tar.zst
NT4.0-e611b132f9b8abe35b362e5870b74bce94a1e58e.zip
Diffstat (limited to 'private/oleutest/cfmex/cdir.cxx')
-rw-r--r--private/oleutest/cfmex/cdir.cxx418
1 files changed, 418 insertions, 0 deletions
diff --git a/private/oleutest/cfmex/cdir.cxx b/private/oleutest/cfmex/cdir.cxx
new file mode 100644
index 000000000..250404676
--- /dev/null
+++ b/private/oleutest/cfmex/cdir.cxx
@@ -0,0 +1,418 @@
+
+//+==========================================================================
+//
+// File: CDir.cxx
+//
+// Purpose: Define the CDirectory class.
+//
+// This class is used to represent a directory name.
+// Along with maintaining the name, it can determine
+// the type of FileSystem.
+//
+//+==========================================================================
+
+
+// --------
+// Includes
+// --------
+
+#include <windows.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <wchar.h>
+#include <wtypes.h>
+
+#include "CFMEx.hxx"
+#include "CDir.hxx"
+
+
+//+------------------------------------------------------------------------------
+//
+// Function: CDirectory::Initialize (no arguments)
+//
+// Synopsis: Generate a directory name, using the TEMP environment
+// variable, and use it to initialize this object.
+//
+// Inputs: None.
+//
+// Outputs: TRUE if the function succeeds, FALSE otherwise.
+//
+//+------------------------------------------------------------------------------
+
+BOOL CDirectory::Initialize()
+{
+ // ---------------
+ // Local Variables
+ // ---------------
+
+ // Assume failure for now.
+ BOOL bSuccess = FALSE;
+
+ // The TEMP environment variable.
+ WCHAR wszSystemTempPath[ MAX_PATH + sizeof( L'\0' )];
+
+ // Reset the error code.
+ m_lError = 0L;
+
+ // ----------
+ // Get %TEMP%
+ // ----------
+
+ if( !GetTempPath( MAX_PATH,
+ wszSystemTempPath )
+ )
+ {
+ m_lError = GetLastError();
+ EXIT( L"GetTempPath() failed (%d)" );
+ }
+
+ // ----------------------
+ // Initialize this object
+ // ----------------------
+
+ // Initialize using the temporary path. We must never pass a NULL here,
+ // or we'll cause an infinite recursion.
+
+ if( wszSystemTempPath == NULL )
+ EXIT( L"Invalid temporary path" );
+ bSuccess = Initialize( wszSystemTempPath );
+
+ // ----
+ // Exit
+ // ----
+
+Exit:
+
+ return( bSuccess );
+
+}
+
+//+-----------------------------------------------------------------------
+//
+// Function: CDirectory::Initialize (with an ANSI string)
+//
+// Synopsis: This function converts the ANSI string to a Unicode
+// string, then initializes the object with it.
+//
+// Inputs: A Unicode string.
+//
+// Outputs: TRUE if the function succeeds, FALSE otherwise.
+//
+//+-----------------------------------------------------------------------
+
+BOOL CDirectory::Initialize( LPCSTR szDirectory )
+{
+ // ---------------
+ // Local Variables
+ // ---------------
+
+ // Assume failure.
+ BOOL bSuccess = FALSE;
+
+ // A buffer for the Unicode path
+ WCHAR wszDirectory[ MAX_UNICODE_PATH + sizeof( L'\0' )];
+
+ // -----
+ // Begin
+ // -----
+
+ // Initialize the error code.
+ m_lError = 0L;
+
+
+ // If we were givin a NULL path, use the version of Initialize
+ // that requires no path.
+
+ if( szDirectory == NULL )
+ {
+ bSuccess = Initialize();
+ goto Exit;
+ }
+
+ // Convert the Ansi name to Unicode.
+
+ if( m_lError = (long) AnsiToUnicode( szDirectory,
+ wszDirectory,
+ strlen( szDirectory )
+ )
+ )
+ {
+ EXIT( L"Unable to convert directory to Unicode" );
+ }
+
+ // Initialize using the temporary path. We must never pass a NULL here,
+ // or we'll cause an infinite recursion.
+
+ if( wszDirectory == NULL )
+ EXIT( L"Invalid Directory (internal error)" );
+ bSuccess = Initialize( wszDirectory );
+
+ // ----
+ // Exit
+ // ----
+
+Exit:
+
+ return( bSuccess );
+
+}
+
+
+//+-----------------------------------------------------------------------
+//
+// Function: CDirectory::Initialize (with a Unicode string)
+//
+// Synopsis: This function is the only form of Initialize
+// (there are several variations of the Initialize member)
+// which really initializes the object. It stores the
+// directory name, and determines the type of filesystem
+// on which it resides.
+//
+// Inputs: A Unicode string.
+//
+// Outputs: TRUE if the function succeeds, FALSE otherwise.
+//
+//+-----------------------------------------------------------------------
+
+BOOL CDirectory::Initialize( LPCWSTR wszDirectory )
+{
+
+ // ---------------
+ // Local Variables
+ // ---------------
+
+ // Assume failure.
+ BOOL bSuccess = FALSE;
+
+ // Buffers for the root of the path and for the volume name.
+ WCHAR wszDirectoryRoot[ MAX_PATH + sizeof( L'\0' )];
+ WCHAR wszVolumeName[ MAX_PATH + sizeof( L'\0' )];
+
+ // Parameters to GetVolumeInformation which we won't use.
+ DWORD dwMaxComponentLength = 0L;
+ DWORD dwFileSystemFlags = 0L;
+
+ // -----
+ // Begin
+ // -----
+
+ // Initialize the error code.
+ m_lError = 0L;
+
+ // If we were given a NULL path, use the variation of Initialization()
+ // which does not require one. Note that we will then be called again,
+ // but this time with a path.
+
+ if( wszDirectory == NULL )
+ {
+ bSuccess = Initialize();
+ goto Exit;
+ }
+
+ // Validate the path.
+
+ if( wcslen( wszDirectory ) > MAX_PATH )
+ {
+ m_lError = wcslen( wszDirectory );
+ EXIT( L"Input path is too long (%d)\n" );
+ }
+
+ // Save the path to our member buffer
+
+ wcscpy( m_wszDirectory, wszDirectory );
+
+
+ // ------------------------
+ // Get the file system name
+ // ------------------------
+
+ // Get the root path to the directory.
+
+ wcscpy( wszDirectoryRoot, wszDirectory );
+ MakeRoot( wszDirectoryRoot );
+
+ // Get the volume information, which will include the filesystem name.
+
+ if( !GetVolumeInformation( wszDirectoryRoot, // Root path name.
+ wszVolumeName, // Buffer for volume name
+ MAX_PATH, // Length of the above buffer
+ NULL, // Buffer for serial number
+ // Longest filename length.
+ &dwMaxComponentLength,
+ &dwFileSystemFlags, // Compression, etc.
+ m_wszFileSystemName,// Buffer for the FS name.
+ MAX_PATH ) // Length of above buffer
+ )
+ {
+ m_lError = GetLastError();
+ EXIT( L"GetVolumeInformation() failed" );
+ }
+
+
+ // Determine the file system type from the name.
+
+ if( !wcscmp( m_wszFileSystemName, L"FAT" ))
+ m_FileSystemType = fstFAT;
+
+ else if( !wcscmp( m_wszFileSystemName, L"NTFS" ))
+ m_FileSystemType = fstNTFS;
+
+ else if( !wcscmp( m_wszFileSystemName, L"OFS" ))
+ m_FileSystemType = fstOFS;
+
+ else
+ m_FileSystemType = fstUnknown;
+
+ bSuccess = TRUE;
+
+ // ----
+ // Exit
+ // ----
+
+Exit:
+
+ DisplayErrors( bSuccess, L"CDirectory::Initialize( wszDirectory )" );
+ return( bSuccess );
+
+}
+
+
+
+//
+// GetRootLength
+//
+// This routine was simply copied from private\windows\shell\shelldll\tracker.cxx,
+// and should not be modified here.
+//
+
+unsigned
+CDirectory::GetRootLength(const WCHAR *pwszPath)
+{
+ ULONG cwcRoot = 0;
+ m_lError = 0L;
+
+ if (pwszPath == 0)
+ pwszPath = L"";
+
+ if (*pwszPath == L'\\')
+ {
+ // If the first character is a path separator (backslash), this
+ // must be a UNC drive designator which must be of the form:
+ // <path-separator><path-separator>(<alnum>+)
+ // <path-separator>(<alnum>+)<path-separator>
+ //
+ // This covers drives like these: \\worf\scratch\ and
+ // \\savik\win4dev\.
+ //
+ pwszPath++;
+ cwcRoot++;
+
+ BOOL fMachine = FALSE;
+ BOOL fShare = FALSE;
+
+ if (*pwszPath == L'\\')
+ {
+ cwcRoot++;
+ pwszPath++;
+
+ while (*pwszPath != '\0' && *pwszPath != L'\\')
+ {
+ cwcRoot++;
+ pwszPath++;
+
+ fMachine = TRUE;
+ }
+
+ if (*pwszPath == L'\\')
+ {
+ cwcRoot++;
+ pwszPath++;
+
+ while (*pwszPath != '\0' && *pwszPath != L'\\')
+ {
+ cwcRoot++;
+ pwszPath++;
+
+ fShare = TRUE;
+ }
+
+ // If there weren't any characters in the machine or
+ // share portions of the UNC name, then the drive
+ // designator is bogus.
+ //
+ if (!fMachine || !fShare)
+ {
+ cwcRoot = 0;
+ }
+ }
+ else
+ {
+ cwcRoot = 0;
+ }
+ }
+ else
+ {
+ cwcRoot = 0;
+ }
+ }
+ else
+ if (iswalpha(*pwszPath))
+ {
+ // If the first character is an alphanumeric, we must have
+ // a drive designator of this form:
+ // (<alnum>)+<drive-separator><path-separator>
+ //
+ // This covers drives like these: a:\, c:\, etc
+ //
+
+ pwszPath++;
+ cwcRoot++;
+
+ if (*pwszPath == L':')
+ {
+ cwcRoot++;
+ pwszPath++;
+ }
+ else
+ {
+ cwcRoot = 0;
+ }
+ }
+
+ // If we have counted one or more characters in the root and these
+ // are followed by a component separator, we need to add the separator
+ // to the root length. Otherwise this is not a valid root and we need
+ // to return a length of zero.
+ //
+ if ((cwcRoot > 0) && (*pwszPath == L'\\'))
+ {
+ cwcRoot++;
+ }
+ else
+ {
+ cwcRoot = 0;
+ }
+
+ return (cwcRoot);
+}
+
+//
+// MakeRoot
+//
+// This routine was simply copied from private\windows\shell\shelldll\tracker.cxx,
+// and should not be modified here.
+//
+
+
+VOID
+CDirectory::MakeRoot(WCHAR *pwszPath)
+{
+ unsigned rootlength = GetRootLength(pwszPath);
+ m_lError = 0L;
+
+ if (rootlength)
+ {
+ pwszPath[rootlength] = L'\0';
+ }
+}
+