aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBjoern B. Brandenburg <bbb@cs.unc.edu>2008-04-07 17:05:57 -0400
committerBjoern B. Brandenburg <bbb@cs.unc.edu>2008-05-01 11:44:50 -0400
commit673d40302d2f9f205d80599df1f7dc41c874a74b (patch)
treea487855aeb54b39b5fc0d37c4b2b95124f611806
parent8b36e6fb97b15ad5953777e621bec9f3191267a9 (diff)
SRP: record owner in semaphores
-rw-r--r--litmus/litmus_sem.c50
1 files changed, 26 insertions, 24 deletions
diff --git a/litmus/litmus_sem.c b/litmus/litmus_sem.c
index 486fb3bef7..8151087c1a 100644
--- a/litmus/litmus_sem.c
+++ b/litmus/litmus_sem.c
@@ -319,21 +319,35 @@ DEFINE_PER_CPU(struct srp, srp);
319 319
320#define system_ceiling(srp) list2prio(srp->ceiling.next) 320#define system_ceiling(srp) list2prio(srp->ceiling.next)
321 321
322
323#define UNDEF_SEM -2
324
325
326/* struct for uniprocessor SRP "semaphore" */
327struct srp_semaphore {
328 struct srp_priority ceiling;
329 struct task_struct* owner;
330 int cpu; /* cpu associated with this "semaphore" and resource */
331};
332
333#define ceiling2sem(c) container_of(c, struct srp_semaphore, ceiling)
334
322static int srp_exceeds_ceiling(struct task_struct* first, 335static int srp_exceeds_ceiling(struct task_struct* first,
323 struct srp* srp) 336 struct srp* srp)
324{ 337{
325 return list_empty(&srp->ceiling) || 338 return list_empty(&srp->ceiling) ||
326 get_rt_period(first) < system_ceiling(srp)->period || 339 get_rt_period(first) < system_ceiling(srp)->period ||
327 (get_rt_period(first) == system_ceiling(srp)->period && 340 (get_rt_period(first) == system_ceiling(srp)->period &&
328 first->pid < system_ceiling(srp)->pid); 341 first->pid < system_ceiling(srp)->pid) ||
342 ceiling2sem(system_ceiling(srp))->owner == first;
329} 343}
330 344
331static void srp_add_prio(struct srp* srp, struct srp_priority* prio) 345static void srp_add_prio(struct srp* srp, struct srp_priority* prio)
332{ 346{
333 struct list_head *pos; 347 struct list_head *pos;
334 if (in_list(&prio->list)) { 348 if (in_list(&prio->list)) {
335 TRACE_CUR("WARNING: SRP violation detected, prio is already in " 349 printk(KERN_CRIT "WARNING: SRP violation detected, prio is already in "
336 "ceiling list!\n"); 350 "ceiling list!\n");
337 return; 351 return;
338 } 352 }
339 list_for_each(pos, &srp->ceiling) 353 list_for_each(pos, &srp->ceiling)
@@ -345,16 +359,6 @@ static void srp_add_prio(struct srp* srp, struct srp_priority* prio)
345 list_add_tail(&prio->list, &srp->ceiling); 359 list_add_tail(&prio->list, &srp->ceiling);
346} 360}
347 361
348#define UNDEF_SEM -2
349
350
351/* struct for uniprocessor SRP "semaphore" */
352struct srp_semaphore {
353 struct srp_priority ceiling;
354 int cpu; /* cpu associated with this "semaphore" and resource */
355 int claimed; /* is the resource claimed (ceiling should be used)? */
356};
357
358 362
359static void* create_srp_semaphore(void) 363static void* create_srp_semaphore(void)
360{ 364{
@@ -366,8 +370,8 @@ static void* create_srp_semaphore(void)
366 370
367 INIT_LIST_HEAD(&sem->ceiling.list); 371 INIT_LIST_HEAD(&sem->ceiling.list);
368 sem->ceiling.period = 0; 372 sem->ceiling.period = 0;
369 sem->claimed = 0;
370 sem->cpu = UNDEF_SEM; 373 sem->cpu = UNDEF_SEM;
374 sem->owner = NULL;
371 atomic_inc(&srp_objects_in_use); 375 atomic_inc(&srp_objects_in_use);
372 return sem; 376 return sem;
373} 377}
@@ -430,22 +434,20 @@ __initcall(srp_sema_boot_init);
430 434
431void do_srp_down(struct srp_semaphore* sem) 435void do_srp_down(struct srp_semaphore* sem)
432{ 436{
433 /* claim... */ 437 /* Update ceiling. */
434 sem->claimed = 1;
435 /* ...and update ceiling */
436 srp_add_prio(&__get_cpu_var(srp), &sem->ceiling); 438 srp_add_prio(&__get_cpu_var(srp), &sem->ceiling);
439 WARN_ON(sem->owner != NULL);
440 sem->owner = current;
437} 441}
438 442
439void do_srp_up(struct srp_semaphore* sem) 443void do_srp_up(struct srp_semaphore* sem)
440{ 444{
441 sem->claimed = 0;
442
443 /* Determine new system priority ceiling for this CPU. */ 445 /* Determine new system priority ceiling for this CPU. */
444 if (in_list(&sem->ceiling.list)) 446 WARN_ON(!in_list(&sem->ceiling.list));
447 if (!in_list(&sem->ceiling.list))
445 list_del(&sem->ceiling.list); 448 list_del(&sem->ceiling.list);
446 else 449
447 TRACE_CUR("WARNING: SRP violation detected, prio not in ceiling" 450 sem->owner = NULL;
448 " list!\n");
449 451
450 /* Wake tasks on this CPU, if they exceed current ceiling. */ 452 /* Wake tasks on this CPU, if they exceed current ceiling. */
451 wake_up_all(&__get_cpu_var(srp).ceiling_blocked); 453 wake_up_all(&__get_cpu_var(srp).ceiling_blocked);