int scan_ubi(libubi_t lib_ubi) { struct ubi_dev_info dev_info; struct ubi_info info; int i, j; if (ubi_get_info(lib_ubi, &info)) return -1; if (!info.dev_count) return 0; ubi_dev = xcalloc(info.dev_count, sizeof(ubi_dev[0])); for (i = info.lowest_dev_num; i <= info.highest_dev_num; ++i) { if (!ubi_dev_present(lib_ubi, i)) continue; if (ubi_get_dev_info1(lib_ubi, i, &dev_info)) { perror("ubi_get_dev_info1"); return -1; } for (j = 0; j < num_mtd_devices; ++j) { if (mtd_dev[j].info.mtd_num == dev_info.mtd_num) break; } if (j == num_mtd_devices) { fprintf(stderr, "Cannot find mtd device %d refered to " "by ubi device %d\n", dev_info.mtd_num, dev_info.dev_num); return -1; } ubi_dev[num_ubi_devices].info = dev_info; mtd_dev[j].ubi = ubi_dev + num_ubi_devices; if (scan_ubi_device(lib_ubi, ubi_dev + num_ubi_devices)) return -1; ++num_ubi_devices; } return 0; }
int ubi_get_dev_info1(libubi_t desc, int dev_num, struct ubi_dev_info *info) { DIR *sysfs_ubi; struct dirent *dirent; struct libubi *lib = (struct libubi *)desc; memset(info, 0, sizeof(struct ubi_dev_info)); info->dev_num = dev_num; if (!ubi_dev_present(desc, dev_num)) return -1; sysfs_ubi = opendir(lib->sysfs_ubi); if (!sysfs_ubi) return -1; info->lowest_vol_id = INT_MAX; while (1) { int vol_id, ret, devno; char tmp_buf[256]; errno = 0; dirent = readdir(sysfs_ubi); if (!dirent) break; if (strlen(dirent->d_name) >= 255) { errmsg("invalid entry in %s: \"%s\"", lib->sysfs_ubi, dirent->d_name); goto out_close; } ret = sscanf(dirent->d_name, UBI_VOL_NAME_PATT"%s", &devno, &vol_id, tmp_buf); if (ret == 2 && devno == dev_num) { info->vol_count += 1; if (vol_id > info->highest_vol_id) info->highest_vol_id = vol_id; if (vol_id < info->lowest_vol_id) info->lowest_vol_id = vol_id; } } if (!dirent && errno) { sys_errmsg("readdir failed on \"%s\"", lib->sysfs_ubi); goto out_close; } if (closedir(sysfs_ubi)) return sys_errmsg("closedir failed on \"%s\"", lib->sysfs_ubi); if (info->lowest_vol_id == INT_MAX) info->lowest_vol_id = 0; if (dev_get_major(lib, dev_num, &info->major, &info->minor)) return -1; if (dev_read_int(lib->dev_mtd_num, dev_num, &info->mtd_num)) return -1; if (dev_read_int(lib->dev_avail_ebs, dev_num, &info->avail_lebs)) return -1; if (dev_read_int(lib->dev_total_ebs, dev_num, &info->total_lebs)) return -1; if (dev_read_int(lib->dev_bad_count, dev_num, &info->bad_count)) return -1; if (dev_read_int(lib->dev_eb_size, dev_num, &info->leb_size)) return -1; if (dev_read_int(lib->dev_bad_rsvd, dev_num, &info->bad_rsvd)) return -1; if (dev_read_ll(lib->dev_max_ec, dev_num, &info->max_ec)) return -1; if (dev_read_int(lib->dev_max_vols, dev_num, &info->max_vol_count)) return -1; if (dev_read_int(lib->dev_min_io_size, dev_num, &info->min_io_size)) return -1; info->avail_bytes = (long long)info->avail_lebs * info->leb_size; info->total_bytes = (long long)info->total_lebs * info->leb_size; return 0; out_close: closedir(sysfs_ubi); return -1; }