# Matching a signal against a bitvector

**URL:** <https://discourse.myhdl.org/t/matching-a-signal-against-a-bitvector/274>\
**Category:** Enhancement Request\
**Created:** [May 30, 2018, 7:19pm UTC](https://discourse.myhdl.org/t/matching-a-signal-against-a-bitvector/274 "2018-05-30T19:19:47Z")\
**Posts on this page:** 1\
**Showing post:** 8

<div class="post-metadata">

**Author:** ![DrPi](https://yyz2.discourse-cdn.com/flex030/user_avatar/discourse.myhdl.org/drpi/32/36_2.png) [@DrPi](https://discourse.myhdl.org/u/DrPi)\
**Post date:** [June 29, 2018, 8:43am UTC](https://discourse.myhdl.org/t/matching-a-signal-against-a-bitvector/274/8 "2018-06-29T08:43:14Z")

</div>

@theller  
Here is a block that does what you want :

```python
class MatchPattern():
    def __init__ (self, pattern="----"):
        self.pattern = pattern
    
        self.hdl = self.hdl1
        
        
    @block
    def hdl1(self, 
             
            i_Clk,
 
            i_DataEn,
            i_Data,
             
            o_Match) :
         
        assert len(i_Data) == len(self.pattern)
         
        data_length = len(i_Data)
        
        xor_init = 0
        and_init = 0
        for i,c in enumerate(reversed(self.pattern)) :
            if c == '1' :
                xor_init |= 1 << i
                and_init |= 1 << i
            elif c == '0' :
                and_init |= 1 << i
            elif c == '-' :
                pass
            else :
                raise ValueError("Value should be '1', '0' or '-'")
        
        xor_vect = Signal(intbv(xor_init)[data_length:])
        xor_vect.read = True
        xor_vect.driven = True
        
        and_vect = Signal(intbv(and_init)[data_length:])
        and_vect.read = True
        and_vect.driven = True
         
        @always_seq(i_Clk.posedge, reset=None)
        def compare() :
            if i_DataEn :
                cmp = True
                for i in range(data_length) :
                    if bool((i_Data[i] ^ xor_vect[i]) & and_vect[i]) :
                        cmp = False
                o_Match.next = cmp

        return compare

```

You can use it this way :

```python
match_inst = MatchPattern("01-10--").hdl(clk, data_en, data, match)

```

During elaboration, we can do everything we want. Here, we create masking vectors.  
xor\_vect and and\_vect should be constants but we don’t have this in MyHDL for now.

Another version of the compare() function is this one :

```python
        @always_seq(i_Clk.posedge, reset=None)
        def compare() :
            if i_DataEn :
                cmp_vect = intbv(0)[data_length:]
                for i in range(data_length) :
                    cmp_vect[i] = bool((i_Data[i] ^ xor_vect[i]) & and_vect[i])
                
                if cmp_vect == 0 :
                    o_Match.next = True
                else :
                    o_Match.next = False

```

Here we create a vector which content is compared to 0 to get the result.  
I don’t know which version is best. I believe it will depend on the toolchain synthesiser.

This is not an optimised design since all bits are computed while they should not. With the following pattern “01–0--”, only 3 bits need to be computed.

This can be done in the following way :

```python
        @always_seq(i_Clk.posedge, reset=None)
        def compare() :
            if i_DataEn :
                cmp_vect = intbv(0)[nb_bits_to_cmp:]
                cmp_index = 0
                for i in range(data_length) :
                    if and_vect[i] :
                        cmp_vect[cmp_index] = bool(i_Data[i] ^ xor_vect[i])
                        cmp_index += 1
                
                if cmp_vect == 0 :
                    o_Match.next = True
                else :
                    o_Match.next = False

```

This works in simulation but I think it will not synthesise (I have not tried).

---

_[View the full topic](https://discourse.myhdl.org/t/matching-a-signal-against-a-bitvector/274)._
