On Wed, May 10, 2017 at 08:35:28PM +0200, Patrick Wildt wrote:
> 
> I don't think this is the correct fix.  It might solve your issue, but I
> don't think it's completely right.  So EFI has those so called device
> paths.  A path is basically a list of nodes.  To compare two paths you
> need to compare the whole path and not just a single node of it.  If you
> store dp instead of dp0 you will basically only save a part of the path,
> not the full path.
> 
> What you can do is print the full path of efi_bootdp like..
> 
>     for (dp = efi_bootdp; !IsDevicePathEnd(dp);
>         dp = NextDevicePathNode(dp)) {
>             printf("%x %x - ", DevicePathType(dp), DevicePathSubType(dp));
>     }
>     printf("\n");
> 
> And do the same for the DPs that are being put into the
> efi_device_path_cmp function.  That will at least print the types, but
> not the content of the nodes.  That's a start into figuring out why it
> does not correctly compare the paths.
> 
> Maybe there's a bug in the compare code?

Sorry, only now I understood what you said... Got

2 1 - 1 1 - 1 5 - 4 1 -

(2 1) (2 1) da db cmp da db cmp diff bootdev 1
(2 1) (2 1) da db cmp da db cmp diff bootdev 1
(2 1) (2 1) da db cmp da db cmp diff bootdev 1

with the following diff


Index: efiboot/efiboot.c
===================================================================
RCS file: /cvs/src/sys/arch/amd64/stand/efiboot/efiboot.c,v
retrieving revision 1.17
diff -u -p -r1.17 efiboot.c
--- efiboot/efiboot.c   3 Mar 2017 08:56:18 -0000       1.17
+++ efiboot/efiboot.c   11 May 2017 21:39:14 -0000
@@ -89,6 +89,8 @@ efi_main(EFI_HANDLE image, EFI_SYSTEM_TA
        if (status == EFI_SUCCESS) {
                for (dp = dp0; !IsDevicePathEnd(dp);
                    dp = NextDevicePathNode(dp)) {
+                       printf("%x %x - ", DevicePathType(dp),
+                                       DevicePathSubType(dp));
                        if (DevicePathType(dp) == MEDIA_DEVICE_PATH &&
                            DevicePathSubType(dp) == MEDIA_HARDDRIVE_DP) {
                                bios_bootdev = 0x80;
@@ -96,6 +98,7 @@ efi_main(EFI_HANDLE image, EFI_SYSTEM_TA
                                break;
                        }
                }
+               printf("\n");
        }
 
 #ifdef __amd64__
@@ -199,10 +202,18 @@ efi_diskprobe(void)
                    (void **)&dp);
                if (EFI_ERROR(status))
                        goto next;
+               printf("(%x %x) (%x %x) ",
+                               DevicePathType(efi_bootdp),
+                               DevicePathSubType(efi_bootdp),
+                               DevicePathType(dp),
+                               DevicePathSubType(dp)
+                               );
                if (!efi_device_path_cmp(efi_bootdp, dp, HARDWARE_DEVICE_PATH)&&
                    !efi_device_path_cmp(efi_bootdp, dp, ACPI_DEVICE_PATH) &&
                    !efi_device_path_cmp(efi_bootdp, dp, MESSAGING_DEVICE_PATH))
                        bootdev = 1;
+
+               printf("bootdev %d\n", bootdev);
 next:
                if (bootdev)
                        TAILQ_INSERT_HEAD(&efi_disklist, di, list);
@@ -222,12 +233,14 @@ efi_device_path_cmp(EFI_DEVICE_PATH *dpa
        for (dp = dpa; !IsDevicePathEnd(dp); dp = NextDevicePathNode(dp)) {
                if (DevicePathType(dp) == dptype) {
                        dpt_a = dp;
+                       printf("da ");
                        break;
                }
        }
        for (dp = dpb; !IsDevicePathEnd(dp); dp = NextDevicePathNode(dp)) {
                if (DevicePathType(dp) == dptype) {
                        dpt_b = dp;
+                       printf("db ");
                        break;
                }
        }
@@ -236,8 +249,11 @@ efi_device_path_cmp(EFI_DEVICE_PATH *dpa
                cmp = DevicePathNodeLength(dpt_a) - DevicePathNodeLength(dpt_b);
                if (cmp)
                        return (cmp);
+               printf("cmp ");
                return (memcmp(dpt_a, dpt_b, DevicePathNodeLength(dpt_a)));
        }
+
+       printf("diff ");
 
        return ((uintptr_t)dpt_a - (uintptr_t)dpt_b);
 }

Reply via email to