Написал макрос определения параметров командной строки (цель - получить имена файлов), но чувствую, что до оптимальности ему еще хромать и хромать... Может кто посоветует лучшее решение: argv - массив, содержит поочередно адрес начала 1-го; адрес конца 1-го аргумента; адрес начала 2го;... argc - число аргументов предполагается что аргументы отделены одним или более пробелами, в конце тоже могут быть пробелы Код (Text): _GET_COMMAND_LINE macro argv,argc ;CLIstart DWORD ? / CLIend DWORD ? pushad ;сохраняем регистры invoke GetCommandLine mov CLIstart,eax ;начало строки ;#####ищем конец строки############# mov edi, eax ;начало в edi xor al,al ;ищем NULL mov ecx,-1 cld repne scasb not ecx ;длина строки dec edi ;scasb проскакивает символ mov CLIend,edi ;конец строки ;#############поиск аргументов######## mov edi,CLIstart xor edx,edx ;инициализация счетчика аргументов xor esi,esi ;инициализация индекса массива аргументов start_find: mov argv[esi],edi ;начало аргумента mov al, 20h ;ищем первый пробел в серии после аргумента cld repne scasb mov ebx,edi add esi,4 ;куда пишем адрес конца аргумента dec edi ;scasb проскакивает символ mov argv[esi],edi ;адрес конца аргумента inc edx ;счетчик аргументов +1 jecxz out_of_line ;проверяем, что строка не исчерпана repe scasb ;ищем первый не пробел в серии пробелов add esi,4 ;куда пишем адрес начала нового аргумента dec edi ;scasb проскакивает символ jmp start_find out_of_line: mov ebx,CLIend mov argv[esi],ebx ;адрес конца аргумента - конец строки mov argc,edx ;возвращаем число аргументов popad ;восстанавливаем регистры ; в результате в argc - число аргументов, в массиве argv- адреса начала и конца аргументов endm
Во-первых, такой функции я не нашел в shell32.inc - есть только CommandLineToArgv в свою очередь в справке по API нет именно второй. Мож косяк с MASM? Во-вторых, как с ней работать, тож непонятно...Может ссылку на пример кода?
есть функция в shell32.dll и она одна. называется CommandLineToArgvW. имеет прототип: LPWSTR * CommandLineToArgvW( LPCWSTR lpCmdLine, // pointer to a command-line string int *pNumArgs // pointer to a variable that receives the argument count ); Юзать примерно так: Код (Text): argc dd ? argv dd ? ... invoke GetCommandLineW invoke CommandLineToArgvW, eax, offset argc mov [argv], eax
Все, понял и разобрался,. Единственно, что волнует - например функции GetCommandLineW и GetCommandLine чем-нибудь различаются?
нет функции GetCommandLine. так же, как и нету MessageBox, CreateFile, CreateWindow. Есть два варианта функций - Ansii (с окончанием A) и Unicode (с окончанием W от wide-char). Соответственно они принимают анси и юникод параметры (если конечно эти функции принимают какие-либ текстовые параметры, иначе есть 1 функция без всяких таких окончаний). В связи с тем что еще после Windows 98 ядро стало функционировать исключительно на юникоде, то W-функции содержат реальный код, а A-функции являются только переходниками к W-функциям. Соответственно нет функции GetCommandLine. Есть GetCommandLineA, которую ты, вероятно, и юзал обычно, но есть и GetCommandLineW. Первая получает параметры в анси формате, вторая - в юникоде. Но вот CommandLIneToArgvW, так уж сложилась, представлена в одном Unicode-варианте. Поэтому и командную строку ей надо переадвать юникодную.
ЗЫ. Наряду с функциями XxxA и XxxW объявляется в SDK так же макрос Xxx, значение которого зависит от кодировки программы. Например, в Си: Код (Text): #ifdef _UNICODE #define MessageBox MessageBoxW #else #define MessageBox MessageBoxA #endif