]> git.pld-linux.org Git - packages/xen.git/blob - 0008-libelf-introduce-macros-for-memory-access-and-pointe.patch
- only run xen services on dom0
[packages/xen.git] / 0008-libelf-introduce-macros-for-memory-access-and-pointe.patch
1 From 40020ab55a1e9a1674ddecdb70299fab4fe8579d Mon Sep 17 00:00:00 2001
2 From: Ian Jackson <ian.jackson@eu.citrix.com>
3 Date: Fri, 14 Jun 2013 16:43:17 +0100
4 Subject: [PATCH 08/23] libelf: introduce macros for memory access and pointer handling
5
6 We introduce a collection of macros which abstract away all the
7 pointer arithmetic and dereferences used for accessing the input ELF
8 and the output area(s).  We use the new macros everywhere.
9
10 For now, these macros are semantically identical to the code they
11 replace, so this patch has no functional change.
12
13 elf_is_elfbinary is an exception: since it doesn't take an elf*, we
14 need to handle it differently.  In a future patch we will change it to
15 take, and check, a length parameter.  For now we just mark it with a
16 fixme.
17
18 That this patch has no functional change can be verified as follows:
19
20   0. Copy the scripts "comparison-generate" and "function-filter"
21      out of this commit message.
22   1. Check out the tree before this patch.
23   2. Run the script ../comparison-generate .... ../before
24   3. Check out the tree after this patch.
25   4. Run the script ../comparison-generate .... ../after
26   5. diff --exclude=\*.[soi] -ruN before/ after/ |less
27
28 Expect these differences:
29   * stubdom/zlib-x86_64/ztest*.s2
30       The filename of this test file apparently contains the pid.
31   * xen/common/version.s2
32       The xen build timestamp appears in two diff hunks.
33
34 Verification that this is all that's needed:
35   In a completely built xen.git,
36      find * -name .*.d -type f | xargs grep -l libelf\.h
37   Expect results in:
38      xen/arch/x86:            Checked above.
39      tools/libxc:             Checked above.
40      tools/xcutils/readnotes: Checked above.
41      tools/xenstore:          Checked above.
42      xen/common/libelf:
43        This is the build for the hypervisor; checked in B above.
44      stubdom:
45        We have one stubdom which reads ELFs using our libelf,
46        pvgrub, which is checked above.
47
48 I have not done this verification for ARM.
49
50 This is part of the fix to a security issue, XSA-55.
51
52 Signed-off-by: Ian Jackson <ian.jackson@eu.citrix.com>
53 Acked-by: Ian Campbell <ian.campbell@citrix.com>
54 Reviewed-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
55
56 -8<- comparison-generate -8<-
57  #!/bin/bash
58  # usage:
59  #  cd xen.git
60  #  .../comparison-generate OUR-CONFIG BUILD-RUNE-PREFIX ../before|../after
61  # eg:
62  #  .../comparison-generate ~/work/.config 'schroot -pc64 --' ../before
63  set -ex
64
65  test $# = 3 || need-exactly-three-arguments
66
67  our_config=$1
68  build_rune_prefix=$2
69  result_dir=$3
70
71  git clean -x -d -f
72
73  cp "$our_config" .
74
75  cat <<END >>.config
76          debug_symbols=n
77          CFLAGS += -save-temps
78  END
79
80  perl -i~ -pe 's/ -g / -g0 / if m/^CFLAGS/' xen/Rules.mk
81
82  if [ -f ./configure ]; then
83          $build_rune_prefix ./configure
84  fi
85
86  $build_rune_prefix make -C xen
87  $build_rune_prefix make -C tools/include
88  $build_rune_prefix make -C stubdom grub
89  $build_rune_prefix make -C tools/libxc
90  $build_rune_prefix make -C tools/xenstore
91  $build_rune_prefix make -C tools/xcutils
92
93  rm -rf "$result_dir"
94  mkdir "$result_dir"
95
96  set +x
97  for f in `find xen tools stubdom -name \*.[soi]`; do
98          mkdir -p "$result_dir"/`dirname $f`
99          cp $f "$result_dir"/${f}
100          case $f in
101          *.s)
102                  ../function-filter <$f >"$result_dir"/${f}2
103                  ;;
104          esac
105  done
106
107  echo ok.
108 -8<-
109
110 -8<- function-filter -8<-
111  #!/usr/bin/perl -w
112  # function-filter
113  # script for massaging gcc-generated labels to be consistent
114  use strict;
115  our @lines;
116  my $sedderybody = "sub seddery () {\n";
117  while (<>) {
118      push @lines, $_;
119      if (m/^(__FUNCTION__|__func__)\.(\d+)\:/) {
120          $sedderybody .= "    s/\\b$1\\.$2\\b/__XSA55MANGLED__$1.$./g;\n";
121      }
122  }
123  $sedderybody .= "}\n1;\n";
124  eval $sedderybody or die $@;
125  foreach (@lines) {
126      seddery();
127      print or die $!;
128  }
129 -8<-
130 ---
131  tools/libxc/xc_dom_elfloader.c     |   30 +++---
132  tools/libxc/xc_hvm_build_x86.c     |    2 +-
133  tools/xcutils/readnotes.c          |   26 +++---
134  xen/common/libelf/libelf-dominfo.c |   51 +++++-----
135  xen/common/libelf/libelf-loader.c  |   84 +++++++++--------
136  xen/common/libelf/libelf-tools.c   |   94 +++++++++---------
137  xen/include/xen/libelf.h           |  188 +++++++++++++++++++++++++++++++-----
138  7 files changed, 312 insertions(+), 163 deletions(-)
139
140 diff --git a/tools/libxc/xc_dom_elfloader.c b/tools/libxc/xc_dom_elfloader.c
141 index e82f6e9..cc0f206 100644
142 --- a/tools/libxc/xc_dom_elfloader.c
143 +++ b/tools/libxc/xc_dom_elfloader.c
144 @@ -115,9 +115,9 @@ static int xc_dom_load_elf_symtab(struct xc_dom_image *dom,
145                                    struct elf_binary *elf, int load)
146  {
147      struct elf_binary syms;
148 -    const elf_shdr *shdr, *shdr2;
149 +    ELF_HANDLE_DECL_NONCONST(elf_shdr) shdr; ELF_HANDLE_DECL(elf_shdr) shdr2;
150      xen_vaddr_t symtab, maxaddr;
151 -    char *hdr;
152 +    ELF_PTRVAL_CHAR hdr;
153      size_t size;
154      int h, count, type, i, tables = 0;
155  
156 @@ -147,11 +147,11 @@ static int xc_dom_load_elf_symtab(struct xc_dom_image *dom,
157          dom->bsd_symtab_start = elf_round_up(elf, dom->kernel_seg.vend);
158      }
159  
160 -    memcpy(hdr + sizeof(int),
161 -           elf->image,
162 +    elf_memcpy_safe(elf, hdr + sizeof(int),
163 +           ELF_IMAGE_BASE(elf),
164             elf_size(elf, elf->ehdr));
165 -    memcpy(hdr + sizeof(int) + elf_size(elf, elf->ehdr),
166 -           elf->image + elf_uval(elf, elf->ehdr, e_shoff),
167 +    elf_memcpy_safe(elf, hdr + sizeof(int) + elf_size(elf, elf->ehdr),
168 +           ELF_IMAGE_BASE(elf) + elf_uval(elf, elf->ehdr, e_shoff),
169             elf_shdr_count(elf) * elf_size(elf, shdr));
170      if ( elf_64bit(elf) )
171      {
172 @@ -189,7 +189,7 @@ static int xc_dom_load_elf_symtab(struct xc_dom_image *dom,
173      count = elf_shdr_count(&syms);
174      for ( h = 0; h < count; h++ )
175      {
176 -        shdr = elf_shdr_by_index(&syms, h);
177 +        shdr = ELF_OBSOLETE_VOIDP_CAST elf_shdr_by_index(&syms, h);
178          type = elf_uval(&syms, shdr, sh_type);
179          if ( type == SHT_STRTAB )
180          {
181 @@ -205,9 +205,9 @@ static int xc_dom_load_elf_symtab(struct xc_dom_image *dom,
182              if ( i == count )
183              {
184                  if ( elf_64bit(&syms) )
185 -                    *(Elf64_Off*)(&shdr->e64.sh_offset) = 0;
186 +                    elf_store_field(elf, shdr, e64.sh_offset, 0);
187                  else
188 -                    *(Elf32_Off*)(&shdr->e32.sh_offset) = 0;
189 +                    elf_store_field(elf, shdr, e32.sh_offset, 0);
190                  continue;
191              }
192          }
193 @@ -216,9 +216,9 @@ static int xc_dom_load_elf_symtab(struct xc_dom_image *dom,
194          {
195              /* Mangled to be based on ELF header location. */
196              if ( elf_64bit(&syms) )
197 -                *(Elf64_Off*)(&shdr->e64.sh_offset) = maxaddr - symtab;
198 +                elf_store_field(elf, shdr, e64.sh_offset, maxaddr - symtab);
199              else
200 -                *(Elf32_Off*)(&shdr->e32.sh_offset) = maxaddr - symtab;
201 +                elf_store_field(elf, shdr, e32.sh_offset, maxaddr - symtab);
202              size = elf_uval(&syms, shdr, sh_size);
203              maxaddr = elf_round_up(&syms, maxaddr + size);
204              tables++;
205 @@ -230,7 +230,7 @@ static int xc_dom_load_elf_symtab(struct xc_dom_image *dom,
206              if ( load )
207              {
208                  shdr2 = elf_shdr_by_index(elf, h);
209 -                memcpy((void*)elf_section_start(&syms, shdr),
210 +                elf_memcpy_safe(elf, ELF_OBSOLETE_VOIDP_CAST elf_section_start(&syms, shdr),
211                         elf_section_start(elf, shdr2),
212                         size);
213              }
214 @@ -238,9 +238,9 @@ static int xc_dom_load_elf_symtab(struct xc_dom_image *dom,
215  
216          /* Name is NULL. */
217          if ( elf_64bit(&syms) )
218 -            *(Elf64_Word*)(&shdr->e64.sh_name) = 0;
219 +            elf_store_field(elf, shdr, e64.sh_name, 0);
220          else
221 -            *(Elf32_Word*)(&shdr->e32.sh_name) = 0;
222 +            elf_store_field(elf, shdr, e32.sh_name, 0);
223      }
224  
225      if ( tables == 0 )
226 @@ -275,7 +275,7 @@ static int xc_dom_parse_elf_kernel(struct xc_dom_image *dom)
227      }
228  
229      /* Find the section-header strings table. */
230 -    if ( elf->sec_strtab == NULL )
231 +    if ( ELF_PTRVAL_INVALID(elf->sec_strtab) )
232      {
233          xc_dom_panic(dom->xch, XC_INVALID_KERNEL, "%s: ELF image"
234                       " has no shstrtab", __FUNCTION__);
235 diff --git a/tools/libxc/xc_hvm_build_x86.c b/tools/libxc/xc_hvm_build_x86.c
236 index cf5d7fb..15b603d 100644
237 --- a/tools/libxc/xc_hvm_build_x86.c
238 +++ b/tools/libxc/xc_hvm_build_x86.c
239 @@ -110,7 +110,7 @@ static int loadelfimage(
240      if ( elf->dest == NULL )
241          goto err;
242  
243 -    elf->dest += elf->pstart & (PAGE_SIZE - 1);
244 +    ELF_ADVANCE_DEST(elf, elf->pstart & (PAGE_SIZE - 1));
245  
246      /* Load the initial elf image. */
247      rc = elf_load_binary(elf);
248 diff --git a/tools/xcutils/readnotes.c b/tools/xcutils/readnotes.c
249 index c926186..2af047d 100644
250 --- a/tools/xcutils/readnotes.c
251 +++ b/tools/xcutils/readnotes.c
252 @@ -61,13 +61,13 @@ struct setup_header {
253  } __attribute__((packed));
254  
255  static void print_string_note(const char *prefix, struct elf_binary *elf,
256 -                             const elf_note *note)
257 +                             ELF_HANDLE_DECL(elf_note) note)
258  {
259         printf("%s: %s\n", prefix, (char*)elf_note_desc(elf, note));
260  }
261  
262  static void print_numeric_note(const char *prefix, struct elf_binary *elf,
263 -                              const elf_note *note)
264 +                              ELF_HANDLE_DECL(elf_note) note)
265  {
266         uint64_t value = elf_note_numeric(elf, note);
267         int descsz = elf_uval(elf, note, descsz);
268 @@ -98,12 +98,12 @@ static void print_l1_mfn_valid_note(const char *prefix, struct elf_binary *elf,
269  
270  }
271  
272 -static int print_notes(struct elf_binary *elf, const elf_note *start, const elf_note *end)
273 +static int print_notes(struct elf_binary *elf, ELF_HANDLE_DECL(elf_note) start, ELF_HANDLE_DECL(elf_note) end)
274  {
275 -       const elf_note *note;
276 +       ELF_HANDLE_DECL(elf_note) note;
277         int notes_found = 0;
278  
279 -       for ( note = start; note < end; note = elf_note_next(elf, note) )
280 +       for ( note = start; ELF_HANDLE_PTRVAL(note) < ELF_HANDLE_PTRVAL(end); note = elf_note_next(elf, note) )
281         {
282                 if (0 != strcmp(elf_note_name(elf, note), "Xen"))
283                         continue;
284 @@ -170,7 +170,7 @@ int main(int argc, char **argv)
285         void *image,*tmp;
286         struct stat st;
287         struct elf_binary elf;
288 -       const elf_shdr *shdr;
289 +       ELF_HANDLE_DECL(elf_shdr) shdr;
290         int notes_found = 0;
291  
292         struct setup_header *hdr;
293 @@ -257,7 +257,7 @@ int main(int argc, char **argv)
294         count = elf_phdr_count(&elf);
295         for ( h=0; h < count; h++)
296         {
297 -               const elf_phdr *phdr;
298 +               ELF_HANDLE_DECL(elf_phdr) phdr;
299                 phdr = elf_phdr_by_index(&elf, h);
300                 if (elf_uval(&elf, phdr, p_type) != PT_NOTE)
301                         continue;
302 @@ -269,8 +269,8 @@ int main(int argc, char **argv)
303                         continue;
304  
305                 notes_found = print_notes(&elf,
306 -                                         elf_segment_start(&elf, phdr),
307 -                                         elf_segment_end(&elf, phdr));
308 +                                         ELF_MAKE_HANDLE(elf_note, elf_segment_start(&elf, phdr)),
309 +                                         ELF_MAKE_HANDLE(elf_note, elf_segment_end(&elf, phdr)));
310         }
311  
312         if ( notes_found == 0 )
313 @@ -278,13 +278,13 @@ int main(int argc, char **argv)
314                 count = elf_shdr_count(&elf);
315                 for ( h=0; h < count; h++)
316                 {
317 -                       const elf_shdr *shdr;
318 +                       ELF_HANDLE_DECL(elf_shdr) shdr;
319                         shdr = elf_shdr_by_index(&elf, h);
320                         if (elf_uval(&elf, shdr, sh_type) != SHT_NOTE)
321                                 continue;
322                         notes_found = print_notes(&elf,
323 -                                                 elf_section_start(&elf, shdr),
324 -                                                 elf_section_end(&elf, shdr));
325 +                                                 ELF_MAKE_HANDLE(elf_note, elf_section_start(&elf, shdr)),
326 +                                                 ELF_MAKE_HANDLE(elf_note, elf_section_end(&elf, shdr)));
327                         if ( notes_found )
328                                 fprintf(stderr, "using notes from SHT_NOTE section\n");
329  
330 @@ -292,7 +292,7 @@ int main(int argc, char **argv)
331         }
332  
333         shdr = elf_shdr_by_name(&elf, "__xen_guest");
334 -       if (shdr)
335 +       if (ELF_HANDLE_VALID(shdr))
336                 printf("__xen_guest: %s\n", (char*)elf_section_start(&elf, shdr));
337  
338         return 0;
339 diff --git a/xen/common/libelf/libelf-dominfo.c b/xen/common/libelf/libelf-dominfo.c
340 index 523837f..7140d59 100644
341 --- a/xen/common/libelf/libelf-dominfo.c
342 +++ b/xen/common/libelf/libelf-dominfo.c
343 @@ -44,7 +44,7 @@ int elf_xen_parse_features(const char *features,
344  
345      for ( pos = 0; features[pos] != '\0'; pos += len )
346      {
347 -        memset(feature, 0, sizeof(feature));
348 +        elf_memset_unchecked(feature, 0, sizeof(feature));
349          for ( len = 0;; len++ )
350          {
351              if ( len >= sizeof(feature)-1 )
352 @@ -96,7 +96,7 @@ int elf_xen_parse_features(const char *features,
353  
354  int elf_xen_parse_note(struct elf_binary *elf,
355                         struct elf_dom_parms *parms,
356 -                       const elf_note *note)
357 +                       ELF_HANDLE_DECL(elf_note) note)
358  {
359  /* *INDENT-OFF* */
360      static const struct {
361 @@ -215,15 +215,16 @@ int elf_xen_parse_note(struct elf_binary *elf,
362  
363  static int elf_xen_parse_notes(struct elf_binary *elf,
364                                 struct elf_dom_parms *parms,
365 -                               const void *start, const void *end)
366 +                               ELF_PTRVAL_CONST_VOID start,
367 +                               ELF_PTRVAL_CONST_VOID end)
368  {
369      int xen_elfnotes = 0;
370 -    const elf_note *note;
371 +    ELF_HANDLE_DECL(elf_note) note;
372  
373      parms->elf_note_start = start;
374      parms->elf_note_end   = end;
375 -    for ( note = parms->elf_note_start;
376 -          (void *)note < parms->elf_note_end;
377 +    for ( note = ELF_MAKE_HANDLE(elf_note, parms->elf_note_start);
378 +          ELF_HANDLE_PTRVAL(note) < parms->elf_note_end;
379            note = elf_note_next(elf, note) )
380      {
381          if ( strcmp(elf_note_name(elf, note), "Xen") )
382 @@ -241,45 +242,46 @@ static int elf_xen_parse_notes(struct elf_binary *elf,
383  int elf_xen_parse_guest_info(struct elf_binary *elf,
384                               struct elf_dom_parms *parms)
385  {
386 -    const char *h;
387 +    ELF_PTRVAL_CONST_CHAR h;
388      char name[32], value[128];
389      int len;
390  
391      h = parms->guest_info;
392 -    while ( *h )
393 +#define STAR(h) (*(h))
394 +    while ( STAR(h) )
395      {
396 -        memset(name, 0, sizeof(name));
397 -        memset(value, 0, sizeof(value));
398 +        elf_memset_unchecked(name, 0, sizeof(name));
399 +        elf_memset_unchecked(value, 0, sizeof(value));
400          for ( len = 0;; len++, h++ )
401          {
402              if ( len >= sizeof(name)-1 )
403                  break;
404 -            if ( *h == '\0' )
405 +            if ( STAR(h) == '\0' )
406                  break;
407 -            if ( *h == ',' )
408 +            if ( STAR(h) == ',' )
409              {
410                  h++;
411                  break;
412              }
413 -            if ( *h == '=' )
414 +            if ( STAR(h) == '=' )
415              {
416                  h++;
417                  for ( len = 0;; len++, h++ )
418                  {
419                      if ( len >= sizeof(value)-1 )
420                          break;
421 -                    if ( *h == '\0' )
422 +                    if ( STAR(h) == '\0' )
423                          break;
424 -                    if ( *h == ',' )
425 +                    if ( STAR(h) == ',' )
426                      {
427                          h++;
428                          break;
429                      }
430 -                    value[len] = *h;
431 +                    value[len] = STAR(h);
432                  }
433                  break;
434              }
435 -            name[len] = *h;
436 +            name[len] = STAR(h);
437          }
438          elf_msg(elf, "%s: %s=\"%s\"\n", __FUNCTION__, name, value);
439  
440 @@ -328,7 +330,8 @@ int elf_xen_parse_guest_info(struct elf_binary *elf,
441  static int elf_xen_note_check(struct elf_binary *elf,
442                                struct elf_dom_parms *parms)
443  {
444 -    if ( (parms->elf_note_start == NULL) && (parms->guest_info == NULL) )
445 +    if ( (ELF_PTRVAL_INVALID(parms->elf_note_start)) &&
446 +         (ELF_PTRVAL_INVALID(parms->guest_info)) )
447      {
448          int machine = elf_uval(elf, elf->ehdr, e_machine);
449          if ( (machine == EM_386) || (machine == EM_X86_64) )
450 @@ -457,12 +460,12 @@ static int elf_xen_addr_calc_check(struct elf_binary *elf,
451  int elf_xen_parse(struct elf_binary *elf,
452                    struct elf_dom_parms *parms)
453  {
454 -    const elf_shdr *shdr;
455 -    const elf_phdr *phdr;
456 +    ELF_HANDLE_DECL(elf_shdr) shdr;
457 +    ELF_HANDLE_DECL(elf_phdr) phdr;
458      int xen_elfnotes = 0;
459      int i, count, rc;
460  
461 -    memset(parms, 0, sizeof(*parms));
462 +    elf_memset_unchecked(parms, 0, sizeof(*parms));
463      parms->virt_base = UNSET_ADDR;
464      parms->virt_entry = UNSET_ADDR;
465      parms->virt_hypercall = UNSET_ADDR;
466 @@ -532,11 +535,11 @@ int elf_xen_parse(struct elf_binary *elf,
467          for ( i = 0; i < count; i++ )
468          {
469              shdr = elf_shdr_by_name(elf, "__xen_guest");
470 -            if ( shdr )
471 +            if ( ELF_HANDLE_VALID(shdr) )
472              {
473                  parms->guest_info = elf_section_start(elf, shdr);
474 -                parms->elf_note_start = NULL;
475 -                parms->elf_note_end   = NULL;
476 +                parms->elf_note_start = ELF_INVALID_PTRVAL;
477 +                parms->elf_note_end   = ELF_INVALID_PTRVAL;
478                  elf_msg(elf, "%s: __xen_guest: \"%s\"\n", __FUNCTION__,
479                          parms->guest_info);
480                  elf_xen_parse_guest_info(elf, parms);
481 diff --git a/xen/common/libelf/libelf-loader.c b/xen/common/libelf/libelf-loader.c
482 index ec0706b..0fef84c 100644
483 --- a/xen/common/libelf/libelf-loader.c
484 +++ b/xen/common/libelf/libelf-loader.c
485 @@ -26,7 +26,7 @@
486  
487  int elf_init(struct elf_binary *elf, const char *image, size_t size)
488  {
489 -    const elf_shdr *shdr;
490 +    ELF_HANDLE_DECL(elf_shdr) shdr;
491      uint64_t i, count, section, offset;
492  
493      if ( !elf_is_elfbinary(image) )
494 @@ -35,7 +35,7 @@ int elf_init(struct elf_binary *elf, const char *image, size_t size)
495          return -1;
496      }
497  
498 -    memset(elf, 0, sizeof(*elf));
499 +    elf_memset_unchecked(elf, 0, sizeof(*elf));
500      elf->image = image;
501      elf->size = size;
502      elf->ehdr = (elf_ehdr *)image;
503 @@ -65,7 +65,7 @@ int elf_init(struct elf_binary *elf, const char *image, size_t size)
504      /* Find section string table. */
505      section = elf_uval(elf, elf->ehdr, e_shstrndx);
506      shdr = elf_shdr_by_index(elf, section);
507 -    if ( shdr != NULL )
508 +    if ( ELF_HANDLE_VALID(shdr) )
509          elf->sec_strtab = elf_section_start(elf, shdr);
510  
511      /* Find symbol table and symbol string table. */
512 @@ -77,9 +77,9 @@ int elf_init(struct elf_binary *elf, const char *image, size_t size)
513              continue;
514          elf->sym_tab = shdr;
515          shdr = elf_shdr_by_index(elf, elf_uval(elf, shdr, sh_link));
516 -        if ( shdr == NULL )
517 +        if ( !ELF_HANDLE_VALID(shdr) )
518          {
519 -            elf->sym_tab = NULL;
520 +            elf->sym_tab = ELF_INVALID_HANDLE(elf_shdr);
521              continue;
522          }
523          elf->sym_strtab = elf_section_start(elf, shdr);
524 @@ -113,10 +113,11 @@ void elf_set_log(struct elf_binary *elf, elf_log_callback *log_callback,
525  }
526  
527  static int elf_load_image(struct elf_binary *elf,
528 -                          void *dst, const void *src, uint64_t filesz, uint64_t memsz)
529 +                          ELF_PTRVAL_VOID dst, ELF_PTRVAL_CONST_VOID src,
530 +                          uint64_t filesz, uint64_t memsz)
531  {
532 -    memcpy(dst, src, filesz);
533 -    memset(dst + filesz, 0, memsz - filesz);
534 +    elf_memcpy_safe(elf, dst, src, filesz);
535 +    elf_memset_safe(elf, dst + filesz, 0, memsz - filesz);
536      return 0;
537  }
538  #else
539 @@ -126,16 +127,17 @@ void elf_set_verbose(struct elf_binary *elf)
540      elf->verbose = 1;
541  }
542  
543 -static int elf_load_image(struct elf_binary *elf,
544 -                          void *dst, const void *src, uint64_t filesz, uint64_t memsz)
545 +static int elf_load_image(struct elf_binary *elf, ELF_PTRVAL_VOID dst, ELF_PTRVAL_CONST_VOID src, uint64_t filesz, uint64_t memsz)
546  {
547      int rc;
548      if ( filesz > ULONG_MAX || memsz > ULONG_MAX )
549          return -1;
550 -    rc = raw_copy_to_guest(dst, src, filesz);
551 +    /* We trust the dom0 kernel image completely, so we don't care
552 +     * about overruns etc. here. */
553 +    rc = raw_copy_to_guest(ELF_UNSAFE_PTR(dst), ELF_UNSAFE_PTR(src), filesz);
554      if ( rc != 0 )
555          return -1;
556 -    rc = raw_clear_guest(dst + filesz, memsz - filesz);
557 +    rc = raw_clear_guest(ELF_UNSAFE_PTR(dst + filesz), memsz - filesz);
558      if ( rc != 0 )
559          return -1;
560      return 0;
561 @@ -146,10 +148,10 @@ static int elf_load_image(struct elf_binary *elf,
562  void elf_parse_bsdsyms(struct elf_binary *elf, uint64_t pstart)
563  {
564      uint64_t sz;
565 -    const elf_shdr *shdr;
566 +    ELF_HANDLE_DECL(elf_shdr) shdr;
567      int i, type;
568  
569 -    if ( !elf->sym_tab )
570 +    if ( !ELF_HANDLE_VALID(elf->sym_tab) )
571          return;
572  
573      pstart = elf_round_up(elf, pstart);
574 @@ -166,7 +168,7 @@ void elf_parse_bsdsyms(struct elf_binary *elf, uint64_t pstart)
575      for ( i = 0; i < elf_shdr_count(elf); i++ )
576      {
577          shdr = elf_shdr_by_index(elf, i);
578 -        type = elf_uval(elf, (elf_shdr *)shdr, sh_type);
579 +        type = elf_uval(elf, shdr, sh_type);
580          if ( (type == SHT_STRTAB) || (type == SHT_SYMTAB) )
581              sz = elf_round_up(elf, sz + elf_uval(elf, shdr, sh_size));
582      }
583 @@ -177,10 +179,12 @@ void elf_parse_bsdsyms(struct elf_binary *elf, uint64_t pstart)
584  
585  static void elf_load_bsdsyms(struct elf_binary *elf)
586  {
587 -    elf_ehdr *sym_ehdr;
588 +    ELF_HANDLE_DECL_NONCONST(elf_ehdr) sym_ehdr;
589      unsigned long sz;
590 -    char *maxva, *symbase, *symtab_addr;
591 -    elf_shdr *shdr;
592 +    ELF_PTRVAL_VOID maxva;
593 +    ELF_PTRVAL_VOID symbase;
594 +    ELF_PTRVAL_VOID symtab_addr;
595 +    ELF_HANDLE_DECL_NONCONST(elf_shdr) shdr;
596      int i, type;
597  
598      if ( !elf->bsd_symtab_pstart )
599 @@ -189,18 +193,18 @@ static void elf_load_bsdsyms(struct elf_binary *elf)
600  #define elf_hdr_elm(_elf, _hdr, _elm, _val)     \
601  do {                                            \
602      if ( elf_64bit(_elf) )                      \
603 -        (_hdr)->e64._elm = _val;                \
604 +        elf_store_field(_elf, _hdr, e64._elm, _val);  \
605      else                                        \
606 -        (_hdr)->e32._elm = _val;                \
607 +        elf_store_field(_elf, _hdr, e32._elm, _val);  \
608  } while ( 0 )
609  
610      symbase = elf_get_ptr(elf, elf->bsd_symtab_pstart);
611      symtab_addr = maxva = symbase + sizeof(uint32_t);
612  
613      /* Set up Elf header. */
614 -    sym_ehdr = (elf_ehdr *)symtab_addr;
615 +    sym_ehdr = ELF_MAKE_HANDLE(elf_ehdr, symtab_addr);
616      sz = elf_uval(elf, elf->ehdr, e_ehsize);
617 -    memcpy(sym_ehdr, elf->ehdr, sz);
618 +    elf_memcpy_safe(elf, ELF_HANDLE_PTRVAL(sym_ehdr), ELF_HANDLE_PTRVAL(elf->ehdr), sz);
619      maxva += sz; /* no round up */
620  
621      elf_hdr_elm(elf, sym_ehdr, e_phoff, 0);
622 @@ -209,37 +213,39 @@ do {                                            \
623      elf_hdr_elm(elf, sym_ehdr, e_phnum, 0);
624  
625      /* Copy Elf section headers. */
626 -    shdr = (elf_shdr *)maxva;
627 +    shdr = ELF_MAKE_HANDLE(elf_shdr, maxva);
628      sz = elf_shdr_count(elf) * elf_uval(elf, elf->ehdr, e_shentsize);
629 -    memcpy(shdr, elf->image + elf_uval(elf, elf->ehdr, e_shoff), sz);
630 -    maxva = (char *)(long)elf_round_up(elf, (long)maxva + sz);
631 +    elf_memcpy_safe(elf, ELF_HANDLE_PTRVAL(shdr),
632 +                    ELF_IMAGE_BASE(elf) + elf_uval(elf, elf->ehdr, e_shoff),
633 +                    sz);
634 +    maxva = ELF_OBSOLETE_VOIDP_CAST elf_round_up(elf, (long)maxva + sz);
635  
636      for ( i = 0; i < elf_shdr_count(elf); i++ )
637      {
638          type = elf_uval(elf, shdr, sh_type);
639          if ( (type == SHT_STRTAB) || (type == SHT_SYMTAB) )
640          {
641 -             elf_msg(elf, "%s: shdr %i at 0x%p -> 0x%p\n", __func__, i,
642 +             elf_msg(elf, "%s: shdr %i at 0x%"ELF_PRPTRVAL" -> 0x%"ELF_PRPTRVAL"\n", __func__, i,
643                       elf_section_start(elf, shdr), maxva);
644               sz = elf_uval(elf, shdr, sh_size);
645 -             memcpy(maxva, elf_section_start(elf, shdr), sz);
646 +             elf_memcpy_safe(elf, maxva, elf_section_start(elf, shdr), sz);
647               /* Mangled to be based on ELF header location. */
648               elf_hdr_elm(elf, shdr, sh_offset, maxva - symtab_addr);
649 -             maxva = (char *)(long)elf_round_up(elf, (long)maxva + sz);
650 +             maxva = ELF_OBSOLETE_VOIDP_CAST elf_round_up(elf, (long)maxva + sz);
651          }
652 -        shdr = (elf_shdr *)((long)shdr +
653 +        shdr = ELF_MAKE_HANDLE(elf_shdr, ELF_HANDLE_PTRVAL(shdr) +
654                              (long)elf_uval(elf, elf->ehdr, e_shentsize));
655      }
656  
657      /* Write down the actual sym size. */
658 -    *(uint32_t *)symbase = maxva - symtab_addr;
659 +    elf_store_val(elf, uint32_t, symbase, maxva - symtab_addr);
660  
661  #undef elf_ehdr_elm
662  }
663  
664  void elf_parse_binary(struct elf_binary *elf)
665  {
666 -    const elf_phdr *phdr;
667 +    ELF_HANDLE_DECL(elf_phdr) phdr;
668      uint64_t low = -1;
669      uint64_t high = 0;
670      uint64_t i, count, paddr, memsz;
671 @@ -267,9 +273,9 @@ void elf_parse_binary(struct elf_binary *elf)
672  
673  int elf_load_binary(struct elf_binary *elf)
674  {
675 -    const elf_phdr *phdr;
676 +    ELF_HANDLE_DECL(elf_phdr) phdr;
677      uint64_t i, count, paddr, offset, filesz, memsz;
678 -    char *dest;
679 +    ELF_PTRVAL_VOID dest;
680  
681      count = elf_uval(elf, elf->ehdr, e_phnum);
682      for ( i = 0; i < count; i++ )
683 @@ -282,9 +288,9 @@ int elf_load_binary(struct elf_binary *elf)
684          filesz = elf_uval(elf, phdr, p_filesz);
685          memsz = elf_uval(elf, phdr, p_memsz);
686          dest = elf_get_ptr(elf, paddr);
687 -        elf_msg(elf, "%s: phdr %" PRIu64 " at 0x%p -> 0x%p\n",
688 -                __func__, i, dest, dest + filesz);
689 -        if ( elf_load_image(elf, dest, elf->image + offset, filesz, memsz) != 0 )
690 +        elf_msg(elf, "%s: phdr %" PRIu64 " at 0x%"ELF_PRPTRVAL" -> 0x%"ELF_PRPTRVAL"\n",
691 +                __func__, i, dest, (ELF_PTRVAL_VOID)(dest + filesz));
692 +        if ( elf_load_image(elf, dest, ELF_IMAGE_BASE(elf) + offset, filesz, memsz) != 0 )
693              return -1;
694      }
695  
696 @@ -292,18 +298,18 @@ int elf_load_binary(struct elf_binary *elf)
697      return 0;
698  }
699  
700 -void *elf_get_ptr(struct elf_binary *elf, unsigned long addr)
701 +ELF_PTRVAL_VOID elf_get_ptr(struct elf_binary *elf, unsigned long addr)
702  {
703      return elf->dest + addr - elf->pstart;
704  }
705  
706  uint64_t elf_lookup_addr(struct elf_binary * elf, const char *symbol)
707  {
708 -    const elf_sym *sym;
709 +    ELF_HANDLE_DECL(elf_sym) sym;
710      uint64_t value;
711  
712      sym = elf_sym_by_name(elf, symbol);
713 -    if ( sym == NULL )
714 +    if ( !ELF_HANDLE_VALID(sym) )
715      {
716          elf_err(elf, "%s: not found: %s\n", __FUNCTION__, symbol);
717          return -1;
718 diff --git a/xen/common/libelf/libelf-tools.c b/xen/common/libelf/libelf-tools.c
719 index 2f54142..f1fd886 100644
720 --- a/xen/common/libelf/libelf-tools.c
721 +++ b/xen/common/libelf/libelf-tools.c
722 @@ -67,10 +67,10 @@ int elf_phdr_count(struct elf_binary *elf)
723      return elf_uval(elf, elf->ehdr, e_phnum);
724  }
725  
726 -const elf_shdr *elf_shdr_by_name(struct elf_binary *elf, const char *name)
727 +ELF_HANDLE_DECL(elf_shdr) elf_shdr_by_name(struct elf_binary *elf, const char *name)
728  {
729      uint64_t count = elf_shdr_count(elf);
730 -    const elf_shdr *shdr;
731 +    ELF_HANDLE_DECL(elf_shdr) shdr;
732      const char *sname;
733      int i;
734  
735 @@ -81,76 +81,80 @@ const elf_shdr *elf_shdr_by_name(struct elf_binary *elf, const char *name)
736          if ( sname && !strcmp(sname, name) )
737              return shdr;
738      }
739 -    return NULL;
740 +    return ELF_INVALID_HANDLE(elf_shdr);
741  }
742  
743 -const elf_shdr *elf_shdr_by_index(struct elf_binary *elf, int index)
744 +ELF_HANDLE_DECL(elf_shdr) elf_shdr_by_index(struct elf_binary *elf, int index)
745  {
746      uint64_t count = elf_shdr_count(elf);
747 -    const void *ptr;
748 +    ELF_PTRVAL_CONST_VOID ptr;
749  
750      if ( index >= count )
751 -        return NULL;
752 +        return ELF_INVALID_HANDLE(elf_shdr);
753  
754 -    ptr = (elf->image
755 +    ptr = (ELF_IMAGE_BASE(elf)
756             + elf_uval(elf, elf->ehdr, e_shoff)
757             + elf_uval(elf, elf->ehdr, e_shentsize) * index);
758 -    return ptr;
759 +    return ELF_MAKE_HANDLE(elf_shdr, ptr);
760  }
761  
762 -const elf_phdr *elf_phdr_by_index(struct elf_binary *elf, int index)
763 +ELF_HANDLE_DECL(elf_phdr) elf_phdr_by_index(struct elf_binary *elf, int index)
764  {
765      uint64_t count = elf_uval(elf, elf->ehdr, e_phnum);
766 -    const void *ptr;
767 +    ELF_PTRVAL_CONST_VOID ptr;
768  
769      if ( index >= count )
770 -        return NULL;
771 +        return ELF_INVALID_HANDLE(elf_phdr);
772  
773 -    ptr = (elf->image
774 +    ptr = (ELF_IMAGE_BASE(elf)
775             + elf_uval(elf, elf->ehdr, e_phoff)
776             + elf_uval(elf, elf->ehdr, e_phentsize) * index);
777 -    return ptr;
778 +    return ELF_MAKE_HANDLE(elf_phdr, ptr);
779  }
780  
781 -const char *elf_section_name(struct elf_binary *elf, const elf_shdr * shdr)
782 +
783 +const char *elf_section_name(struct elf_binary *elf,
784 +                             ELF_HANDLE_DECL(elf_shdr) shdr)
785  {
786 -    if ( elf->sec_strtab == NULL )
787 +    if ( ELF_PTRVAL_INVALID(elf->sec_strtab) )
788          return "unknown";
789 +
790      return elf->sec_strtab + elf_uval(elf, shdr, sh_name);
791  }
792  
793 -const void *elf_section_start(struct elf_binary *elf, const elf_shdr * shdr)
794 +ELF_PTRVAL_CONST_VOID elf_section_start(struct elf_binary *elf, ELF_HANDLE_DECL(elf_shdr) shdr)
795  {
796 -    return elf->image + elf_uval(elf, shdr, sh_offset);
797 +    return ELF_IMAGE_BASE(elf) + elf_uval(elf, shdr, sh_offset);
798  }
799  
800 -const void *elf_section_end(struct elf_binary *elf, const elf_shdr * shdr)
801 +ELF_PTRVAL_CONST_VOID elf_section_end(struct elf_binary *elf, ELF_HANDLE_DECL(elf_shdr) shdr)
802  {
803 -    return elf->image
804 +    return ELF_IMAGE_BASE(elf)
805          + elf_uval(elf, shdr, sh_offset) + elf_uval(elf, shdr, sh_size);
806  }
807  
808 -const void *elf_segment_start(struct elf_binary *elf, const elf_phdr * phdr)
809 +ELF_PTRVAL_CONST_VOID elf_segment_start(struct elf_binary *elf, ELF_HANDLE_DECL(elf_phdr) phdr)
810  {
811 -    return elf->image + elf_uval(elf, phdr, p_offset);
812 +    return ELF_IMAGE_BASE(elf)
813 +        + elf_uval(elf, phdr, p_offset);
814  }
815  
816 -const void *elf_segment_end(struct elf_binary *elf, const elf_phdr * phdr)
817 +ELF_PTRVAL_CONST_VOID elf_segment_end(struct elf_binary *elf, ELF_HANDLE_DECL(elf_phdr) phdr)
818  {
819 -    return elf->image
820 +    return ELF_IMAGE_BASE(elf)
821          + elf_uval(elf, phdr, p_offset) + elf_uval(elf, phdr, p_filesz);
822  }
823  
824 -const elf_sym *elf_sym_by_name(struct elf_binary *elf, const char *symbol)
825 +ELF_HANDLE_DECL(elf_sym) elf_sym_by_name(struct elf_binary *elf, const char *symbol)
826  {
827 -    const void *ptr = elf_section_start(elf, elf->sym_tab);
828 -    const void *end = elf_section_end(elf, elf->sym_tab);
829 -    const elf_sym *sym;
830 +    ELF_PTRVAL_CONST_VOID ptr = elf_section_start(elf, elf->sym_tab);
831 +    ELF_PTRVAL_CONST_VOID end = elf_section_end(elf, elf->sym_tab);
832 +    ELF_HANDLE_DECL(elf_sym) sym;
833      uint64_t info, name;
834  
835      for ( ; ptr < end; ptr += elf_size(elf, sym) )
836      {
837 -        sym = ptr;
838 +        sym = ELF_MAKE_HANDLE(elf_sym, ptr);
839          info = elf_uval(elf, sym, st_info);
840          name = elf_uval(elf, sym, st_name);
841          if ( ELF32_ST_BIND(info) != STB_GLOBAL )
842 @@ -159,33 +163,33 @@ const elf_sym *elf_sym_by_name(struct elf_binary *elf, const char *symbol)
843              continue;
844          return sym;
845      }
846 -    return NULL;
847 +    return ELF_INVALID_HANDLE(elf_sym);
848  }
849  
850 -const elf_sym *elf_sym_by_index(struct elf_binary *elf, int index)
851 +ELF_HANDLE_DECL(elf_sym) elf_sym_by_index(struct elf_binary *elf, int index)
852  {
853 -    const void *ptr = elf_section_start(elf, elf->sym_tab);
854 -    const elf_sym *sym;
855 +    ELF_PTRVAL_CONST_VOID ptr = elf_section_start(elf, elf->sym_tab);
856 +    ELF_HANDLE_DECL(elf_sym) sym;
857  
858 -    sym = ptr + index * elf_size(elf, sym);
859 +    sym = ELF_MAKE_HANDLE(elf_sym, ptr + index * elf_size(elf, sym));
860      return sym;
861  }
862  
863 -const char *elf_note_name(struct elf_binary *elf, const elf_note * note)
864 +const char *elf_note_name(struct elf_binary *elf, ELF_HANDLE_DECL(elf_note) note)
865  {
866 -    return (void *)note + elf_size(elf, note);
867 +    return ELF_HANDLE_PTRVAL(note) + elf_size(elf, note);
868  }
869  
870 -const void *elf_note_desc(struct elf_binary *elf, const elf_note * note)
871 +ELF_PTRVAL_CONST_VOID elf_note_desc(struct elf_binary *elf, ELF_HANDLE_DECL(elf_note) note)
872  {
873      int namesz = (elf_uval(elf, note, namesz) + 3) & ~3;
874  
875 -    return (void *)note + elf_size(elf, note) + namesz;
876 +    return ELF_HANDLE_PTRVAL(note) + elf_size(elf, note) + namesz;
877  }
878  
879 -uint64_t elf_note_numeric(struct elf_binary *elf, const elf_note * note)
880 +uint64_t elf_note_numeric(struct elf_binary *elf, ELF_HANDLE_DECL(elf_note) note)
881  {
882 -    const void *desc = elf_note_desc(elf, note);
883 +    ELF_PTRVAL_CONST_VOID desc = elf_note_desc(elf, note);
884      int descsz = elf_uval(elf, note, descsz);
885  
886      switch (descsz)
887 @@ -200,10 +204,10 @@ uint64_t elf_note_numeric(struct elf_binary *elf, const elf_note * note)
888      }
889  }
890  
891 -uint64_t elf_note_numeric_array(struct elf_binary *elf, const elf_note *note,
892 +uint64_t elf_note_numeric_array(struct elf_binary *elf, ELF_HANDLE_DECL(elf_note) note,
893                                  unsigned int unitsz, unsigned int idx)
894  {
895 -    const void *desc = elf_note_desc(elf, note);
896 +    ELF_PTRVAL_CONST_VOID desc = elf_note_desc(elf, note);
897      int descsz = elf_uval(elf, note, descsz);
898  
899      if ( descsz % unitsz || idx >= descsz / unitsz )
900 @@ -220,12 +224,12 @@ uint64_t elf_note_numeric_array(struct elf_binary *elf, const elf_note *note,
901      }
902  }
903  
904 -const elf_note *elf_note_next(struct elf_binary *elf, const elf_note * note)
905 +ELF_HANDLE_DECL(elf_note) elf_note_next(struct elf_binary *elf, ELF_HANDLE_DECL(elf_note) note)
906  {
907      int namesz = (elf_uval(elf, note, namesz) + 3) & ~3;
908      int descsz = (elf_uval(elf, note, descsz) + 3) & ~3;
909  
910 -    return (void *)note + elf_size(elf, note) + namesz + descsz;
911 +    return ELF_MAKE_HANDLE(elf_note, ELF_HANDLE_PTRVAL(note) + elf_size(elf, note) + namesz + descsz);
912  }
913  
914  /* ------------------------------------------------------------------------ */
915 @@ -234,10 +238,10 @@ int elf_is_elfbinary(const void *image)
916  {
917      const Elf32_Ehdr *ehdr = image;
918  
919 -    return IS_ELF(*ehdr);
920 +    return IS_ELF(*ehdr); /* fixme unchecked */
921  }
922  
923 -int elf_phdr_is_loadable(struct elf_binary *elf, const elf_phdr * phdr)
924 +int elf_phdr_is_loadable(struct elf_binary *elf, ELF_HANDLE_DECL(elf_phdr) phdr)
925  {
926      uint64_t p_type = elf_uval(elf, phdr, p_type);
927      uint64_t p_flags = elf_uval(elf, phdr, p_flags);
928 diff --git a/xen/include/xen/libelf.h b/xen/include/xen/libelf.h
929 index 38e490c..cefd3d3 100644
930 --- a/xen/include/xen/libelf.h
931 +++ b/xen/include/xen/libelf.h
932 @@ -48,6 +48,97 @@ typedef void elf_log_callback(struct elf_binary*, void *caller_data,
933  
934  /* ------------------------------------------------------------------------ */
935  
936 +/* Macros for accessing the input image and output area. */
937 +
938 +/*
939 + * We abstract away the pointerness of these pointers, replacing
940 + * various void*, char* and struct* with the following:
941 + *   PTRVAL      A pointer to a byte; one can do pointer arithmetic
942 + *               on this.
943 + *               This replaces variables which were char*,void*
944 + *               and their const versions, so we provide four
945 + *               different declaration macros:
946 + *                   ELF_PTRVAL_{,CONST}{VOID,CHAR}
947 + *   HANDLE      A pointer to a struct.  There is one of these types
948 + *               for each pointer type - that is, for each "structname".
949 + *               In the arguments to the various HANDLE macros, structname
950 + *               must be a single identifier which is a typedef.
951 + *               It is not permitted to do arithmetic on these
952 + *               pointers.  In the current code attempts to do so will
953 + *               compile, but in the next patch this will become a
954 + *               compile error.
955 + *               We provide two declaration macros for const and
956 + *               non-const pointers.
957 + */
958 +
959 +#define ELF_REALPTR2PTRVAL(realpointer) (realpointer)
960 +  /* Converts an actual C pointer into a PTRVAL */
961 +
962 +#define ELF_HANDLE_DECL_NONCONST(structname)  structname *
963 +#define ELF_HANDLE_DECL(structname)           const structname *
964 +  /* Provides a type declaration for a HANDLE. */
965 +  /* May only be used to declare ONE variable at a time */
966 +
967 +#define ELF_PTRVAL_VOID         void *
968 +#define ELF_PTRVAL_CHAR         char *
969 +#define ELF_PTRVAL_CONST_VOID   const void *
970 +#define ELF_PTRVAL_CONST_CHAR   const char *
971 +  /* Provides a type declaration for a PTRVAL. */
972 +  /* May only be used to declare ONE variable at a time */
973 +
974 +#define ELF_DEFINE_HANDLE(structname) /* empty */
975 +  /*
976 +   * This must be invoked for each HANDLE type to define
977 +   * the actual C type used for that kind of HANDLE.
978 +   */
979 +
980 +#define ELF_PRPTRVAL "p"
981 +  /* printf format a la PRId... for a PTRVAL */
982 +
983 +#define ELF_MAKE_HANDLE(structname, ptrval) (ptrval)
984 +  /* Converts a PTRVAL to a HANDLE */
985 +
986 +#define ELF_IMAGE_BASE(elf) ((elf)->image)
987 +  /* Returns the base of the image as a PTRVAL. */
988 +
989 +#define ELF_HANDLE_PTRVAL(handleval) ((void*)(handleval))
990 +  /* Converts a HANDLE to a PTRVAL. */
991 +
992 +#define ELF_OBSOLETE_VOIDP_CAST (void*)(uintptr_t)
993 +  /*
994 +   * In some places the existing code needs to
995 +   *  - cast away const (the existing code uses const a fair
996 +   *    bit but actually sometimes wants to write to its input)
997 +   *    from a PTRVAL.
998 +   *  - convert an integer representing a pointer to a PTRVAL
999 +   * This macro provides a suitable cast.
1000 +   */
1001 +
1002 +#define ELF_UNSAFE_PTR(ptrval) ((void*)(uintptr_t)(ptrval))
1003 +  /*
1004 +   * Turns a PTRVAL into an actual C pointer.  Before this is done
1005 +   * the caller must have ensured that the PTRVAL does in fact point
1006 +   * to a permissible location.
1007 +   */
1008 +
1009 +/* PTRVALs can be INVALID (ie, NULL). */
1010 +#define ELF_INVALID_PTRVAL            (NULL)        /* returns NULL PTRVAL */
1011 +#define ELF_INVALID_HANDLE(structname)             /* returns NULL handle */ \
1012 +    ELF_MAKE_HANDLE(structname, ELF_INVALID_PTRVAL)
1013 +#define ELF_PTRVAL_VALID(ptrval)      (ptrval)            /* }            */
1014 +#define ELF_HANDLE_VALID(handleval)   (handleval)         /* } predicates */
1015 +#define ELF_PTRVAL_INVALID(ptrval)    ((ptrval) == NULL)  /* }            */
1016 +
1017 +/* For internal use by other macros here */
1018 +#define ELF__HANDLE_FIELD_TYPE(handleval, elm) \
1019 +  typeof((handleval)->elm)
1020 +#define ELF__HANDLE_FIELD_OFFSET(handleval, elm) \
1021 +  offsetof(typeof(*(handleval)),elm)
1022 +
1023 +
1024 +/* ------------------------------------------------------------------------ */
1025 +
1026 +
1027  typedef union {
1028      Elf32_Ehdr e32;
1029      Elf64_Ehdr e64;
1030 @@ -83,6 +174,12 @@ typedef union {
1031      Elf64_Note e64;
1032  } elf_note;
1033  
1034 +ELF_DEFINE_HANDLE(elf_ehdr)
1035 +ELF_DEFINE_HANDLE(elf_shdr)
1036 +ELF_DEFINE_HANDLE(elf_phdr)
1037 +ELF_DEFINE_HANDLE(elf_sym)
1038 +ELF_DEFINE_HANDLE(elf_note)
1039 +
1040  struct elf_binary {
1041      /* elf binary */
1042      const char *image;
1043 @@ -90,10 +187,10 @@ struct elf_binary {
1044      char class;
1045      char data;
1046  
1047 -    const elf_ehdr *ehdr;
1048 -    const char *sec_strtab;
1049 -    const elf_shdr *sym_tab;
1050 -    const char *sym_strtab;
1051 +    ELF_HANDLE_DECL(elf_ehdr) ehdr;
1052 +    ELF_PTRVAL_CONST_CHAR sec_strtab;
1053 +    ELF_HANDLE_DECL(elf_shdr) sym_tab;
1054 +    ELF_PTRVAL_CONST_CHAR sym_strtab;
1055  
1056      /* loaded to */
1057      char *dest;
1058 @@ -135,45 +232,72 @@ struct elf_binary {
1059       : elf_access_unsigned((elf), (str),                                \
1060                             offsetof(typeof(*(str)),e32.elem),           \
1061                             sizeof((str)->e32.elem)))
1062 +  /*
1063 +   * Reads an unsigned field in a header structure in the ELF.
1064 +   * str is a HANDLE, and elem is the field name in it.
1065 +   */
1066  
1067  #define elf_size(elf, str)                              \
1068      ((ELFCLASS64 == (elf)->class)                       \
1069       ? sizeof((str)->e64) : sizeof((str)->e32))
1070 +  /*
1071 +   * Returns the size of the substructure for the appropriate 32/64-bitness.
1072 +   * str should be a HANDLE.
1073 +   */
1074  
1075 -uint64_t elf_access_unsigned(struct elf_binary *elf, const void *ptr,
1076 +uint64_t elf_access_unsigned(struct elf_binary *elf, ELF_PTRVAL_CONST_VOID ptr,
1077                               uint64_t offset, size_t size);
1078 +  /* Reads a field at arbitrary offset and alignemnt */
1079  
1080  uint64_t elf_round_up(struct elf_binary *elf, uint64_t addr);
1081  
1082 +
1083 +#define elf_memcpy_safe(elf, dst, src, sz) memcpy((dst),(src),(sz))
1084 +#define elf_memset_safe(elf, dst, c, sz)   memset((dst),(c),(sz))
1085 +  /*
1086 +   * Versions of memcpy and memset which will (in the next patch)
1087 +   * arrange never to write outside permitted areas.
1088 +   */
1089 +
1090 +#define elf_store_val(elf, type, ptr, val)   (*(type*)(ptr) = (val))
1091 +  /* Stores a value at a particular PTRVAL. */
1092 +
1093 +#define elf_store_field(elf, hdr, elm, val)                     \
1094 +    (elf_store_val((elf), ELF__HANDLE_FIELD_TYPE(hdr, elm),     \
1095 +                   &((hdr)->elm),                               \
1096 +                   (val)))
1097 +  /* Stores a 32/64-bit field.  hdr is a HANDLE and elm is the field name. */
1098 +
1099 +
1100  /* ------------------------------------------------------------------------ */
1101  /* xc_libelf_tools.c                                                        */
1102  
1103  int elf_shdr_count(struct elf_binary *elf);
1104  int elf_phdr_count(struct elf_binary *elf);
1105  
1106 -const elf_shdr *elf_shdr_by_name(struct elf_binary *elf, const char *name);
1107 -const elf_shdr *elf_shdr_by_index(struct elf_binary *elf, int index);
1108 -const elf_phdr *elf_phdr_by_index(struct elf_binary *elf, int index);
1109 +ELF_HANDLE_DECL(elf_shdr) elf_shdr_by_name(struct elf_binary *elf, const char *name);
1110 +ELF_HANDLE_DECL(elf_shdr) elf_shdr_by_index(struct elf_binary *elf, int index);
1111 +ELF_HANDLE_DECL(elf_phdr) elf_phdr_by_index(struct elf_binary *elf, int index);
1112  
1113 -const char *elf_section_name(struct elf_binary *elf, const elf_shdr * shdr);
1114 -const void *elf_section_start(struct elf_binary *elf, const elf_shdr * shdr);
1115 -const void *elf_section_end(struct elf_binary *elf, const elf_shdr * shdr);
1116 +const char *elf_section_name(struct elf_binary *elf, ELF_HANDLE_DECL(elf_shdr) shdr);
1117 +ELF_PTRVAL_CONST_VOID elf_section_start(struct elf_binary *elf, ELF_HANDLE_DECL(elf_shdr) shdr);
1118 +ELF_PTRVAL_CONST_VOID elf_section_end(struct elf_binary *elf, ELF_HANDLE_DECL(elf_shdr) shdr);
1119  
1120 -const void *elf_segment_start(struct elf_binary *elf, const elf_phdr * phdr);
1121 -const void *elf_segment_end(struct elf_binary *elf, const elf_phdr * phdr);
1122 +ELF_PTRVAL_CONST_VOID elf_segment_start(struct elf_binary *elf, ELF_HANDLE_DECL(elf_phdr) phdr);
1123 +ELF_PTRVAL_CONST_VOID elf_segment_end(struct elf_binary *elf, ELF_HANDLE_DECL(elf_phdr) phdr);
1124  
1125 -const elf_sym *elf_sym_by_name(struct elf_binary *elf, const char *symbol);
1126 -const elf_sym *elf_sym_by_index(struct elf_binary *elf, int index);
1127 +ELF_HANDLE_DECL(elf_sym) elf_sym_by_name(struct elf_binary *elf, const char *symbol);
1128 +ELF_HANDLE_DECL(elf_sym) elf_sym_by_index(struct elf_binary *elf, int index);
1129  
1130 -const char *elf_note_name(struct elf_binary *elf, const elf_note * note);
1131 -const void *elf_note_desc(struct elf_binary *elf, const elf_note * note);
1132 -uint64_t elf_note_numeric(struct elf_binary *elf, const elf_note * note);
1133 -uint64_t elf_note_numeric_array(struct elf_binary *, const elf_note *,
1134 +const char *elf_note_name(struct elf_binary *elf, ELF_HANDLE_DECL(elf_note) note);
1135 +ELF_PTRVAL_CONST_VOID elf_note_desc(struct elf_binary *elf, ELF_HANDLE_DECL(elf_note) note);
1136 +uint64_t elf_note_numeric(struct elf_binary *elf, ELF_HANDLE_DECL(elf_note) note);
1137 +uint64_t elf_note_numeric_array(struct elf_binary *, ELF_HANDLE_DECL(elf_note),
1138                                  unsigned int unitsz, unsigned int idx);
1139 -const elf_note *elf_note_next(struct elf_binary *elf, const elf_note * note);
1140 +ELF_HANDLE_DECL(elf_note) elf_note_next(struct elf_binary *elf, ELF_HANDLE_DECL(elf_note) note);
1141  
1142  int elf_is_elfbinary(const void *image);
1143 -int elf_phdr_is_loadable(struct elf_binary *elf, const elf_phdr * phdr);
1144 +int elf_phdr_is_loadable(struct elf_binary *elf, ELF_HANDLE_DECL(elf_phdr) phdr);
1145  
1146  /* ------------------------------------------------------------------------ */
1147  /* xc_libelf_loader.c                                                       */
1148 @@ -189,7 +313,7 @@ void elf_set_log(struct elf_binary *elf, elf_log_callback*,
1149  void elf_parse_binary(struct elf_binary *elf);
1150  int elf_load_binary(struct elf_binary *elf);
1151  
1152 -void *elf_get_ptr(struct elf_binary *elf, unsigned long addr);
1153 +ELF_PTRVAL_VOID elf_get_ptr(struct elf_binary *elf, unsigned long addr);
1154  uint64_t elf_lookup_addr(struct elf_binary *elf, const char *symbol);
1155  
1156  void elf_parse_bsdsyms(struct elf_binary *elf, uint64_t pstart); /* private */
1157 @@ -221,9 +345,9 @@ struct xen_elfnote {
1158  
1159  struct elf_dom_parms {
1160      /* raw */
1161 -    const char *guest_info;
1162 -    const void *elf_note_start;
1163 -    const void *elf_note_end;
1164 +    ELF_PTRVAL_CONST_CHAR guest_info;
1165 +    ELF_PTRVAL_CONST_VOID elf_note_start;
1166 +    ELF_PTRVAL_CONST_VOID elf_note_end;
1167      struct xen_elfnote elf_notes[XEN_ELFNOTE_MAX + 1];
1168  
1169      /* parsed */
1170 @@ -262,10 +386,22 @@ int elf_xen_parse_features(const char *features,
1171                             uint32_t *required);
1172  int elf_xen_parse_note(struct elf_binary *elf,
1173                         struct elf_dom_parms *parms,
1174 -                       const elf_note *note);
1175 +                       ELF_HANDLE_DECL(elf_note) note);
1176  int elf_xen_parse_guest_info(struct elf_binary *elf,
1177                               struct elf_dom_parms *parms);
1178  int elf_xen_parse(struct elf_binary *elf,
1179                    struct elf_dom_parms *parms);
1180  
1181 +#define elf_memcpy_unchecked memcpy
1182 +#define elf_memset_unchecked memset
1183 +  /*
1184 +   * Unsafe versions of memcpy and memset which take actual C
1185 +   * pointers.  These are just like real memcpy and memset.
1186 +   */
1187 +
1188 +
1189 +#define ELF_ADVANCE_DEST(elf, amount)  elf->dest += (amount)
1190 +  /* Advances past amount bytes of the current destination area. */
1191 +
1192 +
1193  #endif /* __XEN_LIBELF_H__ */
1194 -- 
1195 1.7.2.5
1196
This page took 0.111842 seconds and 3 git commands to generate.