public void readMessages() { CANMessage canMessage = new CANMessage(); string rxMessage = string.Empty; Console.WriteLine("readMessages started"); while (true) { lock (m_synchObject) { if (m_endThread) { Console.WriteLine("readMessages ended"); return; } } try { if (m_serialPort.IsOpen) { do { rxMessage = m_serialPort.ReadLine(); rxMessage = rxMessage.Replace("\r", ""); // remove prompt characters... we don't need that stuff rxMessage = rxMessage.Replace("\n", ""); // remove prompt characters... we don't need that stuff } while (rxMessage.StartsWith("w") == false); uint id = Convert.ToUInt32(rxMessage.Substring(1, 3), 16); if (acceptMessageId(id)) { canMessage.setID(id); canMessage.setLength(8); canMessage.setData(0x0000000000000000); for (uint i = 0; i < 8; i++) { canMessage.setCanData(Convert.ToByte(rxMessage.Substring(5 + (2 * (int)i), 2), 16), i); } lock (m_listeners) { AddToCanTrace("RX: " + canMessage.getID().ToString("X3") + " " + canMessage.getLength().ToString("X1") + " " + canMessage.getData().ToString("X16")); //Console.WriteLine("MSG: " + rxMessage); foreach (ICANListener listener in m_listeners) { listener.handleMessage(canMessage); } } } } } catch (Exception) { Console.WriteLine("MSG: " + rxMessage); } } }
/// <summary> /// readMessages is the "run" method of this class. It reads all incomming messages /// and publishes them to registered ICANListeners. /// </summary> public void readMessages() { byte[] msg = new byte[8]; int dlc; int flag, id; long time; Canlib.canStatus status; CANMessage canMessage = new CANMessage(); logger.Debug("readMessages started"); while (true) { lock (m_synchObject) { if (m_endThread) { logger.Debug("readMessages thread ended"); return; } } status = Canlib.canReadWait(handleRead, out id, msg, out dlc, out flag, out time, 250); if ((flag & Canlib.canMSG_ERROR_FRAME) == 0) { if (status == Canlib.canStatus.canOK) { if (acceptMessageId((uint)id)) { canMessage.setID((uint)id); canMessage.setTimeStamp((uint)time); canMessage.setFlags((byte)flag); canMessage.setCanData(msg, (byte)dlc); receivedMessage(canMessage); } } else if (status == Canlib.canStatus.canERR_NOMSG) { Thread.Sleep(1); } else { logger.Debug("error" + status); } } else { logger.Debug("error frame"); } } }
/// <summary> /// readMessages is the "run" method of this class. It reads all incomming messages /// and publishes them to registered ICANListeners. /// </summary> public void readMessages() { uint id; int numMsgs = 1; const int timeout = 1000; CANMessage canMessage = new CANMessage(); logger.Debug("readMessages started"); while (true) { lock (m_synchObject) { if (m_endThread) { logger.Debug("readMessages thread ended"); return; } } IntPtr rxMsgs = Marshal.AllocHGlobal(Marshal.SizeOf(typeof(PassThruMsg))); m_status = passThru.PassThruReadMsgs(m_channelId, rxMsgs, ref numMsgs, timeout); if (m_status == J2534Err.STATUS_NOERROR) { if (numMsgs > 0) { PassThruMsg msg = rxMsgs.AsMsgList(numMsgs)[0]; byte[] all = msg.GetBytes(); id = (uint)(all[2] * 0x100 + all[3]); uint length = msg.DataSize - 4; byte[] data = new byte[length]; Array.Copy(all, 4, data, 0, length); if (acceptMessageId(id)) { canMessage.setID(id); canMessage.setTimeStamp(msg.Timestamp); canMessage.setCanData(data, (byte)(length)); receivedMessage(canMessage); } } } else { logger.Debug(String.Format("PassThruReadMsgs, status:{0}", m_status)); } Marshal.FreeHGlobal(rxMsgs); } }
public void readMessages() { CANMessage canMessage = new CANMessage(); string rxMessage = string.Empty; logger.Debug("readMessages started"); while (true) { lock (m_synchObject) { if (m_endThread) { logger.Debug("readMessages ended"); return; } } try { if (m_serialPort.IsOpen) { do { rxMessage = m_serialPort.ReadLine(); rxMessage = rxMessage.Replace("\r", ""); // remove prompt characters... we don't need that stuff rxMessage = rxMessage.Replace("\n", ""); // remove prompt characters... we don't need that stuff } while (rxMessage.StartsWith("w") == false); uint id = Convert.ToUInt32(rxMessage.Substring(1, 3), 16); if (acceptMessageId(id)) { canMessage.setID(id); canMessage.setLength(8); canMessage.setData(0x0000000000000000); for (uint i = 0; i < 8; i++) { canMessage.setCanData(Convert.ToByte(rxMessage.Substring(5 + (2 * (int)i), 2), 16), i); } receivedMessage(canMessage); } } } catch (Exception) { logger.Debug("MSG: " + rxMessage); } } }
public void readMessages() { CANMessage canMessage = new CANMessage(); string rxMessage = string.Empty; Console.WriteLine("readMessages started"); while (true) { lock (m_synchObject) { if (m_endThread) { Console.WriteLine("readMessages ended"); return; } } try { if (m_serialPort.IsOpen) { do { rxMessage = m_serialPort.ReadLine(); rxMessage = rxMessage.Replace("\r", ""); // remove prompt characters... we don't need that stuff rxMessage = rxMessage.Replace("\n", ""); // remove prompt characters... we don't need that stuff } while (rxMessage.StartsWith("w") == false); uint id = Convert.ToUInt32(rxMessage.Substring(1, 3), 16); if (acceptMessageId(id)) { canMessage.setID(id); canMessage.setLength(8); canMessage.setData(0x0000000000000000); for (uint i = 0; i < 8; i++) canMessage.setCanData(Convert.ToByte(rxMessage.Substring(5 + (2 * (int)i), 2), 16), i); lock (m_listeners) { AddToCanTrace("RX: " + canMessage.getID().ToString("X3") + " " + canMessage.getLength().ToString("X1") + " " + canMessage.getData().ToString("X16")); //Console.WriteLine("MSG: " + rxMessage); foreach (ICANListener listener in m_listeners) { listener.handleMessage(canMessage); } } } } } catch (Exception) { Console.WriteLine("MSG: " + rxMessage); } } }
/// <summary> /// Write a byte array to an address. /// </summary> /// <param name="address">Address. Must be greater than 0x1000</param> /// <param name="data">Data to be written</param> /// <returns></returns> //KWP2000 can read more than 6 bytes at a time.. but for now we are happy with this public bool writeMemory(int address, byte[] memdata) { if (!canUsbDevice.isOpen()) return false; _stallKeepAlive = true; /* for (int i = 0; i < 6; i++) { InitializeSession(); Thread.Sleep(1000); }*/ CANMessage response = new CANMessage(); ulong data = 0; // first send CANMessage msg = new CANMessage(0x7E0, 0, 7); //Console.WriteLine("Writing " + address.ToString("X8") + " len: " + memdata.Length.ToString("X2")); ulong cmd = 0x0000000000003406; // 0x34 = upload data to ECU ulong addressHigh = (uint)address & 0x0000000000FF0000; addressHigh /= 0x10000; ulong addressMiddle = (uint)address & 0x000000000000FF00; addressMiddle /= 0x100; ulong addressLow = (uint)address & 0x00000000000000FF; ulong len = (ulong)memdata.Length; //cmd |= (addressLow * 0x100000000); //cmd |= (addressMiddle * 0x1000000); //cmd |= (addressHigh * 0x10000); // cmd |= (len * 0x1000000000000); msg.setData(cmd); m_canListener.setupWaitMessage(0x7E8); if (!canUsbDevice.sendMessage(msg)) { logger.Debug("Couldn't send message"); } response = new CANMessage(); response = m_canListener.waitMessage(timeoutP2ct); data = response.getData(); CastInfoEvent("Waited for response: " + data.ToString("X8"), ActivityType.ConvertingFile); if (getCanData(data, 0) != 0x01 || getCanData(data, 1) != 0x74) { CastInfoEvent("Unable to write to ECUs memory", ActivityType.ConvertingFile); logger.Debug("Unable to write data to ECUs memory"); //_stallKeepAlive = false; //return false; } //10 F0 36 00 00 10 24 00 cmd = 0x0000000000360010; // 0x34 = upload data to ECU cmd |= (addressLow * 0x100000000000000); cmd |= (addressMiddle * 0x1000000000000); cmd |= (addressHigh * 0x10000000000); cmd |= (len * 0x100); //Console.WriteLine("send: " + cmd.ToString("X16")); msg.setData(cmd); m_canListener.setupWaitMessage(0x7E8); if (!canUsbDevice.sendMessage(msg)) { logger.Debug("Couldn't send message"); } // wait for response, should be 30 00 00 00 00 00 00 00 data = 0; response = new CANMessage(); response = m_canListener.waitMessage(timeoutP2ct); data = response.getData(); int numberOfFrames = (int)len / 7; // remnants? if (((int)len % 7) > 0) numberOfFrames++; byte iFrameNumber = 0x21; int txpnt = 0; if (data == 0x0000000000000030) { for (int i = 0; i < numberOfFrames; i++) { cmd = 0x0000000000000000; // 0x34 = upload data to ECU msg.setData(cmd); msg.setCanData(iFrameNumber, 0); msg.setCanData(memdata[txpnt++], 1); msg.setCanData(memdata[txpnt++], 2); msg.setCanData(memdata[txpnt++], 3); msg.setCanData(memdata[txpnt++], 4); msg.setCanData(memdata[txpnt++], 5); msg.setCanData(memdata[txpnt++], 6); msg.setCanData(memdata[txpnt++], 7); iFrameNumber++; if (!canUsbDevice.sendMessage(msg)) { logger.Debug("Couldn't send message"); } Thread.Sleep(1); // send the data with 7 bytes at a time } m_canListener.setupWaitMessage(0x7E8); response = new CANMessage(); response = m_canListener.waitMessage(timeoutP2ct); data = response.getData(); Console.WriteLine("received: " + data.ToString("X8")); } _stallKeepAlive = false; return true; }
public bool testSRAMWrite(/*int address, byte[] data*/) { StartSession10(); CastInfoEvent("Requesting mandatory data", ActivityType.UploadingBootloader); RequestECUInfo(0x90); RequestECUInfo(0x97); RequestECUInfo(0x92); RequestECUInfo(0xB4); RequestECUInfo(0xC1); RequestECUInfo(0xC2); RequestECUInfo(0xC3); RequestECUInfo(0xC4); RequestECUInfo(0xC5); RequestECUInfo(0xC6); Send0120(); Thread.Sleep(1000); StartSession1081(); StartSession10(); CastInfoEvent("Telling ECU to clear CANbus", ActivityType.UploadingBootloader); SendShutup(); SendA2(); SendA5(); SendA503(); Thread.Sleep(500); SendKeepAlive(); _securityLevel = AccessLevel.AccessLevel01; CastInfoEvent("Requesting security access", ActivityType.UploadingBootloader); RequestSecurityAccess(2000); Thread.Sleep(500); CastInfoEvent("Uploading data", ActivityType.UploadingBootloader); int startAddress = 0x102400; int saved_progress = 0; Bootloader btloaderdata = new Bootloader(); if (requestDownload()) { for (int i = 0; i < 0x46; i++) { //10 F0 36 00 00 10 24 00 //Console.WriteLine("Sending bootloader: " + startAddress.ToString("X8")); // cast event int percentage = (int)(((float)i * 100) / 70F); if (percentage > saved_progress) { CastProgressWriteEvent(percentage); saved_progress = percentage; } byte iFrameNumber = 0x21; if (SendTransferData(0xF0, startAddress, 0x7E8)) { // send 0x22 (34) frames with data from bootloader CANMessage msg = new CANMessage(0x7E0, 0, 8); for (int j = 0; j < 0x22; j++) { ulong cmd = 0x0000000000000000; // 0x34 = upload data to ECU msg.setData(cmd); msg.setCanData(iFrameNumber, 0); msg.setCanData(0x00, 1); msg.setCanData(0x01, 2); msg.setCanData(0x02, 3); msg.setCanData(0x03, 4); msg.setCanData(0x04, 5); msg.setCanData(0x05, 6); msg.setCanData(0x06, 7); iFrameNumber++; if (iFrameNumber > 0x2F) iFrameNumber = 0x20; if (!canUsbDevice.sendMessage(msg)) { logger.Debug("Couldn't send message"); } Thread.Sleep(1); } // send the remaining data m_canListener.setupWaitMessage(0x7E8); // now wait for 01 76 00 00 00 00 00 00 CANMessage response = new CANMessage(); response = new CANMessage(); response = m_canListener.waitMessage(timeoutP2ct); ulong datax = response.getData(); if (getCanData(datax, 0) != 0x01 || getCanData(datax, 1) != 0x76) { return false; } SendKeepAlive(); startAddress += 0xEA; } else { Console.WriteLine("Did not receive correct response from SendTransferData"); } } } return true; }
/// <summary> /// Send ONLY the erase and write commands, ECU is already in running bootloader /// </summary> /// <param name="filename"></param> /// <returns></returns> public bool RecoverECUOLD(string filename) { if (!canUsbDevice.isOpen()) return false; _stallKeepAlive = true; BlockManager bm = new BlockManager(); bm.SetFilename(filename); int startAddress = 0x020000; int saved_progress = 0; SendKeepAlive(); _securityLevel = AccessLevel.AccessLevel01; CastInfoEvent("Erasing FLASH", ActivityType.StartErasingFlash); if (SendrequestDownload(true)) { CastInfoEvent("Programming FLASH", ActivityType.UploadingFlash); for (int blockNumber = 0; blockNumber <= 0xF50; blockNumber++) { int percentage = (int)(((float)blockNumber * 100) / 3920F); if (percentage > saved_progress) { CastProgressWriteEvent(percentage); saved_progress = percentage; } byte[] data2Send = bm.GetNextBlock(); int length = 0xF0; if (blockNumber == 0xF50) length = 0xE6; if (SendTransferData(length, startAddress + (blockNumber * 0xEA), 0x311)) { // send the data from the block // calculate number of frames int numberOfFrames = (int)data2Send.Length / 7; // remnants? if (((int)data2Send.Length % 7) > 0) numberOfFrames++; byte iFrameNumber = 0x21; int txpnt = 0; CANMessage msg = new CANMessage(0x7E0, 0, 8); for (int frame = 0; frame < numberOfFrames; frame++) { ulong cmd = 0x0000000000000000; // 0x34 = upload data to ECU msg.setData(cmd); msg.setCanData(iFrameNumber, 0); msg.setCanData(data2Send[txpnt++], 1); msg.setCanData(data2Send[txpnt++], 2); msg.setCanData(data2Send[txpnt++], 3); msg.setCanData(data2Send[txpnt++], 4); msg.setCanData(data2Send[txpnt++], 5); msg.setCanData(data2Send[txpnt++], 6); msg.setCanData(data2Send[txpnt++], 7); iFrameNumber++; if (iFrameNumber > 0x2F) iFrameNumber = 0x20; if (!canUsbDevice.sendMessage(msg)) { logger.Debug("Couldn't send message"); } Thread.Sleep(1); } // send the remaining data m_canListener.setupWaitMessage(0x7E8); // now wait for 01 76 00 00 00 00 00 00 CANMessage response = new CANMessage(); response = new CANMessage(); response = m_canListener.waitMessage(timeoutP2ct); ulong data = response.getData(); if (getCanData(data, 0) != 0x01 || getCanData(data, 1) != 0x76) { return false; } SendKeepAlive(); } } sw.Stop(); CastInfoEvent("FLASH upload completed", ActivityType.ConvertingFile); // what else to do? Send0120(); CastInfoEvent("Session ended", ActivityType.FinishedFlashing); } else { sw.Stop(); CastInfoEvent("Failed to erase FLASH", ActivityType.ConvertingFile); Send0120(); CastInfoEvent("Session ended", ActivityType.FinishedFlashing); return false; } _stallKeepAlive = false; return true; }