Модераторы: feodorv, GremlinProg, xvr, Fixin
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> cmd в новом окне 
:(
    Опции темы
Alexandr87
Дата 11.9.2007, 13:49 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


дыкий псых
***


Профиль
Группа: Завсегдатай
Сообщений: 1459
Регистрация: 27.11.2004
Где: Алматы, Казахстан

Репутация: нет
Всего: 39



Делаю так
Код

            sprintf(cmdLine, "cmd.exe /k  tokentester.exe %d | tee ./log.txt", slotID);
            WinExec(cmdLine, 0);

Приложение tokentester.exe - консольное.
Мне необходимо, чтобы когда выполняется эта команда - открывалось новое cmd окно - и туда соотвественно вываливался результат работы. Как реализованить. (tee- программа, которя ретранслирует поток стандартного входа в поток стандартного выхода и в обозначенный параметром файл)
PM Jabber   Вверх
_hunter
Дата 11.9.2007, 14:01 (ссылка) |    (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Участник Клуба
Сообщений: 8564
Регистрация: 24.6.2003
Где: Europe::Ukraine:: Kiev

Репутация: 13
Всего: 98



используй CreateProcess и передай CREATE_NEW_CONSOLE в dwCreationFlags 


--------------------
Tempora mutantur, et nos mutamur in illis...
PM ICQ   Вверх
Alexandr87
Дата 12.9.2007, 12:46 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


дыкий псых
***


Профиль
Группа: Завсегдатай
Сообщений: 1459
Регистрация: 27.11.2004
Где: Алматы, Казахстан

Репутация: нет
Всего: 39



Спасибо, правда с использованием этой функции получилось и без этого флага.
PM Jabber   Вверх
Alexandr87
Дата 12.9.2007, 14:08 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


дыкий псых
***


Профиль
Группа: Завсегдатай
Сообщений: 1459
Регистрация: 27.11.2004
Где: Алматы, Казахстан

Репутация: нет
Всего: 39



ммм. появился еще вопрос.

"cmd.exe /с  tokentester.exe %d | tee ./log.txt"

Если я делаю такую комманду она выполянется , но при этом, возвращаемый код, будет 0, т.е. cmd.exe отрабатывает и возвращает свой код, мне нужно получить код возврата программы tokentester.exe. Как?
PM Jabber   Вверх
586
Дата 12.9.2007, 15:10 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 2243
Регистрация: 8.5.2006

Репутация: 39
Всего: 146



"cmd.exe /с  tokentester.exe %d | tee ./log.txt & exit %%errorlevel%%"

Это сообщение отредактировал(а) 586 - 12.9.2007, 16:03
PM   Вверх
Alexandr87
Дата 13.9.2007, 11:48 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


дыкий псых
***


Профиль
Группа: Завсегдатай
Сообщений: 1459
Регистрация: 27.11.2004
Где: Алматы, Казахстан

Репутация: нет
Всего: 39



586, 
чето не работает? у вас получается?

PM Jabber   Вверх
SenkraD
Дата 13.9.2007, 12:47 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 933
Регистрация: 3.2.2006
Где: Украина::Киев

Репутация: 4
Всего: 23



Alexandr87, а зачем ты запускаеш tokentester.exe через командную строку?
что нельзя напрямую запустить её через CreateProcess?



--------------------
 Имеющий язык - да не убоится спросить! 
user posted image
PM MAIL ICQ   Вверх
Alexandr87
Дата 13.9.2007, 12:55 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


дыкий псых
***


Профиль
Группа: Завсегдатай
Сообщений: 1459
Регистрация: 27.11.2004
Где: Алматы, Казахстан

Репутация: нет
Всего: 39



SenkraD, а вы попробуйте smile
tokentester - то конечно запуститься, а вот, то что надо, выполнено не будет, я  имею ввиду:  "tokentester.exe %d | tee ./log.txt"
Я так полагаю что CreateProcess явно не поймет такой конструкции.
PM Jabber   Вверх
SenkraD
Дата 13.9.2007, 13:08 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 933
Регистрация: 3.2.2006
Где: Украина::Киев

Репутация: 4
Всего: 23



Alexandr87,  ну вот модифицированный пример с MSDN:

Код

#include <windows.h>
#include <stdio.h>

void main( VOID )
{
    STARTUPINFO si;
    PROCESS_INFORMATION pi;

    ZeroMemory( &si, sizeof(si) );
    si.cb = sizeof(si);
    ZeroMemory( &pi, sizeof(pi) );

    // Start the child process. 
    if( !CreateProcess( NULL,  TEXT("tokentester.exe %d | tee ./log.txt"), NULL, NULL, FALSE, CREATE_NEW_CONSOLE, NULL, NULL, &si, &pi )
    {
        printf( "CreateProcess failed (%d).\n", GetLastError() );
        return;
    }

    // Wait until child process exits.
    WaitForSingleObject( pi.hProcess, INFINITE );

    // Close process and thread handles. 
    CloseHandle( pi.hProcess );
    CloseHandle( pi.hThread );
}


А вот, может  лишниее уже, часть главы с Рхтерра (вообщем, руский перевод MSDN + коментари и нюансы)
Код

Функция CreateProcess 
Процесс создается при вызове Вашим приложением функции CreateProcess 

BOOL CreateProcess( 
PCTSTR pszApplicationName, 
PTSTR pszCommandLine, 
PSFCURITY_ATTRIBUTES psaProcess, 
PSECURITY_ATTRIBUTES psaThiead, 
BOOL bInheritHandles, 
DWORD fdwCreate, 
PVOID pvEnvironment,
PCTSTR pszCurDir, 
PSTARTUPINFO psiStartInfo, 
PPROCESS_INFORMATION ppiProcInfo);

Когда поток в приложении вызывает CreateProcess, система создает объект ядра "процесс" с начальным значением счстчика числа его пользователей, равным 1. Этот объект — не сам процесс, а компактная структура данных, через которую операци онная система управляет процессом. (Объект ядра "процесс" следует рассматривать как структуру данных со статистической информацией о процессе.) Затем система создает для нового процесса виртуальное адресное пространство и загружает в него код и данные как для исполняемого файла, тaк и для любых DLL (если таковые требу ются). 

Далее система формирует объект ядра "поток" (со счетчиком, равным 1) для пер вичного потоки нового процесса. Как и в первом случае, объект ядра "поток" — это компактная структура данных, через которую система управляет потоком. Первичный поток начинает с исполнения стартового кода из библиотеки С/С++, который в ко нечном счете вызывает функцию WinMain, wWinMain, main или wmain в Вашей про грамме. Если системе удастся создать новый процесс и его первичный поток, Create Process вернет TRUE 

NOTE: 
CreateProcess возвращает TRUE до окончательной инициализации процесса. Это означает, что на данном этапе загрузчик операционной системы еще нс искал все необходимые DLL. Если он не сможет найти хотя бы одну из DLL или корректно провести инициализацию, процесс завершится. Но, поскольку Create Process уже вернула TRUE, родительский процесс ничего не узнает об этих про блемах. 

На этом мы закончим общее описание и перейдем к подробному рассмотрению параметров функции CreateProcess 

Параметры pszApplicationName и pszCommandLine 
Эти параметры определяют имя исполняемого файла, которым будет пользоваться новый процесс, и командную строку, передаваемую этому процессу. Начнем cpszCom mandLine. 

NOTE 
Обратите внимание на тип параметра pszCommandLine: PTSTR. Он означает, что CreateProcess ожидает передачи адреса строки, которая не является констан той Дело в том, что CreateProcess в процессе своего выполнения модифици рует переданную командную строку, но перед возвратом управления восста навливает ее. 

Это очень важно, если командная строка содержится в той части образа Вашего файла, которая предназначена только для чтения, возникнет ошибка доступа. Например, следующий код приведет к такой ошибке, потому что Visual С++ 6.0 поместит строку "NOTEPAD" в память только для чтения: 

STARTUPINFO si = { sizeof(si) };
PROCESS_INFORMATION pi; 
CreateProcess(NULL, TEXT("NOTEPAD"), NULL, NULL, FALSE, 0, NULL. NULL, &si, &pi);

Когда CreateProcess попытается модифицировать строку, произойдет ошиб ка доступа. (В прежних версиях Visual C++ эта строка была бы размещена в памяти для чтения и записи, и вызовы CreateProcess не приводили бы к ошиб кам доступа.) 


Лучший способ решения этой проблемы — перед вызовом CreateProcess ко пировать константную строку во временный буфер: 

STARTUPINFO si = { sizeof(si) }; 
PROCESS_INFORMATION pi; 
TCHAR szComrnandLine[] = TEXT("NOTEPAD"); 
CreateProcess(NULL, szCommandLine, NULL, NULL, FALSE, 0, NULI, NULL, &si, &pi);

Возможно, Вас заинтересуют ключи /Gf и /GF компилятора Visual C++, ко торые исключают дублирование строк и запрещают их размещение в области только для чтения. (Также обратите внимание на ключ /ZI, который позволяет задействовать отладочную функцию Edit & Continue, поддерживаемую Visual Studio, и подразумевает активизацию ключа /GF.) В общем, лучшее, что може те сделать Вы, — использовать ключ /GF или создать временный буфер. А еще лучше, если Microsoft исправит функцию CreateProcess, чтобы та не морочила нам голову. Надеюсь, в следующей версии Windows так и будет. 

Кстати, при вызове ANSI-версии CreateProcess в Windows 2000 таких про блем нет, поскольку в этой версии функции командная строка копируется во временный буфер (см. главу 2) 

Параметр pszCommandLme позволяет указать полную командную строку, исполь зуемую функцией CreateProcess при создании нового процесса. Разбирая эту строку, функция полагает, что первый компонент в ней представляет собой имя исполняе мого файла, который Вы хотите запустить. Если в имени этого файла не указано рас ширение, она считает его EXE. Далее функция приступает к поиску заданного файла и делает это в следующем порядке: 

Каталог, содержащий ЕХЕ-файл вызывающего процесса. 
Текущий каталог вызывающего процесса. 
Системный каталог Windows. 
Основной каталог Windows. 
Каталоги, перечисленные в переменной окружения PATH. 
Конечно, если в имени файла указан полный путь доступа, система сразу обраща ется туда и не просматривает эти каталоги. Найдя нужный исполняемый файл, она создает новый процесс и проецирует код и данные исполняемого файла на адресное пространство этого процесса Затем обращается к процедурам стартового кода из библиотеки С/С++. Тот в свою очередь, как уже говорилось, анализирует командную строку процесса и передает (w)WinMain адрес первого (за именем исполняемого фай ла) аргумента как pszCmdLine. 

Все, о чем я сказал, произойдет, только если параметр pszApplicationName равен NULL (что и бывает в 99% случаев). Вместо NULL можио передать адрес строки с име нем исполняемого файла, который надо запустить. Однако тогда придется указать не только его имя, но и расширение, поскольку в этом случае имя не дополняется рас ширением EXE автоматически. CreateProcess предполагает, что файл находится в те кущем каталоге (если полный путь не задан). Если в текущем каталоге файла нет, функция не станет искать его в других каталогах, и на этом все закончится 

Но даже при указанном в pszApplicationName имени файла CreateProcess все равно передает новому процессу содержимое параметра pszCommandLine как командную строку. Допустим, Вы вызвали CreateProcess так: 

// размещаем строку пути в области памяти для чтения и записи 
TCHAR szPath[] = TEXT("WORDPAD README.TXT"); 

// порождаем новый процесс 
CreateProcess(TEXT("C:\\WINNr\\SYSrEM32\\NOTEPAD EXE"), szPath ); 

Система запускает Notepad, а в его командной строке мы видим "WORDPAD README.TXT". Странно, да? Но так уж она работает, эта функция CreateProcess. Упо мянутая возможность, которую обеспечивает пареметр pszApplicationName, на самом деле введена в CreateProcess для поддержки подсистемы POSIX в Windows 2000. 

Параметры psaProcess, psaThread и blnheritHandles 
Чтобы создать новый процесс, система должна сначала создать объекты ядра "про цесс" и "поток" (для первичного потока процесса). Поскольку это объекты ядра, ро дительский процесс получает возможность связать с ними атрибуты защиты. Пара метры psaProcess и psaThread позволяют определить нужные атрибуты защиты для объектов "процесс" и "поток" соответственно. В эти параметры можно занести NULL, и система закрепит за данными объектами дескрипторы защиты по умолчанию. В качестве альтернативы можно объявить и инициализировать две структуры SECU RITY_ATTRIBlITES; тем самым Вы создадите и присвоите объектам "процесс" и "по ток" свои атрибуты защиты. 

Структуры SECURITY_ATTRIBUTES для параметров psaProcess wpsaTbread исполь зуются и для того, чтобы какой-либо из этих двух объектов получил статус наследуе мого любым дочерним процессом. (О теории, на которой построено наследование описателей объектов ядра, я рассказывал в главе 3.) 

Короткая программа на рис. 4-2 демонстрирует, как наследуются описатели объек тов ядра. Будем считать, что процесс А порождает процесс В и заносит в параметр psaProcess адрес структуры SECURITY_ATTRIBUTES, в которой элемент blnheritHandle установлен как TRUE. Одновременно параметр psaThread указывает на другую струк туру SECURITY_ATTRIBUTES, в которой значение элемента bInheritHandle — FALSE. 

Создавая процесс В, система формирует объекты ядра "процесс" и "поток", а за тем — в структуре, на которую указывает параметрppiProcInfo (о нем поговорим поз же), — возвращает их описатели процессу А, и с этого момента тот может манипули ровать только что созданными объектами "процесс" и "поток". 

Теперь предположим, что процесс А собирается вторично вызвать функцию Create Process, чтобы породить процесс С. Сначала ему нужно определить, стоит ли предос тавлять процессу С доступ к своим объектам ядра. Для этого используется параметр blnberitHandles, Если он приравнен TRUE, система передаст процессу С все наследуе мые описатели В этом случае наследуется и описатель объекта ядра "процесс" про цесса В. А вот описатель объекта "первичный поток" процесса В не наследуется ни при каком значении bInberitHandles. Кроме того, если процесс А вызывает Create Process, передавая через параметр blnberitHandles значение FALSE, процесс С не насле дует никаких описателей, используемых в данный момент процессом А. 

Параметр fdwCreate 
Параметр fdwCreate определяет флаги, влияющие на то, как именно создается новый процесс Флаги комбинируются булевым оператором OR. 

Флаг DEBUG_PROCESS даст возможность родительскому процессу проводить отладку дочернего, а также всех процессов, которые последним могут быть порождены Если этот флаг установлен, система уведомляет родительский про цесс (он теперь получает статус отладчика) о возникновении определенных событий в любом из дочерних процессов (а они получают статус отлаживае мых). 
Флаг DEBUG_ONLY_THIS_PROCESS аналогичен флагу DEBUG_PROCESS с тем исключением, что заставляет систему уведомлять родительский процесс о воз никновении специфических событий только в одном дочернем процессе — его прямом потомке. Тогда, если дочерний процесс создаст ряд дополнительных, отладчик уже нс уведомляется о событиях, "происходящих" в них. 
Флаг CREATE_SUSPENDED позволяет создать процесс и в то же время приоста новить его первичный поток Это позволяет родительскому процессу модифи цировать содержимое памяти в адресном пространстве дочернего, изменять приоритет его первичного потока или включать этот процесс в задание (job) до того, как он получит шанс на выполнение. Внеся нужные изменения в до черний процесс, родительский разрешает выполнение его кода вызовом фун кции ResumeThread (см. главу 7). 
Флаг DFTACHED_PROCESS блокирует доступ процессу, инициированному кон сольной программой, к сопданному родительским процессом консольному окну и сообщает системе, что вывод следует перенаправить в новое окно CUI процесс, создаваемый другим CUI-процессом, по умолчанию использует кон сольное окно родительского процесса (Вы, очевидно, заметили, что при за пуске компилятора С из командного процессора новое консольное окно не создается, весь его вывод "подписывается" в нижнюю часть существующего консольного окна ) Таким образом, этот флаг заставляет новый процесс пере направлять свой вывод в новое консольное окно 
Флаг CREATE_NEW_CONSOLE приводит к созданию нового консольного окна для нового процесса. Имейте в виду, что одновременная установка флагов CREATE_NEW_CONSOLE и DETACHED_PROCESS недопустима. 
Флаг CREATE_NO_WINDOW не дает создавать никаких консольных окон для данного приложения и тем самым позволяет исполнять его без пользователь ского интерфейса. 
Флаг CREATE_NEW_PROCESS_GROUP служит для модификации списка процес сов, уведомляемых о нажатии клавиш Ctrl+C и Ctrl+Break Если в системе од новременно исполняется несколько CUI-процессов, то при нажагии одной из упомянутых комбинаций клавиш система уведомляет об этом только процес сы, включенные в группу. Указав этот флаг при создании нового СUI-процес ca, Вы создаете и новую группу 
Флаг CREATE_DEFAULT_ERROR_MODE сообщает системе, чтo новый процесс не должен наследовать режимы обработки ошибок, установленные в родитель ском (см. раздел, где я рассказывал о функции SetErrorMode). 
Флаг CREATE_SEPARATE_WOW VDM полезен только при запуске 16-разрядно го Wmdows-приложения в Windows 2000. Если он установлен, система созда ет отдельную виртуальную DOS-машину (Virtual DOS-machine, VDM) и запус кает 16-разрядное Windows-приложение именно в ней (По умолчанию все 16 разрядные Windows-приложения выполняются в одной, общей VDM.) Выпол нение приложения в отдельной VDM дает большое преимущество, "рухнув", приложение уничтожит лишь эту VDM, а программы, выполняемые в других VDM, продолжат нормальную работу. Кроме того, 16-разрядные Windows-при ложения, выполняемые в раздельных VDM, имеют и раздельные очереди вво да. Эго значит, что, если одно приложение вдруг "зависнет", приложения в других VDM продолжат прием ввода. Единственный недостаток работы с нес колькими VDM в том, что каждая из них требуеч значительных объемов физи ческой памяти. Windows 98 выполняет все 16-разрядные Windows-приложения только в одной VDM, и изменить тут ничего нельзя. 
Флаг CREATE_SHARED_WOW_VDM полезен только при запуске 16-разрядного Windows-приложения в Windows 2000. По умолчанию все 16-разрядные Windows-приложения выполняются в одной VDM, ссли только не указан флаг CREATE_SEPARATEWOW_VDM. Однако стандартное пoвeдeниeWindows 2000 можно изменить, присвоив значение "yes" параметру DefaultSeparateVDM в paздeлe HKEY_LOCAL_MACHINE\System\CurгentControlSet\Contгol\WOW.(Пoc ле модификации этого параметра систему надо перезагрузить.) Установив зна чение "yes", но указав флаг CREATE_SHARED_WOW_VDM, Вы вновь заставите Windows 2000 выполнять все 16-разрядные Windows-приложения в одной VDM. 
Флаг CREATE_UNICODE_ENVIRONMENT сообщает системе, что блок перемен ных окружения дочернего процесса должен содержать Unicode-символы. По умолчанию блок формируется на основе ANSI-символов 
Флаг CREATE_FORCEDOS заставляет систему выполнять программу MS-DOS, встроенную в 16-разрядное приложение OS/2 
Флаг CREATE_BREAKAWAY_FROM_JOB позволяет процессу, включенному в за дание, создать новый процесс, отделенный от этого задания (см. главу 5). 
Параметр fdwCreate разрешает задать и класс приоритета процесса Однако это необязательно и даже, как правило, нс рекомендуется, система присваивает новому процессу класс приоритета по умолчанию. Возможные классы приоритета перечис лены в следующей таблице. 

Класс приоритета 
 Флаговый идентификатор 
 
Idle (простаивающий) 
 IDLE_PRIORITY_CLASS 
 
Below normal (ниже обычного) 
 BELOW_NORMAL_PRIORITY_CLASS 
 
Normal (обычный) 
 NORMAL PRIORITY CLASS 
 
Above normal (выше обычного) 
 ABOVE_NORMAL_PRIORITY_CLASS 
 
High (высокий) 
 HIGH_PRIORITY_CLASS 
 
Realtime (реального времени) 
 REALTIME_PRIORITY_CLASS 
 

Классы приоритета влияют на распределение процессорного времени междупро цессами и их потоками. (Подробнее на эту тему см. главу 7.) 

NOTE 
Классы приоритета BELOW_NORMAL_PRIORITY_CLASS и ABOVE_NORMAL_ PRIORITY_CLASS введены лишь в Windows 2000; они не поддерживаются в Win dows NT 4.0, Windows 95 или Windows 98. 

Параметр pvEnvironment 
Параметр pvEnvironment указывает на блок памяти, хранящий строки переменных окружения, которыми будет пользоваться новый процесс. Обычно вместо этого па раметра передается NULL, в результате чего дочерний процесс наследует строки пе рсмснных окружения от родительского процесса. В качестве альтернативы можно вызвать функцию GetEnvironmentStrings 

PVOID GetEnvironmentStrings(); 

Она позволяет узнать адрес блока памяти со строками переменных окружения, используемых вызывающим процессом. Полученный адрес можно занести в параметр pvEnvironment функции CreateProcess. (Именно это и делает CreateProcess, если Вы передаете ей NULL вместо pvEnvironment.) Если этот блок памяти Вам больше не ну жен, освободите его, вызнав функцию FreeEnvironmentStrings: 

BOOL FreeEnvironmentStrings(PTSTR pszEnvLronmenLBlock); 

Параметр pszCurDir 
Он позволяет родительскому процессу установить текущие диск и каталог для дочер него процесса. Если его значение — NULL, рабочий каталог нового процесса будет тем же, что и у приложения, его породившего. А если он отличен от NULL, то должен ука зывать на строку (с нулевым символом в конце), содержащую нужный диск и каталог. Заметьте, что в путь надо включать и букву диска. 

Параметр psiStartlnfo 
Этот параметр указывает на структуру STARTUPINFO: 

typedef struct _STARTUPINFO { 
DWORD cb; 
PSTH lpReserved; 
PSTR lpDesktop; 
PSTR lpTitle; 
DWORD dwX; 
DWORD dwY; 

DWORD dwXSize; 
DWORD dwYSize; 
DWORD dwXCountChars; 
DWORD dwYCountChars; 
DWORD dwFillAttribute; 
DWORD dwFlags; 
WORD wShowWindOw; 
WORD cbReserved2; 
PBYTE lpReserved2; 
HANDLE hStdInput; 
HANDLE hStdOutput; 
HANDLE hStdError; 
} STARTUPINFO, *LPSTARTUPINFO; 

Элементы структуры STARTUPINFO используются Windows-функциями при созда нии нового процесса. Надо сказать, что большинство приложений порождает процес сы с атрибутами по умолчанию Но и в этом случае Вы должны инициализировать все элементы структуры STARTUPINFO хотя бы нулевыми значениями, а в элемент сb — заносить размер этой структуры: 

STARTUPINFO si = { sizeof(si) }; CreateProcess(.. , &si, ...}; 

К сожалению, разработчики приложений часто забывают о необходимости ини циализации этой структуры. Если Вы не обнулите ее элементы, в них будет содержать ся мусор, оставшийся в стеке вызывающего потока. Функция CreateProcess, получив такую структуру данных, либо создаст новый процесс, либо нет — все зависит от того, что именно окажется в этом мусоре. 

Когда Вам понадобится изменить какие-то элементы структуры, делайте это пе ред вызовом CreateProcess. Все элементы зтой структуры подробно рассматриваются в таблице 4-3- Но заметьте, что некоторые элементы имеют смысл, только если до чернее приложение создает перекрываемое (overlapped) окно, а другие — если это приложение осуществляет ввод-вывод на консоль 

Элемент 
 Окно или консоль 
 Описание 
 
cb 
 То и другое
 Содержит количество байтов, занимаемых структу рой STARTUPINFO. Служит для контроля версий — на тот случай, если Microsoft расширит эту структуру в будущем Программа должна инициализировать cb как sizeof(STARTUPINFO) 
 
lpReserved 
 То и другое 
 Зарезервирован Инициализируйте как NULL. 
 
IpDesktop 
 То и другое 
 Идентифицирует имя рабочего стола, на котором за пускается приложение Если указанный рабочий стол существует, новый процесс сразу же связывается с ним. В ином случае система сначала создает рабочий стол с атрибутами по умолчанию, присваивает ему имя, указанное в данном элементе структуры, и свя зываем его с новым процессом. Если IpDesktop равен NULL (что чаще всего и бывает), процесс связывается с текущим рабочим столом. 
 
IpTitle 
 Консоль 
 Определяет заголовок консольного окна. Если IpTitle — NULL, в заголовок выводится имя исполняе мого файла. 
 

Таблица 4-3. Элементы структуры STARTUPINFO 

Элемент 
 Окно или консоль 
 Описание 
 
dwX 

dwY 
 То и другое 
 Указывают х- и j'-координаты (в пикселах) окна приложения Эти координаты используются, только если дочерний процесс создаст свое первое перекры ваемое окно с идентификатором CW_USEDEFAULT в параметре х функции CreateWindow. В приложениях, создающих консольные окна, данные элементы опре деляют верхний левый угол консольною окна. 
 
dwXSize 
dwYSize 
 То и другое 
 Определяют ширину и высоту (в пикселах) окна приложения. Эти значения используются, только если дочерний процесс создает свое первое перекрывае мое окно с идентификатором CW_USEUEFAULT в параметре nWtdth функции CreateWindow В приложениях, создающих консольные окна, данные элементы определяют ширину и высоту консольного окна 
 
dwXCountChars dwYCountChars 
 Консоль
 Определяют ширину и высоту (в символах) консольных окон дочернего процесса 
 
dwFillAttnbute
 Консоль
 Задает цвет текста и фона в консольных окнах дочернего процесса 
 
dwFlags 
 То и другое 
 См ниже и следующую таблицу 
 
wSbowWtndow 
 Окно 
 Определяет, как именно должно выглядеть первое перекрываемое окно дочернего процесса, если приложение при первом вызове функции ShowWindow передает в параметре nCmdSbow идентификаюр SW_SHOWDEFAULT. В этот элеменn можно записать любой из идентификаторов типа SW_*, обычно используемых при вызове SbowWindoiv. 
 
cbReserved2 
 То и друюс 
 Зарезервирован Инициализируйте как 0. 
 
lpReserved2 
 То и друюс 
 Зарезервирован. Инициализируйте как NULL. 
 
hStdlnput 
hStdOutlput 
bStdError 
 Консоль 
 Определяют описатели буферов для консольного ввода-вывода. По умолчанию bStdlnpitt идентифицирует буфер клавиатуры, a bStdOutput и bStdError — буфер консольного окна 
 

Теперь, как я и обещал, обсудим элемент dwFlags. Оп содержит набор флагов, по зволяющих управлять созданием дочернего процесса. Большая часть флагов просто сообщает функции CreateProcess, содержат ли прочие элементы структуры START UPINFO полезную информацию или некоторые из них можно игнорировать. Список допустимых флагов приведен в следующей таблице. 

Флаг 
 Описание 
 
STARTF_USESIZE 
 Заставляет использовать элементы divSize и dwYSize 
 
STARTF_USESHOWWINDOW 
 Заставляет использовать элемент wShowWindow 
 
STARTF_USEPOSITION 
 Заставляет использовать элементы dwX и dwY 
 
STARTF_USECOTUNTCHARS 
 Заставляет использовать элементы dwXCountChars и dwYCountCbars 
 
STARTF_USEFILLATTRIBUTE 
 Заставляет использовать элемент dwFillAttnbute 
 
STARTF_USESTDHANDLES 
 Заставляет использовать элементы hStdlnput, hStdOutput и bStdError 
 
Флаг 
 Описание 
 
STARTF_RUN_FULLSCREEN 
 Приводит к тому, что консольное приложение на компью тере с процессором типа х86 запускается в полноэкран ном режиме 
 

Два дополнительных флага — STARTF_FORCEONFEEDBACK и STARTF_FORCEOFF FEEDBACK — позволяют контролировать форму курсора мыши в момент запуска но вого процесса. Поскольку Windows поддерживает истинную вытесняющую многоза дачность, можно запустить одно приложение и, пока оно инициализируется, пора ботать с другой программой. Для визуальной обратной связи с пользователем функ ция CreateProcess временно изменяет форму системного курсора мыши: 

Курсор такой формы подсказывает: можно либо подождать чего-нибудь, что вот вот случится, либо продолжить работу в системе. Если же Вы укажете флаг STARTF_ FORCEOFFFEEDBACK, CreateProcess не станет добавлять "песочные часы" к стандарт ной стрелке. 

Флаг START_FFORCEONFEEDBACK заставляет CreateProcess отслеживать инициали зацию нового процесса и в зависимости от результата проверки изменять форму кур сора. Когда функция CreateProcess вызывается с этим флагом, курсор преобразуется в "песочные часы" Если спустя две секунды от нового процесса не поступает GUI-вы зов, она восстанавливает исходную форму курсора 

Если же в течение двух секунд процесс все же делает GUI-вызов, CreateProcess ждет, когда приложение откроет свое окно. Это должно произойти в течение пяти секунд после GUI-вызова Если окно не появилось, CreateProcess восстанавливает курсор, а появилось — сохраняет его в виде "песочных часов" еще на пять секунд Как только приложение вызовет функцию GetMessage, сообщая тeм самым, что оно закончило инициализацию, CreateProcess немедленно сменит курсор на стандартный и прекра тит мониторинг нового процесса. 

В заключение раздела — несколько слов об элементе wShowWindow структуры STARTUPINFO. Этот элемент инициализируется значением, которое Вы передаете в (w)WinMain через ее последний параметр, nCmdShoiv. Он позволяет указать, в каком виде должно появиться главное окно Вашею приложения В качестве значения ис пользуется один из идентификаторов, обычно передаваемых в ShowWindow (чаще всего SW_SHOWNORMAL или SW_SHOWMINNOACTIVE, но иногда и SW_SHOW DEFAULT). 

После запуска программы из Explorer ее функция (w)WinMain вызывается с SW_SHOWNORMAL в параметре nCmdShow Если же Вы создаете для нее ярлык, то можете указать в его свойствах, в каком виде должно появляться ее главное окно. На рис. 4-3 показано окно свойств для ярлыка Notepad. Обратите внимание на список Run, в котором выбирается начальное состояние окна Notepad. 

Когда Вы активизируете этот ярлык из Explorer, последний создает и инициали зирует структуру STARTUPINFO, a затем вызывает CreateProcess. Это приводит к запус ку Notepad, а его функция (w)WtnMam получаст SW_SIHOWMINNOACTIVE в параметре nCmdSbow, 

Таким образом, пользователь может легко выбирать, в каком окне запускать про грамму — нормальном, свернутом или развернутом. 

 

Рис. 4-3. Окно свойств для ярлыка Notepad 

Наконец, чтобы получить копию структуры STARTUPINFO, инициализированной родительским процессом, приложение может вызвать: 

VOID GetStartupInfo(PSTARTUPINFO pStartupInfo);

Анализируя эту структуру, дочерний процесс может изменять свое поведение в зависимости oi значений ее элементов 

NOTE 
Хотя в документации на Windows об этом четко не сказано, перед вызовом GetStartupInfo нужно инициализировать элемент cb структуры STARTUPINFO: 

STARTUPINFO si = { sizeof(si) }, GetStartupInfo(&si) 

Параметр ppiProclnfo 
Параметр ppiProcInfo указывает на структуру PROCESS_INFORMATION, которую Вы должны предварительно создать; ее элементы инициализируются самой функцией CreateProcess. Структура представляет собой следующее 

typedef struct _PROCESS_INFORMATION { 
HANDLE hProcess;
HANDLE hThread; 
DWORD dwProcessId; 
DWORD dwThreadId;
} PROCESS_TNFORMATION; 

Как я уже говорил, создание нового процесса влечет за собой создание объектов ядра "процесс" и "поток" В момент создания система присваивает счетчику каждого объекта начальное значение — единицу, Далее функция CreateProcess (перед самым возвратом управлении) открывает объекты "процесс" и "поток" и заносит их описа тели, специфичные для данного процесса, в элементы hProcess и hTbread структуры PROCESS_INFORMATION Когда CreateProcebb очкрывает эти объекты, счстчики каждого из них увеличиваются до 2 

Это означает, что, перед тем как система сможет высвободить из памяти объект "процесс", процесс должен быть завершен (счетчик уменьшен до 1), а родительский процесс обязан вызвать функцию CloseHandle (и тем самым обнулить счстчик) То же самое относится и к объекту "поток" поток должен быть завершен, а родительский процесс должен закрыть описатель объекта "поток". Подробнее об освобождении объектов "поток" см, раздел "Дочерние процессы" в этой главе. 

NOTE 
Не забывайте закрывать описатели дочернего процесса и его первичного по тока, иначе, пока Вы не закроете свое приложение, будет происходить утечка ресурсов. Конечно, система высвободит все эти ресурсы после завершения Вашего процесса, по хорошо написанная программа должна сама закрывать описатели дочернего процесса и его первичного потока, как только необхо димость в них отпадает Пропуск этой операции — одна из самых частых ошибок. 

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

Созданному объекту ядра "процесс" присваивается уникальный идентификатор; ни у каких других объектов этого типа в системе нс может быть одинаковых иденти фикаторов. Это же касается и объектов ядра "поток". Причем идентификаторы про цесса и потока тоже разные, и их значения никогда не бывают нулевыми. Завершая свою работу, CreateProcess заносит значения идентификаторов в элементы divProcessId и dwThreadld структуры PROCESS_INFORMATION Эти идентификаторы просто облег чают определение процессов и потоков в системе; их используют, как правило, лишь специализированные утилиты вроде Task Manager. 



--------------------
 Имеющий язык - да не убоится спросить! 
user posted image
PM MAIL ICQ   Вверх
HappyLife
Дата 13.9.2007, 13:10 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 642
Регистрация: 17.5.2006

Репутация: нет
Всего: 8



Alexandr87, Насколько я понимаю, это простые параметры.
PM MAIL   Вверх
Alexandr87
Дата 13.9.2007, 13:16 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


дыкий псых
***


Профиль
Группа: Завсегдатай
Сообщений: 1459
Регистрация: 27.11.2004
Где: Алматы, Казахстан

Репутация: нет
Всего: 39



SenkraD, спасибо конечно за столь большой набор ненужной мне в данный момент информации.
Пожалуйста, прежде, чем давать советы, разберитесь в обсуждаемом вопросе. В частности реккомендую открыть справку windows и почитать там топик про cmd.exe.  "|tee ./log.log " это не параметр программы tokentester, это специальная конструкция перенаправления вывода предыдущей программы на вход программы tee.

Это сообщение отредактировал(а) Alexandr87 - 13.9.2007, 13:20
PM Jabber   Вверх
SenkraD
Дата 13.9.2007, 13:25 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 933
Регистрация: 3.2.2006
Где: Украина::Киев

Репутация: 4
Всего: 23



Alexandr87, прошу прощения - невнимательно прочитал первый пост


--------------------
 Имеющий язык - да не убоится спросить! 
user posted image
PM MAIL ICQ   Вверх
586
Дата 13.9.2007, 16:48 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 2243
Регистрация: 8.5.2006

Репутация: 39
Всего: 146



Цитата(Alexandr87 @  13.9.2007,  12:48 Найти цитируемый пост)
чето не работает?

возможно, cmd.exe не ожидает завершения процесса.
"cmd.exe /с start /b /wait tokentester.exe %d | tee .\\log.txt & exit %%errorlevel%%"
или, если не получится, так:
"cmd.exe /k start /b /wait tokentester.exe %d | tee .\\log.txt & exit %%errorlevel%%"
/b - не создавать новое консольное окно
/wait - Запуск приложения с ожиданием его завершения.
/k - Выполнение указанной команды (строки) без последующего завершения.
%errorlevel% - это код завершения команды.
Два знака '%' нужны, чтобы sprintf игнорил его. В итоге там будет один знак.
Но это только теория, на практике я не тестировал.
PM   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "C/C++: Системное программирование и WinAPI"
Fixin
GremlinProg
xvr
feodorv
  • Большое количество информации и примеров с использованием функций WinAPI можно найти в MSDN
  • Описание сообщений, уведомлений и примеров с использованием компонент WinAPI (BUTTON, EDIT, STATIC, и т.п.), можно найти в MSDN Control Library
  • Непосредственно, перед созданием новой темы, проверьте заголовок и удостоверьтесь, что он отражает суть обсуждения.
  • После заполнения поля "Название темы", обратите внимание на наличие и содержание панели "А здесь смотрели?", возможно Ваш вопрос уже был решен.
  • Приводите часть кода, в которой предположительно находится проблема или ошибка.
  • Если указываете код, пользуйтесь тегами [code][/code], или их кнопочными аналогами.
  • Если вопрос решен, воспользуйтесь соответствующей ссылкой, расположенной напротив названия темы.
  • Один топик - один вопрос!
  • Перед тем как создать тему - прочтите это .

На данный раздел распространяются Правила форума и Правила раздела С++:Общие вопросы .


Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Chipset, Step, Fixin, GremlinProg, xvr. feodorv.

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Системное программирование и WinAPI | Следующая тема »


 




[ Время генерации скрипта: 0.0838 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.