diff options
| author | Trung Tran <trung.tran@ettus.com> | 2018-10-02 17:03:11 -0700 | 
|---|---|---|
| committer | Brent Stapleton <bstapleton@g.hmc.edu> | 2018-10-22 10:37:09 -0700 | 
| commit | b24f8495c592ff6c8ff1a82760df5b6b3d1e7163 (patch) | |
| tree | bd51c9d0abe0f8fd0d301e241ad4338c9a54d38d /mpm/python/usrp_mpm | |
| parent | 5e548c1a08cc559e30507b6dbe5c408a9bf96f51 (diff) | |
| download | uhd-b24f8495c592ff6c8ff1a82760df5b6b3d1e7163.tar.gz uhd-b24f8495c592ff6c8ff1a82760df5b6b3d1e7163.tar.bz2 uhd-b24f8495c592ff6c8ff1a82760df5b6b3d1e7163.zip | |
mpm:n3xx: improve set_time_source,set_clock_source
Add coercing behavior to set_time_source and set_clock_source to
a valid sync source. Also, skip set_sync_source if device already
set to the corresponding one.
Diffstat (limited to 'mpm/python/usrp_mpm')
| -rw-r--r-- | mpm/python/usrp_mpm/periph_manager/n3xx.py | 138 | 
1 files changed, 88 insertions, 50 deletions
| diff --git a/mpm/python/usrp_mpm/periph_manager/n3xx.py b/mpm/python/usrp_mpm/periph_manager/n3xx.py index 48ad48a25..8e396411d 100644 --- a/mpm/python/usrp_mpm/periph_manager/n3xx.py +++ b/mpm/python/usrp_mpm/periph_manager/n3xx.py @@ -149,6 +149,17 @@ class n3xx(ZynqComponents, PeriphManagerBase):          },      } +    ######################################################################### +    # Others properties +    ######################################################################### +     # All valid sync_sources for N3xx in the form of (clock_source, time_source) +    valid_sync_sources = { +        ('internal', 'internal'), +        ('internal', 'sfp0'), +        ('external', 'external'), +        ('external', 'internal'), +        ('gpsdo', 'gpsdo'), +    }      @classmethod      def generate_device_info(cls, eeprom_md, mboard_info, dboard_infos):          """ @@ -374,8 +385,11 @@ class n3xx(ZynqComponents, PeriphManagerBase):          # We need to disable the PPS out during clock and dboard initialization in order          # to avoid glitches.          self.enable_pps_out(False) -        if "clock_source" in args or "time_source" in args: -            self.set_sync_source(args) +        # if there's no clock_source or time_source params, we added here since +        # dboards init procedures need them. +        args['clock_source'] = args.get('clock_source', N3XX_DEFAULT_CLOCK_SOURCE) +        args['time_source'] = args.get('time_source', N3XX_DEFAULT_TIME_SOURCE) +        self.set_sync_source(args)          # Uh oh, some hard coded product-related info: The N300 has no LO          # source connectors on the front panel, so we assume that if this was          # selected, it was an artifact from N310-related code. The user gets @@ -523,7 +537,19 @@ class n3xx(ZynqComponents, PeriphManagerBase):      def set_clock_source(self, *args):          " Sets a new reference clock source "          clock_source = args[0] -        source = {"clock_source": clock_source} +        time_source = self._time_source +        assert clock_source is not None +        assert time_source is not None +        if (clock_source, time_source) not in self.valid_sync_sources: +            if clock_source == 'internal': +                time_source = 'internal' +            elif clock_source == 'external': +                time_source = 'external' +            elif clock_source == 'gpsdo': +                time_source = 'gpsdo' +        source = {"clock_source": clock_source, +                  "time_source": time_source +                 }          self.set_sync_source(source)      def get_time_sources(self): @@ -536,7 +562,21 @@ class n3xx(ZynqComponents, PeriphManagerBase):      def set_time_source(self, time_source):          " Set a time source " -        source = {"time_source": time_source} +        clock_source = self._clock_source +        assert clock_source != None +        assert time_source != None +        if (clock_source, time_source) not in self.valid_sync_sources: +            if time_source == 'sfp0': +                clock_source = 'internal' +            elif time_source == 'internal': +                clock_source = 'internal' +            elif time_source == 'external': +                clock_source = 'external' +            elif time_source == 'gpsdo': +                clock_source = 'gpsdo' +        source = {"time_source": time_source, +                  "clock_source": clock_source +                 }          self.set_sync_source(source)      def set_sync_source(self, args): @@ -544,54 +584,52 @@ class n3xx(ZynqComponents, PeriphManagerBase):          Selects reference clock and PPS sources. Unconditionally re-applies the time          source to ensure continuity between the reference clock and time rates.          """ +          clock_source = args.get('clock_source', self._clock_source) -        if clock_source != self._clock_source: -            assert clock_source in self.get_clock_sources() -            self.log.debug("Setting clock source to `{}'".format(clock_source)) -            # Place the DB clocks in a safe state to allow reference clock -            # transitions. This leaves all the DB clocks OFF. -            for slot, dboard in enumerate(self.dboards): -                if hasattr(dboard, 'set_clk_safe_state'): -                    self.log.trace( -                        "Setting dboard %d components to safe clocking state...", slot) -                    dboard.set_clk_safe_state() -            # Disable the Ref Clock in the FPGA before throwing the external switches. -            self.mboard_regs_control.enable_ref_clk(False) -            # Set the external switches to bring in the new source. -            if clock_source == 'internal': -                self._gpios.set("CLK-MAINSEL-EX_B") -                self._gpios.set("CLK-MAINSEL-25MHz") -                self._gpios.reset("CLK-MAINSEL-GPS") -            elif clock_source == 'gpsdo': -                self._gpios.set("CLK-MAINSEL-EX_B") -                self._gpios.reset("CLK-MAINSEL-25MHz") -                self._gpios.set("CLK-MAINSEL-GPS") -            else: # external -                self._gpios.reset("CLK-MAINSEL-EX_B") -                self._gpios.reset("CLK-MAINSEL-GPS") -                # SKY13350 needs to be in known state -                self._gpios.set("CLK-MAINSEL-25MHz") -            self._clock_source = clock_source -            self.log.debug("Reference clock source is: {}" \ -                           .format(self._clock_source)) -            self.log.debug("Reference clock frequency is: {} MHz" \ -                           .format(self.get_ref_clock_freq()/1e6)) -            # Enable the Ref Clock in the FPGA after giving it a chance to -            # settle. The settling time is a guess. -            time.sleep(0.100) -            self.mboard_regs_control.enable_ref_clk(True) -        else: -            self.log.trace("New reference clock source " -                           "assignment matches previous assignment. Ignoring " -                           "update command.") -        # Whenever the clock source changes, re-apply the time source to ensure -        # frequency changes are applied to the internal PPS counters. -        # If the time_source is not passed as an arg, use the current source. +        assert clock_source in self.get_clock_sources()          time_source = args.get('time_source', self._time_source)          assert time_source in self.get_time_sources() -        # Perform the assignment regardless of whether the source was previously -        # selected, since the internal PPS generator needs to change depending on the -        # refclk frequency. +        if (clock_source == self._clock_source) and (time_source == self._time_source): +            # Nothing change no need to do anything +            self.log.trace("New sync source assignment matches" +                           "previous assignment. Ignoring update command.") +            return +        assert (clock_source, time_source) in self.valid_sync_sources +        # Start setting sync source +        self.log.debug("Setting clock source to `{}'".format(clock_source)) +        # Place the DB clocks in a safe state to allow reference clock +        # transitions. This leaves all the DB clocks OFF. +        for slot, dboard in enumerate(self.dboards): +            if hasattr(dboard, 'set_clk_safe_state'): +                self.log.trace( +                    "Setting dboard %d components to safe clocking state...", slot) +                dboard.set_clk_safe_state() +        # Disable the Ref Clock in the FPGA before throwing the external switches. +        self.mboard_regs_control.enable_ref_clk(False) +        # Set the external switches to bring in the new source. +        if clock_source == 'internal': +            self._gpios.set("CLK-MAINSEL-EX_B") +            self._gpios.set("CLK-MAINSEL-25MHz") +            self._gpios.reset("CLK-MAINSEL-GPS") +        elif clock_source == 'gpsdo': +            self._gpios.set("CLK-MAINSEL-EX_B") +            self._gpios.reset("CLK-MAINSEL-25MHz") +            self._gpios.set("CLK-MAINSEL-GPS") +        else: # external +            self._gpios.reset("CLK-MAINSEL-EX_B") +            self._gpios.reset("CLK-MAINSEL-GPS") +            # SKY13350 needs to be in known state +            self._gpios.set("CLK-MAINSEL-25MHz") +        self._clock_source = clock_source +        self.log.debug("Reference clock source is: {}" \ +                       .format(self._clock_source)) +        self.log.debug("Reference clock frequency is: {} MHz" \ +                       .format(self.get_ref_clock_freq()/1e6)) +        # Enable the Ref Clock in the FPGA after giving it a chance to +        # settle. The settling time is a guess. +        time.sleep(0.100) +        self.mboard_regs_control.enable_ref_clk(True) +        self.log.debug("Setting time source to `{}'".format(time_source))          self._time_source = time_source          ref_clk_freq = self.get_ref_clock_freq()          self.mboard_regs_control.set_time_source(time_source, ref_clk_freq) @@ -636,7 +674,7 @@ class n3xx(ZynqComponents, PeriphManagerBase):                  ref_clk_freq,                  time_source=time_source,                  clock_source=clock_source, -                skip_rfic= args.get('skip_rfic', None) +                skip_rfic=args.get('skip_rfic', None)              )      def set_ref_clock_freq(self, freq): | 
