Exemplo n.º 1
0
 def read(self):
     # pull down to low
     self.__send_and_sleep(0, 0.019)
     data = pycom.pulses_get(self.__pin,100)
     self.__pin.init(Pin.OPEN_DRAIN)
     self.__pin(1)
     #print(data)
     bits = []
     for a,b in data:
     	if a ==1 and 18 <= b <= 28:
     		bits.append(0)
     	if a ==1 and 65 <= b <= 75:
     		bits.append(1)
     #print("longueur bits : %d " % len(bits))
     if len(bits) != 40:
         return DTHResult(DTHResult.ERR_MISSING_DATA, 0, 0)
     #print(bits)
     # we have the bits, calculate bytes
     the_bytes = self.__bits_to_bytes(bits)
     # calculate checksum and check
     checksum = self.__calculate_checksum(the_bytes)
     if the_bytes[4] != checksum:
         return DTHResult(DTHResult.ERR_CRC, 0, 0)
     # ok, we have valid data, return it
     [int_rh, dec_rh, int_t, dec_t, csum] = the_bytes
     if self.__dhttype==0:		#dht11
         rh = int_rh 		#dht11 20% ~ 90%
         t = int_t 	#dht11 0..50°C
     else:			#dht21,dht22
         rh = ((int_rh * 256) + dec_rh)/10
         t = (((int_t & 0x7F) * 256) + dec_t)/10
         if (int_t & 0x80) > 0:
             t *= -1
     return DTHResult(DTHResult.ERR_NO_ERROR, t, rh)
Exemplo n.º 2
0
 def calibrate_rtc(self):
     # the 1.024 factor is because the PIC LF operates at 31 KHz
     # WDT has a frequency divider to generate 1 ms
     # and then there is a binary prescaler, e.g., 1, 2, 4 ... 512, 1024 ms
     # hence the need for the constant
     self._write(bytes([CMD_CALIBRATE]), wait=False)
     self.i2c.deinit()
     Pin('P21', mode=Pin.IN)
     pulses = pycom.pulses_get('P21', 100)
     self.i2c.init(mode=I2C.MASTER,
                   pins=(self.sda, self.scl),
                   baudrate=100000)
     idx = 0
     for i in range(len(pulses)):
         if pulses[i][1] > EXP_RTC_PERIOD:
             idx = i
             break
     try:
         period = pulses[idx][1] - pulses[(idx - 1)][1]
     except:
         period = 0
     if period > 0:
         self.clk_cal_factor = (EXP_RTC_PERIOD / period) * (1000 / 1024)
     if self.clk_cal_factor > 1.25 or self.clk_cal_factor < 0.75:
         self.clk_cal_factor = 1
Exemplo n.º 3
0
    def _send_pulse_and_wait(self):
        """
        Send the pulse to trigger and listen on echo pin.
        We use the method `machine.time_pulse_us()` to get the microseconds until the echo is received.
        """
        self.trigger.value(0)  # Stabilize the sensor
        time.sleep_us(5)
        self.trigger.value(1)
        # Send a 10us pulse.
        time.sleep_us(10)
        self.trigger.value(0)
        try:
            if (uname().sysname == 'WiPy'):
                pulse_list = pulses_get(self.echo, self.echo_timeout_us)
                if (len(pulse_list) == 0):
                    pulse_time = -1
                else:
                    pulse_time = pulse_list[0][1]
            else:
                pulse_time = time_pulse_us(self.echo, 1, self.echo_timeout_us)

            return pulse_time
        except OSError as ex:
            if ex.args[0] == 110:  # 110 = ETIMEDOUT
                raise OSError('Out of range')
            raise ex
Exemplo n.º 4
0
    def calibrate(self):
#         The microcontroller will send the value of CTRL_0 after setting the bit
#            and then will send the following pattern through the data line:
#
#               val | 1 | 0 | 1*| 0 | 1*| 0 | 1
#               ms  | 1 | 1 | 1 | 1 | 8 | 1 | -
#
#            The idea is to measure the real life duration of periods marked with *
#            and substract them. That will remove any errors common to both measurements
#            The result is 7 ms as generated by the PIC LF clock.
#            It can be used to scale any future sleep value.

        # setbits, but limit the number of received bytes to avoid confusion with pattern
        self._magic(CTRL_0_ADDR, 0xFF, 1 << 2, 0, 0)
        self.uart.deinit()
        self._pulses = pycom.pulses_get(COMM_PIN, 150)
        self.uart.init(baudrate=10000, pins=(COMM_PIN, ), timeout_chars=5)
        idx = 0
        for i in range(len(self._pulses)):
            if self._pulses[i][1] > EXP_RTC_PERIOD:
                idx = i
                break
        try:
            self.clk_cal_factor = (self._pulses[idx][1] - self._pulses[(idx - 1)][1]) / EXP_RTC_PERIOD
        except:
            self.clk_cal_factor = 1
        if self.clk_cal_factor > 1.25 or self.clk_cal_factor < 0.75:
            self.clk_cal_factor = 1
Exemplo n.º 5
0
    def calibrate(self):
        """ The microcontroller will send the value of CTRL_0 after setting the bit
            and then will send the following pattern through the data line:

               val | 1 | 0 | 1*| 0 | 1*| 0 | 1
               ms  | 1 | 1 | 1 | 1 | 8 | 1 | -

            The idea is to measure the real life duration of periods marked with *
            and substract them. That will remove any errors common to both measurements
            The result is 7 ms as generated by the PIC LF clock.
            It can be used to scale any future sleep value. """

        # setbits, but limit the number of received bytes to avoid confusion with pattern
        self._magic(CTRL_0_ADDR, 0xFF, 1 << 2, 0, 0)
        self._pulses = pycom.pulses_get(COMM_PIN, 50)
        self.uart.init(baudrate=10000, pins=(COMM_PIN, ), timeout_chars=3)
        try:
            if len(self._pulses) > 6:
                self.clk_cal_factor = (self._pulses[6][1] - self._pulses[4][1]) / EXP_RTC_PERIOD
            else:
                self.clk_cal_factor = (self._pulses[5][1] - self._pulses[3][1]) / EXP_RTC_PERIOD
        except:
            pass
        if self.clk_cal_factor > 1.25 or self.clk_cal_factor < 0.75:
            self.clk_cal_factor = 1
        # flush the buffer
        self.uart.read()
        self.get_wake_status()
Exemplo n.º 6
0
 def calibrate_rtc(self):
     self._write(bytes([CMD_CALIBRATE]), wait=False)
     self.i2c.deinit()
     Pin('P21', mode=Pin.IN)
     pulses = pycom.pulses_get('P21', 50000)
     self.i2c.init(mode=I2C.MASTER, pins=(self.sda, self.scl))
     period = pulses[2][1] - pulses[0][1]
     if period > 0:
         self.clk_cal_factor = (EXP_RTC_PERIOD / period) * 0.98
Exemplo n.º 7
0
 def calibrate_rtc(self):
     # the 1.024 factor is because the PIC LF operates at 31 KHz
     # WDT has a frequency divider to generate 1 ms
     # and then there is a binary prescaler, e.g., 1, 2, 4 ... 512, 1024 ms
     # hence the need for the constant
     self._write(bytes([CMD_CALIBRATE]), wait=False)
     self.i2c.deinit()
     Pin('P21', mode=Pin.IN)
     pulses = pycom.pulses_get('P21', 50000)
     self.i2c.init(mode=I2C.MASTER, pins=(self.sda, self.scl))
     period = pulses[2][1] - pulses[0][1]
     if period > 0:
         self.clk_cal_factor = (EXP_RTC_PERIOD / period) * (1000 / 1024)
Exemplo n.º 8
0
def get_pulses():
    data = [(0,0)]
    cnt = 0
    tester = True
    pulses = 100

    while(tester):
        pin = Pin('P21', mode=Pin.OPEN_DRAIN)
        pin(0)
        sleep_ms(20)
        pin(1)

        data = pulses_get(pin, pulses)         # Fetches all pulses > 100ms
        tester = not (data[0][0] == 1 and len(data) == 80)
    return data
Exemplo n.º 9
0
 def calibrate_rtc(self):
     # the 1.024 factor is because the PIC LF operates at 31 KHz
     # WDT has a frequency divider to generate 1 ms
     # and then there is a binary prescaler, e.g., 1, 2, 4 ... 512, 1024 ms
     # hence the need for the constant
     self._write(bytes([CMD_CALIBRATE]), wait=False)
     self.i2c.deinit()
     Pin('P21', mode=Pin.IN)
     pulses = pycom.pulses_get('P21', 50)
     self.i2c.init(mode=I2C.MASTER, pins=(self.sda, self.scl))
     try:
         period = pulses[2][1] - pulses[0][1]
     except:
         pass
     if period > 0:
         self.clk_cal_factor = (EXP_RTC_PERIOD / period) * (1000 / 1024)
Exemplo n.º 10
0
    def trigger(self):
        # quick fix:
        # re-init pin on each trigger, otherwise no subsequent readings?
        # cf. https://github.com/erikdelange/WiPy-2.0-DHT22/issues/1
        self.pin = Pin(self.pinnumber, mode=Pin.OPEN_DRAIN)

        self.pin(1)  # enforce two second read interval
        time.sleep(2)

        self.pin(0)  # send start signal (1ms low).
        time.sleep_ms(1)

        pulses = pycom.pulses_get(self.pin, 100)  # capture communication

        if len(pulses) != 82:  # 40 data bit plus one acknowledge expected
            self.status = "ReadError"
            return False

        bits = []

        for level, duration in pulses[1:]:
            if level == 1:
                bits.append(0 if duration < 50 else 1)  # convert to 0 or 1

        data = []

        for n in range(5):
            byte = 0
            for i in range(8):  # shift 8 bits into a byte
                byte <<= 1
                byte += bits[n * 8 + i]
            data.append(byte)

        int_rh, dec_rh, int_t, dec_t, csum = data

        if ((int_rh + dec_rh + int_t + dec_t) & 0xFF) != csum:
            self.status = "Checksum Error"
            return False

        self.humidity = ((int_rh * 256) + dec_rh) / 10
        self.temperature = (((int_t & 0x7F) * 256) + dec_t) / 10
        if (int_t & 0x80) > 0:
            self.temperature *= -1

        self.status = "OK"
        self.pin(0)
        return True
Exemplo n.º 11
0
    def trigger(self):
        # quick fix:
        # re-init pin on each trigger, otherwise no subsequent readings?
        # cf. https://github.com/erikdelange/WiPy-2.0-DHT22/issues/1
        self.pin = Pin(self.pinnumber, mode=Pin.OPEN_DRAIN)

        self.pin(1)  # enforce two second read interval
        time.sleep(2)

        self.pin(0)  # send start signal (1ms low).
        time.sleep_ms(1)

        pulses = pycom.pulses_get(self.pin, 100)  # capture communication

        if len(pulses) != 82:  # 40 data bit plus one acknowledge expected
            self.status = "ReadError"
            return False

        bits = []

        for level, duration in pulses[1:]:
            if level == 1:
                bits.append(0 if duration < 50 else 1)  # convert to 0 or 1

        data = []

        for n in range(5):
            byte = 0
            for i in range(8):  # shift 8 bits into a byte
                byte <<= 1
                byte += bits[n * 8 + i]
            data.append(byte)

        int_rh, dec_rh, int_t, dec_t, csum = data

        if ((int_rh + dec_rh + int_t + dec_t) & 0xFF) != csum:
            self.status = "Checksum Error"
            return False

        self.humidity = ((int_rh * 256) + dec_rh) / 10
        self.temperature = (((int_t & 0x7F) * 256) + dec_t) / 10
        if (int_t & 0x80) > 0:
            self.temperature *= -1

        self.status = "OK"
        self.pin(0)
        return True
Exemplo n.º 12
0
    def trigger(self):
        self.pin.init(Pin.OUT)
        self.pin(1)
        time.sleep(2)  # enforce two second read interval

        self.pin(0)  # send start signal (1ms low).
        time.sleep_ms(20)

        pulses = pycom.pulses_get(self.pin, 100)  # capture communication

        time.sleep(2)
        self.pin.init(Pin.OPEN_DRAIN)

        if len(pulses) != 82:  # 40 data bit plus one acknowledge expected
            self.status = "ReadError - received {} only pulses".format(len(pulses))
            return False

        bits = []

        for level, duration in pulses[1:]:
            if level == 1:
                bits.append(0 if duration < 50 else 1)  # convert to 0 or 1

        data = []

        for n in range(5):
            byte = 0
            for i in range(8):  # shift 8 bits into a byte
                byte <<= 1
                byte += bits[n * 8 + i]
            data.append(byte)

        int_rh, dec_rh, int_t, dec_t, csum = data
        print(data)
        if ((int_rh + dec_rh + int_t + dec_t) & 0xFF) != csum:
            self.status = "Checksum Error"
            return False

        self.humidity = (int_rh +(dec_rh*0.1))
        self.temperature = (int_t + dec_t*0.1)
        if (int_t & 0x80) > 0:
            self.temperature *= -1

        self.status = "OK"
        return True
Exemplo n.º 13
0
    def __measure(self):
        if time.ticks_ms() - self.__last_measurement < 1000:
            return

        pin = self.__pin

        # pull down to low
        pin(0)
        time.sleep_ms(20)  # changed from 19 to 20

        # listen for pulses on data line
        data = pycom.pulses_get(pin, 100)

        # reset pin
        pin.init(Pin.OPEN_DRAIN)
        pin(1)

        # convert the received pulses to usable bits
        bits = []
        for value, length in data:
            if value == 1 and 18 <= length <= 28:
                bits.append(0)
            if value == 1 and 65 <= length <= 75:
                bits.append(1)

        # should have 40 bits / 5 bytes
        if len(bits) != 40:
            return

        buffer = bits_to_bytes(bits)

        # calculate checksum and check
        checksum = buffer[0] + buffer[1] + buffer[2] + buffer[3] & 255
        if buffer[4] != checksum:
            return

        # humidity, temperature
        self.__humidity = buffer[0]
        self.__temperature = buffer[2]

        self.__last_measurement = time.ticks_ms()
Exemplo n.º 14
0
    def calibrate(self):
        """ The microcontroller will send the value of CTRL_0 after setting the bit
            and then will send the following pattern through the data line:

               val | 1 | 0 | 1*| 0 | 1*| 0 | 1
               ms  | 1 | 1 | 1 | 1 | 8 | 1 | -

            The idea is to measure the real life duration of periods marked with *
            and substract them. That will remove any errors common to both measurements
            The result is 7 ms as generated by the PIC LF clock.
            It can be used to scale any future sleep value."""

        # setbits, but limit the number of received bytes to avoid confusion with pattern
        self._magic(CTRL_0_ADDR, 0xFF, 1 << 2, 0, 7)
        self.uart.deinit()
        Pin(COMM_PIN, mode=Pin.IN)
        pulses = pycom.pulses_get(COMM_PIN, 50000)
        self.uart = UART(1, baudrate=10000, pins=(COMM_PIN, ))
        self.clk_cal_factor = (pulses[3][1] - pulses[1][1]) / EXP_RTC_PERIOD
        if self.clk_cal_factor > 1.25 or self.clk_cal_factor < 0.75:
            self.clk_cal_factor = 1
Exemplo n.º 15
0
    def calibrate(self):
        """ The microcontroller will send the value of CTRL_0 after setting the bit
            and then will send the following pattern through the data line:

               val | 1 | 0 | 1*| 0 | 1*| 0 | 1
               ms  | 1 | 1 | 1 | 1 | 8 | 1 | -

            The idea is to measure the real life duration of periods marked with *
            and substract them. That will remove any errors common to both measurements
            The result is 7 ms as generated by the PIC LF clock.
            It can be used to scale any future sleep value. """

        # setbits, but limit the number of received bytes to avoid confusion with pattern
        self._magic(CTRL_0_ADDR, 0xFF, 1 << 2, 0, 0)
        self.uart.deinit()
        self._pulses = pycom.pulses_get(COMM_PIN, 50)
        self.uart = UART(1, baudrate=10000, pins=(COMM_PIN, ))
        try:
            self.clk_cal_factor = (self._pulses[4][1] - self._pulses[1][1]) / EXP_RTC_PERIOD
        except:
            pass
        if self.clk_cal_factor > 1.25 or self.clk_cal_factor < 0.75:
            self.clk_cal_factor = 1
Exemplo n.º 16
0
 def calibrate_rtc(self):
     # the 1.024 factor is because the PIC LF operates at 31 KHz
     # WDT has a frequency divider to generate 1 ms
     # and then there is a binary prescaler, e.g., 1, 2, 4 ... 512, 1024 ms
     # hence the need for the constant
     self._write(bytes([CMD_CALIBRATE]), wait=False)
     self.i2c.deinit()
     Pin('P21', mode=Pin.IN)
     pulses = pycom.pulses_get('P21', 100)
     self.i2c.init(mode=I2C.MASTER, pins=(self.sda, self.scl))
     idx = 0
     for i in range(len(pulses)):
         if pulses[i][1] > EXP_RTC_PERIOD:
             idx = i
             break
     try:
         period = pulses[idx][1] - pulses[(idx - 1)][1]
     except:
         period = 0
     if period > 0:
         self.clk_cal_factor = (EXP_RTC_PERIOD / period) * (1000 / 1024)
     if self.clk_cal_factor > 1.25 or self.clk_cal_factor < 0.75:
         self.clk_cal_factor = 1
Exemplo n.º 17
0
 def read(self):
     """
     read
     Reads data from DHT sensor
     """
     # pull down to low
     self.__send_and_sleep(0, 0.019)
     data = pycom.pulses_get(self.__pin, 100) # pylint: disable=E1101
     self.__pin.init(Pin.OPEN_DRAIN)
     self.__pin(1)
     bits = []
     for a, b in data:
         if a == 1 and 18 <= b <= 28:
             bits.append(0)
         if a == 1 and 65 <= b <= 75:
             bits.append(1)
     if len(bits) != 40:
         return DHTResult(DHTResult.ERR_MISSING_DATA, 0, 0)
     # we have the bits, calculate bytes
     the_bytes = bits_to_bytes(bits)
     # calculate checksum and check
     checksum = calculate_checksum(the_bytes)
     if the_bytes[4] != checksum:
         return DHTResult(DHTResult.ERR_CRC, 0, 0)
     # ok, we have valid data, return it
     [int_rh, dec_rh, int_t, dec_t, csum] = the_bytes # pylint: disable=E0632,W0612
     if self.__dhttype == 0:
         #dht11
         rh = int_rh                 #dht11 20% ~ 90%
         t = int_t                   #dht11 0..50 deg C
     else:
         #dht21,dht22
         rh = ((int_rh * 256) + dec_rh)/10
         t = (((int_t & 0x7F) * 256) + dec_t)/10
         if (int_t & 0x80) != 0:
             t = -t
     return DHTResult(DHTResult.ERR_NO_ERROR, t, rh)
Exemplo n.º 18
0
# Enforce a 2 seconds waiting time between measurements.
pin(1)
time.sleep(2)

# Send start signal = 1ms low.
pin(0)
time.sleep_ms(1)

# The DHT22 will repond with an acknowledge signal of 80 us high.
# Then 5 bytes with data are emited, so in total 40 bits.
# Each bit is represented by the duration of the high-time of a pulse, and
# every bit is preceded by a 50 us low.
# List 'pulses' will store the duration of the low- and high-pulses (in us).

pulses = pycom.pulses_get(pin, 100)

pin.init(Pin.OPEN_DRAIN)

# Display the raw measurements
if 1:
    print(len(pulses), "pulses measured")
    for i, (level, duration) in enumerate(pulses):
        print("i = {:2} level: {}  duration: {} us".format(i, level, duration))

# Extract the relevant bits to list 'bits' and skip the acknowledge high
bits = []

for level, duration in pulses[1:]:
    if level == 1:
        bits.append(