Fix DTC tables and Clear DTC result; auto-set ECU type from adapter name
- Rewrite S300 and KPro DTC tables from hvbt_protocol.pdf (the previous tables did not match the PDF; e.g. ERR01.6 is P0350 IGM, not P1361). - Clear DTC: the adapter never echoes the documented ack, but the ECU does clear (bench: 3 of 4 codes cleared, P0350 re-set at once as an active fault). Judge success from the live ERR bytes; wait only 0.6 s for the ack so polling resumes, and report "N of M cleared". - Set the ECU protocol from the adapter name (S300/KPro) on connect; a stale KPro setting made an S300 adapter look unresponsive. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
parent
2bd937aca5
commit
ba79775fbc
@ -7,6 +7,18 @@ import 'bt_service.dart';
|
||||
|
||||
enum EcuType { s300, kpro }
|
||||
|
||||
/// ECU type implied by the adapter's Bluetooth name, or null if the name
|
||||
/// doesn't say. HV adapters advertise it, e.g. "S300[94]-SPP",
|
||||
/// "HVS300-SPP[94]"; a KPro adapter is expected to contain "KPRO"/"K-PRO".
|
||||
EcuType? ecuTypeFromDeviceName(String? name) {
|
||||
if (name == null) return null;
|
||||
final n = name.toUpperCase().replaceAll('-', '');
|
||||
final s300 = n.contains('S300');
|
||||
final kpro = n.contains('KPRO');
|
||||
if (s300 == kpro) return null; // neither, or ambiguous
|
||||
return s300 ? EcuType.s300 : EcuType.kpro;
|
||||
}
|
||||
|
||||
typedef _Matcher = Uint8List? Function(List<int> rxBuf);
|
||||
|
||||
class _Pending {
|
||||
|
||||
@ -1,233 +1,241 @@
|
||||
/// DTC maps for S300 and KPro ECU protocols.
|
||||
/// DTC maps for S300 and KPro ECU protocols, transcribed from the "DTC map"
|
||||
/// sections of hvbt_protocol.pdf.
|
||||
///
|
||||
/// Key format: 'ERRxx_bity' where xx = byte index (00-based), y = bit number (0=LSB).
|
||||
/// Value: 'Pxxxx — description'
|
||||
/// Key format: 'ERRxx_bity' where xx = ERR byte index (00-based), y = bit
|
||||
/// number (0=LSB). Value: '<code> — description'. Bits the PDF leaves
|
||||
/// undocumented ("???") use 'ERRxx.y' as the code so the raw bit is still
|
||||
/// visible on screen.
|
||||
library;
|
||||
|
||||
/// S300 DTC map (ERR00–ERR03, 4 bytes × 8 bits = 32 possible codes)
|
||||
/// S300 DTC map (ERR00–ERR03 = frame bytes 37–40). Descriptions include the
|
||||
/// Honda blink code and sensor abbreviation from the PDF.
|
||||
const Map<String, String> s300DtcMap = {
|
||||
// ERR00 (byte 0x31)
|
||||
'ERR00_bit0': 'P0130 — O2 Sensor (front)',
|
||||
'ERR00_bit1': 'P0135 — O2 Sensor Heater (front)',
|
||||
'ERR00_bit2': 'P0505 — Idle Air Control Valve',
|
||||
'ERR00_bit3': 'P0108 — MAP Sensor High',
|
||||
'ERR00_bit4': 'P0107 — MAP Sensor Low',
|
||||
'ERR00_bit5': 'P0113 — IAT Sensor High',
|
||||
'ERR00_bit6': 'P0112 — IAT Sensor Low',
|
||||
'ERR00_bit7': 'P0118 — ECT Sensor High',
|
||||
|
||||
// ERR01 (byte 0x32)
|
||||
'ERR01_bit0': 'P0117 — ECT Sensor Low',
|
||||
'ERR01_bit1': 'P0336 — CKP Sensor',
|
||||
'ERR01_bit2': 'P0341 — CMP Sensor',
|
||||
'ERR01_bit3': 'P1362 — TDC Sensor (No Signal)',
|
||||
'ERR01_bit4': 'P1363 — TDC Sensor (No Signal 2)',
|
||||
'ERR01_bit5': 'P0335 — CKP Sensor (No Signal)',
|
||||
'ERR01_bit6': 'P1361 — TDC Sensor',
|
||||
'ERR01_bit7': 'P0300 — Random Misfire',
|
||||
|
||||
// ERR02 (byte 0x33)
|
||||
'ERR02_bit0': 'P0301 — Misfire Cylinder 1',
|
||||
'ERR02_bit1': 'P0302 — Misfire Cylinder 2',
|
||||
'ERR02_bit2': 'P0303 — Misfire Cylinder 3',
|
||||
'ERR02_bit3': 'P0304 — Misfire Cylinder 4',
|
||||
'ERR02_bit4': 'P1259 — VTEC System Malfunction',
|
||||
'ERR02_bit5': 'P0420 — Catalyst System Low Efficiency',
|
||||
'ERR02_bit6': 'P0401 — EGR Insufficient Flow',
|
||||
'ERR02_bit7': 'P1456 — EVAP Leak (large) Fuel Tank Side',
|
||||
|
||||
// ERR03 (byte 0x34)
|
||||
'ERR03_bit0': 'P1457 — EVAP Leak (large) Canister Side',
|
||||
'ERR03_bit1': 'P0498 — EVAP Canister Vent Shut Valve',
|
||||
'ERR03_bit2': 'P0497 — EVAP Low Purge Flow',
|
||||
'ERR03_bit3': 'P0122 — TPS Sensor Low',
|
||||
'ERR03_bit4': 'P0123 — TPS Sensor High',
|
||||
'ERR03_bit5': 'P0562 — Battery Voltage Low',
|
||||
'ERR03_bit6': 'P0563 — Battery Voltage High',
|
||||
'ERR03_bit7': 'P1607 — PCM Internal Circuit',
|
||||
};
|
||||
|
||||
/// KPro DTC map (ERR00–ERR17, 18 bytes × 8 bits = 144 possible codes)
|
||||
const Map<String, String> kproDtcMap = {
|
||||
// ERR00
|
||||
'ERR00_bit0': 'P0130 — O2 Sensor (front)',
|
||||
'ERR00_bit1': 'P0135 — O2 Sensor Heater (front)',
|
||||
'ERR00_bit2': 'P0505 — Idle Air Control Valve',
|
||||
'ERR00_bit3': 'P0108 — MAP Sensor High',
|
||||
'ERR00_bit4': 'P0107 — MAP Sensor Low',
|
||||
'ERR00_bit5': 'P0113 — IAT Sensor High',
|
||||
'ERR00_bit6': 'P0112 — IAT Sensor Low',
|
||||
'ERR00_bit7': 'P0118 — ECT Sensor High',
|
||||
'ERR00_bit0': 'P0130 — Oxygen Sensor #1 (O2A, code 1)',
|
||||
'ERR00_bit1': 'P0150 — Oxygen Sensor #2 (O2B, code 2)',
|
||||
'ERR00_bit2': 'P0105 — Manifold Absolute Pressure Sensor (MAP, code 3)',
|
||||
'ERR00_bit3': 'P0335 — Crank Position Sensor (CKP, code 4)',
|
||||
'ERR00_bit4': 'P0105 — Manifold Absolute Pressure Sensor (MAP, code 5)',
|
||||
'ERR00_bit5': 'P0106 — Engine Coolant Sensor (ECT, code 6)',
|
||||
'ERR00_bit6': 'P0123 — Throttle Position Sensor (TPS, code 7)',
|
||||
'ERR00_bit7': 'P1362 — Top Dead Center Sensor (TDC, code 8)',
|
||||
|
||||
// ERR01
|
||||
'ERR01_bit0': 'P0117 — ECT Sensor Low',
|
||||
'ERR01_bit1': 'P0336 — CKP Sensor',
|
||||
'ERR01_bit2': 'P0341 — CMP Sensor',
|
||||
'ERR01_bit3': 'P1362 — TDC Sensor (No Signal)',
|
||||
'ERR01_bit4': 'P1363 — TDC Sensor (No Signal 2)',
|
||||
'ERR01_bit5': 'P0335 — CKP Sensor (No Signal)',
|
||||
'ERR01_bit6': 'P1361 — TDC Sensor',
|
||||
'ERR01_bit7': 'P0300 — Random Misfire',
|
||||
'ERR01_bit0': 'P0340 — Cylinder/Cam Sensor (CYL, code 9)',
|
||||
'ERR01_bit1': 'P0113 — Intake Air Temperature Sensor (IAT, code 10)',
|
||||
'ERR01_bit2': 'P0217 — Engine Overheating (OH, code 11)',
|
||||
'ERR01_bit3': 'P0403 — EGR Lift Valve (EGR, code 12)',
|
||||
'ERR01_bit4': 'P1106 — Atmospheric Pressure Sensor (BARO, code 13)',
|
||||
'ERR01_bit5': 'P0505 — Idle Air Control Valve (IAC, code 14)',
|
||||
'ERR01_bit6': 'P0350 — Ignition Control Module (IGM, code 15)',
|
||||
'ERR01_bit7': 'P0200 — Fuel Injectors (INJ, code 16)',
|
||||
|
||||
// ERR02
|
||||
'ERR02_bit0': 'P0301 — Misfire Cylinder 1',
|
||||
'ERR02_bit1': 'P0302 — Misfire Cylinder 2',
|
||||
'ERR02_bit2': 'P0303 — Misfire Cylinder 3',
|
||||
'ERR02_bit3': 'P0304 — Misfire Cylinder 4',
|
||||
'ERR02_bit4': 'P1259 — VTEC System Malfunction',
|
||||
'ERR02_bit5': 'P0420 — Catalyst System Low Efficiency',
|
||||
'ERR02_bit6': 'P0401 — EGR Insufficient Flow',
|
||||
'ERR02_bit7': 'P1456 — EVAP Leak (large) Fuel Tank Side',
|
||||
'ERR02_bit0': 'P0500 — Vehicle Speed Sensor (VSS, code 17)',
|
||||
'ERR02_bit1': 'ERR02.1 — Undocumented code',
|
||||
'ERR02_bit2': 'P0700 — Automatic Transmission Lockup Control Valve (code 19)',
|
||||
'ERR02_bit3': 'P1298 — Electrical Load Detector (ELD, code 20)',
|
||||
'ERR02_bit4': 'P2649 — VTEC Solenoid (VTS, code 21)',
|
||||
'ERR02_bit5': 'P2647 — VTEC Pressure Valve (VTP, code 22)',
|
||||
'ERR02_bit6': 'P0325 — Knock Sensor (code 23)',
|
||||
'ERR02_bit7': 'P1324 — Knock Sensor (code 24)',
|
||||
|
||||
// ERR03
|
||||
'ERR03_bit0': 'P1457 — EVAP Leak (large) Canister Side',
|
||||
'ERR03_bit1': 'P0498 — EVAP Canister Vent Shut Valve',
|
||||
'ERR03_bit2': 'P0497 — EVAP Low Purge Flow',
|
||||
'ERR03_bit3': 'P0122 — TPS Sensor Low',
|
||||
'ERR03_bit4': 'P0123 — TPS Sensor High',
|
||||
'ERR03_bit5': 'P0562 — Battery Voltage Low',
|
||||
'ERR03_bit6': 'P0563 — Battery Voltage High',
|
||||
'ERR03_bit7': 'P1607 — PCM Internal Circuit',
|
||||
'ERR03_bit0': 'P0750 — Automatic Transmission A Signal (ATA, code 30)',
|
||||
'ERR03_bit1': 'P0755 — Automatic Transmission B Signal (ATB, code 31)',
|
||||
'ERR03_bit2': 'P0135 — Primary Oxygen Sensor Heater (PO2H, code 41)',
|
||||
'ERR03_bit3': 'P0135 — Oxygen Sensor Heater',
|
||||
'ERR03_bit4': 'P0169 — Fuel Supply System (code 43)',
|
||||
'ERR03_bit5': 'ERR03.5 — Undocumented code',
|
||||
'ERR03_bit6': 'ERR03.6 — Undocumented code',
|
||||
'ERR03_bit7': 'ERR03.7 — Undocumented code',
|
||||
};
|
||||
|
||||
/// KPro DTC map (ERR00–ERR17 = frame bytes 62–79).
|
||||
const Map<String, String> kproDtcMap = {
|
||||
// ERR00
|
||||
'ERR00_bit0': 'ERR00.0 — Unknown error 0',
|
||||
'ERR00_bit1': 'P1607 — Internal Circuit Malfunction (check calibration type)',
|
||||
'ERR00_bit2': 'P0131 — O2 Sensor Voltage Low',
|
||||
'ERR00_bit3': 'P0132 — O2 Sensor Voltage High',
|
||||
'ERR00_bit4': 'P0107 — MAP Sensor Low Voltage',
|
||||
'ERR00_bit5': 'P0108 — MAP Sensor High Voltage',
|
||||
'ERR00_bit6': 'P0335 — CRK Sensor No Signal',
|
||||
'ERR00_bit7': 'P0336 — CRK Sensor Intermittent Interruption',
|
||||
|
||||
// ERR01
|
||||
'ERR01_bit0': 'P1128 — MAP Sensor Signal Lower Than Expected',
|
||||
'ERR01_bit1': 'P1129 — MAP Sensor Signal Higher Than Expected',
|
||||
'ERR01_bit2': 'P0117 — ECT Sensor Low Voltage',
|
||||
'ERR01_bit3': 'P0118 — ECT Sensor High Voltage',
|
||||
'ERR01_bit4': 'P0122 — TPS Low Voltage',
|
||||
'ERR01_bit5': 'P0123 — TPS High Voltage',
|
||||
'ERR01_bit6': 'P1121 — TPS Signal Lower Than Expected',
|
||||
'ERR01_bit7': 'P1122 — TPS Signal Higher Than Expected',
|
||||
|
||||
// ERR02
|
||||
'ERR02_bit0': 'P0176 — Ethanol Sensor Input Error',
|
||||
'ERR02_bit1': 'ERR02.1 — No description available',
|
||||
'ERR02_bit2': 'ERR02.2 — No description available',
|
||||
'ERR02_bit3': 'ERR02.3 — No description available',
|
||||
'ERR02_bit4': 'P1362 — TDC Sensor No Signal',
|
||||
'ERR02_bit5': 'P1361 — TDC Sensor Intermittent Signal Interruption',
|
||||
'ERR02_bit6': 'P0112 — IAT Sensor Low Voltage',
|
||||
'ERR02_bit7': 'P0113 — IAT Sensor High Voltage',
|
||||
|
||||
// ERR03
|
||||
'ERR03_bit0': 'P1213 — IMA Sensor Voltage Low',
|
||||
'ERR03_bit1': 'P1214 — IMA Sensor Voltage High',
|
||||
'ERR03_bit2': 'ERR03.2 — EGR Lift Sensor Voltage Error',
|
||||
'ERR03_bit3': 'ERR03.3 — EGR F/B Error',
|
||||
'ERR03_bit4': 'P1107 — Barometric Pressure Low Voltage',
|
||||
'ERR03_bit5': 'P1108 — Barometric Pressure High Voltage',
|
||||
'ERR03_bit6': 'P1106 — Barometric Pressure Sensor Range/Performance',
|
||||
'ERR03_bit7': 'ERR03.7 — Unknown error 37',
|
||||
|
||||
// ERR04
|
||||
'ERR04_bit0': 'P0136 — O2 Sensor (rear)',
|
||||
'ERR04_bit1': 'P0141 — O2 Sensor Heater (rear)',
|
||||
'ERR04_bit2': 'P1166 — Air Fuel Ratio (A/F) Sensor Heater',
|
||||
'ERR04_bit3': 'P1167 — Air Fuel Ratio (A/F) Sensor',
|
||||
'ERR04_bit4': 'P2195 — A/F Sensor Signal Stuck Lean',
|
||||
'ERR04_bit5': 'P2196 — A/F Sensor Signal Stuck Rich',
|
||||
'ERR04_bit6': 'P2237 — A/F Sensor Pump Cell Current Input Low',
|
||||
'ERR04_bit7': 'P2240 — A/F Sensor Pump Cell Current Input High',
|
||||
'ERR04_bit0': 'P0505 — Idle Control System Malfunction',
|
||||
'ERR04_bit1': 'P1519 — Idle Air Control Valve Circuit Malfunction',
|
||||
'ERR04_bit2': 'P0500 — VSS Malfunction',
|
||||
'ERR04_bit3': 'ERR04.3 — VSP',
|
||||
'ERR04_bit4': 'P1297 — ELD Circuit Low Voltage',
|
||||
'ERR04_bit5': 'P1298 — ELD Circuit High Voltage',
|
||||
'ERR04_bit6': 'P1253 — VTEC Solenoid Drive Time Abnormality',
|
||||
'ERR04_bit7': 'ERR04.7 — Unknown error 47',
|
||||
|
||||
// ERR05
|
||||
'ERR05_bit0': 'P2243 — A/F Sensor Reference Voltage Low',
|
||||
'ERR05_bit1': 'P2247 — A/F Sensor Reference Voltage High',
|
||||
'ERR05_bit2': 'P2251 — A/F Sensor VS Cell Voltage Low',
|
||||
'ERR05_bit3': 'P2254 — A/F Sensor VS Cell Voltage High',
|
||||
'ERR05_bit4': 'P0031 — O2 Sensor Heater Current Low (bank 1, sensor 1)',
|
||||
'ERR05_bit5': 'P0032 — O2 Sensor Heater Current High (bank 1, sensor 1)',
|
||||
'ERR05_bit6': 'P0037 — O2 Sensor Heater Current Low (bank 1, sensor 2)',
|
||||
'ERR05_bit7': 'P0038 — O2 Sensor Heater Current High (bank 1, sensor 2)',
|
||||
'ERR05_bit0': 'P1259 — VTEC System Malfunction (Oil Pressure Switch)',
|
||||
'ERR05_bit1': 'ERR05.1 — Unknown error 51',
|
||||
'ERR05_bit2': 'P0325 — Knock Sensor Circuit Malfunction',
|
||||
'ERR05_bit3': 'P1324 — Knock Sensor Circuit Failure',
|
||||
'ERR05_bit4': 'P0563 — VBU Voltage High',
|
||||
'ERR05_bit5': 'ERR05.5 — Unknown error 55',
|
||||
'ERR05_bit6': 'ERR05.6 — Unknown error 56',
|
||||
'ERR05_bit7': 'ERR05.7 — Unknown error 57',
|
||||
|
||||
// ERR06
|
||||
'ERR06_bit0': 'P0068 — MAP/MAF vs Throttle Position Correlation',
|
||||
'ERR06_bit1': 'P0101 — MAF Sensor Range/Performance',
|
||||
'ERR06_bit2': 'P0102 — MAF Sensor Low Input',
|
||||
'ERR06_bit3': 'P0103 — MAF Sensor High Input',
|
||||
'ERR06_bit4': 'P0171 — System Lean (bank 1)',
|
||||
'ERR06_bit5': 'P0172 — System Rich (bank 1)',
|
||||
'ERR06_bit6': 'P0174 — System Lean (bank 2)',
|
||||
'ERR06_bit7': 'P0175 — System Rich (bank 2)',
|
||||
'ERR06_bit0': 'P1162 — Air Fuel Ratio Sensor Circuit Malfunction',
|
||||
'ERR06_bit1': 'ERR06.1 — LAF Sensor AFV1 Short',
|
||||
'ERR06_bit2': 'ERR06.2 — LAF Sensor AFC1 Short',
|
||||
'ERR06_bit3': 'ERR06.3 — Unknown error 63',
|
||||
'ERR06_bit4':
|
||||
'ERR06.4 — Daughter Board Communication Error (battery voltage low when cranking)',
|
||||
'ERR06_bit5': 'ERR06.5 — Unknown error 65',
|
||||
'ERR06_bit6':
|
||||
'P0600 — Multiplexer Not Present (for engine swaps disable in misc parameters)',
|
||||
'ERR06_bit7': 'ERR06.7 — Unknown error 67',
|
||||
|
||||
// ERR07
|
||||
'ERR07_bit0': 'P0325 — Knock Sensor',
|
||||
'ERR07_bit1': 'P0330 — Knock Sensor 2',
|
||||
'ERR07_bit2': 'P0339 — CKP Sensor Intermittent',
|
||||
'ERR07_bit3': 'P0344 — CMP Sensor Intermittent',
|
||||
'ERR07_bit4': 'P0365 — CMP Sensor B Circuit',
|
||||
'ERR07_bit5': 'P0390 — CMP Sensor B Circuit (bank 2)',
|
||||
'ERR07_bit6': 'P0498 — EVAP Canister Vent Shut Valve Low',
|
||||
'ERR07_bit7': 'P0499 — EVAP Canister Vent Shut Valve High',
|
||||
'ERR07_bit0': 'P1505 — PCV Negative Pressure',
|
||||
'ERR07_bit1': 'ERR07.1 — Unknown error 71',
|
||||
'ERR07_bit2': 'ERR07.2 — Unknown error 72',
|
||||
'ERR07_bit3': 'ERR07.3 — Idle Valve',
|
||||
'ERR07_bit4': 'P0135 — Primary HO2S Circuit Malfunction',
|
||||
'ERR07_bit5': 'P1166 — Primary HO2S Heater Circuit Malfunction',
|
||||
'ERR07_bit6': 'P1167 — Primary LAF HO2S Heater System Malfunction',
|
||||
'ERR07_bit7': 'P0134 — Air/Fuel Ratio Sensor No Activity Detected',
|
||||
|
||||
// ERR08
|
||||
'ERR08_bit0': 'P0600 — Serial Communication Link',
|
||||
'ERR08_bit1': 'P0601 — Internal Control Module Memory',
|
||||
'ERR08_bit2': 'P0604 — Internal Control Module RAM',
|
||||
'ERR08_bit3': 'P0605 — Internal Control Module ROM',
|
||||
'ERR08_bit4': 'P0657 — Actuator Supply Voltage A Open',
|
||||
'ERR08_bit5': 'P0685 — ECM/PCM Power Relay Control Open',
|
||||
'ERR08_bit6': 'P0691 — Fan 1 Control Circuit Low',
|
||||
'ERR08_bit7': 'P0692 — Fan 1 Control Circuit High',
|
||||
'ERR08_bit0': 'P0172 — Fuel System Too Rich',
|
||||
'ERR08_bit1': 'P0171 — Fuel System Too Lean',
|
||||
'ERR08_bit2': 'P1162 — Air/Fuel Ratio (A/F) Sensor Slow Response',
|
||||
'ERR08_bit3': 'ERR08.3 — Unknown error 83',
|
||||
'ERR08_bit4': 'P0010 — VTC Oil Control Solenoid Valve Malfunction',
|
||||
'ERR08_bit5': 'P0011 — VTC System Malfunction',
|
||||
'ERR08_bit6': 'P0340 — CMP Sensor No Signal',
|
||||
'ERR08_bit7': 'P0344 — CMP Sensor Intermittent Interruption',
|
||||
|
||||
// ERR09
|
||||
'ERR09_bit0': 'P0693 — Fan 2 Control Circuit Low',
|
||||
'ERR09_bit1': 'P0694 — Fan 2 Control Circuit High',
|
||||
'ERR09_bit2': 'P1454 — EVAP Pressure Sensor Range/Performance',
|
||||
'ERR09_bit3': 'P1455 — EVAP Leak (small)',
|
||||
'ERR09_bit4': 'P1508 — IAC Valve Circuit Low',
|
||||
'ERR09_bit5': 'P1509 — IAC Valve Circuit High',
|
||||
'ERR09_bit6': 'P1519 — Idle Air Control Valve Stuck',
|
||||
'ERR09_bit7': 'P1706 — A/T Range Switch Out Of Range',
|
||||
'ERR09_bit0': 'P0341 — Variable Valve Timing (VTC) Phase Gap',
|
||||
'ERR09_bit1': 'ERR09.1 — Unknown error 91',
|
||||
'ERR09_bit2': 'ERR09.2 — Undocumented code',
|
||||
'ERR09_bit3': 'P1163 — Air Fuel Ratio Sensor Slow Response',
|
||||
'ERR09_bit4': 'P1164 — Air Fuel Ratio Sensor Range/Performance Problem',
|
||||
'ERR09_bit5': 'ERR09.5 — Undocumented code',
|
||||
'ERR09_bit6': 'P0137 — Secondary O2 Circuit Low Voltage',
|
||||
'ERR09_bit7': 'P0138 — Secondary O2 Circuit High Voltage',
|
||||
|
||||
// ERR10
|
||||
'ERR10_bit0': 'P2101 — Throttle Actuator Control Motor Range',
|
||||
'ERR10_bit1': 'P2118 — Throttle Actuator Control Motor Current Range',
|
||||
'ERR10_bit2': 'P2119 — Throttle Actuator Control Throttle Body Range',
|
||||
'ERR10_bit3': 'P2122 — Throttle/Pedal Position Sensor D Low Input',
|
||||
'ERR10_bit4': 'P2123 — Throttle/Pedal Position Sensor D High Input',
|
||||
'ERR10_bit5': 'P2127 — Throttle/Pedal Position Sensor E Low Input',
|
||||
'ERR10_bit6': 'P2128 — Throttle/Pedal Position Sensor E High Input',
|
||||
'ERR10_bit7': 'P2135 — Throttle/Pedal Position Sensor A/B Voltage Correlation',
|
||||
'ERR10_bit0': 'P0139 — Secondary O2 Circuit Slow Response',
|
||||
'ERR10_bit1': 'ERR10.1 — Unknown error 101',
|
||||
'ERR10_bit2': 'P0141 — Secondary O2 Circuit Heater Circuit Malfunction',
|
||||
'ERR10_bit3': 'ERR10.3 — Unknown error 103',
|
||||
'ERR10_bit4': 'P0420 — Catalyst System Efficiency Below Threshold',
|
||||
'ERR10_bit5': 'ERR10.5 — Catalyst / Secondary O2 Sensor',
|
||||
'ERR10_bit6': 'ERR10.6 — Unknown error 106',
|
||||
'ERR10_bit7': 'ERR10.7 — Unknown error 107',
|
||||
|
||||
// ERR11
|
||||
'ERR11_bit0': 'P2138 — Throttle/Pedal Position Sensor D/E Voltage Correlation',
|
||||
'ERR11_bit1': 'P2176 — Throttle Actuator Control System Idle Position Not Learned',
|
||||
'ERR11_bit2': 'P2227 — Barometric Pressure Sensor A Circuit Range',
|
||||
'ERR11_bit3': 'P2228 — Barometric Pressure Sensor A Circuit Low',
|
||||
'ERR11_bit4': 'P2229 — Barometric Pressure Sensor A Circuit High',
|
||||
'ERR11_bit5': 'P2610 — ECM/PCM Internal Engine Off Timer',
|
||||
'ERR11_bit6': 'P2647 — VTEC System High (bank 1)',
|
||||
'ERR11_bit7': 'P2648 — VTEC System Low (bank 1)',
|
||||
'ERR11_bit0': 'P0301 — Cylinder #1 Misfire',
|
||||
'ERR11_bit1': 'ERR11.1 — Unknown error 111',
|
||||
'ERR11_bit2': 'P0302 — Cylinder #2 Misfire',
|
||||
'ERR11_bit3': 'ERR11.3 — Undocumented code',
|
||||
'ERR11_bit4': 'P0303 — Cylinder #3 Misfire',
|
||||
'ERR11_bit5': 'ERR11.5 — Unknown error 115',
|
||||
'ERR11_bit6': 'P0304 — Cylinder #4 Misfire',
|
||||
'ERR11_bit7': 'ERR11.7 — Unknown error 117',
|
||||
|
||||
// ERR12
|
||||
'ERR12_bit0': 'P2649 — VTEC System High (bank 2)',
|
||||
'ERR12_bit1': 'P2650 — VTEC System Low (bank 2)',
|
||||
'ERR12_bit2': 'P3400 — VTEC System Stuck Off (bank 1)',
|
||||
'ERR12_bit3': 'P3497 — VTEC System Stuck Off (bank 2)',
|
||||
'ERR12_bit4': 'U0073 — Control Module Communication Bus Off',
|
||||
'ERR12_bit5': 'U0100 — Lost Communication With ECM/PCM A',
|
||||
'ERR12_bit6': 'U0155 — Lost Communication With Instrument Panel Cluster',
|
||||
'ERR12_bit7': 'U0164 — Lost Communication With HVAC Control Module',
|
||||
'ERR12_bit0': 'P0300 — Random Misfire',
|
||||
'ERR12_bit1': 'ERR12.1 — Unknown error 121',
|
||||
'ERR12_bit2': 'ERR12.2 — EGR Flow',
|
||||
'ERR12_bit3': 'ERR12.3 — Unknown error 123',
|
||||
'ERR12_bit4': 'P0116 — ECT Sensor Range/Performance Problem',
|
||||
'ERR12_bit5': 'ERR12.5 — Unknown error 125',
|
||||
'ERR12_bit6': 'P0128 — Cooling System Malfunction (Thermostat)',
|
||||
'ERR12_bit7': 'ERR12.7 — VTC Solenoid',
|
||||
|
||||
// ERR13
|
||||
'ERR13_bit0': 'P0011 — Camshaft Position A — Timing Over-Advanced (bank 1)',
|
||||
'ERR13_bit1': 'P0012 — Camshaft Position A — Timing Over-Retarded (bank 1)',
|
||||
'ERR13_bit2': 'P0021 — Camshaft Position B — Timing Over-Advanced (bank 1)',
|
||||
'ERR13_bit3': 'P0022 — Camshaft Position B — Timing Over-Retarded (bank 1)',
|
||||
'ERR13_bit4': 'P0340 — CMP Sensor A Circuit (bank 1)',
|
||||
'ERR13_bit5': 'P0345 — CMP Sensor A Circuit (bank 2)',
|
||||
'ERR13_bit6': 'P0366 — CMP Sensor B Circuit Range/Performance (bank 1)',
|
||||
'ERR13_bit7': 'P0391 — CMP Sensor B Circuit Range/Performance (bank 2)',
|
||||
'ERR13_bit0': 'P1456 — EVAP Control System Leakage (Fuel Tank)',
|
||||
'ERR13_bit1': 'P1457 — EVAP Control System Leakage (Canister System)',
|
||||
'ERR13_bit2': 'P0452 — Fuel Tank Pressure Sensor Low Voltage',
|
||||
'ERR13_bit3': 'P0453 — Fuel Tank Pressure Sensor High Voltage',
|
||||
'ERR13_bit4': 'P0451 — Fuel Tank Pressure Sensor Range/Performance',
|
||||
'ERR13_bit5': 'ERR13.5 — Undocumented code',
|
||||
'ERR13_bit6': 'P0443 — EVAP Purge Valve Circuit',
|
||||
'ERR13_bit7': 'ERR13.7 — Unknown error 137',
|
||||
|
||||
// ERR14
|
||||
'ERR14_bit0': 'P0016 — Crankshaft/Camshaft Position Correlation (bank 1, sensor A)',
|
||||
'ERR14_bit1': 'P0017 — Crankshaft/Camshaft Position Correlation (bank 1, sensor B)',
|
||||
'ERR14_bit2': 'P0018 — Crankshaft/Camshaft Position Correlation (bank 2, sensor A)',
|
||||
'ERR14_bit3': 'P0019 — Crankshaft/Camshaft Position Correlation (bank 2, sensor B)',
|
||||
'ERR14_bit4': 'P0008 — Engine Position System (bank 1)',
|
||||
'ERR14_bit5': 'P0009 — Engine Position System (bank 2)',
|
||||
'ERR14_bit6': 'P0014 — Camshaft Position B — Timing Over-Advanced (bank 1)',
|
||||
'ERR14_bit7': 'P0024 — Camshaft Position B — Timing Over-Advanced (bank 2)',
|
||||
'ERR14_bit0': 'ERR14.0 — PF2 Low',
|
||||
'ERR14_bit1': 'ERR14.1 — PF2 High',
|
||||
'ERR14_bit2': 'ERR14.2 — PF2 Monitor',
|
||||
'ERR14_bit3': 'ERR14.3 — Undocumented code',
|
||||
'ERR14_bit4': 'ERR14.4 — TF2 Low',
|
||||
'ERR14_bit5': 'ERR14.5 — TF2 High',
|
||||
'ERR14_bit6': 'ERR14.6 — PF0 Low',
|
||||
'ERR14_bit7': 'ERR14.7 — PF0 High',
|
||||
|
||||
// ERR15
|
||||
'ERR15_bit0': 'P0087 — Fuel Rail/System Pressure Too Low',
|
||||
'ERR15_bit1': 'P0088 — Fuel Rail/System Pressure Too High',
|
||||
'ERR15_bit2': 'P0089 — Fuel Pressure Regulator Performance',
|
||||
'ERR15_bit3': 'P0090 — Fuel Pressure Regulator Control Circuit',
|
||||
'ERR15_bit4': 'P0091 — Fuel Pressure Regulator Control Circuit Low',
|
||||
'ERR15_bit5': 'P0092 — Fuel Pressure Regulator Control Circuit High',
|
||||
'ERR15_bit6': 'P0201 — Injector Circuit/Open Cylinder 1',
|
||||
'ERR15_bit7': 'P0202 — Injector Circuit/Open Cylinder 2',
|
||||
'ERR15_bit0': 'ERR15.0 — TF0 Low',
|
||||
'ERR15_bit1': 'ERR15.1 — TF0 High',
|
||||
'ERR15_bit2': 'ERR15.2 — 3rd O2 Sensor Voltage Low',
|
||||
'ERR15_bit3': 'ERR15.3 — 3rd O2 Sensor Voltage High',
|
||||
'ERR15_bit4': 'ERR15.4 — 3rd O2 Sensor Response',
|
||||
'ERR15_bit5': 'ERR15.5 — Unknown error 155',
|
||||
'ERR15_bit6': 'ERR15.6 — 3rd O2 Sensor Heater Current Abnormality',
|
||||
'ERR15_bit7': 'ERR15.7 — Unknown error 157',
|
||||
|
||||
// ERR16
|
||||
'ERR16_bit0': 'P0203 — Injector Circuit/Open Cylinder 3',
|
||||
'ERR16_bit1': 'P0204 — Injector Circuit/Open Cylinder 4',
|
||||
'ERR16_bit2': 'P0261 — Injector Circuit Low Cylinder 1',
|
||||
'ERR16_bit3': 'P0264 — Injector Circuit Low Cylinder 2',
|
||||
'ERR16_bit4': 'P0267 — Injector Circuit Low Cylinder 3',
|
||||
'ERR16_bit5': 'P0270 — Injector Circuit Low Cylinder 4',
|
||||
'ERR16_bit6': 'P0262 — Injector Circuit High Cylinder 1',
|
||||
'ERR16_bit7': 'P0265 — Injector Circuit High Cylinder 2',
|
||||
'ERR16_bit0': 'ERR16.0 — NOx Ability Monitor',
|
||||
'ERR16_bit1': 'ERR16.1 — Unknown error 161',
|
||||
'ERR16_bit2':
|
||||
'P1077 — Intake Manifold Runner Control System Malfunction (low rpm)',
|
||||
'ERR16_bit3':
|
||||
'P1078 — Intake Manifold Runner Control System Malfunction (high rpm)',
|
||||
'ERR16_bit4': 'P0661 — Intake Manifold Runner Control Low Voltage',
|
||||
'ERR16_bit5': 'P0662 — Intake Manifold Runner Control High Voltage',
|
||||
'ERR16_bit6': 'ERR16.6 — P1 Switch Abnormality',
|
||||
'ERR16_bit7': 'ERR16.7 — Unknown error 167',
|
||||
|
||||
// ERR17
|
||||
'ERR17_bit0': 'P0268 — Injector Circuit High Cylinder 3',
|
||||
'ERR17_bit1': 'P0271 — Injector Circuit High Cylinder 4',
|
||||
'ERR17_bit2': 'P0351 — Ignition Coil A Primary/Secondary Circuit',
|
||||
'ERR17_bit3': 'P0352 — Ignition Coil B Primary/Secondary Circuit',
|
||||
'ERR17_bit4': 'P0353 — Ignition Coil C Primary/Secondary Circuit',
|
||||
'ERR17_bit5': 'P0354 — Ignition Coil D Primary/Secondary Circuit',
|
||||
'ERR17_bit6': 'P0627 — Fuel Pump Control Circuit Open',
|
||||
'ERR17_bit7': 'P0628 — Fuel Pump Control Circuit Low',
|
||||
'ERR17_bit0': 'P0219 — Engine Over-Rev',
|
||||
'ERR17_bit1': 'P0217 — Engine Over-Heating',
|
||||
'ERR17_bit2': 'ERR17.2 — Undocumented code',
|
||||
'ERR17_bit3': 'ERR17.3 — Undocumented code',
|
||||
'ERR17_bit4': 'ERR17.4 — Undocumented code',
|
||||
'ERR17_bit5': 'ERR17.5 — Undocumented code',
|
||||
'ERR17_bit6': 'ERR17.6 — Undocumented code',
|
||||
'ERR17_bit7': 'ERR17.7 — Undocumented code',
|
||||
};
|
||||
|
||||
/// Returns a list of active DTC descriptions from the given raw error bytes
|
||||
|
||||
@ -149,6 +149,14 @@ class BtNotifier extends StateNotifier<BtState> {
|
||||
Future<void> connect(BluetoothDevice device) async {
|
||||
if (state.isConnecting) return; // ignore double taps
|
||||
final session = ++_session;
|
||||
// The adapter's name says which ECU it is wired to; a stale saved
|
||||
// setting for the other ECU makes every request go unanswered.
|
||||
final inferred = ecuTypeFromDeviceName(device.name);
|
||||
if (inferred != null && inferred != _ref.read(settingsProvider).ecuType) {
|
||||
AppLog.i('ECU protocol set to ${inferred.name} from adapter name '
|
||||
'"${device.name}"');
|
||||
_ref.read(settingsProvider.notifier).setEcuType(inferred);
|
||||
}
|
||||
_device = device;
|
||||
_userDisconnected = false;
|
||||
_resetCounters();
|
||||
@ -369,19 +377,93 @@ class BtNotifier extends StateNotifier<BtState> {
|
||||
);
|
||||
}
|
||||
|
||||
/// DTC reset per hvbt_protocol.pdf: { 0x1B, 0x70, NEG8 }; the adapter echoes
|
||||
/// the same 3 bytes as acknowledgement.
|
||||
Future<({bool acknowledged, Uint8List raw})> clearDtcs() async {
|
||||
/// DTC reset per hvbt_protocol.pdf: { 0x1B, 0x70, NEG8 }; the adapter should
|
||||
/// echo the same 3 bytes as acknowledgement.
|
||||
///
|
||||
/// The adapter never sends that ack (confirmed on the bench), so success is
|
||||
/// judged from the data: after sending, polling resumes and the ERR bytes
|
||||
/// of the live frames are watched for [_dtcWatch]. If any code that was
|
||||
/// stored before disappears, the ECU cleared. Codes for faults that are
|
||||
/// still present come straight back (often before the first frame), just
|
||||
/// as with the USB tool, so "all zero" is not required. The ack wait is
|
||||
/// kept short because the adapter stops reading the ECU after ~1 s without
|
||||
/// datalog requests (Bluetooth.pdf §2.4).
|
||||
///
|
||||
/// [codesBefore]/[codesCleared] count stored code bits before the command
|
||||
/// and how many of them were seen cleared.
|
||||
Future<
|
||||
({
|
||||
bool acknowledged,
|
||||
int codesBefore,
|
||||
int codesCleared,
|
||||
Uint8List raw,
|
||||
})> clearDtcs() async {
|
||||
final p = _poller;
|
||||
if (p == null) return (acknowledged: false, raw: Uint8List(0));
|
||||
if (p == null) {
|
||||
return (
|
||||
acknowledged: false,
|
||||
codesBefore: 0,
|
||||
codesCleared: 0,
|
||||
raw: Uint8List(0),
|
||||
);
|
||||
}
|
||||
final ecuType = _ref.read(settingsProvider).ecuType;
|
||||
// ERR00.. bytes: S300 37-40, KPro 62-79 (hvbt_protocol.pdf).
|
||||
List<int> errOf(Uint8List f) =>
|
||||
ecuType == EcuType.s300 ? f.sublist(37, 41) : f.sublist(62, 80);
|
||||
String hex(List<int> b) =>
|
||||
b.map((v) => v.toRadixString(16).padLeft(2, '0')).join(' ');
|
||||
int bits(int v) => v.toRadixString(2).replaceAll('0', '').length;
|
||||
|
||||
final beforeFrame = state.lastFrame;
|
||||
final before = beforeFrame == null ? null : errOf(beforeFrame);
|
||||
final codesBefore = before == null ? 0 : before.fold(0, (n, b) => n + bits(b));
|
||||
AppLog.i('Clear DTC: ERR bytes before = ${before == null ? "?" : hex(before)}');
|
||||
|
||||
// Bits stored before that have been seen clear at least once.
|
||||
final clearedMask = List<int>.filled(before?.length ?? 0, 0);
|
||||
String? lastErr = before == null ? null : hex(before);
|
||||
final watchStart = DateTime.now();
|
||||
final sub = frameStream.listen((f) {
|
||||
final err = errOf(f);
|
||||
final h = hex(err);
|
||||
if (h != lastErr) {
|
||||
final ms = DateTime.now().difference(watchStart).inMilliseconds;
|
||||
AppLog.i('Clear DTC: +$ms ms ERR bytes = $h');
|
||||
lastErr = h;
|
||||
}
|
||||
if (before != null) {
|
||||
for (var i = 0; i < before.length; i++) {
|
||||
clearedMask[i] |= before[i] & ~err[i];
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
final command = Uint8List.fromList([0x1B, 0x70, 0x00]);
|
||||
command[2] = calculateNeg8(Uint8List.fromList([0x1B, 0x70]));
|
||||
final result = await p.sendCommandAwaitReply(command, command);
|
||||
final result = await p.sendCommandAwaitReply(
|
||||
command,
|
||||
command,
|
||||
timeout: const Duration(milliseconds: 600),
|
||||
);
|
||||
await Future<void>.delayed(_dtcWatch);
|
||||
await sub.cancel();
|
||||
|
||||
final codesCleared = clearedMask.fold(0, (n, b) => n + bits(b));
|
||||
AppLog.i('Clear DTC: ack=${result.acknowledged} '
|
||||
'rxBytes=${result.raw.length}');
|
||||
return result;
|
||||
'rxBytes=${result.raw.length} '
|
||||
'codesCleared=$codesCleared/$codesBefore '
|
||||
'ERR bytes after = ${lastErr ?? "?"}');
|
||||
return (
|
||||
acknowledged: result.acknowledged,
|
||||
codesBefore: codesBefore,
|
||||
codesCleared: codesCleared,
|
||||
raw: result.raw,
|
||||
);
|
||||
}
|
||||
|
||||
static const _dtcWatch = Duration(seconds: 5);
|
||||
|
||||
@override
|
||||
void dispose() {
|
||||
_statusTimer?.cancel();
|
||||
|
||||
@ -98,20 +98,29 @@ class _DtcScreenState extends ConsumerState<DtcScreen> {
|
||||
_lastRaw = result.raw;
|
||||
});
|
||||
|
||||
// Success is judged from the live data: the adapter does not send the
|
||||
// ack. Codes for faults that are still present return right away.
|
||||
final String message;
|
||||
if (result.acknowledged) {
|
||||
message = 'Trouble codes cleared';
|
||||
if (result.codesBefore == 0) {
|
||||
message = 'No stored trouble codes to clear';
|
||||
} else if (result.codesCleared > 0) {
|
||||
final cleared = result.codesCleared;
|
||||
final back = result.codesBefore - cleared;
|
||||
message = back == 0
|
||||
? 'Trouble codes cleared'
|
||||
: '$cleared of ${result.codesBefore} codes cleared — $back came '
|
||||
'straight back (active fault, fix the cause first)';
|
||||
} else if (result.acknowledged) {
|
||||
message = 'ECU confirmed the reset, but every code came straight back '
|
||||
'(active faults)';
|
||||
} else if (result.raw.isEmpty) {
|
||||
message = 'No response from ECU — codes may not have cleared';
|
||||
// Can't tell apart from "every fault re-set before the next frame".
|
||||
message = 'No codes cleared — the ECU ignored the reset, or every '
|
||||
'fault is still active';
|
||||
} else {
|
||||
// The scan runs alongside normal polling now, so "not acknowledged"
|
||||
// can mean several seconds' worth of regular datalog traffic with no
|
||||
// ack byte pattern found in it — dumping all of that raw would be
|
||||
// unusable in a snackbar, so just report how much was seen. "View"
|
||||
// opens the full hex to check by hand for anything our narrow 3-byte
|
||||
// pattern match might have missed.
|
||||
message =
|
||||
'No ack seen — ${result.raw.length} bytes of other traffic during the window';
|
||||
// "View" opens the raw reply hex to check by hand.
|
||||
message = 'Unexpected reply (${result.raw.length} bytes) — codes did '
|
||||
'not clear';
|
||||
}
|
||||
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
|
||||
@ -7,16 +7,29 @@ void main() {
|
||||
expect(s300DtcMap.length, equals(32)); // 4 bytes × 8 bits
|
||||
});
|
||||
|
||||
test('P0130 maps to correct description for ERR00 bit0', () {
|
||||
expect(s300DtcMap['ERR00_bit0'], equals('P0130 — O2 Sensor (front)'));
|
||||
// Expected codes come from the S300 "DTC map" in hvbt_protocol.pdf.
|
||||
test('ERR00 bit0 = P0130 (O2A)', () {
|
||||
expect(s300DtcMap['ERR00_bit0'], startsWith('P0130 — '));
|
||||
});
|
||||
|
||||
test('P0505 maps for ERR00 bit2', () {
|
||||
expect(s300DtcMap['ERR00_bit2'], equals('P0505 — Idle Air Control Valve'));
|
||||
test('ERR01 bit5 = P0505 (IAC)', () {
|
||||
expect(s300DtcMap['ERR01_bit5'], startsWith('P0505 — '));
|
||||
});
|
||||
|
||||
test('P1607 maps for ERR03 bit7', () {
|
||||
expect(s300DtcMap['ERR03_bit7'], equals('P1607 — PCM Internal Circuit'));
|
||||
test('bench codes: ERR01.6 = P0350, ERR02.3 = P1298, ERR02.4 = P2649', () {
|
||||
expect(s300DtcMap['ERR01_bit6'], startsWith('P0350 — '));
|
||||
expect(s300DtcMap['ERR02_bit3'], startsWith('P1298 — '));
|
||||
expect(s300DtcMap['ERR02_bit4'], startsWith('P2649 — '));
|
||||
});
|
||||
|
||||
test('undocumented bits show the raw ERR position', () {
|
||||
expect(s300DtcMap['ERR03_bit7'], startsWith('ERR03.7 — '));
|
||||
});
|
||||
|
||||
test('every entry has a code and a description', () {
|
||||
for (final v in [...s300DtcMap.values, ...kproDtcMap.values]) {
|
||||
expect(v.split(' — ').length, equals(2), reason: v);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
@ -26,8 +39,11 @@ void main() {
|
||||
expect(kproDtcMap.length, equals(144));
|
||||
});
|
||||
|
||||
test('P0130 maps for ERR00 bit0', () {
|
||||
expect(kproDtcMap['ERR00_bit0'], equals('P0130 — O2 Sensor (front)'));
|
||||
// Expected codes come from the KPro "DTC map" in hvbt_protocol.pdf.
|
||||
test('ERR00 bit1 = P1607, ERR05 bit0 = P1259, ERR11 bit6 = P0304', () {
|
||||
expect(kproDtcMap['ERR00_bit1'], startsWith('P1607 — '));
|
||||
expect(kproDtcMap['ERR05_bit0'], startsWith('P1259 — '));
|
||||
expect(kproDtcMap['ERR11_bit6'], startsWith('P0304 — '));
|
||||
});
|
||||
|
||||
test('ERR17 entries present', () {
|
||||
@ -44,7 +60,7 @@ void main() {
|
||||
|
||||
test('decodes ERR00 bit0 = P0130', () {
|
||||
final result = decodeDtcs([0x01, 0, 0, 0], s300DtcMap);
|
||||
expect(result, contains('P0130 — O2 Sensor (front)'));
|
||||
expect(result, contains(s300DtcMap['ERR00_bit0']));
|
||||
});
|
||||
|
||||
test('decodes multiple bits in one byte', () {
|
||||
|
||||
22
test/ecu_type_from_name_test.dart
Normal file
22
test/ecu_type_from_name_test.dart
Normal file
@ -0,0 +1,22 @@
|
||||
import 'package:flutter_test/flutter_test.dart';
|
||||
import 'package:hvbt_dash/core/bluetooth/bt_poller.dart';
|
||||
|
||||
void main() {
|
||||
group('ecuTypeFromDeviceName', () {
|
||||
test('real S300 adapter names', () {
|
||||
expect(ecuTypeFromDeviceName('S300[94]-SPP'), EcuType.s300);
|
||||
expect(ecuTypeFromDeviceName('HVS300-SPP[94]'), EcuType.s300);
|
||||
});
|
||||
|
||||
test('KPro names', () {
|
||||
expect(ecuTypeFromDeviceName('HV-KPro-SPP'), EcuType.kpro);
|
||||
expect(ecuTypeFromDeviceName('K-PRO 1234'), EcuType.kpro);
|
||||
});
|
||||
|
||||
test('unknown or missing names leave the setting alone', () {
|
||||
expect(ecuTypeFromDeviceName(null), isNull);
|
||||
expect(ecuTypeFromDeviceName('HC-05'), isNull);
|
||||
expect(ecuTypeFromDeviceName('S300 / KPro'), isNull);
|
||||
});
|
||||
});
|
||||
}
|
||||
Loading…
x
Reference in New Issue
Block a user