title: TRTTIContext multi-thread issue
body: <p>Everything I've read indicates that TRTTIContext is thread-safe.</p>
  
  <p>However, TRTTIContext.FindType seems to fail (returns nil) occasionally when multithreading.  Using a TCriticalSection around it fixes the issue.  Note that I'm using XE6, and the issue doesn't seem to exist in XE. <strong>Edit:</strong> Seems to exist in all Delphi editions that have the new RTTI units.</p>
  
  <p>I've worked up a test project you can use to see for yourself.  Create a new VCL project, drop a TMemo and a TButton, replace unit1 with below, and assign the Form1.OnCreate, Form1.OnDestroy and Button1.OnClick events. The key CS is the GRTTIBlock in TTestThread.Execute. Currently disabled, I get between 3 and 5 failures when I run with 200 threads. Enabling the GRTTIBlock CS removes the failures.</p>
  
  <pre><code>unit Unit1;
  
  interface
  
  uses
    Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants, System.Classes, Vcl.Graphics,
    Vcl.Controls, Vcl.Forms, Vcl.Dialogs, Vcl.StdCtrls, SyncObjs, Contnrs, RTTI;
  
  type
    TTestThread = class(TThread)
    private
      FFailed: Boolean;
      FRan: Boolean;
      FId: Integer;
    protected
      procedure Execute; override;
    public
      property Failed: Boolean read FFailed;
      property Ran: Boolean read FRan;
      property Id: Integer read FId write FId;
    end;
  
    TForm1 = class(TForm)
      Memo1: TMemo;
      Button1: TButton;
      procedure Button1Click(Sender: TObject);
      procedure FormCreate(Sender: TObject);
      procedure FormDestroy(Sender: TObject);
    private
      FThreadBlock: TCriticalSection;
      FMaxThreadCount: Integer;
      FThreadCount: Integer;
      FRanCount: Integer;
      FFailureCount: Integer;
      procedure Log(AStr: String);
      procedure ThreadFinished(Sender: TObject);
      procedure LaunchThreads;
    end;
  
  var
    Form1: TForm1;
  
  implementation
  
  var
    GRTTIBlock: TCriticalSection;
  
  {$R *.dfm}
  
  { TTestThread }
  
  procedure TTestThread.Execute;
  var
    ctx : TRTTIContext;
  begin
  //  GRTTIBlock.Acquire;
    try
      FFailed := not Assigned(ctx.FindType('Unit1.TForm1'));
      FRan := True;
    finally
  //    GRTTIBlock.Release;
    end;
  end;
  
  { TForm1 }
  
  procedure TForm1.Button1Click(Sender: TObject);
  begin
    Randomize;
    LaunchThreads;
    Log(Format('Threads: %d, Ran: %d, Failures: %d',
      [FMaxThreadCount, FRanCount, FFailureCount]));
  end;
  
  procedure TForm1.FormCreate(Sender: TObject);
  begin
    FThreadBlock := TCriticalSection.Create;
  end;
  
  procedure TForm1.FormDestroy(Sender: TObject);
  begin
    FThreadBlock.Free;
  end;
  
  procedure TForm1.Log(AStr: String);
  begin
    Memo1.Lines.Add(AStr);
  end;
  
  procedure TForm1.ThreadFinished(Sender: TObject);
  var
    tt : TTestThread;
  begin
    tt := TTestThread(Sender);
    Log(Format('Thread %d finished', [tt.Id]));
    FThreadBlock.Acquire;
    try
      Dec(FThreadCount);
      if tt.Failed then
        Inc(FFailureCount);
      if tt.Ran then
        Inc(FRanCount);
    finally
      FThreadBlock.Release;
    end;
  end;
  
  procedure TForm1.LaunchThreads;
  var
    c : Integer;
    ol : TObjectList;
    t : TTestThread;
  begin
    FRanCount := 0;
    FFailureCount := 0;
    FMaxThreadCount := 200;
    ol := TObjectList.Create(False);
    try
      // get all the thread objects created and ready
      for c := 1 to FMaxThreadCount do
      begin
        t := TTestThread.Create(True);
        t.FreeOnTerminate := True;
        t.OnTerminate := ThreadFinished;
        t.Id := c;
        ol.Add(t);
      end;
      FThreadCount := FMaxThreadCount;
      // start them all up
      for c := 0 to ol.Count - 1 do
      begin
        TTestThread(ol[c]).Start;
        Log(Format('Thread %d started', [TTestThread(ol[c]).Id]));
      end;
      repeat
        Application.ProcessMessages;
        FThreadBlock.Acquire;
        try
          if FThreadCount &lt;= 0 then
            Break;
        finally
          FThreadBlock.Release;
        end;
      until False;
    finally
      ol.Free;
    end;
  end;
  
  initialization
    GRTTIBlock := TCriticalSection.Create;
  
  finalization
    GRTTIBlock.Free;
  
  end.
  </code></pre>