Наши проекты:
Журнал · Discuz!ML · Wiki · DRKB · Помощь проекту |
||
ПРАВИЛА | FAQ | Помощь | Поиск | Участники | Календарь | Избранное | RSS |
[3.17.28.48] |
|
Сообщ.
#1
,
|
|||||||||||||||||||||||||||||||||||||||
|
Загрузка Интернет страницы, через прокси-сервер, используя, библиотеку wininet. Если пользоваться библиотекой winsock Интернет-страницу загрузить можно, но сделать это гораздо, сложнее , поэтому, я покажу - способ загрузки страницы по средствам библиотеки wininet. Плюс этот функционал будет работать, через прокси-сервер используя функцию UrlMkSetSessionOption из библиотеки urlmon. Функции WinInet API Разберём все функции по порядку и рассмотрим только те параметры, которые нам будут необходимы. InternetOpen Эта функция инициализирует WinInet и возвращает дескриптор, который необходим для вызова других функций WinInet. В случае неудачи возвращается NULL. Более подробную информацию об ошибке можно получить, вызвав функцию GetLastError. HINTERNET WINAPI InternetOpen( LPCTSTR lpszAgent, DWORD dwAccessType, LPCTSTR lpszProxyName, LPCTSTR lpszProxyBypass, DWORD dwFlags ); Параметры:
InternetConnect Эта функция открывает FTP, HTTP или Gopher сессию для заданного сайта. HINTERNET InternetConnect( HINTERNET hInternet, LPCTSTR lpszServerName, INTERNET_PORT nServerPort, LPCTSTR lpszUsername, LPCTSTR lpszPassword, DWORD dwService, DWORD dwFlags, DWORD_PTR dwContext ); Параметры:
InternetOpenUrl Функция принимает полный URL файла и возвращает указатель на него. function InternetOpenUrl(hInet: HINTERNET; lpszUrl: PChar; lpszHeaders: PChar; dwHeadersLength: DWORD; dwFlags: DWORD; dwContext: DWORD): HINTERNET; stdcall; Параметры:
InternetReadFile Функция позволяет считывать данные, используя указатель, полученный в результате вызова InternetOpenUrl. Так же, как и все остальные функции, возвращает TRUE или FALSE. После завершения работы функции нужно освободить указатель Hfile, вызвав InternetCloseHandle(hUrlFile) . function InternetReadFile(hFile: HINTERNET; lpBuffer: Pointer; dwNumberOfBytesToRead: DWORD; var lpdwNumberOfBytesRead: DWORD): BOOL; stdcall; Параметры:
Вот, в принципе, и все об самых основных функциях, которые я пользовала в данной статье они находятся в библе wininet . Структура INTERNET_PROXY_INFO для использования в функции UrlMkSetSessionOption загрузки страницы через проксю, включает в себя следующие параметры: typedef struct { DWORD dwAccessType; LPCTSTR lpszProxy; LPCTSTR lpszProxyBypass; } Функция: procedure UrlMkSetSessionOption (dwOption : Integer; var pBuffer : Pointer; dwBufferLength : Integer; dwReserved : Integer); stdcall; external 'URLMON' name 'UrlMkSetSessionOption' Ну и наконец сам код, который загружает код страницы в поле ; pwi.asm .386 .model flat,stdcall option casemap:none include \masm32\include\windows.inc include \masm32\include\user32.inc include \masm32\include\kernel32.inc include \masm32\include\wininet.inc include \masm32\include\urlmon.inc includelib \masm32\lib\user32.lib includelib \masm32\lib\kernel32.lib includelib \masm32\lib\urlmon.lib includelib \masm32\lib\wininet.lib _T macro p1, p2 ;макрос обработки строк local l ifb <p2>; Строка без имени .data l db p1, 0 .code exitm <addr l> else ; Строка с именем .data p1 db p2, 0 .code exitm <addr p1> endif endm IDC_INPUTDATA equ 1000 ;окно приёма данных IDC_GETHOST equ 1001 ;edit для хоста IDC_PROXI equ 1002 ;edit для прокси IDC_LOAD equ 1003 ;кнопка загрузить IDC_EXIT equ 1004 ;выход ;================= ; Local prototypes ;================= WndProc PROTO :DWORD,:DWORD,:DWORD,:DWORD .data ;прокси - адрес и порт "218.7.13.186:80" < - пригодится ;) hInstance dd 0 AgetUser db '}{}{}{',0;ЮзерАгент - название программы, которое будет отображатся на сервере ;дескрипторы wininet - функций hInternet dd 0 hOpenUrl dd 0 hConnect dd 0 ProxyHP db 20 dup (?);буфер для прокси адреса .data? ByteWRite dd ?;сколько байт записано StrokaIz db 1024 dup (?) ;буфер для хоста iBuffer dw 24000 dup (?);для получения данных busize = $-iBuffer;размер буфера PiProxy INTERNET_PROXY_INFO <>;структура для Proxy соединения .code start: ; ######################################################################### invoke GetModuleHandle, NULL mov hInstance, eax invoke DialogBoxParam,hInstance,_T("MAINDIALOG"),0,ADDR WndProc,0 invoke ExitProcess,eax ; ######################################################################### WndProc proc hWin :DWORD, uMsg :DWORD, wParam :DWORD, lParam :DWORD .if uMsg == WM_INITDIALOG invoke SendMessage,hWin,WM_SETTEXT,0, _T("HtmlProxyGet") .elseif uMsg==WM_COMMAND mov eax, wParam mov edx, eax shr edx, 16 .if edx == BN_CLICKED .if ax == IDC_LOAD;берём адрес и порт прокси - сервера из Edit-control invoke GetDlgItemText,hWin,IDC_PROXI,addr ProxyHP,-1 ;опции прокси сервера mov PiProxy.dwAccessType, INTERNET_OPEN_TYPE_PROXY ;адрес и порт mov PiProxy.lpszProxy,offset ProxyHP ;функция создания Proxy сессии опции прокси параметры структуры размер структуры invoke UrlMkSetSessionOption,INTERNET_OPTION_PROXY,addr PiProxy, SizeOf(INTERNET_PROXY_INFO),0 ;хост из Edit- control invoke GetDlgItemText,hWin,IDC_GETHOST,addr StrokaIz,-1 ;инициализация WinInet и возвращает дескриптора, который ;необходим для вызова других функций WinInet invoke InternetOpen,addr AgetUser,INTERNET_OPEN_TYPE_PRECONFIG,NULL,NULL,0 mov hInternet,eax ;открывает HTTP сессию для заданного сайта invoke InternetConnect, [hInternet],\;Дескриптор, полученный вызовом предыдущей функции. addr StrokaIz,\;хост INTERNET_DEFAULT_HTTP_PORT,\; для обычных соединений NULL,NULL,\ INTERNET_SERVICE_HTTP,\;Тип сервиса 0,\ 1 mov [hConnect],eax ;принимает полный URL файла и возвращает указатель на него. invoke InternetOpenUrl,[hInternet],\;указатель, полученный после вызова InternetOpen. addr StrokaIz,\ 0, 0,\ INTERNET_FLAG_RELOAD,\;флаг, задающий дополнительные параметры перед выполнением функции 0 mov [hOpenUrl],eax ;позволяет считывать данные, используя указатель, ; полученный в результате вызова InternetOpenUrl. ;Так же, как и все остальные функции, возвращает TRUE или FALSE invoke InternetReadFile, [hOpenUrl],\; указатель на файл, полученный после вызова функции InternetOpenUrl addr (iBuffer),\;указатель на буфер, куда будут заноситься данные busize ,\;число байт, которое нужно причитать addr ByteWRite;содержит количество прочитанных байтов. Устанавливается в 0 перед проверкой ошибок. ;выводим html - код invoke SetDlgItemText,hWin,IDC_INPUTDATA, addr iBuffer ; закрытие дескрипторов вызванных wininet - функциями invoke InternetCloseHandle,hOpenUrl invoke InternetCloseHandle,hConnect invoke InternetCloseHandle,hInternet .elseif ax == IDC_EXIT invoke SendMessage, hWin, WM_CLOSE, 0, 0 .endif .endif .elseif uMsg == WM_CLOSE invoke EndDialog,hWin,0 .else mov eax, FALSE ret .endif mov eax, TRUE ret WndProc endp ; ######################################################################## end start Диалог: // wi.rc #define DS_MODALFRAME 0x80L #define WS_POPUP 0x80000000L #define WS_CHILD 0x40000000L #define WS_VISIBLE 0x10000000L #define WS_CAPTION 0x00C00000L #define WS_BORDER 0x00800000L #define WS_SYSMENU 0x00080000L #define WS_GROUP 0x00020000L #define WS_TABSTOP 0x00010000L #define ES_LEFT 0x00000000L #define ES_MULTILINE 0x00000004L #define ES_AUTOVSCROLL 0x00000040L #define ES_AUTOHSCROLL 0x00000080L #define IDC_INPUTDATA 1000 #define IDC_GETHOST 1001 #define IDC_PROXI 1002 #define IDC_LOAD 1003 #define IDC_EXIT 1004 MAINDIALOG DIALOG 10, 15, 282, 199 STYLE DS_MODALFRAME | WS_POPUP | WS_CAPTION | WS_SYSMENU CAPTION "MAINDIALOG" FONT 8, "MS Sans Serif" BEGIN CONTROL "", IDC_INPUTDATA, "EDIT", ES_LEFT | ES_MULTILINE | ES_AUTOVSCROLL | WS_CHILD | WS_VISIBLE | WS_BORDER | WS_TABSTOP, 8, 17, 264, 92 CTEXT "Код страницы", -1, 8, 4, 264, 8, WS_CHILD | WS_VISIBLE | WS_GROUP CTEXT "Нужный хост", -1, 8, 117, 264, 8, WS_CHILD | WS_VISIBLE | WS_GROUP EDITTEXT IDC_GETHOST, 8, 128, 264, 12, ES_LEFT | WS_CHILD | WS_VISIBLE | WS_BORDER | WS_TABSTOP CTEXT "Прокси", -1, 8, 148, 264, 8, WS_CHILD | WS_VISIBLE | WS_GROUP EDITTEXT IDC_PROXI, 8, 160, 264, 12, ES_LEFT | WS_CHILD | WS_VISIBLE | WS_BORDER | WS_TABSTOP DEFPUSHBUTTON "Загрузить", IDC_LOAD, 8, 180, 48, 14, WS_CHILD | WS_VISIBLE | WS_TABSTOP PUSHBUTTON "Выход", IDC_EXIT, 224, 180, 48, 14, WS_CHILD | WS_VISIBLE | WS_TABSTOP END Компилируется: E:\masm32\bin\rc wi.rc E:\masm32\bin\ml /c /coff /nologo pwi.asm E:\masm32\bin\Link /SUBSYSTEM:WINDOWS pwi.obj wi.res Pause Вот и всего то. Конечно, нужно не забывать про обработку ошибок, здесь – это специально не сделано, чтобы нагляднее показать работу wininet функций. Для загрузки огромных сайтов нужно увеличить размер буфера. Также не забываем про указание префикса http протокола - «http://». Ну и конечно, всё зависит от прокси-сервера; приведённый в коде адрес 218.7.13.186:80 , самый быстродейственный на данный момент. Удачи в компиляции. |