PowerBroker2 / ELMduino

Arduino OBD-II Bluetooth Scanner Interface Library for Car Hacking Projects
MIT License
655 stars 124 forks source link

ESP32 wrong values #70

Closed MikolasFromm closed 3 years ago

MikolasFromm commented 3 years ago

Currently using the basic ELM327 with ESP32 TTGO 1.14 inches display.

After I connected to the ELM327 via my phone (after succesful ESP32 connection), I couldn't connect the ESP32 back to the ELM327. That changed when I used the example from BluetoothSerial.h library "bt_remove_paired_devices". After all paired devices has been removed, ESP could connect again.

Now to the problem. When I now print the values - myELM327.kph() and myELM327.engineLoad(), there are non-sence = speed is statically 210, even when car is not moving and the "engineload" is about 8235 %.

Code is taken from your example, only the TFT_eSPI library has been used for printing the values.

Thanks.

PowerBroker2 commented 3 years ago

Use the latest version of the library and enable the class's debugging mode. This will enable highly detailed debugging prints over USB. After you test with debugging mode enabled, post both the code you're using AND the debugging printouts

MikolasFromm commented 3 years ago

UPDATE: Since I can reach my car at the earliest at the morning, I will at least give a bit more of some information.

Firstly, here is the original code.


#include <BluetoothSerial.h>
#include <ELMduino.h>

#include <TFT_eSPI.h>
#include <User_Setup_Select.h>
#include <User_Setup.h>

TFT_eSPI tft = TFT_eSPI();

BluetoothSerial SerialBT;

#define ELM_PORT SerialBT
#define DEBUG_PORT Serial

ELM327 myELM327;

uint32_t kph = 0;
uint32_t engine = 0;

uint8_t address[6] = {0x00, 0x00, 0x00, 0x33, 0x33, 0x33};

void setup()
{
  tft.init();
  tft.setRotation(1);

  // INTRO

  tft.setTextDatum(MC_DATUM);
  tft.fillScreen(TFT_BLACK);
  tft.setTextSize(2);
  tft.setTextColor(TFT_WHITE, TFT_BLACK);
  tft.drawString("Skoda Octavia II", 120, 30, 1);
  tft.setTextColor(TFT_WHITE, TFT_RED);
  tft.drawString("Fasten your", 120, 80, 1);
  tft.drawString("seatbelt, please!", 120, 95, 1);

  DEBUG_PORT.begin(38400);
  ELM_PORT.begin("ESP32", true);
  ELM_PORT.setPin("1234");

  if (!ELM_PORT.connect(address))
  {

    DEBUG_PORT.println("Couldn't connect to OBD scanner - Phase 1");
    while (1);
  }

  if (!myELM327.begin(ELM_PORT, true, 2000))
  {
    Serial.println("Couldn't connect to OBD scanner - Phase 2");
    while (1);
  }

  //CONFIRMATION

  Serial.println("Connected to ELM327");
  tft.fillScreen(TFT_BLACK);
  tft.setTextColor(TFT_BLACK, TFT_GREEN);
  tft.setTextSize(4);
  tft.drawString("CONNECTED", 120, 66, 1);
  delay(3500);
  tft.fillScreen(TFT_BLACK);
}

void loop()
{
  float tempKPH = myELM327.kph();
  float tempENGINE = myELM327.engineLoad();

  if (myELM327.status == ELM_SUCCESS) {

    kph = (uint32_t)tempKPH;
    engine = (uint32_t)tempENGINE;

    tft.setTextColor(TFT_WHITE, TFT_BLACK);

    tft.setTextSize(5);
    tft.setTextDatum(BR_DATUM);
    tft.setTextPadding(tft.textWidth("120", 1));
    tft.drawString(String(tempKPH), 130, 50, 1);

    tft.setTextSize(3);
    tft.setTextDatum(BL_DATUM);
    tft.drawString("km/h", 140, 50, 1);

    if (engine < 50) {
      tft.setTextColor(TFT_GREEN, TFT_BLACK);
    }

    if (engine > 70) {
      tft.setTextColor(TFT_YELLOW, TFT_BLACK);
    }

    if (engine > 90) {
      tft.setTextColor(TFT_RED, TFT_BLACK);
    }

    tft.setTextDatum(MC_DATUM);
    tft.setTextSize(3);
    tft.setTextPadding(tft.textWidth("150", 1));
    tft.drawString(String(tempENGINE), 100, 105, 1);

    tft.setTextDatum(ML_DATUM);
    tft.setTextSize(3);
    tft.drawString("%", 150, 105, 1);
  }
}

I should mention, that exactly this code was running well before the "reconnection" with my Android phone happend.

There are only two things I have spotted in these misterious conditions:

  1. Both values are somehow relatable to the real-time data. If I speed-up, even the value goes higher, but way to higher. (20 kph -> 19246 or whatever wierd number)
  2. In serial monitor, connection beginns (first line of the monitor, only once at the very beginning) with "ASSERT_WARN(2 16), in lc_task.c at line 8775Clearing input serial buffer". Mentionable also is that exactly this "ASSERT_WARN(2 16), in lc.task.c at line 8775" was a repeatedly displayed in serial monitor when ESP32 was unable to succesfully connect before I solved this connection issue with bt_remove_paired_devices from BluetoothSerial.h library.

And this is the Serial.monitor:

ASSERT_WARN(2 16), in lc_task.c at line 8775Clearing input serial buffer
Sending the following command/query: AT Z
Received char: E
Received char: L
Received char: M
Received char: 3
Received char: 2
Received char: 7
Received char:  
Received char: v
Received char: 2
Received char: .
Received char: 1
Received char: \r
Received char: \n
Received char: >
Delimiter found
All chars received: ELM327v2.1
Clearing input serial buffer
Sending the following command/query: AT E0
Received char: O
Received char: K
Received char: \r
Received char: \n
Received char: >
Delimiter found
All chars received: OK
Clearing input serial buffer
Sending the following command/query: AT S0
Received char: O
Received char: K
Received char: \r
Received char: \n
Received char: >
Delimiter found
All chars received: OK
Clearing input serial buffer
Sending the following command/query: AT AL
Received char: O
Received char: K
Received char: \r
Received char: \n
Received char: >
Delimiter found
All chars received: OK
Clearing input serial buffer
Sending the following command/query: AT TP A0
Received char: O
Received char: K
Received char: \r
Received char: \n
Received char: >
Delimiter found
All chars received: OK
Connected to ELM327
Service: 1
PID: 12
Normal length query detected
Query string: 010C
Clearing input serial buffer
Sending the following command/query: 010C
Received char: S
Received char: E
Received char: A
Received char: R
Received char: C
Received char: H
Received char: I
Received char: N
Received char: G
Received char: .
Received char: .
Received char: .
Received char: \r
Received char: \n
All chars received: SEARCHING...
Timeout detected with overflow of 0ms
Service: 1
PID: 4
Normal length query detected
Query string: 0104
Clearing input serial buffer
Sending the following command/query: 0104
All chars received: 
Timeout detected with overflow of 0ms
Service: 1
PID: 12
Normal length query detected
Query string: 010C
Clearing input serial buffer
Sending the following command/query: 010C
Received char: 8
Received char: 4
Received char: F
Received char: 1
Received char: 1
Received char: 0
Received char: 4
Received char: 1
Received char: 0
Received char: C
Received char: 0
Received char: D
Received char: 5
Received char: 8
Received char: 3
Received char: 7
Received char: \r
Received char: \n
Received char: \r
Received char: \n
Received char: >
Delimiter found
All chars received: 84F110410C0D5837
Expected response header: 410C
Single response detected
64-bit response: responseByte_0: 55
responseByte_1: 88
responseByte_2: 13
responseByte_3: 0
responseByte_4: 0
responseByte_5: 0
responseByte_6: 0
responseByte_7: 0
Service: 1
PID: 4
Normal length query detected
Query string: 0104
Clearing input serial buffer
Sending the following command/query: 0104
Received char: 8
Received char: 3
Received char: F
Received char: 1
Received char: 1
Received char: 0
Received char: 4
Received char: 1
Received char: 0
Received char: 4
Received char: 3
Received char: F
Received char: 0
Received char: 8
Received char: \r
Received char: \n
Received char: \r
Received char: \n
Received char: >
Delimiter found
All chars received: 83F11041043F08
Expected response header: 4104
Single response detected
64-bit response: responseByte_0: 8
responseByte_1: 63
responseByte_2: 0
responseByte_3: 0
responseByte_4: 0
responseByte_5: 0
responseByte_6: 0
responseByte_7: 0
Service: 1
PID: 12
Normal length query detected
Query string: 010C
Clearing input serial buffer

Then the serial.monitor is still the same since I call only for two values...

And last but not least - Thanks for this perfect library and your effort to solve (doesn't metter if always succesfully) our problems!

PowerBroker2 commented 3 years ago

Ok, I see the problem: You have to test ELM_SUCCESS for each individual query. In that, you need to change

  float tempKPH = myELM327.kph();
  float tempENGINE = myELM327.engineLoad();

  if (myELM327.status == ELM_SUCCESS) {

To:

  float tempKPH = myELM327.kph();

  if (myELM327.status == ELM_SUCCESS) {
    // do the kph stuff
  }

  float tempENGINE = myELM327.engineLoad();

  if (myELM327.status == ELM_SUCCESS) {
    // do the engine load stuff
  }
MikolasFromm commented 3 years ago

Cool, but is that really a solution for the problem? (Later will try it, but now theoretically) Basically when I call for SUCCESS after the second query, the only thing I can "miss" is a confirmation status of the first query, but that should not strictly effect the read value, right?

Maybe I just don't understand the code correct.

PowerBroker2 commented 3 years ago

It's hard to say. If you make the proposed change and you still get weird values, your car or ELM327 might be the problem...

MikolasFromm commented 3 years ago

Ok, I will try it tommorow. But since this setup was already working, I'm looking for a solution on the software side. :) That being said, is there somehow possible that the android phone can effect ELM327 behaviour?

Also, do you have any clue what the ASSERT_WARN(2 16) could mean? It started to occur after I had connected (and disconnected) my Android phone to the ELM327 [when ESP was off].

PowerBroker2 commented 3 years ago

I'm looking for a solution on the software side.

Hopefully the fix is in your sketch, but you don't always have a choice where the issue is (hardware, software, etc)

Also, do you have any clue what the ASSERT_WARN(2 16) could mean?

Unfortunately, I don't. Sorry

MikolasFromm commented 3 years ago

UPDATE 2: I've tested out your suggestions above, but nothing seems to help. Values are still wierdly big. I've also tried to play with data-types, which myELM327 is reading, but that haven't changed anything either. Next step is probably buying a brand new piece of the ELM327 unit, which should work further more.

Nevertheless, it is worth thinking whether or not to warn other users that this wird behaviour may occur after connecting android phone to the ELM327 unit. I would love to give you more information about this bug, if you are interested, but only when no other ELM327 unit is getting broken. :smile:

That being said, I keep this thread open, until I get next ELM327 unit, on which I can eliminate software issue.

PowerBroker2 commented 3 years ago

Now that you fixed the sketch, I'd be interested in seeing the debug printouts. Again, I can't stress this enough, the debug statements will help me find the bug faster than anything else, so anytime you make changes and things still are messed up, please post the printouts of the latest attempt. Thanks!

IsikUgurlu commented 3 years ago

Hi! First of all thank you for the library and your support.

@MeCoolGJK is not alone. Same issue here with ESP32. I wrote it to Arduino board a few days ago. Today I came up with a dirty fix which solved the problem temporarily. I entered the below code in ELMduino.cpp at line 2601.

response = response >> 8;

Although responseByte_n values are good, all the returned values from findResponse() function are ~256 times bigger. So this dirty fix helps for the moment.

Here is the sketch I used:

#include <LiquidCrystal_I2C.h>
#include "BluetoothSerial.h"
#include "ELMduino.h"

LiquidCrystal_I2C LCD(0x27, 16, 2);
BluetoothSerial SerialBT;
#define ELM_PORT   SerialBT
#define DEBUG_PORT Serial

ELM327 myELM327;

uint32_t rpm = 0;
uint32_t kph = 0;

void setup()
{
#if LED_BUILTIN
  pinMode(LED_BUILTIN, OUTPUT);
  digitalWrite(LED_BUILTIN, LOW);
#endif

  LCD.begin();
  LCD.backlight();
  LCD.clear();

  LCD.setCursor(0,0); LCD.print(" Toyota Corolla ");
  LCD.setCursor(0,1); LCD.print("  Sol HB 2002   ");

  DEBUG_PORT.begin(115200);
  //SerialBT.setPin("1234");
  ELM_PORT.begin("ArduHUD", true);

  if (!ELM_PORT.connect("OBDII"))
  {
    DEBUG_PORT.println("Couldn't connect to OBD scanner - Phase 1");
    LCD.setCursor(0,0); LCD.print("Couldn't connect");
    LCD.setCursor(0,1); LCD.print("   to ELM327    ");
    while(1);
  }

  if (!myELM327.begin(ELM_PORT, false, 2000))
  {
    Serial.println("Couldn't connect to OBD scanner - Phase 2");
    while (1);
  }

  Serial.println("Connected to ELM327");
}

void loop()
{
  float tempRPM = myELM327.rpm();

  if (myELM327.status == ELM_SUCCESS)
  {
    rpm = (uint32_t)tempRPM;
    Serial.print("RPM: "); Serial.println(rpm);
    LCD.setCursor(0,0); LCD.print("RPM:");
    LCD.setCursor(4,0); LCD.print(rpm);
  }
  else
    myELM327.printError();

  int32_t tempKPH = myELM327.kph();

  if (myELM327.status == ELM_SUCCESS)
  {
    kph = tempKPH;
    Serial.print("KPH: "); Serial.println(kph);
    LCD.setCursor(0,1); LCD.print("KPH:");
    LCD.setCursor(4,1); LCD.print(kph);
  }
  else
    myELM327.printError();
}

Here is the log before the fix:

12:37:43.503 -> Connected to ELM327 12:37:47.693 -> Service: 1 12:37:47.693 -> PID: 12 12:37:47.693 -> Normal length query detected 12:37:47.693 -> Query string: 010C 12:37:47.693 -> Clearing input serial buffer 12:37:47.693 -> Sending the following command/query: 010C 12:37:48.126 -> Received char: 4 12:37:48.126 -> Received char: 8 12:37:48.126 -> Received char: 6 12:37:48.126 -> Received char: B 12:37:48.126 -> Received char: 1 12:37:48.126 -> Received char: 0 12:37:48.163 -> Received char: 4 12:37:48.163 -> Received char: 1 12:37:48.163 -> Received char: 0 12:37:48.163 -> Received char: C 12:37:48.163 -> Received char: 0 12:37:48.163 -> Received char: 0 12:37:48.163 -> Received char: 0 12:37:48.163 -> Received char: 0 12:37:48.163 -> Received char: 1 12:37:48.163 -> Received char: 0 12:37:48.163 -> Received char: \r 12:37:48.163 -> Received char: \n 12:37:48.226 -> Received char: \r 12:37:48.259 -> Received char: \n 12:37:48.259 -> Received char: > 12:37:48.259 -> Delimiter found 12:37:48.259 -> All chars received: 486B10410C000010 12:37:48.259 -> Expected response header: 410C 12:37:48.259 -> Single response detected 12:37:48.259 -> 64-bit response: responseByte_0: 16 12:37:48.259 -> responseByte_1: 0 12:37:48.259 -> responseByte_2: 0 12:37:48.259 -> responseByte_3: 0 12:37:48.259 -> responseByte_4: 0 12:37:48.259 -> responseByte_5: 0 12:37:48.259 -> responseByte_6: 0 12:37:48.259 -> responseByte_7: 0 12:37:48.259 -> RPM: 4 12:37:48.259 -> Service: 1 12:37:48.259 -> PID: 13 12:37:48.259 -> Normal length query detected 12:37:48.294 -> Query string: 010D 12:37:48.294 -> Clearing input serial buffer 12:37:48.294 -> Sending the following command/query: 010D 12:37:48.393 -> Received char: 4 12:37:48.393 -> Received char: 8 12:37:48.429 -> Received char: 6 12:37:48.429 -> Received char: B 12:37:48.429 -> Received char: 1 12:37:48.429 -> Received char: 0 12:37:48.429 -> Received char: 4 12:37:48.429 -> Received char: 1 12:37:48.429 -> Received char: 0 12:37:48.429 -> Received char: D 12:37:48.429 -> Received char: 0 12:37:48.429 -> Received char: 0 12:37:48.429 -> Received char: 1 12:37:48.429 -> Received char: 1 12:37:48.429 -> Received char: \r 12:37:48.429 -> Received char: \n 12:37:48.527 -> Received char: \r 12:37:48.527 -> Received char: \n 12:37:48.564 -> Received char: > 12:37:48.564 -> Delimiter found 12:37:48.564 -> All chars received: 486B10410D0011 12:37:48.564 -> Expected response header: 410D 12:37:48.564 -> Single response detected 12:37:48.564 -> 64-bit response: responseByte_0: 17 12:37:48.564 -> responseByte_1: 0 12:37:48.564 -> responseByte_2: 0 12:37:48.564 -> responseByte_3: 0 12:37:48.564 -> responseByte_4: 0 12:37:48.564 -> responseByte_5: 0 12:37:48.564 -> responseByte_6: 0 12:37:48.564 -> responseByte_7: 0 12:37:48.564 -> KPH: 17 12:38:09.285 -> Service: 1 12:38:09.285 -> PID: 12 12:38:09.285 -> Normal length query detected 12:38:09.285 -> Query string: 010C 12:38:09.285 -> Clearing input serial buffer 12:38:09.285 -> Sending the following command/query: 010C 12:38:09.419 -> Received char: 4 12:38:09.419 -> Received char: 8 12:38:09.419 -> Received char: 6 12:38:09.419 -> Received char: B 12:38:09.419 -> Received char: 1 12:38:09.419 -> Received char: 0 12:38:09.419 -> Received char: 4 12:38:09.419 -> Received char: 1 12:38:09.419 -> Received char: 0 12:38:09.452 -> Received char: C 12:38:09.452 -> Received char: 0 12:38:09.452 -> Received char: F 12:38:09.452 -> Received char: B 12:38:09.452 -> Received char: 2 12:38:09.452 -> Received char: D 12:38:09.452 -> Received char: 1 12:38:09.452 -> Received char: \r 12:38:09.452 -> Received char: \n 12:38:09.552 -> Received char: \r 12:38:09.552 -> Received char: \n 12:38:09.552 -> Received char: > 12:38:09.552 -> Delimiter found 12:38:09.552 -> All chars received: 486B10410C0FB2D1 12:38:09.552 -> Expected response header: 410C 12:38:09.586 -> Single response detected 12:38:09.586 -> 64-bit response: responseByte_0: 209 12:38:09.586 -> responseByte_1: 178 12:38:09.586 -> responseByte_2: 15 12:38:09.586 -> responseByte_3: 0 12:38:09.586 -> responseByte_4: 0 12:38:09.586 -> responseByte_5: 0 12:38:09.586 -> responseByte_6: 0 12:38:09.586 -> responseByte_7: 0 12:38:09.586 -> RPM: 257204 12:38:09.586 -> Service: 1 12:38:09.586 -> PID: 13 12:38:09.586 -> Normal length query detected 12:38:09.586 -> Query string: 010D 12:38:09.586 -> Clearing input serial buffer 12:38:09.586 -> Sending the following command/query: 010D 12:38:09.719 -> Received char: 4 12:38:09.719 -> Received char: 8 12:38:09.752 -> Received char: 6 12:38:09.752 -> Received char: B 12:38:09.752 -> Received char: 1 12:38:09.752 -> Received char: 0 12:38:09.752 -> Received char: 4 12:38:09.752 -> Received char: 1 12:38:09.752 -> Received char: 0 12:38:09.752 -> Received char: D 12:38:09.752 -> Received char: 0 12:38:09.752 -> Received char: 4 12:38:09.752 -> Received char: 1 12:38:09.752 -> Received char: 5 12:38:09.752 -> Received char: \r 12:38:09.752 -> Received char: \n 12:38:09.852 -> Received char: \r 12:38:09.886 -> Received char: \n 12:38:09.886 -> Received char: > 12:38:09.886 -> Delimiter found 12:38:09.886 -> All chars received: 486B10410D0415 12:38:09.886 -> Expected response header: 410D 12:38:09.886 -> Single response detected 12:38:09.886 -> 64-bit response: responseByte_0: 21 12:38:09.886 -> responseByte_1: 4 12:38:09.886 -> responseByte_2: 0 12:38:09.886 -> responseByte_3: 0 12:38:09.886 -> responseByte_4: 0 12:38:09.886 -> responseByte_5: 0 12:38:09.886 -> responseByte_6: 0 12:38:09.886 -> responseByte_7: 0 12:38:09.886 -> KPH: 1045

Unfortunately I don't have a log after the fix since I didn't connect ESP32 to laptop and just observed values on the LCD display and the values are good now. But this handy library needs a clean fix, hope we can find it. Regards.

MikolasFromm commented 3 years ago

Hi @IsikUgurlu, I'm happy that I'm not alone. Unfortunately, PowerBroker2 won't be happy from us. I used my opportunity to refund the ELM327 dongle and I'll receive a new one tomorrow. I quess the problem will disappear with the new I/O dongle, but I had gotten one in my hands already, which was not communicating at all, so I hope it will not be the case this time.

Have you also connected your ELM327 dongle to your phone in between the ESP32 usage, so that after the succesful phone connection the ESP was unable to read the data correctly anymore? I just wonder if there isn't a chance that the phone communication with the ELM327 can change its format (or protocol?). Correct me if I'm wrong, but your commit in the ELMduino.cpp is basically shrinking the number of digits from 241593 to 24 (an example).?

@PowerBroker2 Is there a way to exactly specify the protocol being used? Since I don't know the back-end, is it the ELM327 or the ESP32 (or any other computing unit) handling the protocols?

Thanks

IsikUgurlu commented 3 years ago

Hi @MeCoolGJK, it is good to hear that you'll have a new ELM327 dongle soon. This will help us to narrow down our search path.

Yes, I have connected my ELM327 dongle many times to various android devices before trying it out with ESP32, so I cannot tell if the dongle was working fine before pairing it with an android device or not. I bought it more than a year ago and used it several times with android phones, tablets about a month. During that time I kept the dongle plugged in my car all times. After 3 weeks of not driving, the car battery drained off. So I stopped using it from that day on. I must admit that using ELM327 with a mobile device is not practical at all. I was determined not to use ELM327 again until I met with ELMduino library. 2 weeks ago I bought an ESP32 Devkit V1 and gave it a try. I have never received normal values since the beginning. The only relation I could find is that the returned values are about 256 times bigger than the actual ones, like 256.01 or 256.32 times (always > 256). So I started to google first, then I checked the source code without an outcome. I don't know anything about bit-wise coding, so I stuck and wrote a message to Arduino forum that I mentioned earlier. In the mean time I read some sources about bit shifting, which is the heart of findResponse() function (IMHO) and decided to test last night. It worked of course, it's like formatting the output rather than solving the issue. So I'm not happy with this fix.

Sorry if I didn't explain myself well enough last night, I didn't "commit" any change in ELMduino.cpp on github. I changed the source on my PC, in Arduino IDE library. I don't know much about bit-wise programming, so I shouldn't make a comment to your example above not to embarrass myself, but yes bit shifting works like that, 241593 to 24 is shifting to the right by 4 (decimals only).

I don't think the dongle is the problem here. Debug responseByte_n values are good. I suspect ESP32's interpretation has gone wild somehow. For instance on my debug log KPH:1045 is the result of 410D0415 hex value which should be converted as 4 based on the OBDII vehicle speed definition. There is a good web site for those value conversions. But let's see what results we get from your new ELM327 dongle.

Regards.

MikolasFromm commented 3 years ago

Haha, @IsikUgurlu you are not embarrassing yourself at all. I appreciate your will to dig deeper in the code in order to find any solution.

My ELM327 unit came (the cheapest, blue transparent dongle, v1.5) and ESP32 is working well again. No error codes, nothing, only OK signs and then correct values. I'm even using only "OBDII" name instead of the MAC address and with not "setPin" set.

Therefor I can say that the problem is not on the ELM327 hardware site, nor on the ESP32 hardware site. My guess is that a specific selection of a protocol could change its behaviour. Maybe @PowerBroker2 knows a way to select a specific protocol in the codec correctly. Also my earlier question still remains: Who is handling the protocol choice? ESP or ELM? Maybe this can lead us further.

I will stay in touch here for later solutions and I'm looking foward to hearing from PowerBreaker. :)

IsikUgurlu commented 3 years ago

Congratulations @MeCoolGJK, by replacing your dongle you have proven that neither the library, nor ESP32 is responsible from this weird behave. Mine is also solved without replacing the dongle, with the existing one. You showed the correct direction, thank you!

Based on your result, I searched for an AT command which can reset the dongle. I found ATD, it resides nicely in ELMduino.h file:

const char * const SET_ALL_TO_DEFAULTS = "AT D"; // General

Revoking yesterday's dirty fix and changing initializeELM(const char& protocol) in ELMduino.cpp as the following seems worked for me. My car's RPM is now correctly displayed.

bool ELM327::initializeELM(const char& protocol)
{
    char command[10] = { '\0' };
    connected = false;

    sendCommand(SET_ALL_TO_DEFAULTS); // *** NEW ***
        delay(100); // *** NEW ***

    sendCommand(RESET_ALL);
        delay(100);

    sendCommand(ECHO_OFF);
    delay(100);

    sendCommand(PRINTING_SPACES_OFF);
    delay(100);

    sendCommand(ALLOW_LONG_MESSAGES);
    delay(100);

This is done again in my Arduino IDE. It is @PowerBroker2 's decision to implement it in the library anyway. And I don't know if resetting ELM327 parameters to it's defaults can cause any harm to the car's ECU or not. This should be further checked.

Thank you again.

MikolasFromm commented 3 years ago

Wow! That's a huge step you have just done. Congrats for finding the error. We were looking for something exactly like "restore the ELM327 unit" so I'm very happy that you have found it.

I have already tested your edit on my dongle (connected ESP, then connected Android and finally connected ESP back) and it works! Well, your part does, but we need to add a bit more.

It looks like the ELM327 unit is enabling connection only to the last paired device. That being said, the only way to connect to the ELM327 is when the device is new and unkown for the dongle (pairing is being initialized) or the device is the last that has been paired and connected. This luckily has a solution - I have already mentioned the solution before in this thread, but I will make it more clear now.

You can remove paired devices with the BluetoothSerial.h library-example, so that the ESP32 will succesfully connect to the OBDII. Here is the example:


//This example code is in the Public Domain (or CC0 licensed, at your option.)
//By Victor Tchistiak - 2019
//
//This example demonstrates reading and removing paired devices stored on the ESP32 flash memory
//Sometimes you may find your ESP32 device could not connect to the remote device despite
//many successful connections earlier. This is most likely a result of client replacing your paired
//device info with new one from other device. The BT clients store connection info for paired devices,
//but it is limited to a few devices only. When new device pairs and number of stored devices is exceeded,
//one of the previously paired devices would be replaced with new one.
//The only remedy is to delete this saved bound device from your device flash memory
//and pair with the other device again.

#include "esp_bt_main.h"
#include "esp_bt_device.h"
#include"esp_gap_bt_api.h"
#include "esp_err.h"

#define REMOVE_BONDED_DEVICES 1   // <- Set to 0 to view all bonded devices addresses, set to 1 to remove

#define PAIR_MAX_DEVICES 20
uint8_t pairedDeviceBtAddr[PAIR_MAX_DEVICES][6];
char bda_str[18];

bool initBluetooth()
{
  if(!btStart()) {
    Serial.println("Failed to initialize controller");
    return false;
  }

  if(esp_bluedroid_init() != ESP_OK) {
    Serial.println("Failed to initialize bluedroid");
    return false;
  }

  if(esp_bluedroid_enable() != ESP_OK) {
    Serial.println("Failed to enable bluedroid");
    return false;
  }
  return true;
}

char *bda2str(const uint8_t* bda, char *str, size_t size)
{
  if (bda == NULL || str == NULL || size < 18) {
    return NULL;
  }
  sprintf(str, "%02x:%02x:%02x:%02x:%02x:%02x",
          bda[0], bda[1], bda[2], bda[3], bda[4], bda[5]);
  return str;
}

void setup() {
  Serial.begin(115200);

  initBluetooth();
  Serial.print("ESP32 bluetooth address: "); Serial.println(bda2str(esp_bt_dev_get_address(), bda_str, 18));
  // Get the numbers of bonded/paired devices in the BT module
  int count = esp_bt_gap_get_bond_device_num();
  if(!count) {
    Serial.println("No bonded device found.");
  } else {
    Serial.print("Bonded device count: "); Serial.println(count);
    if(PAIR_MAX_DEVICES < count) {
      count = PAIR_MAX_DEVICES; 
      Serial.print("Reset bonded device count: "); Serial.println(count);
    }
    esp_err_t tError =  esp_bt_gap_get_bond_device_list(&count, pairedDeviceBtAddr);
    if(ESP_OK == tError) {
      for(int i = 0; i < count; i++) {
        Serial.print("Found bonded device # "); Serial.print(i); Serial.print(" -> ");
        Serial.println(bda2str(pairedDeviceBtAddr[i], bda_str, 18));     
        if(REMOVE_BONDED_DEVICES) {
          esp_err_t tError = esp_bt_gap_remove_bond_device(pairedDeviceBtAddr[i]);
          if(ESP_OK == tError) {
            Serial.print("Removed bonded device # "); 
          } else {
            Serial.print("Failed to remove bonded device # ");
          }
          Serial.println(i);
        }
      }        
    }
  }
}

void loop() {}

I don't think that it is necessary to include it in the void setup(), but it is great to keep it in mind when debugging.

I'm more than happy to say that this bug has been found and solved. Thanks a lot @IsikUgurlu. Let's wait for @PowerBroker2 for his ideas, until we close this thread.

PowerBroker2 commented 3 years ago

@IsikUgurlu Thank you for looking into this and helping out. I also want to get to the bottom of this but might not have time to until tomorrow or the day after - I wont forget. Most likely I'll add that new configuration parameter as mentioned in your latest reply. You could fork the repo and make a pull request, too if you want.

IsikUgurlu commented 3 years ago

@MeCoolGJK, thanks to you too. You deserve the appreciation more than me, because your analysis was correct since the beginning, you solved the problem. I just used the method which was already there. Thanks to @PowerBroker2 for implementing the library very well structured, so that applying a patch is very easy.

I am also glad that your last connect/reconnect test was successful.

As for pairing, yes, that happened to me 3 times until now, one being today. I used the same sketch you attached above to remove all paired devices from ESP32's flash. ELM327 dongle tends to connect to the last paired device, which is a good behave. It connects faster this way and for instance it will not try to connect to a mobile phone while there is an ESP32 is ready for serving. To overcome this matter I was thinking to insert the above remove bonded devices code to my final trip computer sketch as a function and assign it to a menu/submenu option or a long press button. Let me know your opinion about this.

@PowerBroker2, I am very happy to be useful. Thanks also to @MeCoolGJK for opening this issue and showing me the right path. I never forked/made a pull request before, but yes, I would like to try. I will read the tutorial and see how it goes. Thank you for this opportunity.

Regards.

PowerBroker2 commented 3 years ago

@IsikUgurlu I merged your PR, thank you! @MeCoolGJK I put a link to that sketch you mentioned in the README

Hopefully everything is addressed. If not, just let me know