예제 #1
0
파일: Encoder.cs 프로젝트: gatekeep/MDCTool
        /// <summary>
        /// Create a single packet MDC1200 data array.
        /// </summary>
        /// <param name="packet">MDC packet to create</param>
        public void CreateSingle(MDCPacket packet)
        {
            Messages.Trace("Creating single-length MDC1200 packet " + packet.ToString());

            // initialize MDC1200 header
            GenerateHeader(ref dataArray, ref dataLoaded, NumberOfPreambles, true);

            // create a temporary array DATA_SIZE - 12 (stripping the size used by
            // the header)
            byte[] dp = new byte[CODEWORD_LENGTH];

            // fill the first bytes with the proper opcode and argument data
            dp[0] = packet.Operation;
            dp[1] = packet.Argument;
            dp[2] = (byte)((packet.UnitID >> 8) & 0x00FF);
            dp[3] = (byte)(packet.UnitID & 0x00FF);

            // pack data
            PackData(dp);

            // block copy new data into MDC1200 data array
            Buffer.BlockCopy(dp, 0, this.dataArray, dataLoaded, dp.Length);
            this.dataLoaded += 14;

            // dump output data for debug purposes
            Messages.TraceHex("Raw Data Dump", dataArray);
        }
예제 #2
0
        /// <summary>
        /// Internal function to process the bits of a MDC1200 data stream.
        /// </summary>
        /// <param name="idx">Decoder Index</param>
        /// <returns>True, if CRC was matched and decoding succeeded, otherwise false</returns>
        private bool ProcessBits(int idx)
        {
            int[] lbits = new int[MAX_MDC1200_BITS];
            int   lbc   = 0;

            byte[] data = new byte[14];
            ushort ccrc, rcrc;

            // do deep magic bit manipulation
            for (int i = 0; i < 16; i++)
            {
                // loop through 8 bits
                for (int j = 0; j < 7; j++)
                {
                    int k = (j * 16) + i;
                    lbits[lbc] = this.bits[idx, k];
                    ++lbc;
                }
            }

            for (int i = 0; i < 14; i++)
            {
                data[i] = 0;

                // loop through 8 bits (get each byte)
                for (int j = 0; j < 8; j++)
                {
                    int k = (i * 8) + j;

                    if (lbits[k] != 0)
                    {
                        data[i] |= (byte)(1 << j);
                    }
                }
            }

            // compute CRC
            ccrc = ComputeCRC(data, 4);
            rcrc = (ushort)(data[5] << 8 | data[4]);

            // dump output data for debug purposes
            Messages.TraceHex("Decoded Data Dump CCRC " + ccrc.ToString("X4") + " RCRC " + rcrc.ToString("X4"), data);

            // compare the computed CRC to the recieved CRC
            if (ccrc == rcrc)
            {
                byte crc;

                if (this.shstate[idx] == 2)
                {
                    // copy second packet data
                    second.Operation = data[0];
                    second.Argument  = data[1];
                    second.UnitID    = (ushort)((data[2] << 8) | data[3]);

                    // reset the states for all decoders
                    for (int k = 0; k < MDC_ND; k++)
                    {
                        this.shstate[k] = 0;
                    }

                    this.frameCount = 2;
                }
                else
                {
                    this.frameCount = 1;

                    // copy first packet data
                    first.Operation = data[0];
                    first.Argument  = data[1];
                    first.UnitID    = (ushort)((data[2] << 8) | data[3]);
                    crc             = (byte)((data[4] << 8) | data[5]);

                    // reset the states for all decoders
                    for (int k = 0; k < MDC_ND; k++)
                    {
                        this.shstate[k] = 0;
                    }

                    // check if the operation code is for a "double" packet
                    switch (data[0])
                    {
                    case OpType.DOUBLE_PACKET_TYPE1:
                    case OpType.DOUBLE_PACKET_TYPE2:
                    {
                        // we have a double packet reset the frame count to 0
                        // and set the state to reflect a double packet
                        this.frameCount   = 0;
                        this.shstate[idx] = 2;
                        this.shcount[idx] = 0;

                        ClearBits(idx);
                    }
                    break;

                    default:
                        break;
                    }
                }

                // if our frame count is non-zero execute the decoded callback
                if (this.frameCount > 0)
                {
                    Messages.Trace("Frame Count: " + frameCount);
                    Messages.Trace("MDC Frame 1 = " + ToString(first));

                    // if we have a frame count of > 1 then display second packet data
                    if (this.frameCount > 1)
                    {
                        Messages.Trace("MDC Frame 2 = " + ToString(second));
                    }

                    Messages.Trace("MDC1200 packet First (" + first.ToString() + "), Second (" + second.ToString() + ")");

                    // fire event
                    if (DecoderCallback != null)
                    {
                        DecoderCallback(this.frameCount, first, second);
                    }

                    // reset frame count
                    this.frameCount = 0;
                }

                return(true);
            }
            else
            {
                Messages.Trace("CRC Mismatch! Bad MDC Frame " + this.frameCount);

                // since the CRC is bad reset the frame count
                this.frameCount   = 0;
                this.shstate[idx] = -1;
            }
            return(false);
        }