Beispiel #1
0
    def configure(self,
                  polarity=None,
                  presc=None,
                  filter=None,
                  msec=None,
                  confirm=True):
        """
        Re-configure some capture parameters. None = unchanged

        polarity:  0,1  active level
        presc: 1,2,4,8  pulse counter prescaller
        filter:   0-15  digital input filter
        msec:   <65535  milliseconds for direct capture
        """

        if polarity is not None:
            pb = gex.PayloadBuilder()
            pb.u8(polarity)  # 0,1
            self._send(CMD_SET_POLARITY, pld=pb.close(), confirm=confirm)

        if presc is not None:
            pb = gex.PayloadBuilder()
            pb.u8(presc)
            self._send(CMD_SET_DIR_PRESC, pld=pb.close(), confirm=confirm)

        if filter is not None:
            pb = gex.PayloadBuilder()
            pb.u8(filter)
            self._send(CMD_SET_INPUT_FILTER, pld=pb.close(), confirm=confirm)

        if msec is not None:
            pb = gex.PayloadBuilder()
            pb.u16(msec)
            self._send(CMD_SET_DIR_MSEC, pld=pb.close(), confirm=confirm)
Beispiel #2
0
    def indirect_burst(self, count, timeout=5):
        """
        Perform a burst measure with averaging (sum/count)
        """

        pb = gex.PayloadBuilder()
        pb.u16(count)

        resp = self._query(CMD_INDIRECT_BURST_START,
                           pld=pb.close(),
                           timeout=timeout)
        pp = gex.PayloadParser(resp.data)

        mhz = pp.u16()
        nsamp = pp.u16()
        period = pp.u64()
        ontime = pp.u64()

        rp = FCAP_Report()
        rp.period = period / (nsamp * mhz * 1e6)  # to seconds
        rp.frequency = 1 / rp.period
        rp.ontime = ontime / (nsamp * mhz * 1e6)  # in seconds
        rp.duty = rp.ontime / rp.period

        rp.clock_freq = mhz * 1e6
        rp.sample_count = 1
        rp.period_raw = period
        rp.ontime_raw = ontime

        return rp
Beispiel #3
0
    def waveform(self, channel, waveform, confirm=True):
        """
        Set a waveform. For DC or rectangle,
        use the dedicated functions with extra parameters

        channel: 1,2 (3 = both)
        waveform:
        - None - leave unchanged
        - SINE
        - TRIANGLE
        - SAW_UP
        - SAW_DOWN
        """

        lookup = {
            'SINE': CMD_WAVE_SINE,
            'SIN': CMD_WAVE_SINE,
            'TRI': CMD_WAVE_TRIANGLE,
            'TRIANGLE': CMD_WAVE_TRIANGLE,
            'SAW': CMD_WAVE_SAWTOOTH_UP,
            'RAMP': CMD_WAVE_SAWTOOTH_UP,
            'RAMP_UP': CMD_WAVE_SAWTOOTH_UP,
            'SAW_UP': CMD_WAVE_SAWTOOTH_UP,
            'SAW_DOWN': CMD_WAVE_SAWTOOTH_DOWN,
            'RAMP_DOWN': CMD_WAVE_SAWTOOTH_DOWN,
        }

        if channel != 1 and channel != 2 and channel != 3:
            raise Exception("Bad channel arg: %s" % channel)

        pb = gex.PayloadBuilder()
        pb.u8(channel)  # 0b01 or 0b10
        self._send(lookup[waveform], pld=pb.close(), confirm=confirm)
Beispiel #4
0
    def set_button_thresholds(self, thresholds, confirm=True):
        """ Set binary report thresholds """
        pb = gex.PayloadBuilder()
        for t in thresholds:
            pb.u16(t)

        self._send(CMD_SET_BIN_THR, pb.close(), confirm=confirm)
Beispiel #5
0
    def write(self, payload, addr=0, confirm=True):
        """ Write to a device """
        pb = gex.PayloadBuilder()
        pb.u64(addr)
        pb.blob(payload)

        self._send(10, pb.close(), confirm=confirm)
Beispiel #6
0
 def pulse_ms(self, ms, pins=0b01, active=True, confirm=True):
     """ Send a pulse with length 1-65535 ms on selected pins """
     pb = gex.PayloadBuilder()
     pb.u16(self.pins2int(pins))
     pb.bool(active)
     pb.bool(False)
     pb.u16(ms)
     self._send(CMD_PULSE, pb.close(), confirm=confirm)
Beispiel #7
0
 def pulse_us(self, us, pins=1, active=True, confirm=True):
     """ Send a pulse of 1-999 us on selected pins """
     pb = gex.PayloadBuilder()
     pb.u16(self.pins2int(pins))
     pb.bool(active)
     pb.bool(True)
     pb.u16(us)
     self._send(CMD_PULSE, pb.close(), confirm=confirm)
Beispiel #8
0
    def gw_add_nodes(self, nodes):
        pb = gex.PayloadBuilder()
        pb.u8(ord('n'))
        pb.u8(len(nodes))

        for n in nodes:
            pb.u8(n)

        self.gw_write_raw(pb)
Beispiel #9
0
 def arm(self, pins, auto: bool = False, confirm: bool = False):
     """
     Arm pins for single shot event generation
     pins - array of pin indices to arm
     auto - use auto trigger (auto re-arm after hold-off)
     """
     pb = gex.PayloadBuilder()
     pb.u16(self.pins2int(pins))
     self._send(0x02 if auto else 0x01, pb.close())
Beispiel #10
0
    def disarm(self, pins, confirm: bool = False):
        """
        DisArm pins
        pins - array of pin indices to arm
        """

        pb = gex.PayloadBuilder()
        pb.u16(self.pins2int(pins))
        self._send(0x03, pb.close())
Beispiel #11
0
    def ini_write(self, buffer):
        """ Read the settings INI file """
        if type(buffer) == str:
            buffer = buffer.encode('utf-8')

        pb = gex.PayloadBuilder()
        pb.u32(len(buffer))

        self.bulk_write(cs=None, pld=pb.close(), cmd=gex.MSG_INI_WRITE, bulk=buffer)
Beispiel #12
0
    def set_duty(self, duty_dict, confirm=True):
        """ Set duty (dict - number1234 -> duty 0-1000) """
        pb = gex.PayloadBuilder()

        for (k, v) in enumerate(duty_dict):
            pb.u8(k - 1)
            pb.u16(v)

        self._send(CMD_SET_DUTY, pb.close(), confirm=confirm)
Beispiel #13
0
    def dc_dual(self, ch1, ch2, confirm=True):
        """
        Set DC levels, 0-4095
        """

        pb = gex.PayloadBuilder()
        pb.u8(0b11)
        pb.u16(ch1)
        pb.u16(ch2)
        self._send(CMD_WAVE_DC, pld=pb.close(), confirm=confirm)
Beispiel #14
0
    def set_active_channels(self, channels, confirm=True):
        """
        Set which channels should be active.
        """

        pb = gex.PayloadBuilder()
        pb.u32(self.pins2int(channels))

        self._send(cmd=CMD_ENABLE_CHANNELS, pld=pb.close(), confirm=confirm)
        self.channels = self.pins2list(channels)
Beispiel #15
0
    def query(self, request, rcount, addr=0, verify=True, as_array=False):
        """ Query a device """
        pb = gex.PayloadBuilder()
        pb.u64(addr)
        pb.u16(rcount)
        pb.bool(verify)
        pb.blob(request)

        resp = self._query(11, pb.close())
        return resp.data if not as_array else list(resp.data)
Beispiel #16
0
    def set_frequency_dual(self, freq1, freq2, confirm=True):
        """
        Set frequency of both channels using float in Hz
        """

        pb = gex.PayloadBuilder()
        pb.u8(0b11)
        pb.float(freq1)
        pb.float(freq2)

        self._send(CMD_SET_FREQUENCY, pld=pb.close(), confirm=confirm)
Beispiel #17
0
    def load(self, colors, reverse=True, confirm=True):
        """
        Load colors to the strip.

        The numbers are normally 0xRRGGBB
        If 'reverse' is false, they're treated as little-endian: 0xBBGGRR.
        """
        pb = gex.PayloadBuilder(endian='big' if reverse else 'little')
        for c in colors:
            pb.u24(c)
        self._send(1, pb.close(), confirm=confirm)
Beispiel #18
0
    def set_phase_dual(self, phase1, phase2, confirm=True):
        """
        Set phase for both channels at once
        """

        pb = gex.PayloadBuilder()
        pb.u8(0b11)
        pb.u16((phase1 / 360) * LUT_LEN)
        pb.u16((phase2 / 360) * LUT_LEN)

        self._send(CMD_SET_PHASE, pld=pb.close(), confirm=confirm)
Beispiel #19
0
    def gw_get_net_id(self):
        if self._address is not None:
            # lazy load
            return self._address

        pb = gex.PayloadBuilder()
        pb.u8(ord('i'))
        self.gw_write_raw(pb)

        self.poll(0.5, lambda: self._address is not None)
        return self._address
Beispiel #20
0
    def load(self, buffers, end=0x0000, confirm=True):
        """ Load data - buffers is a list of lists or byte arrays """
        if type(buffers[0]) == int:
            buffers = [buffers]

        pb = gex.PayloadBuilder()
        pb.u16(end)

        for b in buffers:
            pb.blob(b)

        self._send(CMD_WRITE, pb.close(), confirm=confirm)
Beispiel #21
0
    def write(self, payload, sync=False, confirm=True):
        """
        Write bytes. If 'sync' is True, wait for completion. sync implies confirm
        """

        if type(payload) is str:
            payload = payload.encode('utf-8')

        pb = gex.PayloadBuilder()
        pb.blob(payload)  # payload to write

        self._send(0x01 if sync else 0x00, pb.close(), confirm=confirm or sync)
Beispiel #22
0
    def direct_burst(self, msec=1000, presc=None):
        """
        Perform direct burst measurement
        """

        pb = gex.PayloadBuilder()
        pb.u16(msec)
        pb.u8(presc or 0)

        resp = self._query(CMD_DIRECT_BURST_START,
                           pld=pb.close(),
                           timeout=(msec / 1000) + 1)
        return self._process_direct_resp(resp)
Beispiel #23
0
    def write(self, buffer):
        # multipart sending
        pb = gex.PayloadBuilder()
        pb.u8(ord('m'))
        pb.u8(self._slaveAddr)
        pb.u16(len(buffer))

        ck = 0
        for c in buffer:
            ck ^= c
        ck = 0xFF & ~ck

        pb.u8(ck)

        start = 0
        spaceused = len(pb.buf)
        fits = min(64 - spaceused, len(buffer))
        pb.blob(buffer[start:fits])

        # TODO rewrite this to send_raw

        if (spaceused + fits) < 64:
            pb.zeros(64 - (spaceused + fits))
        start += fits

        buf = pb.close()
        self._transport.write(buf)

        while start < len(buffer):
            pb = gex.PayloadBuilder()
            fits = min(64, len(buffer) - start)
            pb.blob(buffer[start:start + fits])
            start += fits

            if fits < 64:
                pb.zeros(64 - fits)

            buf = pb.close()
            self._transport.write(buf)
Beispiel #24
0
    def set_sample_rate(self, freq: int):
        """ Set sample rate in Hz. Returns the real achieved frequency as float. """
        pb = gex.PayloadBuilder()
        pb.u32(freq)
        msg = self._query(CMD_SET_SAMPLE_RATE, pld=pb.close())
        pp = gex.PayloadParser(msg.data)

        req = pp.u32()
        real = pp.float()

        self.sample_rate = real

        return real
Beispiel #25
0
    def direct_start(self, msec=None, presc=None, confirm=True):
        """
        Start continuous PWM measurement

        msec - measurement time (ms), <65535
        presc - pre-divider, 1,2,4,8.

        arg None = unchanged
        """

        pb = gex.PayloadBuilder()
        pb.u16(msec or 0)
        pb.u8(presc or 0)
        self._send(CMD_DIRECT_CONT_START, pld=pb.close(), confirm=confirm)
Beispiel #26
0
    def arm(self, auto=None, confirm=True):
        """
        ARM for trigger.
        The trigger must be configured first.

        if auto is True or False, it sets the auto-rearm flag.
        """

        pb = gex.PayloadBuilder()

        if auto is None:
            pb.u8(255)
        else:
            pb.u8(1 if auto else 0)

        self._send(cmd=CMD_ARM, pld=pb.close(), confirm=confirm)
Beispiel #27
0
    def set_frequency(self, channel, freq, confirm=True):
        """
        Set frequency using float in Hz
        """

        if channel != 1 and channel != 2 and channel != 3:
            raise Exception("Bad channel arg: %s" % channel)

        pb = gex.PayloadBuilder()
        pb.u8(channel)
        pb.float(freq)

        if channel == 3:
            pb.float(freq)

        self._send(CMD_SET_FREQUENCY, pld=pb.close(), confirm=confirm)
Beispiel #28
0
    def setup_trigger(self,
                      channel,
                      level,
                      count,
                      edge='rising',
                      pretrigger=0,
                      holdoff=100,
                      auto=False,
                      confirm=True,
                      handler=None):
        """
        Configure a trigger.

        channel - 0-17 (16-tsense, 17-vrefint)
        level   - triggering threshold, raw (0-4095)
        count   - nbr of samples to capture after trigger
        edge    - "rising", "falling" or "both"
        pretrigger - nbr of samples to capture before the trigger occurred. Limited by the internal buffer.
        holdoff - hold-off time (trigger also can't fire while the capture is ongoing, and if it's not armed)
        auto    - auto re-arm after completing the capture. Normally the state switches to IDLE.
        handler - attaches a callback handler for the received data
        """

        nedge = 0
        if edge == 'rising' or edge == 'up':
            nedge = 1
        elif edge == 'falling' or edge == 'down':
            nedge = 2
        elif edge == 'both':
            nedge = 3
        else:
            raise Exception("Bad edge arg")

        pb = gex.PayloadBuilder()
        pb.u8(channel)
        pb.u16(level)
        pb.u8(nedge)
        pb.u32(pretrigger)
        pb.u32(count)
        pb.u16(holdoff)
        pb.bool(auto)

        self._send(cmd=CMD_SETUP_TRIGGER, pld=pb.close(), confirm=confirm)

        if handler is not None:
            self._trig_listener = handler
Beispiel #29
0
    def set_phase(self, channel, phase360, confirm=True):
        """
        Set channel phase relative to it's "base phase".
        If both channels use the same frequency, this could be used for drawing XY figures.
        """

        if channel != 1 and channel != 2 and channel != 3:
            raise Exception("Bad channel arg: %s" % channel)

        pb = gex.PayloadBuilder()
        pb.u8(channel)
        pb.u16(round((phase360 / 360) * LUT_LEN))

        if channel == 3:
            pb.u16(round((phase360 / 360) * LUT_LEN))

        self._send(CMD_SET_PHASE, pld=pb.close(), confirm=confirm)
Beispiel #30
0
    def rectangle(self, channel, duty=None, high=None, low=None, confirm=True):
        """ Enter rectangle gen mode (duty 0..1000) """

        if channel != 1 and channel != 2 and channel != 3:
            raise Exception("Bad channel arg: %s" % channel)

        pb = gex.PayloadBuilder()
        pb.u8(channel)  # 0b01 or 0b10

        for i in range(0, 1 if channel != 3 else 2):  # repeat if dual
            pb.u16(
                round(duty * LUT_LEN) if duty is not None  # todo ??
                else 0xFFFF)

            pb.u16(high if high is not None else 0xFFFF)
            pb.u16(low if low is not None else 0xFFFF)

        self._send(CMD_WAVE_RECTANGLE, pld=pb.close(), confirm=confirm)