Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/mRemoteNG/PuTTYNG.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'windows/utils/win_strerror.c')
-rw-r--r--windows/utils/win_strerror.c72
1 files changed, 72 insertions, 0 deletions
diff --git a/windows/utils/win_strerror.c b/windows/utils/win_strerror.c
new file mode 100644
index 00000000..5572bc8b
--- /dev/null
+++ b/windows/utils/win_strerror.c
@@ -0,0 +1,72 @@
+/*
+ * Wrapper around the Windows FormatMessage system for retrieving the
+ * text of a system error code, with a simple API similar to strerror.
+ *
+ * Works by keeping a tree234 containing mappings from system error
+ * codes to strings. Entries allocated in this tree are simply never
+ * freed.
+ *
+ * Also, the returned string has its trailing newline removed (so it
+ * can go in places like the Event Log that never want a newline), and
+ * is prefixed with the error number (so that if a user sends an error
+ * report containing a translated error message we can't read, we can
+ * still find out what the error actually was).
+ */
+
+#include "putty.h"
+
+struct errstring {
+ int error;
+ char *text;
+};
+
+static int errstring_find(void *av, void *bv)
+{
+ int *a = (int *)av;
+ struct errstring *b = (struct errstring *)bv;
+ if (*a < b->error)
+ return -1;
+ if (*a > b->error)
+ return +1;
+ return 0;
+}
+static int errstring_compare(void *av, void *bv)
+{
+ struct errstring *a = (struct errstring *)av;
+ return errstring_find(&a->error, bv);
+}
+
+static tree234 *errstrings = NULL;
+
+const char *win_strerror(int error)
+{
+ struct errstring *es;
+
+ if (!errstrings)
+ errstrings = newtree234(errstring_compare);
+
+ es = find234(errstrings, &error, errstring_find);
+
+ if (!es) {
+ char msgtext[65536]; /* maximum size for FormatMessage is 64K */
+
+ es = snew(struct errstring);
+ es->error = error;
+ if (!FormatMessage((FORMAT_MESSAGE_FROM_SYSTEM |
+ FORMAT_MESSAGE_IGNORE_INSERTS), NULL, error,
+ MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
+ msgtext, lenof(msgtext)-1, NULL)) {
+ sprintf(msgtext,
+ "(unable to format: FormatMessage returned %u)",
+ (unsigned int)GetLastError());
+ } else {
+ int len = strlen(msgtext);
+ if (len > 0 && msgtext[len-1] == '\n')
+ msgtext[len-1] = '\0';
+ }
+ es->text = dupprintf("Error %d: %s", error, msgtext);
+ add234(errstrings, es);
+ }
+
+ return es->text;
+}