- •Лабораторная работа №1
- •1.1. Цель и содержание работы
- •1.2. Основные конструкции языка c
- •Int X; // Переменная типа int
- •Int list[20]; // Массив целых величин
- •If (условие) оператор1 else оператор2
- •1.3. Функции ввода-вывода языка с
- •1.4. Создание консольного приложения
- •1.5. Меню интегрированной среды
- •1.6. Компиляция, отладка и запуск программы
- •1.7. Упражнения
- •Лабораторная работа №2
- •2.1. Цель и содержание работы
- •2.2. Использование функций библиотеки ipHlpApi
- •2.3. Упражнения
- •Int iErr; // Код ошибки
- •Лабораторная работа №3
- •3.1. Цель и содержание работы
- •3.2. Библиотека функций Winsock2
- •3.3. Структуры данных для работы с сокетами
- •3.4. Приложение-сервер
- •3.5. Приложение-клиент
- •3.6. Упражнения
- •Лабораторная работа №4
- •4.1. Цель и содержание работы
- •4.2. Функции для работы по протоколу udp
- •4.3. Приложение-сервер
- •4.4. Приложение-клиент
- •4.5. Упражнения
- •Лабораторная работа №5
- •5.1. Цель и содержание работы
- •5.2. Сканирование портов
- •5.3. Функции для определения состояния портов
- •5.4. Упражнения
- •Лабораторная работа №6
- •6.1. Цель и содержание работы
- •6.2. Сниффер
- •6.3. Упражнения
- •Библиографический список
5.3. Функции для определения состояния портов
Если нужно узнать состояние портов локального компьютера, нет необходимости сканировать порты. Есть способ лучше – запросить состояние всех портов с помощью функций GetTcpTable и GetUdpTable.
Данные о TCP-портах хранятся в виде таблицы в структуре типа _MIB_TCPTABLE:
typedef struct _MIB_TCPTABLE { DWORD dwNumEntries; MIB_TCPROW table[ANY_SIZE];
} MIB_TCPTABLE, *PMIB_TCPTABLE;
Переменная dwNumEntries хранит значение, соответствующее количеству элементов в таблице. Структура MIB_TCPROW описывает состояние TCP-порта:
typedef struct _MIB_TCPROW { DWORD dwState; DWORD dwLocalAddr; DWORD dwLocalPort; DWORD dwRemoteAddr; DWORD dwRemotePort;
} MIB_TCPROW, *PMIB_TCPROW;
Поля структуры имеют следующее назначение:
dwState – состояние порта;
dwLocalAddr – локальный адрес (интерфейс, на котором открыт порт);
dwLocalPort – локальный порт (порт, который открыт на компьютере);
dwRemoteAddr – удаленный адрес (адрес, с которого в данный момент установлено соединение с портом);
dwRemotePort – удаленный порт (порт на удаленной машине, через который происходит обращение к локальной машине).
Функция DWORD GetTcpTable(PMIB_TCPTABLE pTcpTable, PDWORD pdwSize, BOOL bOrder) имеет три параметра: указатель на структуру MIB_TCPTABLE, размер этой структуры и признак сортировки (если указано TRUE, то таблица будет отсортирована по номеру порта).
Если в качестве первых двух параметров указать нулевое значение, то во втором параметре будет получен необходимый размер для хранения структур PMIB_TCPTABLE. Для выделения памяти необходимо воспользоваться функцией malloc.
Повторный вызов функции GetTcpTable позволяет через первый параметр (переменная рТсрTаblе типа PMIB_TCPTABLE) получить данные о состоянии всех TCP-портов. Их количество находится в параметре dwNumEntries структуры рТсрTаblе. Информацию об определенном порте можно узнать из параметра table[i], где i – номер порта.
Данные о UDP-портах хранятся в виде таблицы в структуре типа _MIB_UDPTABLE:
typedef struct _MIB_UDPTABLE { DWORD dwNumEntries; MIB_UDPROW table[ANY_SIZE];
} MIB_UDPTABLE, *PMIB_UDPTABLE;
Переменная dwNumEntries хранит значение, соответствующее количеству элементов в таблице.
Структура MIB_UDPROW описывает состояние UDP-порта:
typedef struct _MIB_UDPROW { DWORD dwLocalAddr; DWORD dwLocalPort;
} MIB_UDPROW, *PMIB_UDPROW;
Поля структуры имеют следующее назначение:
dwLocalAddr – локальный адрес (интерфейс, на котором открыт порт);
dwLocalPort – локальный порт (порт, который открыт на компьютере).
Для получения таблицы UDP-портов используется функция
DWORD GetUdpTable(PMIB_UDPTABLE pUdpTable, PDWORD pdwSize, BOOL bOrder). Она используется аналогично GetTcpTable, но узнать можно только локальный адрес и локальный порт, потому что протокол UDP не устанавливает соединения (нет сведений об удаленном компьютере).
Пример программы, которая отображает состояние портов TCP и UDP, приведен в листинге 5.2.
Листинг 5.2. Проверка состояния портов TCP и UDP
#include "stdafx.h"
#include <winsock2.h>
#include <windows.h>
#include <iphlpapi.h>
#include <assert.h>
#include <malloc.h>
int main(int argc, _TCHAR* argv[])
{
DWORD dwStatus = NO_ERROR;
PMIB_TCPTABLE pTcpTable = NULL;
DWORD dwActualSize = 0;
dwStatus = GetTcpTable(pTcpTable, &dwActualSize, TRUE);
pTcpTable = (PMIB_TCPTABLE) malloc(dwActualSize);
assert(pTcpTable);
dwStatus = GetTcpTable(pTcpTable, &dwActualSize, TRUE);
if (dwStatus != NO_ERROR)
{
printf("Couldn't get tcp connection table.\n");
free(pTcpTable); getchar(); return -1;
}
struct in_addr inadLocal, inadRemote;
DWORD dwRemotePort = 0;
char szLocalIp[1000];
char szRemIp[1000];
if (pTcpTable != NULL)
{
printf("==========================================\n");
printf("TCP table:\n\n");
printf(
"Loc Addr\tLoc Port\tRem Addr\tRem Port\tState\n\n");
for (UINT i=0; i<pTcpTable->dwNumEntries; i++)
{
inadLocal.s_addr = pTcpTable->table[i].dwLocalAddr;
inadRemote.s_addr = pTcpTable->table[i].dwRemoteAddr;
strcpy(szLocalIp, inet_ntoa(inadLocal));
strcpy(szRemIp, inet_ntoa(inadRemote));
if(pTcpTable->table[i].dwState==MIB_TCP_STATE_LISTEN)
dwRemotePort = pTcpTable->table[i].dwRemotePort;
else dwRemotePort = 0;
printf("%-15s %u\t\t%-15s %u\t\t", szLocalIp,
ntohs((unsigned short)(0x0000FFFF &
pTcpTable->table[i].dwLocalPort)),
szRemIp, ntohs((unsigned short)(0x0000FFFF &
dwRemotePort)));
switch (pTcpTable->table[i].dwState)
{
case MIB_TCP_STATE_LISTEN:
printf("Listen"); break;
case MIB_TCP_STATE_CLOSED:
printf("Closed"); break;
case MIB_TCP_STATE_TIME_WAIT:
printf("Time wait"); break;
case MIB_TCP_STATE_LAST_ACK:
printf("Last ACK"); break;
case MIB_TCP_STATE_CLOSING:
printf("Closing"); break;
case MIB_TCP_STATE_CLOSE_WAIT:
printf("Close Wait"); break;
case MIB_TCP_STATE_FIN_WAIT1:
printf("FIN wait"); break;
case MIB_TCP_STATE_ESTAB:
printf("EStab"); break;
case MIB_TCP_STATE_SYN_RCVD:
printf("SYN Received"); break;
case MIB_TCP_STATE_SYN_SENT:
printf("SYN Sent"); break;
case MIB_TCP_STATE_DELETE_TCB: printf("Delete");
}
printf("\n");
}
}
free(pTcpTable);
getchar();
dwStatus = NO_ERROR;
PMIB_UDPTABLE pUdpTable = NULL;
dwActualSize = 0;
dwStatus = GetUdpTable(pUdpTable, &dwActualSize, TRUE);
pUdpTable = (PMIB_UDPTABLE) malloc(dwActualSize);
assert(pUdpTable);
dwStatus = GetUdpTable(pUdpTable, &dwActualSize, TRUE);
if (dwStatus != NO_ERROR)
{
printf("Couldn't get udp connection table.\n");
free(pUdpTable); getchar(); return -2;
}
if (pUdpTable != NULL)
{
printf("==========================================\n");
printf("UDP table:\n\n");
printf("Loc Addr\tLoc Port\n\n");
for (UINT i = 0; i < pUdpTable->dwNumEntries; i++)
{
inadLocal.s_addr = pUdpTable->table[i].dwLocalAddr;
printf("%-15s %u\n", inet_ntoa(inadLocal),
ntohs((unsigned short)(0x0000FFFF &
pUdpTable->table[i].dwLocalPort)));
}
}
free(pUdpTable);
getchar();
return 0;
}