diff options
| author | Eli Zaretskii | 2013-02-15 11:01:13 +0200 |
|---|---|---|
| committer | Eli Zaretskii | 2013-02-15 11:01:13 +0200 |
| commit | bcf7fe2aeff7e3aacbfae08ca6001f7615a06709 (patch) | |
| tree | cf9259731e5331bd8ca469c5107f13e713d8d28b /src/w32.c | |
| parent | 974c7646ec5b2985a50007c9d599154d667df349 (diff) | |
| download | emacs-bcf7fe2aeff7e3aacbfae08ca6001f7615a06709.tar.gz emacs-bcf7fe2aeff7e3aacbfae08ca6001f7615a06709.zip | |
Improve error reporting as part of solving bug #13546 on MS-Windows.
src/w32.c (sys_socket, sys_bind, sys_connect, sys_gethostname)
(sys_gethostbyname, sys_getservbyname, sys_getpeername)
(sys_shutdown, sys_setsockopt, sys_listen, sys_getsockname)
(sys_accept, sys_recvfrom, sys_sendto, fcntl): In case of failure,
make sure errno is set to an appropriate value. (Bug#13546)
(socket_to_fd): Add assertion against indexing fd_info[] with a
value that is out of bounds.
(sys_accept): If fd is negative, do not set up the child_process
structure for reading.
Diffstat (limited to 'src/w32.c')
| -rw-r--r-- | src/w32.c | 74 |
1 files changed, 44 insertions, 30 deletions
| @@ -5655,7 +5655,7 @@ sys_socket (int af, int type, int protocol) | |||
| 5655 | 5655 | ||
| 5656 | if (winsock_lib == NULL) | 5656 | if (winsock_lib == NULL) |
| 5657 | { | 5657 | { |
| 5658 | h_errno = ENETDOWN; | 5658 | errno = h_errno = ENETDOWN; |
| 5659 | return INVALID_SOCKET; | 5659 | return INVALID_SOCKET; |
| 5660 | } | 5660 | } |
| 5661 | 5661 | ||
| @@ -5665,7 +5665,13 @@ sys_socket (int af, int type, int protocol) | |||
| 5665 | s = pfn_socket (af, type, protocol); | 5665 | s = pfn_socket (af, type, protocol); |
| 5666 | 5666 | ||
| 5667 | if (s != INVALID_SOCKET) | 5667 | if (s != INVALID_SOCKET) |
| 5668 | return socket_to_fd (s); | 5668 | { |
| 5669 | int retval = socket_to_fd (s); | ||
| 5670 | |||
| 5671 | if (retval == -1) | ||
| 5672 | errno = h_errno; | ||
| 5673 | return retval; | ||
| 5674 | } | ||
| 5669 | 5675 | ||
| 5670 | set_errno (); | 5676 | set_errno (); |
| 5671 | return -1; | 5677 | return -1; |
| @@ -5732,6 +5738,7 @@ socket_to_fd (SOCKET s) | |||
| 5732 | } | 5738 | } |
| 5733 | } | 5739 | } |
| 5734 | } | 5740 | } |
| 5741 | eassert (fd < MAXDESC); | ||
| 5735 | fd_info[fd].hnd = (HANDLE) s; | 5742 | fd_info[fd].hnd = (HANDLE) s; |
| 5736 | 5743 | ||
| 5737 | /* set our own internal flags */ | 5744 | /* set our own internal flags */ |
| @@ -5770,7 +5777,7 @@ sys_bind (int s, const struct sockaddr * addr, int namelen) | |||
| 5770 | { | 5777 | { |
| 5771 | if (winsock_lib == NULL) | 5778 | if (winsock_lib == NULL) |
| 5772 | { | 5779 | { |
| 5773 | h_errno = ENOTSOCK; | 5780 | errno = h_errno = ENOTSOCK; |
| 5774 | return SOCKET_ERROR; | 5781 | return SOCKET_ERROR; |
| 5775 | } | 5782 | } |
| 5776 | 5783 | ||
| @@ -5782,7 +5789,7 @@ sys_bind (int s, const struct sockaddr * addr, int namelen) | |||
| 5782 | set_errno (); | 5789 | set_errno (); |
| 5783 | return rc; | 5790 | return rc; |
| 5784 | } | 5791 | } |
| 5785 | h_errno = ENOTSOCK; | 5792 | errno = h_errno = ENOTSOCK; |
| 5786 | return SOCKET_ERROR; | 5793 | return SOCKET_ERROR; |
| 5787 | } | 5794 | } |
| 5788 | 5795 | ||
| @@ -5791,7 +5798,7 @@ sys_connect (int s, const struct sockaddr * name, int namelen) | |||
| 5791 | { | 5798 | { |
| 5792 | if (winsock_lib == NULL) | 5799 | if (winsock_lib == NULL) |
| 5793 | { | 5800 | { |
| 5794 | h_errno = ENOTSOCK; | 5801 | errno = h_errno = ENOTSOCK; |
| 5795 | return SOCKET_ERROR; | 5802 | return SOCKET_ERROR; |
| 5796 | } | 5803 | } |
| 5797 | 5804 | ||
| @@ -5803,7 +5810,7 @@ sys_connect (int s, const struct sockaddr * name, int namelen) | |||
| 5803 | set_errno (); | 5810 | set_errno (); |
| 5804 | return rc; | 5811 | return rc; |
| 5805 | } | 5812 | } |
| 5806 | h_errno = ENOTSOCK; | 5813 | errno = h_errno = ENOTSOCK; |
| 5807 | return SOCKET_ERROR; | 5814 | return SOCKET_ERROR; |
| 5808 | } | 5815 | } |
| 5809 | 5816 | ||
| @@ -5837,7 +5844,7 @@ sys_gethostname (char * name, int namelen) | |||
| 5837 | if (namelen > MAX_COMPUTERNAME_LENGTH) | 5844 | if (namelen > MAX_COMPUTERNAME_LENGTH) |
| 5838 | return !GetComputerName (name, (DWORD *)&namelen); | 5845 | return !GetComputerName (name, (DWORD *)&namelen); |
| 5839 | 5846 | ||
| 5840 | h_errno = EFAULT; | 5847 | errno = h_errno = EFAULT; |
| 5841 | return SOCKET_ERROR; | 5848 | return SOCKET_ERROR; |
| 5842 | } | 5849 | } |
| 5843 | 5850 | ||
| @@ -5848,7 +5855,7 @@ sys_gethostbyname (const char * name) | |||
| 5848 | 5855 | ||
| 5849 | if (winsock_lib == NULL) | 5856 | if (winsock_lib == NULL) |
| 5850 | { | 5857 | { |
| 5851 | h_errno = ENETDOWN; | 5858 | errno = h_errno = ENETDOWN; |
| 5852 | return NULL; | 5859 | return NULL; |
| 5853 | } | 5860 | } |
| 5854 | 5861 | ||
| @@ -5866,7 +5873,7 @@ sys_getservbyname (const char * name, const char * proto) | |||
| 5866 | 5873 | ||
| 5867 | if (winsock_lib == NULL) | 5874 | if (winsock_lib == NULL) |
| 5868 | { | 5875 | { |
| 5869 | h_errno = ENETDOWN; | 5876 | errno = h_errno = ENETDOWN; |
| 5870 | return NULL; | 5877 | return NULL; |
| 5871 | } | 5878 | } |
| 5872 | 5879 | ||
| @@ -5882,7 +5889,7 @@ sys_getpeername (int s, struct sockaddr *addr, int * namelen) | |||
| 5882 | { | 5889 | { |
| 5883 | if (winsock_lib == NULL) | 5890 | if (winsock_lib == NULL) |
| 5884 | { | 5891 | { |
| 5885 | h_errno = ENETDOWN; | 5892 | errno = h_errno = ENETDOWN; |
| 5886 | return SOCKET_ERROR; | 5893 | return SOCKET_ERROR; |
| 5887 | } | 5894 | } |
| 5888 | 5895 | ||
| @@ -5894,7 +5901,7 @@ sys_getpeername (int s, struct sockaddr *addr, int * namelen) | |||
| 5894 | set_errno (); | 5901 | set_errno (); |
| 5895 | return rc; | 5902 | return rc; |
| 5896 | } | 5903 | } |
| 5897 | h_errno = ENOTSOCK; | 5904 | errno = h_errno = ENOTSOCK; |
| 5898 | return SOCKET_ERROR; | 5905 | return SOCKET_ERROR; |
| 5899 | } | 5906 | } |
| 5900 | 5907 | ||
| @@ -5903,7 +5910,7 @@ sys_shutdown (int s, int how) | |||
| 5903 | { | 5910 | { |
| 5904 | if (winsock_lib == NULL) | 5911 | if (winsock_lib == NULL) |
| 5905 | { | 5912 | { |
| 5906 | h_errno = ENETDOWN; | 5913 | errno = h_errno = ENETDOWN; |
| 5907 | return SOCKET_ERROR; | 5914 | return SOCKET_ERROR; |
| 5908 | } | 5915 | } |
| 5909 | 5916 | ||
| @@ -5915,7 +5922,7 @@ sys_shutdown (int s, int how) | |||
| 5915 | set_errno (); | 5922 | set_errno (); |
| 5916 | return rc; | 5923 | return rc; |
| 5917 | } | 5924 | } |
| 5918 | h_errno = ENOTSOCK; | 5925 | errno = h_errno = ENOTSOCK; |
| 5919 | return SOCKET_ERROR; | 5926 | return SOCKET_ERROR; |
| 5920 | } | 5927 | } |
| 5921 | 5928 | ||
| @@ -5924,7 +5931,7 @@ sys_setsockopt (int s, int level, int optname, const void * optval, int optlen) | |||
| 5924 | { | 5931 | { |
| 5925 | if (winsock_lib == NULL) | 5932 | if (winsock_lib == NULL) |
| 5926 | { | 5933 | { |
| 5927 | h_errno = ENETDOWN; | 5934 | errno = h_errno = ENETDOWN; |
| 5928 | return SOCKET_ERROR; | 5935 | return SOCKET_ERROR; |
| 5929 | } | 5936 | } |
| 5930 | 5937 | ||
| @@ -5937,7 +5944,7 @@ sys_setsockopt (int s, int level, int optname, const void * optval, int optlen) | |||
| 5937 | set_errno (); | 5944 | set_errno (); |
| 5938 | return rc; | 5945 | return rc; |
| 5939 | } | 5946 | } |
| 5940 | h_errno = ENOTSOCK; | 5947 | errno = h_errno = ENOTSOCK; |
| 5941 | return SOCKET_ERROR; | 5948 | return SOCKET_ERROR; |
| 5942 | } | 5949 | } |
| 5943 | 5950 | ||
| @@ -5946,7 +5953,7 @@ sys_listen (int s, int backlog) | |||
| 5946 | { | 5953 | { |
| 5947 | if (winsock_lib == NULL) | 5954 | if (winsock_lib == NULL) |
| 5948 | { | 5955 | { |
| 5949 | h_errno = ENETDOWN; | 5956 | errno = h_errno = ENETDOWN; |
| 5950 | return SOCKET_ERROR; | 5957 | return SOCKET_ERROR; |
| 5951 | } | 5958 | } |
| 5952 | 5959 | ||
| @@ -5960,7 +5967,7 @@ sys_listen (int s, int backlog) | |||
| 5960 | fd_info[s].flags |= FILE_LISTEN; | 5967 | fd_info[s].flags |= FILE_LISTEN; |
| 5961 | return rc; | 5968 | return rc; |
| 5962 | } | 5969 | } |
| 5963 | h_errno = ENOTSOCK; | 5970 | errno = h_errno = ENOTSOCK; |
| 5964 | return SOCKET_ERROR; | 5971 | return SOCKET_ERROR; |
| 5965 | } | 5972 | } |
| 5966 | 5973 | ||
| @@ -5969,7 +5976,7 @@ sys_getsockname (int s, struct sockaddr * name, int * namelen) | |||
| 5969 | { | 5976 | { |
| 5970 | if (winsock_lib == NULL) | 5977 | if (winsock_lib == NULL) |
| 5971 | { | 5978 | { |
| 5972 | h_errno = ENETDOWN; | 5979 | errno = h_errno = ENETDOWN; |
| 5973 | return SOCKET_ERROR; | 5980 | return SOCKET_ERROR; |
| 5974 | } | 5981 | } |
| 5975 | 5982 | ||
| @@ -5981,7 +5988,7 @@ sys_getsockname (int s, struct sockaddr * name, int * namelen) | |||
| 5981 | set_errno (); | 5988 | set_errno (); |
| 5982 | return rc; | 5989 | return rc; |
| 5983 | } | 5990 | } |
| 5984 | h_errno = ENOTSOCK; | 5991 | errno = h_errno = ENOTSOCK; |
| 5985 | return SOCKET_ERROR; | 5992 | return SOCKET_ERROR; |
| 5986 | } | 5993 | } |
| 5987 | 5994 | ||
| @@ -5990,7 +5997,7 @@ sys_accept (int s, struct sockaddr * addr, int * addrlen) | |||
| 5990 | { | 5997 | { |
| 5991 | if (winsock_lib == NULL) | 5998 | if (winsock_lib == NULL) |
| 5992 | { | 5999 | { |
| 5993 | h_errno = ENETDOWN; | 6000 | errno = h_errno = ENETDOWN; |
| 5994 | return -1; | 6001 | return -1; |
| 5995 | } | 6002 | } |
| 5996 | 6003 | ||
| @@ -6002,13 +6009,20 @@ sys_accept (int s, struct sockaddr * addr, int * addrlen) | |||
| 6002 | if (t == INVALID_SOCKET) | 6009 | if (t == INVALID_SOCKET) |
| 6003 | set_errno (); | 6010 | set_errno (); |
| 6004 | else | 6011 | else |
| 6005 | fd = socket_to_fd (t); | 6012 | { |
| 6013 | fd = socket_to_fd (t); | ||
| 6014 | if (fd < 0) | ||
| 6015 | errno = h_errno; /* socket_to_fd sets h_errno */ | ||
| 6016 | } | ||
| 6006 | 6017 | ||
| 6007 | fd_info[s].cp->status = STATUS_READ_ACKNOWLEDGED; | 6018 | if (fd >= 0) |
| 6008 | ResetEvent (fd_info[s].cp->char_avail); | 6019 | { |
| 6020 | fd_info[s].cp->status = STATUS_READ_ACKNOWLEDGED; | ||
| 6021 | ResetEvent (fd_info[s].cp->char_avail); | ||
| 6022 | } | ||
| 6009 | return fd; | 6023 | return fd; |
| 6010 | } | 6024 | } |
| 6011 | h_errno = ENOTSOCK; | 6025 | errno = h_errno = ENOTSOCK; |
| 6012 | return -1; | 6026 | return -1; |
| 6013 | } | 6027 | } |
| 6014 | 6028 | ||
| @@ -6018,7 +6032,7 @@ sys_recvfrom (int s, char * buf, int len, int flags, | |||
| 6018 | { | 6032 | { |
| 6019 | if (winsock_lib == NULL) | 6033 | if (winsock_lib == NULL) |
| 6020 | { | 6034 | { |
| 6021 | h_errno = ENETDOWN; | 6035 | errno = h_errno = ENETDOWN; |
| 6022 | return SOCKET_ERROR; | 6036 | return SOCKET_ERROR; |
| 6023 | } | 6037 | } |
| 6024 | 6038 | ||
| @@ -6030,7 +6044,7 @@ sys_recvfrom (int s, char * buf, int len, int flags, | |||
| 6030 | set_errno (); | 6044 | set_errno (); |
| 6031 | return rc; | 6045 | return rc; |
| 6032 | } | 6046 | } |
| 6033 | h_errno = ENOTSOCK; | 6047 | errno = h_errno = ENOTSOCK; |
| 6034 | return SOCKET_ERROR; | 6048 | return SOCKET_ERROR; |
| 6035 | } | 6049 | } |
| 6036 | 6050 | ||
| @@ -6040,7 +6054,7 @@ sys_sendto (int s, const char * buf, int len, int flags, | |||
| 6040 | { | 6054 | { |
| 6041 | if (winsock_lib == NULL) | 6055 | if (winsock_lib == NULL) |
| 6042 | { | 6056 | { |
| 6043 | h_errno = ENETDOWN; | 6057 | errno = h_errno = ENETDOWN; |
| 6044 | return SOCKET_ERROR; | 6058 | return SOCKET_ERROR; |
| 6045 | } | 6059 | } |
| 6046 | 6060 | ||
| @@ -6052,7 +6066,7 @@ sys_sendto (int s, const char * buf, int len, int flags, | |||
| 6052 | set_errno (); | 6066 | set_errno (); |
| 6053 | return rc; | 6067 | return rc; |
| 6054 | } | 6068 | } |
| 6055 | h_errno = ENOTSOCK; | 6069 | errno = h_errno = ENOTSOCK; |
| 6056 | return SOCKET_ERROR; | 6070 | return SOCKET_ERROR; |
| 6057 | } | 6071 | } |
| 6058 | 6072 | ||
| @@ -6063,7 +6077,7 @@ fcntl (int s, int cmd, int options) | |||
| 6063 | { | 6077 | { |
| 6064 | if (winsock_lib == NULL) | 6078 | if (winsock_lib == NULL) |
| 6065 | { | 6079 | { |
| 6066 | h_errno = ENETDOWN; | 6080 | errno = h_errno = ENETDOWN; |
| 6067 | return -1; | 6081 | return -1; |
| 6068 | } | 6082 | } |
| 6069 | 6083 | ||
| @@ -6086,7 +6100,7 @@ fcntl (int s, int cmd, int options) | |||
| 6086 | return SOCKET_ERROR; | 6100 | return SOCKET_ERROR; |
| 6087 | } | 6101 | } |
| 6088 | } | 6102 | } |
| 6089 | h_errno = ENOTSOCK; | 6103 | errno = h_errno = ENOTSOCK; |
| 6090 | return SOCKET_ERROR; | 6104 | return SOCKET_ERROR; |
| 6091 | } | 6105 | } |
| 6092 | 6106 | ||