BOROSOFTWAREAll work →
scantool/scantool.h 189 lines
4 findings in this fileA13L40A14L62D26L107D25L133
1#ifndef _SCANTOOL_H_
2#define _SCANTOOL_H_
3/*
4 * freediag - Vehicle Diagnostic Utility
5 *
6 *
7 * Copyright (C) 2001 Richard Almeida & Ibex Ltd ([email protected])
8 *
9 * This program is free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 2 of the License, or
12 * (at your option) any later version.
13 *
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
22 *
23 *************************************************************************
24 *
25 *
26 * J1978 Scan tool
27 */
28
29#include <stdint.h>
30#include <stddef.h>
31
32#include "diag.h"
33
34#if defined(__cplusplus)
35extern "C" {
36#endif
37
38
39/* Structure to hold responses */
40typedef struct {
41 uint8_t type;
42 uint8_t len;
43 uint8_t data[7];
44
45} response;
46
47#define TYPE_UNTESTED 0 /* unchecked, prob because ECU doesn't support */
48#define TYPE_FAILED 1 /* Got failure response */
49#define TYPE_GOOD 2 /* Valid info */
50
51/*
52 * This structure holds all the data/config info for a given ecu
53 * - one request can result in more than one ECU responding, and so
54 * the data is stored in this
55 */
56typedef struct {
57 uint8_t valid; /* Valid flag */
58 uint8_t ecu_addr; /* Address */
59
60 uint8_t supress; /* Supress output of data from ECU in monitor mode; not implemented*/
61
62 uint8_t mode1_info[0x100]; /* Pids supported by ECU */
63 uint8_t mode2_info[0x100]; /* Freeze frame version */
64 uint8_t mode5_info[0x100]; /* Mode 5 info */
65 uint8_t mode6_info[0x100]; /* Mode 6 info */
66 uint8_t mode8_info[0x100]; /* Mode 8 info */
67 uint8_t mode9_info[0x100]; /* Mode 9 info */
68
69 uint8_t data_good; /* Flags for above data */
70
71 uint8_t O2_sensors; /* O2 sensors bit mask */
72
73 response mode1_data[256]; /* Response data for all responses */
74 response mode2_data[256]; /* Same, but for freeze frame */
75
76 struct diag_msg *rxmsg; /* Received message */
77} ecu_data;
78
79#define ECU_DATA_PIDS 0x01
80#define ECU_DATA_MODE2 0x02
81#define ECU_DATA_MODE5 0x04
82#define ECU_DATA_MODE6 0x08
83#define ECU_DATA_MODE8 0x10
84#define ECU_DATA_MODE9 0x20
85
86#define MAX_ECU 8 /* Max 8 Ecus responding */
87extern ecu_data ecu_info[MAX_ECU];
88extern unsigned int ecu_count;
89
90struct diag_l2_conn;
91struct diag_l3_conn;
92
93/** Send a SAE J1979 request, get a response, and partially process it
94 *
95 * J1979 messages are 7 data bytes long: mode(SID) byte + max 6 extra bytes
96 * (J1979 5.3.2; table 8)
97 * @return 0 if ok
98 */
99int l3_do_j1979_rqst(struct diag_l3_conn *d_conn, uint8_t mode, uint8_t p1, uint8_t p2,
100 uint8_t p3, uint8_t p4, uint8_t p5, uint8_t p6, void *handle);
101
102/*
103 * Send some data on the connection
104 */
105int l3_do_send( struct diag_l3_conn *d_conn, void *data, size_t len, void *handle);
106int l2_do_send( struct diag_l2_conn *d_conn, void *data, size_t len, void *handle);
107int l2_check_pid_bits(uint8_t *data, int pid);
108int do_l2_9141_start(int destaddr); // 9141 init
109int do_l2_14230_start(int init_type); //14230 init
110int do_j1979_getdtcs(void);
111int do_j1979_getO2sensors(void);
112int diag_cleardtc(void);
113int ecu_connect(void);
114
115struct diag_msg *find_ecu_msg(int byte, databyte_type val);
116
117/*
118 * Handle values for above (l3_do_j1979_rqst, j1979_data_rcv, etc)
119 * XXX This was extremely irregular: they were passed as void pointers.
120 * Now they are rather declared as const ints so we can pass
121 * pointers to that instead of masquerading ints as void pointers.
122 */
123#define RQST_HANDLE_NORMAL 0 /* Normal mode */
124#define RQST_HANDLE_WATCH 1 /* Watching, add timestamp */
125#define RQST_HANDLE_DECODE 2 /* Just decode what arrived */
126#define RQST_HANDLE_NCMS 3 /* Non cont. mon. tests */
127#define RQST_HANDLE_NCMS2 4 /* Ditto, print fails only */
128#define RQST_HANDLE_O2S 5 /* O2 sensor tests */
129#define RQST_HANDLE_READINESS 6 /* Readiness Tests */
130extern const int _RQST_HANDLE_NORMAL; //Normal mode
131extern const int _RQST_HANDLE_WATCH; //Watching; add timestamp
132extern const int _RQST_HANDLE_DECODE; //Just decode what arrived
133extern const int _RQST_HANDLE_NCMS; //Non cont. mon. tests
134extern const int _RQST_HANDLE_NCMS2; //Ditto; print fails only
135extern const int _RQST_HANDLE_O2S; //O2 sensor tests
136extern const int _RQST_HANDLE_READINESS; //Readiness tests
137
138int do_j1979_getdata(int interruptible_flag);
139void do_j1979_basics(void);
140void do_j1979_cms(void);
141void do_j1979_ncms(int);
142void do_j1979_getpids(void);
143void do_j1979_O2tests(void);
144void do_j1979_getO2tests(int O2sensor);
145
146/*
147 * Receive callback routines for various L3/L2 types
148 */
149void j1979_data_rcv(void *handle, struct diag_msg *msg);
150void j1979_watch_rcv(void *handle, struct diag_msg *msg);
151void l2raw_data_rcv(void *handle, struct diag_msg *msg);
152
153
154
155/** J1979 PID structures + utils **/
156struct pid;
157/* format <numbytes> bytes of data into buf, up to <maxlen> chars. */
158typedef void (formatter)(char *buf, int maxlen, int units, const struct pid *, response *, int numbytes);
159
160struct pid {
161 int pidID;
162 const char *desc;
163 formatter *cust_snprintf;
164 int bytes;
165 const char *fmt1; // SI
166 double scale1;
167 double offset1;
168 const char *fmt2; // English (typically)
169 double scale2;
170 double offset2;
171};
172
173#define DATA_VALID(p, d) (d[p->pidID].type == TYPE_GOOD)
174#define DATA_1(p, n, d) (d[p->pidID].data[n]) /* extract 8bit value @offset n */
175#define DATA_2(p, n, d) (DATA_1(p, n, d) * 256 + DATA_1(p, n+1, d)) /* extract 16bit value @offset n */
176#define DATA_RAW(p, n, d) (p->bytes == 1 ? DATA_1(p, n, d) : DATA_2(p, n, d))
177
178#define DATA_SCALED(p, v) (v * p->scale1 + p->offset1)
179#define DATA_ENGLISH(p, v) (v * p->scale2 + p->offset2)
180
181
182const struct pid *get_pid ( unsigned int i );
183
184
185#if defined(__cplusplus)
186}
187#endif
188#endif /* _SCANTOOL_H_ */
189