Ejemplo n.º 1
0
    def test_planetaryposition_jupiter(self):
        """Test the location of Jupiter."""

        t0 = transform.Time('2013-01-08 01:23:45.000', format='STR')

        obs = lwa1.get_observer()
        obs.date = t0.utc_str
        jove = ephem.Jupiter()
        jove.compute(obs)

        p0 = transform.PlanetaryPosition('Jupiter')

        self.assertAlmostEqual(
            p0.apparent_equ(t0)[0], jove.g_ra * 180.0 / math.pi, 4)
        self.assertAlmostEqual(
            p0.apparent_equ(t0)[1], jove.g_dec * 180.0 / math.pi, 4)
Ejemplo n.º 2
0
    def test_planetaryposition_saturn(self):
        """Test the location of Saturn."""

        t0 = transform.Time('2013-01-08 01:23:45.000', format='STR')

        obs = lwa1.get_observer()
        obs.date = t0.utc_str
        sat = ephem.Saturn()
        sat.compute(obs)

        p0 = transform.PlanetaryPosition('Saturn')

        self.assertAlmostEqual(
            p0.apparent_equ(t0)[0], sat.g_ra * 180.0 / math.pi, 4)
        self.assertAlmostEqual(
            p0.apparent_equ(t0)[1], sat.g_dec * 180.0 / math.pi, 4)
Ejemplo n.º 3
0
    def test_geographicalposition_lst(self):
        """Test the tranform.GeographicalPosition sidereal time."""

        t0 = transform.Time('2013-01-08 01:23:45.000', format='STR')

        lon = lwa1.long * 180.0 / math.pi
        lat = lwa1.lat * 180.0 / math.pi
        elv = lwa1.elev
        obs = lwa1.get_observer()

        g0 = transform.GeographicalPosition([lon, lat, elv])

        # The astro.get_apparent_sidereal_time() function doesn't care about
        # elevation
        obs.elev = 0.0

        obs.date = t0.utc_str
        self.assertAlmostEqual(g0.sidereal(t0),
                               obs.sidereal_time() * 12.0 / math.pi, 4)
Ejemplo n.º 4
0
    def test_pointingdirection_azalt(self):
        """Test the transform.PointingDirection az/alt transform."""

        t0 = transform.Time('2013-01-08 01:23:45.000', format='STR')

        lon = lwa1.long * 180.0 / math.pi
        lat = lwa1.lat * 180.0 / math.pi
        elv = lwa1.elev
        obs = lwa1.get_observer()
        obs.date = t0.utc_str
        jove = ephem.Jupiter()
        jove.compute(obs)

        g0 = transform.GeographicalPosition([lon, lat, elv])
        p0 = transform.PlanetaryPosition('Jupiter')
        d0 = transform.PointingDirection(p0, g0)
        str(d0)
        repr(d0)

        self.assertAlmostEqual(d0.hrz(t0)[0], jove.az * 180.0 / math.pi, 0)
        self.assertAlmostEqual(d0.hrz(t0)[1], jove.alt * 180.0 / math.pi, 0)
Ejemplo n.º 5
0
    def test_pointingdirection_rst(self):
        """Test the transform.PointingDirection az/alt transform."""

        t0 = transform.Time('2013-01-08 01:23:45.000', format='STR')

        lon = lwa1.long * 180.0 / math.pi
        lat = lwa1.lat * 180.0 / math.pi
        elv = lwa1.elev
        obs = lwa1.get_observer()
        obs.date = t0.utc_str
        jove = ephem.Jupiter()
        jove.compute(obs)

        g0 = transform.GeographicalPosition([lon, lat, elv])
        p0 = transform.PlanetaryPosition('Jupiter')
        d0 = transform.PointingDirection(p0, g0)

        rst = d0.rst(t0)
        self.assertAlmostEqual(rst.rise,
                               obs.next_rising(jove) * 1.0 + DJD_OFFSET, 2)
        self.assertAlmostEqual(rst.transit,
                               obs.next_transit(jove) * 1.0 + DJD_OFFSET, 2)
        self.assertAlmostEqual(rst.set,
                               obs.next_setting(jove) * 1.0 + DJD_OFFSET, 2)
Ejemplo n.º 6
0
def main(args):
    obs = lwa1.get_observer()
    MST = pytz.timezone('US/Mountain')
    UTC = pytz.utc

    if args.date is None or args.time is None:
        dt = datetime.datetime.utcnow()
        dt = UTC.localize(dt)
    else:
        year, month, day = args.date.split('/', 2)
        hour, minute, second = args.time.split(':', 2)
        iSeconds = int(float(second))
        mSeconds = int(round((float(second) - iSeconds) * 1000000))

        if args.utc:
            # UTC
            dt = UTC.localize(
                datetime.datetime(int(year), int(month), int(day), int(hour),
                                  int(minute), iSeconds, mSeconds))

        elif args.sidereal:
            # LST
            dt = astroDate(int(year), int(month), int(day), 0, 0, 0)
            jd = dt.to_jd()

            ## Get the LST in hours
            LST = int(hour) + int(minute) / 60.0 + (iSeconds +
                                                    mSeconds / 1e6) / 3600.0

            ## Get the Greenwich apparent ST for LST using the longitude of
            ## the site.  The site longitude is stored as radians, so convert
            ## to hours first.
            GAST = LST - obs.long * 12 / math.pi

            ## Get the Greenwich mean ST by removing the equation of the
            ## equinoxes (or some approximation thereof)
            GMST = GAST - _getEquinoxEquation(jd)

            ## Get the value of D0, days since January 1, 2000 @ 12:00 UT,
            ## and T, the number of centuries since the year 2000.  The value
            ## of T isn't terribly important but it is nice to include
            D0 = jd - 2451545.0
            T = D0 / 36525.0

            ## Solve for the UT hour for this LST and map onto 0 -> 24 hours
            ## From: http://aa.usno.navy.mil/faq/docs/GAST.php
            H = GMST - 6.697374558 - 0.06570982441908 * D0 - 0.000026 * T**2
            H /= 1.002737909350795
            while H < 0:
                H += 24 / 1.002737909350795
            while H > 24:
                H -= 24 / 1.002737909350795

            ## Get the full Julian Day that this corresponds to
            jd += H / 24.0

            ## Convert the JD back to a time and extract the relevant
            ## quantities needed to build a datetime instance
            dt = astroGetDate(jd)
            year = dt.years
            month = dt.months
            day = dt.days
            hour = dt.hours
            minute = dt.minutes
            second = int(dt.seconds)
            microsecond = int((dt.seconds - second) * 1e6)
            ## Trim the microsecond down to the millisecond level
            microsecond = int(int(microsecond / 1000.0) * 1000)

            ## Localize as the appropriate time zone
            dt = UTC.localize(
                datetime.datetime(year, month, day, hour, minute, second,
                                  microsecond))

        else:
            # Mountain time
            dt = MST.localize(
                datetime.datetime(int(year), int(month), int(day), int(hour),
                                  int(minute), iSeconds, mSeconds))

        dt = dt.astimezone(UTC)

    obs.date = dt.astimezone(UTC).strftime("%Y/%m/%d %H:%M:%S.%f")
    mjd, mpm = datetime_to_mjdmpm(dt)

    print("Localtime: %s" %
          dt.astimezone(MST).strftime("%B %d, %Y at %H:%M:%S %Z"))
    print("UTC: %s" % dt.astimezone(UTC).strftime("%B %d, %Y at %H:%M:%S %Z"))
    print("LST: %s" % obs.sidereal_time())
    print("MJD: %i" % mjd)
    print("MPM: %i" % mpm)
def main(args):
    # Parse the command line
    config = parseOptions(args)

    # Get LWA-1
    observer = lwa1.get_observer()
    print("Current site is %s at lat %s, lon %s" %
          (lwa1.name, observer.lat, observer.long))

    # Set the current time so we can find the "next" transit.  Go ahead
    # and report the time and the current LST (for reference)
    if len(config['args']) == 1:
        config['args'][0] = config['args'][0].replace('-', '/')
        year, month, day = config['args'][0].split('/', 2)
        year = int(year)
        month = int(month)
        day = int(day)
        tNow = _UTC.localize(datetime(year, month, day))

    else:
        tNow = _UTC.localize(datetime.utcnow())
    observer.date = tNow.strftime("%Y/%m/%d %H:%M:%S")
    print("Current time is %s" %
          tNow.astimezone(_UTC).strftime("%Y/%m/%d %H:%M:%S %Z"))
    print("Current LST at %s is %s" % (lwa1.name, observer.sidereal_time()))

    # Load in the sources and compute
    srcs = [ephem.Sun(), ephem.Jupiter()]
    for line in _srcs:
        srcs.append(ephem.readdb(line))
    for i in xrange(len(srcs)):
        srcs[i].compute(observer)

    #
    # Standard prediction output
    #

    # Header
    print("")
    print("%-10s  %-23s" % (
        "Source",
        "Next Transit",
    ))
    print("=" * (10 + 2 + 23))

    # List
    found = False
    for src in srcs:
        if src.name.lower() == config['source'].lower():
            found = True

            nT = str(
                observer.next_transit(
                    src, start=tNow.strftime("%Y/%m/%d %H:%M:%S")))
            nT = _UTC.localize(datetime.strptime(nT, "%Y/%m/%d %H:%M:%S"))

            print("%-10s %-23s" %
                  (src.name, nT.strftime("%Y/%m/%d %H:%M:%S %Z")))
            print("%-10s %-23s" %
                  ("", nT.astimezone(_MST).strftime("%Y/%m/%d %H:%M:%S %Z")))
            print(" ")
            break

    if found:
        startRec = nT - timedelta(seconds=int(round(config['duration'] / 2.0)))
        mjd, mpm = datetime_to_mjdmpm(startRec)
        dur = int(round(config['duration'] * 1000))
        cmd = 'DR5 REC "%i %i %i TBN_FILT_%i"' % (mjd, mpm, dur,
                                                  config['filter'])

        antpols = 520
        sample_rate = tbn_filters[config['filter']]
        dataRate = 1.0 * sample_rate / 512 * tbnFRAME_SIZE * antpols

        print("Recording:")
        print(" Start: %s" % startRec.strftime("%Y/%m/%d %H:%M:%S %Z"))
        print("        %s" %
              startRec.astimezone(_MST).strftime("%Y/%m/%d %H:%M:%S %Z"))
        print(" Duration: %.3f s" % (dur / 1000.0, ))
        print(" TBN Filter Code: %i" % config['filter'])
        print(" Data rate: %.2f MB/s" % (dataRate / 1024**2, ))
        print(" Data volume: %.2f GB" % (dataRate * dur / 1000.0 / 1024**3, ))
        print(" ")

        print("Data Recorder Command:")
        print(" %s" % cmd)
    else:
        raise RuntimeError("Unknown source '%s'" % config['source'])
Ejemplo n.º 8
0
def main(args):
    # Gather the necessary information to figure out where things are
    observer = lwa1.get_observer()
    antennas = lwa1.antennas
    
    # Divy up the command line arguments
    filename = args[0]
    pointingAz = float(args[1])
    pointingEl = float(args[2])
    
    # Load the data
    dataDict = numpy.load(filename)
    ## Frequency
    central_freq = dataDict['central_freq']
    ## Integration time
    tInt = dataDict['tInt']
    ## Start times of the integrations
    times = dataDict['times']
    ## The visiblity data
    phase = dataDict['simpleVis']
    
    print("Central frequency: %.3f Hz" % central_freq)
    
    # Build the source list
    beginDate = datetime.utcfromtimestamp(times[0])
    observer.date = beginDate.strftime("%Y/%m/%d %H:%M:%S")
    srcs = [ephem.Sun(),]
    for line in _srcs:
        srcs.append( ephem.readdb(line) )
    
    # Identify the location of the reference source (the Sun in this case)
    az = -99
    el = -99
    for i in xrange(len(srcs)):
        srcs[i].compute(observer)
            
        if srcs[i].name == 'Sun':
            az = srcs[i].az  * 180.0/numpy.pi
            el = srcs[i].alt * 180.0/numpy.pi
    
    # Generate geometric delay coefficients
    aln = []
    for i in xrange(phase.shape[1]):
        gd = getGeoDelay(antennas[i], az, el, Degrees=True)
        aln.append( numpy.exp(2j*numpy.pi*central_freq*gd) )
    aln = numpy.array(aln)
    
    # Build the c^l_n values from Steve's "Fun with TBN" memo (Eqn. 10)
    cln = numpy.zeros(phase.shape, dtype=numpy.complex128)
    for i in xrange(cln.shape[1]):
        if i % 2 == 0:
            cln[:,i] = phase[:,i] / phase[:,0]
        else:
            cln[:,i] = phase[:,i] / phase[:,1]
    cln /= aln
    
    # Compute the geometric delay for the requested pointing
    alnPointing = []
    for i in xrange(phase.shape[1]):
        gd = getGeoDelay(antennas[i], pointingAz, pointingEl, Degrees=True)
        alnPointing.append( numpy.exp(2j*numpy.pi*central_freq*gd) )
    alnPointing = numpy.array(alnPointing)
    
    # Calculate the beamforming coefficients
    blnPointing = (cln*alnPointing).conj() / numpy.abs(cln*alnPointing)
    
    # Intepret these purely as delays
    delays = numpy.angle(blnPointing) / (2*numpy.pi*central_freq)
    delays = delays.max() - delays
    
    # Save
    import gain
    import delay
    dftBase = 'phased_beam_%.2faz_%.2fel_%iMHz' % (pointingAz, pointingEl, central_freq/1e6,)
    junk = delay.list2delayfile('.', dftBase, delays[0,:]*1e9)
Ejemplo n.º 9
0
def main(args):
    observer = lwa1.get_observer()
    antennas = lwa1.antennas
    
    reference = args[0]
    filename = args[1]
    dataDict = numpy.load(filename)
    
    ref  = dataDict['ref'].item()
    refX = dataDict['refX'].item()
    refY = dataDict['refY'].item()
    central_freq = dataDict['central_freq'].item()
    tInt = dataDict['tInt'].item()
    times = dataDict['times']
    phase = dataDict['simpleVis']
    
    # Get the start time as a datetime object and build up the list of sources
    beginDate = datetime.utcfromtimestamp(times[0])
    observer.date = beginDate.strftime("%Y/%m/%d %H:%M:%S")
    srcs = [ephem.Sun(),]
    for line in _srcs:
        srcs.append( ephem.readdb(line) )
        
    # Report on the data so far...
    print("Central Frequency: %.3f Hz" % central_freq)
    print("Start date/time: %s" % beginDate.strftime("%Y/%m/%d %H:%M:%S"))
    print("Integration Time: %.3f s" % tInt)
    print("Number of time samples: %i (%.3f s)" % (phase.shape[0], phase.shape[0]*tInt))
    
    # Compute the locations of all of the sources to figure out where the 
    # reference is
    print("Starting Source Positions:")
    
    refSrc = None
    for i in xrange(len(srcs)):
        srcs[i].compute(observer)
        
        if srcs[i].alt > 0:
            print(" source %-4s: alt %4.1f degrees, az %5.1f degrees" % (srcs[i].name, srcs[i].alt*180/numpy.pi, srcs[i].az*180/numpy.pi))
            
        if srcs[i].name == reference:
            refSrc = srcs[i]
            
    if refSrc is None:
        print("Cannot find reference source '%s' in source list, aborting." % reference)
        sys.exit(1)
    
    # Calculate the fringe rates of all sources - for display purposes only
    print("Starting Fringe Rates:")
    for src in srcs:
        if src.alt > 0:
            fRate = getFringeRate(antennas[0], antennas[refX], observer, src, central_freq)
            print(" source %-4s: %+6.3f mHz" % (src.name, fRate*1e3))
    
    # Fringe stopping using the reference source
    print("Fringe stopping:")
    pbar = ProgressBar(max=phase.shape[1])

    phase2 = 1.0*phase
    for l in xrange(phase.shape[1]):
        # Compute the fringe rates across all time
        fRate = [None,]*phase.shape[0]
        for i in xrange(phase.shape[0]):
            currDate = datetime.utcfromtimestamp(times[i])
            observer.date = currDate.strftime("%Y/%m/%d %H:%M:%S")
        
            if l % 2 == 0:
                fRate[i] = getFringeRate(antennas[l], antennas[refX], observer, refSrc, central_freq)
            else:
                fRate[i] = getFringeRate(antennas[l], antennas[refY], observer, refSrc, central_freq)
        
        # Create the basis rate and the residual rates
        baseRate = fRate[0]
        residRate = numpy.array(fRate) - baseRate
    
        # Fringe stop to more the source of interest to the DC component
        phase2[:,l] *= numpy.exp(-2j*numpy.pi* baseRate*(times - times[0]))
        phase2[:,l] *= numpy.exp(-2j*numpy.pi*residRate*(times - times[0]))
        
        pbar.inc()
        sys.stdout.write("%s\r" % pbar.show())
        sys.stdout.flush()
    sys.stdout.write('\n')
    
    # Compute the beam forming coefficients for the reference source
    bln = numpy.zeros(phase2.shape, dtype=numpy.complex128)
    for i in xrange(bln.shape[1]):
        if i % 2 == 0:
            bln[:,i] = phase2[:,i] / phase2[:,0]
        else:
            bln[:,i] = phase2[:,i] / phase2[:,1]
    bln = bln.conj() / numpy.abs(bln)
    
    # Average all time steps together and make sure we end up with 
    # a 2-D array in the end
    bln = bln.mean(axis=0)
    bln.shape = (1,) + bln.shape
    
    # Compute the a^l_n terms for removing the array geometry.
    print("Computing array geometry:")
    pbar = ProgressBar(max=phase2.shape[1])
    
    aln = numpy.zeros_like(phase2)
    for l in xrange(phase2.shape[1]):
        currDate = datetime.utcfromtimestamp(times[0])
        observer.date = currDate.strftime("%Y/%m/%d %H:%M:%S")
        refSrc.compute(observer)
        
        az = refSrc.az
        el = refSrc.alt
        gd = getGeoDelay(antennas[l], az, el, Degrees=False)
        
        aln[:,l] = numpy.exp(2j*numpy.pi*central_freq*gd)
        
        pbar.inc()
        sys.stdout.write("%s\r" % pbar.show())
        sys.stdout.flush()
    sys.stdout.write('\n')
    
    # Calculate the c^l_n terms by removing the array geometry from the
    # phases.
    cln = numpy.zeros(phase2.shape, dtype=numpy.complex128)
    for i in xrange(cln.shape[1]):
        if i % 2 == 0:
            cln[:,i] = phase2[:,i] / phase2[:,0]
        else:
            cln[:,i] = phase2[:,i] / phase2[:,1]
    cln /= aln
    
    # Average all time steps together and make sure we end up with 
    # a 2-D array in the end
    cln = cln.mean(axis=0)
    cln.shape = (1,) + cln.shape
    
    # Save
    outname = filename.replace('-vis','-cln')
    numpy.savez(outname, bln=bln, cln=cln, central_freq=central_freq, reference=reference, basefile=filename)
Ejemplo n.º 10
0
def main(args):
    # The task at hand
    clnfile = args[0]
    az = float(args[1])
    el = float(args[2])
    filename = args[3]

    # The station
    observer = lwa1.get_observer()
    antennas = lwa1.antennas

    # The file's parameters
    fh = open(filename, 'rb')
    nFramesFile = os.path.getsize(filename) / tbn.FRAME_SIZE
    srate = tbn.get_sample_rate(fh)
    antpols = len(antennas)

    # Reference antenna
    ref = 258
    for a in antennas:
        if a.stand.id == ref and a.pol == 0:
            refX = a.digitizer
        elif a.stand.id == ref and a.pol == 1:
            refY = a.digitizer
        else:
            pass

    # Integration time (seconds and frames)
    tInt = 5.0
    nFrames = int(round(tInt * srate / 512 * antpols))
    tInt = nFrames / antpols * 512 / srate

    # Total run length
    #nChunks = int(round(1.0*nFramesFile / nFrames))
    nChunks = 240

    # Read in the first frame and get the date/time of the first sample
    # of the frame.  This is needed to get the list of stands.
    junkFrame = tbn.read_frame(fh)
    fh.seek(-tbn.FRAME_SIZE, 1)
    startFC = junkFrame.header.frame_count
    central_freq = junkFrame.central_freq
    beginDate = junkFrame.time.datetime

    observer.date = beginDate
    srcs = []
    for line in _srcs:
        srcs.append(ephem.readdb(line))
        srcs[-1].compute(observer)

        if srcs[-1].alt > 0:
            print("source %s: alt %.1f degrees, az %.1f degrees" %
                  (srcs[-1].name, srcs[-1].alt * 180 / numpy.pi,
                   srcs[-1].az * 180 / numpy.pi))

    # File summary
    print("Filename: %s" % filename)
    print("Date of First Frame: %s" % str(beginDate))
    print("Ant/Pols: %i" % antpols)
    print("Sample Rate: %i Hz" % srate)
    print("Tuning Frequency: %.3f Hz" % central_freq)
    print("Frames: %i (%.3f s)" %
          (nFramesFile, 1.0 * nFramesFile / antpols * 512 / srate))
    print("---")
    print("Integration: %.3f s (%i frames; %i frames per stand/pol)" %
          (tInt, nFrames, nFrames / antpols))
    print("Chunks: %i" % nChunks)

    junkFrame = tbn.read_frame(fh)
    while junkFrame.header.frame_count < startFC + 3:
        junkFrame = tbn.read_frame(fh)
    fh.seek(-tbn.FRAME_SIZE, 1)

    # Get the beamformer coefficients - three sets:
    #  (1) at the requested az, el
    #  (2) at az, el - 15 degrees
    #  (3) at the transit location of Cyg A
    dataDict = numpy.load(clnfile)
    cln = dataDict['cln']
    aln1 = []
    aln2 = []
    aln3 = []
    for i in xrange(cln.shape[1]):
        gd = getGeoDelay(antennas[i], az, el, central_freq, Degrees=True)
        aln1.append(numpy.exp(2j * numpy.pi * central_freq * gd))

        gd = getGeoDelay(antennas[i], az, el - 15, central_freq, Degrees=True)
        aln2.append(numpy.exp(2j * numpy.pi * central_freq * gd))

        gd = getGeoDelay(antennas[i], 0.5, 83.3, central_freq, Degrees=True)
        aln3.append(numpy.exp(2j * numpy.pi * central_freq * gd))

    aln1 = numpy.array(aln1)
    aln2 = numpy.array(aln2)
    aln3 = numpy.array(aln3)

    bln1 = (cln * aln1).conj() / numpy.abs(cln * aln1)
    bln2 = (cln * aln2).conj() / numpy.abs(cln * aln2)
    bln3 = (cln * aln3).conj() / numpy.abs(cln * aln3)
    for i in xrange(cln.shape[1]):
        if antennas[i].combined_status != 33 or antennas[i].stand.id == ref:
            bln1[:, i] = 0.0
            bln2[:, i] = 0.0
            bln3[:, i] = 0.0

    # Create the FrameBuffer instance
    buffer = TBNFrameBuffer(stands=range(1, antpols / 2 + 1),
                            pols=[0, 1],
                            reorder=False)

    # Create the beam
    times = numpy.zeros(nChunks, dtype=numpy.float64)
    beam1 = numpy.zeros((nChunks, 2), dtype=numpy.float64)
    beam2 = numpy.zeros((nChunks, 2), dtype=numpy.float64)
    beam3 = numpy.zeros((nChunks, 2), dtype=numpy.float64)

    # Go!
    k = 0
    for i in xrange(nChunks):
        # Find out how many frames remain in the file.  If this number is larger
        # than the maximum of frames we can work with at a time (maxFrames),
        # only deal with that chunk
        framesRemaining = nFramesFile - k
        if framesRemaining > nFrames:
            framesWork = nFrames
            data = numpy.zeros((antpols, framesWork / antpols * 512),
                               dtype=numpy.complex64)
        else:
            framesWork = framesRemaining + antpols * buffer.nsegments
            data = numpy.zeros((antpols, framesWork / antpols * 512),
                               dtype=numpy.complex64)
        print("Working on chunk %i, %i frames remaining" %
              (i + 1, framesRemaining))

        count = [0 for a in xrange(antpols)]

        j = 0
        fillsWork = framesWork / antpols
        # Inner loop that actually reads the frames into the data array
        while j < fillsWork:
            try:
                cFrame = tbn.read_frame(fh)
                k = k + 1
            except errors.EOFError:
                break
            except errors.SyncError:
                #print("WARNING: Mark 5C sync error on frame #%i" % (int(fh.tell())/tbn.FRAME_SIZE-1))
                continue

            buffer.append(cFrame)
            cFrames = buffer.get()

            if cFrames is None:
                continue

            valid = sum(lambda x, y: x + int(y.valid), cFrames, 0)
            if valid != antpols:
                print(
                    "WARNING: frame count %i at %i missing %.2f%% of frames" %
                    (cFrames[0].header.frame_count, cFrames[0].payload.timetag,
                     float(antpols - valid) / antpols * 100))
                continue

            for cFrame in cFrames:
                stand, pol = cFrame.header.id

                # In the current configuration, stands start at 1 and go up to 260.  So, we
                # can use this little trick to populate the data array
                aStand = 2 * (stand - 1) + pol

                # Save the time
                if j == 0 and aStand == 0:
                    times[i] = cFrame.time

                data[aStand, count[aStand] * 512:(count[aStand] + 1) *
                     512] = cFrame.payload.data

                # Update the counters so that we can average properly later on
                count[aStand] = count[aStand] + 1

            j += 1

        # Mask
        bad = numpy.where(numpy.abs(data) >= 90)
        data[bad] = 0.0

        # Beam forming
        taskPool = Pool(processes=6)
        taskList = []
        taskList.append(
            (i, 1, 0,
             taskPool.apply_async(form_beam,
                                  args=(data[0::2, :], bln1[0, 0::2]))))
        taskList.append(
            (i, 1, 1,
             taskPool.apply_async(form_beam,
                                  args=(data[1::2, :], bln1[0, 1::2]))))
        taskList.append(
            (i, 2, 0,
             taskPool.apply_async(form_beam,
                                  args=(data[0::2, :], bln2[0, 0::2]))))
        taskList.append(
            (i, 2, 1,
             taskPool.apply_async(form_beam,
                                  args=(data[1::2, :], bln2[0, 1::2]))))
        taskList.append(
            (i, 3, 0,
             taskPool.apply_async(form_beam,
                                  args=(data[0::2, :], bln3[0, 0::2]))))
        taskList.append(
            (i, 3, 1,
             taskPool.apply_async(form_beam,
                                  args=(data[1::2, :], bln3[0, 1::2]))))
        taskPool.close()
        taskPool.join()

        for i, b, p, task in taskList:
            if b == 1:
                beam1[i, p] = task.get()
            elif b == 2:
                beam2[i, p] = task.get()
            else:
                beam3[i, p] = task.get()

        print('1', beam1[i, 0], '2', beam2[i, 0], '3', beam3[i, 0], '1/2',
              beam1[i, 0] / beam2[i, 0], '3/2', beam3[i, 0] / beam2[i, 0])
        del data

    # Plot the data
    print('CygA      :', beam1[:, 0])
    print('Pointing 2:', beam2[:, 0])
    print('Pointing 1:', beam3[:, 0])

    fig = plt.figure()
    ax1 = fig.add_subplot(1, 2, 1)
    ax2 = fig.add_subplot(1, 2, 2)
    ax1.plot(times - times[0], beam1[:, 0])
    ax1.plot(times - times[0], beam2[:, 0])
    ax1.plot(times - times[0], beam3[:, 0])
    ax2.plot(times - times[0], beam1[:, 1])
    ax2.plot(times - times[0], beam2[:, 1])
    ax2.plot(times - times[0], beam3[:, 1])
    plt.show()
Ejemplo n.º 11
0
def main(args):
    # Parse the command line
    filename = args.filename

    # Load in the data to see what we should do
    dataDict = numpy.load(filename)
    srcName = dataDict['source'].item()
    freq = dataDict['freq']
    unx = dataDict['unx']
    lst = dataDict['lst']
    pwrX = dataDict['pwrX']
    pwrY = dataDict['pwrY']
    dataDict.close()

    # Form Stokes I out of X and Y
    pwrI = pwrX + pwrY

    # Read in each of the data sets
    data = {}
    pointing = {}
    tStartPlot = 1e12
    for i, name in enumerate(('south', srcName, 'north')):
        pointing[name] = name

        if unx[0] < tStartPlot:
            tStartPlot = unx[0]

        data[name] = {'t': unx, 'f1': freq, 'I1': pwrI[:, i, :]}

    # Get LWA-1
    observer = lwa1.get_observer()

    # Load in the sources and find the right one
    srcs = getSources()
    simSrcs = getAIPYSources()

    toUse = None
    for srcName in data.keys():
        for src in srcs.keys():
            if src.lower() == srcName.lower():
                toUse = src
                observer.date = datetime.utcfromtimestamp(
                    data[srcName]['t'][0])
                break
    if toUse is None:
        raise RuntimeError("Unknown source in input files")

    toUseAIPY = srcs[toUse].name
    try:
        simSrcs[toUseAIPY]
    except KeyError:
        toUseAIPY = None
        print("Warning: Cannot find flux for this target")

    # Find out when the source should have transitted the beam
    tTransit = 0.0
    zenithAngle = ephem.degrees('180:00:00')
    for name in pointing.keys():
        if name.lower() != srcs[toUse].name.lower():
            continue

        observer.next_transit(srcs[toUse])
        az = srcs[toUse].az
        el = srcs[toUse].alt

        bestT = 0.0
        bestV = 1e6
        for t in data[name]['t']:
            observer.date = datetime.utcfromtimestamp(t).strftime(
                "%Y/%m/%d %H:%M:%S")
            srcs[toUse].compute(observer)

            sep = ephem.separation((srcs[toUse].az, srcs[toUse].alt), (az, el))
            if sep < bestV:
                bestT = t
                bestV = sep
    tTransit = bestT
    observer.date = datetime.utcfromtimestamp(tTransit).strftime(
        "%Y/%m/%d %H:%M:%S")
    zenithAngle = ephem.degrees(ephem.degrees('90:00:00') - el)

    # Plot
    fig = plt.figure()
    ax1 = fig.gca()

    raOffsets1 = {}
    decPowers1 = {}
    fwhmEstimates1 = {}
    sefdEstimate1 = None

    raOffsets2 = {}
    decPowers2 = {}
    fwhmEstimates2 = {}
    sefdEstimate2 = None
    for name in data.keys():
        t = data[name]['t']
        f1 = data[name]['f1']
        I1 = data[name]['I1']

        # Select data that was actually recorded
        good = numpy.where((t > 0) & (I1[:, 10] > 0))[0][:-1]
        t = t[good]
        I1 = I1[good]

        # Sum over the interesting part of the band
        toUseSpec = numpy.where((f1 > 60e6) & (f1 < 80e6))[0]
        I1 = I1[:, toUseSpec].sum(axis=1)

        # Convert the scales to unit flux
        I1 /= I1.max()

        # Fit a Gaussian to the power to find the transit time and beam width
        includeLinear = False
        if includeLinear:
            obsTransit1, sefdMetric1, obsFWHM1, obsSlope1, obsFit1 = fitDriftscan(
                t, I1, includeLinear=True)

            linear1 = obsSlope1 * t
            linear1 -= linear1[:10].mean()

            I1 -= linear1
            obsFit1 -= linear1

        obsTransit1, sefdMetric1, obsFWHM1, obsFit1 = fitDriftscan(
            t, I1, includeLinear=False)

        # Save the results
        diff1 = obsTransit1 - tTransit
        raOffsets1[name] = diff1
        decPowers1[name] = obsFit1.max() - obsFit1.min()
        fwhmEstimates1[name] = obsFWHM1 / 3600. * 15. * numpy.cos(
            srcs[toUse]._dec)

        # Report
        print('Target: %s' % name)
        print('  Tuning 1 @ %.2f MHz' % (f1.mean() / 1e6, ))
        print('    FWHM: %.2f s (%.2f deg)' %
              (obsFWHM1, obsFWHM1 / 3600. * 15. * numpy.cos(srcs[toUse]._dec)))
        print('    Observed Transit: %s' %
              datetime.utcfromtimestamp(obsTransit1))
        print('    Expected Transit: %s' % datetime.utcfromtimestamp(tTransit))
        print('    -> Difference: %.2f s' % diff1)
        if toUseAIPY is None:
            print('    1/(P1/P0 - 1): %.3f' % sefdMetric1)
        else:
            simSrcs[toUseAIPY].compute(observer, afreqs=f1.mean() / 1e9)
            srcFlux = simSrcs[toUseAIPY].jys
            sefd = srcFlux * sefdMetric1 / 1e3
            print('    S / (P1/P0 - 1): %.3f kJy' % sefd)
            if name == srcs[toUse].name:
                sefdEstimate1 = sefd * 1e3

        # Plot
        ax1.plot(t - tStartPlot, I1, label="%s" % name)
        ax1.plot(t - tStartPlot, obsFit1, linestyle=':')

    ylim1 = ax1.get_ylim()
    ax1.vlines(tTransit - tStartPlot,
               *ylim1,
               linestyle='--',
               label='Expected Transit')
    ax1.set_ylim(ylim1)
    ax1.legend(loc=0)
    ax1.set_title('%.2f MHz' % (f1.mean() / 1e6, ))
    ax1.set_xlabel('Elapsed Time [s]')
    ax1.set_ylabel('Power [arb.]')

    # Compute the dec. offset
    dataSet1 = (f1.mean(), raOffsets1, decPowers1, fwhmEstimates1,
                sefdEstimate1)

    sys.stderr.write(
        "Source YYYY/MM/DD HH:MM:SS MHz    Z          errRA      errDec      SEFD      FWHM\n"
    )
    for f, raOffsets, decPowers, fwhmEstimates, sefdEstimate in (dataSet1, ):
        do = []
        dp = []
        bestOffset = None
        bestPower = -1e6
        bestFWHM = None
        for name in decPowers.keys():
            offset = raOffsets[name]
            power = decPowers[name]
            fwhm = fwhmEstimates[name]

            if power > bestPower:
                bestOffset = offset
                bestPower = power
                bestFWHM = fwhm

            if name.find('north') != -1:
                do.append(1.0)
            elif name.find('south') != -1:
                do.append(-1.0)
            else:
                do.append(0.0)
            dp.append(power)

        do = numpy.array(do)
        dp = numpy.array(dp)
        order = numpy.argsort(do)
        do = do[order]
        dp = dp[order]

        try:
            decOffset = fitDecOffset(do, dp, fwhm=bestFWHM)
        except TypeError:
            decOffset = -99

        raOffset = ephem.hours('00:00:%f' % bestOffset)
        decOffset = ephem.degrees('%f' % decOffset)
        fwhmEstimate = ephem.degrees('%f' % bestFWHM)
        print(
            "%-6s %-19s %6.3f %-10s %-10s %-10s %10.3f %-10s" %
            (srcs[toUse].name,
             datetime.utcfromtimestamp(tTransit).strftime("%Y/%m/%d %H:%M:%S"),
             f / 1e6, zenithAngle, raOffset, decOffset, sefdEstimate,
             fwhmEstimate))

    plt.show()