Author Topic: Reading and writing Dwg properties  (Read 10555 times)

0 Members and 1 Guest are viewing this topic.

exmachina

  • Guest
Re: Reading and writing Dwg properties
« Reply #15 on: September 08, 2013, 01:20:14 AM »
Now I know how to compress, but the SummaryInfo section contains Julian dates and I do not know how to convert Julian dates  to Datetime and vice versa. Can anyone help me?

If the size of the section does not change (for example if we only modify the dates) I believe that it is not necessary to rebuild the maps, but we need to rebuil the section header with the new checksums

FYI:
According to the ODA specification when a section exceeds the maximum size (page size) the data are broken into pages, but in this section it is not true, it seems that it does is add padding bytes (zeros) at the end.


R2004 (and R2010, R2013) compression:
Code - C#: [Select]
  1. using System;
  2. using System.IO;
  3.  
  4. namespace Dwg2000Reader
  5. {
  6.     internal static class R2004Compression
  7.     {
  8.  
  9.         public static unsafe void Compress(byte* source, int index, int length, Stream dest)
  10.         {
  11.             // TODO
  12.             byte*[] historyBuffer = new byte*[0x8000];
  13.            
  14.             byte* startPtr = source + index;
  15.             byte* endPtr = startPtr + length;
  16.             byte* tempPtr = startPtr;
  17.             byte* lookAheadBuffer = startPtr + 4;
  18.             int length_ = 0;
  19.             int offset = 0;
  20.             int matchLength = 0;
  21.             int matchOffset = 0;
  22.             int literalLength;
  23.  
  24.             while (lookAheadBuffer < (endPtr - 0x13))
  25.             {
  26.                 if (!FindMatch(historyBuffer, lookAheadBuffer, startPtr, endPtr, ref matchLength, ref matchOffset))
  27.                 {
  28.                     lookAheadBuffer++;
  29.                 }
  30.                 else
  31.                 {
  32.                     literalLength = (int)(lookAheadBuffer - tempPtr);
  33.                     if (length_ != 0)
  34.                         WriteCompressed(offset, length_, literalLength, dest);
  35.                     WriteLiteral(tempPtr, literalLength, dest);
  36.                     lookAheadBuffer += matchLength;
  37.                     tempPtr = lookAheadBuffer;
  38.                     length_ = matchLength;
  39.                     offset = matchOffset;
  40.                 }
  41.             }
  42.  
  43.             literalLength = (int)(endPtr - tempPtr);
  44.  
  45.             if (length_ != 0)
  46.                 WriteCompressed(offset, length_, literalLength, dest);
  47.  
  48.             WriteLiteral(tempPtr, literalLength, dest);
  49.             dest.WriteByte(0x11);
  50.             dest.WriteByte(0);
  51.             dest.WriteByte(0);
  52.  
  53.         }
  54.  
  55.         public static unsafe void Compress(byte[] source, int index, int length, Stream dest)
  56.         {
  57.             fixed (byte* dataPtr = source)
  58.                 Compress(dataPtr, 0, source.Length, dest);
  59.         }
  60.  
  61.         public static void Compress(byte[] source, Stream dest)
  62.         {
  63.             Compress(source, 0, source.Length, dest);
  64.         }
  65.  
  66.         private static unsafe bool FindMatch(byte*[] historyBuffer, byte* lookAheadBuffer, byte* startPtr, byte* endPtr, ref int matchLength, ref int matchOffset)
  67.         {
  68.             matchLength = 0;
  69.  
  70.             byte num = lookAheadBuffer[0];
  71.             byte num2 = lookAheadBuffer[1];
  72.             byte num3 = lookAheadBuffer[2];
  73.             byte num4 = lookAheadBuffer[3];
  74.  
  75.             int index = (((((num4 << 6) ^ num3) << 5) ^ num2) << 5) ^ num;
  76.             index += index >> 5;
  77.             index &= 0x7fff;
  78.  
  79.             byte* wordPtr = historyBuffer[index];
  80.             matchOffset = (int)(lookAheadBuffer - wordPtr);
  81.             if ((wordPtr >= startPtr) && (matchOffset <= 0xbfff))
  82.             {
  83.                 if ((matchOffset > 0x400) && (num4 != wordPtr[3]))
  84.                 {
  85.                     index &= 0x7ff;
  86.                     index ^= 0x401f;
  87.                     wordPtr = historyBuffer[index];
  88.                     matchOffset = (int)(lookAheadBuffer - wordPtr);
  89.                     if (((wordPtr < startPtr) || (matchOffset > 0xbfff)) || ((matchOffset > 0x400) && (num4 != wordPtr[3])))
  90.                     {
  91.                         historyBuffer[index] = lookAheadBuffer;
  92.                         return false;
  93.                     }
  94.                 }
  95.                 if (((num == wordPtr[0]) && (num2 == wordPtr[1])) && (num3 == wordPtr[2]))
  96.                 {
  97.                     matchLength = 3;
  98.                     byte* numPtr = wordPtr + 3;
  99.                     byte* numPtr2 = lookAheadBuffer + 3;
  100.                     while (numPtr2 < endPtr)
  101.                     {
  102.                         numPtr++;
  103.                         numPtr2++;
  104.                         if (numPtr != numPtr2)
  105.                             break;
  106.                         matchLength++;
  107.                     }
  108.                 }
  109.             }
  110.             historyBuffer[index] = lookAheadBuffer;
  111.             return (matchLength >= 3);
  112.         }
  113.  
  114.         private static void WriteCompressed(int offset, int length, int literalLength, Stream dest)
  115.         {
  116.             int num;
  117.             int num2;
  118.             if ((length < 0xf) && (offset <= 0x400))
  119.             {
  120.                 offset--;
  121.                 num = ((length + 1) << 4) | ((offset & 3) << 2);
  122.                 num2 = offset >> 2;
  123.             }
  124.             else
  125.             {
  126.                 if (offset <= 0x4000)
  127.                 {
  128.                     offset--;
  129.                     WriteOpcode(0x20, length, 0x21, dest);
  130.                 }
  131.                 else
  132.                 {
  133.                     offset -= 0x4000;
  134.                     WriteOpcode(0x10 | ((offset >> 11) & 8), length, 9, dest);
  135.                 }
  136.                 num = (offset & 0xff) << 2;
  137.                 num2 = offset >> 6;
  138.             }
  139.             if (literalLength < 4)
  140.                 num |= literalLength;
  141.             dest.WriteByte((byte)num);
  142.             dest.WriteByte((byte)num2);
  143.         }
  144.  
  145.         private static unsafe void WriteLiteral(byte* source, int literalLength, Stream dest)
  146.         {
  147.             if (literalLength > 0)
  148.             {
  149.                 if (literalLength > 3)
  150.                     WriteOpcode(0, literalLength - 1, 0x11, dest);
  151.                 byte* ptr = source;
  152.                 for (int i = 0; i < literalLength; i++)
  153.                 {
  154.                     dest.WriteByte(*ptr);
  155.                     ptr++;
  156.                 }
  157.             }
  158.         }
  159.  
  160.  
  161.         private static void WriteOpcode(int opcode, int length, int threshold, Stream dest)
  162.         {
  163.             if (length <= threshold)
  164.             {
  165.                 opcode |= length - 2;
  166.                 dest.WriteByte((byte)opcode);
  167.             }
  168.             else
  169.             {
  170.                 dest.WriteByte((byte)opcode);
  171.  
  172.                 int value = length - threshold;
  173.                 while (value > 0xff)
  174.                 {
  175.                     value -= 0xff;
  176.                     dest.WriteByte(0);
  177.                 }
  178.                 dest.WriteByte((byte)value);
  179.             }
  180.         }
  181.     }
  182. }


« Last Edit: September 08, 2013, 08:20:06 AM by jar »