Ahmed S. Darwish
2011-Mar-06 12:21 UTC
[syslinux] [PATCH] core: Fix 'trackbuf' descriptor list byte length
(Tested using a Linux bzImage, with and without an initrd.) Per shuffle_and_boot documentation, %ecx must contain the descriptor list byte length, but it's set with such list end address instead. Fix. Signed-off-by: Ahmed S. Darwish <darwish.07 at gmail.com> -- core/bcopy32.inc | 2 ++ core/bcopyxx.inc | 2 ++ core/bootsect.inc | 8 +++++--- core/runkernel.inc | 2 +- 4 files changed, 10 insertions(+), 4 deletions(-) diff --git a/core/bcopy32.inc b/core/bcopy32.inc index 6537546..ab60145 100644 --- a/core/bcopy32.inc +++ b/core/bcopy32.inc @@ -65,6 +65,8 @@ bcopy: jecxz .ret ; If len == 0: this marks the end of the list; dst indicates ; the entry point and src the mode (0 = pm, 1 = rm) ; +; (*) dst, src, and len are four bytes each +; shuffle_and_boot_raw: mov bx,pm_shuffle jmp enter_pm diff --git a/core/bcopyxx.inc b/core/bcopyxx.inc index c669b7a..cfdda0b 100644 --- a/core/bcopyxx.inc +++ b/core/bcopyxx.inc @@ -205,6 +205,8 @@ pm_bcopy: ; If len == 0: this marks the end of the list; dst indicates ; the entry point and src the mode (0 = pm, 1 = rm) ; +; (*) dst, src, and len are four bytes each +; pm_shuffle: cli ; End interrupt service (for good) mov ebx,edi ; EBX <- descriptor list diff --git a/core/bootsect.inc b/core/bootsect.inc index b4402f1..6c20409 100644 --- a/core/bootsect.inc +++ b/core/bootsect.inc @@ -169,7 +169,7 @@ replace_bootstrap_noclearmode: mov [es:di+8],ax ; New DI mov [es:di+4],bx ; New ES %endif - pop ax ; List length + pop ax ; descriptor list entries count push di push es @@ -179,8 +179,8 @@ replace_bootstrap_noclearmode: mov ebx,trackbuf imul di,ax,12 + push di ; length of list add di,bx ; DI <- end of list - push di ; Terminating entry... lea eax,[replace_stub] ; Entrypoint @@ -196,8 +196,10 @@ replace_bootstrap_noclearmode: mov cx,__replacestub_dwords rep movsd + ; ECX <- final list length xor ecx,ecx - pop cx ; ECX <- length of list + pop cx ; original length in bytes + add cx, 12 ; + termination entry size pop word [replace_stub.ss] pop word [replace_stub.esp] diff --git a/core/runkernel.inc b/core/runkernel.inc index 25b073f..2e94346 100644 --- a/core/runkernel.inc +++ b/core/runkernel.inc @@ -453,7 +453,7 @@ setup_move: .no_initrd: push dword run_linux_kernel - push cx ; Length of descriptor list + push cx ; descriptor list entries count ; BX points to the final real mode segment, and will be loaded ; into DS. thanks, -- Darwish http://darwish.07.googlepages.com
H. Peter Anvin
2011-Mar-06 23:21 UTC
[syslinux] [PATCH] core: Fix 'trackbuf' descriptor list byte length
On 03/06/2011 04:21 AM, Ahmed S. Darwish wrote:> (Tested using a Linux bzImage, with and without an initrd.) > > Per shuffle_and_boot documentation, %ecx must contain the descriptor > list byte length, but it's set with such list end address instead. Fix. > > Signed-off-by: Ahmed S. Darwish <darwish.07 at gmail.com>Hmm... unless there are other code paths, it would be easier to simply "inc ax" before the imul here, no?> imul di,ax,12 > + push di ; length of list > add di,bx ; DI <- end of list > - push di > > ; Terminating entry... > lea eax,[replace_stub] ; Entrypoint > @@ -196,8 +196,10 @@ replace_bootstrap_noclearmode: > mov cx,__replacestub_dwords > rep movsd > > + ; ECX <- final list length > xor ecx,ecx > - pop cx ; ECX <- length of list > + pop cx ; original length in bytes > + add cx, 12 ; + termination entry size >-- H. Peter Anvin, Intel Open Source Technology Center I work for Intel. I don't speak on their behalf.