Я говорил образно. Конечно, придется писать свой. У меня такой был только один. Он отвечает за запуск RSIT и написан на VBS (JS в первой версии).
Вообщем провел несколько креш-тестов по WMIC.
Получил и славный код успеха при поврежденном WMIC.
Т.о. наиболее надежно можно получить результат успеха, анализируя сам вывод команды WMIC:
WMIC /Namespace:\\root\default Path SystemRestore Call CreateRestorePoint "SafeZone.cc", 100, 10
Идет выполнение (SystemRestore)->CreateRestorePoint()
Метод успешно вызван.
Параметры вывода:
instance of __PARAMETERS
{
ReturnValue = 0;
};
а именно, наличие строки
ReturnValue = 0;
На счет "Включить создание контрольных точек" спомощью WMIC - не рекомендую такое делать на XP.
В остальных случаях никаких зависаний в теме о лечении я не наблюдал.
отдельным потоком не получится.
То Вы же все равно подставляете cmd /c в скрипты AVZ. AVZ не умеет. Но умеет CMD, сразу возвращая курсор управления кодом к скрипту AVZ:
ExecuteFile('cmd.exe', '/c start "" WMIC /Namespace:\\root\default Path SystemRestore Call CreateRestorePoint "SafeZone.cc", 100, 10', 0, 0, false);
UPD... открыл справку по ExecuteFile и прикололся. Там и пауза, и Terminate уже все реализовано,
позже сделаю, чтоб WMIC вообще "замерзла", посмотрим, как справится эта функция.
А пока реализация в отдельном процессе вне AVZ:
// Вычисляем кол-во процессов
Function GetProcessCountByName(name : string) : integer;
var
i : integer;
count : integer;
begin
// Обновить список процессов
RefreshProcessList;
count := 0;
// Цикл по списку процессов
for i := 0 to GetProcessCount - 1 do begin
if LowerCase(GetProcessName(i)) = name then count := count + 1;
end;
Result := count;
end;
// Прошло ли указанное кол-во секунд (допустимо указывать не > 60)
Function IsElapsedSeconds(LastDate : TDateTime; CurrentDate : TDateTime; SecMax : integer) : Boolean;
var
LastSec, CurSec, Diff : integer;
begin
LastSec := StrToInt(FormatDateTime('ss', LastDate));
CurSec := StrToInt(FormatDateTime('ss', CurrentDate));
Diff := CurSec - LastSec;
if (Diff < 0) then Diff := Diff + 60;
Result := (Diff > SecMax);
end;
// Создать System Recovery Point. Возвращает true в случае успеха.
Function CreateSR : Boolean;
var
W_log, SR_Command : String;
//SL : TStringList;
WmicCount : integer;
LastDate : TDateTime;
begin
// Папка с логом SR
W_log := GetAVZDirectory + '\WMIC.log';
if FileExists(W_log) then DeleteFile(W_log);
// Команда создания SR средствами WMIC
SR_Command := 'WMIC /Namespace:\\root\default Path SystemRestore Call CreateRestorePoint "SafeZone.cc", 100, 10';
// Считаем кол-во процессов WMIC перед его запуском
WmicCount := GetProcessCountByName('wmic.exe');
// Запуск SR через CMD без ожидания завершения операции с логированием вывода в файл W_log, в свернутом окне
ExecuteFile('cmd.exe', '/c start /min "" cmd /c "' + SR_Command + ' > ' + '"' + W_log + '""', 2, 0, false);
// Выжидаем среднее приемлемое время
Sleep(3);
LastDate := now;
// Цикл - своеобразный WatchDog: завершится, если или пройдет граничное время (еще 10 сек.), или кол-во процессов WMIC уменьшится на 1
while (GetProcessCountByName('wmic.exe') > WmicCount) and (not IsElapsedSeconds(LastDate, now, 12)) do begin
Sleep(1);
end;
Sleep(2);
if FileExists(W_log) then begin
// Загрузка из текстового файла (закомментировал - вызывает падение AVZ)
//SL.LoadFromFile(W_log);
//Result := (SL.IndexOf(#9+'ReturnValue = 0;') <> -1);
LoadFileToBuffer(W_log);
// Проверка наличия сигнатуры "ReturnValue = 0;"
Result := (SearchSign('52 65 74 75 72 6E 56 61 6C 75 65 20 3D 20 30 3B',0,0) >= 0);
// Чистим буфер
FreeBuffer;
DeleteFile(W_log);
end
else begin
// Если команда "замерзла", завершаем WMIC принудительно
TerminateProcessByName('wmic.exe');
Result := false;
end;
end;
var
msg : string;
begin
if CreateSR then
msg := 'Контрольная точка успешно создана.'
else
msg := 'Не удалось создать контрольную точку восстановления системы !!!';
MessageDLG(msg, mtInformation, mbOk, 0);
end.
Но кому я это рассказіваю. Все равно никто не слушает.
... У Вас тут кто-то учит писать
простые скрипты, а то у меня не получается?