1c164510sam/*
24dc7b76rpaulo * OS specific functions
34dc7b76rpaulo * Copyright (c) 2005-2009, Jouni Malinen <j@w1.fi>
4c164510sam *
55e9e13erpaulo * This software may be distributed under the terms of the BSD license.
65e9e13erpaulo * See README for more details.
7c164510sam */
8c164510sam
9c164510sam#ifndef OS_H
10c164510sam#define OS_H
11c164510sam
12c164510samtypedef long os_time_t;
13c164510sam
14c164510sam/**
15c164510sam * os_sleep - Sleep (sec, usec)
16c164510sam * @sec: Number of seconds to sleep
17c164510sam * @usec: Number of microseconds to sleep
18c164510sam */
19c164510samvoid os_sleep(os_time_t sec, os_time_t usec);
20c164510sam
21c164510samstruct os_time {
22c164510sam	os_time_t sec;
23c164510sam	os_time_t usec;
24c164510sam};
25c164510sam
2630dc5aerpaulostruct os_reltime {
2730dc5aerpaulo	os_time_t sec;
2830dc5aerpaulo	os_time_t usec;
2930dc5aerpaulo};
3030dc5aerpaulo
31c164510sam/**
32c164510sam * os_get_time - Get current time (sec, usec)
33c164510sam * @t: Pointer to buffer for the time
34c164510sam * Returns: 0 on success, -1 on failure
35c164510sam */
36c164510samint os_get_time(struct os_time *t);
37c164510sam
3830dc5aerpaulo/**
3930dc5aerpaulo * os_get_reltime - Get relative time (sec, usec)
4030dc5aerpaulo * @t: Pointer to buffer for the time
4130dc5aerpaulo * Returns: 0 on success, -1 on failure
4230dc5aerpaulo */
4330dc5aerpauloint os_get_reltime(struct os_reltime *t);
4430dc5aerpaulo
4530dc5aerpaulo
4630dc5aerpaulo/* Helpers for handling struct os_time */
4730dc5aerpaulo
4830dc5aerpaulostatic inline int os_time_before(struct os_time *a, struct os_time *b)
4930dc5aerpaulo{
5030dc5aerpaulo	return (a->sec < b->sec) ||
5130dc5aerpaulo	       (a->sec == b->sec && a->usec < b->usec);
5230dc5aerpaulo}
5330dc5aerpaulo
5430dc5aerpaulo
5530dc5aerpaulostatic inline void os_time_sub(struct os_time *a, struct os_time *b,
5630dc5aerpaulo			       struct os_time *res)
5730dc5aerpaulo{
5830dc5aerpaulo	res->sec = a->sec - b->sec;
5930dc5aerpaulo	res->usec = a->usec - b->usec;
6030dc5aerpaulo	if (res->usec < 0) {
6130dc5aerpaulo		res->sec--;
6230dc5aerpaulo		res->usec += 1000000;
6330dc5aerpaulo	}
6430dc5aerpaulo}
6530dc5aerpaulo
6630dc5aerpaulo
6730dc5aerpaulo/* Helpers for handling struct os_reltime */
6830dc5aerpaulo
6930dc5aerpaulostatic inline int os_reltime_before(struct os_reltime *a,
7030dc5aerpaulo				    struct os_reltime *b)
7130dc5aerpaulo{
7230dc5aerpaulo	return (a->sec < b->sec) ||
7330dc5aerpaulo	       (a->sec == b->sec && a->usec < b->usec);
7430dc5aerpaulo}
7530dc5aerpaulo
7630dc5aerpaulo
7730dc5aerpaulostatic inline void os_reltime_sub(struct os_reltime *a, struct os_reltime *b,
7830dc5aerpaulo				  struct os_reltime *res)
7930dc5aerpaulo{
8030dc5aerpaulo	res->sec = a->sec - b->sec;
8130dc5aerpaulo	res->usec = a->usec - b->usec;
8230dc5aerpaulo	if (res->usec < 0) {
8330dc5aerpaulo		res->sec--;
8430dc5aerpaulo		res->usec += 1000000;
8530dc5aerpaulo	}
8630dc5aerpaulo}
8730dc5aerpaulo
8830dc5aerpaulo
8930dc5aerpaulostatic inline void os_reltime_age(struct os_reltime *start,
9030dc5aerpaulo				  struct os_reltime *age)
9130dc5aerpaulo{
9230dc5aerpaulo	struct os_reltime now;
9330dc5aerpaulo
9430dc5aerpaulo	os_get_reltime(&now);
9530dc5aerpaulo	os_reltime_sub(&now, start, age);
9630dc5aerpaulo}
9730dc5aerpaulo
9830dc5aerpaulo
9930dc5aerpaulostatic inline int os_reltime_expired(struct os_reltime *now,
10030dc5aerpaulo				     struct os_reltime *ts,
10130dc5aerpaulo				     os_time_t timeout_secs)
10230dc5aerpaulo{
10330dc5aerpaulo	struct os_reltime age;
10430dc5aerpaulo
10530dc5aerpaulo	os_reltime_sub(now, ts, &age);
10630dc5aerpaulo	return (age.sec > timeout_secs) ||
10730dc5aerpaulo	       (age.sec == timeout_secs && age.usec > 0);
10830dc5aerpaulo}
109c164510sam
110c164510sam
11130dc5aerpaulostatic inline int os_reltime_initialized(struct os_reltime *t)
11230dc5aerpaulo{
11330dc5aerpaulo	return t->sec != 0 || t->usec != 0;
11430dc5aerpaulo}
115c164510sam
116c164510sam
117c164510sam/**
118c164510sam * os_mktime - Convert broken-down time into seconds since 1970-01-01
119c164510sam * @year: Four digit year
120c164510sam * @month: Month (1 .. 12)
121c164510sam * @day: Day of month (1 .. 31)
122c164510sam * @hour: Hour (0 .. 23)
123c164510sam * @min: Minute (0 .. 59)
124c164510sam * @sec: Second (0 .. 60)
125c164510sam * @t: Buffer for returning calendar time representation (seconds since
126c164510sam * 1970-01-01 00:00:00)
127c164510sam * Returns: 0 on success, -1 on failure
128c164510sam *
129c164510sam * Note: The result is in seconds from Epoch, i.e., in UTC, not in local time
130c164510sam * which is used by POSIX mktime().
131c164510sam */
132c164510samint os_mktime(int year, int month, int day, int hour, int min, int sec,
133c164510sam	      os_time_t *t);
134c164510sam
1355e9e13erpaulostruct os_tm {
1365e9e13erpaulo	int sec; /* 0..59 or 60 for leap seconds */
1375e9e13erpaulo	int min; /* 0..59 */
1385e9e13erpaulo	int hour; /* 0..23 */
1395e9e13erpaulo	int day; /* 1..31 */
1405e9e13erpaulo	int month; /* 1..12 */
1415e9e13erpaulo	int year; /* Four digit year */
1425e9e13erpaulo};
1435e9e13erpaulo
1445e9e13erpauloint os_gmtime(os_time_t t, struct os_tm *tm);
145c164510sam
146c164510sam/**
147c164510sam * os_daemonize - Run in the background (detach from the controlling terminal)
148c164510sam * @pid_file: File name to write the process ID to or %NULL to skip this
149c164510sam * Returns: 0 on success, -1 on failure
150c164510sam */
151c164510samint os_daemonize(const char *pid_file);
152c164510sam
153c164510sam/**
154c164510sam * os_daemonize_terminate - Stop running in the background (remove pid file)
155c164510sam * @pid_file: File name to write the process ID to or %NULL to skip this
156c164510sam */
157c164510samvoid os_daemonize_terminate(const char *pid_file);
158c164510sam
159c164510sam/**
160c164510sam * os_get_random - Get cryptographically strong pseudo random data
161c164510sam * @buf: Buffer for pseudo random data
162c164510sam * @len: Length of the buffer
163c164510sam * Returns: 0 on success, -1 on failure
164c164510sam */
165c164510samint os_get_random(unsigned char *buf, size_t len);
166c164510sam
167c164510sam/**
168c164510sam * os_random - Get pseudo random value (not necessarily very strong)
169c164510sam * Returns: Pseudo random value
170c164510sam */
171c164510samunsigned long os_random(void);
172c164510sam
173c164510sam/**
174c164510sam * os_rel2abs_path - Get an absolute path for a file
175c164510sam * @rel_path: Relative path to a file
176c164510sam * Returns: Absolute path for the file or %NULL on failure
177c164510sam *
178c164510sam * This function tries to convert a relative path of a file to an absolute path
179c164510sam * in order for the file to be found even if current working directory has
180c164510sam * changed. The returned value is allocated and caller is responsible for
181c164510sam * freeing it. It is acceptable to just return the same path in an allocated
182c164510sam * buffer, e.g., return strdup(rel_path). This function is only used to find
183c164510sam * configuration files when os_daemonize() may have changed the current working
184c164510sam * directory and relative path would be pointing to a different location.
185c164510sam */
186c164510samchar * os_rel2abs_path(const char *rel_path);
187c164510sam
188c164510sam/**
189c164510sam * os_program_init - Program initialization (called at start)
190c164510sam * Returns: 0 on success, -1 on failure
191c164510sam *
192c164510sam * This function is called when a programs starts. If there are any OS specific
193c164510sam * processing that is needed, it can be placed here. It is also acceptable to
194c164510sam * just return 0 if not special processing is needed.
195c164510sam */
196c164510samint os_program_init(void);
197c164510sam
198c164510sam/**
199c164510sam * os_program_deinit - Program deinitialization (called just before exit)
200c164510sam *
201c164510sam * This function is called just before a program exists. If there are any OS
202c164510sam * specific processing, e.g., freeing resourced allocated in os_program_init(),
203c164510sam * it should be done here. It is also acceptable for this function to do
204c164510sam * nothing.
205c164510sam */
206c164510samvoid os_program_deinit(void);
207c164510sam
208c164510sam/**
209c164510sam * os_setenv - Set environment variable
210c164510sam * @name: Name of the variable
211c164510sam * @value: Value to set to the variable
212c164510sam * @overwrite: Whether existing variable should be overwritten
213c164510sam * Returns: 0 on success, -1 on error
214c164510sam *
215c164510sam * This function is only used for wpa_cli action scripts. OS wrapper does not
216c164510sam * need to implement this if such functionality is not needed.
217c164510sam */
218c164510samint os_setenv(const char *name, const char *value, int overwrite);
219c164510sam
220c164510sam/**
221c164510sam * os_unsetenv - Delete environent variable
222c164510sam * @name: Name of the variable
223c164510sam * Returns: 0 on success, -1 on error
224c164510sam *
225c164510sam * This function is only used for wpa_cli action scripts. OS wrapper does not
226c164510sam * need to implement this if such functionality is not needed.
227c164510sam */
228c164510samint os_unsetenv(const char *name);
229c164510sam
230c164510sam/**
231c164510sam * os_readfile - Read a file to an allocated memory buffer
232c164510sam * @name: Name of the file to read
233c164510sam * @len: For returning the length of the allocated buffer
234c164510sam * Returns: Pointer to the allocated buffer or %NULL on failure
235c164510sam *
236c164510sam * This function allocates memory and reads the given file to this buffer. Both
237c164510sam * binary and text files can be read with this function. The caller is
238c164510sam * responsible for freeing the returned buffer with os_free().
239c164510sam */
240c164510samchar * os_readfile(const char *name, size_t *len);
241c164510sam
242c164510sam/**
24330dc5aerpaulo * os_file_exists - Check whether the specified file exists
24430dc5aerpaulo * @fname: Path and name of the file
24530dc5aerpaulo * Returns: 1 if the file exists or 0 if not
24630dc5aerpaulo */
24730dc5aerpauloint os_file_exists(const char *fname);
24830dc5aerpaulo
24930dc5aerpaulo/**
2507726170rpaulo * os_fdatasync - Sync a file's (for a given stream) state with storage device
2517726170rpaulo * @stream: the stream to be flushed
2527726170rpaulo * Returns: 0 if the operation succeeded or -1 on failure
2537726170rpaulo */
2547726170rpauloint os_fdatasync(FILE *stream);
2557726170rpaulo
2567726170rpaulo/**
257c164510sam * os_zalloc - Allocate and zero memory
258c164510sam * @size: Number of bytes to allocate
259c164510sam * Returns: Pointer to allocated and zeroed memory or %NULL on failure
260c164510sam *
261c164510sam * Caller is responsible for freeing the returned buffer with os_free().
262c164510sam */
263c164510samvoid * os_zalloc(size_t size);
264c164510sam
2655e9e13erpaulo/**
2665e9e13erpaulo * os_calloc - Allocate and zero memory for an array
2675e9e13erpaulo * @nmemb: Number of members in the array
2685e9e13erpaulo * @size: Number of bytes in each member
2695e9e13erpaulo * Returns: Pointer to allocated and zeroed memory or %NULL on failure
2705e9e13erpaulo *
2715e9e13erpaulo * This function can be used as a wrapper for os_zalloc(nmemb * size) when an
2725e9e13erpaulo * allocation is used for an array. The main benefit over os_zalloc() is in
2735e9e13erpaulo * having an extra check to catch integer overflows in multiplication.
2745e9e13erpaulo *
2755e9e13erpaulo * Caller is responsible for freeing the returned buffer with os_free().
2765e9e13erpaulo */
2775e9e13erpaulostatic inline void * os_calloc(size_t nmemb, size_t size)
2785e9e13erpaulo{
2795e9e13erpaulo	if (size && nmemb > (~(size_t) 0) / size)
2805e9e13erpaulo		return NULL;
2815e9e13erpaulo	return os_zalloc(nmemb * size);
2825e9e13erpaulo}
2835e9e13erpaulo
284c164510sam
285c164510sam/*
286c164510sam * The following functions are wrapper for standard ANSI C or POSIX functions.
287c164510sam * By default, they are just defined to use the standard function name and no
288c164510sam * os_*.c implementation is needed for them. This avoids extra function calls
289c164510sam * by allowing the C pre-processor take care of the function name mapping.
290c164510sam *
291c164510sam * If the target system uses a C library that does not provide these functions,
292c164510sam * build_config.h can be used to define the wrappers to use a different
293c164510sam * function name. This can be done on function-by-function basis since the
294c164510sam * defines here are only used if build_config.h does not define the os_* name.
295c164510sam * If needed, os_*.c file can be used to implement the functions that are not
296c164510sam * included in the C library on the target system. Alternatively,
297c164510sam * OS_NO_C_LIB_DEFINES can be defined to skip all defines here in which case
298c164510sam * these functions need to be implemented in os_*.c file for the target system.
299c164510sam */
300c164510sam
301c164510sam#ifdef OS_NO_C_LIB_DEFINES
302c164510sam
303c164510sam/**
304c164510sam * os_malloc - Allocate dynamic memory
305c164510sam * @size: Size of the buffer to allocate
306c164510sam * Returns: Allocated buffer or %NULL on failure
307c164510sam *
308c164510sam * Caller is responsible for freeing the returned buffer with os_free().
309c164510sam */
310c164510samvoid * os_malloc(size_t size);
311c164510sam
312c164510sam/**
313c164510sam * os_realloc - Re-allocate dynamic memory
314c164510sam * @ptr: Old buffer from os_malloc() or os_realloc()
315c164510sam * @size: Size of the new buffer
316c164510sam * Returns: Allocated buffer or %NULL on failure
317c164510sam *
318c164510sam * Caller is responsible for freeing the returned buffer with os_free().
319c164510sam * If re-allocation fails, %NULL is returned and the original buffer (ptr) is
320c164510sam * not freed and caller is still responsible for freeing it.
321c164510sam */
322c164510samvoid * os_realloc(void *ptr, size_t size);
323c164510sam
324c164510sam/**
325c164510sam * os_free - Free dynamic memory
326c164510sam * @ptr: Old buffer from os_malloc() or os_realloc(); can be %NULL
327c164510sam */
328c164510samvoid os_free(void *ptr);
329c164510sam
330c164510sam/**
331c164510sam * os_memcpy - Copy memory area
332c164510sam * @dest: Destination
333c164510sam * @src: Source
334c164510sam * @n: Number of bytes to copy
335c164510sam * Returns: dest
336c164510sam *
337c164510sam * The memory areas src and dst must not overlap. os_memmove() can be used with
338c164510sam * overlapping memory.
339c164510sam */
340c164510samvoid * os_memcpy(void *dest, const void *src, size_t n);
341c164510sam
342c164510sam/**
343c164510sam * os_memmove - Copy memory area
344c164510sam * @dest: Destination
345c164510sam * @src: Source
346c164510sam * @n: Number of bytes to copy
347c164510sam * Returns: dest
348c164510sam *
349c164510sam * The memory areas src and dst may overlap.
350c164510sam */
351c164510samvoid * os_memmove(void *dest, const void *src, size_t n);
352c164510sam
353c164510sam/**
354c164510sam * os_memset - Fill memory with a constant byte
355c164510sam * @s: Memory area to be filled
356c164510sam * @c: Constant byte
357c164510sam * @n: Number of bytes started from s to fill with c
358c164510sam * Returns: s
359c164510sam */
360c164510samvoid * os_memset(void *s, int c, size_t n);
361c164510sam
362c164510sam/**
363c164510sam * os_memcmp - Compare memory areas
364c164510sam * @s1: First buffer
365c164510sam * @s2: Second buffer
366c164510sam * @n: Maximum numbers of octets to compare
367c164510sam * Returns: An integer less than, equal to, or greater than zero if s1 is
368c164510sam * found to be less than, to match, or be greater than s2. Only first n
369c164510sam * characters will be compared.
370c164510sam */
371c164510samint os_memcmp(const void *s1, const void *s2, size_t n);
372c164510sam
373c164510sam/**
374c164510sam * os_strdup - Duplicate a string
375c164510sam * @s: Source string
376c164510sam * Returns: Allocated buffer with the string copied into it or %NULL on failure
377c164510sam *
378c164510sam * Caller is responsible for freeing the returned buffer with os_free().
379c164510sam */
380c164510samchar * os_strdup(const char *s);
381c164510sam
382c164510sam/**
383c164510sam * os_strlen - Calculate the length of a string
384c164510sam * @s: '\0' terminated string
385c164510sam * Returns: Number of characters in s (not counting the '\0' terminator)
386c164510sam */
387c164510samsize_t os_strlen(const char *s);
388c164510sam
389c164510sam/**
390c164510sam * os_strcasecmp - Compare two strings ignoring case
391c164510sam * @s1: First string
392c164510sam * @s2: Second string
393c164510sam * Returns: An integer less than, equal to, or greater than zero if s1 is
394c164510sam * found to be less than, to match, or be greatred than s2
395c164510sam */
396c164510samint os_strcasecmp(const char *s1, const char *s2);
397c164510sam
398c164510sam/**
399c164510sam * os_strncasecmp - Compare two strings ignoring case
400c164510sam * @s1: First string
401c164510sam * @s2: Second string
402c164510sam * @n: Maximum numbers of characters to compare
403c164510sam * Returns: An integer less than, equal to, or greater than zero if s1 is
404c164510sam * found to be less than, to match, or be greater than s2. Only first n
405c164510sam * characters will be compared.
406c164510sam */
407c164510samint os_strncasecmp(const char *s1, const char *s2, size_t n);
408c164510sam
409c164510sam/**
410c164510sam * os_strchr - Locate the first occurrence of a character in string
411c164510sam * @s: String
412c164510sam * @c: Character to search for
413c164510sam * Returns: Pointer to the matched character or %NULL if not found
414c164510sam */
415c164510samchar * os_strchr(const char *s, int c);
416c164510sam
417c164510sam/**
418c164510sam * os_strrchr - Locate the last occurrence of a character in string
419c164510sam * @s: String
420c164510sam * @c: Character to search for
421c164510sam * Returns: Pointer to the matched character or %NULL if not found
422c164510sam */
423c164510samchar * os_strrchr(const char *s, int c);
424c164510sam
425c164510sam/**
426c164510sam * os_strcmp - Compare two strings
427c164510sam * @s1: First string
428c164510sam * @s2: Second string
429c164510sam * Returns: An integer less than, equal to, or greater than zero if s1 is
430c164510sam * found to be less than, to match, or be greatred than s2
431c164510sam */
432c164510samint os_strcmp(const char *s1, const char *s2);
433c164510sam
434c164510sam/**
435c164510sam * os_strncmp - Compare two strings
436c164510sam * @s1: First string
437c164510sam * @s2: Second string
438c164510sam * @n: Maximum numbers of characters to compare
439c164510sam * Returns: An integer less than, equal to, or greater than zero if s1 is
440c164510sam * found to be less than, to match, or be greater than s2. Only first n
441c164510sam * characters will be compared.
442c164510sam */
443c164510samint os_strncmp(const char *s1, const char *s2, size_t n);
444c164510sam
445c164510sam/**
446c164510sam * os_strstr - Locate a substring
447c164510sam * @haystack: String (haystack) to search from
448c164510sam * @needle: Needle to search from haystack
449c164510sam * Returns: Pointer to the beginning of the substring or %NULL if not found
450c164510sam */
451c164510samchar * os_strstr(const char *haystack, const char *needle);
452c164510sam
453c164510sam/**
454c164510sam * os_snprintf - Print to a memory buffer
455c164510sam * @str: Memory buffer to print into
456c164510sam * @size: Maximum length of the str buffer
457c164510sam * @format: printf format
458c164510sam * Returns: Number of characters printed (not including trailing '\0').
459c164510sam *
460c164510sam * If the output buffer is truncated, number of characters which would have
461c164510sam * been written is returned. Since some C libraries return -1 in such a case,
462c164510sam * the caller must be prepared on that value, too, to indicate truncation.
463c164510sam *
464c164510sam * Note: Some C library implementations of snprintf() may not guarantee null
465c164510sam * termination in case the output is truncated. The OS wrapper function of
466c164510sam * os_snprintf() should provide this guarantee, i.e., to null terminate the
467c164510sam * output buffer if a C library version of the function is used and if that
468c164510sam * function does not guarantee null termination.
469c164510sam *
470c164510sam * If the target system does not include snprintf(), see, e.g.,
471c164510sam * http://www.ijs.si/software/snprintf/ for an example of a portable
472c164510sam * implementation of snprintf.
473c164510sam */
474c164510samint os_snprintf(char *str, size_t size, const char *format, ...);
475c164510sam
476c164510sam#else /* OS_NO_C_LIB_DEFINES */
477c164510sam
4784dc7b76rpaulo#ifdef WPA_TRACE
4794dc7b76rpaulovoid * os_malloc(size_t size);
4804dc7b76rpaulovoid * os_realloc(void *ptr, size_t size);
4814dc7b76rpaulovoid os_free(void *ptr);
4824dc7b76rpaulochar * os_strdup(const char *s);
4834dc7b76rpaulo#else /* WPA_TRACE */
484c164510sam#ifndef os_malloc
485c164510sam#define os_malloc(s) malloc((s))
486c164510sam#endif
487c164510sam#ifndef os_realloc
488c164510sam#define os_realloc(p, s) realloc((p), (s))
489c164510sam#endif
490c164510sam#ifndef os_free
491c164510sam#define os_free(p) free((p))
492c164510sam#endif
4934dc7b76rpaulo#ifndef os_strdup
4944dc7b76rpaulo#ifdef _MSC_VER
4954dc7b76rpaulo#define os_strdup(s) _strdup(s)
4964dc7b76rpaulo#else
4974dc7b76rpaulo#define os_strdup(s) strdup(s)
4984dc7b76rpaulo#endif
4994dc7b76rpaulo#endif
5004dc7b76rpaulo#endif /* WPA_TRACE */
501c164510sam
502c164510sam#ifndef os_memcpy
503c164510sam#define os_memcpy(d, s, n) memcpy((d), (s), (n))
504c164510sam#endif
505c164510sam#ifndef os_memmove
506c164510sam#define os_memmove(d, s, n) memmove((d), (s), (n))
507c164510sam#endif
508c164510sam#ifndef os_memset
509c164510sam#define os_memset(s, c, n) memset(s, c, n)
510c164510sam#endif
511c164510sam#ifndef os_memcmp
512c164510sam#define os_memcmp(s1, s2, n) memcmp((s1), (s2), (n))
513c164510sam#endif
514c164510sam
515c164510sam#ifndef os_strlen
516c164510sam#define os_strlen(s) strlen(s)
517c164510sam#endif
518c164510sam#ifndef os_strcasecmp
519c164510sam#ifdef _MSC_VER
520c164510sam#define os_strcasecmp(s1, s2) _stricmp((s1), (s2))
521c164510sam#else
522c164510sam#define os_strcasecmp(s1, s2) strcasecmp((s1), (s2))
523c164510sam#endif
524c164510sam#endif
525c164510sam#ifndef os_strncasecmp
526c164510sam#ifdef _MSC_VER
527c164510sam#define os_strncasecmp(s1, s2, n) _strnicmp((s1), (s2), (n))
528c164510sam#else
529c164510sam#define os_strncasecmp(s1, s2, n) strncasecmp((s1), (s2), (n))
530c164510sam#endif
531c164510sam#endif
532c164510sam#ifndef os_strchr
533c164510sam#define os_strchr(s, c) strchr((s), (c))
534c164510sam#endif
535c164510sam#ifndef os_strcmp
536c164510sam#define os_strcmp(s1, s2) strcmp((s1), (s2))
537c164510sam#endif
538c164510sam#ifndef os_strncmp
539c164510sam#define os_strncmp(s1, s2, n) strncmp((s1), (s2), (n))
540c164510sam#endif
541c164510sam#ifndef os_strrchr
542c164510sam#define os_strrchr(s, c) strrchr((s), (c))
543c164510sam#endif
544c164510sam#ifndef os_strstr
545c164510sam#define os_strstr(h, n) strstr((h), (n))
546c164510sam#endif
547c164510sam
548c164510sam#ifndef os_snprintf
549c164510sam#ifdef _MSC_VER
550c164510sam#define os_snprintf _snprintf
551c164510sam#else
552c164510sam#define os_snprintf snprintf
553c164510sam#endif
554c164510sam#endif
555c164510sam
556c164510sam#endif /* OS_NO_C_LIB_DEFINES */
557c164510sam
558c164510sam
55930dc5aerpaulostatic inline int os_snprintf_error(size_t size, int res)
56030dc5aerpaulo{
56130dc5aerpaulo	return res < 0 || (unsigned int) res >= size;
56230dc5aerpaulo}
56330dc5aerpaulo
56430dc5aerpaulo
5655e9e13erpaulostatic inline void * os_realloc_array(void *ptr, size_t nmemb, size_t size)
5665e9e13erpaulo{
5675e9e13erpaulo	if (size && nmemb > (~(size_t) 0) / size)
5685e9e13erpaulo		return NULL;
5695e9e13erpaulo	return os_realloc(ptr, nmemb * size);
5705e9e13erpaulo}
5715e9e13erpaulo
57230dc5aerpaulo/**
57330dc5aerpaulo * os_remove_in_array - Remove a member from an array by index
57430dc5aerpaulo * @ptr: Pointer to the array
57530dc5aerpaulo * @nmemb: Current member count of the array
57630dc5aerpaulo * @size: The size per member of the array
57730dc5aerpaulo * @idx: Index of the member to be removed
57830dc5aerpaulo */
57930dc5aerpaulostatic inline void os_remove_in_array(void *ptr, size_t nmemb, size_t size,
58030dc5aerpaulo				      size_t idx)
58130dc5aerpaulo{
58230dc5aerpaulo	if (idx < nmemb - 1)
58330dc5aerpaulo		os_memmove(((unsigned char *) ptr) + idx * size,
58430dc5aerpaulo			   ((unsigned char *) ptr) + (idx + 1) * size,
58530dc5aerpaulo			   (nmemb - idx - 1) * size);
58630dc5aerpaulo}
5875e9e13erpaulo
588c164510sam/**
589c164510sam * os_strlcpy - Copy a string with size bound and NUL-termination
590c164510sam * @dest: Destination
591c164510sam * @src: Source
592c164510sam * @siz: Size of the target buffer
593c164510sam * Returns: Total length of the target string (length of src) (not including
594c164510sam * NUL-termination)
595c164510sam *
596c164510sam * This function matches in behavior with the strlcpy(3) function in OpenBSD.
597c164510sam */
598c164510samsize_t os_strlcpy(char *dest, const char *src, size_t siz);
599c164510sam
60030dc5aerpaulo/**
60130dc5aerpaulo * os_memcmp_const - Constant time memory comparison
60230dc5aerpaulo * @a: First buffer to compare
60330dc5aerpaulo * @b: Second buffer to compare
60430dc5aerpaulo * @len: Number of octets to compare
60530dc5aerpaulo * Returns: 0 if buffers are equal, non-zero if not
60630dc5aerpaulo *
60730dc5aerpaulo * This function is meant for comparing passwords or hash values where
60830dc5aerpaulo * difference in execution time could provide external observer information
60930dc5aerpaulo * about the location of the difference in the memory buffers. The return value
61030dc5aerpaulo * does not behave like os_memcmp(), i.e., os_memcmp_const() cannot be used to
61130dc5aerpaulo * sort items into a defined order. Unlike os_memcmp(), execution time of
61230dc5aerpaulo * os_memcmp_const() does not depend on the contents of the compared memory
61330dc5aerpaulo * buffers, but only on the total compared length.
61430dc5aerpaulo */
61530dc5aerpauloint os_memcmp_const(const void *a, const void *b, size_t len);
61630dc5aerpaulo
6178d61b8dcy
6188d61b8dcy/**
6198d61b8dcy * os_memdup - Allocate duplicate of passed memory chunk
6208d61b8dcy * @src: Source buffer to duplicate
6218d61b8dcy * @len: Length of source buffer
6228d61b8dcy * Returns: %NULL if allocation failed, copy of src buffer otherwise
6238d61b8dcy *
6248d61b8dcy * This function allocates a memory block like os_malloc() would, and
6258d61b8dcy * copies the given source buffer into it.
6268d61b8dcy */
6278d61b8dcyvoid * os_memdup(const void *src, size_t len);
6288d61b8dcy
62930dc5aerpaulo/**
63030dc5aerpaulo * os_exec - Execute an external program
63130dc5aerpaulo * @program: Path to the program
63230dc5aerpaulo * @arg: Command line argument string
63330dc5aerpaulo * @wait_completion: Whether to wait until the program execution completes
63430dc5aerpaulo * Returns: 0 on success, -1 on error
63530dc5aerpaulo */
63630dc5aerpauloint os_exec(const char *program, const char *arg, int wait_completion);
63730dc5aerpaulo
638c164510sam
639c164510sam#ifdef OS_REJECT_C_LIB_FUNCTIONS
640c164510sam#define malloc OS_DO_NOT_USE_malloc
641c164510sam#define realloc OS_DO_NOT_USE_realloc
642c164510sam#define free OS_DO_NOT_USE_free
643c164510sam#define memcpy OS_DO_NOT_USE_memcpy
644c164510sam#define memmove OS_DO_NOT_USE_memmove
645c164510sam#define memset OS_DO_NOT_USE_memset
646c164510sam#define memcmp OS_DO_NOT_USE_memcmp
647c164510sam#undef strdup
648c164510sam#define strdup OS_DO_NOT_USE_strdup
649c164510sam#define strlen OS_DO_NOT_USE_strlen
650c164510sam#define strcasecmp OS_DO_NOT_USE_strcasecmp
651c164510sam#define strncasecmp OS_DO_NOT_USE_strncasecmp
652c164510sam#undef strchr
653c164510sam#define strchr OS_DO_NOT_USE_strchr
654c164510sam#undef strcmp
655c164510sam#define strcmp OS_DO_NOT_USE_strcmp
656c164510sam#undef strncmp
657c164510sam#define strncmp OS_DO_NOT_USE_strncmp
658c164510sam#undef strncpy
659c164510sam#define strncpy OS_DO_NOT_USE_strncpy
660c164510sam#define strrchr OS_DO_NOT_USE_strrchr
661c164510sam#define strstr OS_DO_NOT_USE_strstr
662c164510sam#undef snprintf
663c164510sam#define snprintf OS_DO_NOT_USE_snprintf
664c164510sam
665c164510sam#define strcpy OS_DO_NOT_USE_strcpy
666c164510sam#endif /* OS_REJECT_C_LIB_FUNCTIONS */
667c164510sam
6687726170rpaulo
6697726170rpaulo#if defined(WPA_TRACE_BFD) && defined(CONFIG_TESTING_OPTIONS)
6707726170rpaulo#define TEST_FAIL() testing_test_fail()
6717726170rpauloint testing_test_fail(void);
67222c9018cyextern char wpa_trace_fail_func[256];
67322c9018cyextern unsigned int wpa_trace_fail_after;
67422c9018cyextern char wpa_trace_test_fail_func[256];
67522c9018cyextern unsigned int wpa_trace_test_fail_after;
6767726170rpaulo#else
6777726170rpaulo#define TEST_FAIL() 0
6787726170rpaulo#endif
6797726170rpaulo
680c164510sam#endif /* OS_H */
681