Home | History | Annotate | Download | only in drd
      1 /*
      2   This file is part of drd, a thread error detector.
      3 
      4   Copyright (C) 2006-2017 Bart Van Assche <bvanassche (at) acm.org>.
      5 
      6   This program is free software; you can redistribute it and/or
      7   modify it under the terms of the GNU General Public License as
      8   published by the Free Software Foundation; either version 2 of the
      9   License, or (at your option) any later version.
     10 
     11   This program is distributed in the hope that it will be useful, but
     12   WITHOUT ANY WARRANTY; without even the implied warranty of
     13   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
     14   General Public License for more details.
     15 
     16   You should have received a copy of the GNU General Public License
     17   along with this program; if not, write to the Free Software
     18   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
     19   02111-1307, USA.
     20 
     21   The GNU General Public License is contained in the file COPYING.
     22 */
     23 
     24 
     25 #ifndef __DRD_THREAD_BITMAP_H
     26 #define __DRD_THREAD_BITMAP_H
     27 
     28 
     29 #include "drd_bitmap.h"
     30 #include "drd_thread.h" /* running_thread_get_segment() */
     31 #include "pub_drd_bitmap.h"
     32 
     33 
     34 static __inline__
     35 Bool bm_access_load_1_triggers_conflict(const Addr a1)
     36 {
     37    DRD_(bm_access_load_1)(DRD_(sg_bm)(DRD_(running_thread_get_segment)()), a1);
     38    return DRD_(bm_load_1_has_conflict_with)(DRD_(thread_get_conflict_set)(),
     39                                             a1);
     40 }
     41 
     42 static __inline__
     43 Bool bm_access_load_2_triggers_conflict(const Addr a1)
     44 {
     45    if ((a1 & 1) == 0)
     46    {
     47       bm_access_aligned_load(DRD_(sg_bm)(DRD_(running_thread_get_segment)()), a1, 2);
     48       return bm_aligned_load_has_conflict_with(DRD_(thread_get_conflict_set)(),
     49                                                a1, 2);
     50    }
     51    else
     52    {
     53       DRD_(bm_access_range)(DRD_(sg_bm)(DRD_(running_thread_get_segment)()),
     54                             a1, a1 + 2, eLoad);
     55       return DRD_(bm_has_conflict_with)(DRD_(thread_get_conflict_set)(),
     56                                         a1, a1 + 2, eLoad);
     57    }
     58 }
     59 
     60 static __inline__
     61 Bool bm_access_load_4_triggers_conflict(const Addr a1)
     62 {
     63    if ((a1 & 3) == 0)
     64    {
     65       bm_access_aligned_load(DRD_(sg_bm)(DRD_(running_thread_get_segment)()), a1, 4);
     66       return bm_aligned_load_has_conflict_with(DRD_(thread_get_conflict_set)(),
     67                                                a1, 4);
     68    }
     69    else
     70    {
     71       DRD_(bm_access_range)(DRD_(sg_bm)(DRD_(running_thread_get_segment)()),
     72                             a1, a1 + 4, eLoad);
     73       return DRD_(bm_has_conflict_with)(DRD_(thread_get_conflict_set)(),
     74                                         a1, a1 + 4, eLoad);
     75    }
     76 }
     77 
     78 static __inline__
     79 Bool bm_access_load_8_triggers_conflict(const Addr a1)
     80 {
     81    if ((a1 & 7) == 0)
     82    {
     83       bm_access_aligned_load(DRD_(sg_bm)(DRD_(running_thread_get_segment)()), a1, 8);
     84       return bm_aligned_load_has_conflict_with(DRD_(thread_get_conflict_set)(),
     85                                                a1, 8);
     86    }
     87    else if ((a1 & 3) == 0)
     88    {
     89       bm_access_aligned_load(DRD_(sg_bm)(DRD_(running_thread_get_segment)()), a1 + 0, 4);
     90       bm_access_aligned_load(DRD_(sg_bm)(DRD_(running_thread_get_segment)()), a1 + 4, 4);
     91       return DRD_(bm_has_conflict_with)(DRD_(thread_get_conflict_set)(),
     92                                         a1, a1 + 8, eLoad);
     93    }
     94    else
     95    {
     96       DRD_(bm_access_range)(DRD_(sg_bm)(DRD_(running_thread_get_segment)()),
     97                             a1, a1 + 8, eLoad);
     98       return DRD_(bm_has_conflict_with)(DRD_(thread_get_conflict_set)(),
     99                                         a1, a1 + 8, eLoad);
    100    }
    101 }
    102 
    103 static __inline__
    104 Bool bm_access_load_triggers_conflict(const Addr a1, const Addr a2)
    105 {
    106    DRD_(bm_access_range_load)(DRD_(sg_bm)(DRD_(running_thread_get_segment)()), a1, a2);
    107    return DRD_(bm_load_has_conflict_with)(DRD_(thread_get_conflict_set)(),
    108                                           a1, a2);
    109 }
    110 
    111 static __inline__
    112 Bool bm_access_store_1_triggers_conflict(const Addr a1)
    113 {
    114    DRD_(bm_access_store_1)(DRD_(sg_bm)(DRD_(running_thread_get_segment)()), a1);
    115    return DRD_(bm_store_1_has_conflict_with)(DRD_(thread_get_conflict_set)(),
    116                                              a1);
    117 }
    118 
    119 static __inline__
    120 Bool bm_access_store_2_triggers_conflict(const Addr a1)
    121 {
    122    if ((a1 & 1) == 0)
    123    {
    124       bm_access_aligned_store(DRD_(sg_bm)(DRD_(running_thread_get_segment)()), a1, 2);
    125       return bm_aligned_store_has_conflict_with(DRD_(thread_get_conflict_set)(),
    126                                                 a1, 2);
    127    }
    128    else
    129    {
    130       DRD_(bm_access_range)(DRD_(sg_bm)(DRD_(running_thread_get_segment)()),
    131                             a1, a1 + 2, eStore);
    132       return DRD_(bm_has_conflict_with)(DRD_(thread_get_conflict_set)(),
    133                                         a1, a1 + 2, eStore);
    134    }
    135 }
    136 
    137 static __inline__
    138 Bool bm_access_store_4_triggers_conflict(const Addr a1)
    139 {
    140    if ((a1 & 3) == 0)
    141    {
    142       bm_access_aligned_store(DRD_(sg_bm)(DRD_(running_thread_get_segment)()), a1, 4);
    143       return bm_aligned_store_has_conflict_with(DRD_(thread_get_conflict_set)(),
    144                                                 a1, 4);
    145    }
    146    else
    147    {
    148       DRD_(bm_access_range)(DRD_(sg_bm)(DRD_(running_thread_get_segment)()),
    149                             a1, a1 + 4, eStore);
    150       return DRD_(bm_has_conflict_with)(DRD_(thread_get_conflict_set)(),
    151                                         a1, a1 + 4, eStore);
    152    }
    153 }
    154 
    155 static __inline__
    156 Bool bm_access_store_8_triggers_conflict(const Addr a1)
    157 {
    158    if ((a1 & 7) == 0)
    159    {
    160       bm_access_aligned_store(DRD_(sg_bm)(DRD_(running_thread_get_segment)()), a1, 8);
    161       return bm_aligned_store_has_conflict_with(DRD_(thread_get_conflict_set)(),
    162                                                 a1, 8);
    163    }
    164    else if ((a1 & 3) == 0)
    165    {
    166       bm_access_aligned_store(DRD_(sg_bm)(DRD_(running_thread_get_segment)()),
    167                               a1 + 0, 4);
    168       bm_access_aligned_store(DRD_(sg_bm)(DRD_(running_thread_get_segment)()),
    169                               a1 + 4, 4);
    170       return DRD_(bm_has_conflict_with)(DRD_(thread_get_conflict_set)(),
    171                                         a1, a1 + 8, eStore);
    172    }
    173    else
    174    {
    175       DRD_(bm_access_range)(DRD_(sg_bm)(DRD_(running_thread_get_segment)()),
    176                             a1, a1 + 8, eStore);
    177       return DRD_(bm_has_conflict_with)(DRD_(thread_get_conflict_set)(),
    178                                         a1, a1 + 8, eStore);
    179    }
    180 }
    181 
    182 static __inline__
    183 Bool bm_access_store_triggers_conflict(const Addr a1, const Addr a2)
    184 {
    185    DRD_(bm_access_range_store)(DRD_(sg_bm)(DRD_(running_thread_get_segment)()), a1, a2);
    186    return DRD_(bm_store_has_conflict_with)(DRD_(thread_get_conflict_set)(),
    187                                            a1, a2);
    188 }
    189 
    190 #endif // __DRD_THREAD_BITMAP_H
    191