1 /* CCKDCDSK.C (c) Copyright Greg Smith, 2000-2009 */
2 /* Perform chkdsk for Compressed CKD DASD file */
3
4 /*-------------------------------------------------------------------*/
5 /* Perform check function on a compressed ckd file */
6 /*-------------------------------------------------------------------*/
7
8 #include "hstdinc.h"
9
10 #include "hercules.h"
11
12 int syntax ();
13
14 /*-------------------------------------------------------------------*/
15 /* Main function for stand-alone chkdsk */
16 /*-------------------------------------------------------------------*/
main(int argc,char * argv[])17 int main (int argc, char *argv[])
18 {
19 int i; /* Index */
20 int rc; /* Return code */
21 int level=1; /* Chkdsk level checking */
22 int ro=0; /* 1=Open readonly */
23 int force=0; /* 1=Check if OPENED bit on */
24 CCKDDASD_DEVHDR cdevhdr; /* Compressed CKD device hdr */
25 DEVBLK devblk; /* DEVBLK */
26 DEVBLK *dev=&devblk; /* -> DEVBLK */
27
28 INITIALIZE_UTILITY("cckdcdsk");
29
30 /* parse the arguments */
31 for (argc--, argv++ ; argc > 0 ; argc--, argv++)
32 {
33 if(**argv != '-') break;
34
35 switch(argv[0][1])
36 {
37 case '0':
38 case '1':
39 case '2':
40 case '3':
41 case '4': if (argv[0][2] != '\0') return syntax ();
42 level = (argv[0][1] & 0xf);
43 break;
44 case 'f': if (argv[0][2] != '\0') return syntax ();
45 force = 1;
46 break;
47 case 'r': if (argv[0][2] == 'o' && argv[0][3] == '\0')
48 ro = 1;
49 else return syntax ();
50 break;
51 case 'v': if (argv[0][2] != '\0') return syntax ();
52 display_version
53 (stderr, "Hercules cckd chkdsk program ", FALSE);
54 return 0;
55 default: return syntax ();
56 }
57 }
58
59 if (argc < 1) return syntax ();
60
61 for (i = 0; i < argc; i++)
62 {
63 memset (dev, 0, sizeof(DEVBLK));
64 dev->batch = 1;
65
66 /* open the file */
67 hostpath(dev->filename, argv[i], sizeof(dev->filename));
68 dev->fd = hopen(dev->filename, ro ? O_RDONLY|O_BINARY : O_RDWR|O_BINARY);
69 if (dev->fd < 0)
70 {
71 cckdumsg (dev, 700, "open error: %s\n", strerror(errno));
72 continue;
73 }
74
75 /* Check CCKD_OPENED bit if -f not specified */
76 if (!force)
77 {
78 if (lseek (dev->fd, CCKD_DEVHDR_POS, SEEK_SET) < 0)
79 {
80 cckdumsg (dev, 702, "lseek error offset 0x%" I64_FMT "x: %s\n",
81 (long long)CCKD_DEVHDR_POS, strerror(errno));
82 close (dev->fd);
83 continue;
84 }
85 if ((rc = read (dev->fd, &cdevhdr, CCKD_DEVHDR_SIZE)) < CCKD_DEVHDR_SIZE)
86 {
87 cckdumsg (dev, 703, "read error rc=%d offset 0x%" I64_FMT "x len %d: %s\n",
88 rc, (long long)CCKD_DEVHDR_POS, CCKD_DEVHDR_SIZE,
89 rc < 0 ? strerror(errno) : "incomplete");
90 close (dev->fd);
91 continue;
92 }
93 if (cdevhdr.options & CCKD_OPENED)
94 {
95 cckdumsg (dev, 707, "OPENED bit is on, use -f\n");
96 close (dev->fd);
97 continue;
98 }
99 } /* if (!force) */
100
101 rc = cckd_chkdsk (dev, level);
102
103 close (dev->fd);
104 } /* for each arg */
105
106 return 0;
107 }
108
109 /*-------------------------------------------------------------------*/
110 /* print syntax */
111 /*-------------------------------------------------------------------*/
syntax()112 int syntax()
113 {
114 fprintf (stderr, _("\ncckdcdsk [-v] [-f] [-level] [-ro] file1 [file2 ...]\n"
115 "\n"
116 " -v display version and exit\n"
117 "\n"
118 " -f force check even if OPENED bit is on\n"
119 "\n"
120 " level is a digit 0 - 4:\n"
121 " -0 -- minimal checking (hdr, chdr, l1tab, l2tabs)\n"
122 " -1 -- normal checking (hdr, chdr, l1tab, l2tabs, free spaces)\n"
123 " -2 -- extra checking (hdr, chdr, l1tab, l2tabs, free spaces, trkhdrs)\n"
124 " -3 -- maximal checking (hdr, chdr, l1tab, l2tabs, free spaces, trkimgs)\n"
125 " -4 -- recover everything without using meta-data\n"
126 "\n"
127 " -ro open file readonly, no repairs\n"
128 "\n"));
129 return -1;
130 }
131