From 7cc37bde901a8d9e09f57c7515b01964915d4c25 Mon Sep 17 00:00:00 2001
From: morpheusxx <morpheus_xx@team-mediaportal.com>
Date: Sat, 25 Feb 2012 09:06:31 +0100
Subject: [PATCH 1/2] Locking in FontAssetCore.cs

---
 .../ContentManagement/AssetCore/FontAssetCore.cs   |  166 +++++++++++---------
 1 files changed, 89 insertions(+), 77 deletions(-)

diff --git a/MediaPortal/Source/UI/SkinEngine/ContentManagement/AssetCore/FontAssetCore.cs b/MediaPortal/Source/UI/SkinEngine/ContentManagement/AssetCore/FontAssetCore.cs
index 17d4906..eb6e829 100644
--- a/MediaPortal/Source/UI/SkinEngine/ContentManagement/AssetCore/FontAssetCore.cs
+++ b/MediaPortal/Source/UI/SkinEngine/ContentManagement/AssetCore/FontAssetCore.cs
@@ -55,6 +55,8 @@ namespace MediaPortal.UI.SkinEngine.ContentManagement.AssetCore
     protected int _rowHeight = 0;
     protected int _currentY = 0;
 
+    protected object _syncObj = new object();
+
     #region Ctor
     /// <summary>Creates a new font set.</summary>
     /// <param name="family">The font family.</param>
@@ -197,10 +199,13 @@ namespace MediaPortal.UI.SkinEngine.ContentManagement.AssetCore
     {
       get
       {
-        if (!IsAllocated)
-          Allocate();
-        KeepAlive();
-        return _texture;
+        lock (_syncObj)
+        {
+          if (!IsAllocated)
+            Allocate();
+          KeepAlive();
+          return _texture;
+        }
       }
     }
 
@@ -216,8 +221,10 @@ namespace MediaPortal.UI.SkinEngine.ContentManagement.AssetCore
       if (IsAllocated)
         return;
 
-      _texture = new Texture(GraphicsDevice.Device, MAX_WIDTH, MAX_HEIGHT, 1, Usage.Dynamic, Format.L8, Pool.Default);
-
+      lock (_syncObj)
+      {
+        _texture = new Texture(GraphicsDevice.Device, MAX_WIDTH, MAX_HEIGHT, 1, Usage.Dynamic, Format.L8, Pool.Default);
+      }
       AllocationChanged(AllocationSize);
       // Add 'not defined' glyph
       AddGlyph(0);
@@ -235,71 +242,74 @@ namespace MediaPortal.UI.SkinEngine.ContentManagement.AssetCore
     /// <param name="glyphIndex">The index of the glyph to add.</param>
     private bool AddGlyph(uint glyphIndex)
     {
-      // FreeType measures font size in terms Of 1/64ths of a point.
-      // 1 point = 1/72th of an inch. Resolution is in dots (pixels) per inch.
-      float point_size = 64.0f * _charSet.RenderedSize * 72.0f / _resolution;
-      FT.FT_Set_Char_Size(_family.Face, (int) point_size, 0, _resolution, 0);
+      lock (_syncObj)
+      {
+        // FreeType measures font size in terms Of 1/64ths of a point.
+        // 1 point = 1/72th of an inch. Resolution is in dots (pixels) per inch.
+        float point_size = 64.0f*_charSet.RenderedSize*72.0f/_resolution;
+        FT.FT_Set_Char_Size(_family.Face, (int) point_size, 0, _resolution, 0);
 
-      // Font does not contain that glyph, the 'missing' glyph will be shown instead
-      if (glyphIndex == 0 && _charSet.GetCharacter(0) != null)
-        return false;
+        // Font does not contain that glyph, the 'missing' glyph will be shown instead
+        if (glyphIndex == 0 && _charSet.GetCharacter(0) != null)
+          return false;
 
-      // Load the glyph for the current character.
-      if (FT.FT_Load_Glyph(_family.Face, glyphIndex, FT.FT_LOAD_DEFAULT) != 0)
-        return false;
+        // Load the glyph for the current character.
+        if (FT.FT_Load_Glyph(_family.Face, glyphIndex, FT.FT_LOAD_DEFAULT) != 0)
+          return false;
 
-      FT_FaceRec face = (FT_FaceRec) Marshal.PtrToStructure(_family.Face, typeof(FT_FaceRec));
+        FT_FaceRec face = (FT_FaceRec) Marshal.PtrToStructure(_family.Face, typeof (FT_FaceRec));
 
-      IntPtr glyph;
-      // Load the glyph data into our local array.
-      if (FT.FT_Get_Glyph(face.glyph, out glyph) != 0)
-        return false;
+        IntPtr glyph;
+        // Load the glyph data into our local array.
+        if (FT.FT_Get_Glyph(face.glyph, out glyph) != 0)
+          return false;
 
-      // Convert the glyph to bitmap form.
-      if (FT.FT_Glyph_To_Bitmap(ref glyph, FT_Render_Mode.FT_RENDER_MODE_NORMAL, IntPtr.Zero, 1) != 0)
-        return false;
+        // Convert the glyph to bitmap form.
+        if (FT.FT_Glyph_To_Bitmap(ref glyph, FT_Render_Mode.FT_RENDER_MODE_NORMAL, IntPtr.Zero, 1) != 0)
+          return false;
 
-      // get the structure fron the intPtr
-      FT_BitmapGlyph Glyph = (FT_BitmapGlyph) Marshal.PtrToStructure(glyph, typeof(FT_BitmapGlyph));
+        // get the structure fron the intPtr
+        FT_BitmapGlyph Glyph = (FT_BitmapGlyph) Marshal.PtrToStructure(glyph, typeof (FT_BitmapGlyph));
 
-      // Width/height of char
-      int cwidth = Glyph.bitmap.width;
-      int cheight = Glyph.bitmap.rows;
+        // Width/height of char
+        int cwidth = Glyph.bitmap.width;
+        int cheight = Glyph.bitmap.rows;
 
-      // Width/height of char including padding
-      int pwidth = cwidth + 3 * PAD;
-      int pheight = cheight + 3 * PAD;
+        // Width/height of char including padding
+        int pwidth = cwidth + 3*PAD;
+        int pheight = cheight + 3*PAD;
 
-      // Check glyph index is in the character set range.
-      if (!_charSet.IsInRange(glyphIndex))
-        return false;
+        // Check glyph index is in the character set range.
+        if (!_charSet.IsInRange(glyphIndex))
+          return false;
 
-      // Check glyph fits in our texture
-      if (_currentX + pwidth > MAX_WIDTH)
-      {
-        _currentX = 0;
-        _currentY += _rowHeight;
-        _rowHeight = 0;
-      }
-      if (_currentY + pheight > MAX_HEIGHT)
-        return false;
+        // Check glyph fits in our texture
+        if (_currentX + pwidth > MAX_WIDTH)
+        {
+          _currentX = 0;
+          _currentY += _rowHeight;
+          _rowHeight = 0;
+        }
+        if (_currentY + pheight > MAX_HEIGHT)
+          return false;
 
-      // Create and store a BitmapCharacter for this glyph
-      _charSet.SetCharacter(glyphIndex, CreateCharacter(Glyph));
+        // Create and store a BitmapCharacter for this glyph
+        _charSet.SetCharacter(glyphIndex, CreateCharacter(Glyph));
 
-      // Copy the glyph bitmap to our local array
-      Byte[] BitmapBuffer = new Byte[cwidth * cheight];
-      if (Glyph.bitmap.buffer != IntPtr.Zero)
-        Marshal.Copy(Glyph.bitmap.buffer, BitmapBuffer, 0, cwidth * cheight);
+        // Copy the glyph bitmap to our local array
+        Byte[] BitmapBuffer = new Byte[cwidth*cheight];
+        if (Glyph.bitmap.buffer != IntPtr.Zero)
+          Marshal.Copy(Glyph.bitmap.buffer, BitmapBuffer, 0, cwidth*cheight);
 
-      // Write glyph bitmap to our texture
-      WriteGlyphToTexture(Glyph, pwidth, pheight, BitmapBuffer);
+        // Write glyph bitmap to our texture
+        WriteGlyphToTexture(Glyph, pwidth, pheight, BitmapBuffer);
 
-      _currentX += pwidth;
-      _rowHeight = Math.Max(_rowHeight, pheight);
+        _currentX += pwidth;
+        _rowHeight = Math.Max(_rowHeight, pheight);
 
-      // Free the glyph
-      FT.FT_Done_Glyph(glyph);
+        // Free the glyph
+        FT.FT_Done_Glyph(glyph);
+      }
       return true;
     }
 
@@ -328,32 +338,34 @@ namespace MediaPortal.UI.SkinEngine.ContentManagement.AssetCore
     {
       // Lock the the area we intend to update
       Rectangle charArea = new Rectangle(_currentX, _currentY, pwidth, pheight);
-      DataRectangle rect = _texture.LockRectangle(0, charArea, LockFlags.None);
+      lock (_syncObj)
+      {
+        DataRectangle rect = _texture.LockRectangle(0, charArea, LockFlags.None);
 
-      // Copy FreeType glyph bitmap into our font texture.
-      Byte[] FontPixels = new Byte[pwidth];
-      Byte[] PadPixels = new Byte[pwidth];
+        // Copy FreeType glyph bitmap into our font texture.
+        Byte[] FontPixels = new Byte[pwidth];
+        Byte[] PadPixels = new Byte[pwidth];
 
-      int Pitch = Math.Abs(Glyph.bitmap.pitch);
+        int Pitch = Math.Abs(Glyph.bitmap.pitch);
 
-      // Write the first padding row
-      rect.Data.Write(PadPixels, 0, pwidth);
-      rect.Data.Seek(MAX_WIDTH - pwidth, SeekOrigin.Current);
-      // Write the glyph
-      for (int y = 0; y < Glyph.bitmap.rows; y++)
-      {
-        for (int x = 0; x < Glyph.bitmap.width; x++)
-          FontPixels[x + PAD] = BitmapBuffer[y * Pitch + x];
-        rect.Data.Write(FontPixels, 0, pwidth);
+        // Write the first padding row
+        rect.Data.Write(PadPixels, 0, pwidth);
+        rect.Data.Seek(MAX_WIDTH - pwidth, SeekOrigin.Current);
+        // Write the glyph
+        for (int y = 0; y < Glyph.bitmap.rows; y++)
+        {
+          for (int x = 0; x < Glyph.bitmap.width; x++)
+            FontPixels[x + PAD] = BitmapBuffer[y*Pitch + x];
+          rect.Data.Write(FontPixels, 0, pwidth);
+          rect.Data.Seek(MAX_WIDTH - pwidth, SeekOrigin.Current);
+        }
+        // Write the last padding row
+        rect.Data.Write(PadPixels, 0, pwidth);
         rect.Data.Seek(MAX_WIDTH - pwidth, SeekOrigin.Current);
-      }
-      // Write the last padding row
-      rect.Data.Write(PadPixels, 0, pwidth);
-      rect.Data.Seek(MAX_WIDTH - pwidth, SeekOrigin.Current);
-
-      _texture.UnlockRectangle(0);
 
-      rect.Data.Dispose();
+        _texture.UnlockRectangle(0);
+        rect.Data.Dispose();
+      }
     }
 
     #endregion
-- 
1.7.3.1.msysgit.0

