Beispiel #1
0
 private void TransitionState()
 {
     switch (state) {
         case BinHexUtils.State.HdrFileSize:
             if (scratch[0] > 63)
                 throw new ByteEncoderException(Resources.EncodersStrings.BinHexDecoderFileNameTooLong);
             state = BinHexUtils.State.Header;
             bytesNeeded = scratch[0] + 21;
             break;
         case BinHexUtils.State.Header:
             header = new BinHexHeader(scratch);
             if (!this.DataForkOnly) {
                 var bytes = header.GetBytes();
                 System.Buffer.BlockCopy(bytes, 0, extra, 0, bytes.Length);
                 extraIndex = 0;
                 extraSize = bytes.Length;
             }
             if (0L != header.DataForkLength) {
                 state = BinHexUtils.State.Data;
                 bytesNeeded = (int) header.DataForkLength;
                 runningCRC = 0;
                 break;
             }
             checksum = runningCRC;
             checksum = BinHexUtils.CalculateCrc(checksum);
             state = BinHexUtils.State.DataCRC;
             bytesNeeded = 2;
             scratchSize = scratch.Length;
             scratchIndex = 0;
             break;
         case BinHexUtils.State.Data:
             checksum = runningCRC;
             checksum = BinHexUtils.CalculateCrc(checksum);
             state = BinHexUtils.State.DataCRC;
             bytesNeeded = 2;
             scratchSize = scratch.Length;
             scratchIndex = 0;
             break;
         case BinHexUtils.State.DataCRC:
             if ((checksum & 65280) >> 8 != scratch[0] || (checksum & byte.MaxValue) != scratch[1])
                 throw new ByteEncoderException(Resources.EncodersStrings.BinHexDecoderBadCrc);
             if (this.DataForkOnly) {
                 state = BinHexUtils.State.Ending;
                 repeatCount = 0;
                 encodedSize = 0;
                 lineReady = false;
                 break;
             }
             var length1 = header.DataForkLength%128L != 0L ? (int) (128L - header.DataForkLength%128L) : 0;
             if (length1 != 0) {
                 System.Array.Clear(extra, 0, length1);
                 extraSize = length1;
             }
             if (header.ResourceForkLength > 0L) {
                 state = BinHexUtils.State.Resource;
                 bytesNeeded = (int) header.ResourceForkLength;
                 runningCRC = 0;
                 break;
             }
             checksum = 0;
             checksum = BinHexUtils.CalculateCrc(checksum);
             state = BinHexUtils.State.ResourceCRC;
             bytesNeeded = 2;
             scratchSize = scratch.Length;
             scratchIndex = 0;
             break;
         case BinHexUtils.State.Resource:
             checksum = runningCRC;
             checksum = BinHexUtils.CalculateCrc(checksum);
             state = BinHexUtils.State.ResourceCRC;
             bytesNeeded = 2;
             scratchSize = scratch.Length;
             scratchIndex = 0;
             break;
         case BinHexUtils.State.ResourceCRC:
             if ((checksum & 65280) >> 8 != scratch[0] || (checksum & byte.MaxValue) != scratch[1])
                 throw new ByteEncoderException(Resources.EncodersStrings.BinHexDecoderBadResourceForkCrc);
             var length2 = header.ResourceForkLength%128L != 0L ? (int) (128L - header.ResourceForkLength%128L) : 0;
             if (length2 != 0) {
                 System.Array.Clear(extra, 0, length2);
                 extraSize = length2;
             }
             state = BinHexUtils.State.Ending;
             repeatCount = 0;
             encodedSize = 0;
             lineReady = false;
             break;
         default:
             throw new System.Exception(Resources.EncodersStrings.BinHexDecoderInternalError);
     }
 }
Beispiel #2
0
 public override sealed void Convert(byte[] input, int inputIndex, int inputSize, byte[] output, int outputIndex, int outputSize, bool flush, out int inputUsed, out int outputUsed, out bool completed)
 {
     if (inputSize != 0) {
         if (input == null)
             throw new System.ArgumentNullException(nameof(input));
         if (inputIndex < 0 || inputIndex >= input.Length)
             throw new System.ArgumentOutOfRangeException(nameof(inputIndex));
         if (inputSize < 0 || inputSize > input.Length - inputIndex)
             throw new System.ArgumentOutOfRangeException(nameof(inputSize));
     }
     if (output == null)
         throw new System.ArgumentNullException(nameof(output));
     if (outputIndex < 0 || outputIndex >= output.Length)
         throw new System.ArgumentOutOfRangeException(nameof(outputIndex));
     if (outputSize < 1 || outputSize > output.Length - outputIndex)
         throw new System.ArgumentOutOfRangeException(nameof(outputSize));
     inputUsed = inputIndex;
     outputUsed = outputIndex;
     var inputTotal = 0;
     if (encodedSize != 0) {
         var count = System.Math.Min(encodedSize, outputSize);
         System.Buffer.BlockCopy(encoded, encodedIndex, output, outputIndex, count);
         outputSize -= count;
         outputIndex += count;
         encodedSize -= count;
         if (encodedSize != 0) {
             encodedIndex += count;
             outputUsed = outputIndex - outputUsed;
             inputUsed = 0;
             completed = false;
             return;
         }
         encodedIndex = 0;
     }
     var flag = true;
     while (flag) {
         flag = false;
         switch (state) {
             case BinHexUtils.State.Starting:
                 System.Buffer.BlockCopy(BinHexPrefix, 0, decoded, 0, BinHexPrefix.Length);
                 decodedIndex = 0;
                 decodedSize = BinHexPrefix.Length;
                 state = BinHexUtils.State.Prefix;
                 goto case 2;
             case BinHexUtils.State.Prefix:
                 var count1 = System.Math.Min(decodedSize, outputSize);
                 System.Buffer.BlockCopy(decoded, decodedIndex, output, outputIndex, count1);
                 outputSize -= count1;
                 outputIndex += count1;
                 decodedSize -= count1;
                 if (decodedSize != 0) {
                     decodedIndex += count1;
                     break;
                 }
                 decodedIndex = 0;
                 previousByte = 256;
                 repeatCount = 0;
                 accumCount = 0;
                 lineOffset = 1;
                 lines = 0;
                 checksum = 0;
                 if (this.header != null) {
                     var bytes = header.GetBytes();
                     System.Buffer.BlockCopy(bytes, 0, decoded, 0, bytes.Length);
                     decodedSize = bytes.Length;
                     decodedIndex = 0;
                     macbinHeaderSize = 0;
                 } else {
                     macbinHeader = new byte[128];
                     macbinHeaderOffset = 0;
                     macbinHeaderSize = macbinHeader.Length;
                 }
                 state = BinHexUtils.State.Header;
                 goto case 4;
             case BinHexUtils.State.Header:
                 if (macbinHeaderSize != 0) {
                     var count2 = System.Math.Min(macbinHeaderSize, inputSize);
                     System.Buffer.BlockCopy(input, inputIndex, macbinHeader, macbinHeaderOffset, count2);
                     macbinHeaderOffset += count2;
                     macbinHeaderSize -= count2;
                     inputIndex += count2;
                     inputSize -= count2;
                     if (macbinHeaderSize == 0) {
                         var header = new MacBinaryHeader(macbinHeader);
                         macbinHeader = null;
                         this.header = new BinHexHeader(header);
                         var bytes = this.header.GetBytes();
                         System.Buffer.BlockCopy(bytes, 0, decoded, 0, bytes.Length);
                         decodedSize = bytes.Length;
                         decodedIndex = 0;
                     } else
                         break;
                 }
                 var inputMax1 = decodedSize;
                 if (inputMax1 != 0) {
                     flag = true;
                     this.CompressAndEncode(decoded, ref decodedIndex, ref decodedSize, ref inputTotal, ref inputMax1, false, output, ref outputIndex, ref outputSize);
                 }
                 break;
             case BinHexUtils.State.Data:
                 var inputMax2 = System.Math.Min(decodedSize, inputSize);
                 if (inputMax2 != 0) {
                     flag = true;
                     this.CompressAndEncode(input, ref inputIndex, ref inputSize, ref decodedSize, ref inputMax2, true, output, ref outputIndex, ref outputSize);
                 }
                 break;
             case BinHexUtils.State.DataCRC:
                 if (macbinHeaderSize != 0) {
                     BinHexEncoder.IgnoreChunkFromInput(ref macbinHeaderSize, ref inputIndex, ref inputSize);
                     if (macbinHeaderSize != 0)
                         break;
                 }
                 var inputMax3 = decodedSize;
                 if (inputMax3 != 0) {
                     flag = true;
                     this.CompressAndEncode(decoded, ref decodedIndex, ref decodedSize, ref inputTotal, ref inputMax3, false, output, ref outputIndex, ref outputSize);
                 }
                 break;
             case BinHexUtils.State.Resource:
                 var inputMax4 = System.Math.Min(decodedSize, inputSize);
                 if (inputMax4 != 0) {
                     flag = true;
                     this.CompressAndEncode(input, ref inputIndex, ref inputSize, ref decodedSize, ref inputMax4, true, output, ref outputIndex, ref outputSize);
                 }
                 break;
             case BinHexUtils.State.ResourceCRC:
                 if (macbinHeaderSize != 0) {
                     BinHexEncoder.IgnoreChunkFromInput(ref macbinHeaderSize, ref inputIndex, ref inputSize);
                     if (macbinHeaderSize != 0)
                         break;
                 }
                 var inputMax5 = decodedSize;
                 if (inputMax5 != 0) {
                     flag = true;
                     this.CompressAndEncode(decoded, ref decodedIndex, ref decodedSize, ref inputTotal, ref inputMax5, false, output, ref outputIndex, ref outputSize);
                 }
                 break;
             case BinHexUtils.State.Ending:
                 var count3 = System.Math.Min(decodedSize, outputSize);
                 System.Buffer.BlockCopy(decoded, decodedIndex, output, outputIndex, count3);
                 outputSize -= count3;
                 outputIndex += count3;
                 decodedSize -= count3;
                 if (decodedSize != 0) {
                     decodedIndex += count3;
                     break;
                 }
                 decodedIndex = 0;
                 state = BinHexUtils.State.Ended;
                 goto case 11;
             case BinHexUtils.State.Ended:
                 macbinHeaderSize = inputSize;
                 BinHexEncoder.IgnoreChunkFromInput(ref macbinHeaderSize, ref inputIndex, ref inputSize);
                 break;
         }
         if (encodedSize != 0)
             break;
     }
     if (flush && inputSize == 0 && (state != BinHexUtils.State.Ended && outputSize != 0))
         throw new ByteEncoderException(Resources.EncodersStrings.BinHexEncoderDataCorruptCannotFinishEncoding);
     outputUsed = outputIndex - outputUsed;
     inputUsed = inputIndex - inputUsed;
     completed = inputSize == 0 && (!flush || state == BinHexUtils.State.Ended);
     if (!flush || !completed)
         return;
     state = BinHexUtils.State.Starting;
 }
Beispiel #3
0
 private bool ReadLine(byte[] input, ref int inputIndex, ref int inputSize, bool flush)
 {
     if (state == BinHexUtils.State.Ending) {
         inputIndex += inputSize;
         inputSize = 0;
         return false;
     }
     var flag = false;
     while (inputSize != 0 || flush && encodedSize != 0) {
         byte num = 10;
         if (inputSize != 0) {
             --inputSize;
             num = input[inputIndex++];
         }
         if (num != 10) {
             if (encodedSize >= encoded.Length)
                 throw new ByteEncoderException(Resources.EncodersStrings.BinHexDecoderLineTooLong);
             encoded[encodedSize++] = num;
         } else if (state == BinHexUtils.State.Starting) {
             for (var index = 0U; (long) index < (long) encodedSize; ++index) {
                 if (!ByteEncoder.IsWhiteSpace(encoded[index])) {
                     if ((uint) ((ulong) encodedSize - index) < BinHexPrologue.Length || !ByteEncoder.BeginsWithNI(encoded, (int) index, BinHexPrologue, BinHexPrologue.Length))
                         throw new ByteEncoderException(Resources.EncodersStrings.BinHexDecoderLineCorrupt);
                     state = BinHexUtils.State.Started;
                     repeatCheck = false;
                     accumCount = 0;
                     accum = 0;
                     header = null;
                     break;
                 }
             }
             encodedSize = 0;
         } else {
             while (encodedSize != 0 && (encoded[encodedSize - 1] == 13 || encoded[encodedSize - 1] == 32 || encoded[encodedSize - 1] == 9))
                 --encodedSize;
             if (encodedSize == 0) {
                 if (state != BinHexUtils.State.Started)
                     ;
             } else {
                 flag = true;
                 encodedIndex = 0;
                 break;
             }
         }
     }
     return flag;
 }