commit 123c775aa7a92fc323f88c2e4b6e8185d4c369b4 (HEAD, refs/remotes/origin/master) Author: Stephen Gildea Date: Tue Nov 19 21:26:09 2019 -0800 Expand coverage of unit tests for time-stamp * test/lisp/time-stamp-tests.el: Remove redundant word "test" from the names of all the tests. (time-stamp-custom-time-zone, time-stamp-custom-pattern, time-stamp-custom-inserts-lines, time-stamp-custom-count, time-stamp-helper-safe-locals): New tests diff --git a/test/lisp/time-stamp-tests.el b/test/lisp/time-stamp-tests.el index ae8eaf467d..fb2780af2d 100644 --- a/test/lisp/time-stamp-tests.el +++ b/test/lisp/time-stamp-tests.el @@ -20,13 +20,15 @@ ;;; Code: (require 'ert) +(require 'generator) (eval-when-compile (require 'cl-lib)) (require 'time-stamp) (defmacro with-time-stamp-test-env (&rest body) "Evaluate BODY with some standard time-stamp test variables bound." + (declare (indent defun)) `(let ((user-login-name "test-logname") - (user-full-name "Time Stamp Tester") + (user-full-name "100%d Tester") ;verify "%" passed unchanged (buffer-file-name "/emacs/test/time-stamped-file") (mail-host-address "test-mail-host-name") (ref-time1 '(17337 16613)) ;Monday, Jan 2, 2006, 3:04:05 PM @@ -43,7 +45,16 @@ ;; suppress the byte compiler's "unused" warning. (list ref-time1 ref-time2 ref-time3) ,@body))) -(put 'with-time-stamp-test-env 'lisp-indent-hook 'defun) + +(defmacro with-time-stamp-test-time (reference-time &rest body) + "Force any contained time-stamp call to use time REFERENCE-TIME." + (declare (indent defun)) + `(cl-letf* + ((orig-time-stamp-string-fn (symbol-function 'time-stamp-string)) + ((symbol-function 'time-stamp-string) + (lambda (ts-format) + (apply orig-time-stamp-string-fn ts-format ,reference-time nil)))) + ,@body)) (defmacro time-stamp-should-warn (form) "Similar to `should' but verifies that a format warning is generated." @@ -57,9 +68,152 @@ ;;; Tests: +;;; Tests of customization variables + +(ert-deftest time-stamp-custom-time-zone () + "Test that setting time-stamp-time-zone affects the format." + (with-time-stamp-test-env + (let ((time-stamp-time-zone "PST8")) + (should (equal (time-stamp-string "%H %Z" ref-time1) "07 PST"))) + (let ((time-stamp-time-zone "UTC0")) + (should (equal (time-stamp-string "%H %Z" ref-time1) "15 UTC"))) + (let ((time-stamp-time-zone "GMT0")) + (should (equal (time-stamp-string "%H %Z" ref-time1) "15 GMT"))))) + +(iter-defun time-stamp-test-pattern-sequential () + "Iterate through each possibility for a part of time-stamp-pattern." + (let ((pattern-value-parts + '(("4/" "10/" "-4/" "0/" "") ;0: line limit + ("stamp<" "") ;1: start + ("%-d" "%_H" "%^a" "%#Z" "%:A" "%02H" "%%" "") ;2: format part 1 + (" " "x" ":" "\n" "") ;3: format part 2 + ("%-d" "%_H" "%^a" "%#Z" "%:A" "%02H" "%%") ;4: format part 3 + (">end" "")))) ;5: end + (dotimes (cur (length pattern-value-parts)) + (dotimes (cur-index (length (nth cur pattern-value-parts))) + (cl-flet ((extract-part + (lambda (desired-part) + (let ((part-list (nth desired-part pattern-value-parts))) + (if (= desired-part cur) + (nth cur-index part-list) + (nth 0 part-list)))))) + ;; Don't repeat the default pattern. + (if (or (= cur 0) (> cur-index 0)) + ;; The whole format must start with %, so not all + ;; generated combinations are valid + (if (or (not (equal (extract-part 2) "")) + (equal (extract-part 3) "")) + (iter-yield (list (extract-part 0) + (extract-part 1) + (apply #'concat + (mapcar #'extract-part '(2 3 4))) + (extract-part 5)))))))))) + +(iter-defun time-stamp-test-pattern-multiply () + "Iterate through every combination of parts of time-stamp-pattern." + (let ((line-limit-values '("" "4/")) + (start-values '("" "stamp<")) + (format-values '("%%" "%m")) + (end-values '("" ">end"))) + ;; yield all combinations of the above + (dolist (line-limit line-limit-values) + (dolist (start start-values) + (dolist (format format-values) + (dolist (end end-values) + (iter-yield (list line-limit start format end)))))))) + +(iter-defun time-stamp-test-pattern-all () + (iter-yield-from (time-stamp-test-pattern-sequential)) + (iter-yield-from (time-stamp-test-pattern-multiply))) + +(ert-deftest time-stamp-custom-pattern () + "Test that time-stamp-pattern is parsed correctly." + (iter-do (pattern-parts (time-stamp-test-pattern-all)) + (cl-destructuring-bind (line-limit1 start1 whole-format end1) pattern-parts + (cl-letf + (((symbol-function 'time-stamp-once) + (lambda (start search-limit ts-start ts-end + ts-format _format-lines _end-lines) + ;; Verify that time-stamp parsed time-stamp-pattern and + ;; called us with the correct pieces. + (let ((limit-number (string-to-number line-limit1))) + (if (equal line-limit1 "") + (setq limit-number time-stamp-line-limit)) + (goto-char (point-min)) + (if (> limit-number 0) + (should (= search-limit (line-beginning-position + (1+ limit-number)))) + (should (= search-limit (point-max)))) + (goto-char (point-max)) + (if (< limit-number 0) + (should (= start (line-beginning-position + (1+ limit-number)))) + (should (= start (point-min))))) + (if (equal start1 "") + (should (equal ts-start time-stamp-start)) + (should (equal ts-start start1))) + (if (equal whole-format "%%") + (should (equal ts-format time-stamp-format)) + (should (equal ts-format whole-format))) + (if (equal end1 "") + (should (equal ts-end time-stamp-end)) + (should (equal ts-end end1))) + ;; return nil to stop time-stamp from calling us again + nil))) + (let ((time-stamp-pattern (concat + line-limit1 start1 whole-format end1))) + (with-temp-buffer + ;; prep the buffer with more than the + ;; largest line-limit1 number of lines + (insert "\n\n\n\n\n\n\n\n\n\n\n\n") + ;; Call time-stamp, which will call time-stamp-once, + ;; triggering the tests above. + (time-stamp))))))) + +(ert-deftest time-stamp-custom-inserts-lines () + "Test that time-stamp inserts lines or not, as directed." + (with-time-stamp-test-env + (let ((time-stamp-start "Updated on:") + ;; the newline in the format will insert a line if we let it + (time-stamp-format "\n %Y-%m-%d") + (time-stamp-end "$") + (time-stamp-inserts-lines nil) ;changed later in the test + (buffer-expected-1line "Updated on:\n 2006-01-02\n") + (buffer-expected-2line "Updated on:\n 2006-01-02\n 2006-01-02\n")) + (with-time-stamp-test-time ref-time1 + (with-temp-buffer + (insert "Updated on:\n\n") + (time-stamp) + (should (equal (buffer-string) buffer-expected-1line)) + ;; second call should not add a line + (time-stamp) + (should (equal (buffer-string) buffer-expected-1line)) + + (setq time-stamp-inserts-lines t) + ;; with time-stamp-inserts-lines set, should add a line + (time-stamp) + (should (equal (buffer-string) buffer-expected-2line))))))) + +(ert-deftest time-stamp-custom-count () + "Test that time-stamp updates no more than time-stamp-count templates." + (with-time-stamp-test-env + (let ((time-stamp-start "TS: <") + (time-stamp-format "%Y-%m-%d") + (time-stamp-count 1) ;changed later in the test + (buffer-expected-once "TS: <2006-01-02>\nTS: <>") + (buffer-expected-twice "TS: <2006-01-02>\nTS: <2006-01-02>")) + (with-time-stamp-test-time ref-time1 + (with-temp-buffer + (insert "TS: <>\nTS: <>") + (time-stamp) + (should (equal (buffer-string) buffer-expected-once)) + (setq time-stamp-count 2) + (time-stamp) + (should (equal (buffer-string) buffer-expected-twice))))))) + ;;; Tests of time-stamp-string formatting -(ert-deftest time-stamp-test-format-day-of-week () +(ert-deftest time-stamp-format-day-of-week () "Test time-stamp formats for named day of week." (with-time-stamp-test-env ;; implemented and documented since 1997 @@ -78,7 +232,7 @@ (should (equal (time-stamp-string "%^a" ref-time1) "MON")) (should (equal (time-stamp-string "%A" ref-time1) "Monday")))) -(ert-deftest time-stamp-test-format-month-name () +(ert-deftest time-stamp-format-month-name () "Test time-stamp formats for month name." (with-time-stamp-test-env ;; implemented and documented since 1997 @@ -97,7 +251,7 @@ (should (equal (time-stamp-string "%^b" ref-time1) "JAN")) (should (equal (time-stamp-string "%B" ref-time1) "January")))) -(ert-deftest time-stamp-test-format-day-of-month () +(ert-deftest time-stamp-format-day-of-month () "Test time-stamp formats for day of month." (with-time-stamp-test-env ;; implemented and documented since 1995 @@ -120,7 +274,7 @@ (should (equal (time-stamp-string "%d" ref-time1) "02")) (should (equal (time-stamp-string "%d" ref-time2) "18")))) -(ert-deftest time-stamp-test-format-hours-24 () +(ert-deftest time-stamp-format-hours-24 () "Test time-stamp formats for hour on a 24-hour clock." (with-time-stamp-test-env ;; implemented and documented since 1995 @@ -150,7 +304,7 @@ (should (equal (time-stamp-string "%H" ref-time2) "12")) (should (equal (time-stamp-string "%H" ref-time3) "06")))) -(ert-deftest time-stamp-test-format-hours-12 () +(ert-deftest time-stamp-format-hours-12 () "Test time-stamp formats for hour on a 12-hour clock." (with-time-stamp-test-env ;; implemented and documented since 1995 @@ -180,7 +334,7 @@ (should (equal (time-stamp-string "%I" ref-time2) "12")) (should (equal (time-stamp-string "%I" ref-time3) "06")))) -(ert-deftest time-stamp-test-format-month-number () +(ert-deftest time-stamp-format-month-number () "Test time-stamp formats for month number." (with-time-stamp-test-env ;; implemented and documented since 1995 @@ -203,7 +357,7 @@ (should (equal (time-stamp-string "%m" ref-time1) "01")) (should (equal (time-stamp-string "%m" ref-time2) "11")))) -(ert-deftest time-stamp-test-format-minute () +(ert-deftest time-stamp-format-minute () "Test time-stamp formats for minute." (with-time-stamp-test-env ;; implemented and documented since 1995 @@ -226,7 +380,7 @@ (should (equal (time-stamp-string "%M" ref-time1) "04")) (should (equal (time-stamp-string "%M" ref-time2) "14")))) -(ert-deftest time-stamp-test-format-second () +(ert-deftest time-stamp-format-second () "Test time-stamp formats for second." (with-time-stamp-test-env ;; implemented and documented since 1995 @@ -249,7 +403,7 @@ (should (equal (time-stamp-string "%S" ref-time1) "05")) (should (equal (time-stamp-string "%S" ref-time2) "15")))) -(ert-deftest time-stamp-test-format-year-2digit () +(ert-deftest time-stamp-format-year-2digit () "Test time-stamp formats for %y." (with-time-stamp-test-env ;; implemented and documented since 1995 @@ -274,13 +428,13 @@ (time-stamp-should-warn (equal (time-stamp-string "%4y" ref-time1) "2006")))) -(ert-deftest time-stamp-test-format-year-4digit () +(ert-deftest time-stamp-format-year-4digit () "Test time-stamp format %Y." (with-time-stamp-test-env ;; implemented since 1997, documented since 2019 (should (equal (time-stamp-string "%Y" ref-time1) "2006")))) -(ert-deftest time-stamp-test-format-am-pm () +(ert-deftest time-stamp-format-am-pm () "Test time-stamp formats for AM and PM strings." (with-time-stamp-test-env ;; implemented and documented since 1997 @@ -292,14 +446,14 @@ (should (equal (time-stamp-string "%p" ref-time1) "PM")) (should (equal (time-stamp-string "%p" ref-time3) "AM")))) -(ert-deftest time-stamp-test-format-day-number-in-week () +(ert-deftest time-stamp-format-day-number-in-week () "Test time-stamp formats for day number in week." (with-time-stamp-test-env (should (equal (time-stamp-string "%w" ref-time1) "1")) (should (equal (time-stamp-string "%w" ref-time2) "5")) (should (equal (time-stamp-string "%w" ref-time3) "0")))) -(ert-deftest time-stamp-test-format-time-zone-name () +(ert-deftest time-stamp-format-time-zone-name () "Test time-stamp format %Z." (with-time-stamp-test-env (let ((UTC-abbr (format-time-string "%Z" ref-time1 t)) @@ -309,7 +463,7 @@ ;; implemented since 1997, documented since 2019 (should (equal (time-stamp-string "%#Z" ref-time1) utc-abbr))))) -(ert-deftest time-stamp-test-format-time-zone-offset () +(ert-deftest time-stamp-format-time-zone-offset () "Test time-stamp format %z." (with-time-stamp-test-env (let ((utc-abbr (format-time-string "%#Z" ref-time1 t))) @@ -331,7 +485,7 @@ (should (equal (time-stamp-string "%::z" ref-time1) "+00:00:00")) (should (equal (time-stamp-string "%:::z" ref-time1) "+00")))) -(ert-deftest time-stamp-test-format-non-date-conversions () +(ert-deftest time-stamp-format-non-date-conversions () "Test time-stamp formats for non-date items." (with-time-stamp-test-env ;; implemented and documented since 1995 @@ -344,10 +498,10 @@ ;; documented 1995-2019 (should (equal (time-stamp-string "%s" ref-time1) "test-system-name.example.org")) - (should (equal (time-stamp-string "%U" ref-time1) "Time Stamp Tester")) + (should (equal (time-stamp-string "%U" ref-time1) "100%d Tester")) (should (equal (time-stamp-string "%u" ref-time1) "test-logname")) ;; implemented since 2001, documented since 2019 - (should (equal (time-stamp-string "%L" ref-time1) "Time Stamp Tester")) + (should (equal (time-stamp-string "%L" ref-time1) "100%d Tester")) (should (equal (time-stamp-string "%l" ref-time1) "test-logname")) ;; implemented since 2007, documented since 2019 (should (equal @@ -355,7 +509,7 @@ (should (equal (time-stamp-string "%q" ref-time1) "test-system-name")))) -(ert-deftest time-stamp-test-format-ignored-modifiers () +(ert-deftest time-stamp-format-ignored-modifiers () "Test additional args allowed (but ignored) to allow for future expansion." (with-time-stamp-test-env ;; allowed modifiers @@ -363,12 +517,12 @@ ;; not all punctuation is allowed (should-not (equal (time-stamp-string "%&P" ref-time3) "AM")))) -(ert-deftest time-stamp-test-format-non-conversions () +(ert-deftest time-stamp-format-non-conversions () "Test that without a %, the text is copied literally." (with-time-stamp-test-env (should (equal (time-stamp-string "No percent" ref-time1) "No percent")))) -(ert-deftest time-stamp-test-format-string-width () +(ert-deftest time-stamp-format-string-width () "Test time-stamp string width modifiers." (with-time-stamp-test-env ;; strings truncate on the right or are blank-padded on the left @@ -384,7 +538,7 @@ ;;; Tests of helper functions -(ert-deftest time-stamp-test-helper-zone-type-p () +(ert-deftest time-stamp-helper-zone-type-p () "Test time-stamp-zone-type-p." (should (time-stamp-zone-type-p t)) (should (time-stamp-zone-type-p nil)) @@ -399,4 +553,23 @@ (should-not (time-stamp-zone-type-p '(0 0))) (should-not (time-stamp-zone-type-p '("A" "A")))) +(ert-deftest time-stamp-helper-safe-locals () + "Test that our variables are known to be safe local variables." + (should (safe-local-variable-p 'time-stamp-format "a string")) + (should-not (safe-local-variable-p 'time-stamp-format '(a list))) + (should (safe-local-variable-p 'time-stamp-time-zone "a string")) + (should-not (safe-local-variable-p 'time-stamp-time-zone 0.5)) + (should (safe-local-variable-p 'time-stamp-line-limit 8)) + (should-not (safe-local-variable-p 'time-stamp-line-limit "a string")) + (should (safe-local-variable-p 'time-stamp-start "a string")) + (should-not (safe-local-variable-p 'time-stamp-start 17)) + (should (safe-local-variable-p 'time-stamp-end "a string")) + (should-not (safe-local-variable-p 'time-stamp-end 17)) + (should (safe-local-variable-p 'time-stamp-inserts-lines t)) + (should-not (safe-local-variable-p 'time-stamp-inserts-lines 17)) + (should (safe-local-variable-p 'time-stamp-count 2)) + (should-not (safe-local-variable-p 'time-stamp-count t)) + (should (safe-local-variable-p 'time-stamp-pattern "a string")) + (should-not (safe-local-variable-p 'time-stamp-pattern 17))) + ;;; time-stamp-tests.el ends here commit 0fce8e9391fd107f9267188a36b85aea778b8440 Author: Paul Eggert Date: Tue Nov 19 18:23:01 2019 -0800 Make .pdmp file more reproducible Problem reported by Ulrich Müller and diagnosed by Andreas Schwab . * src/sysdep.c (maybe_disable_address_randomization): Disable ASLR if any kind of dumping, instead of merely if unexec dumping. Omit first arg for simplicity; all uses changed. diff --git a/src/emacs.c b/src/emacs.c index 21a05d337e..8a6e34deda 100644 --- a/src/emacs.c +++ b/src/emacs.c @@ -1054,8 +1054,7 @@ main (int argc, char **argv) load_pdump (argc, argv); #endif - argc = maybe_disable_address_randomization ( - will_dump_with_unexec_p (), argc, argv); + argc = maybe_disable_address_randomization (argc, argv); #if defined GNU_LINUX && defined HAVE_UNEXEC if (!initialized) diff --git a/src/lisp.h b/src/lisp.h index 1d25add928..e0ae2c4262 100644 --- a/src/lisp.h +++ b/src/lisp.h @@ -4576,10 +4576,10 @@ struct tty_display_info; /* Defined in sysdep.c. */ #ifdef HAVE_PERSONALITY_ADDR_NO_RANDOMIZE -extern int maybe_disable_address_randomization (bool, int, char **); +extern int maybe_disable_address_randomization (int, char **); #else INLINE int -maybe_disable_address_randomization (bool dumping, int argc, char **argv) +maybe_disable_address_randomization (int argc, char **argv) { return argc; } diff --git a/src/sysdep.c b/src/sysdep.c index aa18ee22fd..e34ab2eb58 100644 --- a/src/sysdep.c +++ b/src/sysdep.c @@ -158,14 +158,17 @@ static int exec_personality; /* Try to disable randomization if the current process needs it and does not appear to have it already. */ int -maybe_disable_address_randomization (bool dumping, int argc, char **argv) +maybe_disable_address_randomization (int argc, char **argv) { /* Undocumented Emacs option used only by this function. */ static char const aslr_disabled_option[] = "--__aslr-disabled"; if (argc < 2 || strcmp (argv[1], aslr_disabled_option) != 0) { - bool disable_aslr = dumping; + /* If dumping via unexec, ASLR must be disabled, as otherwise + data may be scattered and undumpable as a simple executable. + If pdumping, disabling ASLR makes the .pdmp file reproducible. */ + bool disable_aslr = will_dump_p (); # ifdef __PPC64__ disable_aslr = true; # endif commit aa79f4e8c635537c50a50db211542c0f41443ae2 Author: João Távora Date: Tue Nov 19 23:53:10 2019 +0000 * lisp/icomplete.el (icomplete-fido-kill): Unbreak yes-or-no-p usage Discussed in the context of bug#19064, bug#17272. diff --git a/lisp/icomplete.el b/lisp/icomplete.el index 8410ca5c3e..16167ea21e 100644 --- a/lisp/icomplete.el +++ b/lisp/icomplete.el @@ -253,7 +253,11 @@ require user confirmation." (path (expand-file-name thing dir))) (when (yes-or-no-p (concat "Delete file " path "? ")) (delete-file path) t))))))) - (when (funcall action) + (when (let (;; Allow `yes-or-no-p' to work and don't let it + ;; `icomplete-exhibit' anything. + (enable-recursive-minibuffers t) + (icomplete-mode nil)) + (funcall action)) (completion--cache-all-sorted-completions (icomplete--field-beg) (icomplete--field-end) commit a76a1d0c0b5c63bbed4eeeb7aa87269621956559 Author: Eli Zaretskii Date: Tue Nov 19 17:59:02 2019 +0200 Ensure Rmail summary is updated after editing a message * lisp/mail/rmailedit.el (rmail-cease-edit): If this mbox file has a summary, update the summary after editing. (Bug#38193) diff --git a/lisp/mail/rmailedit.el b/lisp/mail/rmailedit.el index 01d552469f..43422ff3a4 100644 --- a/lisp/mail/rmailedit.el +++ b/lisp/mail/rmailedit.el @@ -149,6 +149,7 @@ This function runs the hooks `text-mode-hook' and `rmail-edit-mode-hook'. (declare-function rmail-summary-enable "rmailsum" ()) +(declare-function rmail-summary-update-line "rmailsum" (n)) (defun rmail-cease-edit () "Finish editing message; switch back to Rmail proper." @@ -340,10 +341,11 @@ This function runs the hooks `text-mode-hook' and `rmail-edit-mode-hook'. ;; Delete previous body. This must be after all insertions at the end, ;; so the marker for the beginning of the next message isn't messed up. (delete-region end (point-max))) - (rmail-set-attribute rmail-edited-attr-index t)) -;;;??? BROKEN perhaps. -;;; (if (boundp 'rmail-summary-vector) -;;; (aset rmail-summary-vector (1- rmail-current-message) nil)) + (rmail-set-attribute rmail-edited-attr-index t) + (if (rmail-summary-exists) + (let ((msgnum rmail-current-message)) + (with-current-buffer rmail-summary-buffer + (rmail-summary-update-line msgnum))))) (rmail-show-message) (rmail-toggle-header (if pruned 1 0)) ;; Restore mime display state. commit 6f30642973975a317a9c94ceba737a4bafc89919 Author: Eli Zaretskii Date: Tue Nov 19 17:48:55 2019 +0200 Fix updating members of zip archives * lisp/arc-mode.el (archive-zip-case-fiddle): Change the default to nil except on MS-DOS. Update the doc string to make clear that a non-nil value also affects updating the archive. (Bug#38260) diff --git a/lisp/arc-mode.el b/lisp/arc-mode.el index 7f435f17a1..0cdc8a147d 100644 --- a/lisp/arc-mode.el +++ b/lisp/arc-mode.el @@ -291,11 +291,16 @@ Archive and member name will be added." (string :format "%v"))) :group 'archive-zip) -(defcustom archive-zip-case-fiddle t - "If non-nil then zip file members may be down-cased. +(declare-function msdos-long-file-names "msdos.c") +(defcustom archive-zip-case-fiddle (and (eq system-type 'ms-dos) + (not (msdos-long-file-names))) + "If non-nil, then all-caps names of zip file members will be down-cased. This case fiddling will only happen for members created by a system -that uses caseless file names." +that uses caseless file names. +In addition, this flag forces members added/updated in the zip archive +to be truncated to DOS 8+3 file-name restrictions." :type 'boolean + :version "27.1" :group 'archive-zip) ;; ------------------------------ ;; Zoo archive configuration commit bb1e7433cb6c9d96ff048a82be1ea6bdc06dba96 Author: Robert Pluim Date: Tue Nov 19 15:28:36 2019 +0100 ; Fix NEWS entry for network-lookup-address-info diff --git a/etc/NEWS b/etc/NEWS index 485d2b1fdf..4887b8e681 100644 --- a/etc/NEWS +++ b/etc/NEWS @@ -231,6 +231,7 @@ To get the old, less-secure behavior, you can set the *** When run by root, emacsclient no longer connects to non-root sockets. (Instead you can use Tramp methods to run root commands in a non-root Emacs.) ++++ ** New function 'network-lookup-address-info'. This does IPv4 and/or IPv6 address lookups on hostnames. commit b6db2ed1ea5d29dbd31871972d702739e88d3818 Author: Robert Pluim Date: Mon Nov 18 10:18:25 2019 +0100 Remember the full GTK font description Remember the full font description instead of just the family so that size/style/weight settings are preserved. * gtkutil.c (xg_get_font) [HAVE_GTK3]: Use the pango font description to set/get the current font (Bug#28901). diff --git a/src/gtkutil.c b/src/gtkutil.c index 25ef5dd248..cf5c31aa20 100644 --- a/src/gtkutil.c +++ b/src/gtkutil.c @@ -2282,7 +2282,16 @@ xg_get_font (struct frame *f, const char *default_name) default_name = x_last_font_name; if (default_name) - gtk_font_chooser_set_font (GTK_FONT_CHOOSER (w), default_name); + { +#ifdef HAVE_GTK3 + PangoFontDescription *desc + = pango_font_description_from_string (default_name); + gtk_font_chooser_set_font_desc (GTK_FONT_CHOOSER (w), desc); + pango_font_description_free (desc); +#else + gtk_font_chooser_set_font (GTK_FONT_CHOOSER (w), default_name); +#endif + } gtk_widget_set_name (w, "emacs-fontdialog"); done = xg_dialog_run (f, w); @@ -2306,8 +2315,10 @@ xg_get_font (struct frame *f, const char *default_name) QCweight, XG_WEIGHT_TO_SYMBOL (weight), QCslant, XG_STYLE_TO_SYMBOL (style)); + char *font_desc_str = pango_font_description_to_string (desc); + dupstring (&x_last_font_name, font_desc_str); + g_free (font_desc_str); pango_font_description_free (desc); - dupstring (&x_last_font_name, family); } #else /* Use old font selector, which just returns the font name. */ commit cf0a76a43831105d74b54f0e50f77eb60460fbea Author: Robert Pluim Date: Mon Nov 18 10:57:55 2019 +0100 Don't error when comparing IPv4 and IPv6 addresses * lisp/net/nsm.el (nsm-network-same-subnet): Compare lengths of local-ip and ip; different lengths can never match. (nsm-should-check): Chop port off end of address. diff --git a/lisp/net/nsm.el b/lisp/net/nsm.el index c47ef55a6f..205b797488 100644 --- a/lisp/net/nsm.el +++ b/lisp/net/nsm.el @@ -204,17 +204,21 @@ LOCAL-IP, MASK, and IP are specified as vectors of integers, and are expected to have the same length. Works for both IPv4 and IPv6 addresses." (let ((matches t) - (length (length local-ip))) - (unless (memq length '(4 5 8 9)) + (ip-length (length ip)) + (local-length (length local-ip))) + (unless (and (memq ip-length '(4 5 8 9)) + (memq local-length '(4 5 8 9))) (error "Unexpected length of IP address %S" local-ip)) - (dotimes (i length) - (setq matches (and matches - (= - (logand (aref local-ip i) - (aref mask i)) - (logand (aref ip i) - (aref mask i)))))) - matches)) + (if (/= ip-length local-length) + nil + (dotimes (i local-length) + (setq matches (and matches + (= + (logand (aref local-ip i) + (aref mask i)) + (logand (aref ip i) + (aref mask i)))))) + matches))) (defun nsm-should-check (host) "Determine whether NSM should check for TLS problems for HOST. @@ -238,7 +242,7 @@ otherwise." (when (nsm-network-same-subnet (substring (car info) 0 -1) (substring (car (cddr info)) 0 -1) - address) + (substring address 0 -1)) (setq off-net nil)))) network-interface-list)) addresses)) commit 067a42f8dd2ce19de3203605ee8c1c08aa192580 Author: Lars Ingebrigtsen Date: Tue Nov 19 11:47:19 2019 +0100 Allow eww to display exotic images like webp * lisp/image.el (image-type): Allow passing in the image type. (create-image): Make conversion work with data in addition to files. * lisp/image/image-converter.el (image-convert-p): Allow taking working on data in addition to files (bug#38036). (image-convert): Ditto. (image-converter--convert): Extend signature to say whether we're getting a file or data. (image-converter--convert-magick): Convert data. (image-converter--convert): Ditto. diff --git a/lisp/image.el b/lisp/image.el index ad2ee6c607..5f24475ce5 100644 --- a/lisp/image.el +++ b/lisp/image.el @@ -369,8 +369,10 @@ be determined." ;; If nothing seems to be supported, return first type that matched. (or first (setq first type)))))))) -(declare-function image-convert-p "image-converter.el" (file)) -(declare-function image-convert "image-converter.el" (image)) +(declare-function image-convert-p "image-converter.el" + (source &optional image-format)) +(declare-function image-convert "image-converter.el" + (image &optional image-format)) ;;;###autoload (defun image-type (source &optional type data-p) @@ -380,12 +382,20 @@ Optional TYPE is a symbol describing the image type. If TYPE is omitted or nil, try to determine the image type from its first few bytes of image data. If that doesn't work, and SOURCE is a file name, use its file extension as image type. -Optional DATA-P non-nil means SOURCE is a string containing image data." + +Optional DATA-P non-nil means SOURCE is a string containing image +data. If DATA-P is a symbol with a name on the format +`image/jpeg', that may be used as a hint to determine the image +type if we can't otherwise guess it." (when (and (not data-p) (not (stringp source))) (error "Invalid image file name `%s'" source)) (unless type (setq type (if data-p - (image-type-from-data source) + (or (image-type-from-data source) + (and image-use-external-converter + (progn + (require 'image-converter) + (image-convert-p source data-p)))) (or (image-type-from-file-header source) (image-type-from-file-name source) (and image-use-external-converter @@ -457,14 +467,18 @@ Images should not be larger than specified by `max-image-size'. Image file names that are not absolute are searched for in the \"images\" sub-directory of `data-directory' and `x-bitmap-file-path' (in that order)." - ;; It is x_find_image_file in image.c that sets the search path. - (setq type (image-type file-or-data type data-p)) - ;; If we have external image conversion switched on (for exotic, - ;; non-native image formats), then we convert the file. - (when (eq type 'image-convert) - (setq file-or-data (image-convert file-or-data) - type 'png - data-p t)) + (let ((data-format + ;; Pass the image format, if any, if this is data. + (and data-p (or (plist-get props :format) t)))) + ;; It is x_find_image_file in image.c that sets the search path. + (setq type (ignore-error unknown-image-type + (image-type file-or-data type data-format))) + ;; If we have external image conversion switched on (for exotic, + ;; non-native image formats), then we convert the file. + (when (eq type 'image-convert) + (setq file-or-data (image-convert file-or-data data-format) + type 'png + data-p t))) (when (image-type-available-p type) (append (list 'image :type type (if data-p :data :file) file-or-data) (and (not (plist-get props :scale)) diff --git a/lisp/image/image-converter.el b/lisp/image/image-converter.el index 2e09976c01..dedccadcf4 100644 --- a/lisp/image/image-converter.el +++ b/lisp/image/image-converter.el @@ -48,43 +48,58 @@ installed on the system." (imagemagick :command "convert" :probe ("-list" "format"))) "List of supported image converters to try.") -(defun image-convert-p (file) - "Return `image-convert' if FILE is an image file that can be converted." +(defun image-convert-p (source &optional data-p) + "Return `image-convert' if SOURCE is an image that can be converted. +SOURCE can either be a file name or a string containing image +data. In the latter case, DATA-P should be non-nil. If DATA-P +is a string, it should be a MIME format string like +\"image/gif\"." ;; Find an installed image converter. (unless image-converter (image-converter--find-converter)) (and image-converter - (string-match image-converter-regexp file) + (or (and (not data-p) + (string-match image-converter-regexp source)) + (and data-p + (symbolp data-p) + (string-match "/" (symbol-name data-p)) + (string-match + image-converter-regexp + (concat "foo." (image-converter--mime-type data-p))))) 'image-convert)) -(defun image-convert (image) +(defun image-convert (image &optional image-format) "Convert IMAGE file to the PNG format. IMAGE can either be a file name, which will make the return value -a string with the image data. It can also be an image object as -returned by `create-image'. If so, it has to be an image object -where created with DATA-P nil (i.e., it has to refer to a file)." +a string with the image data. + +If IMAGE-FORMAT is non-nil, IMAGE is a string containing the +image data, and IMAGE-FORMAT is a symbol with a MIME format name +like \"image/webp\". + +IMAGE can also be an image object as returned by `create-image'." ;; Find an installed image converter. (unless image-converter (image-converter--find-converter)) (unless image-converter (error "No external image converters available")) - (when (and (listp image) - (not (plist-get (cdr image) :file))) - (error "Only images that refer to files can be converted")) (with-temp-buffer (set-buffer-multibyte nil) (when-let ((err (image-converter--convert image-converter (if (listp image) (plist-get (cdr image) :file) - image)))) + image) + (if (listp image) + (plist-get (cdr image) :data-p) + image-format)))) (error "%s" err)) (if (listp image) ;; Return an image object that's the same as we were passed, - ;; but ignore the :type and :file values. + ;; but ignore the :type value. (apply #'create-image (buffer-string) 'png t (cl-loop for (key val) on (cdr image) by #'cddr - unless (memq key '(:type :file)) + unless (eq key :type) append (list key val))) (buffer-string)))) @@ -159,33 +174,65 @@ where created with DATA-P nil (i.e., it has to refer to a file)." image-converter-regexp (concat "\\." (regexp-opt formats) "\\'")) (throw 'done image-converter))))) -(cl-defmethod image-converter--convert ((type (eql graphicsmagick)) file) +(cl-defmethod image-converter--convert ((type (eql graphicsmagick)) source + image-format) "Convert using GraphicsMagick." - (image-converter--convert-magick type file)) + (image-converter--convert-magick type source image-format)) -(cl-defmethod image-converter--convert ((type (eql imagemagick)) file) +(cl-defmethod image-converter--convert ((type (eql imagemagick)) source + image-format) "Convert using ImageMagick." - (image-converter--convert-magick type file)) + (image-converter--convert-magick type source image-format)) + +(defun image-converter--mime-type (image-format) + (and (symbolp image-format) + (cadr (split-string (symbol-name image-format) "/")))) -(defun image-converter--convert-magick (type file) +(defun image-converter--convert-magick (type source image-format) (let ((command (image-converter--value type :command))) - (unless (zerop (apply #'call-process (car command) - nil t nil - (append (cdr command) - (list (expand-file-name file) "png:-")))) + (unless (zerop (if image-format + ;; We have the image data in SOURCE. + (progn + (insert source) + (apply #'call-process-region (point-min) (point-max) + (car command) t t nil + (append + (cdr command) + (list (format "%s:-" + (image-converter--mime-type + image-format)) + "png:-")))) + ;; SOURCE is a file name. + (apply #'call-process (car command) + nil t nil + (append (cdr command) + (list (expand-file-name source) "png:-"))))) ;; If the command failed, hopefully the buffer contains the ;; error message. (buffer-string)))) -(cl-defmethod image-converter--convert ((type (eql ffmpeg)) file) +(cl-defmethod image-converter--convert ((type (eql ffmpeg)) source + image-format) "Convert using ffmpeg." (let ((command (image-converter--value type :command))) - (unless (zerop (apply #'call-process - (car command) - nil '(t nil) nil - (append (cdr command) - (list "-i" (expand-file-name file) - "-c:v" "png" "-f" "image2pipe" "-")))) + (unless (zerop (if image-format + (progn + (insert source) + (apply #'call-process-region + (point-min) (point-max) (car command) + t '(t nil) nil + (append + (cdr command) + (list "-i" "-" + "-c:v" "png" + "-f" "image2pipe" "-")))) + (apply #'call-process + (car command) + nil '(t nil) nil + (append (cdr command) + (list "-i" (expand-file-name source) + "-c:v" "png" "-f" "image2pipe" + "-"))))) "ffmpeg error when converting"))) (provide 'image-converter) commit 49192e9510fe3c491b8c759a639bbe8bccf35856 Author: Juanma Barranquero Date: Tue Nov 19 11:18:48 2019 +0100 Strip "(fn...)" from output of `describe-mode' (bug#38222) * lisp/help.el (help--doc-without-fn): New function. (describe-mode): Use it. diff --git a/lisp/help.el b/lisp/help.el index 3b3d1f977e..22f35df1de 100644 --- a/lisp/help.el +++ b/lisp/help.el @@ -878,6 +878,10 @@ current buffer." (princ ", which is ") (describe-function-1 defn))))))) +(defun help--doc-without-fn (mode) + ;; Remove the (fn...) thingy at the end of the docstring + (replace-regexp-in-string "\n\n(fn[^)]*?)\\'" "" (documentation mode))) + (defun describe-mode (&optional buffer) "Display documentation of current major mode and minor modes. A brief summary of the minor modes comes first, followed by the @@ -951,7 +955,7 @@ documentation for the major and minor modes of that buffer." "no indicator" (format "indicator%s" indicator)))) - (princ (documentation mode-function))) + (princ (help--doc-without-fn mode-function))) (insert-button pretty-minor-mode 'action (car help-button-cache) 'follow-link t @@ -981,7 +985,7 @@ documentation for the major and minor modes of that buffer." nil t) (help-xref-button 1 'help-function-def mode file-name))))) (princ ":\n") - (princ (documentation major-mode))))) + (princ (help--doc-without-fn major-mode))))) ;; For the sake of IELM and maybe others nil)