diff --git a/src/cmd/gc/subr.c b/src/cmd/gc/subr.c
index b8cdd27ad4a5a4ff5eb548566a8dd3fd7ca24ca8..b12153df34f680845819b582c8595c5535e7bef1 100644
--- a/src/cmd/gc/subr.c
+++ b/src/cmd/gc/subr.c
@@ -2916,6 +2916,8 @@ ngotype(Node *n)
  * non-7-bit clean bytes turn into %xx.  The period needs escaping
  * only in the last segment of the path, and it makes for happier
  * users if we escape that as little as possible.
+ *
+ * If you edit this, edit ../ld/lib.c:/^pathtoprefix copy too.
  */
 static char*
 pathtoprefix(char *s)
diff --git a/src/cmd/ld/lib.c b/src/cmd/ld/lib.c
index 33fa0d154623939a2e0d3bc4aca69537584a3b04..82f3f007f437a3daa7dc902c51cc971acdc9e23a 100644
--- a/src/cmd/ld/lib.c
+++ b/src/cmd/ld/lib.c
@@ -903,18 +903,26 @@ unmal(void *v, uint32 n)
  * Convert raw string to the prefix that will be used in the symbol table.
  * Invalid bytes turn into %xx.	 Right now the only bytes that need
  * escaping are %, ., and ", but we escape all control characters too.
+ *
+ * Must be same as ../gc/subr.c:/^pathtoprefix.
  */
 static char*
 pathtoprefix(char *s)
 {
 	static char hex[] = "0123456789abcdef";
-	char *p, *r, *w;
+	char *p, *r, *w, *l;
 	int n;
 
+	// find first character past the last slash, if any.
+	l = s;
+	for(r=s; *r; r++)
+		if(*r == '/')
+			l = r+1;
+
 	// check for chars that need escaping
 	n = 0;
 	for(r=s; *r; r++)
-		if(*r <= ' ' || *r == '.' || *r == '%' || *r == '"')
+		if(*r <= ' ' || (*r == '.' && r >= l) || *r == '%' || *r == '"' || *r >= 0x7f)
 			n++;
 
 	// quick exit
@@ -924,7 +932,7 @@ pathtoprefix(char *s)
 	// escape
 	p = mal((r-s)+1+2*n);
 	for(r=s, w=p; *r; r++) {
-		if(*r <= ' ' || *r == '.' || *r == '%' || *r == '"') {
+		if(*r <= ' ' || (*r == '.' && r >= l) || *r == '%' || *r == '"' || *r >= 0x7f) {
 			*w++ = '%';
 			*w++ = hex[(*r>>4)&0xF];
 			*w++ = hex[*r&0xF];