📄 archivecommandline.cpp
字号:
{
wchar_t c = curData[i];
if (c == L'\0')
{
AddCommandLineWildCardToCensr(wildcardCensor,
name, include, commonRecursedType);
name.Empty();
}
else
name += c;
}
if (!name.IsEmpty())
ThrowException("data error");
}
catch(...)
{
UnmapViewOfFile(data);
throw;
}
UnmapViewOfFile(data);
}
{
NSynchronization::CManualResetEvent event;
if (event.Open(EVENT_MODIFY_STATE, false, GetSystemString(eventName)) == S_OK)
event.Set();
}
}
#endif
static void AddSwitchWildCardsToCensor(NWildcard::CCensor &wildcardCensor,
const UStringVector &strings, bool include,
NRecursedType::EEnum commonRecursedType, UINT codePage)
{
for(int i = 0; i < strings.Size(); i++)
{
const UString &name = strings[i];
NRecursedType::EEnum recursedType;
int pos = 0;
if (name.Length() < kSomeCludePostStringMinSize)
ThrowUserErrorException();
if (::MyCharUpper(name[pos]) == kRecursedIDChar)
{
pos++;
int index = UString(kRecursedPostCharSet).Find(name[pos]);
recursedType = GetRecursedTypeFromIndex(index);
if (index >= 0)
pos++;
}
else
recursedType = commonRecursedType;
if (name.Length() < pos + kSomeCludeAfterRecursedPostStringMinSize)
ThrowUserErrorException();
UString tail = name.Mid(pos + 1);
if (name[pos] == kImmediateNameID)
AddCommandLineWildCardToCensr(wildcardCensor, tail, include, recursedType);
else if (name[pos] == kFileListID)
AddToCensorFromListFile(wildcardCensor, tail, include, recursedType, codePage);
#ifdef _WIN32
else if (name[pos] == kMapNameID)
ParseMapWithPaths(wildcardCensor, tail, include, recursedType);
#endif
else
ThrowUserErrorException();
}
}
#ifdef _WIN32
// This code converts all short file names to long file names.
static void ConvertToLongName(const UString &prefix, UString &name)
{
if (name.IsEmpty() || DoesNameContainWildCard(name))
return;
NFind::CFileInfoW fileInfo;
if (NFind::FindFile(prefix + name, fileInfo))
name = fileInfo.Name;
}
static void ConvertToLongNames(const UString &prefix, CObjectVector<NWildcard::CItem> &items)
{
for (int i = 0; i < items.Size(); i++)
{
NWildcard::CItem &item = items[i];
if (item.Recursive || item.PathParts.Size() != 1)
continue;
ConvertToLongName(prefix, item.PathParts.Front());
}
}
static void ConvertToLongNames(const UString &prefix, NWildcard::CCensorNode &node)
{
ConvertToLongNames(prefix, node.IncludeItems);
ConvertToLongNames(prefix, node.ExcludeItems);
int i;
for (i = 0; i < node.SubNodes.Size(); i++)
ConvertToLongName(prefix, node.SubNodes[i].Name);
// mix folders with same name
for (i = 0; i < node.SubNodes.Size(); i++)
{
NWildcard::CCensorNode &nextNode1 = node.SubNodes[i];
for (int j = i + 1; j < node.SubNodes.Size();)
{
const NWildcard::CCensorNode &nextNode2 = node.SubNodes[j];
if (nextNode1.Name.CompareNoCase(nextNode2.Name) == 0)
{
nextNode1.IncludeItems += nextNode2.IncludeItems;
nextNode1.ExcludeItems += nextNode2.ExcludeItems;
node.SubNodes.Delete(j);
}
else
j++;
}
}
for (i = 0; i < node.SubNodes.Size(); i++)
{
NWildcard::CCensorNode &nextNode = node.SubNodes[i];
ConvertToLongNames(prefix + nextNode.Name + wchar_t(NFile::NName::kDirDelimiter), nextNode);
}
}
static void ConvertToLongNames(NWildcard::CCensor &censor)
{
for (int i = 0; i < censor.Pairs.Size(); i++)
{
NWildcard::CPair &pair = censor.Pairs[i];
ConvertToLongNames(pair.Prefix, pair.Head);
}
}
#endif
static NUpdateArchive::NPairAction::EEnum GetUpdatePairActionType(int i)
{
switch(i)
{
case NUpdateArchive::NPairAction::kIgnore: return NUpdateArchive::NPairAction::kIgnore;
case NUpdateArchive::NPairAction::kCopy: return NUpdateArchive::NPairAction::kCopy;
case NUpdateArchive::NPairAction::kCompress: return NUpdateArchive::NPairAction::kCompress;
case NUpdateArchive::NPairAction::kCompressAsAnti: return NUpdateArchive::NPairAction::kCompressAsAnti;
}
throw 98111603;
}
const UString kUpdatePairStateIDSet = L"PQRXYZW";
const int kUpdatePairStateNotSupportedActions[] = {2, 2, 1, -1, -1, -1, -1};
const UString kUpdatePairActionIDSet = L"0123"; //Ignore, Copy, Compress, Create Anti
const wchar_t *kUpdateIgnoreItselfPostStringID = L"-";
const wchar_t kUpdateNewArchivePostCharID = '!';
static bool ParseUpdateCommandString2(const UString &command,
NUpdateArchive::CActionSet &actionSet, UString &postString)
{
for(int i = 0; i < command.Length();)
{
wchar_t c = MyCharUpper(command[i]);
int statePos = kUpdatePairStateIDSet.Find(c);
if (statePos < 0)
{
postString = command.Mid(i);
return true;
}
i++;
if (i >= command.Length())
return false;
int actionPos = kUpdatePairActionIDSet.Find(::MyCharUpper(command[i]));
if (actionPos < 0)
return false;
actionSet.StateActions[statePos] = GetUpdatePairActionType(actionPos);
if (kUpdatePairStateNotSupportedActions[statePos] == actionPos)
return false;
i++;
}
postString.Empty();
return true;
}
static void ParseUpdateCommandString(CUpdateOptions &options,
const UStringVector &updatePostStrings,
const NUpdateArchive::CActionSet &defaultActionSet)
{
for(int i = 0; i < updatePostStrings.Size(); i++)
{
const UString &updateString = updatePostStrings[i];
if(updateString.CompareNoCase(kUpdateIgnoreItselfPostStringID) == 0)
{
if(options.UpdateArchiveItself)
{
options.UpdateArchiveItself = false;
options.Commands.Delete(0);
}
}
else
{
NUpdateArchive::CActionSet actionSet = defaultActionSet;
UString postString;
if (!ParseUpdateCommandString2(updateString, actionSet, postString))
ThrowUserErrorException();
if(postString.IsEmpty())
{
if(options.UpdateArchiveItself)
options.Commands[0].ActionSet = actionSet;
}
else
{
if(MyCharUpper(postString[0]) != kUpdateNewArchivePostCharID)
ThrowUserErrorException();
CUpdateArchiveCommand uc;
UString archivePath = postString.Mid(1);
if (archivePath.IsEmpty())
ThrowUserErrorException();
uc.UserArchivePath = archivePath;
uc.ActionSet = actionSet;
options.Commands.Add(uc);
}
}
}
}
static const char kByteSymbol = 'B';
static const char kKiloSymbol = 'K';
static const char kMegaSymbol = 'M';
static const char kGigaSymbol = 'G';
static bool ParseComplexSize(const UString &src, UInt64 &result)
{
UString s = src;
s.MakeUpper();
const wchar_t *start = s;
const wchar_t *end;
UInt64 number = ConvertStringToUInt64(start, &end);
int numDigits = (int)(end - start);
if (numDigits == 0 || s.Length() > numDigits + 1)
return false;
if (s.Length() == numDigits)
{
result = number;
return true;
}
int numBits;
switch (s[numDigits])
{
case kByteSymbol:
result = number;
return true;
case kKiloSymbol:
numBits = 10;
break;
case kMegaSymbol:
numBits = 20;
break;
case kGigaSymbol:
numBits = 30;
break;
default:
return false;
}
if (number >= ((UInt64)1 << (64 - numBits)))
return false;
result = number << numBits;
return true;
}
static void SetAddCommandOptions(
NCommandType::EEnum commandType,
const CParser &parser,
CUpdateOptions &options)
{
NUpdateArchive::CActionSet defaultActionSet;
switch(commandType)
{
case NCommandType::kAdd:
defaultActionSet = NUpdateArchive::kAddActionSet;
break;
case NCommandType::kDelete:
defaultActionSet = NUpdateArchive::kDeleteActionSet;
break;
default:
defaultActionSet = NUpdateArchive::kUpdateActionSet;
}
options.UpdateArchiveItself = true;
options.Commands.Clear();
CUpdateArchiveCommand updateMainCommand;
updateMainCommand.ActionSet = defaultActionSet;
options.Commands.Add(updateMainCommand);
if(parser[NKey::kUpdate].ThereIs)
ParseUpdateCommandString(options, parser[NKey::kUpdate].PostStrings,
defaultActionSet);
if(parser[NKey::kWorkingDir].ThereIs)
{
const UString &postString = parser[NKey::kWorkingDir].PostStrings[0];
if (postString.IsEmpty())
NDirectory::MyGetTempPath(options.WorkingDir);
else
options.WorkingDir = postString;
}
options.SfxMode = parser[NKey::kSfx].ThereIs;
if (options.SfxMode)
options.SfxModule = parser[NKey::kSfx].PostStrings[0];
if (parser[NKey::kVolume].ThereIs)
{
const UStringVector &sv = parser[NKey::kVolume].PostStrings;
for (int i = 0; i < sv.Size(); i++)
{
UInt64 size;
if (!ParseComplexSize(sv[i], size))
ThrowException("Incorrect volume size");
options.VolumesSizes.Add(size);
}
}
}
static void SetMethodOptions(const CParser &parser, CObjectVector<CProperty> &properties)
{
if (parser[NKey::kProperty].ThereIs)
{
// options.MethodMode.Properties.Clear();
for(int i = 0; i < parser[NKey::kProperty].PostStrings.Size(); i++)
{
CProperty property;
const UString &postString = parser[NKey::kProperty].PostStrings[i];
int index = postString.Find(L'=');
if (index < 0)
property.Name = postString;
else
{
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -