blob: f4b8d2541dfd8ff085d4f3314663cb18b29565cc [file] [log] [blame]
Patrick Georgi11f00792020-03-04 15:10:45 +01001/* SPDX-License-Identifier: GPL-2.0-only */
Martin Roth9df9e9392016-01-12 15:55:28 -07002
Arthur Heymans50ece622021-05-04 08:46:58 +02003#include <fmap_config.h>
Patrick Georgi9341acd2009-12-23 12:52:56 +00004
Julius Wernerd69ccaf2023-04-05 16:18:32 -07005#if CONFIG(CBFS_VERIFICATION)
6#error "walkcbfs_asm is not safe to use with CBFS verification!"
7#endif
8
Patrick Georgi4d3e4c42015-07-14 22:28:27 +02009/* we use this instead of CBFS_HEADER_ALIGN because the latter is retired. */
10#define CBFS_ALIGNMENT 64
11
Patrick Georgi9341acd2009-12-23 12:52:56 +000012#define CBFS_FILE_MAGIC 0
13#define CBFS_FILE_LEN (CBFS_FILE_MAGIC + 8)
14#define CBFS_FILE_TYPE (CBFS_FILE_LEN + 4)
15#define CBFS_FILE_CHECKSUM (CBFS_FILE_TYPE + 4)
16#define CBFS_FILE_OFFSET (CBFS_FILE_CHECKSUM + 4)
17
18#define CBFS_FILE_STRUCTSIZE (CBFS_FILE_OFFSET + 4)
19
Arthur Heymansddbc7712021-06-12 22:33:25 +020020#if FMAP_SECTION_COREBOOT_START < (0xffffffff - CONFIG_ROM_SIZE + 1)
21#define COREBOOT_CBFS_START (0xffffffff - CONFIG_ROM_SIZE + 1 + FMAP_SECTION_COREBOOT_START)
22#else
23#define COREBOOT_CBFS_START FMAP_SECTION_COREBOOT_START
24#endif
25
Patrick Rudolph38138222020-08-21 16:38:48 +020026.code32
Kyösti Mälkki7522a8f2020-11-20 16:47:38 +020027.section .init
Alexandru Gagniucc46a3922015-10-02 16:17:41 -070028.global walkcbfs_asm
29
Patrick Georgi9341acd2009-12-23 12:52:56 +000030/*
Stefan Reinauer1fdfed12011-04-14 20:33:53 +000031 * input %esi: filename
32 * input %esp: return address (not pointer to return address!)
Alexandru Gagniuc299c2652013-12-08 01:13:43 -060033 * output %eax: pointer to CBFS header
Stefan Reinauer1fdfed12011-04-14 20:33:53 +000034 * clobbers %ebx, %ecx, %edi
35 */
Patrick Georgifab35e32011-03-08 07:50:43 +000036walkcbfs_asm:
Patrick Georgif6fbfaf2010-02-22 12:58:01 +000037 cld
38
Arthur Heymansddbc7712021-06-12 22:33:25 +020039 movl $COREBOOT_CBFS_START, %ebx
Patrick Georgi9341acd2009-12-23 12:52:56 +000040
Patrick Georgi1bb68282009-12-31 12:56:53 +000041 /* determine filename length */
42 mov $0, %eax
431:
44 cmpb $0, (%eax,%esi)
45 jz 2f
46 add $1, %eax
47 jmp 1b
482:
49 add $1, %eax
Patrick Georgi9341acd2009-12-23 12:52:56 +000050walker:
Stefan Reinauer1fdfed12011-04-14 20:33:53 +000051 mov 0(%ebx), %edi /* Check for LARCHIVE header */
Patrick Georgif6fbfaf2010-02-22 12:58:01 +000052 cmp %edi, filemagic
53 jne searchfile
54 mov 4(%ebx), %edi
55 cmp %edi, filemagic+4
56 jne searchfile
57
Stefan Reinauer1fdfed12011-04-14 20:33:53 +000058 /* LARCHIVE header found */
Patrick Georgi9341acd2009-12-23 12:52:56 +000059 mov %ebx, %edi
Lee Leahy6f80ccc2017-03-16 15:18:22 -070060 add $CBFS_FILE_STRUCTSIZE, %edi /* edi = address of first byte after
61 * struct cbfs_file
62 */
Patrick Georgi1bb68282009-12-31 12:56:53 +000063 mov %eax, %ecx
Patrick Georgi9341acd2009-12-23 12:52:56 +000064 repe cmpsb
Stefan Reinauer1fdfed12011-04-14 20:33:53 +000065 /* zero flag set if strings are equal */
Patrick Georgi9341acd2009-12-23 12:52:56 +000066 jnz tryharder
67
Stefan Reinauer1fdfed12011-04-14 20:33:53 +000068 /* we found it! */
Alexandru Gagniuc299c2652013-12-08 01:13:43 -060069 mov %ebx, %eax
Patrick Georgi9341acd2009-12-23 12:52:56 +000070 jmp *%esp
71
72tryharder:
Patrick Georgif6fbfaf2010-02-22 12:58:01 +000073 sub %ebx, %edi
74 sub $CBFS_FILE_STRUCTSIZE, %edi /* edi = # of walked bytes */
Patrick Georgi1bb68282009-12-31 12:56:53 +000075 sub %edi, %esi /* esi = start of filename */
76
77 /* ebx = ecx = (current+offset+len+ALIGN-1) & ~(ALIGN-1) */
Patrick Georgi9341acd2009-12-23 12:52:56 +000078 mov CBFS_FILE_OFFSET(%ebx), %ecx
79 bswap %ecx
80 add %ebx, %ecx
81 mov CBFS_FILE_LEN(%ebx), %edi
82 bswap %edi
83 add %edi, %ecx
Patrick Georgi4d3e4c42015-07-14 22:28:27 +020084 /* round by 64 bytes */
85 add $(CBFS_ALIGNMENT - 1), %ecx
86 and $~(CBFS_ALIGNMENT - 1), %ecx
Patrick Georgif6fbfaf2010-02-22 12:58:01 +000087
88 /* if oldaddr >= addr, leave */
89 cmp %ebx, %ecx
90 jbe out
91
Patrick Georgi9341acd2009-12-23 12:52:56 +000092 mov %ecx, %ebx
93
Patrick Georgif6fbfaf2010-02-22 12:58:01 +000094check_for_exit:
Arthur Heymans50ece622021-05-04 08:46:58 +020095 /* if addr <= COREBOOT_END - 1, continue */
96#define FMAP_SECTION_COREBOOT_END (FMAP_SECTION_COREBOOT_START - 1 + FMAP_SECTION_COREBOOT_SIZE)
Patrick Georgi9341acd2009-12-23 12:52:56 +000097
Arthur Heymans50ece622021-05-04 08:46:58 +020098 movl $FMAP_SECTION_COREBOOT_END, %ecx
Patrick Georgif6fbfaf2010-02-22 12:58:01 +000099 cmp %ecx, %ebx
Patrick Georgi9341acd2009-12-23 12:52:56 +0000100 jbe walker
101
Patrick Georgif6fbfaf2010-02-22 12:58:01 +0000102out:
Patrick Georgi9341acd2009-12-23 12:52:56 +0000103 mov $0, %eax
104 jmp *%esp
Patrick Georgif6fbfaf2010-02-22 12:58:01 +0000105
106
107searchfile:
Patrick Georgi4d3e4c42015-07-14 22:28:27 +0200108 /* if filemagic isn't found, move forward 64 bytes */
109 add $CBFS_ALIGNMENT, %ebx
Patrick Georgif6fbfaf2010-02-22 12:58:01 +0000110 jmp check_for_exit
111
112filemagic:
113 .ascii "LARCHIVE"