00001 #include <stdio.h>
00002 #include <stdlib.h>
00003
00004 #include "hsqlist.h"
00005 #include "hsqueue.h"
00006 #include "hlog.h"
00007 #include "hprocess.h"
00008 #include "hsignal.h"
00009
00010
00017 struct hsqlist {
00019 int queues_num;
00021 struct hsqueue* first_queue;
00023 struct hsqueue* last_queue;
00024 };
00025
00031 static struct hsqlist* queue_lists[HPS_NUMBER] = {NULL, NULL, NULL, NULL, NULL};
00032
00039 static int (*signal_add_queue_)();
00040 static int (*signal_remove_queue_)();
00041
00042 static struct hsqlist* get_list_(int list);
00043 static int set_list_(int list, struct hsqlist* new_list);
00044 static int set_size_(struct hsqlist* list_element, int size);
00045 static int increment_size_(struct hsqlist* list_element);
00046 static int decrement_size_(struct hsqlist* list_element);
00047 static int set_last_queue_(struct hsqlist* list_element, struct hsqueue* queue);
00048 static int set_first_queue_(struct hsqlist* list_element, struct hsqueue* queue);
00049
00050
00051 static struct hsqlist* get_list_(int list)
00052 {
00053 if (!hsqlist_is_valid_range(list))
00054 return NULL;
00055
00056 return queue_lists[list];
00057 }
00058
00059
00060 static int set_list_(int list, struct hsqlist* new_list)
00061 {
00062 if (!hsqlist_is_valid_range(list))
00063 return -1;
00064
00065 queue_lists[list] = new_list;
00066
00067 return 0;
00068 }
00069
00070
00071 static int set_size_(struct hsqlist* list_element, int size)
00072 {
00073 if (list_element == NULL)
00074 return -1;
00075
00076 list_element->queues_num = size;
00077
00078 return 0;
00079 }
00080
00081
00082 static int increment_size_(struct hsqlist* list_element)
00083 {
00084 if (list_element == NULL)
00085 return -1;
00086
00087 list_element->queues_num += 1;
00088
00089 return 0;
00090 }
00091
00092
00093 static int decrement_size_(struct hsqlist* list_element)
00094 {
00095 if (list_element == NULL)
00096 return -1;
00097
00098 if (list_element->queues_num < 1) {
00099 list_element->queues_num = 0;
00100 return -2;
00101 }
00102
00103 list_element->queues_num -= 1;
00104
00105 return 0;
00106 }
00107
00108
00109 static int set_first_queue_(struct hsqlist* list_element, struct hsqueue* queue)
00110 {
00111 if (list_element == NULL)
00112 return -1;
00113
00114 list_element->first_queue = queue;
00115
00116 return 0;
00117 }
00118
00119
00120 static int set_last_queue_(struct hsqlist* list_element, struct hsqueue* queue)
00121 {
00122 if (list_element == NULL)
00123 return -1;
00124
00125 list_element->last_queue = queue;
00126
00127 return 0;
00128 }
00129
00130
00131 int hsqlist_register_signal(int signal, int (*function)())
00132 {
00133 switch (signal) {
00134 case HSIGNAL_ADD_QUEUE:
00135 signal_add_queue_ = function;
00136 return 0;
00137 case HSIGNAL_REMOVE_QUEUE:
00138 signal_remove_queue_ = function;
00139 return 0;
00140 default:
00141 return -1;
00142 }
00143
00144 return -1;
00145 }
00146
00147
00148 int hsqlist_remove(int list)
00149 {
00150 struct hsqlist* list_element = get_list_(list);
00151
00152 if (list_element == NULL)
00153 return -1;
00154
00155 free(list_element);
00156 set_list_(list, NULL);
00157
00158 return 0;
00159 }
00160
00161
00162 int hsqlist_size(int list)
00163 {
00164 struct hsqlist* list_element = get_list_(list);
00165
00166 if (list_element == NULL)
00167 return -1;
00168
00169 return list_element->queues_num;
00170 }
00171
00172
00173 int hsqlist_remove_queue(int list, struct hsqueue* queue)
00174 {
00178
00179 if (queue == NULL)
00180 return -1;
00181
00182 struct hsqlist* list_element = get_list_(list);
00183
00184 if (queue == hsqlist_get_first_queue(list)) {
00185 set_first_queue_(list_element, hsqueue_get_next(queue));
00186 }
00187
00188 if (queue == hsqlist_get_last_queue(list))
00189 set_last_queue_(list_element, hsqueue_get_prev(queue));
00190
00191 decrement_size_(list_element);
00192
00193
00194 signal_remove_queue_(queue);
00195
00196 return 0;
00197 }
00198
00199
00200 int hsqlist_create(int list)
00201 {
00202 if (!hsqlist_is_valid_range(list))
00203 return -1;
00204
00205 if (get_list_(list) != NULL)
00206 return -1;
00207
00208 struct hsqlist* new_list = calloc(1, sizeof(*new_list));
00209 set_size_(new_list, 0);
00210 set_first_queue_(new_list, NULL);
00211 set_last_queue_(new_list, NULL);
00212
00213 set_list_(list, new_list);
00214
00215 return 0;
00216 }
00217
00218 int hsqlist_is_valid_range(int list)
00219 {
00220 if ((list < 0) || (list > HPS_NUMBER)) {
00221 hlog_write(HLOG_ERROR, "hsqlist_is_valid_range: Invalid list range.\n");
00222 return 0;
00223 }
00224
00225 return 1;
00226 }
00227
00228
00229 struct hsqueue* hsqlist_get(int list, int priority)
00230 {
00231 if (!hsqlist_is_valid_range(list))
00232 return NULL;
00233
00234 if (hsqlist_size(list) == 0)
00235 return NULL;
00236
00237
00238
00239 struct hsqueue* queue = hsqlist_get_first_queue(list);
00240
00241 if (queue == NULL)
00242 return NULL;
00243
00244 struct hprocess* process = NULL;
00245
00246 while (queue != NULL) {
00247 process = hsqueue_get_first_process(queue);
00248 if (hprocess_get_priority(process) == priority)
00249 return queue;
00250 queue = hsqueue_get_next(queue);
00251 }
00252
00253
00254 return NULL;
00255 }
00256
00257
00258 int hsqlist_add_queue(int list, struct hsqueue* queue)
00259 {
00260 struct hsqlist* list_element = get_list_(list);
00261
00262
00263
00264 signal_add_queue_(queue, hsqlist_get_last_queue(list), NULL, list);
00265
00266 if (hsqlist_size(list) == 0)
00267 set_first_queue_(list_element, queue);
00268
00269 set_last_queue_(list_element, queue);
00270
00271 return increment_size_(list_element);
00272 }
00273
00274
00275 int hsqlist_insert_queue_before(int list, struct hsqueue* second_queue, struct hsqueue* queue)
00276 {
00277 struct hsqlist* list_element = get_list_(list);
00278
00279
00280 signal_add_queue_(queue, hsqueue_get_prev(second_queue), second_queue, list);
00281
00282 if (hsqlist_size(list) == 0) {
00283 set_first_queue_(list_element, queue);
00284 set_last_queue_(list_element, queue);
00285 } else if (hsqlist_get_first_queue(list) == second_queue)
00286 set_first_queue_(list_element, queue);
00287
00288 return increment_size_(list_element);
00289 }
00290
00291
00292 int hsqlist_get_state(int list)
00293 {
00294 struct hsqueue* first_queue = hsqlist_get_first_queue(list);
00295
00296 if (first_queue == NULL)
00297 return -1;
00298
00299 return hsqueue_get_state(first_queue);
00300 }
00301
00302
00303 struct hsqueue* hsqlist_get_first_queue(int list)
00304 {
00305 struct hsqlist* list_element = get_list_(list);
00306
00307 if (list_element == NULL)
00308 return NULL;
00309
00310 return list_element->first_queue;
00311 }
00312
00313
00314 struct hsqueue* hsqlist_get_last_queue(int list)
00315 {
00316 struct hsqlist* list_element = get_list_(list);
00317
00318 if (list_element == NULL)
00319 return NULL;
00320
00321 return list_element->last_queue;
00322 }
00323
00324