1/* 2 * This program is free software; you can redistribute it and/or 3 * modify it under the terms of the GNU General Public License as 4 * published by the Free Software Foundation; either version 2 of 5 * the License, or (at your option) any later version. 6 * 7 * This program is distributed in the hope that it will be useful, 8 * but WITHOUT ANY WARRANTY; without even the implied warranty of 9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 10 * GNU General Public License for more details. 11 * 12 * You should have received a copy of the GNU General Public License 13 * along with this program; if not, write to the Free Software 14 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, 15 * MA 02111-1307 USA 16 */ 17 18#define VERSION 1 19//#define PC 20 21#include <stdio.h> 22#include <string.h> 23#include <ctype.h> 24#include <stdlib.h> 25#include <unistd.h> 26#include <sys/vfs.h> 27#include <limits.h> 28#include <dirent.h> 29#include <bcmnvram.h> 30 31// From BusyBox and get volume's label. 32#include <autoconf.h> 33#include <volume_id_internal.h> 34#include <shared.h> 35 36#include "disk_initial.h" 37 38#define SYS_BLOCK "/sys/block" 39#define SYS_TTY "/sys/class/tty" 40#define SYS_USB "/sys/class/usb" 41#define SYS_SG "/sys/class/scsi_generic" 42 43#define USB_XHCI_PORT_1 get_usb_xhci_port(0) 44#define USB_XHCI_PORT_2 get_usb_xhci_port(1) 45#define USB_EHCI_PORT_1 get_usb_ehci_port(0) 46#define USB_EHCI_PORT_2 get_usb_ehci_port(1) 47#define USB_OHCI_PORT_1 get_usb_ohci_port(0) 48#define USB_OHCI_PORT_2 get_usb_ohci_port(1) 49#define USB_EHCI_PORT_3 get_usb_ehci_port(2) 50#define USB_OHCI_PORT_3 get_usb_ohci_port(2) 51 52#ifdef BCM_MMC 53#define SDCARD_PORT USB_EHCI_PORT_3 54#endif 55 56enum { 57 DEVICE_TYPE_UNKNOWN=0, 58 DEVICE_TYPE_DISK, 59 DEVICE_TYPE_PRINTER, 60 DEVICE_TYPE_SG, 61 DEVICE_TYPE_CD, 62 DEVICE_TYPE_MODEM, 63 DEVICE_TYPE_BECEEM 64}; 65 66#define usb_dbg printf 67 68int isSerialNode(const char *device_name) 69{ 70 if(strstr(device_name, "ttyUSB") == NULL) 71 return 0; 72 73 return 1; 74} 75 76int isACMNode(const char *device_name) 77{ 78 if(strstr(device_name, "ttyACM") == NULL) 79 return 0; 80 81 return 1; 82} 83 84#ifdef RTCONFIG_USB_BECEEM 85int isBeceemNode(const char *device_name) 86{ 87 if(strstr(device_name, "usbbcm") == NULL) 88 return 0; 89 90 return 1; 91} 92#endif 93 94int isStorageDevice(const char *device_name){ 95 if(!strncmp(device_name, "sd", 2)) 96 return 1; 97 98 return 0; 99} 100 101#ifdef BCM_MMC 102int isMMCDevice(const char *device_name){ 103 if(!strncmp(device_name, "mmcblk", 6)) 104 return 1; 105 106 return 0; 107} 108#endif 109 110int get_device_type_by_device(const char *device_name) 111{ 112 if(device_name == NULL || strlen(device_name) <= 0){ 113 usb_dbg("(%s): The device name is not correct.\n", device_name); 114 return DEVICE_TYPE_UNKNOWN; 115 } 116 117 if(isStorageDevice(device_name) 118#ifdef BCM_MMC 119 || isMMCDevice(device_name) // SD card. 120#endif 121 ){ 122 return DEVICE_TYPE_DISK; 123 } 124#ifdef RTCONFIG_USB_PRINTER 125 if(!strncmp(device_name, "lp", 2)){ 126 return DEVICE_TYPE_PRINTER; 127 } 128#endif 129#ifdef RTCONFIG_USB_MODEM 130 if(!strncmp(device_name, "sg", 2)){ 131 return DEVICE_TYPE_SG; 132 } 133 if(!strncmp(device_name, "sr", 2)){ 134 return DEVICE_TYPE_CD; 135 } 136 if(isSerialNode(device_name) || isACMNode(device_name)){ 137 return DEVICE_TYPE_MODEM; 138 } 139#endif 140#ifdef RTCONFIG_USB_BECEEM 141 if(isBeceemNode(device_name)){ 142 return DEVICE_TYPE_BECEEM; 143 } 144#endif 145 146 return DEVICE_TYPE_UNKNOWN; 147} 148 149#ifdef PC 150char *get_usb_port_by_device(const char *device_name, char *buf, const int buf_size){ 151 int device_type = get_device_type_by_device(device_name); 152 153 if(device_type == DEVICE_TYPE_UNKNOWN) 154 return NULL; 155 156 memset(buf, 0, buf_size); 157 strcpy(buf, "1-1"); 158 159 return buf; 160} 161#else 162char *get_usb_port_by_string(const char *target_string, char *buf, const int buf_size) 163{ 164 memset(buf, 0, buf_size); 165 166 if(strstr(target_string, USB_XHCI_PORT_1)) 167 strcpy(buf, USB_XHCI_PORT_1); 168 else if(strstr(target_string, USB_XHCI_PORT_2)) 169 strcpy(buf, USB_XHCI_PORT_2); 170 else if(strstr(target_string, USB_EHCI_PORT_1)) 171 strcpy(buf, USB_EHCI_PORT_1); 172 else if(strstr(target_string, USB_EHCI_PORT_2)) 173 strcpy(buf, USB_EHCI_PORT_2); 174 else if(strstr(target_string, USB_OHCI_PORT_1)) 175 strcpy(buf, USB_OHCI_PORT_1); 176 else if(strstr(target_string, USB_OHCI_PORT_2)) 177 strcpy(buf, USB_OHCI_PORT_2); 178 else if(strstr(target_string, USB_EHCI_PORT_3)) 179 strcpy(buf, USB_EHCI_PORT_3); 180 else if(strstr(target_string, USB_OHCI_PORT_3)) 181 strcpy(buf, USB_OHCI_PORT_3); 182 else 183 return NULL; 184 185 return buf; 186} 187 188char *get_usb_port_by_device(const char *device_name, char *buf, const int buf_size) 189{ 190 int device_type = get_device_type_by_device(device_name); 191 char device_path[128], usb_path[PATH_MAX]; 192 char disk_name[16]; 193 194 if(device_type == DEVICE_TYPE_UNKNOWN) 195 return NULL; 196 197 memset(device_path, 0, 128); 198 memset(usb_path, 0, PATH_MAX); 199 200 if(device_type == DEVICE_TYPE_DISK){ 201 get_disk_name(device_name, disk_name, 16); 202 sprintf(device_path, "%s/%s/device", SYS_BLOCK, disk_name); 203 if(realpath(device_path, usb_path) == NULL){ 204 usb_dbg("(%s): Fail to get link: %s.\n", device_name, device_path); 205 return NULL; 206 } 207 } 208 else 209#ifdef RTCONFIG_USB_PRINTER 210 if(device_type == DEVICE_TYPE_PRINTER){ 211 sprintf(device_path, "%s/%s/device", SYS_USB, device_name); 212 if(realpath(device_path, usb_path) == NULL){ 213 usb_dbg("(%s): Fail to get link: %s.\n", device_name, device_path); 214 return NULL; 215 } 216 } 217 else 218#endif 219#ifdef RTCONFIG_USB_MODEM 220 if(device_type == DEVICE_TYPE_SG){ 221 sprintf(device_path, "%s/%s/device", SYS_SG, device_name); 222 if(realpath(device_path, usb_path) == NULL){ 223 usb_dbg("(%s): Fail to get link: %s.\n", device_name, device_path); 224 return NULL; 225 } 226 } 227 else 228 if(device_type == DEVICE_TYPE_CD){ 229 sprintf(device_path, "%s/%s/device", SYS_BLOCK, device_name); 230 if(realpath(device_path, usb_path) == NULL){ 231 usb_dbg("(%s): Fail to get link: %s.\n", device_name, device_path); 232 return NULL; 233 } 234 } 235 else 236 if(device_type == DEVICE_TYPE_MODEM){ 237 sprintf(device_path, "%s/%s/device", SYS_TTY, device_name); 238 if(realpath(device_path, usb_path) == NULL){ 239 sleep(1); // Sometimes link would be built slowly, so try again. 240 241 if(realpath(device_path, usb_path) == NULL){ 242 usb_dbg("(%s)(2/2): Fail to get link: %s.\n", device_name, device_path); 243 return NULL; 244 } 245 } 246 } 247 else 248#endif 249#ifdef RTCONFIG_USB_BECEEM 250 if(device_type == DEVICE_TYPE_BECEEM){ 251 sprintf(device_path, "%s/%s/device", SYS_USB, device_name); 252 if(realpath(device_path, usb_path) == NULL){ 253 if(realpath(device_path, usb_path) == NULL){ 254 usb_dbg("(%s)(2/2): Fail to get link: %s.\n", device_name, device_path); 255 return NULL; 256 } 257 } 258 } 259 else 260#endif 261 return NULL; 262 263#ifdef BCM_MMC 264 if(isMMCDevice(device_name)){ // SD card. 265 snprintf(buf, buf_size, "%s", SDCARD_PORT); 266 } 267 else 268#endif 269 if(get_usb_port_by_string(usb_path, buf, buf_size) == NULL){ 270 usb_dbg("(%s): Fail to get usb port: %s.\n", device_name, usb_path); 271 return NULL; 272 } 273 274 return buf; 275} 276#endif 277 278char *get_usb_node_by_string(const char *target_string, char *ret, const int ret_size) 279{ 280 char usb_port[32], buf[16]; 281 char *ptr, *ptr2, *ptr3; 282 int len; 283 284 memset(usb_port, 0, sizeof(usb_port)); 285 if(get_usb_port_by_string(target_string, usb_port, sizeof(usb_port)) == NULL) 286 return NULL; 287 if((ptr = strstr(target_string, usb_port)) == NULL) 288 return NULL; 289 if(ptr != target_string) 290 ptr += strlen(usb_port)+1; 291 292 if((ptr2 = strchr(ptr, ':')) == NULL) 293 return NULL; 294 ptr3 = ptr2; 295 *ptr3 = 0; 296 297 if((ptr2 = strrchr(ptr, '/')) == NULL) 298 ptr2 = ptr; 299 else 300 ptr = ptr2+1; 301 302 len = strlen(ptr); 303 if(len > 16) 304 len = 16; 305 306 memset(buf, 0, sizeof(buf)); 307 strncpy(buf, ptr, len); 308 309 len = strlen(buf); 310 if(len > ret_size) 311 len = ret_size; 312 313 memset(ret, 0, ret_size); 314 strncpy(ret, buf, len); 315 316 *ptr3 = ':'; 317 318 return ret; 319} 320 321char *get_usb_node_by_device(const char *device_name, char *buf, const int buf_size) 322{ 323 int device_type = get_device_type_by_device(device_name); 324 char device_path[128], usb_path[PATH_MAX]; 325 char disk_name[16]; 326 327 if(device_type == DEVICE_TYPE_UNKNOWN) 328 return NULL; 329 330 memset(device_path, 0, 128); 331 memset(usb_path, 0, PATH_MAX); 332 333 if(device_type == DEVICE_TYPE_DISK){ 334 get_disk_name(device_name, disk_name, 16); 335 sprintf(device_path, "%s/%s/device", SYS_BLOCK, disk_name); 336 if(realpath(device_path, usb_path) == NULL){ 337 usb_dbg("(%s): Fail to get link: %s.\n", device_name, device_path); 338 return NULL; 339 } 340 } 341 else 342#ifdef RTCONFIG_USB_PRINTER 343 if(device_type == DEVICE_TYPE_PRINTER){ 344 sprintf(device_path, "%s/%s/device", SYS_USB, device_name); 345 if(realpath(device_path, usb_path) == NULL){ 346 usb_dbg("(%s): Fail to get link: %s.\n", device_name, device_path); 347 return NULL; 348 } 349 } 350 else 351#endif 352#ifdef RTCONFIG_USB_MODEM 353 if(device_type == DEVICE_TYPE_SG){ 354 sprintf(device_path, "%s/%s/device", SYS_SG, device_name); 355 if(realpath(device_path, usb_path) == NULL){ 356 usb_dbg("(%s): Fail to get link: %s.\n", device_name, device_path); 357 return NULL; 358 } 359 } 360 else 361 if(device_type == DEVICE_TYPE_CD){ 362 sprintf(device_path, "%s/%s/device", SYS_BLOCK, device_name); 363 if(realpath(device_path, usb_path) == NULL){ 364 usb_dbg("(%s): Fail to get link: %s.\n", device_name, device_path); 365 return NULL; 366 } 367 } 368 else 369 if(device_type == DEVICE_TYPE_MODEM){ 370 sprintf(device_path, "%s/%s/device", SYS_TTY, device_name); 371 if(realpath(device_path, usb_path) == NULL){ 372 sleep(1); // Sometimes link would be built slowly, so try again. 373 374 if(realpath(device_path, usb_path) == NULL){ 375 usb_dbg("(%s)(2/2): Fail to get link: %s.\n", device_name, device_path); 376 return NULL; 377 } 378 } 379 } 380 else 381#endif 382#ifdef RTCONFIG_USB_BECEEM 383 if(device_type == DEVICE_TYPE_BECEEM){ 384 sprintf(device_path, "%s/%s/device", SYS_USB, device_name); 385 if(realpath(device_path, usb_path) == NULL){ 386 if(realpath(device_path, usb_path) == NULL){ 387 usb_dbg("(%s)(2/2): Fail to get link: %s.\n", device_name, device_path); 388 return NULL; 389 } 390 } 391 } 392 else 393#endif 394 return NULL; 395 396#ifdef BCM_MMC 397 if(isMMCDevice(device_name)){ // SD card. 398 snprintf(buf, buf_size, "%s", SDCARD_PORT); 399 } 400 else 401#endif 402 if(get_usb_node_by_string(usb_path, buf, buf_size) == NULL){ 403 usb_dbg("(%s): Fail to get usb node: %s.\n", device_name, usb_path); 404 return NULL; 405 } 406 407 return buf; 408} 409 410char *get_path_by_node(const char *usb_node, char *buf, const int buf_size){ 411 char usb_port[32], *hub_path; 412 int port_num = 0, len; 413 414 if(usb_node == NULL || buf == NULL || buf_size <= 0) 415 return NULL; 416 417 // Get USB port. 418 if(get_usb_port_by_string(usb_node, usb_port, sizeof(usb_port)) == NULL) 419 return NULL; 420 421 port_num = get_usb_port_number(usb_port); 422 if(port_num == 0) 423 return NULL; 424 425 if(strlen(usb_node) > (len = strlen(usb_port))){ 426 hub_path = (char *)usb_node+len; 427 snprintf(buf, buf_size, "%d%s", port_num, hub_path); 428 } 429 else 430 snprintf(buf, buf_size, "%d", port_num); 431 432 return buf; 433} 434 435void strntrim(char *str){ 436 register char *start, *end; 437 int len; 438 439 if(str == NULL) 440 return; 441 442 len = strlen(str); 443 start = str; 444 end = start+len-1; 445 446 while(start < end && isspace(*start)) 447 ++start; 448 while(start <= end && isspace(*end)) 449 --end; 450 451 end++; 452 453 if((int)(end-start) < len){ 454 memcpy(str, start, (end-start)); 455 str[end-start] = 0; 456 } 457 458 return; 459} 460 461char *read_whole_file(const char *target) { 462 FILE *fp = fopen(target, "r"); 463 char *buffer, *new_str; 464 int i; 465 unsigned int read_bytes = 0; 466 unsigned int each_size = 1024; 467 468 if (fp == NULL) 469 return NULL; 470 471 buffer = (char *)malloc(sizeof(char)*each_size+read_bytes); 472 if (buffer == NULL) { 473 usb_dbg("No memory \"buffer\".\n"); 474 fclose(fp); 475 return NULL; 476 } 477 memset(buffer, 0, sizeof(char)*each_size+read_bytes); 478 479 while ((i = fread(buffer+read_bytes, each_size * sizeof(char), 1, fp)) == 1){ 480 read_bytes += each_size; 481 new_str = (char *)malloc(sizeof(char)*each_size+read_bytes); 482 if (new_str == NULL) { 483 usb_dbg("No memory \"new_str\".\n"); 484 free(buffer); 485 fclose(fp); 486 return NULL; 487 } 488 memset(new_str, 0, sizeof(char)*each_size+read_bytes); 489 memcpy(new_str, buffer, read_bytes); 490 491 free(buffer); 492 buffer = new_str; 493 } 494 495 fclose(fp); 496 return buffer; 497} 498 499char *get_line_from_buffer(const char *buf, char *line, const int line_size){ 500 int buf_len, len; 501 char *ptr; 502 503 if(buf == NULL || (buf_len = strlen(buf)) <= 0) 504 return NULL; 505 506 if((ptr = strchr(buf, '\n')) == NULL) 507 ptr = (char *)(buf+buf_len); 508 509 if((len = ptr-buf) < 0) 510 len = buf-ptr; 511 ++len; // include '\n'. 512 513 memset(line, 0, line_size); 514 strncpy(line, buf, len); 515 516 return line; 517} 518 519disk_info_t *read_disk_data(){ 520 disk_info_t *disk_info_list = NULL, *new_disk_info, **follow_disk_info_list; 521 char *partition_info = read_whole_file(PARTITION_FILE); 522 char *follow_info; 523 char line[64], device_name[16]; 524 u32 major; 525 disk_info_t *parent_disk_info; 526 partition_info_t *new_partition_info, **follow_partition_list; 527 u64 device_size; 528 529 if(partition_info == NULL){ 530 usb_dbg("Failed to open \"%s\"!!\n", PARTITION_FILE); 531 return disk_info_list; 532 } 533 follow_info = partition_info; 534 535 memset(device_name, 0, 16); 536 while(get_line_from_buffer(follow_info, line, 64) != NULL){ 537 follow_info += strlen(line); 538 539 if(sscanf(line, "%u %*u %llu %[^\n ]", &major, &device_size, device_name) != 3) 540 continue; 541 if(major != USB_DISK_MAJOR 542#ifdef BCM_MMC 543 && major != MMC_DISK_MAJOR 544#endif 545 ) 546 continue; 547 if(device_size == 1) // extend partition. 548 continue; 549 550 if(is_disk_name(device_name)){ // Disk 551 follow_disk_info_list = &disk_info_list; 552 while(*follow_disk_info_list != NULL) 553 follow_disk_info_list = &((*follow_disk_info_list)->next); 554 555 new_disk_info = create_disk(device_name, follow_disk_info_list); 556 } 557 else if(is_partition_name(device_name, NULL)){ // Partition 558 // Found a partition device. 559 // Find the parent disk. 560 parent_disk_info = disk_info_list; 561 while(1){ 562 if(parent_disk_info == NULL){ 563 usb_dbg("Error while parsing %s: found " 564 "partition '%s' but haven't seen the disk device " 565 "of which it is a part.\n", PARTITION_FILE, device_name); 566 free(partition_info); 567 return disk_info_list; 568 } 569 570 if(!strncmp(device_name, parent_disk_info->device, 3)) 571 break; 572 573 parent_disk_info = parent_disk_info->next; 574 } 575 576 follow_partition_list = &(parent_disk_info->partitions); 577 while(*follow_partition_list != NULL){ 578 if((*follow_partition_list)->partition_order == 0){ 579 free_partition_data(follow_partition_list); 580 parent_disk_info->partitions = NULL; 581 follow_partition_list = &(parent_disk_info->partitions); 582 } 583 else 584 follow_partition_list = &((*follow_partition_list)->next); 585 } 586 587 new_partition_info = create_partition(device_name, follow_partition_list); 588 if(new_partition_info != NULL) 589 new_partition_info->disk = parent_disk_info; 590 } 591 } 592 593 free(partition_info); 594 return disk_info_list; 595} 596 597int is_disk_name(const char *device_name){ 598 if(get_device_type_by_device(device_name) != DEVICE_TYPE_DISK) 599 return 0; 600 601#ifdef BCM_MMC 602 if(isMMCDevice(device_name)){ 603 if(strchr(device_name, 'p')) 604 return 0; 605 } 606 else 607#endif 608 if(isdigit(device_name[strlen(device_name)-1])) 609 return 0; 610 611 return 1; 612} 613 614disk_info_t *create_disk(const char *device_name, disk_info_t **new_disk_info){ 615 disk_info_t *follow_disk_info; 616 u32 major, minor; 617 u64 size_in_kilobytes = 0; 618 int len; 619 char usb_node[32], port_path[8]; 620 char buf[64], *port, *vendor = NULL, *model = NULL, *ptr; 621 partition_info_t *new_partition_info, **follow_partition_list; 622 623 if(new_disk_info == NULL){ 624 usb_dbg("Bad input!!\n"); 625 return NULL; 626 } 627 628 *new_disk_info = NULL; // initial value. 629 630 if(device_name == NULL || !is_disk_name(device_name)) 631 return NULL; 632 633 if(initial_disk_data(&follow_disk_info) == NULL){ 634 usb_dbg("No memory!!(follow_disk_info)\n"); 635 return NULL; 636 } 637 638 len = strlen(device_name); 639 follow_disk_info->device = (char *)malloc(len+1); 640 if(follow_disk_info->device == NULL){ 641 usb_dbg("No memory!!(follow_disk_info->device)\n"); 642 free_disk_data(&follow_disk_info); 643 return NULL; 644 } 645 strcpy(follow_disk_info->device, device_name); 646 follow_disk_info->device[len] = 0; 647 648 if(!get_disk_major_minor(device_name, &major, &minor)){ 649 usb_dbg("Fail to get disk's major and minor: %s.\n", device_name); 650 free_disk_data(&follow_disk_info); 651 return NULL; 652 } 653 follow_disk_info->major = major; 654 follow_disk_info->minor = minor; 655 656 if(!get_disk_size(device_name, &size_in_kilobytes)){ 657 usb_dbg("Fail to get disk's size_in_kilobytes: %s.\n", device_name); 658 free_disk_data(&follow_disk_info); 659 return NULL; 660 } 661 follow_disk_info->size_in_kilobytes = size_in_kilobytes; 662 663 if(isStorageDevice(device_name) 664#ifdef BCM_MMC 665 || isMMCDevice(device_name) 666#endif 667 ){ 668 // Get USB node. 669 if(get_usb_node_by_device(device_name, usb_node, 32) == NULL){ 670 usb_dbg("(%s): Fail to get usb node.\n", device_name); 671 free_disk_data(&follow_disk_info); 672 return NULL; 673 } 674 675 if(get_path_by_node(usb_node, port_path, 8) == NULL){ 676 usb_dbg("(%s): Fail to get usb path.\n", usb_node); 677 free_disk_data(&follow_disk_info); 678 return NULL; 679 } 680 681 // Get USB port. 682 if(get_usb_port_by_string(usb_node, buf, 64) == NULL){ 683 usb_dbg("Fail to get usb port: %s.\n", usb_node); 684 free_disk_data(&follow_disk_info); 685 return NULL; 686 } 687 688 len = strlen(buf); 689 if(len > 0){ 690 port = (char *)malloc(8); 691 if(port == NULL){ 692 usb_dbg("No memory!!(port)\n"); 693 free_disk_data(&follow_disk_info); 694 return NULL; 695 } 696 memset(port, 0, 8); 697 strncpy(port, port_path, 8); 698 699 follow_disk_info->port = port; 700 } 701 702 // start get vendor. 703 get_disk_vendor(device_name, buf, 64); 704 705 len = strlen(buf); 706 if(len > 0){ 707 vendor = (char *)malloc(len+1); 708 if(vendor == NULL){ 709 usb_dbg("No memory!!(vendor)\n"); 710 free_disk_data(&follow_disk_info); 711 return NULL; 712 } 713 strncpy(vendor, buf, len); 714 vendor[len] = 0; 715 strntrim(vendor); 716 717 follow_disk_info->vendor = vendor; 718 } 719 720 // start get model. 721 get_disk_model(device_name, buf, 64); 722 723 len = strlen(buf); 724 if(len > 0){ 725 model = (char *)malloc(len+1); 726 if(model == NULL){ 727 usb_dbg("No memory!!(model)\n"); 728 free_disk_data(&follow_disk_info); 729 return NULL; 730 } 731 strncpy(model, buf, len); 732 model[len] = 0; 733 strntrim(model); 734 735 follow_disk_info->model = model; 736 } 737 738 // get USB's tag 739 memset(buf, 0, 64); 740 len = 0; 741 ptr = buf; 742 if(vendor != NULL){ 743 len += strlen(vendor); 744 strcpy(ptr, vendor); 745 ptr += len; 746 } 747 if(model != NULL){ 748 if(len > 0){ 749 ++len; // Add a space between vendor and model. 750 strcpy(ptr, " "); 751 ++ptr; 752 } 753 len += strlen(model); 754 strcpy(ptr, model); 755 ptr += len; 756 } 757 758 if(len > 0){ 759 follow_disk_info->tag = (char *)malloc(len+1); 760 if(follow_disk_info->tag == NULL){ 761 usb_dbg("No memory!!(follow_disk_info->tag)\n"); 762 free_disk_data(&follow_disk_info); 763 return NULL; 764 } 765 strcpy(follow_disk_info->tag, buf); 766 follow_disk_info->tag[len] = 0; 767 } 768 else{ 769#ifdef BCM_MMC 770 if(isMMCDevice(device_name)) 771 len = strlen(DEFAULT_MMC_TAG); 772 else 773#endif 774 len = strlen(DEFAULT_USB_TAG); 775 776 follow_disk_info->tag = (char *)malloc(len+1); 777 if(follow_disk_info->tag == NULL){ 778 usb_dbg("No memory!!(follow_disk_info->tag)\n"); 779 free_disk_data(&follow_disk_info); 780 return NULL; 781 } 782#ifdef BCM_MMC 783 if(isMMCDevice(device_name)) 784 strcpy(follow_disk_info->tag, DEFAULT_MMC_TAG); 785 else 786#endif 787 strcpy(follow_disk_info->tag, DEFAULT_USB_TAG); 788 follow_disk_info->tag[len] = 0; 789 } 790 791 follow_partition_list = &(follow_disk_info->partitions); 792 while(*follow_partition_list != NULL) 793 follow_partition_list = &((*follow_partition_list)->next); 794 795 new_partition_info = create_partition(device_name, follow_partition_list); 796 if(new_partition_info != NULL){ 797 new_partition_info->disk = follow_disk_info; 798 799 ++(follow_disk_info->partition_number); 800 ++(follow_disk_info->mounted_number); 801 if(!strcmp(new_partition_info->device, follow_disk_info->device)) 802 new_partition_info->size_in_kilobytes = follow_disk_info->size_in_kilobytes-4; 803 } 804 } 805 806 if(!strcmp(follow_disk_info->device, follow_disk_info->partitions->device)) 807 get_disk_partitionnumber(device_name, &(follow_disk_info->partition_number), &(follow_disk_info->mounted_number)); 808 809 *new_disk_info = follow_disk_info; 810 811 return *new_disk_info; 812} 813 814disk_info_t *initial_disk_data(disk_info_t **disk_info_list){ 815 disk_info_t *follow_disk; 816 817 if(disk_info_list == NULL) 818 return NULL; 819 820 *disk_info_list = (disk_info_t *)malloc(sizeof(disk_info_t)); 821 if(*disk_info_list == NULL) 822 return NULL; 823 824 follow_disk = *disk_info_list; 825 826 follow_disk->tag = NULL; 827 follow_disk->vendor = NULL; 828 follow_disk->model = NULL; 829 follow_disk->device = NULL; 830 follow_disk->major = (u32)0; 831 follow_disk->minor = (u32)0; 832 follow_disk->port = NULL; 833 follow_disk->partition_number = (u32)0; 834 follow_disk->mounted_number = (u32)0; 835 follow_disk->size_in_kilobytes = (u64)0; 836 follow_disk->partitions = NULL; 837 follow_disk->next = NULL; 838 839 return follow_disk; 840} 841 842void free_disk_data(disk_info_t **disk_info_list){ 843 disk_info_t *follow_disk, *old_disk; 844 845 if(disk_info_list == NULL) 846 return; 847 848 follow_disk = *disk_info_list; 849 while(follow_disk != NULL){ 850 if(follow_disk->tag != NULL) 851 free(follow_disk->tag); 852 if(follow_disk->vendor != NULL) 853 free(follow_disk->vendor); 854 if(follow_disk->model != NULL) 855 free(follow_disk->model); 856 if(follow_disk->device != NULL) 857 free(follow_disk->device); 858 if(follow_disk->port != NULL) 859 free(follow_disk->port); 860 861 free_partition_data(&(follow_disk->partitions)); 862 863 old_disk = follow_disk; 864 follow_disk = follow_disk->next; 865 free(old_disk); 866 } 867} 868 869int get_disk_major_minor(const char *disk_name, u32 *major, u32 *minor){ 870 FILE *fp; 871 char target_file[128], buf[8], *ptr; 872 873 if(major == NULL || minor == NULL) 874 return 0; 875 876 *major = 0; // initial value. 877 *minor = 0; // initial value. 878 879 if(disk_name == NULL || !is_disk_name(disk_name)) 880 return 0; 881 882 memset(target_file, 0, 128); 883 sprintf(target_file, "%s/%s/dev", SYS_BLOCK, disk_name); 884 if((fp = fopen(target_file, "r")) == NULL) 885 return 0; 886 887 memset(buf, 0, 8); 888 ptr = fgets(buf, 8, fp); 889 fclose(fp); 890 if(ptr == NULL) 891 return 0; 892 893 if((ptr = strchr(buf, ':')) == NULL) 894 return 0; 895 896 ptr[0] = '\0'; 897 *major = (u32)strtol(buf, NULL, 10); 898 *minor = (u32)strtol(ptr+1, NULL, 10); 899 900 return 1; 901} 902 903int get_disk_size(const char *disk_name, u64 *size_in_kilobytes){ 904 FILE *fp; 905 char target_file[128], buf[16], *ptr; 906 907 if(size_in_kilobytes == NULL) 908 return 0; 909 910 *size_in_kilobytes = 0; // initial value. 911 912 if(disk_name == NULL || !is_disk_name(disk_name)) 913 return 0; 914 915 memset(target_file, 0, 128); 916 sprintf(target_file, "%s/%s/size", SYS_BLOCK, disk_name); 917 if((fp = fopen(target_file, "r")) == NULL) 918 return 0; 919 920 memset(buf, 0, 16); 921 ptr = fgets(buf, 16, fp); 922 fclose(fp); 923 if(ptr == NULL) 924 return 0; 925 926 *size_in_kilobytes = ((u64)strtoll(buf, NULL, 10))/2; 927 928 return 1; 929} 930 931char *get_disk_vendor(const char *disk_name, char *buf, const int buf_size){ 932 FILE *fp; 933 char target_file[128], *ptr; 934 int len; 935 936 if(buf_size <= 0) 937 return NULL; 938 memset(buf, 0, buf_size); 939 940 if(disk_name == NULL || !is_disk_name(disk_name)) 941 return NULL; 942 943 memset(target_file, 0, 128); 944 sprintf(target_file, "%s/%s/device/vendor", SYS_BLOCK, disk_name); 945 if((fp = fopen(target_file, "r")) == NULL) 946 return NULL; 947 948 ptr = fgets(buf, buf_size, fp); 949 fclose(fp); 950 if(ptr == NULL) 951 return NULL; 952 953 len = strlen(buf); 954 buf[len-1] = 0; 955 956 return buf; 957} 958 959char *get_disk_model(const char *disk_name, char *buf, const int buf_size){ 960 FILE *fp; 961 char target_file[128], *ptr; 962 int len; 963 964 if(buf_size <= 0) 965 return NULL; 966 memset(buf, 0, buf_size); 967 968 if(disk_name == NULL || !is_disk_name(disk_name)) 969 return NULL; 970 971 memset(target_file, 0, 128); 972 sprintf(target_file, "%s/%s/device/model", SYS_BLOCK, disk_name); 973 if((fp = fopen(target_file, "r")) == NULL) 974 return NULL; 975 976 ptr = fgets(buf, buf_size, fp); 977 fclose(fp); 978 if(ptr == NULL) 979 return NULL; 980 981 len = strlen(buf); 982 buf[len-1] = 0; 983 984 return buf; 985} 986 987int get_disk_partitionnumber(const char *string, u32 *partition_number, u32 *mounted_number){ 988 char disk_name[16]; 989 char target_path[128]; 990 DIR *dp; 991 struct dirent *file; 992 int len; 993 char *mount_info = NULL, target[8]; 994 995 if(string == NULL) 996 return 0; 997 998 if(partition_number == NULL) 999 return 0; 1000 1001 *partition_number = 0; // initial value. 1002 if(mounted_number != NULL){ 1003 *mounted_number = 0; // initial value. 1004 mount_info = read_whole_file(MOUNT_FILE); 1005 } 1006 1007 len = strlen(string); 1008 if(!is_disk_name(string)){ 1009 while(isdigit(string[len-1])) 1010 --len; 1011 1012#ifdef BCM_MMC 1013 if(string[len-1] == 'p') 1014 --len; 1015#endif 1016 } 1017 else if(mounted_number != NULL && mount_info != NULL){ 1018 memset(target, 0, 8); 1019 sprintf(target, "%s ", string); 1020 if(strstr(mount_info, target) != NULL) 1021 ++(*mounted_number); 1022 } 1023 memset(disk_name, 0, 16); 1024 strncpy(disk_name, string, len); 1025 1026 memset(target_path, 0, 128); 1027 sprintf(target_path, "%s/%s", SYS_BLOCK, disk_name); 1028 if((dp = opendir(target_path)) == NULL){ 1029 if(mount_info != NULL) 1030 free(mount_info); 1031 return 0; 1032 } 1033 1034 len = strlen(disk_name); 1035 while((file = readdir(dp)) != NULL){ 1036 if(file->d_name[0] == '.') 1037 continue; 1038 1039 if(!strncmp(file->d_name, disk_name, len)){ 1040 ++(*partition_number); 1041 1042 if(mounted_number == NULL || mount_info == NULL) 1043 continue; 1044 1045 memset(target, 0, 8); 1046 sprintf(target, "%s ", file->d_name); 1047 if(strstr(mount_info, target) != NULL) 1048 ++(*mounted_number); 1049 } 1050 } 1051 closedir(dp); 1052 if(mount_info != NULL) 1053 free(mount_info); 1054 1055 return 1; 1056} 1057 1058int is_partition_name(const char *device_name, u32 *partition_order){ 1059 int order; 1060 u32 partition_number; 1061 1062 if(partition_order != NULL) 1063 *partition_order = 0; 1064 1065 if(get_device_type_by_device(device_name) != DEVICE_TYPE_DISK) 1066 return 0; 1067 1068 // get the partition number in the device_name 1069#ifdef BCM_MMC 1070 if(isMMCDevice(device_name)) // SD card: mmcblk0p1. 1071 order = (u32)strtol(device_name+8, NULL, 10); 1072 else // sda1. 1073#endif 1074 order = (u32)strtol(device_name+3, NULL, 10); 1075 if(order <= 0 || order == LONG_MIN || order == LONG_MAX) 1076 return 0; 1077 1078 if(!get_disk_partitionnumber(device_name, &partition_number, NULL)) 1079 return 0; 1080 1081 if(partition_order != NULL) 1082 *partition_order = order; 1083 1084 return 1; 1085} 1086 1087int find_partition_label(const char *dev_name, char *label){ 1088 struct volume_id id; 1089 char dev_path[128]; 1090 char usb_port[32]; 1091 char nvram_label[32], nvram_value[512]; 1092 1093 if(label) *label = 0; 1094 1095 memset(usb_port, 0, 32); 1096 if(get_usb_port_by_device(dev_name, usb_port, 32) == NULL) 1097 return 0; 1098 1099 memset(nvram_label, 0, 32); 1100 sprintf(nvram_label, "usb_path_%s_label", dev_name); 1101 1102 memset(nvram_value, 0, 512); 1103 strncpy(nvram_value, nvram_safe_get(nvram_label), 512); 1104 if(strlen(nvram_value) > 0){ 1105 strcpy(label, nvram_value); 1106 1107 return (label && *label != 0); 1108 } 1109 1110 memset(dev_path, 0, 128); 1111 sprintf(dev_path, "/dev/%s", dev_name); 1112 1113 memset(&id, 0x00, sizeof(id)); 1114 if((id.fd = open(dev_path, O_RDONLY)) < 0) 1115 return 0; 1116 1117 volume_id_get_buffer(&id, 0, SB_BUFFER_SIZE); 1118 1119 if(volume_id_probe_linux_swap(&id) == 0 || id.error) 1120 goto ret; 1121 if(volume_id_probe_ext(&id) == 0 || id.error) 1122 goto ret; 1123 if(volume_id_probe_vfat(&id) == 0 || id.error) 1124 goto ret; 1125 if(volume_id_probe_ntfs(&id) == 0 || id.error) 1126 goto ret; 1127 if(volume_id_probe_hfs_hfsplus(&id) == 0 || id.error) 1128 goto ret; 1129 1130ret: 1131 volume_id_free_buffer(&id); 1132 if(label && (*id.label != 0)) 1133 strcpy(label, id.label); 1134 else 1135 strcpy(label, " "); 1136 nvram_set(nvram_label, label); 1137 close(id.fd); 1138 return (label && *label != 0); 1139} 1140 1141partition_info_t *create_partition(const char *device_name, partition_info_t **new_part_info){ 1142 partition_info_t *follow_part_info; 1143 char label[128]; 1144 u32 partition_order = 0; 1145 u64 size_in_kilobytes = 0, total_kilobytes = 0, used_kilobytes = 0; 1146 char buf1[PATH_MAX], buf2[64], buf3[PATH_MAX]; // options of mount info needs more buffer size. 1147 int len; 1148 1149 if(new_part_info == NULL){ 1150 usb_dbg("Bad input!!\n"); 1151 return NULL; 1152 } 1153 1154 *new_part_info = NULL; // initial value. 1155 1156 if(device_name == NULL || get_device_type_by_device(device_name) != DEVICE_TYPE_DISK) 1157 return NULL; 1158 1159 if(!is_disk_name(device_name) && !is_partition_name(device_name, &partition_order)) 1160 return NULL; 1161 1162 if(initial_part_data(&follow_part_info) == NULL){ 1163 usb_dbg("No memory!!(follow_part_info)\n"); 1164 return NULL; 1165 } 1166 1167 len = strlen(device_name); 1168 follow_part_info->device = (char *)malloc(len+1); 1169 if(follow_part_info->device == NULL){ 1170 usb_dbg("No memory!!(follow_part_info->device)\n"); 1171 free_partition_data(&follow_part_info); 1172 return NULL; 1173 } 1174 strncpy(follow_part_info->device, device_name, len); 1175 follow_part_info->device[len] = 0; 1176 1177 if(find_partition_label(device_name, label)){ 1178 strntrim(label); 1179 len = strlen(label); 1180 follow_part_info->label = (char *)malloc(len+1); 1181 if(follow_part_info->label == NULL){ 1182 usb_dbg("No memory!!(follow_part_info->label)\n"); 1183 free_partition_data(&follow_part_info); 1184 return NULL; 1185 } 1186 strncpy(follow_part_info->label, label, len); 1187 follow_part_info->label[len] = 0; 1188 } 1189 1190 follow_part_info->partition_order = partition_order; 1191 1192 if(read_mount_data(device_name, buf1, PATH_MAX, buf2, 64, buf3, PATH_MAX)){ 1193 len = strlen(buf1); 1194 follow_part_info->mount_point = (char *)malloc(len+1); 1195 if(follow_part_info->mount_point == NULL){ 1196 usb_dbg("No memory!!(follow_part_info->mount_point)\n"); 1197 free_partition_data(&follow_part_info); 1198 return NULL; 1199 } 1200 strncpy(follow_part_info->mount_point, buf1, len); 1201 follow_part_info->mount_point[len] = 0; 1202 1203 len = strlen(buf2); 1204 follow_part_info->file_system = (char *)malloc(len+1); 1205 if(follow_part_info->file_system == NULL){ 1206 usb_dbg("No memory!!(follow_part_info->file_system)\n"); 1207 free_partition_data(&follow_part_info); 1208 return NULL; 1209 } 1210 strncpy(follow_part_info->file_system, buf2, len); 1211 follow_part_info->file_system[len] = 0; 1212 1213 len = strlen(buf3); 1214 follow_part_info->permission = (char *)malloc(len+1); 1215 if(follow_part_info->permission == NULL){ 1216 usb_dbg("No memory!!(follow_part_info->permission)\n"); 1217 free_partition_data(&follow_part_info); 1218 return NULL; 1219 } 1220 strncpy(follow_part_info->permission, buf3, len); 1221 follow_part_info->permission[len] = 0; 1222 1223 if(get_mount_size(follow_part_info->mount_point, &total_kilobytes, &used_kilobytes)){ 1224 follow_part_info->size_in_kilobytes = total_kilobytes; 1225 follow_part_info->used_kilobytes = used_kilobytes; 1226 } 1227 } 1228 else{ 1229 /*if(is_disk_name(device_name)){ // Disk 1230 free_partition_data(&follow_part_info); 1231 return NULL; 1232 } 1233 else{//*/ 1234 len = strlen(PARTITION_TYPE_UNKNOWN); 1235 follow_part_info->file_system = (char *)malloc(len+1); 1236 if(follow_part_info->file_system == NULL){ 1237 usb_dbg("No memory!!(follow_part_info->file_system)\n"); 1238 free_partition_data(&follow_part_info); 1239 return NULL; 1240 } 1241 strncpy(follow_part_info->file_system, PARTITION_TYPE_UNKNOWN, len); 1242 follow_part_info->file_system[len] = 0; 1243 1244 get_partition_size(device_name, &size_in_kilobytes); 1245 follow_part_info->size_in_kilobytes = size_in_kilobytes; 1246 //} 1247 } 1248 1249 *new_part_info = follow_part_info; 1250 1251 return *new_part_info; 1252} 1253 1254partition_info_t *initial_part_data(partition_info_t **part_info_list){ 1255 partition_info_t *follow_part; 1256 1257 if(part_info_list == NULL) 1258 return NULL; 1259 1260 *part_info_list = (partition_info_t *)malloc(sizeof(partition_info_t)); 1261 if(*part_info_list == NULL) 1262 return NULL; 1263 1264 follow_part = *part_info_list; 1265 1266 follow_part->device = NULL; 1267 follow_part->label = NULL; 1268 follow_part->partition_order = (u32)0; 1269 follow_part->mount_point = NULL; 1270 follow_part->file_system = NULL; 1271 follow_part->permission = NULL; 1272 follow_part->size_in_kilobytes = (u64)0; 1273 follow_part->used_kilobytes = (u64)0; 1274 follow_part->disk = NULL; 1275 follow_part->next = NULL; 1276 1277 return follow_part; 1278} 1279 1280void free_partition_data(partition_info_t **partition_info_list){ 1281 partition_info_t *follow_partition, *old_partition; 1282 1283 if(partition_info_list == NULL) 1284 return; 1285 1286 follow_partition = *partition_info_list; 1287 while(follow_partition != NULL){ 1288 if(follow_partition->device != NULL) 1289 free(follow_partition->device); 1290 if(follow_partition->label != NULL) 1291 free(follow_partition->label); 1292 if(follow_partition->mount_point != NULL) 1293 free(follow_partition->mount_point); 1294 if(follow_partition->file_system != NULL) 1295 free(follow_partition->file_system); 1296 if(follow_partition->permission != NULL) 1297 free(follow_partition->permission); 1298 1299 follow_partition->disk = NULL; 1300 1301 old_partition = follow_partition; 1302 follow_partition = follow_partition->next; 1303 free(old_partition); 1304 } 1305} 1306 1307int get_partition_size(const char *partition_name, u64 *size_in_kilobytes){ 1308 FILE *fp; 1309 char disk_name[16]; 1310 char target_file[128], buf[16], *ptr; 1311 1312 if(size_in_kilobytes == NULL) 1313 return 0; 1314 1315 *size_in_kilobytes = 0; // initial value. 1316 1317 if(!is_partition_name(partition_name, NULL)) 1318 return 0; 1319 1320 get_disk_name(partition_name, disk_name, 16); 1321 1322 memset(target_file, 0, 128); 1323 sprintf(target_file, "%s/%s/%s/size", SYS_BLOCK, disk_name, partition_name); 1324 if((fp = fopen(target_file, "r")) == NULL) 1325 return 0; 1326 1327 memset(buf, 0, 16); 1328 ptr = fgets(buf, 16, fp); 1329 fclose(fp); 1330 if(ptr == NULL) 1331 return 0; 1332 1333 *size_in_kilobytes = ((u64)strtoll(buf, NULL, 10))/2; 1334 1335 return 1; 1336} 1337 1338int read_mount_data(const char *device_name 1339 , char *mount_point, int mount_len 1340 , char *type, int type_len 1341 , char *right, int right_len 1342 ){ 1343 char *mount_info = read_whole_file(MOUNT_FILE); 1344 char *start, line[PATH_MAX]; 1345 char target[8]; 1346 1347 if(mount_point == NULL || mount_len <= 0 1348 || type == NULL || type_len <= 0 1349 || right == NULL || right_len <= 0 1350 ){ 1351 usb_dbg("Bad input!!\n"); 1352 return 0; 1353 } 1354 1355 if(mount_info == NULL){ 1356 usb_dbg("Failed to open \"%s\"!!\n", MOUNT_FILE); 1357 return 0; 1358 } 1359 1360 memset(target, 0, 8); 1361 sprintf(target, "%s ", device_name); 1362 1363 if((start = strstr(mount_info, target)) == NULL){ 1364 //usb_dbg("disk_initial:: %s: Failed to execute strstr()!\n", device_name); 1365 free(mount_info); 1366 return 0; 1367 } 1368 1369 start += strlen(target); 1370 1371 if(get_line_from_buffer(start, line, PATH_MAX) == NULL){ 1372 usb_dbg("%s: Failed to execute get_line_from_buffer()!\n", device_name); 1373 free(mount_info); 1374 return 0; 1375 } 1376 1377 memset(mount_point, 0, mount_len); 1378 memset(type, 0, type_len); 1379 memset(right, 0, right_len); 1380 1381 if(sscanf(line, "%s %s %[^\n ]", mount_point, type, right) != 3){ 1382 usb_dbg("%s: Failed to execute sscanf()!\n", device_name); 1383 free(mount_info); 1384 return 0; 1385 } 1386 1387 if(!strcmp(type, "ufsd")){ 1388 char full_dev[16]; 1389 1390 memset(full_dev, 0, 16); 1391 sprintf(full_dev, "/dev/%s", device_name); 1392 1393 memset(type, 0, type_len); 1394 strcpy(type, detect_fs_type(full_dev)); 1395 } 1396 1397 right[2] = 0; 1398 1399 free(mount_info); 1400 return 1; 1401} 1402 1403int get_mount_path(const char *const pool, char *mount_path, int mount_len){ 1404 char type[64], right[PATH_MAX]; 1405 1406 return read_mount_data(pool, mount_path, mount_len, type, 64, right, PATH_MAX); 1407} 1408 1409int get_mount_size(const char *mount_point, u64 *total_kilobytes, u64 *used_kilobytes){ 1410 u64 total_size, free_size, used_size; 1411 struct statfs fsbuf; 1412 1413 if(total_kilobytes == NULL || used_kilobytes == NULL) 1414 return 0; 1415 1416 *total_kilobytes = 0; 1417 *used_kilobytes = 0; 1418 1419 if(statfs(mount_point, &fsbuf)) 1420 return 0; 1421 1422 total_size = (u64)((u64)fsbuf.f_blocks*(u64)fsbuf.f_bsize); 1423 free_size = (u64)((u64)fsbuf.f_bfree*(u64)fsbuf.f_bsize); 1424 used_size = total_size-free_size; 1425 1426 *total_kilobytes = total_size/1024; 1427 *used_kilobytes = used_size/1024; 1428 1429 return 1; 1430} 1431 1432char *get_disk_name(const char *string, char *buf, const int buf_size){ 1433 int len; 1434 1435 if(string == NULL || buf_size <= 0) 1436 return NULL; 1437 memset(buf, 0, buf_size); 1438 1439 if(!is_disk_name(string) && !is_partition_name(string, NULL)) 1440 return NULL; 1441 1442 len = strlen(string); 1443 if(!is_disk_name(string)){ 1444 while(isdigit(string[len-1])) 1445 --len; 1446 1447#ifdef BCM_MMC 1448 if(string[len-1] == 'p') 1449 --len; 1450#endif 1451 } 1452 1453 if(len > buf_size) 1454 return NULL; 1455 1456 strncpy(buf, string, len); 1457 1458 return buf; 1459} 1460 1461void print_disk(const disk_info_t *const disk_info){ 1462 if(disk_info == NULL){ 1463 usb_dbg("No disk!\n"); 1464 return; 1465 } 1466 1467 usb_dbg("Disk:\n"); 1468 usb_dbg(" tag: %s.\n", disk_info->tag); 1469 usb_dbg(" vendor: %s.\n", disk_info->vendor); 1470 usb_dbg(" model: %s.\n", disk_info->model); 1471 usb_dbg(" device: %s.\n", disk_info->device); 1472 usb_dbg(" major: %u.\n", disk_info->major); 1473 usb_dbg(" minor: %u.\n", disk_info->minor); 1474 usb_dbg(" port: %s.\n", disk_info->port); 1475 usb_dbg(" partition_number: %u.\n", disk_info->partition_number); 1476 usb_dbg(" mounted_number: %u.\n", disk_info->mounted_number); 1477 usb_dbg("size_in_kilobytes: %llu.\n", disk_info->size_in_kilobytes); 1478 1479 print_partitions(disk_info->partitions); 1480} 1481 1482void print_disks(const disk_info_t *const disk_list){ 1483 disk_info_t *follow_disk; 1484 1485 if(disk_list == NULL){ 1486 usb_dbg("No disk list!\n"); 1487 return; 1488 } 1489 1490 for(follow_disk = (disk_info_t *)disk_list; follow_disk != NULL; follow_disk = follow_disk->next) 1491 print_disk(follow_disk); 1492} 1493 1494void print_partition(const partition_info_t *const partition_info){ 1495 if(partition_info == NULL){ 1496 usb_dbg("No partition!\n"); 1497 return; 1498 } 1499 1500 usb_dbg("Partition:\n"); 1501 if(partition_info->disk != NULL) 1502 usb_dbg(" Parent disk: %s.\n", partition_info->disk->device); 1503 usb_dbg(" device: %s.\n", partition_info->device); 1504 usb_dbg(" label: %s.\n", partition_info->label); 1505 usb_dbg(" partition_order: %u.\n", partition_info->partition_order); 1506 usb_dbg(" mount_point: %s.\n", partition_info->mount_point); 1507 usb_dbg(" file_system: %s.\n", partition_info->file_system); 1508 usb_dbg(" permission: %s.\n", partition_info->permission); 1509 usb_dbg("size_in_kilobytes: %llu.\n", partition_info->size_in_kilobytes); 1510 usb_dbg(" used_kilobytes: %llu.\n", partition_info->used_kilobytes); 1511} 1512 1513void print_partitions(const partition_info_t *const partition_list){ 1514 partition_info_t *follow_partition; 1515 1516 if(partition_list == NULL){ 1517 usb_dbg("No partition list!\n"); 1518 return; 1519 } 1520 1521 for(follow_partition = (partition_info_t *)partition_list; follow_partition != NULL; follow_partition = follow_partition->next) 1522 print_partition(follow_partition); 1523} 1524 1525int main(int argc, char *argv[]){ 1526 disk_info_t *disk_info, *disk_list; 1527 partition_info_t *partition_info; 1528 char buf[PATH_MAX]; 1529 1530 usb_dbg("%d: Using myself to get information:\n", VERSION); 1531 1532 if(argc == 3){ 1533 get_mount_path("sdb1", buf, PATH_MAX); 1534 printf("buf=%s.\n", buf); 1535 } 1536 else if(argc == 2){ 1537 if(is_disk_name(argv[1])){ // Disk 1538 usb_dbg("%d: Get disk(%s)'s information:\n", VERSION, argv[1]); 1539 1540 create_disk(argv[1], &disk_info); 1541 1542 print_disk(disk_info); 1543 1544 free_disk_data(&disk_info); 1545 } 1546 else{ 1547 usb_dbg("%d: Get partition(%s)'s information:\n", VERSION, argv[1]); 1548 1549 create_partition(argv[1], &partition_info); 1550 1551 print_partition(partition_info); 1552 1553 free_partition_data(&partition_info); 1554 } 1555 } 1556 else{ 1557 usb_dbg("%d: Get all Disk information:\n", VERSION); 1558 1559 disk_list = read_disk_data(); 1560 1561 print_disks(disk_list); 1562 1563 free_disk_data(&disk_list); 1564 } 1565 1566 return 0; 1567} 1568