-// Copyright (c) 2017, Tobias Mueller tm(at)tm3d.de
-// All rights reserved.
-//
-// Redistribution and use in source and binary forms, with or without
-// modification, are permitted provided that the following conditions are
-// met:
-//
-// * Redistributions of source code must retain the above copyright
-// notice, this list of conditions and the following disclaimer.
-// * Redistributions in binary form must reproduce the above copyright
-// notice, this list of conditions and the following disclaimer in the
-// documentation and/or other materials provided with the
-// distribution.
-// * All advertising materials mentioning features or use of this
-// software must display the following acknowledgement: This product
-// includes software developed by tm3d.de and its contributors.
-// * Neither the name of tm3d.de nor the names of its contributors may
-// be used to endorse or promote products derived from this software
-// without specific prior written permission.
-//
-// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
-// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
-// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
-// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
-// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
-// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
-// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
-// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
-// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
-// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
-// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
-
-
-#include "owInterface.h"
-#include <unistd.h>
-#include <math.h>
-#include "hexfile.h"
-
-static short oddparity[16] = { 0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0 };
-static unsigned char owi_dscrc_table[] = {
- 0, 94,188,226, 97, 63,221,131,194,156,126, 32,163,253, 31, 65,
- 157,195, 33,127,252,162, 64, 30, 95, 1,227,189, 62, 96,130,220,
- 35,125,159,193, 66, 28,254,160,225,191, 93, 3,128,222, 60, 98,
- 190,224, 2, 92,223,129, 99, 61,124, 34,192,158, 29, 67,161,255,
- 70, 24,250,164, 39,121,155,197,132,218, 56,102,229,187, 89, 7,
- 219,133,103, 57,186,228, 6, 88, 25, 71,165,251,120, 38,196,154,
- 101, 59,217,135, 4, 90,184,230,167,249, 27, 69,198,152,122, 36,
- 248,166, 68, 26,153,199, 37,123, 58,100,134,216, 91, 5,231,185,
- 140,210, 48,110,237,179, 81, 15, 78, 16,242,172, 47,113,147,205,
- 17, 79,173,243,112, 46,204,146,211,141,111, 49,178,236, 14, 80,
- 175,241, 19, 77,206,144,114, 44,109, 51,209,143, 12, 82,176,238,
- 50,108,142,208, 83, 13,239,177,240,174, 76, 18,145,207, 45,115,
- 202,148,118, 40,171,245, 23, 73, 8, 86,180,234,105, 55,213,139,
- 87, 9,235,181, 54,104,138,212,149,203, 41,119,244,170, 72, 22,
- 233,183, 85, 11,136,214, 52,106, 43,117,151,201, 74, 20,246,168,
- 116, 42,200,150, 21, 75,169,247,182,232, 10, 84,215,137,107, 53};
-
-
-uint8_t owInterface::docrc8(uint8_t value) {
- // See Application Note 27
-
- // TEST BUILD
- crc8 = owi_dscrc_table[crc8 ^ value];
- return crc8;
-}
-
-uint16_t owInterface::docrc16(uint16_t cdata) {
- cdata = (cdata ^ (crc16 & 0xff)) & 0xff;
- crc16 >>= 8;
-
- if (oddparity[cdata & 0xf] ^ oddparity[cdata >> 4])
- crc16 ^= 0xc001;
-
- cdata <<= 6;
- crc16 ^= cdata;
- cdata <<= 1;
- crc16 ^= cdata;
-
- return crc16;
-
-
-}
-
-uint8_t owInterface::calcCRC8(std::vector<uint8_t> data) {
- crc8 = 0;
- for(uint8_t v: data)
- docrc8(v);
- return crc8; //0 bei erfolg oder crc wenn crc nicht babei
-}
-
-uint16_t owInterface::calcCRC16(std::vector<uint8_t> data) {
- crc16=0;
- for(uint8_t v:data) {
- docrc16(v);
- }
- return crc16;
-}
-
-int owInterface::testCRC16(std::vector<uint8_t> data) {
- return calcCRC16(data)==0xB001;
-}
-
-void owInterface::resetFlasher() { // go back from Bootloader
- std::vector<uint8_t> data;
- data.push_back(0x89);
- Wait_Free();
- snum_t snum;
- snum.num=0xfa55aa55aa55aaa3;
- MatchRom(snum);
- if (log->last()==OWLOG_ERROR) {Free(); return;}
- Communicate(&data, 1, 0);
-
- Free();
- if (log->last()==OWLOG_ERROR) return;
- usleep(50);
-}
-
-void owInterface::resetID() {
- std::vector<uint8_t> data;
- data.push_back(0x8B);
- Wait_Free();
- snum_t snum;
- snum.num=0xfa55aa55aa55aaa3;
- MatchRom(snum);
- if (log->last()==OWLOG_ERROR) {Free(); return;}
- Communicate(&data, 1, 0);
- Free();
-}
-
-int owInterface::programmPage(int pagenr, std::vector<uint8_t> page, int pagesize) {
- snum_t snum;
- snum.num=0xfa55aa55aa55aaa3;
-// printf("programm page %i",pagenr);
-
-
- int diff = pagesize - page.size();
- if (diff>0) {
- for (int i = 0; i < (diff); i++) page.push_back(0xFF);
- }
- std::vector<uint8_t> cl;
- std::vector<uint8_t> clb; //backup
- cl.push_back(0x0F); //code for Flashing
- cl.push_back((pagenr*pagesize) & 0xFF); //adress in byte
- cl.push_back((pagenr*pagesize) >> 8);
- cl.insert(cl.end(),page.begin(),page.end()); //page
- clb=cl; //make backup
- Wait_Free();
- MatchRom(snum);
- if (log->last()==OWLOG_ERROR) {Free();return -3;}
- Communicate(&cl, 3+pagesize, 0); //send (resive page)
- Free();
- if (log->last()==OWLOG_ERROR) return -3;
- int err=0;
- for(int k=0;k<maxrepeat;k++) { //repeat for readback error
- cl.clear();
- cl.push_back(0xAA); //code for readback scratchpad
- Wait_Free();
- MatchRom(snum);
- if (log->last()==OWLOG_ERROR) {Free();return -3;}
- Communicate(&cl, 1, 2+pagesize); // read back scratchpad
- Free();
- if (log->last()==OWLOG_ERROR) return -3;
- err=0;
- for (int i = 0; i < pagesize+2; i++) {
- if (clb[i + 1] != cl[i + 1]) { //test
- usleep(50000);
- err=1;
- break;
- }
- }
- if (err==0) break;
- }
- if (err==1) {
- usleep(50000);
- return -1; //error in scratchpad
- }
- cl.clear();
- cl.push_back(0x55);//Programm
- Wait_Free();
- MatchRom(snum);
- if (log->last()==OWLOG_ERROR) {Free();return -3;}
- Communicate(&cl, 1, 0);
- Free();
- if (log->last()==OWLOG_ERROR) return -3;
- usleep(50000);
- cl.clear();
- cl.push_back(0xB8);//recal programm memory to scratchpad
- cl.push_back((pagenr*pagesize) & 0xFF);
- cl.push_back((pagenr*pagesize) >> 8);
- Wait_Free();
- MatchRom(snum);
- if (log->last()==OWLOG_ERROR) {Free();return -3;}
- Communicate(&cl, 3, 0); //Copy programm memory to scratch
- Free();
- if (log->last()==OWLOG_ERROR) return -3;
- usleep(50000);
-
- for(int k=0;k<maxrepeat;k++) { //repead for reading scratch error
- cl.clear();
- cl.push_back(0xAA);
- Wait_Free();
- MatchRom(snum);
- if (log->last()==OWLOG_ERROR) {Free();return -3;}
- Communicate(&cl, 1, 2 + pagesize); //Reread scratch
- Free();
- if (log->last()==OWLOG_ERROR) return -3;
- err=0;
- for (int i = 0; i < pagesize + 2; i++) {
- if (cl[i + 1] != clb[i + 1]) {
- usleep(50000);
- err=1;
- break;
- }
- }
- if (err==0) break;
- }
- if (err==1) {
- usleep(50000);
- return -2;
- }
-
-
- return 0;
-}
-
-
-int owInterface::flashHEXFile(std::string filename,snum_t dev,int resetid,int progress) {
- log->set(OWLOG_INFO,"Open Hex-File: %s",filename.c_str());
- hexFile *hf=new hexFile(filename);
- if (hf->lastError==1) {log->set(OWLOG_ERROR,"CRC Error in HEX-File %s",filename.c_str());return -1;}
- if (hf->lastError==2) {log->set(OWLOG_ERROR,"Error interpreting HEX-File %s",filename.c_str());return -2;}
- if (hf->lastError==3) {log->set(OWLOG_ERROR,"File could not be opened: %s",filename.c_str());return -3;}
- unsigned int blcount=hf->getBlockCount(64);
- if (blcount>118) {
- log->set(OWLOG_ERROR,"Code to big, max 7552 Byte allowed (118 Pages). Code has %i pages!",blcount);
- return -5;
- }
- log->set(OWLOG_INFO,"Try to start Bootloader on device %llX",dev.num);
- int r=maxrepeat+1;
- int found;
- do {
- log->clear();
- std::vector<uint8_t> data;
- MatchRom(dev);
- data.push_back(0x88);
- Communicate(&data, 1, 0);
- MatchRom(dev);
- Communicate(&data, 1, 0);
- MatchRom(dev);
- Communicate(&data, 1, 0);
- sleep(3);
- log->set(OWLOG_INFO,"Search for Bootloader...");
- log->setLogLevel(OWLOG_WARNING);
- Find();
- log->setLogLevel(OWLOG_INFO);
- found=0;
- for (owDevice* dev :devices) {
- if (dev->getNum().num==0xfa55aa55aa55aaa3) {
- found=1;
- break;
- }
- }
- if (found==0) log->set(OWLOG_WARNING,"Bootloader not found");
- r--;
- } while ((found==0)&&(r>0));
- if (r==0) {
- log->set(OWLOG_ERROR,"Can not start Bootloader on this device %llX",dev.num);
- return -4;
- }
- log->set(OWLOG_INFO,"Start Programm %i Pages",blcount);
- int rp=0;
- int er=0;
- unsigned int i =0;
- for ( i= 0; i < blcount; i++) {
- std::vector<uint8_t> blk = hf->getBlock(i*64, 64);
- int errc = maxrepeat*5;
- while (errc != 0) {
- log->clear();
- if (programmPage(i, blk, 64) >= 0) {
- if (progress) {printf("#");fflush(stdout);}
- break;
- }
-
- errc -= 1;
- rp++;
- if (progress) {printf("\033[1;31m#\033[0m");fflush(stdout);} //printf("\033[1;33m%s\033[0m\n",s);
-
- }
- if (errc == 0) { er++; break; }
- }
- if (progress) printf("\n");
- if (er != 0) {
- log->set(OWLOG_ERROR,"ERROR Writing Program Memory!!!");
- if (i==0) {
- log->set(OWLOG_ERROR,"If Fuse SELFPRGEN enabled?");
- } else
- log->set(OWLOG_ERROR,"Maybe 1-Wire Connection is verry bad!");
- } else {
- if (resetid) {
- log->set(OWLOG_INFO,"Set 1-Wire ID to ID in hexfile...",blcount);
- resetID();
- sleep(3);
- resetID();
- sleep(3);
- }
- }
-
- log->set(OWLOG_INFO,"Back from bootloader to normal device...",blcount);
-
-
- resetFlasher();
- sleep(1);
- resetFlasher();
- sleep(3);
-
- Find();
-
- return 1;
-
-}
-
-
-int owInterface::owSearch() {
- int id_bit_number;
- int last_zero, rom_byte_number, search_result;
- int id_bit, cmp_id_bit;
- unsigned char rom_byte_mask, search_direction;
-
- // initialize for search
- id_bit_number = 1;
- last_zero = 0;
- rom_byte_number = 0;
- rom_byte_mask = 1;
- search_result = 0;
- crc8 = 0;
-
- // if the last call was not the last one
- if (!LastDeviceFlag) {
- // 1-Wire reset
- Wait_Free();
- if (!Reset()) {
- // reset the search
- LastDiscrepancy = 0;
- LastDeviceFlag = FALSE;
- LastFamilyDiscrepancy = 0;
- Free();
- return FALSE;
- }
- if (log->last()==OWLOG_ERROR) return -3;
- // issue the search command
- sendrecivByte(0xF0);
- if (log->last()==OWLOG_ERROR) return -3;
-
- // loop to do the search
- do {
- // read a bit and its complement
- id_bit = sendrecivBit(1);
- cmp_id_bit = sendrecivBit(1);
- // check for no devices on 1-wire
- if ((id_bit == 1) && (cmp_id_bit == 1))
- break;
- else {
- // all devices coupled have 0 or 1
- if (id_bit != cmp_id_bit)
- search_direction = id_bit; // bit write value for search
- else {
- // if this discrepancy if before the Last Discrepancy
- // on a previous next then pick the same as last time
- if (id_bit_number < LastDiscrepancy)
- search_direction = ((ROM_NO[rom_byte_number] & rom_byte_mask) > 0);
- else
- // if equal to last pick 1, if not then pick 0
- search_direction = (id_bit_number == LastDiscrepancy);
-
- // if 0 was picked then record its position in LastZero
- if (search_direction == 0) {
- last_zero = id_bit_number;
- // check for Last discrepancy in family
- if (last_zero < 9)
- LastFamilyDiscrepancy = last_zero;
- }
- }
- // set or clear the bit in the ROM byte rom_byte_number
- // with mask rom_byte_mask
- if (search_direction == 1)
- ROM_NO[rom_byte_number] |= rom_byte_mask;
- else
- ROM_NO[rom_byte_number] &= ~rom_byte_mask;
- // serial number search direction write bit
- sendrecivBit(search_direction);
- //usleep(50);
-
- // increment the byte counter id_bit_number
- // and shift the mask rom_byte_mask
- id_bit_number++;
- rom_byte_mask <<= 1;
-
- // if the mask is 0 then go to new SerialNum byte rom_byte_number and reset mask
- if (rom_byte_mask == 0) {
- docrc8(ROM_NO[rom_byte_number]); // accumulate the CRC
- rom_byte_number++;
- rom_byte_mask = 1;
- }
- }
- }
- while(rom_byte_number < 8); // loop until through all ROM bytes 0-7
- // if the search was successful then
- if (!((id_bit_number < 65) || (crc8 != 0))) {
- // search successful so set LastDiscrepancy,LastDeviceFlag,search_result
- LastDiscrepancy = last_zero;
- // check for last device
- if (LastDiscrepancy == 0)
- LastDeviceFlag = TRUE;
- search_result = TRUE;
- } else {
- log->set(OWLOG_WARNING,"CRC Error on Search Rom");
- }
- }
-
- // if no device found then reset counters so next 'search' will be like a first
- if (!search_result || !ROM_NO[0]) {
- LastDiscrepancy = 0;
- LastDeviceFlag = FALSE;
- LastFamilyDiscrepancy = 0;
- search_result = FALSE;
- }
- Free();
- return search_result;
-
-
-}
-void owInterface::Clean() {
- for (owDevice* dev :devices) {
- delete dev;
- }
- devices.clear();
- device_nums.clear();
- devices_changed=1;
-}
-
-int owInterface::Find() {
- int rslt,i,cnt=0;
- std::vector<snum_t> found;
- for (int k=0;k<maxrepeat;k++) {
- cnt=0;
- log->clear();
- found.clear();
- rslt = owFirst();
- if (log->last()>=OWLOG_WARNING) continue;
- while (rslt){
- snum_t snum;
- // print device found
- for (i = 7; i >= 0; i--)
- snum.byte[i]=ROM_NO[i];
- //printf("%02X", ROM_NO[i]);
- //printf(" %d\n",++cnt);
- found.push_back(snum);
- cnt++;
- log->clear();
- rslt = owNext();
- if (log->last()>=OWLOG_WARNING) {rslt=-1;break;}
- }
- if (rslt==0) break;
-
- }
- if (log->last()>=OWLOG_WARNING) {
- log->set(OWLOG_ERROR,"To much Errors while search rom");
- //Alles so lassen wie es ist?
- return 0;
- }
- for(snum_t snum:found) {
- int snum_found=0;
- //Device schon forhanden?
- for(snum_t d : device_nums) {
- if (snum.num==d.num) {snum_found=1;break;}
- }
- //nein, dann anlegen.
- if (!snum_found) {
- log->set(OWLOG_INFO,"new dev %llx\n",snum.num);
- devices_changed=1;
- device_nums.push_back(snum);
- owDevice *d=NULL;
-
- switch (snum.byte[0]) {
- case 0x28:d=new owDeviceDS18B20(this,snum);break;
- case 0x26:d=new owDeviceDS2438(this,snum);break;
- case 0x20:d=new owDeviceDS2450(this,snum);break;
- case 0x1D:d=new owDeviceDS2423(this,snum);break;
- default:d=new owDevice(this,snum);
- }
- devices.push_back(d);
- if (d!=NULL) {d->readConfig();}
- }
- }
- //Pruefe nach nicht mehr vorhandenen devices
- int dpos=0;
- for(snum_t d:device_nums) {
- int snum_found=0;
- for(snum_t fd:found) {
- if (fd.num==d.num) {snum_found=1;break;}
- }
- //Device nicht gefunden, vieleicht nur Fehler?
- if (!snum_found) {
- devices[dpos]->lastfound++;
- log->set(OWLOG_INFO,"%llx not found %i times \n",device_nums[dpos].num,devices[dpos]->lastfound);
-
- if (devices[dpos]->lastfound>2) {
-
- log->set(OWLOG_INFO,"del device %llx (pos %i)\n",device_nums[dpos].num,dpos);
-
- devices_changed=1;
- delete devices[dpos];
- device_nums.erase(device_nums.begin()+dpos);
- devices.erase(devices.begin()+dpos);
- //printf("new length %i\n",devices.size());
- dpos--;
- }
-
- } else {
- devices[dpos]->lastfound=0;
- }
- dpos++;
-
- }
- return cnt;
-}
-
-int owInterface::MatchRom(snum_t snum) {
- Reset();
- sendrecivByte(0x55);
- usleep(20);
- for(int i=0;i<8;i++) {
- sendrecivByte(snum.byte[i]);
- usleep(20);
- }
- if (log->last()>OWLOG_WARNING) return 0;
- return 1;
-}
-int owInterface::Communicate(std::vector<uint8_t> *data, int scount, int rcount) {
- int i=0;
- data->resize(scount);
- for(uint8_t v:*data) {
- (*data)[i]=sendrecivByte(v);i++;
- usleep(20);
- }
- for(i=0;i<rcount;i++) {
- data->push_back(sendrecivByte(0xFF));
- usleep(20);
-
- }
- return 0;
-}
-
+// Copyright (c) 2017, Tobias Mueller tm(at)tm3d.de\r
+// All rights reserved.\r
+//\r
+// Redistribution and use in source and binary forms, with or without\r
+// modification, are permitted provided that the following conditions are\r
+// met:\r
+//\r
+// * Redistributions of source code must retain the above copyright\r
+// notice, this list of conditions and the following disclaimer.\r
+// * Redistributions in binary form must reproduce the above copyright\r
+// notice, this list of conditions and the following disclaimer in the\r
+// documentation and/or other materials provided with the\r
+// distribution.\r
+// * All advertising materials mentioning features or use of this\r
+// software must display the following acknowledgement: This product\r
+// includes software developed by tm3d.de and its contributors.\r
+// * Neither the name of tm3d.de nor the names of its contributors may\r
+// be used to endorse or promote products derived from this software\r
+// without specific prior written permission.\r
+//\r
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\r
+// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\r
+// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR\r
+// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT\r
+// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,\r
+// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT\r
+// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,\r
+// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY\r
+// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\r
+// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE\r
+// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\r
+\r
+\r
+#include "owInterface.h"\r
+#ifdef LINUX\r
+#include <unistd.h>\r
+#endif\r
+#include <math.h>\r
+#include "hexfile.h"\r
+\r
+\r
+#ifdef WIN\r
+void usleep(__int64 usec)\r
+{\r
+ HANDLE timer;\r
+ LARGE_INTEGER ft;\r
+\r
+ ft.QuadPart = -(10 * usec); // Convert to 100 nanosecond interval, negative value indicates relative time\r
+\r
+ timer = CreateWaitableTimer(NULL, TRUE, NULL);\r
+ SetWaitableTimer(timer, &ft, 0, NULL, NULL, 0);\r
+ WaitForSingleObject(timer, INFINITE);\r
+ CloseHandle(timer);\r
+}\r
+#endif\r
+\r
+\r
+static short oddparity[16] = { 0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0 };\r
+static unsigned char owi_dscrc_table[] = {\r
+ 0, 94,188,226, 97, 63,221,131,194,156,126, 32,163,253, 31, 65,\r
+ 157,195, 33,127,252,162, 64, 30, 95, 1,227,189, 62, 96,130,220,\r
+ 35,125,159,193, 66, 28,254,160,225,191, 93, 3,128,222, 60, 98,\r
+ 190,224, 2, 92,223,129, 99, 61,124, 34,192,158, 29, 67,161,255,\r
+ 70, 24,250,164, 39,121,155,197,132,218, 56,102,229,187, 89, 7,\r
+ 219,133,103, 57,186,228, 6, 88, 25, 71,165,251,120, 38,196,154,\r
+ 101, 59,217,135, 4, 90,184,230,167,249, 27, 69,198,152,122, 36,\r
+ 248,166, 68, 26,153,199, 37,123, 58,100,134,216, 91, 5,231,185,\r
+ 140,210, 48,110,237,179, 81, 15, 78, 16,242,172, 47,113,147,205,\r
+ 17, 79,173,243,112, 46,204,146,211,141,111, 49,178,236, 14, 80,\r
+ 175,241, 19, 77,206,144,114, 44,109, 51,209,143, 12, 82,176,238,\r
+ 50,108,142,208, 83, 13,239,177,240,174, 76, 18,145,207, 45,115,\r
+ 202,148,118, 40,171,245, 23, 73, 8, 86,180,234,105, 55,213,139,\r
+ 87, 9,235,181, 54,104,138,212,149,203, 41,119,244,170, 72, 22,\r
+ 233,183, 85, 11,136,214, 52,106, 43,117,151,201, 74, 20,246,168,\r
+ 116, 42,200,150, 21, 75,169,247,182,232, 10, 84,215,137,107, 53};\r
+\r
+ \r
+uint8_t owInterface::docrc8(uint8_t value) {\r
+ // See Application Note 27\r
+ \r
+ // TEST BUILD\r
+ crc8 = owi_dscrc_table[crc8 ^ value];\r
+ return crc8;\r
+}\r
+ \r
+uint16_t owInterface::docrc16(uint16_t cdata) {\r
+ cdata = (cdata ^ (crc16 & 0xff)) & 0xff;\r
+ crc16 >>= 8;\r
+\r
+ if (oddparity[cdata & 0xf] ^ oddparity[cdata >> 4])\r
+ crc16 ^= 0xc001;\r
+\r
+ cdata <<= 6;\r
+ crc16 ^= cdata;\r
+ cdata <<= 1;\r
+ crc16 ^= cdata;\r
+\r
+ return crc16;\r
+ \r
+ \r
+}\r
+\r
+uint8_t owInterface::calcCRC8(std::vector<uint8_t> data) {\r
+ crc8 = 0;\r
+ for(uint8_t v: data) \r
+ docrc8(v);\r
+ return crc8; //0 bei erfolg oder crc wenn crc nicht babei\r
+}\r
+\r
+uint16_t owInterface::calcCRC16(std::vector<uint8_t> data) {\r
+ crc16=0;\r
+ for(uint8_t v:data) {\r
+ docrc16(v);\r
+ }\r
+ return crc16;\r
+}\r
+\r
+int owInterface::testCRC16(std::vector<uint8_t> data) {\r
+ return calcCRC16(data)==0xB001;\r
+}\r
+ \r
+void owInterface::resetFlasher() { // go back from Bootloader\r
+ std::vector<uint8_t> data;\r
+ data.push_back(0x89);\r
+ Wait_Free();\r
+ snum_t snum;\r
+ snum.num=0xfa55aa55aa55aaa3;\r
+ MatchRom(snum);\r
+ if (log->last()==OWLOG_ERROR) {Free(); return;}\r
+ Communicate(&data, 1, 0);\r
+ \r
+ Free();\r
+ if (log->last()==OWLOG_ERROR) return;\r
+ usleep(50); \r
+}\r
+\r
+void owInterface::resetID() {\r
+ std::vector<uint8_t> data;\r
+ data.push_back(0x8B);\r
+ Wait_Free();\r
+ snum_t snum;\r
+ snum.num=0xfa55aa55aa55aaa3;\r
+ MatchRom(snum);\r
+ if (log->last()==OWLOG_ERROR) {Free(); return;}\r
+ Communicate(&data, 1, 0);\r
+ Free();\r
+}\r
+\r
+int owInterface::programmPage(int pagenr, std::vector<uint8_t> page, int pagesize) {\r
+ snum_t snum;\r
+ snum.num=0xfa55aa55aa55aaa3;\r
+// printf("programm page %i",pagenr);\r
+ \r
+ \r
+ int diff = pagesize - page.size();\r
+ if (diff>0) {\r
+ for (int i = 0; i < (diff); i++) page.push_back(0xFF);\r
+ }\r
+ std::vector<uint8_t> cl;\r
+ std::vector<uint8_t> clb; //backup \r
+ cl.push_back(0x0F); //code for Flashing\r
+ cl.push_back((pagenr*pagesize) & 0xFF); //adress in byte\r
+ cl.push_back((pagenr*pagesize) >> 8);\r
+ cl.insert(cl.end(),page.begin(),page.end()); //page\r
+ clb=cl; //make backup\r
+ Wait_Free();\r
+ MatchRom(snum); \r
+ if (log->last()==OWLOG_ERROR) {Free();return -3;}\r
+ Communicate(&cl, 3+pagesize, 0); //send (resive page)\r
+ Free();\r
+ if (log->last()==OWLOG_ERROR) return -3;\r
+ int err=0;\r
+ for(int k=0;k<maxrepeat;k++) { //repeat for readback error \r
+ cl.clear();\r
+ cl.push_back(0xAA); //code for readback scratchpad\r
+ Wait_Free();\r
+ MatchRom(snum);\r
+ if (log->last()==OWLOG_ERROR) {Free();return -3;}\r
+ Communicate(&cl, 1, 2+pagesize); // read back scratchpad\r
+ Free();\r
+ if (log->last()==OWLOG_ERROR) return -3;\r
+ err=0;\r
+ for (int i = 0; i < pagesize+2; i++) {\r
+ if (clb[i + 1] != cl[i + 1]) { //test\r
+ usleep(50000);\r
+ err=1;\r
+ break;\r
+ }\r
+ }\r
+ if (err==0) break;\r
+ }\r
+ if (err==1) {\r
+ usleep(50000);\r
+ return -1; //error in scratchpad\r
+ }\r
+ cl.clear();\r
+ cl.push_back(0x55);//Programm\r
+ Wait_Free();\r
+ MatchRom(snum);\r
+ if (log->last()==OWLOG_ERROR) {Free();return -3;}\r
+ Communicate(&cl, 1, 0);\r
+ Free();\r
+ if (log->last()==OWLOG_ERROR) return -3;\r
+ usleep(50000);\r
+ cl.clear();\r
+ cl.push_back(0xB8);//recal programm memory to scratchpad\r
+ cl.push_back((pagenr*pagesize) & 0xFF);\r
+ cl.push_back((pagenr*pagesize) >> 8);\r
+ Wait_Free();\r
+ MatchRom(snum);\r
+ if (log->last()==OWLOG_ERROR) {Free();return -3;}\r
+ Communicate(&cl, 3, 0); //Copy programm memory to scratch\r
+ Free();\r
+ if (log->last()==OWLOG_ERROR) return -3;\r
+ usleep(50000);\r
+ \r
+ for(int k=0;k<maxrepeat;k++) { //repead for reading scratch error\r
+ cl.clear();\r
+ cl.push_back(0xAA);\r
+ Wait_Free();\r
+ MatchRom(snum);\r
+ if (log->last()==OWLOG_ERROR) {Free();return -3;}\r
+ Communicate(&cl, 1, 2 + pagesize); //Reread scratch\r
+ Free();\r
+ if (log->last()==OWLOG_ERROR) return -3;\r
+ err=0;\r
+ for (int i = 0; i < pagesize + 2; i++) {\r
+ if (cl[i + 1] != clb[i + 1]) {\r
+ usleep(50000);\r
+ err=1;\r
+ break;\r
+ }\r
+ }\r
+ if (err==0) break;\r
+ }\r
+ if (err==1) {\r
+ usleep(50000);\r
+ return -2;\r
+ }\r
+\r
+\r
+ return 0;\r
+}\r
+\r
+\r
+int owInterface::flashHEXFile(std::string filename,snum_t dev,int resetid,int progress) {\r
+ log->set(OWLOG_INFO,"Open Hex-File: %s",filename.c_str());\r
+ hexFile *hf=new hexFile(filename);\r
+ if (hf->lastError==1) {log->set(OWLOG_ERROR,"CRC Error in HEX-File %s",filename.c_str());return -1;}\r
+ if (hf->lastError==2) {log->set(OWLOG_ERROR,"Error interpreting HEX-File %s",filename.c_str());return -2;}\r
+ if (hf->lastError==3) {log->set(OWLOG_ERROR,"File could not be opened: %s",filename.c_str());return -3;}\r
+ unsigned int blcount=hf->getBlockCount(64);\r
+ if (blcount>118) {\r
+ log->set(OWLOG_ERROR,"Code to big, max 7552 Byte allowed (118 Pages). Code has %i pages!",blcount);\r
+ return -5;\r
+ }\r
+ log->set(OWLOG_INFO,"Try to start Bootloader on device %llX",dev.num);\r
+ int r=maxrepeat+1;\r
+ int found;\r
+ do {\r
+ log->clear();\r
+ std::vector<uint8_t> data;\r
+ MatchRom(dev);\r
+ data.push_back(0x88);\r
+ Communicate(&data, 1, 0);\r
+ MatchRom(dev);\r
+ Communicate(&data, 1, 0);\r
+ MatchRom(dev);\r
+ Communicate(&data, 1, 0);\r
+#ifdef LINUX\r
+ sleep(3);\r
+#endif\r
+#ifdef WIN\r
+ Sleep(3000);\r
+#endif\r
+ log->set(OWLOG_INFO,"Search for Bootloader...");\r
+ log->setLogLevel(OWLOG_WARNING);\r
+ Find();\r
+ log->setLogLevel(OWLOG_INFO);\r
+ found=0;\r
+ for (owDevice* dev :devices) {\r
+ if (dev->getNum().num==0xfa55aa55aa55aaa3) {\r
+ found=1;\r
+ break;\r
+ } \r
+ }\r
+ if (found==0) log->set(OWLOG_WARNING,"Bootloader not found");\r
+ r--;\r
+ } while ((found==0)&&(r>0));\r
+ if (r==0) {\r
+ log->set(OWLOG_ERROR,"Can not start Bootloader on this device %llX",dev.num);\r
+ return -4;\r
+ }\r
+ log->set(OWLOG_INFO,"Start Programm %i Pages",blcount);\r
+ int rp=0;\r
+ int er=0;\r
+ unsigned int i =0;\r
+ for ( i= 0; i < blcount; i++) {\r
+ std::vector<uint8_t> blk = hf->getBlock(i*64, 64);\r
+ int errc = maxrepeat*5;\r
+ while (errc != 0) {\r
+ log->clear();\r
+ if (programmPage(i, blk, 64) >= 0) {\r
+ if (progress) {printf("#");fflush(stdout);} \r
+ break;\r
+ }\r
+ \r
+ errc -= 1;\r
+ rp++;\r
+ if (progress) {printf("\033[1;31m#\033[0m");fflush(stdout);} //printf("\033[1;33m%s\033[0m\n",s);\r
+ \r
+ }\r
+ if (errc == 0) { er++; break; }\r
+ }\r
+ if (progress) printf("\n");\r
+ if (er != 0) {\r
+ log->set(OWLOG_ERROR,"ERROR Writing Program Memory!!!");\r
+ if (i==0) {\r
+ log->set(OWLOG_ERROR,"If Fuse SELFPRGEN enabled?");\r
+ } else\r
+ log->set(OWLOG_ERROR,"Maybe 1-Wire Connection is verry bad!");\r
+ } else {\r
+ if (resetid) {\r
+ log->set(OWLOG_INFO,"Set 1-Wire ID to ID in hexfile...",blcount); \r
+ resetID();\r
+#ifdef LINUX\r
+ sleep(3);\r
+#endif\r
+#ifdef WIN\r
+ Sleep(3000);\r
+#endif\r
+ resetID(); \r
+#ifdef LINUX\r
+ sleep(3);\r
+#endif\r
+#ifdef WIN\r
+ Sleep(3000);\r
+#endif\r
+ }\r
+ } \r
+ \r
+ log->set(OWLOG_INFO,"Back from bootloader to normal device...",blcount); \r
+ \r
+ \r
+ resetFlasher();\r
+#ifdef LINUX\r
+ sleep(1); \r
+#endif\r
+#ifdef WIN\r
+ Sleep(1000);\r
+#endif\r
+ resetFlasher();\r
+#ifdef LINUX\r
+ sleep(3);\r
+#endif\r
+#ifdef WIN\r
+ Sleep(3000);\r
+#endif\r
+\r
+ Find();\r
+ \r
+ return 1;\r
+ \r
+}\r
+\r
+\r
+int owInterface::owSearch() {\r
+ int id_bit_number;\r
+ int last_zero, rom_byte_number, search_result;\r
+ int id_bit, cmp_id_bit;\r
+ unsigned char rom_byte_mask, search_direction;\r
+\r
+ // initialize for search\r
+ id_bit_number = 1;\r
+ last_zero = 0;\r
+ rom_byte_number = 0;\r
+ rom_byte_mask = 1;\r
+ search_result = 0;\r
+ crc8 = 0;\r
+\r
+ // if the last call was not the last one\r
+ if (!LastDeviceFlag) {\r
+ // 1-Wire reset\r
+ Wait_Free();\r
+ if (!Reset()) {\r
+ // reset the search\r
+ LastDiscrepancy = 0;\r
+ LastDeviceFlag = FALSE;\r
+ LastFamilyDiscrepancy = 0;\r
+ Free();\r
+ return FALSE;\r
+ }\r
+ if (log->last()==OWLOG_ERROR) return -3;\r
+ // issue the search command \r
+ sendrecivByte(0xF0); \r
+ if (log->last()==OWLOG_ERROR) return -3;\r
+\r
+ // loop to do the search\r
+ do {\r
+ // read a bit and its complement\r
+ id_bit = sendrecivBit(1);\r
+ cmp_id_bit = sendrecivBit(1);\r
+ // check for no devices on 1-wire\r
+ if ((id_bit == 1) && (cmp_id_bit == 1))\r
+ break;\r
+ else {\r
+ // all devices coupled have 0 or 1\r
+ if (id_bit != cmp_id_bit)\r
+ search_direction = id_bit; // bit write value for search\r
+ else {\r
+ // if this discrepancy if before the Last Discrepancy\r
+ // on a previous next then pick the same as last time\r
+ if (id_bit_number < LastDiscrepancy)\r
+ search_direction = ((ROM_NO[rom_byte_number] & rom_byte_mask) > 0);\r
+ else\r
+ // if equal to last pick 1, if not then pick 0\r
+ search_direction = (id_bit_number == LastDiscrepancy);\r
+\r
+ // if 0 was picked then record its position in LastZero\r
+ if (search_direction == 0) {\r
+ last_zero = id_bit_number;\r
+ // check for Last discrepancy in family\r
+ if (last_zero < 9)\r
+ LastFamilyDiscrepancy = last_zero;\r
+ }\r
+ }\r
+ // set or clear the bit in the ROM byte rom_byte_number\r
+ // with mask rom_byte_mask\r
+ if (search_direction == 1)\r
+ ROM_NO[rom_byte_number] |= rom_byte_mask;\r
+ else\r
+ ROM_NO[rom_byte_number] &= ~rom_byte_mask;\r
+ // serial number search direction write bit\r
+ sendrecivBit(search_direction);\r
+ //usleep(50);\r
+\r
+ // increment the byte counter id_bit_number\r
+ // and shift the mask rom_byte_mask\r
+ id_bit_number++;\r
+ rom_byte_mask <<= 1;\r
+\r
+ // if the mask is 0 then go to new SerialNum byte rom_byte_number and reset mask\r
+ if (rom_byte_mask == 0) {\r
+ docrc8(ROM_NO[rom_byte_number]); // accumulate the CRC\r
+ rom_byte_number++;\r
+ rom_byte_mask = 1;\r
+ }\r
+ }\r
+ }\r
+ while(rom_byte_number < 8); // loop until through all ROM bytes 0-7\r
+ // if the search was successful then\r
+ if (!((id_bit_number < 65) || (crc8 != 0))) {\r
+ // search successful so set LastDiscrepancy,LastDeviceFlag,search_result\r
+ LastDiscrepancy = last_zero;\r
+ // check for last device\r
+ if (LastDiscrepancy == 0)\r
+ LastDeviceFlag = TRUE;\r
+ search_result = TRUE;\r
+ } else {\r
+ log->set(OWLOG_WARNING,"CRC Error on Search Rom");\r
+ }\r
+ }\r
+\r
+ // if no device found then reset counters so next 'search' will be like a first\r
+ if (!search_result || !ROM_NO[0]) {\r
+ LastDiscrepancy = 0;\r
+ LastDeviceFlag = FALSE;\r
+ LastFamilyDiscrepancy = 0;\r
+ search_result = FALSE;\r
+ }\r
+ Free();\r
+ return search_result;\r
+ \r
+\r
+}\r
+void owInterface::Clean() {\r
+ for (owDevice* dev :devices) {\r
+ delete dev;\r
+ }\r
+ devices.clear();\r
+ device_nums.clear();\r
+ devices_changed=1;\r
+}\r
+\r
+int owInterface::Find() {\r
+ int rslt,i,cnt=0;\r
+ std::vector<snum_t> found;\r
+ for (int k=0;k<maxrepeat;k++) {\r
+ cnt=0;\r
+ log->clear();\r
+ found.clear();\r
+ rslt = owFirst();\r
+ if (log->last()>=OWLOG_WARNING) continue;\r
+ while (rslt){\r
+ snum_t snum;\r
+ // print device found\r
+ for (i = 7; i >= 0; i--)\r
+ snum.byte[i]=ROM_NO[i];\r
+ //printf("%02X", ROM_NO[i]);\r
+ //printf(" %d\n",++cnt);\r
+ found.push_back(snum);\r
+ cnt++;\r
+ log->clear();\r
+ rslt = owNext();\r
+ if (log->last()>=OWLOG_WARNING) {rslt=-1;break;}\r
+ }\r
+ if (rslt==0) break;\r
+ \r
+ }\r
+ if (log->last()>=OWLOG_WARNING) { \r
+ log->set(OWLOG_ERROR,"To much Errors while search rom"); \r
+ //Alles so lassen wie es ist? \r
+ return 0;\r
+ }\r
+ for(snum_t snum:found) {\r
+ int snum_found=0;\r
+ //Device schon forhanden?\r
+ for(snum_t d : device_nums) {\r
+ if (snum.num==d.num) {snum_found=1;break;}\r
+ }\r
+ //nein, dann anlegen.\r
+ if (!snum_found) {\r
+ log->set(OWLOG_INFO,"new dev %llx\n",snum.num);\r
+ devices_changed=1;\r
+ device_nums.push_back(snum);\r
+ owDevice *d=NULL;\r
+ \r
+ switch (snum.byte[0]) {\r
+ case 0x28:d=new owDeviceDS18B20(this,snum);break;\r
+ case 0x26:d=new owDeviceDS2438(this,snum);break;\r
+ case 0x20:d=new owDeviceDS2450(this,snum);break;\r
+ case 0x1D:d=new owDeviceDS2423(this,snum);break;\r
+ default:d=new owDevice(this,snum);\r
+ }\r
+ devices.push_back(d);\r
+ if (d!=NULL) {d->readConfig();}\r
+ }\r
+ }\r
+ //Pruefe nach nicht mehr vorhandenen devices\r
+ int dpos=0;\r
+ for(snum_t d:device_nums) {\r
+ int snum_found=0;\r
+ for(snum_t fd:found) {\r
+ if (fd.num==d.num) {snum_found=1;break;}\r
+ }\r
+ //Device nicht gefunden, vieleicht nur Fehler?\r
+ if (!snum_found) {\r
+ devices[dpos]->lastfound++;\r
+ log->set(OWLOG_INFO,"%llx not found %i times \n",device_nums[dpos].num,devices[dpos]->lastfound); \r
+ \r
+ if (devices[dpos]->lastfound>2) {\r
+\r
+ log->set(OWLOG_INFO,"del device %llx (pos %i)\n",device_nums[dpos].num,dpos);\r
+ \r
+ devices_changed=1;\r
+ delete devices[dpos];\r
+ device_nums.erase(device_nums.begin()+dpos);\r
+ devices.erase(devices.begin()+dpos); \r
+ //printf("new length %i\n",devices.size());\r
+ dpos--;\r
+ } \r
+\r
+ } else {\r
+ devices[dpos]->lastfound=0;\r
+ }\r
+ dpos++;\r
+ \r
+ } \r
+ return cnt; \r
+}\r
+\r
+int owInterface::MatchRom(snum_t snum) {\r
+ Reset();\r
+/* sendrecivByte(0x55);\r
+ usleep(20);\r
+ for(int i=0;i<8;i++) {\r
+ sendrecivByte(snum.byte[i]); \r
+ usleep(20);\r
+ }\r
+ if (log->last()>OWLOG_WARNING) return 0;*/\r
+ std::vector<uint8_t> cl;\r
+ cl.push_back(0x55); //code for Flashing\r
+ for (int i = 0; i<8; i++) {\r
+ cl.push_back(snum.byte[i]);\r
+ }\r
+ Communicate(&cl, 9, 0);\r
+\r
+ return 1;\r
+}\r
+int owInterface::Communicate(std::vector<uint8_t> *data, int scount, int rcount) {\r
+ int i=0;\r
+ data->resize(scount);\r
+ for(uint8_t v:*data) {\r
+ (*data)[i]=sendrecivByte(v);i++;\r
+ usleep(20);\r
+ }\r
+ for(i=0;i<rcount;i++) {\r
+ data->push_back(sendrecivByte(0xFF));\r
+ usleep(20);\r
+ \r
+ }\r
+ return 0;\r
+}\r
+\r