14007Sjoerg/* 287992Sjoerg * Copyright (C) 1994, 2001 by Joerg Wunsch, Dresden 34007Sjoerg * All rights reserved. 44007Sjoerg * 54007Sjoerg * Redistribution and use in source and binary forms, with or without 64007Sjoerg * modification, are permitted provided that the following conditions 74007Sjoerg * are met: 84007Sjoerg * 1. Redistributions of source code must retain the above copyright 94007Sjoerg * notice, this list of conditions and the following disclaimer. 104007Sjoerg * 2. Redistributions in binary form must reproduce the above copyright 114007Sjoerg * notice, this list of conditions and the following disclaimer in the 124007Sjoerg * documentation and/or other materials provided with the distribution. 134007Sjoerg * 144007Sjoerg * THIS SOFTWARE IS PROVIDED BY THE AUTHOR(S) ``AS IS'' AND ANY 154007Sjoerg * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 164007Sjoerg * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 174007Sjoerg * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE 184007Sjoerg * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 194007Sjoerg * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT 204007Sjoerg * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR 214007Sjoerg * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 224007Sjoerg * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 234007Sjoerg * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE 244007Sjoerg * USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH 254007Sjoerg * DAMAGE. 264007Sjoerg */ 274007Sjoerg 28114601Sobrien#include <sys/cdefs.h> 29114601Sobrien__FBSDID("$FreeBSD$"); 3029530Scharnier 3178855Sdd#include <sys/fdcio.h> 3278855Sdd#include <sys/file.h> 3378855Sdd 3429530Scharnier#include <err.h> 354007Sjoerg#include <stdio.h> 364007Sjoerg#include <stdlib.h> 3787992Sjoerg#include <string.h> 3887992Sjoerg#include <sysexits.h> 3923716Speter#include <unistd.h> 404007Sjoerg 4187992Sjoerg#include "fdutil.h" 4278855Sdd 438857Srgrimes 44134081Sphkstatic int format, verbose, show = 1, showfmt; 4587992Sjoergstatic char *fmtstring; 464007Sjoerg 4787992Sjoergstatic void showdev(enum fd_drivetype, const char *); 4887992Sjoergstatic void usage(void); 494007Sjoerg 5078855Sddstatic void 514007Sjoergusage(void) 524007Sjoerg{ 5387992Sjoerg errx(EX_USAGE, 5487992Sjoerg "usage: fdcontrol [-F] [-d dbg] [-f fmt] [-s fmtstr] [-v] device"); 554007Sjoerg} 564007Sjoerg 5787992Sjoergvoid 5887992Sjoergshowdev(enum fd_drivetype type, const char *fname) 5987992Sjoerg{ 6087992Sjoerg const char *name, *descr; 614007Sjoerg 6287992Sjoerg getname(type, &name, &descr); 6387992Sjoerg if (verbose) 6487992Sjoerg printf("%s: %s drive (%s)\n", fname, name, descr); 6587992Sjoerg else 6687992Sjoerg printf("%s\n", name); 6787992Sjoerg} 684007Sjoerg 694007Sjoergint 704007Sjoergmain(int argc, char **argv) 714007Sjoerg{ 7287992Sjoerg enum fd_drivetype type; 7387992Sjoerg struct fd_type ft, newft, *fdtp; 7487992Sjoerg const char *name, *descr; 75194892Sjoerg int fd, i, autofmt; 764007Sjoerg 77134081Sphk autofmt = 0; 78134081Sphk while((i = getopt(argc, argv, "aFf:s:v")) != -1) 7987992Sjoerg switch(i) { 808857Srgrimes 81134081Sphk case 'a': 82134081Sphk autofmt = 1; 8387992Sjoerg case 'F': 8487992Sjoerg showfmt = 1; 8587992Sjoerg show = 0; 8687992Sjoerg break; 878857Srgrimes 8887992Sjoerg case 'f': 89126231Sphk if (!strcmp(optarg, "auto")) { 90126231Sphk format = -1; 91126231Sphk } else if (getnum(optarg, &format)) { 9287992Sjoerg fprintf(stderr, 9387992Sjoerg "Bad argument %s to -f option; must be numeric\n", 9487992Sjoerg optarg); 9587992Sjoerg usage(); 9687992Sjoerg } 9787992Sjoerg show = 0; 9887992Sjoerg break; 998857Srgrimes 10087992Sjoerg case 's': 10187992Sjoerg fmtstring = optarg; 10287992Sjoerg show = 0; 10387992Sjoerg break; 1044007Sjoerg 10587992Sjoerg case 'v': 10687992Sjoerg verbose++; 10787992Sjoerg break; 1088857Srgrimes 10987992Sjoerg default: 11087992Sjoerg usage(); 11187992Sjoerg } 1124007Sjoerg 11387992Sjoerg argc -= optind; 11487992Sjoerg argv += optind; 11587992Sjoerg 11687992Sjoerg if(argc != 1) 11787992Sjoerg usage(); 11887992Sjoerg 119194892Sjoerg if((fd = open(argv[0], O_RDONLY | O_NONBLOCK)) < 0) 12087992Sjoerg err(EX_UNAVAILABLE, "open(%s)", argv[0]); 12187992Sjoerg 12287992Sjoerg if (ioctl(fd, FD_GDTYPE, &type) == -1) 12387992Sjoerg err(EX_OSERR, "ioctl(FD_GDTYPE)"); 12487992Sjoerg if (ioctl(fd, FD_GTYPE, &ft) == -1) 12587992Sjoerg err(EX_OSERR, "ioctl(FD_GTYPE)"); 12687992Sjoerg 12787992Sjoerg if (show) { 12887992Sjoerg showdev(type, argv[0]); 12987992Sjoerg return (0); 1304007Sjoerg } 1318857Srgrimes 132134081Sphk if (autofmt) { 133134081Sphk memset(&newft, 0, sizeof newft); 134134081Sphk ft = newft; 135134081Sphk } 136134081Sphk 13787992Sjoerg if (format) { 13887992Sjoerg getname(type, &name, &descr); 13987992Sjoerg fdtp = get_fmt(format, type); 14087992Sjoerg if (fdtp == 0) 14187992Sjoerg errx(EX_USAGE, 14287992Sjoerg "unknown format %d KB for drive type %s", 14387992Sjoerg format, name); 14487992Sjoerg ft = *fdtp; 1454007Sjoerg } 1464007Sjoerg 14787992Sjoerg if (fmtstring) { 14887992Sjoerg parse_fmt(fmtstring, type, ft, &newft); 14987992Sjoerg ft = newft; 15087992Sjoerg } 1514007Sjoerg 15287992Sjoerg if (showfmt) { 153126231Sphk if (verbose) { 154139905Sdelphij const char *s; 155126231Sphk 156126231Sphk printf("%s: %d KB media type\n", argv[0], 157126231Sphk (128 << ft.secsize) * ft.size / 1024); 158126231Sphk printf("\tFormat:\t\t"); 159126231Sphk print_fmt(ft); 160126231Sphk if (ft.datalen != 0xff && 161126231Sphk ft.datalen != (128 << ft.secsize)) 162126231Sphk printf("\tData length:\t%d\n", ft.datalen); 163126231Sphk printf("\tSector size:\t%d\n", 128 << ft.secsize); 164126231Sphk printf("\tSectors/track:\t%d\n", ft.sectrac); 165126231Sphk printf("\tHeads/cylinder:\t%d\n", ft.heads); 166126231Sphk printf("\tCylinders/disk:\t%d\n", ft.tracks); 167126231Sphk switch (ft.trans) { 168126231Sphk case 0: printf("\tTransfer rate:\t500 kbps\n"); break; 169126231Sphk case 1: printf("\tTransfer rate:\t300 kbps\n"); break; 170126231Sphk case 2: printf("\tTransfer rate:\t250 kbps\n"); break; 171126231Sphk case 3: printf("\tTransfer rate:\t1 Mbps\n"); break; 172126231Sphk } 173126231Sphk printf("\tSector gap:\t%d\n", ft.gap); 174126231Sphk printf("\tFormat gap:\t%d\n", ft.f_gap); 175126231Sphk printf("\tInterleave:\t%d\n", ft.f_inter); 176126231Sphk printf("\tSide offset:\t%d\n", ft.offset_side2); 177126231Sphk printf("\tFlags\t\t<"); 178126231Sphk s = ""; 179126231Sphk if (ft.flags & FL_MFM) { 180126231Sphk printf("%sMFM", s); 181126231Sphk s = ","; 182126231Sphk } 183126231Sphk if (ft.flags & FL_2STEP) { 184126231Sphk printf("%s2STEP", s); 185126231Sphk s = ","; 186126231Sphk } 187126231Sphk if (ft.flags & FL_PERPND) { 188126231Sphk printf("%sPERPENDICULAR", s); 189126231Sphk s = ","; 190126231Sphk } 191134081Sphk if (ft.flags & FL_AUTO) { 192134081Sphk printf("%sAUTO", s); 193134081Sphk s = ","; 194134081Sphk } 195126231Sphk printf(">\n"); 196126231Sphk } else { 197126231Sphk print_fmt(ft); 198126231Sphk } 19987992Sjoerg return (0); 2004007Sjoerg } 2018857Srgrimes 20287992Sjoerg if (format || fmtstring) { 20387992Sjoerg if (ioctl(fd, FD_STYPE, &ft) == -1) 20487992Sjoerg err(EX_OSERR, "ioctl(FD_STYPE)"); 20587992Sjoerg return (0); 20687992Sjoerg } 20787992Sjoerg 20887992Sjoerg return 0; 2094007Sjoerg} 210