Beispiel #1
0
                                       transition_width=25)

    @exported_value(type=BandShape, changes='never')
    def get_band_shape(self):
        """implement IDemodulator"""
        return BandShape.bandpass_transition(
            low=-self.__cutoff,
            high=self.__cutoff,
            transition=self.__transition_width,
        )

    def get_output_type(self):
        """implement IDemodulator"""
        return SignalType(kind='MONO', sample_rate=self.__demod_rate)

    @exported_value(type=unicode, changes='continuous')
    def get_text(self):
        message = safe_delete_head_nowait(self.__char_queue)
        if message:
            textstring = self.__text
            textstring += message.to_string().decode('us-ascii')
            # TODO: Make the buffer longer and arrange so partial updates rather than the entire buffer can be sent to clients.
            self.__text = textstring[-100:]
        return self.__text


pluginMode = ModeDef(mode='PSK31',
                     info='PSK31',
                     demod_class=PSK31Demodulator,
                     available=_available)
Beispiel #2
0
    def get_angle(self):
        return self.__angle

    @setter
    def set_angle(self, value):
        value = float(value)
        compensation = math.pi / 180 * -6.5  # empirical, calibrated against VOR receiver (and therefore probably wrong)
        value = value + compensation
        value = value % (2 * math.pi)
        phase_shift = int(self.__rf_rate / self.__vor_sig_freq *
                          (value / (2 * math.pi)))
        self.__delay.set_dly(phase_shift)
        self.__angle = value

    def get_input_type(self):
        return SignalType(kind='MONO', sample_rate=self.__audio_rate)

    def get_output_type(self):
        return SignalType(kind='IQ', sample_rate=self.__rf_rate)


# Twisted plugin exports
pluginMode = ModeDef(mode='VOR',
                     info='VOR',
                     demod_class=VOR,
                     mod_class=VORModulator)
pluginClient = ClientResourceDef(
    key=__name__,
    resource=static.File(os.path.join(os.path.split(__file__)[0], 'client')),
    load_js_path='vor.js')
Beispiel #3
0
    def __lineReceived(self, line):
        if line == '':  # observed glitch in output
            pass
        elif line.startswith('Enabled demodulators:'):
            pass
        elif line.startswith(
                '$ULTW'
        ) and self.__last_line is not None:  # observed glitch in output; need to glue to previous line, I think?
            ll = self.__last_line
            self.__last_line = None
            self.__target(ll + line)
        elif line.startswith('APRS: '):
            line = line[len('APRS: '):]
            self.__last_line = line
            self.__target(line)
        else:
            # TODO: Log these properly
            print 'Not APRS line: %r' % line


# TODO: Arrange for a way for the user to see why it is unavailable.
_multimon_available = test_subprocess('multimon-ng -h; exit 0',
                                      'available demodulators:',
                                      shell=True)

pluginDef_APRS = ModeDef(
    mode='APRS',  # TODO: Rename mode to be more accurate
    info='APRS',
    demod_class=FMAPRSDemodulator,
    available=_multimon_available)
Beispiel #4
0
        self.state_changed()
        if shape_changed:
            self.state_shape_changed()

    def is_interesting(self):
        """Implements ITelemetryObject."""
        return True

    def get_object_expiry(self):
        """implement ITelemetryObject"""
        return self.__last_heard_time + drop_unheard_timeout_seconds

    @exported_value(type=TimestampT(), changes='explicit', label='Last heard')
    def get_last_heard_time(self):
        return self.__last_heard_time


# TODO: Arrange for a way for the user to see why it is unavailable.
_rtl_433_available = test_subprocess(['rtl_433', '-r', '/dev/null'],
                                     'Reading samples from file',
                                     shell=False)

plugin_mode = ModeDef(
    mode='433',
    info=EnumRow(
        label='rtl_433',
        description='OOK telemetry decoded by rtl_433 mostly found at 433 MHz'
    ),
    demod_class=RTL433Demodulator,
    available=_rtl_433_available)
Beispiel #5
0
#
# ShinySDR is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with ShinySDR.  If not, see <http://www.gnu.org/licenses/>.

from __future__ import absolute_import, division, print_function, unicode_literals

from twisted.python.util import sibpath
from twisted.web import static

from shinysdr.interfaces import ModeDef, ClientResourceDef

from .demodulator import WSPRDemodulator, find_wsprd

plugin_mode = ModeDef(
    mode='WSPR',
    info='WSPR',
    demod_class=WSPRDemodulator,
    unavailability=None if find_wsprd() else 'wsprd not found.')

plugin_client = ClientResourceDef(key=__name__,
                                  resource=static.File(
                                      sibpath(__file__, 'client')),
                                  load_js_path='wspr.js')

__all__ = []
Beispiel #6
0
        Output has frequencies from -250 to +250.
        '''
        return MultistageChannelFilter(input_rate=self.__input_rate,
                                       output_rate=self.__demod_rate,
                                       cutoff_freq=250 - 25,
                                       transition_width=25)

    def state_def(self):
        for d in super(PSK31Demodulator, self).state_def():
            yield d
        # TODO make this possible to be decorator style
        yield 'text', self.__text_cell

    @exported_value(type=BandShape, changes='never')
    def get_band_shape(self):
        """implement IDemodulator"""
        return BandShape.bandpass_transition(
            low=-self.__cutoff,
            high=self.__cutoff,
            transition=self.__transition_width)

    def get_output_type(self):
        """implement IDemodulator"""
        return SignalType(kind='MONO', sample_rate=self.__demod_rate)


pluginMode = ModeDef(mode='PSK31',
                     info='PSK31',
                     demod_class=PSK31Demodulator,
                     unavailability=_unavailability)
Beispiel #7
0
        @exported_value(type=_uvquality_range,
                        changes='this_setter',
                        label='Unvoiced speech quality',
                        parameter='uvquality')
        def get_uvquality(self):
            return self.__uvquality

        @setter
        def set_uvquality(self, value):
            value = _uvquality_range(value)
            if self.__uvquality != value:
                self.__uvquality = value
                self.__do_connect()

    def get_output_type(self):
        return self.__output_type

    @exported_value(type=BandShape, changes='never')
    def get_band_shape(self):
        return self.__fm_demod.get_band_shape()


_modeDef = ModeDef(
    mode=
    u'DSD',  # TODO: Ought to declare all the individual modes that DSD can decode -- once we have a way to not spam the mode selector with that.
    info=EnumRow(
        label=u'DSD',
        description=u'All modes DSD can decode (P25, DMR, D-STAR, …)'),
    demod_class=DSDDemodulator,
    available=bool(_available_version))
from shinysdr.interfaces import ModeDef
from shinysdr.types import EnumRow

plugin_available = ModeDef(mode='available',
                           info=EnumRow(label='expected available'),
                           demod_class=object(),
                           unavailability=None)

plugin_unavailable = ModeDef(mode='unavailable',
                             info=EnumRow(label='expected unavailable'),
                             demod_class=object(),
                             unavailability='For testing.')
Beispiel #9
0
    @exported_value(type=int,
                    changes='explicit',
                    sort_key='050',
                    label='Ident')  # TODO naming may be wrong
    def get_ident(self):
        return self.__ident

    @exported_value(type=six.text_type,
                    changes='explicit',
                    sort_key='020',
                    label='Aircraft type')
    def get_aircraft_type(self):
        return self.__aircraft_type

    @exported_value(type=Track, changes='explicit', sort_key='010', label='')
    def get_track(self):
        return self.__track


plugin_mode = ModeDef(mode='MODE-S',
                      info=EnumRow(
                          label='Mode S',
                          description='Aviation telemetry found at 1090 MHz'),
                      demod_class=ModeSDemodulator,
                      unavailability=_unavailability)
plugin_client = ClientResourceDef(
    key=__name__,
    resource=static.File(os.path.join(os.path.split(__file__)[0], 'client')),
    load_js_path='mode_s.js')
Beispiel #10
0
                        changes='this_setter',
                        label='Unvoiced speech quality',
                        parameter='uvquality')
        def get_uvquality(self):
            return self.__uvquality

        @setter
        def set_uvquality(self, value):
            value = _uvquality_range(value)
            if self.__uvquality != value:
                self.__uvquality = value
                self.__do_connect(True)

    def get_output_type(self):
        return self.__output_type

    @exported_value(type=BandShape, changes='never')
    def get_band_shape(self):
        return self.__fm_demod.get_band_shape()


_modeDef = ModeDef(
    mode=
    u'DSD',  # TODO: Ought to declare all the individual modes that DSD can decode -- once we have a way to not spam the mode selector with that.
    info=EnumRow(
        label=u'DSD',
        description=u'All modes DSD can decode (P25, DMR, D-STAR, …)'),
    demod_class=DSDDemodulator,
    unavailability=None
    if _available_version else 'dsd.dsd_block_ff not found.')
Beispiel #11
0

# Not usable because python blocks have bad interactions with reconfiguration or something.
# class RTTYEncoder(gr.basic_block):
#   """
#   Convert ASCII to a bit-stream with 2 bits per symbol (except for stop bits which are 3).
#   """
#   def __init__(self):
#       gr.basic_block.__init__(self,
#           name=type(self).__name__,
#           in_sig=[numpy.uint8],
#           out_sig=[numpy.float32])
#   
#   def forecast(self, noutput_items, ninput_items_required):
#       ninput_items_required[0] = int(math.ceil(noutput_items / _HALF_BITS_PER_CODE))
#   
#   def general_work(self, input_items, output_items):
#       char_in = input_items[0]
#       bits_out = output_items[0]
#       count_in, count_out = _encode_rtty(char_in, bits_out)
#       self.consume_each(count_in)
#       return count_out


# Plugin exports
pluginMode = ModeDef(mode='RTTY',
    info='RTTY',
    demod_class=RTTYDemodulator,
    mod_class=RTTYModulator,
    unavailability=_unavailability)
Beispiel #12
0
                                        mode=mode,
                                        stereo=True,
                                        audio_rate=audio_rate,
                                        demod_rate=audio_rate,
                                        band_filter=audio_rate * 0.5,
                                        band_filter_transition=audio_rate *
                                        0.2,
                                        **kwargs)

        self.split_block = blocks.complex_to_float(1)

        self.connect(self, self.band_filter_block, self.rf_squelch_block, self)
        self.connect(self.band_filter_block, self.rf_probe_block)


pluginDef_iq = ModeDef(mode='IQ', info='Raw I/Q', demod_class=IQDemodulator)

_am_lower_cutoff_freq = 40
_am_audio_bandwidth = 7500
_am_demod_method_type = EnumT({
    u'async': u'Asynchronous',
    u'lsb': u'Lower sideband',
    u'usb': u'Upper sideband',
    u'stereo': u'ISB stereo',
})


class AMDemodulator(SimpleAudioDemodulator):
    """Amplitude modulation (AM) demodulator."""

    __demod_rate = 16000
Beispiel #13
0
    return out[:count_out]


# Not usable because python blocks have bad interactions with reconfiguration or something.
# class RTTYEncoder(gr.basic_block):
#   """
#   Convert ASCII to a bit-stream with 2 bits per symbol (except for stop bits which are 3).
#   """
#   def __init__(self):
#       gr.basic_block.__init__(self,
#           name=type(self).__name__,
#           in_sig=[numpy.uint8],
#           out_sig=[numpy.float32])
#
#   def forecast(self, noutput_items, ninput_items_required):
#       ninput_items_required[0] = int(math.ceil(noutput_items / _HALF_BITS_PER_CODE))
#
#   def general_work(self, input_items, output_items):
#       char_in = input_items[0]
#       bits_out = output_items[0]
#       count_in, count_out = _encode_rtty(char_in, bits_out)
#       self.consume_each(count_in)
#       return count_out

# Plugin exports
pluginMode = ModeDef(mode='RTTY',
                     info='RTTY',
                     demod_class=RTTYDemodulator,
                     mod_class=RTTYModulator,
                     available=_available)
Beispiel #14
0
# (at your option) any later version.
#
# ShinySDR is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with ShinySDR.  If not, see <http://www.gnu.org/licenses/>.

from __future__ import absolute_import, division, unicode_literals

from twisted.python.util import sibpath
from twisted.web import static

from shinysdr.interfaces import ModeDef, ClientResourceDef

from .demodulator import WSPRDemodulator, find_wsprd

plugin_mode = ModeDef(mode='WSPR',
                      info='WSPR',
                      demod_class=WSPRDemodulator,
                      available=find_wsprd() is not None)

plugin_client = ClientResourceDef(key=__name__,
                                  resource=static.File(
                                      sibpath(__file__, 'client')),
                                  load_js_path='wspr.js')

__all__ = []
Beispiel #15
0

# Not usable because python blocks have bad interactions with reconfiguration or something.
# class RTTYEncoder(gr.basic_block):
#   """
#   Convert ASCII to a bit-stream with 2 bits per symbol (except for stop bits which are 3).
#   """
#   def __init__(self):
#       gr.basic_block.__init__(self,
#           name=type(self).__name__,
#           in_sig=[numpy.uint8],
#           out_sig=[numpy.float32])
#   
#   def forecast(self, noutput_items, ninput_items_required):
#       ninput_items_required[0] = int(math.ceil(noutput_items / _HALF_BITS_PER_CODE))
#   
#   def general_work(self, input_items, output_items):
#       char_in = input_items[0]
#       bits_out = output_items[0]
#       count_in, count_out = _encode_rtty(char_in, bits_out)
#       self.consume_each(count_in)
#       return count_out


# Plugin exports
pluginMode = ModeDef(mode='RTTY',
    info='RTTY',
    demod_class=RTTYDemodulator,
    mod_class=RTTYModulator,
    available=_available and False)  # disabled until it works better