test-serial-UEDan.ino 6.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241
  1. #include <SoftwareSerial.h>
  2. //TEST UNITS
  3. int inVal = 0;
  4. int selMode = 1;
  5. int ECUbytes[8] = {0, 0, 0, 0, 0, 0, 0, 0};
  6. //4th byte is # of packets you idiot.
  7. //double check checksum byte you jackass.
  8. byte ReqData[31] = {128,16,240,26,168,0,0,0,16,0,0,19,0,0,70,0,1,33,0,0,100,2,9,199,2,1,104,0,0,20,130}; // add throttle
  9. byte ReqDataSize = 31;
  10. unsigned long prvTime;
  11. unsigned long curTime;
  12. int milli;
  13. double milesPerHour;
  14. double airFuelR;
  15. double airFlowG;
  16. double milesPerGallon;
  17. //END TEST UNITS
  18. //Rx/Tx pins used for SSM
  19. SoftwareSerial sendSerial = SoftwareSerial(10, 11); //Rx, Tx
  20. void setup() {
  21. //TEST SETUP
  22. pinMode(12, INPUT);
  23. //END TEST SETUP
  24. //Setup Start
  25. Serial.begin(115200); //for diagnostics
  26. Serial.println("Serial Started");
  27. while (!Serial) {
  28. // wait
  29. }
  30. Serial.println("starting SSM Serial");
  31. sendSerial.begin(4800); //SSM uses 4800 8N1 baud rate
  32. while (!sendSerial) {
  33. //wait
  34. delay(50);
  35. }
  36. Serial.println("Ready!");
  37. delay(50);
  38. // writeSSM(ReqData, ReqDataSize, sendSerial); //send intial SSM poll
  39. delay (2);
  40. }
  41. void loop() {
  42. /*TEST LOOP
  43. inVal = digitalRead(12);
  44. if (inVal == 0) {
  45. if (selMode == 10) {
  46. selMode = 0;
  47. }
  48. selMode++;
  49. //Serial.println("Mode plus");
  50. //printMode(selMode);
  51. delay(500);
  52. }
  53. */
  54. curTime = millis();
  55. milli=curTime - prvTime;
  56. if (milli > 250) {
  57. sendSerial.flush();
  58. //delay(5);
  59. // Serial.print("SentTime:");
  60. // Serial.println(milli);
  61. writeSSM(ReqData, ReqDataSize, sendSerial);
  62. //Serial.print("Timer Popped | ");
  63. //Serial.println(sendSerial.available());
  64. prvTime=millis();
  65. }
  66. if (sendSerial.available()) {
  67. readECU(ECUbytes, 8, false);
  68. prvTime = curTime;
  69. milesPerHour = (ECUbytes[0] * 0.621371192); //P9 0x000010
  70. airFuelR = ((ECUbytes[2] / 128.00) * 14.7); //P58 0x000046
  71. airFlowG = (((ECUbytes[1] * 256.00) + ECUbytes[7]) / 100.00); //P12 0x000013 and 0x000014
  72. milesPerGallon = (milesPerHour/3600.00)/(airFlowG/(airFuelR)/2800.00);
  73. Serial.print("MPH:");
  74. Serial.print(milesPerHour, 0);
  75. Serial.print(" | ");
  76. Serial.print("Mass airflow/s:");
  77. Serial.print(airFlowG);
  78. Serial.print(" | ");
  79. Serial.print("AFR: ");
  80. Serial.print(airFuelR);
  81. Serial.print(" | ");
  82. Serial.print("MPG:");
  83. Serial.print(milesPerGallon);
  84. Serial.print(" | ");
  85. Serial.print("Cruise:"); //0x000121
  86. Serial.print(ECUbytes[3], BIN);
  87. Serial.print(" | ");
  88. Serial.print("Defogger:");
  89. Serial.print(ECUbytes[4], BIN); //0x000064
  90. Serial.print(" | ");
  91. Serial.print("Gear:"); //0x0209C7
  92. Serial.print(ECUbytes[5]);
  93. Serial.print(" | ");
  94. Serial.print("IAM:"); //0x020168
  95. Serial.println(ECUbytes[6]);
  96. }
  97. }
  98. //TEST FUNCTION, PIN7
  99. void printMode(int selMode) {
  100. switch (selMode)
  101. {
  102. case 1:
  103. Serial.print("This is case 1 mode ");
  104. Serial.println(selMode);
  105. digitalWrite(13, HIGH);
  106. break;
  107. case 2:
  108. Serial.print("This is case 2 mode ");
  109. Serial.println(selMode);
  110. digitalWrite(13, LOW);
  111. break;
  112. case 3 ... 5:
  113. Serial.print("This is case 3 to 5 mode ");
  114. Serial.println(selMode);
  115. digitalWrite(13, HIGH);
  116. break;
  117. case 6 ... 9:
  118. Serial.print("This is case 6 to 9 mode ");
  119. Serial.println(selMode);
  120. digitalWrite(13, LOW);
  121. break;
  122. case 10:
  123. Serial.print("This is case 10 mode ");
  124. Serial.println(selMode);
  125. digitalWrite(13, HIGH);
  126. }
  127. }
  128. /* returns the 8 least significant bits of an input byte*/
  129. byte CheckSum(byte sum) {
  130. byte counter = 0;
  131. byte power = 1;
  132. for (byte n = 0; n < 8; n++) {
  133. counter += bitRead(sum, n) * power;
  134. power = power * 2;
  135. }
  136. return counter;
  137. }
  138. /*writes data over the software serial port
  139. the &digiSerial passes a reference to the external
  140. object so that we can control it outside of the function*/
  141. void writeSSM(byte data[], byte length, SoftwareSerial &digiSerial) {
  142. //Serial.println(F("Sending packet... "));
  143. for (byte x = 0; x < length; x++) {
  144. digiSerial.write(data[x]);
  145. }
  146. //Serial.println(F("done sending."));
  147. }
  148. //this will change the values in dataArray, populating them with values respective of the poll array address calls
  149. boolean readECU(int* dataArray, byte dataArrayLength, boolean nonZeroes)
  150. {
  151. byte data = 0;
  152. boolean isPacket = false;
  153. byte sumBytes = 0;
  154. byte checkSumByte = 0;
  155. byte dataSize = 0;
  156. byte bytePlace = 0;
  157. byte zeroesLoopSpot = 0;
  158. byte loopLength = 20;
  159. for (byte j = 0; j < loopLength; j++)
  160. {
  161. data = sendSerial.read();
  162. delay(2);
  163. if (data == 128 && dataSize == 0) { //0x80 or 128 marks the beginning of a packet
  164. isPacket = true;
  165. j = 0;
  166. //Serial.println("Begin Packet");
  167. }
  168. //terminate function and return false if no response is detected
  169. if (j == (loopLength - 1) && isPacket != true)
  170. {
  171. return false;
  172. }
  173. if (isPacket == true && data != -1) {
  174. Serial.print(data); // for debugging: shows in-packet data
  175. Serial.print(" ");
  176. if (bytePlace == 3) { // how much data is coming
  177. dataSize = data;
  178. loopLength = data + 6;
  179. }
  180. if (bytePlace > 4 && bytePlace - 5 < dataArrayLength && nonZeroes == false)
  181. {
  182. dataArray[bytePlace - 5] = data;
  183. }
  184. else if (bytePlace > 4 && zeroesLoopSpot < dataArrayLength / 2 && nonZeroes == true && data != 0 && bytePlace < dataSize + 4)
  185. {
  186. dataArray[zeroesLoopSpot] = data;
  187. dataArray[zeroesLoopSpot + (dataArrayLength / 2)] = bytePlace;
  188. zeroesLoopSpot++;
  189. }
  190. bytePlace += 1; //increment bytePlace
  191. //once the data is all recieved, checksum and re-set counters
  192. // Serial.print("byte place: ");
  193. // Serial.println(bytePlace);
  194. if (bytePlace == dataSize + 5) {
  195. checkSumByte = CheckSum(sumBytes); //the 8 least significant bits of sumBytes
  196. if (data != checkSumByte) {
  197. Serial.println(F("checksum error"));
  198. return false;
  199. }
  200. // Serial.println("Checksum is good");
  201. isPacket = false;
  202. sumBytes = 0;
  203. bytePlace = 0;
  204. checkSumByte = 0;
  205. dataSize = 0;
  206. return true;
  207. }
  208. else {
  209. sumBytes += data; // this is to compare with the checksum byte
  210. //Serial.print(F("sum: "));
  211. //Serial.println(sumBytes);
  212. }
  213. }
  214. }
  215. Serial.println("");
  216. }