source: mainline/uspace/lib/usb/src/pipes.c@ 41e645c

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export
Last change on this file since 41e645c was 27a0012, checked in by Vojtech Horky <vojtechhorky@…>, 15 years ago

Add local implementation of get_interface

  • Property mode set to 100644
File size: 6.0 KB
Line 
1/*
2 * Copyright (c) 2011 Vojtech Horky
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 *
9 * - Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * - Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 * - The name of the author may not be used to endorse or promote products
15 * derived from this software without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
18 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
21 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
29/** @addtogroup libusb
30 * @{
31 */
32/** @file
33 * USB endpoint pipes miscellaneous functions.
34 */
35#include <usb/usb.h>
36#include <usb/pipes.h>
37#include <usbhc_iface.h>
38#include <usb_iface.h>
39#include <errno.h>
40#include <assert.h>
41
42/** Tell USB address assigned to given device.
43 *
44 * @param phone Phone to parent device.
45 * @param dev Device in question.
46 * @return USB address or error code.
47 */
48static usb_address_t get_my_address(int phone, device_t *dev)
49{
50 sysarg_t address;
51 int rc = async_req_2_1(phone, DEV_IFACE_ID(USB_DEV_IFACE),
52 IPC_M_USB_GET_ADDRESS,
53 dev->handle, &address);
54
55 if (rc != EOK) {
56 return rc;
57 }
58
59 return (usb_address_t) address;
60}
61
62/** Tell USB interface assigned to given device.
63 *
64 * @param device Device in question.
65 * @return Interface number (negative code means any).
66 */
67int usb_device_get_assigned_interface(device_t *device)
68{
69 int parent_phone = devman_parent_device_connect(device->handle,
70 IPC_FLAG_BLOCKING);
71 if (parent_phone < 0) {
72 return -1;
73 }
74
75 sysarg_t iface_no;
76 int rc = async_req_2_1(parent_phone, DEV_IFACE_ID(USB_DEV_IFACE),
77 IPC_M_USB_GET_INTERFACE,
78 device->handle, &iface_no);
79
80 async_hangup(parent_phone);
81
82 if (rc != EOK) {
83 return -1;
84 }
85
86 return (int) iface_no;
87}
88
89/** Initialize connection to USB device.
90 *
91 * @param connection Connection structure to be initialized.
92 * @param device Generic device backing the USB device.
93 * @return Error code.
94 */
95int usb_device_connection_initialize_from_device(
96 usb_device_connection_t *connection, device_t *device)
97{
98 assert(connection);
99 assert(device);
100
101 int rc;
102 devman_handle_t hc_handle;
103 usb_address_t my_address;
104
105 rc = usb_hc_find(device->handle, &hc_handle);
106 if (rc != EOK) {
107 return rc;
108 }
109
110 int parent_phone = devman_parent_device_connect(device->handle,
111 IPC_FLAG_BLOCKING);
112 if (parent_phone < 0) {
113 return parent_phone;
114 }
115
116 my_address = get_my_address(parent_phone, device);
117 if (my_address < 0) {
118 rc = my_address;
119 goto leave;
120 }
121
122 rc = usb_device_connection_initialize(connection,
123 hc_handle, my_address);
124
125leave:
126 async_hangup(parent_phone);
127 return rc;
128}
129
130/** Initialize connection to USB device.
131 *
132 * @param connection Connection structure to be initialized.
133 * @param host_controller_handle Devman handle of host controller device is
134 * connected to.
135 * @param device_address Device USB address.
136 * @return Error code.
137 */
138int usb_device_connection_initialize(usb_device_connection_t *connection,
139 devman_handle_t host_controller_handle, usb_address_t device_address)
140{
141 assert(connection);
142
143 if ((device_address < 0) || (device_address >= USB11_ADDRESS_MAX)) {
144 return EINVAL;
145 }
146
147 connection->hc_handle = host_controller_handle;
148 connection->address = device_address;
149
150 return EOK;
151}
152
153/** Initialize connection to USB device on default address.
154 *
155 * @param dev_connection Device connection structure to be initialized.
156 * @param hc_connection Initialized connection to host controller.
157 * @return Error code.
158 */
159int usb_device_connection_initialize_on_default_address(
160 usb_device_connection_t *dev_connection,
161 usb_hc_connection_t *hc_connection)
162{
163 assert(dev_connection);
164
165 if (hc_connection == NULL) {
166 return EBADMEM;
167 }
168
169 return usb_device_connection_initialize(dev_connection,
170 hc_connection->hc_handle, (usb_address_t) 0);
171}
172
173
174/** Start a session on the endpoint pipe.
175 *
176 * A session is something inside what any communication occurs.
177 * It is expected that sessions would be started right before the transfer
178 * and ended - see usb_endpoint_pipe_end_session() - after the last
179 * transfer.
180 * The reason for this is that session actually opens some communication
181 * channel to the host controller (or to the physical hardware if you
182 * wish) and thus it involves acquiring kernel resources.
183 * Since they are limited, sessions shall not be longer than strictly
184 * necessary.
185 *
186 * @param pipe Endpoint pipe to start the session on.
187 * @return Error code.
188 */
189int usb_endpoint_pipe_start_session(usb_endpoint_pipe_t *pipe)
190{
191 assert(pipe);
192
193 if (pipe->hc_phone >= 0) {
194 return EBUSY;
195 }
196
197 int phone = devman_device_connect(pipe->wire->hc_handle, 0);
198 if (phone < 0) {
199 return phone;
200 }
201
202 pipe->hc_phone = phone;
203
204 return EOK;
205}
206
207
208/** Ends a session on the endpoint pipe.
209 *
210 * @see usb_endpoint_pipe_start_session
211 *
212 * @param pipe Endpoint pipe to end the session on.
213 * @return Error code.
214 */
215int usb_endpoint_pipe_end_session(usb_endpoint_pipe_t *pipe)
216{
217 assert(pipe);
218
219 if (pipe->hc_phone < 0) {
220 return ENOENT;
221 }
222
223 int rc = async_hangup(pipe->hc_phone);
224 if (rc != EOK) {
225 return rc;
226 }
227
228 pipe->hc_phone = -1;
229
230 return EOK;
231}
232
233/**
234 * @}
235 */
Note: See TracBrowser for help on using the repository browser.