disk.c revision 8157
124139Sjoerg/* 224139Sjoerg * ---------------------------------------------------------------------------- 324139Sjoerg * "THE BEER-WARE LICENSE" (Revision 42): 424139Sjoerg * <phk@login.dknet.dk> wrote this file. As long as you retain this notice you 524139Sjoerg * can do whatever you want with this stuff. If we meet some day, and you think 624139Sjoerg * this stuff is worth it, you can buy me a beer in return. Poul-Henning Kamp 724139Sjoerg * ---------------------------------------------------------------------------- 824139Sjoerg * 924139Sjoerg * $Id: disk.c,v 1.2 1995/04/29 01:55:21 phk Exp $ 1024139Sjoerg * 1124139Sjoerg */ 1224139Sjoerg 1324139Sjoerg#include <stdio.h> 1424139Sjoerg#include <stdlib.h> 1524139Sjoerg#include <unistd.h> 1624139Sjoerg#include <fcntl.h> 1724139Sjoerg#include <string.h> 1824139Sjoerg#include <err.h> 1924139Sjoerg#include <sys/types.h> 2024139Sjoerg#include <sys/ioctl.h> 2124139Sjoerg#include <sys/disklabel.h> 2224139Sjoerg#include <sys/diskslice.h> 2324139Sjoerg#include "libdisk.h" 2424139Sjoerg 2524139Sjoerg#define DOSPTYP_EXTENDED 5 2624139Sjoerg#define DOSPTYP_ONTRACK 84 2724139Sjoerg 2824139Sjoergstruct disk * 2924139SjoergOpen_Disk(char *name) 3024139Sjoerg{ 3124139Sjoerg return Int_Open_Disk(name,0); 3224139Sjoerg} 3324139Sjoerg 3424139Sjoergstruct disk * 3524139SjoergInt_Open_Disk(char *name, u_long size) 3624139Sjoerg{ 3724139Sjoerg int i,fd; 3824139Sjoerg struct diskslices ds; 3924139Sjoerg char device[64]; 4024139Sjoerg struct disk *d; 4124139Sjoerg 4224139Sjoerg strcpy(device,"/dev/r"); 4324139Sjoerg strcat(device,name); 4424139Sjoerg 4524139Sjoerg fd = open(device,O_RDONLY); 4624139Sjoerg if (fd < 0) { 4724139Sjoerg warn("open(%s) failed",device); 4824139Sjoerg return 0; 4924139Sjoerg } 5024139Sjoerg i = ioctl(fd,DIOCGSLICEINFO,&ds); 5124139Sjoerg if (i < 0) { 5224139Sjoerg warn("DIOCSLICEINFO(%s) failed",device); 5324139Sjoerg close(fd); 5424139Sjoerg return 0; 5524139Sjoerg } 5624139Sjoerg 5724139Sjoerg d = (struct disk *)malloc(sizeof *d); 58 if(!d) err(1,"malloc failed"); 59 60 memset(d,0,sizeof *d); 61 62 d->name = strdup(name); 63 64 if (!size) 65 size = ds.dss_slices[WHOLE_DISK_SLICE].ds_size; 66 67 Add_Chunk(d, 0, size, name,whole,0,0); 68 if (ds.dss_slices[COMPATIBILITY_SLICE].ds_offset) 69 Add_Chunk(d, 0, 1, "-",reserved,0,0); 70 71 for(i=BASE_SLICE;i<ds.dss_nslices;i++) { 72 char sname[20]; 73 chunk_e ce; 74 u_long flags=0; 75 int subtype=0; 76 if (! ds.dss_slices[i].ds_size) 77 continue; 78 sprintf(sname,"%ss%d",name,i-1); 79 switch (ds.dss_slices[i].ds_type) { 80 case 0xa5: 81 ce = freebsd; 82 break; 83 case 0x1: 84 case 0x6: 85 ce = fat; 86 break; 87 case DOSPTYP_EXTENDED: 88 ce = extended; 89 break; 90 default: 91 ce = foo; 92 subtype = -ds.dss_slices[i].ds_type; 93 break; 94 } 95 flags |= CHUNK_ALIGN; 96 Add_Chunk(d,ds.dss_slices[i].ds_offset, 97 ds.dss_slices[i].ds_size, sname,ce,subtype,flags); 98 if (ce == extended) 99 Add_Chunk(d,ds.dss_slices[i].ds_offset, 100 1, "-",reserved, subtype, flags); 101 if (ds.dss_slices[i].ds_type == 0xa5) { 102 struct disklabel *dl; 103 int j; 104 105 dl = read_disklabel(fd, 106 ds.dss_slices[i].ds_offset + LABELSECTOR); 107 if(dl) { 108 for(j=0; j < dl->d_npartitions; j++) { 109 char pname[20]; 110 sprintf(pname,"%s%c",sname,j+'a'); 111 if (j == 2) 112 continue; 113 if (!dl->d_partitions[j].p_size) 114 continue; 115 Add_Chunk(d, 116 dl->d_partitions[j].p_offset, 117 dl->d_partitions[j].p_size, 118 pname,part,0,0); 119 } 120 } 121 free(dl); 122 } 123 } 124 close(fd); 125 return d; 126} 127 128void 129Debug_Disk(struct disk *d) 130{ 131 printf("Debug_Disk(%s)",d->name); 132 printf(" flags=%lx",d->flags); 133 printf(" real_geom=%lu/%lu/%lu",d->real_cyl,d->real_hd,d->real_sect); 134 printf(" bios_geom=%lu/%lu/%lu\n",d->bios_cyl,d->bios_hd,d->bios_sect); 135 Debug_Chunk(d->chunks); 136} 137 138void 139Free_Disk(struct disk *d) 140{ 141 if(d->chunks) 142 Free_Chunk(d->chunks); 143 if(d->name) 144 free(d->name); 145 free(d); 146} 147 148struct disk * 149Clone_Disk(struct disk *d) 150{ 151 struct disk *d2; 152 153 d2 = (struct disk*) malloc(sizeof *d2); 154 if(!d2) err(1,"malloc failed"); 155 *d2 = *d; 156 d2->name = strdup(d2->name); 157 d2->chunks = Clone_Chunk(d2->chunks); 158 return d2; 159} 160 161void 162Collapse_Disk(struct disk *d) 163{ 164 165 while(Collapse_Chunk(d,d->chunks)) 166 ; 167} 168