]> git.ipfire.org Git - thirdparty/valgrind.git/commitdiff
drd: Remove drd/drd_list.h again because of its GPLv2 license.
authorBart Van Assche <bvanassche@acm.org>
Wed, 25 Jan 2012 20:36:27 +0000 (20:36 +0000)
committerBart Van Assche <bvanassche@acm.org>
Wed, 25 Jan 2012 20:36:27 +0000 (20:36 +0000)
For more info about Valgrind source code licensing, see also:
[1] Top level README line 51.
[2] http://valgrind.org/docs/manual/manual-intro.html#manual-intro.overview, last paragraph.

git-svn-id: svn://svn.valgrind.org/valgrind/trunk@12356

drd/drd_list.h [deleted file]
drd/drd_segment.c
drd/drd_segment.h
drd/drd_thread.c
drd/drd_thread.h

diff --git a/drd/drd_list.h b/drd/drd_list.h
deleted file mode 100644 (file)
index c39305a..0000000
+++ /dev/null
@@ -1,202 +0,0 @@
-/*
-  This file is part of drd, a thread error detector.
-
-  Copyright (C) 1990-2011 Linus Torvalds and other kernel authors.
-  Copyright (C) 2012 Bart Van Assche <bvanassche@acm.org>.
-
-  This program is free software; you can redistribute it and/or
-  modify it under the terms of version 2 of the GNU General Public
-  License as published by the Free Software Foundation.
-
-  This program is distributed in the hope that it will be useful, but
-  WITHOUT ANY WARRANTY; without even the implied warranty of
-  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-  General Public License for more details.
-
-  You should have received a copy of the GNU General Public License
-  along with this program; if not, write to the Free Software
-  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
-  02111-1307, USA.
-
-  The GNU General Public License is contained in the file COPYING.
-*/
-
-#ifndef _DRD_LIST_H_
-#define _DRD_LIST_H_
-
-/*
- * Doubly linked lists. See also the Linux kernel headers <linux/types.h>.
- */
-
-/**
- * container_of - cast a member of a structure out to the containing structure
- * @ptr:        the pointer to the member.
- * @type:       the type of the container struct this is embedded in.
- * @member:     the name of the member within the struct.
- *
- */
-#define container_of(ptr, type, member) ({                      \
-         const typeof( ((type *)0)->member ) *__mptr = (ptr);   \
-         (type *)( (char *)__mptr - offsetof(type,member) );})
-
-struct list_head {
-   struct list_head *next;
-   struct list_head *prev;
-};
-
-#define LIST_HEAD_INIT(name) { &(name), &(name) }
-
-static inline void init_list_head(struct list_head *list)
-{
-   list->next = list;
-   list->prev = list;
-}
-
-static inline void __list_add(struct list_head *new,
-                              struct list_head *prev,
-                              struct list_head *next)
-{
-   next->prev = new;
-   new->next = next;
-   new->prev = prev;
-   prev->next = new;
-}
-
-/**
- * list_add - add a new entry
- * @new: new entry to be added
- * @head: list head to add it after
- *
- * Insert a new entry after the specified head.
- */
-static inline void list_add(struct list_head *new, struct list_head *head)
-{
-   __list_add(new, head, head->next);
-}
-
-/**
- * list_add_tail - add a new entry
- * @new: new entry to be added
- * @head: list head to add it before
- *
- * Insert a new entry before the specified head.
- * This is useful for implementing queues.
- */
-static inline void list_add_tail(struct list_head *new, struct list_head *head)
-{
-   __list_add(new, head->prev, head);
-}
-
-/*
- * Delete a list entry by making the prev/next entries
- * point to each other.
- *
- * This is only for internal list manipulation where we know
- * the prev/next entries already!
- */
-static inline void __list_del(struct list_head * prev, struct list_head * next)
-{
-   next->prev = prev;
-   prev->next = next;
-}
-
-/**
- * list_del - deletes entry from list.
- * @entry: the element to delete from the list.
- * Note: list_empty() on entry does not return true after this, the entry is
- * in an undefined state.
- */
-static inline void list_del(struct list_head *entry)
-{
-   __list_del(entry->prev, entry->next);
-   entry->next = NULL;
-   entry->prev = NULL;
-}
-
-/**
- * list_is_last - tests whether @list is the last entry in list @head
- * @list: the entry to test
- * @head: the head of the list
- */
-static inline int list_is_last(const struct list_head *list,
-                                const struct list_head *head)
-{
-   return list->next == head;
-}
-
-/**
- * list_empty - tests whether a list is empty
- * @head: the list to test.
- */
-static inline int list_empty(const struct list_head *head)
-{
-   return head->next == head;
-}
-
-/**
- * list_entry - get the struct for this entry
- * @ptr:        the &struct list_head pointer.
- * @type:       the type of the struct this is embedded in.
- * @member:     the name of the list_struct within the struct.
- */
-#define list_entry(ptr, type, member) \
-   container_of(ptr, type, member)
-
-/**
- * list_first_entry - get the first element from a list
- * @ptr:        the list head to take the element from.
- * @type:       the type of the struct this is embedded in.
- * @member:     the name of the list_struct within the struct.
- *
- * Note, that list is expected to be not empty.
- */
-#define list_first_entry(ptr, type, member) \
-   list_entry((ptr)->next, type, member)
-
-#define list_next_entry(ptr, type, member) \
-   list_entry((ptr)->next, type, member)
-
-#define list_last_entry(ptr, type, member) \
-   list_entry((ptr)->prev, type, member)
-
-/**
- * list_for_each_entry  -       iterate over list of given type
- * @pos:        the type * to use as a loop cursor.
- * @head:       the head for your list.
- * @member:     the name of the list_struct within the struct.
- */
-#define list_for_each_entry(pos, head, member)                          \
-   for (pos = list_entry((head)->next, typeof(*pos), member);           \
-        &pos->member != (head);                                         \
-        pos = list_entry(pos->member.next, typeof(*pos), member))
-
-/**
- * list_for_each_entry_reverse - iterate backwards over list of given type.
- * @pos:        the type * to use as a loop cursor.
- * @head:       the head for your list.
- * @member:     the name of the list_struct within the struct.
- */
-#define list_for_each_entry_reverse(pos, head, member)                  \
-   for (pos = list_entry((head)->prev, typeof(*pos), member);           \
-        &pos->member != (head);                                         \
-        pos = list_entry(pos->member.prev, typeof(*pos), member))
-
-#define list_for_each_entry_reverse_continue(pos, head, member)         \
-   for ( ;                                                              \
-        &pos->member != (head);                                         \
-        pos = list_entry(pos->member.prev, typeof(*pos), member))
-
-/**
- * list_for_each_entry_safe - iterate over list of given type safe against removal of list entry
- * @pos:        the type * to use as a loop cursor.
- * @n:          another type * to use as temporary storage
- * @head:       the head for your list.
- * @member:     the name of the list_struct within the struct.
- */
-#define list_for_each_entry_safe(pos, n, head, member)                  \
-   for (pos = list_entry((head)->next, typeof(*pos), member),           \
-           n = list_entry(pos->member.next, typeof(*pos), member);      \
-        &pos->member != (head);                                         \
-        pos = n, n = list_entry(n->member.next, typeof(*n), member))
-
-#endif /* _DRD_LIST_H_ */
index 40db038925a1143ef69aff31445364dac82d13f1..32a74c33e2fbc572a8dd5af7fd57c046165bcef7 100644 (file)
@@ -36,7 +36,7 @@
 
 /* Global variables. */
 
-struct list_head DRD_(g_sg_list) = LIST_HEAD_INIT(DRD_(g_sg_list));
+Segment* DRD_(g_sg_list);
 
 
 /* Local variables. */
@@ -73,10 +73,10 @@ static void sg_init(Segment* const sg,
    creator_sg = (creator != DRD_INVALID_THREADID
                  ? DRD_(thread_get_segment)(creator) : 0);
 
-   sg->g_list.next = NULL;
-   sg->g_list.prev = NULL;
-   sg->thr_list.next = NULL;
-   sg->thr_list.prev = NULL;
+   sg->g_next = NULL;
+   sg->g_prev = NULL;
+   sg->thr_next = NULL;
+   sg->thr_prev = NULL;
    sg->tid = created;
    sg->refcnt = 1;
 
@@ -126,7 +126,11 @@ Segment* DRD_(sg_new)(const DrdThreadId creator, const DrdThreadId created)
    sg = VG_(malloc)("drd.segment.sn.1", sizeof(*sg));
    tl_assert(sg);
    sg_init(sg, creator, created);
-   list_add(&sg->g_list, &DRD_(g_sg_list));
+   if (DRD_(g_sg_list)) {
+      DRD_(g_sg_list)->g_prev = sg;
+      sg->g_next = DRD_(g_sg_list);
+   }
+   DRD_(g_sg_list) = sg;
    return sg;
 }
 
@@ -145,7 +149,12 @@ static void DRD_(sg_delete)(Segment* const sg)
    s_segments_alive_count--;
 
    tl_assert(sg);
-   list_del(&sg->g_list);
+   if (sg->g_next)
+      sg->g_next->g_prev = sg->g_prev;
+   if (sg->g_prev)
+      sg->g_prev->g_next = sg->g_next;
+   else
+      DRD_(g_sg_list) = sg->g_next;
    DRD_(sg_cleanup)(sg);
    VG_(free)(sg);
 }
index 5782b4ad1ee4ef64833f548aa0cc2852f3e207b5..1df257fc04a3c042712a0d6f2e415bb3a73099a1 100644 (file)
@@ -33,7 +33,6 @@
  */
 
 
-#include "drd_list.h"
 #include "drd_vc.h"
 #include "pub_drd_bitmap.h"
 #include "pub_tool_execontext.h" // ExeContext
 
 typedef struct segment
 {
-   struct list_head   g_list;
+   struct segment*    g_next;
+   struct segment*    g_prev;
    /** Pointers to next and previous segments executed by the same thread. */
-   struct list_head   thr_list;
+   struct segment*    thr_next;
+   struct segment*    thr_prev;
    DrdThreadId        tid;
    /** Reference count: number of pointers that point to this segment. */
    int                refcnt;
@@ -59,7 +60,7 @@ typedef struct segment
    struct bitmap      bm;
 } Segment;
 
-extern struct list_head DRD_(g_sg_list);
+extern Segment* DRD_(g_sg_list);
 
 Segment* DRD_(sg_new)(const DrdThreadId creator, const DrdThreadId created);
 static int DRD_(sg_get_refcnt)(const Segment* const sg);
index 0b522284cd111f72fe6c92b1c21b71c297b2a36f..c2f1a85b33aff728ab99c6b435e2d276d2a38dd4 100644 (file)
@@ -142,10 +142,6 @@ void DRD_(thread_set_join_list_vol)(const int jlv)
 
 void DRD_(thread_init)(void)
 {
-   int i;
-
-   for (i = 0; i < DRD_N_THREADS; i++)
-      init_list_head(&DRD_(g_threadinfo)[i].sg_list);
 }
 
 /**
@@ -201,7 +197,8 @@ static DrdThreadId DRD_(VgThreadIdToNewDrdThreadId)(const ThreadId tid)
          DRD_(g_threadinfo)[i].pthread_create_nesting_level = 0;
          DRD_(g_threadinfo)[i].synchr_nesting = 0;
          DRD_(g_threadinfo)[i].deletion_seq = s_deletion_tail - 1;
-         tl_assert(list_empty(&DRD_(g_threadinfo)[i].sg_list));
+         tl_assert(DRD_(g_threadinfo)[i].sg_first == NULL);
+         tl_assert(DRD_(g_threadinfo)[i].sg_last == NULL);
 
          tl_assert(DRD_(IsValidDrdThreadId)(i));
 
@@ -297,7 +294,8 @@ DrdThreadId DRD_(thread_pre_create)(const DrdThreadId creator,
    tl_assert(0 <= (int)created && created < DRD_N_THREADS
              && created != DRD_INVALID_THREADID);
 
-   tl_assert(list_empty(&DRD_(g_threadinfo)[created].sg_list));
+   tl_assert(DRD_(g_threadinfo)[created].sg_first == NULL);
+   tl_assert(DRD_(g_threadinfo)[created].sg_last == NULL);
    /* Create an initial segment for the newly created thread. */
    thread_append_segment(created, DRD_(sg_new)(creator, created));
 
@@ -496,10 +494,10 @@ void DRD_(thread_delete)(const DrdThreadId tid, const Bool detached)
    tl_assert(DRD_(IsValidDrdThreadId)(tid));
 
    tl_assert(DRD_(g_threadinfo)[tid].synchr_nesting >= 0);
-   list_for_each_entry_safe(sg, sg_prev, &DRD_(g_threadinfo)[tid].sg_list,
-                            thr_list)
-   {
-      list_del(&sg->thr_list);
+   for (sg = DRD_(g_threadinfo)[tid].sg_last; sg; sg = sg_prev) {
+      sg_prev = sg->thr_prev;
+      sg->thr_next = NULL;
+      sg->thr_prev = NULL;
       DRD_(sg_put)(sg);
    }
    DRD_(g_threadinfo)[tid].valid = False;
@@ -509,9 +507,10 @@ void DRD_(thread_delete)(const DrdThreadId tid, const Bool detached)
       DRD_(g_threadinfo)[tid].detached_posix_thread = False;
    else
       tl_assert(!DRD_(g_threadinfo)[tid].detached_posix_thread);
-   tl_assert(list_empty(&DRD_(g_threadinfo)[tid].sg_list));
+   DRD_(g_threadinfo)[tid].sg_first = NULL;
+   DRD_(g_threadinfo)[tid].sg_last = NULL;
 
-   tl_assert(! DRD_(IsValidDrdThreadId)(tid));
+   tl_assert(!DRD_(IsValidDrdThreadId)(tid));
 }
 
 /**
@@ -746,7 +745,14 @@ void thread_append_segment(const DrdThreadId tid, Segment* const sg)
    tl_assert(DRD_(sane_ThreadInfo)(&DRD_(g_threadinfo)[tid]));
 #endif
 
-   list_add_tail(&sg->thr_list, &DRD_(g_threadinfo)[tid].sg_list);
+   // add at tail
+   sg->thr_prev = DRD_(g_threadinfo)[tid].sg_last;
+   sg->thr_next = NULL;
+   if (DRD_(g_threadinfo)[tid].sg_last)
+      DRD_(g_threadinfo)[tid].sg_last->thr_next = sg;
+   DRD_(g_threadinfo)[tid].sg_last = sg;
+   if (DRD_(g_threadinfo)[tid].sg_first == NULL)
+      DRD_(g_threadinfo)[tid].sg_first = sg;
 
 #ifdef ENABLE_DRD_CONSISTENCY_CHECKS
    tl_assert(DRD_(sane_ThreadInfo)(&DRD_(g_threadinfo)[tid]));
@@ -767,7 +773,14 @@ void thread_discard_segment(const DrdThreadId tid, Segment* const sg)
    tl_assert(DRD_(sane_ThreadInfo)(&DRD_(g_threadinfo)[tid]));
 #endif
 
-   list_del(&sg->thr_list);
+   if (sg->thr_prev)
+      sg->thr_prev->thr_next = sg->thr_next;
+   if (sg->thr_next)
+      sg->thr_next->thr_prev = sg->thr_prev;
+   if (sg == DRD_(g_threadinfo)[tid].sg_first)
+      DRD_(g_threadinfo)[tid].sg_first = sg->thr_next;
+   if (sg == DRD_(g_threadinfo)[tid].sg_last)
+      DRD_(g_threadinfo)[tid].sg_last = sg->thr_prev;
    DRD_(sg_put)(sg);
 
 #ifdef ENABLE_DRD_CONSISTENCY_CHECKS
@@ -781,13 +794,13 @@ void thread_discard_segment(const DrdThreadId tid, Segment* const sg)
  */
 VectorClock* DRD_(thread_get_vc)(const DrdThreadId tid)
 {
-   struct list_head* sg_list;
+   Segment* latest_sg;
 
    tl_assert(0 <= (int)tid && tid < DRD_N_THREADS
              && tid != DRD_INVALID_THREADID);
-   sg_list = &DRD_(g_threadinfo)[tid].sg_list;
-   tl_assert(!list_empty(sg_list));
-   return &list_last_entry(sg_list, Segment, thr_list)->vc;
+   latest_sg = DRD_(g_threadinfo)[tid].sg_last;
+   tl_assert(latest_sg);
+   return &latest_sg->vc;
 }
 
 /**
@@ -795,16 +808,16 @@ VectorClock* DRD_(thread_get_vc)(const DrdThreadId tid)
  */
 void DRD_(thread_get_latest_segment)(Segment** sg, const DrdThreadId tid)
 {
-   struct list_head* sg_list;
+   Segment* latest_sg;
 
    tl_assert(sg);
    tl_assert(0 <= (int)tid && tid < DRD_N_THREADS
              && tid != DRD_INVALID_THREADID);
-   sg_list = &DRD_(g_threadinfo)[tid].sg_list;
-   tl_assert(!list_empty(sg_list));
+   latest_sg = DRD_(g_threadinfo)[tid].sg_last;
+   tl_assert(latest_sg);
 
    DRD_(sg_put)(*sg);
-   *sg = DRD_(sg_get)(list_last_entry(sg_list, Segment, thr_list));
+   *sg = DRD_(sg_get)(latest_sg);
 }
 
 /**
@@ -817,15 +830,13 @@ static void DRD_(thread_compute_minimum_vc)(VectorClock* vc)
 {
    unsigned i;
    Bool first;
-   struct list_head* sg_list;
    Segment* latest_sg;
 
    first = True;
    for (i = 0; i < DRD_N_THREADS; i++)
    {
-      sg_list = &DRD_(g_threadinfo)[i].sg_list;
-      if (!list_empty(sg_list)) {
-         latest_sg = list_last_entry(sg_list, Segment, thr_list);
+      latest_sg = DRD_(g_threadinfo)[i].sg_last;
+      if (latest_sg) {
          if (first)
             DRD_(vc_assign)(vc, &latest_sg->vc);
          else
@@ -844,15 +855,13 @@ static void DRD_(thread_compute_maximum_vc)(VectorClock* vc)
 {
    unsigned i;
    Bool first;
-   struct list_head* sg_list;
    Segment* latest_sg;
 
    first = True;
    for (i = 0; i < DRD_N_THREADS; i++)
    {
-      sg_list = &DRD_(g_threadinfo)[i].sg_list;
-      if (!list_empty(sg_list)) {
-         latest_sg = list_last_entry(sg_list, Segment, thr_list);
+      latest_sg = DRD_(g_threadinfo)[i].sg_last;
+      if (latest_sg) {
          if (first)
             DRD_(vc_assign)(vc, &latest_sg->vc);
          else
@@ -893,17 +902,15 @@ static void thread_discard_ordered_segments(void)
       DRD_(vc_cleanup)(&thread_vc_max);
    }
 
-   for (i = 0; i < DRD_N_THREADS; i++)
-   {
+   for (i = 0; i < DRD_N_THREADS; i++) {
       Segment* sg;
       Segment* sg_next;
-      struct list_head* sg_list;
 
-      sg_list = &DRD_(g_threadinfo)[i].sg_list;
-      list_for_each_entry_safe(sg, sg_next, sg_list, thr_list) {
-         if (list_is_last(&sg->thr_list, sg_list)
-             || !DRD_(vc_lte)(&sg->vc, &thread_vc_min))
-            break;
+      for (sg = DRD_(g_threadinfo)[i].sg_first;
+           sg && (sg_next = sg->thr_next)
+              && DRD_(vc_lte)(&sg->vc, &thread_vc_min);
+           sg = sg_next)
+      {
          thread_discard_segment(i, sg);
       }
    }
@@ -944,35 +951,26 @@ static Bool thread_consistent_segment_ordering(const DrdThreadId tid,
                                                Segment* const sg2)
 {
    unsigned i;
-   struct list_head* sg_list;
 
-   sg_list = &DRD_(g_threadinfo)[tid].sg_list;
-   tl_assert(!list_is_last(&sg1->thr_list, sg_list));
-   tl_assert(!list_is_last(&sg2->thr_list, sg_list));
-   tl_assert(list_next_entry(&sg1->thr_list, Segment, thr_list) == sg2);
+   tl_assert(sg1->thr_next);
+   tl_assert(sg2->thr_next);
+   tl_assert(sg1->thr_next == sg2);
    tl_assert(DRD_(vc_lte)(&sg1->vc, &sg2->vc));
 
    for (i = 0; i < DRD_N_THREADS; i++)
    {
       Segment* sg;
 
-      sg_list = &DRD_(g_threadinfo)[i].sg_list;
-      list_for_each_entry(sg, sg_list, thr_list)
-      {
-         if (list_is_last(&sg->thr_list, sg_list)
-             || DRD_(sg_get_refcnt)(sg) > 1)
-         {
+      for (sg = DRD_(g_threadinfo)[i].sg_first; sg; sg = sg->thr_next) {
+         if (!sg->thr_next || DRD_(sg_get_refcnt)(sg) > 1) {
             if (DRD_(vc_lte)(&sg2->vc, &sg->vc))
                break;
             if (DRD_(vc_lte)(&sg1->vc, &sg->vc))
                return False;
          }
       }
-      list_for_each_entry_reverse(sg, sg_list, thr_list)
-      {
-         if (list_is_last(&sg->thr_list, sg_list)
-             || DRD_(sg_get_refcnt)(sg) > 1)
-         {
+      for (sg = DRD_(g_threadinfo)[i].sg_last; sg; sg = sg->thr_prev) {
+         if (!sg->thr_next || DRD_(sg_get_refcnt)(sg) > 1) {
             if (DRD_(vc_lte)(&sg->vc, &sg1->vc))
                break;
             if (DRD_(vc_lte)(&sg->vc, &sg2->vc))
@@ -1016,15 +1014,11 @@ static void thread_merge_segments(void)
       tl_assert(DRD_(sane_ThreadInfo)(&DRD_(g_threadinfo)[i]));
 #endif
 
-      struct list_head* sg_list = &DRD_(g_threadinfo)[i].sg_list;
-      list_for_each_entry(sg, sg_list, thr_list)
-      {
-         if (DRD_(sg_get_refcnt)(sg) == 1
-             && !list_is_last(&sg->thr_list, sg_list)) {
-            Segment* sg_next = list_next_entry(&sg->thr_list, Segment,
-                                               thr_list);
+      for (sg = DRD_(g_threadinfo)[i].sg_first; sg; sg = sg->thr_next) {
+         if (DRD_(sg_get_refcnt)(sg) == 1 && sg->thr_next) {
+            Segment* const sg_next = sg->thr_next;
             if (DRD_(sg_get_refcnt)(sg_next) == 1
-                && !list_is_last(&sg_next->thr_list, sg_list)
+                && sg_next->thr_next
                 && thread_consistent_segment_ordering(i, sg, sg_next))
             {
                /* Merge sg and sg_next into sg. */
@@ -1046,7 +1040,6 @@ static void thread_merge_segments(void)
  */
 void DRD_(thread_new_segment)(const DrdThreadId tid)
 {
-   struct list_head* sg_list;
    Segment* last_sg;
    Segment* new_sg;
 
@@ -1054,9 +1047,7 @@ void DRD_(thread_new_segment)(const DrdThreadId tid)
              && tid != DRD_INVALID_THREADID);
    tl_assert(thread_conflict_set_up_to_date(DRD_(g_drd_running_tid)));
 
-   sg_list = &DRD_(g_threadinfo)[tid].sg_list;
-   last_sg = list_empty(sg_list) ? NULL
-      : list_last_entry(sg_list, Segment, thr_list);
+   last_sg = DRD_(g_threadinfo)[tid].sg_last;
    new_sg = DRD_(sg_new)(tid, tid);
    thread_append_segment(tid, new_sg);
    if (tid == DRD_(g_drd_running_tid) && last_sg)
@@ -1083,8 +1074,10 @@ void DRD_(thread_combine_vc_join)(DrdThreadId joiner, DrdThreadId joinee)
              && joiner != DRD_INVALID_THREADID);
    tl_assert(0 <= (int)joinee && joinee < DRD_N_THREADS
              && joinee != DRD_INVALID_THREADID);
-   tl_assert(!list_empty(&DRD_(g_threadinfo)[joiner].sg_list));
-   tl_assert(!list_empty(&DRD_(g_threadinfo)[joinee].sg_list));
+   tl_assert(DRD_(g_threadinfo)[joiner].sg_first);
+   tl_assert(DRD_(g_threadinfo)[joiner].sg_last);
+   tl_assert(DRD_(g_threadinfo)[joinee].sg_first);
+   tl_assert(DRD_(g_threadinfo)[joinee].sg_last);
 
    if (DRD_(sg_get_trace)())
    {
@@ -1131,7 +1124,8 @@ static void thread_combine_vc_sync(DrdThreadId tid, const Segment* sg)
 
    tl_assert(0 <= (int)tid && tid < DRD_N_THREADS
              && tid != DRD_INVALID_THREADID);
-   tl_assert(!list_empty(&DRD_(g_threadinfo)[tid].sg_list));
+   tl_assert(DRD_(g_threadinfo)[tid].sg_first);
+   tl_assert(DRD_(g_threadinfo)[tid].sg_last);
    tl_assert(sg);
    tl_assert(vc);
 
@@ -1194,7 +1188,7 @@ void DRD_(thread_stop_using_mem)(const Addr a1, const Addr a2)
 {
    Segment* p;
 
-   list_for_each_entry(p, &DRD_(g_sg_list), g_list)
+   for (p = DRD_(g_sg_list); p; p = p->g_next)
       DRD_(bm_clear)(DRD_(sg_bm)(p), a1, a2);
 
    DRD_(bm_clear)(DRD_(g_conflict_set), a1, a2);
@@ -1228,14 +1222,12 @@ void DRD_(thread_set_record_stores)(const DrdThreadId tid, const Bool enabled)
 void DRD_(thread_print_all)(void)
 {
    unsigned i;
-   struct list_head* sg_list;
    Segment* p;
 
    for (i = 0; i < DRD_N_THREADS; i++)
    {
-      sg_list = &DRD_(g_threadinfo)[i].sg_list;
-      if (!list_empty(sg_list))
-      {
+      p = DRD_(g_threadinfo)[i].sg_first;
+      if (p) {
          VG_(printf)("**************\n"
                      "* thread %3d (%d/%d/%d/%d/0x%lx/%d) *\n"
                      "**************\n",
@@ -1246,7 +1238,7 @@ void DRD_(thread_print_all)(void)
                      DRD_(g_threadinfo)[i].posix_thread_exists,
                      DRD_(g_threadinfo)[i].pt_threadid,
                      DRD_(g_threadinfo)[i].detached_posix_thread);
-         list_for_each_entry(p, sg_list, thr_list)
+         for ( ; p; p = p->thr_next)
             DRD_(sg_print)(p);
       }
    }
@@ -1283,15 +1275,11 @@ thread_report_conflicting_segments_segment(const DrdThreadId tid,
              && tid != DRD_INVALID_THREADID);
    tl_assert(p);
 
-   for (i = 0; i < DRD_N_THREADS; i++)
-   {
-      if (i != tid)
-      {
+   for (i = 0; i < DRD_N_THREADS; i++) {
+      if (i != tid) {
          Segment* q;
-         struct list_head *sg_list;
 
-         sg_list = &DRD_(g_threadinfo)[i].sg_list;
-         list_for_each_entry_reverse(q, sg_list, thr_list) {
+         for (q = DRD_(g_threadinfo)[i].sg_last; q; q = q->thr_prev) {
             /*
              * Since q iterates over the segments of thread i in order of
              * decreasing vector clocks, if q->vc <= p->vc, then
@@ -1300,11 +1288,9 @@ thread_report_conflicting_segments_segment(const DrdThreadId tid,
              */
             if (DRD_(vc_lte)(&q->vc, &p->vc))
                break;
-            if (! DRD_(vc_lte)(&p->vc, &q->vc))
-            {
+            if (!DRD_(vc_lte)(&p->vc, &q->vc)) {
                if (DRD_(bm_has_conflict_with)(DRD_(sg_bm)(q), addr, addr + size,
-                                              access_type))
-               {
+                                              access_type)) {
                   Segment* q_next;
 
                   tl_assert(q->stacktrace);
@@ -1320,8 +1306,7 @@ thread_report_conflicting_segments_segment(const DrdThreadId tid,
                   else
                      VG_(message)(Vg_UserMsg,
                                   "Other segment end (thread %d)\n", i);
-                  q_next = list_is_last(&q->thr_list, sg_list)
-                     ? NULL : list_next_entry(&q->thr_list, Segment, thr_list);
+                  q_next = q->thr_next;
                   show_call_stack(i, q_next ? q_next->stacktrace : 0);
                   if (VG_(clo_xml))
                      VG_(printf_xml)("  </other_segment_end>\n");
@@ -1343,7 +1328,7 @@ void DRD_(thread_report_conflicting_segments)(const DrdThreadId tid,
    tl_assert(0 <= (int)tid && tid < DRD_N_THREADS
              && tid != DRD_INVALID_THREADID);
 
-   list_for_each_entry(p, &DRD_(g_threadinfo)[tid].sg_list, thr_list) {
+   for (p = DRD_(g_threadinfo)[tid].sg_first; p; p = p->thr_next) {
       if (DRD_(bm_has)(DRD_(sg_bm)(p), addr, addr + size, access_type))
          thread_report_conflicting_segments_segment(tid, addr, size,
                                                     access_type, p);
@@ -1418,12 +1403,11 @@ static void thread_compute_conflict_set(struct bitmap** conflict_set,
       VG_(free)(str);
    }
 
-   p = list_last_entry(&DRD_(g_threadinfo)[tid].sg_list, Segment, thr_list);
+   p = DRD_(g_threadinfo)[tid].sg_last;
    {
       unsigned j;
 
-      if (s_trace_conflict_set)
-      {
+      if (s_trace_conflict_set) {
          char* vc;
 
          vc = DRD_(vc_aprint)(&p->vc);
@@ -1432,18 +1416,14 @@ static void thread_compute_conflict_set(struct bitmap** conflict_set,
          VG_(free)(vc);
       }
 
-      for (j = 0; j < DRD_N_THREADS; j++)
-      {
-         if (j != tid && DRD_(IsValidDrdThreadId)(j))
-         {
+      for (j = 0; j < DRD_N_THREADS; j++) {
+         if (j != tid && DRD_(IsValidDrdThreadId)(j)) {
             Segment* q;
-            list_for_each_entry_reverse(q, &DRD_(g_threadinfo)[j].sg_list,
-                                        thr_list) {
-               if (! DRD_(vc_lte)(&q->vc, &p->vc)
-                   && ! DRD_(vc_lte)(&p->vc, &q->vc))
-               {
-                  if (s_trace_conflict_set)
-                  {
+
+            for (q = DRD_(g_threadinfo)[j].sg_last; q; q = q->thr_prev) {
+               if (!DRD_(vc_lte)(&q->vc, &p->vc)
+                   && !DRD_(vc_lte)(&p->vc, &q->vc)) {
+                  if (s_trace_conflict_set) {
                      char* str;
 
                      str = DRD_(vc_aprint)(&q->vc);
@@ -1453,11 +1433,8 @@ static void thread_compute_conflict_set(struct bitmap** conflict_set,
                      VG_(free)(str);
                   }
                   DRD_(bm_merge2)(*conflict_set, DRD_(sg_bm)(q));
-               }
-               else
-               {
-                  if (s_trace_conflict_set)
-                  {
+               } else {
+                  if (s_trace_conflict_set) {
                      char* str;
 
                      str = DRD_(vc_aprint)(&q->vc);
@@ -1477,8 +1454,7 @@ static void thread_compute_conflict_set(struct bitmap** conflict_set,
    s_conflict_set_bitmap2_creation_count
       += DRD_(bm_get_bitmap2_creation_count)();
 
-   if (s_trace_conflict_set_bm)
-   {
+   if (s_trace_conflict_set_bm) {
       VG_(message)(Vg_DebugMsg, "[%d] new conflict set:\n", tid);
       DRD_(bm_print)(*conflict_set);
       VG_(message)(Vg_DebugMsg, "[%d] end of new conflict set.\n", tid);
@@ -1525,14 +1501,13 @@ void DRD_(thread_update_conflict_set)(const DrdThreadId tid,
       if (j == tid || ! DRD_(IsValidDrdThreadId)(j))
          continue;
 
-      list_for_each_entry_reverse(q, &DRD_(g_threadinfo)[j].sg_list, thr_list) {
-         Bool included_in_old_conflict_set, included_in_new_conflict_set;
-
-         if (DRD_(vc_lte)(&q->vc, new_vc))
-            break;
-
-         included_in_old_conflict_set = !DRD_(vc_lte)(old_vc, &q->vc);
-         included_in_new_conflict_set = !DRD_(vc_lte)(new_vc, &q->vc);
+      for (q = DRD_(g_threadinfo)[j].sg_last;
+           q && !DRD_(vc_lte)(&q->vc, new_vc);
+           q = q->thr_prev) {
+         const Bool included_in_old_conflict_set
+            = !DRD_(vc_lte)(old_vc, &q->vc);
+         const Bool included_in_new_conflict_set
+            = !DRD_(vc_lte)(new_vc, &q->vc);
 
          if (UNLIKELY(s_trace_conflict_set)) {
             char* str;
@@ -1549,16 +1524,12 @@ void DRD_(thread_update_conflict_set)(const DrdThreadId tid,
             DRD_(bm_mark)(DRD_(g_conflict_set), DRD_(sg_bm)(q));
       }
 
-      list_for_each_entry_reverse_continue(q, &DRD_(g_threadinfo)[j].sg_list,
-                                           thr_list) {
-         Bool included_in_old_conflict_set, included_in_new_conflict_set;
-
-         if (DRD_(vc_lte)(&q->vc, old_vc))
-            break;
-
-         included_in_old_conflict_set = !DRD_(vc_lte)(old_vc, &q->vc);
-         included_in_new_conflict_set
-            = !DRD_(vc_lte)(&q->vc, new_vc) && !DRD_(vc_lte)(new_vc, &q->vc);
+      for ( ; q && !DRD_(vc_lte)(&q->vc, old_vc); q = q->thr_prev) {
+         const Bool included_in_old_conflict_set
+            = !DRD_(vc_lte)(old_vc, &q->vc);
+         const Bool included_in_new_conflict_set
+            = !DRD_(vc_lte)(&q->vc, new_vc)
+            && !DRD_(vc_lte)(new_vc, &q->vc);
 
          if (UNLIKELY(s_trace_conflict_set)) {
             char* str;
@@ -1578,16 +1549,13 @@ void DRD_(thread_update_conflict_set)(const DrdThreadId tid,
 
    DRD_(bm_clear_marked)(DRD_(g_conflict_set));
 
-   p = list_last_entry(&DRD_(g_threadinfo)[tid].sg_list, Segment, thr_list);
-   for (j = 0; j < DRD_N_THREADS; j++)
-   {
-      if (j != tid && DRD_(IsValidDrdThreadId)(j))
-      {
+   p = DRD_(g_threadinfo)[tid].sg_last;
+   for (j = 0; j < DRD_N_THREADS; j++) {
+      if (j != tid && DRD_(IsValidDrdThreadId)(j)) {
          Segment* q;
-         list_for_each_entry_reverse(q, &DRD_(g_threadinfo)[j].sg_list,
-                                     thr_list) {
-            if (DRD_(vc_lte)(&q->vc, &p->vc))
-               break;
+         for (q = DRD_(g_threadinfo)[j].sg_last;
+              q && !DRD_(vc_lte)(&q->vc, &p->vc);
+              q = q->thr_prev) {
             if (!DRD_(vc_lte)(&p->vc, &q->vc))
                DRD_(bm_merge2_marked)(DRD_(g_conflict_set), DRD_(sg_bm)(q));
          }
index cfe04d18123df54898be4584747dc8b553f555be..27231999204efceda8278a59a15980f44e7b8235 100644 (file)
@@ -29,7 +29,6 @@
 /* Include directives. */
 
 #include "drd_basics.h"
-#include "drd_list.h"
 #include "drd_segment.h"
 #include "pub_drd_bitmap.h"
 #include "pub_tool_libcassert.h"  /* tl_assert()        */
@@ -67,7 +66,8 @@ typedef UWord PThreadId;
 /** Per-thread information managed by DRD. */
 typedef struct
 {
-   struct list_head sg_list;/**< Segment list. */
+   struct segment* sg_first;/**< Segment list. */
+   struct segment* sg_last;
    ThreadId  vg_threadid;   /**< Valgrind thread ID. */
    PThreadId pt_threadid;   /**< POSIX thread ID. */
    Addr      stack_min_min; /**< Lowest value stack pointer ever had. */
@@ -340,17 +340,12 @@ Bool DRD_(thread_address_on_any_stack)(const Addr a)
 static __inline__
 Segment* DRD_(thread_get_segment)(const DrdThreadId tid)
 {
-   struct list_head* sg_list;
-
 #ifdef ENABLE_DRD_CONSISTENCY_CHECKS
    tl_assert(0 <= (int)tid && tid < DRD_N_THREADS
              && tid != DRD_INVALID_THREADID);
+   tl_assert(DRD_(g_threadinfo)[tid].sg_last);
 #endif
-   sg_list = &DRD_(g_threadinfo)[tid].sg_list;
-#ifdef ENABLE_DRD_CONSISTENCY_CHECKS
-   tl_assert(!list_empty(sg_list));
-#endif
-   return list_last_entry(sg_list, Segment, thr_list);
+   return DRD_(g_threadinfo)[tid].sg_last;
 }
 
 /** Return a pointer to the latest segment for the running thread. */