/* * Convert A LFN Filename to a 8.3 filename * * IN: * pLfnName : Name of an ext2 directory entry * EntryLen : Length of bytes of pLfnName * * OUT: * ShortName : ASCIIZ 8.3 filename * */ void LfnToShortName(char *EntryName, int EntryLen, char *ShortName, int Offset) { USHORT uni_lfn[MAX_PATH]; USHORT uni_short[14]; _QWORD qword; DWORD rval; /* * Convert to Unicode Short FileName, make sure we do not * convert . or .. */ if (isDotOrDotDot(EntryName, EntryLen)) { strncpy(ShortName, EntryName, EntryLen); ShortName[EntryLen] = 0; } else { /* * Convert BCS LFN to Unicode LFN FileName */ BCSToUni(uni_lfn, EntryName, EntryLen, BCS_OEM, &qword); uni_lfn[qword.ddLower >> 1] = 0; /* * Create the Unicode 8.3 name */ rval = CreateBasis(uni_short, uni_lfn, qword.ddLower); if (rval & (BASIS_LOSS | BASIS_UPCASE | BASIS_TRUNC)) AppendBasisTail(uni_short, (INT) Offset%100); /* * Convert to BCS */ UniToBCS(ShortName, uni_short, 2 * ustrlen(uni_short), 12, BCS_OEM, &qword); ShortName[qword.ddLower] = 0; } }
bool QFileSystemIteratorPrivate::advanceHelper() { if (m_dirStructs.isEmpty()) return true; //printf("ADV %d %d\n", int(m_currentDirShown), int(m_nextDirShown)); if ((filters & QDir::Dirs)) { m_currentDirShown = m_nextDirShown; if (m_nextDirShown == ShowDir) { //printf("RESTING ON DIR %s %x\n", m_dirPaths.top().constData(), int(filters)); m_nextDirShown = (filters & QDir::NoDotAndDotDot) ? DontShowDir : ShowDotDir; // skip start directory itself if (m_dirStructs.size() == 1 && m_currentDirShown == ShowDir) return advanceHelper(); return true; } if (m_nextDirShown == ShowDotDir) { //printf("RESTING ON DOT %s %x\n", m_dirPaths.top().constData(), int(filters)); m_nextDirShown = ShowDotDotDir; return true; } if (m_nextDirShown == ShowDotDotDir) { //printf("RESTING ON DOTDOT %s %x\n", m_dirPaths.top().constData(), int(filters)); m_nextDirShown = DontShowDir; return true; } m_currentDirShown = DontShowDir; } #ifdef Q_OS_WIN m_entry = &m_fileSearchResult; if (m_bFirstSearchResult) { m_bFirstSearchResult = false; } else { if (!FindNextFile(m_dirStructs.top(), m_entry)) m_entry = 0; } while (m_entry && isDotOrDotDot(m_entry->cFileName)) if (!FindNextFile(m_dirStructs.top(), m_entry)) m_entry = 0; if (!m_entry) { m_dirPaths.pop(); FindClose(m_dirStructs.pop()); return false; } if (m_entry->dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) { QByteArray ba = m_dirPaths.top(); ba += '\\'; ba += QString::fromWCharArray(m_entry->cFileName); pushSubDirectory(ba); } #else m_entry = ::readdir(m_dirStructs.top()); while (m_entry && isDotOrDotDot(m_entry->d_name)) m_entry = ::readdir(m_dirStructs.top()); //return false; // further iteration possibly needed //printf("READ %p %s\n", m_entry, m_entry ? m_entry->d_name : ""); if (!m_entry) { m_dirPaths.pop(); DIR *dir = m_dirStructs.pop(); ::closedir(dir); return false; // further iteration possibly needed } const char *name = m_entry->d_name; QByteArray ba = m_dirPaths.top(); ba += '/'; ba += name; struct stat st; lstat(ba.constData(), &st); if (S_ISDIR(st.st_mode)) { pushSubDirectory(ba); return false; // further iteration possibly needed } #endif return false; // further iteration possiblye needed }
/* Cool Long to Short file name conversion routine. * * PRE: * If isFCB is true --> ShortName must be at least 11 bytes long * otherwise is must be at least 13 bytes long * * POST: * When converting LFN to 8.3 names, we will prevent name clashes due * to case sensitivity, that is, filename.c and Filename.c cannot both * convert to FILENAME.C. Either one of them has to be converted to * FILENA~1.C (or something like that). Since in UNIX file systems, * lower cased file names are more natural, we apply the following * conversion rule: if a filename contains an _uppercased_ character, * it will have a numerical tail appended (the ~1). Of course, filenames * that have too long file name (>8) or extention lenghts (>3) or * contain invalid characters will have a numerical tail appended as * well. * * IN: * LfnName : pointer to LfnName, it not be zero terminated * LfnNameLen : lenght of LfnName (excluding a possible '\0') * isFCB : specifies whether or not the converted shortname * will be in FCB format * OUT: * ShortName : pointer to a buffer for the converted shortname */ static BOOL LongToUpperShort(char *LfnName, int LfnNameLen, char *ShortName) { char *pc; char c; int i; BOOL isconverted; isconverted = FALSE; pc = ShortName; /* * . and .. need no conversion */ if (isDotOrDotDot(LfnName, LfnNameLen)) { strncpy(ShortName, LfnName, LfnNameLen); ShortName[LfnNameLen] = 0; return FALSE; } /* * convert hidden files (starting with a dot) to underscore */ if (LfnName[0]=='.') { LfnName++; LfnNameLen--; *pc++ = '_'; } /* * copy filename part */ for (i=0 ; i<8 && LfnNameLen ; i++) { c = *LfnName++; LfnNameLen--; /* * if '.' we found the extention */ if (c=='.') break; /* * if c is present in the bad character list, we * convert it to an underscore */ if (strchr(sBadChars, c)) { isconverted = TRUE; c = '_'; } else if (isalpha(c)) if (isupper(c)) isconverted = TRUE; else c = toupper(c); *pc++ = c; } /* * If we scanned 8 characters, the filename still * contains characters and we do not see a '.' * the filename part is too long */ if (i==8 && LfnNameLen && (*LfnName != '.')) isconverted = TRUE; /* * search dot for extension of the filename */ for(; LfnNameLen && c!='.' ; LfnNameLen--, c=*LfnName++) ; /* * copy extension */ if (c == '.') *pc++ = '.'; /* * copy the extension part */ for (i=0 ; i<3 && LfnNameLen ; i++) { c = *LfnName++; LfnNameLen--; /* * if c is present in the bad character list or is a * '.' (a second '.'), we convert it to * an underscore */ if (c == '.' || strchr(sBadChars, c)) { isconverted = TRUE; c = '_'; } else if (isalpha(c)) if (isupper(c)) isconverted = TRUE; else c = toupper(c); *pc++ = c; } /* * If, at this point, the filename still contains characters * the file extension part is too long */ if (LfnNameLen) isconverted = TRUE; *pc = 0; return isconverted; }