dereferencing NULL pointer
File: drivers/net/usb/.tmp_hso.o.preproc
Full description: {AutomatonChecker of /usr/share/stanse/checkers/AutomatonChecker/kernel_memory.xml} in function 'hso_free_tiomget' dereferencing NULL pointer [traces: 1]
Importance: 0
Checker: AutomatonChecker of /usr/share/stanse/checkers/AutomatonChecker/kernel_memory.xml
Trace:
line 2475: not affected ==> pointer is still NULL.
line 2475: not affected ==> pointer is still NULL.
line 2476: not affected ==> pointer is still NULL.
line 2537: not affected ==> pointer is still NULL.
line 2426: dereferencing NULL pointer here.[serial]
This one is:
False positive index (the lower the better): 0
File contents (this file is distributed under the terms specified in the original file):
1|static inline struct hso_serial *get_serial_by_tty(struct tty_struct *tty)
2|{
3| if (tty)
4| return tty->driver_data;
5| return ((void *)0);
6|}
7|enum pkt_parse_state {
8| WAIT_IP,
9| WAIT_DATA,
10| WAIT_SYNC
11|};
12|
13|
14|
15|
16|
17|struct hso_shared_int {
18| struct usb_endpoint_descriptor *intr_endp;
19| void *shared_intr_buf;
20| struct urb *shared_intr_urb;
21| struct usb_device *usb;
22| int use_count;
23| int ref_count;
24| struct mutex shared_int_lock;
25|};
26|
27|struct hso_net {
28| struct hso_device *parent;
29| struct net_device *net;
30| struct rfkill *rfkill;
31|
32| struct usb_endpoint_descriptor *in_endp;
33| struct usb_endpoint_descriptor *out_endp;
34|
35| struct urb *mux_bulk_rx_urb_pool[4];
36| struct urb *mux_bulk_tx_urb;
37| void *mux_bulk_rx_buf_pool[4];
38| void *mux_bulk_tx_buf;
39|
40| struct sk_buff *skb_rx_buf;
41| struct sk_buff *skb_tx_buf;
42|
43| enum pkt_parse_state rx_parse_state;
44| spinlock_t net_lock;
45|
46| unsigned short rx_buf_size;
47| unsigned short rx_buf_missing;
48| struct iphdr rx_ip_hdr;
49|
50| unsigned long flags;
51|};
52|
53|enum rx_ctrl_state{
54| RX_IDLE,
55| RX_SENT,
56| RX_PENDING
57|};
58|struct hso_serial_state_notification {
59| u8 bmRequestType;
60| u8 bNotification;
61| u16 wValue;
62| u16 wIndex;
63| u16 wLength;
64| u16 UART_state_bitmap;
65|} ;
66|
67|struct hso_tiocmget {
68| struct mutex mutex;
69| wait_queue_head_t waitq;
70| int intr_completed;
71| struct usb_endpoint_descriptor *endp;
72| struct urb *urb;
73| struct hso_serial_state_notification serial_state_notification;
74| u16 prev_UART_state_bitmap;
75| struct uart_icount icount;
76|};
77|
78|
79|struct hso_serial {
80| struct hso_device *parent;
81| int magic;
82| u8 minor;
83|
84| struct hso_shared_int *shared_int;
85|
86|
87|
88| struct urb *rx_urb[2];
89| u8 num_rx_urbs;
90| u8 *rx_data[2];
91| u16 rx_data_length;
92|
93| struct urb *tx_urb;
94| u8 *tx_data;
95| u8 *tx_buffer;
96| u16 tx_data_length;
97| u16 tx_data_count;
98| u16 tx_buffer_count;
99| struct usb_ctrlrequest ctrl_req_tx;
100| struct usb_ctrlrequest ctrl_req_rx;
101|
102| struct usb_endpoint_descriptor *in_endp;
103| struct usb_endpoint_descriptor *out_endp;
104|
105| enum rx_ctrl_state rx_state;
106| u8 rts_state;
107| u8 dtr_state;
108| unsigned tx_urb_used:1;
109|
110|
111| struct tty_struct *tty;
112| int open_count;
113| spinlock_t serial_lock;
114|
115| int (*write_data) (struct hso_serial *serial);
116| struct hso_tiocmget *tiocmget;
117|
118|
119|
120|
121| int curr_rx_urb_idx;
122| u16 curr_rx_urb_offset;
123| u8 rx_urb_filled[2];
124| struct tasklet_struct unthrottle_tasklet;
125| struct work_struct retry_unthrottle_workqueue;
126|};
127|
128|struct hso_device {
129| union {
130| struct hso_serial *dev_serial;
131| struct hso_net *dev_net;
132| } port_data;
133|
134| u32 port_spec;
135|
136| u8 is_active;
137| u8 usb_gone;
138| struct work_struct async_get_intf;
139| struct work_struct async_put_intf;
140| struct work_struct reset_device;
141|
142| struct usb_device *usb;
143| struct usb_interface *interface;
144|
145| struct device *dev;
146| struct kref ref;
147| struct mutex mutex;
148|};
149|static int hso_serial_tiocmset(struct tty_struct *tty, struct file *file,
150| unsigned int set, unsigned int clear);
151|static void ctrl_callback(struct urb *urb);
152|static int put_rxbuf_data(struct urb *urb, struct hso_serial *serial);
153|static void hso_kick_transmit(struct hso_serial *serial);
154|
155|static int hso_mux_submit_intr_urb(struct hso_shared_int *mux_int,
156| struct usb_device *usb, gfp_t gfp);
157|static void handle_usb_error(int status, const char *function,
158| struct hso_device *hso_dev);
159|static struct usb_endpoint_descriptor *hso_get_ep(struct usb_interface *intf,
160| int type, int dir);
161|static int hso_get_mux_ports(struct usb_interface *intf, unsigned char *ports);
162|static void hso_free_interface(struct usb_interface *intf);
163|static int hso_start_serial_device(struct hso_device *hso_dev, gfp_t flags);
164|static int hso_stop_serial_device(struct hso_device *hso_dev);
165|static int hso_start_net_device(struct hso_device *hso_dev);
166|static void hso_free_shared_int(struct hso_shared_int *shared_int);
167|static int hso_stop_net_device(struct hso_device *hso_dev);
168|static void hso_serial_ref_free(struct kref *ref);
169|static void hso_std_serial_read_bulk_callback(struct urb *urb);
170|static int hso_mux_serial_read(struct hso_serial *serial);
171|static void async_get_intf(struct work_struct *data);
172|static void async_put_intf(struct work_struct *data);
173|static int hso_put_activity(struct hso_device *hso_dev);
174|static int hso_get_activity(struct hso_device *hso_dev);
175|static void tiocmget_intr_callback(struct urb *urb);
176|static void reset_device(struct work_struct *data);
177|
178|
179|
180|
181|
182|
183|static inline struct hso_net *dev2net(struct hso_device *hso_dev)
184|{
185| return hso_dev->port_data.dev_net;
186|}
187|
188|static inline struct hso_serial *dev2ser(struct hso_device *hso_dev)
189|{
190| return hso_dev->port_data.dev_serial;
191|}
192|static int debug;
193|static int tty_major;
194|static int disable_net;
195|
196|
197|static const char driver_name[] = "hso";
198|static const char tty_filename[] = "ttyHS";
199|static const char *version = "drivers/net/usb/.tmp_hso.o.armored.c" ": " "Option Wireless";
200|
201|static struct usb_driver hso_driver;
202|
203|static struct tty_driver *tty_drv;
204|static struct hso_device *serial_table[256];
205|static struct hso_device *network_table[10];
206|static spinlock_t serial_table_lock;
207|
208|static const s32 default_port_spec[] = {
209| 0x0100 | 0x12,
210| 0x0200 | 0x10,
211| 0x0200 | 0x11,
212| 0
213|};
214|
215|static const s32 icon321_port_spec[] = {
216| 0x0100 | 0x12,
217| 0x0200 | 0x9,
218| 0x0200 | 0x11,
219| 0x0200 | 0x10,
220| 0
221|};
222|static const struct usb_device_id hso_ids[] = {
223| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x6711), .driver_info = (kernel_ulong_t)default_port_spec},
224| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x6731), .driver_info = (kernel_ulong_t)default_port_spec},
225| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x6751), .driver_info = (kernel_ulong_t)default_port_spec},
226| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x6771), .driver_info = (kernel_ulong_t)default_port_spec},
227| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x6791), .driver_info = (kernel_ulong_t)default_port_spec},
228| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x6811), .driver_info = (kernel_ulong_t)default_port_spec},
229| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x6911), .driver_info = (kernel_ulong_t)default_port_spec},
230| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x6951), .driver_info = (kernel_ulong_t)default_port_spec},
231| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x6971), .driver_info = (kernel_ulong_t)default_port_spec},
232| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7011), .driver_info = (kernel_ulong_t)default_port_spec},
233| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7031), .driver_info = (kernel_ulong_t)default_port_spec},
234| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7051), .driver_info = (kernel_ulong_t)default_port_spec},
235| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7071), .driver_info = (kernel_ulong_t)default_port_spec},
236| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7111), .driver_info = (kernel_ulong_t)default_port_spec},
237| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7211), .driver_info = (kernel_ulong_t)default_port_spec},
238| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7251), .driver_info = (kernel_ulong_t)default_port_spec},
239| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7271), .driver_info = (kernel_ulong_t)default_port_spec},
240| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7311), .driver_info = (kernel_ulong_t)default_port_spec},
241| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0xc031), .driver_info = (kernel_ulong_t)default_port_spec},
242| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0xd013), .driver_info = (kernel_ulong_t)icon321_port_spec},
243| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0xd031), .driver_info = (kernel_ulong_t)icon321_port_spec},
244| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0xd033), .driver_info = (kernel_ulong_t)icon321_port_spec},
245| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7301)},
246| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7361)},
247| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7381)},
248| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7401)},
249| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7501)},
250| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7601)},
251| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7701)},
252| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7706)},
253| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7801)},
254| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7901)},
255| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7A01)},
256| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x7A05)},
257| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x8200)},
258| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x8201)},
259| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x8300)},
260| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x8302)},
261| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x8304)},
262| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x8400)},
263| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x8600)},
264| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x8800)},
265| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x8900)},
266| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0x9000)},
267| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0xd035)},
268| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0xd055)},
269| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0xd155)},
270| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0xd255)},
271| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0xd057)},
272| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0xd157)},
273| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0xd257)},
274| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0xd357)},
275| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0xd058)},
276| {.match_flags = (0x0001 | 0x0002), .idVendor = (0x0af0), .idProduct = (0xc100)},
277| {}
278|};
279|extern const struct usb_device_id __mod_usb_device_table ;
280|
281|
282|static ssize_t hso_sysfs_show_porttype(struct device *dev,
283| struct device_attribute *attr,
284| char *buf)
285|{
286| struct hso_device *hso_dev = dev_get_drvdata(dev);
287| char *port_name;
288|
289| if (!hso_dev)
290| return 0;
291|
292| switch (hso_dev->port_spec & 0xFF) {
293| case 0x1:
294| port_name = "Control";
295| break;
296| case 0x2:
297| port_name = "Application";
298| break;
299| case 0x5:
300| port_name = "Application2";
301| break;
302| case 0x3:
303| port_name = "GPS";
304| break;
305| case 0x6:
306| port_name = "GPS Control";
307| break;
308| case 0x4:
309| port_name = "PCSC";
310| break;
311| case 0x10:
312| port_name = "Diagnostic";
313| break;
314| case 0x9:
315| port_name = "Diagnostic2";
316| break;
317| case 0x11:
318| port_name = "Modem";
319| break;
320| case 0x12:
321| port_name = "Network";
322| break;
323| default:
324| port_name = "Unknown";
325| break;
326| }
327|
328| return sprintf(buf, "%s\n", port_name);
329|}
330|static struct device_attribute dev_attr_hsotype = { .attr = {.name = "hsotype", .mode = (00400|00040|00004) }, .show = hso_sysfs_show_porttype, .store = ((void *)0), };
331|
332|static int hso_urb_to_index(struct hso_serial *serial, struct urb *urb)
333|{
334| int idx;
335|
336| for (idx = 0; idx < serial->num_rx_urbs; idx++)
337| if (serial->rx_urb[idx] == urb)
338| return idx;
339| dev_err(serial->parent->dev, "hso_urb_to_index failed\n");
340| return -1;
341|}
342|
343|
344|static u32 hso_mux_to_port(int mux)
345|{
346| u32 result;
347|
348| switch (mux) {
349| case 0x1:
350| result = 0x1;
351| break;
352| case 0x2:
353| result = 0x2;
354| break;
355| case 0x4:
356| result = 0x4;
357| break;
358| case 0x8:
359| result = 0x3;
360| break;
361| case 0x10:
362| result = 0x5;
363| break;
364| default:
365| result = 0x0;
366| }
367| return result;
368|}
369|
370|
371|static u32 hso_port_to_mux(int port)
372|{
373| u32 result;
374|
375| switch (port & 0xFF) {
376| case 0x1:
377| result = 0x0;
378| break;
379| case 0x2:
380| result = 0x1;
381| break;
382| case 0x4:
383| result = 0x2;
384| break;
385| case 0x3:
386| result = 0x3;
387| break;
388| case 0x5:
389| result = 0x4;
390| break;
391| default:
392| result = 0x0;
393| }
394| return result;
395|}
396|
397|static struct hso_serial *get_serial_by_shared_int_and_type(
398| struct hso_shared_int *shared_int,
399| int mux)
400|{
401| int i, port;
402|
403| port = hso_mux_to_port(mux);
404|
405| for (i = 0; i < 256; i++) {
406| if (serial_table[i] &&
407| (dev2ser(serial_table[i])->shared_int == shared_int) &&
408| ((serial_table[i]->port_spec & 0xFF) == port)) {
409| return dev2ser(serial_table[i]);
410| }
411| }
412|
413| return ((void *)0);
414|}
415|
416|static struct hso_serial *get_serial_by_index(unsigned index)
417|{
418| struct hso_serial *serial = ((void *)0);
419| unsigned long flags;
420|
421| __st_spin_lock_irqsave_st__(&serial_table_lock, flags);
422| if (serial_table[index])
423| serial = dev2ser(serial_table[index]);
424| __st_spin_unlock_irqrestore_st__(&serial_table_lock, flags);
425|
426| return serial;
427|}
428|
429|static int get_free_serial_index(void)
430|{
431| int index;
432| unsigned long flags;
433|
434| __st_spin_lock_irqsave_st__(&serial_table_lock, flags);
435| for (index = 0; index < 256; index++) {
436| if (serial_table[index] == ((void *)0)) {
437| __st_spin_unlock_irqrestore_st__(&serial_table_lock, flags);
438| return index;
439| }
440| }
441| __st_spin_unlock_irqrestore_st__(&serial_table_lock, flags);
442|
443| printk("<3>" "%s: no free serial devices in table\n", __func__);
444| return -1;
445|}
446|
447|static void set_serial_by_index(unsigned index, struct hso_serial *serial)
448|{
449| unsigned long flags;
450|
451| __st_spin_lock_irqsave_st__(&serial_table_lock, flags);
452| if (serial)
453| serial_table[index] = serial->parent;
454| else
455| serial_table[index] = ((void *)0);
456| __st_spin_unlock_irqrestore_st__(&serial_table_lock, flags);
457|}
458|
459|static void handle_usb_error(int status, const char *function,
460| struct hso_device *hso_dev)
461|{
462| char *explanation;
463|
464| switch (status) {
465| case -19:
466| explanation = "no device";
467| break;
468| case -2:
469| explanation = "endpoint not enabled";
470| break;
471| case -32:
472| explanation = "endpoint stalled";
473| break;
474| case -28:
475| explanation = "not enough bandwidth";
476| break;
477| case -108:
478| explanation = "device disabled";
479| break;
480| case -113:
481| explanation = "device suspended";
482| break;
483| case -22:
484| case -11:
485| case -27:
486| case -90:
487| explanation = "internal error";
488| break;
489| case -84:
490| case -71:
491| case -62:
492| case -110:
493| explanation = "protocol error";
494| if (hso_dev)
495| schedule_work(&hso_dev->reset_device);
496| break;
497| default:
498| explanation = "unknown status";
499| break;
500| }
501|
502|
503| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "%s: received USB status - %s (%d)" "\n", 717, __func__, function, explanation, status); } while (0); } while (0);
504|}
505|
506|
507|
508|
509|static int hso_net_open(struct net_device *net)
510|{
511| struct hso_net *odev = netdev_priv(net);
512| unsigned long flags = 0;
513|
514| if (!odev) {
515| dev_err(&net->dev, "No net device !\n");
516| return -19;
517| }
518|
519| odev->skb_tx_buf = ((void *)0);
520|
521|
522| __st_spin_lock_irqsave_st__(&odev->net_lock, flags);
523| odev->rx_parse_state = WAIT_IP;
524| odev->rx_buf_size = 0;
525| odev->rx_buf_missing = sizeof(struct iphdr);
526| __st_spin_unlock_irqrestore_st__(&odev->net_lock, flags);
527|
528|
529| set_bit(0, &odev->flags);
530| hso_start_net_device(odev->parent);
531|
532|
533| netif_start_queue(net);
534|
535| return 0;
536|}
537|
538|
539|static int hso_net_close(struct net_device *net)
540|{
541| struct hso_net *odev = netdev_priv(net);
542|
543|
544| netif_stop_queue(net);
545|
546| clear_bit(0, &odev->flags);
547|
548| hso_stop_net_device(odev->parent);
549|
550|
551| return 0;
552|}
553|
554|
555|static void write_bulk_callback(struct urb *urb)
556|{
557| struct hso_net *odev = urb->context;
558| int status = urb->status;
559|
560|
561| if (!odev || !(__builtin_constant_p((0)) ? constant_test_bit((0), (&odev->flags)) : variable_test_bit((0), (&odev->flags)))) {
562| dev_err(&urb->dev->dev, "%s: device not running\n", __func__);
563| return;
564| }
565|
566|
567| if (!netif_device_present(odev->net)) {
568| dev_err(&urb->dev->dev, "%s: net device not present\n",
569| __func__);
570| return;
571| }
572|
573|
574|
575| if (status)
576| handle_usb_error(status, __func__, odev->parent);
577|
578| hso_put_activity(odev->parent);
579|
580|
581| netif_wake_queue(odev->net);
582|}
583|
584|
585|static netdev_tx_t hso_net_start_xmit(struct sk_buff *skb,
586| struct net_device *net)
587|{
588| struct hso_net *odev = netdev_priv(net);
589| int result;
590|
591|
592| netif_stop_queue(net);
593| if (hso_get_activity(odev->parent) == -11) {
594| odev->skb_tx_buf = skb;
595| return NETDEV_TX_OK;
596| }
597|
598|
599| ;
600|
601| __st_memcpy_st__(odev->mux_bulk_tx_buf, skb->data, skb->len);
602| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "len: %d/%d" "\n", 816, __func__, skb->len, 2048); } while (0); } while (0);
603|
604|
605| usb_fill_bulk_urb(odev->mux_bulk_tx_urb,
606| odev->parent->usb,
607| ((3 << 30) | __create_pipe(odev->parent->usb, odev->out_endp-> bEndpointAddress & 0x7F))
608|
609| ,
610| odev->mux_bulk_tx_buf, skb->len, write_bulk_callback,
611| odev);
612|
613|
614| odev->mux_bulk_tx_urb->transfer_flags |= 0x0040;
615|
616|
617| result = usb_submit_urb(odev->mux_bulk_tx_urb, ((( gfp_t)0x20u)));
618| if (result) {
619| dev_warn(&odev->parent->interface->dev,
620| "failed mux_bulk_tx_urb %d\n", result);
621| net->stats.tx_errors++;
622| netif_start_queue(net);
623| } else {
624| net->stats.tx_packets++;
625| net->stats.tx_bytes += skb->len;
626| }
627| consume_skb(skb);
628|
629| return NETDEV_TX_OK;
630|}
631|
632|static const struct ethtool_ops ops = {
633| .get_link = ethtool_op_get_link
634|};
635|
636|
637|static void hso_net_tx_timeout(struct net_device *net)
638|{
639| struct hso_net *odev = netdev_priv(net);
640|
641| if (!odev)
642| return;
643|
644|
645| dev_warn(&net->dev, "Tx timed out.\n");
646|
647|
648| if (odev->mux_bulk_tx_urb &&
649| (odev->mux_bulk_tx_urb->status == -115))
650| usb_unlink_urb(odev->mux_bulk_tx_urb);
651|
652|
653| net->stats.tx_errors++;
654|}
655|
656|
657|static void packetizeRx(struct hso_net *odev, unsigned char *ip_pkt,
658| unsigned int count, unsigned char is_eop)
659|{
660| unsigned short temp_bytes;
661| unsigned short buffer_offset = 0;
662| unsigned short frame_len;
663| unsigned char *tmp_rx_buf;
664|
665|
666| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "Rx %d bytes" "\n", 880, __func__, count); } while (0); } while (0);
667| ;
668|
669| while (count) {
670| switch (odev->rx_parse_state) {
671| case WAIT_IP:
672|
673|
674| temp_bytes =
675| (count <
676| odev->rx_buf_missing) ? count : odev->
677| rx_buf_missing;
678|
679| __st_memcpy_st__(((unsigned char *)(&odev->rx_ip_hdr)) +
680| odev->rx_buf_size, ip_pkt + buffer_offset,
681| temp_bytes);
682|
683| odev->rx_buf_size += temp_bytes;
684| buffer_offset += temp_bytes;
685| odev->rx_buf_missing -= temp_bytes;
686| count -= temp_bytes;
687|
688| if (!odev->rx_buf_missing) {
689|
690|
691| frame_len = (__builtin_constant_p((__u16)(( __u16)(__be16)(odev->rx_ip_hdr.tot_len))) ? ((__u16)( (((__u16)(( __u16)(__be16)(odev->rx_ip_hdr.tot_len)) & (__u16)0x00ffU) << 8) | (((__u16)(( __u16)(__be16)(odev->rx_ip_hdr.tot_len)) & (__u16)0xff00U) >> 8))) : __fswab16(( __u16)(__be16)(odev->rx_ip_hdr.tot_len)));
692|
693| if ((frame_len > 1500) ||
694| (frame_len < sizeof(struct iphdr))) {
695| dev_err(&odev->net->dev,
696| "Invalid frame (%d) length\n",
697| frame_len);
698| odev->rx_parse_state = WAIT_SYNC;
699| continue;
700| }
701|
702| odev->skb_rx_buf = netdev_alloc_skb(odev->net,
703| frame_len);
704| if (!odev->skb_rx_buf) {
705|
706| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "could not allocate memory" "\n", 920, __func__); } while (0); } while (0);
707| odev->rx_parse_state = WAIT_SYNC;
708| return;
709| }
710|
711|
712|
713| tmp_rx_buf =
714| skb_put(odev->skb_rx_buf,
715| sizeof(struct iphdr));
716| __st_memcpy_st__(tmp_rx_buf, (char *)&(odev->rx_ip_hdr),
717| sizeof(struct iphdr));
718|
719|
720| odev->rx_buf_size = sizeof(struct iphdr);
721|
722|
723| odev->rx_buf_missing =
724| frame_len - sizeof(struct iphdr);
725| odev->rx_parse_state = WAIT_DATA;
726| }
727| break;
728|
729| case WAIT_DATA:
730| temp_bytes = (count < odev->rx_buf_missing)
731| ? count : odev->rx_buf_missing;
732|
733|
734|
735|
736| tmp_rx_buf = skb_put(odev->skb_rx_buf, temp_bytes);
737| __st_memcpy_st__(tmp_rx_buf, ip_pkt + buffer_offset, temp_bytes);
738|
739| odev->rx_buf_missing -= temp_bytes;
740| count -= temp_bytes;
741| buffer_offset += temp_bytes;
742| odev->rx_buf_size += temp_bytes;
743| if (!odev->rx_buf_missing) {
744|
745|
746| odev->skb_rx_buf->protocol = (( __be16)(__builtin_constant_p((__u16)((0x0800))) ? ((__u16)( (((__u16)((0x0800)) & (__u16)0x00ffU) << 8) | (((__u16)((0x0800)) & (__u16)0xff00U) >> 8))) : __fswab16((0x0800))));
747|
748| odev->skb_rx_buf->ip_summed =
749| 1;
750|
751| skb_reset_mac_header(odev->skb_rx_buf);
752|
753|
754| netif_rx(odev->skb_rx_buf);
755|
756| odev->skb_rx_buf = ((void *)0);
757|
758|
759| odev->net->stats.rx_packets++;
760|
761| odev->net->stats.rx_bytes += odev->rx_buf_size;
762|
763| odev->rx_buf_size = 0;
764| odev->rx_buf_missing = sizeof(struct iphdr);
765| odev->rx_parse_state = WAIT_IP;
766| }
767| break;
768|
769| case WAIT_SYNC:
770| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " " W_S" "\n", 984, __func__); } while (0); } while (0);
771| count = 0;
772| break;
773| default:
774| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " " " "\n", 988, __func__); } while (0); } while (0);
775| count--;
776| break;
777| }
778| }
779|
780|
781| if (is_eop) {
782| if (odev->rx_parse_state == WAIT_SYNC) {
783| odev->rx_parse_state = WAIT_IP;
784| odev->rx_buf_size = 0;
785| odev->rx_buf_missing = sizeof(struct iphdr);
786| }
787| }
788|}
789|
790|
791|static void read_bulk_callback(struct urb *urb)
792|{
793| struct hso_net *odev = urb->context;
794| struct net_device *net;
795| int result;
796| int status = urb->status;
797|
798|
799| if (status) {
800| handle_usb_error(status, __func__, odev->parent);
801| return;
802| }
803|
804|
805| if (!odev || !(__builtin_constant_p((0)) ? constant_test_bit((0), (&odev->flags)) : variable_test_bit((0), (&odev->flags)))) {
806| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "BULK IN callback but driver is not active!" "\n", 1020, __func__); } while (0); } while (0);
807| return;
808| }
809| usb_mark_last_busy(urb->dev);
810|
811| net = odev->net;
812|
813| if (!netif_device_present(net)) {
814|
815| return;
816| }
817|
818| if (odev->parent->port_spec & 0x01000000) {
819| u32 rest;
820| u8 crc_check[4] = { 0xDE, 0xAD, 0xBE, 0xEF };
821| rest = urb->actual_length %
822| (( __u16)(__le16)(odev->in_endp->wMaxPacketSize));
823| if (((rest == 5) || (rest == 6)) &&
824| !memcmp(((u8 *) urb->transfer_buffer) +
825| urb->actual_length - 4, crc_check, 4)) {
826| urb->actual_length -= 4;
827| }
828| }
829|
830|
831| if (urb->actual_length) {
832|
833|
834| __st_spin_lock_st__(&odev->net_lock);
835| packetizeRx(odev, urb->transfer_buffer, urb->actual_length,
836| (urb->transfer_buffer_length >
837| urb->actual_length) ? 1 : 0);
838| __st_spin_unlock_st__(&odev->net_lock);
839| }
840|
841|
842|
843| usb_fill_bulk_urb(urb,
844| odev->parent->usb,
845| ((3 << 30) | __create_pipe(odev->parent->usb, odev->in_endp-> bEndpointAddress & 0x7F) | 0x80)
846|
847| ,
848| urb->transfer_buffer, 2048,
849| read_bulk_callback, odev);
850|
851|
852|
853| result = usb_submit_urb(urb, ((( gfp_t)0x20u)));
854| if (result)
855| dev_warn(&odev->parent->interface->dev,
856| "%s failed submit mux_bulk_rx_urb %d\n", __func__,
857| result);
858|}
859|
860|
861|
862|static void hso_init_termios(struct ktermios *termios)
863|{
864|
865|
866|
867| termios->c_iflag &=
868| ~(0000001
869| | 0000002
870| | 0000010
871| | 0000040
872| | 0000100
873| | 0000200
874| | 0000400
875| | 0002000);
876|
877|
878| termios->c_oflag &= ~0000001;
879|
880| termios->c_lflag &=
881| ~(0000010
882| | 0000100
883| | 0000002
884|
885| | 0000001
886|
887| | 0100000);
888|
889| termios->c_cflag &=
890| ~(0000060
891| | 0000400
892| | 0010017
893| | 0010000);
894|
895| termios->c_cflag |= 0000060;
896|
897|
898| tty_termios_encode_baud_rate(termios, 115200, 115200);
899|}
900|
901|static void _hso_serial_set_termios(struct tty_struct *tty,
902| struct ktermios *old)
903|{
904| struct hso_serial *serial = get_serial_by_tty(tty);
905| struct ktermios *termios;
906|
907| if (!serial) {
908| printk("<3>" "%s: no tty structures", __func__);
909| return;
910| }
911|
912| do { if (0x08 & debug) do { printk("<6>" "[%d:%s]: " "port %d" "\n", 1126, __func__, serial->minor); } while (0); } while (0);
913|
914|
915|
916|
917| termios = tty->termios;
918| termios->c_iflag &= ~0002000;
919|
920| termios->c_cflag &=
921| ~(0000060
922| | 0000400
923| | 0010017
924| | 0010000);
925|
926| termios->c_cflag |= 0000060;
927|
928|
929| tty_encode_baud_rate(tty, 115200, 115200);
930|}
931|
932|static void hso_resubmit_rx_bulk_urb(struct hso_serial *serial, struct urb *urb)
933|{
934| int result;
935|
936|
937| usb_fill_bulk_urb(urb, serial->parent->usb,
938| ((3 << 30) | __create_pipe(serial->parent->usb, serial->in_endp-> bEndpointAddress & 0x7F) | 0x80)
939|
940| ,
941| urb->transfer_buffer, serial->rx_data_length,
942| hso_std_serial_read_bulk_callback, serial);
943|
944|
945| result = usb_submit_urb(urb, ((( gfp_t)0x20u)));
946| if (result) {
947| dev_err(&urb->dev->dev, "%s failed submit serial rx_urb %d\n",
948| __func__, result);
949| }
950|}
951|
952|
953|
954|
955|static void put_rxbuf_data_and_resubmit_bulk_urb(struct hso_serial *serial)
956|{
957| int count;
958| struct urb *curr_urb;
959|
960| while (serial->rx_urb_filled[serial->curr_rx_urb_idx]) {
961| curr_urb = serial->rx_urb[serial->curr_rx_urb_idx];
962| count = put_rxbuf_data(curr_urb, serial);
963| if (count == -1)
964| return;
965| if (count == 0) {
966| serial->curr_rx_urb_idx++;
967| if (serial->curr_rx_urb_idx >= serial->num_rx_urbs)
968| serial->curr_rx_urb_idx = 0;
969| hso_resubmit_rx_bulk_urb(serial, curr_urb);
970| }
971| }
972|}
973|
974|static void put_rxbuf_data_and_resubmit_ctrl_urb(struct hso_serial *serial)
975|{
976| int count = 0;
977| struct urb *urb;
978|
979| urb = serial->rx_urb[0];
980| if (serial->open_count > 0) {
981| count = put_rxbuf_data(urb, serial);
982| if (count == -1)
983| return;
984| }
985|
986|
987| if (count == 0 && ((urb->actual_length != 0) ||
988| (serial->rx_state == RX_PENDING))) {
989| serial->rx_state = RX_SENT;
990| hso_mux_serial_read(serial);
991| } else
992| serial->rx_state = RX_IDLE;
993|}
994|
995|
996|
997|static void hso_std_serial_read_bulk_callback(struct urb *urb)
998|{
999| struct hso_serial *serial = urb->context;
1000| int status = urb->status;
1001|
1002|
1003| if (!serial) {
1004| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "serial == NULL" "\n", 1218, __func__); } while (0); } while (0);
1005| return;
1006| } else if (status) {
1007| handle_usb_error(status, __func__, serial->parent);
1008| return;
1009| }
1010|
1011| do { if (0x08 & debug) do { printk("<6>" "[%d:%s]: " "\n--- Got serial_read_bulk callback %02x ---" "\n", 1225, __func__, status); } while (0); } while (0);
1012| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "Actual length = %d\n" "\n", 1226, __func__, urb->actual_length); } while (0); } while (0);
1013| ;
1014|
1015|
1016| if (serial->open_count == 0)
1017| return;
1018|
1019| if (status == 0) {
1020| if (serial->parent->port_spec & 0x01000000) {
1021| u32 rest;
1022| u8 crc_check[4] = { 0xDE, 0xAD, 0xBE, 0xEF };
1023| rest =
1024| urb->actual_length %
1025| (( __u16)(__le16)(serial->in_endp->wMaxPacketSize));
1026| if (((rest == 5) || (rest == 6)) &&
1027| !memcmp(((u8 *) urb->transfer_buffer) +
1028| urb->actual_length - 4, crc_check, 4)) {
1029| urb->actual_length -= 4;
1030| }
1031| }
1032|
1033| __st_spin_lock_st__(&serial->serial_lock);
1034| serial->rx_urb_filled[hso_urb_to_index(serial, urb)] = 1;
1035| put_rxbuf_data_and_resubmit_bulk_urb(serial);
1036| __st_spin_unlock_st__(&serial->serial_lock);
1037| } else if (status == -2 || status == -104) {
1038|
1039| do { if (0x02 & debug) do { printk("<6>" "[%d:%s]: " "Port %d, successfully unlinked urb" "\n", 1253, __func__, serial->minor); } while (0); } while (0);
1040| __st_spin_lock_st__(&serial->serial_lock);
1041| serial->rx_urb_filled[hso_urb_to_index(serial, urb)] = 0;
1042| hso_resubmit_rx_bulk_urb(serial, urb);
1043| __st_spin_unlock_st__(&serial->serial_lock);
1044| } else {
1045| do { if (0x02 & debug) do { printk("<6>" "[%d:%s]: " "Port %d, status = %d for read urb" "\n", 1259, __func__, serial->minor, status); } while (0); } while (0);
1046| return;
1047| }
1048|}
1049|
1050|
1051|
1052|
1053|
1054|static void hso_unthrottle_tasklet(struct hso_serial *serial)
1055|{
1056| unsigned long flags;
1057|
1058| __st_spin_lock_irqsave_st__(&serial->serial_lock, flags);
1059| if ((serial->parent->port_spec & 0x0100))
1060| put_rxbuf_data_and_resubmit_ctrl_urb(serial);
1061| else
1062| put_rxbuf_data_and_resubmit_bulk_urb(serial);
1063| __st_spin_unlock_irqrestore_st__(&serial->serial_lock, flags);
1064|}
1065|
1066|static void hso_unthrottle(struct tty_struct *tty)
1067|{
1068| struct hso_serial *serial = get_serial_by_tty(tty);
1069|
1070| tasklet_hi_schedule(&serial->unthrottle_tasklet);
1071|}
1072|
1073|static void hso_unthrottle_workfunc(struct work_struct *work)
1074|{
1075| struct hso_serial *serial =
1076| ({ const typeof( ((struct hso_serial *)0)->retry_unthrottle_workqueue ) *__mptr = (work); (struct hso_serial *)( (char *)__mptr - 1 );})
1077| ;
1078| hso_unthrottle_tasklet(serial);
1079|}
1080|
1081|
1082|static int hso_serial_open(struct tty_struct *tty, struct file *filp)
1083|{
1084| struct hso_serial *serial = get_serial_by_index(tty->index);
1085| int result;
1086|
1087|
1088| if (serial == ((void *)0) || serial->magic != 0x48534f31) {
1089| ({ int __ret_warn_on = !!(1); if (__builtin_expect(!!(__ret_warn_on), 0)) warn_slowpath_null("drivers/net/usb/.tmp_hso.o.armored.c", 1303); __builtin_expect(!!(__ret_warn_on), 0); });
1090| tty->driver_data = ((void *)0);
1091| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "Failed to open port" "\n", 1305, __func__); } while (0); } while (0);
1092| return -19;
1093| }
1094|
1095| __st_mutex_lock_st__(&serial->parent->mutex);
1096| result = usb_autopm_get_interface(serial->parent->interface);
1097| if (result < 0)
1098| goto err_out;
1099|
1100| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "Opening %d" "\n", 1314, __func__, serial->minor); } while (0); } while (0);
1101| kref_get(&serial->parent->ref);
1102|
1103|
1104| __st_spin_lock_irq_st__(&serial->serial_lock);
1105| tty->driver_data = serial;
1106| tty_kref_put(serial->tty);
1107| serial->tty = tty_kref_get(tty);
1108| __st_spin_unlock_irq_st__(&serial->serial_lock);
1109|
1110|
1111| serial->open_count++;
1112| if (serial->open_count == 1) {
1113| serial->rx_state = RX_IDLE;
1114|
1115| _hso_serial_set_termios(tty, ((void *)0));
1116| tasklet_init(&serial->unthrottle_tasklet,
1117| (void (*)(unsigned long))hso_unthrottle_tasklet,
1118| (unsigned long)serial);
1119| do { do { static struct lock_class_key __key; __init_work(((&serial->retry_unthrottle_workqueue)), 0); ((&serial->retry_unthrottle_workqueue))->data = (atomic_long_t) { (WORK_STRUCT_NO_CPU) }; lockdep_init_map(&((&serial->retry_unthrottle_workqueue))->lockdep_map, "(&serial->retry_unthrottle_workqueue)", &__key, 0); INIT_LIST_HEAD(&((&serial->retry_unthrottle_workqueue))->entry); do { (((&serial->retry_unthrottle_workqueue)))->func = (((hso_unthrottle_workfunc))); } while (0); } while (0); } while (0)
1120| ;
1121| result = hso_start_serial_device(serial->parent, __st_GFP_KERNEL_st__);
1122| if (result) {
1123| hso_stop_serial_device(serial->parent);
1124| serial->open_count--;
1125| kref_put(&serial->parent->ref, hso_serial_ref_free);
1126| }
1127| } else {
1128| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "Port was already open" "\n", 1342, __func__); } while (0); } while (0);
1129| }
1130|
1131| usb_autopm_put_interface(serial->parent->interface);
1132|
1133|
1134| if (result)
1135| hso_serial_tiocmset(tty, ((void *)0), 0x004 | 0x002, 0);
1136|err_out:
1137| __st_mutex_unlock_st__(&serial->parent->mutex);
1138| return result;
1139|}
1140|
1141|
1142|static void hso_serial_close(struct tty_struct *tty, struct file *filp)
1143|{
1144| struct hso_serial *serial = tty->driver_data;
1145| u8 usb_gone;
1146|
1147| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "Closing serial port" "\n", 1361, __func__); } while (0); } while (0);
1148|
1149|
1150| if (serial == ((void *)0))
1151| return;
1152|
1153| __st_mutex_lock_st__(&serial->parent->mutex);
1154| usb_gone = serial->parent->usb_gone;
1155|
1156| if (!usb_gone)
1157| usb_autopm_get_interface(serial->parent->interface);
1158|
1159|
1160|
1161| serial->open_count--;
1162|
1163| if (serial->open_count <= 0) {
1164| serial->open_count = 0;
1165| __st_spin_lock_irq_st__(&serial->serial_lock);
1166| if (serial->tty == tty) {
1167| serial->tty->driver_data = ((void *)0);
1168| serial->tty = ((void *)0);
1169| tty_kref_put(tty);
1170| }
1171| __st_spin_unlock_irq_st__(&serial->serial_lock);
1172| if (!usb_gone)
1173| hso_stop_serial_device(serial->parent);
1174| tasklet_kill(&serial->unthrottle_tasklet);
1175| cancel_work_sync(&serial->retry_unthrottle_workqueue);
1176| }
1177|
1178| if (!usb_gone)
1179| usb_autopm_put_interface(serial->parent->interface);
1180|
1181| __st_mutex_unlock_st__(&serial->parent->mutex);
1182|
1183| kref_put(&serial->parent->ref, hso_serial_ref_free);
1184|}
1185|
1186|
1187|static int hso_serial_write(struct tty_struct *tty, const unsigned char *buf,
1188| int count)
1189|{
1190| struct hso_serial *serial = get_serial_by_tty(tty);
1191| int space, tx_bytes;
1192| unsigned long flags;
1193|
1194|
1195| if (serial == ((void *)0)) {
1196| printk("<3>" "%s: serial is NULL\n", __func__);
1197| return -19;
1198| }
1199|
1200| __st_spin_lock_irqsave_st__(&serial->serial_lock, flags);
1201|
1202| space = serial->tx_data_length - serial->tx_buffer_count;
1203| tx_bytes = (count < space) ? count : space;
1204|
1205| if (!tx_bytes)
1206| goto out;
1207|
1208| __st_memcpy_st__(serial->tx_buffer + serial->tx_buffer_count, buf, tx_bytes);
1209| serial->tx_buffer_count += tx_bytes;
1210|
1211|out:
1212| __st_spin_unlock_irqrestore_st__(&serial->serial_lock, flags);
1213|
1214| hso_kick_transmit(serial);
1215|
1216| return tx_bytes;
1217|}
1218|
1219|
1220|static int hso_serial_write_room(struct tty_struct *tty)
1221|{
1222| struct hso_serial *serial = get_serial_by_tty(tty);
1223| int room;
1224| unsigned long flags;
1225|
1226| __st_spin_lock_irqsave_st__(&serial->serial_lock, flags);
1227| room = serial->tx_data_length - serial->tx_buffer_count;
1228| __st_spin_unlock_irqrestore_st__(&serial->serial_lock, flags);
1229|
1230|
1231| return room;
1232|}
1233|
1234|
1235|static void hso_serial_set_termios(struct tty_struct *tty, struct ktermios *old)
1236|{
1237| struct hso_serial *serial = get_serial_by_tty(tty);
1238| unsigned long flags;
1239|
1240| if (old)
1241| do { if (0x10 & debug) do { printk("<6>" "[%d:%s]: " "Termios called with: cflags new[%d] - old[%d]" "\n",
1242| 1456
1243| , __func__, tty->termios->c_cflag, old->c_cflag); } while (0); } while (0)
1244| ;
1245|
1246|
1247| __st_spin_lock_irqsave_st__(&serial->serial_lock, flags);
1248| if (serial->open_count)
1249| _hso_serial_set_termios(tty, old);
1250| else
1251| tty->termios = old;
1252| __st_spin_unlock_irqrestore_st__(&serial->serial_lock, flags);
1253|
1254|
1255|}
1256|
1257|
1258|static int hso_serial_chars_in_buffer(struct tty_struct *tty)
1259|{
1260| struct hso_serial *serial = get_serial_by_tty(tty);
1261| int chars;
1262| unsigned long flags;
1263|
1264|
1265| if (serial == ((void *)0))
1266| return 0;
1267|
1268| __st_spin_lock_irqsave_st__(&serial->serial_lock, flags);
1269| chars = serial->tx_buffer_count;
1270| __st_spin_unlock_irqrestore_st__(&serial->serial_lock, flags);
1271|
1272| return chars;
1273|}
1274|static int tiocmget_submit_urb(struct hso_serial *serial,
1275| struct hso_tiocmget *tiocmget,
1276| struct usb_device *usb)
1277|{
1278| int result;
1279|
1280| if (serial->parent->usb_gone)
1281| return -19;
1282| usb_fill_int_urb(tiocmget->urb, usb,
1283| ((1 << 30) | __create_pipe(usb, tiocmget->endp-> bEndpointAddress & 0x7F) | 0x80)
1284|
1285| ,
1286| &tiocmget->serial_state_notification,
1287| sizeof(struct hso_serial_state_notification),
1288| tiocmget_intr_callback, serial,
1289| tiocmget->endp->bInterval);
1290| result = usb_submit_urb(tiocmget->urb, ((( gfp_t)0x20u)));
1291| if (result) {
1292| dev_warn(&usb->dev, "%s usb_submit_urb failed %d\n", __func__,
1293| result);
1294| }
1295| return result;
1296|
1297|}
1298|
1299|static void tiocmget_intr_callback(struct urb *urb)
1300|{
1301| struct hso_serial *serial = urb->context;
1302| struct hso_tiocmget *tiocmget;
1303| int status = urb->status;
1304| u16 UART_state_bitmap, prev_UART_state_bitmap;
1305| struct uart_icount *icount;
1306| struct hso_serial_state_notification *serial_state_notification;
1307| struct usb_device *usb;
1308|
1309|
1310| if (!serial)
1311| return;
1312| if (status) {
1313| handle_usb_error(status, __func__, serial->parent);
1314| return;
1315| }
1316| tiocmget = serial->tiocmget;
1317| if (!tiocmget)
1318| return;
1319| usb = serial->parent->usb;
1320| serial_state_notification = &tiocmget->serial_state_notification;
1321| if (serial_state_notification->bmRequestType != (0xa1) ||
1322| serial_state_notification->bNotification != (0x20) ||
1323| (( __u16)(__le16)(serial_state_notification->wValue)) != (0x0) ||
1324| (( __u16)(__le16)(serial_state_notification->wIndex)) != (0x2) ||
1325| (( __u16)(__le16)(serial_state_notification->wLength)) != (0x2)) {
1326| dev_warn(&usb->dev,
1327| "hso received invalid serial state notification\n");
1328|
1329| ;
1330| } else {
1331|
1332| UART_state_bitmap = (( __u16)(__le16)(serial_state_notification-> UART_state_bitmap))
1333| ;
1334| prev_UART_state_bitmap = tiocmget->prev_UART_state_bitmap;
1335| icount = &tiocmget->icount;
1336| __st_spin_lock_st__(&serial->serial_lock);
1337| if ((UART_state_bitmap & (0x1<<6)) !=
1338| (prev_UART_state_bitmap & (0x1<<6)))
1339| icount->parity++;
1340| if ((UART_state_bitmap & (0x1<<5)) !=
1341| (prev_UART_state_bitmap & (0x1<<5)))
1342| icount->parity++;
1343| if ((UART_state_bitmap & (0x1<<4)) !=
1344| (prev_UART_state_bitmap & (0x1<<4)))
1345| icount->frame++;
1346| if ((UART_state_bitmap & (0x1<<3)) &&
1347| !(prev_UART_state_bitmap & (0x1<<3)))
1348| icount->rng++;
1349| if ((UART_state_bitmap & (0x1<<2)) !=
1350| (prev_UART_state_bitmap & (0x1<<2)))
1351| icount->brk++;
1352| if ((UART_state_bitmap & (0x1<<1)) !=
1353| (prev_UART_state_bitmap & (0x1<<1)))
1354| icount->dsr++;
1355| if ((UART_state_bitmap & (0x1<<0)) !=
1356| (prev_UART_state_bitmap & (0x1<<0)))
1357| icount->dcd++;
1358| tiocmget->prev_UART_state_bitmap = UART_state_bitmap;
1359| __st_spin_unlock_st__(&serial->serial_lock);
1360| tiocmget->intr_completed = 1;
1361| __wake_up(&tiocmget->waitq, 1, 1, ((void *)0));
1362| }
1363| __st_memset_st__(serial_state_notification, 0,
1364| sizeof(struct hso_serial_state_notification));
1365| tiocmget_submit_urb(serial,
1366| tiocmget,
1367| serial->parent->usb);
1368|}
1369|static int
1370|hso_wait_modem_status(struct hso_serial *serial, unsigned long arg)
1371|{
1372| wait_queue_t wait = { .private = get_current(), .func = default_wake_function, .task_list = { ((void *)0), ((void *)0) } };
1373| struct uart_icount cprev, cnow;
1374| struct hso_tiocmget *tiocmget;
1375| int ret;
1376|
1377| tiocmget = serial->tiocmget;
1378| if (!tiocmget)
1379| return -2;
1380|
1381|
1382|
1383| __st_spin_lock_irq_st__(&serial->serial_lock);
1384| __st_memcpy_st__(&cprev, &tiocmget->icount, sizeof(struct uart_icount));
1385| __st_spin_unlock_irq_st__(&serial->serial_lock);
1386| add_wait_queue(&tiocmget->waitq, &wait);
1387| for (;;) {
1388| __st_spin_lock_irq_st__(&serial->serial_lock);
1389| __st_memcpy_st__(&cnow, &tiocmget->icount, sizeof(struct uart_icount));
1390| __st_spin_unlock_irq_st__(&serial->serial_lock);
1391| do { (void)({ __typeof(*((&get_current()->state))) __x = (((1))); switch (sizeof(*&get_current()->state)) { case 1: { volatile u8 *__ptr = (volatile u8 *)((&get_current()->state)); asm volatile("xchgb %0,%1" : "=q" (__x), "+m" (*__ptr) : "0" (__x) : "memory"); break; } case 2: { volatile u16 *__ptr = (volatile u16 *)((&get_current()->state)); asm volatile("xchgw %0,%1" : "=r" (__x), "+m" (*__ptr) : "0" (__x) : "memory"); break; } case 4: { volatile u32 *__ptr = (volatile u32 *)((&get_current()->state)); asm volatile("xchgl %0,%1" : "=r" (__x), "+m" (*__ptr) : "0" (__x) : "memory"); break; } case 8: { volatile u64 *__ptr = (volatile u64 *)((&get_current()->state)); asm volatile("xchgq %0,%1" : "=r" (__x), "+m" (*__ptr) : "0" (__x) : "memory"); break; } default: __xchg_wrong_size(); } __x; }); } while (0);
1392| if (((arg & 0x080) && (cnow.rng != cprev.rng)) ||
1393| ((arg & 0x100) && (cnow.dsr != cprev.dsr)) ||
1394| ((arg & 0x040) && (cnow.dcd != cprev.dcd))) {
1395| ret = 0;
1396| break;
1397| }
1398| schedule();
1399|
1400| if (signal_pending(get_current())) {
1401| ret = -512;
1402| break;
1403| }
1404| cprev = cnow;
1405| }
1406| get_current()->state = 0;
1407| remove_wait_queue(&tiocmget->waitq, &wait);
1408|
1409| return ret;
1410|}
1411|
1412|
1413|
1414|
1415|
1416|
1417|
1418|static int hso_get_count(struct tty_struct *tty,
1419| struct serial_icounter_struct *icount)
1420|{
1421| struct uart_icount cnow;
1422| struct hso_serial *serial = get_serial_by_tty(tty);
1423| struct hso_tiocmget *tiocmget = serial->tiocmget;
1424|
1425| __st_memset_st__(&icount, 0, sizeof(struct serial_icounter_struct));
1426|
1427| if (!tiocmget)
1428| return -2;
1429| __st_spin_lock_irq_st__(&serial->serial_lock);
1430| __st_memcpy_st__(&cnow, &tiocmget->icount, sizeof(struct uart_icount));
1431| __st_spin_unlock_irq_st__(&serial->serial_lock);
1432|
1433| icount->cts = cnow.cts;
1434| icount->dsr = cnow.dsr;
1435| icount->rng = cnow.rng;
1436| icount->dcd = cnow.dcd;
1437| icount->rx = cnow.rx;
1438| icount->tx = cnow.tx;
1439| icount->frame = cnow.frame;
1440| icount->overrun = cnow.overrun;
1441| icount->parity = cnow.parity;
1442| icount->brk = cnow.brk;
1443| icount->buf_overrun = cnow.buf_overrun;
1444|
1445| return 0;
1446|}
1447|
1448|
1449|static int hso_serial_tiocmget(struct tty_struct *tty, struct file *file)
1450|{
1451| int retval;
1452| struct hso_serial *serial = get_serial_by_tty(tty);
1453| struct hso_tiocmget *tiocmget;
1454| u16 UART_state_bitmap;
1455|
1456|
1457| if (!serial) {
1458| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "no tty structures" "\n", 1679, __func__); } while (0); } while (0);
1459| return -22;
1460| }
1461| __st_spin_lock_irq_st__(&serial->serial_lock);
1462| retval = ((serial->rts_state) ? 0x004 : 0) |
1463| ((serial->dtr_state) ? 0x002 : 0);
1464| tiocmget = serial->tiocmget;
1465| if (tiocmget) {
1466|
1467| UART_state_bitmap = (( __u16)(__le16)(tiocmget->prev_UART_state_bitmap))
1468| ;
1469| if (UART_state_bitmap & (0x1<<3))
1470| retval |= 0x080;
1471| if (UART_state_bitmap & (0x1<<0))
1472| retval |= 0x040;
1473| if (UART_state_bitmap & (0x1<<1))
1474| retval |= 0x100;
1475| }
1476| __st_spin_unlock_irq_st__(&serial->serial_lock);
1477| return retval;
1478|}
1479|
1480|static int hso_serial_tiocmset(struct tty_struct *tty, struct file *file,
1481| unsigned int set, unsigned int clear)
1482|{
1483| int val = 0;
1484| unsigned long flags;
1485| int if_num;
1486| struct hso_serial *serial = get_serial_by_tty(tty);
1487|
1488|
1489| if (!serial) {
1490| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "no tty structures" "\n", 1711, __func__); } while (0); } while (0);
1491| return -22;
1492| }
1493|
1494| if ((serial->parent->port_spec & 0xFF) != 0x11)
1495| return -22;
1496|
1497| if_num = serial->parent->interface->altsetting->desc.bInterfaceNumber;
1498|
1499| __st_spin_lock_irqsave_st__(&serial->serial_lock, flags);
1500| if (set & 0x004)
1501| serial->rts_state = 1;
1502| if (set & 0x002)
1503| serial->dtr_state = 1;
1504|
1505| if (clear & 0x004)
1506| serial->rts_state = 0;
1507| if (clear & 0x002)
1508| serial->dtr_state = 0;
1509|
1510| if (serial->dtr_state)
1511| val |= 0x01;
1512| if (serial->rts_state)
1513| val |= 0x02;
1514|
1515| __st_spin_unlock_irqrestore_st__(&serial->serial_lock, flags);
1516|
1517| return usb_control_msg(serial->parent->usb,
1518| ((2 << 30) | __create_pipe(serial->parent->usb, 0) | 0x80), 0x22,
1519| 0x21, val, if_num, ((void *)0), 0,
1520| 5000);
1521|}
1522|
1523|static int hso_serial_ioctl(struct tty_struct *tty, struct file *file,
1524| unsigned int cmd, unsigned long arg)
1525|{
1526| struct hso_serial *serial = get_serial_by_tty(tty);
1527| int ret = 0;
1528| do { if (0x08 & debug) do { printk("<6>" "[%d:%s]: " "IOCTL cmd: %d, arg: %ld" "\n", 1749, __func__, cmd, arg); } while (0); } while (0);
1529|
1530| if (!serial)
1531| return -19;
1532| switch (cmd) {
1533| case 0x545C:
1534| ret = hso_wait_modem_status(serial, arg);
1535| break;
1536| default:
1537| ret = -515;
1538| break;
1539| }
1540| return ret;
1541|}
1542|
1543|
1544|
1545|static void hso_kick_transmit(struct hso_serial *serial)
1546|{
1547| u8 *temp;
1548| unsigned long flags;
1549| int res;
1550|
1551| __st_spin_lock_irqsave_st__(&serial->serial_lock, flags);
1552| if (!serial->tx_buffer_count)
1553| goto out;
1554|
1555| if (serial->tx_urb_used)
1556| goto out;
1557|
1558|
1559| if (hso_get_activity(serial->parent) == -11)
1560| goto out;
1561|
1562|
1563| temp = serial->tx_buffer;
1564| serial->tx_buffer = serial->tx_data;
1565| serial->tx_data = temp;
1566| serial->tx_data_count = serial->tx_buffer_count;
1567| serial->tx_buffer_count = 0;
1568|
1569|
1570| if (temp && serial->write_data) {
1571| res = serial->write_data(serial);
1572| if (res >= 0)
1573| serial->tx_urb_used = 1;
1574| }
1575|out:
1576| __st_spin_unlock_irqrestore_st__(&serial->serial_lock, flags);
1577|}
1578|
1579|
1580|static int mux_device_request(struct hso_serial *serial, u8 type, u16 port,
1581| struct urb *ctrl_urb,
1582| struct usb_ctrlrequest *ctrl_req,
1583| u8 *ctrl_urb_data, u32 size)
1584|{
1585| int result;
1586| int pipe;
1587|
1588|
1589| if (!serial || !ctrl_urb || !ctrl_req) {
1590| printk("<3>" "%s: Wrong arguments\n", __func__);
1591| return -22;
1592| }
1593|
1594|
1595| ctrl_req->wValue = 0;
1596| ctrl_req->wIndex = (( __le16)(__u16)(hso_port_to_mux(port)));
1597| ctrl_req->wLength = (( __le16)(__u16)(size));
1598|
1599| if (type == 0x01) {
1600|
1601| ctrl_req->bRequestType = 0x80 |
1602| 0x20 |
1603| 0x01;
1604| ctrl_req->bRequest = 0x01;
1605| pipe = ((2 << 30) | __create_pipe(serial->parent->usb, 0) | 0x80);
1606| } else {
1607|
1608| ctrl_req->bRequestType = 0 |
1609| 0x20 |
1610| 0x01;
1611| ctrl_req->bRequest = 0x00;
1612| pipe = ((2 << 30) | __create_pipe(serial->parent->usb, 0));
1613| }
1614|
1615| do { if (0x02 & debug) do { printk("<6>" "[%d:%s]: " "%s command (%02x) len: %d, port: %d" "\n",
1616|
1617| 1838
1618| , __func__, type == 0x01 ? "Read" : "Write", ctrl_req->bRequestType, ctrl_req->wLength, port); } while (0); } while (0)
1619|
1620| ;
1621|
1622|
1623| ctrl_urb->transfer_flags = 0;
1624| usb_fill_control_urb(ctrl_urb,
1625| serial->parent->usb,
1626| pipe,
1627| (u8 *) ctrl_req,
1628| ctrl_urb_data, size, ctrl_callback, serial);
1629|
1630| result = usb_submit_urb(ctrl_urb, ((( gfp_t)0x20u)));
1631| if (result) {
1632| dev_err(&ctrl_urb->dev->dev,
1633| "%s failed submit ctrl_urb %d type %d\n", __func__,
1634| result, type);
1635| return result;
1636| }
1637|
1638|
1639| return size;
1640|}
1641|
1642|
1643|static int hso_mux_serial_read(struct hso_serial *serial)
1644|{
1645| if (!serial)
1646| return -22;
1647|
1648|
1649| __st_memset_st__(serial->rx_data[0], 0, 1024);
1650|
1651|
1652| if (serial->num_rx_urbs != 1) {
1653| dev_err(&serial->parent->interface->dev,
1654| "ERROR: mux'd reads with multiple buffers "
1655| "not possible\n");
1656| return 0;
1657| }
1658| return mux_device_request(serial,
1659| 0x01,
1660| serial->parent->port_spec & 0xFF,
1661| serial->rx_urb[0],
1662| &serial->ctrl_req_rx,
1663| serial->rx_data[0], serial->rx_data_length);
1664|}
1665|
1666|
1667|static void intr_callback(struct urb *urb)
1668|{
1669| struct hso_shared_int *shared_int = urb->context;
1670| struct hso_serial *serial;
1671| unsigned char *port_req;
1672| int status = urb->status;
1673| int i;
1674|
1675| usb_mark_last_busy(urb->dev);
1676|
1677|
1678| if (!shared_int)
1679| return;
1680|
1681|
1682| if (status) {
1683| handle_usb_error(status, __func__, ((void *)0));
1684| return;
1685| }
1686| do { if (0x08 & debug) do { printk("<6>" "[%d:%s]: " "\n--- Got intr callback 0x%02X ---" "\n", 1904, __func__, status); } while (0); } while (0);
1687|
1688|
1689| port_req = urb->transfer_buffer;
1690| do { if (0x08 & debug) do { printk("<6>" "[%d:%s]: " " port_req = 0x%.2X\n" "\n", 1908, __func__, *port_req); } while (0); } while (0);
1691|
1692| for (i = 0; i < 8; i++) {
1693|
1694| if (*port_req & (1 << i)) {
1695| serial = get_serial_by_shared_int_and_type(shared_int,
1696| (1 << i));
1697| if (serial != ((void *)0)) {
1698| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "Pending read interrupt on port %d\n" "\n", 1916, __func__, i); } while (0); } while (0);
1699| __st_spin_lock_st__(&serial->serial_lock);
1700| if (serial->rx_state == RX_IDLE &&
1701| serial->open_count > 0) {
1702|
1703|
1704| if (!serial->rx_urb_filled[0]) {
1705| serial->rx_state = RX_SENT;
1706| hso_mux_serial_read(serial);
1707| } else
1708| serial->rx_state = RX_PENDING;
1709| } else {
1710| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "Already a read pending on " "port %d or port not open\n" "\n",
1711| 1929
1712| , __func__, i); } while (0); } while (0)
1713| ;
1714| }
1715| __st_spin_unlock_st__(&serial->serial_lock);
1716| }
1717| }
1718| }
1719|
1720| hso_mux_submit_intr_urb(shared_int, urb->dev, ((( gfp_t)0x20u)));
1721|}
1722|
1723|
1724|static int hso_mux_serial_write_data(struct hso_serial *serial)
1725|{
1726| if (((void *)0) == serial)
1727| return -22;
1728|
1729| return mux_device_request(serial,
1730| 0x00,
1731| serial->parent->port_spec & 0xFF,
1732| serial->tx_urb,
1733| &serial->ctrl_req_tx,
1734| serial->tx_data, serial->tx_data_count);
1735|}
1736|
1737|
1738|static void hso_std_serial_write_bulk_callback(struct urb *urb)
1739|{
1740| struct hso_serial *serial = urb->context;
1741| int status = urb->status;
1742| struct tty_struct *tty;
1743|
1744|
1745| if (!serial) {
1746| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "serial == NULL" "\n", 1962, __func__); } while (0); } while (0);
1747| return;
1748| }
1749|
1750| __st_spin_lock_st__(&serial->serial_lock);
1751| serial->tx_urb_used = 0;
1752| tty = tty_kref_get(serial->tty);
1753| __st_spin_unlock_st__(&serial->serial_lock);
1754| if (status) {
1755| handle_usb_error(status, __func__, serial->parent);
1756| tty_kref_put(tty);
1757| return;
1758| }
1759| hso_put_activity(serial->parent);
1760| if (tty) {
1761| tty_wakeup(tty);
1762| tty_kref_put(tty);
1763| }
1764| hso_kick_transmit(serial);
1765|
1766| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " " " "\n", 1982, __func__); } while (0); } while (0);
1767|}
1768|
1769|
1770|static int hso_std_serial_write_data(struct hso_serial *serial)
1771|{
1772| int count = serial->tx_data_count;
1773| int result;
1774|
1775| usb_fill_bulk_urb(serial->tx_urb,
1776| serial->parent->usb,
1777| ((3 << 30) | __create_pipe(serial->parent->usb, serial->out_endp-> bEndpointAddress & 0x7F))
1778|
1779| ,
1780| serial->tx_data, serial->tx_data_count,
1781| hso_std_serial_write_bulk_callback, serial);
1782|
1783| result = usb_submit_urb(serial->tx_urb, ((( gfp_t)0x20u)));
1784| if (result) {
1785| dev_warn(&serial->parent->usb->dev,
1786| "Failed to submit urb - res %d\n", result);
1787| return result;
1788| }
1789|
1790| return count;
1791|}
1792|
1793|
1794|static void ctrl_callback(struct urb *urb)
1795|{
1796| struct hso_serial *serial = urb->context;
1797| struct usb_ctrlrequest *req;
1798| int status = urb->status;
1799| struct tty_struct *tty;
1800|
1801|
1802| if (!serial)
1803| return;
1804|
1805| __st_spin_lock_st__(&serial->serial_lock);
1806| serial->tx_urb_used = 0;
1807| tty = tty_kref_get(serial->tty);
1808| __st_spin_unlock_st__(&serial->serial_lock);
1809| if (status) {
1810| handle_usb_error(status, __func__, serial->parent);
1811| tty_kref_put(tty);
1812| return;
1813| }
1814|
1815|
1816| req = (struct usb_ctrlrequest *)(urb->setup_packet);
1817| do { if (0x08 & debug) do { printk("<6>" "[%d:%s]: " "\n--- Got muxed ctrl callback 0x%02X ---" "\n", 2033, __func__, status); } while (0); } while (0);
1818| do { if (0x08 & debug) do { printk("<6>" "[%d:%s]: " "Actual length of urb = %d\n" "\n", 2034, __func__, urb->actual_length); } while (0); } while (0);
1819| ;
1820|
1821| if (req->bRequestType ==
1822| (0x80 | 0x20 | 0x01)) {
1823|
1824| serial->rx_urb_filled[0] = 1;
1825| __st_spin_lock_st__(&serial->serial_lock);
1826| put_rxbuf_data_and_resubmit_ctrl_urb(serial);
1827| __st_spin_unlock_st__(&serial->serial_lock);
1828| } else {
1829| hso_put_activity(serial->parent);
1830| if (tty)
1831| tty_wakeup(tty);
1832|
1833| hso_kick_transmit(serial);
1834| }
1835| tty_kref_put(tty);
1836|}
1837|
1838|
1839|static int put_rxbuf_data(struct urb *urb, struct hso_serial *serial)
1840|{
1841| struct tty_struct *tty;
1842| int write_length_remaining = 0;
1843| int curr_write_len;
1844|
1845|
1846| if (urb == ((void *)0) || serial == ((void *)0)) {
1847| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "serial = NULL" "\n", 2063, __func__); } while (0); } while (0);
1848| return -2;
1849| }
1850|
1851|
1852| tty = tty_kref_get(serial->tty);
1853|
1854|
1855| if (tty) {
1856| write_length_remaining = urb->actual_length -
1857| serial->curr_rx_urb_offset;
1858| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "data to push to tty" "\n", 2074, __func__); } while (0); } while (0);
1859| while (write_length_remaining) {
1860| if ((__builtin_constant_p((0)) ? constant_test_bit((0), (&tty->flags)) : variable_test_bit((0), (&tty->flags)))) {
1861| tty_kref_put(tty);
1862| return -1;
1863| }
1864| curr_write_len = tty_insert_flip_string
1865| (tty, urb->transfer_buffer +
1866| serial->curr_rx_urb_offset,
1867| write_length_remaining);
1868| serial->curr_rx_urb_offset += curr_write_len;
1869| write_length_remaining -= curr_write_len;
1870| tty_flip_buffer_push(tty);
1871| }
1872| }
1873| if (write_length_remaining == 0) {
1874| serial->curr_rx_urb_offset = 0;
1875| serial->rx_urb_filled[hso_urb_to_index(serial, urb)] = 0;
1876| }
1877| tty_kref_put(tty);
1878| return write_length_remaining;
1879|}
1880|
1881|
1882|
1883|
1884|static void hso_log_port(struct hso_device *hso_dev)
1885|{
1886| char *port_type;
1887| char port_dev[20];
1888|
1889| switch (hso_dev->port_spec & 0xFF) {
1890| case 0x1:
1891| port_type = "Control";
1892| break;
1893| case 0x2:
1894| port_type = "Application";
1895| break;
1896| case 0x3:
1897| port_type = "GPS";
1898| break;
1899| case 0x6:
1900| port_type = "GPS control";
1901| break;
1902| case 0x5:
1903| port_type = "Application2";
1904| break;
1905| case 0x4:
1906| port_type = "PCSC";
1907| break;
1908| case 0x10:
1909| port_type = "Diagnostic";
1910| break;
1911| case 0x9:
1912| port_type = "Diagnostic2";
1913| break;
1914| case 0x11:
1915| port_type = "Modem";
1916| break;
1917| case 0x12:
1918| port_type = "Network";
1919| break;
1920| default:
1921| port_type = "Unknown";
1922| break;
1923| }
1924| if ((hso_dev->port_spec & 0xFF) == 0x12) {
1925| sprintf(port_dev, "%s", dev2net(hso_dev)->net->name);
1926| } else
1927| sprintf(port_dev, "/dev/%s%d", tty_filename,
1928| dev2ser(hso_dev)->minor);
1929|
1930| ({ if (0) dev_printk("<7>", &hso_dev->interface->dev, "HSO: Found %s port %s\n", port_type, port_dev); 0; })
1931| ;
1932|}
1933|
1934|static int hso_start_net_device(struct hso_device *hso_dev)
1935|{
1936| int i, result = 0;
1937| struct hso_net *hso_net = dev2net(hso_dev);
1938|
1939| if (!hso_net)
1940| return -19;
1941|
1942|
1943| for (i = 0; i < 4; i++) {
1944|
1945|
1946| usb_fill_bulk_urb(hso_net->mux_bulk_rx_urb_pool[i],
1947| hso_dev->usb,
1948| ((3 << 30) | __create_pipe(hso_dev->usb, hso_net->in_endp-> bEndpointAddress & 0x7F) | 0x80)
1949|
1950| ,
1951| hso_net->mux_bulk_rx_buf_pool[i],
1952| 2048, read_bulk_callback,
1953| hso_net);
1954|
1955|
1956| result = usb_submit_urb(hso_net->mux_bulk_rx_urb_pool[i],
1957| ((( gfp_t)0x10u)));
1958| if (result)
1959| dev_warn(&hso_dev->usb->dev,
1960| "%s failed mux_bulk_rx_urb[%d] %d\n", __func__,
1961| i, result);
1962| }
1963|
1964| return result;
1965|}
1966|
1967|static int hso_stop_net_device(struct hso_device *hso_dev)
1968|{
1969| int i;
1970| struct hso_net *hso_net = dev2net(hso_dev);
1971|
1972| if (!hso_net)
1973| return -19;
1974|
1975| for (i = 0; i < 4; i++) {
1976| if (hso_net->mux_bulk_rx_urb_pool[i])
1977| usb_kill_urb(hso_net->mux_bulk_rx_urb_pool[i]);
1978|
1979| }
1980| if (hso_net->mux_bulk_tx_urb)
1981| usb_kill_urb(hso_net->mux_bulk_tx_urb);
1982|
1983| return 0;
1984|}
1985|
1986|static int hso_start_serial_device(struct hso_device *hso_dev, gfp_t flags)
1987|{
1988| int i, result = 0;
1989| struct hso_serial *serial = dev2ser(hso_dev);
1990|
1991| if (!serial)
1992| return -19;
1993|
1994|
1995|
1996| if (!(serial->parent->port_spec & 0x0100)) {
1997| for (i = 0; i < serial->num_rx_urbs; i++) {
1998| usb_fill_bulk_urb(serial->rx_urb[i],
1999| serial->parent->usb,
2000| ((3 << 30) | __create_pipe(serial->parent->usb, serial->in_endp-> bEndpointAddress & 0x7F) | 0x80)
2001|
2002|
2003| ,
2004| serial->rx_data[i],
2005| serial->rx_data_length,
2006| hso_std_serial_read_bulk_callback,
2007| serial);
2008| result = usb_submit_urb(serial->rx_urb[i], flags);
2009| if (result) {
2010| dev_warn(&serial->parent->usb->dev,
2011| "Failed to submit urb - res %d\n",
2012| result);
2013| break;
2014| }
2015| }
2016| } else {
2017| __st_mutex_lock_st__(&serial->shared_int->shared_int_lock);
2018| if (!serial->shared_int->use_count) {
2019| result =
2020| hso_mux_submit_intr_urb(serial->shared_int,
2021| hso_dev->usb, flags);
2022| }
2023| serial->shared_int->use_count++;
2024| __st_mutex_unlock_st__(&serial->shared_int->shared_int_lock);
2025| }
2026| if (serial->tiocmget)
2027| tiocmget_submit_urb(serial,
2028| serial->tiocmget,
2029| serial->parent->usb);
2030| return result;
2031|}
2032|
2033|static int hso_stop_serial_device(struct hso_device *hso_dev)
2034|{
2035| int i;
2036| struct hso_serial *serial = dev2ser(hso_dev);
2037| struct hso_tiocmget *tiocmget;
2038|
2039| if (!serial)
2040| return -19;
2041|
2042| for (i = 0; i < serial->num_rx_urbs; i++) {
2043| if (serial->rx_urb[i]) {
2044| usb_kill_urb(serial->rx_urb[i]);
2045| serial->rx_urb_filled[i] = 0;
2046| }
2047| }
2048| serial->curr_rx_urb_idx = 0;
2049| serial->curr_rx_urb_offset = 0;
2050|
2051| if (serial->tx_urb)
2052| usb_kill_urb(serial->tx_urb);
2053|
2054| if (serial->shared_int) {
2055| __st_mutex_lock_st__(&serial->shared_int->shared_int_lock);
2056| if (serial->shared_int->use_count &&
2057| (--serial->shared_int->use_count == 0)) {
2058| struct urb *urb;
2059|
2060| urb = serial->shared_int->shared_intr_urb;
2061| if (urb)
2062| usb_kill_urb(urb);
2063| }
2064| __st_mutex_unlock_st__(&serial->shared_int->shared_int_lock);
2065| }
2066| tiocmget = serial->tiocmget;
2067| if (tiocmget) {
2068| __wake_up(&tiocmget->waitq, 1, 1, ((void *)0));
2069| usb_kill_urb(tiocmget->urb);
2070| }
2071|
2072| return 0;
2073|}
2074|
2075|static void hso_serial_common_free(struct hso_serial *serial)
2076|{
2077| int i;
2078|
2079| if (serial->parent->dev)
2080| device_remove_file(serial->parent->dev, &dev_attr_hsotype);
2081|
2082| tty_unregister_device(tty_drv, serial->minor);
2083|
2084| for (i = 0; i < serial->num_rx_urbs; i++) {
2085|
2086| usb_free_urb(serial->rx_urb[i]);
2087|
2088| kfree(serial->rx_data[i]);
2089| }
2090|
2091|
2092| usb_free_urb(serial->tx_urb);
2093| kfree(serial->tx_data);
2094|}
2095|
2096|static int hso_serial_common_create(struct hso_serial *serial, int num_urbs,
2097| int rx_size, int tx_size)
2098|{
2099| struct device *dev;
2100| int minor;
2101| int i;
2102|
2103| minor = get_free_serial_index();
2104| if (minor < 0)
2105| goto exit;
2106|
2107|
2108| serial->parent->dev = tty_register_device(tty_drv, minor,
2109| &serial->parent->interface->dev);
2110| dev = serial->parent->dev;
2111| dev_set_drvdata(dev, serial->parent);
2112| i = device_create_file(dev, &dev_attr_hsotype);
2113|
2114|
2115| serial->minor = minor;
2116| serial->magic = 0x48534f31;
2117| do { spinlock_check(&serial->serial_lock); do { static struct lock_class_key __key; __raw_spin_lock_init((&(&serial->serial_lock)->rlock), "&(&serial->serial_lock)->rlock", &__key); } while (0); } while (0);
2118| serial->num_rx_urbs = num_urbs;
2119|
2120|
2121|
2122|
2123| serial->rx_data_length = rx_size;
2124| for (i = 0; i < serial->num_rx_urbs; i++) {
2125| serial->rx_urb[i] = usb_alloc_urb(0, __st_GFP_KERNEL_st__);
2126| if (!serial->rx_urb[i]) {
2127| dev_err(dev, "Could not allocate urb?\n");
2128| goto exit;
2129| }
2130| serial->rx_urb[i]->transfer_buffer = ((void *)0);
2131| serial->rx_urb[i]->transfer_buffer_length = 0;
2132| serial->rx_data[i] = kzalloc(serial->rx_data_length,
2133| __st_GFP_KERNEL_st__);
2134| if (!serial->rx_data[i]) {
2135| dev_err(dev, "%s - Out of memory\n", __func__);
2136| goto exit;
2137| }
2138| }
2139|
2140|
2141| serial->tx_urb = usb_alloc_urb(0, __st_GFP_KERNEL_st__);
2142| if (!serial->tx_urb) {
2143| dev_err(dev, "Could not allocate urb?\n");
2144| goto exit;
2145| }
2146| serial->tx_urb->transfer_buffer = ((void *)0);
2147| serial->tx_urb->transfer_buffer_length = 0;
2148|
2149| serial->tx_data_count = 0;
2150| serial->tx_buffer_count = 0;
2151| serial->tx_data_length = tx_size;
2152| serial->tx_data = kzalloc(serial->tx_data_length, __st_GFP_KERNEL_st__);
2153| if (!serial->tx_data) {
2154| dev_err(dev, "%s - Out of memory\n", __func__);
2155| goto exit;
2156| }
2157| serial->tx_buffer = kzalloc(serial->tx_data_length, __st_GFP_KERNEL_st__);
2158| if (!serial->tx_buffer) {
2159| dev_err(dev, "%s - Out of memory\n", __func__);
2160| goto exit;
2161| }
2162|
2163| return 0;
2164|exit:
2165| hso_serial_common_free(serial);
2166| return -1;
2167|}
2168|
2169|
2170|static struct hso_device *hso_create_device(struct usb_interface *intf,
2171| int port_spec)
2172|{
2173| struct hso_device *hso_dev;
2174|
2175| hso_dev = kzalloc(sizeof(*hso_dev), ((( gfp_t)0x20u)));
2176| if (!hso_dev)
2177| return ((void *)0);
2178|
2179| hso_dev->port_spec = port_spec;
2180| hso_dev->usb = interface_to_usbdev(intf);
2181| hso_dev->interface = intf;
2182| kref_init(&hso_dev->ref);
2183| do { static struct lock_class_key __key; __mutex_init((&hso_dev->mutex), "&hso_dev->mutex", &__key); } while (0);
2184|
2185| do { do { static struct lock_class_key __key; __init_work(((&hso_dev->async_get_intf)), 0); ((&hso_dev->async_get_intf))->data = (atomic_long_t) { (WORK_STRUCT_NO_CPU) }; lockdep_init_map(&((&hso_dev->async_get_intf))->lockdep_map, "(&hso_dev->async_get_intf)", &__key, 0); INIT_LIST_HEAD(&((&hso_dev->async_get_intf))->entry); do { (((&hso_dev->async_get_intf)))->func = (((async_get_intf))); } while (0); } while (0); } while (0);
2186| do { do { static struct lock_class_key __key; __init_work(((&hso_dev->async_put_intf)), 0); ((&hso_dev->async_put_intf))->data = (atomic_long_t) { (WORK_STRUCT_NO_CPU) }; lockdep_init_map(&((&hso_dev->async_put_intf))->lockdep_map, "(&hso_dev->async_put_intf)", &__key, 0); INIT_LIST_HEAD(&((&hso_dev->async_put_intf))->entry); do { (((&hso_dev->async_put_intf)))->func = (((async_put_intf))); } while (0); } while (0); } while (0);
2187| do { do { static struct lock_class_key __key; __init_work(((&hso_dev->reset_device)), 0); ((&hso_dev->reset_device))->data = (atomic_long_t) { (WORK_STRUCT_NO_CPU) }; lockdep_init_map(&((&hso_dev->reset_device))->lockdep_map, "(&hso_dev->reset_device)", &__key, 0); INIT_LIST_HEAD(&((&hso_dev->reset_device))->entry); do { (((&hso_dev->reset_device)))->func = (((reset_device))); } while (0); } while (0); } while (0);
2188|
2189| return hso_dev;
2190|}
2191|
2192|
2193|static int remove_net_device(struct hso_device *hso_dev)
2194|{
2195| int i;
2196|
2197| for (i = 0; i < 10; i++) {
2198| if (network_table[i] == hso_dev) {
2199| network_table[i] = ((void *)0);
2200| break;
2201| }
2202| }
2203| if (i == 10)
2204| return -1;
2205| return 0;
2206|}
2207|
2208|
2209|static void hso_free_net_device(struct hso_device *hso_dev)
2210|{
2211| int i;
2212| struct hso_net *hso_net = dev2net(hso_dev);
2213|
2214| if (!hso_net)
2215| return;
2216|
2217| remove_net_device(hso_net->parent);
2218|
2219| if (hso_net->net) {
2220| unregister_netdev(hso_net->net);
2221| free_netdev(hso_net->net);
2222| }
2223|
2224|
2225| for (i = 0; i < 4; i++) {
2226| usb_free_urb(hso_net->mux_bulk_rx_urb_pool[i]);
2227| kfree(hso_net->mux_bulk_rx_buf_pool[i]);
2228| hso_net->mux_bulk_rx_buf_pool[i] = ((void *)0);
2229| }
2230| usb_free_urb(hso_net->mux_bulk_tx_urb);
2231| kfree(hso_net->mux_bulk_tx_buf);
2232| hso_net->mux_bulk_tx_buf = ((void *)0);
2233|
2234| kfree(hso_dev);
2235|}
2236|
2237|static const struct net_device_ops hso_netdev_ops = {
2238| .ndo_open = hso_net_open,
2239| .ndo_stop = hso_net_close,
2240| .ndo_start_xmit = hso_net_start_xmit,
2241| .ndo_tx_timeout = hso_net_tx_timeout,
2242|};
2243|
2244|
2245|static void hso_net_init(struct net_device *net)
2246|{
2247| struct hso_net *hso_net = netdev_priv(net);
2248|
2249| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "sizeof hso_net is %d" "\n", 2465, __func__, (int)sizeof(*hso_net)); } while (0); } while (0);
2250|
2251|
2252| net->netdev_ops = &hso_netdev_ops;
2253| net->watchdog_timeo = (250*10);
2254| net->flags = 0x10 | 0x80 | 0x1000;
2255| net->type = 0xFFFE;
2256| net->mtu = 1500 - 14;
2257| net->tx_queue_len = 10;
2258| ( (net)->ethtool_ops = (&ops) );
2259|
2260|
2261| do { spinlock_check(&hso_net->net_lock); do { static struct lock_class_key __key; __raw_spin_lock_init((&(&hso_net->net_lock)->rlock), "&(&hso_net->net_lock)->rlock", &__key); } while (0); } while (0);
2262|}
2263|
2264|
2265|static int add_net_device(struct hso_device *hso_dev)
2266|{
2267| int i;
2268|
2269| for (i = 0; i < 10; i++) {
2270| if (network_table[i] == ((void *)0)) {
2271| network_table[i] = hso_dev;
2272| break;
2273| }
2274| }
2275| if (i == 10)
2276| return -1;
2277| return 0;
2278|}
2279|
2280|static int hso_rfkill_set_block(void *data, bool blocked)
2281|{
2282| struct hso_device *hso_dev = data;
2283| int enabled = !blocked;
2284| int rv;
2285|
2286| __st_mutex_lock_st__(&hso_dev->mutex);
2287| if (hso_dev->usb_gone)
2288| rv = 0;
2289| else
2290| rv = usb_control_msg(hso_dev->usb, ((2 << 30) | __create_pipe(hso_dev->usb, 0) | 0x80),
2291| enabled ? 0x82 : 0x81, 0x40, 0, 0, ((void *)0), 0,
2292| 5000);
2293| __st_mutex_unlock_st__(&hso_dev->mutex);
2294| return rv;
2295|}
2296|
2297|static const struct rfkill_ops hso_rfkill_ops = {
2298| .set_block = hso_rfkill_set_block,
2299|};
2300|
2301|
2302|static void hso_create_rfkill(struct hso_device *hso_dev,
2303| struct usb_interface *interface)
2304|{
2305| struct hso_net *hso_net = dev2net(hso_dev);
2306| struct device *dev = &hso_net->net->dev;
2307| char *rfkn;
2308|
2309| rfkn = kzalloc(20, __st_GFP_KERNEL_st__);
2310| if (!rfkn)
2311| dev_err(dev, "%s - Out of memory\n", __func__);
2312|
2313| snprintf(rfkn, 20, "hso-%d",
2314| interface->altsetting->desc.bInterfaceNumber);
2315|
2316| hso_net->rfkill = rfkill_alloc(rfkn,
2317| &interface_to_usbdev(interface)->dev,
2318| RFKILL_TYPE_WWAN,
2319| &hso_rfkill_ops, hso_dev);
2320| if (!hso_net->rfkill) {
2321| dev_err(dev, "%s - Out of memory\n", __func__);
2322| kfree(rfkn);
2323| return;
2324| }
2325| if (rfkill_register(hso_net->rfkill) < 0) {
2326| rfkill_destroy(hso_net->rfkill);
2327| kfree(rfkn);
2328| hso_net->rfkill = ((void *)0);
2329| dev_err(dev, "%s - Failed to register rfkill\n", __func__);
2330| return;
2331| }
2332|}
2333|
2334|static struct device_type hso_type = {
2335| .name = "wwan",
2336|};
2337|
2338|
2339|static struct hso_device *hso_create_net_device(struct usb_interface *interface,
2340| int port_spec)
2341|{
2342| int result, i;
2343| struct net_device *net;
2344| struct hso_net *hso_net;
2345| struct hso_device *hso_dev;
2346|
2347| hso_dev = hso_create_device(interface, port_spec);
2348| if (!hso_dev)
2349| return ((void *)0);
2350|
2351|
2352|
2353| net = alloc_netdev_mq(sizeof(struct hso_net), "hso%d", hso_net_init, 1);
2354| if (!net) {
2355| dev_err(&interface->dev, "Unable to create ethernet device\n");
2356| goto exit;
2357| }
2358|
2359| hso_net = netdev_priv(net);
2360|
2361| hso_dev->port_data.dev_net = hso_net;
2362| hso_net->net = net;
2363| hso_net->parent = hso_dev;
2364|
2365| hso_net->in_endp = hso_get_ep(interface, 2,
2366| 0x80);
2367| if (!hso_net->in_endp) {
2368| dev_err(&interface->dev, "Can't find BULK IN endpoint\n");
2369| goto exit;
2370| }
2371| hso_net->out_endp = hso_get_ep(interface, 2,
2372| 0);
2373| if (!hso_net->out_endp) {
2374| dev_err(&interface->dev, "Can't find BULK OUT endpoint\n");
2375| goto exit;
2376| }
2377| ((net)->dev.parent = (&interface->dev));
2378| ((net)->dev.type = (&hso_type));
2379|
2380|
2381| result = register_netdev(net);
2382| if (result) {
2383| dev_err(&interface->dev, "Failed to register device\n");
2384| goto exit;
2385| }
2386|
2387|
2388| for (i = 0; i < 4; i++) {
2389| hso_net->mux_bulk_rx_urb_pool[i] = usb_alloc_urb(0, __st_GFP_KERNEL_st__);
2390| if (!hso_net->mux_bulk_rx_urb_pool[i]) {
2391| dev_err(&interface->dev, "Could not allocate rx urb\n");
2392| goto exit;
2393| }
2394| hso_net->mux_bulk_rx_buf_pool[i] = kzalloc(2048,
2395| __st_GFP_KERNEL_st__);
2396| if (!hso_net->mux_bulk_rx_buf_pool[i]) {
2397| dev_err(&interface->dev, "Could not allocate rx buf\n");
2398| goto exit;
2399| }
2400| }
2401| hso_net->mux_bulk_tx_urb = usb_alloc_urb(0, __st_GFP_KERNEL_st__);
2402| if (!hso_net->mux_bulk_tx_urb) {
2403| dev_err(&interface->dev, "Could not allocate tx urb\n");
2404| goto exit;
2405| }
2406| hso_net->mux_bulk_tx_buf = kzalloc(2048, __st_GFP_KERNEL_st__);
2407| if (!hso_net->mux_bulk_tx_buf) {
2408| dev_err(&interface->dev, "Could not allocate tx buf\n");
2409| goto exit;
2410| }
2411|
2412| add_net_device(hso_dev);
2413|
2414| hso_log_port(hso_dev);
2415|
2416| hso_create_rfkill(hso_dev, interface);
2417|
2418| return hso_dev;
2419|exit:
2420| hso_free_net_device(hso_dev);
2421| return ((void *)0);
2422|}
2423|
2424|static void hso_free_tiomget(struct hso_serial *serial)
2425|{
2426| struct hso_tiocmget *tiocmget = serial->tiocmget;
|dereferencing NULL pointer here.[serial] prev
2427| if (tiocmget) {
2428| if (tiocmget->urb) {
2429| usb_free_urb(tiocmget->urb);
2430| tiocmget->urb = ((void *)0);
2431| }
2432| serial->tiocmget = ((void *)0);
2433| kfree(tiocmget);
2434|
2435| }
2436|}
2437|
2438|
2439|static void hso_free_serial_device(struct hso_device *hso_dev)
2440|{
2441| struct hso_serial *serial = dev2ser(hso_dev);
2442|
2443| if (!serial)
2444| return;
2445| set_serial_by_index(serial->minor, ((void *)0));
2446|
2447| hso_serial_common_free(serial);
2448|
2449| if (serial->shared_int) {
2450| __st_mutex_lock_st__(&serial->shared_int->shared_int_lock);
2451| if (--serial->shared_int->ref_count == 0)
2452| hso_free_shared_int(serial->shared_int);
2453| else
2454| __st_mutex_unlock_st__(&serial->shared_int->shared_int_lock);
2455| }
2456| hso_free_tiomget(serial);
2457| kfree(serial);
2458| kfree(hso_dev);
2459|}
2460|
2461|
2462|static struct hso_device *hso_create_bulk_serial_device(
2463| struct usb_interface *interface, int port)
2464|{
2465| struct hso_device *hso_dev;
2466| struct hso_serial *serial;
2467| int num_urbs;
2468| struct hso_tiocmget *tiocmget;
2469|
2470| hso_dev = hso_create_device(interface, port);
2471| if (!hso_dev)
2472| return ((void *)0);
2473|
2474| serial = kzalloc(sizeof(*serial), __st_GFP_KERNEL_st__);
|pointer is NULL. prev next
2475| if (!serial)
|not affected ==> pointer is still NULL. prev next
2476| goto exit;
|not affected ==> pointer is still NULL. prev next
2477|
2478| serial->parent = hso_dev;
2479| hso_dev->port_data.dev_serial = serial;
2480|
2481| if ((port & 0xFF) == 0x11) {
2482| num_urbs = 2;
2483| serial->tiocmget = kzalloc(sizeof(struct hso_tiocmget),
2484| __st_GFP_KERNEL_st__);
2485|
2486|
2487|
2488| if (serial->tiocmget) {
2489| tiocmget = serial->tiocmget;
2490| tiocmget->urb = usb_alloc_urb(0, __st_GFP_KERNEL_st__);
2491| if (tiocmget->urb) {
2492| do { static struct lock_class_key __key; __mutex_init((&tiocmget->mutex), "&tiocmget->mutex", &__key); } while (0);
2493| do { static struct lock_class_key __key; __init_waitqueue_head((&tiocmget->waitq), &__key); } while (0);
2494| tiocmget->endp = hso_get_ep(
2495| interface,
2496| 3,
2497| 0x80);
2498| } else
2499| hso_free_tiomget(serial);
2500| }
2501| }
2502| else
2503| num_urbs = 1;
2504|
2505| if (hso_serial_common_create(serial, num_urbs, 4096,
2506| 8192))
2507| goto exit;
2508|
2509| serial->in_endp = hso_get_ep(interface, 2,
2510| 0x80);
2511| if (!serial->in_endp) {
2512| dev_err(&interface->dev, "Failed to find BULK IN ep\n");
2513| goto exit2;
2514| }
2515|
2516| if (!
2517| (serial->out_endp =
2518| hso_get_ep(interface, 2, 0))) {
2519| dev_err(&interface->dev, "Failed to find BULK IN ep\n");
2520| goto exit2;
2521| }
2522|
2523| serial->write_data = hso_std_serial_write_data;
2524|
2525|
2526| set_serial_by_index(serial->minor, serial);
2527|
2528|
2529| hso_log_port(hso_dev);
2530|
2531|
2532| return hso_dev;
2533|
2534|exit2:
2535| hso_serial_common_free(serial);
|<context>When called from here. next
2536|exit:
2537| hso_free_tiomget(serial);
|not affected ==> pointer is still NULL. prev next
2538| kfree(serial);
2539| kfree(hso_dev);
2540| return ((void *)0);
2541|}
2542|
2543|
2544|static
2545|struct hso_device *hso_create_mux_serial_device(struct usb_interface *interface,
2546| int port,
2547| struct hso_shared_int *mux)
2548|{
2549| struct hso_device *hso_dev;
2550| struct hso_serial *serial;
2551| int port_spec;
2552|
2553| port_spec = 0x0100;
2554| port_spec &= ~0xFF;
2555|
2556| port_spec |= hso_mux_to_port(port);
2557| if ((port_spec & 0xFF) == 0x0)
2558| return ((void *)0);
2559|
2560| hso_dev = hso_create_device(interface, port_spec);
2561| if (!hso_dev)
2562| return ((void *)0);
2563|
2564| serial = kzalloc(sizeof(*serial), __st_GFP_KERNEL_st__);
2565| if (!serial)
2566| goto exit;
2567|
2568| hso_dev->port_data.dev_serial = serial;
2569| serial->parent = hso_dev;
2570|
2571| if (hso_serial_common_create
2572| (serial, 1, 1024, 64))
2573| goto exit;
2574|
2575| serial->tx_data_length--;
2576| serial->write_data = hso_mux_serial_write_data;
2577|
2578| serial->shared_int = mux;
2579| __st_mutex_lock_st__(&serial->shared_int->shared_int_lock);
2580| serial->shared_int->ref_count++;
2581| __st_mutex_unlock_st__(&serial->shared_int->shared_int_lock);
2582|
2583|
2584| set_serial_by_index(serial->minor, serial);
2585|
2586|
2587| hso_log_port(hso_dev);
2588|
2589|
2590| return hso_dev;
2591|
2592|exit:
2593| if (serial) {
2594| tty_unregister_device(tty_drv, serial->minor);
2595| kfree(serial);
2596| }
2597| if (hso_dev)
2598| kfree(hso_dev);
2599| return ((void *)0);
2600|
2601|}
2602|
2603|static void hso_free_shared_int(struct hso_shared_int *mux)
2604|{
2605| usb_free_urb(mux->shared_intr_urb);
2606| kfree(mux->shared_intr_buf);
2607| __st_mutex_unlock_st__(&mux->shared_int_lock);
2608| kfree(mux);
2609|}
2610|
2611|static
2612|struct hso_shared_int *hso_create_shared_int(struct usb_interface *interface)
2613|{
2614| struct hso_shared_int *mux = kzalloc(sizeof(*mux), __st_GFP_KERNEL_st__);
2615|
2616| if (!mux)
2617| return ((void *)0);
2618|
2619| mux->intr_endp = hso_get_ep(interface, 3,
2620| 0x80);
2621| if (!mux->intr_endp) {
2622| dev_err(&interface->dev, "Can't find INT IN endpoint\n");
2623| goto exit;
2624| }
2625|
2626| mux->shared_intr_urb = usb_alloc_urb(0, __st_GFP_KERNEL_st__);
2627| if (!mux->shared_intr_urb) {
2628| dev_err(&interface->dev, "Could not allocate intr urb?\n");
2629| goto exit;
2630| }
2631| mux->shared_intr_buf =
2632| kzalloc((( __u16)(__le16)(mux->intr_endp->wMaxPacketSize)),
2633| __st_GFP_KERNEL_st__);
2634| if (!mux->shared_intr_buf) {
2635| dev_err(&interface->dev, "Could not allocate intr buf?\n");
2636| goto exit;
2637| }
2638|
2639| do { static struct lock_class_key __key; __mutex_init((&mux->shared_int_lock), "&mux->shared_int_lock", &__key); } while (0);
2640|
2641| return mux;
2642|
2643|exit:
2644| kfree(mux->shared_intr_buf);
2645| usb_free_urb(mux->shared_intr_urb);
2646| kfree(mux);
2647| return ((void *)0);
2648|}
2649|
2650|
2651|static int hso_get_config_data(struct usb_interface *interface)
2652|{
2653| struct usb_device *usbdev = interface_to_usbdev(interface);
2654| u8 config_data[17];
2655| u32 if_num = interface->altsetting->desc.bInterfaceNumber;
2656| s32 result;
2657|
2658| if (usb_control_msg(usbdev, ((2 << 30) | __create_pipe(usbdev, 0) | 0x80),
2659| 0x86, 0xC0, 0, 0, config_data, 17,
2660| 5000) != 0x11) {
2661| return -5;
2662| }
2663|
2664| switch (config_data[if_num]) {
2665| case 0x0:
2666| result = 0;
2667| break;
2668| case 0x1:
2669| result = 0x10;
2670| break;
2671| case 0x2:
2672| result = 0x3;
2673| break;
2674| case 0x3:
2675| result = 0x6;
2676| break;
2677| case 0x4:
2678| result = 0x2;
2679| break;
2680| case 0x5:
2681| result = 0x5;
2682| break;
2683| case 0x6:
2684| result = 0x1;
2685| break;
2686| case 0x7:
2687| result = 0x12;
2688| break;
2689| case 0x8:
2690| result = 0x11;
2691| break;
2692| case 0x9:
2693| result = 0x7;
2694| break;
2695| case 0xa:
2696| result = 0x4;
2697| break;
2698| case 0xb:
2699| result = 0x8;
2700| break;
2701| default:
2702| result = 0;
2703| }
2704|
2705| if (result)
2706| result |= 0x0200;
2707|
2708| if (config_data[16] & 0x1)
2709| result |= 0x01000000;
2710|
2711| return result;
2712|}
2713|
2714|
2715|static int hso_probe(struct usb_interface *interface,
2716| const struct usb_device_id *id)
2717|{
2718| int mux, i, if_num, port_spec;
2719| unsigned char port_mask;
2720| struct hso_device *hso_dev = ((void *)0);
2721| struct hso_shared_int *shared_int;
2722| struct hso_device *tmp_dev = ((void *)0);
2723|
2724| if_num = interface->altsetting->desc.bInterfaceNumber;
2725|
2726|
2727|
2728| if (id->driver_info)
2729| port_spec = ((u32 *)(id->driver_info))[if_num];
2730| else
2731| port_spec = hso_get_config_data(interface);
2732|
2733| if (interface->cur_altsetting->desc.bInterfaceClass != 0xFF) {
2734| dev_err(&interface->dev, "Not our interface\n");
2735| return -19;
2736| }
2737|
2738|
2739| if (interface->num_altsetting > 1)
2740| usb_set_interface(interface_to_usbdev(interface), if_num, 1);
2741| interface->needs_remote_wakeup = 1;
2742|
2743|
2744| switch (port_spec & 0xFF00) {
2745| case 0x0100:
2746| if ((port_spec & 0xFF) == 0x12) {
2747|
2748| if (!disable_net) {
2749| hso_dev = hso_create_net_device(interface,
2750| port_spec);
2751| if (!hso_dev)
2752| goto exit;
2753| tmp_dev = hso_dev;
2754| }
2755| }
2756|
2757| if (hso_get_mux_ports(interface, &port_mask))
2758|
2759| goto exit;
2760|
2761| shared_int = hso_create_shared_int(interface);
2762| if (!shared_int)
2763| goto exit;
2764|
2765| for (i = 1, mux = 0; i < 0x100; i = i << 1, mux++) {
2766| if (port_mask & i) {
2767| hso_dev = hso_create_mux_serial_device(
2768| interface, i, shared_int);
2769| if (!hso_dev)
2770| goto exit;
2771| }
2772| }
2773|
2774| if (tmp_dev)
2775| hso_dev = tmp_dev;
2776| break;
2777|
2778| case 0x0200:
2779|
2780| if (((port_spec & 0xFF) == 0x12) &&
2781| !disable_net)
2782| hso_dev = hso_create_net_device(interface, port_spec);
2783| else
2784| hso_dev =
2785| hso_create_bulk_serial_device(interface, port_spec);
2786| if (!hso_dev)
2787| goto exit;
2788| break;
2789| default:
2790| goto exit;
2791| }
2792|
2793|
2794| usb_set_intfdata(interface, hso_dev);
2795|
2796|
2797| return 0;
2798|exit:
2799| hso_free_interface(interface);
2800| return -19;
2801|}
2802|
2803|
2804|static void hso_disconnect(struct usb_interface *interface)
2805|{
2806| hso_free_interface(interface);
2807|
2808|
2809| usb_set_intfdata(interface, ((void *)0));
2810|}
2811|
2812|static void async_get_intf(struct work_struct *data)
2813|{
2814| struct hso_device *hso_dev =
2815| ({ const typeof( ((struct hso_device *)0)->async_get_intf ) *__mptr = (data); (struct hso_device *)( (char *)__mptr - 1 );});
2816| usb_autopm_get_interface(hso_dev->interface);
2817|}
2818|
2819|static void async_put_intf(struct work_struct *data)
2820|{
2821| struct hso_device *hso_dev =
2822| ({ const typeof( ((struct hso_device *)0)->async_put_intf ) *__mptr = (data); (struct hso_device *)( (char *)__mptr - 1 );});
2823| usb_autopm_put_interface(hso_dev->interface);
2824|}
2825|
2826|static int hso_get_activity(struct hso_device *hso_dev)
2827|{
2828| if (hso_dev->usb->state == USB_STATE_SUSPENDED) {
2829| if (!hso_dev->is_active) {
2830| hso_dev->is_active = 1;
2831| schedule_work(&hso_dev->async_get_intf);
2832| }
2833| }
2834|
2835| if (hso_dev->usb->state != USB_STATE_CONFIGURED)
2836| return -11;
2837|
2838| usb_mark_last_busy(hso_dev->usb);
2839|
2840| return 0;
2841|}
2842|
2843|static int hso_put_activity(struct hso_device *hso_dev)
2844|{
2845| if (hso_dev->usb->state != USB_STATE_SUSPENDED) {
2846| if (hso_dev->is_active) {
2847| hso_dev->is_active = 0;
2848| schedule_work(&hso_dev->async_put_intf);
2849| return -11;
2850| }
2851| }
2852| hso_dev->is_active = 0;
2853| return 0;
2854|}
2855|
2856|
2857|static int hso_suspend(struct usb_interface *iface, pm_message_t message)
2858|{
2859| int i, result;
2860|
2861|
2862| for (i = 0; i < 256; i++) {
2863| if (serial_table[i] && (serial_table[i]->interface == iface)) {
2864| result = hso_stop_serial_device(serial_table[i]);
2865| if (result)
2866| goto out;
2867| }
2868| }
2869|
2870|
2871| for (i = 0; i < 10; i++) {
2872| if (network_table[i] &&
2873| (network_table[i]->interface == iface)) {
2874| result = hso_stop_net_device(network_table[i]);
2875| if (result)
2876| goto out;
2877| }
2878| }
2879|
2880|out:
2881| return 0;
2882|}
2883|
2884|
2885|static int hso_resume(struct usb_interface *iface)
2886|{
2887| int i, result = 0;
2888| struct hso_net *hso_net;
2889|
2890|
2891| for (i = 0; i < 256; i++) {
2892| if (serial_table[i] && (serial_table[i]->interface == iface)) {
2893| if (dev2ser(serial_table[i])->open_count) {
2894| result =
2895| hso_start_serial_device(serial_table[i], ((( gfp_t)0x10u)));
2896| hso_kick_transmit(dev2ser(serial_table[i]));
2897| if (result)
2898| goto out;
2899| }
2900| }
2901| }
2902|
2903|
2904| for (i = 0; i < 10; i++) {
2905| if (network_table[i] &&
2906| (network_table[i]->interface == iface)) {
2907| hso_net = dev2net(network_table[i]);
2908| if (hso_net->flags & 0x1) {
2909|
2910|
2911| if (hso_net->skb_tx_buf) {
2912| ({ if (0) dev_printk("<7>", &iface->dev, "Transmitting" " lingering data\n"); 0; })
2913|
2914| ;
2915| hso_net_start_xmit(hso_net->skb_tx_buf,
2916| hso_net->net);
2917| hso_net->skb_tx_buf = ((void *)0);
2918| }
2919| result = hso_start_net_device(network_table[i]);
2920| if (result)
2921| goto out;
2922| }
2923| }
2924| }
2925|
2926|out:
2927| return result;
2928|}
2929|
2930|static void reset_device(struct work_struct *data)
2931|{
2932| struct hso_device *hso_dev =
2933| ({ const typeof( ((struct hso_device *)0)->reset_device ) *__mptr = (data); (struct hso_device *)( (char *)__mptr - 1 );});
2934| struct usb_device *usb = hso_dev->usb;
2935| int result;
2936|
2937| if (hso_dev->usb_gone) {
2938| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "No reset during disconnect\n" "\n", 3154, __func__); } while (0); } while (0);
2939| } else {
2940| result = usb_lock_device_for_reset(usb, hso_dev->interface);
2941| if (result < 0)
2942| do { if (0x01 & debug) do { printk("<6>" "[%d:%s]: " "unable to lock device for reset: %d\n" "\n", 3158, __func__, result); } while (0); } while (0);
2943| else {
2944| usb_reset_device(usb);
2945| device_unlock(&(usb)->dev);
2946| }
2947| }
2948|}
2949|
2950|static void hso_serial_ref_free(struct kref *ref)
2951|{
2952| struct hso_device *hso_dev = ({ const typeof( ((struct hso_device *)0)->ref ) *__mptr = (ref); (struct hso_device *)( (char *)__mptr - 1 );});
2953|
2954| hso_free_serial_device(hso_dev);
2955|}
2956|
2957|static void hso_free_interface(struct usb_interface *interface)
2958|{
2959| struct hso_serial *hso_dev;
2960| struct tty_struct *tty;
2961| int i;
2962|
2963| for (i = 0; i < 256; i++) {
2964| if (serial_table[i] &&
2965| (serial_table[i]->interface == interface)) {
2966| hso_dev = dev2ser(serial_table[i]);
2967| __st_spin_lock_irq_st__(&hso_dev->serial_lock);
2968| tty = tty_kref_get(hso_dev->tty);
2969| __st_spin_unlock_irq_st__(&hso_dev->serial_lock);
2970| if (tty)
2971| tty_hangup(tty);
2972| __st_mutex_lock_st__(&hso_dev->parent->mutex);
2973| tty_kref_put(tty);
2974| hso_dev->parent->usb_gone = 1;
2975| __st_mutex_unlock_st__(&hso_dev->parent->mutex);
2976| kref_put(&serial_table[i]->ref, hso_serial_ref_free);
2977| }
2978| }
2979|
2980| for (i = 0; i < 10; i++) {
2981| if (network_table[i] &&
2982| (network_table[i]->interface == interface)) {
2983| struct rfkill *rfk = dev2net(network_table[i])->rfkill;
2984|
2985|
2986| netif_stop_queue(dev2net(network_table[i])->net);
2987| hso_stop_net_device(network_table[i]);
2988| cancel_work_sync(&network_table[i]->async_put_intf);
2989| cancel_work_sync(&network_table[i]->async_get_intf);
2990| if (rfk) {
2991| rfkill_unregister(rfk);
2992| rfkill_destroy(rfk);
2993| }
2994| hso_free_net_device(network_table[i]);
2995| }
2996| }
2997|}
2998|
2999|
3000|
3001|
3002|static struct usb_endpoint_descriptor *hso_get_ep(struct usb_interface *intf,
3003| int type, int dir)
3004|{
3005| int i;
3006| struct usb_host_interface *iface = intf->cur_altsetting;
3007| struct usb_endpoint_descriptor *endp;
3008|
3009| for (i = 0; i < iface->desc.bNumEndpoints; i++) {
3010| endp = &iface->endpoint[i].desc;
3011| if (((endp->bEndpointAddress & 0x80) == dir) &&
3012| (usb_endpoint_type(endp) == type))
3013| return endp;
3014| }
3015|
3016| return ((void *)0);
3017|}
3018|
3019|
3020|static int hso_get_mux_ports(struct usb_interface *intf, unsigned char *ports)
3021|{
3022| int i;
3023| struct usb_host_interface *iface = intf->cur_altsetting;
3024|
3025| if (iface->extralen == 3) {
3026| *ports = iface->extra[2];
3027| return 0;
3028| }
3029|
3030| for (i = 0; i < iface->desc.bNumEndpoints; i++) {
3031| if (iface->endpoint[i].extralen == 3) {
3032| *ports = iface->endpoint[i].extra[2];
3033| return 0;
3034| }
3035| }
3036|
3037| return -1;
3038|}
3039|
3040|
3041|static int hso_mux_submit_intr_urb(struct hso_shared_int *shared_int,
3042| struct usb_device *usb, gfp_t gfp)
3043|{
3044| int result;
3045|
3046| usb_fill_int_urb(shared_int->shared_intr_urb, usb,
3047| ((1 << 30) | __create_pipe(usb, shared_int->intr_endp->bEndpointAddress & 0x7F) | 0x80)
3048| ,
3049| shared_int->shared_intr_buf,
3050| 1,
3051| intr_callback, shared_int,
3052| shared_int->intr_endp->bInterval);
3053|
3054| result = usb_submit_urb(shared_int->shared_intr_urb, gfp);
3055| if (result)
3056| dev_warn(&usb->dev, "%s failed mux_intr_urb %d\n", __func__,
3057| result);
3058|
3059| return result;
3060|}
3061|
3062|
3063|static const struct tty_operations hso_serial_ops = {
3064| .open = hso_serial_open,
3065| .close = hso_serial_close,
3066| .write = hso_serial_write,
3067| .write_room = hso_serial_write_room,
3068| .ioctl = hso_serial_ioctl,
3069| .set_termios = hso_serial_set_termios,
3070| .chars_in_buffer = hso_serial_chars_in_buffer,
3071| .tiocmget = hso_serial_tiocmget,
3072| .tiocmset = hso_serial_tiocmset,
3073| .get_icount = hso_get_count,
3074| .unthrottle = hso_unthrottle
3075|};
3076|
3077|static struct usb_driver hso_driver = {
3078| .name = driver_name,
3079| .probe = hso_probe,
3080| .disconnect = hso_disconnect,
3081| .id_table = hso_ids,
3082| .suspend = hso_suspend,
3083| .resume = hso_resume,
3084| .reset_resume = hso_resume,
3085| .supports_autosuspend = 1,
3086|};
3087|
3088|static int hso_init(void)
3089|{
3090| int i;
3091| int result;
3092|
3093|
3094| printk("<6>" "hso: %s\n", version);
3095|
3096|
3097| do { spinlock_check(&serial_table_lock); do { static struct lock_class_key __key; __raw_spin_lock_init((&(&serial_table_lock)->rlock), "&(&serial_table_lock)->rlock", &__key); } while (0); } while (0);
3098| for (i = 0; i < 256; i++)
3099| serial_table[i] = ((void *)0);
3100|
3101|
3102| tty_drv = alloc_tty_driver(256);
3103| if (!tty_drv)
3104| return -12;
3105|
3106|
3107| tty_drv->magic = 0x5402;
3108| tty_drv->owner = (&__this_module);
3109| tty_drv->driver_name = driver_name;
3110| tty_drv->name = tty_filename;
3111|
3112|
3113| if (tty_major)
3114| tty_drv->major = tty_major;
3115|
3116| tty_drv->minor_start = 0;
3117| tty_drv->num = 256;
3118| tty_drv->type = 0x0003;
3119| tty_drv->subtype = 1;
3120| tty_drv->flags = 0x0004 | 0x0008;
3121| tty_drv->init_termios = tty_std_termios;
3122| hso_init_termios(&tty_drv->init_termios);
3123| tty_set_operations(tty_drv, &hso_serial_ops);
3124|
3125|
3126| result = tty_register_driver(tty_drv);
3127| if (result) {
3128| printk("<3>" "%s - tty_register_driver failed(%d)\n",
3129| __func__, result);
3130| return result;
3131| }
3132|
3133|
3134| result = usb_register(&hso_driver);
3135| if (result) {
3136| printk("<3>" "Could not register hso driver? error: %d\n",
3137| result);
3138|
3139| tty_unregister_driver(tty_drv);
3140| return result;
3141| }
3142|
3143|
3144| return 0;
3145|}
3146|
3147|static void hso_exit(void)
3148|{
3149| printk("<6>" "hso: unloaded\n");
3150|
3151| tty_unregister_driver(tty_drv);
3152|
3153| usb_deregister(&hso_driver);
3154|}
3155|
3156|
3157|static inline initcall_t __inittest(void) { return hso_init; } int init_module(void) ;;
3158|static inline exitcall_t __exittest(void) { return hso_exit; } void cleanup_module(void) ;;
3159|
3160|static const char __mod_author3376[] = "author" "=" "Option Wireless";
3161|static const char __mod_description3377[] = "description" "=" "USB High Speed Option driver";
3162|static const char __mod_license3378[] = "license" "=" "GPL";
3163|
3164|
3165|static const char __mod_debug3381[] = "parm" "=" "debug" ":" "Level of debug [0x01 | 0x02 | 0x04 | 0x08 | 0x10]";
3166|static inline int *__check_debug(void) { return(&(debug)); }; static int __param_perm_check_debug = (sizeof(struct { int:-!!(((00400|00040|00004) | 00200) < 0 || ((00400|00040|00004) | 00200) > 0777 || (((00400|00040|00004) | 00200) & 2)); })) + (sizeof(struct { int:-!!(sizeof("") > (64 - sizeof(unsigned long))); })); static const char __param_str_debug[] = "debug"; static struct kernel_param const __param_debug = { __param_str_debug, ¶m_ops_int, (00400|00040|00004) | 00200, 0 ? 2 : 0, { &debug } }; static const char __mod_debugtype3382[] = "parmtype" "=" "debug" ":" "int";
3167|
3168|
3169|static const char __mod_tty_major3385[] = "parm" "=" "tty_major" ":" "Set the major tty number";
3170|static inline int *__check_tty_major(void) { return(&(tty_major)); }; static int __param_perm_check_tty_major = (sizeof(struct { int:-!!(((00400|00040|00004) | 00200) < 0 || ((00400|00040|00004) | 00200) > 0777 || (((00400|00040|00004) | 00200) & 2)); })) + (sizeof(struct { int:-!!(sizeof("") > (64 - sizeof(unsigned long))); })); static const char __param_str_tty_major[] = "tty_major"; static struct kernel_param const __param_tty_major = { __param_str_tty_major, ¶m_ops_int, (00400|00040|00004) | 00200, 0 ? 2 : 0, { &tty_major } }; static const char __mod_tty_majortype3386[] = "parmtype" "=" "tty_major" ":" "int";
3171|
3172|
3173|static const char __mod_disable_net3389[] = "parm" "=" "disable_net" ":" "Disable the network interface";
3174|static inline int *__check_disable_net(void) { return(&(disable_net)); }; static int __param_perm_check_disable_net = (sizeof(struct { int:-!!(((00400|00040|00004) | 00200) < 0 || ((00400|00040|00004) | 00200) > 0777 || (((00400|00040|00004) | 00200) & 2)); })) + (sizeof(struct { int:-!!(sizeof("") > (64 - sizeof(unsigned long))); })); static const char __param_str_disable_net[] = "disable_net"; static struct kernel_param const __param_disable_net = { __param_str_disable_net, ¶m_ops_int, (00400|00040|00004) | 00200, 0 ? 2 : 0, { &disable_net } }; static const char __mod_disable_nettype3390[] = "parmtype" "=" "disable_net" ":" "int";