Windows: Replace the sanitize_path() function with normalize_path()

Once upon a time the sanitize_path() function was needed to generate a
consistent path format in order to hash the resulting string for use as
session IDs. Since commit 71a779d078 ("Windows: Rework WinUSB
enumeration process to fix issues on Win8+"), this hashing method is no
longer used for session IDs, thus the sanitize_path() function was no
longer explicitly needed.

User lo1ol also reports in issue #633 that the function actually causes
issues with devices where there is a path component following the device
interface GUID. Rather than patching the function to fix this specific
behavior, just replace it with a simpler function that returns an
uppercased duplicate of the input string.

Closes #633, Closes #662

Signed-off-by: Chris Dickens <christopher.a.dickens@gmail.com>
diff --git a/libusb/os/windows_winusb.c b/libusb/os/windows_winusb.c
index 67013d6..7e67176 100644
--- a/libusb/os/windows_winusb.c
+++ b/libusb/os/windows_winusb.c
@@ -128,43 +128,19 @@
 #endif
 
 /*
- * Sanitize Microsoft's paths: convert to uppercase, add prefix and fix backslashes.
- * Return an allocated sanitized string or NULL on error.
+ * Normalize Microsoft's paths: return a duplicate of the given path
+ * with all characters converted to uppercase
  */
-static char *sanitize_path(const char *path)
+static char *normalize_path(const char *path)
 {
-	const char root_prefix[] = {'\\', '\\', '.', '\\'};
-	size_t j, size;
-	char *ret_path;
-	size_t add_root = 0;
+	char *ret_path = _strdup(path);
+	char *p;
 
-	if (path == NULL)
-		return NULL;
-
-	size = strlen(path) + 1;
-
-	// Microsoft indiscriminately uses '\\?\', '\\.\', '##?#" or "##.#" for root prefixes.
-	if (!((size > 3) && (((path[0] == '\\') && (path[1] == '\\') && (path[3] == '\\'))
-			|| ((path[0] == '#') && (path[1] == '#') && (path[3] == '#'))))) {
-		add_root = sizeof(root_prefix);
-		size += add_root;
-	}
-
-	ret_path = malloc(size);
 	if (ret_path == NULL)
 		return NULL;
 
-	strcpy(&ret_path[add_root], path);
-
-	// Ensure consistency with root prefix
-	memcpy(ret_path, root_prefix, sizeof(root_prefix));
-
-	// Same goes for '\' and '#' after the root prefix. Ensure '#' is used
-	for (j = sizeof(root_prefix); j < size; j++) {
-		ret_path[j] = (char)toupper((int)ret_path[j]); // Fix case too
-		if (ret_path[j] == '\\')
-			ret_path[j] = '#';
-	}
+	for (p = ret_path; *p != '\0'; p++)
+		*p = (char)toupper((unsigned char)*p);
 
 	return ret_path;
 }
@@ -324,7 +300,7 @@
 		return LIBUSB_ERROR_OTHER;
 	}
 
-	*dev_interface_path = sanitize_path(dev_interface_details->DevicePath);
+	*dev_interface_path = normalize_path(dev_interface_details->DevicePath);
 	free(dev_interface_details);
 
 	if (*dev_interface_path == NULL) {
@@ -2241,7 +2217,7 @@
 	SP_DEVICE_INTERFACE_DETAIL_DATA_A *dev_interface_details = NULL;
 	HDEVINFO dev_info = INVALID_HANDLE_VALUE;
 	SP_DEVINFO_DATA dev_info_data;
-	char *dev_path_no_guid = NULL;
+	char *dev_path_no_guid;
 	char filter_path[] = "\\\\.\\libusb0-0000";
 	bool found_filter = false;
 	HANDLE file_handle, winusb_handle;
@@ -2278,7 +2254,7 @@
 						break;
 
 					// ignore GUID part
-					dev_path_no_guid = sanitize_path(strtok(dev_interface_details->DevicePath, "{"));
+					dev_path_no_guid = strtok(dev_interface_details->DevicePath, "{");
 					if (dev_path_no_guid == NULL)
 						continue;
 
diff --git a/libusb/version_nano.h b/libusb/version_nano.h
index 5028718..67bcc19 100644
--- a/libusb/version_nano.h
+++ b/libusb/version_nano.h
@@ -1 +1 @@
-#define LIBUSB_NANO 11483
+#define LIBUSB_NANO 11484