X-Git-Url: http://git.mutantstargoat.com/user/nuclear/?a=blobdiff_plain;f=src%2Frawdisk.c;fp=src%2Frawdisk.c;h=b2576ba1feab85eed98f9c560b3226ad46dadd5f;hb=df3263076df0ad443dd9262b6250820c038fa7f2;hp=0000000000000000000000000000000000000000;hpb=d9e1c38ba7dc1bb25604586a197b794983e28d78;p=instimg diff --git a/src/rawdisk.c b/src/rawdisk.c new file mode 100644 index 0000000..b2576ba --- /dev/null +++ b/src/rawdisk.c @@ -0,0 +1,81 @@ +#include +#include +#include +#include +#include +#include +#include +#include "rawdisk.h" + +static GUID guid_iface_disk = {0x53f56307, 0xb6bf, 0x11d0, {0x94, 0xf2, 0x00, 0xa0, 0xc9, 0x1e, 0xfb, 0x8b}}; + +int rawdisk_detect(struct rawdisk_device *disks, int max_disks) +{ + int devidx, ifidx, count; + HDEVINFO devset; + SP_DEVINFO_DATA devdata; + SP_DEVICE_INTERFACE_DATA devif; + SP_DEVICE_INTERFACE_DETAIL_DATA_A *devdetail; + DWORD size, regtype; + char devname[1024]; + + if((devset = SetupDiGetClassDevs(&guid_iface_disk, 0, 0, + DIGCF_PRESENT | DIGCF_DEVICEINTERFACE)) == INVALID_HANDLE_VALUE) { + fprintf(stderr, "failed to enumerate devices\n"); + return -1; + } + + count = 0; + devidx = 0; + for(;;) { + memset(&devdata, 0, sizeof devdata); + devdata.cbSize = sizeof devdata; + if(!SetupDiEnumDeviceInfo(devset, devidx, &devdata)) { + if(GetLastError() == ERROR_NO_MORE_ITEMS) break; + devidx++; + continue; + } + + regtype = SPDRP_PHYSICAL_DEVICE_OBJECT_NAME; + SetupDiGetDeviceRegistryProperty(devset, &devdata, SPDRP_FRIENDLYNAME, + ®type, (unsigned char*)devname, sizeof devname, &size); + + count = 0; + ifidx = 0; + for(;;) { + memset(&devif, 0, sizeof devif); + devif.cbSize = sizeof devif; + if(!SetupDiEnumDeviceInterfaces(devset, &devdata, &guid_iface_disk, ifidx, &devif)) { + if(GetLastError() == ERROR_NO_MORE_ITEMS) break; + ifidx++; + continue; + } + + SetupDiGetDeviceInterfaceDetail(devset, &devif, 0, 0, &size, 0); + if(!(devdetail = malloc(size))) { + fprintf(stderr, "failed to allocate device interface detail buffer (size: %lu)\n", (unsigned long)size); + return -1; + } + devdetail->cbSize = sizeof *devdetail; + SetupDiGetDeviceInterfaceDetail(devset, &devif, devdetail, size, 0, 0); + + + if(count < max_disks) { + disks[count].path = strdup(devdetail->DevicePath); + disks[count].name = strdup(devname); + if(!disks[count].path || !disks[count].name) { + fprintf(stderr, "failed to allocate device strings\n"); + return -1; + } + count++; + } + + free(devdetail); + ifidx++; + } + + devidx++; + } + + return count; +}