Неработает CreateFile. Помогите!!

Тема в разделе "WASM.BEGINNERS", создана пользователем jaga, 2 дек 2008.

  1. jaga

    jaga Дмитрий

    Публикаций:
    0
    Регистрация:
    25 окт 2008
    Сообщения:
    33
    Адрес:
    Пермская обл.
    Я попробовал написать программу которая просто создает текстовый файл и запоминает его хендл для дальнейших действий. Посмотрев в OllyDbg я увидел что CreateFile возврашает не хендл созданного файла а просто цифру 10. Файл создается а вот хендла нету(( От чего может быть такая ошибка? Помогите пожалуйста.
    Вот код самой программы.
    Код (Text):
    1. include 'C:\fasm\include\win32ax.inc'
    2.  
    3. section '.data' data readable writeable
    4.         X       db     '123.txt',0
    5.         hFileR          dd      ?
    6.  
    7.  
    8. section '.code' code readable executable
    9. start:
    10.  
    11.                 invoke      CreateFile,X,GENERIC_WRITE,\
    12.                             FILE_SHARE_READ,\
    13.                             0,CREATE_ALWAYS,\
    14.                             FILE_ATTRIBUTE_NORMAL,\
    15.                             0
    16.                 mov             [hFileR],eax
    17.  
    18.                 invoke          ExitProcess,0
    19.  
    20. .end start
     
  2. Ursus

    Ursus Member

    Публикаций:
    0
    Регистрация:
    15 мар 2006
    Сообщения:
    238
    Адрес:
    Russia
    Охо-хо-хо-хо, горюшко, с чего ты взял, что "10" - это не хендл созданного файла? Что ты ожидал там увидеть???
     
  3. Partner

    Partner Павел

    Публикаций:
    0
    Регистрация:
    28 фев 2008
    Сообщения:
    917
    Адрес:
    Los Angeles
    А какую цифру вы предпочитаете для хэндла ? Чем не нравится цифра 10 ?
     
  4. jaga

    jaga Дмитрий

    Публикаций:
    0
    Регистрация:
    25 окт 2008
    Сообщения:
    33
    Адрес:
    Пермская обл.
    Спасибо)) А не подскажите как тогда будет например выглядить открытие файла и запись в него данных?
     
  5. Y_Mur

    Y_Mur Active Member

    Публикаций:
    0
    Регистрация:
    6 сен 2006
    Сообщения:
    2.494
    jaga
    а с чего ты взял что хендл будет выглядеть как то по другому? :)))
    если CreateFile не срабатывает она возвращает INVALID_HANDLE_VALUE = -1, тогда вызывай GetLastError и смотри почему, а у тебя всё нормально ;)
     
  6. AsmGuru62

    AsmGuru62 Member

    Публикаций:
    0
    Регистрация:
    12 сен 2002
    Сообщения:
    689
    Адрес:
    Toronto
    Код (Text):
    1. dwStored dd 0
    2. ...
    3. invoke WriteFile, [hFileR], X, 7, dwStored, 0
    4. invoke CloseHandle, [hFileR]
    И потом открой файл в NOTEPAD-е.
     
  7. jaga

    jaga Дмитрий

    Публикаций:
    0
    Регистрация:
    25 окт 2008
    Сообщения:
    33
    Адрес:
    Пермская обл.
    Спасибо!
     
  8. Semiono

    Semiono Member

    Публикаций:
    0
    Регистрация:
    27 ноя 2005
    Сообщения:
    777
    Научите меня WriteFile ??? Вот как эта прога работает в первом посте? Нафига "mov [hFileR],eax" регистр помещается в ячейку памяти, что это даёт ?
    Я просто хотел по этому исходнику чтонить сочинить чтоб запись в файл было. Но ничего не получается, нипойму я эти WinAPI.

    Код (Text):
    1. include '%SystemRoot%\Apps\Fasm\include\win32ax.inc'
    2. section '.data' data readable writeable
    3. X db 'C:\123.txt',0
    4. section '.code' code readable executable
    5. start:
    6. invoke WriteFile,X,X,X,X,X
    7. invoke ExitProcess,0
    8. .end start
    Почему никакой реакции? Нафиг мне хендлы, мнеб примитивно хотяб, и нагуглить ничего не могу,
    все умные чтоль сразу горы кода век неразгести! А гдеж для маленьких примерчиги?

    Мож закрыть чё " INVOKE CloseHandle, fileHandle " типа? Ох опять эти хендлы =)

    Надо ли сначала CreateFile ? Или сразу можно WriteFile ?

    ...я имею ввиду как можно вывести хоть какой-то код из программы в некий файл?
    Типа Хело Ворлд, тока не на экран
     
  9. Osen

    Osen Рие

    Публикаций:
    0
    Регистрация:
    5 апр 2008
    Сообщения:
    283
    Адрес:
    Париж
    Semiono
    охохохохохо!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
    Рано ты за кодинг взялся. Чтобы читать или писать в файл нужен хэндл файла, по сути это число. Хэндл можно получить вызовом CreateFile. Это не просто цифра, после вызова CreateFile, в таблице описателей процесса будет этот описатель, который будет ассоциирован с открытым файлом. Указывая эту цифру (10) в параметре WriteFile ты говоришь винде работать именно с этим файлом который ты открыл CreateFile'ом. И кстати после вызова (CALL) CreateFile в регистре EAX будет этот хэндл. Он сохраняется в ячейке памяти, чтобы потом его использовать. Кстати полезно пользоваться MSDN - там описываются параметры всех функций Windows. В том числе и WriteFile. Ты ему хрень передал в посл. примере, конечно ничего не заработает. Первый параметр это как раз число которое вернул CreateFile. Хэндл (Handle) в переводе - "ручка". Т.е. по этой цифре функции работы с файлами (ReadFile, WriteFile) поймут какой файл используется, в какой файл ты хочешь счиать, из какого записать. Т.е. не надо в каждом вызове указывать имя файла, надо один раз указать имя в вызове CreateFile. Более того хэндлы обладают правами доступа. Это тоже важная часть описателя. Через один описатель(хэндл) ты можешь и читать и писать, через другой только читать и т.д. Для образовательных целей советую скачать Process Explorer и глянуть список хэндлов (описателей) процесса какого-нибудь. Кстати бывают хэндлы не только файлов, но и многих других объектов. Кароче бери Рихтера и читай. Это книжка такая. Это можно нагуглить.
     
  10. Semiono

    Semiono Member

    Публикаций:
    0
    Регистрация:
    27 ноя 2005
    Сообщения:
    777
    Значится всётаки надо Create создать сначала!
    У мну тут пример был, но я его замучился в фасм перекраивать =)
    Код (Text):
    1. TITLE Using WriteFile                       (WriteFile.asm)
    2.  
    3. ; This program writes text to an output file.
    4. ; Last update: 1/30/02
    5.  
    6. INCLUDE Irvine32.inc
    7.  
    8. .data
    9. buffer BYTE "This text is written to an output file.",0dh,0ah
    10. bufSize = ($-buffer)
    11. errMsg BYTE "Cannot create file",0dh,0ah,0
    12. filename     BYTE "output.txt",0
    13. fileHandle   DWORD ?    ; handle to output file
    14. bytesWritten DWORD ?            ; number of bytes written
    15.  
    16. .code
    17. main PROC
    18.         INVOKE CreateFile,
    19.           ADDR filename, GENERIC_WRITE, DO_NOT_SHARE, NULL,
    20.           CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0
    21.  
    22.         mov fileHandle,eax              ; save file handle
    23.         .IF eax == INVALID_HANDLE_VALUE
    24.           mov  edx,OFFSET errMsg                ; Display error message
    25.           call WriteString
    26.           jmp  QuitNow
    27.         .ENDIF
    28.  
    29.         INVOKE WriteFile,               ; write text to file
    30.             fileHandle,         ; file handle
    31.             ADDR buffer,                ; buffer pointer
    32.             bufSize,            ; number of bytes to write
    33.             ADDR bytesWritten,          ; number of bytes written
    34.             0           ; overlapped execution flag
    35.  
    36.         INVOKE CloseHandle, fileHandle
    37.  
    38. QuitNow:
    39.         exit
    40. main ENDP
    41. END main
    Я сначала по поводу хендлов подумал, что раз CreateFile не требует хендла, то может и WriteFile аналогично?
    Хм. почему бы и нет, ведь передаётся же дата с чем работать X db 'C:\123.txt',0
    Но я не против хендлов как таковых, просто хочеться вникнуть
    =)

    8-)
     
  11. Osen

    Osen Рие

    Публикаций:
    0
    Регистрация:
    5 апр 2008
    Сообщения:
    283
    Адрес:
    Париж
    Semiono
    Я очень рад что вы поняли про описатели =) Вообще это фундаментальные вещи которые пишут в книгах, поэтому возьмите книгу и прочитайте.
     
  12. Semiono

    Semiono Member

    Публикаций:
    0
    Регистрация:
    27 ноя 2005
    Сообщения:
    777
    Код (Text):
    1. section '.data' data readable writeable
    2.         X       db     '123.txt',0
    3.         hFile          dd      ?
    4.     Msg db 'Hello'
    5.     zzzz dd ?
    6. section '.code' code readable executable
    7. start:
    8. invoke CreateFile,X,GENERIC_WRITE,FILE_SHARE_READ,0,CREATE_ALWAYS,FILE_ATTRIBUTE_NORMAL,0
    9.      mov [hFile],eax
    10.   invoke WriteFile,[hFile],Msg,5,zzzz,0
    11.      invoke ExitProcess,0
    12. .end start
    А почему поле " __out_opt LPDWORD lpNumberOfBytesWritten " нельзя цыфрой сразу указать? или NULL ? Вообще что я накатал хоть правильно или можно проще было?

    Почему всётаки eax помещать в [hFile] нужно было? Даже логичнее наоборот какойнить указатель в регистр загрузить, что тут за фитча таиться?
     
  13. Clerk

    Clerk Забанен

    Публикаций:
    0
    Регистрация:
    4 янв 2008
    Сообщения:
    6.689
    Адрес:
    РБ, Могилёв
    Semiono
    Может стоить потрассировать код под олей, дабы видеть что и для чего. hFile это переменная, которая хранит то магическое число.
     
  14. Osen

    Osen Рие

    Публикаций:
    0
    Регистрация:
    5 апр 2008
    Сообщения:
    283
    Адрес:
    Париж
    Semiono
    Инфу про любой параметр можно узнать в MSDN. Это единственный источник знаний на который надо опираться.

    Все правильно, но описатели надо закрывать CloseHandle.
     
  15. Y_Mur

    Y_Mur Active Member

    Публикаций:
    0
    Регистрация:
    6 сен 2006
    Сообщения:
    2.494
    Semiono
    Функция WriteFile возвращает два значения - результат записи (получилось/не получилось) и количество реально записанных байт, поэтому и нужно обязательно сказать адрес ей куда девать второе возвращаемое значение (NumberOfBytesWritten). Сделать так чтобы просто в eax возвращалость NumberOfBytesWritten (а 0 значит ошибка) нельзя потому, что возможна ситуация - удалось записать только часть информации, тогда нужно вернуть и сообщение об ошибке в eax и ненулевое количество байт которые удалость записать.
     
  16. leo

    leo Active Member

    Публикаций:
    0
    Регистрация:
    4 авг 2004
    Сообщения:
    2.542
    Адрес:
    Russia
    Semiono
    Потому, что регистр eax затирается при вызове функций и его значение нужно сохранить в переменной hFile для дальнейшего использования. В твоем примере в WriteFile можно и само значение eax передать, но после WriteFile значение в eax уже будет другим, поэтому в CloseHandle (или в последующие вызовы WriteFile) нужно будет передавать не eax, а сохраненное значение [hFile]
     
  17. Semiono

    Semiono Member

    Публикаций:
    0
    Регистрация:
    27 ноя 2005
    Сообщения:
    777
    Спасиб, пацаны!
    Загрузить в OllyGbg это само собой, я просто наспех методом тыка начал решить, хотя "неправильный" код мнеб сразу тоже правду не сказал бы кажись.
    msdn скачал по теме уже давно, признаться они флудят там, вернее им бы на fasm луче б писать, было бы правильней тогда, у них там систем-администраторский язык повествования, трудно усваиваимый мозг =)
    * Да про CloseHandle забыл! Y_Mur, leo очень по делу, большое спасибо!
     
  18. Semiono

    Semiono Member

    Публикаций:
    0
    Регистрация:
    27 ноя 2005
    Сообщения:
    777
    Пожалуй "хорошим тоном" будет коментировать winapi-код так
    Код (Text):
    1. invoke  WriteFile,\  ; BOOL WINAPI WriteFile
    2.            [hFile],\     ; __in HANDLE hFile
    3.            Msg,\        ; __in LPCVOID lpBuffer
    4.            5,\            ; __in DWORD nNumberOfBytesToWrite
    5.            bWrtn,\      ; __out_opt LPDWORD lpNumberOfBytesWritten
    6.            0               ; __inout_opt LPOVERLAPPED lpOverlapped
    сразу же бросается то что имеют место всякие типы данных 0_o
    поглядев на DWORD я сразу же подумал об LPCSTR, но не тут-то было!
    Оказывается это CString::operator
    Может стоит в таком случае создать "справочник" или таблицу всего такого для Fasm.
    Или не стоит? Я бы сам зделал, но пока не знаю в какие дебри это уходит и насколько.
    Всмысле, msdn это понятно, но было бы лучше иметь сразу механический перевод в db dw dd всех типов для асма?

    Ещё не понятно почему запись функций различается, о чём это вообще говорит? -
    HANDLE WINAPI CreateFile
    BOOL WINAPI WriteFile

    разве bool и handle вещи одного порядка? как будто сравнивать снег с телевизором =)
     
  19. Y_Mur

    Y_Mur Active Member

    Публикаций:
    0
    Регистрация:
    6 сен 2006
    Сообщения:
    2.494
    Semiono
    это у тебя всё с непривычки к асму ;)) и судя по тому что ты написал к программированию вообще ;))
    Для начала пиши как тебе удобнее, а потом сам сравнив разные варианты записи поймёшь что удобнее всего в строку invoke имя_функции, аргументы. А если вдруг с большого перекуру мануалов забыл тип или назначение какого нибудь аргумента заглянул в msdn и порядок :))
    И с чего это тебя вдруг удивляет что одна функция возвращает handle, другая bool, третья integer, четвёртая errorcode, и т.д. :)))
     
  20. Osen

    Osen Рие

    Публикаций:
    0
    Регистрация:
    5 апр 2008
    Сообщения:
    283
    Адрес:
    Париж
    Semiono
    В третий раз говорю, MSDN единственный надежный источник. Если ты ламер не надо вот только кричать это по сто раз. Тошнить начинает.