diff packages/devs/flash/intel/strata/current/src/strata.c @ 156:b939e9cada46

Merge from eCos master repository on 2001-03-29-21:44:39-BST
author jlarmour
date Fri, 06 Apr 2001 17:20:13 +0000
parents
children 511f4dc167f6
line wrap: on
line diff
new file mode 100644
--- /dev/null
+++ b/packages/devs/flash/intel/strata/current/src/strata.c
@@ -0,0 +1,165 @@
+//==========================================================================
+//
+//      strata.c
+//
+//      Flash programming
+//
+//==========================================================================
+//####COPYRIGHTBEGIN####
+//                                                                          
+// -------------------------------------------                              
+// The contents of this file are subject to the Red Hat eCos Public License 
+// Version 1.1 (the "License"); you may not use this file except in         
+// compliance with the License.  You may obtain a copy of the License at    
+// http://www.redhat.com/                                                   
+//                                                                          
+// Software distributed under the License is distributed on an "AS IS"      
+// basis, WITHOUT WARRANTY OF ANY KIND, either express or implied.  See the 
+// License for the specific language governing rights and limitations under 
+// the License.                                                             
+//                                                                          
+// The Original Code is eCos - Embedded Configurable Operating System,      
+// released September 30, 1998.                                             
+//                                                                          
+// The Initial Developer of the Original Code is Red Hat.                   
+// Portions created by Red Hat are                                          
+// Copyright (C) 1998, 1999, 2000, 2001 Red Hat, Inc.
+// All Rights Reserved.                                                     
+// -------------------------------------------                              
+//                                                                          
+//####COPYRIGHTEND####
+//==========================================================================
+//#####DESCRIPTIONBEGIN####
+//
+// Author(s):    gthomas, hmt
+// Contributors: gthomas
+// Date:         2001-02-14
+// Purpose:      
+// Description:  
+//              
+//####DESCRIPTIONEND####
+//
+//==========================================================================
+
+#include <pkgconf/system.h>
+#include <pkgconf/hal.h>
+#include <cyg/hal/hal_arch.h>
+#include <cyg/hal/hal_cache.h>
+
+#define  _FLASH_PRIVATE_
+#include <cyg/io/flash.h>
+
+#include "strata.h"
+
+#define _si(p) ((p[1]<<8)|p[0])
+
+extern void diag_dump_buf(void *buf, CYG_ADDRWORD len);
+
+extern int strncmp(const char *s1, const char *s2, int len);
+
+int
+flash_hwr_init(void)
+{
+    struct FLASH_query data, *qp;
+    extern char flash_query, flash_query_end;
+    typedef int code_fun(unsigned char *);
+    code_fun *_flash_query;
+    int code_len, stat, num_regions, region_size, buffer_size;
+
+    // Copy 'program' code to RAM for execution
+    code_len = (unsigned long)&flash_query_end - (unsigned long)&flash_query;
+    _flash_query = (code_fun *)flash_info.work_space;
+    memcpy(_flash_query, &flash_query, code_len);
+    HAL_DCACHE_SYNC();  // Should guarantee this code will run
+    HAL_ICACHE_DISABLE(); // is also required to avoid old contents
+
+    stat = (*_flash_query)((unsigned char *)&data);
+    HAL_ICACHE_ENABLE();
+
+    qp = &data;
+    if ( (qp->manuf_code == FLASH_Intel_code)
+#ifdef CYGOPT_FLASH_IS_BOOTBLOCK
+         // device types go as follows: 0x90 for 16-bits, 0xD0 for 8-bits,
+         // plus 0 or 1 for -T (Top Boot) or -B (Bottom Boot)
+         //     [FIXME: whatever that means :FIXME]
+         // [I think it means the boot blocks are top/bottom of addr space]
+         // plus the following size codes:
+         //    0: 16Mbit    2:  8Mbit    4:  4Mbit
+         //    6: 32Mbit    8: 64Mbit
+#if 16 == CYGNUM_FLASH_WIDTH         
+         && (0x90 == (0xF0 & qp->device_code)) // 16-bit devices
+#elif 8 == CYGNUM_FLASH_WIDTH
+         && (0xD0 == (0xF0 & qp->device_code)) // 8-bit devices
+#else
+         && 0
+#error Only understand 16 and 8-bit bootblock flash types
+#endif
+        ) {
+        int lookup[] = { 16, 8, 4, 32, 64 };
+#define BLOCKSIZE (0x10000)
+        region_size = BLOCKSIZE;
+        num_regions = qp->device_code & 0x0F;
+        num_regions >>= 1;
+        if ( num_regions > 4 )
+            goto flash_type_unknown;
+        num_regions = lookup[num_regions];
+        num_regions *= 1024 * 1024;     // to bits
+        num_regions /= 8;               // to bytes
+        num_regions /= BLOCKSIZE;       // to blocks
+        buffer_size = 0;
+#else // CYGOPT_FLASH_IS_BOOTBLOCK
+         && (strncmp(qp->id, "QRY", 3) == 0)) {
+        num_regions = _si(qp->num_regions)+1;
+        region_size = _si(qp->region_size)*256;       
+        if (_si(qp->buffer_size)) {
+            buffer_size = CYGNUM_FLASH_DEVICES << _si(qp->buffer_size);
+        } else {
+            buffer_size = 0;
+        }
+#endif // Not CYGOPT_FLASH_IS_BOOTBLOCK
+
+        flash_info.block_size = region_size*CYGNUM_FLASH_DEVICES;
+        flash_info.buffer_size = buffer_size;
+        flash_info.blocks = num_regions;
+        flash_info.start = (void *)CYGNUM_FLASH_BASE;
+        flash_info.end = (void *)(CYGNUM_FLASH_BASE +
+                        (num_regions*region_size*CYGNUM_FLASH_DEVICES));
+        return FLASH_ERR_OK;
+    }
+ flash_type_unknown:
+    printf("Can't identify FLASH, sorry, man %x, dev %x, id [%4s] stat %x\n",
+           qp->manuf_code, qp->device_code, qp->id, stat );
+    diag_dump_buf(qp, sizeof(data));
+    return FLASH_ERR_HWR;
+}
+
+// Map a hardware status to a package error
+int
+flash_hwr_map_error(int err)
+{
+    if (err & FLASH_ErrorMask) {
+        printf("Err = %x\n", err);
+        if (err & FLASH_ErrorProgram)
+            return FLASH_ERR_PROGRAM;
+        else if (err & FLASH_ErrorErase)
+            return FLASH_ERR_ERASE;
+        else 
+            return FLASH_ERR_HWR;  // FIXME
+    } else {
+        return FLASH_ERR_OK;
+    }
+}
+
+// See if a range of FLASH addresses overlaps currently running code
+bool
+flash_code_overlaps(void *start, void *end)
+{
+    extern char _stext[], _etext[];
+
+    return ((((unsigned long)&_stext >= (unsigned long)start) &&
+             ((unsigned long)&_stext < (unsigned long)end)) ||
+            (((unsigned long)&_etext >= (unsigned long)start) &&
+             ((unsigned long)&_etext < (unsigned long)end)));
+}
+
+// EOF strata.c