diff options
Diffstat (limited to 'src/xfont.c')
-rw-r--r-- | src/xfont.c | 158 |
1 files changed, 93 insertions, 65 deletions
diff --git a/src/xfont.c b/src/xfont.c index b61c374fdc3..81808e7a62e 100644 --- a/src/xfont.c +++ b/src/xfont.c @@ -31,6 +31,7 @@ along with GNU Emacs. If not, see <https://www.gnu.org/licenses/>. */ #include "character.h" #include "charset.h" #include "font.h" +#include "pdumper.h" /* X core font driver. */ @@ -45,18 +46,20 @@ struct xfont_info /* Prototypes of support functions. */ -static XCharStruct *xfont_get_pcm (XFontStruct *, XChar2b *); +static XCharStruct *xfont_get_pcm (XFontStruct *, unsigned char2b); /* Get metrics of character CHAR2B in XFONT. Value is null if CHAR2B is not contained in the font. */ static XCharStruct * -xfont_get_pcm (XFontStruct *xfont, XChar2b *char2b) +xfont_get_pcm (XFontStruct *xfont, unsigned char2b) { /* The result metric information. */ XCharStruct *pcm = NULL; + const unsigned char byte1 = char2b >> 8; + const unsigned char byte2 = char2b & 0xFF; - eassert (xfont && char2b); + eassert (xfont); if (xfont->per_char != NULL) { @@ -65,13 +68,13 @@ xfont_get_pcm (XFontStruct *xfont, XChar2b *char2b) /* min_char_or_byte2 specifies the linear character index corresponding to the first element of the per_char array, max_char_or_byte2 is the index of the last character. A - character with non-zero CHAR2B->byte1 is not in the font. + character with non-zero byte1 is not in the font. A character with byte2 less than min_char_or_byte2 or greater max_char_or_byte2 is not in the font. */ - if (char2b->byte1 == 0 - && char2b->byte2 >= xfont->min_char_or_byte2 - && char2b->byte2 <= xfont->max_char_or_byte2) - pcm = xfont->per_char + char2b->byte2 - xfont->min_char_or_byte2; + if (byte1 == 0 + && byte2 >= xfont->min_char_or_byte2 + && byte2 <= xfont->max_char_or_byte2) + pcm = xfont->per_char + byte2 - xfont->min_char_or_byte2; } else { @@ -88,14 +91,14 @@ xfont_get_pcm (XFontStruct *xfont, XChar2b *char2b) D = max_char_or_byte2 - min_char_or_byte2 + 1 / = integer division \ = integer modulus */ - if (char2b->byte1 >= xfont->min_byte1 - && char2b->byte1 <= xfont->max_byte1 - && char2b->byte2 >= xfont->min_char_or_byte2 - && char2b->byte2 <= xfont->max_char_or_byte2) + if (byte1 >= xfont->min_byte1 + && byte1 <= xfont->max_byte1 + && byte2 >= xfont->min_char_or_byte2 + && byte2 <= xfont->max_char_or_byte2) pcm = (xfont->per_char + ((xfont->max_char_or_byte2 - xfont->min_char_or_byte2 + 1) - * (char2b->byte1 - xfont->min_byte1)) - + (char2b->byte2 - xfont->min_char_or_byte2)); + * (byte1 - xfont->min_byte1)) + + (byte2 - xfont->min_char_or_byte2)); } } else @@ -103,8 +106,8 @@ xfont_get_pcm (XFontStruct *xfont, XChar2b *char2b) /* If the per_char pointer is null, all glyphs between the first and last character indexes inclusive have the same information, as given by both min_bounds and max_bounds. */ - if (char2b->byte2 >= xfont->min_char_or_byte2 - && char2b->byte2 <= xfont->max_char_or_byte2) + if (byte2 >= xfont->min_char_or_byte2 + && byte2 <= xfont->max_char_or_byte2) pcm = &xfont->max_bounds; } @@ -131,7 +134,7 @@ compare_font_names (const void *name1, const void *name2) /* Decode XLFD as iso-8859-1 into OUTPUT, and return the byte length of the decoding result. LEN is the byte length of XLFD, or -1 if - XLFD is NULL terminated. The caller must assure that OUTPUT is at + XLFD is NUL terminated. The caller must assure that OUTPUT is at least twice (plus 1) as large as XLFD. */ static ptrdiff_t @@ -190,9 +193,8 @@ xfont_chars_supported (Lisp_Object chars, XFontStruct *xfont, { for (; CONSP (chars); chars = XCDR (chars)) { - int c = XINT (XCAR (chars)); + int c = XFIXNUM (XCAR (chars)); unsigned code = ENCODE_CHAR (charset, c); - XChar2b char2b; if (code == CHARSET_INVALID_CODE (charset)) break; @@ -200,9 +202,7 @@ xfont_chars_supported (Lisp_Object chars, XFontStruct *xfont, continue; if (code >= 0x10000) break; - char2b.byte1 = code >> 8; - char2b.byte2 = code & 0xFF; - if (! xfont_get_pcm (xfont, &char2b)) + if (! xfont_get_pcm (xfont, code)) break; } return (NILP (chars)); @@ -213,9 +213,8 @@ xfont_chars_supported (Lisp_Object chars, XFontStruct *xfont, for (i = ASIZE (chars) - 1; i >= 0; i--) { - int c = XINT (AREF (chars, i)); + int c = XFIXNUM (AREF (chars, i)); unsigned code = ENCODE_CHAR (charset, c); - XChar2b char2b; if (code == CHARSET_INVALID_CODE (charset)) continue; @@ -223,9 +222,7 @@ xfont_chars_supported (Lisp_Object chars, XFontStruct *xfont, break; if (code >= 0x10000) continue; - char2b.byte1 = code >> 8; - char2b.byte2 = code & 0xFF; - if (xfont_get_pcm (xfont, &char2b)) + if (xfont_get_pcm (xfont, code)) break; } return (i >= 0); @@ -376,18 +373,18 @@ xfont_list_pattern (Display *display, const char *pattern, continue; ASET (entity, FONT_TYPE_INDEX, Qx); /* Avoid auto-scaled fonts. */ - if (INTEGERP (AREF (entity, FONT_DPI_INDEX)) - && INTEGERP (AREF (entity, FONT_AVGWIDTH_INDEX)) - && XINT (AREF (entity, FONT_DPI_INDEX)) != 0 - && XINT (AREF (entity, FONT_AVGWIDTH_INDEX)) == 0) + if (FIXNUMP (AREF (entity, FONT_DPI_INDEX)) + && FIXNUMP (AREF (entity, FONT_AVGWIDTH_INDEX)) + && XFIXNUM (AREF (entity, FONT_DPI_INDEX)) != 0 + && XFIXNUM (AREF (entity, FONT_AVGWIDTH_INDEX)) == 0) continue; /* Avoid not-allowed scalable fonts. */ if (NILP (Vscalable_fonts_allowed)) { int size = 0; - if (INTEGERP (AREF (entity, FONT_SIZE_INDEX))) - size = XINT (AREF (entity, FONT_SIZE_INDEX)); + if (FIXNUMP (AREF (entity, FONT_SIZE_INDEX))) + size = XFIXNUM (AREF (entity, FONT_SIZE_INDEX)); else if (FLOATP (AREF (entity, FONT_SIZE_INDEX))) size = XFLOAT_DATA (AREF (entity, FONT_SIZE_INDEX)); if (size == 0 && i_pass == 0) @@ -672,8 +669,8 @@ xfont_open (struct frame *f, Lisp_Object entity, int pixel_size) return Qnil; } - if (XINT (AREF (entity, FONT_SIZE_INDEX)) != 0) - pixel_size = XINT (AREF (entity, FONT_SIZE_INDEX)); + if (XFIXNUM (AREF (entity, FONT_SIZE_INDEX)) != 0) + pixel_size = XFIXNUM (AREF (entity, FONT_SIZE_INDEX)); else if (pixel_size == 0) { if (FRAME_FONT (f)) @@ -800,19 +797,17 @@ xfont_open (struct frame *f, Lisp_Object entity, int pixel_size) else { XCharStruct *pcm; - XChar2b char2b; Lisp_Object val; - char2b.byte1 = 0x00, char2b.byte2 = 0x20; - pcm = xfont_get_pcm (xfont, &char2b); + pcm = xfont_get_pcm (xfont, 0x20); if (pcm) font->space_width = pcm->width; else font->space_width = 0; val = Ffont_get (font_object, QCavgwidth); - if (INTEGERP (val)) - font->average_width = XINT (val) / 10; + if (FIXNUMP (val)) + font->average_width = XFIXNUM (val) / 10; if (font->average_width < 0) font->average_width = - font->average_width; else @@ -822,8 +817,8 @@ xfont_open (struct frame *f, Lisp_Object entity, int pixel_size) { int width = font->space_width, n = pcm != NULL; - for (char2b.byte2 = 33; char2b.byte2 <= 126; char2b.byte2++) - if ((pcm = xfont_get_pcm (xfont, &char2b)) != NULL) + for (unsigned char2b = 33; char2b <= 126; ++char2b) + if ((pcm = xfont_get_pcm (xfont, char2b)) != NULL) width += pcm->width, n++; if (n > 0) font->average_width = width / n; @@ -933,7 +928,6 @@ xfont_encode_char (struct font *font, int c) XFontStruct *xfont = ((struct xfont_info *) font)->xfont; struct charset *charset; unsigned code; - XChar2b char2b; charset = CHARSET_FROM_ID (font->encoding_charset); code = ENCODE_CHAR (charset, c); @@ -945,13 +939,11 @@ xfont_encode_char (struct font *font, int c) return (ENCODE_CHAR (charset, c) != CHARSET_INVALID_CODE (charset) ? code : FONT_INVALID_CODE); } - char2b.byte1 = code >> 8; - char2b.byte2 = code & 0xFF; - return (xfont_get_pcm (xfont, &char2b) ? code : FONT_INVALID_CODE); + return (xfont_get_pcm (xfont, code) ? code : FONT_INVALID_CODE); } static void -xfont_text_extents (struct font *font, unsigned int *code, +xfont_text_extents (struct font *font, const unsigned int *code, int nglyphs, struct font_metrics *metrics) { XFontStruct *xfont = ((struct xfont_info *) font)->xfont; @@ -960,13 +952,11 @@ xfont_text_extents (struct font *font, unsigned int *code, for (i = 0, first = true; i < nglyphs; i++) { - XChar2b char2b; static XCharStruct *pcm; if (code[i] >= 0x10000) continue; - char2b.byte1 = code[i] >> 8, char2b.byte2 = code[i] & 0xFF; - pcm = xfont_get_pcm (xfont, &char2b); + pcm = xfont_get_pcm (xfont, code[i]); if (! pcm) continue; if (first) @@ -999,6 +989,7 @@ xfont_draw (struct glyph_string *s, int from, int to, int x, int y, bool with_background) { XFontStruct *xfont = ((struct xfont_info *) s->font)->xfont; + Display *display = FRAME_X_DISPLAY (s->f); int len = to - from; GC gc = s->gc; int i; @@ -1006,7 +997,7 @@ xfont_draw (struct glyph_string *s, int from, int to, int x, int y, if (s->gc != s->face->gc) { block_input (); - XSetFont (s->display, gc, xfont->fid); + XSetFont (display, gc, xfont->fid); unblock_input (); } @@ -1015,26 +1006,26 @@ xfont_draw (struct glyph_string *s, int from, int to, int x, int y, USE_SAFE_ALLOCA; char *str = SAFE_ALLOCA (len); for (i = 0; i < len ; i++) - str[i] = XCHAR2B_BYTE2 (s->char2b + from + i); + str[i] = s->char2b[from + i] & 0xFF; block_input (); if (with_background) { if (s->padding_p) for (i = 0; i < len; i++) - XDrawImageString (FRAME_X_DISPLAY (s->f), FRAME_X_DRAWABLE (s->f), + XDrawImageString (display, FRAME_X_DRAWABLE (s->f), gc, x + i, y, str + i, 1); else - XDrawImageString (FRAME_X_DISPLAY (s->f), FRAME_X_DRAWABLE (s->f), + XDrawImageString (display, FRAME_X_DRAWABLE (s->f), gc, x, y, str, len); } else { if (s->padding_p) for (i = 0; i < len; i++) - XDrawString (FRAME_X_DISPLAY (s->f), FRAME_X_DRAWABLE (s->f), + XDrawString (display, FRAME_X_DRAWABLE (s->f), gc, x + i, y, str + i, 1); else - XDrawString (FRAME_X_DISPLAY (s->f), FRAME_X_DRAWABLE (s->f), + XDrawString (display, FRAME_X_DRAWABLE (s->f), gc, x, y, str, len); } unblock_input (); @@ -1047,21 +1038,51 @@ xfont_draw (struct glyph_string *s, int from, int to, int x, int y, { if (s->padding_p) for (i = 0; i < len; i++) - XDrawImageString16 (FRAME_X_DISPLAY (s->f), FRAME_X_DRAWABLE (s->f), - gc, x + i, y, s->char2b + from + i, 1); + { + const unsigned code = s->char2b[from + i]; + const XChar2b char2b = { .byte1 = code >> 8, + .byte2 = code & 0xFF }; + XDrawImageString16 (display, FRAME_X_DRAWABLE (s->f), + gc, x + i, y, &char2b, 1); + } else - XDrawImageString16 (FRAME_X_DISPLAY (s->f), FRAME_X_DRAWABLE (s->f), - gc, x, y, s->char2b + from, len); + { + USE_SAFE_ALLOCA; + const unsigned *code = s->char2b + from; + XChar2b *char2b; + SAFE_NALLOCA (char2b, 1, len); + for (int i = 0; i < len; ++i) + char2b[i] = (XChar2b) { .byte1 = code[i] >> 8, + .byte2 = code[i] & 0xFF }; + XDrawImageString16 (display, FRAME_X_DRAWABLE (s->f), + gc, x, y, char2b, len); + SAFE_FREE (); + } } else { if (s->padding_p) for (i = 0; i < len; i++) - XDrawString16 (FRAME_X_DISPLAY (s->f), FRAME_X_DRAWABLE (s->f), - gc, x + i, y, s->char2b + from + i, 1); + { + const unsigned code = s->char2b[from + i]; + const XChar2b char2b = { .byte1 = code >> 8, + .byte2 = code & 0xFF }; + XDrawString16 (display, FRAME_X_DRAWABLE (s->f), + gc, x + i, y, &char2b, 1); + } else - XDrawString16 (FRAME_X_DISPLAY (s->f), FRAME_X_DRAWABLE (s->f), - gc, x, y, s->char2b + from, len); + { + USE_SAFE_ALLOCA; + const unsigned *code = s->char2b + from; + XChar2b *char2b; + SAFE_NALLOCA (char2b, 1, len); + for (int i = 0; i < len; ++i) + char2b[i] = (XChar2b) { .byte1 = code[i] >> 8, + .byte2 = code[i] & 0xFF }; + XDrawString16 (display, FRAME_X_DRAWABLE (s->f), + gc, x, y, char2b, len); + SAFE_FREE (); + } } unblock_input (); @@ -1077,6 +1098,7 @@ xfont_check (struct frame *f, struct font *font) } +static void syms_of_xfont_for_pdumper (void); struct font_driver const xfont_driver = { @@ -1101,6 +1123,12 @@ syms_of_xfont (void) staticpro (&xfont_scripts_cache); xfont_scripts_cache = CALLN (Fmake_hash_table, QCtest, Qequal); staticpro (&xfont_scratch_props); - xfont_scratch_props = Fmake_vector (make_number (8), Qnil); + xfont_scratch_props = make_nil_vector (8); + pdumper_do_now_and_after_load (syms_of_xfont_for_pdumper); +} + +static void +syms_of_xfont_for_pdumper (void) +{ register_font_driver (&xfont_driver, NULL); } |