/**
 * @file
 *
 * ALIB PSPP Pcie Smu Lib V1
 *
 *
 *
 * @xrefitem bom "File Content Label" "Release Content"
 * @e project:     AGESA
 * @e sub-project: GNB
 * @e \$Revision: 25430 $   @e \$Date: 2010-01-18 22:25:55 -0800 (Mon, 18 Jan 2010) $
 *
 */
/*
 *****************************************************************************
 *
 * Copyright (c) 2011, Advanced Micro Devices, Inc.
 * 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 Advanced Micro Devices, Inc. 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 ADVANCED MICRO DEVICES, INC. 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.
 *
 * ***************************************************************************
 *
 */
  /*----------------------------------------------------------------------------------------*/
  /**
   *  SMU indirect register read
   *
   *  Arg0 - Smu register offset
   *
   */
  Method (procNbSmuIndirectRegisterRead, 1, NotSerialized) {
    Store (procIndirectRegisterRead (0x0, 0x60, 0xCD), Local0)
    // Access 32 bit width
    Increment (Arg0)
    // Reverse ReqToggle
    Or (And (Local0, 0xFEFFFFFF), And (Not (And (Local0, 0x01000000)), 0x01000000),Local0)
    // Assign Address and ReqType = 0
    Or (And (Local0, 0xFD00FFFF), ShiftLeft (Arg0, 16), Local0)

    procIndirectRegisterWrite (0x0, 0x60, 0xCD, Local0)

    Store (procIndirectRegisterRead (0x0, 0x60, 0xCE), Local0)
    return (Local0)
  }

  /*----------------------------------------------------------------------------------------*/
  /**
   *  SMU indirect register Write
   *
   *  Arg0 - Smu register offset
   *  Arg1 - Value
   *  Arg2 - Width, 0 = 16, 1 = 32
   *
   */
  Method (procNbSmuIndirectRegisterWrite, 3, NotSerialized) {
    Store (procIndirectRegisterRead (0x0, 0x60, 0xCD), Local0)
    // Get low 16 bit value
    Store (And (Arg1, 0xFFFF), Local1)
    // Reverse ReqToggle
    Or (And (Local0, 0xFEFFFFFF), And (Not (And (Local0, 0x01000000)), 0x01000000),Local0)
    // Assign Address
    Or (And (Local0, 0xFD000000), ShiftLeft (Arg0, 16), Local0)
    // ReqType = 1
    Or (Local0, 0x02000000, Local0)
    // Assign Low 16 bit value
    Or (Local0, Local1, Local0)

    procIndirectRegisterWrite (0x0, 0x60, 0xCD, Local0)

    if (LEqual (Arg2, 1)) {
      // Get high 16 bit value
      Store (ShiftRight (Arg1, 16), Local1)
      // Reverse ReqToggle
      Or (And (Local0, 0xFEFFFFFF), And (Not (And (Local0, 0x01000000)), 0x01000000),Local0)
      // Assign Address
      Or (And (Local0, 0xFF000000), ShiftLeft (Add (Arg0, 1), 16), Local0)
      // Assign High 16 bit value
      Or (Local0, Local1, Local0)

      procIndirectRegisterWrite (0x0, 0x60, 0xCD, Local0)
    }

  }

  /*----------------------------------------------------------------------------------------*/
  /**
   *  SMU Service request
   *
   *  Arg0 - Smu service id
   *  Arg1 - Flags - Poll Ack = 1, Poll down = 2
   *
   */
  Method (procNbSmuServiceRequest, 2, NotSerialized) {
    Store ("NbSmuServiceRequest Enter", Debug)
    Store ("Request id =", Debug)
    Store (Arg0, Debug)

    Or (ShiftLeft (Arg0, 3), 0x1, Local0)
    procNbSmuIndirectRegisterWrite (0x3, Local0, 1)

    if (LAnd (Arg1, 1)) {
      while (LNotEqual (AND(procNbSmuIndirectRegisterRead (0x3), 0x2), 0x2)) {
      	Store ("--Wait Ack--", Debug)
      }
    }
    if (LAnd (Arg1, 2)) {
      while (LNotEqual (AND(procNbSmuIndirectRegisterRead (0x3), 0x4), 0x4)) {
      	Store ("--Wait Done--", Debug)
      }
    }
    // Clear IRQ register
    procNbSmuIndirectRegisterWrite (0x3, 0, 1)
    Store ("NbSmuServiceRequest Exit", Debug)
  }

  /*----------------------------------------------------------------------------------------*/
  /**
   *  Write RCU register
   *
   *  Arg0 - Register Address
   *  Arg1 - Register Data
   *
   */
  Method (procSmuRcuWrite, 2, NotSerialized) {
     procNbSmuIndirectRegisterWrite (0xB, Arg0, 0)
     procNbSmuIndirectRegisterWrite (0x5, Arg1, 1)

  }

  /*----------------------------------------------------------------------------------------*/
  /**
   *  Read RCU register
   *
   *  Arg0 	- Register Address
   *  Retval	- RCU register value
   */
  Method (procSmuRcuRead, 1, NotSerialized) {
    procNbSmuIndirectRegisterWrite (0xB, Arg0, 0)
    Store (procNbSmuIndirectRegisterRead (0x5), Local0)
    return (Local0)
  }

  /*----------------------------------------------------------------------------------------*/
  /**
   *  SMU SRBM Register Read
   *
   *  Arg0 - FCR register address
   *
   */
  Method (procNbSmuSrbmRegisterRead, 1, NotSerialized) {
    //SMUx0B_x8600
    Store (Or (And (Arg0, 0xFF), 0x01865000), Local0)
    //SMUx0B_x8604
    Store (Or (And (Arg0, 0xFFFFFF00), 4), Local1)
    //SMUx0B_x8608
    Store (Or (ShiftLeft (3, 30), ShiftLeft (1, 18)), Local2)
    //Write SMU RCU
    procSmuRcuWrite (0x8600, Local0)
    procSmuRcuWrite (0x8604, Local1)
    procSmuRcuWrite (0x8608, Local2)
    // ServiceId
    if (LEqual (ShiftRight (Arg0, 16), 0xFE00)) {
      procNbSmuServiceRequest (0xD, 0x3)
    }
    if (LEqual (ShiftRight (Arg0, 16), 0xFE30)) {
      procNbSmuServiceRequest (0xB, 0x3)
    }
    return (procSmuRcuRead(0x8650))
  }


  /*----------------------------------------------------------------------------------------*/
  /**
   *  SMU SRBM Register Write
   *
   *  Arg0 - FCR register address
   *  Arg1 - Value
   *
   */
  Method (procNbSmuSrbmRegisterWrite, 2, NotSerialized) {
    //SMUx0B_x8600
    Store (Or (And (Arg0, 0xFF), 0x01865000), Local0)
    //SMUx0B_x8604
    Store (Or (And (Arg0, 0xFFFFFF00), 4), Local1)
    //SMUx0B_x8608
    Store (Or (ShiftLeft (3, 30), ShiftLeft (1, 18)), Local2)
    Or (Local2, ShiftLeft (1, 16), Local2)
    //Write SMU RCU
    procSmuRcuWrite (0x8600, Local0)
    procSmuRcuWrite (0x8604, Local1)
    procSmuRcuWrite (0x8608, Local2)
    //Write Data
    procSmuRcuWrite (0x8650, Arg1)
    // ServiceId
    procNbSmuServiceRequest (0xB, 0x3)
  }
