Changeset 0116f21 in mainline for kernel/generic/src/main/shutdown.c
- Timestamp:
- 2019-07-18T15:30:31Z (6 years ago)
- Children:
- bb580548
- Parents:
- 40043e8
- git-author:
- Matthieu Riolo <matthieu.riolo@…> (2019-07-18 15:26:49)
- git-committer:
- Matthieu Riolo <matthieu.riolo@…> (2019-07-18 15:30:31)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
kernel/generic/src/main/shutdown.c
r40043e8 r0116f21 37 37 */ 38 38 39 #include <abi/shutdown.h> 39 40 #include <shutdown.h> 40 41 #include <log.h> 41 42 #include <cpu.h> 42 #include <arch/asm.h>43 #include <arch.h>44 43 #include <console/kconsole.h> 45 #include <proc/task.h> 44 #include <console/console.h> 45 #include <proc/thread.h> 46 #include <stdlib.h> 47 48 /* pointer to the thread for the shutdown process */ 49 thread_t *shutdown_thread = NULL; 46 50 47 51 /** Halt flag */ … … 81 85 } 82 86 87 /* Reboots the kernel */ 83 88 void reboot(void) 84 89 { … … 93 98 } 94 99 100 /* argument structure for the shutdown thread */ 101 typedef struct { 102 sysarg_t mode; 103 sysarg_t delay; 104 } sys_shutdown_arg_t; 105 106 /* function for the shutdown thread */ 107 static void sys_shutdown_function(void *arguments) 108 { 109 sys_shutdown_arg_t *arg = (sys_shutdown_arg_t *)arguments; 110 111 if (arg->delay != 0) { 112 thread_sleep(arg->delay); 113 } 114 115 if (thread_interrupted(THREAD)) { 116 free(arguments); 117 return; 118 } 119 120 if (arg->mode == SHUTDOWN_REBOOT) { 121 reboot(); 122 } else { 123 halt(); 124 } 125 } 126 127 /* system call handler for shutdown */ 128 sys_errno_t sys_shutdown(sysarg_t mode, sysarg_t delay, sysarg_t kconsole) 129 { 130 131 #if (defined(CONFIG_DEBUG)) && (defined(CONFIG_KCONSOLE)) 132 if (kconsole) { 133 grab_console(); 134 } 135 #endif 136 137 irq_spinlock_lock(&threads_lock, true); 138 thread_t *thread = atomic_load(&shutdown_thread); 139 if (thread != NULL) { 140 thread_interrupt(thread); 141 atomic_store(&shutdown_thread, NULL); 142 } 143 irq_spinlock_unlock(&threads_lock, true); 144 145 /* `cancel` or default has been called */ 146 if (mode != SHUTDOWN_HALT && mode != SHUTDOWN_REBOOT) { 147 return EOK; 148 } 149 150 sys_shutdown_arg_t *arg = malloc(sizeof(sys_shutdown_arg_t)); 151 if (arg == NULL) { 152 return ENOMEM; 153 } 154 155 //TODO: find a better way for accessing the kernel task 156 irq_spinlock_lock(&tasks_lock, true); 157 task_t *kernel_task = task_find_by_id(1); 158 irq_spinlock_unlock(&tasks_lock, true); 159 160 if (kernel_task == NULL) { 161 goto error; 162 } 163 164 arg->mode = mode; 165 arg->delay = delay; 166 167 thread = thread_create(sys_shutdown_function, arg, kernel_task, THREAD_FLAG_NONE, "shutdown"); 168 169 if (thread == NULL) { 170 goto error; 171 } 172 173 thread_ready(thread); 174 atomic_store(&shutdown_thread, thread); 175 return EOK; 176 177 error: 178 free(arg); 179 return ENOENT; 180 } 181 95 182 /** @} 96 183 */
Note:
See TracChangeset
for help on using the changeset viewer.