mirror of https://github.com/PCSX2/pcsx2.git
DEV9: Use correct buffer type in Win32 GetAdapter
Returned data is not sequenced IP_ADAPTER_ADDRESSES entries We will use implicit object creation avoid UB
This commit is contained in:
parent
3aff833b5c
commit
a6ddbdb879
|
@ -57,30 +57,34 @@ using namespace PacketReader::IP;
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
AdapterUtils::Adapter* AdapterUtils::GetAllAdapters(AdapterBuffer* buffer, bool includeHidden)
|
AdapterUtils::Adapter* AdapterUtils::GetAllAdapters(AdapterBuffer* buffer, bool includeHidden)
|
||||||
{
|
{
|
||||||
int neededSize = includeHidden ? 256 : 128;
|
// It is recommend to pre-allocate enough space to be able to call GetAdaptersAddresses just once.
|
||||||
std::unique_ptr<IP_ADAPTER_ADDRESSES[]> adapterInfo = std::make_unique<IP_ADAPTER_ADDRESSES[]>(neededSize);
|
// Also provide extra space if we are including hidden adapters.
|
||||||
ULONG dwBufLen = sizeof(IP_ADAPTER_ADDRESSES) * neededSize;
|
int neededSize = includeHidden ? 100000 : 50000;
|
||||||
|
// Each IP_ADAPTER_ADDRESSES will have pointers other structures which are also copied into this buffer.
|
||||||
|
// Subsequent IP_ADAPTER_ADDRESSES (accessed via .Next) are also not aligned to sizeof(IP_ADAPTER_ADDRESSES) boundaries.
|
||||||
|
std::unique_ptr<std::byte[]> adapterInfo = std::make_unique_for_overwrite<std::byte[]>(neededSize);
|
||||||
|
ULONG dwBufLen = neededSize;
|
||||||
|
|
||||||
DWORD dwStatus = GetAdaptersAddresses(
|
DWORD dwStatus = GetAdaptersAddresses(
|
||||||
AF_UNSPEC,
|
AF_UNSPEC,
|
||||||
GAA_FLAG_INCLUDE_PREFIX | GAA_FLAG_INCLUDE_GATEWAYS | (includeHidden ? GAA_FLAG_INCLUDE_ALL_INTERFACES : 0),
|
GAA_FLAG_INCLUDE_PREFIX | GAA_FLAG_INCLUDE_GATEWAYS | (includeHidden ? GAA_FLAG_INCLUDE_ALL_INTERFACES : 0),
|
||||||
NULL,
|
NULL,
|
||||||
adapterInfo.get(),
|
reinterpret_cast<PIP_ADAPTER_ADDRESSES>(adapterInfo.get()),
|
||||||
&dwBufLen);
|
&dwBufLen);
|
||||||
|
|
||||||
if (dwStatus == ERROR_BUFFER_OVERFLOW)
|
if (dwStatus == ERROR_BUFFER_OVERFLOW)
|
||||||
{
|
{
|
||||||
DevCon.WriteLn("DEV9: GetWin32Adapter() buffer too small, resizing");
|
DevCon.WriteLn("DEV9: GetWin32Adapter() buffer too small, resizing");
|
||||||
neededSize = dwBufLen / sizeof(IP_ADAPTER_ADDRESSES) + 1;
|
neededSize = dwBufLen + 500;
|
||||||
adapterInfo = std::make_unique<IP_ADAPTER_ADDRESSES[]>(neededSize);
|
adapterInfo = std::make_unique_for_overwrite<std::byte[]>(neededSize);
|
||||||
dwBufLen = sizeof(IP_ADAPTER_ADDRESSES) * neededSize;
|
dwBufLen = neededSize;
|
||||||
DevCon.WriteLn("DEV9: New size %i", neededSize);
|
DevCon.WriteLn("DEV9: New size %i", neededSize);
|
||||||
|
|
||||||
dwStatus = GetAdaptersAddresses(
|
dwStatus = GetAdaptersAddresses(
|
||||||
AF_UNSPEC,
|
AF_UNSPEC,
|
||||||
GAA_FLAG_INCLUDE_PREFIX | GAA_FLAG_INCLUDE_GATEWAYS | (includeHidden ? GAA_FLAG_INCLUDE_ALL_INTERFACES : 0),
|
GAA_FLAG_INCLUDE_PREFIX | GAA_FLAG_INCLUDE_GATEWAYS | (includeHidden ? GAA_FLAG_INCLUDE_ALL_INTERFACES : 0),
|
||||||
NULL,
|
NULL,
|
||||||
adapterInfo.get(),
|
reinterpret_cast<PIP_ADAPTER_ADDRESSES>(adapterInfo.get()),
|
||||||
&dwBufLen);
|
&dwBufLen);
|
||||||
}
|
}
|
||||||
if (dwStatus != ERROR_SUCCESS)
|
if (dwStatus != ERROR_SUCCESS)
|
||||||
|
@ -88,11 +92,12 @@ AdapterUtils::Adapter* AdapterUtils::GetAllAdapters(AdapterBuffer* buffer, bool
|
||||||
|
|
||||||
buffer->swap(adapterInfo);
|
buffer->swap(adapterInfo);
|
||||||
|
|
||||||
return buffer->get();
|
// Trigger implicit object creation.
|
||||||
|
return std::launder(reinterpret_cast<PIP_ADAPTER_ADDRESSES>(buffer->get()));
|
||||||
}
|
}
|
||||||
bool AdapterUtils::GetAdapter(const std::string& name, Adapter* adapter, AdapterBuffer* buffer)
|
bool AdapterUtils::GetAdapter(const std::string& name, Adapter* adapter, AdapterBuffer* buffer)
|
||||||
{
|
{
|
||||||
std::unique_ptr<IP_ADAPTER_ADDRESSES[]> adapterInfo;
|
std::unique_ptr<std::byte[]> adapterInfo;
|
||||||
PIP_ADAPTER_ADDRESSES pAdapter = GetAllAdapters(&adapterInfo);
|
PIP_ADAPTER_ADDRESSES pAdapter = GetAllAdapters(&adapterInfo);
|
||||||
if (pAdapter == nullptr)
|
if (pAdapter == nullptr)
|
||||||
return false;
|
return false;
|
||||||
|
@ -113,7 +118,7 @@ bool AdapterUtils::GetAdapter(const std::string& name, Adapter* adapter, Adapter
|
||||||
}
|
}
|
||||||
bool AdapterUtils::GetAdapterAuto(Adapter* adapter, AdapterBuffer* buffer)
|
bool AdapterUtils::GetAdapterAuto(Adapter* adapter, AdapterBuffer* buffer)
|
||||||
{
|
{
|
||||||
std::unique_ptr<IP_ADAPTER_ADDRESSES[]> adapterInfo;
|
std::unique_ptr<std::byte[]> adapterInfo;
|
||||||
PIP_ADAPTER_ADDRESSES pAdapter = GetAllAdapters(&adapterInfo);
|
PIP_ADAPTER_ADDRESSES pAdapter = GetAllAdapters(&adapterInfo);
|
||||||
if (pAdapter == nullptr)
|
if (pAdapter == nullptr)
|
||||||
return false;
|
return false;
|
||||||
|
|
|
@ -23,7 +23,7 @@ namespace AdapterUtils
|
||||||
{
|
{
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
typedef IP_ADAPTER_ADDRESSES Adapter;
|
typedef IP_ADAPTER_ADDRESSES Adapter;
|
||||||
typedef std::unique_ptr<IP_ADAPTER_ADDRESSES[]> AdapterBuffer;
|
typedef std::unique_ptr<std::byte[]> AdapterBuffer;
|
||||||
#elif defined(__POSIX__)
|
#elif defined(__POSIX__)
|
||||||
typedef ifaddrs Adapter;
|
typedef ifaddrs Adapter;
|
||||||
struct IfAdaptersDeleter
|
struct IfAdaptersDeleter
|
||||||
|
|
|
@ -221,7 +221,7 @@ std::vector<AdapterEntry> PCAPAdapter::GetAdapters()
|
||||||
entry.guid = std::string(&d->name[strlen(PCAPPREFIX)]);
|
entry.guid = std::string(&d->name[strlen(PCAPPREFIX)]);
|
||||||
|
|
||||||
IP_ADAPTER_ADDRESSES adapterInfo;
|
IP_ADAPTER_ADDRESSES adapterInfo;
|
||||||
std::unique_ptr<IP_ADAPTER_ADDRESSES[]> buffer;
|
AdapterUtils::AdapterBuffer buffer;
|
||||||
|
|
||||||
if (AdapterUtils::GetAdapter(entry.guid, &adapterInfo, &buffer))
|
if (AdapterUtils::GetAdapter(entry.guid, &adapterInfo, &buffer))
|
||||||
entry.name = StringUtil::WideStringToUTF8String(std::wstring(adapterInfo.FriendlyName));
|
entry.name = StringUtil::WideStringToUTF8String(std::wstring(adapterInfo.FriendlyName));
|
||||||
|
|
Loading…
Reference in New Issue