Beispiel #1
0
/* This performs a two-way transfer over AXI DMA, both sending data out and
 * receiving it back over DMA. The user determines if this call is  blocking. */
int axidma_twoway_transfer(axidma_dev_t dev, int tx_channel, void *tx_buf,
        size_t tx_len, int rx_channel, void *rx_buf, size_t rx_len, bool wait)
{
    int rc;
    struct axidma_inout_transaction trans;

    assert(valid_channel(dev, tx_channel, AXIDMA_WRITE));
    assert(valid_channel(dev, rx_channel, AXIDMA_READ));

    // Setup the argument structure for the IOCTL
    trans.wait = wait;
    trans.tx_channel_id = tx_channel;
    trans.tx_buf = tx_buf;
    trans.tx_buf_len = tx_len;
    trans.rx_channel_id = rx_channel;
    trans.rx_buf = rx_buf;
    trans.rx_buf_len = rx_len;

    // Perform the read-write transfer
    rc = ioctl(dev->fd, AXIDMA_DMA_READWRITE, &trans);
    if (rc < 0) {
        perror("Failed to perform the AXI DMA read-write transfer");
    }

    return rc;
}
Beispiel #2
0
/* This performs a one-way transfer over AXI DMA, the direction being specified
 * by the user. The user determines if this is blocking or not with `wait. */
int axidma_oneway_transfer(axidma_dev_t dev, enum axidma_dir dir, int channel,
                           void *buf, size_t len, bool wait)
{
    int rc;
    struct axidma_transaction trans;
    unsigned long axidma_cmd;

    assert(dir == AXIDMA_READ || dir == AXIDMA_WRITE);
    assert(dir != AXIDMA_READ || valid_channel(dev, channel, AXIDMA_READ));
    assert(dir != AXIDMA_WRITE || valid_channel(dev, channel, AXIDMA_WRITE));

    // Setup the argument structure to the IOCTL
    trans.wait = wait;
    trans.channel_id = channel;
    trans.buf = buf;
    trans.buf_len = len;
    axidma_cmd = dir_to_ioctl(dir);

    // Perform the given transfer
    rc = ioctl(dev->fd, axidma_cmd, &trans);
    if (rc < 0) {
        perror("Failed to perform the AXI DMA transfer");
        return rc;
    }

    return 0;
}
Beispiel #3
0
/*
  send a buffer out a MAVLink channel
 */
void comm_send_buffer(mavlink_channel_t chan, const uint8_t *buf, uint8_t len)
{
    if (!valid_channel(chan)) {
        return;
    }
    mavlink_comm_port[chan]->write(buf, len);
}
Beispiel #4
0
/// Read a byte from the nominated MAVLink channel
///
/// @param chan		Channel to receive on
/// @returns		Byte read
///
uint8_t comm_receive_ch(mavlink_channel_t chan)
{
    if (!valid_channel(chan)) {
        return 0;
    }

    return (uint8_t)mavlink_comm_port[chan]->read();
}
Beispiel #5
0
/*
  lock a channel, preventing use by MAVLink
 */
void GCS_MAVLINK::lock_channel(mavlink_channel_t _chan, bool lock)
{
    if (!valid_channel(chan)) {
        return;
    }
    if (lock) {
        mavlink_locked_mask |= (1U<<(unsigned)_chan);
    } else {
        mavlink_locked_mask &= ~(1U<<(unsigned)_chan);
    }
}
Beispiel #6
0
/* This function stops all transfers on the given channel with the given
 * direction. This function is required to stop any video transfers, or any
 * non-blocking transfers. */
void axidma_stop_transfer(axidma_dev_t dev, int channel, enum axidma_dir dir)
{
    struct axidma_chan chan;

    assert(dir == AXIDMA_READ || dir == AXIDMA_WRITE);
    assert(dir != AXIDMA_READ || valid_channel(dev, channel, AXIDMA_READ));
    assert(dir != AXIDMA_WRITE || valid_channel(dev, channel, AXIDMA_WRITE));

    // Setup the argument structure for the IOCTL
    chan.channel_id = channel;
    chan.dir = dir;
    chan.type = AXIDMA_DMA;

    // Stop all transfers on the given DMA channel
    if (ioctl(dev->fd, AXIDMA_STOP_DMA_CHANNEL, &chan) < 0) {
        perror("Failed to stop the DMA channel");
        assert(false);
    }

    return;
}
Beispiel #7
0
/// Check for available data on the nominated MAVLink channel
///
/// @param chan		Channel to check
/// @returns		Number of bytes available
uint16_t comm_get_available(mavlink_channel_t chan)
{
    if (!valid_channel(chan)) {
        return 0;
    }
    if ((1U<<chan) & mavlink_locked_mask) {
        return 0;
    }
    int16_t bytes = mavlink_comm_port[chan]->available();
	if (bytes == -1) {
		return 0;
	}
    return (uint16_t)bytes;
}
Beispiel #8
0
/// Check for available transmit space on the nominated MAVLink channel
///
/// @param chan		Channel to check
/// @returns		Number of bytes available
uint16_t comm_get_txspace(mavlink_channel_t chan)
{
    if (!valid_channel(chan)) {
        return 0;
    }
    if ((1U<<chan) & mavlink_locked_mask) {
        return 0;
    }
	int16_t ret = mavlink_comm_port[chan]->txspace();
	if (ret < 0) {
		ret = 0;
	}
    return (uint16_t)ret;
}
Beispiel #9
0
void
GCS_MAVLINK::init(AP_HAL::UARTDriver *port, mavlink_channel_t mav_chan)
{
    if (!valid_channel(mav_chan)) {
        return;
    }

    _port = port;
    chan = mav_chan;

    mavlink_comm_port[chan] = _port;
    initialised = true;
    _queued_parameter = NULL;
    reset_cli_timeout();
}
Beispiel #10
0
/*
  return true if a channel has flow control
 */
bool GCS_MAVLINK::have_flow_control(void)
{
    if (!valid_channel(chan)) {
        return false;
    }

    if (mavlink_comm_port[chan] == NULL) {
        return false;
    }

    if (chan == MAVLINK_COMM_0) {
        // assume USB console has flow control
        return hal.gpio->usb_connected() || mavlink_comm_port[chan]->get_flow_control() != AP_HAL::UARTDriver::FLOW_CONTROL_DISABLE;
    } else {
        // all other channels
        return mavlink_comm_port[chan]->get_flow_control() != AP_HAL::UARTDriver::FLOW_CONTROL_DISABLE;
    }
}
Beispiel #11
0
/* This function performs a video transfer over AXI DMA, setting up the DMA to
 * read from the given frame buffers on-demand continuously. This call is
 * always non-blocking. The transfer must be stopped with a call to
 * axidma_stop_transfer. */
int axidma_video_transfer(axidma_dev_t dev, int display_channel, size_t width,
        size_t height, size_t depth, void **frame_buffers, int num_buffers)
{
    int rc;
    struct axidma_video_transaction trans;

    assert(valid_channel(dev, display_channel, AXIDMA_WRITE));

    // Setup the argument structure for the IOCTL
    trans.channel_id = display_channel;
    trans.num_frame_buffers = num_buffers;
    trans.frame_buffers = frame_buffers;
    trans.width = width;
    trans.height = height;
    trans.depth = depth;

    // Perform the video transfer
    rc = ioctl(dev->fd, AXIDMA_DMA_VIDEO_WRITE, &trans);
    if (rc < 0) {
        perror("Failed to perform the AXI DMA video write transfer");
    }

    return rc;
}