Debugging Techniques in Constructive Computer Architecture

undefined
 
Constructive Computer Architecture
 
Tutorial 2
Debugging BSV and
Typeclasses.
 
 
 
9/24/2024
 
http://csg.csail.mit.edu/6.175
 
T01-1
 
Outline
 
Debugging BSV code
Typeclasses and functional style.
 
And maybe conflict-Freeness
 
9/24/2024
 
L03-2
 
http://csg.csail.mit.edu/6.175
Software Debugging
Print Statements
 
See a bug, not sure what causes it
Add print statements
Recompile
Run
Still see bug, but you have narrowed it down
to a smaller portion of code
Repeat with more print statements…
Find bug, fix bug, and remove print
statements
9/24/2024
L03-3
http://csg.csail.mit.edu/6.175
 
BSV Debugging
Display Statements
 
See a bug, not sure what causes it
Add display statements
Recompile
Run
Still see bug, but you have narrowed it down
to a smaller portion of code
Repeat with more display statements…
Find bug, fix bug, and remove display
statements
 
9/24/2024
 
L03-4
 
http://csg.csail.mit.edu/6.175
 
BSV Display Statements
 
The $display() command is an
action
 that prints statements to
the simulation console
Examples:
$display(“Hello World!”);
$display(“The value of x is %d”, x);
$display(“The value of y is “,
fshow(y));
 
9/24/2024
 
L03-5
 
http://csg.csail.mit.edu/6.175
Ways to Display Values
Format Specifiers
 
%d – decimal
%b – binary
%o – octal
%h – hexadecimal
%0d, %0b, %0o, %0h
Show value without extra whitespace
padding
9/24/2024
L03-6
http://csg.csail.mit.edu/6.175
Ways to Display Values
fshow
 
fshow is a function in the FShow typeclass
It can be derived for enumerations and
structures
Example:
 
typedef emun
 {Red, Blue} Colors 
deriving
(FShow);
Color c = Red;
$display
(“c is “, fshow(c));
9/24/2024
L03-7
http://csg.csail.mit.edu/6.175
 
Prints “c is Red”
 
Two big families of bugs
 
 Functional bug
E.g “a*d+b*c” instead of “a*d-b*c”
 Liveness bug
Scheduling issue
 
9/24/2024
 
L03-8
 
http://csg.csail.mit.edu/6.175
 
Functional bug
 
module mkTest(Det);
   method ActionValue#(Data) det(Data a,Data
b,Data c,Data c);
 
let res = a*d + b*c;
 
$display(“%d %d %d %d %d”, a,b,c,d, res);
 
return res;
   endmethod
Endmodule
 
9/24/2024
 
L03-9
 
http://csg.csail.mit.edu/6.175
 
Method for debugging
liveness
 
Add $display(“Name rule”) in
every rule and method of your
design.
You get to see what is firing.
There are probably not firing when they
should:
Think about the implicit and explicit guards
that would prevent a rule/method to fire.
If thinking is not enough?
 
9/24/2024
 
L03-10
 
http://csg.csail.mit.edu/6.175
 
Method for debugging
liveness
 
If thinking is not enough:
You can add an extra rules that just
print the explicit guards of all the
methods
 
9/24/2024
 
L03-11
 
http://csg.csail.mit.edu/6.175
 
Method for debugging
liveness
 
module mkTest(Det);
[…]
   rule problematic (complexExpression);
       $display(“Problematic fire”);
        […] //Other stuff (methods called etc…)
   endrule
endmodule
 
9/24/2024
 
L03-12
 
http://csg.csail.mit.edu/6.175
 
Method for debugging
liveness
 
module mkTest(Det);
[…]
   rule debugRule;
 
$display(“Guard is %b”,complexExpression);
   endrule;
   rule problematic (complexExpression);
       $display(“Problematic fire”);
   endrule
endmodule
 
9/24/2024
 
L03-13
 
http://csg.csail.mit.edu/6.175
 
Liveness
 
If the guard is false when you
expected it to be true:
Well you just found your problem
If the guard is true:
Check the implicit guards with the
same technique:
 
9/24/2024
 
L03-14
 
http://csg.csail.mit.edu/6.175
 
Method for debugging
liveness
 
module mkTest(Det);
[…]
   rule debugRule;
 
$display(“Guard is %b”,complexExpression);
   endrule;
   rule problematic (complexExpression);
       $display(“Problematic fire”);
       […]
       submodule1.meth1();
   endrule
endmodule
 
9/24/2024
 
L03-15
 
http://csg.csail.mit.edu/6.175
 
Method for debugging
liveness
 
module mkSubmodule1(Submodule1);
 
rule debugRule;
 
$display(“Guard is %b”,complexExpression);
      endrule;
      method Action meth1()if(complexExpression);
      […]
      endmethod
endmodule
 
9/24/2024
 
L03-16
 
http://csg.csail.mit.edu/6.175
 
Method for debugging
liveness
 
Repeat until you are confident that
the problem does not come from a
false guard:
Reminder: registers can always be
written and read so they don’t pose
problem for guards.
Usually you don’t have to do that
recursively because you already know
that your submodules are corrects.
 
9/24/2024
 
L03-17
 
http://csg.csail.mit.edu/6.175
 
All my guards are good,
still it does not work
 
 
9/24/2024
 
L03-18
 
http://csg.csail.mit.edu/6.175
 
All my guards are good,
still it does not work
 
Scheduling problem: an other rule
is preventing the one I want to
fire.
 
9/24/2024
 
L03-19
 
http://csg.csail.mit.edu/6.175
 
All my guards are good,
still it does not work
 
module mkTest();
[…]
 
rule r1;
          […]
 
    myfifo.enq(1);
      endrule
 
rule r2;
          […]
 
    myfifo.enq(2);
 
endrule
endmodule
 
9/24/2024
 
L03-20
 
http://csg.csail.mit.edu/6.175
Final note: be careful
module mkTest();
[…]
 
rule r1;
          […]
          x <= y;
 
endrule
 
rule r2;
          […]
          $display(“x is” ,x);
 
    y <=2;
 
endrule
endmodule
9/24/2024
L03-21
http://csg.csail.mit.edu/6.175
 
Don’t display value within a
rule that are not already read
by that rule
undefined
 
Typeclasses
 
 
9/24/2024
 
L03-22
 
http://csg.csail.mit.edu/6.175
Typeclasses
 
A typeclass is a group of functions that can be defined
on multiple types
Examples:
 
typeclass
 Arith#(type t);
    
function
 t \+(t x, t y);
    
function
 t \-(t x, t y);
    // ... more arithmetic functions
endtypeclass
 
typeclass
 Literal#(type t);
    
function
 t fromInteger(Integer x);
    
function
 Bool inLiteralRange(t target,
                            Integer literal);
endtypeclass
9/24/2024
http://csg.csail.mit.edu/6.175
T02-23
 
Instances
 
Types are added to typeclasses by creating
instances of that typeclass
 
instance
 Arith#(Bit#(n));
    
function
 Bit#(n) \+(Bit#(n) a, Bit#(n) b);
        
return
 truncate(csa(a,b));
    
endfunction
    function 
Bit#(n)
 
\-(Bit#(n) a, Bit#(n) b);
        return
 truncate(csa(a, -b));
    
endfunction
    
// more functions...
endinstance
 
9/24/2024
 
http://csg.csail.mit.edu/6.175
 
T02-24
 
Provisos
 
Provisos restrict type variables used in
functions and modules through typeclasses
If a function or module doesn’t have the
necessary provisos, the compiler will throw an
error along with the required provisos to add
The add1 function with the proper provisos is
shown below:
 
9/24/2024
 
http://csg.csail.mit.edu/6.175
 
function
 t add1(t x) 
provisos
(Arith#(t), Literal#(t));
    
return
 x + 1;
endfunction
 
T02-25
Special Typeclasses for
Provisos
 
There are some Typeclasses defined on
numeric types that are only for provisos:
Add#( n1, n2, n3 )
asserts that n1 + n2 = n3
Mul#( n1, n2, n3 )
asserts that n1 * n2 = n3
An inequality constraint can be constructed
using free type variables since all type
variables are non-negative
Add#( n1, _a, n2 )
asserts that n1 + _a = n2
equivalent to n1 <= n2 if _a is a free type variable
9/24/2024
http://csg.csail.mit.edu/6.175
T02-26
The Bits Typeclasses
 
The Bits typeclass is defined below
 
typeclass
 Bits#(type t, numeric type tSz);
    
function
 Bit#(tSz) pack(t x);
    
function
 t unpack(Bit#(tSz) x);
endtypeclass
 
This typeclass contains functions to go
between t and Bit#(tSz)
mkReg(Reg#(t)) requires t to have an
instance of Bits#(t, tSz)
9/24/2024
http://csg.csail.mit.edu/6.175
T02-27
 
Custom Bits#(a,n) instance
 
typedef
 
enum
 { red, green, blue } Color 
deriving
 (Eq); // not bits
 
instance
 Bits#(Color, 2);
    
function
 Bit#(2) pack(a x);
        
if
( x == red ) 
return
 0;
        
else if
( x == green ) 
return
 1;
        
else
 return 2;
    
endfunction
    
function
 Color unpack(Bit#(2) y)
        
if
( x == 0 ) 
return
 red;
        
else if
( x == 1 ) 
return
 green;
        
else return 
blue;
    
endfunction
endinstance
 
9/24/2024
 
http://csg.csail.mit.edu/6.175
 
T02-28
Typeclasses Summary
 
Typeclasses allow polymorphism across
types
Provisos restrict modules type parameters
to specified type classes
Typeclass Examples:
Eq: contains == and !=
Ord: contains <, >, <=, >=, etc.
Bits: contains pack and unpack
Arith: contains arithmetic functions
Bitwise: contains bitwise logic
FShow: contains the fshow function to
format values nicely as strings
9/24/2024
http://csg.csail.mit.edu/6.175
T02-29
undefined
 
Conflict-freeness.
 
Or be careful for what you
wish
 
9/24/2024
 
L03-30
 
http://csg.csail.mit.edu/6.175
Up/Down Counter
Conflicting design
module
 mkCounter( Counter );
    Reg#(Bit#(8)) count <- mkReg(0);
    
method
 Bit#(8) read;
        
return
 count;
    
endmethod
    
method
 Action increment;
        count <= count + 1;
    
endmethod
    
method
 Action decrement;
        count <= count – 1;
    
endmethod
endmodule
9/24/2024
http://csg.csail.mit.edu/6.175
T02-31
 
Concurrent Design
A general technique
 
9/24/2024
 
http://csg.csail.mit.edu/6.175
 
Replace conflicting registers with EHRs
Choose an order for the methods
Assign ports of the EHR sequentially to
the methods depending on the desired
schedule
 
Method described in paper that
introduces EHRs: “The Ephemeral History
Register: Flexible Scheduling for Rule-
Based Designs” by Daniel Rosenband
 
T02-32
Up/Down Counter
Concurrent design: read < inc < dec
module
 mkCounter( Counter );
    
Ehr#(3, Bit#(8)) count <- mkEhr(0);
    
method
 Bit#(8) read;
        
return
 count[ ];
    
endmethod
    
method
 Action increment;
        count[ ] <= count[ ] + 1;
    
endmethod
    
method
 Action decrement;
        count[ ] <= count[ ] – 1;
    
endmethod
endmodule
9/24/2024
http://csg.csail.mit.edu/6.175
 
 
 
 
 
                     
0
 
 
              1           1
 
 
              2           2
T02-33
 
Up/Down Counter
Concurrent design: read < inc < dec
 
module
 mkCounter( Counter );
    Ehr#(
2
, Bit#(8)) count <- mkEhr(0);
 
    
method
 Bit#(8) read;
        
return
 count[
0
];
    
endmethod
    
method
 Action increment;
        count[
0
] <= count[
0
] + 1;
    
endmethod
    
method
 Action decrement;
        count[
1
] <= count[
1
] – 1;
    
endmethod
endmodule
 
9/24/2024
 
http://csg.csail.mit.edu/6.175
 
This design only needs
2 EHR ports now
 
T02-34
 
Conflict-Free Design
A more or less general technique
 
9/24/2024
 
http://csg.csail.mit.edu/6.175
 
Replace conflicting Action and ActionValue
methods with writes to EHRs representing method
call requests
If there are no arguments for the method call, the
EHR should hold a value of 
Bool
If there are arguments for the method call, the EHR
should hold a value of
Maybe#(Tuple2#(TypeArg1,TypeArg2))
 or
something similar
Create a canonicalize rule to handle all of the
method call requests at the same time
Reset all the method call requests to 
False
 or
tagged invalid
 at the end of the canonicalize rule
Guard method calls with method call requests
If there is an outstanding request, don’t allow a
second one to happen
 
T02-35
 
Up/Down Counter
Conflict-Free design – methods
 
module
 mkCounter( Counter );
    Reg#(Bit#(8)) count <- mkReg(0);
    Ehr#(2, Bool) inc_req <- mkEhr(False);
    Ehr#(2, Bool) dec_req <- mkEhr(False);
    // canonicalize rule on next slide
    method
 Bit#(8) read = count;
    method
 Action increment 
if(!inc_req[0])
;
        
inc_req[0] <= True;
    endmethod
    method
 Action decrement 
if(!dec_req[0])
;
        dec_req[0] <= True;
    endmethod
endmodule
 
9/24/2024
 
http://csg.csail.mit.edu/6.175
 
T02-36
 
Up/Down Counter
Conflict-Free design – canonicalize rule
 
module
 mkCounter( Counter );
    // Reg and EHR definitions on previous slide
    
rule
 canonicalize;
        
if
(
inc_req[1] && !dec_req[1]
) 
begin
            count <= count+1;
        
end else if
(
dec_req[1] && !inc_req[1]
) 
begin
            count <= count-1;
        
end
        
inc_req[1] <= False;
        dec_req[1] <= False;
    
endrule
    // methods on previous slide
endmodule
 
9/24/2024
 
http://csg.csail.mit.edu/6.175
 
T02-37
Well it’s morally broken
module
 mkTest();
   Reg#(Bit#(8)) r <- mkReg(0);
 
let myCounter <- mkCounter();
 
rule r1;
 
    $display(“r”);
       myCounter.increment();
   endrule
 
rule r2;
 
     r <= myCounter.read();
   endrule
   rule display;
       $display( r);
   endrule
endmodule
9/24/2024
L03-38
http://csg.csail.mit.edu/6.175
 
We can schedule read
after increment, but read
will always see old Values
because it is scheduled
before canonicalize.
 
Fix: but read< {inc,dec}.
 
module
 mkCounter( Counter );
    Reg#(Bit#(8)) count <- mkReg(0);
    Ehr#(2, Bool) inc_req <- mkEhr(False);
    Ehr#(2, Bool) dec_req <- mkEhr(False);
    // canonicalize rule on next slide
    method
 Bit#(8) read 
if(!inc_req[0] &&
                           !dec_req[0]) 
= count;
    method
 Action increment 
if(!inc_req[0])
;
        
inc_req[0] <= True;
    endmethod
    method
 Action decrement 
if(!dec_req[0])
;
        dec_req[0] <= True;
    endmethod
 
 
9/24/2024
 
L03-39
 
http://csg.csail.mit.edu/6.175
 
Interesting questions
 
Is it possible to write a CF counter?
 
Is it possible to give an algorithm
that will always make a module
conflict free, but a non broken one.
 
9/24/2024
 
L03-40
 
http://csg.csail.mit.edu/6.175
Slide Note
Embed
Share

Explore debugging methods in constructive computer architecture tutorial sessions, focusing on debugging BSV code, typeclasses, and functional style. Learn how to use print and display statements effectively, handle conflicts, and identify and fix common bugs. Dive into the significance of ways to display values, format specifiers, and the FShow typeclass for efficient debugging practices.

  • Debugging Techniques
  • Computer Architecture
  • BSV
  • Typeclasses
  • Bug Fixing

Uploaded on Sep 24, 2024 | 0 Views


Download Presentation

Please find below an Image/Link to download the presentation.

The content on the website is provided AS IS for your information and personal use only. It may not be sold, licensed, or shared on other websites without obtaining consent from the author. Download presentation by click this link. If you encounter any issues during the download, it is possible that the publisher has removed the file from their server.

E N D

Presentation Transcript


  1. Constructive Computer Architecture Tutorial 2 Debugging BSV and Typeclasses. 9/24/2024 http://csg.csail.mit.edu/6.175 T01-1

  2. Outline Debugging BSV code Typeclasses and functional style. And maybe conflict-Freeness 9/24/2024 http://csg.csail.mit.edu/6.175 L03-2

  3. Software Debugging Print Statements See a bug, not sure what causes it Add print statements Recompile Run Still see bug, but you have narrowed it down to a smaller portion of code Repeat with more print statements Find bug, fix bug, and remove print statements 9/24/2024 http://csg.csail.mit.edu/6.175 L03-3

  4. BSV Debugging Display Statements See a bug, not sure what causes it Add display statements Recompile Run Still see bug, but you have narrowed it down to a smaller portion of code Repeat with more display statements Find bug, fix bug, and remove display statements 9/24/2024 http://csg.csail.mit.edu/6.175 L03-4

  5. BSV Display Statements The $display() command is an action that prints statements to the simulation console Examples: $display( Hello World! ); $display( The value of x is %d , x); $display( The value of y is , fshow(y)); 9/24/2024 http://csg.csail.mit.edu/6.175 L03-5

  6. Ways to Display Values Format Specifiers %d decimal %b binary %o octal %h hexadecimal %0d, %0b, %0o, %0h Show value without extra whitespace padding 9/24/2024 http://csg.csail.mit.edu/6.175 L03-6

  7. Ways to Display Values fshow fshow is a function in the FShow typeclass It can be derived for enumerations and structures Example: typedef emun {Red, Blue} Colors deriving(FShow); Color c = Red; $display( c is , fshow(c)); Prints c is Red 9/24/2024 http://csg.csail.mit.edu/6.175 L03-7

  8. Two big families of bugs Functional bug E.g a*d+b*c instead of a*d-b*c Liveness bug Scheduling issue 9/24/2024 http://csg.csail.mit.edu/6.175 L03-8

  9. Functional bug module mkTest(Det); method ActionValue#(Data) det(Data a,Data b,Data c,Data c); let res = a*d + b*c; $display( %d %d %d %d %d , a,b,c,d, res); return res; endmethod Endmodule 9/24/2024 http://csg.csail.mit.edu/6.175 L03-9

  10. Method for debugging liveness Add $display( Name rule ) in every rule and method of your design. You get to see what is firing. There are probably not firing when they should: Think about the implicit and explicit guards that would prevent a rule/method to fire. If thinking is not enough? 9/24/2024 http://csg.csail.mit.edu/6.175 L03-10

  11. Method for debugging liveness If thinking is not enough: You can add an extra rules that just print the explicit guards of all the methods 9/24/2024 http://csg.csail.mit.edu/6.175 L03-11

  12. Method for debugging liveness module mkTest(Det); [ ] rule problematic (complexExpression); $display( Problematic fire ); [ ] //Other stuff (methods called etc ) endrule endmodule 9/24/2024 http://csg.csail.mit.edu/6.175 L03-12

  13. Method for debugging liveness module mkTest(Det); [ ] rule debugRule; $display( Guard is %b ,complexExpression); endrule; rule problematic (complexExpression); $display( Problematic fire ); endrule endmodule 9/24/2024 http://csg.csail.mit.edu/6.175 L03-13

  14. Liveness If the guard is false when you expected it to be true: Well you just found your problem If the guard is true: Check the implicit guards with the same technique: 9/24/2024 http://csg.csail.mit.edu/6.175 L03-14

  15. Method for debugging liveness module mkTest(Det); [ ] rule debugRule; $display( Guard is %b ,complexExpression); endrule; rule problematic (complexExpression); $display( Problematic fire ); [ ] submodule1.meth1(); endrule endmodule 9/24/2024 http://csg.csail.mit.edu/6.175 L03-15

  16. Method for debugging liveness module mkSubmodule1(Submodule1); rule debugRule; $display( Guard is %b ,complexExpression); endrule; method Action meth1()if(complexExpression); [ ] endmethod endmodule 9/24/2024 http://csg.csail.mit.edu/6.175 L03-16

  17. Method for debugging liveness Repeat until you are confident that the problem does not come from a false guard: Reminder: registers can always be written and read so they don t pose problem for guards. Usually you don t have to do that recursively because you already know that your submodules are corrects. 9/24/2024 http://csg.csail.mit.edu/6.175 L03-17

  18. All my guards are good, still it does not work 9/24/2024 http://csg.csail.mit.edu/6.175 L03-18

  19. All my guards are good, still it does not work Scheduling problem: an other rule is preventing the one I want to fire. 9/24/2024 http://csg.csail.mit.edu/6.175 L03-19

  20. All my guards are good, still it does not work module mkTest(); [ ] rule r1; [ ] myfifo.enq(1); endrule rule r2; [ ] myfifo.enq(2); endrule endmodule 9/24/2024 http://csg.csail.mit.edu/6.175 L03-20

  21. Final note: be careful module mkTest(); [ ] rule r1; [ ] x <= y; endrule rule r2; [ ] $display( x is ,x); y <=2; endrule endmodule Don t display value within a rule that are not already read by that rule 9/24/2024 http://csg.csail.mit.edu/6.175 L03-21

  22. Typeclasses 9/24/2024 http://csg.csail.mit.edu/6.175 L03-22

  23. Typeclasses A typeclass is a group of functions that can be defined on multiple types Examples: typeclass Arith#(type t); function t \+(t x, t y); function t \-(t x, t y); // ... more arithmetic functions endtypeclass typeclass Literal#(type t); function t fromInteger(Integer x); function Bool inLiteralRange(t target, Integer literal); endtypeclass 9/24/2024 http://csg.csail.mit.edu/6.175 T02-23

  24. Instances Types are added to typeclasses by creating instances of that typeclass instance Arith#(Bit#(n)); function Bit#(n) \+(Bit#(n) a, Bit#(n) b); return truncate(csa(a,b)); endfunction function Bit#(n)\-(Bit#(n) a, Bit#(n) b); return truncate(csa(a, -b)); endfunction // more functions... endinstance 9/24/2024 http://csg.csail.mit.edu/6.175 T02-24

  25. Provisos Provisos restrict type variables used in functions and modules through typeclasses If a function or module doesn t have the necessary provisos, the compiler will throw an error along with the required provisos to add The add1 function with the proper provisos is shown below: function t add1(t x) provisos(Arith#(t), Literal#(t)); return x + 1; endfunction 9/24/2024 http://csg.csail.mit.edu/6.175 T02-25

  26. Special Typeclasses for Provisos There are some Typeclasses defined on numeric types that are only for provisos: Add#( n1, n2, n3 ) asserts that n1 + n2 = n3 Mul#( n1, n2, n3 ) asserts that n1 * n2 = n3 An inequality constraint can be constructed using free type variables since all type variables are non-negative Add#( n1, _a, n2 ) asserts that n1 + _a = n2 equivalent to n1 <= n2 if _a is a free type variable 9/24/2024 http://csg.csail.mit.edu/6.175 T02-26

  27. The Bits Typeclasses The Bits typeclass is defined below typeclass Bits#(type t, numeric type tSz); function Bit#(tSz) pack(t x); function t unpack(Bit#(tSz) x); endtypeclass This typeclass contains functions to go between t and Bit#(tSz) mkReg(Reg#(t)) requires t to have an instance of Bits#(t, tSz) 9/24/2024 http://csg.csail.mit.edu/6.175 T02-27

  28. Custom Bits#(a,n) instance typedefenum { red, green, blue } Color deriving (Eq); // not bits instance Bits#(Color, 2); function Bit#(2) pack(a x); if( x == red ) return 0; else if( x == green ) return 1; else return 2; endfunction function Color unpack(Bit#(2) y) if( x == 0 ) return red; else if( x == 1 ) return green; else return blue; endfunction endinstance 9/24/2024 http://csg.csail.mit.edu/6.175 T02-28

  29. Typeclasses Summary Typeclasses allow polymorphism across types Provisos restrict modules type parameters to specified type classes Typeclass Examples: Eq: contains == and != Ord: contains <, >, <=, >=, etc. Bits: contains pack and unpack Arith: contains arithmetic functions Bitwise: contains bitwise logic FShow: contains the fshow function to format values nicely as strings 9/24/2024 http://csg.csail.mit.edu/6.175 T02-29

  30. Conflict-freeness. Or be careful for what you wish 9/24/2024 http://csg.csail.mit.edu/6.175 L03-30

  31. Up/Down Counter Conflicting design module mkCounter( Counter ); Reg#(Bit#(8)) count <- mkReg(0); method Bit#(8) read; return count; endmethod method Action increment; count <= count + 1; endmethod method Action decrement; count <= count 1; endmethod endmodule Can t fire in the same cycle 9/24/2024 http://csg.csail.mit.edu/6.175 T02-31

  32. Concurrent Design A general technique Replace conflicting registers with EHRs Choose an order for the methods Assign ports of the EHR sequentially to the methods depending on the desired schedule Method described in paper that introduces EHRs: The Ephemeral History Register: Flexible Scheduling for Rule- Based Designs by Daniel Rosenband 9/24/2024 http://csg.csail.mit.edu/6.175 T02-32

  33. Up/Down Counter Concurrent design: read < inc < dec module mkCounter( Counter ); Ehr#(3, Bit#(8)) count <- mkEhr(0); method Bit#(8) read; return count[ ]; endmethod method Action increment; count[ ] <= count[ ] + 1; endmethod method Action decrement; count[ ] <= count[ ] 1; endmethod endmodule 0 These two methods can use the same port 1 1 2 2 9/24/2024 http://csg.csail.mit.edu/6.175 T02-33

  34. Up/Down Counter Concurrent design: read < inc < dec module mkCounter( Counter ); Ehr#(2, Bit#(8)) count <- mkEhr(0); This design only needs 2 EHR ports now method Bit#(8) read; return count[0]; endmethod method Action increment; count[0] <= count[0] + 1; endmethod method Action decrement; count[1] <= count[1] 1; endmethod endmodule 9/24/2024 http://csg.csail.mit.edu/6.175 T02-34

  35. Conflict-Free Design A more or less general technique Replace conflicting Action and ActionValue methods with writes to EHRs representing method call requests If there are no arguments for the method call, the EHR should hold a value of Bool If there are arguments for the method call, the EHR should hold a value of Maybe#(Tuple2#(TypeArg1,TypeArg2)) or something similar Create a canonicalize rule to handle all of the method call requests at the same time Reset all the method call requests to False or tagged invalid at the end of the canonicalize rule Guard method calls with method call requests If there is an outstanding request, don t allow a second one to happen 9/24/2024 http://csg.csail.mit.edu/6.175 T02-35

  36. Up/Down Counter Conflict-Free design methods module mkCounter( Counter ); Reg#(Bit#(8)) count <- mkReg(0); Ehr#(2, Bool) inc_req <- mkEhr(False); Ehr#(2, Bool) dec_req <- mkEhr(False); // canonicalize rule on next slide method Bit#(8) read = count; method Action increment if(!inc_req[0]); inc_req[0] <= True; endmethod method Action decrement if(!dec_req[0]); dec_req[0] <= True; endmethod endmodule 9/24/2024 http://csg.csail.mit.edu/6.175 T02-36

  37. Up/Down Counter Conflict-Free design canonicalize rule module mkCounter( Counter ); // Reg and EHR definitions on previous slide rule canonicalize; if(inc_req[1] && !dec_req[1]) begin count <= count+1; end else if(dec_req[1] && !inc_req[1]) begin count <= count-1; end inc_req[1] <= False; dec_req[1] <= False; endrule // methods on previous slide endmodule 9/24/2024 http://csg.csail.mit.edu/6.175 T02-37

  38. Well its morally broken module mkTest(); Reg#(Bit#(8)) r <- mkReg(0); let myCounter <- mkCounter(); rule r1; $display( r ); myCounter.increment(); endrule rule r2; r <= myCounter.read(); endrule rule display; $display( r); endrule endmodule We can schedule read after increment, but read will always see old Values because it is scheduled before canonicalize. 9/24/2024 http://csg.csail.mit.edu/6.175 L03-38

  39. Fix: but read< {inc,dec}. module mkCounter( Counter ); Reg#(Bit#(8)) count <- mkReg(0); Ehr#(2, Bool) inc_req <- mkEhr(False); Ehr#(2, Bool) dec_req <- mkEhr(False); // canonicalize rule on next slide method Bit#(8) read if(!inc_req[0] && !dec_req[0]) = count; method Action increment if(!inc_req[0]); inc_req[0] <= True; endmethod method Action decrement if(!dec_req[0]); dec_req[0] <= True; endmethod http://csg.csail.mit.edu/6.175 9/24/2024 L03-39

  40. Interesting questions Is it possible to write a CF counter? Is it possible to give an algorithm that will always make a module conflict free, but a non broken one. 9/24/2024 http://csg.csail.mit.edu/6.175 L03-40

More Related Content

giItT1WQy@!-/#giItT1WQy@!-/#giItT1WQy@!-/#giItT1WQy@!-/#giItT1WQy@!-/#giItT1WQy@!-/#