diff -r c7c26511138f -r 360bd6b35136 imgtools/romtools/readimage/src/image_reader.cpp --- a/imgtools/romtools/readimage/src/image_reader.cpp Wed Jun 16 16:51:40 2010 +0300 +++ b/imgtools/romtools/readimage/src/image_reader.cpp Wed Jun 23 16:56:47 2010 +0800 @@ -1,504 +1,477 @@ -/* -* Copyright (c) 2005-2009 Nokia Corporation and/or its subsidiary(-ies). -* All rights reserved. -* This component and the accompanying materials are made available -* under the terms of the License "Eclipse Public License v1.0" -* which accompanies this distribution, and is available -* at the URL "http://www.eclipse.org/legal/epl-v10.html". -* -* Initial Contributors: -* Nokia Corporation - initial contribution. -* -* Contributors: -* -* Description: -* @internalComponent -* @released -* -*/ - - -#include "image_reader.h" - -ImageReader::ImageReader(const char* aFile) : iDisplayOptions(0),iImgFileName(aFile) -{ -} - -ImageReader::~ImageReader() -{ -} - -void ImageReader::SetDisplayOptions(TUint32 aFlag) -{ - iDisplayOptions |= aFlag; -} - -bool ImageReader::DisplayOptions(TUint32 aFlag) -{ - return ((iDisplayOptions & aFlag) != 0); -} - -void ImageReader::DumpData(TUint* aData, TUint aLength) -{ - TUint *p=aData; - TUint i=0; - char line[256]; - char *cp=(char*)aData; - TUint j=0; - memset(line,' ',sizeof(line)); - while (iwidth(6); - out->fill('0'); - *out << i << ":"; - while (iwidth(8); - out->fill('0'); - *out << *p++; - i+=4; - ccount++; - for (j=0; j<4; j++) - { - char c=*cp++; - if (c<32) - { - c = '.'; - } - *linep++ = c; - } - } - *linep = '\0'; - *out << line+(ccount*5) << endl; - } - } - - - -/** -Function to extract specified file from a given image. - -@internalComponent -@released - -@param aOffset - starting offset of the file in the image. -@param aSize - size of the file in the image. -@param aFileName - name of the file. -@param aPath - full path of the file inside image. -@param aFilePath - path where file has to be extracted. -*/ -void ImageReader::ExtractFile(TUint aOffset,TInt aSize,const char* aFileName,const char* aPath,char* aFilePath,char* aData) -{ - // concatenate path where specified file needs to be extracted with - // path where file is located in the image. - string fullPath( aFilePath ); - string delimiter( "\\" ); - string appStr( "\\\\" ); - fullPath.append( aPath ); - - // replace all the occurrence of slash with double slash. - FindAndInsertString( fullPath, delimiter, delimiter ); - // now terminate the string with double slash. - fullPath.append( appStr ); - - // create specified directory where file needs to be extracted. - CreateSpecifiedDir( &fullPath[0], appStr.c_str() ); - - // concatenate path information with the filename - fullPath.append( aFileName ); - - // create an output stream to extract the specified file. - ofstream outfile (fullPath.c_str(), ios::out | ios::binary); - // create an input stream by opening the specified image file. - ifstream infile(ImageReader::iImgFileName.c_str(),ios::in|ios::binary); - - //declare a buffer to store the data. - char* buffer = new char[aSize]; - - if(aData != NULL) - { - memcpy(buffer, aData + aOffset, aSize); - } - else if(infile.is_open()) - { - // place the get pointer for the current input stream to offset bytes away from origin. - infile.seekg(aOffset,ios::beg); - //read number of bytes specified by the variable size - //from the stream and place it on to buffer. - infile.read(buffer,aSize); - //close the input stream after reading. - infile.close(); - } - else - { - throw ImageReaderException(ImageReader::iImgFileName.c_str(), "Failed to open the image file"); - } - - if(outfile.is_open()) - { - //writes number of bytes specified by the variable size - //from buffer to the current output stream. - outfile.write(buffer,aSize); - //close the output stream after writing. - outfile.close(); - } - else - { - throw ImageReaderException(aFileName, "Failed to extract the file"); - } - - //delete the buffer. - delete[] buffer; -} - -/** -Function to create a given directory. - -@internalComponent -@released - -@param aSrcPath - path of the directory that needs to be created. -@param aDelimiter - delimiter. -*/ -void ImageReader::CreateSpecifiedDir(char* aSrcPath,const char* aDelimiter) -{ - char* currWorkingDir = new char[_MAX_BUFFER_SIZE_]; - string origPath; - - origPath.assign(aSrcPath); - - - // get the current working directory and store in buffer. - if( _getcwd(currWorkingDir,_MAX_BUFFER_SIZE_) == NULL ) - { - // throw an exception if unable to get current working directory information. - throw ImageReaderException((char*)ImageReader::iImgFileName.c_str(), "Failed to get the current working directory"); - } - else - { - char* cPtr = strtok(aSrcPath,aDelimiter); - - // check whether cPtr is a drive or a directory. - if(IsDrive(cPtr)) - { - // if yes, then change the directory to cPtr. - string changeToDrive ; - changeToDrive.assign(cPtr); - changeToDrive.append(aDelimiter); - - // change the current working directory to the specified directory. - if( _chdir(changeToDrive.c_str()) ) - { - // throw an exception if unable to change the directory specified. - throw ImageReaderException((char*)ImageReader::iImgFileName.c_str(), "Failed to change to the directory specified"); - } - } - else - { - // if not,then create a cPtr directory. - _mkdir(cPtr); - // change the current working directory to cPtr. - _chdir(cPtr); - } - // repeat till cPtr is NULL. - while (cPtr!=NULL) - { - if (cPtr = strtok(NULL,aDelimiter)) - { - // create the directory. - _mkdir(cPtr); - // change current working directory. - _chdir(cPtr); - } - } - // revert back the working directory. - _chdir(currWorkingDir); - // replace the source path with the original path information. - strcpy(aSrcPath,origPath.c_str()); - delete[] currWorkingDir; - } -} - - -/** -Function to check whether the given string is a drive or a folder. - -@internalComponent -@released - -@param aStr - string to be checked. -@return - returns True if the given string is a drive else returns false. -*/ -TBool ImageReader::IsDrive(char* aStr) -{ - TInt strlength = strlen(aStr); - //check for the last character in a given string, - //if the last character is colon then return true else false. - if(!strcmp(&aStr[strlength - 1],":")) - { - return true; - } - else - { - return false; - } -} - - -/** -Function to insert a given string with a delimiter. - -@internalComponent -@released - -@param aSrcStr - string to be modified. -@param aDelimiter - string to be checked. -@param aAppStr - string to be inserted with the delimiter. -*/ -void ImageReader::FindAndInsertString(string& aSrcStr,string& aDelimiter,string& aAppStr) -{ - string::size_type loc = 0; - string::size_type pos =0; - while(( pos = aSrcStr.find( aDelimiter, loc ) ) != ( string::npos ) ) - { - if( pos != string::npos ) - { - aSrcStr.insert(pos,aAppStr); - loc = pos + aAppStr.length() + 1; - } - } -} - -/** -Function to replace a delimiter with a given string. - -@internalComponent -@released - -@param aSrcStr - string to be modified. -@param aDelimiter - string to be checked. -@param aReplStr - string to be replaced with the delimiter. -*/ -void ImageReader::FindAndReplaceString( string& aSrcStr, string& aDelimiter, string& aReplStr ) -{ - string::size_type loc = 0; - string::size_type pos =0; - while(( pos = aSrcStr.find( aDelimiter,loc) ) != ( string::npos ) ) - { - if( pos != string::npos ) - { - aSrcStr.replace( pos, aReplStr.length(),aReplStr ); - loc = pos + aReplStr.length() + 1; - } - } -} - -/** -Function to extract individual or a subset of file. - -@internalComponent -@released - -@param aData - ROM/ROFS image buffer pointer. -*/ -void ImageReader::ExtractFileSet(char* aData) -{ - FILEINFOMAP fileInfoMap; - string dirSep(DIR_SEPARATOR), backSlash("\\"), Pattern; - TUint extfileCount = 0, noWcardFlag = 0, pos; - - //Get the filelist map - GetFileInfo(fileInfoMap); - - //Check for wildcards - pos = iPattern.rfind("\\"); - if(pos == string::npos) - { - pos = iPattern.rfind("/"); - if(pos == string::npos) - pos = 0; - } - pos = iPattern.find_first_of("*?", pos); - if(pos == string::npos) - { - noWcardFlag = 1; - } - - //Process the map - if(fileInfoMap.size() > 0) - { - FILEINFOMAP::iterator begin = fileInfoMap.begin(); - FILEINFOMAP::iterator end = fileInfoMap.end(); - - // Replace all backslashes with forward slashes - Pattern = iPattern; - FindAndReplaceString(Pattern, backSlash, dirSep); - - // Insert root directory at the beginning if it is not there - pos = Pattern.find_first_not_of(" ", 0); - if(pos != string::npos) - { - if(Pattern.at(pos) != *DIR_SEPARATOR) - Pattern.insert(pos, dirSep); - } - - // Assign CWD for destination path if it is empty - if(ImageReader::iZdrivePath.empty()) - ImageReader::iZdrivePath.assign("."); - - while(begin != end) - { - int status = 0; - PFILEINFO pInfo = 0; - string fileName = (*begin).first; - pInfo = (*begin).second; - - // First match - status = FileNameMatch(Pattern, fileName, (iDisplayOptions & RECURSIVE_FLAG)); - - // If no match - if((!status) && noWcardFlag) - { - string newPattern(Pattern); - - // Add * at the end - if(newPattern.at(Pattern.length()-1) != *DIR_SEPARATOR) - { - newPattern.append(DIR_SEPARATOR); - } - newPattern += "*"; - status = FileNameMatch(newPattern, fileName, (iDisplayOptions & RECURSIVE_FLAG)); - - // If it matches update the pattern and reset wildcard flag - if(status) - { - Pattern = newPattern; - noWcardFlag = 0; - } - } - - if(status) - { - // Extract the file - - // Separarate the path and file name - string fullPath = fileName.substr(0, fileName.rfind(DIR_SEPARATOR)); - string file = fileName.substr(fileName.rfind(DIR_SEPARATOR)+1, fileName.length()); - FindAndReplaceString(fullPath, dirSep, backSlash); - - // Extract only those files exists in the image - if(pInfo->iSize && pInfo->iOffset) - { - ExtractFile(pInfo->iOffset, pInfo->iSize, file.c_str(), fullPath.c_str() , - &ImageReader::iZdrivePath[0], aData); - - extfileCount++; - } - } - - if(pInfo) - delete pInfo; - ++begin; - } - fileInfoMap.clear(); - } - - // Throw error if the extracted file count is zero - if(!extfileCount) - { - throw ImageReaderException((char*)ImageReader::iImgFileName.c_str(), "No matching files found for the given pattern"); - } -} - -/** -To match the given file name aganist the given pattern with wildcards - -@internalComponent -@released - -@param aPattern - input filename pattern. -@param aFileName - input file name. -@param aRecursiveFlag - recursive search flag. -*/ -int ImageReader::FileNameMatch(string aPattern, string aFileName, int aRecursiveFlag) -{ - const char *InputString = aFileName.c_str(); - const char *Pattern = aPattern.c_str(); - const char *CurrPattern = 0, *CurrString = 0; - - // If the input is empty then return false - if((aPattern.empty()) || (!InputString)) - return 0; - - // First candidate match - // Step 1: Look for the exact matches between the input pattern and the given file-name till - // the first occurrence of wildcard character (*). This should also skip a character - // from matching for the occurrence of wildcard character(?) in the pattern. - while ((*InputString) && (*Pattern != '*')) - { - if ((toupper(*Pattern) != toupper(*InputString)) && (*Pattern != '?')) - { - return 0; - } - Pattern++; - InputString++; - } - - // Wildcard match - // Step 2: Now the input string (file-name) should be checked against the wildcard characters (* and ?). - // Skip the input string if the pattern points to wildcard character(*). Do the exact match for - // other characters in the patterns except the wildcard character(?). The path-separator should be - // considered as non-match for non-recursive option. - while (*InputString) - { - if ((*Pattern == '*')) - { - if (!*++Pattern) - { - // If recursive flag is set then this case matches for any character of the input string - // from the current position - if(aRecursiveFlag) - return 1; - } - - // Update the current pattern and the current inputstring - CurrPattern = Pattern; - CurrString = InputString+1; - } - else if ((toupper(*Pattern) == toupper(*InputString)) || (*Pattern == '?')) - { - // Exact match for the path separator - // So recursively call the function to look for the exact path level match - if(*Pattern == '/') - return FileNameMatch(Pattern, InputString, aRecursiveFlag); - - // Exact match so increment both - Pattern++; - InputString++; - } - else if ((*InputString == *DIR_SEPARATOR) && (!aRecursiveFlag)) - { - // Inputstring points to path separator and it is not expected here for non-recursive case - return 0; - } - else - { - // Default case where it matches for the wildcard character * - Pattern = CurrPattern; - InputString = CurrString++; - } - } - - // Leave any more stars in the pattern - while (*Pattern == '*') - { - Pattern++; - } - - // Return the status - return !*Pattern; -} +/* +* Copyright (c) 2005-2009 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of the License "Eclipse Public License v1.0" +* which accompanies this distribution, and is available +* at the URL "http://www.eclipse.org/legal/epl-v10.html". +* +* Initial Contributors: +* Nokia Corporation - initial contribution. +* +* Contributors: +* +* Description: +* @internalComponent +* @released +* +*/ + + +#include "image_reader.h" +#include +#include +#include + +using namespace boost::filesystem; +ImageReader::ImageReader(const char* aFile) : iDisplayOptions(0),iImgFileName(aFile) { +} + +ImageReader::~ImageReader() { +} + +void ImageReader::SetDisplayOptions(TUint32 aFlag) { + iDisplayOptions |= aFlag; +} + +bool ImageReader::DisplayOptions(TUint32 aFlag) { + return ((iDisplayOptions & aFlag) != 0); +} + +void ImageReader::DumpData(TUint* aData, TUint aLength) { + TUint *p=aData; + TUint i=0; + char line[256]; + char *cp=(char*)aData; + TUint j=0; + memset(line,' ',sizeof(line)); + while (iwidth(6); + out->fill('0'); + *out << i << ":"; + while (iwidth(8); + out->fill('0'); + *out << *p++; + i+=4; + ccount++; + for (j=0; j<4; j++) { + char c=*cp++; + if (c<32) { + c = '.'; + } + *linep++ = c; + } + } + *linep = '\0'; + *out << line+(ccount*5) << endl; + } + } + + + +/** +Function to extract specified file from a given image. + +@internalComponent +@released + +@param aOffset - starting offset of the file in the image. +@param aSize - size of the file in the image. +@param aFileName - name of the file. +@param aPath - full path of the file inside image. +@param aFilePath - path where file has to be extracted. +*/ +void ImageReader::ExtractFile(TUint aOffset,TInt aSize,const char* aFileName,const char* aPath,const char* aFilePath,const char* aData) { + // concatenate path where specified file needs to be extracted with + // path where file is located in the image. + string fullPath( aFilePath ); + if(*aPath != SLASH_CHAR1 && *aPath != SLASH_CHAR2){ + char ch = aFilePath[fullPath.length() - 1]; + if(ch != SLASH_CHAR1 && ch != SLASH_CHAR2) + fullPath += SLASH_CHAR1 ; + } + int startImagePath = (int)fullPath.length(); + fullPath += aPath ; + + // create specified directory where file needs to be extracted. + // to lower + char* data = const_cast(fullPath.data() + startImagePath); + for(; *data != 0 ; data++){ + if(*data >= 'A' && *data <= 'Z'){ + *data |= 0x20 ; + } + } + CreateSpecifiedDir(fullPath); + + data -- ; + if(*data != SLASH_CHAR1) + fullPath += SLASH_CHAR1 ; + + // concatenate path information with the filename + fullPath += aFileName ; + + // create an output stream to extract the specified file. + ofstream outfile (fullPath.c_str(), ios_base::out | ios_base::binary); + // create an input stream by opening the specified image file. + ifstream infile(ImageReader::iImgFileName.c_str(),ios_base::in|ios_base::binary); + + //declare a buffer to store the data. + char* buffer = new char[aSize]; + + if(aData != NULL){ + memcpy(buffer, aData + aOffset, aSize); + } + else if(infile.is_open()) { + // place the get pointer for the current input stream to offset bytes away from origin. + infile.seekg(aOffset,ios_base::beg); + //read number of bytes specified by the variable size + //from the stream and place it on to buffer. + infile.read(buffer,aSize); + //close the input stream after reading. + infile.close(); + } + else { + throw ImageReaderException(ImageReader::iImgFileName.c_str(), "Failed to open the image file"); + } + + if(outfile.is_open()) { + //writes number of bytes specified by the variable size + //from buffer to the current output stream. + outfile.write(buffer,aSize); + //close the output stream after writing. + outfile.close(); + } + else { + throw ImageReaderException(aFileName, "Failed to extract the file"); + } + + //delete the buffer. + delete[] buffer; +} + +/** +Function to create a given directory. + +@internalComponent +@released + +@param aSrcPath - path of the directory that needs to be created. +*/ +void ImageReader::CreateSpecifiedDir(const string& aSrcPath) { + char* currWorkingDir = new char[PATH_MAX]; + int len = aSrcPath.length() ; + const char* origPath = aSrcPath.c_str(); + char* path = new char[len + 2]; + + memcpy(path,origPath,len); + if(path[len - 1] != SLASH_CHAR1 && path[len - 1] != SLASH_CHAR2){ + path[len] = SLASH_CHAR1 ; + len ++ ; + } + path[len] = 0; + char* start = path; + char* end = path + len ; + char errMsg[400] ; + *errMsg = 0; + char* dirEnd ; + + // get the current working directory and store in buffer. + if( getcwd(currWorkingDir,PATH_MAX) == NULL ) { + // throw an exception if unable to get current working directory information. + snprintf(errMsg,400,"Failed to get the current working directory") ; + goto L_EXIT; + } +#ifdef WIN32 +//check dir + if(isalpha(start[0]) && start[1] == ':'){ + char ch = start[3] ; + start[3] = 0; + if(chdir(start)) { + snprintf(errMsg, 400 ,"Failed to change to the directory \"%s\".",path); + goto L_EXIT; + } + start[3] = ch ; + start += 3 ; + } + else if(*start == SLASH_CHAR1 || *start == SLASH_CHAR2){ + if(chdir("\\")){ + snprintf(errMsg, 400 ,"Failed to change to the directory \"\\\"."); + goto L_EXIT; + } + start ++ ; + } +#else + if(*start == SLASH_CHAR1 || *start == SLASH_CHAR2){ + if(chdir("/")) { + snprintf(errMsg, 400 ,"Failed to change to the directory \"/\"."); + goto L_EXIT; + } + start ++ ; + } +#endif + dirEnd = start ; + + while( start < end ) { + while(*dirEnd != SLASH_CHAR1 && *dirEnd != SLASH_CHAR2) + dirEnd ++ ; + *dirEnd = 0 ; + + if(!exists(start)) { + MKDIR(start); + } + if(chdir(start)){ + snprintf(errMsg, 400 ,"Failed to change to the directory \"%s\".",path); + goto L_EXIT; + } + *dirEnd = SLASH_CHAR1; + start = dirEnd + 1; + dirEnd = start ; + } +L_EXIT: + chdir(currWorkingDir); + delete[] currWorkingDir; + delete [] path; + if(*errMsg) + throw ImageReaderException(ImageReader::iImgFileName.c_str(), errMsg); +} + + + + + +/** +Function to insert a given string with a delimiter. + +@internalComponent +@released + +@param aSrcStr - string to be modified. +@param aDelimiter - string to be checked. +@param aAppStr - string to be inserted with the delimiter. +*/ +void ImageReader::FindAndInsertString(string& aSrcStr,string& aDelimiter,string& aAppStr) { + string::size_type loc = 0; + string::size_type pos =0; + while(( pos = aSrcStr.find( aDelimiter, loc ) ) != ( string::npos ) ) { + if( pos != string::npos ) { + aSrcStr.insert(pos,aAppStr); + loc = pos + aAppStr.length() + 1; + } + } +} + +/** +Function to replace a delimiter with a given string. + +@internalComponent +@released + +@param aSrcStr - string to be modified. +@param aDelimiter - string to be checked. +@param aReplStr - string to be replaced with the delimiter. +*/ +void ImageReader::FindAndReplaceString( string& aSrcStr, string& aDelimiter, string& aReplStr ) { + string::size_type loc = 0; + string::size_type pos =0; + while(( pos = aSrcStr.find( aDelimiter,loc) ) != ( string::npos ) ) { + if( pos != string::npos ) { + aSrcStr.replace( pos, aReplStr.length(),aReplStr ); + loc = pos + aReplStr.length() + 1; + } + } +} + +/** +Function to extract individual or a subset of file. + +@internalComponent +@released + +@param aData - ROM/ROFS image buffer pointer. +*/ +void ImageReader::ExtractFileSet(const char* aData) { + FILEINFOMAP fileInfoMap; + TUint extfileCount = 0, noWcardFlag = 0 ; + + //Get the filelist map + GetFileInfo(fileInfoMap); + + //Check for wildcards + const char* patternStr = iPattern.c_str(); + TInt dp = iPattern.length() - 1; + while(dp >= 0){ + if(patternStr[dp] == SLASH_CHAR1 || patternStr[dp] == SLASH_CHAR2) + break ; + dp -- ; + } + size_t pos = iPattern.find_first_of("*?",dp + 1); + if(pos == string::npos) + noWcardFlag = 1; + + //Process the map + if(fileInfoMap.size() > 0) { + FILEINFOMAP::iterator begin = fileInfoMap.begin(); + FILEINFOMAP::iterator end = fileInfoMap.end(); + + // Replace all backslashes with forward slashes + string pat(iPattern); + for(size_t n = 0 ; n < iPattern.length(); n++){ + if(patternStr[n] == SLASH_CHAR2) + pat[n] = SLASH_CHAR1 ; + } + + // Insert root directory at the beginning if it is not there + pos = pat.find_first_not_of(" ", 0); + if(pos != string::npos) { + if(pat.at(pos) != SLASH_CHAR1) + pat.insert(pos, 1,SLASH_CHAR1); + } + + // Assign CWD for destination path if it is empty + if(ImageReader::iZdrivePath.empty()) + ImageReader::iZdrivePath.assign("."); + + while(begin != end) { + + string fileName((*begin).first); + PFILEINFO pInfo = (*begin).second; + + // First match + int status = FileNameMatch(pat, fileName, (iDisplayOptions & RECURSIVE_FLAG)); + + // If no match + if((!status) && noWcardFlag) { + string newPattern(pat); + + // Add * at the end + if(newPattern.at(pat.length()-1) != SLASH_CHAR1) { + newPattern += SLASH_CHAR1; + } + newPattern += "*"; + status = FileNameMatch(newPattern, fileName, (iDisplayOptions & RECURSIVE_FLAG)); + + // If it matches update the pattern and reset wildcard flag + if(status) { + pat = newPattern; + noWcardFlag = 0; + } + } + + if(status) { + // Extract the file + + // Separarate the path and file name + int slash_pos = fileName.rfind(SLASH_CHAR1); + string fullPath = fileName.substr(0,slash_pos ); + string file = fileName.substr(slash_pos + 1, fileName.length()); + //FindAndReplaceString(fullPath, dirSep, backSlash); + char* fpStr = const_cast(fullPath.c_str()); + for(size_t m = 0 ; m < fullPath.length() ; m++){ + if(fpStr[m] == SLASH_CHAR2) + fpStr[m] = SLASH_CHAR1 ; + } + + // Extract only those files exists in the image + if(pInfo->iSize && pInfo->iOffset) { + ExtractFile(pInfo->iOffset, pInfo->iSize, file.c_str(), fullPath.c_str() , + ImageReader::iZdrivePath.c_str(), aData); + + extfileCount++; + } + } + + if(pInfo) + delete pInfo; + ++begin; + } + fileInfoMap.clear(); + } + + // Throw error if the extracted file count is zero + if(!extfileCount) { + throw ImageReaderException(ImageReader::iImgFileName.c_str(), "No matching files found for the given pattern"); + } +} + +/** +To match the given file name aganist the given pattern with wildcards + +@internalComponent +@released + +@param aPattern - input filename pattern. +@param aFileName - input file name. +@param aRecursiveFlag - recursive search flag. +*/ +int ImageReader::FileNameMatch(const string& aPattern, const string& aFileName, int aRecursiveFlag) { + const char *InputString = aFileName.c_str(); + const char *Pattern = aPattern.c_str(); + const char *CurrPattern = 0, *CurrString = 0; + + // If the input is empty then return false + if((aPattern.empty()) || (!InputString)) + return 0; + + // First candidate match + // Step 1: Look for the exact matches between the input pattern and the given file-name till + // the first occurrence of wildcard character (*). This should also skip a character + // from matching for the occurrence of wildcard character(?) in the pattern. + while ((*InputString) && (*Pattern != '*')) { + if ((toupper(*Pattern) != toupper(*InputString)) && (*Pattern != '?')) { + return 0; + } + Pattern++; + InputString++; + } + + // Wildcard match + // Step 2: Now the input string (file-name) should be checked against the wildcard characters (* and ?). + // Skip the input string if the pattern points to wildcard character(*). Do the exact match for + // other characters in the patterns except the wildcard character(?). The path-separator should be + // considered as non-match for non-recursive option. + while (*InputString) { + if ((*Pattern == '*')) { + if (!*++Pattern) { + // If recursive flag is set then this case matches for any character of the input string + // from the current position + if(aRecursiveFlag) + return 1; + } + + // Update the current pattern and the current inputstring + CurrPattern = Pattern; + CurrString = InputString+1; + } + else if ((toupper(*Pattern) == toupper(*InputString)) || (*Pattern == '?')) { + // Exact match for the path separator + // So recursively call the function to look for the exact path level match + if(*Pattern == SLASH_CHAR1) + return FileNameMatch(Pattern, InputString, aRecursiveFlag); + + // Exact match so increment both + Pattern++; + InputString++; + } + else if ((*InputString == SLASH_CHAR1) && (!aRecursiveFlag)) { + // Inputstring points to path separator and it is not expected here for non-recursive case + return 0; + } + else { + // Default case where it matches for the wildcard character * + Pattern = CurrPattern; + InputString = CurrString++; + } + } + + // Leave any more stars in the pattern + while (*Pattern == '*') + Pattern++; + + // Return the status + return !*Pattern; +}