Skip to content

Instantly share code, notes, and snippets.

@brianbri6
Forked from cjdell/Program.cs
Created June 1, 2022 04:27
Show Gist options
  • Save brianbri6/671a8ab96d0f52e6d60182e9eba4723b to your computer and use it in GitHub Desktop.
Save brianbri6/671a8ab96d0f52e6d60182e9eba4723b to your computer and use it in GitHub Desktop.
Chevy Volt / Opel Ampera SHVCS DTC Clearing
/* This is an experimental script which I used to successfully clear the "Service High Voltage Charging System" message which can occur due to a loss of isolation.
* Previously I had to pay frequently to access the expensive SPS programming system to clear this code whilst attempting to resolve the underlying cause.
* This script was generated by a tool I developed to analyse J2534 log files.
* This could work for other cars but I can't comment on success. Please do not run this unless you understand the consequences!
* I intend to convert to a version that will work with ELM327 once I learn how these work.
* The program requires the J2534-Sharp library as a dependency.
* https://github.com/BrianHumlicek/J2534-Sharp
*/
using System;
using System.Linq;
using System.Text;
using System.Threading;
using SAE.J2534;
namespace J5234Examples
{
class Program
{
static void Main(string[] args)
{
Device device1;
Channel channel1;
int filter1;
int filter2;
// Change this line is using something different to the VXDIAG VCX Nano!
string DllFileName = APIFactory.GetAPIinfo().First(api => api.Name.Contains("VXDIAG")).Filename;
API API = APIFactory.GetAPI(DllFileName);
Console.WriteLine("PTOpen");
device1 = API.GetDevice();
Console.WriteLine("PTReadVersion");
Console.WriteLine(device1.FirmwareVersion);
Console.WriteLine("PTConnect");
// 6 = ISO15765
channel1 = device1.GetChannel((Protocol)6, (Baud)500000, 0);
Console.WriteLine("PTIoctl");
// 32768 = CAN_MIXED_FORMAT
channel1.SetConfig(new[] { new SConfig((Parameter)32768, 1) });
Console.WriteLine("PTStartMsgFilter");
filter1 = channel1.StartMsgFilter(new MessageFilter() { FilterType = (Filter)3, Mask = new byte[] { 0xff, 0xff, 0xff, 0xff }, Pattern = new byte[] { 0x00, 0x00, 0x07, 0xec }, FlowControl = new byte[] { 0x00, 0x00, 0x07, 0xe4 } });
Console.WriteLine("PTStartMsgFilter");
filter2 = channel1.StartMsgFilter(new MessageFilter() { FilterType = (Filter)1, Mask = new byte[] { 0xff, 0xff, 0xff, 0xff }, Pattern = new byte[] { 0x00, 0x00, 0x05, 0xec }, FlowControl = null });
Console.WriteLine("Pause");
Console.WriteLine("Sleep(2000)\n");
Thread.Sleep(2000);
Console.WriteLine("PTWriteMsgs");
Console.WriteLine(">>> 00 00 07 e4 27 01");
// 64 = ISO15765_FRAME_PAD
channel1.SendMessages(new[] { new Message(new byte[] { 0x00, 0x00, 0x07, 0xe4, 0x27, 0x01 }, (TxFlag)64) });
Console.WriteLine("ReadBlock");
ReadUntilMessage(channel1, new byte[] { 0x00, 0x00, 0x07, 0xec, 0x67, 0x01, 0x58, 0xe3 }, 1500);
Console.WriteLine("PTWriteMsgs");
Console.WriteLine(">>> 00 00 07 e4 27 02 75 6c");
// 64 = ISO15765_FRAME_PAD
channel1.SendMessages(new[] { new Message(new byte[] { 0x00, 0x00, 0x07, 0xe4, 0x27, 0x02, 0x75, 0x6c }, (TxFlag)64) });
Console.WriteLine("ReadBlock");
ReadUntilMessage(channel1, new byte[] { 0x00, 0x00, 0x07, 0xec, 0x67, 0x02 }, 1500);
Console.WriteLine("PTWriteMsgs");
Console.WriteLine(">>> 00 00 07 e4 ae fc 02 00 00 46 00");
// 64 = ISO15765_FRAME_PAD
channel1.SendMessages(new[] { new Message(new byte[] { 0x00, 0x00, 0x07, 0xe4, 0xae, 0xfc, 0x02, 0x00, 0x00, 0x46, 0x00 }, (TxFlag)64) });
Console.WriteLine("ReadBlock");
ReadUntilMessage(channel1, new byte[] { 0x00, 0x00, 0x07, 0xec, 0xee, 0xfc }, 1500);
Console.WriteLine("PTWriteMsgs");
Console.WriteLine(">>> 00 00 07 e4 ae fc 02 00 00 49 00");
// 64 = ISO15765_FRAME_PAD
channel1.SendMessages(new[] { new Message(new byte[] { 0x00, 0x00, 0x07, 0xe4, 0xae, 0xfc, 0x02, 0x00, 0x00, 0x49, 0x00 }, (TxFlag)64) });
Console.WriteLine("ReadBlock");
ReadUntilMessage(channel1, new byte[] { 0x00, 0x00, 0x07, 0xec, 0xee, 0xfc }, 7000);
Console.WriteLine("Pause");
Console.WriteLine("Sleep(2000)\n");
Thread.Sleep(2000);
Console.WriteLine("PTStopMsgFilter");
channel1.StopMsgFilter(filter1);
Console.WriteLine("PTStopMsgFilter");
channel1.StopMsgFilter(filter2);
Console.WriteLine("PTDisconnect");
channel1.Dispose();
Console.WriteLine("PTClose");
device1.Dispose();
}
static void ReadUntilMessage(Channel c, byte[] message, int timeout)
{
var attempts = 5;
Console.WriteLine("ReadUntilMessage: " + BytesToHexString(message));
while (true)
{
var results = c.GetMessages(1, timeout);
PrintBytes(results);
if (results.Result == ResultCode.BUFFER_EMPTY)
{
Console.WriteLine("Waiting for message...");
attempts--;
if (attempts == 0) return;
continue;
}
if (results.Messages.Length == 1)
{
if (results.Messages[0].Data.SequenceEqual(message))
{
Console.WriteLine("FOUND\n");
return;
}
}
}
}
static string BytesToHexString(byte[] bytes)
{
StringBuilder builder = new StringBuilder();
for (int i = 0; i < bytes.Length; i++)
{
builder.Append(bytes[i].ToString("x2"));
}
return builder.ToString();
}
static void PrintBytes(GetMessageResults results)
{
StringBuilder builder = new StringBuilder();
foreach (var msg in results.Messages)
{
for (int i = 0; i < msg.Data.Length; i++)
{
builder.Append(msg.Data[i].ToString("x2"));
}
builder.Append("\n");
}
Console.WriteLine(builder.ToString());
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment