[HarfBuzz] harfbuzz: Branch 'master' - 4 commits

Behdad Esfahbod behdad at kemper.freedesktop.org
Mon Jun 18 19:37:20 UTC 2018


 src/hb-blob.cc       |   44 +++++++++++++++++++++++++++++++++++++++++++-
 util/helper-cairo.cc |   14 ++++++++++----
 util/options.cc      |    8 +++++---
 util/options.hh      |    2 ++
 4 files changed, 60 insertions(+), 8 deletions(-)

New commits:
commit 941f2b85489b344698bf036922c589483034a7f2
Author: Ebrahim Byagowi <ebrahim at gnu.org>
Date:   Mon Jun 18 20:35:40 2018 +0430

    Support pipe and friends on hb_blob_create_from_file (#1061)
    
    With this hb-view/hb-shape support pipes and possibly socket and named pipe
    also, anything fails just on mmap.
    
    We can later do the same for Windows also.
    
    This however reveals two issues, the fact most of our bots don't have HAVE_MMAP and using
    this instead the other fread/fopen reader can make failure on CI. I should look at them separately
    this change however is very low risk I believe.

diff --git a/src/hb-blob.cc b/src/hb-blob.cc
index c138648c..77dbc715 100644
--- a/src/hb-blob.cc
+++ b/src/hb-blob.cc
@@ -499,6 +499,36 @@ hb_blob_t::try_make_writable (void)
 # define MAP_NORESERVE 0
 #endif
 
+static hb_blob_t *
+_fread_to_end (FILE *file)
+{
+  int allocated = BUFSIZ * 16;
+  char *blob = (char *) malloc (allocated);
+  if (blob == nullptr) return hb_blob_get_empty ();
+
+  int len = 0;
+  while (!feof (file))
+  {
+    if (allocated - len < BUFSIZ)
+    {
+      allocated *= 2;
+      char *new_blob = (char *) realloc (blob, allocated);
+      if (unlikely (!new_blob)) goto fail;
+      blob = new_blob;
+    }
+
+    len += fread (blob + len, 1, allocated - len, file);
+    if (ferror (file)) goto fail;
+  }
+
+  return hb_blob_create (blob, len, HB_MEMORY_MODE_WRITABLE, blob,
+			 (hb_destroy_func_t) free);
+
+fail:
+  free (blob);
+  return hb_blob_get_empty ();
+}
+
 struct hb_mapped_file_t
 {
   char *contents;
@@ -557,7 +587,19 @@ hb_blob_create_from_file (const char *file_name)
 				  writable ? PROT_READ|PROT_WRITE : PROT_READ,
 				  MAP_PRIVATE | MAP_NORESERVE, fd, 0);
 
-  if (unlikely (file->contents == MAP_FAILED)) goto fail;
+  if (unlikely (file->contents == MAP_FAILED))
+  {
+    free (file);
+    FILE *f = fdopen (fd, "rb");
+    if (unlikely (f == nullptr))
+    {
+      CLOSE (fd);
+      return hb_blob_get_empty ();
+    }
+    hb_blob_t *blob = _fread_to_end (f);
+    fclose (f);
+    return blob;
+  }
 
 #elif defined(_WIN32) || defined(__CYGWIN__)
   HANDLE fd = CreateFile (file_name,
commit d0c2889dfc43da92c76d6eab5482b1298744dc9c
Author: Ebrahim Byagowi <ebrahim at gnu.org>
Date:   Mon Jun 18 19:59:33 2018 +0430

    Revert file blob sanitization and index checking (#1062)
    
    As https://github.com/harfbuzz/harfbuzz/pull/1059#issuecomment-397912812 we
    like to still work with blobs that harfbuzz itself can't handle directly that are failing sanitization
    currently apparently.

diff --git a/util/options.cc b/util/options.cc
index 299466fe..682e40c4 100644
--- a/util/options.cc
+++ b/util/options.cc
@@ -670,16 +670,8 @@ font_options_t::get_font (void) const
     blob = hb_blob_create_from_file (font_file);
   }
 
-  if (hb_blob_get_length (blob) == 0)
-    fail (false, "No such file or directory, or is empty");
-
-  unsigned int face_count = hb_face_count (blob);
-
-  if (face_count == 0)
-    fail (false, "Not a font file"); // most likely
-
-  if (face_index > face_count)
-    fail (false, "The requested font index wasn't available in the file");
+  if (blob == hb_blob_get_empty ())
+    fail (false, "No such file or directory");
 
   /* Create the face */
   hb_face_t *face = hb_face_create (blob, face_index);
diff --git a/util/options.hh b/util/options.hh
index 5287395a..2160d5ec 100644
--- a/util/options.hh
+++ b/util/options.hh
@@ -485,7 +485,7 @@ struct font_options_t : option_group_t
   mutable double font_size_y;
   char *font_funcs;
 
-private:
+  private:
   mutable hb_font_t *font;
 };
 
commit c53697d3f2a3fae8b68ec4c5146c7000a07e0963
Author: Ebrahim Byagowi <ebrahim at gnu.org>
Date:   Sun Jun 17 17:04:55 2018 +0430

    Verbose fail when something is wrong with hb-shape/hb-view input font file (#1059)
    
    This checks if the blob isn't empty and uses `hb_face_count`
    to see if the font file passes the simple font file sanitization
    so can detect if the input is actually a font and checks also
    whether input font-index is out of range.

diff --git a/util/options.cc b/util/options.cc
index 4c65735f..299466fe 100644
--- a/util/options.cc
+++ b/util/options.cc
@@ -670,6 +670,17 @@ font_options_t::get_font (void) const
     blob = hb_blob_create_from_file (font_file);
   }
 
+  if (hb_blob_get_length (blob) == 0)
+    fail (false, "No such file or directory, or is empty");
+
+  unsigned int face_count = hb_face_count (blob);
+
+  if (face_count == 0)
+    fail (false, "Not a font file"); // most likely
+
+  if (face_index > face_count)
+    fail (false, "The requested font index wasn't available in the file");
+
   /* Create the face */
   hb_face_t *face = hb_face_create (blob, face_index);
   hb_blob_destroy (blob);
commit aa0c5df4199ef4e96df2b856c8f629e49fdd5120
Author: Ebrahim Byagowi <ebrahim at gnu.org>
Date:   Sun Jun 17 16:49:34 2018 +0430

    Fix reading fonts from stdin (#1060)
    
    We were passing the font path directly to freetype so rendering
    was broken when we are getting the font from stdin.
    
    This fixes it by using FT_New_Memory_Face instead.
    
    This fixes:
    * build/util/hb-view /dev/stdin text < font.ttf
    * build/util/hb-view - text < font.ttf
    * cat font.ttf | build/util/hb-view - text
    
    but doesn't work on
    * cat font.ttf | build/util/hb-view /dev/stdin text
    
    which I will try to fix separately.

diff --git a/util/helper-cairo.cc b/util/helper-cairo.cc
index b9f49851..3eaf90a7 100644
--- a/util/helper-cairo.cc
+++ b/util/helper-cairo.cc
@@ -89,10 +89,16 @@ helper_cairo_create_scaled_font (const font_options_t *font_opts)
       atexit (free_ft_library);
 #endif
     }
-    FT_New_Face (ft_library,
-		 font_opts->font_file,
-		 font_opts->face_index,
-		 &ft_face);
+
+    unsigned int blob_length;
+    const char *blob_data = hb_blob_get_data (font_opts->blob, &blob_length);
+
+    if (FT_New_Memory_Face (ft_library,
+			    (const FT_Byte *) blob_data,
+                            blob_length,
+			    font_opts->face_index,
+			    &ft_face))
+      fail (false, "FT_New_Memory_Face fail");
   }
   if (!ft_face)
   {
diff --git a/util/options.cc b/util/options.cc
index 24dc41f2..4c65735f 100644
--- a/util/options.cc
+++ b/util/options.cc
@@ -643,8 +643,6 @@ font_options_t::get_font (void) const
   if (font)
     return font;
 
-  hb_blob_t *blob = nullptr;
-
   /* Create the blob */
   if (!font_file)
     fail (true, "No font file set");
@@ -663,8 +661,9 @@ font_options_t::get_font (void) const
 	      strerror (errno));
       g_string_append_len (gs, buf, ret);
     }
+    unsigned int len = gs->len;
     char *font_data = g_string_free (gs, false);
-    blob = hb_blob_create (font_data, gs->len,
+    blob = hb_blob_create (font_data, len,
 			   HB_MEMORY_MODE_WRITABLE, font_data,
 			   (hb_destroy_func_t) g_free);
   } else {
diff --git a/util/options.hh b/util/options.hh
index 8dfc8420..5287395a 100644
--- a/util/options.hh
+++ b/util/options.hh
@@ -455,6 +455,7 @@ struct font_options_t : option_group_t
     font_size_x = font_size_y = default_font_size;
     font_funcs = nullptr;
 
+    blob = nullptr;
     font = nullptr;
 
     add_options (parser);
@@ -471,6 +472,7 @@ struct font_options_t : option_group_t
   hb_font_t *get_font (void) const;
 
   char *font_file;
+  mutable hb_blob_t *blob;
   int face_index;
   hb_variation_t *variations;
   unsigned int num_variations;
@@ -483,7 +485,7 @@ struct font_options_t : option_group_t
   mutable double font_size_y;
   char *font_funcs;
 
-  private:
+private:
   mutable hb_font_t *font;
 };
 


More information about the HarfBuzz mailing list