]> git.neil.brown.name Git - mdadm.git/blob - Query.c
Stop: drop any partitions that may be associated with an array when stopping it.
[mdadm.git] / Query.c
1 /*
2  * mdadm - manage Linux "md" devices aka RAID arrays.
3  *
4  * Copyright (C) 2002-2006 Neil Brown <neilb@suse.de>
5  *
6  *
7  *    This program is free software; you can redistribute it and/or modify
8  *    it under the terms of the GNU General Public License as published by
9  *    the Free Software Foundation; either version 2 of the License, or
10  *    (at your option) any later version.
11  *
12  *    This program is distributed in the hope that it will be useful,
13  *    but WITHOUT ANY WARRANTY; without even the implied warranty of
14  *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  *    GNU General Public License for more details.
16  *
17  *    You should have received a copy of the GNU General Public License
18  *    along with this program; if not, write to the Free Software
19  *    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
20  *
21  *    Author: Neil Brown
22  *    Email: <neilb@cse.unsw.edu.au>
23  *    Paper: Neil Brown
24  *           School of Computer Science and Engineering
25  *           The University of New South Wales
26  *           Sydney, 2052
27  *           Australia
28  */
29
30 #include        "mdadm.h"
31 #include        "md_p.h"
32 #include        "md_u.h"
33
34 int Query(char *dev)
35 {
36         /* Give a brief description of the device,
37          * whether it is an md device and whether it has
38          * a superblock
39          */
40         int fd = open(dev, O_RDONLY);
41         int vers;
42         int ioctlerr;
43         int superror, superrno;
44         struct mdinfo info;
45         mdu_array_info_t array;
46         struct supertype *st = NULL;
47
48         unsigned long long larray_size;
49         struct stat stb;
50         char *mddev;
51         mdu_disk_info_t disc;
52         char *activity;
53
54         if (fd < 0){
55                 fprintf(stderr, Name ": cannot open %s: %s\n",
56                         dev, strerror(errno));
57                 return 1;
58         }
59
60         vers = md_get_version(fd);
61         if (ioctl(fd, GET_ARRAY_INFO, &array)<0)
62                 ioctlerr = errno;
63         else ioctlerr = 0;
64
65         fstat(fd, &stb);
66
67         if (vers>=9000 && !ioctlerr) {
68                 if (!get_dev_size(fd, NULL, &larray_size))
69                         larray_size = 0;
70         }
71
72         if (vers < 0)
73                 printf("%s: is not an md array\n", dev);
74         else if (vers < 9000)
75                 printf("%s: is an md device, but kernel cannot provide details\n", dev);
76         else if (ioctlerr == ENODEV)
77                 printf("%s: is an md device which is not active\n", dev);
78         else if (ioctlerr)
79                 printf("%s: is an md device, but gives \"%s\" when queried\n",
80                        dev, strerror(ioctlerr));
81         else {
82                 printf("%s: %s %s %d devices, %d spare%s. Use mdadm --detail for more detail.\n",
83                        dev,
84                        human_size_brief(larray_size),
85                        map_num(pers, array.level),
86                        array.raid_disks,
87                        array.spare_disks, array.spare_disks==1?"":"s");
88         }
89         st = guess_super(fd);
90         if (st) {
91                 superror = st->ss->load_super(st, fd, dev);
92                 superrno = errno;
93         } else
94                 superror = -1;
95         close(fd);
96         if (superror == 0) {
97                 /* array might be active... */
98                 st->ss->getinfo_super(st, &info);
99                 if (st->ss == &super0) {
100                         mddev = get_md_name(info.array.md_minor);
101                         disc.number = info.disk.number;
102                         activity = "undetected";
103                         if (mddev && (fd = open(mddev, O_RDONLY))>=0) {
104                                 if (md_get_version(fd) >= 9000 &&
105                                     ioctl(fd, GET_ARRAY_INFO, &array)>= 0) {
106                                         if (ioctl(fd, GET_DISK_INFO, &disc) >= 0 &&
107                                             makedev((unsigned)disc.major,(unsigned)disc.minor) == stb.st_rdev)
108                                                 activity = "active";
109                                         else
110                                                 activity = "mismatch";
111                                 }
112                                 close(fd);
113                         }
114                 } else {
115                         activity = "unknown";
116                         mddev = "array";
117                 }
118                 printf("%s: device %d in %d device %s %s %s.  Use mdadm --examine for more detail.\n",
119                        dev,
120                        info.disk.number, info.array.raid_disks,
121                        activity,
122                        map_num(pers, info.array.level),
123                        mddev);
124                 if (st->ss == &super0)
125                         put_md_name(mddev);
126         }
127         return 0;
128 }
129