Skip to content

Commit c8c1a4c

Browse files
committed
efi/fake_mem: Refactor main two code chunks into functions
There is a whole load of generic EFI memory map code inside of the fake_mem driver which is better suited to being grouped with the rest of the generic EFI code for manipulating EFI memory maps. In preparation for that, this patch refactors the core code, so that it's possible to move entire functions later. Tested-by: Dave Young <dyoung@redhat.com> [kexec/kdump] Tested-by: Ard Biesheuvel <ard.biesheuvel@linaro.org> [arm] Acked-by: Ard Biesheuvel <ard.biesheuvel@linaro.org> Cc: Leif Lindholm <leif.lindholm@linaro.org> Cc: Peter Jones <pjones@redhat.com> Cc: Borislav Petkov <bp@alien8.de> Cc: Mark Rutland <mark.rutland@arm.com> Cc: Taku Izumi <izumi.taku@jp.fujitsu.com> Signed-off-by: Matt Fleming <matt@codeblueprint.co.uk>
1 parent dca0f97 commit c8c1a4c

File tree

1 file changed

+134
-95
lines changed

1 file changed

+134
-95
lines changed

drivers/firmware/efi/fake_mem.c

Lines changed: 134 additions & 95 deletions
Original file line numberDiff line numberDiff line change
@@ -54,43 +54,151 @@ static int __init cmp_fake_mem(const void *x1, const void *x2)
5454
return 0;
5555
}
5656

57+
/**
58+
* efi_fake_memmap_split_count - Count number of additional EFI memmap entries
59+
* @md: EFI memory descriptor to split
60+
* @range: Address range (start, end) to split around
61+
*
62+
* Returns the number of additional EFI memmap entries required to
63+
* accomodate @range.
64+
*/
65+
static int efi_fake_memmap_split_count(efi_memory_desc_t *md, struct range *range)
66+
{
67+
u64 m_start, m_end;
68+
u64 start, end;
69+
int count = 0;
70+
71+
start = md->phys_addr;
72+
end = start + (md->num_pages << EFI_PAGE_SHIFT) - 1;
73+
74+
/* modifying range */
75+
m_start = range->start;
76+
m_end = range->end;
77+
78+
if (m_start <= start) {
79+
/* split into 2 parts */
80+
if (start < m_end && m_end < end)
81+
count++;
82+
}
83+
84+
if (start < m_start && m_start < end) {
85+
/* split into 3 parts */
86+
if (m_end < end)
87+
count += 2;
88+
/* split into 2 parts */
89+
if (end <= m_end)
90+
count++;
91+
}
92+
93+
return count;
94+
}
95+
96+
/**
97+
* efi_fake_memmap_insert - Insert a fake memory region in an EFI memmap
98+
* @old_memmap: The existing EFI memory map structure
99+
* @buf: Address of buffer to store new map
100+
* @mem: Fake memory map entry to insert
101+
*
102+
* It is suggested that you call efi_fake_memmap_split_count() first
103+
* to see how large @buf needs to be.
104+
*/
105+
static void efi_fake_memmap_insert(struct efi_memory_map *old_memmap,
106+
void *buf, struct fake_mem *mem)
107+
{
108+
u64 m_start, m_end, m_attr;
109+
efi_memory_desc_t *md;
110+
u64 start, end;
111+
void *old, *new;
112+
113+
/* modifying range */
114+
m_start = mem->range.start;
115+
m_end = mem->range.end;
116+
m_attr = mem->attribute;
117+
118+
for (old = old_memmap->map, new = buf;
119+
old < old_memmap->map_end;
120+
old += old_memmap->desc_size, new += old_memmap->desc_size) {
121+
122+
/* copy original EFI memory descriptor */
123+
memcpy(new, old, old_memmap->desc_size);
124+
md = new;
125+
start = md->phys_addr;
126+
end = md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT) - 1;
127+
128+
if (m_start <= start && end <= m_end)
129+
md->attribute |= m_attr;
130+
131+
if (m_start <= start &&
132+
(start < m_end && m_end < end)) {
133+
/* first part */
134+
md->attribute |= m_attr;
135+
md->num_pages = (m_end - md->phys_addr + 1) >>
136+
EFI_PAGE_SHIFT;
137+
/* latter part */
138+
new += old_memmap->desc_size;
139+
memcpy(new, old, old_memmap->desc_size);
140+
md = new;
141+
md->phys_addr = m_end + 1;
142+
md->num_pages = (end - md->phys_addr + 1) >>
143+
EFI_PAGE_SHIFT;
144+
}
145+
146+
if ((start < m_start && m_start < end) && m_end < end) {
147+
/* first part */
148+
md->num_pages = (m_start - md->phys_addr) >>
149+
EFI_PAGE_SHIFT;
150+
/* middle part */
151+
new += old_memmap->desc_size;
152+
memcpy(new, old, old_memmap->desc_size);
153+
md = new;
154+
md->attribute |= m_attr;
155+
md->phys_addr = m_start;
156+
md->num_pages = (m_end - m_start + 1) >>
157+
EFI_PAGE_SHIFT;
158+
/* last part */
159+
new += old_memmap->desc_size;
160+
memcpy(new, old, old_memmap->desc_size);
161+
md = new;
162+
md->phys_addr = m_end + 1;
163+
md->num_pages = (end - m_end) >>
164+
EFI_PAGE_SHIFT;
165+
}
166+
167+
if ((start < m_start && m_start < end) &&
168+
(end <= m_end)) {
169+
/* first part */
170+
md->num_pages = (m_start - md->phys_addr) >>
171+
EFI_PAGE_SHIFT;
172+
/* latter part */
173+
new += old_memmap->desc_size;
174+
memcpy(new, old, old_memmap->desc_size);
175+
md = new;
176+
md->phys_addr = m_start;
177+
md->num_pages = (end - md->phys_addr + 1) >>
178+
EFI_PAGE_SHIFT;
179+
md->attribute |= m_attr;
180+
}
181+
}
182+
}
183+
57184
void __init efi_fake_memmap(void)
58185
{
59-
u64 start, end, m_start, m_end, m_attr;
60186
struct efi_memory_map_data data;
61187
int new_nr_map = efi.memmap.nr_map;
62188
efi_memory_desc_t *md;
63189
phys_addr_t new_memmap_phy;
64190
void *new_memmap;
65-
void *old, *new;
66191
int i;
67192

68193
if (!nr_fake_mem)
69194
return;
70195

71196
/* count up the number of EFI memory descriptor */
72-
for_each_efi_memory_desc(md) {
73-
start = md->phys_addr;
74-
end = start + (md->num_pages << EFI_PAGE_SHIFT) - 1;
75-
76-
for (i = 0; i < nr_fake_mem; i++) {
77-
/* modifying range */
78-
m_start = fake_mems[i].range.start;
79-
m_end = fake_mems[i].range.end;
80-
81-
if (m_start <= start) {
82-
/* split into 2 parts */
83-
if (start < m_end && m_end < end)
84-
new_nr_map++;
85-
}
86-
if (start < m_start && m_start < end) {
87-
/* split into 3 parts */
88-
if (m_end < end)
89-
new_nr_map += 2;
90-
/* split into 2 parts */
91-
if (end <= m_end)
92-
new_nr_map++;
93-
}
197+
for (i = 0; i < nr_fake_mem; i++) {
198+
for_each_efi_memory_desc(md) {
199+
struct range *r = &fake_mems[i].range;
200+
201+
new_nr_map += efi_fake_memmap_split_count(md, r);
94202
}
95203
}
96204

@@ -108,77 +216,8 @@ void __init efi_fake_memmap(void)
108216
return;
109217
}
110218

111-
for (old = efi.memmap.map, new = new_memmap;
112-
old < efi.memmap.map_end;
113-
old += efi.memmap.desc_size, new += efi.memmap.desc_size) {
114-
115-
/* copy original EFI memory descriptor */
116-
memcpy(new, old, efi.memmap.desc_size);
117-
md = new;
118-
start = md->phys_addr;
119-
end = md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT) - 1;
120-
121-
for (i = 0; i < nr_fake_mem; i++) {
122-
/* modifying range */
123-
m_start = fake_mems[i].range.start;
124-
m_end = fake_mems[i].range.end;
125-
m_attr = fake_mems[i].attribute;
126-
127-
if (m_start <= start && end <= m_end)
128-
md->attribute |= m_attr;
129-
130-
if (m_start <= start &&
131-
(start < m_end && m_end < end)) {
132-
/* first part */
133-
md->attribute |= m_attr;
134-
md->num_pages = (m_end - md->phys_addr + 1) >>
135-
EFI_PAGE_SHIFT;
136-
/* latter part */
137-
new += efi.memmap.desc_size;
138-
memcpy(new, old, efi.memmap.desc_size);
139-
md = new;
140-
md->phys_addr = m_end + 1;
141-
md->num_pages = (end - md->phys_addr + 1) >>
142-
EFI_PAGE_SHIFT;
143-
}
144-
145-
if ((start < m_start && m_start < end) && m_end < end) {
146-
/* first part */
147-
md->num_pages = (m_start - md->phys_addr) >>
148-
EFI_PAGE_SHIFT;
149-
/* middle part */
150-
new += efi.memmap.desc_size;
151-
memcpy(new, old, efi.memmap.desc_size);
152-
md = new;
153-
md->attribute |= m_attr;
154-
md->phys_addr = m_start;
155-
md->num_pages = (m_end - m_start + 1) >>
156-
EFI_PAGE_SHIFT;
157-
/* last part */
158-
new += efi.memmap.desc_size;
159-
memcpy(new, old, efi.memmap.desc_size);
160-
md = new;
161-
md->phys_addr = m_end + 1;
162-
md->num_pages = (end - m_end) >>
163-
EFI_PAGE_SHIFT;
164-
}
165-
166-
if ((start < m_start && m_start < end) &&
167-
(end <= m_end)) {
168-
/* first part */
169-
md->num_pages = (m_start - md->phys_addr) >>
170-
EFI_PAGE_SHIFT;
171-
/* latter part */
172-
new += efi.memmap.desc_size;
173-
memcpy(new, old, efi.memmap.desc_size);
174-
md = new;
175-
md->phys_addr = m_start;
176-
md->num_pages = (end - md->phys_addr + 1) >>
177-
EFI_PAGE_SHIFT;
178-
md->attribute |= m_attr;
179-
}
180-
}
181-
}
219+
for (i = 0; i < nr_fake_mem; i++)
220+
efi_fake_memmap_insert(&efi.memmap, new_memmap, &fake_mems[i]);
182221

183222
/* swap into new EFI memmap */
184223
early_memunmap(new_memmap, efi.memmap.desc_size * new_nr_map);

0 commit comments

Comments
 (0)