This patch implements "magic" lookup for "pid/…", as used when looking up /proc/self. The patch comes from the 't/magic-pid' branch at . It squashes commit 392e52286a302ca6157fbd221295e64ab6b6d8ba (by Justus Winter) and commit 392e52286a302ca6157fbd221295e64ab6b6d8ba (a subsequent fix by Samuel Thibault). From: Justus Winter <4winter@informatik.uni-hamburg.de> Subject: [PATCH] hurd: Handle `pid' magical lookup retry * hurd/lookup-retry.c: Handle `pid' magical lookup retry. diff --git a/hurd/lookup-retry.c b/hurd/lookup-retry.c index aee2ba8f93..6ed8de1653 100644 --- a/hurd/lookup-retry.c +++ b/hurd/lookup-retry.c @@ -25,6 +25,7 @@ #include #include <_itoa.h> #include +#include /* Translate the error from dir_lookup into the error the user sees. */ static inline error_t @@ -59,6 +60,7 @@ __hurd_file_name_lookup_retry (error_t (*use_init_port) error_t err; char *file_name; int nloops; + file_t lastdir = MACH_PORT_NULL; error_t lookup_op (file_t startdir) { @@ -107,14 +109,15 @@ __hurd_file_name_lookup_retry (error_t (*use_init_port) { case FS_RETRY_REAUTH: if (err = reauthenticate (*result)) - return err; + goto out; /* Fall through. */ case FS_RETRY_NORMAL: if (nloops++ >= __eloop_threshold ()) { __mach_port_deallocate (__mach_task_self (), *result); - return ELOOP; + err = ELOOP; + goto out; } /* An empty RETRYNAME indicates we have the final port. */ @@ -174,7 +177,7 @@ __hurd_file_name_lookup_retry (error_t (*use_init_port) if (err) __mach_port_deallocate (__mach_task_self (), *result); - return err; + goto out; } startdir = *result; @@ -189,7 +192,10 @@ __hurd_file_name_lookup_retry (error_t (*use_init_port) if (*result != MACH_PORT_NULL) __mach_port_deallocate (__mach_task_self (), *result); if (nloops++ >= __eloop_threshold ()) - return ELOOP; + { + err = ELOOP; + goto out; + } file_name = &retryname[1]; break; @@ -208,7 +214,8 @@ __hurd_file_name_lookup_retry (error_t (*use_init_port) (*end != '/' && *end != '\0')) { errno = save; - return ENOENT; + err = ENOENT; + goto out; } if (! get_dtable_port) err = EGRATUITOUS; @@ -226,9 +233,12 @@ __hurd_file_name_lookup_retry (error_t (*use_init_port) } errno = save; if (err) - return err; + goto out; if (*end == '\0') - return 0; + { + err = 0; + goto out; + } else { /* Do a normal retry on the remaining components. */ @@ -255,9 +265,12 @@ __hurd_file_name_lookup_retry (error_t (*use_init_port) if (err = __host_info (__mach_host_self (), HOST_BASIC_INFO, (integer_t *) &hostinfo, &hostinfocnt)) - return err; + goto out; if (hostinfocnt != HOST_BASIC_INFO_COUNT) - return EGRATUITOUS; + { + err = EGRATUITOUS; + goto out; + } p = _itoa (hostinfo.cpu_subtype, &retryname[8], 10, 0); *--p = '/'; p = _itoa (hostinfo.cpu_type, &retryname[8], 10, 0); @@ -293,10 +306,11 @@ __hurd_file_name_lookup_retry (error_t (*use_init_port) } case '\0': - return opentty (result); + err = opentty (result); + goto out; case '/': if (err = opentty (&startdir)) - return err; + goto out; strcpy (retryname, &retryname[4]); break; default: @@ -306,14 +320,48 @@ __hurd_file_name_lookup_retry (error_t (*use_init_port) goto bad_magic; break; + case 'p': + if (retryname[1] == 'i' && retryname[2] == 'd' && + (retryname[3] == '/' || retryname[3] == 0)) + { + char *p, buf[1024]; /* XXX */ + size_t len; + p = _itoa (__getpid (), &buf[sizeof buf], 10, 0); + len = &buf[sizeof buf] - p; + memcpy (buf, p, len); + strcpy (buf + len, &retryname[3]); + strcpy (retryname, buf); + + /* Do a normal retry on the remaining components. */ + __mach_port_mod_refs (__mach_task_self (), lastdir, + MACH_PORT_RIGHT_SEND, 1); + startdir = lastdir; + file_name = retryname; + } + else + goto bad_magic; + break; + default: bad_magic: - return EGRATUITOUS; + err = EGRATUITOUS; + goto out; } break; default: - return EGRATUITOUS; + err = EGRATUITOUS; + goto out; + } + + if (MACH_PORT_VALID (*result) && *result != lastdir) + { + if (MACH_PORT_VALID (lastdir)) + __mach_port_deallocate (__mach_task_self (), lastdir); + + lastdir = *result; + __mach_port_mod_refs (__mach_task_self (), lastdir, + MACH_PORT_RIGHT_SEND, 1); } if (startdir != MACH_PORT_NULL) @@ -326,6 +374,10 @@ __hurd_file_name_lookup_retry (error_t (*use_init_port) err = (*use_init_port) (dirport, &lookup_op); } while (! err); +out: + if (MACH_PORT_VALID (lastdir)) + __mach_port_deallocate (__mach_task_self (), lastdir); + return err; } weak_alias (__hurd_file_name_lookup_retry, hurd_file_name_lookup_retry)