Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Низкоуровневое программирование > Win Api
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 31.10.2015, 01:43   #21
calypso
Форумчанин
 
Регистрация: 02.12.2012
Сообщений: 250
По умолчанию

Переписал код на Visual C++ , то же самое ошибка переполнения буфера даже на инициализации GetIfTable:
Код:
#pragma once
#include <Windows.h>
#include <IPHlpApi.h>
#pragma comment(lib, "IPHlpApi.lib")


#define MALLOC(x) HeapAlloc(GetProcessHeap(),0,(x))
#define FREE(x) HeapFree(GetProcessHeap(),0,(x))
<...>
private: System::Void button1_Click(System::Object^  sender, System::EventArgs^  e) {
				 DWORD dwSize=0;
				 DWORD dwRetVal=0;
				 MIB_IFTABLE *pIfTable;
				 MIB_IFROW *pIfRow;
				 int oshibka;
				 pIfTable=(MIB_IFTABLE*) MALLOC(sizeof(MIB_IFTABLE));
				 if (pIfTable==NULL) MessageBox::Show("Ошибка при выделении памяти под GetIfTable!");
				 //инициализация GetIfTable чтобы получить размер dwSize
				 dwSize=sizeof(MIB_IFTABLE);
				 if (GetIfTable(pIfTable,&dwSize,0)==ERROR_INSUFFICIENT_BUFFER) MessageBox::Show("Ошибка переполнения буфера");
				 else 
					 //второй вызов GetIfTable который должен завершиться без ошибок
					 if (GetIfTable(pIfTable,&dwSize,0)==NO_ERROR) MessageBox::Show("Успешно!");
					 else 
						 {
							 oshibka=GetLastError();
							 MessageBox::Show("Ошибка при вызове функции GetIfTable: "+oshibka.ToString());
					     }
			 }
calypso вне форума Ответить с цитированием
Старый 31.10.2015, 10:25   #22
waleri
Старожил
 
Регистрация: 13.07.2012
Сообщений: 6,493
По умолчанию

Отформатируйте код - сразу увидите первую ошибку.
Вторая - память кто выделять будет?
waleri вне форума Ответить с цитированием
Старый 02.11.2015, 13:36   #23
calypso
Форумчанин
 
Регистрация: 02.12.2012
Сообщений: 250
По умолчанию

Да действительно, не внимательно cкопировал код из MSDN.
https://msdn.microsoft.com/en-us/lib...=vs.85%29.aspx
Забыл кусок:
Код:
FREE(pIfTable);
        pIfTable = (MIB_IFTABLE *) MALLOC(dwSize);
        if (pIfTable == NULL) {
            printf("Error allocating memory\n");
Итого, структура заполняется. dwOutOctets и dwInOctets всё отображают как надо.
Единственное что, wszName и bDescr выводит квадратики-крякозябры, все варианты конвертации перебрал. И dwOperStatus не определено.
Система Windows XP SP3, может в этом причина
calypso вне форума Ответить с цитированием
Старый 02.11.2015, 13:37   #24
calypso
Форумчанин
 
Регистрация: 02.12.2012
Сообщений: 250
По умолчанию

Ну и конечно надо разобраться, почему это всё не хочет на Делфи работать.
calypso вне форума Ответить с цитированием
Старый 02.11.2015, 13:50   #25
Пепел Феникса
Старожил
 
Аватар для Пепел Феникса
 
Регистрация: 28.01.2009
Сообщений: 21,000
По умолчанию

Цитата:
Единственное что, wszName и bDescr выводит квадратики-крякозябры, все варианты конвертации перебрал.
а как выводите?
Хорошо поставленный вопрос это уже половина ответа. | Каков вопрос, таков ответ.
Программа делает то что написал программист, а не то что он хотел.
Функции/утилиты ждут в параметрах то что им надо, а не то что вы хотите.
Пепел Феникса вне форума Ответить с цитированием
Старый 02.11.2015, 17:47   #26
calypso
Форумчанин
 
Регистрация: 02.12.2012
Сообщений: 250
По умолчанию

wszName это WCHAR получается. Пробовал и gcnew String(), и ,marshal_as<> - все равно выводит квадратики.
Код:
listBox1->Items->Add("Имя интерфейса: "+msclr::interop::marshal_as<String^>(pIfRow->wszName));
label1->Text=("Принято байт: "+(pIfRow->dwInOctets).ToString());
label2->Text=("Отправлено байт: "+(pIfRow->dwOutOctets).ToString());
Параметры в формате DWORD конвертируются без проблем.
calypso вне форума Ответить с цитированием
Старый 03.11.2015, 13:45   #27
calypso
Форумчанин
 
Регистрация: 02.12.2012
Сообщений: 250
По умолчанию

Интересно что на Windows 8.1 под Visual Studio 2012 всё отображается как надо.
Только wszName это не "Сетевое подключение 8", а больше похоже на идентификатор ветки реестра TCP/...
calypso вне форума Ответить с цитированием
Старый 05.11.2015, 01:11   #28
calypso
Форумчанин
 
Регистрация: 02.12.2012
Сообщений: 250
По умолчанию

Получилась такая штука:
Код:
private: System::Void timer1_Tick(System::Object^  sender, System::EventArgs^  e) {
				 time1=GetTickCount();
				 DWORD dwSize=0;
				 DWORD dwRetVal=0;
				 int i,j;
				 MIB_IFTABLE *pIfTable;
				 MIB_IFROW *pIfRow;
				 int oshibka;
				 pIfTable=(MIB_IFTABLE*) MALLOC(sizeof(MIB_IFTABLE));
				 //инициализация GetIfTable чтобы получить размер dwSize
				 dwSize=sizeof(MIB_IFTABLE);
				 if (GetIfTable(pIfTable,&dwSize,0)==ERROR_INSUFFICIENT_BUFFER)
					 {
						 FREE(pIfTable);
						 pIfTable=(MIB_IFTABLE*) MALLOC(dwSize);
					 }
					 //второй вызов GetIfTable который должен завершиться без ошибок
					 if (GetIfTable(pIfTable,&dwSize,0)==NO_ERROR) 
						 {
							 if (pIfTable->dwNumEntries>0)
							 {
								pIfRow=(MIB_IFROW*) MALLOC(sizeof(MIB_IFROW));
								if (pIfRow==NULL)
								{
									if (pIfRow!=NULL)
									{
										FREE(pIfTable);
										pIfTable=NULL;
									}
								}
							 }
					   }
					 else 
						 {
							 oshibka=GetLastError();
						    }
					 for (i=0;i<(int)pIfTable->dwNumEntries;i++)
					 {
						 pIfRow->dwIndex=pIfTable->table[i].dwIndex;
						 if ((dwRetVal=GetIfEntry(pIfRow))==NO_ERROR)
						 {
							 if ((pIfRow->wszName!=NULL) && (pIfRow->dwType==IF_TYPE_ETHERNET_CSMACD))
						     {
							//	listBox1->Items->Add("Имя интерфейса: "+msclr::interop::marshal_as<String^>(pIfRow->wszName));
							double down1=Convert::ToDouble((pIfRow->dwInOctets)/1024.0/1024.0);
							double up1=Convert::ToDouble((pIfRow->dwOutOctets)/1024.0/1024.0);
							label1->Text=("Принято байт: "+(pIfRow->dwInOctets).ToString()+" ("+Convert::ToString(Math::Round(down1,2))+" МБ)");
							label2->Text=("Отправлено байт: "+(pIfRow->dwOutOctets).ToString()+" ("+Convert::ToString(Math::Round(up1,2))+" МБ)");
							if (counter>0)
							{
								if (time1==time2) time1=time1+1;
								label3->Text=("Скорость приема: "+(((pIfRow->dwInOctets-download1)/(time1-time2)).ToString()));
							    label4->Text=("Скорость отправки: "+(((pIfRow->dwOutOctets-upload1)/(time1-time2)).ToString()));
							}
							download1=pIfRow->dwInOctets;
							upload1=pIfRow->dwOutOctets;
							time2=GetTickCount();
							counter++;
							 }
						 }
					 }
				  }
private: System::Void Form1_Load(System::Object^  sender, System::EventArgs^  e) {
			 counter=0;
		 }
Если в системе 1 сетевой интерфейс, то проблем вообще нет. Работает как часы.
У меня сетевых карт 3 штуки + Виста лепит несколько левых "интерфейсов". Появилась проблема, как отсортировать реальные интерфейсы из мусора:
calypso вне форума Ответить с цитированием
Старый 06.11.2015, 13:43   #29
calypso
Форумчанин
 
Регистрация: 02.12.2012
Сообщений: 250
По умолчанию

Нашел и на Паскале ошибку. Вместо:
Код:
if  GetIfTable(nil, dwSize, False)= ERROR_INSUFFICIENT_BUFFER
должно быть
Код:
if  GetIfTable(ifTable, dwSize, False)= ERROR_INSUFFICIENT_BUFFER
Что впрочем, логично, никакого смысла передавать функции пустой параметр nil нет. Наверно это такое пасхальное яйцо автора кода, чтобы бездумно не копировали у него исходник.
calypso вне форума Ответить с цитированием
Старый 06.11.2015, 14:47   #30
waleri
Старожил
 
Регистрация: 13.07.2012
Сообщений: 6,493
По умолчанию

dwSize = 0, тогда можно передавать NULL.
waleri вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц

Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск


Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Как узнать скорость передачи данных (при копировании файлов) по сети calypso Работа с сетью в Delphi 0 02.12.2012 19:56
Сканирование документов по сети / Scan over Ethernet mixael Работа с сетью в Delphi 0 08.10.2010 11:03
Как определить текущую строку StringGrid Veiron Общие вопросы Delphi 2 24.09.2009 03:03
Определить текущую ячейку на листе НикНик Microsoft Office Excel 5 18.08.2008 09:40
Как определить IP-адресс компьютера в локальной сети? SalasAndriy C/C++ Сетевое программирование 2 29.11.2007 02:09