Re: State of ccache on Windows

"Michael Augustin" <[email protected]>
Newsgroups gmane.comp.compilers.ccache
Message-ID <trinity-7cf1ad37-b358-4549-8249-416aa61f1ab2-1371685204484@3capp-gmx-bs53>
Hi CCache-Developer, Hi Andrew,

I've tried to get the latest version running on Windows, since ccache-win32-project and cygwin version is only 2.4.

I had success with compiling from source together with mingw/msys.

After starting up it complained about asserts. I've made some changes in the attached patch to get CCACHE_BASEDIR working with windows pathnames and drive letters. At least in my case, I could build into different build directories and the cache was working, because of the filepath abstracting with CCACHE_BASEDIR.

I've set CCACHE_BASEDIR to a directory with / like "C:/projects/myapp". In ccache I try to convert the paths from \\ to /.

Please look at the patch and tell me, what you think about it.

Kind regards,

Mica

_______________________________________________
ccache mailing list
[email protected]
https://lists.samba.org/mailman/listinfo/ccache
0001-Fix-ccache-to-work-with-windows-paths-and-CCACHE_BAS.patch (application/octet-stream, 3.1 KB)
From c47835b3c61b69687903ac9aa2f0c485a113d744 Mon Sep 17 00:00:00 2001
From: Michael Augustin <[email protected]>
Date: Thu, 20 Jun 2013 01:22:52 +0200
Subject: [PATCH] Fix ccache to work with windows paths and CCACHE_BASEDIR

---
 ccache.h |  3 +++
 util.c   | 43 +++++++++++++++++++++++++++++++++++++++----
 2 files changed, 42 insertions(+), 4 deletions(-)

diff --git a/ccache.h b/ccache.h
index 00aec46..c3a495b 100644
--- a/ccache.h
+++ b/ccache.h
@@ -67,6 +67,9 @@ enum stats {
 #define str_eq(s1, s2) (strcmp((s1), (s2)) == 0)
 #define str_startswith(s, p) (strncmp((s), (p), strlen((p))) == 0)
 
+#define ISLOWER(c) ('a' <= (c) && (c) <= 'z')
+#define TOUPPER(c) (ISLOWER(c) ? 'A' + ((c) - 'a') : (c))
+
 /* ------------------------------------------------------------------------- */
 /* args.c */
 
diff --git a/util.c b/util.c
index ad0f040..19eff48 100644
--- a/util.c
+++ b/util.c
@@ -970,6 +970,7 @@ x_realpath(const char *path)
 	long maxlen = path_max(path);
 	char *ret, *p;
 #ifdef _WIN32
+	unsigned int i;
 	HANDLE path_handle;
 #endif
 
@@ -981,9 +982,19 @@ x_realpath(const char *path)
 	path_handle = CreateFile(
 		path, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING,
 		FILE_ATTRIBUTE_NORMAL, NULL);
-	GetFinalPathNameByHandle(path_handle, ret, maxlen, FILE_NAME_NORMALIZED);
-	CloseHandle(path_handle);
-	p = ret+4;// strip the \\?\ from the file name
+	if (path_handle != INVALID_HANDLE_VALUE)
+	{
+		GetFinalPathNameByHandle(path_handle, ret, maxlen, FILE_NAME_NORMALIZED);
+		CloseHandle(path_handle);
+		p = ret+4;// strip the \\?\ from the file name
+	}
+	else
+	{
+		strcpy(ret, path);
+		p = ret;
+	}
+	for (i=0; i<strlen(p); i++) if ( p[i] == '\\' ) p[i]='/';
+	p[i]=0x0;
 #else
 	/* yes, there are such systems. This replacement relies on
 	   the fact that when we call x_realpath we only care about symlinks */
@@ -1011,10 +1022,19 @@ char *
 gnu_getcwd(void)
 {
 	unsigned size = 128;
+#ifdef _WIN32
+	unsigned int i;
+#endif
 
 	while (true) {
 		char *buffer = (char *)x_malloc(size);
 		if (getcwd(buffer, size) == buffer) {
+#ifdef _WIN32
+			// drive letter in uppercase please
+			buffer[0]=TOUPPER(buffer[0]);
+			for (i=0; i<strlen(buffer); i++) if ( buffer[i] == '\\' ) buffer[i]='/';
+			buffer[i]=0x0;
+#endif
 			return buffer;
 		}
 		free(buffer);
@@ -1100,6 +1120,9 @@ get_cwd(void)
 	char *cwd;
 	struct stat st_pwd;
 	struct stat st_cwd;
+#ifdef _WIN32
+	unsigned int i;
+#endif
 
 	cwd = gnu_getcwd();
 	if (!cwd) {
@@ -1117,6 +1140,11 @@ get_cwd(void)
 	}
 	if (st_pwd.st_dev == st_cwd.st_dev && st_pwd.st_ino == st_cwd.st_ino) {
 		free(cwd);
+#ifdef _WIN32
+		pwd[0]=TOUPPER(pwd[0]);
+		for (i=0; i<strlen(pwd); i++) if ( pwd[i] == '\\' ) pwd[i]='/';
+		pwd[i]=0x0;
+#endif
 		return x_strdup(pwd);
 	} else {
 		return cwd;
@@ -1189,11 +1217,18 @@ get_relative_path(const char *from, const char *to)
 	int i;
 	const char *p;
 	char *result;
-
+#ifdef _WIN32
+	assert(from && from[1] == ':');
+#else
 	assert(from && from[0] == '/');
+#endif
 	assert(to);
 
+#ifdef _WIN32
+	if (!*to || to[1] != ':') {
+#else
 	if (!*to || *to != '/') {
+#endif
 		return x_strdup(to);
 	}
 
-- 
1.7.11.msysgit.1
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.