#include "stm32f1xx_hal.h" #include "oneWireDriver.h" #include #include // global search state static unsigned char ROM_NO[8]; static uint8_t LastDiscrepancy; static uint8_t LastFamilyDiscrepancy; static bool LastDeviceFlag; void reset_oneWireSearch() { // reset the search state LastDiscrepancy = 0; LastDeviceFlag = false; LastFamilyDiscrepancy = 0; for(int i = 7; ; i--) { ROM_NO[i] = 0; if ( i == 0) break; } } bool oneWireSearch(uint64_t *newAddr ) { const bool search_mode = true; uint8_t id_bit_number; uint8_t last_zero, rom_byte_number; bool search_result; uint8_t 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 = false; // if the last call was not the last one if (!LastDeviceFlag) { // 1-Wire reset if (!oneWire_init()) { // reset the search LastDiscrepancy = 0; LastDeviceFlag = false; LastFamilyDiscrepancy = 0; return false; } // issue the search command if (search_mode == true) { writeByte(0xF0); // NORMAL SEARCH } else { writeByte(0xEC); // CONDITIONAL SEARCH } // loop to do the search do { // read a bit and its complement id_bit = readSlot(); cmp_id_bit = readSlot(); // 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 writeSlot(search_direction); // 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) { 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)) { // search successful so set LastDiscrepancy,LastDeviceFlag,search_result LastDiscrepancy = last_zero; // check for last device if (LastDiscrepancy == 0) { LastDeviceFlag = true; } search_result = true; } } // 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; } else { for (int i = 0; i < 8; i++) { (*newAddr)<<=8; (*newAddr) |= ROM_NO[i]; } } return search_result; } static void sendROMCode(const uint64_t adr) { for( uint8_t i = 8; i>0; i--) writeByte( (uint8_t)(adr >> ((i-1)*8))&0xFF ); } void setConfigRegister(const uint64_t adr, const uint8_t value) { oneWire_init(); writeByte(0x55); // match ROM sendROMCode(adr); writeByte(0x55); // Write Scratchpad (3 bytes) writeByte(0x00); writeByte(0x00); writeByte( (((value)|0x1F)&0x7F) ); } static uint32_t initReadTemp(const uint64_t adr) { uint32_t noOfSlots = 0; oneWire_init(); writeByte(0x55); // match ROM sendROMCode(adr); writeByte(0x44); // convert t while( readSlot() == 0 ) { noOfSlots++; us_delay(1000); if( noOfSlots > 800 ) break; // Cancel after 800mS } return noOfSlots; } float readTemperature(const uint64_t adr) { initReadTemp(adr); oneWire_init(); writeByte(0x55); // skip ROM sendROMCode(adr); writeByte(0xBE); // Read Scratchpad uint8_t b0 = readByte(); uint8_t b1 = readByte(); //uint8_t b2 = readByte(); //uint8_t b3 = readByte(); uint8_t b4 = readByte(); //uint8_t b5 = readByte(); //uint8_t b6 = readByte(); //uint8_t b7 = readByte(); uint16_t raw = (int16_t)((b1 << 8) | b0); uint16_t cfg = (b4 & 0x60); // at lower res, the low bits are undefined, so let's zero them if (cfg == 0x00) raw = raw & ~7; // 9 bit resolution, 93.75 ms else if (cfg == 0x20) raw = raw & ~3; // 10 bit res, 187.5 ms else if (cfg == 0x40) raw = raw & ~1; // 11 bit res, 375 ms //// default is 12 bit resolution, 750 ms conversion time float temperature = (float)raw / 16.0; //printf("%lumS : %02X %02X %02X %02X %02X",time_ms,b0,b1,b2,b3,b4); //printf(" %02X %02X %02X = %.02f\n",b5,b6,b7,temperature); return temperature; }