@@ -71,6 +71,11 @@ def unlock(self):
7171 else :
7272 raise ValueError ("Not locked" )
7373
74+ def _check_lock (self ):
75+ if not self ._locked :
76+ raise RuntimeError ("First call try_lock()" )
77+ return True
78+
7479 def __enter__ (self ):
7580 return self
7681
@@ -111,25 +116,28 @@ def __init__(self, scl, sda, *, frequency=400000, timeout=1):
111116 def scan (self ):
112117 """Perform an I2C Device Scan"""
113118 found = []
114- for address in range (0 , 0x80 ):
115- if self ._probe (address ):
116- found .append (address )
119+ if self ._check_lock ():
120+ for address in range (0 , 0x80 ):
121+ if self ._probe (address ):
122+ found .append (address )
117123 return found
118124
119125 def writeto (self , address , buffer , * , start = 0 , end = None , stop = True ):
120126 """Write data from the buffer to an address"""
121127 if end is None :
122128 end = len (buffer )
123- self ._write (address , buffer [start :end ], stop )
129+ if self ._check_lock ():
130+ self ._write (address , buffer [start :end ], stop )
124131
125132 def readfrom_into (self , address , buffer , * , start = 0 , end = None ):
126133 """Read data from an address and into the buffer"""
127134 if end is None :
128135 end = len (buffer )
129136
130- readin = self ._read (address , end - start )
131- for i in range (end - start ):
132- buffer [i + start ] = readin [i ]
137+ if self ._check_lock ():
138+ readin = self ._read (address , end - start )
139+ for i in range (end - start ):
140+ buffer [i + start ] = readin [i ]
133141
134142 def writeto_then_readfrom (
135143 self ,
@@ -150,8 +158,9 @@ def writeto_then_readfrom(
150158 out_end = len (buffer_out )
151159 if in_end is None :
152160 in_end = len (buffer_in )
153- self .writeto (address , buffer_out , start = out_start , end = out_end , stop = stop )
154- self .readfrom_into (address , buffer_in , start = in_start , end = in_end )
161+ if self ._check_lock ():
162+ self .writeto (address , buffer_out , start = out_start , end = out_end , stop = stop )
163+ self .readfrom_into (address , buffer_in , start = in_start , end = in_end )
155164
156165 def _scl_low (self ):
157166 self ._scl .value = 0
@@ -308,7 +317,7 @@ def __init__(self, clock, MOSI=None, MISO=None):
308317
309318 def configure (self , * , baudrate = 100000 , polarity = 0 , phase = 0 , bits = 8 ):
310319 """Configures the SPI bus. Only valid when locked."""
311- if self ._locked :
320+ if self ._check_lock () :
312321 if not isinstance (baudrate , int ):
313322 raise ValueError ("baudrate must be an integer" )
314323 if not isinstance (bits , int ):
@@ -325,9 +334,6 @@ def configure(self, *, baudrate=100000, polarity=0, phase=0, bits=8):
325334 self ._bits = bits
326335 self ._half_period = (1 / self ._baudrate ) / 2 # 50% Duty Cyle delay
327336
328- else :
329- raise RuntimeError ("First call try_lock()" )
330-
331337 def _wait (self , start = None ):
332338 """Wait for up to one half cycle"""
333339 while (start + self ._half_period ) > monotonic ():
@@ -344,26 +350,28 @@ def write(self, buffer, start=0, end=None):
344350 if end is None :
345351 end = len (buffer )
346352
347- start_time = monotonic ()
348- for byte in buffer [start :end ]:
349- for bit_position in range (self ._bits ):
350- bit_value = byte & 0x80 >> bit_position
351- # Set clock to base
352- if not self ._phase : # Mode 0, 2
353- self ._mosi .value = bit_value
354- self ._sclk .value = self ._polarity
355- start_time = self ._wait (start_time )
356-
357- # Flip clock off base
358- if self ._phase : # Mode 1, 3
359- self ._mosi .value = bit_value
360- self ._sclk .value = not self ._polarity
361- start_time = self ._wait (start_time )
362-
363- # Return pins to base positions
364- self ._mosi .value = 0
365- self ._sclk .value = self ._polarity
353+ if self ._check_lock ():
354+ start_time = monotonic ()
355+ for byte in buffer [start :end ]:
356+ for bit_position in range (self ._bits ):
357+ bit_value = byte & 0x80 >> bit_position
358+ # Set clock to base
359+ if not self ._phase : # Mode 0, 2
360+ self ._mosi .value = bit_value
361+ self ._sclk .value = self ._polarity
362+ start_time = self ._wait (start_time )
366363
364+ # Flip clock off base
365+ if self ._phase : # Mode 1, 3
366+ self ._mosi .value = bit_value
367+ self ._sclk .value = not self ._polarity
368+ start_time = self ._wait (start_time )
369+
370+ # Return pins to base positions
371+ self ._mosi .value = 0
372+ self ._sclk .value = self ._polarity
373+
374+ # pylint: disable=too-many-branches
367375 def readinto (self , buffer , start = 0 , end = None , write_value = 0 ):
368376 """Read into the buffer specified by buf while writing zeroes. Requires the SPI being
369377 locked. If the number of bytes to read is 0, nothing happens.
@@ -372,43 +380,44 @@ def readinto(self, buffer, start=0, end=None, write_value=0):
372380 raise RuntimeError ("Read attempted with no MISO pin specified." )
373381 if end is None :
374382 end = len (buffer )
375- start_time = monotonic ()
376- for byte_position , _ in enumerate (buffer [start :end ]):
377- for bit_position in range (self ._bits ):
378- bit_mask = 0x80 >> bit_position
379- bit_value = write_value & 0x80 >> bit_position
380- # Return clock to base
381- self ._sclk .value = self ._polarity
382- start_time = self ._wait (start_time )
383- # Handle read on leading edge of clock.
384- if not self ._phase : # Mode 0, 2
385- if self ._mosi is not None :
386- self ._mosi .value = bit_value
387- if self ._miso .value :
388- # Set bit to 1 at appropriate location.
389- buffer [byte_position ] |= bit_mask
390- else :
391- # Set bit to 0 at appropriate location.
392- buffer [byte_position ] &= ~ bit_mask
393- # Flip clock off base
394- self ._sclk .value = not self ._polarity
395- start_time = self ._wait (start_time )
396- # Handle read on trailing edge of clock.
397- if self ._phase : # Mode 1, 3
398- if self ._mosi is not None :
399- self ._mosi .value = bit_value
400- if self ._miso .value :
401- # Set bit to 1 at appropriate location.
402- buffer [byte_position ] |= bit_mask
403- else :
404- # Set bit to 0 at appropriate location.
405- buffer [byte_position ] &= ~ bit_mask
406383
407- # Return pins to base positions
408- self ._mosi .value = 0
409- self ._sclk .value = self ._polarity
384+ if self ._check_lock ():
385+ start_time = monotonic ()
386+ for byte_position , _ in enumerate (buffer [start :end ]):
387+ for bit_position in range (self ._bits ):
388+ bit_mask = 0x80 >> bit_position
389+ bit_value = write_value & 0x80 >> bit_position
390+ # Return clock to base
391+ self ._sclk .value = self ._polarity
392+ start_time = self ._wait (start_time )
393+ # Handle read on leading edge of clock.
394+ if not self ._phase : # Mode 0, 2
395+ if self ._mosi is not None :
396+ self ._mosi .value = bit_value
397+ if self ._miso .value :
398+ # Set bit to 1 at appropriate location.
399+ buffer [byte_position ] |= bit_mask
400+ else :
401+ # Set bit to 0 at appropriate location.
402+ buffer [byte_position ] &= ~ bit_mask
403+ # Flip clock off base
404+ self ._sclk .value = not self ._polarity
405+ start_time = self ._wait (start_time )
406+ # Handle read on trailing edge of clock.
407+ if self ._phase : # Mode 1, 3
408+ if self ._mosi is not None :
409+ self ._mosi .value = bit_value
410+ if self ._miso .value :
411+ # Set bit to 1 at appropriate location.
412+ buffer [byte_position ] |= bit_mask
413+ else :
414+ # Set bit to 0 at appropriate location.
415+ buffer [byte_position ] &= ~ bit_mask
416+
417+ # Return pins to base positions
418+ self ._mosi .value = 0
419+ self ._sclk .value = self ._polarity
410420
411- # pylint: disable=too-many-branches
412421 def write_readinto (
413422 self ,
414423 buffer_out ,
@@ -435,40 +444,43 @@ def write_readinto(
435444 if len (buffer_out [out_start :out_end ]) != len (buffer_in [in_start :in_end ]):
436445 raise RuntimeError ("Buffer slices must be equal length" )
437446
438- start_time = monotonic ()
439- for byte_position , _ in enumerate (buffer_out [out_start :out_end ]):
440- for bit_position in range (self ._bits ):
441- bit_mask = 0x80 >> bit_position
442- bit_value = buffer_out [byte_position + out_start ] & 0x80 >> bit_position
443- in_byte_position = byte_position + in_start
444- # Return clock to 0
445- self ._sclk .value = self ._polarity
446- start_time = self ._wait (start_time )
447- # Handle read on leading edge of clock.
448- if not self ._phase : # Mode 0, 2
449- self ._mosi .value = bit_value
450- if self ._miso .value :
451- # Set bit to 1 at appropriate location.
452- buffer_in [in_byte_position ] |= bit_mask
453- else :
454- # Set bit to 0 at appropriate location.
455- buffer_in [in_byte_position ] &= ~ bit_mask
456- # Flip clock off base
457- self ._sclk .value = not self ._polarity
458- start_time = self ._wait (start_time )
459- # Handle read on trailing edge of clock.
460- if self ._phase : # Mode 1, 3
461- self ._mosi .value = bit_value
462- if self ._miso .value :
463- # Set bit to 1 at appropriate location.
464- buffer_in [in_byte_position ] |= bit_mask
465- else :
466- # Set bit to 0 at appropriate location.
467- buffer_in [in_byte_position ] &= ~ bit_mask
468-
469- # Return pins to base positions
470- self ._mosi .value = 0
471- self ._sclk .value = self ._polarity
447+ if self ._check_lock ():
448+ start_time = monotonic ()
449+ for byte_position , _ in enumerate (buffer_out [out_start :out_end ]):
450+ for bit_position in range (self ._bits ):
451+ bit_mask = 0x80 >> bit_position
452+ bit_value = (
453+ buffer_out [byte_position + out_start ] & 0x80 >> bit_position
454+ )
455+ in_byte_position = byte_position + in_start
456+ # Return clock to 0
457+ self ._sclk .value = self ._polarity
458+ start_time = self ._wait (start_time )
459+ # Handle read on leading edge of clock.
460+ if not self ._phase : # Mode 0, 2
461+ self ._mosi .value = bit_value
462+ if self ._miso .value :
463+ # Set bit to 1 at appropriate location.
464+ buffer_in [in_byte_position ] |= bit_mask
465+ else :
466+ # Set bit to 0 at appropriate location.
467+ buffer_in [in_byte_position ] &= ~ bit_mask
468+ # Flip clock off base
469+ self ._sclk .value = not self ._polarity
470+ start_time = self ._wait (start_time )
471+ # Handle read on trailing edge of clock.
472+ if self ._phase : # Mode 1, 3
473+ self ._mosi .value = bit_value
474+ if self ._miso .value :
475+ # Set bit to 1 at appropriate location.
476+ buffer_in [in_byte_position ] |= bit_mask
477+ else :
478+ # Set bit to 0 at appropriate location.
479+ buffer_in [in_byte_position ] &= ~ bit_mask
480+
481+ # Return pins to base positions
482+ self ._mosi .value = 0
483+ self ._sclk .value = self ._polarity
472484
473485 # pylint: enable=too-many-branches
474486
0 commit comments