Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
W
wine-winehq
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Registry
Registry
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
wine
wine-winehq
Commits
090f5974
Commit
090f5974
authored
May 13, 2003
by
Juan Lang
Committed by
Alexandre Julliard
May 13, 2003
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Use iphlpapi to implement SIO_GET_INTERFACE_LIST in WSAIoctl, and
corrects iiFlags entry in the returned interface list.
parent
0ae5c5fc
Hide whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
81 additions
and
226 deletions
+81
-226
Makefile.in
dlls/winsock/Makefile.in
+1
-1
socket.c
dlls/winsock/socket.c
+80
-225
No files found.
dlls/winsock/Makefile.in
View file @
090f5974
...
...
@@ -4,7 +4,7 @@ TOPOBJDIR = ../..
SRCDIR
=
@srcdir@
VPATH
=
@srcdir@
MODULE
=
ws2_32.dll
IMPORTS
=
user32 kernel32 ntdll
IMPORTS
=
user32
iphlpapi
kernel32 ntdll
ALTNAMES
=
winsock.dll
LDDLLFLAGS
=
@LDDLLFLAGS@
...
...
dlls/winsock/socket.c
View file @
090f5974
...
...
@@ -117,6 +117,7 @@
#include "wine/winsock16.h"
#include "winnt.h"
#include "wownt32.h"
#include "iphlpapi.h"
#include "wine/server.h"
#include "wine/debug.h"
...
...
@@ -206,10 +207,6 @@ typedef struct /* WSAAsyncSelect() control struct */
#define WS_MAX_SOCKETS_PER_PROCESS 128
/* reasonable guess */
#define WS_MAX_UDP_DATAGRAM 1024
#define PROCFS_NETDEV_FILE "/proc/net/dev"
/* Points to the file in the /proc fs
that lists the network devices.
Do we need an #ifdef LINUX for this? */
static
void
*
he_buffer
;
/* typecast for Win16/32 ws_hostent */
static
SEGPTR
he_buffer_seg
;
static
void
*
se_buffer
;
/* typecast for Win16/32 ws_servent */
...
...
@@ -1983,122 +1980,101 @@ INT WINAPI WSAIoctl (SOCKET s,
case
SIO_GET_INTERFACE_LIST
:
{
INTERFACE_INFO
*
intArray
=
(
INTERFACE_INFO
*
)
lpbOutBuffer
;
int
i
,
numInt
;
struct
ifreq
ifInfo
;
char
ifName
[
512
];
DWORD
size
,
numInt
,
apiReturn
;
TRACE
(
"-> SIO_GET_INTERFACE_LIST request
\n
"
);
/* FIXME: length of output buffer not checked */
numInt
=
WSAIOCTL_GetInterfaceCount
(
);
if
(
numInt
<
0
)
apiReturn
=
GetAdaptersInfo
(
NULL
,
&
size
);
if
(
apiReturn
==
ERROR_NO_DATA
)
{
ERR
(
"Unable to open /proc filesystem to determine number of network interfaces!
\n
"
);
close
(
fd
);
WSASetLastError
(
WSAEINVAL
);
return
(
SOCKET_ERROR
);
numInt
=
0
;
}
for
(
i
=
0
;
i
<
numInt
;
i
++
)
else
if
(
apiReturn
==
ERROR_BUFFER_OVERFLOW
)
{
if
(
!
WSAIOCTL_GetInterfaceName
(
i
,
ifName
))
{
ERR
(
"Error parsing /proc filesystem!
\n
"
);
close
(
fd
);
WSASetLastError
(
WSAEINVAL
);
return
(
SOCKET_ERROR
);
}
ifInfo
.
ifr_addr
.
sa_family
=
AF_INET
;
PIP_ADAPTER_INFO
table
=
(
PIP_ADAPTER_INFO
)
HeapAlloc
(
GetProcessHeap
(),
0
,
size
);
/* IP Address */
strcpy
(
ifInfo
.
ifr_name
,
ifName
);
if
(
ioctl
(
fd
,
SIOCGIFADDR
,
&
ifInfo
)
<
0
)
if
(
table
)
{
ERR
(
"Error obtaining IP address
\n
"
);
close
(
fd
);
WSASetLastError
(
WSAEINVAL
);
return
(
SOCKET_ERROR
);
if
(
GetAdaptersInfo
(
table
,
&
size
)
==
NO_ERROR
)
{
PIP_ADAPTER_INFO
ptr
;
for
(
ptr
=
table
,
numInt
=
0
;
ptr
;
ptr
=
ptr
->
Next
,
intArray
++
,
numInt
++
)
{
unsigned
int
addr
,
mask
,
bcast
;
struct
ifreq
ifInfo
;
/* Socket Status Flags */
strncpy
(
ifInfo
.
ifr_name
,
ptr
->
AdapterName
,
IFNAMSIZ
);
ifInfo
.
ifr_name
[
IFNAMSIZ
-
1
]
=
'\0'
;
if
(
ioctl
(
fd
,
SIOCGIFFLAGS
,
&
ifInfo
)
<
0
)
{
ERR
(
"Error obtaining status flags for socket!
\n
"
);
HeapFree
(
GetProcessHeap
(),
0
,
table
);
close
(
fd
);
WSASetLastError
(
WSAEINVAL
);
return
(
SOCKET_ERROR
);
}
else
{
/* set flags; the values of IFF_* are not the same
under Linux and Windows, therefore must generate
new flags */
intArray
->
iiFlags
=
0
;
if
(
ifInfo
.
ifr_flags
&
IFF_BROADCAST
)
intArray
->
iiFlags
|=
WS_IFF_BROADCAST
;
if
(
ifInfo
.
ifr_flags
&
IFF_POINTOPOINT
)
intArray
->
iiFlags
|=
WS_IFF_POINTTOPOINT
;
if
(
ifInfo
.
ifr_flags
&
IFF_LOOPBACK
)
intArray
->
iiFlags
|=
WS_IFF_LOOPBACK
;
if
(
ifInfo
.
ifr_flags
&
IFF_UP
)
intArray
->
iiFlags
|=
WS_IFF_UP
;
}
addr
=
inet_addr
(
ptr
->
IpAddressList
.
IpAddress
.
String
);
mask
=
inet_addr
(
ptr
->
IpAddressList
.
IpMask
.
String
);
bcast
=
addr
|
(
addr
&
!
mask
);
intArray
->
iiAddress
.
AddressIn
.
sin_family
=
AF_INET
;
intArray
->
iiAddress
.
AddressIn
.
sin_port
=
0
;
intArray
->
iiAddress
.
AddressIn
.
sin_addr
.
WS_s_addr
=
addr
;
intArray
->
iiNetmask
.
AddressIn
.
sin_family
=
AF_INET
;
intArray
->
iiNetmask
.
AddressIn
.
sin_port
=
0
;
intArray
->
iiNetmask
.
AddressIn
.
sin_addr
.
WS_s_addr
=
mask
;
intArray
->
iiBroadcastAddress
.
AddressIn
.
sin_family
=
AF_INET
;
intArray
->
iiBroadcastAddress
.
AddressIn
.
sin_port
=
0
;
intArray
->
iiBroadcastAddress
.
AddressIn
.
sin_addr
.
WS_s_addr
=
bcast
;
}
HeapFree
(
GetProcessHeap
(),
0
,
table
);
}
else
{
ERR
(
"Unable to get interface table!
\n
"
);
close
(
fd
);
HeapFree
(
GetProcessHeap
(),
0
,
table
);
WSASetLastError
(
WSAEINVAL
);
return
(
SOCKET_ERROR
);
}
}
else
{
struct
WS_sockaddr_in
*
ipTemp
=
(
struct
WS_sockaddr_in
*
)
&
ifInfo
.
ifr_addr
;
intArray
->
iiAddress
.
AddressIn
.
sin_family
=
AF_INET
;
intArray
->
iiAddress
.
AddressIn
.
sin_port
=
ipTemp
->
sin_port
;
intArray
->
iiAddress
.
AddressIn
.
sin_addr
.
WS_s_addr
=
ipTemp
->
sin_addr
.
S_un
.
S_addr
;
}
/* Broadcast Address */
strcpy
(
ifInfo
.
ifr_name
,
ifName
);
if
(
ioctl
(
fd
,
SIOCGIFBRDADDR
,
&
ifInfo
)
<
0
)
{
ERR
(
"Error obtaining Broadcast IP address
\n
"
);
close
(
fd
);
WSASetLastError
(
WSAEINVAL
);
return
(
SOCKET_ERROR
);
}
else
{
struct
WS_sockaddr_in
*
ipTemp
=
(
struct
WS_sockaddr_in
*
)
&
ifInfo
.
ifr_broadaddr
;
intArray
->
iiBroadcastAddress
.
AddressIn
.
sin_family
=
AF_INET
;
intArray
->
iiBroadcastAddress
.
AddressIn
.
sin_port
=
ipTemp
->
sin_port
;
intArray
->
iiBroadcastAddress
.
AddressIn
.
sin_addr
.
WS_s_addr
=
ipTemp
->
sin_addr
.
S_un
.
S_addr
;
}
/* Subnet Mask */
strcpy
(
ifInfo
.
ifr_name
,
ifName
);
if
(
ioctl
(
fd
,
SIOCGIFNETMASK
,
&
ifInfo
)
<
0
)
{
ERR
(
"Error obtaining Subnet IP address
\n
"
);
close
(
fd
);
WSASetLastError
(
WSAEINVAL
);
return
(
SOCKET_ERROR
);
}
else
{
/* Trying to avoid some compile problems across platforms.
(Linux, FreeBSD, Solaris...) */
#ifndef ifr_netmask
#ifndef ifr_addr
intArray
->
iiNetmask
.
AddressIn
.
sin_family
=
AF_INET
;
intArray
->
iiNetmask
.
AddressIn
.
sin_port
=
0
;
intArray
->
iiNetmask
.
AddressIn
.
sin_addr
.
WS_s_addr
=
0
;
ERR
(
"Unable to determine Netmask on your platform!
\n
"
);
#else
struct
WS_sockaddr_in
*
ipTemp
=
(
struct
WS_sockaddr_in
*
)
&
ifInfo
.
ifr_addr
;
intArray
->
iiNetmask
.
AddressIn
.
sin_family
=
AF_INET
;
intArray
->
iiNetmask
.
AddressIn
.
sin_port
=
ipTemp
->
sin_port
;
intArray
->
iiNetmask
.
AddressIn
.
sin_addr
.
WS_s_addr
=
ipTemp
->
sin_addr
.
S_un
.
S_addr
;
#endif
#else
struct
WS_sockaddr_in
*
ipTemp
=
(
struct
WS_sockaddr_in
*
)
&
ifInfo
.
ifr_netmask
;
intArray
->
iiNetmask
.
AddressIn
.
sin_family
=
AF_INET
;
intArray
->
iiNetmask
.
AddressIn
.
sin_port
=
ipTemp
->
sin_port
;
intArray
->
iiNetmask
.
AddressIn
.
sin_addr
.
WS_s_addr
=
ipTemp
->
sin_addr
.
S_un
.
S_addr
;
#endif
}
/* Socket Status Flags */
strcpy
(
ifInfo
.
ifr_name
,
ifName
);
if
(
ioctl
(
fd
,
SIOCGIFFLAGS
,
&
ifInfo
)
<
0
)
{
ERR
(
"Error obtaining status flags for socket!
\n
"
);
close
(
fd
);
WSASetLastError
(
WSAEINVAL
);
return
(
SOCKET_ERROR
);
}
else
{
/* FIXME - Is this the right flag to use? */
intArray
->
iiFlags
=
ifInfo
.
ifr_flags
;
}
intArray
++
;
/* Prepare for another interface */
}
else
{
ERR
(
"Unable to get interface table!
\n
"
);
close
(
fd
);
WSASetLastError
(
WSAEINVAL
);
return
(
SOCKET_ERROR
);
}
/* Calculate the size of the array being returned */
*
lpcbBytesReturned
=
sizeof
(
INTERFACE_INFO
)
*
numInt
;
break
;
...
...
@@ -2125,127 +2101,6 @@ INT WINAPI WSAIoctl (SOCKET s,
}
/*
Helper function for WSAIoctl - Get count of the number of interfaces
by parsing /proc filesystem.
*/
int
WSAIOCTL_GetInterfaceCount
(
void
)
{
FILE
*
procfs
;
char
buf
[
512
];
/* Size doesn't matter, something big */
int
intcnt
=
0
;
/* Open /proc filesystem file for network devices */
procfs
=
fopen
(
PROCFS_NETDEV_FILE
,
"r"
);
if
(
!
procfs
)
{
/* If we can't open the file, return an error */
return
(
-
1
);
}
/* Omit first two lines, they are only headers */
fgets
(
buf
,
sizeof
buf
,
procfs
);
fgets
(
buf
,
sizeof
buf
,
procfs
);
while
(
fgets
(
buf
,
sizeof
buf
,
procfs
))
{
/* Each line in the file represents a network interface */
intcnt
++
;
}
fclose
(
procfs
);
return
(
intcnt
);
}
/*
Helper function for WSAIoctl - Get name of device from interface number
by parsing /proc filesystem.
*/
int
WSAIOCTL_GetInterfaceName
(
int
intNumber
,
char
*
intName
)
{
FILE
*
procfs
;
char
buf
[
512
];
/* Size doesn't matter, something big */
int
i
;
/* Open /proc filesystem file for network devices */
procfs
=
fopen
(
PROCFS_NETDEV_FILE
,
"r"
);
if
(
!
procfs
)
{
/* If we can't open the file, return an error */
return
(
-
1
);
}
/* Omit first two lines, they are only headers */
fgets
(
buf
,
sizeof
(
buf
),
procfs
);
fgets
(
buf
,
sizeof
(
buf
),
procfs
);
for
(
i
=
0
;
i
<
intNumber
;
i
++
)
{
/* Skip the lines that don't interest us. */
fgets
(
buf
,
sizeof
(
buf
),
procfs
);
}
fgets
(
buf
,
sizeof
(
buf
),
procfs
);
/* This is the line we want */
/* Parse out the line, grabbing only the name of the device
to the intName variable
The Line comes in like this: (we only care about the device name)
lo: 21970 377 0 0 0 0 0 0 21970 377 0 0 0 0 0 0
*/
i
=
0
;
while
(
isspace
(
buf
[
i
]))
/* Skip initial space(s) */
{
i
++
;
}
while
(
buf
[
i
])
{
if
(
isspace
(
buf
[
i
]))
{
break
;
}
if
(
buf
[
i
]
==
':'
)
/* FIXME: Not sure if this block (alias detection) works properly */
{
/* This interface could be an alias... */
int
hold
=
i
;
char
*
dotname
=
intName
;
*
intName
++
=
buf
[
i
++
];
while
(
isdigit
(
buf
[
i
]))
{
*
intName
++
=
buf
[
i
++
];
}
if
(
buf
[
i
]
!=
':'
)
{
/* ... It wasn't, so back up */
i
=
hold
;
intName
=
dotname
;
}
if
(
buf
[
i
]
==
'\0'
)
{
fclose
(
procfs
);
return
(
FALSE
);
}
i
++
;
break
;
}
*
intName
++
=
buf
[
i
++
];
}
*
intName
++
=
'\0'
;
fclose
(
procfs
);
return
(
TRUE
);
}
/***********************************************************************
* ioctlsocket (WS2_32.10)
*/
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment