diff options
author | Jay Fenlason, Stefan Richter <stefanr@s5r6.in-berlin.de> | 2009-01-04 10:23:29 -0500 |
---|---|---|
committer | Stefan Richter <stefanr@s5r6.in-berlin.de> | 2009-03-24 15:56:43 -0400 |
commit | b1bda4cdc2037447bd66753bf5ccab66d91b0b59 (patch) | |
tree | 6aae47fb85125c15150d6d306354de5deb1e316f /include | |
parent | b769bd17656f991c5588c676376e5ec77d25997a (diff) |
firewire: cdev: add ioctls for isochronous resource management
Based on
Date: Tue, 18 Nov 2008 11:41:27 -0500
From: Jay Fenlason <fenlason@redhat.com>
Subject: [Patch V4] Add ISO resource management support
with several changes to the ABI and implementation. Only the part of
the ABI which enables auto-reallocation and auto-deallocation is
included here.
This implements ioctls for kernel-assisted allocation of isochronous
channels and isochronous bandwidth. The benefits are:
- The client does not have to have write access to the /dev/fw* device
corresponding to the IRM.
- The client does not have to perform reallocation after bus resets.
- Channel and bandwidth are deallocated by the kernel if the file is
closed before the client deallocated the resources. Thus resources
are released even if the client crashes.
It is anticipated that future in-kernel code (firewire-core IRM code;
the firewire port of firedtv), will use the fw-iso.c portions of this
code too.
Signed-off-by: Stefan Richter <stefanr@s5r6.in-berlin.de>
Tested-by: David Moore <dcm@acm.org>
Diffstat (limited to 'include')
-rw-r--r-- | include/linux/firewire-cdev.h | 100 |
1 files changed, 87 insertions, 13 deletions
diff --git a/include/linux/firewire-cdev.h b/include/linux/firewire-cdev.h index 86c8ff5326f9..25b96dd0574f 100644 --- a/include/linux/firewire-cdev.h +++ b/include/linux/firewire-cdev.h | |||
@@ -25,10 +25,12 @@ | |||
25 | #include <linux/types.h> | 25 | #include <linux/types.h> |
26 | #include <linux/firewire-constants.h> | 26 | #include <linux/firewire-constants.h> |
27 | 27 | ||
28 | #define FW_CDEV_EVENT_BUS_RESET 0x00 | 28 | #define FW_CDEV_EVENT_BUS_RESET 0x00 |
29 | #define FW_CDEV_EVENT_RESPONSE 0x01 | 29 | #define FW_CDEV_EVENT_RESPONSE 0x01 |
30 | #define FW_CDEV_EVENT_REQUEST 0x02 | 30 | #define FW_CDEV_EVENT_REQUEST 0x02 |
31 | #define FW_CDEV_EVENT_ISO_INTERRUPT 0x03 | 31 | #define FW_CDEV_EVENT_ISO_INTERRUPT 0x03 |
32 | #define FW_CDEV_EVENT_ISO_RESOURCE_ALLOCATED 0x04 | ||
33 | #define FW_CDEV_EVENT_ISO_RESOURCE_DEALLOCATED 0x05 | ||
32 | 34 | ||
33 | /** | 35 | /** |
34 | * struct fw_cdev_event_common - Common part of all fw_cdev_event_ types | 36 | * struct fw_cdev_event_common - Common part of all fw_cdev_event_ types |
@@ -147,12 +149,46 @@ struct fw_cdev_event_iso_interrupt { | |||
147 | }; | 149 | }; |
148 | 150 | ||
149 | /** | 151 | /** |
152 | * struct fw_cdev_event_iso_resource - Iso resources were allocated or freed | ||
153 | * @closure: See &fw_cdev_event_common; | ||
154 | * set by %FW_CDEV_IOC_ALLOCATE_ISO_RESOURCE ioctl | ||
155 | * @type: %FW_CDEV_EVENT_ISO_RESOURCE_ALLOCATED or | ||
156 | * %FW_CDEV_EVENT_ISO_RESOURCE_DEALLOCATED | ||
157 | * @handle: Reference by which an allocated resource can be deallocated | ||
158 | * @channel: Isochronous channel which was (de)allocated, if any | ||
159 | * @bandwidth: Bandwidth allocation units which were (de)allocated, if any | ||
160 | * @channels_available: Last known availability of channels | ||
161 | * @bandwidth_available: Last known availability of bandwidth | ||
162 | * | ||
163 | * An %FW_CDEV_EVENT_ISO_RESOURCE_ALLOCATED event is sent after an isochronous | ||
164 | * resource was allocated at the IRM. The client has to check @channel and | ||
165 | * @bandwidth for whether the allocation actually succeeded. | ||
166 | * | ||
167 | * @channel is <0 if no channel was allocated. | ||
168 | * @bandwidth is 0 if no bandwidth was allocated. | ||
169 | * | ||
170 | * An %FW_CDEV_EVENT_ISO_RESOURCE_DEALLOCATED event is sent after an isochronous | ||
171 | * resource was deallocated at the IRM. It is also sent when automatic | ||
172 | * reallocation after a bus reset failed. | ||
173 | */ | ||
174 | struct fw_cdev_event_iso_resource { | ||
175 | __u64 closure; | ||
176 | __u32 type; | ||
177 | __u32 handle; | ||
178 | __s32 channel; | ||
179 | __s32 bandwidth; | ||
180 | }; | ||
181 | |||
182 | /** | ||
150 | * union fw_cdev_event - Convenience union of fw_cdev_event_ types | 183 | * union fw_cdev_event - Convenience union of fw_cdev_event_ types |
151 | * @common: Valid for all types | 184 | * @common: Valid for all types |
152 | * @bus_reset: Valid if @common.type == %FW_CDEV_EVENT_BUS_RESET | 185 | * @bus_reset: Valid if @common.type == %FW_CDEV_EVENT_BUS_RESET |
153 | * @response: Valid if @common.type == %FW_CDEV_EVENT_RESPONSE | 186 | * @response: Valid if @common.type == %FW_CDEV_EVENT_RESPONSE |
154 | * @request: Valid if @common.type == %FW_CDEV_EVENT_REQUEST | 187 | * @request: Valid if @common.type == %FW_CDEV_EVENT_REQUEST |
155 | * @iso_interrupt: Valid if @common.type == %FW_CDEV_EVENT_ISO_INTERRUPT | 188 | * @iso_interrupt: Valid if @common.type == %FW_CDEV_EVENT_ISO_INTERRUPT |
189 | * @iso_resource: Valid if @common.type == | ||
190 | * %FW_CDEV_EVENT_ISO_RESOURCE_ALLOCATED or | ||
191 | * %FW_CDEV_EVENT_ISO_RESOURCE_DEALLOCATED | ||
156 | * | 192 | * |
157 | * Convenience union for userspace use. Events could be read(2) into an | 193 | * Convenience union for userspace use. Events could be read(2) into an |
158 | * appropriately aligned char buffer and then cast to this union for further | 194 | * appropriately aligned char buffer and then cast to this union for further |
@@ -163,13 +199,15 @@ struct fw_cdev_event_iso_interrupt { | |||
163 | * not fit will be discarded so that the next read(2) will return a new event. | 199 | * not fit will be discarded so that the next read(2) will return a new event. |
164 | */ | 200 | */ |
165 | union fw_cdev_event { | 201 | union fw_cdev_event { |
166 | struct fw_cdev_event_common common; | 202 | struct fw_cdev_event_common common; |
167 | struct fw_cdev_event_bus_reset bus_reset; | 203 | struct fw_cdev_event_bus_reset bus_reset; |
168 | struct fw_cdev_event_response response; | 204 | struct fw_cdev_event_response response; |
169 | struct fw_cdev_event_request request; | 205 | struct fw_cdev_event_request request; |
170 | struct fw_cdev_event_iso_interrupt iso_interrupt; | 206 | struct fw_cdev_event_iso_interrupt iso_interrupt; |
207 | struct fw_cdev_event_iso_resource iso_resource; | ||
171 | }; | 208 | }; |
172 | 209 | ||
210 | /* available since kernel version 2.6.22 */ | ||
173 | #define FW_CDEV_IOC_GET_INFO _IOWR('#', 0x00, struct fw_cdev_get_info) | 211 | #define FW_CDEV_IOC_GET_INFO _IOWR('#', 0x00, struct fw_cdev_get_info) |
174 | #define FW_CDEV_IOC_SEND_REQUEST _IOW('#', 0x01, struct fw_cdev_send_request) | 212 | #define FW_CDEV_IOC_SEND_REQUEST _IOW('#', 0x01, struct fw_cdev_send_request) |
175 | #define FW_CDEV_IOC_ALLOCATE _IOWR('#', 0x02, struct fw_cdev_allocate) | 213 | #define FW_CDEV_IOC_ALLOCATE _IOWR('#', 0x02, struct fw_cdev_allocate) |
@@ -178,13 +216,18 @@ union fw_cdev_event { | |||
178 | #define FW_CDEV_IOC_INITIATE_BUS_RESET _IOW('#', 0x05, struct fw_cdev_initiate_bus_reset) | 216 | #define FW_CDEV_IOC_INITIATE_BUS_RESET _IOW('#', 0x05, struct fw_cdev_initiate_bus_reset) |
179 | #define FW_CDEV_IOC_ADD_DESCRIPTOR _IOWR('#', 0x06, struct fw_cdev_add_descriptor) | 217 | #define FW_CDEV_IOC_ADD_DESCRIPTOR _IOWR('#', 0x06, struct fw_cdev_add_descriptor) |
180 | #define FW_CDEV_IOC_REMOVE_DESCRIPTOR _IOW('#', 0x07, struct fw_cdev_remove_descriptor) | 218 | #define FW_CDEV_IOC_REMOVE_DESCRIPTOR _IOW('#', 0x07, struct fw_cdev_remove_descriptor) |
181 | |||
182 | #define FW_CDEV_IOC_CREATE_ISO_CONTEXT _IOWR('#', 0x08, struct fw_cdev_create_iso_context) | 219 | #define FW_CDEV_IOC_CREATE_ISO_CONTEXT _IOWR('#', 0x08, struct fw_cdev_create_iso_context) |
183 | #define FW_CDEV_IOC_QUEUE_ISO _IOWR('#', 0x09, struct fw_cdev_queue_iso) | 220 | #define FW_CDEV_IOC_QUEUE_ISO _IOWR('#', 0x09, struct fw_cdev_queue_iso) |
184 | #define FW_CDEV_IOC_START_ISO _IOW('#', 0x0a, struct fw_cdev_start_iso) | 221 | #define FW_CDEV_IOC_START_ISO _IOW('#', 0x0a, struct fw_cdev_start_iso) |
185 | #define FW_CDEV_IOC_STOP_ISO _IOW('#', 0x0b, struct fw_cdev_stop_iso) | 222 | #define FW_CDEV_IOC_STOP_ISO _IOW('#', 0x0b, struct fw_cdev_stop_iso) |
223 | |||
224 | /* available since kernel version 2.6.24 */ | ||
186 | #define FW_CDEV_IOC_GET_CYCLE_TIMER _IOR('#', 0x0c, struct fw_cdev_get_cycle_timer) | 225 | #define FW_CDEV_IOC_GET_CYCLE_TIMER _IOR('#', 0x0c, struct fw_cdev_get_cycle_timer) |
187 | 226 | ||
227 | /* available since kernel version 2.6.30 */ | ||
228 | #define FW_CDEV_IOC_ALLOCATE_ISO_RESOURCE _IOWR('#', 0x0d, struct fw_cdev_allocate_iso_resource) | ||
229 | #define FW_CDEV_IOC_DEALLOCATE_ISO_RESOURCE _IOW('#', 0x0e, struct fw_cdev_deallocate) | ||
230 | |||
188 | /* FW_CDEV_VERSION History | 231 | /* FW_CDEV_VERSION History |
189 | * | 232 | * |
190 | * 1 Feb 18, 2007: Initial version. | 233 | * 1 Feb 18, 2007: Initial version. |
@@ -284,9 +327,9 @@ struct fw_cdev_allocate { | |||
284 | }; | 327 | }; |
285 | 328 | ||
286 | /** | 329 | /** |
287 | * struct fw_cdev_deallocate - Free an address range allocation | 330 | * struct fw_cdev_deallocate - Free a CSR address range or isochronous resource |
288 | * @handle: Handle to the address range, as returned by the kernel when the | 331 | * @handle: Handle to the address range or iso resource, as returned by the |
289 | * range was allocated | 332 | * kernel when the range or resource was allocated |
290 | */ | 333 | */ |
291 | struct fw_cdev_deallocate { | 334 | struct fw_cdev_deallocate { |
292 | __u32 handle; | 335 | __u32 handle; |
@@ -479,4 +522,35 @@ struct fw_cdev_get_cycle_timer { | |||
479 | __u32 cycle_timer; | 522 | __u32 cycle_timer; |
480 | }; | 523 | }; |
481 | 524 | ||
525 | /** | ||
526 | * struct fw_cdev_allocate_iso_resource - Allocate a channel or bandwidth | ||
527 | * @closure: Passed back to userspace in correponding iso resource events | ||
528 | * @channels: Isochronous channels of which one is to be allocated | ||
529 | * @bandwidth: Isochronous bandwidth units to be allocated | ||
530 | * @handle: Handle to the allocation, written by the kernel | ||
531 | * | ||
532 | * The %FW_CDEV_IOC_ALLOCATE_ISO_RESOURCE ioctl initiates allocation of an | ||
533 | * isochronous channel and/or of isochronous bandwidth at the isochronous | ||
534 | * resource manager (IRM). Only one of the channels specified in @channels is | ||
535 | * allocated. An %FW_CDEV_EVENT_ISO_RESOURCE_ALLOCATED is sent after | ||
536 | * communication with the IRM, indicating success or failure in the event data. | ||
537 | * The kernel will automatically reallocate the resources after bus resets. | ||
538 | * Should a reallocation fail, an %FW_CDEV_EVENT_ISO_RESOURCE_DEALLOCATED event | ||
539 | * will be sent. The kernel will also automatically deallocate the resources | ||
540 | * when the file descriptor is closed. | ||
541 | * | ||
542 | * @channels is a host-endian bitfield with the most significant bit | ||
543 | * representing channel 0 and the least significant bit representing channel 63: | ||
544 | * 1ULL << (63 - c) | ||
545 | * | ||
546 | * @bandwidth is expressed in bandwidth allocation units, i.e. the time to send | ||
547 | * one quadlet of data (payload or header data) at speed S1600. | ||
548 | */ | ||
549 | struct fw_cdev_allocate_iso_resource { | ||
550 | __u64 closure; | ||
551 | __u64 channels; | ||
552 | __u32 bandwidth; | ||
553 | __u32 handle; | ||
554 | }; | ||
555 | |||
482 | #endif /* _LINUX_FIREWIRE_CDEV_H */ | 556 | #endif /* _LINUX_FIREWIRE_CDEV_H */ |