xge-queue.h revision 256281
1185377Ssam/*-
2187831Ssam * Copyright (c) 2002-2007 Neterion, Inc.
3185377Ssam * All rights reserved.
4185377Ssam *
5185377Ssam * Redistribution and use in source and binary forms, with or without
6185377Ssam * modification, are permitted provided that the following conditions
7185377Ssam * are met:
8185377Ssam * 1. Redistributions of source code must retain the above copyright
9185377Ssam *    notice, this list of conditions and the following disclaimer.
10185377Ssam * 2. Redistributions in binary form must reproduce the above copyright
11185377Ssam *    notice, this list of conditions and the following disclaimer in the
12185377Ssam *    documentation and/or other materials provided with the distribution.
13185377Ssam *
14185377Ssam * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
15185377Ssam * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16185377Ssam * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17187831Ssam * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
18185377Ssam * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19185377Ssam * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
20185377Ssam * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21185377Ssam * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
22185377Ssam * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
23185377Ssam * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
24185377Ssam * SUCH DAMAGE.
25185377Ssam *
26185377Ssam * $FreeBSD: stable/10/sys/dev/nxge/include/xge-queue.h 173139 2007-10-29 14:19:32Z rwatson $
27185377Ssam */
28185377Ssam
29185377Ssam#ifndef XGE_QUEUE_H
30185377Ssam#define XGE_QUEUE_H
31185377Ssam
32235972Sadrian#include <dev/nxge/include/xge-os-pal.h>
33235972Sadrian#include <dev/nxge/include/xge-defs.h>
34188979Ssam#include <dev/nxge/include/xge-list.h>
35188979Ssam#include <dev/nxge/include/xgehal-event.h>
36185377Ssam
37185377Ssam__EXTERN_BEGIN_DECLS
38185377Ssam
39185377Ssam#define XGE_QUEUE_BUF_SIZE      0x1000
40185377Ssam#define XGE_DEFAULT_EVENT_MAX_DATA_SIZE 16
41185377Ssam
42185377Ssam/**
43185377Ssam * enum xge_queue_status_e - Enumerates return codes of the xge_queue
44185377Ssam * manipulation APIs.
45185377Ssam * @XGE_QUEUE_IS_FULL: Queue is full, need to grow.
46188979Ssam * @XGE_QUEUE_IS_EMPTY: Queue is empty.
47188979Ssam * @XGE_QUEUE_OUT_OF_MEMORY: Out of memory.
48185377Ssam * @XGE_QUEUE_NOT_ENOUGH_SPACE: Exceeded specified event size,
49185377Ssam * see xge_queue_consume().
50185380Ssam * @XGE_QUEUE_OK: Neither one of the codes listed above.
51185380Ssam *
52185377Ssam * Enumerates return codes of xge_queue_consume()
53185377Ssam * and xge_queue_produce() APIs.
54185377Ssam */
55185377Ssamtypedef enum xge_queue_status_e {
56185377Ssam	XGE_QUEUE_OK            = 0,
57185377Ssam	XGE_QUEUE_IS_FULL       = 1,
58185377Ssam	XGE_QUEUE_IS_EMPTY      = 2,
59185377Ssam	XGE_QUEUE_OUT_OF_MEMORY         = 3,
60185377Ssam	XGE_QUEUE_NOT_ENOUGH_SPACE  = 4
61185377Ssam} xge_queue_status_e;
62185377Ssam
63185377Ssamtypedef void* xge_queue_h;
64185377Ssam
65185377Ssam/**
66185377Ssam * struct xge_queue_item_t - Queue item.
67185377Ssam * @item: List item. Note that the queue is "built" on top of
68185377Ssam *        the bi-directional linked list.
69185377Ssam * @event_type: Event type. Includes (but is not restricted to)
70185377Ssam * one of the xge_hal_event_e{} enumerated types.
71185377Ssam * @data_size: Size of the enqueued user data. Note that xge_queue_t
72185377Ssam * items are allowed to have variable sizes.
73217621Sadrian * @is_critical: For critical events, e.g. ECC.
74238607Sadrian * @context: Opaque (void*) "context", for instance event producer object.
75238607Sadrian *
76238607Sadrian * Item of the xge_queue_t{}. The queue is protected
77185377Ssam * in terms of multi-threaded concurrent access.
78185377Ssam * See also: xge_queue_t{}.
79185377Ssam */
80185377Ssamtypedef struct xge_queue_item_t {
81185377Ssam	xge_list_t          item;
82185377Ssam	xge_hal_event_e     event_type;
83185377Ssam	int                 data_size;
84185377Ssam	int                 is_critical;
85185377Ssam	void                *context;
86185377Ssam} xge_queue_item_t;
87185377Ssam
88185377Ssam/**
89185377Ssam * function xge_queued_f - Item-enqueued callback.
90185377Ssam * @data: Per-queue context independent of the event. E.g., device handle.
91185377Ssam * @event_type: HAL or ULD-defined event type. Note that HAL own
92217684Sadrian *        events are enumerated by xge_hal_event_e{}.
93217684Sadrian *
94185377Ssam * Per-queue optional callback. If not NULL, called by HAL each
95185377Ssam * time an event gets added to the queue.
96185377Ssam */
97185377Ssamtypedef void (*xge_queued_f) (void *data, int event_type);
98185377Ssam
99185377Ssam/**
100185377Ssam * struct xge_queue_t - Protected dynamic queue of variable-size items.
101185377Ssam * @start_ptr: Points to the start of the queue.
102185377Ssam * @end_ptr: Points to the end of the queue.
103185377Ssam * @head_ptr: Points to the head of the queue. It gets changed during queue
104185380Ssam *            produce/consume operations.
105185377Ssam * @tail_ptr: Points to the tail of the queue. It gets changed during queue
106185377Ssam *            produce/consume operations.
107185377Ssam * @lock: Lock for queue operations(syncronization purpose).
108185377Ssam * @pages_initial:Number of pages to be initially allocated at the time
109185377Ssam *        of queue creation.
110185377Ssam * @pages_max: Max number of pages that can be allocated in the queue.
111185377Ssam * @pages_current: Number of pages currently allocated
112185377Ssam * @list_head: Points to the list of queue elements that are produced, but yet
113185377Ssam *             to be consumed.
114243424Sadrian * @signal_callback: (TODO)
115185377Ssam * @pdev: PCI device handle
116185377Ssam * @irqh: PCI device IRQ handle.
117185377Ssam * @queued_func: Optional callback function to be called each time a new
118185377Ssam * item is added to the queue.
119185377Ssam * @queued_data: Arguments to the callback function.
120185377Ssam * @has_critical_event: Non-zero, if the queue contains a critical event,
121185377Ssam * see xge_hal_event_e{}.
122185377Ssam * Protected dynamically growing queue. The queue is used to support multiple
123185377Ssam * producer/consumer type scenarios. The queue is a strict FIFO: first come
124185377Ssam * first served.
125185377Ssam * Queue users may "produce" (see xge_queue_produce()) and "consume"
126185377Ssam * (see xge_queue_consume()) items (a.k.a. events) variable sizes.
127185377Ssam * See also: xge_queue_item_t{}.
128185377Ssam */
129185377Ssamtypedef struct xge_queue_t {
130185377Ssam	void                *start_ptr;
131185377Ssam	void                *end_ptr;
132185377Ssam	void                *head_ptr;
133234873Sadrian	void                *tail_ptr;
134234873Sadrian	spinlock_t          lock;
135222644Sadrian	unsigned int        pages_initial;
136234873Sadrian	unsigned int        pages_max;
137185377Ssam	unsigned int        pages_current;
138222584Sadrian	xge_list_t          list_head;
139222584Sadrian	pci_dev_h           pdev;
140222584Sadrian	pci_irq_h           irqh;
141239642Sadrian	xge_queued_f        queued_func;
142222815Sadrian	void                *queued_data;
143224709Sadrian	int             has_critical_event;
144230791Sadrian} xge_queue_t;
145222584Sadrian
146185377Ssam/* ========================== PUBLIC API ================================= */
147185377Ssam
148185377Ssamxge_queue_h xge_queue_create(pci_dev_h pdev, pci_irq_h irqh, int pages_initial,
149185377Ssam	    int pages_max, xge_queued_f queued_func, void *queued_data);
150185377Ssam
151185377Ssamvoid xge_queue_destroy(xge_queue_h queueh);
152185377Ssam
153185377Ssamvoid* xge_queue_item_data(xge_queue_item_t *item);
154185377Ssam
155185377Ssamxge_queue_status_e
156185377Ssamxge_queue_produce(xge_queue_h queueh, int event_type, void *context,
157185377Ssam	    int is_critical, const int data_size, void *data);
158185377Ssam
159185377Ssamstatic inline xge_queue_status_e
160185377Ssamxge_queue_produce_context(xge_queue_h queueh, int event_type, void *context) {
161185377Ssam	return xge_queue_produce(queueh, event_type, context, 0, 0, 0);
162225444Sadrian}
163185377Ssam
164185377Ssamxge_queue_status_e xge_queue_consume(xge_queue_h queueh, int data_max_size,
165185377Ssam	    xge_queue_item_t *item);
166185377Ssam
167185377Ssamvoid xge_queue_flush(xge_queue_h queueh);
168185377Ssam
169185377Ssam/* ========================== PRIVATE API ================================= */
170185377Ssam
171185377Ssamxge_queue_status_e __io_queue_grow(xge_queue_h qh);
172185377Ssam
173185377Ssamint __queue_get_reset_critical (xge_queue_h qh);
174185377Ssam
175185377Ssam__EXTERN_END_DECLS
176185377Ssam
177185377Ssam#endif /* XGE_QUEUE_H */
178185377Ssam