/*
 * Copyright (c) 1999-2013 Mark D. Hill and David A. Wood
 * All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are
 * met: redistributions of source code must retain the above copyright
 * notice, this list of conditions and the following disclaimer;
 * redistributions in binary form must reproduce the above copyright
 * notice, this list of conditions and the following disclaimer in the
 * documentation and/or other materials provided with the distribution;
 * neither the name of the copyright holders nor the names of its
 * contributors may be used to endorse or promote products derived from
 * this software without specific prior written permission.
 *
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 */

machine(L2Cache, "MESI Directory L2 Cache CMP")
 : CacheMemory * L2cache;
   Cycles l2_request_latency := 2;
   Cycles l2_response_latency := 2;
   Cycles to_l1_latency := 1;

  // Message Queues
  // From local bank of L2 cache TO the network
  MessageBuffer * DirRequestFromL2Cache, network="To", virtual_network="0",
    ordered="false", vnet_type="request";  // this L2 bank -> Memory

  MessageBuffer * L1RequestFromL2Cache, network="To", virtual_network="2",
    ordered="false", vnet_type="request";  // this L2 bank -> a local L1

  MessageBuffer * responseFromL2Cache, network="To", virtual_network="1",
    ordered="false", vnet_type="response";  // this L2 bank -> a local L1 || Memory

  // FROM the network to this local bank of L2 cache
  MessageBuffer * unblockToL2Cache, network="From", virtual_network="2",
    ordered="false", vnet_type="unblock";  // a local L1 || Memory -> this L2 bank

  MessageBuffer * L1RequestToL2Cache, network="From", virtual_network="0",
    ordered="false", vnet_type="request";  // a local L1 -> this L2 bank

  MessageBuffer * responseToL2Cache, network="From", virtual_network="1",
    ordered="false", vnet_type="response";  // a local L1 || Memory -> this L2 bank
{
  // STATES
  state_declaration(State, desc="L2 Cache states", default="L2Cache_State_NP") {
    // Base states
    NP, AccessPermission:Invalid, desc="Not present in either cache";
    SS, AccessPermission:Read_Only, desc="L2 cache entry Shared, also present in one or more L1s";
    M, AccessPermission:Read_Write, desc="L2 cache entry Modified, not present in any L1s", format="!b";
    MT, AccessPermission:Maybe_Stale, desc="L2 cache entry Modified in a local L1, assume L2 copy stale", format="!b";

    // L2 replacement
    M_I, AccessPermission:Busy, desc="L2 cache replacing, have all acks, sent dirty data to memory, waiting for ACK from memory";
    MT_I, AccessPermission:Busy, desc="L2 cache replacing, getting data from exclusive";
    MCT_I, AccessPermission:Busy, desc="L2 cache replacing, clean in L2, getting data or ack from exclusive";
    I_I, AccessPermission:Busy, desc="L2 replacing clean data, need to inv sharers and then drop data";
    S_I, AccessPermission:Busy, desc="L2 replacing dirty data, collecting acks from L1s";

    // Transient States for fetching data from memory
    ISS, AccessPermission:Busy, desc="L2 idle, got single L1_GETS, issued memory fetch, have not seen response yet";
    IS, AccessPermission:Busy, desc="L2 idle, got L1_GET_INSTR or multiple L1_GETS, issued memory fetch, have not seen response yet";
    IM, AccessPermission:Busy, desc="L2 idle, got L1_GETX, issued memory fetch, have not seen response(s) yet";

    // Blocking states
    SS_MB, AccessPermission:Busy, desc="Blocked for L1_GETX from SS";
    MT_MB, AccessPermission:Busy, desc="Blocked for L1_GETX from MT";

    MT_IIB, AccessPermission:Busy, desc="Blocked for L1_GETS from MT, waiting for unblock and data";
    MT_IB, AccessPermission:Busy, desc="Blocked for L1_GETS from MT, got unblock, waiting for data";
    MT_SB, AccessPermission:Busy, desc="Blocked for L1_GETS from MT, got data,  waiting for unblock";

  }

  // EVENTS
  enumeration(Event, desc="L2 Cache events") {
    // L2 events

    // events initiated by the local L1s
    L1_GET_INSTR,            desc="a L1I GET INSTR request for a block maped to us";
    L1_GETS,                 desc="a L1D GETS request for a block maped to us";
    L1_GETX,                 desc="a L1D GETX request for a block maped to us";
    L1_UPGRADE,                 desc="a L1D GETX request for a block maped to us";

    L1_PUTX,                 desc="L1 replacing data";
    L1_PUTX_old,             desc="L1 replacing data, but no longer sharer";

    // events initiated by this L2
    L2_Replacement,     desc="L2 Replacement", format="!r";
    L2_Replacement_clean,     desc="L2 Replacement, but data is clean", format="!r";

    // events from memory controller
    Mem_Data,     desc="data from memory", format="!r";
    Mem_Ack,     desc="ack from memory", format="!r";

    // M->S data writeback
    WB_Data,  desc="data from L1";
    WB_Data_clean,  desc="clean data from L1";
    Ack,      desc="writeback ack";
    Ack_all,      desc="writeback ack";

    Unblock, desc="Unblock from L1 requestor";
    Exclusive_Unblock, desc="Unblock from L1 requestor";

    MEM_Inv, desc="Invalidation from directory";
  }

  // TYPES

  // CacheEntry
  structure(Entry, desc="...", interface="AbstractCacheEntry") {
    State CacheState,          desc="cache state";
    NetDest Sharers,               desc="tracks the L1 shares on-chip";
    MachineID Exclusive,          desc="Exclusive holder of block";
    DataBlock DataBlk,       desc="data for the block";
    bool Dirty, default="false", desc="data is dirty";
  }

  // TBE fields
  structure(TBE, desc="...") {
    Address Addr,            desc="Physical address for this TBE";
    State TBEState,             desc="Transient state";
    DataBlock DataBlk,          desc="Buffer for the data block";
    bool Dirty, default="false", desc="Data is Dirty";

    NetDest L1_GetS_IDs,            desc="Set of the internal processors that want the block in shared state";
    MachineID L1_GetX_ID,          desc="ID of the L1 cache to forward the block to once we get a response";
    int pendingAcks,            desc="number of pending acks for invalidates during writeback";
  }

  structure(TBETable, external="yes") {
    TBE lookup(Address);
    void allocate(Address);
    void deallocate(Address);
    bool isPresent(Address);
  }

  TBETable L2_TBEs, template="<L2Cache_TBE>", constructor="m_number_of_TBEs";

  void set_cache_entry(AbstractCacheEntry a);
  void unset_cache_entry();
  void set_tbe(TBE a);
  void unset_tbe();
  void wakeUpBuffers(Address a);
  void profileMsgDelay(int virtualNetworkType, Cycles c);

  // inclusive cache, returns L2 entries only
  Entry getCacheEntry(Address addr), return_by_pointer="yes" {
    return static_cast(Entry, "pointer", L2cache[addr]);
  }

  bool isSharer(Address addr, MachineID requestor, Entry cache_entry) {
    if (is_valid(cache_entry)) {
      return cache_entry.Sharers.isElement(requestor);
    } else {
      return false;
    }
  }

  void addSharer(Address addr, MachineID requestor, Entry cache_entry) {
    assert(is_valid(cache_entry));
    DPRINTF(RubySlicc, "machineID: %s, requestor: %s, address: %s\n",
            machineID, requestor, addr);
    cache_entry.Sharers.add(requestor);
  }

  State getState(TBE tbe, Entry cache_entry, Address addr) {
    if(is_valid(tbe)) {
      return tbe.TBEState;
    } else if (is_valid(cache_entry)) {
      return cache_entry.CacheState;
    }
    return State:NP;
  }

  void setState(TBE tbe, Entry cache_entry, Address addr, State state) {
    // MUST CHANGE
    if (is_valid(tbe)) {
      tbe.TBEState := state;
    }

    if (is_valid(cache_entry)) {
      cache_entry.CacheState := state;
    }
  }

  AccessPermission getAccessPermission(Address addr) {
    TBE tbe := L2_TBEs[addr];
    if(is_valid(tbe)) {
      DPRINTF(RubySlicc, "%s\n", L2Cache_State_to_permission(tbe.TBEState));
      return L2Cache_State_to_permission(tbe.TBEState);
    }

    Entry cache_entry := getCacheEntry(addr);
    if(is_valid(cache_entry)) {
      DPRINTF(RubySlicc, "%s\n", L2Cache_State_to_permission(cache_entry.CacheState));
      return L2Cache_State_to_permission(cache_entry.CacheState);
    }

    DPRINTF(RubySlicc, "%s\n", AccessPermission:NotPresent);
    return AccessPermission:NotPresent;
  }

  DataBlock getDataBlock(Address addr), return_by_ref="yes" {
    TBE tbe := L2_TBEs[addr];
    if(is_valid(tbe)) {
        return tbe.DataBlk;
    }

    return getCacheEntry(addr).DataBlk;
  }

  void setAccessPermission(Entry cache_entry, Address addr, State state) {
    if (is_valid(cache_entry)) {
      cache_entry.changePermission(L2Cache_State_to_permission(state));
    }
  }

  Event L1Cache_request_type_to_event(CoherenceRequestType type, Address addr,
                                      MachineID requestor, Entry cache_entry) {
    if(type == CoherenceRequestType:GETS) {
      return Event:L1_GETS;
    } else if(type == CoherenceRequestType:GET_INSTR) {
      return Event:L1_GET_INSTR;
    } else if (type == CoherenceRequestType:GETX) {
      return Event:L1_GETX;
    } else if (type == CoherenceRequestType:UPGRADE) {
      if ( is_valid(cache_entry) && cache_entry.Sharers.isElement(requestor) ) {
        return Event:L1_UPGRADE;
      } else {
        return Event:L1_GETX;
      }
    } else if (type == CoherenceRequestType:PUTX) {
      if (isSharer(addr, requestor, cache_entry)) {
        return Event:L1_PUTX;
      } else {
        return Event:L1_PUTX_old;
      }
    } else {
      DPRINTF(RubySlicc, "address: %s, Request Type: %s\n", addr, type);
      error("Invalid L1 forwarded request type");
    }
  }

  int getPendingAcks(TBE tbe) {
    return tbe.pendingAcks;
  }

  bool isDirty(Entry cache_entry) {
    assert(is_valid(cache_entry));
    return cache_entry.Dirty;
  }

  // ** OUT_PORTS **

  out_port(L1RequestL2Network_out, RequestMsg, L1RequestFromL2Cache);
  out_port(DirRequestL2Network_out, RequestMsg, DirRequestFromL2Cache);
  out_port(responseL2Network_out, ResponseMsg, responseFromL2Cache);


  in_port(L1unblockNetwork_in, ResponseMsg, unblockToL2Cache, rank = 2) {
    if(L1unblockNetwork_in.isReady()) {
      peek(L1unblockNetwork_in,  ResponseMsg) {
        Entry cache_entry := getCacheEntry(in_msg.Addr);
        TBE tbe := L2_TBEs[in_msg.Addr];
        DPRINTF(RubySlicc, "Addr: %s State: %s Sender: %s Type: %s Dest: %s\n",
                in_msg.Addr, getState(tbe, cache_entry, in_msg.Addr),
                in_msg.Sender, in_msg.Type, in_msg.Destination);

        assert(in_msg.Destination.isElement(machineID));
        if (in_msg.Type == CoherenceResponseType:EXCLUSIVE_UNBLOCK) {
          trigger(Event:Exclusive_Unblock, in_msg.Addr, cache_entry, tbe);
        } else if (in_msg.Type == CoherenceResponseType:UNBLOCK) {
          trigger(Event:Unblock, in_msg.Addr, cache_entry, tbe);
        } else {
          error("unknown unblock message");
        }
      }
    }
  }

  // Response  L2 Network - response msg to this particular L2 bank
  in_port(responseL2Network_in, ResponseMsg, responseToL2Cache, rank = 1) {
    if (responseL2Network_in.isReady()) {
      peek(responseL2Network_in, ResponseMsg) {
        // test wether it's from a local L1 or an off chip source
        assert(in_msg.Destination.isElement(machineID));
        Entry cache_entry := getCacheEntry(in_msg.Addr);
        TBE tbe := L2_TBEs[in_msg.Addr];

        if(machineIDToMachineType(in_msg.Sender) == MachineType:L1Cache) {
          if(in_msg.Type == CoherenceResponseType:DATA) {
            if (in_msg.Dirty) {
              trigger(Event:WB_Data, in_msg.Addr, cache_entry, tbe);
            } else {
              trigger(Event:WB_Data_clean, in_msg.Addr, cache_entry, tbe);
            }
          } else if (in_msg.Type == CoherenceResponseType:ACK) {
            if ((getPendingAcks(tbe) - in_msg.AckCount) == 0) {
              trigger(Event:Ack_all, in_msg.Addr, cache_entry, tbe);
            } else {
              trigger(Event:Ack, in_msg.Addr, cache_entry, tbe);
            }
          } else {
            error("unknown message type");
          }

        } else { // external message
          if(in_msg.Type == CoherenceResponseType:MEMORY_DATA) {
              trigger(Event:Mem_Data, in_msg.Addr, cache_entry, tbe);
          } else if(in_msg.Type == CoherenceResponseType:MEMORY_ACK) {
              trigger(Event:Mem_Ack, in_msg.Addr, cache_entry, tbe);
          } else if(in_msg.Type == CoherenceResponseType:INV) {
              trigger(Event:MEM_Inv, in_msg.Addr, cache_entry, tbe);
          } else {
            error("unknown message type");
          }
        }
      }
    }  // if not ready, do nothing
  }

  // L1 Request
  in_port(L1RequestL2Network_in, RequestMsg, L1RequestToL2Cache, rank = 0) {
    if(L1RequestL2Network_in.isReady()) {
      peek(L1RequestL2Network_in,  RequestMsg) {
        Entry cache_entry := getCacheEntry(in_msg.Addr);
        TBE tbe := L2_TBEs[in_msg.Addr];

        DPRINTF(RubySlicc, "Addr: %s State: %s Req: %s Type: %s Dest: %s\n",
                in_msg.Addr, getState(tbe, cache_entry, in_msg.Addr),
                in_msg.Requestor, in_msg.Type, in_msg.Destination);

        assert(machineIDToMachineType(in_msg.Requestor) == MachineType:L1Cache);
        assert(in_msg.Destination.isElement(machineID));

        if (is_valid(cache_entry)) {
          // The L2 contains the block, so proceeded with handling the request
          trigger(L1Cache_request_type_to_event(in_msg.Type, in_msg.Addr,
                                                in_msg.Requestor, cache_entry),
                  in_msg.Addr, cache_entry, tbe);
        } else {
          if (L2cache.cacheAvail(in_msg.Addr)) {
            // L2 does't have the line, but we have space for it in the L2
            trigger(L1Cache_request_type_to_event(in_msg.Type, in_msg.Addr,
                                                  in_msg.Requestor, cache_entry),
                    in_msg.Addr, cache_entry, tbe);
          } else {
            // No room in the L2, so we need to make room before handling the request
            Entry L2cache_entry := getCacheEntry(L2cache.cacheProbe(in_msg.Addr));
            if (isDirty(L2cache_entry)) {
              trigger(Event:L2_Replacement, L2cache.cacheProbe(in_msg.Addr),
                      L2cache_entry, L2_TBEs[L2cache.cacheProbe(in_msg.Addr)]);
            } else {
              trigger(Event:L2_Replacement_clean, L2cache.cacheProbe(in_msg.Addr),
                      L2cache_entry, L2_TBEs[L2cache.cacheProbe(in_msg.Addr)]);
            }
          }
        }
      }
    }
  }


  // ACTIONS

  action(a_issueFetchToMemory, "a", desc="fetch data from memory") {
    peek(L1RequestL2Network_in, RequestMsg) {
      enqueue(DirRequestL2Network_out, RequestMsg, l2_request_latency) {
        out_msg.Addr := address;
        out_msg.Type := CoherenceRequestType:GETS;
        out_msg.Requestor := machineID;
        out_msg.Destination.add(map_Address_to_Directory(address));
        out_msg.MessageSize := MessageSizeType:Control;
      }
    }
  }

  action(b_forwardRequestToExclusive, "b", desc="Forward request to the exclusive L1") {
    peek(L1RequestL2Network_in, RequestMsg) {
      enqueue(L1RequestL2Network_out, RequestMsg, to_l1_latency) {
        assert(is_valid(cache_entry));
        out_msg.Addr := address;
        out_msg.Type := in_msg.Type;
        out_msg.Requestor := in_msg.Requestor;
        out_msg.Destination.add(cache_entry.Exclusive);
        out_msg.MessageSize := MessageSizeType:Request_Control;
      }
    }
  }

  action(c_exclusiveReplacement, "c", desc="Send data to memory") {
    enqueue(responseL2Network_out, ResponseMsg, l2_response_latency) {
      assert(is_valid(cache_entry));
      out_msg.Addr := address;
      out_msg.Type := CoherenceResponseType:MEMORY_DATA;
      out_msg.Sender := machineID;
      out_msg.Destination.add(map_Address_to_Directory(address));
      out_msg.DataBlk := cache_entry.DataBlk;
      out_msg.Dirty := cache_entry.Dirty;
      out_msg.MessageSize := MessageSizeType:Response_Data;
    }
  }

  action(c_exclusiveCleanReplacement, "cc", desc="Send ack to memory for clean replacement") {
    enqueue(responseL2Network_out, ResponseMsg, l2_response_latency) {
      out_msg.Addr := address;
      out_msg.Type := CoherenceResponseType:ACK;
      out_msg.Sender := machineID;
      out_msg.Destination.add(map_Address_to_Directory(address));
      out_msg.MessageSize := MessageSizeType:Response_Control;
    }
  }

  action(ct_exclusiveReplacementFromTBE, "ct", desc="Send data to memory") {
    enqueue(responseL2Network_out, ResponseMsg, l2_response_latency) {
      assert(is_valid(tbe));
      out_msg.Addr := address;
      out_msg.Type := CoherenceResponseType:MEMORY_DATA;
      out_msg.Sender := machineID;
      out_msg.Destination.add(map_Address_to_Directory(address));
      out_msg.DataBlk := tbe.DataBlk;
      out_msg.Dirty := tbe.Dirty;
      out_msg.MessageSize := MessageSizeType:Response_Data;
    }
  }

  action(d_sendDataToRequestor, "d", desc="Send data from cache to reqeustor") {
    peek(L1RequestL2Network_in, RequestMsg) {
      enqueue(responseL2Network_out, ResponseMsg, l2_response_latency) {
        assert(is_valid(cache_entry));
        out_msg.Addr := address;
        out_msg.Type := CoherenceResponseType:DATA;
        out_msg.Sender := machineID;
        out_msg.Destination.add(in_msg.Requestor);
        out_msg.DataBlk := cache_entry.DataBlk;
        out_msg.MessageSize := MessageSizeType:Response_Data;

        out_msg.AckCount := 0 - cache_entry.Sharers.count();
        if (cache_entry.Sharers.isElement(in_msg.Requestor)) {
          out_msg.AckCount := out_msg.AckCount + 1;
        }
      }
    }
  }

  action(dd_sendExclusiveDataToRequestor, "dd", desc="Send data from cache to reqeustor") {
    peek(L1RequestL2Network_in, RequestMsg) {
      enqueue(responseL2Network_out, ResponseMsg, l2_response_latency) {
        assert(is_valid(cache_entry));
        out_msg.Addr := address;
        out_msg.Type := CoherenceResponseType:DATA_EXCLUSIVE;
        out_msg.Sender := machineID;
        out_msg.Destination.add(in_msg.Requestor);
        out_msg.DataBlk := cache_entry.DataBlk;
        out_msg.MessageSize := MessageSizeType:Response_Data;

        out_msg.AckCount := 0 - cache_entry.Sharers.count();
        if (cache_entry.Sharers.isElement(in_msg.Requestor)) {
          out_msg.AckCount := out_msg.AckCount + 1;
        }
      }
    }
  }

  action(ds_sendSharedDataToRequestor, "ds", desc="Send data from cache to reqeustor") {
    peek(L1RequestL2Network_in, RequestMsg) {
      enqueue(responseL2Network_out, ResponseMsg, l2_response_latency) {
        assert(is_valid(cache_entry));
        out_msg.Addr := address;
        out_msg.Type := CoherenceResponseType:DATA;
        out_msg.Sender := machineID;
        out_msg.Destination.add(in_msg.Requestor);
        out_msg.DataBlk := cache_entry.DataBlk;
        out_msg.MessageSize := MessageSizeType:Response_Data;
        out_msg.AckCount := 0;
      }
    }
  }

  action(e_sendDataToGetSRequestors, "e", desc="Send data from cache to all GetS IDs") {
    assert(is_valid(tbe));
    assert(tbe.L1_GetS_IDs.count() > 0);
    enqueue(responseL2Network_out, ResponseMsg, to_l1_latency) {
      assert(is_valid(cache_entry));
      out_msg.Addr := address;
      out_msg.Type := CoherenceResponseType:DATA;
      out_msg.Sender := machineID;
      out_msg.Destination := tbe.L1_GetS_IDs;  // internal nodes
      out_msg.DataBlk := cache_entry.DataBlk;
      out_msg.MessageSize := MessageSizeType:Response_Data;
    }
  }

  action(ex_sendExclusiveDataToGetSRequestors, "ex", desc="Send data from cache to all GetS IDs") {
    assert(is_valid(tbe));
    assert(tbe.L1_GetS_IDs.count() == 1);
    enqueue(responseL2Network_out, ResponseMsg, to_l1_latency) {
      assert(is_valid(cache_entry));
      out_msg.Addr := address;
      out_msg.Type := CoherenceResponseType:DATA_EXCLUSIVE;
      out_msg.Sender := machineID;
      out_msg.Destination := tbe.L1_GetS_IDs;  // internal nodes
      out_msg.DataBlk := cache_entry.DataBlk;
      out_msg.MessageSize := MessageSizeType:Response_Data;
    }
  }

  action(ee_sendDataToGetXRequestor, "ee", desc="Send data from cache to GetX ID") {
    enqueue(responseL2Network_out, ResponseMsg, to_l1_latency) {
      assert(is_valid(tbe));
      assert(is_valid(cache_entry));
      out_msg.Addr := address;
      out_msg.Type := CoherenceResponseType:DATA;
      out_msg.Sender := machineID;
      out_msg.Destination.add(tbe.L1_GetX_ID);
      DPRINTF(RubySlicc, "%s\n", out_msg.Destination);
      out_msg.DataBlk := cache_entry.DataBlk;
      DPRINTF(RubySlicc, "Address: %s, Destination: %s, DataBlock: %s\n",
              out_msg.Addr, out_msg.Destination, out_msg.DataBlk);
      out_msg.MessageSize := MessageSizeType:Response_Data;
    }
  }

  action(f_sendInvToSharers, "f", desc="invalidate sharers for L2 replacement") {
    enqueue(L1RequestL2Network_out, RequestMsg, to_l1_latency) {
      assert(is_valid(cache_entry));
      out_msg.Addr := address;
      out_msg.Type := CoherenceRequestType:INV;
      out_msg.Requestor := machineID;
      out_msg.Destination := cache_entry.Sharers;
      out_msg.MessageSize := MessageSizeType:Request_Control;
    }
  }

  action(fw_sendFwdInvToSharers, "fw", desc="invalidate sharers for request") {
    peek(L1RequestL2Network_in, RequestMsg) {
      enqueue(L1RequestL2Network_out, RequestMsg, to_l1_latency) {
        assert(is_valid(cache_entry));
        out_msg.Addr := address;
        out_msg.Type := CoherenceRequestType:INV;
        out_msg.Requestor := in_msg.Requestor;
        out_msg.Destination := cache_entry.Sharers;
        out_msg.MessageSize := MessageSizeType:Request_Control;
      }
    }
  }

  action(fwm_sendFwdInvToSharersMinusRequestor, "fwm", desc="invalidate sharers for request, requestor is sharer") {
    peek(L1RequestL2Network_in, RequestMsg) {
      enqueue(L1RequestL2Network_out, RequestMsg, to_l1_latency) {
        assert(is_valid(cache_entry));
        out_msg.Addr := address;
        out_msg.Type := CoherenceRequestType:INV;
        out_msg.Requestor := in_msg.Requestor;
        out_msg.Destination := cache_entry.Sharers;
        out_msg.Destination.remove(in_msg.Requestor);
        out_msg.MessageSize := MessageSizeType:Request_Control;
      }
    }
  }

  // OTHER ACTIONS
  action(i_allocateTBE, "i", desc="Allocate TBE for request") {
    check_allocate(L2_TBEs);
    assert(is_valid(cache_entry));
    L2_TBEs.allocate(address);
    set_tbe(L2_TBEs[address]);
    tbe.L1_GetS_IDs.clear();
    tbe.DataBlk := cache_entry.DataBlk;
    tbe.Dirty := cache_entry.Dirty;
    tbe.pendingAcks := cache_entry.Sharers.count();
  }

  action(s_deallocateTBE, "s", desc="Deallocate external TBE") {
    L2_TBEs.deallocate(address);
    unset_tbe();
  }

  action(jj_popL1RequestQueue, "\j", desc="Pop incoming L1 request queue") {
    profileMsgDelay(0, L1RequestL2Network_in.dequeue());
  }

  action(k_popUnblockQueue, "k", desc="Pop incoming unblock queue") {
    profileMsgDelay(0, L1unblockNetwork_in.dequeue());
  }

  action(o_popIncomingResponseQueue, "o", desc="Pop Incoming Response queue") {
    profileMsgDelay(1, responseL2Network_in.dequeue());
  }

  action(m_writeDataToCache, "m", desc="Write data from response queue to cache") {
    peek(responseL2Network_in, ResponseMsg) {
      assert(is_valid(cache_entry));
      cache_entry.DataBlk := in_msg.DataBlk;
      if (in_msg.Dirty) {
        cache_entry.Dirty := in_msg.Dirty;
      }
    }
  }

  action(mr_writeDataToCacheFromRequest, "mr", desc="Write data from response queue to cache") {
    peek(L1RequestL2Network_in, RequestMsg) {
      assert(is_valid(cache_entry));
      cache_entry.DataBlk := in_msg.DataBlk;
      if (in_msg.Dirty) {
        cache_entry.Dirty := in_msg.Dirty;
      }
    }
  }

  action(q_updateAck, "q", desc="update pending ack count") {
    peek(responseL2Network_in, ResponseMsg) {
      assert(is_valid(tbe));
      tbe.pendingAcks := tbe.pendingAcks - in_msg.AckCount;
      APPEND_TRANSITION_COMMENT(in_msg.AckCount);
      APPEND_TRANSITION_COMMENT(" p: ");
      APPEND_TRANSITION_COMMENT(tbe.pendingAcks);
    }
  }

  action(qq_writeDataToTBE, "\qq", desc="Write data from response queue to TBE") {
    peek(responseL2Network_in, ResponseMsg) {
      assert(is_valid(tbe));
      tbe.DataBlk := in_msg.DataBlk;
      tbe.Dirty := in_msg.Dirty;
    }
  }

  action(ss_recordGetSL1ID, "\s", desc="Record L1 GetS for load response") {
    peek(L1RequestL2Network_in, RequestMsg) {
      assert(is_valid(tbe));
      tbe.L1_GetS_IDs.add(in_msg.Requestor);
    }
  }

  action(xx_recordGetXL1ID, "\x", desc="Record L1 GetX for store response") {
    peek(L1RequestL2Network_in, RequestMsg) {
      assert(is_valid(tbe));
      tbe.L1_GetX_ID := in_msg.Requestor;
    }
  }

  action(set_setMRU, "\set", desc="set the MRU entry") {
    L2cache.setMRU(address);
  }

  action(qq_allocateL2CacheBlock, "\q", desc="Set L2 cache tag equal to tag of block B.") {
    if (is_invalid(cache_entry)) {
      set_cache_entry(L2cache.allocate(address, new Entry));
    }
  }

  action(rr_deallocateL2CacheBlock, "\r", desc="Deallocate L2 cache block.  Sets the cache to not present, allowing a replacement in parallel with a fetch.") {
    L2cache.deallocate(address);
    unset_cache_entry();
  }

  action(t_sendWBAck, "t", desc="Send writeback ACK") {
    peek(L1RequestL2Network_in, RequestMsg) {
      enqueue(responseL2Network_out, ResponseMsg, to_l1_latency) {
        out_msg.Addr := address;
        out_msg.Type := CoherenceResponseType:WB_ACK;
        out_msg.Sender := machineID;
        out_msg.Destination.add(in_msg.Requestor);
        out_msg.MessageSize := MessageSizeType:Response_Control;
      }
    }
  }

  action(ts_sendInvAckToUpgrader, "ts", desc="Send ACK to upgrader") {
    peek(L1RequestL2Network_in, RequestMsg) {
      enqueue(responseL2Network_out, ResponseMsg, to_l1_latency) {
        assert(is_valid(cache_entry));
        out_msg.Addr := address;
        out_msg.Type := CoherenceResponseType:ACK;
        out_msg.Sender := machineID;
        out_msg.Destination.add(in_msg.Requestor);
        out_msg.MessageSize := MessageSizeType:Response_Control;
        // upgrader doesn't get ack from itself, hence the + 1
        out_msg.AckCount := 0 - cache_entry.Sharers.count() + 1;
      }
    }
  }

  action(uu_profileMiss, "\um", desc="Profile the demand miss") {
      ++L2cache.demand_misses;
  }

  action(uu_profileHit, "\uh", desc="Profile the demand hit") {
      ++L2cache.demand_hits;
  }

  action(nn_addSharer, "\n", desc="Add L1 sharer to list") {
    peek(L1RequestL2Network_in, RequestMsg) {
      assert(is_valid(cache_entry));
      addSharer(address, in_msg.Requestor, cache_entry);
      APPEND_TRANSITION_COMMENT( cache_entry.Sharers );
    }
  }

  action(nnu_addSharerFromUnblock, "\nu", desc="Add L1 sharer to list") {
    peek(L1unblockNetwork_in, ResponseMsg) {
      assert(is_valid(cache_entry));
      addSharer(address, in_msg.Sender, cache_entry);
    }
  }

  action(kk_removeRequestSharer, "\k", desc="Remove L1 Request sharer from list") {
    peek(L1RequestL2Network_in, RequestMsg) {
      assert(is_valid(cache_entry));
      cache_entry.Sharers.remove(in_msg.Requestor);
    }
  }

  action(ll_clearSharers, "\l", desc="Remove all L1 sharers from list") {
    peek(L1RequestL2Network_in, RequestMsg) {
      assert(is_valid(cache_entry));
      cache_entry.Sharers.clear();
    }
  }

  action(mm_markExclusive, "\m", desc="set the exclusive owner") {
    peek(L1RequestL2Network_in, RequestMsg) {
      assert(is_valid(cache_entry));
      cache_entry.Sharers.clear();
      cache_entry.Exclusive := in_msg.Requestor;
      addSharer(address, in_msg.Requestor, cache_entry);
    }
  }

  action(mmu_markExclusiveFromUnblock, "\mu", desc="set the exclusive owner") {
    peek(L1unblockNetwork_in, ResponseMsg) {
      assert(is_valid(cache_entry));
      cache_entry.Sharers.clear();
      cache_entry.Exclusive := in_msg.Sender;
      addSharer(address, in_msg.Sender, cache_entry);
    }
  }

  action(zz_stallAndWaitL1RequestQueue, "zz", desc="recycle L1 request queue") {
    stall_and_wait(L1RequestL2Network_in, address);
  }

  action(zn_recycleResponseNetwork, "zn", desc="recycle memory request") {
    responseL2Network_in.recycle();
  }

  action(kd_wakeUpDependents, "kd", desc="wake-up dependents") {
    wakeUpBuffers(address);
  }

  //*****************************************************
  // TRANSITIONS
  //*****************************************************


  //===============================================
  // BASE STATE - I

  // Transitions from I (Idle)
  transition({NP, IS, ISS, IM, SS, M, M_I, I_I, S_I, MT_IB, MT_SB}, L1_PUTX) {
    t_sendWBAck;
    jj_popL1RequestQueue;
  }

  transition({NP, SS, M, MT, M_I, I_I, S_I, IS, ISS, IM, MT_IB, MT_SB}, L1_PUTX_old) {
    t_sendWBAck;
    jj_popL1RequestQueue;
  }

  transition({IM, IS, ISS, SS_MB, MT_MB, MT_IIB, MT_IB, MT_SB}, {L2_Replacement, L2_Replacement_clean}) {
    zz_stallAndWaitL1RequestQueue;
  }

  transition({IM, IS, ISS, SS_MB, MT_MB, MT_IIB, MT_IB, MT_SB}, MEM_Inv) {
    zn_recycleResponseNetwork;
  }

  transition({I_I, S_I, M_I, MT_I, MCT_I, NP}, MEM_Inv) {
    o_popIncomingResponseQueue;
  }


  transition({SS_MB, MT_MB, MT_IIB, MT_IB, MT_SB}, {L1_GETS, L1_GET_INSTR, L1_GETX, L1_UPGRADE}) {
    zz_stallAndWaitL1RequestQueue;
  }


  transition(NP, L1_GETS,  ISS) {
    qq_allocateL2CacheBlock;
    ll_clearSharers;
    nn_addSharer;
    i_allocateTBE;
    ss_recordGetSL1ID;
    a_issueFetchToMemory;
    uu_profileMiss;
    jj_popL1RequestQueue;
  }

  transition(NP, L1_GET_INSTR, IS) {
    qq_allocateL2CacheBlock;
    ll_clearSharers;
    nn_addSharer;
    i_allocateTBE;
    ss_recordGetSL1ID;
    a_issueFetchToMemory;
    uu_profileMiss;
    jj_popL1RequestQueue;
  }

  transition(NP, L1_GETX, IM) {
    qq_allocateL2CacheBlock;
    ll_clearSharers;
    // nn_addSharer;
    i_allocateTBE;
    xx_recordGetXL1ID;
    a_issueFetchToMemory;
    uu_profileMiss;
    jj_popL1RequestQueue;
  }


  // transitions from IS/IM

  transition(ISS, Mem_Data, MT_MB) {
    m_writeDataToCache;
    ex_sendExclusiveDataToGetSRequestors;
    s_deallocateTBE;
    o_popIncomingResponseQueue;
  }

  transition(IS, Mem_Data, SS) {
    m_writeDataToCache;
    e_sendDataToGetSRequestors;
    s_deallocateTBE;
    o_popIncomingResponseQueue;
    kd_wakeUpDependents;
  }

  transition(IM, Mem_Data, MT_MB) {
    m_writeDataToCache;
    ee_sendDataToGetXRequestor;
    s_deallocateTBE;
    o_popIncomingResponseQueue;
  }

  transition({IS, ISS}, {L1_GETS, L1_GET_INSTR}, IS) {
    nn_addSharer;
    ss_recordGetSL1ID;
    uu_profileMiss;
    jj_popL1RequestQueue;
  }

  transition({IS, ISS}, L1_GETX) {
    zz_stallAndWaitL1RequestQueue;
  }

  transition(IM, {L1_GETX, L1_GETS, L1_GET_INSTR}) {
    zz_stallAndWaitL1RequestQueue;
  }

  // transitions from SS
  transition(SS, {L1_GETS, L1_GET_INSTR}) {
    ds_sendSharedDataToRequestor;
    nn_addSharer;
    set_setMRU;
    uu_profileHit;
    jj_popL1RequestQueue;
  }


  transition(SS, L1_GETX, SS_MB) {
    d_sendDataToRequestor;
    // fw_sendFwdInvToSharers;
    fwm_sendFwdInvToSharersMinusRequestor;
    set_setMRU;
    uu_profileHit;
    jj_popL1RequestQueue;
  }

  transition(SS, L1_UPGRADE, SS_MB) {
    fwm_sendFwdInvToSharersMinusRequestor;
    ts_sendInvAckToUpgrader;
    set_setMRU;
    uu_profileHit;
    jj_popL1RequestQueue;
  }

  transition(SS, L2_Replacement_clean, I_I) {
    i_allocateTBE;
    f_sendInvToSharers;
    rr_deallocateL2CacheBlock;
  }

  transition(SS, {L2_Replacement, MEM_Inv}, S_I) {
    i_allocateTBE;
    f_sendInvToSharers;
    rr_deallocateL2CacheBlock;
  }


  transition(M, L1_GETX, MT_MB) {
    d_sendDataToRequestor;
    set_setMRU;
    uu_profileHit;
    jj_popL1RequestQueue;
  }

  transition(M, L1_GET_INSTR, SS) {
    d_sendDataToRequestor;
    nn_addSharer;
    set_setMRU;
    uu_profileHit;
    jj_popL1RequestQueue;
  }

  transition(M, L1_GETS, MT_MB) {
    dd_sendExclusiveDataToRequestor;
    set_setMRU;
    uu_profileHit;
    jj_popL1RequestQueue;
  }

  transition(M, {L2_Replacement, MEM_Inv}, M_I) {
    i_allocateTBE;
    c_exclusiveReplacement;
    rr_deallocateL2CacheBlock;
  }

  transition(M, L2_Replacement_clean, M_I) {
    i_allocateTBE;
    c_exclusiveCleanReplacement;
    rr_deallocateL2CacheBlock;
  }


  // transitions from MT

  transition(MT, L1_GETX, MT_MB) {
    b_forwardRequestToExclusive;
    uu_profileMiss;
    set_setMRU;
    jj_popL1RequestQueue;
  }


  transition(MT, {L1_GETS, L1_GET_INSTR}, MT_IIB) {
    b_forwardRequestToExclusive;
    uu_profileMiss;
    set_setMRU;
    jj_popL1RequestQueue;
  }

  transition(MT, {L2_Replacement, MEM_Inv}, MT_I) {
    i_allocateTBE;
    f_sendInvToSharers;
    rr_deallocateL2CacheBlock;
  }

  transition(MT, L2_Replacement_clean, MCT_I) {
    i_allocateTBE;
    f_sendInvToSharers;
    rr_deallocateL2CacheBlock;
  }

  transition(MT, L1_PUTX, M) {
    ll_clearSharers;
    mr_writeDataToCacheFromRequest;
    t_sendWBAck;
    jj_popL1RequestQueue;
  }

  transition({SS_MB,MT_MB}, Exclusive_Unblock, MT) {
    // update actual directory
    mmu_markExclusiveFromUnblock;
    k_popUnblockQueue;
    kd_wakeUpDependents;
  }

  transition(MT_IIB, {L1_PUTX, L1_PUTX_old}){
    zz_stallAndWaitL1RequestQueue;
  }

  transition(MT_IIB, Unblock, MT_IB) {
    nnu_addSharerFromUnblock;
    k_popUnblockQueue;
  }

  transition(MT_IIB, {WB_Data, WB_Data_clean}, MT_SB) {
    m_writeDataToCache;
    o_popIncomingResponseQueue;
  }

  transition(MT_IB, {WB_Data, WB_Data_clean}, SS) {
    m_writeDataToCache;
    o_popIncomingResponseQueue;
    kd_wakeUpDependents;
  }

  transition(MT_SB, Unblock, SS) {
    nnu_addSharerFromUnblock;
    k_popUnblockQueue;
    kd_wakeUpDependents;
  }

  // writeback states
  transition({I_I, S_I, MT_I, MCT_I, M_I}, {L1_GETX, L1_UPGRADE, L1_GETS, L1_GET_INSTR}) {
    zz_stallAndWaitL1RequestQueue;
  }

  transition(I_I, Ack) {
    q_updateAck;
    o_popIncomingResponseQueue;
  }

  transition(I_I, Ack_all, M_I) {
    c_exclusiveCleanReplacement;
    o_popIncomingResponseQueue;
  }

  transition({MT_I, MCT_I}, WB_Data, M_I) {
    qq_writeDataToTBE;
    ct_exclusiveReplacementFromTBE;
    o_popIncomingResponseQueue;
  }

  transition(MCT_I, {WB_Data_clean, Ack_all}, M_I) {
    c_exclusiveCleanReplacement;
    o_popIncomingResponseQueue;
  }

  transition(MCT_I,  {L1_PUTX, L1_PUTX_old}){
    zz_stallAndWaitL1RequestQueue;
  }

  // L1 never changed Dirty data
  transition(MT_I, {WB_Data_clean, Ack_all}, M_I) {
    ct_exclusiveReplacementFromTBE;
    o_popIncomingResponseQueue;
  }

  transition(MT_I, {L1_PUTX, L1_PUTX_old}){
    zz_stallAndWaitL1RequestQueue;
  }

  // possible race between unblock and immediate replacement
  transition({MT_MB,SS_MB}, {L1_PUTX, L1_PUTX_old}) {
    zz_stallAndWaitL1RequestQueue;
  }

  transition(S_I, Ack) {
    q_updateAck;
    o_popIncomingResponseQueue;
  }

  transition(S_I, Ack_all, M_I) {
    ct_exclusiveReplacementFromTBE;
    o_popIncomingResponseQueue;
  }

  transition(M_I, Mem_Ack, NP) {
    s_deallocateTBE;
    o_popIncomingResponseQueue;
    kd_wakeUpDependents;
  }
}
