[Solved] Pysense - Light sensor shows zero after cycling through deep sleep
-
I am running 1.7.6.b1 on LoPy on a Pysense board and I have confirmed that almost all the sensors work normally and continue to work after the Pysense has been through a Deep Sleep cycle.
However, the light sensor only works when first powered up.
If the Pysense is put to sleep, when it wakes the board resets, runs the code but the light sensor always shows 0 for all sleep cycles after the first.Here is some test code that shows the effect:
# Test script running on LoPy release 1.7.6.b1 attached to Pysense board from machine import Pin from pysense import Pysense #Basic Pysense board settings from LTR329ALS01 import LTR329ALS01 #light meter import utime # escape button button=Pin('P14') # Set up the sensors BD = Pysense() lightsensor= LTR329ALS01(pysense=BD) # Record some light measurements if button(): #Pysense button normally high - this is not pressed during the test with open('/flash/mylog.log',mode='a') as f: while 1: # Main loop (Light,dummy)= lightsensor.lux() utime.sleep(1) f.write(' LIGHT SENSOR '+str(Light)+'\r\n') utime.sleep(1) f.close() BD.setup_sleep(5)# sleep in seconds BD.go_to_sleep() #utime.sleep(5) pass
The resulting Log file shows a line for each cycle:
LIGHT SENSOR 32
LIGHT SENSOR 0
LIGHT SENSOR 0
LIGHT SENSOR 0
LIGHT SENSOR 0
LIGHT SENSOR 0
LIGHT SENSOR 0Any ideas how to reset/remove/recover the light sensor ?
-
I am using the official library taken from here https://github.com/pycom/pycom-libraries/blob/master/shields/lib/LTR329ALS01.py which indeed as you noticed does not contain the ALS_STATUS status register reading logic.
According to the datasheet https://www.mouser.com/datasheet/2/239/Lite-On_LTR-329ALS-01 DS_ver1.1-348647.pdf Page 22 the Device operation flow chard shows indeed kind of a loop until that status register indicate a new data is available. on Page 24 it shows a pseudo code mentioning what you are suggesting (which is checking the data readiness before performing the actual read). Page 21 it describe how to perform the check of the validity of the read.
I can try to patch the lib according to such information and push a PR to the official repo if this is solving the problem :-).
Keep You posted and thanks for your help!
Stef
-
@Stefano-Ordine
i do not see in the library reading status register
ALS_STATUS Register (0x8C)
maybe this is a the problem
-
@livius thanks for the reply, I implemented your idea of delaying 500ms between one read and another by coding this snippet:
... lt = LTR329ALS01(py) [light_blue, light_red] = (0,0) for index in range(100): print('index %d' % (index)) light = lt.light() [light_blue, light_red] = light if (light_blue != 0): print('after %d reads I got %d' % (index, light_blue)) break print('light_blue %d' % (light_blue)) time.sleep_ms(500) ...
it always succeed on the second reads as you can see from this output:
// First light read after flashing the firmware rst:0x7 (TG0WDT_SYS_RESET),boot:0x1a (SPI_FAST_FLASH_BOOT) ... index 0 after 0 reads I got 80 ... // First light read after waking up from deep sleep rst:0x5 (DEEPSLEEP_RESET),boot:0x1a (SPI_FAST_FLASH_BOOT) ... index 0 light_blue 0 index 1 after 1 reads I got 50 // Second light read after waking up from deep sleep rst:0x5 (DEEPSLEEP_RESET),boot:0x1a (SPI_FAST_FLASH_BOOT) ... index 0 light_blue 0 index 1 after 1 reads I got 87 // Third light read after waking up from deep sleep rst:0x5 (DEEPSLEEP_RESET),boot:0x1a (SPI_FAST_FLASH_BOOT) ... index 0 light_blue 0 index 1 after 1 reads I got 71
Is there anything I can do for You to help solving this?
-
to test try this:
i = 0 while i<=100: ch1low = lt.i2c.readfrom_mem(lt.ALS_I2CADDR , lt.ALS_DATA_CH1_LOW, 1) ch1high = lt.i2c.readfrom_mem(lt.ALS_I2CADDR , lt.ALS_DATA_CH1_HIGH, 1) ch0low = lt.i2c.readfrom_mem(lt.ALS_I2CADDR , lt.ALS_DATA_CH0_LOW, 1) ch0high = lt.i2c.readfrom_mem(lt.ALS_I2CADDR , lt.ALS_DATA_CH0_HIGH, 1) print(i, ch1low, ch1high, ch0low, ch0high) time.sleep_ms(500) i+=1
and look if somewhere you got some values
-
@markN I tried to dummy read like you suggested like this:
... from pysense import Pysense from LTR329ALS01 import LTR329ALS01 ... py = Pysense() ... lt = LTR329ALS01(py) dummy = lt.light() light = lt.light() ... pybytes.deepsleep(time_milliseconds)
but still getting 0 values on waking up after deepsleeping...
is the dummy reads mentioned in your last post to be intented as I shown? any other idea on how to solve this?For context I adding these additional details:
The light function into the lib/LTR329ALS01.py is defined like this:class LTR329ALS01: ... def __init__(self, pysense = None, sda = 'P22', scl = 'P21', gain = ALS_GAIN_1X, integration = ALS_INT_100, rate = ALS_RATE_500): if pysense is not None: self.i2c = pysense.i2c else: self.i2c = I2C(0, mode=I2C.MASTER, pins=(sda, scl)) self.gain = gain self.integration = integration contr = self._getContr(gain) self.i2c.writeto_mem(ALS_I2CADDR, ALS_CONTR_REG, bytearray([contr])) measrate = self._getMeasRate(integration, rate) self.i2c.writeto_mem(ALS_I2CADDR, ALS_MEAS_RATE_REG, bytearray([measrate])) time.sleep(0.01) def _getContr(self, gain): return ((gain & 0x07) << 2) + 0x01 def _getMeasRate(self, integration, rate): return ((integration & 0x07) << 3) + (rate & 0x07) def _getWord(self, high, low): return ((high & 0xFF) << 8) + (low & 0xFF) def light(self): ch1low = self.i2c.readfrom_mem(ALS_I2CADDR , ALS_DATA_CH1_LOW, 1) ch1high = self.i2c.readfrom_mem(ALS_I2CADDR , ALS_DATA_CH1_HIGH, 1) data1 = int(self._getWord(ch1high[0], ch1low[0])) ch0low = self.i2c.readfrom_mem(ALS_I2CADDR , ALS_DATA_CH0_LOW, 1) ch0high = self.i2c.readfrom_mem(ALS_I2CADDR , ALS_DATA_CH0_HIGH, 1) data0 = int(self._getWord(ch0high[0], ch0low[0])) return (data0, data1) ...
-
@markN how did You solve this problem, I am experiencing the same.
Thanks :-)
-
@markN Please can you share your code? I have the same issue :-(
-
@markN I have now solved this. The light sensor seems to have an internal buffer that is keeping an old value. Placing a dummy read of the light sensor at the beginning of the code flushes out the old value (which is 0 if the Pysense has gone through a deep sleep cycle).