def __init__(self, cs_bar_pin, clk_pin=1000000, mosi_pin=0, miso_pin=0, chip='MCP3208',
                 channel_max=None, bit_length=None, single_ended=True):
        """Initialize the code and set the GPIO pins.
        The last argument, ch_max, is 2 for the MCP3202, 4 for the
        MCP3204 or 8 for the MCS3208."""

        self._CLK = clk_pin
        self._MOSI = mosi_pin
        self._MISO = miso_pin
        self._CS_bar = cs_bar_pin

        chip_dictionary = {
                "MCP3202": (2, 12),
                "MCP3204": (4, 12),
                "MCP3208": (8, 12),
                "MCP3002": (2, 10),
                "MCP3004": (4, 10),
                "MCP3008": (8, 10)
        }

        if chip in chip_dictionary:
            self._ChannelMax = chip_dictionary[chip][0]
            self._BitLength = chip_dictionary[chip][1]
        elif chip is None and (channel_max is not None) and (bit_length is not None):
            self._ChannelMax = channel_max
            self._BitLength = bit_length
        else:
            print("Unknown chip: {} - Please re-initialize.")
            self._ChannelMax = 0
            self._BitLength = 0
            return

        self._SingleEnded = single_ended
        self._Vref = 3.3
        self._values = MyValues(self.read_adc, self._ChannelMax)
        self._volts = MyValues(self.read_volts, self._ChannelMax)

        # This is used to speed up the SPIDEV communication. Send out MSB first.
        # control[0] - bit7-3: upper 5 bits 0, because we can only send 8 bit sequences.
        #            - bit2   : Start bit - starts conversion in ADCs
        #            - bit1   : Select single_ended=1 or differential=0
        #            - bit0   : D2 high bit of channel select.
        # control[1] - bit7   : D1 middle bit of channel select.
        #            - bit6   : D0 low bit of channel select.
        #            - bit5-0 : Don't care.
        if self._SingleEnded:
            self._control0 = [0b00000110, 0b00100000, 0]  # Pre-compute part of the control word.
        else:
            self._control0 = [0b00000100, 0b00100000, 0]  # Pre-compute part of the control word.

        if self._MOSI > 0:  # Bing Bang mode
            assert self._MISO != 0 and self._CLK < 32
            if GPIO.getmode() != 11:
                GPIO.setmode(GPIO.BCM)        # Use the BCM numbering scheme

            GPIO.setup(self._CLK, GPIO.OUT)     # Setup the ports for in and output
            GPIO.setup(self._MOSI, GPIO.OUT)
            GPIO.setup(self._MISO, GPIO.IN)
            GPIO.setup(self._CS_bar, GPIO.OUT)

            GPIO.output(self._CLK, 0)           # Set the clock low.
            GPIO.output(self._MOSI, 0)          # Set the Master Out low
            GPIO.output(self._CS_bar, 1)        # Set the CS_bar high

        else:
            self._dev = spidev.SpiDev(0, self._CS_bar)  # Start a SpiDev device
            self._dev.mode = 0                          # Set SPI mode (phase)
            self._dev.max_speed_hz = self._CLK          # Set the data rate
            self._dev.bits_per_word = 8                 # Number of bit per word. ALWAYS 8