Skip to content

Commit b46dcfa

Browse files
committed
xtensa: allow merging vectors into .text section
Currently code for exception/IRQ vectors is stored in kernel image as initialization data and is copied to its working addresses during startup. It doesn't always make sense. In many cases vectors location can be automatically decided at kernel link time and code can be placed right there. This is especially useful for XIP kernel. Signed-off-by: Max Filippov <[email protected]>
1 parent 9a736fc commit b46dcfa

File tree

3 files changed

+48
-0
lines changed

3 files changed

+48
-0
lines changed

arch/xtensa/include/asm/vectors.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,11 @@ static inline unsigned long xtensa_get_kio_paddr(void)
6767
#endif /* CONFIG_MMU */
6868

6969
#define RESET_VECTOR1_VADDR (XCHAL_RESET_VECTOR1_VADDR)
70+
#ifdef CONFIG_VECTORS_OFFSET
7071
#define VECBASE_VADDR (KERNELOFFSET - CONFIG_VECTORS_OFFSET)
72+
#else
73+
#define VECBASE_VADDR _vecbase
74+
#endif
7175

7276
#if defined(XCHAL_HAVE_VECBASE) && XCHAL_HAVE_VECBASE
7377

arch/xtensa/kernel/setup.c

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -455,6 +455,7 @@ void __init setup_arch(char **cmdline_p)
455455

456456
mem_reserve(__pa(&_stext), __pa(&_end));
457457

458+
#ifdef CONFIG_VECTORS_OFFSET
458459
mem_reserve(__pa(&_WindowVectors_text_start),
459460
__pa(&_WindowVectors_text_end));
460461

@@ -491,6 +492,8 @@ void __init setup_arch(char **cmdline_p)
491492
__pa(&_Level6InterruptVector_text_end));
492493
#endif
493494

495+
#endif /* CONFIG_VECTORS_OFFSET */
496+
494497
#ifdef CONFIG_SMP
495498
mem_reserve(__pa(&_SecondaryResetVector_text_start),
496499
__pa(&_SecondaryResetVector_text_end));

arch/xtensa/kernel/vmlinux.lds.S

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,7 @@ jiffies = jiffies_64;
5959
* garbage.)
6060
*/
6161

62+
#ifdef CONFIG_VECTORS_OFFSET
6263
#define SECTION_VECTOR(sym, section, addr, max_prevsec_size, prevsec) \
6364
section addr : AT((MIN(LOADADDR(prevsec) + max_prevsec_size, \
6465
LOADADDR(prevsec) + SIZEOF(prevsec)) + 3) & ~ 3) \
@@ -68,6 +69,11 @@ jiffies = jiffies_64;
6869
*(section) \
6970
sym ## _end = ABSOLUTE(.); \
7071
}
72+
#else
73+
#define SECTION_VECTOR(section, addr) \
74+
. = addr; \
75+
*(section)
76+
#endif
7177

7278
/*
7379
* Mapping of input sections to output sections when linking.
@@ -85,6 +91,37 @@ SECTIONS
8591
{
8692
/* The HEAD_TEXT section must be the first section! */
8793
HEAD_TEXT
94+
95+
#ifndef CONFIG_VECTORS_OFFSET
96+
. = ALIGN(PAGE_SIZE);
97+
_vecbase = .;
98+
99+
SECTION_VECTOR (.WindowVectors.text, WINDOW_VECTORS_VADDR)
100+
#if XCHAL_EXCM_LEVEL >= 2
101+
SECTION_VECTOR (.Level2InterruptVector.text, INTLEVEL2_VECTOR_VADDR)
102+
#endif
103+
#if XCHAL_EXCM_LEVEL >= 3
104+
SECTION_VECTOR (.Level3InterruptVector.text, INTLEVEL3_VECTOR_VADDR)
105+
#endif
106+
#if XCHAL_EXCM_LEVEL >= 4
107+
SECTION_VECTOR (.Level4InterruptVector.text, INTLEVEL4_VECTOR_VADDR)
108+
#endif
109+
#if XCHAL_EXCM_LEVEL >= 5
110+
SECTION_VECTOR (.Level5InterruptVector.text, INTLEVEL5_VECTOR_VADDR)
111+
#endif
112+
#if XCHAL_EXCM_LEVEL >= 6
113+
SECTION_VECTOR (.Level6InterruptVector.text, INTLEVEL6_VECTOR_VADDR)
114+
#endif
115+
SECTION_VECTOR (.DebugInterruptVector.literal, DEBUG_VECTOR_VADDR - 4)
116+
SECTION_VECTOR (.DebugInterruptVector.text, DEBUG_VECTOR_VADDR)
117+
SECTION_VECTOR (.KernelExceptionVector.literal, KERNEL_VECTOR_VADDR - 4)
118+
SECTION_VECTOR (.KernelExceptionVector.text, KERNEL_VECTOR_VADDR)
119+
SECTION_VECTOR (.UserExceptionVector.literal, USER_VECTOR_VADDR - 4)
120+
SECTION_VECTOR (.UserExceptionVector.text, USER_VECTOR_VADDR)
121+
SECTION_VECTOR (.DoubleExceptionVector.literal, DOUBLEEXC_VECTOR_VADDR - 48)
122+
SECTION_VECTOR (.DoubleExceptionVector.text, DOUBLEEXC_VECTOR_VADDR)
123+
#endif
124+
88125
TEXT_TEXT
89126
VMLINUX_SYMBOL(__sched_text_start) = .;
90127
*(.sched.literal .sched.text)
@@ -132,6 +169,7 @@ SECTIONS
132169
. = ALIGN(16);
133170
__boot_reloc_table_start = ABSOLUTE(.);
134171

172+
#ifdef CONFIG_VECTORS_OFFSET
135173
RELOCATE_ENTRY(_WindowVectors_text,
136174
.WindowVectors.text);
137175
#if XCHAL_EXCM_LEVEL >= 2
@@ -164,6 +202,7 @@ SECTIONS
164202
.DoubleExceptionVector.text);
165203
RELOCATE_ENTRY(_DebugInterruptVector_text,
166204
.DebugInterruptVector.text);
205+
#endif
167206
#if defined(CONFIG_SMP)
168207
RELOCATE_ENTRY(_SecondaryResetVector_text,
169208
.SecondaryResetVector.text);
@@ -186,6 +225,7 @@ SECTIONS
186225
. = ALIGN(4);
187226
.dummy : { LONG(0) }
188227

228+
#ifdef CONFIG_VECTORS_OFFSET
189229
/* The vectors are relocated to the real position at startup time */
190230

191231
SECTION_VECTOR (_WindowVectors_text,
@@ -277,6 +317,7 @@ SECTIONS
277317

278318
. = (LOADADDR( .DoubleExceptionVector.text ) + SIZEOF( .DoubleExceptionVector.text ) + 3) & ~ 3;
279319

320+
#endif
280321
#if defined(CONFIG_SMP)
281322

282323
SECTION_VECTOR (_SecondaryResetVector_text,

0 commit comments

Comments
 (0)