]> rtime.felk.cvut.cz Git - lincan.git/blob - embedded/app/usbcan/finish.c
USBCAN converter code updated to match full version of LinCAN sources.
[lincan.git] / embedded / app / usbcan / finish.c
1 /**************************************************************************/
2 /* File: finish.c - finalization of the driver operations                 */
3 /*                                                                        */
4 /* LinCAN - (Not only) Linux CAN bus driver                               */
5 /* Copyright (C) 2002-2009 DCE FEE CTU Prague <http://dce.felk.cvut.cz>   */
6 /* Copyright (C) 2002-2009 Pavel Pisa <pisa@cmp.felk.cvut.cz>             */
7 /* Funded by OCERA and FRESCOR IST projects                               */
8 /* Based on CAN driver code by Arnaud Westenberg <arnaud@wanadoo.nl>      */
9 /*                                                                        */
10 /* LinCAN is free software; you can redistribute it and/or modify it      */
11 /* under terms of the GNU General Public License as published by the      */
12 /* Free Software Foundation; either version 2, or (at your option) any    */
13 /* later version.  LinCAN is distributed in the hope that it will be      */
14 /* useful, but WITHOUT ANY WARRANTY; without even the implied warranty    */
15 /* of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU    */
16 /* General Public License for more details. You should have received a    */
17 /* copy of the GNU General Public License along with LinCAN; see file     */
18 /* COPYING. If not, write to the Free Software Foundation, 675 Mass Ave,  */
19 /* Cambridge, MA 02139, USA.                                              */
20 /*                                                                        */
21 /* To allow use of LinCAN in the compact embedded systems firmware        */
22 /* and RT-executives (RTEMS for example), main authors agree with next    */
23 /* special exception:                                                     */
24 /*                                                                        */
25 /* Including LinCAN header files in a file, instantiating LinCAN generics */
26 /* or templates, or linking other files with LinCAN objects to produce    */
27 /* an application image/executable, does not by itself cause the          */
28 /* resulting application image/executable to be covered by                */
29 /* the GNU General Public License.                                        */
30 /* This exception does not however invalidate any other reasons           */
31 /* why the executable file might be covered by the GNU Public License.    */
32 /* Publication of enhanced or derived LinCAN files is required although.  */
33 /**************************************************************************/
34
35 #include "./can/can.h"
36 #include "./can/can_sysdep.h"
37 #include "./can/main.h"
38 #include "./can/devcommon.h"
39 #include "./can/finish.h"
40 #include "./can/setup.h"
41
42
43 /**
44  * msgobj_done - destroys one CAN message object
45  * @obj: pointer to CAN message object structure
46  */
47 void msgobj_done(struct msgobj_t *obj)
48 {
49         int delayed=0;
50         if(obj->qends) {
51                 delayed=canqueue_ends_done_chip(obj->qends);
52                 if(delayed < 0)
53                         CANMSG("msgobj_done: problem with chip queue ends\n");
54         }
55
56         if((obj->hostchip) && (obj->object>0)) {
57                 if(obj->hostchip->msgobj[obj->object-1] == obj)
58                         obj->hostchip->msgobj[obj->object-1]=NULL;
59                 else
60                         CANMSG("msgobj_done: not registered in the canchip_t\n");
61                 obj->hostchip=NULL;
62         }
63
64         if((obj->minor>=0)) {
65                 if(objects_p[obj->minor] == obj)
66                         objects_p[obj->minor] = NULL;
67                 else
68                         CANMSG("msgobj_done: not registered as minor\n");
69         }
70
71 //      del_timer_sync(&obj->tx_timeout);
72
73         if(obj->qends) {
74                 /*delayed free could be required there in the future,
75                   actual use patter cannot generate such situation*/
76                 if(!delayed) {
77                         free(obj->qends);
78                 }
79         }
80         obj->qends=NULL;
81 }
82
83
84 /**
85  * canchip_done - destroys one CAN chip representation
86  * @chip: pointer to CAN chip structure
87  */
88 void canchip_done(struct canchip_t *chip)
89 {
90
91         int i;
92         struct msgobj_t *obj;
93
94         if(chip->flags & CHIP_ATTACHED)
95                 chip->chipspecops->release_chip(chip);
96
97         if((chip->hostdevice) && (chip->chip_idx>=0)) {
98                 if(chip->hostdevice->chip[chip->chip_idx] == chip)
99                         chip->hostdevice->chip[chip->chip_idx] = NULL;
100                 else
101                         CANMSG("canchip_done: not registered in hostdevice\n");
102         }
103
104 // Not using interrupts
105 //      can_chip_free_irq(chip);
106
107 //      can_synchronize_irq(chip->chip_irq);
108
109         for(i=0; i<chip->max_objects; i++){
110                 if((obj=chip->msgobj[i])==NULL)
111                         continue;
112                 msgobj_done(obj);
113                 free(obj);
114         }
115
116         free(chip->chipspecops);
117         chip->chipspecops=NULL;
118
119 }
120
121 /**
122  * candevice_done - destroys representation of one CAN device/board
123  * @candev: pointer to CAN device/board structure
124  */
125 void candevice_done(struct candevice_t *candev)
126 {
127         int i;
128         struct canchip_t *chip;
129
130         for(i=0; i<candev->nr_all_chips; i++){
131                 if((chip=candev->chip[i])==NULL)
132                         continue;
133                 canchip_done(chip);
134                 free(chip);
135
136         }
137         if(candev->flags & CANDEV_IO_RESERVED) {
138                 candev->hwspecops->release_io(candev);
139                 candev->flags &= ~CANDEV_IO_RESERVED;
140         }
141         free(candev->hwspecops);
142         candev->hwspecops=NULL;
143 }
144
145 /**
146  * candevice_done - destroys representation of all CAN devices/boards
147  * @canhw: pointer to the root of all CAN hardware representation
148  */
149 void canhardware_done(struct canhardware_t *canhw)
150 {
151         int i;
152         struct candevice_t *candev;
153
154         for(i=0; i<canhw->nr_boards; i++){
155                 if((candev=canhw->candevice[i])==NULL)
156                         continue;
157                 candevice_done(candev);
158                 free(candev);
159         }
160
161 }