1 # SPDX-FileCopyrightText: 2021 Melissa LeBlanc-Williams for Adafruit Industries
 
   3 # SPDX-License-Identifier: MIT
 
   6 from adafruit_blinka.microcontroller.ftdi_mpsse.mpsse.url import (
 
  13     """A basic Pin class for use with FTDI MPSSEs."""
 
  25     def __init__(self, pin_id=None, interface_id=None):
 
  26         # setup GPIO controller if not done yet
 
  27         # use one provided by I2C as default
 
  28         if not Pin.mpsse_gpio:
 
  29             # pylint: disable=import-outside-toplevel
 
  30             from pyftdi.i2c import I2cController
 
  32             # pylint: enable=import-outside-toplevel
 
  35             if interface_id is None:
 
  36                 i2c.configure(get_ft232h_url())
 
  38                 i2c.configure(get_ft2232h_url(interface_id))
 
  39             Pin.mpsse_gpio = i2c.get_gpio()
 
  40         # check if pin is valid
 
  42             if Pin.mpsse_gpio.all_pins & 1 << pin_id == 0:
 
  43                 raise ValueError("Can not use pin {} as GPIO.".format(pin_id))
 
  44         # ID is just bit position
 
  47     def init(self, mode=IN, pull=None):
 
  48         """Initialize the Pin"""
 
  50             raise RuntimeError("Can not init a None type pin.")
 
  51         # MPSSE does't have configurable internal pulls?
 
  53             raise NotImplementedError("Internal pull up/down not currently supported.")
 
  54         pin_mask = Pin.mpsse_gpio.pins | 1 << self.id
 
  55         current = Pin.mpsse_gpio.direction
 
  57             current |= 1 << self.id
 
  59             current &= ~(1 << self.id)
 
  60         Pin.mpsse_gpio.set_direction(pin_mask, current)
 
  62     def value(self, val=None):
 
  63         """Set or return the Pin Value"""
 
  65             raise RuntimeError("Can not access a None type pin.")
 
  66         current = Pin.mpsse_gpio.read(with_output=True)
 
  69             return 1 if current & 1 << self.id != 0 else 0
 
  71         if val in (self.LOW, self.HIGH):
 
  73                 current |= 1 << self.id
 
  75                 current &= ~(1 << self.id)
 
  76             # must mask out any input pins
 
  77             Pin.mpsse_gpio.write(current & Pin.mpsse_gpio.direction)
 
  80         raise RuntimeError("Invalid value for pin")