aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorJoakim Verona2013-02-26 00:03:36 +0100
committerJoakim Verona2013-02-26 00:03:36 +0100
commit6f75e5103f0b1d6395fb5b0fea2a4a9c9f4601f7 (patch)
tree44f49e30237e3a897287c8b05c807c3212e464da /src
parent1b907e3f10d78d2bc58e2c8fd707d29b44498865 (diff)
parentd9bb0d4811696c94affc751a2de1906d3b54baf9 (diff)
downloademacs-6f75e5103f0b1d6395fb5b0fea2a4a9c9f4601f7.tar.gz
emacs-6f75e5103f0b1d6395fb5b0fea2a4a9c9f4601f7.zip
auto upstream
Diffstat (limited to 'src')
-rw-r--r--src/ChangeLog76
-rw-r--r--src/Makefile.in34
-rw-r--r--src/autodeps.mk1
-rw-r--r--src/callint.c4
-rw-r--r--src/deps.mk2
-rw-r--r--src/emacs.c26
-rw-r--r--src/eval.c2
-rw-r--r--src/filelock.c113
-rw-r--r--src/makefile.w32-in2
-rw-r--r--src/mem-limits.h43
-rw-r--r--src/pre-crt0.c10
-rw-r--r--src/textprop.c125
-rw-r--r--src/unexaix.c2
-rw-r--r--src/unexcoff.c4
-rw-r--r--src/vm-limit.c103
-rw-r--r--src/w32.c11
-rw-r--r--src/w32proc.c32
17 files changed, 343 insertions, 247 deletions
diff --git a/src/ChangeLog b/src/ChangeLog
index 8d3fc1e56fb..135d4d48b41 100644
--- a/src/ChangeLog
+++ b/src/ChangeLog
@@ -1,3 +1,79 @@
12013-02-25 Eli Zaretskii <eliz@gnu.org>
2
3 Implement CLASH_DETECTION for MS-Windows.
4
5 * filelock.c [WINDOWSNT]: Include w32.h.
6 (MAKE_LOCK_NAME): Don't use 'lock', it clashes with MS runtime
7 function of that name. Up-case the macro arguments.
8 (IS_LOCK_FILE): New macro.
9 (fill_in_lock_file_name): Use IS_LOCK_FILE instead of S_ISLNK.
10 (create_lock_file): New function, with body extracted from
11 lock_file_1.
12 [WINDOWSNT]: Implement lock files by writing a regular file with
13 the lock information as its contents.
14 (read_lock_data): New function, on Posix platforms just calls
15 emacs_readlinkat.
16 [WINDOWSNT]: Read the lock info from the file.
17 (current_lock_owner): Call read_lock_data instead of calling
18 emacs_readlinkat directly.
19 (lock_file) [WINDOWSNT]: Run the file name through
20 dostounix_filename.
21
22 * w32proc.c (sys_kill): Support the case of SIG = 0, in which case
23 just check if the process by that PID exists.
24
25 * w32.c (sys_open): Don't reset the _O_CREAT flag if _O_EXCL is
26 also present, as doing so will fail to error out if the file
27 already exists.
28
29 * makefile.w32-in ($(BLD)/filelock.$(O)): Depend on src/w32.h.
30
31 * textprop.c (Fadd_text_properties, Fremove_text_properties)
32 (Fremove_list_of_text_properties): Skip all of the intervals in
33 the region between START and END that already have resp. don't
34 have the requested properties, not just the first one. Add
35 assertions that the loop afterwards always modifies the
36 properties. (Bug#13743)
37
382013-02-25 Stefan Monnier <monnier@iro.umontreal.ca>
39
40 * callint.c (Fcall_interactively): Use the right lexical environment
41 for `interactive' specs (bug#13811).
42 * eval.c (Feval): Accept a lexical environment.
43
442013-02-25 Paul Eggert <eggert@cs.ucla.edu>
45
46 Simplify data_start configuration (Bug#13783).
47 This is a followon simplification to the fix for Bug#13650.
48 * Makefile.in (LD_FIRSTFLAG, LIB_GCC, CRT_DIR, LIB_STANDARD)
49 (START_FILES): Remove. All uses removed.
50 (otherobj): Remove $(VMLIMIT_OBJ), as it's now first.
51 (ALLOBJS): Move here from autodeps.mk, and with VMLIMITS_OBJ first.
52 (buildobj.h): Use it.
53 ($(ALLOBJS)): Depend on globals.h.
54 (temacs$(EXEEXT)): Use $(ALLOBJS).
55 * autodeps.mk (ALLOBJS): Move to Makefile.in.
56 * deps.mk (vm-limit.o):
57 * makefile.w32-in ($(BLD)/vm-limit.$(O)):
58 Do not depend on mem-limits.h.
59 * emacs.c (__do_global_ctors, __do_global_ctors_aux)
60 (__do_global_dtors, __CTOR_LIST__, __DTOR_LIST__)
61 [__GNUC__ && !ORDINARY_LINK]: Remove.
62 * mem-limits.h, pre-crt0.c: Remove.
63 * unexaix.c, unexcoff.c: Don't include mem-limits.h.
64 * unexcoff.c (etext): New decl.
65 (make_hdr): Use DATA_START instead of start_of_data.
66 * vm-limit.c: Move most of mem-limits.h's contents here.
67 (data_start): New decl. It's OK if this is approximate,
68 so simplify-away some unnecessary exactness.
69 (POINTER): Remove; all uses removed.
70 (data_space_start): Now char *, to avoid casts.
71 (exceeds_lisp_ptr): New function, replacing the old
72 EXCEEDS_LISP_PTR macro. All uses changed.
73 (check_memory_limits): Simplify and remove casts.
74 (start_of_data) [!CANNOT_DUMP || !SYSTEM_MALLOC]: Remove.
75 (memory_warnings): Use data_start instead of start_of_data.
76
12013-02-24 Andreas Schwab <schwab@linux-m68k.org> 772013-02-24 Andreas Schwab <schwab@linux-m68k.org>
2 78
3 * xdisp.c (set_message): Only check for debug-on-message if STRING 79 * xdisp.c (set_message): Only check for debug-on-message if STRING
diff --git a/src/Makefile.in b/src/Makefile.in
index 47803ab59f3..8a9a43ac124 100644
--- a/src/Makefile.in
+++ b/src/Makefile.in
@@ -36,7 +36,6 @@ WINDRES = @WINDRES@
36CFLAGS = @CFLAGS@ 36CFLAGS = @CFLAGS@
37CPPFLAGS = @CPPFLAGS@ 37CPPFLAGS = @CPPFLAGS@
38LDFLAGS = @LDFLAGS@ 38LDFLAGS = @LDFLAGS@
39LD_FIRSTFLAG=@LD_FIRSTFLAG@
40EXEEXT = @EXEEXT@ 39EXEEXT = @EXEEXT@
41version = @version@ 40version = @version@
42# Substitute an assignment for the MAKE variable, because 41# Substitute an assignment for the MAKE variable, because
@@ -102,10 +101,8 @@ LD_SWITCH_X_SITE_RPATH=@LD_SWITCH_X_SITE_RPATH@
102## System-specific LDFLAGS. 101## System-specific LDFLAGS.
103LD_SWITCH_SYSTEM=@LD_SWITCH_SYSTEM@ 102LD_SWITCH_SYSTEM=@LD_SWITCH_SYSTEM@
104 103
105## This holds any special options for linking temacs only (ie, not 104## This holds any special options for linking temacs only (i.e., not
106## used by configure). Not used elsewhere because it sometimes 105## used by configure).
107## contains options that have to do with using Emacs's crt0,
108## which are only good with temacs.
109LD_SWITCH_SYSTEM_TEMACS=@LD_SWITCH_SYSTEM_TEMACS@ 106LD_SWITCH_SYSTEM_TEMACS=@LD_SWITCH_SYSTEM_TEMACS@
110 107
111## Flags to pass to ld only for temacs. 108## Flags to pass to ld only for temacs.
@@ -120,14 +117,6 @@ PAXCTL = @PAXCTL@
120## Some systems define this to request special libraries. 117## Some systems define this to request special libraries.
121LIBS_SYSTEM=@LIBS_SYSTEM@ 118LIBS_SYSTEM=@LIBS_SYSTEM@
122 119
123## Where to find libgcc.a, if using gcc and necessary.
124LIB_GCC=@LIB_GCC@
125
126CRT_DIR=@CRT_DIR@
127## May use $CRT_DIR.
128LIB_STANDARD=@LIB_STANDARD@
129START_FILES = @START_FILES@
130
131## -lm, or empty. 120## -lm, or empty.
132LIB_MATH=@LIB_MATH@ 121LIB_MATH=@LIB_MATH@
133 122
@@ -401,17 +390,16 @@ POST_ALLOC_OBJ=@POST_ALLOC_OBJ@
401 390
402## List of object files that make-docfile should not be told about. 391## List of object files that make-docfile should not be told about.
403otherobj= $(TERMCAP_OBJ) $(PRE_ALLOC_OBJ) $(GMALLOC_OBJ) $(RALLOC_OBJ) \ 392otherobj= $(TERMCAP_OBJ) $(PRE_ALLOC_OBJ) $(GMALLOC_OBJ) $(RALLOC_OBJ) \
404 $(POST_ALLOC_OBJ) $(VMLIMIT_OBJ) $(WIDGET_OBJ) $(LIBOBJS) 393 $(POST_ALLOC_OBJ) $(WIDGET_OBJ) $(LIBOBJS)
405 394
395## All object files linked into temacs. $(VMLIMIT_OBJ) should be first.
396ALLOBJS = $(VMLIMIT_OBJ) $(obj) $(otherobj)
406 397
407## Configure inserts the file lisp.mk at this point, defining $lisp. 398## Configure inserts the file lisp.mk at this point, defining $lisp.
408@lisp_frag@ 399@lisp_frag@
409 400
410 401
411## Construct full set of libraries to be linked. 402## Construct full set of libraries to be linked.
412## Note that SunOS needs -lm to come before -lc; otherwise, you get
413## duplicated symbols. If the standard libraries were compiled
414## with GCC, we might need LIB_GCC again after them.
415LIBES = $(LIBS) $(W32_LIBS) $(LIBS_GNUSTEP) $(LIBX_BASE) $(LIBIMAGE) \ 403LIBES = $(LIBS) $(W32_LIBS) $(LIBS_GNUSTEP) $(LIBX_BASE) $(LIBIMAGE) \
416 $(LIBX_OTHER) $(LIBSOUND) \ 404 $(LIBX_OTHER) $(LIBSOUND) \
417 $(RSVG_LIBS) $(IMAGEMAGICK_LIBS) $(LIB_CLOCK_GETTIME) \ 405 $(RSVG_LIBS) $(IMAGEMAGICK_LIBS) $(LIB_CLOCK_GETTIME) \
@@ -422,7 +410,7 @@ LIBES = $(LIBS) $(W32_LIBS) $(LIBS_GNUSTEP) $(LIBX_BASE) $(LIBIMAGE) \
422 $(LIBS_TERMCAP) $(GETLOADAVG_LIBS) $(SETTINGS_LIBS) $(LIBSELINUX_LIBS) \ 410 $(LIBS_TERMCAP) $(GETLOADAVG_LIBS) $(SETTINGS_LIBS) $(LIBSELINUX_LIBS) \
423 $(FREETYPE_LIBS) $(FONTCONFIG_LIBS) $(LIBOTF_LIBS) $(M17N_FLT_LIBS) \ 411 $(FREETYPE_LIBS) $(FONTCONFIG_LIBS) $(LIBOTF_LIBS) $(M17N_FLT_LIBS) \
424 $(LIBACL_LIBS) $(LIBGNUTLS_LIBS) $(LIB_PTHREAD) $(LIB_PTHREAD_SIGMASK) \ 412 $(LIBACL_LIBS) $(LIBGNUTLS_LIBS) $(LIB_PTHREAD) $(LIB_PTHREAD_SIGMASK) \
425 $(LIB_GCC) $(LIB_MATH) $(LIB_STANDARD) $(LIB_GCC) 413 $(LIB_MATH)
426 414
427all: emacs$(EXEEXT) $(OTHER_FILES) 415all: emacs$(EXEEXT) $(OTHER_FILES)
428.PHONY: all 416.PHONY: all
@@ -469,7 +457,7 @@ $(libsrc)/make-docfile$(EXEEXT):
469 cd $(libsrc); $(MAKE) $(MFLAGS) make-docfile$(EXEEXT) 457 cd $(libsrc); $(MAKE) $(MFLAGS) make-docfile$(EXEEXT)
470 458
471buildobj.h: Makefile 459buildobj.h: Makefile
472 echo "#define BUILDOBJ \"$(obj) $(otherobj) " "\"" > buildobj.h 460 echo "#define BUILDOBJ \"$(ALLOBJS) " "\"" >$@
473 461
474globals.h: gl-stamp; @true 462globals.h: gl-stamp; @true
475 463
@@ -481,15 +469,15 @@ gl-stamp: $(libsrc)/make-docfile$(EXEEXT) $(GLOBAL_SOURCES)
481 $(srcdir)/../build-aux/move-if-change gl-tmp globals.h 469 $(srcdir)/../build-aux/move-if-change gl-tmp globals.h
482 echo timestamp > $@ 470 echo timestamp > $@
483 471
484$(obj) $(otherobj): globals.h 472$(ALLOBJS): globals.h
485 473
486$(lib)/libgnu.a: $(config_h) 474$(lib)/libgnu.a: $(config_h)
487 cd $(lib) && $(MAKE) libgnu.a 475 cd $(lib) && $(MAKE) libgnu.a
488 476
489temacs$(EXEEXT): $(START_FILES) stamp-oldxmenu $(obj) $(otherobj) \ 477temacs$(EXEEXT): stamp-oldxmenu $(ALLOBJS) \
490 $(lib)/libgnu.a $(W32_RES) 478 $(lib)/libgnu.a $(W32_RES)
491 $(CC) $(LD_FIRSTFLAG) $(ALL_CFLAGS) $(TEMACS_LDFLAGS) $(LDFLAGS) \ 479 $(CC) $(ALL_CFLAGS) $(TEMACS_LDFLAGS) $(LDFLAGS) \
492 -o temacs $(START_FILES) $(obj) $(otherobj) $(lib)/libgnu.a $(LIBES) \ 480 -o temacs $(ALLOBJS) $(lib)/libgnu.a $(LIBES) \
493 $(W32_RES_LINK) 481 $(W32_RES_LINK)
494 test "$(CANNOT_DUMP)" = "yes" || \ 482 test "$(CANNOT_DUMP)" = "yes" || \
495 test "X$(PAXCTL)" = X || $(PAXCTL) -r temacs$(EXEEXT) 483 test "X$(PAXCTL)" = X || $(PAXCTL) -r temacs$(EXEEXT)
diff --git a/src/autodeps.mk b/src/autodeps.mk
index fb0e21366c7..8b014a7508c 100644
--- a/src/autodeps.mk
+++ b/src/autodeps.mk
@@ -2,5 +2,4 @@
2 2
3## This is inserted in src/Makefile if AUTO_DEPEND=yes. 3## This is inserted in src/Makefile if AUTO_DEPEND=yes.
4 4
5ALLOBJS=$(START_FILES) ${obj} ${otherobj}
6-include $(ALLOBJS:%.o=${DEPDIR}/%.d) 5-include $(ALLOBJS:%.o=${DEPDIR}/%.d)
diff --git a/src/callint.c b/src/callint.c
index 3e295a3b26b..b0d4bcdd011 100644
--- a/src/callint.c
+++ b/src/callint.c
@@ -342,8 +342,8 @@ invoke it. If KEYS is omitted or nil, the return value of
342 /* Compute the arg values using the user's expression. */ 342 /* Compute the arg values using the user's expression. */
343 GCPRO2 (input, filter_specs); 343 GCPRO2 (input, filter_specs);
344 specs = Feval (specs, 344 specs = Feval (specs,
345 CONSP (funval) && EQ (Qclosure, XCAR (funval)) 345 CONSP (funval) && EQ (Qclosure, XCAR (funval))
346 ? Qt : Qnil); 346 ? CAR_SAFE (XCDR (funval)) : Qnil);
347 UNGCPRO; 347 UNGCPRO;
348 if (events != num_input_events || !NILP (record_flag)) 348 if (events != num_input_events || !NILP (record_flag))
349 { 349 {
diff --git a/src/deps.mk b/src/deps.mk
index 47185c9262c..83444474c59 100644
--- a/src/deps.mk
+++ b/src/deps.mk
@@ -144,7 +144,7 @@ macros.o: macros.c window.h buffer.h commands.h macros.h keyboard.h msdos.h \
144 dispextern.h lisp.h globals.h $(config_h) systime.h coding.h composite.h 144 dispextern.h lisp.h globals.h $(config_h) systime.h coding.h composite.h
145gmalloc.o: gmalloc.c $(config_h) 145gmalloc.o: gmalloc.c $(config_h)
146ralloc.o: ralloc.c lisp.h $(config_h) 146ralloc.o: ralloc.c lisp.h $(config_h)
147vm-limit.o: vm-limit.c mem-limits.h lisp.h globals.h $(config_h) 147vm-limit.o: vm-limit.c lisp.h globals.h $(config_h)
148marker.o: marker.c buffer.h character.h lisp.h globals.h $(config_h) 148marker.o: marker.c buffer.h character.h lisp.h globals.h $(config_h)
149minibuf.o: minibuf.c syntax.h frame.h window.h keyboard.h systime.h \ 149minibuf.o: minibuf.c syntax.h frame.h window.h keyboard.h systime.h \
150 buffer.h commands.h character.h msdos.h $(INTERVALS_H) keymap.h \ 150 buffer.h commands.h character.h msdos.h $(INTERVALS_H) keymap.h \
diff --git a/src/emacs.c b/src/emacs.c
index 43fcae8e062..2d5a61c62b0 100644
--- a/src/emacs.c
+++ b/src/emacs.c
@@ -524,32 +524,6 @@ DEFUN ("invocation-directory", Finvocation_directory, Sinvocation_directory,
524static char const dump_tz[] = "UtC0"; 524static char const dump_tz[] = "UtC0";
525#endif 525#endif
526 526
527#ifndef ORDINARY_LINK
528/* We don't include crtbegin.o and crtend.o in the link,
529 so these functions and variables might be missed.
530 Provide dummy definitions to avoid error.
531 (We don't have any real constructors or destructors.) */
532#ifdef __GNUC__
533
534/* Define a dummy function F. Declare F too, to pacify gcc
535 -Wmissing-prototypes. */
536#define DEFINE_DUMMY_FUNCTION(f) \
537 void f (void) ATTRIBUTE_CONST EXTERNALLY_VISIBLE; void f (void) {}
538
539#ifndef GCC_CTORS_IN_LIBC
540DEFINE_DUMMY_FUNCTION (__do_global_ctors)
541DEFINE_DUMMY_FUNCTION (__do_global_ctors_aux)
542DEFINE_DUMMY_FUNCTION (__do_global_dtors)
543/* GNU/Linux has a bug in its library; avoid an error. */
544#ifndef GNU_LINUX
545char * __CTOR_LIST__[2] EXTERNALLY_VISIBLE = { (char *) (-1), 0 };
546#endif
547char * __DTOR_LIST__[2] EXTERNALLY_VISIBLE = { (char *) (-1), 0 };
548#endif /* GCC_CTORS_IN_LIBC */
549DEFINE_DUMMY_FUNCTION (__main)
550#endif /* __GNUC__ */
551#endif /* ORDINARY_LINK */
552
553/* Test whether the next argument in ARGV matches SSTR or a prefix of 527/* Test whether the next argument in ARGV matches SSTR or a prefix of
554 LSTR (at least MINLEN characters). If so, then if VALPTR is non-null 528 LSTR (at least MINLEN characters). If so, then if VALPTR is non-null
555 (the argument is supposed to have a value) store in *VALPTR either 529 (the argument is supposed to have a value) store in *VALPTR either
diff --git a/src/eval.c b/src/eval.c
index 030bf14bcea..5db6f9d0bf3 100644
--- a/src/eval.c
+++ b/src/eval.c
@@ -1898,7 +1898,7 @@ If LEXICAL is t, evaluate using lexical scoping. */)
1898{ 1898{
1899 ptrdiff_t count = SPECPDL_INDEX (); 1899 ptrdiff_t count = SPECPDL_INDEX ();
1900 specbind (Qinternal_interpreter_environment, 1900 specbind (Qinternal_interpreter_environment,
1901 NILP (lexical) ? Qnil : Fcons (Qt, Qnil)); 1901 CONSP (lexical) || NILP (lexical) ? lexical : Fcons (Qt, Qnil));
1902 return unbind_to (count, eval_sub (form)); 1902 return unbind_to (count, eval_sub (form));
1903} 1903}
1904 1904
diff --git a/src/filelock.c b/src/filelock.c
index cd2cd2e53a2..4d556de2454 100644
--- a/src/filelock.c
+++ b/src/filelock.c
@@ -43,6 +43,9 @@ along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */
43#include "buffer.h" 43#include "buffer.h"
44#include "coding.h" 44#include "coding.h"
45#include "systime.h" 45#include "systime.h"
46#ifdef WINDOWSNT
47#include "w32.h" /* for dostounix_filename */
48#endif
46 49
47#ifdef CLASH_DETECTION 50#ifdef CLASH_DETECTION
48 51
@@ -288,13 +291,22 @@ typedef struct
288#define FREE_LOCK_INFO(i) do { xfree ((i).user); xfree ((i).host); } while (0) 291#define FREE_LOCK_INFO(i) do { xfree ((i).user); xfree ((i).host); } while (0)
289 292
290 293
291/* Write the name of the lock file for FN into LFNAME. Length will be 294/* Write the name of the lock file for FNAME into LOCKNAME. Length
292 that of FN plus two more for the leading `.#' plus 1 for the 295 will be that of FN plus two more for the leading `.#' plus 1 for
293 trailing period plus one for the digit after it plus one for the 296 the trailing period plus one for the digit after it plus one for
294 null. */ 297 the null. */
295#define MAKE_LOCK_NAME(lock, file) \ 298#define MAKE_LOCK_NAME(LOCKNAME, FNAME) \
296 (lock = alloca (SBYTES (file) + 2 + 1 + 1 + 1), \ 299 (LOCKNAME = alloca (SBYTES (FNAME) + 2 + 1 + 1 + 1), \
297 fill_in_lock_file_name (lock, (file))) 300 fill_in_lock_file_name (LOCKNAME, (FNAME)))
301
302#ifdef WINDOWSNT
303/* 256 chars for user, 1024 chars for host, 10 digits for each of 2 int's. */
304#define MAX_LFINFO (256 + 1024 + 10 + 10 + 2)
305 /* min size: .@PID */
306#define IS_LOCK_FILE(ST) (MAX_LFINFO >= (ST).st_size && (ST).st_size >= 3)
307#else
308#define IS_LOCK_FILE(ST) S_ISLNK ((ST).st_mode)
309#endif
298 310
299static void 311static void
300fill_in_lock_file_name (register char *lockfile, register Lisp_Object fn) 312fill_in_lock_file_name (register char *lockfile, register Lisp_Object fn)
@@ -318,7 +330,7 @@ fill_in_lock_file_name (register char *lockfile, register Lisp_Object fn)
318 330
319 p = lockfile + length + 2; 331 p = lockfile + length + 2;
320 332
321 while (lstat (lockfile, &st) == 0 && !S_ISLNK (st.st_mode)) 333 while (lstat (lockfile, &st) == 0 && !IS_LOCK_FILE (st))
322 { 334 {
323 if (count > 9) 335 if (count > 9)
324 { 336 {
@@ -329,6 +341,49 @@ fill_in_lock_file_name (register char *lockfile, register Lisp_Object fn)
329 } 341 }
330} 342}
331 343
344static int
345create_lock_file (char *lfname, char *lock_info_str, bool force)
346{
347 int err;
348
349#ifdef WINDOWSNT
350 /* Symlinks are supported only by latest versions of Windows, and
351 creating them is a privileged operation that often triggers UAC
352 elevation prompts. Therefore, instead of using symlinks, we
353 create a regular file with the lock info written as its
354 contents. */
355 {
356 int fd = emacs_open (lfname, O_WRONLY | O_BINARY | O_CREAT | O_EXCL,
357 S_IREAD | S_IWRITE);
358
359 if (fd < 0 && errno == EEXIST && force)
360 fd = emacs_open (lfname, O_WRONLY | O_BINARY | O_TRUNC,
361 S_IREAD | S_IWRITE);
362 if (fd >= 0)
363 {
364 ssize_t lock_info_len = strlen (lock_info_str);
365
366 err = 0;
367 if (emacs_write (fd, lock_info_str, lock_info_len) != lock_info_len)
368 err = -1;
369 if (emacs_close (fd))
370 err = -1;
371 }
372 else
373 err = -1;
374 }
375#else
376 err = symlink (lock_info_str, lfname);
377 if (errno == EEXIST && force)
378 {
379 unlink (lfname);
380 err = symlink (lock_info_str, lfname);
381 }
382#endif
383
384 return err;
385}
386
332/* Lock the lock file named LFNAME. 387/* Lock the lock file named LFNAME.
333 If FORCE, do so even if it is already locked. 388 If FORCE, do so even if it is already locked.
334 Return true if successful. */ 389 Return true if successful. */
@@ -355,13 +410,7 @@ lock_file_1 (char *lfname, bool force)
355 410
356 esprintf (lock_info_str, boot ? "%s@%s.%"pMd":%"pMd : "%s@%s.%"pMd, 411 esprintf (lock_info_str, boot ? "%s@%s.%"pMd":%"pMd : "%s@%s.%"pMd,
357 user_name, host_name, pid, boot); 412 user_name, host_name, pid, boot);
358 413 err = create_lock_file (lfname, lock_info_str, force);
359 err = symlink (lock_info_str, lfname);
360 if (errno == EEXIST && force)
361 {
362 unlink (lfname);
363 err = symlink (lock_info_str, lfname);
364 }
365 414
366 symlink_errno = errno; 415 symlink_errno = errno;
367 SAFE_FREE (); 416 SAFE_FREE ();
@@ -377,6 +426,32 @@ within_one_second (time_t a, time_t b)
377 return (a - b >= -1 && a - b <= 1); 426 return (a - b >= -1 && a - b <= 1);
378} 427}
379 428
429static Lisp_Object
430read_lock_data (char *lfname)
431{
432#ifndef WINDOWSNT
433 return emacs_readlinkat (AT_FDCWD, lfname);
434#else
435 int fd = emacs_open (lfname, O_RDONLY | O_BINARY, S_IREAD);
436 ssize_t nbytes;
437 char lfinfo[MAX_LFINFO + 1];
438
439 if (fd < 0)
440 return Qnil;
441
442 nbytes = emacs_read (fd, lfinfo, MAX_LFINFO);
443 emacs_close (fd);
444
445 if (nbytes > 0)
446 {
447 lfinfo[nbytes] = '\0';
448 return build_string (lfinfo);
449 }
450 else
451 return Qnil;
452#endif
453}
454
380/* Return 0 if nobody owns the lock file LFNAME or the lock is obsolete, 455/* Return 0 if nobody owns the lock file LFNAME or the lock is obsolete,
381 1 if another process owns it (and set OWNER (if non-null) to info), 456 1 if another process owns it (and set OWNER (if non-null) to info),
382 2 if the current process owns it, 457 2 if the current process owns it,
@@ -390,7 +465,7 @@ current_lock_owner (lock_info_type *owner, char *lfname)
390 lock_info_type local_owner; 465 lock_info_type local_owner;
391 intmax_t n; 466 intmax_t n;
392 char *at, *dot, *colon; 467 char *at, *dot, *colon;
393 Lisp_Object lfinfo_object = emacs_readlinkat (AT_FDCWD, lfname); 468 Lisp_Object lfinfo_object = read_lock_data (lfname);
394 char *lfinfo; 469 char *lfinfo;
395 struct gcpro gcpro1; 470 struct gcpro gcpro1;
396 471
@@ -552,6 +627,12 @@ lock_file (Lisp_Object fn)
552 orig_fn = fn; 627 orig_fn = fn;
553 GCPRO1 (fn); 628 GCPRO1 (fn);
554 fn = Fexpand_file_name (fn, Qnil); 629 fn = Fexpand_file_name (fn, Qnil);
630#ifdef WINDOWSNT
631 /* Ensure we have only '/' separators, to avoid problems with
632 looking (inside fill_in_lock_file_name) for backslashes in file
633 names encoded by some DBCS codepage. */
634 dostounix_filename (SSDATA (fn), 1);
635#endif
555 encoded_fn = ENCODE_FILE (fn); 636 encoded_fn = ENCODE_FILE (fn);
556 637
557 /* Create the name of the lock-file for file fn */ 638 /* Create the name of the lock-file for file fn */
diff --git a/src/makefile.w32-in b/src/makefile.w32-in
index 6e1873f8e49..93f12900dde 100644
--- a/src/makefile.w32-in
+++ b/src/makefile.w32-in
@@ -864,6 +864,7 @@ $(BLD)/fileio.$(O) : \
864 864
865$(BLD)/filelock.$(O) : \ 865$(BLD)/filelock.$(O) : \
866 $(SRC)/filelock.c \ 866 $(SRC)/filelock.c \
867 $(SRC)/w32.h \
867 $(NT_INC)/pwd.h \ 868 $(NT_INC)/pwd.h \
868 $(NT_INC)/sys/file.h \ 869 $(NT_INC)/sys/file.h \
869 $(NT_INC)/sys/stat.h \ 870 $(NT_INC)/sys/stat.h \
@@ -1492,7 +1493,6 @@ $(BLD)/unexw32.$(O) : \
1492 1493
1493$(BLD)/vm-limit.$(O) : \ 1494$(BLD)/vm-limit.$(O) : \
1494 $(SRC)/vm-limit.c \ 1495 $(SRC)/vm-limit.c \
1495 $(SRC)/mem-limits.h \
1496 $(SRC)/w32heap.h \ 1496 $(SRC)/w32heap.h \
1497 $(NT_INC)/unistd.h \ 1497 $(NT_INC)/unistd.h \
1498 $(CONFIG_H) \ 1498 $(CONFIG_H) \
diff --git a/src/mem-limits.h b/src/mem-limits.h
deleted file mode 100644
index 941ccf5f121..00000000000
--- a/src/mem-limits.h
+++ /dev/null
@@ -1,43 +0,0 @@
1/* Includes for memory limit warnings.
2 Copyright (C) 1990, 1993-1996, 2001-2013 Free Software Foundation,
3 Inc.
4
5This file is part of GNU Emacs.
6
7GNU Emacs is free software: you can redistribute it and/or modify
8it under the terms of the GNU General Public License as published by
9the Free Software Foundation, either version 3 of the License, or
10(at your option) any later version.
11
12GNU Emacs is distributed in the hope that it will be useful,
13but WITHOUT ANY WARRANTY; without even the implied warranty of
14MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15GNU General Public License for more details.
16
17You should have received a copy of the GNU General Public License
18along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */
19
20#ifdef MSDOS
21#include <dpmi.h>
22extern int etext;
23#endif
24
25/* Some systems need this before <sys/resource.h>. */
26#include <sys/types.h>
27
28#ifdef HAVE_SYS_RESOURCE_H
29# include <sys/time.h>
30# include <sys/resource.h>
31#else
32# if HAVE_SYS_VLIMIT_H
33# include <sys/vlimit.h> /* Obsolete, says glibc */
34# endif
35#endif
36
37extern char *start_of_data (void) ATTRIBUTE_CONST;
38#if USE_LSB_TAG || UINTPTR_MAX <= VAL_MAX
39#define EXCEEDS_LISP_PTR(ptr) 0
40#else
41#define EXCEEDS_LISP_PTR(ptr) \
42 (((uintptr_t) (ptr) & ~DATA_SEG_BITS) >> VALBITS)
43#endif
diff --git a/src/pre-crt0.c b/src/pre-crt0.c
deleted file mode 100644
index 6b9618c8dc3..00000000000
--- a/src/pre-crt0.c
+++ /dev/null
@@ -1,10 +0,0 @@
1/* This file is loaded before crt0.o on machines where we do not
2 remap part of the data space into text space in unexec.
3 On these machines, there is no problem with standard crt0.o's
4 that make environ an initialized variable. However, we do
5 need to make sure the label data_start exists anyway. */
6
7/* Create a label to appear at the beginning of data space.
8 Its value is nonzero so that it cannot be put into bss. */
9
10int data_start = 1;
diff --git a/src/textprop.c b/src/textprop.c
index c1f6e59bf2e..49fe427913c 100644
--- a/src/textprop.c
+++ b/src/textprop.c
@@ -1133,6 +1133,7 @@ Return t if any property value actually changed, nil otherwise. */)
1133 register ptrdiff_t s, len; 1133 register ptrdiff_t s, len;
1134 register int modified = 0; 1134 register int modified = 0;
1135 struct gcpro gcpro1; 1135 struct gcpro gcpro1;
1136 ptrdiff_t got;
1136 1137
1137 properties = validate_plist (properties); 1138 properties = validate_plist (properties);
1138 if (NILP (properties)) 1139 if (NILP (properties))
@@ -1152,26 +1153,25 @@ Return t if any property value actually changed, nil otherwise. */)
1152 and live buffers are always protected. */ 1153 and live buffers are always protected. */
1153 GCPRO1 (properties); 1154 GCPRO1 (properties);
1154 1155
1155 /* If we're not starting on an interval boundary, we have to 1156 /* If this interval already has the properties, we can skip it. */
1156 split this interval. */ 1157 if (interval_has_all_properties (properties, i))
1157 if (i->position != s)
1158 { 1158 {
1159 /* If this interval already has the properties, we can 1159 got = LENGTH (i) - (s - i->position);
1160 skip it. */ 1160 do {
1161 if (interval_has_all_properties (properties, i)) 1161 if (got >= len)
1162 { 1162 RETURN_UNGCPRO (Qnil);
1163 ptrdiff_t got = (LENGTH (i) - (s - i->position)); 1163 len -= got;
1164 if (got >= len) 1164 i = next_interval (i);
1165 RETURN_UNGCPRO (Qnil); 1165 got = LENGTH (i);
1166 len -= got; 1166 } while (interval_has_all_properties (properties, i));
1167 i = next_interval (i); 1167 }
1168 } 1168 else if (i->position != s)
1169 else 1169 {
1170 { 1170 /* If we're not starting on an interval boundary, we have to
1171 unchanged = i; 1171 split this interval. */
1172 i = split_interval_right (unchanged, s - unchanged->position); 1172 unchanged = i;
1173 copy_properties (unchanged, i); 1173 i = split_interval_right (unchanged, s - unchanged->position);
1174 } 1174 copy_properties (unchanged, i);
1175 } 1175 }
1176 1176
1177 if (BUFFERP (object)) 1177 if (BUFFERP (object))
@@ -1195,7 +1195,8 @@ Return t if any property value actually changed, nil otherwise. */)
1195 signal_after_change (XINT (start), XINT (end) - XINT (start), 1195 signal_after_change (XINT (start), XINT (end) - XINT (start),
1196 XINT (end) - XINT (start)); 1196 XINT (end) - XINT (start));
1197 1197
1198 return modified ? Qt : Qnil; 1198 eassert (modified);
1199 return Qt;
1199 } 1200 }
1200 1201
1201 if (LENGTH (i) == len) 1202 if (LENGTH (i) == len)
@@ -1426,6 +1427,7 @@ Use `set-text-properties' if you want to remove all text properties. */)
1426 register INTERVAL i, unchanged; 1427 register INTERVAL i, unchanged;
1427 register ptrdiff_t s, len; 1428 register ptrdiff_t s, len;
1428 register int modified = 0; 1429 register int modified = 0;
1430 ptrdiff_t got;
1429 1431
1430 if (NILP (object)) 1432 if (NILP (object))
1431 XSETBUFFER (object, current_buffer); 1433 XSETBUFFER (object, current_buffer);
@@ -1437,26 +1439,25 @@ Use `set-text-properties' if you want to remove all text properties. */)
1437 s = XINT (start); 1439 s = XINT (start);
1438 len = XINT (end) - s; 1440 len = XINT (end) - s;
1439 1441
1440 if (i->position != s) 1442 /* If there are no properties on this entire interval, return. */
1443 if (! interval_has_some_properties (properties, i))
1441 { 1444 {
1442 /* No properties on this first interval -- return if 1445 got = (LENGTH (i) - (s - i->position));
1443 it covers the entire region. */ 1446 do {
1444 if (! interval_has_some_properties (properties, i)) 1447 if (got >= len)
1445 { 1448 return Qnil;
1446 ptrdiff_t got = (LENGTH (i) - (s - i->position)); 1449 len -= got;
1447 if (got >= len) 1450 i = next_interval (i);
1448 return Qnil; 1451 got = LENGTH (i);
1449 len -= got; 1452 } while (! interval_has_some_properties (properties, i));
1450 i = next_interval (i); 1453 }
1451 } 1454 /* Split away the beginning of this interval; what we don't
1452 /* Split away the beginning of this interval; what we don't 1455 want to modify. */
1453 want to modify. */ 1456 else if (i->position != s)
1454 else 1457 {
1455 { 1458 unchanged = i;
1456 unchanged = i; 1459 i = split_interval_right (unchanged, s - unchanged->position);
1457 i = split_interval_right (unchanged, s - unchanged->position); 1460 copy_properties (unchanged, i);
1458 copy_properties (unchanged, i);
1459 }
1460 } 1461 }
1461 1462
1462 if (BUFFERP (object)) 1463 if (BUFFERP (object))
@@ -1470,7 +1471,13 @@ Use `set-text-properties' if you want to remove all text properties. */)
1470 if (LENGTH (i) >= len) 1471 if (LENGTH (i) >= len)
1471 { 1472 {
1472 if (! interval_has_some_properties (properties, i)) 1473 if (! interval_has_some_properties (properties, i))
1473 return modified ? Qt : Qnil; 1474 {
1475 eassert (modified);
1476 if (BUFFERP (object))
1477 signal_after_change (XINT (start), XINT (end) - XINT (start),
1478 XINT (end) - XINT (start));
1479 return Qt;
1480 }
1474 1481
1475 if (LENGTH (i) == len) 1482 if (LENGTH (i) == len)
1476 { 1483 {
@@ -1512,6 +1519,7 @@ Return t if any property was actually removed, nil otherwise. */)
1512 register ptrdiff_t s, len; 1519 register ptrdiff_t s, len;
1513 register int modified = 0; 1520 register int modified = 0;
1514 Lisp_Object properties; 1521 Lisp_Object properties;
1522 ptrdiff_t got;
1515 properties = list_of_properties; 1523 properties = list_of_properties;
1516 1524
1517 if (NILP (object)) 1525 if (NILP (object))
@@ -1524,26 +1532,25 @@ Return t if any property was actually removed, nil otherwise. */)
1524 s = XINT (start); 1532 s = XINT (start);
1525 len = XINT (end) - s; 1533 len = XINT (end) - s;
1526 1534
1527 if (i->position != s) 1535 /* If there are no properties on the interval, return. */
1536 if (! interval_has_some_properties_list (properties, i))
1528 { 1537 {
1529 /* No properties on this first interval -- return if 1538 got = (LENGTH (i) - (s - i->position));
1530 it covers the entire region. */ 1539 do {
1531 if (! interval_has_some_properties_list (properties, i)) 1540 if (got >= len)
1532 { 1541 return Qnil;
1533 ptrdiff_t got = (LENGTH (i) - (s - i->position)); 1542 len -= got;
1534 if (got >= len) 1543 i = next_interval (i);
1535 return Qnil; 1544 got = LENGTH (i);
1536 len -= got; 1545 } while (! interval_has_some_properties_list (properties, i));
1537 i = next_interval (i); 1546 }
1538 } 1547 /* Split away the beginning of this interval; what we don't
1539 /* Split away the beginning of this interval; what we don't 1548 want to modify. */
1540 want to modify. */ 1549 else if (i->position != s)
1541 else 1550 {
1542 { 1551 unchanged = i;
1543 unchanged = i; 1552 i = split_interval_right (unchanged, s - unchanged->position);
1544 i = split_interval_right (unchanged, s - unchanged->position); 1553 copy_properties (unchanged, i);
1545 copy_properties (unchanged, i);
1546 }
1547 } 1554 }
1548 1555
1549 /* We are at the beginning of an interval, with len to scan. 1556 /* We are at the beginning of an interval, with len to scan.
diff --git a/src/unexaix.c b/src/unexaix.c
index da44480fdca..44a824b8c12 100644
--- a/src/unexaix.c
+++ b/src/unexaix.c
@@ -59,8 +59,6 @@ what you give them. Help stamp out software-hoarding! */
59#include <unistd.h> 59#include <unistd.h>
60#include <fcntl.h> 60#include <fcntl.h>
61 61
62#include "mem-limits.h"
63
64extern char _data[]; 62extern char _data[];
65extern char _text[]; 63extern char _text[];
66 64
diff --git a/src/unexcoff.c b/src/unexcoff.c
index 466a5c0e491..2e662a34145 100644
--- a/src/unexcoff.c
+++ b/src/unexcoff.c
@@ -99,7 +99,7 @@ struct aouthdr
99 99
100#include <sys/file.h> 100#include <sys/file.h>
101 101
102#include "mem-limits.h" 102extern int etext;
103 103
104static long block_copy_start; /* Old executable start point */ 104static long block_copy_start; /* Old executable start point */
105static struct filehdr f_hdr; /* File header */ 105static struct filehdr f_hdr; /* File header */
@@ -168,7 +168,7 @@ make_hdr (int new, int a_out,
168 pagemask = getpagesize () - 1; 168 pagemask = getpagesize () - 1;
169 169
170 /* Adjust text/data boundary. */ 170 /* Adjust text/data boundary. */
171 data_start = (int) start_of_data (); 171 data_start = (int) DATA_START;
172 data_start = ADDR_CORRECT (data_start); 172 data_start = ADDR_CORRECT (data_start);
173 data_start = data_start & ~pagemask; /* (Down) to page boundary. */ 173 data_start = data_start & ~pagemask; /* (Down) to page boundary. */
174 174
diff --git a/src/vm-limit.c b/src/vm-limit.c
index fc7a253325a..3fca8bd26c1 100644
--- a/src/vm-limit.c
+++ b/src/vm-limit.c
@@ -19,7 +19,37 @@ along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */
19#include <config.h> 19#include <config.h>
20#include <unistd.h> /* for 'environ', on AIX */ 20#include <unistd.h> /* for 'environ', on AIX */
21#include "lisp.h" 21#include "lisp.h"
22#include "mem-limits.h" 22
23#ifdef MSDOS
24#include <dpmi.h>
25extern int etext;
26#endif
27
28/* Some systems need this before <sys/resource.h>. */
29#include <sys/types.h>
30
31#ifdef HAVE_SYS_RESOURCE_H
32# include <sys/time.h>
33# include <sys/resource.h>
34#else
35# if HAVE_SYS_VLIMIT_H
36# include <sys/vlimit.h> /* Obsolete, says glibc */
37# endif
38#endif
39
40/* Start of data. It is OK if this is approximate; it's used only as
41 a heuristic. */
42#ifdef DATA_START
43# define data_start ((char *) DATA_START)
44#else
45extern char data_start[];
46# ifndef HAVE_DATA_START
47/* Initialize to nonzero, so that it's put into data and not bss.
48 Link this file's object code first, so that this symbol is near the
49 start of data. */
50char data_start[1] = { 1 };
51# endif
52#endif
23 53
24/* 54/*
25 Level number of warnings already issued. 55 Level number of warnings already issued.
@@ -35,12 +65,20 @@ static enum warnlevel warnlevel;
35 0 means don't issue them. */ 65 0 means don't issue them. */
36static void (*warn_function) (const char *); 66static void (*warn_function) (const char *);
37 67
38/* Start of data space; can be changed by calling malloc_init. */ 68/* Start of data space; can be changed by calling memory_warnings. */
39static void *data_space_start; 69static char *data_space_start;
40 70
41/* Number of bytes of writable memory we can expect to be able to get. */ 71/* Number of bytes of writable memory we can expect to be able to get. */
42static size_t lim_data; 72static size_t lim_data;
43 73
74/* Return true if PTR cannot be represented as an Emacs Lisp object. */
75static bool
76exceeds_lisp_ptr (void *ptr)
77{
78 return (! USE_LSB_TAG
79 && VAL_MAX < UINTPTR_MAX
80 && ((uintptr_t) ptr & ~DATA_SEG_BITS) >> VALBITS != 0);
81}
44 82
45#ifdef HAVE_GETRLIMIT 83#ifdef HAVE_GETRLIMIT
46 84
@@ -122,10 +160,12 @@ check_memory_limits (void)
122{ 160{
123#ifdef REL_ALLOC 161#ifdef REL_ALLOC
124 extern void *(*real_morecore) (ptrdiff_t); 162 extern void *(*real_morecore) (ptrdiff_t);
163#else
164 void *(*real_morecore) (ptrdiff_t) = 0;
125#endif 165#endif
126 extern void *(*__morecore) (ptrdiff_t); 166 extern void *(*__morecore) (ptrdiff_t);
127 167
128 void *cp; 168 char *cp;
129 size_t five_percent; 169 size_t five_percent;
130 size_t data_size; 170 size_t data_size;
131 enum warnlevel new_warnlevel; 171 enum warnlevel new_warnlevel;
@@ -135,13 +175,8 @@ check_memory_limits (void)
135 five_percent = lim_data / 20; 175 five_percent = lim_data / 20;
136 176
137 /* Find current end of memory and issue warning if getting near max */ 177 /* Find current end of memory and issue warning if getting near max */
138#ifdef REL_ALLOC 178 cp = (real_morecore ? real_morecore : __morecore) (0);
139 if (real_morecore) 179 data_size = cp - data_space_start;
140 cp = (char *) (*real_morecore) (0);
141 else
142#endif
143 cp = (char *) (*__morecore) (0);
144 data_size = (char *) cp - (char *) data_space_start;
145 180
146 if (!warn_function) 181 if (!warn_function)
147 return; 182 return;
@@ -188,49 +223,10 @@ check_memory_limits (void)
188 warnlevel = warned_85; 223 warnlevel = warned_85;
189 } 224 }
190 225
191 if (EXCEEDS_LISP_PTR (cp)) 226 if (exceeds_lisp_ptr (cp))
192 (*warn_function) ("Warning: memory in use exceeds lisp pointer size"); 227 (*warn_function) ("Warning: memory in use exceeds lisp pointer size");
193} 228}
194 229
195#if !defined (CANNOT_DUMP) || !defined (SYSTEM_MALLOC)
196/* Some systems that cannot dump also cannot implement these. */
197
198/*
199 * Return the address of the start of the data segment prior to
200 * doing an unexec. After unexec the return value is undefined.
201 * See crt0.c for further information and definition of data_start.
202 *
203 * Apparently, on BSD systems this is etext at startup. On
204 * USG systems (swapping) this is highly mmu dependent and
205 * is also dependent on whether or not the program is running
206 * with shared text. Generally there is a (possibly large)
207 * gap between end of text and start of data with shared text.
208 *
209 */
210
211char *
212start_of_data (void)
213{
214#ifdef BSD_SYSTEM
215 extern char etext;
216 return (void *) &etext;
217#elif defined DATA_START
218 return (void *) DATA_START;
219#elif defined ORDINARY_LINK
220 /*
221 * This is a hack. Since we're not linking crt0.c or pre_crt0.c,
222 * data_start isn't defined. We take the address of environ, which
223 * is known to live at or near the start of the system crt0.c, and
224 * we don't sweat the handful of bytes that might lose.
225 */
226 return (void *) &environ;
227#else
228 extern int data_start;
229 return (void *) &data_start;
230#endif
231}
232#endif /* (not CANNOT_DUMP or not SYSTEM_MALLOC) */
233
234/* Enable memory usage warnings. 230/* Enable memory usage warnings.
235 START says where the end of pure storage is. 231 START says where the end of pure storage is.
236 WARNFUN specifies the function to call to issue a warning. */ 232 WARNFUN specifies the function to call to issue a warning. */
@@ -240,10 +236,7 @@ memory_warnings (void *start, void (*warnfun) (const char *))
240{ 236{
241 extern void (* __after_morecore_hook) (void); /* From gmalloc.c */ 237 extern void (* __after_morecore_hook) (void); /* From gmalloc.c */
242 238
243 if (start) 239 data_space_start = start ? start : data_start;
244 data_space_start = start;
245 else
246 data_space_start = start_of_data ();
247 240
248 warn_function = warnfun; 241 warn_function = warnfun;
249 __after_morecore_hook = check_memory_limits; 242 __after_morecore_hook = check_memory_limits;
diff --git a/src/w32.c b/src/w32.c
index 5011642adf2..aff9771e4bb 100644
--- a/src/w32.c
+++ b/src/w32.c
@@ -3402,10 +3402,13 @@ int
3402sys_open (const char * path, int oflag, int mode) 3402sys_open (const char * path, int oflag, int mode)
3403{ 3403{
3404 const char* mpath = map_w32_filename (path, NULL); 3404 const char* mpath = map_w32_filename (path, NULL);
3405 /* Try to open file without _O_CREAT, to be able to write to hidden 3405 int res = -1;
3406 and system files. Force all file handles to be 3406
3407 non-inheritable. */ 3407 /* If possible, try to open file without _O_CREAT, to be able to
3408 int res = _open (mpath, (oflag & ~_O_CREAT) | _O_NOINHERIT, mode); 3408 write to existing hidden and system files. Force all file
3409 handles to be non-inheritable. */
3410 if ((oflag & (_O_CREAT | _O_EXCL)) != (_O_CREAT | _O_EXCL))
3411 res = _open (mpath, (oflag & ~_O_CREAT) | _O_NOINHERIT, mode);
3409 if (res < 0) 3412 if (res < 0)
3410 res = _open (mpath, oflag | _O_NOINHERIT, mode); 3413 res = _open (mpath, oflag | _O_NOINHERIT, mode);
3411 if (res >= 0 && res < MAXDESC) 3414 if (res >= 0 && res < MAXDESC)
diff --git a/src/w32proc.c b/src/w32proc.c
index 961791a40ed..84589388cd7 100644
--- a/src/w32proc.c
+++ b/src/w32proc.c
@@ -2263,12 +2263,42 @@ sys_kill (pid_t pid, int sig)
2263 pid = -pid; 2263 pid = -pid;
2264 2264
2265 /* Only handle signals that will result in the process dying */ 2265 /* Only handle signals that will result in the process dying */
2266 if (sig != SIGINT && sig != SIGKILL && sig != SIGQUIT && sig != SIGHUP) 2266 if (sig != 0
2267 && sig != SIGINT && sig != SIGKILL && sig != SIGQUIT && sig != SIGHUP)
2267 { 2268 {
2268 errno = EINVAL; 2269 errno = EINVAL;
2269 return -1; 2270 return -1;
2270 } 2271 }
2271 2272
2273 if (sig == 0)
2274 {
2275 /* It will take _some_ time before PID 4 or less on Windows will
2276 be Emacs... */
2277 if (pid <= 4)
2278 {
2279 errno = EPERM;
2280 return -1;
2281 }
2282 proc_hand = OpenProcess (PROCESS_QUERY_INFORMATION, 0, pid);
2283 if (proc_hand == NULL)
2284 {
2285 DWORD err = GetLastError ();
2286
2287 switch (err)
2288 {
2289 case ERROR_ACCESS_DENIED: /* existing process, but access denied */
2290 errno = EPERM;
2291 return -1;
2292 case ERROR_INVALID_PARAMETER: /* process PID does not exist */
2293 errno = ESRCH;
2294 return -1;
2295 }
2296 }
2297 else
2298 CloseHandle (proc_hand);
2299 return 0;
2300 }
2301
2272 cp = find_child_pid (pid); 2302 cp = find_child_pid (pid);
2273 if (cp == NULL) 2303 if (cp == NULL)
2274 { 2304 {