ArmPkg: Add ARM Architectural Timer support

ARM Architectural Timer support is defined by the ARM Generic Timer Specification.



git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@12455 6f19259b-4bc3-4df7-8a09-765794883524
This commit is contained in:
oliviermartin
2011-09-27 16:35:16 +00:00
parent 0c0e7ef451
commit da9675a241
15 changed files with 1468 additions and 1 deletions

View File

@@ -0,0 +1,275 @@
/** @file
*
* Copyright (c) 2011, ARM Limited. All rights reserved.
*
* This program and the accompanying materials
* are licensed and made available under the terms and conditions of the BSD License
* which accompanies this distribution. The full text of the license may be found at
* http://opensource.org/licenses/bsd-license.php
*
* THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
* WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
*
**/
#include <Uefi.h>
#include <Chipset/ArmV7.h>
#include <Library/BaseMemoryLib.h>
#include <Library/MemoryAllocationLib.h>
#include <Library/ArmLib.h>
#include <Library/BaseLib.h>
#include <Library/DebugLib.h>
#include "ArmV7Lib.h"
#include "ArmLibPrivate.h"
#include <Library/ArmV7ArchTimerLib.h>
VOID
EFIAPI
ArmArchTimerReadReg (
IN ARM_ARCH_TIMER_REGS Reg,
OUT VOID *DstBuf
)
{
// Check if the Generic/Architecture timer is implemented
if (ArmIsArchTimerImplemented ()) {
switch (Reg) {
case CntFrq:
*((UINTN *)DstBuf) = ArmReadCntFrq ();
break;
case CntPct:
*((UINT64 *)DstBuf) = ArmReadCntPct ();
break;
case CntkCtl:
*((UINTN *)DstBuf) = ArmReadCntkCtl();
break;
case CntpTval:
*((UINTN *)DstBuf) = ArmReadCntpTval ();
break;
case CntpCtl:
*((UINTN *)DstBuf) = ArmReadCntpCtl ();
break;
case CntvTval:
*((UINTN *)DstBuf) = ArmReadCntvTval ();
break;
case CntvCtl:
*((UINTN *)DstBuf) = ArmReadCntvCtl ();
break;
case CntvCt:
*((UINT64 *)DstBuf) = ArmReadCntvCt ();
break;
case CntpCval:
*((UINT64 *)DstBuf) = ArmReadCntpCval ();
break;
case CntvCval:
*((UINT64 *)DstBuf) = ArmReadCntvCval ();
break;
case CntvOff:
*((UINT64 *)DstBuf) = ArmReadCntvOff ();
break;
case CnthCtl:
case CnthpTval:
case CnthpCtl:
case CnthpCval:
DEBUG ((EFI_D_ERROR, "The register is related to Hyperviser Mode. Can't perform requested operation\n "));
break;
default:
DEBUG ((EFI_D_ERROR, "Unknown ARM Generic Timer register %x. \n ", Reg));
}
} else {
DEBUG ((EFI_D_ERROR, "Attempt to read ARM Generic Timer registers. But ARM Generic Timer extension is not implemented \n "));
ASSERT (0);
}
}
VOID
EFIAPI
ArmArchTimerWriteReg (
IN ARM_ARCH_TIMER_REGS Reg,
IN VOID *SrcBuf
)
{
// Check if the Generic/Architecture timer is implemented
if (ArmIsArchTimerImplemented ()) {
switch (Reg) {
case CntFrq:
ArmWriteCntFrq (*((UINTN *)SrcBuf));
break;
case CntPct:
DEBUG ((EFI_D_ERROR, "Can't write to Read Only Register: CNTPCT \n"));
break;
case CntkCtl:
ArmWriteCntkCtl (*((UINTN *)SrcBuf));
break;
case CntpTval:
ArmWriteCntpTval (*((UINTN *)SrcBuf));
break;
case CntpCtl:
ArmWriteCntpCtl (*((UINTN *)SrcBuf));
break;
case CntvTval:
ArmWriteCntvTval (*((UINTN *)SrcBuf));
break;
case CntvCtl:
ArmWriteCntvCtl (*((UINTN *)SrcBuf));
break;
case CntvCt:
DEBUG ((EFI_D_ERROR, "Can't write to Read Only Register: CNTVCT \n"));
break;
case CntpCval:
ArmWriteCntpCval (*((UINT64 *)SrcBuf) );
break;
case CntvCval:
ArmWriteCntvCval (*((UINT64 *)SrcBuf) );
break;
case CntvOff:
ArmWriteCntvOff (*((UINT64 *)SrcBuf));
break;
case CnthCtl:
case CnthpTval:
case CnthpCtl:
case CnthpCval:
DEBUG ((EFI_D_ERROR, "The register is related to Hypervisor Mode. Can't perform requested operation\n "));
break;
default:
DEBUG ((EFI_D_ERROR, "Unknown ARM Generic Timer register %x. \n ", Reg));
}
} else {
DEBUG ((EFI_D_ERROR, "Attempt to write to ARM Generic Timer registers. But ARM Generic Timer extension is not implemented \n "));
ASSERT (0);
}
}
VOID
EFIAPI
ArmArchTimerEnableTimer (
VOID
)
{
UINTN TimerCtrlReg;
ArmArchTimerReadReg (CntpCtl, (VOID *)&TimerCtrlReg);
TimerCtrlReg |= ARM_ARCH_TIMER_ENABLE;
ArmArchTimerWriteReg (CntpCtl, (VOID *)&TimerCtrlReg);
}
VOID
EFIAPI
ArmArchTimerDisableTimer (
VOID
)
{
UINTN TimerCtrlReg;
ArmArchTimerReadReg (CntpCtl, (VOID *)&TimerCtrlReg);
TimerCtrlReg &= ~ARM_ARCH_TIMER_ENABLE;
ArmArchTimerWriteReg (CntpCtl, (VOID *)&TimerCtrlReg);
}
VOID
EFIAPI
ArmArchTimerSetTimerFreq (
IN UINTN FreqInHz
)
{
ArmArchTimerWriteReg (CntFrq, (VOID *)&FreqInHz);
}
UINTN
EFIAPI
ArmArchTimerGetTimerFreq (
VOID
)
{
UINTN ArchTimerFreq = 0;
ArmArchTimerReadReg (CntFrq, (VOID *)&ArchTimerFreq);
return ArchTimerFreq;
}
UINTN
EFIAPI
ArmArchTimerGetTimerVal (
VOID
)
{
UINTN ArchTimerVal;
ArmArchTimerReadReg (CntpTval, (VOID *)&ArchTimerVal);
return ArchTimerVal;
}
VOID
EFIAPI
ArmArchTimerSetTimerVal (
IN UINTN Val
)
{
ArmArchTimerWriteReg (CntpTval, (VOID *)&Val);
}
UINT64
EFIAPI
ArmArchTimerGetSystemCount (
VOID
)
{
UINT64 SystemCount;
ArmArchTimerReadReg (CntPct, (VOID *)&SystemCount);
return SystemCount;
}
UINTN
EFIAPI
ArmArchTimerGetTimerCtrlReg (
VOID
)
{
UINTN Val;
ArmArchTimerReadReg (CntpCtl, (VOID *)&Val);
return Val;
}
VOID
EFIAPI
ArmArchTimerSetTimerCtrlReg (
UINTN Val
)
{
ArmArchTimerWriteReg (CntpCtl, (VOID *)&Val);
}
VOID
EFIAPI
ArmArchTimerSetCompareVal (
IN UINT64 Val
)
{
ArmArchTimerWriteReg (CntpCval, (VOID *)&Val);
}

View File

@@ -0,0 +1,119 @@
#------------------------------------------------------------------------------
#
# Copyright (c) 2011, ARM Limited. All rights reserved.
#
# This program and the accompanying materials
# are licensed and made available under the terms and conditions of the BSD License
# which accompanies this distribution. The full text of the license may be found at
# http://opensource.org/licenses/bsd-license.php
#
# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
#
#------------------------------------------------------------------------------
.text
.align 2
GCC_ASM_EXPORT (ArmReadCntFrq)
GCC_ASM_EXPORT (ArmWriteCntFrq)
GCC_ASM_EXPORT (ArmReadCntPct)
GCC_ASM_EXPORT (ArmReadCntkCtl)
GCC_ASM_EXPORT (ArmWriteCntkCtl)
GCC_ASM_EXPORT (ArmReadCntpTval)
GCC_ASM_EXPORT (ArmWriteCntpTval)
GCC_ASM_EXPORT (ArmReadCntpCtl)
GCC_ASM_EXPORT (ArmWriteCntpCtl)
GCC_ASM_EXPORT (ArmReadCntvTval)
GCC_ASM_EXPORT (ArmWriteCntvTval)
GCC_ASM_EXPORT (ArmReadCntvCtl)
GCC_ASM_EXPORT (ArmWriteCntvCtl)
GCC_ASM_EXPORT (ArmReadCntvCt)
GCC_ASM_EXPORT (ArmReadCntpCval)
GCC_ASM_EXPORT (ArmWriteCntpCval)
GCC_ASM_EXPORT (ArmReadCntvCval)
GCC_ASM_EXPORT (ArmWriteCntvCval)
GCC_ASM_EXPORT (ArmReadCntvOff)
GCC_ASM_EXPORT (ArmWriteCntvOff)
ASM_PFX(ArmReadCntFrq):
mrc p15, 0, r0, c14, c0, 0 @ Read CNTFRQ
bx lr
ASM_PFX(ArmWriteCntFrq):
mcr p15, 0, r0, c14, c0, 0 @ Write to CNTFRQ
bx lr
ASM_PFX(ArmReadCntPct):
mrrc p15, 0, r0, r1, c14 @ Read CNTPT (Physical counter register)
bx lr
ASM_PFX(ArmReadCntkCtl):
mrc p15, 0, r0, c14, c1, 0 @ Read CNTK_CTL (Timer PL1 Control Register)
bx lr
ASM_PFX(ArmWriteCntkCtl):
mcr p15, 0, r0, c14, c1, 0 @ Write to CNTK_CTL (Timer PL1 Control Register)
bx lr
ASM_PFX(ArmReadCntpTval):
mrc p15, 0, r0, c14, c2, 0 @ Read CNTP_TVAL (PL1 physical timer value register)
bx lr
ASM_PFX(ArmWriteCntpTval):
mcr p15, 0, r0, c14, c2, 0 @ Write to CNTP_TVAL (PL1 physical timer value register)
bx lr
ASM_PFX(ArmReadCntpCtl):
mrc p15, 0, r0, c14, c2, 1 @ Read CNTP_CTL (PL1 Physical Timer Control Register)
bx lr
ASM_PFX(ArmWriteCntpCtl):
mcr p15, 0, r0, c14, c2, 1 @ Write to CNTP_CTL (PL1 Physical Timer Control Register)
bx lr
ASM_PFX(ArmReadCntvTval):
mrc p15, 0, r0, c14, c3, 0 @ Read CNTV_TVAL (Virtual Timer Value register)
bx lr
ASM_PFX(ArmWriteCntvTval):
mcr p15, 0, r0, c14, c3, 0 @ Write to CNTV_TVAL (Virtual Timer Value register)
bx lr
ASM_PFX(ArmReadCntvCtl):
mrc p15, 0, r0, c14, c3, 1 @ Read CNTV_CTL (Virtual Timer Control Register)
bx lr
ASM_PFX(ArmWriteCntvCtl):
mcr p15, 0, r0, c14, c3, 1 @ Write to CNTV_CTL (Virtual Timer Control Register)
bx lr
ASM_PFX(ArmReadCntvCt):
mrrc p15, 1, r0, r1, c14 @ Read CNTVCT (Virtual Count Register)
bx lr
ASM_PFX(ArmReadCntpCval):
mrrc p15, 2, r0, r1, c14 @ Read CNTP_CTVAL (Physical Timer Compare Value Register)
bx lr
ASM_PFX(ArmWriteCntpCval):
mcrr p15, 2, r0, r1, c14 @ Write to CNTP_CTVAL (Physical Timer Compare Value Register)
bx lr
ASM_PFX(ArmReadCntvCval):
mrrc p15, 3, r0, r1, c14 @ Read CNTV_CTVAL (Virtual Timer Compare Value Register)
bx lr
ASM_PFX(ArmWriteCntvCval):
mcrr p15, 3, r0, r1, c14 @ write to CNTV_CTVAL (Virtual Timer Compare Value Register)
bx lr
ASM_PFX(ArmReadCntvOff):
mrrc p15, 4, r0, r1, c14 @ Read CNTVOFF (virtual Offset register)
bx lr
ASM_PFX(ArmWriteCntvOff):
mcrr p15, 4, r0, r1, c14 @ Write to CNTVOFF (Virtual Offset register)
bx lr
ASM_FUNCTION_REMOVE_IF_UNREFERENCED

View File

@@ -0,0 +1,119 @@
//------------------------------------------------------------------------------
//
// Copyright (c) 2011, ARM Limited. All rights reserved.
//
// This program and the accompanying materials
// are licensed and made available under the terms and conditions of the BSD License
// which accompanies this distribution. The full text of the license may be found at
// http://opensource.org/licenses/bsd-license.php
//
// THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
// WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
//
//------------------------------------------------------------------------------
EXPORT ArmReadCntFrq
EXPORT ArmWriteCntFrq
EXPORT ArmReadCntPct
EXPORT ArmReadCntkCtl
EXPORT ArmWriteCntkCtl
EXPORT ArmReadCntpTval
EXPORT ArmWriteCntpTval
EXPORT ArmReadCntpCtl
EXPORT ArmWriteCntpCtl
EXPORT ArmReadCntvTval
EXPORT ArmWriteCntvTval
EXPORT ArmReadCntvCtl
EXPORT ArmWriteCntvCtl
EXPORT ArmReadCntvCt
EXPORT ArmReadCntpCval
EXPORT ArmWriteCntpCval
EXPORT ArmReadCntvCval
EXPORT ArmWriteCntvCval
EXPORT ArmReadCntvOff
EXPORT ArmWriteCntvOff
AREA ArmV7ArchTimerSupport, CODE, READONLY
PRESERVE8
ArmReadCntFrq
mrc p15, 0, r0, c14, c0, 0 ; Read CNTFRQ
bx lr
ArmWriteCntFrq
mcr p15, 0, r0, c14, c0, 0 ; Write to CNTFRQ
bx lr
ArmReadCntPct
mrrc p15, 0, r0, r1, c14 ; Read CNTPT (Physical counter register)
bx lr
ArmReadCntkCtl
mrc p15, 0, r0, c14, c1, 0 ; Read CNTK_CTL (Timer PL1 Control Register)
bx lr
ArmWriteCntkCtl
mcr p15, 0, r0, c14, c1, 0 ; Write to CNTK_CTL (Timer PL1 Control Register)
bx lr
ArmReadCntpTval
mrc p15, 0, r0, c14, c2, 0 ; Read CNTP_TVAL (PL1 physical timer value register)
bx lr
ArmWriteCntpTval
mcr p15, 0, r0, c14, c2, 0 ; Write to CNTP_TVAL (PL1 physical timer value register)
bx lr
ArmReadCntpCtl
mrc p15, 0, r0, c14, c2, 1 ; Read CNTP_CTL (PL1 Physical Timer Control Register)
bx lr
ArmWriteCntpCtl
mcr p15, 0, r0, c14, c2, 1 ; Write to CNTP_CTL (PL1 Physical Timer Control Register)
bx lr
ArmReadCntvTval
mrc p15, 0, r0, c14, c3, 0 ; Read CNTV_TVAL (Virtual Timer Value register)
bx lr
ArmWriteCntvTval
mcr p15, 0, r0, c14, c3, 0 ; Write to CNTV_TVAL (Virtual Timer Value register)
bx lr
ArmReadCntvCtl
mrc p15, 0, r0, c14, c3, 1 ; Read CNTV_CTL (Virtual Timer Control Register)
bx lr
ArmWriteCntvCtl
mcr p15, 0, r0, c14, c3, 1 ; Write to CNTV_CTL (Virtual Timer Control Register)
bx lr
ArmReadCntvCt
mrrc p15, 1, r0, r1, c14 ; Read CNTVCT (Virtual Count Register)
bx lr
ArmReadCntpCval
mrrc p15, 2, r0, r1, c14 ; Read CNTP_CTVAL (Physical Timer Compare Value Register)
bx lr
ArmWriteCntpCval
mcrr p15, 2, r0, r1, c14 ; Write to CNTP_CTVAL (Physical Timer Compare Value Register)
bx lr
ArmReadCntvCval
mrrc p15, 3, r0, r1, c14 ; Read CNTV_CTVAL (Virtual Timer Compare Value Register)
bx lr
ArmWriteCntvCval
mcrr p15, 3, r0, r1, c14 ; write to CNTV_CTVAL (Virtual Timer Compare Value Register)
bx lr
ArmReadCntvOff
mrrc p15, 4, r0, r1, c14 ; Read CNTVOFF (virtual Offset register)
bx lr
ArmWriteCntvOff
mcrr p15, 4, r0, r1, c14 ; Write to CNTVOFF (Virtual Offset register)
bx lr
END

View File

@@ -35,6 +35,10 @@
ArmV7Lib.c
ArmV7Mmu.c
ArmV7ArchTimer.c
ArmV7ArchTimerSupport.S | GCC
ArmV7ArchTimerSupport.asm | RVCT
[Packages]
ArmPkg/ArmPkg.dec
MdePkg/MdePkg.dec

View File

@@ -34,6 +34,10 @@
ArmV7Lib.c
ArmV7Mmu.c
ArmV7ArchTimer.c
ArmV7ArchTimerSupport.S | GCC
ArmV7ArchTimerSupport.asm | RVCT
[Packages]
ArmPkg/ArmPkg.dec

View File

@@ -31,6 +31,10 @@
ArmV7Support.asm | RVCT
ArmV7Lib.c
ArmV7ArchTimer.c
ArmV7ArchTimerSupport.S | GCC
ArmV7ArchTimerSupport.asm | RVCT
[Packages]
ArmPkg/ArmPkg.dec