Added C++ ctors and partial SDHOST driver

This commit is contained in:
kristina 2016-05-21 03:22:03 +01:00
parent cfe4fe742e
commit c90348397a
6 changed files with 284 additions and 8 deletions

View File

@ -4,7 +4,10 @@ TARGET_ARM_CHAINLOADER = arm_chainloader.bin
SRCS = \
start.s \
drivers/uart.c \
drivers/cprman.cc \
drivers/sdhost.cc \
../lib/xprintf.c \
../lib/udelay.c \
firmware_rendezvous.c \
main.c
@ -27,11 +30,13 @@ OBJ := $(addprefix $(TARGET_BUILD_DIR)/, $(addsuffix .o, $(basename $(SRCS))))
CROSS_COMPILE = arm-none-eabi-
CC = $(CROSS_COMPILE)gcc
CXX = $(CROSS_COMPILE)gcc
AS = $(CC)
OBJCOPY = $(CROSS_COMPILE)objcopy
LINKFLAGS = -nostdlib -march=$(ARCH) -Wl,--build-id=none -T linker.lds
COMMON_FLAGS = -c -nostdlib -nostartfiles -ffreestanding -march=$(ARCH) -I../ -I./ -mfpu=vfp -mfloat-abi=hard -mtune=arm1176jzf-s
CFLAGS = $(COMMON_FLAGS) -std=c11
CXXFLAGS = $(COMMON_FLAGS) -std=c++11 -fno-exceptions -fno-rtti
ASFLAGS = $(COMMON_FLAGS) -x assembler-with-cpp
HEADERS := \
@ -54,6 +59,11 @@ $(TARGET_BUILD_DIR)/%.o: %.c $(HEADERS)
@echo $(WARN_COLOR)CC $(NO_COLOR) $@
@$(CC) $(CFLAGS) $< -o $@
$(TARGET_BUILD_DIR)/%.o: %.cc $(HEADERS)
$(CREATE_SUBDIR)
@echo $(WARN_COLOR)CXX $(NO_COLOR) $@
@$(CXX) $(CXXFLAGS) $< -o $@
$(TARGET_BUILD_DIR)/%.o: %.s $(HEADERS)
$(CREATE_SUBDIR)
@echo $(WARN_COLOR)AS $(NO_COLOR) $@

View File

@ -1,5 +1,25 @@
#pragma once
#include <stdint.h>
#include <lib/xprintf.h>
#define printf xprintf
#define printf xprintf
#ifdef __cplusplus
extern "C" {
#endif
extern void udelay(uint32_t time);
#define STATIC_INIT_PRIORITY(x) __attribute__((init_priority(x)))
#define STATIC_CPRMAN_DRIVER STATIC_INIT_PRIORITY(101)
#define STATIC_DRIVER STATIC_INIT_PRIORITY(200)
#define STATIC_APP STATIC_INIT_PRIORITY(600)
#define mfence() __sync_synchronize()
#ifdef __cplusplus
}
#endif

View File

86
arm_chainloader/drivers/sd2.hpp Executable file
View File

@ -0,0 +1,86 @@
#pragma once
/* Error Code */
#define SD_NO_ERROR 0x0
#define SD_CRC_ERR 0x80
#define SD_TO_ERR 0x40
#define SD_NO_CARD 0x20
#define SD_BUSY 0x10
#define SD_STS_ERR 0x08
#define SD_RSP_TIMEOUT 0x04
#define SD_IO_ERR 0x02
/* Return code for MMC switch bus */
#define SWITCH_SUCCESS 0
#define SWITCH_ERR 1
#define SWITCH_FAIL 2
/* MMC/SD Command Index */
/* Basic command (class 0) */
#define GO_IDLE_STATE 0
#define SEND_OP_COND 1
#define ALL_SEND_CID 2
#define SET_RELATIVE_ADDR 3
#define SEND_RELATIVE_ADDR 3
#define SET_DSR 4
#define IO_SEND_OP_COND 5
#define SWITCH 6
#define SELECT_CARD 7
#define DESELECT_CARD 7
/* CMD8 is "SEND_EXT_CSD" for MMC4.x Spec
* while is "SEND_IF_COND" for SD 2.0
*/
#define SEND_EXT_CSD 8
#define SEND_IF_COND 8
#define SEND_CSD 9
#define SEND_CID 10
#define VOLTAGE_SWITCH 11
#define READ_DAT_UTIL_STOP 11
#define STOP_TRANSMISSION 12
#define SEND_STATUS 13
#define GO_INACTIVE_STATE 15
#define SET_BLOCKLEN 16
#define READ_SINGLE_BLOCK 17
#define READ_MULTIPLE_BLOCK 18
#define SEND_TUNING_PATTERN 19
#define BUSTEST_R 14
#define BUSTEST_W 19
#define WRITE_BLOCK 24
#define WRITE_MULTIPLE_BLOCK 25
#define PROGRAM_CSD 27
#define ERASE_WR_BLK_START 32
#define ERASE_WR_BLK_END 33
#define ERASE_CMD 38
#define LOCK_UNLOCK 42
#define IO_RW_DIRECT 52
#define APP_CMD 55
#define GEN_CMD 56
#define SET_BUS_WIDTH 6
#define SD_STATUS 13
#define SEND_NUM_WR_BLOCKS 22
#define SET_WR_BLK_ERASE_COUNT 23
#define SD_APP_OP_COND 41
#define SET_CLR_CARD_DETECT 42
#define SEND_SCR 51
#define SD_READ_COMPLETE 0x00
#define SD_READ_TO 0x01
#define SD_READ_ADVENCE 0x02
#define SD_CHECK_MODE 0x00
#define SD_SWITCH_MODE 0x80
#define SD_FUNC_GROUP_1 0x01
#define SD_FUNC_GROUP_2 0x02
#define SD_FUNC_GROUP_3 0x03
#define SD_FUNC_GROUP_4 0x04
#define SD_CHECK_SPEC_V1_1 0xFF
#define NO_ARGUMENT 0x00
#define CHECK_PATTERN 0x000000AA
#define VOLTAGE_SUPPLY_RANGE 0x00000100
#define SUPPORT_HIGH_AND_EXTENDED_CAPACITY 0x40000000
#define SUPPORT_MAX_POWER_PERMANCE 0x10000000
#define SUPPORT_1V8 0x01000000
#define SWTICH_NO_ERR 0x00
#define CARD_NOT_EXIST 0x01
#define SPEC_NOT_SUPPORT 0x02
#define CHECK_MODE_ERR 0x03
#define CHECK_NOT_READY 0x04
#define SWITCH_CRC_ERR 0x05
#define SWITCH_MODE_ERR 0x06
#define SWITCH_PASS 0x07

131
arm_chainloader/drivers/sdhost.cc Executable file
View File

@ -0,0 +1,131 @@
/*=============================================================================
Copyright (C) 2016 Kristina Brooks
All rights reserved.
This program 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.
This program 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.
FILE DESCRIPTION
SDHOST driver. This used to be known as ALTMMC.
=============================================================================*/
#include <chainloader.h>
#include <hardware.h>
#include "sd2.hpp"
#define SDEDM_WRITE_THRESHOLD_SHIFT 9
#define SDEDM_READ_THRESHOLD_SHIFT 14
#define SDEDM_THRESHOLD_MASK 0x1f
#define SAFE_READ_THRESHOLD 4
#define SAFE_WRITE_THRESHOLD 4
#define logf(fmt, ...) printf("[sdhost::%s]: " fmt, __FUNCTION__, ##__VA_ARGS__);
struct sdhost_t {
void set_power(bool on) {
SH_VDD = on ? SH_VDD_POWER_ON_SET : 0x0;
}
bool wait(uint32_t timeout = 10000) {
uint32_t t = timeout;
while(SH_CMD & SH_CMD_NEW_FLAG_SET) {
if (t == 0) {
logf("timed out after %dus!\n", timeout)
return false;
}
t--;
udelay(10);
}
return true;
}
bool send(uint32_t command, uint32_t arg) {
if (!wait())
return false;
SH_ARG = arg;
SH_CMD = (command & SH_CMD_COMMAND_SET) | SH_CMD_NEW_FLAG_SET;
udelay(300);
mfence();
return true;
}
void configure_pinmux() {
GP_FSEL4 = 0x24000000;
GP_FSEL5 = 0x924;
GP_PUD = 2;
logf("GPIOs set!\n");
}
void reset() {
logf("resetting controller ...\n");
set_power(false);
SH_CMD = 0;
SH_ARG = 0;
SH_TOUT = 0xF00000;
SH_CDIV = 0;
SH_HSTS = 0x7f8;
SH_HCFG = 0;
SH_HBCT = 0;
SH_HBLC = 0;
uint32_t temp = SH_EDM;
temp &= ~((SDEDM_THRESHOLD_MASK<<SDEDM_READ_THRESHOLD_SHIFT) |
(SDEDM_THRESHOLD_MASK<<SDEDM_WRITE_THRESHOLD_SHIFT));
temp |= (SAFE_READ_THRESHOLD << SDEDM_READ_THRESHOLD_SHIFT) |
(SAFE_WRITE_THRESHOLD << SDEDM_WRITE_THRESHOLD_SHIFT);
SH_EDM = temp;
udelay(300);
set_power(true);
udelay(300);
mfence();
}
void init_card() {
send(GO_IDLE_STATE, 0);
send(SEND_IF_COND, 0x155);
wait();
logf("SEND_IF_COND response is: 0x%X\n", SH_RSP0);
}
sdhost_t() {
logf("starting up ...\n");
configure_pinmux();
reset();
SH_HCFG = SH_HCFG_SLOW_CARD_SET | SH_HCFG_WIDE_INT_BUS_SET;
SH_CDIV = 0x96;
udelay(300);
logf("sdhost controller ready!\n");
init_card();
}
};
sdhost_t STATIC_DRIVER g_SDHostDriver {};

View File

@ -1,10 +1,39 @@
MEMORY
{
ram : ORIGIN = 0x0, LENGTH = 0x100000
}
SECTIONS
{
.text : { *(.text*) } > ram
.bss : { *(.bss*) } > ram
. = 0x0;
_text = .;
.text : {
*(.text)
*(.text.*)
*(.gnu.warning)
}
_etext = .;
.rodata : { *(.rodata) *(.rodata.*) }
. = ALIGN(4096);
_erodata = .;
. = ALIGN(32 / 8);
PROVIDE (__init_array_start = .);
.init_array : {
*(.init_array)
*(.init_array.*)
}
PROVIDE (__init_array_end = .);
.data : { /* Data */
*(.data)
}
.bss : {
_edata = .;
__bss_start = .;
*(.bss)
}
_end = . ;
}