Surprise! An ELM327 cable can read the Volvo 850 vehicle mileage, the Service Reminder counters, their counter limits that determine when the Service light illuminates, and it can read some other data maintained by the Instrument Panel (otherwise known as the Instrument Cluster, or the COMBI).
The contention that the ELM327 can read the Volvo 850 mileage and the Service Reminder counters / limits contradicted the conventional wisdom at Matthew's Volvo site and all other Volvo forums that I had seen as late as 2013-04-30 (when this page was created).
To help you test if you can read your Volvo 850's mileage with an ELM327, I've included: a list of the hardware and software requirements, some links to help in getting the ELM327 setup properly, and, most importantly, the AT commands and KWPD3B0 (request-generating) commands that need to be sent to the ELM327, the responses which were generated on my 1997 Volvo 850 T5, and detailed explanations of those responses.
Note:
The COMBI will sometimes be referred to as ECU 51 on this page.
(A list of other Volvo 850 ECUs' hexadecimal #s is available
here).
The following were used to read the data shown on this page:
1997 Volvo 850 T5 OBDII port.
It's known that the method shown on this page has worked for at least one Volvo in each of the following categories:
It's not yet known if the method shown on this current page works for these Volvos:
The method probably works for most all the USA 1996-1997 850 that have a VDO cluster. It might work for some of the USA 1995 850 with an OBDII port (though this USA 1995 850 NA wagon w/ Motronic 4.3, manufactured 1995-03, could not read the mileage, but it could perform OBDII emission diagnostics). Furthermore, the method on this page probably works for some of the non-USA 1995+ 850 that have an OBDII port (though those non-USA cars probably will not be able to perform much, if any, OBDII emission diagnostics).
Some of the 00-padded (KWPD3B0-oriented) commands on this page are known to not work for the 1998 V70 & XC70 models. Consequently, a separate, but similar, page has been created which contains some extra details and should work equally well both for the 1996-1997 850 and the 1998 S70/V70/C70/XC70.
If you have a 1998 S70 / V70 / C70 / XC70, or if you simply want to use the same set of instructions for all the 1996-1998 Volvo 850 / S70 / V70 / C70 / XC70, then click here.~$18 ELM327 clone cable (v1.4 or higher).
My guess is that many ELM327 (v1.2 or higher) based devices will now work -- especially those that are based on the real (non-clone) ELM327 chip from Elm Electronics -- since (as of 2019-07-20) the commands on this page now use ATSR 13 as the preferred alternative to ATRA 13.
ScanTool.net OBDLink SX (USB), OBDLink LX (Bluetooth), OBDLink MX (Bluetooth), and OBDLink MX+ (Bluetooth for Windows/Android/iOS) devices -- with the latest firmware -- are also known to work quite well. As long as they have the latest firmware, (with respect to 850 communication) they appear to operate like ELM327 v1.4 or higher, even though they respond to ATI as "ELM327 v1.3a".
See ATTA, ATSR (or ATRA), and ATSI below for some other notes relating to ELM327 versions >= v1.2 and < v1.4.
Free, downloadable Silicon Labs CP210x VCP driver for use with ELM327 USB cable.
I've used CP210x_VCP_Win_XP_S2K3_Vista_7.exe (version v6.5.3) on WinXP, and I've used CP210x_VCP_Windows.zip (version v6.6.1) on both WinXP and Win7.
See Setup -- where "STEP 1" is mentioned -- for links to download the latest Silicon Labs CP210x VCP drivers for Windows, Linux, Mac, etc.
You may need to use different driver(s), eg, FTDI, Prolific, etc. That Setup page may help in locating them.
Free WinXP Hyperterminal program.
Free WinXP / Win7 / Win8 / Win8.1 / Win10
Realterm v2.0.0.70
(original
or
signed) program.
Probably any good terminal emulator would work. For example, if you don't like Realterm for some reason, you could try the very easy-to-use STNterm [search for "stnterm" on that page]. STNterm is known to work on WinXP thru Win10. On Android, you might try the OBD Now Terminal app or the Bluetooth USB WIFI Terminal app, either of which is adequate for issuing single commands one at a time.
See the jonesrh, Elm Electronics, Hyperterminal equivalent, and Wikipedia links included here for other terminal emulators on various platforms.
Hints:
If you don't have the above items, you'll have to improvise.
***IMPORTANT***
For example, the answer provided to the
Volvo 850 OBDII FAQ
question
"How to detect fake ELM327 devices that can not talk
KWPD3B0?" may help to avoid buying an ultra-cheap ELM327
device which can not read the '96-'97 Volvo 850 mileage,
and which can not perform other KWPD3B0 communication!
You can also check
these hints
for using mikeri's milageread (on Windows)
or applagapp's "ELM327 Identifier" app (on Android)
to verify your ELM327 tool's ability
to communicate via the Volvo special KWPD3B0 protocol.
Everything after this section assumes: a) that you already have the ELM327 operational enough to successfully perform an ISO9141-2 style Slow Init connection, and b) that you have a terminal emulator setup properly. If you already know your ELM327 can perform an ISO9141-2 connect with your Volvo 850, and you already know a terminal emulator is setup properly, then you can skip to the next section on Read COMBI data.
Otherwise, now is the time to first explore one or more of the following resources before trying to connect and read the vehicle mileage:
The first thing to get operational is your ability to talk to the ELM327. A serial terminal emulator can be used to do this. Terminal emulators work both with the USA Volvo 850s that have OBDII emission diagnostics and with the European Volvo 850s that do not provide OBDII emission diagnostics. You can use the terminal emulator links included here to find a suitable one.
Note:
For some ELM327-compatible devices,
you can even perform this initial connection test to the ELM327
without the ELM327 being connected to the car. That's the case
for ELM327-compatibles that use a USB serial interface.
Using a terminal emulator, issue the following five (5) ELM327 commands, each on a separate line: ATZ, ATL1, ATE1, ATI, ATIIA 51.
Once you:
then:
you've at least got your ELM327 talking with your smart phone / tablet / laptop / etc.
If the "ATIIA 51" command responded exactly the same as the "ATI" command, then you can not use the instructions on this page to retrieve the mileage, since your ELM327 device is incapable of communicating with the Volvo special KWPD3B0 protocol necessary to read the vehicle mileage and to further communicate with the COMBI, SRS, ABS, etc. This page will be of no use to you while using a KWPD3B0-incapable pseudo-ELM327 !!!
Warning:
Some purported ELM327 devices are
incapable of KWPD3B0 communication!!!
See the
Volvo 850 OBDII FAQ
question "How to detect fake ELM327 devices
that can not talk KWPD3B0?" to help avoid buying
a device which can not read the
'96-'97 Volvo 850 mileage,
and which can not perform other KWPD3B0 communication.
However, if the "ATIIA 51" command responded with "OK", then:
you've verified that the most important ELM327 command necessary to communicate with a Volvo 850 using the KWPD3B0 protocol does indeed work. Most likely it'll be OK to continue further on this page and attempt to communicate with the COMBI. [To perform a more complete check, see the FAQ question mentioned in the Warning above or see this.]
Once you get the ATZ, ATL1, ATE1, ATI, and ATIIA 51 working, if you have an 850 which can not handle OBDII emission diagnostics (eg, a European Volvo 850 with an ECM which does not handle OBDII emission diagnostics), then jump to the next section on Read COMBI data.
If you have not yet connected via any OBDII diagnostic software and you have a USA 850 which has an J1962 OBDII port, you can still check if the ISO9141-2 style Slow Init connection can be established before jumping to the next section. Just use the terminal emulator to issue these 6 commands to the ELM327: ATZ, ATL1, ATE1, 0100, 0100, 03 -- each on a separate line. Check if the 0100, 0101, and 03 OBDII commands and their responses appear similar to the following example when there were 0 emission diagnostic DTCs and the headers/checksums display was turned off:
or similar to the following example for a vehicle that also had a Secondary Air system and which had 5 misfire oriented DTCs: P1310, P0304, P0303, P0305, and P0300, as well as the Check Engine Light (CEL) on. The 0100 command's 4100 response is shown both without and with headers (and checksums).
If that is not the case -- ie, you can not initialize
successfully (eg, you get "BUS INIT...ERROR" responses), and/or
you can not get the 0100, 0101, and 03 commands
to generate responses that are formatted somewhat similar
to one of the above examples
(where responses to 0100 and 0101 begin with 41 or 48), and
if you know your car has OBDII emission diagnostic
capability -- then you might need to:
a) reseat your ELM327 connector into the car's J1962 OBDII port,
b) review your ELM327 driver setup,
c) turn on your ignition,
d) do some more web research, and/or
e) ask some questions in the
MVS 850... forum or some other Volvo forum.
Or you could always just continue to the next section and see what happens.
A list follows of the commands to read the 850 mileage (using B90300). It is what you would use immediately after plugging in all the cables (or after your ELM327 seemed to lock up or otherwise seem to be unresponsive or behaving unexpectedly).
>ATZ
>ATL1
>ATE1
>ATSP 3 (might be necessary to establish ISO 9141-2 as default)
>ATH1
>ATAL
>ATKW0
>ATSR 13 <<< Remember to use this or "ATRA 13"! <<<
>ATIIA 51
>ATWM 82 51 13 A1
>ATSI (optional)
>ATSH 84 51 13
>B90300
Another, even shorter, way involves: stopping any existing communication via ATPC [the ECUs will stop communicating in a little over 5 seconds], performing a less involved init sequence, then reading the mileage. This shorter sequence (shown below) is oftentimes all that's necessary when the ATZ thru ATSI sequence above has already been used to successfully establish communication with one of the ECUs via the keyword D3 B0 protocol (as is done when reading each ECU's DTCs, etc. in succession).
>ATPC >ATIIA 51 >ATWM 82 51 13 A1 >ATSI (optional) >ATSH 84 51 13 >B90300
A more extended list follows of the minimum to read the 850 ECU 51 DTCs (using AE0100) and all ECU 51 B9 data (using B9xx00). Keep in mind the same as above applies to this list also -- ie, ATPC can replace the ATZ thru ATSR 13 commands if all 8 of those commands had been successfully issued previously and are still in effect.
>ATZ
>ATL1
>ATE1
>ATSP 3 (might be necessary to establish ISO 9141-2 as default)
>ATH1
>ATAL
>ATKW0
>ATSR 13 <<< Remember to use this or "ATRA 13"! <<<
>ATIIA 51
>ATWM 82 51 13 A1
>ATSI (optional)
>ATSH 84 51 13
>AE0100
>B90100
>B90300
>B90400
>B90500
>B90600
>B90700
>B90800
>B90900
>B90A00
>B90B00
>B90C00
>B90D00
>B90E00
>B9F000
Details of all that just-displayed 850 example's listed commands and their responses are now described (with extra ATI, ATDP, ATBD, ATKW, and ATPC commands thrown in for good measure):
>------ This looks like a good ISO9141-2 style slow initialization, where the ELM327 interprets the entire exchange as the following 6 byte message: * proper ECU: 51 (sent by ELM327 at 5 baud) * proper sync byte: 55 (sent by ECU 51 at 10400 baud) * proper keywords: D3 B0 ( " " " ) * B0 complement: 4F (sent by ELM327 at 10400 baud) * 51 complement: AE (sent by ECU 51 at 10400 baud) >------ followed several seconds later by a "82 51 13 A1 87" keepalive request sent by ELM327 as tester 13 to ECU 51. >------ NOTE: For ScanTool.net OBDLink SX/LX/MX/MX+ devices, it's useless to use ATBD commands, since they always respond: 00 00 00 00 00 00 00 00 00 00 00 00 00.
>------ ECU 51 B9 data recorded at: 2013-04-20 19:32. ------ B903 = 34 30, ie, 3034 hex = 12340, which implies mileage of 12340 * 10 = 123400. This is 123400 - 121820 = 1580 miles (2543 km) since the last reading on 2013-01-18. ------ Changes from last ECU 51 B9 readings on 2013-01-18 09:48 are: B903 -- (3034 - 2F96) hex = 9E hex = +158, implies 1580 miles (2543 km). B906 -- (3AE3 - 3971) hex = 172 hex = +370, implies 92 days 12 hours. B908 -- (0D75 - 0D19) hex = 5C hex = +92 engine hours. B903 matches well with actual values. B906 matches extremely well with actual values. B908 is plausible.
We'll go down through each of the commands and responses in the just-shown, detailed 850 (00-padded) COMBI commands/responses example, paying particular attention to each of the B9xx data values (returned in the F9xx response), and explaining what I've been able to infer about them. In the process, we'll see:
the typical way to setup the ELM327 to communicate via the Volvo keyword D3 B0 protocol (KWPD3B0),
the COMBI's DTCs,
the mileage (which does not include any mileage "lost" when the ABS module was failing),
the Service Reminder counters and limits, and
possible interpretations of the remaining B9xx data.
The first 3 commands are ATZ, ATL1, and ATE1 to reinitialize the ELM327, to turn on linefeeds, and to turn on echo. The ATZ output that identifies the ELM327 version will get garbled until the ATL1 is issued. So don't be surprised.
Note:
I didn't display the ATZ output and ATL1 output above as it actually
appears on the Hyperterminal display. If you want to see that,
refer to the
Volvo 850 OBDII FAQ question:
How do I read emission diagnostics DTCs by manually issued commands to the ELM327?,
in its Steps 1-6.
Hint #1:
ATL1 and ATE1 work well for me with Hyperterminal or with
volvo850diag / Realterm v2.0.0.70.
However, some terminal emulators or
programs work better with ATL0 and/or ATE0.
For example, STNterm works better with ATE0.
Experiment to see what works best for your situation,
then adapt the ATL1 and ATE1 commands in the command list so that
your resultant display looks like the ELM327 AT commands,
KWPD3B0 commands, and their responses shown on this page.
The ATI simply documents the ELM327 version if you couldn't see it properly from the ATZ command.
The ATSP 3 (or ATSP 3A or ATSP A3) command will establish ISO 9141-2 as the default protocol. If the 'A' is included before or after the '3', then the default protocol will be set to AUTO, ISO 9141-2, and the ELM327 will fallback to "AUTO" if the attempt to connect via "ISO 9141-2" fails. It is probably wise to issue ATSP 3 at least once when you first start using your ELM327 device. Afterwards, because the ELM327 is good at remembering what protocol connected successfully, it may only be necessary to issue the ATSP command after you have used the ELM327 to connect to a vehicle which uses a different protocol than "ISO 9141-2".
The ATDP command documents the current protocol. During a lot of my testing, the protocol was forced to be ISO 9141-2, so that there was no confusion whatsoever which protocol was being used. However, things seem to also work well if the protocol is set to AUTO, ISO 9141-2. The ATDP command is included here simply to remind you that -- if the value is not either "ISO 9141-2" or "AUTO, ISO 9141-2", then things might not work as described here, and you'll likely need to issue ATSP 3 (or ATSP 3A).
Some other values for ATDP work partially, if they include AUTO, but I don't recommend use of any of them for the '96-'97 850, since they don't work anywhere near as well as the "ISO 9141-2" or "AUTO, ISO 9141-2" mentioned in the previous 2 paragraphs.
The ATH1 turns on headers/checksum display. I very strongly suggest displaying the headers when using non-emissions diagnostics communication between the ELM327 and the Volvo 850. There's several important things that you can not see if you don't display the headers. Consequently, the documentation on this site will almost always include those headers and checksums (at least for the non-emissions diagnostics using the Volvo special KWPD3B0 protocol).
The ATAL command relaxes the testing for message lengths. Normal OBDII protocols restrict the number of data bytes to 7. In other words, in those protocols up to 7 bytes are allowed after the header and before the checksum. When ATAL is used, the ELM327 will allow up to 8 data bytes when sending and an unlimited number of data bytes when receiving. Use of ATAL is necessary for viewing a wide variety of responses sent back from the Volvo 850 using the Volvo keyword D3 B0 protocol (KWPD3B0). For the '96-'97 850, I strongly suggest always using ATAL when doing KWPD3B0-based diagnostics, and recommend never using ATAL when doing standard OBDII emissions diagnostics.
The ATKW0 command disables the keyword checking when performing the ISO 9141-2 protocol initiation. This is necessary when using the Volvo keyword D3 B0 protocol for non-emissions diagnostics, since the ELM327 knows nothing about those Volvo special keywords: D3 B0. They are not part of any standard (that the ELM327 knows about).
The ATTA 13 command changes the tester address. A tester address of 13 has successfully been used with all the 850 ECUs mentioned in the Volvo 850 keyword D3 B0 protocol ECU list (including the Immobilizer). Tester address 13 is the one used by Vol-FCR, and it's the same one used by both rkam and Brick-Diag.
On 2016-11-14, Adam Goldman enlightened me:
"I think the ATTA command to the ELM is not necessary...
Since the settings made by ATTA end up being overridden anyway with ATSH
and ATWM, you can skip the ATTA and do only ATSH, ATWM and ATSR/ATRA.
This would probably be of most interest to those on ELM v1.2/1.3 where
ATPP to set the tester address would thus be unnecessary."
My testing of skipping ATTA 13 and only doing ATSR (or ATRA), ATWM, and ATSH reveals his contention is true.
In volvo850diag v0.9 -- to simplify instructions so they are applicable to all ELM327 compatible devices from ELM327 v1.2 onwards -- both the ATTA 13 command (and its cumbersome ATPP 06 alternative) were eliminated entirely, and ATSR 13 became the default way that volvo850diag sets the Receive Address.The ATSR 13 (or ATRA 13) command manually sets the receive address, thereby turning off the ELM327's AR (Automatically set the Receive address) mode. This is a very important, essential command which forces the ELM327 to only accept responses addressed to 13.
The ATSR 13 (or ATRA 13) command is only used by KWPD3B0 communication, eg, to the Volvo's COMBI, ABS, SRS, Automatic Transmission, Power Seats, Motronic 4.4, etc. It should definitely not be used for OBDII emission diagnostics. When the ATZ is issued preceding OBDII emission diagnostics, it will erase the effect of ATSR 13 (or ATRA 13) and revert the ELM327 back to AR mode, as if an ATAR command had been issued.
History:
I only discovered ATRA 13 in late 2013-10, a year after discovering
how to perform KWPD3B0 communication via the ELM327.
So there's examples here and there on the web that don't display
this in the command list. But rest assured,
KWPD3B0 communication works much better when using ATRA 13
(or ATSR 13) --
especially while scanning ABS (ECU 01) and AW 50-42 (ECU 6E)
with ELM327 clone devices.
Important Mandatory
Requirement for ELM327 v1.2 and
v1.2a owners:
If your ELM327 does not have the ATRA command because it is a
v1.2 or v1.2a, then you
**must**
use "ATSR 13" instead of "ATRA 13".
ATRA and ATSR are synonymous commands.
ATTA 13 and ATRA 13 have been replaced with the single
ATSR 13
command:
On 2019-07-20,
this page was changed to list ATSR 13 (instead of ATRA 13)
as the preferred command to set the Selective Receive Address,
since ATSR 13 applies to a larger set of ELM327 chips.
At the same time, the ATTA 13 command was eliminated
from the command lists.
The ATIIA 51 command sets the Slow Init address to 51 (to override the default of 33 which the ISO 9141-2 spec requires for the OBDII emission diagnostics).
Warning:
The proper response to an ATIIA 51 command is: OK.
If the ATIIA 51 command does not respond with OK
-- eg,
if the ATIIA 51 command responds the same as the ATI command --
then you have an old or fake ELM327 which can not
perform KWPD3B0 communication !!!
The ATWM 82 51 13 A1 command overrides the default settings for the Wakeup Message (aka "periodic idle", aka "Keepalive", aka "watchdog message"). The message sent will be "82 51 13 A1 cs", where "cs" is the automatically generated checksum.
These Wakeup (Keepalive) messages are by default sent every 3 seconds, but you can change that with the ATSW command. For example ATSW CC changes the interval to roughly 4 seconds.
I've experimented with the ATWM message and discovered you can use ATWM 83 51 13 A1 00 or ATWM 84 51 13 A1 00 00 to accomplish the same "periodic idle" purpose for 1996-1997 Volvo 850. But I don't suggest doing that, unless you are forced to for some reason. Those longer formats do not work with the 1998 V70, XC70, etc.
The ATSI command will manually start a Slow Initialization.
Originally, I thought it might be safer to begin the ISO 9141-2 Slow Initialization manually, rather than having the initialization automatically triggered when the first data request is sent, since:
However, as the following note explains, it is possible to bypass this command successfully.
Note for ELM327 v1.2 or v1.3 owners
(and anyone wanting to bypass the ATSI):
If your ELM327 doesn't have the ATSI command because it is a v1.2 or
v1.3, then you ought to be able to simply delete the ATSI command,
the two optional ATBD commands, and the optional ATKW command from
the procedures and follow the remainder of the procedures as is.
That would effectively issue
the ATSH command for the initial post-initialization command
before initialization is performed. You'll just have to
experiment with having a sufficient delay both before and after
the first command which will cause the implicit Slow Init in order to
get the "non-ATSI" approach to work consistently.
That approach is used with the
"Read All DTCs", "Quick Scan All ECUs", "Full Scan All ECUs",
"My Extra Scans", and ECU xx "Read DTCs" buttons in
volvo850diag,
and it works very successfully.
I wouldn't worry about any possible "incongruities"
just mentioned.
In fact, bypassing the ATSI command is now my preferred approach. I just let the ELM327 perform the Slow Init when it thinks that it should.
Because ATSI and the following ATBD and ATKW commands sometimes can come in handy for debugging connection problems, they are still listed here for completeness.
The two ATBD commands and the ATKW command which follow the ATSI are all three optional.
The 1st ATBD command is issued immediately after seeing the "BUS INIT: ...OK" response from the ATSI command, so that it can capture the "51 55 D3 B0 4F AE" sequence. The main thing I look for is the ECU address, 51 in this case, and the D3 B0 keyword bytes. But this is actually a standard ISO 9141-2 initialization response, other than the keywords used aren't mentioned in any ISO literature.
The 2nd ATBD command is issued about 4-5 seconds later, after the first Wakeup Message (ie, Keepalive) has been sent. The ATBD buffer should then contain: a 1-byte length of the immediately following Wakeup Message and checksum, the Wakeup Message specified by the ATWM command, the automatically generated checksum, and several bytes of garbage.
Neither ATBD command should be issued if you're using a ScanTool.net OBDLink device, since those devices just respond with a meaningless string of 00s. For OBDLink devices, you have to use the ATKW command to verify the keywords are D3 B0.
The "------" comments were added by me then later edited to be more readable. That's the standard way that I document what I'm doing while using the ELM327. Of course, you do not need to enter the comments when you're duplicating the sequences.
Those "------" comments are a good introductory explanation of the ISO9141-2 init sequence.
The ATKW command clearly shows the keywords. It is optional and is useful when you want to check the keywords, yet: a) the ATBD command (after an ATSI) was issued too late and didn't show the D3 B0 keywords, or b) the ELM327 compatible device -- eg, OBDLink SX, OBDLink LX, OBDLink MX, OBDLink MX+, etc -- does not have a useful ATBD command.
The ATSH 84 51 13 command sets up the proper header for KWPD3B0 requests that will have 3 bytes sandwiched after the header and before the checksum. The way to interpret this header (and all other Volvo keyword D3 B0 protocol request headers that I've seen used in 850 ECUs) is:
84 is equivalent to 4 bytes, so when using this "84 51 13" header, 3 bytes of data must always be specified by the user (when sending the KWPD3B0 command to the ELM327). The "ATSH 84 51 13" command must precede KWPD3B0 commands that consist of 6 hex digits -- eg, AE0100, B90300, B9F000, A50701.
The "ATSH 83 51 13" command must precede KWPD3B0 commands that consist of 4 hex digits, ie, those that involve 2 bytes (between header and checksum).
The "ATSH 82 51 13" command must precede KWPD3B0 commands that consist of 2 hex digits, ie, those that involve 1 byte (between header and checksum).
The "ATSH 87 51 13" command must precede KWPD3B0 commands that consist of 12 hex digits, ie, those that involve 6 bytes (between header and checksum).
You get the idea.
Once a header is manually setup via an ATSH command, it remains in effect until another ATSH is issued, or the ELM327 is reset (via ATZ, ATD, ATWS, or power down).
The AE0100 command is one convenient way to retrieve the ECU 51 DTCs from 850s using the ELM327 (*even if* ATSR 13 or ATRA 13 is not used). The use of the 3-byte AE0100 somehow triggers the Volvo 850 ECU 51 and/or the ELM327 to communicate in a manner where the ELM327 can automatically tie the AE0100 command with its response and obviate the need to use a subsequent ATBD command to see the response (or part of the response).
The AE0100 command actually generates a KWPD3B0 request represented by "84 51 13 AE 01 00 cs", where "cs" is the automatically generated checksum. As you can see the "84 51 13" is the header that we specified with the ATSH command, and the "AE 01 00" is the AE0100 command that we just specified.
The "84 13 51 EE 01 05 DC" response to the AE0100 command (in our example above) is interpreted as follows:
However, if our response to the AE0100 command had been "83 13 51 EE 01 D6", then we would have interpreted it as:
And what does that mean? You guessed it -- ECU 51 (COMBI) has 0 DTCs!
There's 0 DTCs after the EE 01 and before the checksum.
The B9xx00 commands retrieve what's considered the COMBI data that encompasses the vehicle mileage, the counters and limits associated with illuminating the Service light (to remind about getting the oil changed), and miscellaneous other parameters.
Each ECU 51 B9xx00 command actually generates a KWPD3B0 request represented by "84 51 13 B9 xx 00 cs", where "xx" = 01, 03, 04, ..., 0D, 0E, or F0, and where "cs" is the automatically generated checksum. As you can see the "84 51 13" is the header that we specified with the ATSH command, and the "B9 xx 00" comes from the B9xx00 command sent to the ELM327.
Their F9xx positive ack responses all have similar patterns:
Each of the specific B9xx00 command descriptions below will only focus on their responses' 6th thru last-1 bytes.
To get a rough preview of my present understanding of the COMBI's B9 values, check out jonesrh's ECU 51 B9 Meaning of Values raw notes, and consider leaving the raw notes open while reading the rest of this page. Sometimes those notes contain more info than this page.
The B90100 command retrieves the 1 byte: A4 (hex) = 164 (decimal):
>B90100 84 13 51 F9 01 A4 86
This value has never changed for me. At first I thought it might be the "Ländercode" (ie, Country Code) which is displayed on the Brick-Diag Kombi-Parameter screen. If so, then 164 = USA. However, several other USA 850 owners have submitted a different value for this: 24 (hex) = 36 (decimal), so my original Country Code guess may be incorrect.
Some examples are included in the more generic "ELM327 Reads Volvo 850 and SVC70 Mileage" page's B901 section.
The B90300 command retrieves 2 bytes which represent the vehicle mileage. The lower order byte consistently increments once every 10 miles (~16.1 km), *IF* your ABS is sending the speed signal correctly. The ABS can actually be faulty for other reasons, but if it consistently delivers a valid speed signal, then this B903 value will increment (very close to or exactly) once every 10 miles.
As you recall the B90300 command and its response were:
>B90300 85 13 51 F9 03 34 30 49
The way to calculate the mileage from the 2 bytes in the B90300 request's F903 response are as follows:
Get the two bytes after the "F9 03" and before the checksum. In our example, that is "34 30". Remember those are hex values.
Swap those two bytes. In our example, that becomes 3034 hex.
Convert the hex to decimal, then multiply by 10. In our case we have: 3034 hex = 12340 decimal, and 12340 * 10 = 123400. That represents 123400 miles.
Convert to kilometers by multiplying by 1.609344 km/mile. In our case we have: 123400 miles * 1.609344 km/mile = 198593 km.
So 123400 miles (198593 km) is the Vehicle Mileage (minus any lost mileage).
If you have some reasonable idea of the mileage "lost" due to ABS failure, then you can add that to the above figure. For example, in my case, I've kept meticulous records of precisely how many gallons of gas have been added to my car since I bought it. I can also come up with what I think is an "accurate enough for my purposes" Average MPG, since I had periodically calculated that off and on when I went from near empty to near full tanks of gas. After multiplying the Average MPG and the # of gallons, I concluded 10100 was a good estimate of my lost miles. So in our example, adding 123400 + 10100 = 133500 should be a good estimate of the vehicle mileage when planning for maintenance purposes, and for informing anyone that might buy the car eventually.
Mileage Calculation Hint #1:
To save some time in doing the mileage calculation, I've included
a page which can do the calculation for you:
Volvo 850 V70 keyword D3 B0 protocol interpreter.
You can even paste the contents of an entire ELM327 diagnostic session
into the interpreter's
Paste Volvo 850/SVC70 communication here box
and see what the interpreter can glean from the session.
I think you'll find it useful.
But remember the complete response -- with headers and checksum --
must be included for (almost all) responses from
ECU 51 and the other ECUs, and the responses must be left-aligned
(almost always),
else the interpreter will not be able to parse those ECUs' responses.
Mileage Calculation Hint #2:
Alternatively, you might try using the Google Sheets
Volvo 850 Mileage Converter
(that I think was developed by the author of the
Reading Mileage from a 1997 Volvo 850R blog at potatofi.com).
You change the values in "Block 6" and "Block 7" to match
those bytes in the ECU 51 F903 response, then observe the miles and
km in the "Block 6" column on the purple colored lines 7 and 8.
The B90400 command retrieves 2 bytes which represent the vehicle mileage at last Service Light Reset. Its units are 10 miles (~16.1 km), just like those for the response to B90300.
As you recall the B90400 command and its response were:
>B90400 85 13 51 F9 04 24 19 23
The way to calculate the mileage from the 2 bytes in the B90400 request's F904 response is similar to the way it is done for the B903/F903 mileage:
Get the two bytes after the "F9 04" and before the checksum. In our example, that is "24 19". Remember those are hex values.
Swap those two bytes. In our example, that becomes 1924 hex.
Convert the hex to decimal, then multiply by 10. In our case we have: 1924 hex = 6436 decimal, and 6436 * 10 = 64360. That represents 64360 miles.
Convert to kilometers by multiplying by 1.609344 km/mile. In our case we have: 64360 miles * 1.609344 km/mile = 103577 km.
So 64360 miles (103577 km) is the Vehicle Mileage (minus any lost mileage) when the last Service Light Reset was performed.
Jump to the next section on B90500 to see how the COMBI uses the B904 Mileage at (last) Service Light Reset when evaluating if the Service light should be illuminated.
The previous remainder of this section -- which contained specifics of my car which helped show a Service Light Reset had been performed over 10 years in the past, and helped show my car probably still had the original cluster -- have been deleted from this page. If you're interested in those nitty gritty details, click here.
The B90500 command retrieves 1 byte which is (as of 2015-12-28) thought to always equal:
The B905 value is thought to always be in km/500 (for all cars worldwide), regardless whether the instrument panel displays mileage as miles or km).
As you recall the example's B90500 command and response were:
>B90500 84 13 51 F9 05 10 F6
The way to calculate the Service Reminder Interval in Kilometers from the 1 byte in the B90500 request's F905 response is:
Get the one byte after the "F9 05" and before the checksum. In our example, that is "10". Remember that's a hex value.
Convert the hex to decimal, then multiply by 500. In our case we have: 10 hex = 16 decimal, and 16 * 500 = 8000.
So 8000 is the Service Reminder Interval in Kilometers.
Taking that a step further, we can calculate the Service Reminder Interval in Miles:
Divide the result in step 2 by the exact value 1.609344.
In our case the result is: 8000 / 1.609344 = 4971.
So 4971 is the Service Reminder Interval in Miles.
[Alternatively, you could have multipled the result in step 2 by the "close enough" approximation 0.6213712. For example, 8000 km * 0.6213712 km/mile = 4971 miles.]
My 1997 Volvo 850 Owner's Manual says on p2:5 concerning the Service reminder indicator intervals:
"This light will come on at 10,000 mile (16,000 km) intervals*,
after 750 hours of driving or after 12 months, whichever occurs
first...
* Turbo-charged model intervals: 5,000 miles
(8,000 km), 500 hours of driving or after 12 months,
whichever occurs first."
The way the COMBI evaluates the Mileage since Last Service Light Reset and compares to its corresponding limit is thought to be: simply compare the Mileage since Last Service Reset virtual counter (ie, B903 - B904) vs. the Service Reminder Interval limit (B905), after applying appropriate multipliers -- a) regardless what the "lost mileage" value in B90A is, and b) regardless if the instrument cluster (and/or Trip Computer if any) displays mileage as miles or km, and c) using the observation that B905 is a multiple of 500 km...
(B903 - B904) * 10 miles >= B905 * (500 / 1.609344) miles
(B903 - B904) * 16.09344 km >= B905 * 500 km
B903 is thought to increment every 10.0 mile = 16.09344 km (precisely).
B905 = Multiple of 500 km when SRI Mileage Limit is triggered.
The SERVICE light apparently works independently of any "lost mileage" that might be recorded one way or another in B90A.
This approach uses one single SRI Mileage comparison formula for all '96-'97 850 worldwide. Its Comparison #1 form is more useful if you measure in miles. Its Comparison #2 form is more useful if you measure in kilometers. Both forms are identical in predicting / detecting when the SERVICE light comes on. That box does a good (though not perfect, within-a-few-miles) job of predicting when the SERVICE light is illuminated.
The B90600 command retrieves 2 bytes which mean the exact # of 6 hour periods since last Service Light Reset.
As you recall the example's B90600 command and response were:
>B90600 85 13 51 F9 06 E3 3A 05
The way to calculate the 1/4 Days since Service Light Reset from the 2 bytes in the B90600 request's F906 response is:
Get the two bytes after the "F9 06" and before the checksum. In our example, that is "E3 3A". Remember those are hex values.
Swap those two bytes. In our example, that becomes 3AE3 hex.
Convert the hex to decimal. In our case we have: 3AE3 hex = 15075 decimal.
So there's been 15075 * 1/4 days = 3768.75 days since the last Service Light Reset.
The example's B9xx data was recorded 2013-04-20 19:32. The car's CarFax shows the last "Oil and filter changed" service on 2002-12-26. Assuming there are 365.25 days per year, 3768.75 days / 365.25 = 10.318 years. Roughly speaking that should be about 10 years + 4 months - ~1 week in the past. The 2002-12-26 date is within a day of that calculation. Amazing!
You could also do the backtracking by counting exactly how many days occurred in each month and year until you exhaust your 1/4 day counter. The results should be very close to the same.
The B90700 command retrieves 2 bytes which equal the Service Reminder Interval in exact # of 6 hour periods.
If you divide this value by 4, you'll get the precise # of calendar days since Last Service Light Reset (accurate to within 1/4 day) at which time the Service light will illuminate again due to this calendar time interval having transpired.
Most software will display this interval in Months, where it is (inaccurately, but close enough) assumed that each month has 30 days.
The example's B90700 command and response were:
>B90700 85 13 51 F9 07 A0 05 8E
The way to calculate the Service Reminder Interval in 1/4 Days from the 2 bytes in the B90700 request's F907 response is:
Get the two bytes after the "F9 07" and before the checksum. In our example, that is "A0 05". Remember those are hex values.
Swap those two bytes. In our example, that becomes 05A0 hex.
Convert the hex to decimal. In our case we have: 05A0 hex = 1440 decimal.
Since the 1440 can be factored into 12 * 30 * 4, and can plausibly be interpreted as:
it is probably true that if the Service light were to illuminate due to the 12 month interval transpiring, it would actually do so 5-6 days early each year (since the 1440 6-hour periods equates to 360 days instead of the typical year's 365 days or the leap year's 366 days).
The way the COMBI evaluates the 1/4 Days since Last Service Light Reset counter vs. its corresponding limit is simply...
If B906 >= B907, then illuminate the Service light.
Note that once again, the design principle of conceptual integrity seems to have kicked in. Both B906 and B907 have to do with the number of 1/4 days, so they are grouped together.
The B90800 command retrieves 2 bytes which equal Engine Hours since Service Light Reset.
I kept an accurate record of "engine on" minutes over a several week period and can attest that this B908 data reflects Engine Hours, plus or minus an hour or two, when measured over a period of several days to several weeks. Further testing just before and just after an SRI Reset reveals those hours are indeed Engine Hours since Service Light Reset. That's consistent with the fact that "Engine Hours since Service Light Reset" is one of the parameters which can trigger the Service light to be illuminated (according to the Volvo 850 Owner's Manual).
The example's B90800 command and response were:
>B90800 85 13 51 F9 08 75 0D 6C
The way to calculate Engine Hours since Service Light Reset from the 2 bytes in the B90800 request's F908 response is:
Get the two bytes after the "F9 08" and before the checksum. In our example, that is "75 0D". Remember those are hex values.
Swap those two bytes. In our example, that becomes 0D75 hex.
Convert the hex to decimal. In our case we have: 0D75 hex = 3445 decimal.
So there's been 3445 "engine on" hours since the last Service Light Reset.
The B90900 command retrieves 2 bytes which equal the Service Reminder Interval for Engine Hours. On my car, this value had always equaled 500 (until I experimented with reprogramming it).
The example's B90900 command and response were:
>B90900 85 13 51 F9 09 F4 01 E0
The way to calculate Service Reminder Interval in Engine Hours from the 2 bytes in the B90900 request's F909 response is:
Get the two bytes after the "F9 09" and before the checksum. In our example, that is "F4 01". Remember those are hex values.
Swap those two bytes. In our example, that becomes 01F4 hex.
Convert the hex to decimal. In our case we have: 01F4 hex = 500 decimal.
So 500 hours is the Service Reminder Interval Engine Hours limit.
The Volvo 850 Owner's Manual says, per the Service reminder indicator intervals quote listed in the B90500 section, that a Turbo's Service Reminder Interval is 500 hours of "driving". The Brick-Diag "Kombi-Service" screen snapshot says "Motorbetrieb (h)", ie, Engine Operation Hours, can be 1000, 750, or 500. So I'm guessing that the "driving" comment in the Volvo Owner's Manual really means Engine Hours. It probably just means the hours the engine is turned on, and therefore even includes the engine hours when you sit idling for very long periods of time.
The way the COMBI evaluates the Engine Hours since Service Light Reset counter vs. its corresponding limit is simply...
If B908 >= B909, then illuminate the Service light.
Note that once again, the design principle of conceptual integrity has kicked in. Both B908 and B909 deal with the same subject, Engine Hours, so they are grouped together.
The B90A00 command retrieves 2 bytes which are believed to be what Brick-Diag Free v0.0.6.6, the Volvo Scan Tool (VST), and the OTP Volvo 850 Service Manuals DVD calls "Manipulation".
The OTP Volvo 850 Service Manuals DVD (OTP-TP-51956) document "Combined Instrument, VDO 850 1996-" (TP-3801032), says on p28, p150, p151, and p153 -- all 4 pages merged together -- that the "Manipulation of speedometer" parameter indicates in hours how long the Vehicle Speed Signal (VSS) to the COMBI has been disabled while the car was being driven. Apparently, the "RPM > 1500 rpm, Engine Coolant > 50 C (122 F)" constraint (mentioned on p95 for the "CI-221 Vehicle Speed Signal Missing" DTC) must be satisfied before the Manipulation hours is incremented.
The Volvo 850 VDO cluster's "Manipulation hours" is further believed to indirectly approximate -- one way or another -- the "lost" mileage from when the ABS module was not supplying the Vehicle Speed Sensor (VSS) signal.
The example's B90A00 command and response were:
>B90A00 85 13 51 F9 0A 22 00 0E
The way to calculate a value from the 2 bytes in the B90A00 request's F90A response is:
Get the two bytes after the "F9 0A" and before the checksum. In our example, that is "22 00". Remember those are hex values.
Swap those two bytes. In our example, that becomes 0022 hex.
Convert the hex to decimal. In our case we have: 0022 hex = 34 decimal.
If your B90A value (returned in the F90A response) = 0, then you can skip the remainder of this B90A00 section, and jump directly to B90B00.
But if your B90A value is >= 1, you might want to read further...
To be honest, the correct way to estimate lost mileage from B90A is not really understood! This section merely mentions two guesses (along with a couple of links for a more detailed explanation and to explore some alternative ideas).
Approach #1 - B90A-derived hours * Avg MPH or Avg Km/h
The only way I can think of to calculate "lost" mileage from "Manipulation" hours is to multiply the hours derived from B90A by an estimated Average MPH or Average KmPH that applied during the hours that VSS was missing.
In my Volvo 850 T5 case, this "B90A hours * Avg MPH" approach failed miserably to estimate the "lost" mileage. So I explored alternative approaches...
Approach #2 - B90A * 500 km
The idea that best explains my 850's estimated 10100 miles of "lost" mileage is to assume B90A, after converting to decimal, must be multiplied by 500 km (ie, the same units as B905). Surprisingly enough, this calculation agrees with my 10100 miles "lost" mileage estimate -- to within 5% !!! The formula might be stated:
I've never seen ECU 51 B90A increment while the ABS module sends a valid speed signal. The only time I've seen the (1st byte of the) B90A data increment is while a faulty ABS was being used that did not supply a consistent speed signal. It incremented once during the 9-day period, from the time I started measuring B90A data until shortly before I replaced the ABS with another one which did supply a proper speed signal.
Ideas for further exploration:
For more details on the two approaches listed above, see the
B90A section on the correlary, more general purpose page
which handles the '96-'98 850/S70/V70/C70/XC70 together.
For some details on alternative ways to interpret B90A,
see item 0A in
jonesrh's ECU 51 B9 Meaning of Values raw notes.
The B90B00 command retrieves 1 byte which is speculated to be a binary flag, like On/Off or Yes/No.
The example's B90B00 command and response were:
>B90B00 84 13 51 F9 0B FF EB
The way to calculate something meaningful from the 1 byte in the B90B00 request's F90B response is:
Get the one byte after the "F9 0B" and before the checksum. In our example, that is "FF".
Convert the hex to decimal or something else. In our case we have: FF hex = either 255 decimal (if unsigned), or -1 (if signed), or Yes, On, Enabled (if it is a binary flag, with probably 00 hex equating to No, Off, Disabled).
I haven't yet been able to come to a certain conclusion about this B90B data.
At one time I thought B90B was a "Boost Pressure Gauge exists" flag, ie, what is probably the "Ladedruck-Anzeige" on the Brick-Diag Kombi-Parameter screen. My car does have a Turbo gauge in the dash, which is what the Volvo 850 Owner's Manual calls "Boost pressure gauge". It is located between the Fuel Gauge and the Coolant Temperature gauge, but positioned a little higher than those two gauges. The manual states that the Turbo gauge is only for certain turbo-charged models. So its plausible that a flag needs to be maintained by the COMBI computer to remember whether this gauge exists or not.
Since tzanis has a Canada '97 850 GLT which does have B90B = FF, yet his car does not have a Turbo Boost gauge, that blows my "B90B = Boost Pressure Gauge exists" hypothesis out of the water. Back to brainstorming another explanation for B90B.
Again, some other Volvo owners will need to report this info, either with FF or other values for B90B, and they'll need to also report whether they do or don't have the Turbo gauge as shown on the Volvo 850 Owner's Manual p2:2, have VDO vs. Yazaki clusters, and what are the min and max of the tachometer's red range, etc. That way we can develop a clearer understanding of what B90B (and/or some of the other ECU 51 B9xx data) really is.
Got any ideas? Or got any better explanations?
The B90C00 command retrieves 3 bytes which might represent 3 different temperatures.
The example's B90C00 command and response were:
>B90C00 86 13 51 F9 0C 4B 6E 78 20
There are several possible ways to calculate something meaningful from the 3 bytes in the B90C00 request's F90C response are. They are explained in detail at B90C. On the present page we will: a) bypass most of the details included on that more general page which treats B90C info for both 850 and S70/V70/XC70, and b) only mention the one single, simple way that XantheFIN introduced to me -- interpret the B90C data as directly representing Celsius temperatures:
Get the three bytes after the "F9 0B" and before the checksum. In our example, that is "4B 6E 78".
Convert them each individually from hex to decimal. That yields 75, 110, 120.
Assume those directly represent 3 temperatures in Celsius -- 75 C, 110 C, 120 C -- that are possibly used in the algorithm to control the Instrument Panel's Temp gauge.
This is a plausible temperature interpretation, since the values are thought to align fairly well with the temperatures when the Temp needle "almost reaches horizontal", "begins to rise above horizontal", and "reaches (at, near, or in the) red zone".
In our example, the three bytes yield:
The first of those temperatures corresponds to my 850 Temp Gauge's needle being slightly below horizontal -- about a 10-15 degree angle below horizontal. It is speculated that the 2nd and 3rd temps corresponds approximately to the temp at which the Temp needle begins rising above horizontal, and the temp at which the needle reaches the red zone, respectively. I have not tested that speculation about the 2nd and 3rd (supposed) temp values meaning. But it does agree with the OTP Volvo 850 DVD documents that say the normal operating temp is 80 C to 105 C. So you might expect that the Temp Gauge needle begins to rise above horizontal relatively soon after rising above the 105 C top of the normal operating range. It's plausible that 110 C is when the rise starts.
But I'm still not convinced this is the correct interpretation, since the OTP Volvo 850 DVD seems to have nothing that suggests temperature setpoints are a parameter which can be read.
Got any ideas? Or got any better explanations? If B90C is not temperatures, what is it?
The B90D00 command retrieves 1 byte. Its meaning is not known for certain, but probably it is simply a placeholder for the Fuel Level Adjustment available on '98 S70/V70/etc.
The example's B90D00 command and response were:
>B90D00 84 13 51 F9 0D 00 EE
The way to calculate something meaningful from the 1 byte in the B90D00 request's F90D response is:
Get the one byte after the "F9 0D" and before the checksum. In our example, that is "00".
Convert the hex to decimal or something else. In our case we have: 00 hex = either 0 decimal, or No, Off, Disabled, Not Encountered (if it is a binary flag, with probably FF hex equating to Yes, On, Enabled, Encountered).
I toyed with several ideas to explain this B90D data, and have finally come to the conclusion that its value always equaling 00 for the 850 cars simply means that the 850 cars do *not* allow any Fuel Level Adjustment.
For more details on how 850 (and SVC70) ECU 51 B90D is (as of 2017-05-16) interpreted as Fuel Level Adjustment (or lack thereof), see B90D. Also, see item 0D in jonesrh's ECU 51 B9 Meaning of Values raw notes. But keep in mind that it's still not certain that 850 ECU 51 B90D wasn't used for some other purpose besides simply being a dormant Fuel Level Adjustment function that wasn't implemented until the SVC70.
The B90E command retrieves 1 byte which seems be an encoding of Tire Size.
The example's B90E00 command and response were:
>B90E00 84 13 51 F9 0E C3 B2
The way to calculate the Tire Size encoding from the 1 byte in the B90E00 request's F90E response is:
Get the 1 byte after the "F9 0E" and before the checksum. In our example, that is "C3".
Convert the hex to decimal. In our case we have: C3 hex = 195 decimal.
Since "Reifen", ie, tire (size), is listed on the Brick-Diag Kombi-Parameter screen, and since 185, 195, and 205 were three tire widths mentioned in the Wheels and tires section on p5:2 and p5:3 of the Volvo 850 Owner's Manual, you might think that it's safe to conclude that B90E is the Tire Width (in mm).
However, several Volvo owners have submitted values to kwpd3b0_interpreter.html which don't look anything like a tire width in mm. And all 3 tire values: Section Width, Aspect Ratio, and Wheel Diameter -- ie, the 195, 60, 15 of 195/60R15, the 205, 55, 16 of 205/55R16, etc -- have to be used to determine the distance traveled per revolution, not just one of the 3 values. [For some details on those two situations, see the more generic "ELM327 Reads Volvo 850 and SVC70 Mileage" page's B90E section, or see jonesrh's ECU 51 B9 Meaning of Values raw notes item 0E.]
The various Tire Size encoding(s) detailed in the 2 links just listed are still not yet fully understood.
Anybody know how they precisely relate to tire circumference?
Or anybody know how they precisely relate to the Section Width, Aspect Ratio, and Wheel Diameter?
The B9F000 command retrieves 15 bytes which contain the Hardware and Software versions and revisions of the ECU. What I am calling the Hardware version and Software version appears to me to be a Volvo part number, ie, a 7-digit number beginning with 9. Vol-FCR calls them "Module Id" and "Software Code", respectively.
The example's ECU 51 (COMBI) B9F000 command and response were:
>B9F000 92 13 51 F9 F0 00 09 44 23 78 30 30 32 09 44 22 07 30 30 31 60
The way to parse the 15 bytes of data in the B9F000 request's F9F0 response is:
Get the 15 bytes after the "F9 F0" and before the checksum.
In our example, that is:
00 09 44 23 78 30 30 32 09 44 22 07 30 30 31
I don't know what the first 00 byte is, unless it is part of the next field.
The subsequent "09 44 23 78" is strung together as "09442378" and is probably a Volvo part number for the ECU hardware. Normally this number is stamped on the outside of the ECU's container.
The subsequent "30 30 32" is a 3-character ASCII string. In our case, it equals "002". This is the hardware revision #.
The subsequent "09 44 22 07" is strung together as "09442207" and is probably a Volvo part number for the ECU's software. I believe this number is also stamped on the outside of the ECU's container.
The subsequent "30 30 31" is a 3-character ASCII string. In our example here, it equals "001". This is the software revision #.
The ATPC performs a Protocol Close to cease any existing communication channels between the ELM327 and the Volvo. This is the easiest way to stop the ELM327 from sending any more automatic A1 (Keepalive) messages.
Issuing the ATPC (almost) negates the need to send an A0 (Stop Communication) message (like Vol-FCR and Brick-Diag Free v0.0.6.6 do). The A0 is superior in that it will immediately cause the ECU to terminate the connection. Whereas the ATPC will simply cause the ELM327 to stop sending the Keepalive messages, so it may take as much as 5+ seconds for the comm link to actually be severed by the ECU, depending on when the last Keepalive had been sent by the ELM327.
The ELM327 parameters seem to retain their values after an ATPC, so that any immediately subsequent init (of either this same ECU or any of the other ECUs that communicate via KWPD3B0) only have to use the proper ECU-specific ATIIA and ATWM commands before either:
issuing an ATSI command to explicitly perform the ISO9141-2 Slow Init, then following that with the appropriate ECU-specific, next-KWPD3B0-request-specific ATSH command before issuing other KWPD3B0 (request generating) commands; or
issuing the proper ATSH command and a KWPD3B0 (request generating) command (eg, AE0100 or B90300 or B9F000) to implicitly trigger the ISO9141-2 Slow Init, before issuing other KWPD3B0 (request generating) commands.
Here's some useful external references:
ELM327 data sheet (for one of the latest versions of the ELM327). It's both a user manual and a development guide.
ELM327 v2.3 data sheet (for the chip that became available in 2020-05).
ELM327 v1.4b data sheet. This is the data sheet on Elm Electronics' data sheet page which (probably) most closely matches a typical ELM327 v1.5 clone.
ELM327L v2.3 Now Available.
ELM Electronics' OBD chip products overview page.
One of these pages will likely mention the latest ELM327 chip
(ELM327 v2.3 or newer).
Here's two useful internal references with some info that's not documented anywhere else:
Volvo 850 OBDII FAQ.
Got a question? Maybe its answered here.
It's worth a quick review.
ELM327 Commands to Scan a Volvo 850.
This contains elm327_volvo_850_scan_all.txt,
a very extensive list of the ELM327 commands to do a thorough
scan of the Volvo 850 -- much more thorough than the COMBI
oriented list on this page. It's certainly thorough enough for
most DIYers purposes. The commands are listed in the typical order
that I would type (or send) them. This is also well worth a
quick review, or maybe even a very long study!
Once you've generated an ELM327 log from all or portions of this command list along with the Volvo 850's responses, you can paste the contents of that log into the KWPD3B0 interpreter's Paste Volvo 850/SVC70 communication here box, then press the Interpret button, to glean some of what the log recorded.
Here's a tool to help you semi-automatically scan the Volvo 850:
volvo850diag.zip,
ie, volvo850diag to be run on your "local" machine.
The "local" version of volvo850diag
uses an ELM327, Realterm (v2.0.0.70 only),
Internet Explorer (IE8 on WinXP, IE11 on Win7/Win8.1/Win10),
and Javascript to communicate with a
'96-'97 Volvo 850. The contents of
its automatically generated log can also be pasted into the
Volvo 850 V70 keyword D3 B0 protocol interpreter
to make some sense out of the hex mumbo-jumbo.
Here's links to info on 2 programs that can both read the 850 mileage and automatically display it:
mikeri's milageread -- either .py source or Windows .exe.
xiaotec "850 OBD-II" -- Android app (available on Google Play).
See Volvo 850 Diagnostic Links for additional reference links.