Форум программистов «Весельчак У»
  *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

  • Рекомендуем проверить настройки временной зоны в вашем профиле (страница "Внешний вид форума", пункт "Часовой пояс:").
  • У нас больше нет рассылок. Если вам приходят письма от наших бывших рассылок mail.ru и subscribe.ru, то знайте, что это не мы рассылаем.
   Начало  
Наши сайты
Помощь Поиск Календарь Почта Войти Регистрация  
 
Страниц: [1]   Вниз
  Печать  
Автор Тема: запрет повторного запуска бат  (Прочитано 18322 раз)
0 Пользователей и 1 Гость смотрят эту тему.
Serguntii
Помогающий

ru
Offline Offline

« : 13-06-2014 13:23 » 

Подскажите плз как запретить повторный запуск бат скрипта?
Записан
Finch
Спокойный
Администратор

il
Offline Offline
Пол: Мужской
Пролетал мимо


« Ответ #1 : 13-06-2014 14:28 » 

Стандартное решение. Создать какой либо уникальный именнованный объект в системе.
Записан

Не будите спашяго дракона.
             Джаффар (Коша)
Dale
Блюзмен
Команда клуба

ru
Offline Offline
Пол: Мужской

WWW
« Ответ #2 : 13-06-2014 14:31 » 

Например, использовать вспомогательный файл в качестве семафора.

В самом начале скрипт проверяет наличие этого файла. Если есть, значит, копия уже выполняется, и следует немедленный выход.

Если файла нет, он немедленно создается, затем скрипт выполняет полезную работу и в конце удаляет файл. Важно обеспечить, чтобы файл удалялся всегда, даже если по ходу выполнения скрипта возникла фатальная ошибка. Иначе придется подчищать файл-семафор вручную.
Записан

Всего лишь неделя кодирования с последующей неделей отладки могут сэкономить целый час, потраченный на планирование программы. - Дж. Коплин.

Ходить по воде и разрабатывать программное обеспечение по спецификациям очень просто, когда и то, и другое заморожено. - Edward V. Berard

Любые проблемы в информатике решаются добавлением еще одного уровня косвенности – кроме, разумеется, проблемы переизбытка уровней косвенности. — Дэвид Уилер.
Serguntii
Помогающий

ru
Offline Offline

« Ответ #3 : 13-06-2014 14:37 » 

Создать файл не проблема а как удалить, если скрипт закрыли или убили через диспетчер задач?
Записан
Ochkarik
Команда клуба

ru
Offline Offline
Пол: Мужской

« Ответ #4 : 13-06-2014 15:21 » 

файл... а переменные окружения использовать?)
Записан

RTFM уже хоть раз наконец!  RTFM :[ ну или хотя бы STFW...
Dale
Блюзмен
Команда клуба

ru
Offline Offline
Пол: Мужской

WWW
« Ответ #5 : 13-06-2014 15:26 » 

Насчет переменных окружения есть некоторые сомнения по поводу их области видимости. Видимость файла глобальна без вариантов.
Записан

Всего лишь неделя кодирования с последующей неделей отладки могут сэкономить целый час, потраченный на планирование программы. - Дж. Коплин.

Ходить по воде и разрабатывать программное обеспечение по спецификациям очень просто, когда и то, и другое заморожено. - Edward V. Berard

Любые проблемы в информатике решаются добавлением еще одного уровня косвенности – кроме, разумеется, проблемы переизбытка уровней косвенности. — Дэвид Уилер.
Serguntii
Помогающий

ru
Offline Offline

« Ответ #6 : 13-06-2014 17:39 » 

Сейчас в голову пришла такая мысль. Если сделать утилтку которая будет запускать скрипт бат методом shellexecute (.....sw_hide)
В утилитке наверно будет проще проверить скрипт запущен или нет ?
« Последнее редактирование: 13-06-2014 17:43 от Serguntii » Записан
zubr
Гость
« Ответ #7 : 13-06-2014 18:34 » 

Если вариант программы, запускающей скрипт устраивает, то конечно shellexecute, WaitForSingleObject и как сказал Finch - CreateMutex

И лучше батник вообще на диске не хранить, а создавать из программы, чтобы у пользователя не было возможности его вручную запустить.
« Последнее редактирование: 13-06-2014 18:37 от zubr » Записан
Serguntii
Помогающий

ru
Offline Offline

« Ответ #8 : 13-06-2014 18:49 » 

Опишу весь алгоритм что делает скрипт, может что еще посоветуете , у меня опыта мало в этих делах.
1 проверяет наличие сети если нет ждет.
2 если сеть есть проверяет запущенна ли программа 1 если нет запускает. 
3 проверяет запущенна ли программа 2 если нет запускает.
4 проверяет запущенна ли программа 3 если нет запускает.
5 возвращается на пункт 1.
Записан
Dale
Блюзмен
Команда клуба

ru
Offline Offline
Пол: Мужской

WWW
« Ответ #9 : 13-06-2014 19:51 » 

Не проще использовать планировщик заданий? Настроить циклический запуск с достаточно коротким интервалом и запретом повторного запуска программы, и пускай сам выполняет всю работу.
Записан

Всего лишь неделя кодирования с последующей неделей отладки могут сэкономить целый час, потраченный на планирование программы. - Дж. Коплин.

Ходить по воде и разрабатывать программное обеспечение по спецификациям очень просто, когда и то, и другое заморожено. - Edward V. Berard

Любые проблемы в информатике решаются добавлением еще одного уровня косвенности – кроме, разумеется, проблемы переизбытка уровней косвенности. — Дэвид Уилер.
Serguntii
Помогающий

ru
Offline Offline

« Ответ #10 : 14-06-2014 03:59 » 

Скрипт можно перенести на другой компьютер, а настройки планировщика как перенести можно?
Записан
Finch
Спокойный
Администратор

il
Offline Offline
Пол: Мужской
Пролетал мимо


« Ответ #11 : 14-06-2014 04:29 » 

Serguntii, На другом компьютере ты скрипт тоже должен ручками запускать. Также и планировшик.
Записан

Не будите спашяго дракона.
             Джаффар (Коша)
zubr
Гость
« Ответ #12 : 14-06-2014 04:32 » 

Планировщик можно запускать программно. Есть утилита schtasks или at для запуска из под системы.
То есть сделать скрипт установщик, который настроит планировщик. Но его надо запустить только один раз на компе для установки настроек планировщика.
Записан
Serguntii
Помогающий

ru
Offline Offline

« Ответ #13 : 14-06-2014 04:49 » 

Цитата
На другом компьютере ты скрипт тоже должен ручками запускать. Также и планировшик.
В автозапуск его он должен крутиться все время.

Цитата
Планировщик можно запускать программно. Есть утилита schtasks или at для запуска из под системы.
То есть сделать скрипт установщик, который настроит планировщик. Но его надо запустить только один раз на компе для установки настроек планировщика.
Попробую разобраться с планировщиком.

Сделал запуск через ShellExecute но не запускается, что может быть? Путь до бат файла определяется правильно.
Еще вопрос как проверить в этом коде, скрипт уже работает что бы повторно его не запустить?

Код:
#include "stdafx.h"
#include "Windows.h"
#include <wchar.h>
#include <stdio.h>


int _tmain(int argc, _TCHAR* argv[])
{
LPWSTR cwd = (LPWSTR) calloc(sizeof(wchar_t), 512);
LPWSTR pathbat = (LPWSTR)  calloc(sizeof(wchar_t), 1024);
LPWSTR namebat =  L"StartProg.bat";

    GetCurrentDirectory(GetCurrentDirectory(0, NULL),cwd);
wsprintf(pathbat, L"%s\\%s", cwd, namebat);

wprintf(L"%s",pathbat);

HINSTANCE hReturnCode=ShellExecute(NULL, NULL, pathbat, NULL, NULL, SW_HIDE);
return 0;
}


« Последнее редактирование: 14-06-2014 05:07 от Serguntii » Записан
zubr
Гость
« Ответ #14 : 14-06-2014 05:36 » 

Цитата
Сделал запуск через ShellExecute но не запускается когда путь с пробелами, что можно сделать?
Еще вопрос как проверить в этом коде, скрипт уже работает что бы повторно его не запустить?
Путь поставить в кавычки.
А сделать лучше не через ShellExecute а через ShellExecuteEx (тогда есть возможность узнать когда процесс закрылся) или через CreateProcess.
Чтобы определить что уже работает можно заюзать CreateMutex. Вот пример кода:
Код:
     HANDLE hMutex = NULL;

     hMutex = CreateMutex(NULL, FALSE, L"MyMytexName");
     if(hMutex && (ERROR_ALREADY_EXISTS == GetLastError()))
     {                 
    CloseHandle(hMutex);       
   return;  //выходим из программы, так как уже один экземпляр запущен
     }

    STARTUPINFO si;
    PROCESS_INFORMATION pi;

    RtlZeroMemory(&si, sizeof(STARTUPINFO));
    si.cb = sizeof(STARTUPINFO);
    RtlZeroMemory(&pi, sizeof(PROCESS_INFORMATION));
    if(CreateProcess(batpath, NULL, NULL, NULL, FALSE, 0, NULL, NULL, &si, &pi))
   {
WaitForSingleObject(pi.hProcess, INFINITE); //ждем завершения скрипта
CloseHandle(pi.hThread);
CloseHandle(pi.hProcess);
    }
Записан
Serguntii
Помогающий

ru
Offline Offline

« Ответ #15 : 14-06-2014 05:56 » 

Еще бы спрятать окно  si.wShowWindow = SW_HIDE; не помогает. Хотя он и так задан RtlZeroMemory(&si, sizeof(STARTUPINFO));  SW_HIDE == 0

Добавлено через 14 минут и 25 секунд:
Спасибо вопрос решен все работает.
Код:
#include "stdafx.h"
#include "Windows.h"
#include <wchar.h>
#include <stdio.h>



int _tmain(int argc, _TCHAR* argv[])
{

ShowWindow(GetConsoleWindow(), SW_HIDE);
LPWSTR cwd = (LPWSTR) calloc(sizeof(wchar_t), 512);
LPWSTR pathbat = (LPWSTR)  calloc(sizeof(wchar_t), 1024);
LPWSTR namebat =  L"StartProg.bat";

GetCurrentDirectory(GetCurrentDirectory(0, NULL),cwd);
wsprintf(pathbat, L"%s\\%s", cwd, namebat);



HANDLE hMutex = NULL;

hMutex = CreateMutex(NULL, FALSE, L"StartScriptBatWater");
if(hMutex && (ERROR_ALREADY_EXISTS == GetLastError()))
{                 
CloseHandle(hMutex);       
return 0;  //выходим из программы, так как уже один экземпляр запущен
}

STARTUPINFO si;
PROCESS_INFORMATION pi;

RtlZeroMemory(&si, sizeof(STARTUPINFO));
si.cb = sizeof(STARTUPINFO);
RtlZeroMemory(&pi, sizeof(PROCESS_INFORMATION));

if(CreateProcess(pathbat, NULL, NULL, NULL, FALSE, NORMAL_PRIORITY_CLASS|CREATE_NO_WINDOW, NULL, NULL, &si, &pi))
{
WaitForSingleObject(pi.hProcess, INFINITE); //ждем завершения скрипта
CloseHandle(pi.hThread);
CloseHandle(pi.hProcess);
}


return 0;
}

« Последнее редактирование: 14-06-2014 06:13 от sergeyan » Записан
Страниц: [1]   Вверх
  Печать  
 

Powered by SMF 1.1.21 | SMF © 2015, Simple Machines