1/* 2 * Generic FIFO32 component, based on FIFO8. 3 * 4 * Copyright (c) 2016 Jean-Christophe Dubois 5 * 6 * This program is free software; you can redistribute it and/or 7 * modify it under the terms of the GNU General Public License 8 * as published by the Free Software Foundation; either version 9 * 2 of the License, or (at your option) any later version. 10 * 11 * You should have received a copy of the GNU General Public License along 12 * with this program; if not, see <http://www.gnu.org/licenses/>. 13 */ 14 15#ifndef FIFO32_H 16#define FIFO32_H 17 18#include "qemu/osdep.h" 19#include "qemu/fifo8.h" 20 21typedef struct { 22 Fifo8 fifo; 23} Fifo32; 24 25/** 26 * fifo32_create: 27 * @fifo: struct Fifo32 to initialise with new FIFO 28 * @capacity: capacity of the newly created FIFO expressed in 32 bit words 29 * 30 * Create a FIFO of the specified size. Clients should call fifo32_destroy() 31 * when finished using the fifo. The FIFO is initially empty. 32 */ 33 34static inline void fifo32_create(Fifo32 *fifo, uint32_t capacity) 35{ 36 fifo8_create(&fifo->fifo, capacity * sizeof(uint32_t)); 37} 38 39/** 40 * fifo32_destroy: 41 * @fifo: FIFO to cleanup 42 * 43 * Cleanup a FIFO created with fifo32_create(). Frees memory created for FIFO 44 * storage. The FIFO is no longer usable after this has been called. 45 */ 46 47static inline void fifo32_destroy(Fifo32 *fifo) 48{ 49 fifo8_destroy(&fifo->fifo); 50} 51 52/** 53 * fifo32_num_free: 54 * @fifo: FIFO to check 55 * 56 * Return the number of free uint32_t slots in the FIFO. 57 * 58 * Returns: Number of free 32 bit words. 59 */ 60 61static inline uint32_t fifo32_num_free(Fifo32 *fifo) 62{ 63 return DIV_ROUND_UP(fifo8_num_free(&fifo->fifo), sizeof(uint32_t)); 64} 65 66/** 67 * fifo32_num_used: 68 * @fifo: FIFO to check 69 * 70 * Return the number of used uint32_t slots in the FIFO. 71 * 72 * Returns: Number of used 32 bit words. 73 */ 74 75static inline uint32_t fifo32_num_used(Fifo32 *fifo) 76{ 77 return DIV_ROUND_UP(fifo8_num_used(&fifo->fifo), sizeof(uint32_t)); 78} 79 80/** 81 * fifo32_push: 82 * @fifo: FIFO to push to 83 * @data: 32 bits data word to push 84 * 85 * Push a 32 bits data word to the FIFO. Behaviour is undefined if the FIFO 86 * is full. Clients are responsible for checking for fullness using 87 * fifo32_is_full(). 88 */ 89 90static inline void fifo32_push(Fifo32 *fifo, uint32_t data) 91{ 92 int i; 93 94 for (i = 0; i < sizeof(data); i++) { 95 fifo8_push(&fifo->fifo, data & 0xff); 96 data >>= 8; 97 } 98} 99 100/** 101 * fifo32_push_all: 102 * @fifo: FIFO to push to 103 * @data: data to push 104 * @size: number of 32 bit words to push 105 * 106 * Push a 32 bit word array to the FIFO. Behaviour is undefined if the FIFO 107 * is full. Clients are responsible for checking the space left in the FIFO 108 * using fifo32_num_free(). 109 */ 110 111static inline void fifo32_push_all(Fifo32 *fifo, const uint32_t *data, 112 uint32_t num) 113{ 114 int i; 115 116 for (i = 0; i < num; i++) { 117 fifo32_push(fifo, data[i]); 118 } 119} 120 121/** 122 * fifo32_pop: 123 * @fifo: fifo to pop from 124 * 125 * Pop a 32 bits data word from the FIFO. Behaviour is undefined if the FIFO 126 * is empty. Clients are responsible for checking for emptiness using 127 * fifo32_is_empty(). 128 * 129 * Returns: The popped 32 bits data word. 130 */ 131 132static inline uint32_t fifo32_pop(Fifo32 *fifo) 133{ 134 uint32_t ret = 0; 135 int i; 136 137 for (i = 0; i < sizeof(uint32_t); i++) { 138 ret |= (fifo8_pop(&fifo->fifo) << (i * 8)); 139 } 140 141 return ret; 142} 143 144/** 145 * There is no fifo32_pop_buf() because the data is not stored in the buffer 146 * as a set of native-order words. 147 */ 148 149/** 150 * fifo32_reset: 151 * @fifo: FIFO to reset 152 * 153 * Reset a FIFO. All data is discarded and the FIFO is emptied. 154 */ 155 156static inline void fifo32_reset(Fifo32 *fifo) 157{ 158 fifo8_reset(&fifo->fifo); 159} 160 161/** 162 * fifo32_is_empty: 163 * @fifo: FIFO to check 164 * 165 * Check if a FIFO is empty. 166 * 167 * Returns: True if the fifo is empty, false otherwise. 168 */ 169 170static inline bool fifo32_is_empty(Fifo32 *fifo) 171{ 172 return fifo8_is_empty(&fifo->fifo); 173} 174 175/** 176 * fifo32_is_full: 177 * @fifo: FIFO to check 178 * 179 * Check if a FIFO is full. 180 * 181 * Returns: True if the fifo is full, false otherwise. 182 */ 183 184static inline bool fifo32_is_full(Fifo32 *fifo) 185{ 186 return fifo8_num_free(&fifo->fifo) < sizeof(uint32_t); 187} 188 189#define VMSTATE_FIFO32(_field, _state) VMSTATE_FIFO8(_field.fifo, _state) 190 191#endif /* FIFO32_H */ 192