diff options
author | Andrew Jeffery <andrew@aj.id.au> | 2018-07-17 11:32:53 +0930 |
---|---|---|
committer | Stewart Smith <stewart@linux.ibm.com> | 2018-10-31 16:49:21 +1100 |
commit | 20e3d130d003e592387d65da8912c859eb4241f1 (patch) | |
tree | d92243986ab83c6a99dc5e45ef9cdbe28f7731b2 /platforms | |
parent | 5421d79dd212cced423d4dee85b01a118326ea14 (diff) | |
download | skiboot-20e3d130d003e592387d65da8912c859eb4241f1.zip skiboot-20e3d130d003e592387d65da8912c859eb4241f1.tar.gz skiboot-20e3d130d003e592387d65da8912c859eb4241f1.tar.bz2 |
ast-io: Rework setup/tear-down of communication with the BMC
[ Upstream commit ebc8524a3a457f73083d984296bfd797940a711c ]
It's possible for the platform to configure the BMC with SuperIO
access disabled. Rework the interfaces to report failures if SuperIO is
not enabled, and clean up once we're finished.
Signed-off-by: Andrew Jeffery <andrew@aj.id.au>
Signed-off-by: Stewart Smith <stewart@linux.ibm.com>
Diffstat (limited to 'platforms')
-rw-r--r-- | platforms/astbmc/astbmc.h | 1 | ||||
-rw-r--r-- | platforms/astbmc/common.c | 112 | ||||
-rw-r--r-- | platforms/astbmc/romulus.c | 2 | ||||
-rw-r--r-- | platforms/astbmc/witherspoon.c | 3 |
4 files changed, 96 insertions, 22 deletions
diff --git a/platforms/astbmc/astbmc.h b/platforms/astbmc/astbmc.h index fb6c68a..fc53d1a 100644 --- a/platforms/astbmc/astbmc.h +++ b/platforms/astbmc/astbmc.h @@ -89,6 +89,7 @@ extern void astbmc_init(void); extern void astbmc_ext_irq_serirq_cpld(unsigned int chip_id); extern int pnor_init(void); extern void check_all_slot_table(void); +extern void astbmc_exit(void); extern void slot_table_init(const struct slot_table_entry *top_table); extern void slot_table_get_slot_info(struct phb *phb, struct pci_device * pd); diff --git a/platforms/astbmc/common.c b/platforms/astbmc/common.c index 6c9f97d..03482fe 100644 --- a/platforms/astbmc/common.c +++ b/platforms/astbmc/common.c @@ -380,25 +380,13 @@ static void astbmc_fixup_psi_bar(void) xscom_write(chip->id, 0x201090A, psibar); } -void astbmc_early_init(void) +static void astbmc_fixup_uart(void) { - /* Hostboot's device-tree isn't quite right yet */ - astbmc_fixup_dt(); - - /* Hostboot forgets to populate the PSI BAR */ - astbmc_fixup_psi_bar(); - - /* Send external interrupts to me */ - psi_set_external_irq_policy(EXTERNAL_IRQ_POLICY_SKIBOOT); - - /* Initialize AHB accesses via AST2400 */ - ast_io_init(); - /* - * Depending on which image we are running, it may be configuring - * the virtual UART or not. Check if VUART is enabled and use - * SIO if not. We also correct the configuration of VUART as some - * BMC images don't setup the interrupt properly + * Depending on which image we are running, it may be configuring the + * virtual UART or not. Check if VUART is enabled and use SIO if not. + * We also correct the configuration of VUART as some BMC images don't + * setup the interrupt properly */ if (ast_is_vuart1_enabled()) { printf("PLAT: Using virtual UART\n"); @@ -408,11 +396,37 @@ void astbmc_early_init(void) printf("PLAT: Using SuperIO UART\n"); ast_setup_sio_uart1(UART_IO_BASE, UART_LPC_IRQ); } +} + +void astbmc_early_init(void) +{ + /* Hostboot's device-tree isn't quite right yet */ + astbmc_fixup_dt(); - /* Similarly, some BMCs don't configure the BT interrupt properly */ - ast_setup_ibt(BT_IO_BASE, BT_LPC_IRQ); + /* Hostboot forgets to populate the PSI BAR */ + astbmc_fixup_psi_bar(); + + /* Send external interrupts to me */ + psi_set_external_irq_policy(EXTERNAL_IRQ_POLICY_SKIBOOT); - ast_setup_sio_mbox(MBOX_IO_BASE, MBOX_LPC_IRQ); + if (ast_sio_init()) { + if (!ast_can_isolate_sp()) { + /* + * BMCs claiming support for isolation must have + * correctly configured the UART and BT for host + * firmware. If not, let's apply some fixups for broken + * BMC firmwares. + */ + if (ast_io_init()) { + astbmc_fixup_uart(); + ast_setup_ibt(BT_IO_BASE, BT_LPC_IRQ); + } else + prerror("PLAT: AST IO initialisation failed!\n"); + } + + ast_setup_sio_mbox(MBOX_IO_BASE, MBOX_LPC_IRQ); + } else + prerror("PLAT: AST SIO initialisation failed!\n"); /* Setup UART and use it as console */ uart_init(); @@ -422,6 +436,64 @@ void astbmc_early_init(void) prd_init(); } +static bool astbmc_isolate_via_io(void) +{ + uint32_t hw_strapping; + uint32_t silicon_rev; + uint8_t family; + + silicon_rev = ast_ahb_readl(SCU_REVISION_ID); + family = SCU_REVISION_SOC_FAMILY(silicon_rev); + + if (family == SCU_REVISION_SOC_FAMILY_2400) { + /* Strapping is read-modify-write on SCU70 */ + hw_strapping = SCU_STRAP_SIO_DECODE_DISABLE; + hw_strapping |= ast_ahb_readl(SCU_HW_STRAPPING); + } else if (family == SCU_REVISION_SOC_FAMILY_2500) { + /* + * Strapping is W1S on SCU70, W1C on SCU7C. We're setting a bit + * so read-modify-write *should* work, but in reality it breaks + * the AXI/AHB divider, so don't do that. + */ + hw_strapping = SCU_STRAP_SIO_DECODE_DISABLE; + } else { + prerror("PLAT: Unrecognised BMC silicon revision 0x%x, isolation failed\n", + silicon_rev); + return false; + } + + ast_ahb_writel(hw_strapping, SCU_HW_STRAPPING); + + return true; +} + +static bool astbmc_isolate_via_ipmi(void) +{ + return false; +} + +static void astbmc_isolate(void) +{ + bool isolated; + + isolated = ast_io_is_rw() ? astbmc_isolate_via_io() + : astbmc_isolate_via_ipmi(); + + if (!isolated) { + prlog(PR_EMERG, "PLAT: BMC isolation failed\n"); + abort(); + } + + prlog(PR_INFO, "PLAT: Isolated BMC\n"); +} + +void astbmc_exit(void) +{ + if (ast_can_isolate_sp()) + astbmc_isolate(); + ipmi_wdt_final_reset(); +} + const struct bmc_platform astbmc_ami = { .name = "AMI", .ipmi_oem_partial_add_esel = IPMI_CODE(0x3a, 0xf0), diff --git a/platforms/astbmc/romulus.c b/platforms/astbmc/romulus.c index 8d3d104..67c5946 100644 --- a/platforms/astbmc/romulus.c +++ b/platforms/astbmc/romulus.c @@ -80,6 +80,6 @@ DECLARE_PLATFORM(romulus) = { .cec_power_down = astbmc_ipmi_power_down, .cec_reboot = astbmc_ipmi_reboot, .elog_commit = ipmi_elog_commit, - .exit = ipmi_wdt_final_reset, + .exit = astbmc_exit, .terminate = ipmi_terminate, }; diff --git a/platforms/astbmc/witherspoon.c b/platforms/astbmc/witherspoon.c index cb09eef..d663709 100644 --- a/platforms/astbmc/witherspoon.c +++ b/platforms/astbmc/witherspoon.c @@ -29,6 +29,7 @@ #include <phb4.h> #include "astbmc.h" +#include "ast.h" /* * HACK: Hostboot doesn't export the correct data for the system VPD EEPROM @@ -165,7 +166,7 @@ DECLARE_PLATFORM(witherspoon) = { .cec_power_down = astbmc_ipmi_power_down, .cec_reboot = astbmc_ipmi_reboot, .elog_commit = ipmi_elog_commit, - .exit = ipmi_wdt_final_reset, + .exit = astbmc_exit, .terminate = ipmi_terminate, .pci_get_slot_info = dt_slot_get_slot_info, |