title: MSSQL VARBINARY to PDF using PHP
body: <p>Using a custom DevExpress application our users are uploading PDF files which get stored in a VARBINARY(MAX) column on a MSSQL 2008 database.</p>
  
  <p>I have LAMP box which successfully connects to that database using the FreeTDS driver.</p>
  
  <p>I'm able to retrieve other types of information (images stored as blobs, dates, strings etc) but when I try to serve PDFs they become corrupted somehow.</p>
  
  <p>If I do a comparison of the file before upload and after download using a hex editor I can see they are different (the string in the after shot matches what is on the db 128B08...)</p>
  
  <p><img src="https://imgur.com/Kc9GM.png" alt="Before and after">  </p>
  
  <p>The PHP I am using to serve the file:</p>
  
  <pre><code>&lt;?php
  header("Pragma: public");
  header("Expires: 0");
  header("Cache-Control: must-revalidate, post-check=0, pre-check=0");
  header("Cache-Control: public"); 
  header("Content-Description: File Transfer");
  header("Content-type:application/pdf");
  header("Content-Disposition:attachment;filename=" . $arr[0]['FileName']);
  header("Content-Transfer-Encoding: binary");
  echo $arr[0]['FileContent'];
  </code></pre>
  
  <p>The C# used to save the file to the db:</p>
  
  <pre><code>public void LoadFromStream(string fileName, Stream stream)
  {
    Guard.ArgumentNotNull(stream, "stream");
    Guard.ArgumentNotNullOrEmpty(fileName, "fileName");
    FileName = fileName;
    byte[] bytes = new byte[stream.Length];
    stream.Read(bytes, 0, bytes.Length);
    Content = bytes;
  }
  
  public void SaveToStream(Stream stream)
  {
    if (string.IsNullOrEmpty(FileName))
    {
      throw new InvalidOperationException();
    }
    stream.Write(Content, 0, Size);
    stream.Flush();
  }
  
  public byte[] Content
  {
    get { return GetDelayedPropertyValue&lt;byte[]&gt;("Content"); }
    set
    {
      int oldSize = size;
      if (value != null)
      {
        size = value.Length;
      }
      else
      {
        size = 0;
      }
      SetDelayedPropertyValue&lt;byte[]&gt;("Content", value);
      OnChanged("Size", oldSize, size);
    }
  }
  </code></pre>
  
  <p>I've read just about every article I can find by searching "php varbinary, php output stream, php varbinary stream, varbinary encoding". Help or suggestions much appreciated!</p>