summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rwxr-xr-xsrc/build/debug/simics-debug-framework.py12
-rw-r--r--src/include/arch/ppc.H6
-rw-r--r--src/include/usr/pnor/pnorif.H11
-rw-r--r--src/usr/hwpf/hwp/start_payload/start_payload.C83
4 files changed, 105 insertions, 7 deletions
diff --git a/src/build/debug/simics-debug-framework.py b/src/build/debug/simics-debug-framework.py
index b0ae39551..de639f4fb 100755
--- a/src/build/debug/simics-debug-framework.py
+++ b/src/build/debug/simics-debug-framework.py
@@ -6,7 +6,10 @@
#
# OpenPOWER HostBoot Project
#
-# COPYRIGHT International Business Machines Corp. 2011,2014
+# Contributors Listed Below - COPYRIGHT 2011,2014
+# [+] Google Inc.
+# [+] International Business Machines Corp.
+#
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -503,6 +506,13 @@ def magic_instruction_callback(user_arg, cpu, arg):
cpu.r3 = 1
print "TimeManager::cv_isSimicsRunning = true"
+ if arg == 7012: # MAGIC_LOAD_PAYLOAD
+ load_addr = cpu.r3
+ flash_file = conf.fpga0.sfc_master_mmio_image.files[0][0]
+ print 'loading payload from', flash_file, 'to 0x%x' % load_addr
+ cmd = 'shell "fcp --force -o0 -R %s:PAYLOAD simicsPayload.ecc; ecc --remove --p8 simicsPayload.ecc simicsPayload"; load-file simicsPayload 0x%x' % (flash_file, load_addr)
+ SIM_run_alone( run_command, cmd )
+
if arg == 7055: # MAGIC_CONTINUOUS_TRACE
hb_tracBinaryBuffer = cpu.r4
hb_tracBinaryBufferSz = cpu.r5
diff --git a/src/include/arch/ppc.H b/src/include/arch/ppc.H
index 722771ff6..8d22c0790 100644
--- a/src/include/arch/ppc.H
+++ b/src/include/arch/ppc.H
@@ -5,7 +5,10 @@
/* */
/* OpenPOWER HostBoot Project */
/* */
-/* COPYRIGHT International Business Machines Corp. 2011,2014 */
+/* Contributors Listed Below - COPYRIGHT 2011,2014 */
+/* [+] Google Inc. */
+/* [+] International Business Machines Corp. */
+/* */
/* */
/* Licensed under the Apache License, Version 2.0 (the "License"); */
/* you may not use this file except in compliance with the License. */
@@ -413,6 +416,7 @@ enum
MAGIC_MEMORYLEAK_FUNCTION = 7009, // A memory was function called.
MAGIC_FAKEPAYLOAD_ENTER = 7010, // Entered the fake payload.
MAGIC_SIMICS_CHECK = 7011, // Check if system is running on simics
+ MAGIC_LOAD_PAYLOAD = 7012, // load payload from flash
MAGIC_CONTINUOUS_TRACE = 7055, // extract mixed trace buffer
};
diff --git a/src/include/usr/pnor/pnorif.H b/src/include/usr/pnor/pnorif.H
index 6593be1e8..94a9632b6 100644
--- a/src/include/usr/pnor/pnorif.H
+++ b/src/include/usr/pnor/pnorif.H
@@ -5,7 +5,10 @@
/* */
/* OpenPOWER HostBoot Project */
/* */
-/* COPYRIGHT International Business Machines Corp. 2011,2014 */
+/* Contributors Listed Below - COPYRIGHT 2011,2014 */
+/* [+] Google Inc. */
+/* [+] International Business Machines Corp. */
+/* */
/* */
/* Licensed under the Apache License, Version 2.0 (the "License"); */
/* you may not use this file except in compliance with the License. */
@@ -67,14 +70,16 @@ struct SectionInfo_t
{
SectionId id; /**< Identifier for this section */
const char* name; /**< Name of the section */
-
uint64_t vaddr; /**< Virtual address for the start of the section */
- uint64_t size; /**< Actual size of content in bytes */
+ uint64_t size; /**< Size of partition in bytes */
bool eccProtected; /**< Section is ECC protected */
bool sha512Version; /**< Version Checking */
bool sha512perEC; /**< Version Checking perEC */
};
+
+
+
/**
* @brief Return the size and address of a given section of PNOR data
*
diff --git a/src/usr/hwpf/hwp/start_payload/start_payload.C b/src/usr/hwpf/hwp/start_payload/start_payload.C
index 96cde5a1b..249d30808 100644
--- a/src/usr/hwpf/hwp/start_payload/start_payload.C
+++ b/src/usr/hwpf/hwp/start_payload/start_payload.C
@@ -5,7 +5,10 @@
/* */
/* OpenPOWER HostBoot Project */
/* */
-/* COPYRIGHT International Business Machines Corp. 2012,2014 */
+/* Contributors Listed Below - COPYRIGHT 2012,2014 */
+/* [+] Google Inc. */
+/* [+] International Business Machines Corp. */
+/* */
/* */
/* Licensed under the Apache License, Version 2.0 (the "License"); */
/* you may not use this file except in compliance with the License. */
@@ -55,6 +58,7 @@
#include <hwpf/hwp/occ/occ.H>
#include <sys/mm.h>
#include <devicefw/userif.H>
+#include <util/misc.H>
#include <initservice/isteps_trace.H>
#include <hwpisteperror.H>
@@ -77,6 +81,9 @@
#include <intr/interrupt.H>
#include <kernel/ipc.H> // for internode data areas
#include <mbox/ipc_msg_types.H>
+#include <pnor/pnorif.H>
+#include <sys/mm.h>
+#include <algorithm>
// Uncomment these files as they become available:
// #include "host_start_payload/host_start_payload.H"
@@ -89,7 +96,6 @@ using namespace fapi;
using namespace ISTEP;
using namespace ISTEP_ERROR;
-
/**
* @brief This function will call the Initservice interface to shutdown
* Hostboot. This function will call shutdown, passing in system
@@ -507,6 +513,77 @@ void* call_host_start_payload( void *io_pArgs )
return l_StepError.getErrorHandle();
}
+static void simics_load_payload(uint64_t addr) __attribute__((noinline));
+static void simics_load_payload(uint64_t addr)
+{
+ MAGIC_INSTRUCTION(MAGIC_LOAD_PAYLOAD);
+}
+
+static errlHndl_t load_pnor_section(PNOR::SectionId i_section,
+ uint64_t i_physAddr)
+{
+ // Get the section info from PNOR.
+ PNOR::SectionInfo_t pnorSectionInfo;
+ errlHndl_t err = PNOR::getSectionInfo( i_section,
+ pnorSectionInfo );
+ if( err != NULL )
+ {
+ return err;
+ }
+ const uint32_t payloadSize = pnorSectionInfo.size;
+
+ printk( "Loading PNOR section %d (%s) %d bytes @0x%lx\n",
+ i_section,
+ pnorSectionInfo.name,
+ payloadSize,
+ i_physAddr );
+
+ // Use simics optimization if we are running under simics which has very
+ // slow PNOR access.
+ if ( Util::isSimicsRunning() )
+ {
+ simics_load_payload( i_physAddr );
+ }
+ else
+ {
+ // Map in the physical memory we are loading into.
+ uint64_t loadAddr = reinterpret_cast<uint64_t>(
+ mm_block_map( reinterpret_cast<void*>( i_physAddr ),
+ payloadSize ) );
+
+ // Print out inital progress bar.
+#ifdef CONFIG_CONSOLE
+ const int progressSteps = 80;
+ int progress = 0;
+ for ( int i = 0; i < progressSteps; ++i )
+ {
+ printk( "." );
+ }
+ printk( "\r" );
+#endif
+
+ // Load the data block by block and update the progress bar.
+ const uint32_t BLOCK_SIZE = 4096;
+ for ( uint32_t i = 0; i < payloadSize; i += BLOCK_SIZE )
+ {
+ memcpy( reinterpret_cast<void*>( loadAddr + i ),
+ reinterpret_cast<void*>( pnorSectionInfo.vaddr + i ),
+ std::min( payloadSize - i, BLOCK_SIZE ) );
+#ifdef CONFIG_CONSOLE
+ for ( int new_progress = (i * progressSteps) / payloadSize;
+ progress <= new_progress; progress++ )
+ {
+ printk( "=" );
+ }
+#endif
+ }
+#ifdef CONFIG_CONSOLE
+ printk( "\n" );
+#endif
+ }
+
+ return NULL;
+}
//
// Call shutdown
@@ -607,6 +684,8 @@ errlHndl_t callShutdown ( uint64_t i_masterInstance,
// SP Base Services not enabled
if( is_sapphire_load() && (!INITSERVICE::spBaseServicesEnabled()))
{
+ err = load_pnor_section( PNOR::PAYLOAD, payloadBase );
+ if ( err ) { break; }
payloadData = DEVTREE::get_flatdevtree_phys_addr();
}
}
OpenPOWER on IntegriCloud