nbhw16: add shield command (dualcan and comio)
This commit is contained in:
parent
1fc30e873a
commit
22506ffe45
|
|
@ -168,6 +168,8 @@ typedef enum _BD_Tags
|
||||||
BD_Pd_Module5 = 4105,
|
BD_Pd_Module5 = 4105,
|
||||||
BD_Pd_Sim = 4122,
|
BD_Pd_Sim = 4122,
|
||||||
PD_Dev_Tree = 4125, /**< "String" -> Devicetree file name */
|
PD_Dev_Tree = 4125, /**< "String" -> Devicetree file name */
|
||||||
|
PD_SerDes = 4128, /**< "Uint16" -> SERDES Configuration (e.g. NB1800) */
|
||||||
|
PD_Shield = 4129, /**< "String" -> Shield Population (e.g. CAN/RS485) for NB800 */
|
||||||
|
|
||||||
/* project specific tags */
|
/* project specific tags */
|
||||||
BD_BootPart = 32768, /**< "UInt8" */
|
BD_BootPart = 32768, /**< "UInt8" */
|
||||||
|
|
|
||||||
|
|
@ -109,6 +109,7 @@ static bd_bool_t _get_mac( bd_uint16_t tag, bd_uint_t index, bd_uint8_t pResult[
|
||||||
|
|
||||||
return BD_FALSE;
|
return BD_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
static bd_bool_t _get_uint8( bd_uint16_t tag, bd_uint_t index, bd_uint8_t* pResult ) {
|
static bd_bool_t _get_uint8( bd_uint16_t tag, bd_uint_t index, bd_uint8_t* pResult ) {
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
|
|
@ -121,6 +122,18 @@ static bd_bool_t _get_uint8( bd_uint16_t tag, bd_uint_t index, bd_uint8_t* pResu
|
||||||
return BD_FALSE;
|
return BD_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static bd_bool_t _get_uint16( bd_uint16_t tag, bd_uint_t index, bd_uint16_t* pResult ) {
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for (i = 0; i < bdctx_count; i++) {
|
||||||
|
if (BD_GetUInt16(&bdctx_list[i], tag, index, pResult)) {
|
||||||
|
return BD_TRUE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return BD_FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
static bd_bool_t _get_uint32( bd_uint16_t tag, bd_uint_t index, bd_uint32_t* pResult ) {
|
static bd_bool_t _get_uint32( bd_uint16_t tag, bd_uint_t index, bd_uint32_t* pResult ) {
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
|
|
@ -227,6 +240,18 @@ int bd_get_devicetree(char* devicetreename, size_t len)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int bd_get_shield(int shieldnr)
|
||||||
|
{
|
||||||
|
bd_uint16_t shield = 0;
|
||||||
|
|
||||||
|
if (!_get_uint16(PD_Shield, shieldnr, &shield) ) {
|
||||||
|
debug("%s() no shield populated\n", __func__);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return shield;
|
||||||
|
}
|
||||||
|
|
||||||
static u8 try_partition_read(void)
|
static u8 try_partition_read(void)
|
||||||
{
|
{
|
||||||
BD_PartitionEntry64 partition;
|
BD_PartitionEntry64 partition;
|
||||||
|
|
|
||||||
|
|
@ -17,5 +17,6 @@ int bd_get_devicetree(char* devicetreename, size_t len);
|
||||||
int bd_get_context(BD_Context *bdctx, uint32_t i2caddress, uint32_t offset);
|
int bd_get_context(BD_Context *bdctx, uint32_t i2caddress, uint32_t offset);
|
||||||
void bd_register_context_list(const BD_Context *list, size_t count);
|
void bd_register_context_list(const BD_Context *list, size_t count);
|
||||||
u8 bd_get_boot_partition(void);
|
u8 bd_get_boot_partition(void);
|
||||||
|
int bd_get_shield(int shieldnr);
|
||||||
|
|
||||||
#endif /* __BOARD_DESCRIPTOR_H */
|
#endif /* __BOARD_DESCRIPTOR_H */
|
||||||
|
|
|
||||||
|
|
@ -41,7 +41,6 @@
|
||||||
DECLARE_GLOBAL_DATA_PTR;
|
DECLARE_GLOBAL_DATA_PTR;
|
||||||
|
|
||||||
/* GPIO that controls power to DDR on EVM-SK */
|
/* GPIO that controls power to DDR on EVM-SK */
|
||||||
#define GPIO_TO_PIN(bank, gpio) (32 * (bank) + (gpio))
|
|
||||||
#define GPIO_DDR_VTT_EN GPIO_TO_PIN(0, 7)
|
#define GPIO_DDR_VTT_EN GPIO_TO_PIN(0, 7)
|
||||||
#define ICE_GPIO_DDR_VTT_EN GPIO_TO_PIN(0, 18)
|
#define ICE_GPIO_DDR_VTT_EN GPIO_TO_PIN(0, 18)
|
||||||
#define GPIO_PR1_MII_CTRL GPIO_TO_PIN(3, 4)
|
#define GPIO_PR1_MII_CTRL GPIO_TO_PIN(3, 4)
|
||||||
|
|
|
||||||
|
|
@ -10,4 +10,4 @@ ifeq ($(CONFIG_SKIP_LOWLEVEL_INIT),)
|
||||||
obj-y := mux.o
|
obj-y := mux.o
|
||||||
endif
|
endif
|
||||||
|
|
||||||
obj-y += board.o ../common/bdparser.o ../common/board_descriptor.o
|
obj-y += board.o ../common/bdparser.o ../common/board_descriptor.o shield.o shield_can.o shield_comio.o fileaccess.o
|
||||||
|
|
|
||||||
|
|
@ -37,6 +37,10 @@
|
||||||
#include "../common/bdparser.h"
|
#include "../common/bdparser.h"
|
||||||
#include "../common/board_descriptor.h"
|
#include "../common/board_descriptor.h"
|
||||||
#include "board.h"
|
#include "board.h"
|
||||||
|
#include "shield.h"
|
||||||
|
#include "shield_can.h"
|
||||||
|
#include "shield_comio.h"
|
||||||
|
#include "fileaccess.h"
|
||||||
|
|
||||||
DECLARE_GLOBAL_DATA_PTR;
|
DECLARE_GLOBAL_DATA_PTR;
|
||||||
|
|
||||||
|
|
@ -324,9 +328,8 @@ int check_reset_button(void)
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
} else { /* Boot into recovery for duration > 15s */
|
} else { /* Boot into recovery for duration > 15s */
|
||||||
|
|
||||||
/* set consoledev to external port */
|
/* set consoledev to external port */
|
||||||
setenv("consoledev", "ttyO0");
|
setenv("consoledev", "ttyS1");
|
||||||
|
|
||||||
printf("Booting recovery image...\n");
|
printf("Booting recovery image...\n");
|
||||||
|
|
||||||
|
|
@ -514,6 +517,93 @@ static void check_fct(void)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static void set_fdtshieldcmd(const char *fdt_cmd)
|
||||||
|
{
|
||||||
|
setenv("fdtshieldcmd", fdt_cmd);
|
||||||
|
}
|
||||||
|
|
||||||
|
struct shield_command {
|
||||||
|
int shield_id;
|
||||||
|
const char *default_shieldcmd;
|
||||||
|
const char *fdtshieldcmd;
|
||||||
|
};
|
||||||
|
|
||||||
|
#define SHIELD_COM_IO 0
|
||||||
|
#define SHIELD_DUALCAN 1
|
||||||
|
|
||||||
|
static struct shield_command known_shield_commands[] = {
|
||||||
|
{
|
||||||
|
SHIELD_COM_IO,
|
||||||
|
"shield comio mode rs232",
|
||||||
|
"fdt get value serial0 /aliases serial0;" \
|
||||||
|
"fdt set $serial0 status okay"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
SHIELD_DUALCAN,
|
||||||
|
"shield dualcan termination off off",
|
||||||
|
"fdt get value can0 /aliases d_can0;" \
|
||||||
|
"fdt get value can1 /aliases d_can1;" \
|
||||||
|
"fdt set $can0 status okay;" \
|
||||||
|
"fdt set $can1 status okay;" \
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
static const struct shield_command* get_shield_command(int shield_id)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for (i = 0; i < ARRAY_SIZE(known_shield_commands); i++) {
|
||||||
|
if (known_shield_commands[i].shield_id == shield_id) {
|
||||||
|
return &known_shield_commands[i];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void shield_config(void)
|
||||||
|
{
|
||||||
|
#define MAX_SHIELD_CMD_LEN 128
|
||||||
|
char shieldcmd_linux[MAX_SHIELD_CMD_LEN];
|
||||||
|
const char *shieldcmd;
|
||||||
|
const struct shield_command *cmd;
|
||||||
|
int len;
|
||||||
|
|
||||||
|
int shield_id = bd_get_shield(0);
|
||||||
|
if (shield_id < 0) {
|
||||||
|
printf("No shield found in bd\n");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
cmd = get_shield_command(shield_id);
|
||||||
|
if (cmd == NULL) {
|
||||||
|
printf ("Unknown shield id %d\n", shield_id);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
shieldcmd = cmd->default_shieldcmd;
|
||||||
|
|
||||||
|
/* If a shield configuration set by linux take it without bd check, we asume that Linux knows
|
||||||
|
* what to do. */
|
||||||
|
len = read_file("/root/boot/shieldcmd", shieldcmd_linux, MAX_SHIELD_CMD_LEN);
|
||||||
|
if (len > 0) {
|
||||||
|
puts("Shield command found in file, using it\n");
|
||||||
|
shieldcmd = shieldcmd_linux;
|
||||||
|
}
|
||||||
|
|
||||||
|
setenv("shieldcmd", shieldcmd);
|
||||||
|
|
||||||
|
set_fdtshieldcmd(cmd->fdtshieldcmd);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void shield_init(void)
|
||||||
|
{
|
||||||
|
can_shield_init();
|
||||||
|
comio_shield_init();
|
||||||
|
|
||||||
|
shield_config();
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef CONFIG_BOARD_LATE_INIT
|
#ifdef CONFIG_BOARD_LATE_INIT
|
||||||
|
|
@ -533,6 +623,7 @@ int board_late_init(void)
|
||||||
|
|
||||||
/* mmcblk0p1 => root0, mmcblk0p2 => root1 so +1 */
|
/* mmcblk0p1 => root0, mmcblk0p2 => root1 so +1 */
|
||||||
setenv_ulong("root_part", boot_partition + 1);
|
setenv_ulong("root_part", boot_partition + 1);
|
||||||
|
fs_set_console();
|
||||||
|
|
||||||
check_reset_button();
|
check_reset_button();
|
||||||
|
|
||||||
|
|
@ -551,7 +642,10 @@ int board_late_init(void)
|
||||||
enable_wlan_clock();
|
enable_wlan_clock();
|
||||||
|
|
||||||
#if !defined(CONFIG_SPL_BUILD)
|
#if !defined(CONFIG_SPL_BUILD)
|
||||||
|
shield_init();
|
||||||
|
|
||||||
check_fct();
|
check_fct();
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
||||||
|
|
@ -24,4 +24,6 @@ void enable_uart4_pin_mux(void);
|
||||||
void enable_uart5_pin_mux(void);
|
void enable_uart5_pin_mux(void);
|
||||||
void enable_i2c0_pin_mux(void);
|
void enable_i2c0_pin_mux(void);
|
||||||
void enable_board_pin_mux(void);
|
void enable_board_pin_mux(void);
|
||||||
|
|
||||||
|
#define GPIO_TO_PIN(bank, gpio) (32 * (bank) + (gpio))
|
||||||
#endif
|
#endif
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,71 @@
|
||||||
|
#include <common.h>
|
||||||
|
#include <fs.h>
|
||||||
|
|
||||||
|
#define OVERLAY_PART "1:3"
|
||||||
|
|
||||||
|
int read_file(const char* filename, char *buf, int size)
|
||||||
|
{
|
||||||
|
loff_t filesize = 0;
|
||||||
|
loff_t len;
|
||||||
|
int ret;
|
||||||
|
|
||||||
|
/* If consoldev is set take this as productive conosle instead of default console */
|
||||||
|
if (fs_set_blk_dev("mmc", OVERLAY_PART, FS_TYPE_EXT) != 0) {
|
||||||
|
puts("Error, can not set blk device\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* File does not exist, do not print an error message */
|
||||||
|
if (fs_size(filename, &filesize)) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (filesize < size)
|
||||||
|
size = filesize;
|
||||||
|
|
||||||
|
/* If consoldev is set take this as productive conosle instead of default console */
|
||||||
|
if (fs_set_blk_dev("mmc", OVERLAY_PART, FS_TYPE_EXT) != 0) {
|
||||||
|
puts("Error, can not set blk device\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
if ((ret = fs_read(filename, (ulong)buf, 0, size, &len))) {
|
||||||
|
printf("Can't read file %s (size %d, len %lld, ret %d)\n", filename, size, len, ret);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
buf[len] = 0;
|
||||||
|
|
||||||
|
return len;
|
||||||
|
}
|
||||||
|
|
||||||
|
void fs_set_console(void)
|
||||||
|
{
|
||||||
|
loff_t len;
|
||||||
|
char buf[50] = "\n";
|
||||||
|
char *defaultconsole = getenv("defaultconsole");
|
||||||
|
|
||||||
|
if (defaultconsole == 0) {
|
||||||
|
/* This is the default console that should be used for e.g. recovery boot */
|
||||||
|
sprintf(buf, "ttyS1");
|
||||||
|
setenv("defaultconsole", buf);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* If consoldev is set take this as productive conosle instead of default console */
|
||||||
|
if (fs_set_blk_dev("mmc", OVERLAY_PART, FS_TYPE_EXT) != 0) {
|
||||||
|
puts("Error, can not set blk device\n");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
fs_read("/root/boot/consoledev", (ulong)buf, 0, 5, &len);
|
||||||
|
if ((len != 5) || (strstr(buf, "tty")!=buf) || ((buf[4]<'0') && (buf[4]>'1'))) {
|
||||||
|
puts("Using default console\n");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
setenv("defaultconsoel", buf);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
@ -0,0 +1,14 @@
|
||||||
|
/**@file /home/eichenberger/projects/nbhw16/u-boot/board/nm/netbird_v2/fileaccess.h
|
||||||
|
* @author eichenberger
|
||||||
|
* @version 704
|
||||||
|
* @date
|
||||||
|
* Created: Tue 06 Jun 2017 02:02:33 PM CEST \n
|
||||||
|
* Last Update: Tue 06 Jun 2017 02:02:33 PM CEST
|
||||||
|
*/
|
||||||
|
#ifndef FILEACCESS_H
|
||||||
|
#define FILEACCESS_H
|
||||||
|
|
||||||
|
void fs_set_console(void);
|
||||||
|
int read_file(const char* filename, char *buf, int size);
|
||||||
|
|
||||||
|
#endif // FILEACCESS_H
|
||||||
|
|
@ -55,13 +55,15 @@ static struct module_pin_mux i2c0_pin_mux[] = {
|
||||||
|
|
||||||
/* V2OK */
|
/* V2OK */
|
||||||
static struct module_pin_mux uart0_netbird_pin_mux[] = {
|
static struct module_pin_mux uart0_netbird_pin_mux[] = {
|
||||||
{OFFSET(uart0_rxd), (MODE(0) | PULLUDEN | PULLUP_EN | RXACTIVE)}, /* (E15) UART0_RXD */
|
/* Leave UART0 unconfigured because we want to configure it as needed by linux (can/spi/uart/etc) */
|
||||||
{OFFSET(uart0_txd), (MODE(0) | PULLUDEN | PULLUP_EN)}, /* (E16) UART0_TXD */
|
{OFFSET(uart0_rxd), (MODE(7) | PULLUDDIS | RXACTIVE)}, /* (E15) UART0_RXD */
|
||||||
{OFFSET(uart0_ctsn), (MODE(0) | PULLUDEN | PULLUP_EN | RXACTIVE)}, /* (E18) UART0_CTSN */
|
{OFFSET(uart0_txd), (MODE(7) | PULLUDDIS | RXACTIVE)}, /* (E16) UART0_TXD */
|
||||||
{OFFSET(uart0_rtsn), (MODE(0) | PULLUDEN | PULLUP_EN)}, /* (E17) UART0_RTSN */
|
{OFFSET(uart0_ctsn), (MODE(7) | PULLUDDIS | RXACTIVE )}, /* (E18) UART0_CTSN */
|
||||||
|
{OFFSET(uart0_rtsn), (MODE(7) | PULLUDEN | PULLUP_EN )}, /* (E17) UART0_RTSN */
|
||||||
{-1},
|
{-1},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
/* V2OK */
|
/* V2OK */
|
||||||
static struct module_pin_mux uart1_netbird_pin_mux[] = {
|
static struct module_pin_mux uart1_netbird_pin_mux[] = {
|
||||||
{OFFSET(uart1_rxd), (MODE(0) | PULLUDEN | PULLUP_EN | RXACTIVE)}, /* (D16) uart1_rxd.uart1_rxd */
|
{OFFSET(uart1_rxd), (MODE(0) | PULLUDEN | PULLUP_EN | RXACTIVE)}, /* (D16) uart1_rxd.uart1_rxd */
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,73 @@
|
||||||
|
#define DEBUG
|
||||||
|
|
||||||
|
#include <common.h>
|
||||||
|
#include <asm/gpio.h>
|
||||||
|
#include <asm/arch/mux.h>
|
||||||
|
|
||||||
|
#include "shield.h"
|
||||||
|
#include "board.h"
|
||||||
|
|
||||||
|
#define MAX_SHIELDS 16
|
||||||
|
|
||||||
|
static struct shield_t *shields[MAX_SHIELDS];
|
||||||
|
static int shield_count = 0;
|
||||||
|
|
||||||
|
/* Perhaps this function shouldn't leave in shields.c? */
|
||||||
|
int shield_gpio_request_as_input(unsigned int gpio, const char *label)
|
||||||
|
{
|
||||||
|
int ret;
|
||||||
|
|
||||||
|
ret = gpio_request(gpio, label);
|
||||||
|
if ((ret < 0)) {
|
||||||
|
printf("Could not request shield slot %s gpio\n", label);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = gpio_direction_input(gpio);
|
||||||
|
if ((ret < 0)) {
|
||||||
|
printf("Could not configure shield slot %s gpio as input\n", label);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void shield_register(struct shield_t *shield)
|
||||||
|
{
|
||||||
|
if (shield_count >= MAX_SHIELDS) {
|
||||||
|
printf("Max shield count reached (%d), please increment MAX_SHIELDS\n", MAX_SHIELDS);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
shields[shield_count++] = shield;
|
||||||
|
}
|
||||||
|
|
||||||
|
int shield_set_mode(const char* shield_type, int argc, char * const argv[])
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for (i = 0; i < shield_count; i++) {
|
||||||
|
if (strcmp(shield_type, shields[i]->name) == 0) {
|
||||||
|
return shields[i]->setmode(argv, argc);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
printf("Shield %s is unknown\n", shield_type);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int do_shieldmode(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
|
||||||
|
{
|
||||||
|
if (argc < 3) {
|
||||||
|
puts("Invalid command (see help)\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return shield_set_mode(argv[1], argc - 2, &argv[2]);
|
||||||
|
}
|
||||||
|
|
||||||
|
U_BOOT_CMD(
|
||||||
|
shield, 6, 1, do_shieldmode,
|
||||||
|
"Set the shield mode",
|
||||||
|
"dualcan termination [on|off] [on|off]\n"
|
||||||
|
"shield comio mode [rs232|rs485] termination [on|off]\n"
|
||||||
|
);
|
||||||
|
|
||||||
|
|
@ -0,0 +1,21 @@
|
||||||
|
/**@file /home/eichenberger/projects/nbhw16/u-boot/board/nm/netbird_v2/shield.h
|
||||||
|
* @author eichenberger
|
||||||
|
* @version 704
|
||||||
|
* @date
|
||||||
|
* Created: Wed 31 May 2017 02:56:16 PM CEST \n
|
||||||
|
* Last Update: Wed 31 May 2017 02:56:16 PM CEST
|
||||||
|
*/
|
||||||
|
#ifndef SHIELD_H
|
||||||
|
#define SHIELD_H
|
||||||
|
|
||||||
|
struct shield_t{
|
||||||
|
char name[64];
|
||||||
|
int (*setmode)(char * const argv[], int argc);
|
||||||
|
};
|
||||||
|
|
||||||
|
int shield_setmode(int mode);
|
||||||
|
void shield_register(struct shield_t *shield);
|
||||||
|
|
||||||
|
int shield_gpio_request_as_input(unsigned int gpio, const char *label);
|
||||||
|
|
||||||
|
#endif // SHIELD_H
|
||||||
|
|
@ -0,0 +1,191 @@
|
||||||
|
#define DEBUG
|
||||||
|
|
||||||
|
#include <common.h>
|
||||||
|
#include <asm/gpio.h>
|
||||||
|
#include <asm/arch/mux.h>
|
||||||
|
|
||||||
|
#include "shield.h"
|
||||||
|
#include "board.h"
|
||||||
|
|
||||||
|
#define NETBIRD_GPIO_RST_SHIELD_N GPIO_TO_PIN(0, 27)
|
||||||
|
#define NETBIRD_GPIO_LATCH GPIO_TO_PIN(0, 7)
|
||||||
|
#define NETBIRD_GPIO_MODE_0 GPIO_TO_PIN(1, 8)
|
||||||
|
#define NETBIRD_GPIO_MODE_1 GPIO_TO_PIN(1, 10)
|
||||||
|
|
||||||
|
|
||||||
|
static int shield_slot_initialized = 0;
|
||||||
|
|
||||||
|
|
||||||
|
static struct module_pin_mux can_shield_netbird_pin_mux_config[] = {
|
||||||
|
/* Leave UART0 unconfigured because we want to configure it as needed by linux (can/spi/uart/etc) */
|
||||||
|
{OFFSET(uart0_ctsn), (MODE(7) | PULLUDEN | PULLUP_EN)}, /* CAN1 tx */
|
||||||
|
{OFFSET(uart0_rxd), (MODE(7) | PULLUDEN | PULLUP_EN)}, /* CAN0 tx */
|
||||||
|
{OFFSET(ecap0_in_pwm0_out), (MODE(7) | PULLUDEN | PULLUP_EN)}, /* Latch EN */
|
||||||
|
{-1},
|
||||||
|
};
|
||||||
|
|
||||||
|
static struct module_pin_mux can_shield_netbird_pin_mux_final[] = {
|
||||||
|
/* Leave UART0 unconfigured because we want to configure it as needed by linux (can/spi/uart/etc) */
|
||||||
|
{OFFSET(uart0_ctsn), (MODE(2) | PULLUDEN | PULLUP_EN)}, /* CAN1 tx */
|
||||||
|
{OFFSET(uart0_rtsn), (MODE(2) | PULLUDDIS | RXACTIVE)}, /* CAN1 rx */
|
||||||
|
{OFFSET(uart0_txd), (MODE(2) | PULLUDDIS | RXACTIVE)}, /* CAN0 rx */
|
||||||
|
{OFFSET(uart0_rxd), (MODE(2) | PULLUDEN | PULLUP_EN)}, /* CAN0 tx */
|
||||||
|
{-1},
|
||||||
|
};
|
||||||
|
|
||||||
|
static int request_gpios(void)
|
||||||
|
{
|
||||||
|
int ret;
|
||||||
|
|
||||||
|
debug("Shiled configure gpios\n");
|
||||||
|
ret = shield_gpio_request_as_input(NETBIRD_GPIO_RST_SHIELD_N, "shield-rst");
|
||||||
|
if ((ret < 0))
|
||||||
|
return -1;
|
||||||
|
ret = shield_gpio_request_as_input(NETBIRD_GPIO_LATCH, "shield-load");
|
||||||
|
if ((ret < 0))
|
||||||
|
return -1;
|
||||||
|
ret = shield_gpio_request_as_input(NETBIRD_GPIO_MODE_0, "shield-mode0");
|
||||||
|
if ((ret < 0))
|
||||||
|
return -1;
|
||||||
|
ret = shield_gpio_request_as_input(NETBIRD_GPIO_MODE_1, "shield-mode1");
|
||||||
|
if ((ret < 0))
|
||||||
|
return -1;
|
||||||
|
|
||||||
|
shield_slot_initialized = 1;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int configure_shieldmode(int mode)
|
||||||
|
{
|
||||||
|
int ret;
|
||||||
|
|
||||||
|
if (mode < 0 || mode > 3) {
|
||||||
|
printf("Invalid shield mode %d\n", mode);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
debug("Shield type dualcan\n");
|
||||||
|
debug ("Set shield mode to %d\n", mode);
|
||||||
|
|
||||||
|
if (!shield_slot_initialized) {
|
||||||
|
if (request_gpios()) {
|
||||||
|
puts("Failed to request gpios\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
debug("Configure shield pin muxing for configuration\n");
|
||||||
|
configure_module_pin_mux(can_shield_netbird_pin_mux_config);
|
||||||
|
|
||||||
|
debug("Make sure shield module is in reset\n");
|
||||||
|
ret = gpio_direction_output(NETBIRD_GPIO_RST_SHIELD_N, 0);
|
||||||
|
if (ret < 0) {
|
||||||
|
puts("Can not set shield-rst as output\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
udelay(10);
|
||||||
|
|
||||||
|
debug("Set latch to high\n");
|
||||||
|
ret = gpio_direction_output(NETBIRD_GPIO_LATCH, 1);
|
||||||
|
if (ret < 0) {
|
||||||
|
puts("Can not set shield-load as output\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
udelay(10);
|
||||||
|
|
||||||
|
debug("Write mode to GPIOs\n");
|
||||||
|
ret = gpio_direction_output(NETBIRD_GPIO_MODE_0, mode & 0x01);
|
||||||
|
if (ret < 0) {
|
||||||
|
puts("Can not set shield-mode0 as output\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
ret = gpio_direction_output(NETBIRD_GPIO_MODE_1, mode & 0x02);
|
||||||
|
if (ret < 0) {
|
||||||
|
puts("Can not set shield-mode1 as output\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
udelay(10);
|
||||||
|
|
||||||
|
debug("Set latch to low\n");
|
||||||
|
gpio_set_value(NETBIRD_GPIO_LATCH, 0);
|
||||||
|
udelay(10);
|
||||||
|
|
||||||
|
debug("Set mode0 and mode1 to highz again\n");
|
||||||
|
ret = gpio_direction_input(NETBIRD_GPIO_MODE_0);
|
||||||
|
if ((ret < 0)) {
|
||||||
|
puts("Could not configure shield slot mode0 gpio as input\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = gpio_direction_input(NETBIRD_GPIO_MODE_1);
|
||||||
|
if ((ret < 0)) {
|
||||||
|
puts("Could not configure shield slot mode1 gpio as input\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
udelay(10);
|
||||||
|
|
||||||
|
debug("Take shield out of reset\n");
|
||||||
|
gpio_set_value(NETBIRD_GPIO_RST_SHIELD_N, 1);
|
||||||
|
udelay(10);
|
||||||
|
|
||||||
|
debug("Set final can shield muxing\n");
|
||||||
|
configure_module_pin_mux(can_shield_netbird_pin_mux_final);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
static int get_termination(const char* termination)
|
||||||
|
{
|
||||||
|
if (strcmp("on", termination) == 0) {
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
else if (strcmp("off", termination) == 0) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
printf ("Invalid termination mode %s (falling back to off)", termination);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int get_mode_from_args(char * const argv[], int argc)
|
||||||
|
{
|
||||||
|
#define CAN_PORTS 2
|
||||||
|
int terminations[CAN_PORTS];
|
||||||
|
int i;
|
||||||
|
|
||||||
|
assert(argc == (CAN_PORTS + 1));
|
||||||
|
|
||||||
|
if (strcmp ("termination", argv[0])) {
|
||||||
|
puts("The only option for dualcan is terminations\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (i = 0; i < CAN_PORTS; i ++) {
|
||||||
|
terminations[i] = get_termination(argv[i + 1]);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Termination is inverse */
|
||||||
|
return (!terminations[0] << 0) | (!terminations[1] << 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int set_shieldmode(char * const argv[], int argc)
|
||||||
|
{
|
||||||
|
if (argc != 3) {
|
||||||
|
puts("Too few arguments for dualcan\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
configure_shieldmode(get_mode_from_args(argv, argc));
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct shield_t can_shield = {
|
||||||
|
"dualcan", set_shieldmode
|
||||||
|
};
|
||||||
|
|
||||||
|
void can_shield_init(void)
|
||||||
|
{
|
||||||
|
shield_register(&can_shield);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
@ -0,0 +1,9 @@
|
||||||
|
#ifndef SHIELD_CAN_H
|
||||||
|
#define SHIELD_CAN_H
|
||||||
|
|
||||||
|
int shield_can_init(void);
|
||||||
|
int shield_can_setmode(int mode);
|
||||||
|
|
||||||
|
void can_shield_init(void);
|
||||||
|
|
||||||
|
#endif // SHIELD_CAN_H
|
||||||
|
|
@ -0,0 +1,214 @@
|
||||||
|
/* #define DEBUG */
|
||||||
|
|
||||||
|
#include <common.h>
|
||||||
|
#include <asm/gpio.h>
|
||||||
|
#include <asm/arch/mux.h>
|
||||||
|
|
||||||
|
#include "shield.h"
|
||||||
|
#include "board.h"
|
||||||
|
|
||||||
|
#define NETBIRD_GPIO_RST_SHIELD_N GPIO_TO_PIN(0, 27)
|
||||||
|
#define NETBIRD_GPIO_LOAD GPIO_TO_PIN(1, 9)
|
||||||
|
#define NETBIRD_GPIO_MODE_0 GPIO_TO_PIN(1, 11)
|
||||||
|
#define NETBIRD_GPIO_MODE_1 GPIO_TO_PIN(1, 10)
|
||||||
|
|
||||||
|
|
||||||
|
static int shield_slot_initialized = 0;
|
||||||
|
|
||||||
|
|
||||||
|
/* V2OK */
|
||||||
|
static struct module_pin_mux shield_gpio_safe_netbird_pin_mux[] = {
|
||||||
|
/* Leave UART0 unconfigured because we want to configure it as needed by linux (can/spi/uart/etc) */
|
||||||
|
{OFFSET(uart0_rxd), (MODE(7) | PULLUDDIS | RXACTIVE)}, /* (E15) UART0_RXD */
|
||||||
|
{OFFSET(uart0_txd), (MODE(7) | PULLUDDIS | RXACTIVE)}, /* (E16) UART0_TXD */
|
||||||
|
{-1},
|
||||||
|
};
|
||||||
|
|
||||||
|
static struct module_pin_mux shield_gpio_netbird_pin_mux[] = {
|
||||||
|
/* Leave UART0 unconfigured because we want to configure it as needed by linux (can/spi/uart/etc) */
|
||||||
|
{OFFSET(uart0_rxd), (MODE(7) | PULLUDDIS)}, /* (E15) UART0_RXD */
|
||||||
|
{OFFSET(uart0_txd), (MODE(7) | PULLUDEN | PULLUP_EN)}, /* (E16) UART0_TXD */
|
||||||
|
{-1},
|
||||||
|
};
|
||||||
|
|
||||||
|
static int request_gpios(void)
|
||||||
|
{
|
||||||
|
int ret;
|
||||||
|
|
||||||
|
debug("Extension slot init\n");
|
||||||
|
ret = shield_gpio_request_as_input(NETBIRD_GPIO_RST_SHIELD_N, "shield-rst");
|
||||||
|
if ((ret < 0))
|
||||||
|
return -1;
|
||||||
|
ret = shield_gpio_request_as_input(NETBIRD_GPIO_LOAD, "shield-load");
|
||||||
|
if ((ret < 0))
|
||||||
|
return -1;
|
||||||
|
ret = shield_gpio_request_as_input(NETBIRD_GPIO_MODE_0, "shield-mode0");
|
||||||
|
if ((ret < 0))
|
||||||
|
return -1;
|
||||||
|
ret = shield_gpio_request_as_input(NETBIRD_GPIO_MODE_1, "shield-mode1");
|
||||||
|
if ((ret < 0))
|
||||||
|
return -1;
|
||||||
|
|
||||||
|
shield_slot_initialized = 1;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int configure_shieldmode(int mode)
|
||||||
|
{
|
||||||
|
int ret;
|
||||||
|
|
||||||
|
if (mode < 0 || mode > 3) {
|
||||||
|
printf("Invalid shield mode %d\n", mode);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
debug("Shield type comio\n");
|
||||||
|
debug ("Set shield mode to %d\n", mode);
|
||||||
|
|
||||||
|
if (!shield_slot_initialized) {
|
||||||
|
if (request_gpios()) {
|
||||||
|
puts("Failed to request gpios\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
debug("Make sure shield module is in reset\n");
|
||||||
|
ret = gpio_direction_output(NETBIRD_GPIO_RST_SHIELD_N, 0);
|
||||||
|
if (ret < 0) {
|
||||||
|
puts("Can not set shield-rst as output\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
udelay(10);
|
||||||
|
|
||||||
|
debug("Enable gpio pull-ups\n");
|
||||||
|
configure_module_pin_mux(shield_gpio_netbird_pin_mux);
|
||||||
|
|
||||||
|
debug("Set load to low\n");
|
||||||
|
ret = gpio_direction_output(NETBIRD_GPIO_LOAD, 0);
|
||||||
|
if (ret < 0) {
|
||||||
|
puts("Can not set shield-load as output\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
udelay(10);
|
||||||
|
|
||||||
|
debug("Write mode to GPIOs\n");
|
||||||
|
ret = gpio_direction_output(NETBIRD_GPIO_MODE_0, mode & 0x01);
|
||||||
|
if (ret < 0) {
|
||||||
|
puts("Can not set shield-mode0 as output\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
ret = gpio_direction_output(NETBIRD_GPIO_MODE_1, mode & 0x02);
|
||||||
|
if (ret < 0) {
|
||||||
|
puts("Can not set shield-mode1 as output\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
udelay(10);
|
||||||
|
|
||||||
|
debug("Set load to high\n");
|
||||||
|
gpio_set_value(NETBIRD_GPIO_LOAD, 1);
|
||||||
|
udelay(10);
|
||||||
|
|
||||||
|
debug("Set mode0 and mode1 to highz again\n");
|
||||||
|
ret = gpio_direction_input(NETBIRD_GPIO_MODE_0);
|
||||||
|
if ((ret < 0)) {
|
||||||
|
puts("Could not configure shield slot mode0 gpio as input\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = gpio_direction_input(NETBIRD_GPIO_MODE_1);
|
||||||
|
if ((ret < 0)) {
|
||||||
|
puts("Could not configure shield slot mode1 gpio as input\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
udelay(10);
|
||||||
|
|
||||||
|
debug("Disable pullups on shield gpios\n");
|
||||||
|
configure_module_pin_mux(shield_gpio_safe_netbird_pin_mux);
|
||||||
|
udelay(10);
|
||||||
|
|
||||||
|
debug("Take shield out of reset\n");
|
||||||
|
gpio_set_value(NETBIRD_GPIO_RST_SHIELD_N, 1);
|
||||||
|
udelay(10);
|
||||||
|
|
||||||
|
debug("Set gpio load as input again\n");
|
||||||
|
ret = gpio_direction_input(NETBIRD_GPIO_LOAD);
|
||||||
|
if (ret < 0) {
|
||||||
|
puts("Can not configure shield slot load as input");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
static int get_rs232(const char *mode)
|
||||||
|
{
|
||||||
|
if (strcmp("rs232", mode) == 0) {
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static int get_termination(const char* termination)
|
||||||
|
{
|
||||||
|
if (strcmp("on", termination) == 0) {
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
else if (strcmp("off", termination) == 0) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
printf ("Invalid termination mode %s (falling back to off)", termination);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int get_mode_from_args(char * const argv[], int argc)
|
||||||
|
{
|
||||||
|
int termination = 0;
|
||||||
|
int rs232 = 0;
|
||||||
|
|
||||||
|
assert(argc >= 2);
|
||||||
|
|
||||||
|
if (strcmp ("mode", argv[0])) {
|
||||||
|
puts("Invalid arguments (see help)\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
rs232 = get_rs232(argv[1]);
|
||||||
|
|
||||||
|
if (argc > 2) {
|
||||||
|
if (rs232 || strcmp("termination", argv[2])) {
|
||||||
|
puts("Invalid arguments, do not configure termination\n");
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
termination = get_termination(argv[3]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Termination is inverse */
|
||||||
|
return (rs232 << 0) | ((!termination) << 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
int set_shieldmode(char * const argv[], int argc)
|
||||||
|
{
|
||||||
|
if (argc < 2) {
|
||||||
|
puts("Too few arguments for comio\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
configure_shieldmode(get_mode_from_args(argv, argc));
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct shield_t comio_shield = {
|
||||||
|
"comio", set_shieldmode
|
||||||
|
};
|
||||||
|
|
||||||
|
void comio_shield_init(void)
|
||||||
|
{
|
||||||
|
shield_register(&comio_shield);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
@ -0,0 +1,6 @@
|
||||||
|
#ifndef SHIELD_COMIO_H
|
||||||
|
#define SHIELD_COMIO_H
|
||||||
|
|
||||||
|
void comio_shield_init(void);
|
||||||
|
|
||||||
|
#endif // SHIELD_COMIO_H
|
||||||
|
|
@ -58,7 +58,8 @@
|
||||||
"kernel_addr=" KERNEL_ADDR "\0" \
|
"kernel_addr=" KERNEL_ADDR "\0" \
|
||||||
"load_addr=" LOAD_ADDR "\0" \
|
"load_addr=" LOAD_ADDR "\0" \
|
||||||
"root_part=1\0" /* Default root partition, overwritte in board file */ \
|
"root_part=1\0" /* Default root partition, overwritte in board file */ \
|
||||||
"add_sd_bootargs=setenv bootargs $bootargs root=/dev/mmcblk0p$root_part rootfstype=ext4 console=ttyS1,115200 rootwait loglevel=4\0" \
|
"defaultconsole=ttyS1\0" /* Default output console */ \
|
||||||
|
"add_sd_bootargs=setenv bootargs $bootargs root=/dev/mmcblk0p$root_part rootfstype=ext4 console=$defaultconsole,115200 rootwait loglevel=4\0" \
|
||||||
"add_version_bootargs=setenv bootargs $bootargs\0" \
|
"add_version_bootargs=setenv bootargs $bootargs\0" \
|
||||||
"fdt_skip_update=yes\0" \
|
"fdt_skip_update=yes\0" \
|
||||||
"ethprime=cpsw\0" \
|
"ethprime=cpsw\0" \
|
||||||
|
|
@ -69,7 +70,7 @@
|
||||||
"sdboot=if mmc dev 1; then echo Copying Linux from SD to RAM...; "\
|
"sdboot=if mmc dev 1; then echo Copying Linux from SD to RAM...; "\
|
||||||
"if test -e mmc 1:$root_part /boot/$kernel_image; then run sdprod; " \
|
"if test -e mmc 1:$root_part /boot/$kernel_image; then run sdprod; " \
|
||||||
"else run sdbringup; fi; " \
|
"else run sdbringup; fi; " \
|
||||||
"run add_sd_bootargs; run add_version_bootargs; " \
|
"run add_sd_bootargs; run add_version_bootargs; run shieldcmd; run modifyfdtcmd; " \
|
||||||
"bootz $kernel_addr - $fdt_addr; fi\0" \
|
"bootz $kernel_addr - $fdt_addr; fi\0" \
|
||||||
"bootcmd=run sdboot\0" \
|
"bootcmd=run sdboot\0" \
|
||||||
"ipaddr=192.168.1.1\0" \
|
"ipaddr=192.168.1.1\0" \
|
||||||
|
|
@ -83,7 +84,10 @@
|
||||||
"tftptimeoutcountmax=5\0" \
|
"tftptimeoutcountmax=5\0" \
|
||||||
"bootpretryperiod=2000\0" \
|
"bootpretryperiod=2000\0" \
|
||||||
"autoload=false\0" \
|
"autoload=false\0" \
|
||||||
"tftp_recovery=tftpboot $kernel_addr recovery-image; tftpboot $fdt_addr recovery-dtb; setenv bootargs rdinit=/etc/preinit console=ttyO1,115200 debug; bootz $kernel_addr - $fdt_addr\0" \
|
"shieldcmd=\0" \
|
||||||
|
"fdtshieldcmd=\0" \
|
||||||
|
"modifyfdtcmd=fdt addr $fdt_addr; run fdtshieldcmd;\0" \
|
||||||
|
"tftp_recovery=tftpboot $kernel_addr recovery-image; tftpboot $fdt_addr recovery-dtb; setenv bootargs rdinit=/etc/preinit console=$defaultconsole,115200 debug; run shieldcmd; run modifyfdtcmd; bootz $kernel_addr - $fdt_addr\0" \
|
||||||
"pxe_recovery=sleep 3 && dhcp && pxe get && pxe boot\0" \
|
"pxe_recovery=sleep 3 && dhcp && pxe get && pxe boot\0" \
|
||||||
"recovery=run pxe_recovery || setenv ipaddr $ipaddr; setenv serverip $serverip; run tftp_recovery\0" /* setenv ipaddr and serverip is necessary, because dhclient can destroy the IPs inernally */
|
"recovery=run pxe_recovery || setenv ipaddr $ipaddr; setenv serverip $serverip; run tftp_recovery\0" /* setenv ipaddr and serverip is necessary, because dhclient can destroy the IPs inernally */
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue