Changeset 099c834 in mainline for uspace/lib/c/generic/stdlib.c
- Timestamp:
- 2018-06-18T13:56:02Z (7 years ago)
- Branches:
- lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
- Children:
- 6c440362
- Parents:
- 379db9ef
- git-author:
- Jiri Svoboda <jiri@…> (2018-06-16 22:43:05)
- git-committer:
- Jiri Svoboda <jiri@…> (2018-06-18 13:56:02)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
uspace/lib/c/generic/stdlib.c
r379db9ef r099c834 1 1 /* 2 2 * Copyright (c) 2006 Ondrej Palkovsky 3 * Copyright (c) 2018 Jiri Svoboda 3 4 * All rights reserved. 4 5 * … … 33 34 */ 34 35 36 #include <adt/list.h> 37 #include <fibril_synch.h> 35 38 #include <stdlib.h> 39 #include "private/libc.h" 40 #include "private/stdlib.h" 36 41 37 42 static int glbl_seed = 1; 38 43 44 static LIST_INITIALIZE(exit_handlers); 45 static FIBRIL_MUTEX_INITIALIZE(exit_handlers_lock); 46 47 static LIST_INITIALIZE(quick_exit_handlers); 48 static FIBRIL_MUTEX_INITIALIZE(quick_exit_handlers_lock); 49 50 39 51 int rand(void) 40 52 { … … 46 58 glbl_seed = seed % RAND_MAX; 47 59 } 60 61 /** Register exit handler. 62 * 63 * @param func Function to be called during program terimnation 64 * @return Zero on success, nonzero on failure 65 */ 66 int atexit(void (*func)(void)) 67 { 68 __exit_handler_t *entry; 69 70 entry = malloc(sizeof(__exit_handler_t)); 71 if (entry == NULL) 72 return -1; 73 74 entry->func = func; 75 76 fibril_mutex_lock(&exit_handlers_lock); 77 list_prepend(&entry->llist, &exit_handlers); 78 fibril_mutex_unlock(&exit_handlers_lock); 79 return 0; 80 } 81 82 /** Terminate program with exit status. 83 * 84 * @param status Exit status 85 */ 86 void exit(int status) 87 { 88 link_t *link; 89 __exit_handler_t *eh; 90 91 /* Call exit handlers */ 92 fibril_mutex_lock(&exit_handlers_lock); 93 while (!list_empty(&exit_handlers)) { 94 link = list_first(&exit_handlers); 95 list_remove(link); 96 fibril_mutex_unlock(&exit_handlers_lock); 97 98 eh = list_get_instance(link, __exit_handler_t, llist); 99 eh->func(); 100 fibril_mutex_lock(&exit_handlers_lock); 101 } 102 103 fibril_mutex_unlock(&exit_handlers_lock); 104 105 _Exit(status); 106 } 107 108 /** Register quick exit handler. 109 * 110 * @param func Function to be called during quick program terimnation 111 * @return Zero on success, nonzero on failure 112 */ 113 int at_quick_exit(void (*func)(void)) 114 { 115 __exit_handler_t *entry; 116 117 entry = malloc(sizeof(__exit_handler_t)); 118 if (entry == NULL) 119 return -1; 120 121 entry->func = func; 122 123 fibril_mutex_lock(&exit_handlers_lock); 124 list_prepend(&entry->llist, &exit_handlers); 125 fibril_mutex_unlock(&exit_handlers_lock); 126 return 0; 127 } 128 129 /** Quickly terminate program with exit status. 130 * 131 * @param status Exit status 132 */ 133 void quick_exit(int status) 134 { 135 link_t *link; 136 __exit_handler_t *eh; 137 138 /* Call quick exit handlers */ 139 fibril_mutex_lock(&quick_exit_handlers_lock); 140 while (!list_empty(&quick_exit_handlers)) { 141 link = list_first(&quick_exit_handlers); 142 list_remove(link); 143 fibril_mutex_unlock(&quick_exit_handlers_lock); 144 145 eh = list_get_instance(link, __exit_handler_t, llist); 146 eh->func(); 147 fibril_mutex_lock(&quick_exit_handlers_lock); 148 } 149 150 fibril_mutex_unlock(&quick_exit_handlers_lock); 151 152 _Exit(status); 153 } 154 155 void _Exit(int status) 156 { 157 __libc_exit(status); 158 } 159 160 /** Abnormal program termination */ 161 void abort(void) 162 { 163 __libc_abort(); 164 } 165 48 166 49 167 /** Compute quotient and remainder of int division.
Note:
See TracChangeset
for help on using the changeset viewer.