Subversion Repositories HomeAutomation

Rev

Rev 770 | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | SVN | RSS feed

Rev 770 Rev 800
1
using System;
1
using System;
2
using System.Collections.Generic;
2
using System.Collections.Generic;
3
using System.Text;
3
using System.Text;
4
using System.Threading;
4
using System.Threading;
5
 
5
 
6
//this class should probably be integrated into canNMT instead
6
//this class should probably be integrated into canNMT instead
7
 
7
 
8
public class Downloader {
8
public class Downloader {
9
    private HexFile hf;
9
    private HexFile hf;
10
    private DaemonConnection dc;
10
    private DaemonConnection dc;
11
    private bool isBiosUpdate;
11
    private bool isBiosUpdate;
12
    private ulong dlOffset = 0;
12
    private ulong dlOffset = 0;
13
    //private Thread down;
13
    //private Thread down;
14
    private byte receiveID;
14
    private byte receiveID;
15
    private uint hwid;
15
    private uint hwid;
16
    private bool HWID_INUSE;
16
    private bool HWID_INUSE;
17
   
17
   
18
    private enum dState { SEND_START, WAIT_ACK_PRG, SEND_PGM_DATA, WAIT_ACK_DATA, RESEND_ADDR, WAIT_DONE, SEND_DONE, SEND_BIOS_UPDATE, SEND_RESET, DONE, DEBUG_STATE2, WAIT_BOOT, SEND_EMPTY_START, WAIT_ACK_PRG_EMPTY, SEND_EMPTY_DATA, WAIT_ACK_EMPTY_DATA, SEND_DONE_EMPTY, WAIT_DONE_EMPTY};
18
    private enum dState { SEND_START, WAIT_ACK_PRG, SEND_PGM_DATA, WAIT_ACK_DATA, RESEND_ADDR, WAIT_DONE, SEND_DONE, SEND_BIOS_UPDATE, SEND_RESET, DONE, DEBUG_STATE2, WAIT_BOOT, SEND_EMPTY_START, WAIT_ACK_PRG_EMPTY, SEND_EMPTY_DATA, WAIT_ACK_EMPTY_DATA, SEND_DONE_EMPTY, WAIT_DONE_EMPTY};
19
   
19
   
20
    private const byte CAN_NMT              = 0x00;
20
    private const byte CAN_NMT              = 0x00;
21
   
21
   
22
    private const byte CAN_NMT_RESET        = 0x04;
22
    private const byte CAN_NMT_RESET        = 0x04;
23
    private const byte CAN_NMT_BIOS_START   = 0x08;
23
    private const byte CAN_NMT_BIOS_START   = 0x08;
24
    private const byte CAN_NMT_PGM_START    = 0x0C;
24
    private const byte CAN_NMT_PGM_START    = 0x0C;
25
    private const byte CAN_NMT_PGM_DATA     = 0x10;
25
    private const byte CAN_NMT_PGM_DATA     = 0x10;
26
    private const byte CAN_NMT_PGM_END      = 0x14;
26
    private const byte CAN_NMT_PGM_END      = 0x14;
27
    private const byte CAN_NMT_PGM_COPY     = 0x18;
27
    private const byte CAN_NMT_PGM_COPY     = 0x18;
28
    private const byte CAN_NMT_PGM_ACK      = 0x1C;
28
    private const byte CAN_NMT_PGM_ACK      = 0x1C;
29
    private const byte CAN_NMT_PGM_NACK     = 0x20;
29
    private const byte CAN_NMT_PGM_NACK     = 0x20;
30
    private const byte CAN_NMT_START_APP    = 0x24;
30
    private const byte CAN_NMT_START_APP    = 0x24;
31
    private const byte CAN_NMT_APP_START    = 0x28;
31
    private const byte CAN_NMT_APP_START    = 0x28;
32
    private const byte CAN_NMT_HEARTBEAT    = 0x2C;
32
    private const byte CAN_NMT_HEARTBEAT    = 0x2C;
33
   
33
   
34
    private const byte MY_ID = 0x00;
34
    private const byte MY_ID = 0x00;
35
    //private const byte TARGET_ID = 0x78;
35
    //private const byte TARGET_ID = 0x78;
36
    private const byte MY_NID = 0x0;
36
    private const byte MY_NID = 0x0;
37
    private const byte ADDR0_INDEX = 0;
37
    private const byte ADDR0_INDEX = 0;
38
    private const byte ADDR1_INDEX = 1;
38
    private const byte ADDR1_INDEX = 1;
39
    private const byte ADDR2_INDEX = 2;
39
    private const byte ADDR2_INDEX = 2;
40
    private const byte ADDR3_INDEX = 3;
40
    private const byte ADDR3_INDEX = 3;
41
 
41
 
42
    private const byte HWID0_INDEX = 4;
42
    private const byte HWID0_INDEX = 4;
43
    private const byte HWID1_INDEX = 5;
43
    private const byte HWID1_INDEX = 5;
44
    private const byte HWID2_INDEX = 6;
44
    private const byte HWID2_INDEX = 6;
45
    private const byte HWID3_INDEX = 7;
45
    private const byte HWID3_INDEX = 7;
46
   
46
   
47
    private const int TIMEOUT_MS = 1000;
47
    private const int TIMEOUT_MS = 1000;
48
    private const int TIMEOUT_SHORT_MS = 200;
48
    private const int TIMEOUT_SHORT_MS = 200;
49
   
49
   
50
    private long timeStart = 0;
50
    private long timeStart = 0;
51
   
51
   
52
    public Downloader(HexFile hf, DaemonConnection dc, byte receiveID, bool isBiosUpdate, bool HWID_INUSE, uint hwid) {
52
    public Downloader(HexFile hf, DaemonConnection dc, byte receiveID, bool isBiosUpdate, bool HWID_INUSE, uint hwid) {
53
        this.hf = hf;
53
        this.hf = hf;
54
        this.dc = dc;
54
        this.dc = dc;
55
        this.receiveID = receiveID;
55
        this.receiveID = receiveID;
56
        this.isBiosUpdate = isBiosUpdate;
56
        this.isBiosUpdate = isBiosUpdate;
57
        this.hwid = hwid;
57
        this.hwid = hwid;
58
        this.HWID_INUSE = HWID_INUSE;
58
        this.HWID_INUSE = HWID_INUSE;
59
    }
59
    }
60
   
60
   
61
    public int calcCRC(HexFile hf) {
61
    public int calcCRC(HexFile hf) {
62
        int crc=0;
62
        int crc=0;
63
        for (ulong i=hf.getAddrLower(); i <= hf.getAddrUpper(); i++) {
63
        for (ulong i=hf.getAddrLower(); i <= hf.getAddrUpper(); i++) {
64
            crc = crc16_update(crc, hf.getByte(i));
64
            crc = crc16_update(crc, hf.getByte(i));
65
        }
65
        }
66
        return crc;
66
        return crc;
67
    }
67
    }
68
   
68
   
69
    public int crc16_update(int crc, byte a) {
69
    public int crc16_update(int crc, byte a) {
70
        int i;
70
        int i;
71
        crc ^= a;
71
        crc ^= a;
72
        for (i = 0; i < 8; ++i) {
72
        for (i = 0; i < 8; ++i) {
73
            if ((crc & 1) != 0)
73
            if ((crc & 1) != 0)
74
                crc = (crc >> 1) ^ 0xA001;
74
                crc = (crc >> 1) ^ 0xA001;
75
            else
75
            else
76
                crc = (crc >> 1);
76
                crc = (crc >> 1);
77
        }
77
        }
78
        return crc;
78
        return crc;
79
    }
79
    }
80
   
80
   
81
    public bool go() {
81
    public bool go() {
82
        if (dc==null || hf==null || hf.getLength()==0) return false;
82
        if (dc==null || hf==null || hf.getLength()==0) return false;
83
        return downloader();
83
        return downloader();
84
    }
84
    }
85
   
85
   
86
    public void abort() {
86
    public void abort() {
87
        //if (down != null && down.IsAlive) down.Abort();
87
        //if (down != null && down.IsAlive) down.Abort();
88
    }
88
    }
89
   
89
   
90
    public bool downloader() {
90
    public bool downloader() {
91
        dState pgs = dState.SEND_START;
91
        dState pgs = dState.SEND_START;
92
        int t = 0;
92
        int t = 0;
93
        int t2 = 0;
93
        int t2 = 0;
94
        CanPacket outCm = null;
94
        CanPacket outCm = null;
95
        CanPacket cm = null;
95
        CanPacket cm = null;
96
        byte[] data = new byte[8];
96
        byte[] data = new byte[8];
97
        uint byteSent = 0;
97
        uint byteSent = 0;
98
        ulong currentAddress = 0;
98
        ulong currentAddress = 0;
99
        bool done = false;
99
        bool done = false;
100
        bool errorOccured = false;
100
        bool errorOccured = false;
101
       
101
       
102
        try {
102
        try {
103
            if (isBiosUpdate) {
103
            if (isBiosUpdate) {
104
                dlOffset = hf.getAddrLower();
104
                dlOffset = hf.getAddrLower();
105
                //Console.WriteLine(dlOffset);
105
                //Console.WriteLine(dlOffset);
106
                //dlOffset = 200;
106
                //dlOffset = 200;
107
            }
107
            }
108
 
108
 
109
            CanNMT cpn = new CanNMT(HWID_INUSE);
109
            CanNMT cpn = new CanNMT(HWID_INUSE);
110
            cpn.setReceiver(receiveID);
110
            cpn.setReceiver(receiveID);
111
            bool hasMessage = false;
111
            bool hasMessage = false;
112
           
112
           
113
            while (!done) {
113
            while (!done) {
114
                Thread.Sleep(1);
114
                Thread.Sleep(1);
115
               
115
               
116
                switch (pgs) {
116
                switch (pgs) {
117
                    case dState.SEND_START:
117
                    case dState.SEND_START:
118
                        // Send boot start packet to target.
118
                        // Send boot start packet to target.
119
                        // and wait for ack.
119
                        // and wait for ack.
120
                        currentAddress = hf.getAddrLower();
120
                        currentAddress = hf.getAddrLower();
121
                        //data[RID_INDEX] = TARGET_ID;
121
                        //data[RID_INDEX] = TARGET_ID;
122
                        data[ADDR0_INDEX] = (byte)((currentAddress-dlOffset) & 0x0000FF);
122
                        data[ADDR0_INDEX] = (byte)((currentAddress-dlOffset) & 0x0000FF);
123
                        data[ADDR1_INDEX] = (byte)(((currentAddress-dlOffset) & 0x00FF00) >> 8);
123
                        data[ADDR1_INDEX] = (byte)(((currentAddress-dlOffset) & 0x00FF00) >> 8);
124
                        data[ADDR2_INDEX] = (byte)(((currentAddress-dlOffset) & 0xFF0000) >> 16);
124
                        data[ADDR2_INDEX] = (byte)(((currentAddress-dlOffset) & 0xFF0000) >> 16);
125
                        data[ADDR3_INDEX] = 0;
125
                        data[ADDR3_INDEX] = 0;
126
                        if (HWID_INUSE) {
126
                        if (HWID_INUSE) {
127
                            data[HWID0_INDEX] = (byte)((hwid) & 0xFF);
127
                            data[HWID0_INDEX] = (byte)((hwid) & 0xFF);
128
                            data[HWID1_INDEX] = (byte)((hwid>>8) & 0xFF);
128
                            data[HWID1_INDEX] = (byte)((hwid>>8) & 0xFF);
129
                            data[HWID2_INDEX] = (byte)((hwid>>16) & 0xFF);
129
                            data[HWID2_INDEX] = (byte)((hwid>>16) & 0xFF);
130
                            data[HWID3_INDEX] = (byte)((hwid>>24) & 0xFF);
130
                            data[HWID3_INDEX] = (byte)((hwid>>24) & 0xFF);
131
                        }
131
                        }
132
                        //outCm = new CanPacket(CAN_NMT, CAN_NMT_PGM_START, MY_ID, receiveID, 4, data);
132
                        //outCm = new CanPacket(CAN_NMT, CAN_NMT_PGM_START, MY_ID, receiveID, 4, data);
133
                        outCm = cpn.getPgmStartPacket(data);
133
                        outCm = cpn.getPgmStartPacket(data);
134
                        dc.sendCanPacket(outCm);
134
                        dc.sendCanPacket(outCm);
135
                        t = Environment.TickCount;
135
                        t = Environment.TickCount;
136
                        t2 = Environment.TickCount;
136
                        t2 = Environment.TickCount;
137
                        pgs = dState.WAIT_ACK_PRG;
137
                        pgs = dState.WAIT_ACK_PRG;
138
                        timeStart = Environment.TickCount;
138
                        timeStart = Environment.TickCount;
139
                        break;
139
                        break;
140
                   
140
                   
141
                   
141
                   
142
                    case dState.WAIT_ACK_PRG:
142
                    case dState.WAIT_ACK_PRG:
143
                        // Check for timeout, resend start packet in that case..
143
                        // Check for timeout, resend start packet in that case..
144
                        if ((Environment.TickCount - t) > TIMEOUT_MS) {
144
                        if ((Environment.TickCount - t) > TIMEOUT_MS) {
145
                            Console.WriteLine("Timeout while waiting for start prg ack.");
145
                            Console.WriteLine("Timeout while waiting for start prg ack.");
146
                            errorOccured = true;
146
                            errorOccured = true;
147
                            pgs = dState.SEND_RESET;
147
                            pgs = dState.SEND_RESET;
148
                        }
148
                        }
149
                        //Thread.Sleep(1);
149
                        //Thread.Sleep(1);
150
                        // If received ack.
150
                        // If received ack.
151
                        hasMessage = dc.getData(out cm);
151
                        hasMessage = dc.getData(out cm);
152
                        if (hasMessage) {
152
                        if (hasMessage) {
153
                            CanNMT cpnin = new CanNMT(cm, HWID_INUSE);
153
                            CanNMT cpnin = new CanNMT(cm, HWID_INUSE);
154
                            if (cpnin.isNMTPacket()) {
154
                            if (cpnin.isNMTPacket()) {
155
                            //if (cpnin.isNMTPacket() && (cpnin.getSender() == receiveID)) {
155
                            //if (cpnin.isNMTPacket() && (cpnin.getSender() == receiveID)) {
156
                                // If no error
156
                                // If no error
157
                                if (cpnin.getType() == CAN_NMT_PGM_ACK) {
157
                                if (cpnin.getType() == CAN_NMT_PGM_ACK) {
158
                                    // Start sending program data..
158
                                    // Start sending program data..
159
                                    byteSent = 0;
159
                                    byteSent = 0;
160
                                    pgs = dState.SEND_PGM_DATA;
160
                                    pgs = dState.SEND_PGM_DATA;
161
                                }
161
                                }
162
                                else if (cpnin.getType() == CAN_NMT_PGM_NACK ) {
162
                                else if (cpnin.getType() == CAN_NMT_PGM_NACK ) {
163
                                    // else ..
163
                                    // else ..
164
                                    Console.WriteLine("Nack on CAN_NMT_PGM_START.");
164
                                    Console.WriteLine("Nack on CAN_NMT_PGM_START.");
165
                                    errorOccured = true;
165
                                    errorOccured = true;
166
                                    pgs = dState.SEND_RESET;
166
                                    pgs = dState.SEND_RESET;
167
                                }
167
                                }
168
                            }
168
                            }
169
                        }
169
                        }
170
                        break;
170
                        break;
171
                       
171
                       
172
                    case dState.SEND_PGM_DATA:
172
                    case dState.SEND_PGM_DATA:
173
                        //Console.WriteLine("byteSent = "+byteSent);
173
                        //Console.WriteLine("byteSent = "+byteSent);
174
                        Console.Write(".");
174
                        Console.Write(".");
175
                        // Send program data.
175
                        // Send program data.
176
                        byte datalength = 2;
176
                        byte datalength = 2;
177
                        for (ulong i = 0; i < 6; i++) {
177
                        for (ulong i = 0; i < 6; i++) {
178
                            // Populate data.
178
                            // Populate data.
179
                            data[i+2] = hf.getByte(currentAddress + i + byteSent);
179
                            data[i+2] = hf.getByte(currentAddress + i + byteSent);
180
                            if (currentAddress + i + byteSent > hf.getAddrUpper()) {
180
                            if (currentAddress + i + byteSent > hf.getAddrUpper()) {
181
                                break;  //then done
181
                                break;  //then done
182
                            }
182
                            }
183
                            datalength++;
183
                            datalength++;
184
                        }
184
                        }
185
                        data[0] = (byte)(byteSent & 0x00FF);
185
                        data[0] = (byte)(byteSent & 0x00FF);
186
                        data[1] = (byte)((byteSent & 0xFF00) >> 8);
186
                        data[1] = (byte)((byteSent & 0xFF00) >> 8);
187
 
187
 
188
                        outCm = cpn.getPgmDataPacket(data, datalength);
188
                        outCm = cpn.getPgmDataPacket(data, datalength);
189
                        dc.sendCanPacket(outCm);
189
                        dc.sendCanPacket(outCm);
190
                       
190
                       
191
                        t = Environment.TickCount;
191
                        t = Environment.TickCount;
192
                        t2 = Environment.TickCount;
192
                        t2 = Environment.TickCount;
193
                        byteSent += 6;
193
                        byteSent += 6;
194
                        pgs = dState.WAIT_ACK_DATA;
194
                        pgs = dState.WAIT_ACK_DATA;
195
                        break;
195
                        break;
196
                       
196
                       
197
                       
197
                       
198
                    case dState.WAIT_ACK_DATA:
198
                    case dState.WAIT_ACK_DATA:
199
                        // Wait for pgm ack.
199
                        // Wait for pgm ack.
200
                        if ((Environment.TickCount - t) > TIMEOUT_MS) {
200
                        if ((Environment.TickCount - t) > TIMEOUT_MS) {
201
                            // Woops, error. 
201
                            // Woops, error. 
202
                            Console.WriteLine("Timeout while waiting for data ack.");
202
                            Console.WriteLine("Timeout while waiting for data ack.");
203
                            errorOccured = true;
203
                            errorOccured = true;
204
                            pgs = dState.SEND_RESET;
204
                            pgs = dState.SEND_RESET;
205
                        }
205
                        }
206
                        else if ((Environment.TickCount - t2) > TIMEOUT_SHORT_MS) {
206
                        else if ((Environment.TickCount - t2) > TIMEOUT_SHORT_MS) {
207
                            // Woops, error. 
207
                            // Woops, error. 
208
                            Console.Write(":");
208
                            Console.Write(":");
209
                            byteSent -= 6;
209
                            byteSent -= 6;
210
                            pgs = dState.SEND_PGM_DATA;
210
                            pgs = dState.SEND_PGM_DATA;
211
                            break;
211
                            break;
212
                        }
212
                        }
213
                        //Thread.Sleep(1);
213
                        //Thread.Sleep(1);
214
                        // If received ack.
214
                        // If received ack.
215
                        hasMessage = dc.getData(out cm);
215
                        hasMessage = dc.getData(out cm);
216
                        if (hasMessage) {
216
                        if (hasMessage) {
217
                            CanNMT cpnin = new CanNMT(cm, HWID_INUSE);
217
                            CanNMT cpnin = new CanNMT(cm, HWID_INUSE);
218
                            if (cpnin.isNMTPacket()) {
218
                            if (cpnin.isNMTPacket()) {
219
                            //if (cpnin.isNMTPacket() && (cpnin.getSender() == receiveID)) {
219
                            //if (cpnin.isNMTPacket() && (cpnin.getSender() == receiveID)) {
220
                                // If no error
220
                                // If no error
221
                                if (cpnin.getType() == CAN_NMT_PGM_ACK) {
221
                                if (cpnin.getType() == CAN_NMT_PGM_ACK) {
222
                                    //currentAddress += 2;
222
                                    //currentAddress += 2;
223
                                    // Check if end.
223
                                    // Check if end.
224
                                    if (currentAddress + byteSent > hf.getAddrUpper()) {
224
                                    if (currentAddress + byteSent > hf.getAddrUpper()) {
225
                                        // Yes, we are done, send done.
225
                                        // Yes, we are done, send done.
226
                                        pgs = dState.SEND_DONE;
226
                                        pgs = dState.SEND_DONE;
227
                                    }
227
                                    }
228
                                    else {
228
                                    else {
229
                                        // More to write.
229
                                        // More to write.
230
                                        //byteSent = 0;
230
                                        //byteSent = 0;
231
                                        pgs = dState.SEND_PGM_DATA;
231
                                        pgs = dState.SEND_PGM_DATA;
232
                                    }
232
                                    }
233
                                }
233
                                }
234
                                else if (cpnin.getType() == CAN_NMT_PGM_NACK ) {
234
                                else if (cpnin.getType() == CAN_NMT_PGM_NACK ) {
235
                                    // else ..
235
                                    // else ..
236
                                    Console.WriteLine("Nack on CAN_NMT_PGM_DATA.");
236
                                    Console.WriteLine("Nack on CAN_NMT_PGM_DATA.");
237
                                    errorOccured = true;
237
                                    errorOccured = true;
238
                                    pgs = dState.SEND_RESET;
238
                                    pgs = dState.SEND_RESET;
239
                                }
239
                                }
240
                            }
240
                            }
241
                        }
241
                        }
242
                        break;
242
                        break;
243
                       
243
                       
244
                    case dState.SEND_DONE:
244
                    case dState.SEND_DONE:
245
                        // Send done
245
                        // Send done
246
                        outCm = cpn.getPgmEndPacket();
246
                        outCm = cpn.getPgmEndPacket();
247
                        dc.sendCanPacket(outCm);
247
                        dc.sendCanPacket(outCm);
248
 
248
 
249
                        t = Environment.TickCount;
249
                        t = Environment.TickCount;
250
                        t2 = Environment.TickCount;
250
                        t2 = Environment.TickCount;
251
                        pgs = dState.WAIT_DONE;
251
                        pgs = dState.WAIT_DONE;
252
                        break;
252
                        break;
253
                       
253
                       
254
                       
254
                       
255
                    case dState.WAIT_DONE:
255
                    case dState.WAIT_DONE:
256
                        // Check for timeout, resend done packet in that case..
256
                        // Check for timeout, resend done packet in that case..
257
                        if ((Environment.TickCount - t) > TIMEOUT_MS) {
257
                        if ((Environment.TickCount - t) > TIMEOUT_MS) {
258
                            Console.WriteLine("Timeout while waiting for end prg ack.");
258
                            Console.WriteLine("Timeout while waiting for end prg ack.");
259
                            errorOccured = true;
259
                            errorOccured = true;
260
                            pgs = dState.SEND_RESET;
260
                            pgs = dState.SEND_RESET;
261
                        }
261
                        }
262
                        //Thread.Sleep(1);
262
                        //Thread.Sleep(1);
263
                       
263
                       
264
                        hasMessage = dc.getData(out cm);
264
                        hasMessage = dc.getData(out cm);
265
                        if (hasMessage) {
265
                        if (hasMessage) {
266
                            CanNMT cpnin = new CanNMT(cm, HWID_INUSE);
266
                            CanNMT cpnin = new CanNMT(cm, HWID_INUSE);
267
                            if (cpnin.isNMTPacket()) {
267
                            if (cpnin.isNMTPacket()) {
268
                            //if (cpnin.isNMTPacket() && (cpnin.getSender() == receiveID)) {
268
                            //if (cpnin.isNMTPacket() && (cpnin.getSender() == receiveID)) {
269
                                // If no error
269
                                // If no error
270
                                if (cpnin.getType() == CAN_NMT_PGM_ACK) {
270
                                if (cpnin.getType() == CAN_NMT_PGM_ACK) {
271
                                    Console.WriteLine("");
271
                                    Console.WriteLine("");
272
                                    //
272
                                    //
273
                                    int crc = calcCRC(hf);
273
                                    int crc = calcCRC(hf);
274
                               
274
                               
275
                                    if (cm.getDataLength() == 2) {
275
                                    if (cm.getDataLength() == 2) {
276
                                        byte[] cmdata = cm.getData();
276
                                        byte[] cmdata = cm.getData();
277
                                        if ((cmdata[0] == (crc & 0xFF)) && (cmdata[1] == (crc>>8))) {
277
                                        if ((cmdata[0] == (crc & 0xFF)) && (cmdata[1] == (crc>>8))) {
278
                                            if (!isBiosUpdate) {
278
                                            if (!isBiosUpdate) {
279
                                                Console.WriteLine("Done, successfully programmed application.");
279
                                                Console.WriteLine("Done, successfully programmed application.");
280
                                                pgs = dState.SEND_RESET;
280
                                                pgs = dState.SEND_RESET;
281
                                            } else {
281
                                            } else {
282
                                                Console.WriteLine("Done, successfully programmed bios to application space.");
282
                                                Console.WriteLine("Done, successfully programmed bios to application space.");
283
                                                pgs = dState.SEND_BIOS_UPDATE;
283
                                                pgs = dState.SEND_BIOS_UPDATE;
284
                                            }
284
                                            }
285
                                        } else {
285
                                        } else {
286
                                            string nodecrc = String.Format("{0:x4}", (int)cmdata[0] + (int)(cmdata[1]<<8));
286
                                            string nodecrc = String.Format("{0:x4}", (int)cmdata[0] + (int)(cmdata[1]<<8));
287
                                            nodecrc = "0x"+nodecrc;
287
                                            nodecrc = "0x"+nodecrc;
288
                                            string realcrc = String.Format("{0:x4}", (int)(crc & 0xFF) + (int)(crc & 0xFF00));
288
                                            string realcrc = String.Format("{0:x4}", (int)(crc & 0xFF) + (int)(crc & 0xFF00));
289
                                            realcrc = "0x"+realcrc;
289
                                            realcrc = "0x"+realcrc;
290
                                            Console.WriteLine("CRC failed. Node sent CRC "+nodecrc+" but should be "+realcrc+".");
290
                                            Console.WriteLine("CRC failed. Node sent CRC "+nodecrc+" but should be "+realcrc+".");
291
                                            errorOccured = true;
291
                                            errorOccured = true;
292
                                            pgs = dState.SEND_RESET;
292
                                            pgs = dState.SEND_RESET;
293
                                        }
293
                                        }
294
                                       
294
                                       
295
                                        byteSent = 0;
295
                                        byteSent = 0;
296
                                    }
296
                                    }
297
                                    //Console.WriteLine("crc: " + crc + " " + (crc>>8) + " " + (crc & 0xFF));
297
                                    //Console.WriteLine("crc: " + crc + " " + (crc>>8) + " " + (crc & 0xFF));
298
                                    //Console.WriteLine("ACKpkg with CRC: " + cm.ToString());
298
                                    //Console.WriteLine("ACKpkg with CRC: " + cm.ToString());
299
                                    // 
299
                                    // 
300
                                }
300
                                }
301
                                else if (cpnin.getType() == CAN_NMT_PGM_NACK) {
301
                                else if (cpnin.getType() == CAN_NMT_PGM_NACK) {
302
                                    // else resend addr..
302
                                    // else resend addr..
303
                                    Console.WriteLine("Nack on CAN_NMT_PGM_END.");
303
                                    Console.WriteLine("Nack on CAN_NMT_PGM_END.");
304
                                    errorOccured = true;
304
                                    errorOccured = true;
305
                                    pgs = dState.SEND_RESET;
305
                                    pgs = dState.SEND_RESET;
306
                                }
306
                                }
307
                            }
307
                            }
308
                        }
308
                        }
309
                        break;
309
                        break;
310
                       
310
                       
311
                    case dState.SEND_BIOS_UPDATE:
311
                    case dState.SEND_BIOS_UPDATE:
312
                        data[0] = (byte)(0 & 0x00FF);
312
                        data[0] = (byte)(0 & 0x00FF);
313
                        data[1] = (byte)((0 & 0xFF00) >> 8);
313
                        data[1] = (byte)((0 & 0xFF00) >> 8);
314
                        data[2] = (byte)(dlOffset & 0x00FF);
314
                        data[2] = (byte)(dlOffset & 0x00FF);
315
                        data[3] = (byte)((dlOffset & 0xFF00) >> 8);
315
                        data[3] = (byte)((dlOffset & 0xFF00) >> 8);
316
                        data[4] = (byte)((hf.getAddrUpper()-hf.getAddrLower()+1) & 0x00FF);
316
                        data[4] = (byte)((hf.getAddrUpper()-hf.getAddrLower()+1) & 0x00FF);
317
                        data[5] = (byte)(((hf.getAddrUpper()-hf.getAddrLower()+1) & 0xFF00) >> 8);
317
                        data[5] = (byte)(((hf.getAddrUpper()-hf.getAddrLower()+1) & 0xFF00) >> 8);
318
                       
318
                       
319
                        outCm = cpn.getPgmCopyPacket(data);
319
                        outCm = cpn.getPgmCopyPacket(data);
320
                        Console.WriteLine("Now say a prayer, moving bios");
320
                        Console.WriteLine("Now say a prayer, moving bios");
321
                        dc.sendCanPacket(outCm);
321
                        dc.sendCanPacket(outCm);
322
                        t = Environment.TickCount;
322
                        t = Environment.TickCount;
323
                        t2 = Environment.TickCount;
323
                        t2 = Environment.TickCount;
324
                        pgs = dState.WAIT_BOOT;
324
                        pgs = dState.WAIT_BOOT;
325
                        //pgs = dState.DONE;
325
                        //pgs = dState.DONE;
326
                        break;
326
                        break;
327
 
327
 
328
                    case dState.WAIT_BOOT:
328
                    case dState.WAIT_BOOT:
329
                        // Wait for node reset answer (boot msg).
329
                        // Wait for node reset answer (boot msg).
330
                        if ((Environment.TickCount - t) > 3*TIMEOUT_MS) {
330
                        if ((Environment.TickCount - t) > 3*TIMEOUT_MS) {
331
                            // Woops, error. 
331
                            // Woops, error. 
332
                            Console.WriteLine("Timeout while waiting for node to boot.");
332
                            Console.WriteLine("Timeout while waiting for node to boot.");
333
                            errorOccured = true;
333
                            errorOccured = true;
334
                            pgs = dState.SEND_DONE;
334
                            pgs = dState.SEND_DONE;
335
                        }
335
                        }
336
                        //Thread.Sleep(1);
336
                        //Thread.Sleep(1);
337
                        // If received boot msg.
337
                        // If received boot msg.
338
                        hasMessage = dc.getData(out cm);
338
                        hasMessage = dc.getData(out cm);
339
                        if (hasMessage) {
339
                        if (hasMessage) {
340
                            CanNMT cpnin = new CanNMT(cm, HWID_INUSE);
340
                            CanNMT cpnin = new CanNMT(cm, HWID_INUSE);
341
                            if (cpnin.isNMTPacket()) {
341
                            if (cpnin.isNMTPacket()) {
342
                            //if (cpnin.isNMTPacket() && (cpnin.getSender() == receiveID)) {
342
                            //if (cpnin.isNMTPacket() && (cpnin.getSender() == receiveID)) {
343
                                // If no error
343
                                // If no error
344
                                if (cpnin.getType() == CAN_NMT_BIOS_START) {
344
                                if (cpnin.getType() == CAN_NMT_BIOS_START) {
345
                                    pgs = dState.SEND_EMPTY_START;
345
                                    pgs = dState.SEND_EMPTY_START;
346
                                }
346
                                }
347
                                else {
347
                                else {
348
                                    // else ..
348
                                    // else ..
349
                                }
349
                                }
350
                            }
350
                            }
351
                        }
351
                        }
352
                        break;
352
                        break;
353
                       
353
                       
354
                    case dState.SEND_EMPTY_START:
354
                    case dState.SEND_EMPTY_START:
355
                        // Send boot start packet to target.
355
                        // Send boot start packet to target.
356
                        // and wait for ack.
356
                        // and wait for ack.
357
                       
357
                       
358
                        //data[RID_INDEX] = TARGET_ID;
358
                        //data[RID_INDEX] = TARGET_ID;
359
                        data[ADDR0_INDEX] = (byte)((0) & 0x0000FF);
359
                        data[ADDR0_INDEX] = (byte)((0) & 0x0000FF);
360
                        data[ADDR1_INDEX] = (byte)(((0) & 0x00FF00) >> 8);
360
                        data[ADDR1_INDEX] = (byte)(((0) & 0x00FF00) >> 8);
361
                        data[ADDR2_INDEX] = (byte)(((0) & 0xFF0000) >> 16);
361
                        data[ADDR2_INDEX] = (byte)(((0) & 0xFF0000) >> 16);
362
                        data[ADDR3_INDEX] = 0;
362
                        data[ADDR3_INDEX] = 0;
363
                        if (HWID_INUSE) {
363
                        if (HWID_INUSE) {
364
                            data[HWID0_INDEX] = (byte)((hwid) & 0xFF);
364
                            data[HWID0_INDEX] = (byte)((hwid) & 0xFF);
365
                            data[HWID1_INDEX] = (byte)((hwid>>8) & 0xFF);
365
                            data[HWID1_INDEX] = (byte)((hwid>>8) & 0xFF);
366
                            data[HWID2_INDEX] = (byte)((hwid>>16) & 0xFF);
366
                            data[HWID2_INDEX] = (byte)((hwid>>16) & 0xFF);
367
                            data[HWID3_INDEX] = (byte)((hwid>>24) & 0xFF);
367
                            data[HWID3_INDEX] = (byte)((hwid>>24) & 0xFF);
368
                        }
368
                        }
369
                        //outCm = new CanPacket(CAN_NMT, CAN_NMT_PGM_START, MY_ID, receiveID, 4, data);
369
                        //outCm = new CanPacket(CAN_NMT, CAN_NMT_PGM_START, MY_ID, receiveID, 4, data);
370
                        outCm = cpn.getPgmStartPacket(data);
370
                        outCm = cpn.getPgmStartPacket(data);
371
                        dc.sendCanPacket(outCm);
371
                        dc.sendCanPacket(outCm);
372
                        t = Environment.TickCount;
372
                        t = Environment.TickCount;
373
                        t2 = Environment.TickCount;
373
                        t2 = Environment.TickCount;
374
                        pgs = dState.WAIT_ACK_PRG_EMPTY;
374
                        pgs = dState.WAIT_ACK_PRG_EMPTY;
375
                        break;
375
                        break;
376
                   
376
                   
377
                   
377
                   
378
                    case dState.WAIT_ACK_PRG_EMPTY:
378
                    case dState.WAIT_ACK_PRG_EMPTY:
379
                        // Check for timeout, resend start packet in that case..
379
                        // Check for timeout, resend start packet in that case..
380
                        if ((Environment.TickCount - t) > 3*TIMEOUT_MS) {
380
                        if ((Environment.TickCount - t) > 3*TIMEOUT_MS) {
381
                            Console.WriteLine("Timeout while waiting for start prg ack during empty-first-block-cycle.");
381
                            Console.WriteLine("Timeout while waiting for start prg ack during empty-first-block-cycle.");
382
                            errorOccured = true;
382
                            errorOccured = true;
383
                            pgs = dState.SEND_RESET;
383
                            pgs = dState.SEND_RESET;
384
                        }
384
                        }
385
                        //Thread.Sleep(1);
385
                        //Thread.Sleep(1);
386
                        // If received ack.
386
                        // If received ack.
387
                        hasMessage = dc.getData(out cm);
387
                        hasMessage = dc.getData(out cm);
388
                        if (hasMessage) {
388
                        if (hasMessage) {
389
                            CanNMT cpnin = new CanNMT(cm, HWID_INUSE);
389
                            CanNMT cpnin = new CanNMT(cm, HWID_INUSE);
390
                            if (cpnin.isNMTPacket()) {
390
                            if (cpnin.isNMTPacket()) {
391
                            //if (cpnin.isNMTPacket() && (cpnin.getSender() == receiveID)) {
391
                            //if (cpnin.isNMTPacket() && (cpnin.getSender() == receiveID)) {
392
                                // If no error
392
                                // If no error
393
                                if (cpnin.getType() == CAN_NMT_PGM_ACK) {
393
                                if (cpnin.getType() == CAN_NMT_PGM_ACK) {
394
                                    // Start sending program data..
394
                                    // Start sending program data..
395
                                    byteSent = 0;
395
                                    byteSent = 0;
396
                                    pgs = dState.SEND_EMPTY_DATA;
396
                                    pgs = dState.SEND_EMPTY_DATA;
397
                                }
397
                                }
398
                                else if (cpnin.getType() == CAN_NMT_PGM_NACK ) {
398
                                else if (cpnin.getType() == CAN_NMT_PGM_NACK ) {
399
                                    // else ..
399
                                    // else ..
400
                                    Console.WriteLine("Nack on CAN_NMT_PGM_START.");
400
                                    Console.WriteLine("Nack on CAN_NMT_PGM_START.");
401
                                    errorOccured = true;
401
                                    errorOccured = true;
402
                                    pgs = dState.SEND_RESET;
402
                                    pgs = dState.SEND_RESET;
403
                                }
403
                                }
404
                            }
404
                            }
405
                        }
405
                        }
406
                        break;
406
                        break;
407
                       
407
                       
408
                    case dState.SEND_EMPTY_DATA:
408
                    case dState.SEND_EMPTY_DATA:
409
                        // Send program data.
409
                        // Send program data.
410
                        data[0] = 0;
410
                        data[0] = 0;
411
                        data[1] = 0;
411
                        data[1] = 0;
412
                        data[2] = 0xff;
412
                        data[2] = 0xff;
413
                        data[3] = 0xff;
413
                        data[3] = 0xff;
414
 
414
 
415
                        outCm = cpn.getPgmDataPacket(data, 4);
415
                        outCm = cpn.getPgmDataPacket(data, 4);
416
                        dc.sendCanPacket(outCm);
416
                        dc.sendCanPacket(outCm);
417
                       
417
                       
418
                        t = Environment.TickCount;
418
                        t = Environment.TickCount;
419
                        t2 = Environment.TickCount;
419
                        t2 = Environment.TickCount;
420
                        byteSent += 6;
420
                        byteSent += 6;
421
                        pgs = dState.WAIT_ACK_EMPTY_DATA;
421
                        pgs = dState.WAIT_ACK_EMPTY_DATA;
422
                        break;
422
                        break;
423
                       
423
                       
424
                       
424
                       
425
                    case dState.WAIT_ACK_EMPTY_DATA:
425
                    case dState.WAIT_ACK_EMPTY_DATA:
426
                        // Wait for pgm ack.
426
                        // Wait for pgm ack.
427
                        if ((Environment.TickCount - t) > 2*TIMEOUT_MS) {
427
                        if ((Environment.TickCount - t) > 2*TIMEOUT_MS) {
428
                            // Woops, error. 
428
                            // Woops, error. 
429
                            Console.WriteLine("Timeout while waiting for data ack.");
429
                            Console.WriteLine("Timeout while waiting for data ack.");
430
                            errorOccured = true;
430
                            errorOccured = true;
431
                            pgs = dState.SEND_RESET;
431
                            pgs = dState.SEND_RESET;
432
                        }
432
                        }
433
                        //Thread.Sleep(1);
433
                        //Thread.Sleep(1);
434
                        // If received ack.
434
                        // If received ack.
435
                        hasMessage = dc.getData(out cm);
435
                        hasMessage = dc.getData(out cm);
436
                        if (hasMessage) {
436
                        if (hasMessage) {
437
                            CanNMT cpnin = new CanNMT(cm, HWID_INUSE);
437
                            CanNMT cpnin = new CanNMT(cm, HWID_INUSE);
438
                            if (cpnin.isNMTPacket()) {
438
                            if (cpnin.isNMTPacket()) {
439
                            //if (cpnin.isNMTPacket() && (cpnin.getSender() == receiveID)) {
439
                            //if (cpnin.isNMTPacket() && (cpnin.getSender() == receiveID)) {
440
                                // If no error
440
                                // If no error
441
                                if (cpnin.getType() == CAN_NMT_PGM_ACK) {
441
                                if (cpnin.getType() == CAN_NMT_PGM_ACK) {
442
                                    pgs = dState.SEND_DONE_EMPTY;
442
                                    pgs = dState.SEND_DONE_EMPTY;
443
                                }
443
                                }
444
                                else if (cpnin.getType() == CAN_NMT_PGM_NACK ) {
444
                                else if (cpnin.getType() == CAN_NMT_PGM_NACK ) {
445
                                    // else ..
445
                                    // else ..
446
                                    Console.WriteLine("Nack on CAN_NMT_PGM_DATA.");
446
                                    Console.WriteLine("Nack on CAN_NMT_PGM_DATA.");
447
                                    errorOccured = true;
447
                                    errorOccured = true;
448
                                    pgs = dState.SEND_RESET;
448
                                    pgs = dState.SEND_RESET;
449
                                }
449
                                }
450
                            }
450
                            }
451
                        }
451
                        }
452
                        break;
452
                        break;
453
                       
453
                       
454
                    case dState.SEND_DONE_EMPTY:
454
                    case dState.SEND_DONE_EMPTY:
455
                        // Send done
455
                        // Send done
456
                        outCm = cpn.getPgmEndPacket();
456
                        outCm = cpn.getPgmEndPacket();
457
                        dc.sendCanPacket(outCm);
457
                        dc.sendCanPacket(outCm);
458
 
458
 
459
                        t = Environment.TickCount;
459
                        t = Environment.TickCount;
460
                        t2 = Environment.TickCount;
460
                        t2 = Environment.TickCount;
461
                        pgs = dState.WAIT_DONE_EMPTY;
461
                        pgs = dState.WAIT_DONE_EMPTY;
462
                        break;
462
                        break;
463
                       
463
                       
464
                       
464
                       
465
                    case dState.WAIT_DONE_EMPTY:
465
                    case dState.WAIT_DONE_EMPTY:
466
                        // Check for timeout, resend done packet in that case..
466
                        // Check for timeout, resend done packet in that case..
467
                        if ((Environment.TickCount - t) > TIMEOUT_MS) {
467
                        if ((Environment.TickCount - t) > TIMEOUT_MS) {
468
                            Console.WriteLine("Timeout while waiting for end prg ack.");
468
                            Console.WriteLine("Timeout while waiting for end prg ack.");
469
                            errorOccured = true;
469
                            errorOccured = true;
470
                            pgs = dState.SEND_RESET;
470
                            pgs = dState.SEND_RESET;
471
                        }
471
                        }
472
                        //Thread.Sleep(1);
472
                        //Thread.Sleep(1);
473
                       
473
                       
474
                        hasMessage = dc.getData(out cm);
474
                        hasMessage = dc.getData(out cm);
475
                        if (hasMessage) {
475
                        if (hasMessage) {
476
                            CanNMT cpnin = new CanNMT(cm, HWID_INUSE);
476
                            CanNMT cpnin = new CanNMT(cm, HWID_INUSE);
477
                            if (cpnin.isNMTPacket()) {
477
                            if (cpnin.isNMTPacket()) {
478
                            //if (cpnin.isNMTPacket() && (cpnin.getSender() == receiveID)) {
478
                            //if (cpnin.isNMTPacket() && (cpnin.getSender() == receiveID)) {
479
                                // If no error
479
                                // If no error
480
                                if (cpnin.getType() == CAN_NMT_PGM_ACK) {
480
                                if (cpnin.getType() == CAN_NMT_PGM_ACK) {
481
                                    Console.WriteLine("");
481
                                    Console.WriteLine("");
482
                                    //
482
                                    //
483
                                    Console.WriteLine("Done, successfully cleaned application flash.");
483
                                    Console.WriteLine("Done, successfully cleaned application flash.");
484
                                    pgs = dState.SEND_RESET;
484
                                    pgs = dState.SEND_RESET;
485
                                }
485
                                }
486
                                else if (cpnin.getType() == CAN_NMT_PGM_NACK) {
486
                                else if (cpnin.getType() == CAN_NMT_PGM_NACK) {
487
                                    // else resend addr..
487
                                    // else resend addr..
488
                                    Console.WriteLine("Nack on CAN_NMT_PGM_END.");
488
                                    Console.WriteLine("Nack on CAN_NMT_PGM_END.");
489
                                    errorOccured = true;
489
                                    errorOccured = true;
490
                                    pgs = dState.SEND_RESET;
490
                                    pgs = dState.SEND_RESET;
491
                                }
491
                                }
492
                            }
492
                            }
493
                        }
493
                        }
494
                        break;                     
494
                        break;                     
495
                    case dState.SEND_RESET:
495
                    case dState.SEND_RESET:
496
                        // Send reset
496
                        // Send reset
497
                        cpn.doReset(dc, receiveID, hwid);
497
                        cpn.doReset(dc, receiveID, hwid);
498
                        t = Environment.TickCount;
498
                        t = Environment.TickCount;
499
                        t2 = Environment.TickCount;
499
                        t2 = Environment.TickCount;
500
                        pgs = dState.DONE;
500
                        pgs = dState.DONE;
501
                        break;
501
                        break;
502
                       
502
                       
503
                       
503
                       
504
                    case dState.DONE:
504
                    case dState.DONE:
505
                        done = true;
505
                        done = true;
506
                        //down.Abort();
506
                        //down.Abort();
507
                        if (!errorOccured) {
507
                        if (!errorOccured) {
508
                            long tsecs = ((Environment.TickCount - timeStart) / 1000);
508
                            long tsecs = ((Environment.TickCount - timeStart) / 1000);
509
                            double bitRate = hf.getLength() / ((double)(Environment.TickCount - timeStart) / 1000.0);
509
                            double bitRate = hf.getLength() / ((double)(Environment.TickCount - timeStart) / 1000.0);
510
                           
510
                           
511
                            if (tsecs <= 0) tsecs = 1;
511
                            if (tsecs <= 0) tsecs = 1;
512
                            long mins = tsecs / 60;
512
                            long mins = tsecs / 60;
513
                            long secs = tsecs % 60;
513
                            long secs = tsecs % 60;
514
                            string pad = "";
514
                            string pad = "";
515
                            if (secs < 10) {
515
                            if (secs < 10) {
516
                                pad = "0";
516
                                pad = "0";
517
                            }
517
                            }
518
                            Console.WriteLine("Time spent: " + mins + ":" + pad + secs + ", " + Math.Round(bitRate, 2) + " bytes/s");
518
                            Console.WriteLine("Time spent: " + mins + ":" + pad + secs + ", " + Math.Round(bitRate, 2) + " bytes/s");
519
                        }
519
                        }
520
                        //Console.Write("> ");
520
                        //Console.Write("> ");
521
                        break;
521
                        break;
522
                }
522
                }
523
            }
523
            }
524
           
524
           
525
        } catch(Exception) {
525
        } catch(Exception) {
526
            Console.WriteLine("Exception occured");
526
            Console.WriteLine("Exception occured");
527
            //Console.WriteLine(e);
527
            //Console.WriteLine(e);
528
            //skriva ut antal bytes skrivna vore bra här, kanske nån annan form av hjälp för debug, något gick snett liksom
528
            //skriva ut antal bytes skrivna vore bra här, kanske nån annan form av hjälp för debug, något gick snett liksom
529
           
529
           
530
        }
530
        }
531
       
531
       
532
        return !errorOccured;
532
        return !errorOccured;
533
    }
533
    }
534
}
534
}
535
 
535