travis-ci: remove duplicate build
[pandora-u-boot.git] / disk / part_efi.c
index b1e0155..1924338 100644 (file)
@@ -41,10 +41,10 @@ static inline u32 efi_crc32(const void *buf, u32 len)
 
 static int pmbr_part_valid(struct partition *part);
 static int is_pmbr_valid(legacy_mbr * mbr);
-static int is_gpt_valid(block_dev_desc_t *dev_desc, u64 lba,
+static int is_gpt_valid(struct blk_desc *dev_desc, u64 lba,
                                gpt_header *pgpt_head, gpt_entry **pgpt_pte);
-static gpt_entry *alloc_read_gpt_entries(block_dev_desc_t * dev_desc,
-                               gpt_header * pgpt_head);
+static gpt_entry *alloc_read_gpt_entries(struct blk_desc *dev_desc,
+                                        gpt_header *pgpt_head);
 static int is_pte_valid(gpt_entry * pte);
 
 static char *print_efiname(gpt_entry *pte)
@@ -176,7 +176,7 @@ static void prepare_backup_gpt_header(gpt_header *gpt_h)
  * Public Functions (include/part.h)
  */
 
-void print_part_efi(block_dev_desc_t * dev_desc)
+void part_print_efi(struct blk_desc *dev_desc)
 {
        ALLOC_CACHE_ALIGN_BUFFER_PAD(gpt_header, gpt_head, 1, dev_desc->blksz);
        gpt_entry *gpt_pte = NULL;
@@ -184,10 +184,6 @@ void print_part_efi(block_dev_desc_t * dev_desc)
        char uuid[37];
        unsigned char *uuid_bin;
 
-       if (!dev_desc) {
-               printf("%s: Invalid Argument(s)\n", __func__);
-               return;
-       }
        /* This function validates AND fills in the GPT header and PTE */
        if (is_gpt_valid(dev_desc, GPT_PRIMARY_PARTITION_TABLE_LBA,
                         gpt_head, &gpt_pte) != 1) {
@@ -237,14 +233,14 @@ void print_part_efi(block_dev_desc_t * dev_desc)
        return;
 }
 
-int get_partition_info_efi(block_dev_desc_t * dev_desc, int part,
-                               disk_partition_t * info)
+int part_get_info_efi(struct blk_desc *dev_desc, int part,
+                     disk_partition_t *info)
 {
        ALLOC_CACHE_ALIGN_BUFFER_PAD(gpt_header, gpt_head, 1, dev_desc->blksz);
        gpt_entry *gpt_pte = NULL;
 
        /* "part" argument must be at least 1 */
-       if (!dev_desc || !info || part < 1) {
+       if (part < 1) {
                printf("%s: Invalid Argument(s)\n", __func__);
                return -1;
        }
@@ -281,7 +277,7 @@ int get_partition_info_efi(block_dev_desc_t * dev_desc, int part,
 
        sprintf((char *)info->name, "%s",
                        print_efiname(&gpt_pte[part - 1]));
-       sprintf((char *)info->type, "U-Boot");
+       strcpy((char *)info->type, "U-Boot");
        info->bootable = is_bootable(&gpt_pte[part - 1]);
 #ifdef CONFIG_PARTITION_UUIDS
        uuid_bin_to_str(gpt_pte[part - 1].unique_partition_guid.b, info->uuid,
@@ -300,31 +296,12 @@ int get_partition_info_efi(block_dev_desc_t * dev_desc, int part,
        return 0;
 }
 
-int get_partition_info_efi_by_name(block_dev_desc_t *dev_desc,
-       const char *name, disk_partition_t *info)
-{
-       int ret;
-       int i;
-       for (i = 1; i < GPT_ENTRY_NUMBERS; i++) {
-               ret = get_partition_info_efi(dev_desc, i, info);
-               if (ret != 0) {
-                       /* no more entries in table */
-                       return -1;
-               }
-               if (strcmp(name, (const char *)info->name) == 0) {
-                       /* matched */
-                       return 0;
-               }
-       }
-       return -2;
-}
-
-int test_part_efi(block_dev_desc_t * dev_desc)
+static int part_test_efi(struct blk_desc *dev_desc)
 {
        ALLOC_CACHE_ALIGN_BUFFER_PAD(legacy_mbr, legacymbr, 1, dev_desc->blksz);
 
        /* Read legacy MBR from block 0 and validate it */
-       if ((dev_desc->block_read(dev_desc->dev, 0, 1, (ulong *)legacymbr) != 1)
+       if ((blk_dread(dev_desc, 0, 1, (ulong *)legacymbr) != 1)
                || (is_pmbr_valid(legacymbr) != 1)) {
                return -1;
        }
@@ -337,7 +314,7 @@ int test_part_efi(block_dev_desc_t * dev_desc)
  *
  * @return - zero on success, otherwise error
  */
-static int set_protective_mbr(block_dev_desc_t *dev_desc)
+static int set_protective_mbr(struct blk_desc *dev_desc)
 {
        /* Setup the Protective MBR */
        ALLOC_CACHE_ALIGN_BUFFER(legacy_mbr, p_mbr, 1);
@@ -354,16 +331,16 @@ static int set_protective_mbr(block_dev_desc_t *dev_desc)
        p_mbr->partition_record[0].nr_sects = (u32) dev_desc->lba - 1;
 
        /* Write MBR sector to the MMC device */
-       if (dev_desc->block_write(dev_desc->dev, 0, 1, p_mbr) != 1) {
+       if (blk_dwrite(dev_desc, 0, 1, p_mbr) != 1) {
                printf("** Can't write to device %d **\n",
-                       dev_desc->dev);
+                       dev_desc->devnum);
                return -1;
        }
 
        return 0;
 }
 
-int write_gpt_table(block_dev_desc_t *dev_desc,
+int write_gpt_table(struct blk_desc *dev_desc,
                gpt_header *gpt_h, gpt_entry *gpt_e)
 {
        const int pte_blk_cnt = BLOCK_CNT((gpt_h->num_partition_entries
@@ -386,31 +363,28 @@ int write_gpt_table(block_dev_desc_t *dev_desc,
        gpt_h->header_crc32 = cpu_to_le32(calc_crc32);
 
        /* Write the First GPT to the block right after the Legacy MBR */
-       if (dev_desc->block_write(dev_desc->dev, 1, 1, gpt_h) != 1)
+       if (blk_dwrite(dev_desc, 1, 1, gpt_h) != 1)
                goto err;
 
-       if (dev_desc->block_write(dev_desc->dev, 2, pte_blk_cnt, gpt_e)
+       if (blk_dwrite(dev_desc, 2, pte_blk_cnt, gpt_e)
            != pte_blk_cnt)
                goto err;
 
        prepare_backup_gpt_header(gpt_h);
 
-       if (dev_desc->block_write(dev_desc->dev,
-                                 (lbaint_t)le64_to_cpu(gpt_h->last_usable_lba)
-                                 + 1,
-                                 pte_blk_cnt, gpt_e) != pte_blk_cnt)
+       if (blk_dwrite(dev_desc, (lbaint_t)le64_to_cpu(gpt_h->last_usable_lba)
+                      + 1, pte_blk_cnt, gpt_e) != pte_blk_cnt)
                goto err;
 
-       if (dev_desc->block_write(dev_desc->dev,
-                                 (lbaint_t)le64_to_cpu(gpt_h->my_lba), 1,
-                                 gpt_h) != 1)
+       if (blk_dwrite(dev_desc, (lbaint_t)le64_to_cpu(gpt_h->my_lba), 1,
+                      gpt_h) != 1)
                goto err;
 
        debug("GPT successfully written to block device!\n");
        return 0;
 
  err:
-       printf("** Can't write to device %d **\n", dev_desc->dev);
+       printf("** Can't write to device %d **\n", dev_desc->devnum);
        return -1;
 }
 
@@ -446,7 +420,7 @@ int gpt_fill_pte(gpt_header *gpt_h, gpt_entry *gpt_e,
                        gpt_e[i].starting_lba = cpu_to_le64(offset);
                        offset += partitions[i].size;
                }
-               if (offset >= last_usable_lba) {
+               if (offset > (last_usable_lba + 1)) {
                        printf("Partitions layout exceds disk size\n");
                        return -1;
                }
@@ -517,7 +491,7 @@ int gpt_fill_pte(gpt_header *gpt_h, gpt_entry *gpt_e,
        return 0;
 }
 
-int gpt_fill_header(block_dev_desc_t *dev_desc, gpt_header *gpt_h,
+int gpt_fill_header(struct blk_desc *dev_desc, gpt_header *gpt_h,
                char *str_guid, int parts_count)
 {
        gpt_h->signature = cpu_to_le64(GPT_HEADER_SIGNATURE);
@@ -539,7 +513,7 @@ int gpt_fill_header(block_dev_desc_t *dev_desc, gpt_header *gpt_h,
        return 0;
 }
 
-int gpt_restore(block_dev_desc_t *dev_desc, char *str_disk_guid,
+int gpt_restore(struct blk_desc *dev_desc, char *str_disk_guid,
                disk_partition_t *partitions, int parts_count)
 {
        int ret;
@@ -595,7 +569,7 @@ static void gpt_convert_efi_name_to_char(char *s, efi_char16_t *es, int n)
        }
 }
 
-int gpt_verify_headers(block_dev_desc_t *dev_desc, gpt_header *gpt_head,
+int gpt_verify_headers(struct blk_desc *dev_desc, gpt_header *gpt_head,
                       gpt_entry **gpt_pte)
 {
        /*
@@ -619,7 +593,7 @@ int gpt_verify_headers(block_dev_desc_t *dev_desc, gpt_header *gpt_head,
        return 0;
 }
 
-int gpt_verify_partitions(block_dev_desc_t *dev_desc,
+int gpt_verify_partitions(struct blk_desc *dev_desc,
                          disk_partition_t *partitions, int parts,
                          gpt_header *gpt_head, gpt_entry **gpt_pte)
 {
@@ -658,11 +632,17 @@ int gpt_verify_partitions(block_dev_desc_t *dev_desc,
                gpt_part_size = le64_to_cpu(gpt_e[i].ending_lba) -
                        le64_to_cpu(gpt_e[i].starting_lba) + 1;
                debug("size(LBA) - GPT: %8llu, ENV: %8llu ",
-                     gpt_part_size, (u64) partitions[i].size);
+                     (unsigned long long)gpt_part_size,
+                     (unsigned long long)partitions[i].size);
 
                if (le64_to_cpu(gpt_part_size) != partitions[i].size) {
+                       /* We do not check the extend partition size */
+                       if ((i == parts - 1) && (partitions[i].size == 0))
+                               continue;
+
                        error("Partition %s size: %llu does not match %llu!\n",
-                             efi_str, gpt_part_size, (u64) partitions[i].size);
+                             efi_str, (unsigned long long)gpt_part_size,
+                             (unsigned long long)partitions[i].size);
                        return -1;
                }
 
@@ -678,12 +658,12 @@ int gpt_verify_partitions(block_dev_desc_t *dev_desc,
                /* Check if GPT and ENV start LBAs match */
                debug("start LBA - GPT: %8llu, ENV: %8llu\n",
                      le64_to_cpu(gpt_e[i].starting_lba),
-                     (u64) partitions[i].start);
+                     (unsigned long long)partitions[i].start);
 
                if (le64_to_cpu(gpt_e[i].starting_lba) != partitions[i].start) {
                        error("Partition %s start: %llu does not match %llu!\n",
                              efi_str, le64_to_cpu(gpt_e[i].starting_lba),
-                             (u64) partitions[i].start);
+                             (unsigned long long)partitions[i].start);
                        return -1;
                }
        }
@@ -691,7 +671,7 @@ int gpt_verify_partitions(block_dev_desc_t *dev_desc,
        return 0;
 }
 
-int is_valid_gpt_buf(block_dev_desc_t *dev_desc, void *buf)
+int is_valid_gpt_buf(struct blk_desc *dev_desc, void *buf)
 {
        gpt_header *gpt_h;
        gpt_entry *gpt_e;
@@ -712,7 +692,7 @@ int is_valid_gpt_buf(block_dev_desc_t *dev_desc, void *buf)
        return 0;
 }
 
-int write_mbr_and_gpt_partitions(block_dev_desc_t *dev_desc, void *buf)
+int write_mbr_and_gpt_partitions(struct blk_desc *dev_desc, void *buf)
 {
        gpt_header *gpt_h;
        gpt_entry *gpt_e;
@@ -737,7 +717,7 @@ int write_mbr_and_gpt_partitions(block_dev_desc_t *dev_desc, void *buf)
        /* write MBR */
        lba = 0;        /* MBR is always at 0 */
        cnt = 1;        /* MBR (1 block) */
-       if (dev_desc->block_write(dev_desc->dev, lba, cnt, buf) != cnt) {
+       if (blk_dwrite(dev_desc, lba, cnt, buf) != cnt) {
                printf("%s: failed writing '%s' (%d blks at 0x" LBAF ")\n",
                       __func__, "MBR", cnt, lba);
                return 1;
@@ -746,7 +726,7 @@ int write_mbr_and_gpt_partitions(block_dev_desc_t *dev_desc, void *buf)
        /* write Primary GPT */
        lba = GPT_PRIMARY_PARTITION_TABLE_LBA;
        cnt = 1;        /* GPT Header (1 block) */
-       if (dev_desc->block_write(dev_desc->dev, lba, cnt, gpt_h) != cnt) {
+       if (blk_dwrite(dev_desc, lba, cnt, gpt_h) != cnt) {
                printf("%s: failed writing '%s' (%d blks at 0x" LBAF ")\n",
                       __func__, "Primary GPT Header", cnt, lba);
                return 1;
@@ -754,7 +734,7 @@ int write_mbr_and_gpt_partitions(block_dev_desc_t *dev_desc, void *buf)
 
        lba = le64_to_cpu(gpt_h->partition_entry_lba);
        cnt = gpt_e_blk_cnt;
-       if (dev_desc->block_write(dev_desc->dev, lba, cnt, gpt_e) != cnt) {
+       if (blk_dwrite(dev_desc, lba, cnt, gpt_e) != cnt) {
                printf("%s: failed writing '%s' (%d blks at 0x" LBAF ")\n",
                       __func__, "Primary GPT Entries", cnt, lba);
                return 1;
@@ -765,7 +745,7 @@ int write_mbr_and_gpt_partitions(block_dev_desc_t *dev_desc, void *buf)
        /* write Backup GPT */
        lba = le64_to_cpu(gpt_h->partition_entry_lba);
        cnt = gpt_e_blk_cnt;
-       if (dev_desc->block_write(dev_desc->dev, lba, cnt, gpt_e) != cnt) {
+       if (blk_dwrite(dev_desc, lba, cnt, gpt_e) != cnt) {
                printf("%s: failed writing '%s' (%d blks at 0x" LBAF ")\n",
                       __func__, "Backup GPT Entries", cnt, lba);
                return 1;
@@ -773,7 +753,7 @@ int write_mbr_and_gpt_partitions(block_dev_desc_t *dev_desc, void *buf)
 
        lba = le64_to_cpu(gpt_h->my_lba);
        cnt = 1;        /* GPT Header (1 block) */
-       if (dev_desc->block_write(dev_desc->dev, lba, cnt, gpt_h) != cnt) {
+       if (blk_dwrite(dev_desc, lba, cnt, gpt_h) != cnt) {
                printf("%s: failed writing '%s' (%d blks at 0x" LBAF ")\n",
                       __func__, "Backup GPT Header", cnt, lba);
                return 1;
@@ -834,7 +814,7 @@ static int is_pmbr_valid(legacy_mbr * mbr)
  * Description: returns 1 if valid,  0 on error.
  * If valid, returns pointers to PTEs.
  */
-static int is_gpt_valid(block_dev_desc_t *dev_desc, u64 lba,
+static int is_gpt_valid(struct blk_desc *dev_desc, u64 lba,
                        gpt_header *pgpt_head, gpt_entry **pgpt_pte)
 {
        if (!dev_desc || !pgpt_head) {
@@ -843,8 +823,7 @@ static int is_gpt_valid(block_dev_desc_t *dev_desc, u64 lba,
        }
 
        /* Read GPT Header from device */
-       if (dev_desc->block_read(dev_desc->dev, (lbaint_t)lba, 1, pgpt_head)
-                       != 1) {
+       if (blk_dread(dev_desc, (lbaint_t)lba, 1, pgpt_head) != 1) {
                printf("*** ERROR: Can't read GPT header ***\n");
                return 0;
        }
@@ -877,10 +856,11 @@ static int is_gpt_valid(block_dev_desc_t *dev_desc, u64 lba,
  * Allocates space for PTEs based on information found in @gpt.
  * Notes: remember to free pte when you're done!
  */
-static gpt_entry *alloc_read_gpt_entries(block_dev_desc_t * dev_desc,
-                                        gpt_header * pgpt_head)
+static gpt_entry *alloc_read_gpt_entries(struct blk_desc *dev_desc,
+                                        gpt_header *pgpt_head)
 {
        size_t count = 0, blk_cnt;
+       lbaint_t blk;
        gpt_entry *pte = NULL;
 
        if (!dev_desc || !pgpt_head) {
@@ -891,9 +871,10 @@ static gpt_entry *alloc_read_gpt_entries(block_dev_desc_t * dev_desc,
        count = le32_to_cpu(pgpt_head->num_partition_entries) *
                le32_to_cpu(pgpt_head->sizeof_partition_entry);
 
-       debug("%s: count = %u * %u = %zu\n", __func__,
+       debug("%s: count = %u * %u = %lu\n", __func__,
              (u32) le32_to_cpu(pgpt_head->num_partition_entries),
-             (u32) le32_to_cpu(pgpt_head->sizeof_partition_entry), count);
+             (u32) le32_to_cpu(pgpt_head->sizeof_partition_entry),
+             (ulong)count);
 
        /* Allocate memory for PTE, remember to FREE */
        if (count != 0) {
@@ -902,19 +883,15 @@ static gpt_entry *alloc_read_gpt_entries(block_dev_desc_t * dev_desc,
        }
 
        if (count == 0 || pte == NULL) {
-               printf("%s: ERROR: Can't allocate 0x%zX "
-                      "bytes for GPT Entries\n",
-                       __func__, count);
+               printf("%s: ERROR: Can't allocate %#lX bytes for GPT Entries\n",
+                      __func__, (ulong)count);
                return NULL;
        }
 
        /* Read GPT Entries from device */
+       blk = le64_to_cpu(pgpt_head->partition_entry_lba);
        blk_cnt = BLOCK_CNT(count, dev_desc);
-       if (dev_desc->block_read (dev_desc->dev,
-               (lbaint_t)le64_to_cpu(pgpt_head->partition_entry_lba),
-               (lbaint_t) (blk_cnt), pte)
-               != blk_cnt) {
-
+       if (blk_dread(dev_desc, blk, (lbaint_t)blk_cnt, pte) != blk_cnt) {
                printf("*** ERROR: Can't read GPT Entries ***\n");
                free(pte);
                return NULL;
@@ -953,4 +930,18 @@ static int is_pte_valid(gpt_entry * pte)
                return 1;
        }
 }
+
+/*
+ * Add an 'a_' prefix so it comes before 'dos' in the linker list. We need to
+ * check EFI first, since a DOS partition is often used as a 'protective MBR'
+ * with EFI.
+ */
+U_BOOT_PART_TYPE(a_efi) = {
+       .name           = "EFI",
+       .part_type      = PART_TYPE_EFI,
+       .max_entries    = GPT_ENTRY_NUMBERS,
+       .get_info       = part_get_info_ptr(part_get_info_efi),
+       .print          = part_print_ptr(part_print_efi),
+       .test           = part_test_efi,
+};
 #endif