private void serial_conn_DataReceived(object sender, System.IO.Ports.SerialDataReceivedEventArgs e)
        {
            System.IO.Ports.SerialPort port = (System.IO.Ports.SerialPort)sender;
            byte[] data = new byte[port.BytesToRead];

            int bytesToRead = port.BytesToRead;

            // Fyll på array hela tiden i slutet.
            port.Read(data, 0, data.Length);
            Array.Copy(data, 0, iBuff, iBuffPointer, data.Length);
            iBuffPointer += bytesToRead;

            // När array större eller lika med PACKET_LENGTH...
            while (iBuffPointer >= PACKET_LENGTH)
            {
                int startIndex = 0;

                // Sök igenom efter start byte från början.
                for (int i = 0; i < iBuffPointer; i++)
                {
                    // Poppa alla bytes som inte är startbyte.
                    if (iBuff[i] != UART_START_BYTE) startIndex++;
                    else
                    {
                        // När startbyte hittas, kolla om återstående längd är större eller lika med PACKET_LENGTH (inkl startbyte)
                        if ((iBuffPointer - startIndex) >= PACKET_LENGTH)
                        {
                            //om så, kolla PACKET_LENGTH-1 byte fram.
                            if (iBuff[startIndex + PACKET_LENGTH-1] == UART_END_BYTE)
                            {
                                // Om byte PACKET_LENGTH-1 är slutbyte så extraktas startIndex till slutbyteindex.
                                CanPacket cm = new CanPacket(iBuff, (uint)startIndex + 1);
                                cmQueue.Enqueue(cm);

                                if (newIncommingCanMessage != null) newIncommingCanMessage.Invoke(this, EventArgs.Empty);

                                // Sätt ny startindex och avsluta loop.
                                startIndex += PACKET_LENGTH;
                                break;
                            }
                        }
                    }
                }
                // och i slutet göra en array copy.
                // Flytta ner allt efter slutbyte till index 0 i array.
                Array.Copy(iBuff, startIndex, iBuff, 0, iBuffPointer - PACKET_LENGTH);
                iBuffPointer -= startIndex;
            }
        }
 public bool getPacket(out CanPacket cm)
 {
     cm = null;
     if (cmQueue.Count > 0)
     {
         cm = cmQueue.Dequeue();
         return true;
     }
     return false;
 }
 public bool sendPacket(CanPacket cm)
 {
     if (serial_conn.IsOpen)
     {
         byte[] b = new byte[PACKET_LENGTH];
         b[0] = UART_START_BYTE;
         Array.Copy(cm.getBytes(), 0, b, 1, PACKET_LENGTH-2);
         b[PACKET_LENGTH-1] = UART_END_BYTE;
         serial_conn.Write(b, 0, PACKET_LENGTH);
         return true;
     }
     return false;
 }
示例#4
0
        public void downloader()
        {
            int t = 0;
            CanPacket outCp = null;
            CanPacket cp = null;
            byte[] data = new byte[8];
            byte offset = 0;
            ulong currentAddress = 0;

            int doneCount = DONE_TO_SEND;

            try
            {
                while (true)
                {
                    bool hasMessage = sc.getPacket(out cp);
                    if (hasMessage)
                    {
                        Array.Copy(cp.data, data, 8);
                    }
                    bool hasMessageFromTarget = (hasMessage && cp.type== td.PACKET_TYPE.ptPGM && cp.pgm._class == td.PGM_CLASS.pcCTRL && cp.sid == TARGET_ID);

                    switch (pgs)
                    {
                        case dState.SEND_START:
                            // Send boot start packet to target.
                            // and wait for ack.
                            currentAddress = eestart;
                            data[4] = TARGET_ID;
                            data[3] = (byte)eetype;
                            data[2] = (byte)((currentAddress & 0xFF0000) >> 16);
                            data[1] = (byte)((currentAddress & 0xFF00) >> 8);
                            data[0] = (byte)(currentAddress & 0xFF);
                            outCp = new CanPacket(new CanPacket.canPGMPacket(td.PGM_CLASS.pcCTRL,(ushort)td.PGM_CTRL_TYPE.pctEE_START),MY_ID,5,data);

                            sc.sendPacket(outCp);
                            t = Environment.TickCount;
                            pgs = dState.WAIT_ACK;
                            timeStart = Environment.TickCount;
                            hasFoundNode = false;
                            break;

                        case dState.WAIT_ACK:

                            // Check for timeout, resend start packet in that case..
                            if ((Environment.TickCount - t) > TIMEOUT_MS)
                            {
                                pgs = dState.SEND_START;
                            }

                            // If received ack.
                            if (hasMessageFromTarget && cp.pgm.id==(ushort)td.PGM_CTRL_TYPE.pctEE_ACK)
                            {
                                // Start sending program data..
                                offset = 0;
                                pgs = dState.SEND_PGM_DATA;
                                hasFoundNode = true;
                            }
                            // if nack
                            if (hasMessageFromTarget && cp.pgm.id == (ushort)td.PGM_CTRL_TYPE.pctEE_NACK)
                            {
                                // else resend start..
                                pgs = dState.SEND_START;
                            }

                            break;

                        case dState.SEND_PGM_DATA:
                            // Send program data.
                            for (ulong i = 0; i < 7; i++)
                            {
                                // Populate data.
                                data[i] = eebytes[currentAddress + i + offset];
                            }
                            data[7] = offset;

                            outCp = new CanPacket(new CanPacket.canPGMPacket(td.PGM_CLASS.pcCTRL,(ushort)td.PGM_CTRL_TYPE.pctEE_PGM), MY_ID, 8, data);
                            sc.sendPacket(outCp);
                            t = Environment.TickCount;
                            pgs = dState.WAIT_OWN_PACKET;
                            break;

                        case dState.WAIT_OWN_PACKET:
                            // Wait reciving own packet, if timeout, resend last.
                            if ((Environment.TickCount - t) > TIMEOUT_MS)
                            {
                                pgs = dState.SEND_PGM_DATA;
                            }

                            // If received own packet..
                            if (hasMessage && outCp.Equals(cp))
                            {
                                offset += 7;

                                // Check if 56 bytes sent or not..
                                if (offset % 56 == 0)
                                {
                                    // Yes, send crc.
                                    t = Environment.TickCount;
                                    pgs = dState.SEND_CRC;
                                }
                                else
                                {
                                    // No, send more.
                                    pgs = dState.SEND_PGM_DATA;
                                }

                            }
                            break;

                        case dState.SEND_CRC:
                            byte[] pgmData = new byte[56];
                            for(ulong i=0;i<56;i++) pgmData[i] = eebytes[i+currentAddress];

                            ushort crc = crc16.calc_crc(pgmData, 56);
                            data[4] = (byte)((crc & 0xFF00) >> 8);
                            data[3] = (byte)(crc & 0xFF);
                            data[2] = (byte)(((currentAddress + offset) & 0xFF0000) >> 16);
                            data[1] = (byte)(((currentAddress + offset) & 0xFF00) >> 8);
                            data[0] = (byte)((currentAddress + offset) & 0xFF);
                            outCp = new CanPacket(new CanPacket.canPGMPacket(td.PGM_CLASS.pcCTRL,(ushort)td.PGM_CTRL_TYPE.pctEE_CRC), MY_ID, 8, data);
                            sc.sendPacket(outCp);
                            t = Environment.TickCount;
                            pgs = dState.WAIT_CRC_ACK;
                            break;

                        case dState.WAIT_CRC_ACK:
                            // Check for timeout, resend start packet in that case..
                            if ((Environment.TickCount - t) > TIMEOUT_MS)
                            {
                                pgs = dState.SEND_CRC;
                            }

                            // If received ack.
                            if (hasMessageFromTarget && cp.pgm.id == (ushort)td.PGM_CTRL_TYPE.pctEE_ACK)
                            {
                                // Start send more program data..
                                currentAddress += offset;

                                offset = 0;
                                pgs = dState.SEND_PGM_DATA;
                                hasFoundNode = true;

                                if (currentAddress > (eelength+eestart))
                                {
                                    // Yes, we are done, send done.
                                    pgs = dState.SEND_DONE;
                                }
                            }
                            // if nack
                            if (hasMessageFromTarget && cp.pgm.id == (ushort)td.PGM_CTRL_TYPE.pctEE_NACK)
                            {
                                // else resend pgm data...
                                offset = 0;
                                pgs = dState.SEND_PGM_DATA;
                            }

                            break;

                        case dState.SEND_DONE:
                            data[2] = (byte)(((eelength) & 0xFF0000) >> 16);
                            data[1] = (byte)(((eelength) & 0xFF00) >> 8);
                            data[0] = (byte)((eelength) & 0xFF);
                            outCp = new CanPacket(new CanPacket.canPGMPacket(td.PGM_CLASS.pcCTRL,(ushort)td.PGM_CTRL_TYPE.pctEE_DONE), MY_ID, 3, data);
                            sc.sendPacket(outCp);
                            t = Environment.TickCount;
                            pgs = dState.SEND_WAIT_DONE;
                            doneCount--;
                            break;

                        case dState.SEND_WAIT_DONE:
                            if (doneCount < 0)
                            {
                                pgs = dState.DONE;
                            }
                            else if ((Environment.TickCount-t)>TIMEOUT_MS)
                            {
                                pgs = dState.SEND_DONE;
                            }

                            break;

                        case dState.DONE:
                            abortmode = abortMode.PROGRAM;
                            down.Abort();
                            break;

                    }

                    Thread.Sleep(10);
                }

            } catch(Exception)
            {
                threadAbort.Invoke(this, new threadAbortEvent((int)(Environment.TickCount - timeStart), eelength, abortmode));
            }
        }