source: mainline/uspace/drv/bus/usb/vhc/hub/virthub.c@ 2c4e1cc

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export
Last change on this file since 2c4e1cc was 33b8d024, checked in by Jiří Zárevúcky <zarevucky.jiri@…>, 8 years ago

Remove const qualifier from the argument of free() and realloc(),
as well as in numerous other variables that hold ownership of memory.

By convention, a pointer that holds ownership is _never_ qualified by const.
This is reflected in the standard type signature of free() and realloc().
Allowing const pointers to hold ownership may seem superficially convenient,
but is actually quite confusing to experienced C programmers.

  • Property mode set to 100644
File size: 7.0 KB
Line 
1/*
2 * Copyright (c) 2010 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 drvusbvhc
30 * @{
31 */
32/** @file
33 * @brief
34 */
35
36#include <usb/classes/classes.h>
37#include <usb/classes/hub.h>
38#include <usbvirt/device.h>
39#include <assert.h>
40#include <errno.h>
41#include <str_error.h>
42#include <stdio.h>
43#include <stdlib.h>
44#include <str.h>
45#include <ddf/driver.h>
46
47#include "virthub.h"
48#include "hub.h"
49
50
51/** Standard device descriptor. */
52usb_standard_device_descriptor_t std_device_descriptor = {
53 .length = sizeof(usb_standard_device_descriptor_t),
54 .descriptor_type = USB_DESCTYPE_DEVICE,
55 .usb_spec_version = 0x110,
56 .device_class = USB_CLASS_HUB,
57 .device_subclass = 0,
58 .device_protocol = 0,
59 .max_packet_size = 64,
60 .configuration_count = 1
61};
62
63/** Standard interface descriptor. */
64usb_standard_interface_descriptor_t std_interface_descriptor = {
65 .length = sizeof(usb_standard_interface_descriptor_t),
66 .descriptor_type = USB_DESCTYPE_INTERFACE,
67 .interface_number = 0,
68 .alternate_setting = 0,
69 .endpoint_count = 1,
70 .interface_class = USB_CLASS_HUB,
71 .interface_subclass = 0,
72 .interface_protocol = 0,
73 .str_interface = 0
74};
75
76/** Hub descriptor. */
77hub_descriptor_t hub_descriptor = {
78 .length = sizeof(hub_descriptor_t),
79 .type = USB_DESCTYPE_HUB,
80 .port_count = HUB_PORT_COUNT,
81 .characteristics = HUB_CHAR_NO_POWER_SWITCH_FLAG | HUB_CHAR_NO_OC_FLAG,
82 .power_on_warm_up = 50, /* Huh? */
83 .max_current = 100, /* Huh again. */
84 .removable_device = { 0 },
85 .port_power = { 0xFF }
86};
87
88/** Endpoint descriptor. */
89usb_standard_endpoint_descriptor_t endpoint_descriptor = {
90 .length = sizeof(usb_standard_endpoint_descriptor_t),
91 .descriptor_type = USB_DESCTYPE_ENDPOINT,
92 .endpoint_address = HUB_STATUS_CHANGE_PIPE | 128,
93 .attributes = USB_TRANSFER_INTERRUPT,
94 .max_packet_size = 8,
95 .poll_interval = 0xFF
96};
97
98/** Standard configuration descriptor. */
99usb_standard_configuration_descriptor_t std_configuration_descriptor = {
100 .length = sizeof(usb_standard_configuration_descriptor_t),
101 .descriptor_type = USB_DESCTYPE_CONFIGURATION,
102 .total_length =
103 sizeof(usb_standard_configuration_descriptor_t)
104 + sizeof(std_interface_descriptor)
105 + sizeof(hub_descriptor)
106 + sizeof(endpoint_descriptor)
107 ,
108 .interface_count = 1,
109 .configuration_number = HUB_CONFIGURATION_ID,
110 .str_configuration = 0,
111 .attributes = 128, /* denotes bus-powered device */
112 .max_power = 50
113};
114
115/** All hub configuration descriptors. */
116static usbvirt_device_configuration_extras_t extra_descriptors[] = {
117 {
118 .data = (uint8_t *) &std_interface_descriptor,
119 .length = sizeof(std_interface_descriptor)
120 },
121 {
122 .data = (uint8_t *) &hub_descriptor,
123 .length = sizeof(hub_descriptor)
124 },
125 {
126 .data = (uint8_t *) &endpoint_descriptor,
127 .length = sizeof(endpoint_descriptor)
128 }
129};
130
131/** Hub configuration. */
132usbvirt_device_configuration_t configuration = {
133 .descriptor = &std_configuration_descriptor,
134 .extra = extra_descriptors,
135 .extra_count = sizeof(extra_descriptors)/sizeof(extra_descriptors[0])
136};
137
138/** Hub standard descriptors. */
139usbvirt_descriptors_t descriptors = {
140 .device = &std_device_descriptor,
141 .configuration = &configuration,
142 .configuration_count = 1,
143};
144
145/** Initializes virtual hub device.
146 *
147 * @param dev Virtual USB device backend.
148 * @return Error code.
149 */
150errno_t virthub_init(usbvirt_device_t *dev, const char* name)
151{
152 if (dev == NULL) {
153 return EBADMEM;
154 }
155 dev->ops = &hub_ops;
156 dev->descriptors = &descriptors;
157 dev->address = 0;
158
159 char *n = str_dup(name);
160 if (!n)
161 return ENOMEM;
162
163 hub_t *hub = malloc(sizeof(hub_t));
164 if (hub == NULL) {
165 free(n);
166 return ENOMEM;
167 }
168
169 dev->name = n;
170 hub_init(hub);
171 dev->device_data = hub;
172
173 return EOK;
174}
175
176/** Connect a device to a virtual hub.
177 *
178 * @param dev Virtual device representing the hub.
179 * @param conn Device to be connected.
180 * @return Port device was connected to.
181 */
182int virthub_connect_device(usbvirt_device_t *dev, vhc_virtdev_t *conn)
183{
184 assert(dev != NULL);
185 assert(conn != NULL);
186
187 hub_t *hub = (hub_t *) dev->device_data;
188
189 hub_acquire(hub);
190 size_t port = hub_connect_device(hub, conn);
191 hub_release(hub);
192
193 return port;
194}
195
196/** Disconnect a device from a virtual hub.
197 *
198 * @param dev Virtual device representing the hub.
199 * @param conn Device to be disconnected.
200 * @return Error code.
201 */
202errno_t virthub_disconnect_device(usbvirt_device_t *dev, vhc_virtdev_t *conn)
203{
204 assert(dev != NULL);
205 assert(conn != NULL);
206
207 hub_t *hub = (hub_t *) dev->device_data;
208
209 hub_acquire(hub);
210 hub_disconnect_device(hub, conn);
211 hub_release(hub);
212
213 return EOK;
214}
215
216/** Whether trafic is propagated to given device.
217 *
218 * @param dev Virtual device representing the hub.
219 * @param conn Connected device.
220 * @return Whether port is signalling to the device.
221 */
222bool virthub_is_device_enabled(usbvirt_device_t *dev, vhc_virtdev_t *conn)
223{
224 assert(dev != NULL);
225 assert(conn != NULL);
226
227 hub_t *hub = (hub_t *) dev->device_data;
228
229 hub_acquire(hub);
230
231 hub_port_state_t state = HUB_PORT_STATE_UNKNOWN;
232 size_t port = hub_find_device(hub, conn);
233 if (port != (size_t) -1) {
234 state = hub_get_port_state(hub, port);
235 }
236 hub_release(hub);
237
238 return state == HUB_PORT_STATE_ENABLED;
239}
240
241/** Format status of a virtual hub.
242 *
243 * @param dev Virtual device representing the hub.
244 * @param[out] status Hub status information.
245 * @param[in] len Size of the @p status buffer.
246 */
247void virthub_get_status(usbvirt_device_t *dev, char *status, size_t len)
248{
249 assert(dev != NULL);
250 if (len == 0) {
251 return;
252 }
253
254 hub_t *hub = (hub_t *) dev->device_data;
255
256 char port_status[HUB_PORT_COUNT + 1];
257
258 size_t i;
259 for (i = 0; i < HUB_PORT_COUNT; i++) {
260 port_status[i] = hub_port_state_to_char(
261 hub_get_port_state(hub, i));
262 }
263 port_status[HUB_PORT_COUNT] = 0;
264
265 snprintf(status, len, "vhub:%s", port_status);
266}
267
268/**
269 * @}
270 */
Note: See TracBrowser for help on using the repository browser.