tizen 2.4 release
[kernel/u-boot-tm1.git] / drivers / usb / gadget / dwc_otg / dwc_os.h
1 /* =========================================================================
2  * $File: //dwh/usb_iip/dev/software/dwc_common_port/dwc_os.h $
3  * $Revision: #1 $
4  * $Date: 2008/12/21 $
5  * $Change: 1156609 $
6  *
7  * Synopsys Portability Library Software and documentation
8  * (hereinafter, "Software") is an Unsupported proprietary work of
9  * Synopsys, Inc. unless otherwise expressly agreed to in writing
10  * between Synopsys and you.
11  *
12  * The Software IS NOT an item of Licensed Software or Licensed Product
13  * under any End User Software License Agreement or Agreement for
14  * Licensed Product with Synopsys or any supplement thereto. You are
15  * permitted to use and redistribute this Software in source and binary
16  * forms, with or without modification, provided that redistributions
17  * of source code must retain this notice. You may not view, use,
18  * disclose, copy or distribute this file or any information contained
19  * herein except pursuant to this license grant from Synopsys. If you
20  * do not agree with this notice, including the disclaimer below, then
21  * you are not authorized to use the Software.
22  *
23  * THIS SOFTWARE IS BEING DISTRIBUTED BY SYNOPSYS SOLELY ON AN "AS IS"
24  * BASIS AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
25  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
26  * FOR A PARTICULAR PURPOSE ARE HEREBY DISCLAIMED. IN NO EVENT SHALL
27  * SYNOPSYS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
28  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
29  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
30  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
31  * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
32  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
33  * USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
34  * DAMAGE.
35  * ========================================================================= */
36 #ifndef _DWC_OS_H_
37 #define _DWC_OS_H_
38
39 /** @file
40  *
41  * DWC portability library, low level os-wrapper functions
42  *
43  */
44
45 /* These basic types need to be defined by some OS header file or custom header
46  * file for your specific target architecture.
47  *
48  * uint8_t, int8_t, uint16_t, int16_t, uint32_t, int32_t, uint64_t, int64_t
49  *
50  * Any custom or alternate header file must be added and enabled here.
51  */
52
53 #ifdef DWC_LINUX
54 #  include <linux/types.h>
55 #  ifdef CONFIG_DEBUG_MUTEXES
56 #    include <linux/mutex.h>
57 #  endif
58 #else
59 #  include <stdint.h>
60 #endif
61
62
63 /** @name Primitive Types and Values */
64
65 /** We define a boolean type for consistency.  Can be either YES or NO */
66 typedef uint8_t dwc_bool_t;
67 #define YES  1
68 #define NO   0
69
70 /** @todo make them positive and return the negative error code */
71 /** @name Error Codes */
72 #define DWC_E_INVALID         1001
73 #define DWC_E_NO_MEMORY       1002
74 #define DWC_E_NO_DEVICE       1003
75 #define DWC_E_NOT_SUPPORTED   1004
76 #define DWC_E_TIMEOUT         1005
77 #define DWC_E_BUSY            1006
78 #define DWC_E_AGAIN           1007
79 #define DWC_E_RESTART         1008
80 #define DWC_E_ABORT           1009
81 #define DWC_E_SHUTDOWN        1010
82 #define DWC_E_NO_DATA         1011
83 #define DWC_E_DISCONNECT      2000
84 #define DWC_E_UNKNOWN         3000
85 #define DWC_E_NO_STREAM_RES   4001
86 #define DWC_E_COMMUNICATION   4002
87 #define DWC_E_OVERFLOW        4003
88 #define DWC_E_PROTOCOL        4004
89 #define DWC_E_IN_PROGRESS     4005
90 #define DWC_E_PIPE            4006
91 #define DWC_E_IO              4007
92 #define DWC_E_NO_SPACE        4008
93
94 /** @name Tracing/Logging Functions
95  *
96  * These function provide the capability to add tracing, debugging, and error
97  * messages, as well exceptions as assertions.  The WUDEV uses these
98  * extensively.  These could be logged to the main console, the serial port, an
99  * internal buffer, etc.  These functions could also be no-op if they are too
100  * expensive on your system.  By default undefining the DEBUG macro already
101  * no-ops some of these functions. */
102 #include <stdarg.h>
103
104 /** Returns non-zero if in interrupt context. */
105 extern dwc_bool_t DWC_IN_IRQ(void);
106 #define dwc_in_irq DWC_IN_IRQ
107
108 /** Returns "IRQ" if DWC_IN_IRQ is true. */
109 static inline char *dwc_irq(void) {
110         return DWC_IN_IRQ() ? "IRQ" : "";
111 }
112
113 /**
114  * A vprintf() clone.  Just call vprintf if you've got it.
115  */
116 extern void DWC_VPRINTF(char *format, va_list args);
117 #define dwc_vprintf DWC_VPRINTF
118
119 /**
120  * A vsnprintf() clone.  Just call vprintf if you've got it.
121  */
122 extern int DWC_VSNPRINTF(char *str, int size, char *format, va_list args);
123 #define dwc_vsnprintf DWC_VSNPRINTF
124
125 /**
126  * printf() clone.  Just call printf if you've go it.
127  */
128 extern void DWC_PRINTF(char *format, ...)
129 /* This provides compiler level static checking of the parameters if you're
130  * using GCC. */
131 #ifdef __GNUC__
132         __attribute__ ((format(printf, 1, 2)));
133 #else
134   ;
135 #endif
136 #define dwc_printf DWC_PRINTF
137
138 /**
139  * sprintf() clone.  Just call sprintf if you've got it.
140  */
141 extern int DWC_SPRINTF(char *string, char *format, ...)
142 #ifdef __GNUC__
143      __attribute__ ((format(printf, 2, 3)));
144 #else
145      ;
146 #endif
147 #define dwc_sprintf DWC_SPRINTF
148
149 /**
150  * snprintf() clone.  Just call snprintf if you've got it.
151  */
152 extern int DWC_SNPRINTF(char *string, int size, char *format, ...)
153 #ifdef __GNUC__
154      __attribute__ ((format(printf, 3, 4)));
155 #else
156      ;
157 #endif
158 #define dwc_snprintf DWC_SNPRINTF
159
160 /**
161  * Prints a WARNING message.  On systems that don't differentiate between
162  * warnings and regular log messages, just print it.  Indicates that something
163  * may be wrong with the driver.  Works like printf().
164  *
165  * Use the DWC_WARN macro to call this function.
166  */
167 extern void __DWC_WARN(char *format, ...)
168 #ifdef __GNUC__
169      __attribute__ ((format(printf, 1, 2)));
170 #else
171      ;
172 #endif
173
174 /**
175  * Prints an error message.  On systems that don't differentiate between errors
176  * and regular log messages, just print it.  Indicates that something went wrong
177  * with the driver, but it can be recovered from.  Works like printf().
178  *
179  * Use the DWC_ERROR macro to call this function.
180  */
181 extern void __DWC_ERROR(char *format, ...)
182 #ifdef __GNUC__
183      __attribute__ ((format(printf, 1, 2)));
184 #else
185      ;
186 #endif
187
188 /**
189  * Prints an exception error message and takes some user-defined action such as
190  * print out a backtrace or trigger a breakpoint.  Indicates that something went
191  * abnormally wrong with the driver such as programmer error, or other
192  * exceptional condition.  It should not be ignored so even on systems without
193  * printing capability, some action should be taken to notify the developer of
194  * it.  Works like printf().
195  */
196 extern void DWC_EXCEPTION(char *format, ...)
197 #ifdef __GNUC__
198      __attribute__ ((format(printf, 1, 2)));
199 #else
200      ;
201 #endif
202 #define dwc_exception DWC_EXCEPTION
203
204 #ifdef DEBUG
205 /**
206  * Prints out a debug message.  Used for logging/trace messages.
207  *
208  * Use the DWC_DEBUG macro to call this function
209  */
210 extern void __DWC_DEBUG(char *format, ...)
211 #ifdef __GNUC__
212      __attribute__ ((format(printf, 1, 2)));
213 #else
214      ;
215 #endif
216 #else
217 #define __DWC_DEBUG(...)
218 #endif
219
220 #include <common.h>
221 /**
222  * Prints out a Debug message.
223  */
224 #define DWC_DEBUG(_format, _args...) __DWC_DEBUG("DEBUG:%s:%s: " _format "\n", __func__, dwc_irq(), ## _args)
225 #define dwc_debug DWC_DEBUG
226 /**
227  * Prints out an informative message.
228  */
229 #define DWC_INFO(_format, _args...) DWC_PRINTF("INFO:%s: " _format "\n", dwc_irq(), ## _args)
230 #define dwc_info DWC_INFO
231 /**
232  * Prints out a warning message.
233  */
234 #define DWC_WARN(_format, _args...) __DWC_WARN("WARN:%s:%s:%d: " _format "\n", dwc_irq(), __func__, __LINE__, ## _args)
235 #define dwc_warn DWC_WARN
236 /**
237  * Prints out an error message.
238  */
239 #define DWC_ERROR(_format, _args...) __DWC_ERROR("ERROR:%s:%s:%d: " _format "\n", dwc_irq(), __func__, __LINE__, ## _args)
240 #define dwc_error DWC_ERROR
241
242 #define DWC_PROTO_ERROR(_format, _args...) __DWC_WARN("ERROR:%s:%s:%d: " _format "\n", dwc_irq(), __func__, __LINE__, ## _args)
243 #define dwc_proto_error DWC_PROTO_ERROR
244
245 #ifdef DEBUG
246 /** Prints out a exception error message if the _expr expression fails.  Disabled
247  * if DEBUG is not enabled. */
248 #define DWC_ASSERT(_expr, _format, _args...) if (!(_expr)) { DWC_EXCEPTION("%s:%s:%d: " _format "\n", dwc_irq(), __FILE__, __LINE__, ## _args); }
249 #else
250 #define DWC_ASSERT(_x...)
251 #endif
252 #define dwc_assert DWC_ASSERT
253
254 /** @name Byter Ordering
255  * The following functions are for conversions between processor's byte ordering
256  * and specific ordering you want.
257  */
258
259 /** Converts 32 bit data in CPU byte ordering to little endian. */
260 extern uint32_t DWC_CPU_TO_LE32(uint32_t *p);
261 #define dwc_cpu_to_le32 DWC_CPU_TO_LE32
262 /** Converts 32 bit data in CPU byte orderint to big endian. */
263 extern uint32_t DWC_CPU_TO_BE32(uint32_t *p);
264 #define dwc_cpu_to_be32 DWC_CPU_TO_BE32
265
266 /** Converts 32 bit little endian data to CPU byte ordering. */
267 extern uint32_t DWC_LE32_TO_CPU(uint32_t *p);
268 #define dwc_le32_to_cpu DWC_LE32_TO_CPU
269 /** Converts 32 bit big endian data to CPU byte ordering. */
270 extern uint32_t DWC_BE32_TO_CPU(uint32_t *p);
271 #define dwc_be32_to_cpu DWC_BE32_TO_CPU
272
273 /** Converts 16 bit data in CPU byte ordering to little endian. */
274 extern uint16_t DWC_CPU_TO_LE16(uint16_t *p);
275 #define dwc_cpu_to_le16 DWC_CPU_TO_LE16
276 /** Converts 16 bit data in CPU byte orderint to big endian. */
277 extern uint16_t DWC_CPU_TO_BE16(uint16_t *p);
278 #define dwc_cpu_to_be16 DWC_CPU_TO_BE16
279
280 /** Converts 16 bit little endian data to CPU byte ordering. */
281 extern uint16_t DWC_LE16_TO_CPU(uint16_t *p);
282 #define dwc_le16_to_cpu DWC_LE16_TO_CPU
283 /** Converts 16 bit bi endian data to CPU byte ordering. */
284 extern uint16_t DWC_BE16_TO_CPU(uint16_t *p);
285 #define dwc_be16_to_cpu DWC_BE16_TO_CPU
286
287 /** @name Register Read/Write
288  *
289  * The following five functions should be implemented to read/write registers of
290  * 32-bit and 64-bit sizes.  All modules use this to read/write register values.
291  * The reg value is a pointer to the register calculated from the void *base
292  * variable passed into the driver when it is started.  */
293
294 /** Reads the content of a 32-bit register. */
295 extern uint32_t DWC_READ_REG32(uint32_t volatile *reg);
296 #define dwc_read_reg32 DWC_READ_REG32
297 /** Reads the content of a 64-bit register. */
298 extern uint64_t DWC_READ_REG64(uint64_t volatile *reg);
299 #define dwc_read_reg64 DWC_READ_REG64
300 /** Writes to a 32-bit register. */
301 extern void DWC_WRITE_REG32(uint32_t volatile *reg, uint32_t value);
302 #define dwc_write_reg32 DWC_WRITE_REG32
303 /** Writes to a 64-bit register. */
304 extern void DWC_WRITE_REG64(uint64_t volatile *reg, uint64_t value);
305 #define dwc_write_reg64 DWC_WRITE_REG64
306 /**  
307  * Modify bit values in a register.  Using the
308  * algorithm: (reg_contents & ~clear_mask) | set_mask.
309  */
310 extern void DWC_MODIFY_REG32(uint32_t volatile *reg, uint32_t clear_mask, uint32_t set_mask);
311 #define dwc_modify_reg32 DWC_MODIFY_REG32
312
313 /** @cond */
314
315 /** @name Some convenience MACROS used internally.  Define DEBUG_REGS to log the
316  * register writes. */
317
318 #ifdef DEBUG_REGS
319
320 #define dwc_define_read_write_reg_n(_reg,_container_type) \
321 static inline uint32_t dwc_read_##_reg##_n(_container_type *container, int num) { \
322         return DWC_READ_REG32(&container->regs->_reg[num]); \
323 } \
324 static inline void dwc_write_##_reg##_n(_container_type *container, int num, uint32_t data) { \
325         DWC_DEBUG("WRITING %8s[%d]: %p: %08x", #_reg, num, &(((uint32_t*)container->regs->_reg)[num]), data); \
326         DWC_WRITE_REG32(&(((uint32_t*)container->regs->_reg)[num]), data); \
327 }
328
329 #define dwc_define_read_write_reg(_reg,_container_type) \
330 static inline uint32_t dwc_read_##_reg(_container_type *container) { \
331         return DWC_READ_REG32(&container->regs->_reg); \
332 } \
333 static inline void dwc_write_##_reg(_container_type *container, uint32_t data) { \
334         DWC_DEBUG("WRITING %11s: %p: %08x", #_reg, &container->regs->_reg, data); \
335         DWC_WRITE_REG32(&container->regs->_reg, data); \
336 }
337
338 #else
339
340 #define dwc_define_read_write_reg_n(_reg,_container_type) \
341 static inline uint32_t dwc_read_##_reg##_n(_container_type *container, int num) { \
342         return DWC_READ_REG32(&container->regs->_reg[num]); \
343 } \
344 static inline void dwc_write_##_reg##_n(_container_type *container, int num, uint32_t data) { \
345         DWC_WRITE_REG32(&(((uint32_t*)container->regs->_reg)[num]), data); \
346 }
347
348 #define dwc_define_read_write_reg(_reg,_container_type) \
349 static inline uint32_t dwc_read_##_reg(_container_type *container) { \
350         return DWC_READ_REG32(&container->regs->_reg); \
351 } \
352 static inline void dwc_write_##_reg(_container_type *container, uint32_t data) { \
353         DWC_WRITE_REG32(&container->regs->_reg, data); \
354 }
355
356 #endif
357
358 /** @endcond */
359
360
361 /** @name Crypto Functions
362  *
363  * These are the low-level cryptographic functions used by the driver. */
364
365 /** Perform AES CBC */
366 extern int DWC_AES_CBC(uint8_t *message, uint32_t messagelen, uint8_t *key, uint32_t keylen, uint8_t iv[16], uint8_t *out);
367 #define dwc_aes_cbc DWC_AES_CBC
368 /** Fill the provided buffer with random bytes.  These should be cryptographic grade random numbers. */
369 extern void DWC_RANDOM_BYTES(uint8_t *buffer, uint32_t length);
370 #define dwc_random_bytes DWC_RANDOM_BYTES
371 /** Perform the SHA-256 hash function */
372 extern int DWC_SHA256(uint8_t *message, uint32_t len, uint8_t *out);
373 #define dwc_sha256 DWC_SHA256
374 /** Calculated the HMAC-SHA256 */
375 extern int DWC_HMAC_SHA256(uint8_t *message, uint32_t messagelen, uint8_t *key, uint32_t keylen, uint8_t *out);
376 #define dwc_hmac_sha256 DWC_HMAC_SHA256
377
378
379 /** @name Memory Allocation
380  *
381  * These function provide access to memory allocation.  There are only 2 DMA
382  * functions and 3 Regular memory functions that need to be implemented.  None
383  * of the memory debugging routines need to be implemented.  The allocation
384  * routines all ZERO the contents of the memory.
385  *
386  * Defining DEBUG_MEMORY turns on memory debugging and statistic gathering.
387  * This checks for memory leaks, keeping track of alloc/free pairs.  It also
388  * keeps track of how much memory the driver is using at any given time. */
389
390 #define DWC_PAGE_SIZE 4096
391 #define DWC_PAGE_OFFSET(addr) (((uint32_t)addr) & 0xfff)
392 #define DWC_PAGE_ALIGNED(addr) ((((uint32_t)addr) & 0xfff) == 0)
393
394 #define DWC_INVALID_DMA_ADDR 0x0
395
396 typedef uint32_t dwc_dma_t;
397
398
399 /** Allocates a DMA capable buffer and zeroes its contents. */
400 extern void *__DWC_DMA_ALLOC(uint32_t size, dwc_dma_t *dma_addr);
401
402 /** Frees a previosly allocated buffer. */
403 extern void __DWC_DMA_FREE(uint32_t size, void *virt_addr, dwc_dma_t dma_addr);
404
405 /** Allocates a block of memory and zeroes its contents. */
406 extern void *__DWC_ALLOC(uint32_t size);
407
408 /** Allocates a block of memory and zeroes its contents, in an atomic manner
409  * which can be used inside interrupt context.  The size should be sufficiently
410  * small, a few KB at most, such that failures are not likely to occur.  Can just call
411  * __DWC_ALLOC if it is atomic. */
412 extern void *__DWC_ALLOC_ATOMIC(uint32_t size);
413
414 /** Frees a previously allocated buffer. */
415 extern void __DWC_FREE(void *addr);
416
417 #ifndef DEBUG_MEMORY
418
419 #define DWC_ALLOC(_size_) __DWC_ALLOC(_size_)
420 #define DWC_ALLOC_ATOMIC(_size_) __DWC_ALLOC_ATOMIC(_size_)
421 #define DWC_FREE(_addr_) __DWC_FREE(_addr_)
422 #define DWC_DMA_ALLOC(_size_,_dma_) __DWC_DMA_ALLOC(_size_,_dma_)
423 #define DWC_DMA_FREE(_size_,_virt_,_dma_) __DWC_DMA_FREE(_size_,_virt_,_dma_)
424
425 #else
426
427 extern void *dwc_alloc_debug(uint32_t size, char const *func, int line);
428 extern void *dwc_alloc_atomic_debug(uint32_t size, char const *func, int line);
429 extern void dwc_free_debug(void *addr, char const *func, int line);
430 extern void *dwc_dma_alloc_debug(uint32_t size, dwc_dma_t *dma_addr, char const *func, int line);
431 extern void dwc_dma_free_debug(uint32_t size, void *virt_addr, dwc_dma_t dma_addr, char const *func, int line);
432
433 extern void dwc_memory_debug_start(void);
434 extern void dwc_memory_debug_stop(void);
435 extern void dwc_memory_debug_report(void);
436
437 #define DWC_ALLOC(_size_) (dwc_alloc_debug(_size_, __func__, __LINE__))
438 #define DWC_ALLOC_ATOMIC(_size_) (dwc_alloc_atomic_debug(_size_, __func__, __LINE__))
439 #define DWC_FREE(_addr_) (dwc_free_debug(_addr_, __func__, __LINE__))
440 #define DWC_DMA_ALLOC(_size_,_dma_) dwc_dma_alloc_debug(_size_, _dma_, __func__, __LINE__)
441 #define DWC_DMA_FREE(_size_,_virt_,_dma_) dwc_dma_free_debug(_size_, _virt_, _dma_, __func__, __LINE__)
442
443 #endif /* DEBUG_MEMORY */
444
445 #define dwc_alloc DWC_ALLOC
446 #define dwc_alloc_atomic DWC_ALLOC_ATOMIC
447 #define dwc_free DWC_FREE
448 #define dwc_dma_alloc DWC_DMA_ALLOC
449 #define dwc_dma_free DWC_DMA_FREE
450
451
452 /** @name Memory and String Processing */
453
454 /** memset() clone */
455 extern void *DWC_MEMSET(void *dest, uint8_t byte, uint32_t size);
456 #define dwc_memset DWC_MEMSET
457 /** memcpy() clone */
458 extern void *DWC_MEMCPY(void *dest, void const *src, uint32_t size);
459 #define dwc_memcpy DWC_MEMCPY
460 /** memmove() clone */
461 extern void *DWC_MEMMOVE(void *dest, void *src, uint32_t size);
462 #define dwc_memmove DWC_MEMMOVE
463 /** memcmp() clone */
464 extern int DWC_MEMCMP(void *m1, void *m2, uint32_t size);
465 #define dwc_memcmp DWC_MEMCMP
466 /** strcmp() clone */
467 extern int DWC_STRCMP(void *s1, void *s2);
468 #define dwc_strcmp DWC_STRCMP
469 /** strncmp() clone */
470 extern int DWC_STRNCMP(void *s1, void *s2, uint32_t size);
471 #define dwc_strncmp DWC_STRNCMP
472 /** strlen() clone, for NULL terminated ASCII strings */
473 extern int DWC_STRLEN(char const *str);
474 #define dwc_strlen DWC_STRLEN
475 /** strcpy() clone, for NULL terminated ASCII strings */
476 extern char *DWC_STRCPY(char *to, const char *from);
477 #define dwc_strcpy DWC_STRCPY
478
479 /** strdup() clone.  If you wish to use memory allocation debugging, this
480  * implementation of strdup should use the DWC_* memory routines instead of
481  * calling a predefined strdup.  Otherwise the memory allocated by this routine
482  * will not be seen by the debugging routines. */
483 extern char *DWC_STRDUP(char const *str);
484 #define dwc_strdup DWC_STRDUP
485
486 /** NOT an atoi() clone.  Read the description carefully.  Returns an integer
487  * converted from the string str in base 10 unless the string begins with a "0x"
488  * in which case it is base 16.  String must be a NULL terminated sequence of
489  * ASCII characters and may optionally begin with whitespace, a + or -, and a
490  * "0x" prefix if base 16.  The remaining characters must be valid digits for
491  * the number and end with a NULL character.  If any invalid characters are
492  * encountered or it returns with a negative error code and the results of the
493  * conversion are undefined.  On sucess it returns 0.  Overflow conditions are
494  * undefined.  An example implementation using atoi() can be referenced from the
495  * Linux implementation. */
496 extern int DWC_ATOI(char *str, int32_t *value);
497 #define dwc_atoi DWC_ATOI
498 /** Same as above but for unsigned. */
499 extern int DWC_ATOUI(char *str, uint32_t *value);
500 #define dwc_atoui DWC_ATOUI
501 /** This routine returns a UTF16LE unicode encoded string from a UTF8 string. */
502 extern int DWC_UTF8_TO_UTF16LE(uint8_t const *utf8string, uint16_t *utf16string, unsigned len);
503 #define dwc_utf8_to_utf16le DWC_UTF8_TO_UTF16LE
504
505 /** @name Wait queues
506  *
507  * Wait queues provide a means of synchronizing between threads or processes.  A
508  * process can block on a waitq if some condition is not true, waiting for it to
509  * become true.  When the waitq is triggered all waiting process will get
510  * unblocked and the condition will be check again.  Waitqs should be triggered
511  * every time a condition can potentially change.*/
512 struct dwc_waitq;
513 typedef struct dwc_waitq dwc_waitq_t;
514
515 /** The type of waitq condition callback function.  This is called every time
516  * condition is evaluated. */
517 typedef int (*dwc_waitq_condition_t)(void *data);
518
519 /** Allocate a waitq */
520 extern dwc_waitq_t *DWC_WAITQ_ALLOC(void);
521 #define dwc_waitq_alloc DWC_WAITQ_ALLOC
522 /** Free a waitq */
523 extern void DWC_WAITQ_FREE(dwc_waitq_t *wq);
524 #define dwc_waitq_free DWC_WAITQ_FREE
525
526 /** Check the condition and if it is false, block on the waitq.  When unblocked, check the
527  * condition again.  The function returns when the condition becomes true.  The return value
528  * is 0 on condition true, DWC_WAITQ_ABORTED on abort or killed, or DWC_WAITQ_UNKNOWN on error. */
529 extern int32_t DWC_WAITQ_WAIT(dwc_waitq_t *wq, dwc_waitq_condition_t condition, void *data);
530 #define dwc_waitq_wait DWC_WAITQ_WAIT;
531 /** Check the condition and if it is false, block on the waitq.  When unblocked,
532  * check the condition again.  The function returns when the condition become
533  * true or the timeout has passed.  The return value is 0 on condition true or
534  * DWC_TIMED_OUT on timeout, or DWC_WAITQ_ABORTED, or DWC_WAITQ_UNKNOWN on
535  * error. */
536 extern int32_t DWC_WAITQ_WAIT_TIMEOUT(dwc_waitq_t *wq, dwc_waitq_condition_t condition, void *data, int32_t msecs);
537 #define dwc_waitq_wait_timeout DWC_WAITQ_WAIT_TIMEOUT
538 /** Trigger a waitq, unblocking all processes.  This should be called whenever a condition
539  * has potentially changed. */
540 extern void DWC_WAITQ_TRIGGER(dwc_waitq_t *wq);
541 #define dwc_waitq_trigger DWC_WAITQ_TRIGGER
542 /** Unblock all processes waiting on the waitq with an ABORTED result. */
543 extern void DWC_WAITQ_ABORT(dwc_waitq_t *wq);
544 #define dwc_waitq_abort DWC_WAITQ_ABORT
545
546 /** @name Work queues
547  *
548  * Workqs are used to queue a callback function to be called at some later time,
549  * in another thread. */
550 struct dwc_workq;
551 typedef struct dwc_workq dwc_workq_t;
552
553 /** The type of the callback function to be called. */
554 typedef void (*dwc_work_callback_t)(void *data);
555
556 /** Allocate a workq */
557 extern dwc_workq_t *DWC_WORKQ_ALLOC(char *name);
558 #define dwc_workq_alloc DWC_WORKQ_ALLOC
559 /** Free a workq.  All work must be completed before being freed. */
560 extern void DWC_WORKQ_FREE(dwc_workq_t *workq);
561 #define dwc_workq_free DWC_WORKQ_FREE
562 /** Schedule a callback on the workq, passing in data.  The function will be
563  * scheduled at some later time. */
564 extern void DWC_WORKQ_SCHEDULE(dwc_workq_t *workq, dwc_work_callback_t work_cb, void *data, char *format, ...)
565 #ifdef __GNUC__
566         __attribute__ ((format(printf, 4, 5)));
567 #else
568   ;
569 #endif
570 #define dwc_workq_schedule DWC_WORKQ_SCHEDULE
571
572 /** Schedule a callback on the workq, that will be called until at least 
573  * given number miliseconds have passed. */
574 extern void DWC_WORKQ_SCHEDULE_DELAYED(dwc_workq_t *workq, dwc_work_callback_t work_cb, void *data, uint32_t time, char *format, ...)
575 #ifdef __GNUC__
576         __attribute__ ((format(printf, 5, 6)));
577 #else
578   ;
579 #endif
580 #define dwc_workq_schedule_delayed DWC_WORKQ_SCHEDULE_DELAYED
581
582 /** The number of processes in the workq */
583 extern int DWC_WORKQ_PENDING(dwc_workq_t *workq);
584 #define dwc_workq_pending DWC_WORKQ_PENDING
585 /** Blocks until all the work in the workq is complete or timed out.  Returns <
586  * 0 on timeout. */
587 extern int DWC_WORKQ_WAIT_WORK_DONE(dwc_workq_t *workq, int timeout);
588 #define dwc_workq_wait_work_done DWC_WORKQ_WAIT_WORK_DONE
589
590 /** @name Tasklets
591  *
592  */
593 struct dwc_tasklet;
594 typedef struct dwc_tasklet dwc_tasklet_t;
595
596 typedef void (*dwc_tasklet_callback_t)(void *data);
597
598 extern dwc_tasklet_t *DWC_TASK_ALLOC(dwc_tasklet_callback_t cb, void *data);
599 #define dwc_task_alloc DWC_TASK_ALLOC
600 extern void DWC_TASK_FREE(dwc_tasklet_t *t);
601 #define dwc_task_free DWC_TASK_FREE
602 extern void DWC_TASK_SCHEDULE(dwc_tasklet_t *task);
603 #define dwc_task_schedule DWC_TASK_SCHEDULE
604
605 /** @name Timer
606  *
607  * Callbacks must be small and atomic.
608  */
609 struct dwc_timer;
610 typedef struct dwc_timer dwc_timer_t;
611
612 typedef void (*dwc_timer_callback_t)(void *data);
613
614 extern dwc_timer_t *DWC_TIMER_ALLOC(char *name, dwc_timer_callback_t cb, void *data);
615 #define dwc_timer_alloc DWC_TIMER_ALLOC
616 extern void DWC_TIMER_FREE(dwc_timer_t *timer);
617 #define dwc_timer_free DWC_TIMER_FREE
618
619 /** Schedules the timer to run at time ms from now.  And will repeat at every
620  * repeat_interval msec therafter
621  *
622  * Modifies a timer that is still awaiting execution to a new expiration time.
623  * The mod_time is added to the old time.  */
624 extern void DWC_TIMER_SCHEDULE(dwc_timer_t *timer, uint32_t time);
625 #define dwc_timer_schedule DWC_TIMER_SCHEDULE
626
627 /** Disables the timer from execution. */
628 extern void DWC_TIMER_CANCEL(dwc_timer_t *timer);
629 #define dwc_timer_cancel DWC_TIMER_CANCEL
630
631
632
633 /** @name Spinlocks
634  *
635  * These locks are used when the work between the lock/unlock is atomic and
636  * short.  Interrupts are also disabled during the lock/unlock and thus they are
637  * suitable to lock between interrupt/non-interrupt context.  They also lock
638  * between processes if you have multiple CPUs or Preemption.  If you don't have
639  * multiple CPUS or Preemption, then the you can simply implement the
640  * DWC_SPINLOCK and DWC_SPINUNLOCK to disable and enable interrupts.  Because
641  * the work between the lock/unlock is atomic, the process context will never
642  * change, and so you never have to lock between processes.  */
643
644 struct dwc_spinlock;
645 typedef struct dwc_spinlock dwc_spinlock_t;
646
647 /** Returns an initialized lock variable.  This function should allocate and
648  * initialize the OS-specific data structure used for locking.  This data
649  * structure is to be used for the DWC_LOCK and DWC_UNLOCK functions and should
650  * be freed by the DWC_FREE_LOCK when it is no longer used. */
651 extern dwc_spinlock_t *DWC_SPINLOCK_ALLOC(void);
652 #define dwc_spinlock_alloc DWC_SPINLOCK_ALLOC
653
654 /** Frees an initialized lock variable. */
655 extern void DWC_SPINLOCK_FREE(dwc_spinlock_t *lock);
656 #define dwc_spinlock_free DWC_SPINLOCK_FREE
657
658 /** Disables interrupts and blocks until it acquires the lock.
659  *
660  * @param lock Pointer to the spinlock.
661  * @param flags Unsigned long for irq flags storage.
662  */
663 extern void DWC_SPINLOCK_IRQSAVE(dwc_spinlock_t *lock, unsigned long *flags);
664 #define dwc_spinlock_irqsave DWC_SPINLOCK_IRQSAVE
665
666 /** Re-enables the interrupt and releases the lock.
667  *
668  * @param lock Pointer to the spinlock.
669  * @param flags Unsigned long for irq flags storage.  Must be the same as was
670  * passed into DWC_LOCK.
671  */
672 extern void DWC_SPINUNLOCK_IRQRESTORE(dwc_spinlock_t *lock, unsigned long flags);
673 #define dwc_spinunlock_irqrestore DWC_SPINUNLOCK_IRQRESTORE
674
675 /** Blocks until it acquires the lock.
676  *
677  * @param lock Pointer to the spinlock.
678  */
679 extern void DWC_SPINLOCK(dwc_spinlock_t *lock);
680 #define dwc_spinlock DWC_SPINLOCK
681
682 /** Releases the lock.
683  *
684  * @param lock Pointer to the spinlock.
685  */
686 extern void DWC_SPINUNLOCK(dwc_spinlock_t *lock);
687 #define dwc_spinunlock DWC_SPINUNLOCK
688
689 /** @name Mutexes
690  *
691  * Unlike spinlocks Mutexes lock only between processes and the work between the
692  * lock/unlock CAN block, therefore it CANNOT be called from interrupt context.
693  */
694
695 struct dwc_mutex;
696 typedef struct dwc_mutex dwc_mutex_t;
697
698
699 /* For Linux Mutex Debugging make it inline because the debugging routines use
700  * the symbol to determine recursive locking.  This makes it falsely think
701  * recursive locking occurs. */
702 #if (defined(DWC_LINUX) && defined(CONFIG_DEBUG_MUTEXES))
703 #define DWC_MUTEX_ALLOC_LINUX_DEBUG(__mutexp) ({ \
704         __mutexp = (dwc_mutex_t *)DWC_ALLOC(sizeof(struct mutex)); \
705         mutex_init((struct mutex *)__mutexp); \
706 })
707 #endif
708 extern dwc_mutex_t *DWC_MUTEX_ALLOC(void);
709 #define dwc_mutex_alloc DWC_MUTEX_ALLOC
710
711 /* For memory leak debugging when using Linux Mutex Debugging */
712 #if (defined(DWC_LINUX) && defined(CONFIG_DEBUG_MUTEXES))
713 #define DWC_MUTEX_FREE(__mutexp) do { \
714         mutex_destroy((struct mutex *)__mutexp); \
715         DWC_FREE(__mutexp); \
716 } while(0)
717 #else
718 extern void DWC_MUTEX_FREE(dwc_mutex_t *mutex);
719 #define dwc_mutex_free DWC_MUTEX_FREE
720 #endif
721
722 extern void DWC_MUTEX_LOCK(dwc_mutex_t *mutex);
723 #define dwc_mutex_lock DWC_MUTEX_LOCK
724 /** Non-blocking lock returns 1 on successful lock. */
725 extern int DWC_MUTEX_TRYLOCK(dwc_mutex_t *mutex);
726 #define dwc_mutex_trylock DWC_MUTEX_TRYLOCK
727 extern void DWC_MUTEX_UNLOCK(dwc_mutex_t *mutex);
728 #define dwc_mutex_unlock DWC_MUTEX_UNLOCK
729
730
731
732
733 /** @name Time */
734
735 /** Microsecond delay.
736  *
737  * @param usecs  Microseconds to delay.
738  */
739 extern void DWC_UDELAY(uint32_t usecs);
740 #define dwc_udelay DWC_UDELAY
741
742 /** Millisecond delay.
743  *
744  * @param msecs  Milliseconds to delay.
745  */
746 extern void DWC_MDELAY(uint32_t msecs);
747 #define dwc_mdelay DWC_MDELAY
748
749 /** Non-busy waiting.
750  * Sleeps for specified number of milliseconds.
751  *
752  * @param msecs Milliseconds to sleep.
753  */
754 extern void DWC_MSLEEP(uint32_t msecs);
755 #define dwc_msleep DWC_MSLEEP
756
757 extern uint32_t DWC_TIME(void);
758 #define dwc_time DWC_TIME
759
760 #endif // _DWC_OS_H_
761
762
763
764
765 /** @mainpage DWC Portability and Common Library
766  *
767  * This is the documentation for the DWC Portability and Common Library.
768  *
769  * @section intro Introduction
770  *
771  * The DWC Portability library consists of wrapper calls and data structures to
772  * all low-level functions which are typically provided by the OS.  The WUDEV
773  * driver uses only these functions.  In order to port the WUDEV driver, only
774  * the functions in this library need to be re-implemented, with the same
775  * behavior as documented here.
776  *
777  * The Common library consists of higher level functions, which rely only on
778  * calling the functions from the DWC Portability library.  These common
779  * routines are shared across modules.  Some of the common libraries need to be
780  * used directly by the driver programmer when porting WUDEV.  Such as the
781  * parameter and notification libraries.
782  *
783  * @section low Portability Library OS Wrapper Functions
784  *
785  * Any function starting with DWC and in all CAPS is a low-level OS-wrapper that
786  * needs to be implemented when porting, for example DWC_MUTEX_ALLOC().  All of
787  * these functions are included in the dwc_os.h file.
788  *
789  * There are many functions here covering a wide array of OS services.  Please
790  * see dwc_os.h for details, and implementation notes for each function.
791  *
792  * @section common Common Library Functions
793  *
794  * Any function starting with dwc and in all lowercase is a common library
795  * routine.  These functions have a portable implementation and do not need to
796  * be reimplemented when porting.  The common routines can be used by any
797  * driver, and some must be used by the end user to control the drivers.  For
798  * example, you must use the Parameter common library in order to set the
799  * parameters in the WUDEV module.
800  *
801  * The common libraries consist of the following:
802  *
803  * - Connection Contexts - Used internally and can be used by end-user.  See dwc_cc.h
804  * - Parameters - Used internally and can be used by end-user.  See dwc_params.h
805  * - Notifications - Used internally and can be used by end-user.  See dwc_notifier.h
806  * - Lists - Used internally and can be used by end-user.  See dwc_list.h
807  * - Memory Debugging - Used internally and can be used by end-user.  See dwc_os.h
808  * - Modpow - Used internally only.  See dwc_modpow.h
809  * - DH - Used internally only.  See dwc_dh.h
810  * - Crypto - Used internally only.  See dwc_crypto.h
811  *
812  *
813  * @section prereq Prerequistes For dwc_os.h
814  * @subsection types Data Types
815  *
816  * The dwc_os.h file assumes that several low-level data types are pre defined for the
817  * compilation environment.  These data types are:
818  *
819  * - uint8_t - unsigned 8-bit data type
820  * - int8_t - signed 8-bit data type
821  * - uint16_t - unsigned 16-bit data type
822  * - int16_t - signed 16-bit data type
823  * - uint32_t - unsigned 32-bit data type
824  * - int32_t - signed 32-bit data type
825  * - uint64_t - unsigned 64-bit data type
826  * - int64_t - signed 64-bit data type
827  *
828  * Ensure that these are defined before using dwc_os.h.  The easiest way to do
829  * that is to modify the top of the file to include the appropriate header.
830  * This is already done for the Linux environment.  If the DWC_LINUX macro is
831  * defined, the correct header will be added.  A standard header <stdint.h> is
832  * also used for environments where standard C headers are available.
833  *
834  * @subsection stdarg Variable Arguments
835  *
836  * Variable arguments are provided by a standard C header <stdarg.h>.  it is
837  * available in Both the Linux and ANSI C enviornment.  An equivalent must be
838  * provided in your enviornment in order to use dwc_os.h with the debug and
839  * tracing message functionality.
840  *
841  * @subsection thread Threading
842  *
843  * WUDEV Core must be run on an operating system that provides for multiple
844  * threads/processes.  Threading can be implemented in many ways, even in
845  * embedded systems without an operating system.  At the bare minimum, the
846  * system should be able to start any number of processes at any time to handle
847  * special work.  It need not be a pre-emptive system.  Process context can
848  * change upon a call to a blocking function.  The hardware interrupt context
849  * that calls the module's ISR() function must be differentiable from process
850  * context, even if your processes are impemented via a hardware interrupt.
851  * Further locking mechanism between process must exist (or be implemented), and
852  * process context must have a way to disable interrupts for a period of time to
853  * lock them out.  If all of this exists, the functions in dwc_os.h related to
854  * threading should be able to be implemented with the defined behavior.
855  *
856  */