mirror of https://github.com/wolfSSL/wolfBoot.git
Progress on adding NXP QorIQ P1021 support.
parent
e88a7dcae3
commit
022b8d3c13
40
INSTALL.md
40
INSTALL.md
|
@ -19,38 +19,48 @@ https://github.com/wolfSSL/wolfssl/archive/master.zip
|
|||
|
||||
1. Extract wolfBoot
|
||||
2. `cd wolfBoot/lib`
|
||||
3. Extact wolfSSL (should be named `lib/wolfssl`)
|
||||
3. Extract wolfSSL (should be named `lib/wolfssl`)
|
||||
|
||||
Directory should look like:
|
||||
|
||||
```
|
||||
wolfBoot
|
||||
-> config
|
||||
-> docs
|
||||
-> hal
|
||||
-> examples (sample configurations)
|
||||
-> docs (markdown docs)
|
||||
-> hal (Hardware target abstractions)
|
||||
-> spi
|
||||
-> uart
|
||||
-> IDE
|
||||
-> include
|
||||
-> lib
|
||||
-> lib (wolfSSL and wolfTPM submodules)
|
||||
-> wolfssl
|
||||
-> src
|
||||
-> wolfcrypt/src
|
||||
-> src
|
||||
-> test-app
|
||||
-> tools
|
||||
-> image.c (crypto verify/hash)
|
||||
-> loader.c (main)
|
||||
-> libwolfboot.c (User application API’s)
|
||||
-> update_*.c (flash/ram wolfBoot_start)
|
||||
-> test-app (example applications)
|
||||
-> tools
|
||||
-> keytools (signing and key generation tools)
|
||||
```
|
||||
|
||||
## Configuration
|
||||
|
||||
Use `make config` to walk-through setting up the platform, architecture and partition settings.
|
||||
OR
|
||||
Use the `config/examples` as a template to wolfBoot root as `.config`.
|
||||
Use the `config/examples` as a template to wolfBoot root as `.config`.
|
||||
Example: `cp ./config/examples/zynqmp.config .config`
|
||||
|
||||
## Setup the Key
|
||||
|
||||
Use the key generation tool in `tools/keytool` or get existing keys.
|
||||
Copy `rsa4096.der` to wolfBoot root
|
||||
Copy `rsa4096_pub_key.c` to `./src`
|
||||
Build the key tools: `make keytools`
|
||||
|
||||
The key generation is handled the first time you use `make`, however we do provide some tools to help use existing keys.
|
||||
See tools in `tools/keytool`. Public key(s) are populated into the `src/keystore.c`.
|
||||
The signing key used goes into wolfBoot root (example `rsa4096.der`).
|
||||
|
||||
## Building
|
||||
|
||||
|
@ -58,6 +68,16 @@ Copy `rsa4096_pub_key.c` to `./src`
|
|||
make
|
||||
```
|
||||
|
||||
The “make [target]”
|
||||
* `keytools`: Build the C version of the key tools
|
||||
* `wolfboot.bin`: Build the .elf and .bin version of the bootloader only
|
||||
* `test-app/image.bin`: Builds the test application
|
||||
* `test-app/image_v1_signed.bin`: Builds the test application signed with version 1
|
||||
* `factory.bin`: Builds bootloader and test application signed and appended together
|
||||
|
||||
Note: Default is “factory.bin”
|
||||
|
||||
|
||||
## Building with Cross Compile
|
||||
|
||||
QNX Example:
|
||||
|
|
21
README.md
21
README.md
|
@ -1,4 +1,5 @@
|
|||
# wolfBoot
|
||||
|
||||
wolfSSL Secure Bootloader ([Home page](https://www.wolfssl.com/products/wolfboot/))
|
||||
|
||||
wolfBoot is a portable, OS-agnostic, secure bootloader solution for 32-bit microcontrollers,
|
||||
|
@ -8,7 +9,6 @@ Due to the minimalist design of the bootloader and the tiny HAL API, wolfBoot is
|
|||
from any OS or bare-metal application, and can be easily ported and integrated in existing embedded software
|
||||
projects to provide a secure firmware update mechanism.
|
||||
|
||||
|
||||
## Features
|
||||
- Multi-slot partitioning of the flash device
|
||||
- Integrity verification of the firmware image(s)
|
||||
|
@ -93,16 +93,19 @@ For more detailed information about firmware update implementation, see [Firmwar
|
|||
|
||||
### Makefile
|
||||
|
||||
To build using the Makefile, create a `.config` file with your build specifications in the wolfBoot root directory. You can find a
|
||||
To build using the Makefile, create a `.config` file with your build specifications in the wolfBoot root directory. You can find a
|
||||
number of examples that you can use inside [config/examples](config/examples). Then run `make keytools` to generate the signing
|
||||
and key generation tools. If you have wolfCrypt-py installed and would like to use it, you can skip this step.
|
||||
and key generation tools. If you have wolfCrypt-py installed and would like to use it, you can skip this step.
|
||||
|
||||
Documentation for the flash configuration options used in `.config` can be found in [docs/compile.md](docs/compile.md).
|
||||
|
||||
For example, to build using our provided `stm32h7.config`:
|
||||
|
||||
```
|
||||
cp config/examples/stm32h7.config .config
|
||||
make keytools
|
||||
make
|
||||
```
|
||||
```
|
||||
|
||||
### CMake
|
||||
|
||||
|
@ -116,7 +119,7 @@ $ mkdir build
|
|||
$ cd build
|
||||
$ cmake -DWOLFBOOT_TARGET=stm32h7 -DBUILD_TEST_APPS=yes -DWOLFBOOT_PARTITION_BOOT_ADDRESS=0x8020000 -DWOLFBOOT_SECTOR_SIZE=0x20000 -DWOLFBOOT_PARTITION_SIZE=0xD0000 -DWOLFBOOT_PARTITION_UPDATE_ADDRESS=0x80F0000 -DWOLFBOOT_PARTITION_SWAP_ADDRESS=0x81C0000 ..
|
||||
$ make
|
||||
```
|
||||
```
|
||||
|
||||
The output should look something like:
|
||||
```
|
||||
|
@ -174,7 +177,7 @@ Selected cipher: ECC256
|
|||
Selected hash : SHA256
|
||||
Public key: /home/user/wolfBoot/build/wolfboot_signing_private_key.der
|
||||
Output image: /home/user/wolfBoot/build/test-app/image_v1_signed.bin
|
||||
Target partition id : 1
|
||||
Target partition id : 1
|
||||
Calculating SHA256 digest...
|
||||
Signing the digest...
|
||||
Output image(s) successfully created.
|
||||
|
@ -206,7 +209,7 @@ Selected cipher: ECC256
|
|||
Selected hash : SHA256
|
||||
Public key: /home/user/wolfBoot/build/wolfboot_signing_private_key.der
|
||||
Output image: /home/user/wolfBoot/build/test-app/image_v1_signed.bin
|
||||
Target partition id : 1
|
||||
Target partition id : 1
|
||||
Calculating SHA256 digest...
|
||||
Signing the digest...
|
||||
Output image(s) successfully created.
|
||||
|
@ -223,12 +226,12 @@ Signing and hashing algorithms can be specified with `-DSIGN=<alg>` and `-DHASH=
|
|||
options to configuring wolfBoot, add `-LAH` to your cmake command, along with the partition specifications.
|
||||
```
|
||||
$ cmake -DWOLFBOOT_TARGET=stm32h7 -DWOLFBOOT_PARTITION_BOOT_ADDRESS=0x8020000 -DWOLFBOOT_SECTOR_SIZE=0x20000 -DWOLFBOOT_PARTITION_SIZE=0xD0000 -DWOLFBOOT_PARTITION_UPDATE_ADDRESS=0x80F0000 -DWOLFBOOT_PARTITION_SWAP_ADDRESS=0x81C0000 -LAH ..
|
||||
```
|
||||
```
|
||||
|
||||
##### stm32f4
|
||||
```
|
||||
$ cmake -DWOLFBOOT_TARGET=stm32f4 -DWOLFBOOT_PARTITION_SIZE=0x20000 -DWOLFBOOT_SECTOR_SIZE=0x20000 -DWOLFBOOT_PARTITION_BOOT_ADDRESS=0x08020000 -DWOLFBOOT_PARTITION_UPDATE_ADDRESS=0x08040000 -DWOLFBOOT_PARTITION_SWAP_ADDRESS=0x08060000 ..
|
||||
```
|
||||
```
|
||||
|
||||
##### stm32u5
|
||||
```
|
||||
|
|
16
arch.mk
16
arch.mk
|
@ -274,6 +274,22 @@ ifeq ($(TARGET),nxp_t2080)
|
|||
endif
|
||||
endif
|
||||
|
||||
ifeq ($(TARGET),nxp_p1021)
|
||||
# Power PC big endian
|
||||
ARCH_FLAGS=-m32 -mhard-float -mcpu=e500mc
|
||||
CFLAGS+=$(ARCH_FLAGS) -DBIG_ENDIAN_ORDER
|
||||
CFLAGS+=-DMMU -DWOLFBOOT_DUALBOOT
|
||||
CFLAGS+=-pipe # use pipes instead of temp files
|
||||
CFLAGS+=-feliminate-unused-debug-types
|
||||
LDFLAGS+=$(ARCH_FLAGS)
|
||||
LDFLAGS+=-Wl,--hash-style=both # generate both sysv and gnu symbol hash table
|
||||
LDFLAGS+=-Wl,--as-needed # remove weak functions not used
|
||||
UPDATE_OBJS:=src/update_ram.o
|
||||
ifeq ($(SPMATH),1)
|
||||
MATH_OBJS += ./lib/wolfssl/wolfcrypt/src/sp_c32.o
|
||||
endif
|
||||
endif
|
||||
|
||||
ifeq ($(TARGET),ti_hercules)
|
||||
# HALCoGen Source and Include?
|
||||
CORTEX_R5=1
|
||||
|
|
|
@ -0,0 +1,52 @@
|
|||
ARCH=PPC
|
||||
TARGET=nxp_p1021
|
||||
SIGN?=ECC384
|
||||
HASH?=SHA384
|
||||
IMAGE_HEADER_SIZE?=512
|
||||
DEBUG?=0
|
||||
DEBUG_UART?=1
|
||||
VTOR?=1
|
||||
CORTEX_M0?=0
|
||||
NO_ASM?=0
|
||||
EXT_FLASH?=0
|
||||
SPI_FLASH?=0
|
||||
NO_XIP?=0
|
||||
UART_FLASH?=0
|
||||
ALLOW_DOWNGRADE?=0
|
||||
NVM_FLASH_WRITEONCE?=0
|
||||
WOLFBOOT_VERSION?=0
|
||||
NO_MPU?=0
|
||||
SPMATH?=1
|
||||
RAM_CODE?=1
|
||||
DUALBANK_SWAP?=0
|
||||
WOLFTPM?=0
|
||||
|
||||
# NAND Base Address
|
||||
ARCH_FLASH_OFFSET?=0xE8000000
|
||||
|
||||
# Flash Sector Size
|
||||
WOLFBOOT_SECTOR_SIZE=0x10000
|
||||
|
||||
# wolfBoot start address
|
||||
WOLFBOOT_ORIGIN=0xEFF40000
|
||||
# wolfBoot parition size (custom)
|
||||
BOOTLOADER_PARTITION_SIZE=0x20000
|
||||
|
||||
# Application Partition Size
|
||||
WOLFBOOT_PARTITION_SIZE?=0xA00000
|
||||
# Location in Flash for Application Partition
|
||||
WOLFBOOT_PARTITION_BOOT_ADDRESS?=0xE8080000
|
||||
# Load Partition to RAM Address
|
||||
WOLFBOOT_LOAD_ADDRESS?=0x19000
|
||||
|
||||
# Location in Flash for Update Partition
|
||||
WOLFBOOT_PARTITION_UPDATE_ADDRESS?=0xE8A80000
|
||||
|
||||
# Location of temporary sector used during updates
|
||||
WOLFBOOT_PARTITION_SWAP_ADDRESS?=0xE8060000
|
||||
|
||||
# DTS (Device Tree)
|
||||
WOLFBOOT_DTS_BOOT_ADDRESS?=0xE8040000
|
||||
WOLFBOOT_DTS_UPDATE_ADDRESS?=0xE8050000
|
||||
# DTS Load to RAM Address
|
||||
WOLFBOOT_LOAD_DTS_ADDRESS?=0x40000
|
|
@ -10,6 +10,7 @@ This README describes configuration of supported targets.
|
|||
* [NXP LPC54xxx](#nxp-lpc54xxx)
|
||||
* [NXP iMX-RT](#nxp-imx-rt)
|
||||
* [NXP Kinetis](#nxp-kinetis)
|
||||
* [NXP P1021 PPC](#nxp-p1021-ppc)
|
||||
* [NXP T2080 PPC](#nxp-t2080-ppc)
|
||||
* [Qemu x86-64 UEFI](#qemu-x86-64-uefi)
|
||||
* [SiFive HiFive1 RISC-V](#sifive-hifive1-risc-v)
|
||||
|
|
|
@ -0,0 +1,607 @@
|
|||
/* nxp_p1021.c
|
||||
*
|
||||
* Copyright (C) 2022 wolfSSL Inc.
|
||||
*
|
||||
* This file is part of wolfBoot.
|
||||
*
|
||||
* wolfBoot is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* wolfBoot is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
|
||||
*/
|
||||
#include <stdint.h>
|
||||
#include "target.h"
|
||||
#include "printf.h"
|
||||
|
||||
/* P1021 */
|
||||
#define CCSRBAR (0xFF700000)
|
||||
#define SYS_CLK (400000000)
|
||||
|
||||
/* P1021 PC16552D Dual UART */
|
||||
#define BAUD_RATE 115200
|
||||
#define UART_SEL 0 /* select UART 0 or 1 */
|
||||
|
||||
#define UART_BASE(n) (CCSRBAR + 0x4500 + (n * 0x100))
|
||||
|
||||
#define UART_RBR(n) *((volatile uint8_t*)(UART_BASE(n) + 0)) /* receiver buffer register */
|
||||
#define UART_THR(n) *((volatile uint8_t*)(UART_BASE(n) + 0)) /* transmitter holding register */
|
||||
#define UART_IER(n) *((volatile uint8_t*)(UART_BASE(n) + 1)) /* interrupt enable register */
|
||||
#define UART_IIR(n) *((volatile uint8_t*)(UART_BASE(n) + 2)) /* interrupt ID register */
|
||||
#define UART_FCR(n) *((volatile uint8_t*)(UART_BASE(n) + 2)) /* FIFO control register */
|
||||
#define UART_LCR(n) *((volatile uint8_t*)(UART_BASE(n) + 3)) /* line control register */
|
||||
#define UART_MCR(n) *((volatile uint8_t*)(UART_BASE(n) + 4)) /* modem control register */
|
||||
#define UART_LSR(n) *((volatile uint8_t*)(UART_BASE(n) + 5)) /* line status register */
|
||||
|
||||
/* enabled when UART_LCR_DLAB set */
|
||||
#define UART_DLB(n) *((volatile uint8_t*)(UART_BASE(n) + 0)) /* divisor least significant byte register */
|
||||
#define UART_DMB(n) *((volatile uint8_t*)(UART_BASE(n) + 1)) /* divisor most significant byte register */
|
||||
|
||||
#define UART_FCR_TFR (0x04) /* Transmitter FIFO reset */
|
||||
#define UART_FCR_RFR (0x02) /* Receiver FIFO reset */
|
||||
#define UART_FCR_FEN (0x01) /* FIFO enable */
|
||||
#define UART_LCR_DLAB (0x80) /* Divisor latch access bit */
|
||||
#define UART_LCR_WLS (0x03) /* Word length select: 8-bits */
|
||||
#define UART_LSR_TEMT (0x40) /* Transmitter empty */
|
||||
#define UART_LSR_THRE (0x20) /* Transmitter holding register empty */
|
||||
|
||||
/* P1021 LAW - Local Access Window (Memory Map) - RM 2.4 */
|
||||
#define LAWBAR_BASE(n) (CCSRBAR + 0xC00 + (n * 0x10))
|
||||
#define LAWBARHn(n) *((volatile uint32_t*)(LAWBAR_BASE(n) + 0x0))
|
||||
#define LAWBARLn(n) *((volatile uint32_t*)(LAWBAR_BASE(n) + 0x4))
|
||||
#define LAWBARn(n) *((volatile uint32_t*)(LAWBAR_BASE(n) + 0x8))
|
||||
|
||||
#define LAWBARn_ENABLE (1<<31)
|
||||
#define LAWBARn_TRGT_ID(id) (id<<20)
|
||||
|
||||
/* P1021 Global Source/Target ID Assignments - RM Table 2-7 */
|
||||
enum law_target_id {
|
||||
LAW_TRGT_DDR = 0x0F,
|
||||
LAW_TRGT_IFC = 0x1F, /* Integrated Flash Controller */
|
||||
};
|
||||
|
||||
/* P1021 2.4.3 - size is equal to 2^(enum + 1) */
|
||||
enum law_sizes {
|
||||
LAW_SIZE_4KB = 0x0B,
|
||||
LAW_SIZE_8KB,
|
||||
LAW_SIZE_16KB,
|
||||
LAW_SIZE_32KB,
|
||||
LAW_SIZE_64KB,
|
||||
LAW_SIZE_128KB, /* 0x10 */
|
||||
LAW_SIZE_256KB,
|
||||
LAW_SIZE_512KB,
|
||||
LAW_SIZE_1MB,
|
||||
LAW_SIZE_2MB,
|
||||
LAW_SIZE_4MB,
|
||||
LAW_SIZE_8MB,
|
||||
LAW_SIZE_16MB,
|
||||
LAW_SIZE_32MB,
|
||||
LAW_SIZE_64MB,
|
||||
LAW_SIZE_128MB,
|
||||
LAW_SIZE_256MB, /* 0x1B */
|
||||
LAW_SIZE_512MB,
|
||||
LAW_SIZE_1GB,
|
||||
LAW_SIZE_2GB,
|
||||
LAW_SIZE_4GB,
|
||||
LAW_SIZE_8GB, /* 0x20 */
|
||||
LAW_SIZE_16GB,
|
||||
LAW_SIZE_32GB,
|
||||
LAW_SIZE_64GB,
|
||||
LAW_SIZE_128GB,
|
||||
LAW_SIZE_256GB,
|
||||
LAW_SIZE_512GB,
|
||||
LAW_SIZE_1TB,
|
||||
};
|
||||
|
||||
|
||||
/* MMU Assist Registers E6500RM 2.13.10 */
|
||||
#define MAS0_TLBSEL_MSK 0x30000000
|
||||
#define MAS0_TLBSEL(x) (((x) << 28) & MAS0_TLBSEL_MSK)
|
||||
#define MAS0_ESEL_MSK 0x0FFF0000
|
||||
#define MAS0_ESEL(x) (((x) << 16) & MAS0_ESEL_MSK)
|
||||
#define MAS0_NV(x) ((x) & 0x00000FFF)
|
||||
|
||||
#define MAS1_VALID 0x80000000
|
||||
#define MAS1_IPROT 0x40000000
|
||||
#define MAS1_TID(x) (((x) << 16) & 0x3FFF0000)
|
||||
#define MAS1_TS 0x00001000
|
||||
#define MAS1_TSIZE(x) (((x) << 7) & 0x00000F80)
|
||||
#define TSIZE_TO_BYTES(x) (1ULL << ((x) + 10))
|
||||
|
||||
#define MAS2_EPN 0xFFFFF000
|
||||
#define MAS2_X0 0x00000040
|
||||
#define MAS2_X1 0x00000020
|
||||
#define MAS2_W 0x00000010
|
||||
#define MAS2_I 0x00000008
|
||||
#define MAS2_M 0x00000004
|
||||
#define MAS2_G 0x00000002
|
||||
#define MAS2_E 0x00000001
|
||||
|
||||
#define MAS3_RPN 0xFFFFF000
|
||||
#define MAS3_U0 0x00000200
|
||||
#define MAS3_U1 0x00000100
|
||||
#define MAS3_U2 0x00000080
|
||||
#define MAS3_U3 0x00000040
|
||||
#define MAS3_UX 0x00000020
|
||||
#define MAS3_SX 0x00000010
|
||||
#define MAS3_UW 0x00000008
|
||||
#define MAS3_SW 0x00000004
|
||||
#define MAS3_UR 0x00000002
|
||||
#define MAS3_SR 0x00000001
|
||||
|
||||
#define MAS7_RPN 0xFFFFFFFF
|
||||
|
||||
#define BOOKE_PAGESZ_4K 2
|
||||
#define BOOKE_PAGESZ_16M 14
|
||||
#define BOOKE_PAGESZ_256M 18
|
||||
#define BOOKE_PAGESZ_2G 21
|
||||
|
||||
#define BOOKE_MAS0(tlbsel,esel,nv) \
|
||||
(MAS0_TLBSEL(tlbsel) | MAS0_ESEL(esel) | MAS0_NV(nv))
|
||||
#define BOOKE_MAS1(v,iprot,tid,ts,tsize) \
|
||||
((((v) << 31) & MAS1_VALID) | \
|
||||
(((iprot) << 30) & MAS1_IPROT) | \
|
||||
(MAS1_TID(tid)) | \
|
||||
(((ts) << 12) & MAS1_TS) | \
|
||||
(MAS1_TSIZE(tsize)))
|
||||
#define BOOKE_MAS2(epn, wimge) \
|
||||
(((epn) & MAS3_RPN) | (wimge))
|
||||
#define BOOKE_MAS3(rpn, user, perms) \
|
||||
(((rpn) & MAS3_RPN) | (user) | (perms))
|
||||
#define BOOKE_MAS7(rpn) \
|
||||
(((uint64_t)(rpn)) >> 32)
|
||||
|
||||
|
||||
/* P1021 IFC (Integrated Flash Controller) - RM 13.3 */
|
||||
#define IFC_BASE (CCSRBAR + 0x00124000)
|
||||
#define IFC_MAX_BANKS 8
|
||||
|
||||
#define IFC_CSPR_EXT(n) *((volatile uint32_t*)(IFC_BASE + 0x000C + (n * 0xC))) /* Extended Base Address */
|
||||
#define IFC_CSPR(n) *((volatile uint32_t*)(IFC_BASE + 0x0010 + (n * 0xC))) /* Chip-select Property */
|
||||
#define IFC_AMASK(n) *((volatile uint32_t*)(IFC_BASE + 0x00A0 + (n * 0xC)))
|
||||
#define IFC_CSOR(n) *((volatile uint32_t*)(IFC_BASE + 0x0130 + (n * 0xC)))
|
||||
#define IFC_CSOR_EXT(n) *((volatile uint32_t*)(IFC_BASE + 0x0134 + (n * 0xC)))
|
||||
#define IFC_FTIM0(n) *((volatile uint32_t*)(IFC_BASE + 0x01C0 + (n * 0x30)))
|
||||
#define IFC_FTIM1(n) *((volatile uint32_t*)(IFC_BASE + 0x01C4 + (n * 0x30)))
|
||||
#define IFC_FTIM2(n) *((volatile uint32_t*)(IFC_BASE + 0x01C8 + (n * 0x30)))
|
||||
#define IFC_FTIM3(n) *((volatile uint32_t*)(IFC_BASE + 0x01CC + (n * 0x30)))
|
||||
|
||||
#define IFC_CSPR_PHYS_ADDR(x) (((uint32_t)x) & 0xFFFF0000) /* Physical base address */
|
||||
#define IFC_CSPR_PORT_SIZE_8 0x00000080 /* Port Size 8 */
|
||||
#define IFC_CSPR_PORT_SIZE_16 0x00000100 /* Port Size 16 */
|
||||
#define IFC_CSPR_WP 0x00000040 /* Write Protect */
|
||||
#define IFC_CSPR_MSEL_NOR 0x00000000 /* Mode Select - NOR */
|
||||
#define IFC_CSPR_MSEL_NAND 0x00000002 /* Mode Select - NAND */
|
||||
#define IFC_CSPR_MSEL_GPCM 0x00000004 /* Mode Select - GPCM (General-purpose chip-select machine) */
|
||||
#define IFC_CSPR_V 0x00000001 /* Bank Valid */
|
||||
|
||||
/* NAND Timings (IFC clocks) */
|
||||
#define IFC_FTIM0_NOR_TACSE(n) (((n) & 0x0F) << 28) /* After address hold cycle */
|
||||
#define IFC_FTIM0_NOR_TEADC(n) (((n) & 0x3F) << 16) /* External latch address delay cycles */
|
||||
#define IFC_FTIM0_NOR_TAVDS(n) (((n) & 0x3F) << 8) /* Delay between CS assertion */
|
||||
#define IFC_FTIM0_NOR_TEAHC(n) (((n) & 0x3F) << 0) /* External latch address hold cycles */
|
||||
#define IFC_FTIM1_NOR_TACO(n) (((n) & 0xFF) << 24) /* CS assertion to output enable */
|
||||
#define IFC_FTIM1_NOR_TRAD(n) (((n) & 0x3F) << 8) /* read access delay */
|
||||
#define IFC_FTIM1_NOR_TSEQ(n) (((n) & 0x3F) << 0) /* sequential read access delay */
|
||||
#define IFC_FTIM2_NOR_TCS(n) (((n) & 0x0F) << 24) /* Chip-select assertion setup time */
|
||||
#define IFC_FTIM2_NOR_TCH(n) (((n) & 0x0F) << 18) /* Chip-select hold time */
|
||||
#define IFC_FTIM2_NOR_TWPH(n) (((n) & 0x3F) << 10) /* Chip-select hold time */
|
||||
#define IFC_FTIM2_NOR_TWP(n) (((n) & 0xFF) << 0) /* Write enable pulse width */
|
||||
|
||||
/* GPCM Timings (IFC clocks) */
|
||||
#define IFC_FTIM0_GPCM_TACSE(n) (((n) & 0x0F) << 28) /* After address hold cycle */
|
||||
#define IFC_FTIM0_GPCM_TEADC(n) (((n) & 0x3F) << 16) /* External latch address delay cycles */
|
||||
#define IFC_FTIM0_GPCM_TEAHC(n) (((n) & 0x3F) << 0) /* External latch address hold cycles */
|
||||
#define IFC_FTIM1_GPCM_TACO(n) (((n) & 0xFF) << 24) /* CS assertion to output enable */
|
||||
#define IFC_FTIM1_GPCM_TRAD(n) (((n) & 0x3F) << 8) /* read access delay */
|
||||
#define IFC_FTIM2_GPCM_TCS(n) (((n) & 0x0F) << 24) /* Chip-select assertion setup time */
|
||||
#define IFC_FTIM2_GPCM_TCH(n) (((n) & 0x0F) << 18) /* Chip-select hold time */
|
||||
#define IFC_FTIM2_GPCM_TWP(n) (((n) & 0xFF) << 0) /* Write enable pulse width */
|
||||
|
||||
/* IFC AMASK - RM Table 13-3 - Count of MSB minus 1 */
|
||||
enum ifc_amask_sizes {
|
||||
IFC_AMASK_64KB = 0xFFFF,
|
||||
IFC_AMASK_128KB = 0xFFFE,
|
||||
IFC_AMASK_256KB = 0xFFFC,
|
||||
IFC_AMASK_512KB = 0xFFF8,
|
||||
IFC_AMASK_1MB = 0xFFF0,
|
||||
IFC_AMASK_2MB = 0xFFC0,
|
||||
IFC_AMASK_4MB = 0xFF80,
|
||||
IFC_AMASK_8MB = 0xFF00,
|
||||
IFC_AMASK_16MB = 0xFE00,
|
||||
IFC_AMASK_32MB = 0xFC00,
|
||||
IFC_AMASK_128MB = 0xF800,
|
||||
IFC_AMASK_256MB = 0xF000,
|
||||
IFC_AMASK_512MB = 0xE000,
|
||||
IFC_AMASK_1GB = 0xC000,
|
||||
IFC_AMASK_2GB = 0x8000,
|
||||
IFC_AMASK_4GB = 0x0000,
|
||||
};
|
||||
|
||||
|
||||
/* NAND Flash */
|
||||
#define FLASH_BASE 0xFC000000
|
||||
|
||||
#define FLASH_BANK_SIZE (64*1024*1024)
|
||||
#define FLASH_PAGE_SIZE (1024) /* program buffer */
|
||||
#define FLASH_SECTOR_SIZE (128*1024)
|
||||
#define FLASH_SECTORS (FLASH_BANK_SIZE / FLASH_SECTOR_SIZE)
|
||||
#define FLASH_CFI_16BIT 0x02 /* word */
|
||||
#define FLASH_CFI_WIDTH FLASH_CFI_16BIT
|
||||
|
||||
#define FLASH_ERASE_TOUT 60000 /* Flash Erase Timeout (ms) */
|
||||
#define FLASH_WRITE_TOUT 500 /* Flash Write Timeout (ms) */
|
||||
|
||||
/* DDR */
|
||||
#if 0 /* DDR support not done */
|
||||
#define ENABLE_DDR
|
||||
#endif
|
||||
|
||||
/* DDR3: 512MB, 333.333 MHz (666.667 MT/s) */
|
||||
#define DDR_ADDRESS 0x00000000
|
||||
#define DDR_SIZE (512 * 1024 * 1024)
|
||||
#define DDR_N_RANKS 2
|
||||
#define DDR_RANK_DENS 0x100000000
|
||||
#define DDR_SDRAM_WIDTH 64
|
||||
#define DDR_EC_SDRAM_W 8
|
||||
#define DDR_N_ROW_ADDR 16
|
||||
#define DDR_N_COL_ADDR 10
|
||||
#define DDR_N_BANKS 8
|
||||
#define DDR_EDC_CONFIG 2
|
||||
#define DDR_BURSTL_MASK 0x0c
|
||||
#define DDR_TCKMIN_X_PS 1500
|
||||
#define DDR_TCMMAX_PS 3000
|
||||
#define DDR_CASLAT_X 0x000007E0
|
||||
#define DDR_TAA_PS 13500
|
||||
#define DDR_TRCD_PS 13500
|
||||
#define DDR_TRP_PS 13500
|
||||
#define DDR_TRAS_PS 36000
|
||||
#define DDR_TRC_PS 49500
|
||||
#define DDR_TFAW_PS 30000
|
||||
#define DDR_TWR_PS 15000
|
||||
#define DDR_TRFC_PS 260000
|
||||
#define DDR_TRRD_PS 6000
|
||||
#define DDR_TWTR_PS 7500
|
||||
#define DDR_TRTP_PS 7500
|
||||
#define DDR_REF_RATE_PS 7800000
|
||||
|
||||
#define DDR_CS0_BNDS_VAL 0x000000FF
|
||||
#define DDR_CS1_BNDS_VAL 0x010001FF
|
||||
#define DDR_CS2_BNDS_VAL 0x0300033F
|
||||
#define DDR_CS3_BNDS_VAL 0x0340037F
|
||||
#define DDR_CS0_CONFIG_VAL 0x80044402
|
||||
#define DDR_CS1_CONFIG_VAL 0x80044402
|
||||
#define DDR_CS2_CONFIG_VAL 0x00000202
|
||||
#define DDR_CS3_CONFIG_VAL 0x00040202
|
||||
#define DDR_CS_CONFIG_2_VAL 0x00000000
|
||||
|
||||
#define DDR_TIMING_CFG_0_VAL 0xFF530004
|
||||
#define DDR_TIMING_CFG_1_VAL 0x98906345
|
||||
#define DDR_TIMING_CFG_2_VAL 0x0040A114
|
||||
#define DDR_TIMING_CFG_3_VAL 0x010A1100
|
||||
#define DDR_TIMING_CFG_4_VAL 0x00000001
|
||||
#define DDR_TIMING_CFG_5_VAL 0x04402400
|
||||
|
||||
#define DDR_SDRAM_MODE_VAL 0x00441C70
|
||||
#define DDR_SDRAM_MODE_2_VAL 0x00980000
|
||||
#define DDR_SDRAM_MODE_3_8_VAL 0x00000000
|
||||
#define DDR_SDRAM_MD_CNTL_VAL 0x00000000
|
||||
|
||||
#define DDR_SDRAM_CFG_VAL 0xE7040000
|
||||
#define DDR_SDRAM_CFG_2_VAL 0x00401010
|
||||
|
||||
#define DDR_SDRAM_INTERVAL_VAL 0x0C300100
|
||||
#define DDR_DATA_INIT_VAL 0xDEADBEEF
|
||||
#define DDR_SDRAM_CLK_CNTL_VAL 0x02400000
|
||||
#define DDR_ZQ_CNTL_VAL 0x89080600
|
||||
|
||||
#define DDR_WRLVL_CNTL_VAL 0x8675F604
|
||||
#define DDR_WRLVL_CNTL_2_VAL 0x05060607
|
||||
#define DDR_WRLVL_CNTL_3_VAL 0x080A0A0B
|
||||
|
||||
#define DDR_SDRAM_RCW_1_VAL 0x00000000
|
||||
#define DDR_SDRAM_RCW_2_VAL 0x00000000
|
||||
|
||||
#define DDR_DDRCDR_1_VAL 0x80040000
|
||||
#define DDR_DDRCDR_2_VAL 0x00000001
|
||||
|
||||
#define DDR_ERR_INT_EN_VAL 0x0000001D
|
||||
#define DDR_ERR_SBE_VAL 0x00010000
|
||||
|
||||
|
||||
/* 12.4 DDR Memory Map */
|
||||
#define DDR_BASE (CCSRBAR + 0x8000)
|
||||
|
||||
#define DDR_CS_BNDS(n) *((volatile uint32_t*)(DDR_BASE + 0x000 + (n * 8))) /* Chip select n memory bounds */
|
||||
#define DDR_CS_CONFIG(n) *((volatile uint32_t*)(DDR_BASE + 0x080 + (n * 4))) /* Chip select n configuration */
|
||||
#define DDR_CS_CONFIG_2(n) *((volatile uint32_t*)(DDR_BASE + 0x0C0 + (n * 4))) /* Chip select n configuration 2 */
|
||||
#define DDR_SDRAM_CFG *((volatile uint32_t*)(DDR_BASE + 0x110)) /* DDR SDRAM control configuration */
|
||||
#define DDR_SDRAM_CFG_2 *((volatile uint32_t*)(DDR_BASE + 0x114)) /* DDR SDRAM control configuration 2 */
|
||||
#define DDR_SDRAM_INTERVAL *((volatile uint32_t*)(DDR_BASE + 0x124)) /* DDR SDRAM interval configuration */
|
||||
#define DDR_INIT_ADDR *((volatile uint32_t*)(DDR_BASE + 0x148)) /* DDR training initialization address */
|
||||
#define DDR_INIT_EXT_ADDR *((volatile uint32_t*)(DDR_BASE + 0x14C)) /* DDR training initialization extended address */
|
||||
#define DDR_DATA_INIT *((volatile uint32_t*)(DDR_BASE + 0x128)) /* DDR training initialization value */
|
||||
#define DDR_TIMING_CFG_0 *((volatile uint32_t*)(DDR_BASE + 0x104)) /* DDR SDRAM timing configuration 0 */
|
||||
#define DDR_TIMING_CFG_1 *((volatile uint32_t*)(DDR_BASE + 0x108)) /* DDR SDRAM timing configuration 1 */
|
||||
#define DDR_TIMING_CFG_2 *((volatile uint32_t*)(DDR_BASE + 0x10C)) /* DDR SDRAM timing configuration 2 */
|
||||
#define DDR_TIMING_CFG_3 *((volatile uint32_t*)(DDR_BASE + 0x100)) /* DDR SDRAM timing configuration 3 */
|
||||
#define DDR_TIMING_CFG_4 *((volatile uint32_t*)(DDR_BASE + 0x160)) /* DDR SDRAM timing configuration 4 */
|
||||
#define DDR_TIMING_CFG_5 *((volatile uint32_t*)(DDR_BASE + 0x164)) /* DDR SDRAM timing configuration 5 */
|
||||
#define DDR_TIMING_CFG_6 *((volatile uint32_t*)(DDR_BASE + 0x168)) /* DDR SDRAM timing configuration 6 */
|
||||
#define DDR_ZQ_CNTL *((volatile uint32_t*)(DDR_BASE + 0x170)) /* DDR ZQ calibration control */
|
||||
#define DDR_WRLVL_CNTL *((volatile uint32_t*)(DDR_BASE + 0x174)) /* DDR write leveling control */
|
||||
#define DDR_WRLVL_CNTL_2 *((volatile uint32_t*)(DDR_BASE + 0x190)) /* DDR write leveling control 2 */
|
||||
#define DDR_WRLVL_CNTL_3 *((volatile uint32_t*)(DDR_BASE + 0x194)) /* DDR write leveling control 3 */
|
||||
#define DDR_SR_CNTR *((volatile uint32_t*)(DDR_BASE + 0x17C)) /* DDR Self Refresh Counter */
|
||||
#define DDR_SDRAM_RCW_1 *((volatile uint32_t*)(DDR_BASE + 0x180)) /* DDR Register Control Word 1 */
|
||||
#define DDR_SDRAM_RCW_2 *((volatile uint32_t*)(DDR_BASE + 0x184)) /* DDR Register Control Word 2 */
|
||||
#define DDR_DDRCDR_1 *((volatile uint32_t*)(DDR_BASE + 0xB28)) /* DDR Control Driver Register 1 */
|
||||
#define DDR_DDRCDR_2 *((volatile uint32_t*)(DDR_BASE + 0xB2C)) /* DDR Control Driver Register 2 */
|
||||
#define DDR_DDRDSR_1 *((volatile uint32_t*)(DDR_BASE + 0xB20)) /* DDR Debug Status Register 1 */
|
||||
#define DDR_DDRDSR_2 *((volatile uint32_t*)(DDR_BASE + 0xB24)) /* DDR Debug Status Register 2 */
|
||||
#define DDR_ERR_DISABLE *((volatile uint32_t*)(DDR_BASE + 0xE44)) /* Memory error disable */
|
||||
#define DDR_ERR_INT_EN *((volatile uint32_t*)(DDR_BASE + 0xE48)) /* Memory error interrupt enable */
|
||||
#define DDR_ERR_SBE *((volatile uint32_t*)(DDR_BASE + 0xE58)) /* Single-Bit ECC memory error management */
|
||||
#define DDR_SDRAM_MODE *((volatile uint32_t*)(DDR_BASE + 0x118)) /* DDR SDRAM mode configuration */
|
||||
#define DDR_SDRAM_MODE_2 *((volatile uint32_t*)(DDR_BASE + 0x11C)) /* DDR SDRAM mode configuration 2 */
|
||||
#define DDR_SDRAM_MODE_3 *((volatile uint32_t*)(DDR_BASE + 0x200)) /* DDR SDRAM mode configuration 3 */
|
||||
#define DDR_SDRAM_MODE_4 *((volatile uint32_t*)(DDR_BASE + 0x204)) /* DDR SDRAM mode configuration 4 */
|
||||
#define DDR_SDRAM_MODE_5 *((volatile uint32_t*)(DDR_BASE + 0x208)) /* DDR SDRAM mode configuration 5 */
|
||||
#define DDR_SDRAM_MODE_6 *((volatile uint32_t*)(DDR_BASE + 0x20C)) /* DDR SDRAM mode configuration 6 */
|
||||
#define DDR_SDRAM_MODE_7 *((volatile uint32_t*)(DDR_BASE + 0x210)) /* DDR SDRAM mode configuration 7 */
|
||||
#define DDR_SDRAM_MODE_8 *((volatile uint32_t*)(DDR_BASE + 0x214)) /* DDR SDRAM mode configuration 8 */
|
||||
#define DDR_SDRAM_MD_CNTL *((volatile uint32_t*)(DDR_BASE + 0x120)) /* DDR SDRAM mode control */
|
||||
#define DDR_SDRAM_INTERVAL *((volatile uint32_t*)(DDR_BASE + 0x124)) /* DDR SDRAM interval configuration */
|
||||
#define DDR_SDRAM_CLK_CNTL *((volatile uint32_t*)(DDR_BASE + 0x130)) /* DDR SDRAM clock control */
|
||||
|
||||
#define DDR_SDRAM_CFG_MEM_EN 0x80000000 /* SDRAM interface logic is enabled */
|
||||
#define DDR_SDRAM_CFG2_D_INIT 0x00000010 /* data initialization in progress */
|
||||
|
||||
|
||||
#ifdef DEBUG_UART
|
||||
static void uart_init(void)
|
||||
{
|
||||
/* calc divisor for UART
|
||||
* example config values:
|
||||
* clock_div, baud, base_clk 163 115200 300000000
|
||||
* +0.5 to round up
|
||||
*/
|
||||
uint32_t div = (((SYS_CLK / 2.0) / (16 * BAUD_RATE)) + 0.5);
|
||||
|
||||
while (!(UART_LSR(UART_SEL) & UART_LSR_TEMT))
|
||||
;
|
||||
|
||||
/* set ier, fcr, mcr */
|
||||
UART_IER(UART_SEL) = 0;
|
||||
UART_FCR(UART_SEL) = (UART_FCR_TFR | UART_FCR_RFR | UART_FCR_FEN);
|
||||
|
||||
/* enable baud rate access (DLAB=1) - divisor latch access bit*/
|
||||
UART_LCR(UART_SEL) = (UART_LCR_DLAB | UART_LCR_WLS);
|
||||
/* set divisor */
|
||||
UART_DLB(UART_SEL) = (div & 0xff);
|
||||
UART_DMB(UART_SEL) = ((div>>8) & 0xff);
|
||||
/* disable rate access (DLAB=0) */
|
||||
UART_LCR(UART_SEL) = (UART_LCR_WLS);
|
||||
}
|
||||
|
||||
void uart_write(const char* buf, uint32_t sz)
|
||||
{
|
||||
uint32_t pos = 0;
|
||||
while (sz-- > 0) {
|
||||
while (!(UART_LSR(UART_SEL) & UART_LSR_THRE))
|
||||
;
|
||||
UART_THR(UART_SEL) = buf[pos++];
|
||||
}
|
||||
}
|
||||
#endif /* DEBUG_UART */
|
||||
|
||||
/* called from boot_ppc_start.S */
|
||||
void law_init(void)
|
||||
{
|
||||
/* IFC - NAND Flash */
|
||||
LAWBARn (1) = 0; /* reset */
|
||||
LAWBARHn(1) = FLASH_BASE;
|
||||
LAWBARLn(1) = FLASH_BASE;
|
||||
LAWBARn (1) = LAWBARn_ENABLE | LAWBARn_TRGT_ID(LAW_TRGT_IFC) | LAW_SIZE_128MB;
|
||||
|
||||
}
|
||||
|
||||
extern void write_tlb(uint32_t mas0, uint32_t mas1, uint32_t mas2, uint32_t mas3,
|
||||
uint32_t mas7);
|
||||
|
||||
void set_tlb(uint8_t tlb, uint8_t esel, uint32_t epn, uint64_t rpn,
|
||||
uint8_t perms, uint8_t wimge,
|
||||
uint8_t ts, uint8_t tsize, uint8_t iprot)
|
||||
{
|
||||
uint32_t _mas0, _mas1, _mas2, _mas3, _mas7;
|
||||
|
||||
_mas0 = BOOKE_MAS0(tlb, esel, 0);
|
||||
_mas1 = BOOKE_MAS1(1, iprot, 0, ts, tsize);
|
||||
_mas2 = BOOKE_MAS2(epn, wimge);
|
||||
_mas3 = BOOKE_MAS3(rpn, 0, perms);
|
||||
_mas7 = BOOKE_MAS7(rpn);
|
||||
|
||||
write_tlb(_mas0, _mas1, _mas2, _mas3, _mas7);
|
||||
}
|
||||
|
||||
static void hal_flash_init(void)
|
||||
{
|
||||
/* NAND IFC Flash Timing Parameters */
|
||||
IFC_FTIM0(0) = (IFC_FTIM0_NOR_TACSE(4) | \
|
||||
IFC_FTIM0_NOR_TEADC(5) | \
|
||||
IFC_FTIM0_NOR_TEAHC(5));
|
||||
IFC_FTIM1(0) = (IFC_FTIM1_NOR_TACO(53) |
|
||||
IFC_FTIM1_NOR_TRAD(26) |
|
||||
IFC_FTIM1_NOR_TSEQ(19));
|
||||
IFC_FTIM2(0) = (IFC_FTIM2_NOR_TCS(4) |
|
||||
IFC_FTIM2_NOR_TCH(4) |
|
||||
IFC_FTIM2_NOR_TWPH(14) |
|
||||
IFC_FTIM2_NOR_TWP(28));
|
||||
IFC_FTIM3(0) = 0;
|
||||
/* NAND IFC Definitions (CS0) */
|
||||
IFC_CSPR_EXT(0) = (0xF);
|
||||
IFC_CSPR(0) = (IFC_CSPR_PHYS_ADDR(FLASH_BASE) | \
|
||||
IFC_CSPR_PORT_SIZE_16 | \
|
||||
IFC_CSPR_MSEL_NOR | \
|
||||
IFC_CSPR_V);
|
||||
IFC_AMASK(0) = IFC_AMASK_128MB;
|
||||
IFC_CSOR(0) = 0x0000000C; /* TRHZ (80 clocks for read enable high) */
|
||||
}
|
||||
|
||||
void hal_ddr_init(void)
|
||||
{
|
||||
#ifdef ENABLE_DDR
|
||||
/* Setup DDR CS (chip select) bounds */
|
||||
DDR_CS_BNDS(0) = DDR_CS0_BNDS_VAL;
|
||||
DDR_CS_CONFIG(0) = DDR_CS0_CONFIG_VAL;
|
||||
DDR_CS_CONFIG_2(0) = DDR_CS_CONFIG_2_VAL;
|
||||
DDR_CS_BNDS(1) = DDR_CS1_BNDS_VAL;
|
||||
DDR_CS_CONFIG(1) = DDR_CS1_CONFIG_VAL;
|
||||
DDR_CS_CONFIG_2(1) = DDR_CS_CONFIG_2_VAL;
|
||||
DDR_CS_BNDS(2) = DDR_CS2_BNDS_VAL;
|
||||
DDR_CS_CONFIG(2) = DDR_CS2_CONFIG_VAL;
|
||||
DDR_CS_CONFIG_2(2) = DDR_CS_CONFIG_2_VAL;
|
||||
DDR_CS_BNDS(3) = DDR_CS3_BNDS_VAL;
|
||||
DDR_CS_CONFIG(3) = DDR_CS3_CONFIG_VAL;
|
||||
DDR_CS_CONFIG_2(3) = DDR_CS_CONFIG_2_VAL;
|
||||
|
||||
/* DDR SDRAM timing configuration */
|
||||
DDR_TIMING_CFG_0 = DDR_TIMING_CFG_0_VAL;
|
||||
DDR_TIMING_CFG_1 = DDR_TIMING_CFG_1_VAL;
|
||||
DDR_TIMING_CFG_2 = DDR_TIMING_CFG_2_VAL;
|
||||
DDR_TIMING_CFG_3 = DDR_TIMING_CFG_3_VAL;
|
||||
DDR_TIMING_CFG_4 = DDR_TIMING_CFG_4_VAL;
|
||||
DDR_TIMING_CFG_5 = DDR_TIMING_CFG_5_VAL;
|
||||
|
||||
/* DDR SDRAM mode configuration */
|
||||
DDR_SDRAM_MODE = DDR_SDRAM_MODE_VAL;
|
||||
DDR_SDRAM_MODE_2 = DDR_SDRAM_MODE_2_VAL;
|
||||
DDR_SDRAM_MODE_3 = DDR_SDRAM_MODE_3_8_VAL;
|
||||
DDR_SDRAM_MODE_4 = DDR_SDRAM_MODE_3_8_VAL;
|
||||
DDR_SDRAM_MODE_5 = DDR_SDRAM_MODE_3_8_VAL;
|
||||
DDR_SDRAM_MODE_6 = DDR_SDRAM_MODE_3_8_VAL;
|
||||
DDR_SDRAM_MODE_7 = DDR_SDRAM_MODE_3_8_VAL;
|
||||
DDR_SDRAM_MODE_8 = DDR_SDRAM_MODE_3_8_VAL;
|
||||
DDR_SDRAM_MD_CNTL = DDR_SDRAM_MD_CNTL_VAL;
|
||||
|
||||
/* DDR Configuration */
|
||||
DDR_SDRAM_INTERVAL = DDR_SDRAM_INTERVAL_VAL;
|
||||
DDR_SDRAM_CLK_CNTL = DDR_SDRAM_CLK_CNTL_VAL;
|
||||
DDR_DATA_INIT = DDR_DATA_INIT_VAL;
|
||||
DDR_ZQ_CNTL = DDR_ZQ_CNTL_VAL;
|
||||
DDR_WRLVL_CNTL = DDR_WRLVL_CNTL_VAL;
|
||||
DDR_WRLVL_CNTL_2 = DDR_WRLVL_CNTL_2_VAL;
|
||||
DDR_WRLVL_CNTL_3 = DDR_WRLVL_CNTL_3_VAL;
|
||||
DDR_SR_CNTR = 0;
|
||||
DDR_SDRAM_RCW_1 = 0;
|
||||
DDR_SDRAM_RCW_2 = 0;
|
||||
DDR_DDRCDR_1 = DDR_DDRCDR_1_VAL;
|
||||
DDR_DDRCDR_2 = DDR_DDRCDR_2_VAL;
|
||||
DDR_SDRAM_CFG_2 = DDR_SDRAM_CFG_2_VAL;
|
||||
DDR_INIT_ADDR = 0;
|
||||
DDR_INIT_EXT_ADDR = 0;
|
||||
DDR_ERR_DISABLE = 0;
|
||||
DDR_ERR_INT_EN = DDR_ERR_INT_EN_VAL;
|
||||
DDR_ERR_SBE = DDR_ERR_SBE_VAL;
|
||||
|
||||
/* Set values, but do not enable the DDR yet */
|
||||
DDR_SDRAM_CFG = (DDR_SDRAM_CFG_VAL & ~DDR_SDRAM_CFG_MEM_EN);
|
||||
|
||||
/* TODO: Errata A009942 */
|
||||
|
||||
/* Enable controller */
|
||||
DDR_SDRAM_CFG |= DDR_SDRAM_CFG_MEM_EN;
|
||||
asm volatile("sync;isync");
|
||||
|
||||
/* Map LAW for DDR */
|
||||
LAWBARn (4) = 0; /* reset */
|
||||
LAWBARHn(4) = 0;
|
||||
LAWBARLn(4) = 0x0000000;
|
||||
LAWBARn (4) = LAWBARn_ENABLE | LAWBARn_TRGT_ID(LAW_TRGT_DDR_1) | LAW_SIZE_8GB;
|
||||
|
||||
/* Wait for data initialization is complete */
|
||||
while ((DDR_SDRAM_CFG_2 & DDR_SDRAM_CFG2_D_INIT));
|
||||
|
||||
/* DDR - TBL=1, Entry 19 */
|
||||
set_tlb(1, 19, DDR_ADDRESS, 0,
|
||||
MAS3_SX | MAS3_SW | MAS3_SR, 0,
|
||||
0, BOOKE_PAGESZ_2G, 1);
|
||||
#endif
|
||||
}
|
||||
|
||||
void hal_init(void)
|
||||
{
|
||||
#ifdef DEBUG_UART
|
||||
uint32_t fw;
|
||||
|
||||
uart_init();
|
||||
uart_write("wolfBoot Init\n", 14);
|
||||
#endif
|
||||
|
||||
hal_flash_init();
|
||||
}
|
||||
|
||||
int hal_flash_write(uint32_t address, const uint8_t *data, int len)
|
||||
{
|
||||
(void)address;
|
||||
(void)data;
|
||||
(void)len;
|
||||
/* TODO: Implement NAND flash write using IFC */
|
||||
return 0;
|
||||
}
|
||||
|
||||
int hal_flash_erase(uint32_t address, int len)
|
||||
{
|
||||
(void)address;
|
||||
(void)len;
|
||||
/* TODO: Implement NAND flash erase using IFC */
|
||||
return 0;
|
||||
}
|
||||
|
||||
void hal_flash_unlock(void)
|
||||
{
|
||||
/* Disable all flash protection bits */
|
||||
/* enter Non-volatile protection mode (C0h) */
|
||||
*((volatile uint16_t*)(FLASH_BASE + 0xAAA)) = 0xAAAA;
|
||||
*((volatile uint16_t*)(FLASH_BASE + 0x554)) = 0x5555;
|
||||
*((volatile uint16_t*)(FLASH_BASE + 0xAAA)) = 0xC0C0;
|
||||
/* clear all protection bit (80h/30h) */
|
||||
*((volatile uint16_t*)(FLASH_BASE + 0x000)) = 0x8080;
|
||||
*((volatile uint16_t*)(FLASH_BASE + 0x000)) = 0x3030;
|
||||
/* exit Non-volatile protection mode (90h/00h) */
|
||||
*((volatile uint16_t*)(FLASH_BASE + 0x000)) = 0x9090;
|
||||
*((volatile uint16_t*)(FLASH_BASE + 0x000)) = 0x0000;
|
||||
}
|
||||
|
||||
void hal_flash_lock(void)
|
||||
{
|
||||
/* Enable all flash protection bits */
|
||||
/* enter Non-volatile protection mode (C0h) */
|
||||
*((volatile uint16_t*)(FLASH_BASE + 0xAAA)) = 0xAAAA;
|
||||
*((volatile uint16_t*)(FLASH_BASE + 0x554)) = 0x5555;
|
||||
*((volatile uint16_t*)(FLASH_BASE + 0xAAA)) = 0xC0C0;
|
||||
/* set all protection bit (A0h/00h) */
|
||||
*((volatile uint16_t*)(FLASH_BASE + 0x000)) = 0xA0A0;
|
||||
*((volatile uint16_t*)(FLASH_BASE + 0x000)) = 0x0000;
|
||||
/* exit Non-volatile protection mode (90h/00h) */
|
||||
*((volatile uint16_t*)(FLASH_BASE + 0x000)) = 0x9090;
|
||||
*((volatile uint16_t*)(FLASH_BASE + 0x000)) = 0x0000;
|
||||
}
|
||||
|
||||
void hal_prepare_boot(void)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void* hal_get_dts_address(void)
|
||||
{
|
||||
return (void*)WOLFBOOT_LOAD_DTS_ADDRESS;
|
||||
}
|
|
@ -0,0 +1,76 @@
|
|||
OUTPUT_ARCH( "powerpc" )
|
||||
|
||||
ENTRY( _reset )
|
||||
|
||||
/* On initial start, only a limited space(4k) is accessible.
|
||||
* Code here bootstraps to enable access to other needed address spaces */
|
||||
BOOTSTRAP_TLB = 0xEFFFF000;
|
||||
|
||||
/* Entry point where RCW directs code to execute from */
|
||||
BOOTSTRAP_ENTRY = 0xEFFFFFFC;
|
||||
|
||||
MEMORY
|
||||
{
|
||||
FLASH (rx) : ORIGIN = @WOLFBOOT_ORIGIN@, LENGTH = @BOOTLOADER_PARTITION_SIZE@
|
||||
/* Note: If DDR not setup, can use L1 memory at 0xFDD00000 and 0x4000 length */
|
||||
RAM (rwx) : ORIGIN = 0x00000000, LENGTH = 0x1FFFFFFF
|
||||
}
|
||||
|
||||
SECTIONS
|
||||
{
|
||||
/* boot code boot_ppc_start.S for _reset */
|
||||
.boot BOOTSTRAP_TLB :
|
||||
{
|
||||
KEEP(*(.boot))
|
||||
} = 0xFFFC
|
||||
. = ALIGN(4);
|
||||
|
||||
/* entry point branch offset to _reset */
|
||||
.reset BOOTSTRAP_ENTRY :
|
||||
{
|
||||
KEEP(*(.reset))
|
||||
} = 0x4
|
||||
. = ALIGN(4);
|
||||
|
||||
.text :
|
||||
{
|
||||
*(.text*)
|
||||
*(.rodata*)
|
||||
*(.sdata*)
|
||||
} > FLASH
|
||||
|
||||
/* Read-only sections, merged into text segment: */
|
||||
.interp : { *(.interp) }
|
||||
.hash : { *(.hash) }
|
||||
.dynsym : { *(.dynsym) }
|
||||
.dynstr : { *(.dynstr) }
|
||||
.gnu.version : { *(.gnu.version) }
|
||||
.gnu.version_r : { *(.gnu.version_r) }
|
||||
.gnu.hash : { *(.gnu.hash) }
|
||||
.rela.dyn : { *(.rela.dyn) }
|
||||
|
||||
_stored_data = .;
|
||||
|
||||
.data : AT (_stored_data)
|
||||
{
|
||||
_start_data = .;
|
||||
KEEP(*(.data*))
|
||||
. = ALIGN(4);
|
||||
KEEP(*(.ramcode))
|
||||
. = ALIGN(4);
|
||||
_end_data = .;
|
||||
} > RAM
|
||||
|
||||
.bss (NOLOAD) :
|
||||
{
|
||||
_start_bss = .;
|
||||
__bss_start__ = .;
|
||||
*(.bss*)
|
||||
*(COMMON)
|
||||
. = ALIGN(4);
|
||||
_end_bss = .;
|
||||
__bss_end__ = .;
|
||||
_end = .;
|
||||
} > RAM
|
||||
|
||||
}
|
|
@ -125,7 +125,6 @@ setup_mmu:
|
|||
tlbwe
|
||||
isync
|
||||
|
||||
|
||||
/* For TS/AS=1 map all 8M of boot ROM
|
||||
* This window is always enabled T2080 RM (See LAW 2.3.5)
|
||||
*/
|
||||
|
@ -447,12 +446,30 @@ ram_q:
|
|||
tlbwe
|
||||
isync
|
||||
|
||||
|
||||
/* enable branch prediction */
|
||||
#define BUCSR 0x3F5 /* Branch Control and Status Register */
|
||||
#define BUCSR_STAC_EN 0x01000000 /* Segment target addr cache enable */
|
||||
#define BUCSR_LS_EN 0x00400000 /* Link stack enable */
|
||||
#define BUCSR_BBFI 0x00000200 /* Branch buffer flash invalidate */
|
||||
#define BUCSR_BPEN 0x00000001 /* Branch prediction enable */
|
||||
#define BUCSR_ENABLE (BUCSR_STAC_EN | BUCSR_LS_EN | BUCSR_BBFI | BUCSR_BPEN)
|
||||
lis 0, (BUCSR_ENABLE)@h
|
||||
ori 0, 0, (BUCSR_ENABLE)@l
|
||||
mtspr BUCSR, 0
|
||||
|
||||
/* time base enable */
|
||||
lis 4, 0x0000
|
||||
ori 4, 4, 0x4000
|
||||
mtspr 0x3F0, 4
|
||||
|
||||
/* switch back to AS/TS=0 */
|
||||
lis 3,(MSR_DE)@h
|
||||
ori 3,3,(MSR_DE)@l
|
||||
mtmsr 3
|
||||
isync
|
||||
|
||||
|
||||
/* PowerPC e500 Application Binary Interface User’s Guide
|
||||
* 2.3.5.1.1 Minimal Stack Frame: No Local Variables or Saved Parameters
|
||||
*/
|
||||
|
|
|
@ -0,0 +1,114 @@
|
|||
/* app_nxp_p1021.c
|
||||
*
|
||||
* Copyright (C) 2022 wolfSSL Inc.
|
||||
*
|
||||
* This file is part of wolfBoot.
|
||||
*
|
||||
* wolfBoot is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* wolfBoot is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
|
||||
*/
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
/* P1021 */
|
||||
#define CCSRBAR (0xFF700000)
|
||||
#define SYS_CLK (400000000)
|
||||
|
||||
/* P1021 PC16552D Dual UART */
|
||||
#define BAUD_RATE 115200
|
||||
#define UART_SEL 0 /* select UART 0 or 1 */
|
||||
|
||||
#define UART_BASE(n) (CCSRBAR + 0x4500 + (n * 0x100))
|
||||
|
||||
#define UART_RBR(n) *((volatile uint8_t*)(UART_BASE(n) + 0)) /* receiver buffer register */
|
||||
#define UART_THR(n) *((volatile uint8_t*)(UART_BASE(n) + 0)) /* transmitter holding register */
|
||||
#define UART_IER(n) *((volatile uint8_t*)(UART_BASE(n) + 1)) /* interrupt enable register */
|
||||
#define UART_IIR(n) *((volatile uint8_t*)(UART_BASE(n) + 2)) /* interrupt ID register */
|
||||
#define UART_FCR(n) *((volatile uint8_t*)(UART_BASE(n) + 2)) /* FIFO control register */
|
||||
#define UART_LCR(n) *((volatile uint8_t*)(UART_BASE(n) + 3)) /* line control register */
|
||||
#define UART_MCR(n) *((volatile uint8_t*)(UART_BASE(n) + 4)) /* modem control register */
|
||||
#define UART_LSR(n) *((volatile uint8_t*)(UART_BASE(n) + 5)) /* line status register */
|
||||
|
||||
/* enabled when UART_LCR_DLAB set */
|
||||
#define UART_DLB(n) *((volatile uint8_t*)(UART_BASE(n) + 0)) /* divisor least significant byte register */
|
||||
#define UART_DMB(n) *((volatile uint8_t*)(UART_BASE(n) + 1)) /* divisor most significant byte register */
|
||||
|
||||
#define UART_FCR_TFR (0x04) /* Transmitter FIFO reset */
|
||||
#define UART_FCR_RFR (0x02) /* Receiver FIFO reset */
|
||||
#define UART_FCR_FEN (0x01) /* FIFO enable */
|
||||
#define UART_LCR_DLAB (0x80) /* Divisor latch access bit */
|
||||
#define UART_LCR_WLS (0x03) /* Word length select: 8-bits */
|
||||
#define UART_LSR_TEMT (0x40) /* Transmitter empty */
|
||||
#define UART_LSR_THRE (0x20) /* Transmitter holding register empty */
|
||||
|
||||
|
||||
static void uart_init(void)
|
||||
{
|
||||
/* calc divisor for UART
|
||||
* example config values:
|
||||
* clock_div, baud, base_clk 163 115200 300000000
|
||||
* +0.5 to round up
|
||||
*/
|
||||
uint32_t div = (((SYS_CLK / 2.0) / (16 * BAUD_RATE)) + 0.5);
|
||||
|
||||
while (!(UART_LSR(UART_SEL) & UART_LSR_TEMT))
|
||||
;
|
||||
|
||||
/* set ier, fcr, mcr */
|
||||
UART_IER(UART_SEL) = 0;
|
||||
UART_FCR(UART_SEL) = (UART_FCR_TFR | UART_FCR_RFR | UART_FCR_FEN);
|
||||
|
||||
/* enable baud rate access (DLAB=1) - divisor latch access bit*/
|
||||
UART_LCR(UART_SEL) = (UART_LCR_DLAB | UART_LCR_WLS);
|
||||
/* set divisor */
|
||||
UART_DLB(UART_SEL) = (div & 0xff);
|
||||
UART_DMB(UART_SEL) = ((div>>8) & 0xff);
|
||||
/* disable rate access (DLAB=0) */
|
||||
UART_LCR(UART_SEL) = (UART_LCR_WLS);
|
||||
}
|
||||
|
||||
static void uart_write(const char* buf, uint32_t sz)
|
||||
{
|
||||
uint32_t pos = 0;
|
||||
while (sz-- > 0) {
|
||||
while (!(UART_LSR(UART_SEL) & UART_LSR_THRE))
|
||||
;
|
||||
UART_THR(UART_SEL) = buf[pos++];
|
||||
}
|
||||
}
|
||||
|
||||
static const char* hex_lut = "0123456789abcdef";
|
||||
|
||||
void main(void)
|
||||
{
|
||||
int i = 0;
|
||||
int j = 0;
|
||||
int k = 0;
|
||||
char snum[8];
|
||||
|
||||
uart_write("Test App\n", 9);
|
||||
|
||||
/* Wait for reboot */
|
||||
while(1) {
|
||||
for (j=0; j<1000000; j++)
|
||||
;
|
||||
i++;
|
||||
|
||||
uart_write("\r\n0x", 4);
|
||||
for (k=0; k<8; k++) {
|
||||
snum[7 - k] = hex_lut[(i >> 4*k) & 0xf];
|
||||
}
|
||||
uart_write(snum, 8);
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue