Revert DPRINT1.
[reactos.git] / reactos / drivers / usb / cromwell / sys / linuxwrapper.c
1 /*
2 * USB support based on Linux kernel source
3 *
4 * 2003-06-21 Georg Acher (georg@acher.org)
5 *
6 * Concept:
7 *
8 * 1) Forget all device interrupts, scheduling, semaphores, threads etc.
9 * 1a) Forget all DMA and PCI helper functions
10 * 2) Forget usbdevfs, procfs and ioctls
11 * 3) Emulate OHCI interrupts and root hub timer by polling
12 * 4) Emulate hub kernel thread by polling
13 * 5) Emulate synchronous USB-messages (usb_*_msg) with busy waiting
14 *
15 * To be done:
16 * 6) Remove code bloat
17 *
18 */
19
20 #include "../usb_wrapper.h"
21
22 /* internal state */
23
24 static struct pci_dev *pci_probe_dev;
25 extern int (*thread_handler)(void*);
26 extern void* thread_parm;
27
28 struct my_irqs reg_irqs[MAX_IRQS];
29 int num_irqs;
30 int need_wakeup;
31
32 int my_jiffies;
33
34 struct timer_list *main_timer_list[MAX_TIMERS];
35 struct dummy_process act_cur={0};
36 struct dummy_process *my_current;
37
38 int (*thread_handler)(void*);
39 void* thread_parm;
40
41 #define MAX_DRVS 8
42 static struct device_driver *m_drivers[MAX_DRVS];
43 static int drvs_num;
44
45 /*------------------------------------------------------------------------*/
46 /*
47 * Helper functions for top-level system
48 */
49 /*------------------------------------------------------------------------*/
50 void init_wrapper(struct pci_dev *probe_dev)
51 {
52 int n;
53 for(n=0;n<MAX_TIMERS;n++)
54 {
55 main_timer_list[n]=NULL;
56 }
57
58 my_jiffies=0;
59 num_irqs=0;
60 my_current=&act_cur;
61 pci_probe_dev=probe_dev;
62
63 for(n=0;n<MAX_IRQS;n++)
64 {
65 reg_irqs[n].handler=NULL;
66 reg_irqs[n].irq=-1;
67 }
68 drvs_num=0;
69 need_wakeup=0;
70 for(n=0;n<MAX_DRVS;n++)
71 m_drivers[n]=NULL;
72 }
73 /*------------------------------------------------------------------------*/
74 void handle_irqs(int irq)
75 {
76 int n;
77 printk("handle irqs\n");
78 for(n=0;n<MAX_IRQS;n++)
79 {
80 if (reg_irqs[n].handler && (irq==reg_irqs[n].irq || irq==-1))
81 reg_irqs[n].handler(reg_irqs[n].irq,reg_irqs[n].data,NULL);
82 }
83 }
84 /*------------------------------------------------------------------------*/
85 void inc_jiffies(int n)
86 {
87 my_jiffies+=n;
88 }
89 /*------------------------------------------------------------------------*/
90 void do_all_timers(void)
91 {
92 int n;
93 for(n=0;n<MAX_TIMERS;n++)
94 {
95 if (main_timer_list[n] &&
96 main_timer_list[n]->function && main_timer_list[n]->expires)
97 {
98 void (*function)(unsigned long)=main_timer_list[n]->function;
99 unsigned long data=main_timer_list[n]->data;
100 main_timer_list[n]->expires=0;
101
102 main_timer_list[n]=NULL; // remove timer
103 printk("do timer %i fn %p\n",n,function);
104
105 function(data);
106 }
107 }
108 }
109 /*------------------------------------------------------------------------*/
110 // Purpose: Remember thread procedure and data in global var
111 // ReactOS Purpose: Create real kernel thread
112 int my_kernel_thread(int STDCALL (*handler)(void*), void* parm, int flags)
113 {
114 HANDLE hThread;
115 //thread_handler=handler;
116 //thread_parm=parm;
117 //return 42; // PID :-)
118
119 ASSERT(KeGetCurrentIrql() == PASSIVE_LEVEL);
120
121 PsCreateSystemThread(&hThread,
122 THREAD_ALL_ACCESS,
123 NULL,
124 NULL,
125 NULL,
126 (PKSTART_ROUTINE)handler,
127 parm);
128
129 return (int)hThread; // FIXME: Correct?
130 }
131
132 // Kill the process
133 int my_kill_proc(int pid, int signal, int unk)
134 {
135 HANDLE hThread;
136
137 // TODO: Implement actual process killing
138
139 hThread = (HANDLE)pid;
140 ZwClose(hThread);
141
142 return 0;
143 }
144
145 /*------------------------------------------------------------------------*/
146 /* Device management
147 * As simple as possible, but as complete as necessary ...
148 */
149 /*------------------------------------------------------------------------*/
150
151
152 /* calls probe function for hotplug (which does device matching), this is the
153 only link between usbcore and the registered device drivers! */
154 int my_device_add(struct device *dev)
155 {
156 int n,found=0;
157 printk("drv_num %i %p %p\n",drvs_num,m_drivers[0]->probe,m_drivers[1]->probe);
158
159 if (dev->driver)
160 {
161 if (dev->driver->probe)
162 return dev->driver->probe(dev);
163 }
164 else
165 {
166 for(n=0;n<drvs_num;n++)
167 {
168 if (m_drivers[n]->probe)
169 {
170 dev->driver=m_drivers[n];
171 printk("probe%i %p ",n,m_drivers[n]->probe);
172
173 if (m_drivers[n]->probe(dev) == 0)
174 {
175 // return 0;
176 found=1;
177 }
178 }
179 }
180 if (found) return 0;
181 }
182 dev->driver=NULL;
183 return -ENODEV;
184 }
185 /*------------------------------------------------------------------------*/
186 int my_driver_register(struct device_driver *driver)
187 {
188
189 if (drvs_num<MAX_DRVS)
190 {
191 printk("driver_register %i: %p %p",drvs_num,driver,driver->probe);
192
193 m_drivers[drvs_num++]=driver;
194 return 0;
195 }
196 return -1;
197 }
198 /*------------------------------------------------------------------------*/
199 int my_device_unregister(struct device *dev)
200 {
201 if (dev->driver && dev->driver->remove)
202 dev->driver->remove(dev);
203 return 0;
204
205 }
206 /*------------------------------------------------------------------------*/
207 struct device *my_get_device(struct device *dev)
208 {
209 return NULL;
210 }
211 /*------------------------------------------------------------------------*/
212 void my_device_initialize(struct device *dev)
213 {
214 }
215 /*------------------------------------------------------------------------*/
216 void my_wake_up(PKEVENT evnt)
217 {
218 need_wakeup=1;
219
220 KeSetEvent(evnt, 0, FALSE); // Signal event
221 }
222 /*------------------------------------------------------------------------*/
223 void my_init_waitqueue_head(PKEVENT evnt)
224 {
225 // this is used only in core/message.c, and it isn't needed there
226 //KeInitializeEvent(evnt, NotificationEvent, TRUE); // signalled state
227 }
228 /*------------------------------------------------------------------------*/
229 /* wait until woken up (only one wait allowed!) */
230 int my_schedule_timeout(int x)
231 {
232 int wait=1;
233 x+=10; // safety
234 printk("schedule_timeout %i\n",x);
235
236 while(x>0)
237 {
238 do_all_timers();
239 #ifndef HAVE_IRQS
240 handle_irqs(-1);
241
242 #endif
243 if (need_wakeup)
244 break;
245 wait_ms(wait);
246 inc_jiffies(wait);
247 x-=wait;
248 }
249 need_wakeup=0;
250 printk("schedule DONE!!!!!!\n");
251
252 return x;
253 }
254 /*------------------------------------------------------------------------*/
255 void my_wait_for_completion(struct completion *x)
256 {
257 int n=100;
258 printk("wait for completion\n");
259
260 while(!x->done && (n>0))
261 {
262 do_all_timers();
263 #ifndef HAVE_IRQS
264 handle_irqs(-1);
265
266 #endif
267 wait_ms(10);
268 n--;
269 }
270 printk("wait for completion done %i\n",x->done);
271
272 }
273 /*------------------------------------------------------------------------*/
274 void my_interruptible_sleep_on(PKEVENT evnt)
275 {
276 KeWaitForSingleObject(evnt, Executive, KernelMode, FALSE, NULL);
277 KeClearEvent(evnt); // reset to not-signalled
278 }
279 /*------------------------------------------------------------------------*/
280 // Helper for pci_module_init
281 /*------------------------------------------------------------------------*/
282 int my_pci_module_init(struct pci_driver *x)
283 {
284 struct pci_dev *dev=pci_probe_dev;
285 const struct pci_device_id *id=NULL;
286 if (!pci_probe_dev)
287 {
288 DPRINT1("PCI device not set!\n");
289 return 0;
290 }
291 x->probe(dev, id);
292 return 0;
293 }
294 /*------------------------------------------------------------------------*/
295 struct pci_dev *my_pci_find_slot(int a,int b)
296 {
297 return NULL;
298 }
299 /*------------------------------------------------------------------------*/
300 int my_pci_write_config_word(struct pci_dev *dev, int where, u16 val)
301 {
302 //dev->bus, dev->devfn, where, val
303 OHCI_DEVICE_EXTENSION *dev_ext = (OHCI_DEVICE_EXTENSION *)dev->dev_ext;
304
305 //FIXME: Is returning this value correct?
306 //FIXME: Mixing pci_dev and win structs isn't a good thing at all
307 return HalSetBusDataByOffset(PCIConfiguration, dev->bus->number, dev_ext->SystemIoSlotNumber, &val, where, sizeof(val));
308 }
309 /*------------------------------------------------------------------------*/
310 int my_request_irq(unsigned int irq,
311 int (*handler)(int,void *, struct pt_regs *),
312 unsigned long mode, const char *desc, void *data)
313 {
314 if (num_irqs<MAX_IRQS)
315 {
316 reg_irqs[num_irqs].handler=handler;
317 reg_irqs[num_irqs].irq=irq;
318 reg_irqs[num_irqs].data=data;
319 num_irqs++;
320 return 0;
321 }
322 return 1;
323 }
324 /*------------------------------------------------------------------------*/
325 int my_free_irq(int irq, void* p)
326 {
327 /* No free... */
328 return 0;
329 }
330 /*------------------------------------------------------------------------*/
331 // Lookaside funcs
332 /*------------------------------------------------------------------------*/
333 kmem_cache_t *my_kmem_cache_create(const char *tag, size_t alloc_size,
334 size_t offset, unsigned long flags,
335 void *ctor,
336 void *dtor)
337 {
338 //TODO: Take in account ctor and dtor - callbacks for alloc/free, flags and offset
339 //FIXME: We assume this cache is always NPaged
340 PNPAGED_LOOKASIDE_LIST Lookaside;
341 ULONG Tag=0x11223344; //FIXME: Make this from tag
342
343 Lookaside = ExAllocatePool(NonPagedPool, sizeof(NPAGED_LOOKASIDE_LIST));
344
345 ExInitializeNPagedLookasideList(
346 Lookaside,
347 NULL,
348 NULL,
349 0,
350 alloc_size,
351 Tag,
352 0);
353
354 return (kmem_cache_t *)Lookaside;
355 }
356 /*------------------------------------------------------------------------*/
357 BOOLEAN my_kmem_cache_destroy(kmem_cache_t *co)
358 {
359 ExDeleteNPagedLookasideList((PNPAGED_LOOKASIDE_LIST)co);
360
361 ExFreePool(co);
362 return FALSE;
363 }
364 /*------------------------------------------------------------------------*/
365 void *my_kmem_cache_alloc(kmem_cache_t *co, int flags)
366 {
367 return ExAllocateFromNPagedLookasideList((PNPAGED_LOOKASIDE_LIST)co);
368 }
369 /*------------------------------------------------------------------------*/
370 void my_kmem_cache_free(kmem_cache_t *co, void *ptr)
371 {
372 ExFreeToNPagedLookasideList((PNPAGED_LOOKASIDE_LIST)co, ptr);
373 }
374 /*------------------------------------------------------------------------*/
375 // DMA, not used now
376 /*------------------------------------------------------------------------*/
377 void *my_dma_pool_alloc(struct dma_pool *pool, int gfp_flags, dma_addr_t *dma_handle)
378 {
379 // HalAllocCommonBuffer
380 // But ideally IoGetDmaAdapter
381 return NULL;
382 }