diff options
| author | Pip Cet | 2025-05-28 14:11:07 +0000 |
|---|---|---|
| committer | Pip Cet | 2025-05-28 19:22:57 +0000 |
| commit | d14fc6b75f128ed538c123ec79bd3d955ca9bf70 (patch) | |
| tree | 5434a330405fb3bd2b7e21e83995e850111ee82e | |
| parent | 295f73d23d337593959ec7d73ecbcfa61a732f0f (diff) | |
| download | emacs-d14fc6b75f128ed538c123ec79bd3d955ca9bf70.tar.gz emacs-d14fc6b75f128ed538c123ec79bd3d955ca9bf70.zip | |
Fix unsafe SDATA usage in print.c (bug#78590)
* src/print.c (print_string_1): Renamed from 'print_string', with an
extra argument to disable nonascii escaping.
(print_string): New function.
(print_object): Use 'print_string_1', not 'strout'.
| -rw-r--r-- | src/print.c | 14 | ||||
| -rw-r--r-- | test/src/print-tests.el | 18 |
2 files changed, 28 insertions, 4 deletions
diff --git a/src/print.c b/src/print.c index b17ec337f70..b6ee89478c7 100644 --- a/src/print.c +++ b/src/print.c | |||
| @@ -469,18 +469,18 @@ strout (const char *ptr, ptrdiff_t size, ptrdiff_t size_byte, | |||
| 469 | because printing one char can relocate. */ | 469 | because printing one char can relocate. */ |
| 470 | 470 | ||
| 471 | static void | 471 | static void |
| 472 | print_string (Lisp_Object string, Lisp_Object printcharfun) | 472 | print_string_1 (Lisp_Object string, Lisp_Object printcharfun, bool escape_nonascii) |
| 473 | { | 473 | { |
| 474 | if (EQ (printcharfun, Qt) || NILP (printcharfun)) | 474 | if (EQ (printcharfun, Qt) || NILP (printcharfun)) |
| 475 | { | 475 | { |
| 476 | ptrdiff_t chars; | 476 | ptrdiff_t chars; |
| 477 | 477 | ||
| 478 | if (print_escape_nonascii) | 478 | if (escape_nonascii) |
| 479 | string = string_escape_byte8 (string); | 479 | string = string_escape_byte8 (string); |
| 480 | 480 | ||
| 481 | if (STRING_MULTIBYTE (string)) | 481 | if (STRING_MULTIBYTE (string)) |
| 482 | chars = SCHARS (string); | 482 | chars = SCHARS (string); |
| 483 | else if (! print_escape_nonascii | 483 | else if (! escape_nonascii |
| 484 | && (EQ (printcharfun, Qt) | 484 | && (EQ (printcharfun, Qt) |
| 485 | ? ! NILP (BVAR (&buffer_defaults, enable_multibyte_characters)) | 485 | ? ! NILP (BVAR (&buffer_defaults, enable_multibyte_characters)) |
| 486 | : ! NILP (BVAR (current_buffer, enable_multibyte_characters)))) | 486 | : ! NILP (BVAR (current_buffer, enable_multibyte_characters)))) |
| @@ -543,6 +543,12 @@ print_string (Lisp_Object string, Lisp_Object printcharfun) | |||
| 543 | } | 543 | } |
| 544 | } | 544 | } |
| 545 | } | 545 | } |
| 546 | |||
| 547 | static void | ||
| 548 | print_string (Lisp_Object string, Lisp_Object printcharfun) | ||
| 549 | { | ||
| 550 | print_string_1 (string, printcharfun, print_escape_nonascii); | ||
| 551 | } | ||
| 546 | 552 | ||
| 547 | DEFUN ("write-char", Fwrite_char, Swrite_char, 1, 2, 0, | 553 | DEFUN ("write-char", Fwrite_char, Swrite_char, 1, 2, 0, |
| 548 | doc: /* Output character CHARACTER to stream PRINTCHARFUN. | 554 | doc: /* Output character CHARACTER to stream PRINTCHARFUN. |
| @@ -2282,7 +2288,7 @@ print_object (Lisp_Object obj, Lisp_Object printcharfun, bool escapeflag) | |||
| 2282 | } | 2288 | } |
| 2283 | else if (STRINGP (num)) | 2289 | else if (STRINGP (num)) |
| 2284 | { | 2290 | { |
| 2285 | strout (SSDATA (num), SCHARS (num), SBYTES (num), printcharfun); | 2291 | print_string_1 (num, printcharfun, false); |
| 2286 | goto next_obj; | 2292 | goto next_obj; |
| 2287 | } | 2293 | } |
| 2288 | } | 2294 | } |
diff --git a/test/src/print-tests.el b/test/src/print-tests.el index af57311135b..036248fd091 100644 --- a/test/src/print-tests.el +++ b/test/src/print-tests.el | |||
| @@ -540,5 +540,23 @@ otherwise, use a different charset." | |||
| 540 | (should (eq callback-buffer buffer)) | 540 | (should (eq callback-buffer buffer)) |
| 541 | (should (equal str "tata")))) | 541 | (should (equal str "tata")))) |
| 542 | 542 | ||
| 543 | (ert-deftest test-print-number-realloc () | ||
| 544 | ;; Test for bug#78590. Note that this may in rare cases crash unfixed | ||
| 545 | ;; Emacs versions. | ||
| 546 | (let ((print-circle t) | ||
| 547 | (print-number-table (make-hash-table)) | ||
| 548 | (print-continuous-numbering t) | ||
| 549 | (str "yy") | ||
| 550 | (outstr "")) | ||
| 551 | (garbage-collect) | ||
| 552 | (ignore (make-string 100 ?a)) | ||
| 553 | (puthash str (make-string 3 ?x) print-number-table) | ||
| 554 | (prin1 str | ||
| 555 | (lambda (c) | ||
| 556 | (setq outstr (concat outstr (string c))) | ||
| 557 | (garbage-collect) | ||
| 558 | (ignore (make-string 100 ?b)))) | ||
| 559 | (should (equal outstr "xxx")))) | ||
| 560 | |||
| 543 | (provide 'print-tests) | 561 | (provide 'print-tests) |
| 544 | ;;; print-tests.el ends here | 562 | ;;; print-tests.el ends here |