1*4882a593Smuzhiyun /* SPDX-License-Identifier: GPL-2.0-only */ 2*4882a593Smuzhiyun /* 3*4882a593Smuzhiyun * Copyright (c) 2016, NVIDIA CORPORATION. All rights reserved. 4*4882a593Smuzhiyun */ 5*4882a593Smuzhiyun 6*4882a593Smuzhiyun #ifndef __TEGRA_IVC_H 7*4882a593Smuzhiyun 8*4882a593Smuzhiyun #include <linux/device.h> 9*4882a593Smuzhiyun #include <linux/dma-mapping.h> 10*4882a593Smuzhiyun #include <linux/types.h> 11*4882a593Smuzhiyun 12*4882a593Smuzhiyun struct tegra_ivc_header; 13*4882a593Smuzhiyun 14*4882a593Smuzhiyun struct tegra_ivc { 15*4882a593Smuzhiyun struct device *peer; 16*4882a593Smuzhiyun 17*4882a593Smuzhiyun struct { 18*4882a593Smuzhiyun struct tegra_ivc_header *channel; 19*4882a593Smuzhiyun unsigned int position; 20*4882a593Smuzhiyun dma_addr_t phys; 21*4882a593Smuzhiyun } rx, tx; 22*4882a593Smuzhiyun 23*4882a593Smuzhiyun void (*notify)(struct tegra_ivc *ivc, void *data); 24*4882a593Smuzhiyun void *notify_data; 25*4882a593Smuzhiyun 26*4882a593Smuzhiyun unsigned int num_frames; 27*4882a593Smuzhiyun size_t frame_size; 28*4882a593Smuzhiyun }; 29*4882a593Smuzhiyun 30*4882a593Smuzhiyun /** 31*4882a593Smuzhiyun * tegra_ivc_read_get_next_frame - Peek at the next frame to receive 32*4882a593Smuzhiyun * @ivc pointer of the IVC channel 33*4882a593Smuzhiyun * 34*4882a593Smuzhiyun * Peek at the next frame to be received, without removing it from 35*4882a593Smuzhiyun * the queue. 36*4882a593Smuzhiyun * 37*4882a593Smuzhiyun * Returns a pointer to the frame, or an error encoded pointer. 38*4882a593Smuzhiyun */ 39*4882a593Smuzhiyun void *tegra_ivc_read_get_next_frame(struct tegra_ivc *ivc); 40*4882a593Smuzhiyun 41*4882a593Smuzhiyun /** 42*4882a593Smuzhiyun * tegra_ivc_read_advance - Advance the read queue 43*4882a593Smuzhiyun * @ivc pointer of the IVC channel 44*4882a593Smuzhiyun * 45*4882a593Smuzhiyun * Advance the read queue 46*4882a593Smuzhiyun * 47*4882a593Smuzhiyun * Returns 0, or a negative error value if failed. 48*4882a593Smuzhiyun */ 49*4882a593Smuzhiyun int tegra_ivc_read_advance(struct tegra_ivc *ivc); 50*4882a593Smuzhiyun 51*4882a593Smuzhiyun /** 52*4882a593Smuzhiyun * tegra_ivc_write_get_next_frame - Poke at the next frame to transmit 53*4882a593Smuzhiyun * @ivc pointer of the IVC channel 54*4882a593Smuzhiyun * 55*4882a593Smuzhiyun * Get access to the next frame. 56*4882a593Smuzhiyun * 57*4882a593Smuzhiyun * Returns a pointer to the frame, or an error encoded pointer. 58*4882a593Smuzhiyun */ 59*4882a593Smuzhiyun void *tegra_ivc_write_get_next_frame(struct tegra_ivc *ivc); 60*4882a593Smuzhiyun 61*4882a593Smuzhiyun /** 62*4882a593Smuzhiyun * tegra_ivc_write_advance - Advance the write queue 63*4882a593Smuzhiyun * @ivc pointer of the IVC channel 64*4882a593Smuzhiyun * 65*4882a593Smuzhiyun * Advance the write queue 66*4882a593Smuzhiyun * 67*4882a593Smuzhiyun * Returns 0, or a negative error value if failed. 68*4882a593Smuzhiyun */ 69*4882a593Smuzhiyun int tegra_ivc_write_advance(struct tegra_ivc *ivc); 70*4882a593Smuzhiyun 71*4882a593Smuzhiyun /** 72*4882a593Smuzhiyun * tegra_ivc_notified - handle internal messages 73*4882a593Smuzhiyun * @ivc pointer of the IVC channel 74*4882a593Smuzhiyun * 75*4882a593Smuzhiyun * This function must be called following every notification. 76*4882a593Smuzhiyun * 77*4882a593Smuzhiyun * Returns 0 if the channel is ready for communication, or -EAGAIN if a channel 78*4882a593Smuzhiyun * reset is in progress. 79*4882a593Smuzhiyun */ 80*4882a593Smuzhiyun int tegra_ivc_notified(struct tegra_ivc *ivc); 81*4882a593Smuzhiyun 82*4882a593Smuzhiyun /** 83*4882a593Smuzhiyun * tegra_ivc_reset - initiates a reset of the shared memory state 84*4882a593Smuzhiyun * @ivc pointer of the IVC channel 85*4882a593Smuzhiyun * 86*4882a593Smuzhiyun * This function must be called after a channel is reserved before it is used 87*4882a593Smuzhiyun * for communication. The channel will be ready for use when a subsequent call 88*4882a593Smuzhiyun * to notify the remote of the channel reset. 89*4882a593Smuzhiyun */ 90*4882a593Smuzhiyun void tegra_ivc_reset(struct tegra_ivc *ivc); 91*4882a593Smuzhiyun 92*4882a593Smuzhiyun size_t tegra_ivc_align(size_t size); 93*4882a593Smuzhiyun unsigned tegra_ivc_total_queue_size(unsigned queue_size); 94*4882a593Smuzhiyun int tegra_ivc_init(struct tegra_ivc *ivc, struct device *peer, void *rx, 95*4882a593Smuzhiyun dma_addr_t rx_phys, void *tx, dma_addr_t tx_phys, 96*4882a593Smuzhiyun unsigned int num_frames, size_t frame_size, 97*4882a593Smuzhiyun void (*notify)(struct tegra_ivc *ivc, void *data), 98*4882a593Smuzhiyun void *data); 99*4882a593Smuzhiyun void tegra_ivc_cleanup(struct tegra_ivc *ivc); 100*4882a593Smuzhiyun 101*4882a593Smuzhiyun #endif /* __TEGRA_IVC_H */ 102