OpenCores
URL https://opencores.org/ocsvn/xenie/xenie/trunk

Subversion Repositories xenie

[/] [xenie/] [trunk/] [examples/] [Eth_example/] [mb_fw/] [xenie_eth_test_womtd/] [src/] [fw.c] - Blame information for rev 4

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 4 DFC
/***************************************************************************
2
 *
3
 * (C) Copyright 2017 DFC Design, s.r.o., Brno, Czech Republic
4
 * Author: Marek Kvas (m.kvas@dspfpga.com)
5
 *
6
 ***************************************************************************
7
 *
8
 * This file is part of Xenia Ethernet Example project.
9
 *
10
 * Xenia Ethernet Example project is free software: you can
11
 * redistribute it and/or modify it under the terms of
12
 * the GNU Lesser General Public License as published by the Free
13
 * Software Foundation, either version 3 of the License, or
14
 * (at your option) any later version.
15
 *
16
 * Xenia Ethernet Example project is distributed in the hope that
17
 * it will be useful, but WITHOUT ANY WARRANTY; without even
18
 * the implied warranty of MERCHANTABILITY or FITNESS FOR A
19
 * PARTICULAR PURPOSE.  See the GNU Lesser General Public License
20
 * for more details.
21
 *
22
 * You should have received a copy of the GNU Lesser General Public
23
 * License along with Xenia Ethernet Example project.  If not,
24
 * see <http://www.gnu.org/licenses/>.
25
 *
26
 ***************************************************************************
27
 */
28
 
29
#include <stdio.h>
30
#include <stdlib.h>
31
#include "uprintf.h"
32
#include "fw.h"
33
 
34
/* Min/max defs */
35
#define MIN(A, B) (((A) > (B))?(B):(A))
36
#define MAX(A, B) (((A) > (B))?(A):(B))
37
 
38
/*
39
 * Free dynamically allocated fw_hdr_ext
40
 * structure.
41
 *
42
 * Function always succeeds.
43
 */
44
void fw_free_hdr_ext_ptr(struct fw_hdr_ext **s)
45
{
46
        if(*s == NULL)
47
                return;
48
        if((*s)->fw_meta_ptr != NULL)
49
                free((*s)->fw_meta_ptr);
50
        if((*s)->fw_data_ptr != NULL)
51
                free((*s)->fw_data_ptr);
52
 
53
        free(*s);
54
        *s = NULL;
55
}
56
 
57
/*
58
 * Check for presence of FW in flash and
59
 * dynamically allocate structure describing it.
60
 * FW is recognized by magic on the beginning of
61
 * header.
62
 *
63
 * On success, zero is returned. On error,
64
 * negative number is returned.
65
 */
66
 
67
int fw_find_in_flash(struct spansion_flash *sf, uint32_t fw_hdr_flash_offset, struct fw_hdr_ext **fw_hdr_ext_ptr)
68
{
69
        int i;
70
        int res;
71
        int ret = 0;
72
        uint8_t rd_buf[SPANSION_FLASH_PAGE_SIZE + SPANSION_FLASH_BUF_OVERHEAD +1];
73
        struct fw_hdr_ext *fhe;
74
        uint8_t *dst;
75
        int byte_count;
76
        uint32_t flash_addr;
77
 
78
        /* Allocate space for structure */
79
        fhe = malloc(sizeof(*fhe));
80
        if(fhe == NULL) {
81
                ret = -1; goto err;
82
        }
83
        fhe->fw_hdr_flash_off = fw_hdr_flash_offset;
84
 
85
        /* Read FW header */
86
        res = spansion_flash_quad_io_read(sf, fhe->fw_hdr_flash_off,
87
                        rd_buf, sizeof(fhe->fw_hdr));
88
        if(res != XST_SUCCESS) {
89
                ret = -3; goto err;
90
        }
91
        /* Copy header from buffer */
92
        memcpy(&fhe->fw_hdr, rd_buf+SPANSION_FLASH_BUF_OVERHEAD, sizeof(fhe->fw_hdr)); /* be careful about offset */
93
        /* Check magic */
94
        if(strncmp("MVFW", fhe->fw_hdr.magic, 4)) {
95
                ret = -4; goto err;
96
        }
97
 
98
        /* Read metadata from header (allocate memory for it)*/
99
        i = fhe->fw_hdr.fw_offset - sizeof(struct fw_hdr);
100
 
101
        fhe->fw_meta_ptr = malloc(i + 1);
102
        if(fhe->fw_meta_ptr == NULL) {
103
                ret = -5; goto err;
104
        }
105
        dst = fhe->fw_meta_ptr;
106
        flash_addr = fhe->fw_hdr_flash_off;
107
 
108
        while (i > 0) {
109
                byte_count = MIN(i, SPANSION_FLASH_PAGE_SIZE);
110
                res = spansion_flash_quad_io_read(sf, flash_addr, rd_buf, byte_count);
111
                if(res != XST_SUCCESS) {
112
                        ret = -6; goto err;
113
                }
114
                memcpy(dst, rd_buf + SPANSION_FLASH_BUF_OVERHEAD, byte_count);
115
                dst += byte_count;
116
                flash_addr += byte_count;
117
                i-= byte_count;
118
        }
119
        *dst = '\0';
120
 
121
        *fw_hdr_ext_ptr = fhe;
122
        return ret;
123
err:
124
        fw_free_hdr_ext_ptr(&fhe);
125
        return ret;
126
}
127
 
128
void fw_print_info(struct fw_hdr_ext *fhe)
129
{
130
        uprintf("FW header at: 0x%08x\r\n", fhe->fw_hdr_flash_off);
131
        uprintf("FW at: 0x%08x (offset 0x%08x)\r\n", fhe->fw_hdr_flash_off + fhe->fw_hdr.fw_offset,
132
                        fhe->fw_hdr.fw_offset);
133
        uprintf("FW length: %u B\r\n", fhe->fw_hdr.fw_length);
134
}
135
 
136
/*
137
 * Read FW described by fw_hdr_ext_ptr.
138
 * Buffer for FW is dynamically allocated.
139
 *
140
 * On success, zero is returned. On error,
141
 * negative number is returned.
142
 */
143
int fw_read_from_flash(struct spansion_flash *sf, struct fw_hdr_ext *fw_hdr_ext_ptr)
144
{
145
        int i;
146
        int res;
147
        uint8_t rd_buf[SPANSION_FLASH_PAGE_SIZE + SPANSION_FLASH_BUF_OVERHEAD +1];
148
        u8 *dst;
149
        int byte_count;
150
        uint32_t flash_addr;
151
 
152
        /* Allocate memory for buffer */
153
        fw_hdr_ext_ptr->fw_data_ptr = malloc(fw_hdr_ext_ptr->fw_hdr.fw_length);
154
        if(fw_hdr_ext_ptr->fw_data_ptr == NULL)
155
                return -1;
156
 
157
        /* Read whole fw */
158
        i = fw_hdr_ext_ptr->fw_hdr.fw_length;
159
        dst = fw_hdr_ext_ptr->fw_data_ptr;
160
        flash_addr = fw_hdr_ext_ptr->fw_hdr_flash_off + fw_hdr_ext_ptr->fw_hdr.fw_offset;
161
        byte_count = 0;
162
        while (i > 0) {
163
                byte_count = MIN(i, SPANSION_FLASH_PAGE_SIZE);
164
                res = spansion_flash_quad_io_read(sf, flash_addr, rd_buf, byte_count);
165
                if(res != XST_SUCCESS) {
166
                        return -2;
167
                }
168
                memcpy(dst, rd_buf + SPANSION_FLASH_BUF_OVERHEAD, byte_count);
169
                dst += byte_count;
170
                flash_addr += byte_count;
171
                i-= byte_count;
172
        }
173
 
174
        return 0;
175
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.