[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] Re: [Xen-devel] Relocatable Xen early boot code
On 12/06/15 12:14, Daniel Kiper wrote: > Hey, > > During work on multiboot2 protocol support for Xen on EFI platform > I discovered that we need relocatable Xen early boot code (which is > mostly 32-bit code). More you can find here: > > http://lists.xen.org/archives/html/xen-devel/2015-02/msg01257.html > > I would like to focus on solution #1 described above. I have working PoC > which implements it. We also discussed various solutions for this issue > during Xen Hackhaton in Shanghai. As Andrew and Jan asked I tried to > implement solution based on segment registers. However, after revisiting > this issue and further investigation I still have some doubts. You can > read about my findings below. > > Here I do not want to discuss GRUB2 and multiboot2 protocol support details > for relocatable images. It is not needed. It is sufficient to know that it > is able to put loaded image anywhere in available memory below 4 GiB. Loaded > image is informed about its base address according to multiboot2 protocol via > special tag. This is new feature not available in upstream GRUB2. I work on > upstreaming it in parallel. Relevant patches will be posted together with > Xen patches. > > 1) My PoC uses %ebp (last unused register available globally in Xen early > boot code; there is assumption that %ds == %es == %ss) as a storage for > Xen image base address. If boot protocol do not support relocatable images > it is filled with static value calculated during build. Otherwise it is > taken from special multiboot2 tag. > > We need Xen image base address to access memory in Xen image area in at > least three different cases: > a) direct memory access, e.g.: mov %eax,sym_offset(boot_tsc_stamp)(%ebp) > b) memory address calculation, e.g.: lea > sym_offset(__page_tables_start)(%ebp),%edx, > c) update static addresses calculated during build, e.g. prebuild page > tables. > > If we have Xen image base address in a register then all mentioned > operations > are quite simple. > > This idea is based on x86_64 addressing mode which uses %rip as a > reference. > > 2) Andrew and Jan suggested that we can use segment descriptor to store Xen > image base address. This way all references to variables in Xen image can > be easily calculated during build and they will be static. However, > relevant > segment descriptor must be updated during Xen start. > > At first sight, it looks that %cs, %ds, %es, %ss should be initialized as > is > (start: 0, size: 4 GiB, ...). This way we will not break references to > trampoline > and all other variables living outside of Xen image. Additionally, we are > sure > that all references to variables from C code (xen/arch/x86/boot/reloc.c) > are > pointing always to the same place regardless of x86 instruction generated > by > compiler and segment register used by this instruction for addressing. So, > it > looks that potentially we can use %fs or %gs as segment register to access > variables living in Xen image. Looks good... Case a and b from solution #1 > seams > easy to resolve by prefixing by chosen segment register. Case c requires > an extra > register to store temporarily Xen image base address. Looks quite easy... > However, > looking at xen/arch/x86/boot/cmdline.S (at first sight this is the worst > thing) > I am not so happy with segment register solution. Unfortunately all > functions > get as argument just displacement in segment. This means that we must > rework > all stuff there and pass segment(s) as additional argument(s) because most > of > code checks memory in and out of Xen image in parallel. Of course we can > use > solution similar to case c described above but I think that then whole > stuff > move closer to idea #1. This way we will have something which uses things > from #1 and #2. I do not think that this is solution which we want. > > 3) There is a third solution which is a mixture of #1 and #2. We can use e.g. > %fs:0 (e.g. located somewhere in Xen image) to store Xen image base > address. > If this value is needed then we can access it directly, e.g. add > %fs:0,%esi, > or copy to temporary register and use as required. > > So, I am still in favor of #1. It is clean and easy. It does not require a > lot of work. > #2 has a potential but requires a lot of changes in fragile cmdline.S (maybe > others > difficult places). Is it worth? I think that #3 is a backup solution in case > we choose > #1 and later it will appear that we need a globally unused register. I really don't understand why we have command line parsing written asm. I had half a mind to rewrite it all in C, (similar to the existing reloc code, but have gcc just create the .s and #include it as before, so external references work in a rational way). It would be far clearer like that. As stated at the hackathon, the problem with using %ebp is that it turns all implicit %ds references into implicit %ss references, and tends to add a SIB+imm32 to each instruction with a memory reference (ebp relative memory references, and r13 for that matter, have restrictions in the way in which they can be encoded). ~Andrew _______________________________________________ Xen-devel mailing list Xen-devel@xxxxxxxxxxxxx http://lists.xen.org/xen-devel
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |