diff options
| author | Paul Eggert | 2016-10-11 13:06:42 -0700 |
|---|---|---|
| committer | Paul Eggert | 2016-10-11 13:07:19 -0700 |
| commit | 1dd54e3eef7543720eff161457677a35fae2435c (patch) | |
| tree | 647a6acfc6c0af0910a1cfeb2014a3fe2b76aeb9 /src | |
| parent | 5cc3c13d164e392218a4dbc277fdab8c757a91af (diff) | |
| download | emacs-1dd54e3eef7543720eff161457677a35fae2435c.tar.gz emacs-1dd54e3eef7543720eff161457677a35fae2435c.zip | |
Work around Samba bug with ':' in symlink contents
* src/filelock.c (current_lock_owner): When reading the contents
of a lock, treat the UTF-8 for U+F022 as if it were ':' (Bug#24656).
Diffstat (limited to 'src')
| -rw-r--r-- | src/filelock.c | 35 |
1 files changed, 22 insertions, 13 deletions
diff --git a/src/filelock.c b/src/filelock.c index a2e1df99f07..d4dfc1dd007 100644 --- a/src/filelock.c +++ b/src/filelock.c | |||
| @@ -72,8 +72,9 @@ along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */ | |||
| 72 | 72 | ||
| 73 | /* Normally use a symbolic link to represent a lock. | 73 | /* Normally use a symbolic link to represent a lock. |
| 74 | The strategy: to lock a file FN, create a symlink .#FN in FN's | 74 | The strategy: to lock a file FN, create a symlink .#FN in FN's |
| 75 | directory, with link data `user@host.pid'. This avoids a single | 75 | directory, with link data USER@HOST.PID:BOOT. This avoids a single |
| 76 | mount (== failure) point for lock files. | 76 | mount (== failure) point for lock files. The :BOOT is omitted if |
| 77 | the boot time is not available. | ||
| 77 | 78 | ||
| 78 | When the host in the lock data is the current host, we can check if | 79 | When the host in the lock data is the current host, we can check if |
| 79 | the pid is valid with kill. | 80 | the pid is valid with kill. |
| @@ -102,13 +103,11 @@ along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */ | |||
| 102 | 103 | ||
| 103 | This is compatible with the locking scheme used by Interleaf (which | 104 | This is compatible with the locking scheme used by Interleaf (which |
| 104 | has contributed this implementation for Emacs), and was designed by | 105 | has contributed this implementation for Emacs), and was designed by |
| 105 | Ethan Jacobson, Kimbo Mundy, and others. | 106 | Karl Berry, Ethan Jacobson, Kimbo Mundy, and others. |
| 106 | |||
| 107 | --karl@cs.umb.edu/karl@hq.ileaf.com. | ||
| 108 | 107 | ||
| 109 | On some file systems, notably those of MS-Windows, symbolic links | 108 | On some file systems, notably those of MS-Windows, symbolic links |
| 110 | do not work well, so instead of a symlink .#FN -> 'user@host.pid', | 109 | do not work well, so instead of a symlink .#FN -> USER@HOST.PID:BOOT, |
| 111 | the lock is a regular file .#FN with contents 'user@host.pid'. To | 110 | the lock is a regular file .#FN with contents USER@HOST.PID:BOOT. To |
| 112 | establish a lock, a nonce file is created and then renamed to .#FN. | 111 | establish a lock, a nonce file is created and then renamed to .#FN. |
| 113 | On MS-Windows this renaming is atomic unless the lock is forcibly | 112 | On MS-Windows this renaming is atomic unless the lock is forcibly |
| 114 | acquired. On other systems the renaming is atomic if the lock is | 113 | acquired. On other systems the renaming is atomic if the lock is |
| @@ -289,8 +288,8 @@ enum { MAX_LFINFO = 8 * 1024 }; | |||
| 289 | 288 | ||
| 290 | typedef struct | 289 | typedef struct |
| 291 | { | 290 | { |
| 292 | /* Location of '@', '.', ':' in USER. If there's no colon, COLON | 291 | /* Location of '@', '.', and ':' (or equivalent) in USER. If there's |
| 293 | points to the end of USER. */ | 292 | no colon or equivalent, COLON points to the end of USER. */ |
| 294 | char *at, *dot, *colon; | 293 | char *at, *dot, *colon; |
| 295 | 294 | ||
| 296 | /* Lock file contents USER@HOST.PID with an optional :BOOT_TIME | 295 | /* Lock file contents USER@HOST.PID with an optional :BOOT_TIME |
| @@ -548,7 +547,7 @@ current_lock_owner (lock_info_type *owner, char *lfname) | |||
| 548 | if (!dot) | 547 | if (!dot) |
| 549 | return -1; | 548 | return -1; |
| 550 | 549 | ||
| 551 | /* The PID is everything from the last `.' to the `:'. */ | 550 | /* The PID is everything from the last '.' to the ':' or equivalent. */ |
| 552 | if (! c_isdigit (dot[1])) | 551 | if (! c_isdigit (dot[1])) |
| 553 | return -1; | 552 | return -1; |
| 554 | errno = 0; | 553 | errno = 0; |
| @@ -556,7 +555,8 @@ current_lock_owner (lock_info_type *owner, char *lfname) | |||
| 556 | if (errno == ERANGE) | 555 | if (errno == ERANGE) |
| 557 | pid = -1; | 556 | pid = -1; |
| 558 | 557 | ||
| 559 | /* After the `:', if there is one, comes the boot time. */ | 558 | /* After the ':' or equivalent, if there is one, comes the boot time. */ |
| 559 | char *boot = owner->colon + 1; | ||
| 560 | switch (owner->colon[0]) | 560 | switch (owner->colon[0]) |
| 561 | { | 561 | { |
| 562 | case 0: | 562 | case 0: |
| @@ -564,10 +564,19 @@ current_lock_owner (lock_info_type *owner, char *lfname) | |||
| 564 | lfinfo_end = owner->colon; | 564 | lfinfo_end = owner->colon; |
| 565 | break; | 565 | break; |
| 566 | 566 | ||
| 567 | case '\357': | ||
| 568 | /* Treat "\357\200\242" (U+F022 in UTF-8) as if it were ":". | ||
| 569 | This works around a bug in Samba, which can mistakenly | ||
| 570 | transliterate ':' to U+F022 in symlink contents (Bug#24656). | ||
| 571 | See <https://bugzilla.redhat.com/show_bug.cgi?id=1271407#c8>. */ | ||
| 572 | if (! (boot[0] == '\200' && boot[1] == '\242')) | ||
| 573 | return -1; | ||
| 574 | boot += 2; | ||
| 575 | /* Fall through. */ | ||
| 567 | case ':': | 576 | case ':': |
| 568 | if (! c_isdigit (owner->colon[1])) | 577 | if (! c_isdigit (boot[0])) |
| 569 | return -1; | 578 | return -1; |
| 570 | boot_time = strtoimax (owner->colon + 1, &lfinfo_end, 10); | 579 | boot_time = strtoimax (boot, &lfinfo_end, 10); |
| 571 | break; | 580 | break; |
| 572 | 581 | ||
| 573 | default: | 582 | default: |