⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ethsock.cxx

📁 pwlib源码库
💻 CXX
📖 第 1 页 / 共 4 页
字号:
{  if (!IsOpen())    return SetErrorValues(NotOpen, EBADF);  DWORD filter = 0;  if (!driver->QueryOid(OID_GEN_CURRENT_PACKET_FILTER, filter))    return SetErrorValues(Miscellaneous, driver->GetLastError()|PWIN32ErrorFlag);  if (filter == 0)    return PEthSocket::FilterDirected;  mask = 0;  for (PINDEX i = 0; i < PARRAYSIZE(FilterMasks); i++) {    if ((filter&FilterMasks[i].ndis) != 0)      mask |= FilterMasks[i].pwlib;  }  type = (WORD)filterType;  return TRUE;}BOOL PEthSocket::SetFilter(unsigned filter, WORD type){  if (!IsOpen())    return SetErrorValues(NotOpen, EBADF);  DWORD bits = 0;  for (PINDEX i = 0; i < PARRAYSIZE(FilterMasks); i++) {    if ((filter&FilterMasks[i].pwlib) != 0)      bits |= FilterMasks[i].ndis;  }  if (!driver->SetOid(OID_GEN_CURRENT_PACKET_FILTER, bits))    return SetErrorValues(Miscellaneous, driver->GetLastError()|PWIN32ErrorFlag);  filterType = type;  return TRUE;}PEthSocket::MediumTypes PEthSocket::GetMedium(){  if (!IsOpen()) {    SetErrorValues(NotOpen, EBADF);    return NumMediumTypes;  }  DWORD medium = 0xffffffff;  if (!driver->QueryOid(OID_GEN_MEDIA_SUPPORTED, medium) || medium == 0xffffffff) {    SetErrorValues(Miscellaneous, driver->GetLastError()|PWIN32ErrorFlag);    return NumMediumTypes;  }  static const DWORD MediumValues[NumMediumTypes] = {    0xffffffff, NdisMedium802_3, NdisMediumWan, 0xffffffff  };  for (int type = Medium802_3; type < NumMediumTypes; type++) {    if (MediumValues[type] == medium)      return (MediumTypes)type;  }  return MediumUnknown;}BOOL PEthSocket::Read(void * data, PINDEX length){  if (!IsOpen())    return SetErrorValues(NotOpen, EBADF, LastReadError);  PINDEX idx;  PINDEX numBuffers = readBuffers.GetSize();  do {    HANDLE handles[MAXIMUM_WAIT_OBJECTS];    for (idx = 0; idx < numBuffers; idx++) {      PWin32PacketBuffer & buffer = readBuffers[idx];      if (buffer.InProgress()) {        if (WaitForSingleObject(buffer.GetEvent(), 0) == WAIT_OBJECT_0)          if (!buffer.ReadComplete(*driver))            return ConvertOSError(-1, LastReadError);      }      else {        if (!buffer.ReadAsync(*driver))          return ConvertOSError(-1, LastReadError);      }      if (buffer.IsCompleted() && buffer.IsType(filterType)) {        lastReadCount = buffer.GetData(data, length);        return TRUE;      }      handles[idx] = buffer.GetEvent();    }    DWORD result;    PINDEX retries = 100;    for (;;) {      result = WaitForMultipleObjects(numBuffers, handles, FALSE, INFINITE);      if (result >= WAIT_OBJECT_0 && result < WAIT_OBJECT_0 + (DWORD)numBuffers)        break;      if (::GetLastError() != ERROR_INVALID_HANDLE || retries == 0)        return ConvertOSError(-1, LastReadError);      retries--;    }    idx = result - WAIT_OBJECT_0;    if (!readBuffers[idx].ReadComplete(*driver))      return ConvertOSError(-1, LastReadError);  } while (!readBuffers[idx].IsType(filterType));  lastReadCount = readBuffers[idx].GetData(data, length);  return TRUE;}BOOL PEthSocket::Write(const void * data, PINDEX length){  if (!IsOpen())    return SetErrorValues(NotOpen, EBADF, LastWriteError);  HANDLE handles[MAXIMUM_WAIT_OBJECTS];  PINDEX numBuffers = writeBuffers.GetSize();  PINDEX idx;  for (idx = 0; idx < numBuffers; idx++) {    PWin32PacketBuffer & buffer = writeBuffers[idx];    if (buffer.InProgress()) {      if (WaitForSingleObject(buffer.GetEvent(), 0) == WAIT_OBJECT_0)        if (!buffer.WriteComplete(*driver))          return ConvertOSError(-1, LastWriteError);    }    if (!buffer.InProgress()) {      lastWriteCount = buffer.PutData(data, length);      return ConvertOSError(buffer.WriteAsync(*driver) ? 0 : -1, LastWriteError);    }    handles[idx] = buffer.GetEvent();  }  DWORD result = WaitForMultipleObjects(numBuffers, handles, FALSE, INFINITE);  if (result < WAIT_OBJECT_0 || result >= WAIT_OBJECT_0 + (DWORD) numBuffers)    return ConvertOSError(-1, LastWriteError);  idx = result - WAIT_OBJECT_0;  if (!writeBuffers[idx].WriteComplete(*driver))    return ConvertOSError(-1, LastWriteError);  lastWriteCount = writeBuffers[idx].PutData(data, length);  return ConvertOSError(writeBuffers[idx].WriteAsync(*driver) ? 0 : -1, LastWriteError);}///////////////////////////////////////////////////////////////////////////////PWin32PacketBuffer::PWin32PacketBuffer(PINDEX sz)  : PBYTEArray(sz){  status = Uninitialised;  count = 0;}PINDEX PWin32PacketBuffer::GetData(void * buf, PINDEX size){  if (count > (DWORD)size)    count = size;  memcpy(buf, theArray, count);  return count;}PINDEX PWin32PacketBuffer::PutData(const void * buf, PINDEX length){  count = min(GetSize(), length);  memcpy(theArray, buf, count);  return count;}BOOL PWin32PacketBuffer::ReadAsync(PWin32PacketDriver & pkt){  if (status == Progressing)    return FALSE;  status = Uninitialised;  if (!pkt.BeginRead(theArray, GetSize(), count, overlap))    return FALSE;  if (pkt.GetLastError() == ERROR_SUCCESS)    status = Completed;  else    status = Progressing;  return TRUE;}BOOL PWin32PacketBuffer::ReadComplete(PWin32PacketDriver & pkt){  if (status != Progressing)    return status == Completed;  if (!pkt.CompleteIO(count, overlap)) {    status = Uninitialised;    return FALSE;  }  status = Completed;  return TRUE;}BOOL PWin32PacketBuffer::WriteAsync(PWin32PacketDriver & pkt){  if (status == Progressing)    return FALSE;  status = Uninitialised;  if (!pkt.BeginWrite(theArray, count, overlap))    return FALSE;  if (pkt.GetLastError() == ERROR_SUCCESS)    status = Completed;  else    status = Progressing;  return TRUE;}BOOL PWin32PacketBuffer::WriteComplete(PWin32PacketDriver & pkt){  if (status != Progressing)    return status == Completed;  DWORD dummy;  if (pkt.CompleteIO(dummy, overlap)) {    status = Completed;    return TRUE;  }  status = Uninitialised;  return FALSE;}BOOL PWin32PacketBuffer::IsType(WORD filterType) const{  if (filterType == PEthSocket::TypeAll)    return TRUE;  const PEthSocket::Frame * frame = (const PEthSocket::Frame *)theArray;  WORD len_or_type = ntohs(frame->snap.length);  if (len_or_type > sizeof(*frame))    return len_or_type == filterType;  if (frame->snap.dsap == 0xaa && frame->snap.ssap == 0xaa)    return ntohs(frame->snap.type) == filterType;   // SNAP header  if (frame->snap.dsap == 0xff && frame->snap.ssap == 0xff)    return PEthSocket::TypeIPX == filterType;   // Special case for Novell netware's stuffed up 802.3  if (frame->snap.dsap == 0xe0 && frame->snap.ssap == 0xe0)    return PEthSocket::TypeIPX == filterType;   // Special case for Novell netware's 802.2  return frame->snap.dsap == filterType;    // A pure 802.2 protocol id}////////////////////////////////////////////////////////////////////////////////*static PMutex & GetSNMPMutex(){  static PMutex snmpmutex;  return snmpmutex;}*/BOOL PIPSocket::GetGatewayAddress(Address & addr){  PWaitAndSignal m(GetSNMPMutex());  PWin32SnmpLibrary & snmp = PWin32SnmpLibrary::Current();  PWin32AsnOid gatewayOid = "1.3.6.1.2.1.4.21.1.7.0.0.0.0";  return snmp.GetOid(gatewayOid, addr);}PString PIPSocket::GetGatewayInterface(){  PWaitAndSignal m(GetSNMPMutex());  PWin32SnmpLibrary & snmp = PWin32SnmpLibrary::Current();  AsnInteger ifNum = -1;  PWin32AsnOid gatewayOid = "1.3.6.1.2.1.4.21.1.2.0.0.0.0";  if (!snmp.GetOid(gatewayOid, ifNum) && ifNum >= 0)    return PString::Empty();  return snmp.GetInterfaceName(ifNum);}PIPSocket::Address PIPSocket::GetGatewayInterfaceAddress(){  PWaitAndSignal m(GetSNMPMutex());  PWin32SnmpLibrary & snmp = PWin32SnmpLibrary::Current();  AsnInteger ifNum = -1;  PWin32AsnOid gatewayOid = "1.3.6.1.2.1.4.21.1.2.0.0.0.0";  if (!snmp.GetOid(gatewayOid, ifNum) && ifNum >= 0)    return PString::Empty();  return snmp.GetInterfaceAddress(ifNum);}BOOL PIPSocket::GetRouteTable(RouteTable & table){  PWaitAndSignal m(GetSNMPMutex());  PWin32SnmpLibrary & snmp = snmp.Current();  table.RemoveAll();  PWin32AsnOid baseOid = "1.3.6.1.2.1.4.21.1";  PWin32AsnOid oid = baseOid;  DWORD lastVariable = 1;  PWin32AsnAny value;  PLongArray ifNum;  PINDEX idx = 0;  while (snmp.GetNextOid(oid, value) && (baseOid *= oid)) {    if (lastVariable != oid[9]) {      lastVariable = oid[9];      if (lastVariable == 2)        ifNum.SetSize(table.GetSize());      idx = 0;    }    switch (lastVariable) {      case 1 : // network address        {          Address addr;          if (!value.GetIpAddress(addr))            return FALSE;  // Very confused route table          table.Append(new RouteEntry(addr));          break;        }      case 2 : // device interface        if (!value.GetInteger(ifNum[idx]))          return FALSE;        break;      case 3 : // metric        if (!value.GetInteger(table[idx].metric))          return FALSE;        break;      case 7 : // Get destination (next hop)        if (!value.GetIpAddress(table[idx].destination))          return FALSE;        break;      case 11 : // Get mask        if (!value.GetIpAddress(table[idx].net_mask))          return FALSE;        break;    }    idx++;  }  for (idx = 0; idx < table.GetSize(); idx++)    table[idx].interfaceName = snmp.GetInterfaceName(ifNum[idx]);  return TRUE;}unsigned PIPSocket::AsNumeric(PIPSocket::Address addr)		{ 	return ((addr.Byte1() << 24) | (addr.Byte2()  << 16) |           (addr.Byte3()  << 8) | addr.Byte4()); }PIPSocket::Address PIPSocket::GetRouteAddress(PIPSocket::Address RemoteAddress){Address localaddr;	if (!RemoteAddress.IsRFC1918()) {				 // Remote Address is not Local		if (!GetNetworkInterface(localaddr)) {			 // User not connected directly to Internet			localaddr = GetGatewayInterfaceAddress(); // Get the default Gateway NIC address			 if ( localaddr != 0 )					  // No connection to the Internet?						 return localaddr;		}	} else {		PIPSocket::InterfaceTable interfaceTable;		if (PIPSocket::GetInterfaceTable(interfaceTable)) {			PINDEX i;			for (i = 0; i < interfaceTable.GetSize(); ++i) {				localaddr = interfaceTable[i].GetAddress();				if (!localaddr.IsLoopback() && localaddr.IsRFC1918()) {					if (IsAddressReachable(localaddr,							interfaceTable[i].GetNetMask(),RemoteAddress))								return localaddr;				}			}		}	}	return 0;}BOOL PIPSocket::IsAddressReachable(PIPSocket::Address LocalIP,								   PIPSocket::Address LocalMask, 								   PIPSocket::Address RemoteIP){	BYTE t = 255;	int t1=t,t2=t,t3 =t,t4=t;	int b1=0,b2=0,b3=0,b4=0;	if ((int)LocalMask.Byte1() > 0)	{	t1 = LocalIP.Byte1() + (t-LocalMask.Byte1()); b1 = LocalIP.Byte1();}		if ((int)LocalMask.Byte2() > 0)	{	t2 = LocalIP.Byte2() + (t-LocalMask.Byte2()); b2 = LocalIP.Byte2();}	if ((int)LocalMask.Byte3() > 0)	{	t3 = LocalIP.Byte3() + (t-LocalMask.Byte3()); b3 = LocalIP.Byte3();}	if ((int)LocalMask.Byte4() > 0)	{	t4 = LocalIP.Byte4() + (t-LocalMask.Byte4()); b4 = LocalIP.Byte4();}	Address lt = Address((BYTE)t1,(BYTE)t2,(BYTE)t3,(BYTE)t4);	Address lb = Address((BYTE)b1,(BYTE)b2,(BYTE)b3,(BYTE)b4);		if (AsNumeric(RemoteIP) > AsNumeric(lb) && 				AsNumeric(lt) > AsNumeric(RemoteIP))					return TRUE;	return FALSE;}PString PIPSocket::GetInterface(PIPSocket::Address addr){  PIPSocket::InterfaceTable if_table;  if (PIPSocket::GetInterfaceTable( if_table ) ) {	  for (PINDEX i=0; i < if_table.GetSize(); i++) {		PIPSocket::InterfaceEntry if_entry = if_table[i];		   if (if_entry.GetAddress() == addr) 			   return if_entry.GetName();	  }          }  return PString();}BOOL PIPSocket::GetInterfaceTable(InterfaceTable & table){  PWin32SnmpLibrary & snmp = snmp.Current();  PWaitAndSignal m(GetSNMPMutex());  table.RemoveAll();  /*  if (!snmp.IsLoaded()) {    // Error loading the SNMP library, fail safe to using whatever the    // address of the local host is.    Address ipAddr;    if (!GetHostAddress(ipAddr))      return FALSE;    Address netMask(255,255,255,255);    table.Append(new InterfaceEntry("FailSafe Interface", ipAddr, netMask, PString::Empty()));    table.Append(new InterfaceEntry("localhost", PIPSocket::Address(), netMask, PString::Empty()));    return TRUE;  }  */  PWin32AsnOid baseOid = "1.3.6.1.2.1.4.20.1";  PWin32AsnOid oid = baseOid;  PWin32AsnAny value;  while (snmp.GetNextOid(oid, value)) {    if (!(baseOid *= oid))      break;    if (value.asnType != ASN_IPADDRESS)      break;    Address ipAddr;    value.GetIpAddress(ipAddr);    oid[9] = 3;    Address netMask;    if (!snmp.GetOid(oid, netMask))      break;    oid[9] = 2;    AsnInteger ifIndex = -1;    if (!snmp.GetOid(oid, ifIndex))      break;    PString macAddr;    PEthSocket::Address ifPhysAddress("");    PWin32AsnOid ifOid = "1.3.6.1.2.1.2.2.1.6.0";    ifOid[10] = ifIndex;    UINT len;    if (snmp.GetOid(ifOid, &ifPhysAddress, sizeof(ifPhysAddress), &len) && len > 0)      macAddr = ifPhysAddress;      PString name = snmp.GetInterfaceName(ipAddr);    if (name.IsEmpty()) {      PWin32AsnOid nameOid = "1.3.6.1.2.1.2.2.1.2.0";      nameOid[10] = ifIndex;      if (!snmp.GetOid(nameOid, name))        break;      name.MakeMinimumSize();    }#ifdef _WIN32_WCE // Getting rid of ghost ips    if ( !name.IsEmpty() )#endif      table.Append(new InterfaceEntry(name, ipAddr, netMask, macAddr));    oid[9] = 1;  }  return TRUE;}///////////////////////////////////////////////////////////////////////////////

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -