error.c
Go to the documentation of this file.00001
00019 #include <includes.h>
00020
00021 #ifndef __VERSION_0_1__
00022 #warning RangerOS mismatch, expected v0.1.
00023 #endif
00024
00025
00026 static volatile ERROR_BUFFER er_buffer;
00027 static volatile ERROR_INFO* er_active;
00028 static VOID_VOID_F er_transmit = voidvoid;
00029 static INT_VOID_F er_get_timestamp = intvoid;
00030 static BOARD_ID er_board_id;
00031 static int er_is_init = 0;
00032 static const int er_length = ((int)(ERROR_LAST_ID)/32)+1;
00033 static volatile unsigned int er_flags[er_length];
00041 void error_init(VOID_VOID_F transmit_function, INT_VOID_F timestamp_function, BOARD_ID board_id)
00042 {
00043 er_buffer.first = 0;
00044 er_buffer.next = 0;
00045 er_buffer.overflows = 0;
00046 er_buffer.empty = 1;
00047 er_transmit = transmit_function;
00048 er_get_timestamp = timestamp_function;
00049 er_board_id = board_id;
00050 er_is_init = 1;
00051 }
00052
00053 MUTEX er_mutex;
00060 void error_occurred(ERROR_ID error_code)
00061 {
00062 volatile int index, bit;
00063 if (er_is_init){
00064 volatile int index, bit;
00065 if (!mutex_check(&er_mutex)){
00066 mutex_lock(&er_mutex);
00067 index = (int)(error_code) / 32;
00068 bit = (int)(error_code) % 32;
00069 er_flags[index] |= (1<<bit);
00070
00071 mutex_unlock(&er_mutex);
00072 } else {
00073 }
00074 }
00075 }
00076
00077 MUTEX er_irq_mutex;
00084 void error_occurred_irq(ERROR_ID error_code)
00085 {
00086 volatile int index, bit;
00087 if (er_is_init){
00088 if (!mutex_check(&er_irq_mutex)){
00089 mutex_lock(&er_irq_mutex);
00090 index = (int)(error_code) / 32;
00091 bit = (int)(error_code) % 32;
00092 er_flags[index] |= (1<<bit);
00093
00094 mutex_unlock(&er_irq_mutex);
00095 } else {
00096 }
00097 }
00098 }
00099 MUTEX er_fiq_mutex;
00106 void error_occurred_fiq(ERROR_ID error_code)
00107 {
00108 volatile int index, bit;
00109 if (er_is_init){
00110 if (!mutex_check(&er_fiq_mutex)){
00111 mutex_lock(&er_fiq_mutex);
00112 index = (int)(error_code) / 32;
00113 bit = (int)(error_code) % 32;
00114 er_flags[index] |= (1<<bit);
00115
00116 mutex_unlock(&er_fiq_mutex);
00117 } else {
00118 }
00119 }
00120 }
00121
00127 void error_update(void){
00128 int chunk, bit;
00129 int index;
00130 int found = 0;
00131 ERROR_ID error_code;
00132 volatile ERROR_BUFFER* buf;
00133 volatile ERROR_INFO new_error;
00134
00135 if (er_is_init){
00136 for (chunk = 0; chunk < er_length; chunk++){
00137 if (er_flags[chunk]){
00138 for (bit = 0; bit < 32; bit++){
00139 if (er_flags[chunk] & (1<<bit)){
00140 error_code = (ERROR_ID)(bit + (32 * chunk));
00141
00142 buf = &er_buffer;
00143
00144
00145 if (!(buf->empty)){
00146 index = buf->first;
00147 while (index != buf->next) {
00148 if (buf->errors[index].error_id == error_code) {
00149 buf->errors[index].frequency++;
00150 found = 1;
00151 break;
00152 }
00153 if (index + 1 >= ERR_BUF_SIZE){
00154 index = 0;
00155 } else {
00156 index++;
00157 }
00158 }
00159 }
00160
00161
00162 if (!found) {
00163 new_error.error_id = error_code;
00164 new_error.frequency = 1;
00165 new_error.time_occurred = er_get_timestamp();
00166 error_push(buf, new_error);
00167 }
00168 }
00169 }
00170 er_flags[chunk] = 0;
00171 }
00172 }
00173 }
00174 }
00175
00182 static void error_push(volatile ERROR_BUFFER* buffer, volatile ERROR_INFO new_error)
00183 {
00184
00185 if ((buffer->next == buffer->first) && !(buffer->empty)){
00186 buffer->overflows++;
00187 if (buffer->first + 1 >= ERR_BUF_SIZE){
00188 buffer->first = 0;
00189 } else {
00190 buffer->first++;
00191 }
00192 }
00193
00194 buffer->errors[buffer->next] = new_error;
00195 if (buffer->next + 1 >= ERR_BUF_SIZE){
00196 buffer->next = 0;
00197 } else {
00198 buffer->next++;
00199 }
00200 buffer->empty = 0;
00201 }
00202
00209 static volatile ERROR_INFO* error_pop(volatile ERROR_BUFFER* buffer)
00210 {
00211 volatile ERROR_INFO* err = 0;
00212 if (!buffer->empty){
00213 err = &(buffer->errors[buffer->first]);
00214 if (buffer->first + 1 >= ERR_BUF_SIZE){
00215 buffer->first = 0;
00216 } else {
00217 buffer->first++;
00218 }
00219 buffer->overflows = 0;
00220 if (buffer->first == buffer->next){
00221 buffer->empty = 1;
00222 }
00223 }
00224 return err;
00225 }
00226
00231 int error_get_time(void)
00232 {
00233 if (er_is_init){
00234 return (int)(er_active->time_occurred);
00235 } else {
00236 return 0;
00237 }
00238 }
00247 int error_get_info(void)
00248 {
00249 if (er_is_init){
00250 long int info = (er_active->error_id & 0xFFFF) | ((er_board_id & 0x3F) << 16) | ((er_active->frequency & 0x3FF) << 22);
00251 return info;
00252 } else {
00253 return 0;
00254 }
00255 }
00256
00261 BOARD_ID error_get_board(void)
00262 {
00263 return er_board_id;
00264 }
00265
00270 ERROR_ID error_get_id(void)
00271 {
00272 if (er_is_init){
00273 return (ERROR_ID)er_active->error_id;
00274 } else {
00275 return ERROR_DEFAULT;
00276 }
00277 }
00278
00283 int error_get_frequency(void)
00284 {
00285 if (er_is_init){
00286 return er_active->frequency;
00287 } else {
00288 return 0;
00289 }
00290 }
00291
00299 void error_send_next(void)
00300 {
00301 if (er_is_init){
00302 if (!er_buffer.empty){
00303 er_active = error_pop(&er_buffer);
00304 if (er_active != 0){
00305 er_transmit();
00306 }
00307 }
00308 }
00309 }
00310
00311
00312
00313