1218885Sdim//===- llvm/Support/Win32/system_error.inc - Windows error_code --*- C++ -*-===//
2218885Sdim//
3218885Sdim//                     The LLVM Compiler Infrastructure
4218885Sdim//
5218885Sdim// This file is distributed under the University of Illinois Open Source
6218885Sdim// License. See LICENSE.TXT for details.
7218885Sdim//
8218885Sdim//===----------------------------------------------------------------------===//
9218885Sdim//
10218885Sdim// This file provides the Windows specific implementation of the error_code
11218885Sdim// and error_condition classes.
12218885Sdim//
13218885Sdim//===----------------------------------------------------------------------===//
14218885Sdim
15218885Sdim//===----------------------------------------------------------------------===//
16218885Sdim//=== WARNING: Implementation here must contain only generic Windows code that
17218885Sdim//===          is guaranteed to work on *all* Windows variants.
18218885Sdim//===----------------------------------------------------------------------===//
19218885Sdim
20218885Sdim#include <windows.h>
21218885Sdim#include <winerror.h>
22218885Sdim
23218885Sdimusing namespace llvm;
24218885Sdim
25218885Sdimstd::string
26218885Sdim_system_error_category::message(int ev) const {
27218885Sdim  LPVOID lpMsgBuf = 0;
28218885Sdim  DWORD retval = ::FormatMessageA(
29218885Sdim    FORMAT_MESSAGE_ALLOCATE_BUFFER |
30218885Sdim    FORMAT_MESSAGE_FROM_SYSTEM |
31218885Sdim    FORMAT_MESSAGE_IGNORE_INSERTS,
32218885Sdim    NULL,
33218885Sdim    ev,
34218885Sdim    MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), // Default language
35218885Sdim    (LPSTR) &lpMsgBuf,
36218885Sdim    0,
37218885Sdim    NULL);
38218885Sdim  if (retval == 0) {
39218885Sdim    ::LocalFree(lpMsgBuf);
40218885Sdim    return std::string("Unknown error");
41218885Sdim  }
42218885Sdim
43218885Sdim  std::string str( static_cast<LPCSTR>(lpMsgBuf) );
44218885Sdim  ::LocalFree(lpMsgBuf);
45218885Sdim
46218885Sdim  while (str.size()
47218885Sdim     && (str[str.size()-1] == '\n' || str[str.size()-1] == '\r'))
48218885Sdim    str.erase( str.size()-1 );
49218885Sdim  if (str.size() && str[str.size()-1] == '.')
50218885Sdim    str.erase( str.size()-1 );
51218885Sdim  return str;
52218885Sdim}
53218885Sdim
54218885Sdim// I'd rather not double the line count of the following.
55218885Sdim#define MAP_ERR_TO_COND(x, y) case x: return make_error_condition(errc::y)
56218885Sdim
57218885Sdimerror_condition
58218885Sdim_system_error_category::default_error_condition(int ev) const {
59218885Sdim  switch (ev) {
60218885Sdim  MAP_ERR_TO_COND(0, success);
61218885Sdim  // Windows system -> posix_errno decode table  ---------------------------//
62218885Sdim  // see WinError.h comments for descriptions of errors
63218885Sdim  MAP_ERR_TO_COND(ERROR_ACCESS_DENIED,       permission_denied);
64218885Sdim  MAP_ERR_TO_COND(ERROR_ALREADY_EXISTS,      file_exists);
65218885Sdim  MAP_ERR_TO_COND(ERROR_BAD_UNIT,            no_such_device);
66218885Sdim  MAP_ERR_TO_COND(ERROR_BUFFER_OVERFLOW,     filename_too_long);
67218885Sdim  MAP_ERR_TO_COND(ERROR_BUSY,                device_or_resource_busy);
68218885Sdim  MAP_ERR_TO_COND(ERROR_BUSY_DRIVE,          device_or_resource_busy);
69218885Sdim  MAP_ERR_TO_COND(ERROR_CANNOT_MAKE,         permission_denied);
70218885Sdim  MAP_ERR_TO_COND(ERROR_CANTOPEN,            io_error);
71218885Sdim  MAP_ERR_TO_COND(ERROR_CANTREAD,            io_error);
72218885Sdim  MAP_ERR_TO_COND(ERROR_CANTWRITE,           io_error);
73218885Sdim  MAP_ERR_TO_COND(ERROR_CURRENT_DIRECTORY,   permission_denied);
74218885Sdim  MAP_ERR_TO_COND(ERROR_DEV_NOT_EXIST,       no_such_device);
75218885Sdim  MAP_ERR_TO_COND(ERROR_DEVICE_IN_USE,       device_or_resource_busy);
76218885Sdim  MAP_ERR_TO_COND(ERROR_DIR_NOT_EMPTY,       directory_not_empty);
77218885Sdim  MAP_ERR_TO_COND(ERROR_DIRECTORY,           invalid_argument);
78218885Sdim  MAP_ERR_TO_COND(ERROR_DISK_FULL,           no_space_on_device);
79218885Sdim  MAP_ERR_TO_COND(ERROR_FILE_EXISTS,         file_exists);
80218885Sdim  MAP_ERR_TO_COND(ERROR_FILE_NOT_FOUND,      no_such_file_or_directory);
81218885Sdim  MAP_ERR_TO_COND(ERROR_HANDLE_DISK_FULL,    no_space_on_device);
82218885Sdim  MAP_ERR_TO_COND(ERROR_HANDLE_EOF,          value_too_large);
83218885Sdim  MAP_ERR_TO_COND(ERROR_INVALID_ACCESS,      permission_denied);
84218885Sdim  MAP_ERR_TO_COND(ERROR_INVALID_DRIVE,       no_such_device);
85218885Sdim  MAP_ERR_TO_COND(ERROR_INVALID_FUNCTION,    function_not_supported);
86218885Sdim  MAP_ERR_TO_COND(ERROR_INVALID_HANDLE,      invalid_argument);
87218885Sdim  MAP_ERR_TO_COND(ERROR_INVALID_NAME,        invalid_argument);
88218885Sdim  MAP_ERR_TO_COND(ERROR_LOCK_VIOLATION,      no_lock_available);
89218885Sdim  MAP_ERR_TO_COND(ERROR_LOCKED,              no_lock_available);
90218885Sdim  MAP_ERR_TO_COND(ERROR_NEGATIVE_SEEK,       invalid_argument);
91218885Sdim  MAP_ERR_TO_COND(ERROR_NOACCESS,            permission_denied);
92218885Sdim  MAP_ERR_TO_COND(ERROR_NOT_ENOUGH_MEMORY,   not_enough_memory);
93218885Sdim  MAP_ERR_TO_COND(ERROR_NOT_READY,           resource_unavailable_try_again);
94218885Sdim  MAP_ERR_TO_COND(ERROR_NOT_SAME_DEVICE,     cross_device_link);
95218885Sdim  MAP_ERR_TO_COND(ERROR_OPEN_FAILED,         io_error);
96218885Sdim  MAP_ERR_TO_COND(ERROR_OPEN_FILES,          device_or_resource_busy);
97218885Sdim  MAP_ERR_TO_COND(ERROR_OPERATION_ABORTED,   operation_canceled);
98218885Sdim  MAP_ERR_TO_COND(ERROR_OUTOFMEMORY,         not_enough_memory);
99218885Sdim  MAP_ERR_TO_COND(ERROR_PATH_NOT_FOUND,      no_such_file_or_directory);
100218885Sdim  MAP_ERR_TO_COND(ERROR_BAD_NETPATH,         no_such_file_or_directory);
101218885Sdim  MAP_ERR_TO_COND(ERROR_READ_FAULT,          io_error);
102218885Sdim  MAP_ERR_TO_COND(ERROR_RETRY,               resource_unavailable_try_again);
103218885Sdim  MAP_ERR_TO_COND(ERROR_SEEK,                io_error);
104218885Sdim  MAP_ERR_TO_COND(ERROR_SHARING_VIOLATION,   permission_denied);
105218885Sdim  MAP_ERR_TO_COND(ERROR_TOO_MANY_OPEN_FILES, too_many_files_open);
106218885Sdim  MAP_ERR_TO_COND(ERROR_WRITE_FAULT,         io_error);
107218885Sdim  MAP_ERR_TO_COND(ERROR_WRITE_PROTECT,       permission_denied);
108218885Sdim  MAP_ERR_TO_COND(ERROR_SEM_TIMEOUT,         timed_out);
109218885Sdim  MAP_ERR_TO_COND(WSAEACCES,                 permission_denied);
110218885Sdim  MAP_ERR_TO_COND(WSAEADDRINUSE,             address_in_use);
111218885Sdim  MAP_ERR_TO_COND(WSAEADDRNOTAVAIL,          address_not_available);
112218885Sdim  MAP_ERR_TO_COND(WSAEAFNOSUPPORT,           address_family_not_supported);
113218885Sdim  MAP_ERR_TO_COND(WSAEALREADY,               connection_already_in_progress);
114218885Sdim  MAP_ERR_TO_COND(WSAEBADF,                  bad_file_descriptor);
115218885Sdim  MAP_ERR_TO_COND(WSAECONNABORTED,           connection_aborted);
116218885Sdim  MAP_ERR_TO_COND(WSAECONNREFUSED,           connection_refused);
117218885Sdim  MAP_ERR_TO_COND(WSAECONNRESET,             connection_reset);
118218885Sdim  MAP_ERR_TO_COND(WSAEDESTADDRREQ,           destination_address_required);
119218885Sdim  MAP_ERR_TO_COND(WSAEFAULT,                 bad_address);
120218885Sdim  MAP_ERR_TO_COND(WSAEHOSTUNREACH,           host_unreachable);
121218885Sdim  MAP_ERR_TO_COND(WSAEINPROGRESS,            operation_in_progress);
122218885Sdim  MAP_ERR_TO_COND(WSAEINTR,                  interrupted);
123218885Sdim  MAP_ERR_TO_COND(WSAEINVAL,                 invalid_argument);
124218885Sdim  MAP_ERR_TO_COND(WSAEISCONN,                already_connected);
125218885Sdim  MAP_ERR_TO_COND(WSAEMFILE,                 too_many_files_open);
126218885Sdim  MAP_ERR_TO_COND(WSAEMSGSIZE,               message_size);
127218885Sdim  MAP_ERR_TO_COND(WSAENAMETOOLONG,           filename_too_long);
128218885Sdim  MAP_ERR_TO_COND(WSAENETDOWN,               network_down);
129218885Sdim  MAP_ERR_TO_COND(WSAENETRESET,              network_reset);
130218885Sdim  MAP_ERR_TO_COND(WSAENETUNREACH,            network_unreachable);
131218885Sdim  MAP_ERR_TO_COND(WSAENOBUFS,                no_buffer_space);
132218885Sdim  MAP_ERR_TO_COND(WSAENOPROTOOPT,            no_protocol_option);
133218885Sdim  MAP_ERR_TO_COND(WSAENOTCONN,               not_connected);
134218885Sdim  MAP_ERR_TO_COND(WSAENOTSOCK,               not_a_socket);
135218885Sdim  MAP_ERR_TO_COND(WSAEOPNOTSUPP,             operation_not_supported);
136218885Sdim  MAP_ERR_TO_COND(WSAEPROTONOSUPPORT,        protocol_not_supported);
137218885Sdim  MAP_ERR_TO_COND(WSAEPROTOTYPE,             wrong_protocol_type);
138218885Sdim  MAP_ERR_TO_COND(WSAETIMEDOUT,              timed_out);
139218885Sdim  MAP_ERR_TO_COND(WSAEWOULDBLOCK,            operation_would_block);
140218885Sdim  default: return error_condition(ev, system_category());
141218885Sdim  }
142218885Sdim}
143