Версия для печати темы

Нажмите сюда для просмотра этой темы в обычном формате

Форум «Всё о Паскале» _ Ада и другие языки _ Создание и уничтожение процессов

Автор: Rocket 9.11.2008 21:23

Скажите пожалуйста, как создать и уничтожить процесс в ОС семейства Microsoft Windows? Знаю о существовании системного вызова CreateProcess(…), допускающего использование множества дополнительных параметров. Если возможно, то напишите пожалуйста текстовый пример использования CreateProcess(…).

Автор: volvo 9.11.2008 21:28

Вот простейший пример: http://www.firststeps.ru/mfc/winapi/r.php?131

Автор: Rocket 9.11.2008 21:37

Цитата(volvo @ 9.11.2008 17:28) *

Вот простейший пример: http://www.firststeps.ru/mfc/winapi/r.php?131


Почему-то у меня не создаётся процесс... И что за библиотека
#include "stdafx.h"
?

Автор: volvo 9.11.2008 21:43

Что значит "не создается"? Не появляется Notepad? А файл notepad.exe точно лежит там, где указано? У меня запустилось...

Цитата
И что за библиотека
Если у тебя не VC, можешь убрать эту строку... Это для MFC.

Автор: Rocket 9.11.2008 21:59

Цитата(volvo @ 9.11.2008 17:43) *

Что значит "не создается"? Не появляется Notepad? А файл notepad.exe точно лежит там, где указано? У меня запустилось...

Если у тебя не VC, можешь убрать эту строку... Это для MFC.

Да, не появляется программа, которую хочу запустить. Я запускаю другой exe-шник.

И вообще ряд ошибок возникает:
2 In file included from E:/Dev-Cpp/include/c++/3.4.2/backward/iostream.h:31, from J:\OsLab3.cpp

2 from J:\OsLab3.cpp

32:2 #warning This file includes at least one deprecated or antiquated header. Please consider using one of the 32 headers found in section 17.4.1.2 of the C++ standard. Examples include substituting the <X> header for the <X.h> header for C++ includes, or <iostream> instead of the deprecated header <iostream.h>. To disable this warning use -Wno-deprecated.

4 `main' must return `int'

In function `int main(...)':

9 [Warning] passing NULL used for non-pointer converting 6 of `BOOL CreateProcessA(const CHAR*, CHAR*, _SECURITY_ATTRIBUTES*, _SECURITY_ATTRIBUTES*, BOOL, DWORD, void*, const CHAR*, _STARTUPINFOA*, _PROCESS_INFORMATION*)'

Автор: volvo 9.11.2008 22:18

Цитата
И вообще ряд ошибок возникает:
Ну так сначала исправь ошибки а потом будешь говорить, получается у тебя что-нибудь или нет... Ты ж программу не откомпилировал, что ты хочешь запустить?

Вот это компилируется без предупреждений/ошибок, и прекрасно работает:
#include <windows.h>
#include <iostream>

using namespace std;

int main()
{
STARTUPINFO cif;
ZeroMemory(&cif,sizeof(STARTUPINFO));
PROCESS_INFORMATION pi;
if (CreateProcess("c:\\windows\\notepad.exe",NULL,
NULL,NULL,FALSE,0,NULL,NULL,& cif,& pi)==TRUE)
{
cout << "process" << endl;
cout << "handle " << pi.hProcess << endl;
Sleep(1000); // подождать
TerminateProcess(pi.hProcess,NO_ERROR); // убрать процесс
}
return 0;
}


Автор: Rocket 11.11.2008 4:27

Цитата(volvo @ 9.11.2008 18:18) *

Ну так сначала исправь ошибки а потом будешь говорить, получается у тебя что-нибудь или нет... Ты ж программу не откомпилировал, что ты хочешь запустить?

Вот это компилируется без предупреждений/ошибок, и прекрасно работает:
#include <windows.h>
#include <iostream>

using namespace std;

int main()
{
STARTUPINFO cif;
ZeroMemory(&cif,sizeof(STARTUPINFO));
PROCESS_INFORMATION pi;
if (CreateProcess("c:\\windows\\notepad.exe",NULL,
NULL,NULL,FALSE,0,NULL,NULL,& cif,& pi)==TRUE)
{
cout << "process" << endl;
cout << "handle " << pi.hProcess << endl;
Sleep(1000); // подождать
TerminateProcess(pi.hProcess,NO_ERROR); // убрать процесс
}
return 0;
}




Да, действительно работает прекрасно)
А вот как реализовать программу, которая запускала бы исполняемые файлы ( файлы с расширениями .exe, .bat, .cmd) из указанного в качестве параметра каталога. После завершения каждого запущенного процесса соответствующий исполняемый файл должен удаляться. В случае, если в указанном каталоге отсутствуют файлы, программа должна ожидать их появления. Учесть, что запуск файлов с расширениями .bat и .cmd может быть осуществлен только с помощью командного процессора cmd.exe.
?

Автор: volvo 11.11.2008 5:35

Искать в папке файлы с необходимыми расширениями (FindFirstFile/FindNextFile), в зависимости от расширения добавлять или нет к командной строке "cmd.exe", и запускать процесс... После запуска процесса ждать его завершения через WaitForSingleObject, а потом удалять файл...

Пробуй, что не получится - поможем smile.gif

Автор: Rocket 14.11.2008 21:03

Цитата(volvo @ 11.11.2008 1:35) *

Искать в папке файлы с необходимыми расширениями (FindFirstFile/FindNextFile), в зависимости от расширения добавлять или нет к командной строке "cmd.exe", и запускать процесс... После запуска процесса ждать его завершения через WaitForSingleObject, а потом удалять файл...

Пробуй, что не получится - поможем smile.gif

А где можно прочитать про эти функции (FindFirstFile/FindNextFile)? в интернете что-то не получается нарыть...а хотелось бы взглянуть на пример использования...

Автор: volvo 14.11.2008 21:12

Тебя что, на MSDN забанили? smile.gif
http://msdn.microsoft.com/en-us/library/aa364418(VS.85).aspx, там же в списке "See Also" есть и FindNextFile, и FindClose

Автор: Rocket 15.11.2008 2:14

Цитата(volvo @ 14.11.2008 17:12) *

Тебя что, на MSDN забанили? smile.gif
http://msdn.microsoft.com/en-us/library/aa364418(VS.85).aspx, там же в списке "See Also" есть и FindNextFile, и FindClose

Да тут чёрт голову сломит smile.gif
Вот что у меня получилось...конечно по большей части скорей не получилось, но всё же :

#include <iostream>
#include <io.h>
#include <windows.h>
#include <string.h>
#include <conio.h>
using namespace std;
void strdel(char *st)
{
for(int i=strlen(st)-1;st[i]!='\\';i--)
st[i]='\0';
}

int main()
{
_finddata_t data;
int x=-1,y;
char maska[]="E:\\abra\\*.exe";
char path[]="E:\\abra\\";


STARTUPINFO si={sizeof(si)};
PROCESS_INFORMATION pi;

ZeroMemory(&si, sizeof(si));

while(x==-1)
x=_findfirst(maska,&data);

y=x;
strcat(path,data.name);
cout <<"path: " <<path <<endl;
if(CreateProcess(path,NULL,NULL,NULL,false,0,NULL,NULL,&si,&pi))
{
Sleep(1000);

TerminateProcess(pi.hProcess,NO_ERROR);
cout <<endl;
DeleteFile(maska);
}
strdel(path);
cout <<"path: " <<path <<endl;

while(true)
{

x=_findnext(y,&data);
if(x==0)
{
strcat(path,data.name);

if(CreateProcess(path,NULL,NULL,NULL,false,0,NULL,NULL,&si,&pi))
{
Sleep(1000);
TerminateProcess(pi.hProcess,NO_ERROR);
DeleteFile(maska);
strdel(path);
}
}

}

return 0;
}

То есть я нахожу exe-шники, создаю процесс, но удалить не получается... В задании ещё что-то про командную строку сказано... Помогите пожалуйста довести программу до ума!

Автор: volvo 15.11.2008 2:59

Цитата
удалить не получается
- это не диагностика... Почему не получается? Что возвращает TerminateProcess?

    if(CreateProcess(path,NULL,NULL,NULL,false,0,NULL,NULL,& si, & pi))
{
Sleep(1000);

if(!TerminateProcess(pi.hProcess,NO_ERROR))
{
cout << "error code = " << GetLastError() << endl;
}
else cout << "process deleted" << endl;

cout <<endl;
DeleteFile(maska);
}
Что выдает?

Автор: Rocket 15.11.2008 3:22

Цитата(volvo @ 14.11.2008 22:59) *

- это не диагностика... Почему не получается? Что возвращает TerminateProcess?

    if(CreateProcess(path,NULL,NULL,NULL,false,0,NULL,NULL,& si, & pi))
{
Sleep(1000);

if(!TerminateProcess(pi.hProcess,NO_ERROR))
{
cout << "error code = " << GetLastError() << endl;
}
else cout << "process deleted" << endl;

cout <<endl;
DeleteFile(maska);
}
Что выдает?


Я не так выразился : не удаляется сам файл из папки. TerminateProcess срабатывает...

Автор: volvo 15.11.2008 3:30

То же самое (проверку на 0 и печать в этом случае кода ошибки) делай для DeleteFile, результат - в студию; почти все WinAPI функции возвращают 0 в случае неудачи, и код ошибки берется через GetLastError.

Только учти, что при удалении файла есть особые случаи:
1) если файл read-only, то перед удалением надо этот атрибут снять;
2) для удаления файла у тебя должны быть права на удаление этого файла, либо права на удаление потомка для той папки, в которой файл лежит...

Автор: Rocket 15.11.2008 3:39

Цитата(volvo @ 14.11.2008 23:30) *

То же самое (проверку на 0 и печать в этом случае кода ошибки) делай для DeleteFile, результат - в студию; почти все WinAPI функции возвращают 0 в случае неудачи, и код ошибки берется через GetLastError.

Только учти, что при удалении файла есть особые случаи:
1) если файл read-only, то перед удалением надо этот атрибут снять;
2) для удаления файла у тебя должны быть права на удаление этого файла, либо права на удаление потомка для той папки, в которой файл лежит...


Так, номер ошибки : 2 во всех случаях...

Автор: Rocket 15.11.2008 4:34

Цитата(volvo @ 14.11.2008 23:30) *


Только учти, что при удалении файла есть особые случаи:
1) если файл read-only, то перед удалением надо этот атрибут снять;
2) для удаления файла у тебя должны быть права на удаление этого файла, либо права на удаление потомка для той папки, в которой файл лежит...

Как все эти операции проделать?

Автор: volvo 15.11.2008 5:46

Эти операции здесь ни при чем. Ошибка №2 - это ERROR_FILE_NOT_FOUND... Вот кусок программы, которая у меня прекрасно нашла все требуемые файлы и удалила их:

int main()
{
WIN32_FIND_DATA wfd;

char *maska = "G:\\T\\*.txt";
char *path = "G:\\T\\";
HANDLE hf = NULL;

STARTUPINFO si = { sizeof(si) };
PROCESS_INFORMATION pi;

ZeroMemory(&si, sizeof(si));

if ((hf = FindFirstFile(maska, &wfd)) == INVALID_HANDLE_VALUE)
return 1; // ошибка, нет нужных файлов

do
{
if (!(wfd.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)) {
char full_name[MAX_PATH];
strcpy(full_name, path);
strcat(full_name, wfd.cFileName);

if(CreateProcess(full_name, NULL, NULL, NULL, false, 0, NULL, NULL,& si,& pi)) {
// ...
}
cout << full_name << endl;
DeleteFile(full_name);
}
} while (FindNextFile(hf, &wfd));
FindClose (hf);

return 0;
}
Добавь туда все, что тебе надо после запуска процесса, должно работать...

Автор: Rocket 18.11.2008 22:45

Цитата(volvo @ 15.11.2008 1:46) *

Эти операции здесь ни при чем. Ошибка №2 - это ERROR_FILE_NOT_FOUND... Вот кусок программы, которая у меня прекрасно нашла все требуемые файлы и удалила их:
int main()
{
WIN32_FIND_DATA wfd;

char *maska = "G:\\T\\*.txt";
char *path = "G:\\T\\";
HANDLE hf = NULL;

STARTUPINFO si = { sizeof(si) };
PROCESS_INFORMATION pi;

ZeroMemory(&si, sizeof(si));

if ((hf = FindFirstFile(maska, &wfd)) == INVALID_HANDLE_VALUE)
return 1; // ошибка, нет нужных файлов

do
{
if (!(wfd.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)) {
char full_name[MAX_PATH];
strcpy(full_name, path);
strcat(full_name, wfd.cFileName);

if(CreateProcess(full_name, NULL, NULL, NULL, false, 0, NULL, NULL,& si,& pi)) {
// ...
}
cout << full_name << endl;
DeleteFile(full_name);
}
} while (FindNextFile(hf, &wfd));
FindClose (hf);

return 0;
}
Добавь туда все, что тебе надо после запуска процесса, должно работать...

Большое спасибо за помощь, всё отлично работает! good.gif