------------------------------------------------------------ revno: 117510 committer: Eli Zaretskii branch nick: trunk timestamp: Thu 2014-07-10 22:09:26 +0300 message: Implement memory-info for MS-Windows. src/w32.c (w32_memory_info): New function. src/w32.h (w32_memory_info): Prototype it. src/alloc.c (Fmemory_info) [WINDOWSNT]: Call it. diff: === modified file 'src/ChangeLog' --- src/ChangeLog 2014-07-10 12:33:35 +0000 +++ src/ChangeLog 2014-07-10 19:09:26 +0000 @@ -1,3 +1,10 @@ +2014-07-10 Eli Zaretskii + + Implement memory-info for MS-Windows. + * w32.c (w32_memory_info): New function. + * w32.h (w32_memory_info): Prototype it. + * alloc.c (Fmemory_info) [WINDOWSNT]: Call it. + 2014-07-10 Dmitry Antipov * coding.h (struct coding_system): Remove 'error_positions' (unused) === modified file 'src/alloc.c' --- src/alloc.c 2014-07-10 12:33:35 +0000 +++ src/alloc.c 2014-07-10 19:09:26 +0000 @@ -6875,7 +6875,7 @@ values are zero. If the system is not supported, return nil. */) (void) { -#ifdef HAVE_LINUX_SYSINFO +#if defined HAVE_LINUX_SYSINFO struct sysinfo si; uintmax_t units; @@ -6885,12 +6885,22 @@ units = si.mem_unit; #else units = 1; -#endif +#endif return list4i ((uintmax_t) si.totalram * units / 1024, (uintmax_t) si.freeram * units / 1024, (uintmax_t) si.totalswap * units / 1024, (uintmax_t) si.freeswap * units / 1024); -#else /* not HAVE_LINUX_SYSINFO */ +#elif defined WINDOWSNT + unsigned long long totalram, freeram, totalswap, freeswap; + + if (w32_memory_info (&totalram, &freeram, &totalswap, &freeswap) == 0) + return list4i ((uintmax_t) totalram / 1024, + (uintmax_t) freeram / 1024, + (uintmax_t) totalswap / 1024, + (uintmax_t) freeswap / 1024); + else + return Qnil; +#else /* not HAVE_LINUX_SYSINFO, not WINDOWSNT */ /* FIXME: add more systems. */ return Qnil; #endif /* HAVE_LINUX_SYSINFO */ === modified file 'src/w32.c' --- src/w32.c 2014-07-09 02:04:12 +0000 +++ src/w32.c 2014-07-10 19:09:26 +0000 @@ -6955,6 +6955,35 @@ return attrs; } +int +w32_memory_info (unsigned long long *totalram, unsigned long long *freeram, + unsigned long long *totalswap, unsigned long long *freeswap) +{ + MEMORYSTATUS memst; + MEMORY_STATUS_EX memstex; + + /* Use GlobalMemoryStatusEx if available, as it can report more than + 2GB of memory. */ + if (global_memory_status_ex (&memstex)) + { + *totalram = memstex.ullTotalPhys; + *freeram = memstex.ullAvailPhys; + *totalswap = memstex.ullTotalPageFile; + *freeswap = memstex.ullAvailPageFile; + return 0; + } + else if (global_memory_status (&memst)) + { + *totalram = memst.dwTotalPhys; + *freeram = memst.dwAvailPhys; + *totalswap = memst.dwTotalPageFile; + *freeswap = memst.dwAvailPageFile; + return 0; + } + else + return -1; +} + /* Wrappers for winsock functions to map between our file descriptors and winsock's handles; also set h_errno for convenience. === modified file 'src/w32.h' --- src/w32.h 2014-02-06 15:27:46 +0000 +++ src/w32.h 2014-07-10 19:09:26 +0000 @@ -206,6 +206,10 @@ extern void sys_sleep (int); extern int sys_link (const char *, const char *); +/* Return total and free memory info. */ +extern int w32_memory_info (unsigned long long *, unsigned long long *, + unsigned long long *, unsigned long long *); + #ifdef HAVE_GNUTLS #include ------------------------------------------------------------ revno: 117509 committer: Eli Zaretskii branch nick: trunk timestamp: Thu 2014-07-10 21:19:37 +0300 message: lisp/files.el (warn-maybe-out-of-memory): Fix the wording of the warning. diff: === modified file 'lisp/ChangeLog' --- lisp/ChangeLog 2014-07-10 12:33:35 +0000 +++ lisp/ChangeLog 2014-07-10 18:19:37 +0000 @@ -1,3 +1,8 @@ +2014-07-10 Eli Zaretskii + + * files.el (warn-maybe-out-of-memory): Fix the wording of the + warning. + 2014-07-10 Dmitry Antipov * files.el (warn-maybe-out-of-memory): New function. === modified file 'lisp/files.el' --- lisp/files.el 2014-07-10 13:00:45 +0000 +++ lisp/files.el 2014-07-10 18:19:37 +0000 @@ -1804,10 +1804,10 @@ (let ((total-free-memory (+ (nth 1 meminfo) (nth 3 meminfo)))) (when (> (/ size 1024) total-free-memory) (warn - "You are trying to open file which size (%s) -exceeds an amount of available free memory (%s). If that -fails, try to open it with `find-file-literally' (but note -that some characters may be displayed incorrectly)." + "You are trying to open a file whose size (%s) +exceeds the amount of currently available free memory (%s). +If that fails, try to open it with `find-file-literally' +\(but note that some characters might be displayed incorrectly)." (file-size-human-readable size) (file-size-human-readable (* (float total-free-memory) 1024))))))))) ------------------------------------------------------------ revno: 117508 committer: Dmitry Antipov branch nick: trunk timestamp: Thu 2014-07-10 17:00:45 +0400 message: * files.el (warn-maybe-out-of-memory): Fix last change. diff: === modified file 'lisp/files.el' --- lisp/files.el 2014-07-10 12:33:35 +0000 +++ lisp/files.el 2014-07-10 13:00:45 +0000 @@ -1798,19 +1798,19 @@ (defun warn-maybe-out-of-memory (size) "Warn if an attempt to open file of SIZE bytes may run out of memory." - (let ((meminfo (memory-info))) - (when (consp meminfo) - (let ((total-free-memory (+ (nth 1 meminfo) (nth 3 meminfo)))) - (when (and (not (zerop size)) - (> (/ size 1024) total-free-memory)) - (warn - "You are trying to open file which size (%s) + (when (and (numberp size) (not (zerop size))) + (let ((meminfo (memory-info))) + (when (consp meminfo) + (let ((total-free-memory (+ (nth 1 meminfo) (nth 3 meminfo)))) + (when (> (/ size 1024) total-free-memory) + (warn + "You are trying to open file which size (%s) exceeds an amount of available free memory (%s). If that fails, try to open it with `find-file-literally' (but note that some characters may be displayed incorrectly)." - (file-size-human-readable size) - (file-size-human-readable - (* (float total-free-memory) 1024)))))))) + (file-size-human-readable size) + (file-size-human-readable + (* (float total-free-memory) 1024))))))))) (defun find-file-noselect (filename &optional nowarn rawfile wildcards) "Read file FILENAME into a buffer and return the buffer. ------------------------------------------------------------ revno: 117507 committer: Dmitry Antipov branch nick: trunk timestamp: Thu 2014-07-10 16:33:35 +0400 message: * configure.ac: Check whether sys/sysinfo.h provides Linux 'sysinfo' function and 'struct sysinfo' type. * src/alloc.c (Fmemory_info): New function. * lisp/files.el (warn-maybe-out-of-memory): New function. (find-file-noselect): Use it. diff: === modified file 'ChangeLog' --- ChangeLog 2014-06-28 22:57:23 +0000 +++ ChangeLog 2014-07-10 12:33:35 +0000 @@ -1,3 +1,8 @@ +2014-07-10 Dmitry Antipov + + * configure.ac: Check whether sys/sysinfo.h provides + Linux 'sysinfo' function and 'struct sysinfo' type. + 2014-06-28 Glenn Morris * configure.ac (lwlib_deps_frag, oldxmenu_deps_frag): New output files. === modified file 'configure.ac' --- configure.ac 2014-06-28 22:57:23 +0000 +++ configure.ac 2014-07-10 12:33:35 +0000 @@ -1510,6 +1510,7 @@ dnl checks for header files AC_CHECK_HEADERS_ONCE( sys/systeminfo.h + sys/sysinfo.h coff.h pty.h sys/resource.h sys/utsname.h pwd.h utmp.h util.h) @@ -1525,6 +1526,21 @@ [Define to 1 if personality LINUX32 can be set.]) fi +if test "$ac_cv_header_sys_sysinfo_h" = yes; then + AC_MSG_CHECKING([if Linux sysinfo may be used]) + AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[#include ]], + [[struct sysinfo si; sysinfo (&si)]])], + emacs_cv_linux_sysinfo=yes, emacs_cv_linux_sysinfo=no) + AC_MSG_RESULT($emacs_cv_linux_sysinfo) + if test $emacs_cv_linux_sysinfo = yes; then + AC_DEFINE([HAVE_LINUX_SYSINFO], 1, [Define to 1 if you have Linux sysinfo function.]) + AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[#include ]], + [[struct sysinfo si; return si.mem_unit]])], + AC_DEFINE(LINUX_SYSINFO_UNIT, 1, + [Define to 1 if Linux sysinfo sizes are in multiples of mem_unit bytes.])) + fi +fi + dnl On Solaris 8 there's a compilation warning for term.h because dnl it doesn't define `bool'. AC_CHECK_HEADERS(term.h, , , -) === modified file 'lisp/ChangeLog' --- lisp/ChangeLog 2014-07-09 14:51:52 +0000 +++ lisp/ChangeLog 2014-07-10 12:33:35 +0000 @@ -1,3 +1,8 @@ +2014-07-10 Dmitry Antipov + + * files.el (warn-maybe-out-of-memory): New function. + (find-file-noselect): Use it. + 2014-07-09 Sam Steingold * progmodes/cperl-mode.el (cperl-block-p): Treat the perl keyword === modified file 'lisp/files.el' --- lisp/files.el 2014-06-28 01:10:27 +0000 +++ lisp/files.el 2014-07-10 12:33:35 +0000 @@ -1796,6 +1796,22 @@ (file-size-human-readable size) op-type)))) (error "Aborted"))) +(defun warn-maybe-out-of-memory (size) + "Warn if an attempt to open file of SIZE bytes may run out of memory." + (let ((meminfo (memory-info))) + (when (consp meminfo) + (let ((total-free-memory (+ (nth 1 meminfo) (nth 3 meminfo)))) + (when (and (not (zerop size)) + (> (/ size 1024) total-free-memory)) + (warn + "You are trying to open file which size (%s) +exceeds an amount of available free memory (%s). If that +fails, try to open it with `find-file-literally' (but note +that some characters may be displayed incorrectly)." + (file-size-human-readable size) + (file-size-human-readable + (* (float total-free-memory) 1024)))))))) + (defun find-file-noselect (filename &optional nowarn rawfile wildcards) "Read file FILENAME into a buffer and return the buffer. If a buffer exists visiting FILENAME, return that one, but @@ -1848,7 +1864,8 @@ (setq buf other)))) ;; Check to see if the file looks uncommonly large. (when (not (or buf nowarn)) - (abort-if-file-too-large (nth 7 attributes) "open" filename)) + (abort-if-file-too-large (nth 7 attributes) "open" filename) + (warn-maybe-out-of-memory (nth 7 attributes))) (if buf ;; We are using an existing buffer. (let (nonexistent) === modified file 'src/ChangeLog' --- src/ChangeLog 2014-07-10 04:35:55 +0000 +++ src/ChangeLog 2014-07-10 12:33:35 +0000 @@ -9,6 +9,8 @@ (decode_coding_big5, decode_coding_charset, decode_coding) (encode_coding): Adjust users. + * alloc.c (Fmemory_info): New function. + 2014-07-09 Paul Eggert * syntax.c (back_comment): Use more-natural location for label. === modified file 'src/alloc.c' --- src/alloc.c 2014-07-02 03:26:19 +0000 +++ src/alloc.c 2014-07-10 12:33:35 +0000 @@ -49,6 +49,10 @@ #include #include /* For backtrace. */ +#ifdef HAVE_LINUX_SYSINFO +#include +#endif + #if (defined ENABLE_CHECKING \ && defined HAVE_VALGRIND_VALGRIND_H \ && !defined USE_VALGRIND) @@ -6865,7 +6869,33 @@ check_string_bytes (!noninteractive); } - +DEFUN ("memory-info", Fmemory_info, Smemory_info, 0, 0, 0, + doc: /* Return a list of (TOTAL-RAM FREE-RAM TOTAL-SWAP FREE-SWAP). +All values are in Kbytes. If there is no swap space, last two +values are zero. If the system is not supported, return nil. */) + (void) +{ +#ifdef HAVE_LINUX_SYSINFO + struct sysinfo si; + uintmax_t units; + + if (sysinfo (&si)) + emacs_abort (); +#ifdef LINUX_SYSINFO_UNIT + units = si.mem_unit; +#else + units = 1; +#endif + return list4i ((uintmax_t) si.totalram * units / 1024, + (uintmax_t) si.freeram * units / 1024, + (uintmax_t) si.totalswap * units / 1024, + (uintmax_t) si.freeswap * units / 1024); +#else /* not HAVE_LINUX_SYSINFO */ + /* FIXME: add more systems. */ + return Qnil; +#endif /* HAVE_LINUX_SYSINFO */ +} + /* Debugging aids. */ DEFUN ("memory-limit", Fmemory_limit, Smemory_limit, 0, 0, 0, @@ -7204,6 +7234,7 @@ defsubr (&Spurecopy); defsubr (&Sgarbage_collect); defsubr (&Smemory_limit); + defsubr (&Smemory_info); defsubr (&Smemory_use_counts); defsubr (&Ssuspicious_object); ------------------------------------------------------------ revno: 117506 committer: Dmitry Antipov branch nick: trunk timestamp: Thu 2014-07-10 08:35:55 +0400 message: * coding.h (struct coding_system): Remove 'error_positions' (unused) and 'errors' (set but unused) fields. Use bitfields for 'eol_seen', 'mode', 'common_flags' and 'result' fields, adjust layout to avoid extra padding and shrink struct coding_system by 56 bytes (x86_64). * coding.c (decode_coding_utf_8, decode_coding_utf_16) (decode_coding_emacs_mule, decode_coding_iso_2022, decode_coding_sjis) (decode_coding_big5, decode_coding_charset, decode_coding) (encode_coding): Adjust users. diff: === modified file 'src/ChangeLog' --- src/ChangeLog 2014-07-09 23:39:58 +0000 +++ src/ChangeLog 2014-07-10 04:35:55 +0000 @@ -1,3 +1,14 @@ +2014-07-10 Dmitry Antipov + + * coding.h (struct coding_system): Remove 'error_positions' (unused) + and 'errors' (set but unused) fields. Use bitfields for 'eol_seen', + 'mode', 'common_flags' and 'result' fields, adjust layout to avoid + extra padding and shrink struct coding_system by 56 bytes (x86_64). + * coding.c (decode_coding_utf_8, decode_coding_utf_16) + (decode_coding_emacs_mule, decode_coding_iso_2022, decode_coding_sjis) + (decode_coding_big5, decode_coding_charset, decode_coding) + (encode_coding): Adjust users. + 2014-07-09 Paul Eggert * syntax.c (back_comment): Use more-natural location for label. === modified file 'src/coding.c' --- src/coding.c 2014-07-09 10:36:35 +0000 +++ src/coding.c 2014-07-10 04:35:55 +0000 @@ -1486,7 +1486,6 @@ consumed_chars = consumed_chars_base; ONE_MORE_BYTE (c); *charbuf++ = ASCII_CHAR_P (c) ? c : BYTE8_TO_CHAR (c); - coding->errors++; } no_more_source: @@ -1685,7 +1684,6 @@ /* The first two bytes are not BOM. Treat them as bytes for a normal character. */ src = src_base; - coding->errors++; } CODING_UTF_16_BOM (coding) = utf_without_bom; } @@ -1742,7 +1740,6 @@ c1 = surrogate & 0xFF, c2 = surrogate >> 8; *charbuf++ = c1; *charbuf++ = c2; - coding->errors++; if (UTF_16_HIGH_SURROGATE_P (c)) CODING_UTF_16_SURROGATE (coding) = surrogate = c; else @@ -2598,7 +2595,6 @@ ONE_MORE_BYTE (c); *charbuf++ = ASCII_CHAR_P (c) ? c : BYTE8_TO_CHAR (c); char_offset++; - coding->errors++; } no_more_source: @@ -4006,7 +4002,6 @@ ONE_MORE_BYTE (c); *charbuf++ = c < 0 ? -c : ASCII_CHAR_P (c) ? c : BYTE8_TO_CHAR (c); char_offset++; - coding->errors++; /* Reset the invocation and designation status to the safest one; i.e. designate ASCII to the graphic register 0, and invoke that register to the graphic plane 0. This typically @@ -4837,7 +4832,6 @@ ONE_MORE_BYTE (c); *charbuf++ = c < 0 ? -c : BYTE8_TO_CHAR (c); char_offset++; - coding->errors++; } no_more_source: @@ -4933,7 +4927,6 @@ ONE_MORE_BYTE (c); *charbuf++ = c < 0 ? -c : BYTE8_TO_CHAR (c); char_offset++; - coding->errors++; } no_more_source: @@ -5642,7 +5635,6 @@ ONE_MORE_BYTE (c); *charbuf++ = c < 0 ? -c : ASCII_CHAR_P (c) ? c : BYTE8_TO_CHAR (c); char_offset++; - coding->errors++; } no_more_source: @@ -7375,7 +7367,6 @@ coding->produced = coding->produced_char = 0; coding->chars_at_source = 0; record_conversion_result (coding, CODING_RESULT_SUCCESS); - coding->errors = 0; ALLOC_CONVERSION_WORK_AREA (coding, coding->src_bytes); @@ -7771,7 +7762,6 @@ coding->consumed = coding->consumed_char = 0; coding->produced = coding->produced_char = 0; record_conversion_result (coding, CODING_RESULT_SUCCESS); - coding->errors = 0; ALLOC_CONVERSION_WORK_AREA (coding, coding->src_chars); === modified file 'src/coding.h' --- src/coding.h 2014-04-05 19:30:36 +0000 +++ src/coding.h 2014-07-10 04:35:55 +0000 @@ -434,11 +434,37 @@ /* Flag bits of the coding system. The meaning of each bit is common to all types of coding systems. */ - int common_flags; + unsigned common_flags : 14; /* Mode bits of the coding system. See the comments of the macros CODING_MODE_XXX. */ - unsigned int mode; + unsigned mode : 5; + + /* The following two members specify how binary 8-bit code 128..255 + are represented in source and destination text respectively. True + means they are represented by 2-byte sequence, false means they are + represented by 1-byte as is (see the comment in character.h). */ + bool_bf src_multibyte : 1; + bool_bf dst_multibyte : 1; + + /* True if the source of conversion is not in the member + `charbuf', but at `src_object'. */ + bool_bf chars_at_source : 1; + + /* Nonzero if the result of conversion is in `destination' + buffer rather than in `dst_object'. */ + bool_bf raw_destination : 1; + + /* Set to true if charbuf contains an annotation. */ + bool_bf annotated : 1; + + /* Used internally in coding.c. See the comment of detect_ascii. */ + unsigned eol_seen : 3; + + /* Finish status of code conversion. */ + ENUM_BF (coding_result_code) result : 3; + + int max_charset_id; /* Detailed information specific to each type of coding system. */ union @@ -451,16 +477,8 @@ struct undecided_spec undecided; } spec; - int max_charset_id; unsigned char *safe_charsets; - /* The following two members specify how binary 8-bit code 128..255 - are represented in source and destination text respectively. True - means they are represented by 2-byte sequence, false means they are - represented by 1-byte as is (see the comment in character.h). */ - bool_bf src_multibyte : 1; - bool_bf dst_multibyte : 1; - /* How may heading bytes we can skip for decoding. This is set to -1 in setup_coding_system, and updated by detect_coding. So, when this is equal to the byte length of the text being @@ -472,21 +490,9 @@ sequence. Set by detect_coding_utf_8. */ ptrdiff_t detected_utf8_bytes, detected_utf8_chars; - /* Used internally in coding.c. See the comment of detect_ascii. */ - int eol_seen; - /* The following members are set by encoding/decoding routine. */ ptrdiff_t produced, produced_char, consumed, consumed_char; - /* Number of error source data found in a decoding routine. */ - ptrdiff_t errors; - - /* Store the positions of error source data. */ - ptrdiff_t *error_positions; - - /* Finish status of code conversion. */ - enum coding_result_code result; - ptrdiff_t src_pos, src_pos_byte, src_chars, src_bytes; Lisp_Object src_object; const unsigned char *source; @@ -510,17 +516,6 @@ int *charbuf; int charbuf_size, charbuf_used; - /* True if the source of conversion is not in the member - `charbuf', but at `src_object'. */ - bool_bf chars_at_source : 1; - - /* Nonzero if the result of conversion is in `destination' - buffer rather than in `dst_object'. */ - bool_bf raw_destination : 1; - - /* Set to true if charbuf contains an annotation. */ - bool_bf annotated : 1; - unsigned char carryover[64]; int carryover_bytes;