static GstFlowReturn
gst_fluid_dec_chain (GstPad * sinkpad, GstObject * parent, GstBuffer * buffer)
{
  GstFlowReturn res = GST_FLOW_OK;
  GstFluidDec *fluiddec;
  GstClockTime pts;

  fluiddec = GST_FLUID_DEC (parent);

  if (GST_BUFFER_IS_DISCONT (buffer)) {
    fluiddec->discont = TRUE;
  }

  pts = GST_BUFFER_PTS (buffer);

  if (pts != GST_CLOCK_TIME_NONE) {
    guint64 sample =
        gst_util_uint64_scale_int (pts, FLUID_DEC_RATE, GST_SECOND);

    if (fluiddec->last_pts == GST_CLOCK_TIME_NONE) {
      fluiddec->last_pts = pts;
      fluiddec->last_sample = sample;
    } else if (fluiddec->last_pts < pts) {
      /* generate samples for the elapsed time */
      res = produce_samples (fluiddec, pts, sample);
    }
  }

  if (res == GST_FLOW_OK) {
    handle_buffer (fluiddec, buffer);
  }
  gst_buffer_unref (buffer);

  return res;
}
Exemple #2
0
/** [tx_meta_now] */
int sync_tx_meta_now_example(struct bladerf *dev, int16_t *samples,
                             unsigned int num_samples, unsigned int tx_count,
                             unsigned int timeout_ms)
{
    int status = 0;
    struct bladerf_metadata meta;
    unsigned int i;

    memset(&meta, 0, sizeof(meta));

    /* Send entire burst worth of samples in one function call */
    meta.flags = BLADERF_META_FLAG_TX_BURST_START |
                 BLADERF_META_FLAG_TX_NOW |
                 BLADERF_META_FLAG_TX_BURST_END;

    for (i = 0; i < tx_count && status == 0; i++) {
        /* Fetch or produce IQ samples...*/
        produce_samples(samples, num_samples);

        status = bladerf_sync_tx(dev, samples, num_samples, &meta, timeout_ms);
        if (status != 0) {
            fprintf(stderr, "TX failed: %s\n", bladerf_strerror(status));
        } else {
            uint64_t curr_ts;

            status = bladerf_get_timestamp(dev, BLADERF_MODULE_TX, &curr_ts);
            if (status != 0) {
                fprintf(stderr, "Failed to get current TX timestamp: %s\n",
                        bladerf_strerror(status));
            } else {
                printf("TX'd at approximately t=%016"PRIu64"\n", curr_ts);
            }

            /* Delay next transmission by approximately 5 ms
             *
             * This is a very imprecise, "quick and dirty" means to do so in
             * cases where no particular intra-burst time is required. */
            usleep(5000);
        }
    }

    /* Wait for samples to be TX'd before completing.  */
    if (status == 0) {
        status = bladerf_get_timestamp(dev, BLADERF_MODULE_TX, &meta.timestamp);
        if (status != 0) {
            fprintf(stderr, "Failed to get current TX timestamp: %s\n",
                    bladerf_strerror(status));
            return status;
        } else {
            status = wait_for_timestamp(dev, BLADERF_MODULE_TX,
                                        meta.timestamp + 2 * num_samples,
                                        timeout_ms);
            if (status != 0) {
                fprintf(stderr, "Failed to wait for timestamp.\n");
            }
        }
    }

    return status;
}
Exemple #3
0
/** [tx_meta_sched] */
int sync_tx_meta_sched_example(struct bladerf *dev,
                             int16_t *samples, unsigned int num_samples,
                             unsigned int tx_count, unsigned int samplerate,
                             unsigned int timeout_ms)
{
    int status = 0;
    unsigned int i;
    struct bladerf_metadata meta;

    memset(&meta, 0, sizeof(meta));

    /* Send entire burst worth of samples in one function call */
    meta.flags = BLADERF_META_FLAG_TX_BURST_START |
                 BLADERF_META_FLAG_TX_BURST_END;

    /* Retrieve the current timestamp so we can schedule our transmission
     * in the future. */
    status = bladerf_get_timestamp(dev, BLADERF_MODULE_TX, &meta.timestamp);
    if (status != 0) {
        fprintf(stderr, "Failed to get current TX timestamp: %s\n",
                bladerf_strerror(status));
        return status;
    } else {
        printf("Current TX timestamp: %016"PRIu64"\n", meta.timestamp);
    }

    for (i = 0; i < tx_count && status == 0; i++) {
        /* Get sample to transmit... */
        produce_samples(samples, num_samples);

        /* Schedule burst 5 ms into the future */
        meta.timestamp += samplerate / 200;

        status = bladerf_sync_tx(dev, samples, num_samples, &meta, timeout_ms);
        if (status != 0) {
            fprintf(stderr, "TX failed: %s\n", bladerf_strerror(status));
            return status;
        } else {
            printf("TX'd @ t=%016"PRIu64"\n", meta.timestamp);
        }
    }

    /* Wait for samples to finish being transmitted. */
    if (status == 0) {
        meta.timestamp += 2 * num_samples;

        status = wait_for_timestamp(dev, BLADERF_MODULE_TX,
                                    meta.timestamp, timeout_ms);

        if (status != 0) {
            fprintf(stderr, "Failed to wait for timestamp.\n");
        }
    }

    return status;
}
Exemple #4
0
/** [tx_meta_update] */
int sync_tx_meta_update_example(struct bladerf *dev,
                                int16_t *samples, unsigned int num_samples,
                                unsigned int tx_count, unsigned int samplerate,
                                unsigned int timeout_ms)
{
    int status = 0;
    unsigned int i;
    struct bladerf_metadata meta;
    int16_t zeros[] = { 0, 0, 0, 0 }; /* Two 0+0j samples */

    memset(&meta, 0, sizeof(meta));

    /* The first call to bladerf_sync_tx() will start our long "burst" at
     * a specific timestamp.
     *
     * In successive calls, we'll break this long "burst" up into shorter bursts
     * by using the BLADERF_META_FLAG_TX_UPDATE_TIMESTAMP flag with new
     * timestamps.  The discontinuities will be zero-padded.
     */
    meta.flags = BLADERF_META_FLAG_TX_BURST_START;

    /* Retrieve the current timestamp so we can schedule our transmission
     * in the future. */
    status = bladerf_get_timestamp(dev, BLADERF_MODULE_TX, &meta.timestamp);
    if (status != 0) {
        fprintf(stderr, "Failed to get current TX timestamp: %s\n",
                bladerf_strerror(status));
        return status;
    } else {
        printf("Current TX timestamp: %016"PRIu64"\n", meta.timestamp);
    }

    /* Start 5 ms in the future */
    meta.timestamp += samplerate / 200;

    for (i = 0; i < tx_count && status == 0; i++) {
        /* Get sample to transmit... */
        produce_samples(samples, num_samples);

        status = bladerf_sync_tx(dev, samples, num_samples, &meta, timeout_ms);
        if (status != 0) {
            fprintf(stderr, "TX failed: %s\n", bladerf_strerror(status));
            return status;
        } else {
            printf("TX'd @ t=%016"PRIu64"\n", meta.timestamp);
        }

        /* Instruct bladerf_sync_tx() to position samples within this burst at
         * the specified timestamp. 0+0j will be transmitted up until that
         * point. */
        meta.flags = BLADERF_META_FLAG_TX_UPDATE_TIMESTAMP;

        /* Schedule samples to be transmitted 1.25 ms after the completion of
         * the previous burst */
        meta.timestamp += num_samples + samplerate / 800;

    }

    /* End the burst and flush remaining samples. */
    meta.flags = BLADERF_META_FLAG_TX_BURST_END;
    status = bladerf_sync_tx(dev, zeros, 2, &meta, timeout_ms);

    /* Wait for samples to finish being transmitted. */
    if (status == 0) {
        meta.timestamp += 2 * num_samples;

        status = wait_for_timestamp(dev, BLADERF_MODULE_TX,
                                    meta.timestamp, timeout_ms);

        if (status != 0) {
            fprintf(stderr, "Failed to wait for timestamp.\n");
        }
    } else {
        fprintf(stderr, "Failed to complete burst: %s\n",
                bladerf_strerror(status));
    }


    return status;
}