]>
Commit | Line | Data |
---|---|---|
832b75ed | 1 | /* |
4d59bff9 | 2 | * knowndrives.cpp |
832b75ed GG |
3 | * |
4 | * Home page of code is: http://smartmontools.sourceforge.net | |
5 | * Address of support mailing list: smartmontools-support@lists.sourceforge.net | |
6 | * | |
2127e193 GI |
7 | * Copyright (C) 2003-9 Philip Williams, Bruce Allen |
8 | * Copyright (C) 2008-9 Christian Franke <smartmontools-support@lists.sourceforge.net> | |
832b75ed GG |
9 | * |
10 | * This program is free software; you can redistribute it and/or modify | |
11 | * it under the terms of the GNU General Public License as published by | |
12 | * the Free Software Foundation; either version 2, or (at your option) | |
13 | * any later version. | |
14 | * | |
15 | * You should have received a copy of the GNU General Public License | |
16 | * (for example COPYING); if not, write to the Free | |
17 | * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |
18 | * | |
19 | */ | |
20 | ||
21 | #include "config.h" | |
22 | #include "int64.h" | |
23 | #include <stdio.h> | |
24 | #include "atacmds.h" | |
832b75ed GG |
25 | #include "extern.h" |
26 | #include "knowndrives.h" | |
2127e193 | 27 | #include "utility.h" |
832b75ed | 28 | |
2127e193 GI |
29 | #ifdef HAVE_UNISTD_H |
30 | #include <unistd.h> | |
31 | #endif | |
32 | #ifdef _WIN32 | |
33 | #include <io.h> // access() | |
34 | #endif | |
35 | ||
36 | #include <stdexcept> | |
37 | ||
bed94269 | 38 | const char *knowndrives_c_cvsid="$Id: knowndrives.cpp 2986 2009-11-16 22:43:50Z manfred99 $" |
2127e193 | 39 | ATACMDS_H_CVSID CONFIG_H_CVSID EXTERN_H_CVSID INT64_H_CVSID KNOWNDRIVES_H_CVSID UTILITY_H_CVSID; |
832b75ed GG |
40 | |
41 | #define MODEL_STRING_LENGTH 40 | |
42 | #define FIRMWARE_STRING_LENGTH 8 | |
43 | #define TABLEPRINTWIDTH 19 | |
44 | ||
832b75ed GG |
45 | |
46 | /* Table of settings for known drives terminated by an element containing all | |
47 | * zeros. The drivesettings structure is described in knowndrives.h. Note | |
48 | * that lookupdrive() will search knowndrives[] from the start to end or | |
49 | * until it finds the first match, so the order in knowndrives[] is important | |
50 | * for distinct entries that could match the same drive. */ | |
51 | ||
52 | // Note that the table just below uses EXTENDED REGULAR EXPRESSIONS. | |
53 | // A good on-line reference for these is: | |
54 | // http://www.zeus.com/extra/docsystem/docroot/apps/web/docs/modules/access/regex.html | |
55 | ||
2127e193 GI |
56 | // Starting with CVS version 1.179 of this file, the regular expressions |
57 | // for drive model and firmware must match the full string. The effect of | |
58 | // "^FULLSTRING$" is identical to "FULLSTRING". The special characters '^' | |
59 | // and '$' are no longer required, but still allowed. The form ".*SUBSTRING.*" | |
60 | // can be used if substring match is desired. | |
61 | ||
62 | static const drive_settings builtin_knowndrives[] = { | |
63 | // BEGIN drivedb.h (DO NOT DELETE - used by Makefile) | |
64 | { "Apple SSD SM128", | |
65 | "APPLE SSD SM128", | |
66 | "", "", "" | |
67 | }, | |
68 | { "Asus-Phison SSD", | |
69 | "ASUS-PHISON SSD", | |
70 | "", "", "" | |
71 | }, | |
72 | { "OCZ Vertex SSD", | |
bed94269 GI |
73 | "OCZ[ -]VERTEX.*", |
74 | "", "", | |
75 | " -v 9,raw64" | |
76 | " -v 12,raw64" | |
77 | " -v 184,raw64,Initial_Bad_Block_Count" | |
78 | " -v 195,raw64,Program_Failure_Blk_Ct" | |
79 | " -v 196,raw64,Erase_Failure_Blk_Ct" | |
80 | " -v 197,raw64,Read_Failure_Blk_Ct" | |
81 | " -v 198,raw64,Read_Sectors_Tot_Ct" | |
82 | " -v 199,raw64,Write_Sectors_Tot_Ct" | |
83 | " -v 200,raw64,Read_Commands_Tot_Ct" | |
84 | " -v 201,raw64,Write_Commands_Tot_Ct" | |
85 | " -v 202,raw64,Error_Bits_Flash_Tot_Ct" | |
86 | " -v 203,raw64,Corr_Read_Errors_Tot_Ct" | |
87 | " -v 204,raw64,Bad_Block_Full_Flag" | |
88 | " -v 205,raw64,Max_PE_Count_Spec" | |
89 | " -v 206,raw64,Min_Erase_Count" | |
90 | " -v 207,raw64,Max_Erase_Count" | |
91 | " -v 208,raw64,Average_Erase_Count" | |
92 | " -v 209,raw64,Remaining_Lifetime_Perc" | |
93 | }, | |
94 | { "OCZ Agility SSD", | |
95 | "OCZ[ -]AGILITY", | |
96 | "", "", | |
97 | " -v 9,raw64" | |
98 | " -v 12,raw64" | |
99 | " -v 184,raw64,Initial_Bad_Block_Count" | |
100 | " -v 195,raw64,Program_Failure_Blk_Ct" | |
101 | " -v 196,raw64,Erase_Failure_Blk_Ct" | |
102 | " -v 197,raw64,Read_Failure_Blk_Ct" | |
103 | " -v 198,raw64,Read_Sectors_Tot_Ct" | |
104 | " -v 199,raw64,Write_Sectors_Tot_Ct" | |
105 | " -v 200,raw64,Read_Commands_Tot_Ct" | |
106 | " -v 201,raw64,Write_Commands_Tot_Ct" | |
107 | " -v 202,raw64,Error_Bits_Flash_Tot_Ct" | |
108 | " -v 203,raw64,Corr_Read_Errors_Tot_Ct" | |
109 | " -v 204,raw64,Bad_Block_Full_Flag" | |
110 | " -v 205,raw64,Max_PE_Count_Spec" | |
111 | " -v 206,raw64,Min_Erase_Count" | |
112 | " -v 207,raw64,Max_Erase_Count" | |
113 | " -v 208,raw64,Average_Erase_Count" | |
114 | " -v 209,raw64,Remaining_Lifetime_Perc" | |
115 | }, | |
116 | { "Intel X25-E SSD", | |
117 | "SSDSA2SH(032|064)G1.* INTEL", | |
118 | "", "", | |
119 | "-v 225,raw48,Host_Writes_Count" | |
2127e193 GI |
120 | }, |
121 | { "Transcend Solid-State Drive", | |
122 | "TS(8|16|32|64|128)GSSD25-(M|S)", | |
123 | "", "", "" | |
124 | }, | |
125 | { "Transcend Solid-State Drive V series", | |
126 | "TS(8|16|32|64|128|192)GSSD25S-(M|S)", | |
127 | "", "", "" | |
128 | }, | |
129 | { "Marvell SSD SD88SA024BA0 (SUN branded)", | |
130 | "MARVELL SD88SA024BA0 SUN24G 0902M0054V", | |
131 | "", "", "" | |
132 | }, | |
133 | { "HP 1TB SATA disk GB1000EAFJL", | |
134 | "GB1000EAFJL", | |
135 | "", "", "" | |
136 | }, | |
832b75ed | 137 | { "IBM Deskstar 60GXP series", // ER60A46A firmware |
2127e193 GI |
138 | "(IBM-|Hitachi )?IC35L0[12346]0AVER07.*", |
139 | "ER60A46A", | |
140 | "", "" | |
832b75ed GG |
141 | }, |
142 | { "IBM Deskstar 60GXP series", // All other firmware | |
2127e193 GI |
143 | "(IBM-|Hitachi )?IC35L0[12346]0AVER07.*", |
144 | "", | |
832b75ed GG |
145 | "IBM Deskstar 60GXP drives may need upgraded SMART firmware.\n" |
146 | "Please see http://www.geocities.com/dtla_update/index.html#rel and\n" | |
bed94269 | 147 | "http://www.ibm.com/pc/support/site.wss/MIGR-42215.html", |
2127e193 | 148 | "" |
832b75ed GG |
149 | }, |
150 | { "IBM Deskstar 40GV & 75GXP series (A5AA/A6AA firmware)", | |
2127e193 GI |
151 | "(IBM-)?DTLA-30[57]0[123467][05].*", |
152 | "T[WX][123468AG][OF]A[56]AA", | |
153 | "", "" | |
832b75ed GG |
154 | }, |
155 | { "IBM Deskstar 40GV & 75GXP series (all other firmware)", | |
2127e193 GI |
156 | "(IBM-)?DTLA-30[57]0[123467][05].*", |
157 | "", | |
832b75ed GG |
158 | "IBM Deskstar 40GV and 75GXP drives may need upgraded SMART firmware.\n" |
159 | "Please see http://www.geocities.com/dtla_update/ and\n" | |
bed94269 | 160 | "http://www.ibm.com/pc/support/site.wss/MIGR-42215.html", |
2127e193 | 161 | "" |
832b75ed | 162 | }, |
2127e193 GI |
163 | { "", // ExcelStor J240, J340, J360, J680, and J880 |
164 | "ExcelStor Technology J(24|34|36|68|88)0", | |
165 | "", "", "" | |
832b75ed | 166 | }, |
2127e193 GI |
167 | { "", // Fujitsu M1623TAU |
168 | "FUJITSU M1623TAU", | |
169 | "", | |
170 | "", | |
171 | "-v 9,seconds" | |
832b75ed | 172 | }, |
ba59cff1 | 173 | { "Fujitsu MHG series", |
2127e193 GI |
174 | "FUJITSU MHG2...ATU?.*", |
175 | "", | |
176 | "", | |
177 | "-v 9,seconds" | |
832b75ed | 178 | }, |
ba59cff1 | 179 | { "Fujitsu MHH series", |
2127e193 GI |
180 | "FUJITSU MHH2...ATU?.*", |
181 | "", | |
182 | "", | |
183 | "-v 9,seconds" | |
832b75ed | 184 | }, |
ba59cff1 | 185 | { "Fujitsu MHJ series", |
2127e193 GI |
186 | "FUJITSU MHJ2...ATU?.*", |
187 | "", | |
188 | "", | |
189 | "-v 9,seconds" | |
ba59cff1 GG |
190 | }, |
191 | { "Fujitsu MHK series", | |
2127e193 GI |
192 | "FUJITSU MHK2...ATU?.*", |
193 | "", | |
194 | "", | |
195 | "-v 9,seconds" | |
196 | }, | |
197 | { "", // Fujitsu MHL2300AT | |
198 | "FUJITSU MHL2300AT", | |
199 | "", | |
ba59cff1 GG |
200 | "This drive's firmware has a harmless Drive Identity Structure\n" |
201 | "checksum error bug.", | |
2127e193 | 202 | "-v 9,seconds" |
ba59cff1 | 203 | }, |
2127e193 GI |
204 | { "", // MHM2200AT, MHM2150AT, MHM2100AT, MHM2060AT |
205 | "FUJITSU MHM2(20|15|10|06)0AT", | |
206 | "", | |
ba59cff1 GG |
207 | "This drive's firmware has a harmless Drive Identity Structure\n" |
208 | "checksum error bug.", | |
2127e193 | 209 | "-v 9,seconds" |
ba59cff1 GG |
210 | }, |
211 | { "Fujitsu MHN series", | |
2127e193 GI |
212 | "FUJITSU MHN2...AT", |
213 | "", | |
214 | "", | |
215 | "-v 9,seconds" | |
216 | }, | |
217 | { "", // Fujitsu MHR2020AT | |
218 | "FUJITSU MHR2020AT", | |
219 | "", | |
220 | "", | |
221 | "-v 9,seconds" | |
222 | }, | |
223 | { "", // Fujitsu MHR2040AT | |
224 | "FUJITSU MHR2040AT", | |
225 | "", // Tested on 40BA | |
226 | "", | |
227 | "-v 9,seconds -v 192,emergencyretractcyclect " | |
228 | "-v 198,offlinescanuncsectorct -v 200,writeerrorcount" | |
ba59cff1 | 229 | }, |
832b75ed | 230 | { "Fujitsu MHSxxxxAT family", |
2127e193 GI |
231 | "FUJITSU MHS20[6432]0AT( .)?", |
232 | "", | |
233 | "", | |
234 | "-v 9,seconds -v 192,emergencyretractcyclect " | |
235 | "-v 198,offlinescanuncsectorct -v 200,writeerrorcount " | |
236 | "-v 201,detectedtacount" | |
832b75ed | 237 | }, |
ba59cff1 | 238 | { "Fujitsu MHT series", |
2127e193 GI |
239 | "FUJITSU MHT2...(AH|AS|AT|BH)U?.*", |
240 | "", | |
241 | "", | |
242 | "-v 9,seconds" | |
ba59cff1 GG |
243 | }, |
244 | { "Fujitsu MHU series", | |
2127e193 GI |
245 | "FUJITSU MHU2...ATU?.*", |
246 | "", | |
247 | "", | |
248 | "-v 9,seconds" | |
ba59cff1 GG |
249 | }, |
250 | { "Fujitsu MHV series", | |
2127e193 GI |
251 | "FUJITSU MHV2...(AH|AS|AT|BH|BS|BT).*", |
252 | "", | |
253 | "", | |
254 | "-v 9,seconds" | |
832b75ed | 255 | }, |
4d59bff9 | 256 | { "Fujitsu MPA..MPG series", |
2127e193 GI |
257 | "FUJITSU MP[A-G]3...A[HTEV]U?.*", |
258 | "", | |
259 | "", | |
260 | "-v 9,seconds" | |
261 | }, | |
262 | { "Fujitsu MHY2 BH series", | |
263 | "FUJITSU MHY2(04|06|08|10|12|16|20|25)0BH.*", | |
bed94269 GI |
264 | "", "", |
265 | "-v 240,raw48,Transfer_Error_Rate" | |
2127e193 GI |
266 | }, |
267 | { "Fujitsu MHW2 BH series", | |
268 | "FUJITSU MHW2(04|06|08|10|12|16)0BH.*", | |
269 | "", "", "" | |
270 | }, | |
271 | { "Fujitsu MHW2 BJ series", | |
272 | "FUJITSU MHW2(08|12|16)0BJ.*", | |
273 | "", "", "" | |
274 | }, | |
275 | { "Fujitsu MHZ2 BH series", | |
276 | "FUJITSU MHZ2(04|08|12|16|20|25|32)0BH.*", | |
277 | "", "", "" | |
278 | }, | |
279 | { "Fujitsu MHZ2 BJ series", | |
280 | "FUJITSU MHZ2(08|12|16|20|25|32)0BJ.*", | |
281 | "", | |
282 | "", | |
283 | "-v 9,minutes" | |
284 | }, | |
285 | { "Fujitsu MHZ2 BS series", | |
286 | "FUJITSU MHZ2(12|25)0BS.*", | |
287 | "", "", "" | |
288 | }, | |
289 | { "", // Samsung SV4012H (known firmware) | |
290 | "SAMSUNG SV4012H", | |
291 | "RM100-08", | |
292 | "", | |
293 | "-v 9,halfminutes -F samsung" | |
294 | }, | |
295 | { "", // Samsung SV4012H (all other firmware) | |
296 | "SAMSUNG SV4012H", | |
297 | "", | |
298 | "May need -F samsung disabled; see manual for details.", | |
299 | "-v 9,halfminutes -F samsung" | |
300 | }, | |
301 | { "", // Samsung SV0412H (known firmware) | |
302 | "SAMSUNG SV0412H", | |
303 | "SK100-01", | |
304 | "", | |
305 | "-v 9,halfminutes -v 194,10xCelsius -F samsung" | |
306 | }, | |
307 | { "", // Samsung SV0412H (all other firmware) | |
308 | "SAMSUNG SV0412H", | |
309 | "", | |
310 | "May need -F samsung disabled; see manual for details.", | |
311 | "-v 9,halfminutes -v 194,10xCelsius -F samsung" | |
312 | }, | |
313 | { "", // Samsung SV1204H (known firmware) | |
314 | "SAMSUNG SV1204H", | |
315 | "RK100-1[3-5]", | |
316 | "", | |
317 | "-v 9,halfminutes -v 194,10xCelsius -F samsung" | |
318 | }, | |
319 | { "", // Samsung SV1204H (all other firmware) | |
320 | "SAMSUNG SV1204H", | |
321 | "", | |
322 | "May need -F samsung disabled; see manual for details.", | |
323 | "-v 9,halfminutes -v 194,10xCelsius -F samsung" | |
324 | }, | |
325 | { "", // SAMSUNG SV0322A tested with FW JK200-35 | |
326 | "SAMSUNG SV0322A", | |
327 | "", "", "" | |
328 | }, | |
329 | { "", // SAMSUNG SP40A2H with RR100-07 firmware | |
330 | "SAMSUNG SP40A2H", | |
331 | "RR100-07", | |
332 | "", | |
333 | "-v 9,halfminutes -F samsung" | |
334 | }, | |
335 | { "", // SAMSUNG SP80A4H with RT100-06 firmware | |
336 | "SAMSUNG SP80A4H", | |
337 | "RT100-06", | |
338 | "", | |
339 | "-v 9,halfminutes -F samsung" | |
340 | }, | |
341 | { "", // SAMSUNG SP8004H with QW100-61 firmware | |
342 | "SAMSUNG SP8004H", | |
343 | "QW100-61", | |
344 | "", | |
345 | "-v 9,halfminutes -F samsung" | |
346 | }, | |
347 | { "SAMSUNG SpinPoint F1 DT series", // tested with HD103UJ/1AA01113 | |
348 | "SAMSUNG HD(083G|16[12]G|25[12]H|32[12]H|50[12]I|642J|75[23]L|10[23]U)J", | |
349 | "", "", "" | |
350 | }, | |
351 | { "SAMSUNG SpinPoint F1 RE series", // tested with HE103UJ/1AA01113 | |
352 | "SAMSUNG HE(252H|322H|502I|642J|753L|103U)J", | |
353 | "", "", "" | |
354 | }, | |
355 | { "SAMSUNG SpinPoint S250 series", // tested with HD200HJ/KF100-06 | |
356 | "SAMSUNG HD(162|200|250)HJ", | |
357 | "", "", "" | |
ba59cff1 | 358 | }, |
4d59bff9 | 359 | { "SAMSUNG SpinPoint T133 series", // tested with HD300LJ/ZT100-12, HD400LJ/ZZ100-14, HD401LJ/ZZ100-15 |
2127e193 GI |
360 | "SAMSUNG HD(250KD|(30[01]|320|40[01])L[DJ])", |
361 | "", "", "" | |
ba59cff1 | 362 | }, |
a37e7145 | 363 | { "SAMSUNG SpinPoint T166 series", // tested with HD501LJ/CR100-10 |
2127e193 GI |
364 | "SAMSUNG HD(080G|160H|32[01]K|403L|50[01]L)J", |
365 | "", "", "" | |
ba59cff1 | 366 | }, |
a37e7145 | 367 | { "SAMSUNG SpinPoint P120 series", // VF100-37 firmware, tested with SP2514N/VF100-37 |
2127e193 GI |
368 | "SAMSUNG SP(16[01]3|2[05][01]4)[CN]", |
369 | "VF100-37", | |
370 | "", | |
371 | "-F samsung3" | |
a37e7145 GG |
372 | }, |
373 | { "SAMSUNG SpinPoint P120 series", // other firmware, tested with SP2504C/VT100-33 | |
2127e193 GI |
374 | "SAMSUNG SP(16[01]3|2[05][01]4)[CN]", |
375 | "", | |
376 | "May need -F samsung3 enabled; see manual for details.", | |
377 | "" | |
a37e7145 | 378 | }, |
ba59cff1 | 379 | { "SAMSUNG SpinPoint P80 SD series", // tested with HD160JJ/ZM100-33 |
2127e193 GI |
380 | "SAMSUNG HD(080H|120I|160J)J", |
381 | "", "", "" | |
ba59cff1 | 382 | }, |
a37e7145 | 383 | { "SAMSUNG SpinPoint P80 series", // BH100-35 firmware, tested with SP0842N/BH100-35 |
2127e193 GI |
384 | "SAMSUNG SP(0451|08[0124]2|12[0145]3|16[0145]4)[CN]", |
385 | "BH100-35", | |
386 | "", | |
387 | "-F samsung3" | |
a37e7145 GG |
388 | }, |
389 | { "SAMSUNG SpinPoint P80 series", // firmware *-35 or later | |
2127e193 GI |
390 | "SAMSUNG SP(0451|08[0124]2|12[0145]3|16[0145]4)[CN]", |
391 | ".*-3[5-9]", | |
392 | "May need -F samsung3 enabled; see manual for details.", | |
393 | "" | |
a37e7145 | 394 | }, |
1953ff6d | 395 | { "SAMSUNG SpinPoint P80 series", // firmware *-25...34, tested with SP1614C/SW100-25 and -34 |
2127e193 GI |
396 | "SAMSUNG SP(0451|08[0124]2|12[0145]3|16[0145]4)[CN]", |
397 | ".*-(2[5-9]|3[0-4])", | |
398 | "", | |
399 | "-v 9,halfminutes -v 198,increasing" | |
400 | }, | |
401 | { "SAMSUNG SpinPoint P80 series", // firmware *-23...24, tested with | |
402 | // SP0802N/TK100-23, | |
403 | // SP1213N/TL100-23, | |
404 | // SP1604N/TM100-23 and -24 | |
405 | "SAMSUNG SP(0451|08[0124]2|12[0145]3|16[0145]4)[CN]", | |
406 | ".*-2[34]", | |
407 | "", | |
408 | "-v 9,halfminutes -F samsung2" | |
409 | }, | |
410 | { "SAMSUNG SpinPoint P80 series", // unknown firmware | |
411 | "SAMSUNG SP(0451|08[0124]2|12[0145]3|16[0145]4)[CN]", | |
412 | "", | |
413 | "May need -F samsung2 or -F samsung3 enabled; see manual for details.", | |
414 | "" | |
832b75ed | 415 | }, |
2127e193 GI |
416 | /* |
417 | // TODO: Make the entries below more specific. | |
418 | // These entries produce misleading results, because newer | |
419 | // Samsung disks reuse the version numbers *-NN. | |
420 | { "", // All Samsung drives with '.*-25' firmware | |
421 | "SAMSUNG.*", | |
422 | ".*-25", | |
423 | "May need -F samsung2 disabled; see manual for details.", | |
424 | "-v 9,halfminutes -F samsung2" | |
425 | }, | |
426 | { "", // All Samsung drives with '.*-26 or later (currently to -39)' firmware | |
427 | "SAMSUNG.*", | |
428 | ".*-(2[6789]|3[0-9])", | |
429 | "", | |
430 | "-v 9,halfminutes" | |
431 | }, | |
432 | { "", // Samsung ALL OTHER DRIVES | |
433 | "SAMSUNG.*", | |
434 | "", | |
435 | "May need -F samsung or -F samsung2 enabled; see manual for details.", | |
436 | "" | |
437 | }, | |
438 | */ | |
832b75ed | 439 | { "Maxtor Fireball 541DX family", |
2127e193 GI |
440 | "Maxtor 2B0(0[468]|1[05]|20)H1", |
441 | "", | |
442 | "", | |
443 | "-v 9,minutes -v 194,unknown" | |
832b75ed GG |
444 | }, |
445 | { "Maxtor Fireball 3 family", | |
2127e193 GI |
446 | "Maxtor 2F0[234]0[JL]0", |
447 | "", | |
448 | "", | |
449 | "-v 9,minutes" | |
450 | }, | |
451 | { "Maxtor DiamondMax 1280 ATA family", // no self-test log, ATA2-Fast | |
452 | "Maxtor 8(1280A2|2160A4|2560A4|3840A6|4000A6|5120A8)", | |
453 | "", | |
454 | "", | |
455 | "-v 9,minutes" | |
832b75ed GG |
456 | }, |
457 | { "Maxtor DiamondMax 2160 Ultra ATA family", | |
2127e193 GI |
458 | "Maxtor 8(2160D2|3228D3|3240D3|4320D4|6480D6|8400D8|8455D8)", |
459 | "", | |
460 | "", | |
461 | "-v 9,minutes" | |
832b75ed GG |
462 | }, |
463 | { "Maxtor DiamondMax 2880 Ultra ATA family", | |
2127e193 GI |
464 | "Maxtor 9(0510D4|0576D4|0648D5|0720D5|0840D6|0845D6|0864D6|1008D7|1080D8|1152D8)", |
465 | "", | |
466 | "", | |
467 | "-v 9,minutes" | |
832b75ed GG |
468 | }, |
469 | { "Maxtor DiamondMax 3400 Ultra ATA family", | |
2127e193 GI |
470 | "Maxtor 9(1(360|350|202)D8|1190D7|10[12]0D6|0840D5|06[48]0D4|0510D3|1(350|202)E8|1010E6|0840E5|0640E4)", |
471 | "", | |
472 | "", | |
473 | "-v 9,minutes" | |
832b75ed GG |
474 | }, |
475 | { "Maxtor DiamondMax D540X-4G family", | |
2127e193 GI |
476 | "Maxtor 4G(120J6|160J[68])", |
477 | "", | |
478 | "", | |
479 | "-v 9,minutes -v 194,unknown" | |
832b75ed GG |
480 | }, |
481 | { "Maxtor DiamondMax D540X-4K family", | |
2127e193 GI |
482 | "MAXTOR 4K(020H1|040H2|060H3|080H4)", |
483 | "", "", "" | |
832b75ed GG |
484 | }, |
485 | { "Maxtor DiamondMax Plus D740X family", | |
2127e193 GI |
486 | "MAXTOR 6L0(20[JL]1|40[JL]2|60[JL]3|80[JL]4)", |
487 | "", "", "" | |
832b75ed GG |
488 | }, |
489 | { "Maxtor DiamondMax Plus 5120 Ultra ATA 33 family", | |
2127e193 GI |
490 | "Maxtor 9(0512D2|0680D3|0750D3|0913D4|1024D4|1360D6|1536D6|1792D7|2048D8)", |
491 | "", | |
492 | "", | |
493 | "-v 9,minutes" | |
832b75ed GG |
494 | }, |
495 | { "Maxtor DiamondMax Plus 6800 Ultra ATA 66 family", | |
2127e193 GI |
496 | "Maxtor 9(2732U8|2390U7|204[09]U6|1707U5|1366U4|1024U3|0845U3|0683U2)", |
497 | "", | |
498 | "", | |
499 | "-v 9,minutes" | |
832b75ed GG |
500 | }, |
501 | { "Maxtor DiamondMax D540X-4D", | |
2127e193 GI |
502 | "Maxtor 4D0(20H1|40H2|60H3|80H4)", |
503 | "", | |
504 | "", | |
505 | "-v 9,minutes -v 194,unknown" | |
832b75ed GG |
506 | }, |
507 | { "Maxtor DiamondMax 16 family", | |
2127e193 GI |
508 | "Maxtor 4(R0[68]0[JL]0|R1[26]0L0|A160J0|R120L4)", |
509 | "", | |
510 | "", | |
511 | "-v 9,minutes" | |
832b75ed | 512 | }, |
ba59cff1 | 513 | { "Maxtor DiamondMax 4320 Ultra ATA family", |
2127e193 GI |
514 | "Maxtor (91728D8|91512D7|91303D6|91080D5|90845D4|90645D3|90648D[34]|90432D2)", |
515 | "", | |
516 | "", | |
517 | "-v 9,minutes" | |
832b75ed GG |
518 | }, |
519 | { "Maxtor DiamondMax 17 VL family", | |
2127e193 GI |
520 | "Maxtor 9(0431U1|0641U2|0871U2|1301U3|1741U4)", |
521 | "", | |
522 | "", | |
523 | "-v 9,minutes" | |
832b75ed GG |
524 | }, |
525 | { "Maxtor DiamondMax 20 VL family", | |
2127e193 GI |
526 | "Maxtor (94091U8|93071U6|92561U5|92041U4|91731U4|91531U3|91361U3|91021U2|90841U2|90651U2)", |
527 | "", | |
528 | "", | |
529 | "-v 9,minutes" | |
530 | }, | |
531 | { "Maxtor DiamondMax VL 30 family", // U: ATA66, H: ATA100 | |
532 | "Maxtor (33073U4|32049U3|31536U2|30768U1|33073H4|32305H3|31536H2|30768H1)", | |
533 | "", | |
534 | "", | |
535 | "-v 9,minutes" | |
832b75ed GG |
536 | }, |
537 | { "Maxtor DiamondMax 36 family", | |
2127e193 GI |
538 | "Maxtor (93652U8|92739U6|91826U4|91369U3|90913U2|90845U2|90435U1)", |
539 | "", | |
540 | "", | |
541 | "-v 9,minutes" | |
832b75ed GG |
542 | }, |
543 | { "Maxtor DiamondMax 40 ATA 66 series", | |
2127e193 GI |
544 | "Maxtor 9(0684U2|1024U2|1362U3|1536U3|2049U4|2562U5|3073U6|4098U8)", |
545 | "", | |
546 | "", | |
547 | "-v 9,minutes" | |
832b75ed GG |
548 | }, |
549 | { "Maxtor DiamondMax Plus 40 series (Ultra ATA 66 and Ultra ATA 100)", | |
2127e193 GI |
550 | "Maxtor (54098[UH]8|53073[UH]6|52732[UH]6|52049[UH]4|51536[UH]3|51369[UH]3|51024[UH]2)", |
551 | "", | |
552 | "", | |
553 | "-v 9,minutes" | |
832b75ed GG |
554 | }, |
555 | { "Maxtor DiamondMax 40 VL Ultra ATA 100 series", | |
2127e193 GI |
556 | "Maxtor 3(1024H1|1535H2|2049H2|3073H3|4098H4)( B)?", |
557 | "", | |
558 | "", | |
559 | "-v 9,minutes" | |
832b75ed GG |
560 | }, |
561 | { "Maxtor DiamondMax Plus 45 Ulta ATA 100 family", | |
2127e193 GI |
562 | "Maxtor 5(4610H6|4098H6|3073H4|2049H3|1536H2|1369H2|1023H2)", |
563 | "", | |
564 | "", | |
565 | "-v 9,minutes" | |
832b75ed | 566 | }, |
ba59cff1 | 567 | { "Maxtor DiamondMax 60 ATA 66 family", |
2127e193 GI |
568 | "Maxtor 9(1023U2|1536U2|2049U3|2305U3|3073U4|4610U6|6147U8)", |
569 | "", | |
570 | "", | |
571 | "-v 9,minutes" | |
ba59cff1 GG |
572 | }, |
573 | { "Maxtor DiamondMax 60 ATA 100 family", | |
2127e193 GI |
574 | "Maxtor 9(1023H2|1536H2|2049H3|2305H3|3073H4|4098H6|4610H6|6147H8)", |
575 | "", | |
576 | "", | |
577 | "-v 9,minutes" | |
ba59cff1 | 578 | }, |
832b75ed | 579 | { "Maxtor DiamondMax Plus 60 family", |
2127e193 GI |
580 | "Maxtor 5T0(60H6|40H4|30H3|20H2|10H1)", |
581 | "", | |
582 | "", | |
583 | "-v 9,minutes" | |
832b75ed GG |
584 | }, |
585 | { "Maxtor DiamondMax 80 family", | |
2127e193 GI |
586 | "Maxtor (98196H8|96147H6)", |
587 | "", | |
588 | "", | |
589 | "-v 9,minutes" | |
832b75ed GG |
590 | }, |
591 | { "Maxtor DiamondMax 536DX family", | |
2127e193 GI |
592 | "Maxtor 4W(100H6|080H6|060H4|040H3|030H2)", |
593 | "", | |
594 | "", | |
595 | "-v 9,minutes" | |
832b75ed GG |
596 | }, |
597 | { "Maxtor DiamondMax Plus 8 family", | |
2127e193 GI |
598 | "Maxtor 6(E0[234]|K04)0L0", |
599 | "", | |
600 | "", | |
601 | "-v 9,minutes" | |
832b75ed | 602 | }, |
ba59cff1 | 603 | { "Maxtor DiamondMax 10 family (ATA/133 and SATA/150)", |
2127e193 GI |
604 | "Maxtor 6(B(30|25|20|16|12|10|08)0[MPRS]|L(080[MLP]|(100|120)[MP]|160[MP]|200[MPRS]|250[RS]|300[RS]))0", |
605 | "", | |
606 | "", | |
607 | "-v 9,minutes" | |
832b75ed | 608 | }, |
ba59cff1 | 609 | { "Maxtor DiamondMax 10 family (SATA/300)", |
2127e193 GI |
610 | "Maxtor 6V(080E|160E|200E|250F|300F|320F)0", |
611 | "", "", "" | |
ba59cff1 | 612 | }, |
832b75ed | 613 | { "Maxtor DiamondMax Plus 9 family", |
2127e193 GI |
614 | "Maxtor 6Y((060|080|120|160)L0|(060|080|120|160|200|250)P0|(060|080|120|160|200|250)M0)", |
615 | "", | |
616 | "", | |
617 | "-v 9,minutes" | |
832b75ed | 618 | }, |
ba59cff1 | 619 | { "Maxtor DiamondMax 11 family", |
2127e193 GI |
620 | "Maxtor 6H[45]00[FR]0", |
621 | "", "", "" | |
ba59cff1 | 622 | }, |
1953ff6d | 623 | { "Maxtor DiamondMax 17", |
2127e193 GI |
624 | "Maxtor 6G(080L|160[PE])0", |
625 | "", "", "" | |
1953ff6d GG |
626 | }, |
627 | { "Seagate Maxtor DiamondMax 20", | |
2127e193 GI |
628 | "MAXTOR STM3(40|80|160)[28]1[12]0?AS?", |
629 | "", "", "" | |
1953ff6d GG |
630 | }, |
631 | { "Seagate Maxtor DiamondMax 21", | |
2127e193 GI |
632 | "MAXTOR STM3(160215|(250|320)820|320620|500630)AS?", |
633 | "", "", "" | |
634 | }, | |
635 | { "Seagate Maxtor DiamondMax 22", // fixed firmware | |
636 | "(MAXTOR )?STM3(500320|750330|1000340)AS?", | |
637 | "MX1A", // http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207969 | |
638 | "", "" | |
639 | }, | |
640 | { "Seagate Maxtor DiamondMax 22", // fixed firmware | |
641 | "(MAXTOR )?STM3(160813|320614|640323|1000334)AS?", | |
642 | "MX1B", // http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207975 | |
643 | "", "" | |
644 | }, | |
645 | { "Seagate Maxtor DiamondMax 22", // buggy firmware | |
646 | "(MAXTOR )?STM3(500320|750330|1000340)AS?", | |
647 | "MX15", | |
648 | "There are known problems with these drives,\n" | |
649 | "AND THIS FIRMWARE VERSION IS AFFECTED,\n" | |
650 | "see the following Seagate web pages:\n" | |
651 | "http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207931\n" | |
652 | "http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207969", | |
653 | "" | |
654 | }, | |
655 | { "Seagate Maxtor DiamondMax 22", // unknown firmware | |
656 | "(MAXTOR )?STM3(160813|32061[34]|500320|640323|750330|10003(34|40))AS?", | |
657 | "", | |
658 | "There are known problems with these drives,\n" | |
659 | "see the following Seagate web pages:\n" | |
660 | "http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207931\n" | |
661 | "http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207969\n" | |
662 | "http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207975", | |
663 | "" | |
664 | }, | |
665 | { "Seagate Maxtor DiamondMax 23", | |
666 | "STM3((160|250)31|(320|500)41|(750|1000)52)8AS?", | |
667 | "", "", "" | |
1953ff6d | 668 | }, |
832b75ed | 669 | { "Maxtor MaXLine Plus II", |
2127e193 GI |
670 | "Maxtor 7Y250[PM]0", |
671 | "", | |
672 | "", | |
673 | "-v 9,minutes" | |
832b75ed GG |
674 | }, |
675 | { "Maxtor MaXLine II family", | |
2127e193 GI |
676 | "Maxtor [45]A(25|30|32)0[JN]0", |
677 | "", | |
678 | "", | |
679 | "-v 9,minutes" | |
832b75ed | 680 | }, |
ba59cff1 | 681 | { "Maxtor MaXLine III family (ATA/133 and SATA/150)", |
2127e193 GI |
682 | "Maxtor 7L(25|30)0[SR]0", |
683 | "", | |
684 | "", | |
685 | "-v 9,minutes" | |
ba59cff1 GG |
686 | }, |
687 | { "Maxtor MaXLine III family (SATA/300)", | |
2127e193 GI |
688 | "Maxtor 7V(25|30)0F0", |
689 | "", "", "" | |
ba59cff1 GG |
690 | }, |
691 | { "Maxtor MaXLine Pro 500 family", // There is also a 7H500R0 model, but I | |
2127e193 GI |
692 | "Maxtor 7H500F0", // haven't added it because I suspect |
693 | "", // it might need vendoropts_9_minutes | |
694 | "", "" // and nobody has submitted a report yet | |
ba59cff1 | 695 | }, |
2127e193 GI |
696 | { "", // HITACHI_DK14FA-20B |
697 | "HITACHI_DK14FA-20B", | |
698 | "", | |
699 | "", | |
700 | "-v 9,minutes -v 193,loadunload" | |
832b75ed GG |
701 | }, |
702 | { "HITACHI Travelstar DK23XX/DK23XXB series", | |
2127e193 GI |
703 | "HITACHI_DK23..-..B?", |
704 | "", | |
705 | "", | |
706 | "-v 9,minutes -v 193,loadunload" | |
832b75ed GG |
707 | }, |
708 | { "Hitachi Endurastar J4K20/N4K20 (formerly DK23FA-20J)", | |
2127e193 GI |
709 | "(HITACHI_DK23FA-20J|HTA422020F9AT[JN]0)", |
710 | "", | |
711 | "", | |
712 | "-v 9,minutes -v 193,loadunload" | |
713 | }, | |
714 | { "Hitachi Endurastar J4K30/N4K30", | |
715 | "HE[JN]4230[23]0F9AT00", | |
716 | "", | |
717 | "", | |
718 | "-v 9,minutes -v 193,loadunload" | |
719 | }, | |
720 | { "Hitachi Travelstar C4K60 family", // 1.8" slim drive | |
721 | "HTC4260[23]0G5CE00|HTC4260[56]0G8CE00", | |
722 | "", | |
723 | "", | |
724 | "-v 9,minutes -v 193,loadunload" | |
832b75ed | 725 | }, |
ba59cff1 | 726 | { "IBM Travelstar 4GT family", |
2127e193 GI |
727 | "IBM-DTCA-2(324|409)0", |
728 | "", "", "" | |
729 | }, | |
730 | { "IBM Travelstar 6GN family", | |
731 | "IBM-DBCA-20(324|486|648)0", | |
732 | "", "", "" | |
ba59cff1 | 733 | }, |
832b75ed | 734 | { "IBM Travelstar 25GS, 18GT, and 12GN family", |
2127e193 GI |
735 | "IBM-DARA-2(25|18|15|12|09|06)000", |
736 | "", "", "" | |
737 | }, | |
738 | { "IBM Travelstar 14GS", | |
739 | "IBM-DCYA-214000", | |
740 | "", "", "" | |
741 | }, | |
742 | { "IBM Travelstar 4LP", | |
743 | "IBM-DTNA-2(180|216)0", | |
744 | "", "", "" | |
832b75ed GG |
745 | }, |
746 | { "IBM Travelstar 48GH, 30GN, and 15GN family", | |
2127e193 GI |
747 | "(IBM-|Hitachi )?IC25(T048ATDA05|N0(30|20|15|12|10|07|06|05)ATDA04)-.", |
748 | "", "", "" | |
832b75ed GG |
749 | }, |
750 | { "IBM Travelstar 32GH, 30GT, and 20GN family", | |
2127e193 GI |
751 | "IBM-DJSA-2(32|30|20|10|05)", |
752 | "", "", "" | |
832b75ed | 753 | }, |
ba59cff1 | 754 | { "IBM Travelstar 4GN family", |
2127e193 GI |
755 | "IBM-DKLA-2(216|324|432)0", |
756 | "", "", "" | |
832b75ed GG |
757 | }, |
758 | { "IBM/Hitachi Travelstar 60GH and 40GN family", | |
2127e193 GI |
759 | "(IBM-|Hitachi )?IC25(T060ATC[SX]05|N0[4321]0ATC[SX]04)-.", |
760 | "", "", "" | |
832b75ed GG |
761 | }, |
762 | { "IBM/Hitachi Travelstar 40GNX family", | |
2127e193 GI |
763 | "(IBM-|Hitachi )?IC25N0[42]0ATC[SX]05-.", |
764 | "", "", "" | |
832b75ed GG |
765 | }, |
766 | { "Hitachi Travelstar 80GN family", | |
2127e193 GI |
767 | "(Hitachi )?IC25N0[23468]0ATMR04-.", |
768 | "", "", "" | |
832b75ed | 769 | }, |
1953ff6d | 770 | { "Hitachi Travelstar 4K40", |
2127e193 GI |
771 | "(Hitachi )?HTS4240[234]0M9AT00", |
772 | "", "", "" | |
773 | }, | |
774 | { "Hitachi Travelstar 4K120", | |
775 | "(Hitachi )?(HTS4212(60|80|10|12)H9AT00|HTS421260G9AT00)", | |
776 | "", "", "" | |
1953ff6d | 777 | }, |
832b75ed | 778 | { "Hitachi Travelstar 5K80 family", |
2127e193 GI |
779 | "(Hitachi )?HTS5480[8642]0M9AT00", |
780 | "", "", "" | |
832b75ed GG |
781 | }, |
782 | { "Hitachi Travelstar 5K100 series", | |
2127e193 GI |
783 | "(Hitachi )?HTS5410[1864]0G9(AT|SA)00", |
784 | "", "", "" | |
832b75ed | 785 | }, |
ba59cff1 | 786 | { "Hitachi Travelstar E5K100 series", |
2127e193 GI |
787 | "(Hitachi )?HTE541040G9(AT|SA)00", |
788 | "", "", "" | |
1953ff6d GG |
789 | }, |
790 | { "Hitachi Travelstar 5K120", | |
2127e193 GI |
791 | "(Hitachi )?HTS5412(60|80|10|12)H9(AT|SA)00", |
792 | "", "", "" | |
ba59cff1 | 793 | }, |
a37e7145 | 794 | { "Hitachi Travelstar 5K160 series", |
2127e193 GI |
795 | "(Hitachi |HITACHI )?HTS5416([468]0|1[26])J9(AT|SA)00", |
796 | "", "", "" | |
797 | }, | |
798 | { "Hitachi Travelstar E5K160 series", | |
799 | "(Hitachi )?HTE5416(12|16|60|80)J9(AT|SA)00", | |
800 | "", "", "" | |
801 | }, | |
802 | { "Hitachi Travelstar 5K250 series", | |
803 | "(Hitachi |HITACHI )?HTS5425(80|12|16|20|25)K9(A3|SA)00", | |
804 | "", "", "" | |
a37e7145 | 805 | }, |
bed94269 GI |
806 | { "Hitachi Travelstar 5K320 series", |
807 | "(Hitachi |HITACHI )?HT(S|E)5432(80|12|16|25|32)L9(A300|SA01)", | |
808 | "", "", "" | |
809 | }, | |
832b75ed | 810 | { "Hitachi Travelstar 7K60", |
2127e193 GI |
811 | "(Hitachi )?HTS726060M9AT00", |
812 | "", "", "" | |
1953ff6d GG |
813 | }, |
814 | { "Hitachi Travelstar E7K60", | |
2127e193 GI |
815 | "(Hitachi )?HTE7260[46]0M9AT00", |
816 | "", "", "" | |
832b75ed | 817 | }, |
ba59cff1 | 818 | { "Hitachi Travelstar 7K100", |
2127e193 GI |
819 | "(Hitachi )?HTS7210[168]0G9(AT|SA)00", |
820 | "", "", "" | |
ba59cff1 GG |
821 | }, |
822 | { "Hitachi Travelstar E7K100", | |
2127e193 GI |
823 | "(Hitachi )?HTE7210[168]0G9(AT|SA)00", |
824 | "", "", "" | |
ba59cff1 | 825 | }, |
1953ff6d | 826 | { "Hitachi Travelstar 7K200", |
2127e193 GI |
827 | "(Hitachi )?HTS7220(80|10|12|16|20)K9(A3|SA)00", |
828 | "", "", "" | |
832b75ed | 829 | }, |
2127e193 GI |
830 | { "IBM Deskstar 14GXP and 16GP series", |
831 | "IBM-DTTA-3(7101|7129|7144|5032|5043|5064|5084|5101|5129|5168)0", | |
832 | "", "", "" | |
832b75ed | 833 | }, |
2127e193 GI |
834 | { "IBM Deskstar 25GP and 22GXP family", |
835 | "IBM-DJNA-3(5(101|152|203|250)|7(091|135|180|220))0", | |
836 | "", "", "" | |
832b75ed | 837 | }, |
2127e193 GI |
838 | { "IBM Deskstar 37GP and 34GXP family", |
839 | "IBM-DPTA-3(5(375|300|225|150)|7(342|273|205|136))0", | |
840 | "", "", "" | |
832b75ed | 841 | }, |
2127e193 GI |
842 | { "IBM/Hitachi Deskstar 120GXP family", |
843 | "(IBM-)?IC35L((020|040|060|080|120)AVVA|0[24]0AVVN)07-[01]", | |
844 | "", "", "" | |
845 | }, | |
846 | { "IBM/Hitachi Deskstar GXP-180 family", | |
847 | "(IBM-)?IC35L(030|060|090|120|180)AVV207-[01]", | |
848 | "", "", "" | |
832b75ed GG |
849 | }, |
850 | { "Hitachi Deskstar 7K80 series", | |
2127e193 GI |
851 | "(Hitachi )?HDS7280([48]0PLAT20|(40)?PLA320|80PLA380).*", |
852 | "", "", "" | |
832b75ed | 853 | }, |
1953ff6d | 854 | { "Hitachi Deskstar 7K160", |
2127e193 GI |
855 | "(Hitachi )?HDS7216(80|16)PLA[3T]80.*", |
856 | "", "", "" | |
1953ff6d | 857 | }, |
832b75ed | 858 | { "Hitachi Deskstar 7K250 series", |
2127e193 GI |
859 | "(Hitachi )?HDS7225((40|80|12|16)VLAT20|(12|16|25)VLAT80|(80|12|16|25)VLSA80)", |
860 | "", "", "" | |
861 | }, | |
862 | { "Hitachi Deskstar 7K250 (SUN branded)", | |
863 | "HITACHI HDS7225SBSUN250G.*", | |
864 | "", "", "" | |
832b75ed | 865 | }, |
ba59cff1 | 866 | { "Hitachi Deskstar T7K250 series", |
2127e193 GI |
867 | "(Hitachi )?HDT7225((25|20|16)DLA(T80|380))", |
868 | "", "", "" | |
ba59cff1 | 869 | }, |
832b75ed | 870 | { "Hitachi Deskstar 7K400 series", |
2127e193 GI |
871 | "(Hitachi )?HDS724040KL(AT|SA)80", |
872 | "", "", "" | |
832b75ed | 873 | }, |
ba59cff1 | 874 | { "Hitachi Deskstar 7K500 series", |
2127e193 GI |
875 | "(Hitachi )?HDS725050KLA(360|T80)", |
876 | "", "", "" | |
877 | }, | |
878 | { "Hitachi Deskstar P7K500 series", | |
879 | "(Hitachi )?HDP7250(16|25|32|40|50)GLA(36|38|T8)0", | |
880 | "", "", "" | |
832b75ed | 881 | }, |
1953ff6d | 882 | { "Hitachi Deskstar T7K500", |
2127e193 GI |
883 | "(Hitachi )?HDT7250(25|32|40|50)VLA(360|380|T80)", |
884 | "", "", "" | |
1953ff6d GG |
885 | }, |
886 | { "Hitachi Deskstar 7K1000", | |
2127e193 GI |
887 | "(Hitachi )?HDS7210(50|75|10)KLA330", |
888 | "", "", "" | |
889 | }, | |
890 | { "Hitachi Deskstar 7K1000.B", | |
891 | "(Hitachi )?HDT7210((16|25)SLA380|(32|50|64|75|10)SLA360)", | |
892 | "", "", "" | |
1953ff6d | 893 | }, |
bed94269 GI |
894 | { "Hitachi Deskstar 7K2000", |
895 | "Hitachi HDS722020ALA330", | |
896 | "", "", "" | |
897 | }, | |
1953ff6d | 898 | { "Hitachi Ultrastar 7K1000", |
2127e193 GI |
899 | "(Hitachi )?HUA7210(50|75|10)KLA330", |
900 | "", "", "" | |
901 | }, | |
902 | { "Toshiba 2.5\" HDD series (10-20 GB)", | |
903 | "TOSHIBA MK(101[67]GAP|15[67]GAP|20(1[678]GAP|(18|23)GAS))", | |
904 | "", "", "" | |
1953ff6d | 905 | }, |
ba59cff1 | 906 | { "Toshiba 2.5\" HDD series (30-60 GB)", |
2127e193 GI |
907 | "TOSHIBA MK((6034|4032)GSX|(6034|4032)GAX|(6026|4026|4019|3019)GAXB?|(6025|6021|4025|4021|4018|3025|3021|3018)GAS|(4036|3029)GACE?|(4018|3017)GAP)", |
908 | "", "", "" | |
832b75ed | 909 | }, |
ba59cff1 | 910 | { "Toshiba 2.5\" HDD series (80 GB and above)", |
2127e193 GI |
911 | "TOSHIBA MK(80(25GAS|26GAX|32GAX|32GSX)|10(31GAS|32GAX)|12(33GAS|34G[AS]X)|2035GSS)", |
912 | "", "", "" | |
913 | }, | |
914 | { "Toshiba 2.5\" HDD MK..52GSX series", | |
915 | "TOSHIBA MK(80|12|16|25|32)52GSX", | |
916 | "", "", "" | |
832b75ed | 917 | }, |
1953ff6d | 918 | { "Toshiba 1.8\" HDD series", |
2127e193 GI |
919 | "TOSHIBA MK[23468]00[4-9]GA[HL]", |
920 | "", "", "" | |
921 | }, | |
922 | { "", // TOSHIBA MK6022GAX | |
923 | "TOSHIBA MK6022GAX", | |
924 | "", "", "" | |
925 | }, | |
926 | { "", // TOSHIBA MK6409MAV | |
927 | "TOSHIBA MK6409MAV", | |
928 | "", "", "" | |
929 | }, | |
930 | { "Toshiba MKx019GAXB (SUN branded)", | |
931 | "TOS MK[34]019GAXB SUN[34]0G", | |
932 | "", "", "" | |
832b75ed | 933 | }, |
ba59cff1 | 934 | { "Seagate Momentus family", |
2127e193 GI |
935 | "ST9(20|28|40|48)11A", |
936 | "", "", "" | |
832b75ed | 937 | }, |
ba59cff1 | 938 | { "Seagate Momentus 42 family", |
2127e193 GI |
939 | "ST9(2014|3015|4019)A", |
940 | "", "", "" | |
832b75ed | 941 | }, |
2127e193 GI |
942 | { "Seagate Momentus 4200.2 series", |
943 | "ST9(100822|808210|60821|50212|402113|30219)A", | |
944 | "", "", "" | |
832b75ed | 945 | }, |
ba59cff1 | 946 | { "Seagate Momentus 5400.2 series", |
2127e193 GI |
947 | "ST9(808211|60822|408114|308110|120821|10082[34]|8823|6812|4813|3811)AS?", |
948 | "", "", "" | |
949 | }, | |
950 | { "Seagate Momentus 5400.3 series", | |
951 | "ST9(4081[45]|6081[35]|8081[15]|100828|120822|160821)AS?", | |
952 | "", "", "" | |
953 | }, | |
954 | { "Seagate Momentus 5400.3 ED series", | |
955 | "ST9(4081[45]|6081[35]|8081[15]|100828|120822|160821)AB", | |
956 | "", "", "" | |
832b75ed | 957 | }, |
2127e193 GI |
958 | { "Seagate Momentus 5400.4 series", |
959 | "ST9(120817|(160|200|250)827)AS", | |
960 | "", "", "" | |
1953ff6d | 961 | }, |
2127e193 GI |
962 | { "Seagate Momentus 5400.5 series", |
963 | "ST9((80|120|160)310|(250|320)320)AS", | |
964 | "", "", "" | |
965 | }, | |
966 | { "Seagate Momentus 5400.6 series", | |
967 | "ST9((12|25)0315AS|500325)ASG?", | |
968 | "", "", "" | |
969 | }, | |
970 | { "Seagate Momentus 5400 PSD series", // Hybrid drives | |
971 | "ST9(808212|(120|160)8220)AS", | |
972 | "", "", "" | |
1953ff6d | 973 | }, |
ba59cff1 | 974 | { "Seagate Momentus 7200.1 series", |
2127e193 GI |
975 | "ST9(10021|80825|6023|4015)AS?", |
976 | "", "", "" | |
977 | }, | |
978 | { "Seagate Momentus 7200.2 series", | |
979 | "ST9(80813|100821|120823|160823|200420)ASG?", | |
980 | "", "", "" | |
832b75ed | 981 | }, |
2127e193 GI |
982 | { "Seagate Momentus 7200.3 series", |
983 | "ST9((80|120|160)411|(250|320)421)ASG?", | |
984 | "", "", "" | |
985 | }, | |
bed94269 GI |
986 | { "Seagate Momentus 7200.4 series", |
987 | "ST9(160412|250410|320423|500420)ASG?", | |
988 | "", "", "" | |
989 | }, | |
990 | { "Seagate Momentus 7200 FDE.2 series", | |
991 | "ST9((160413|25041[12]|320426|50042[12])AS|(16041[89]|2504[16]4|32042[67]|500426)ASG)", | |
992 | "", "", "" | |
993 | }, | |
2127e193 GI |
994 | { "Seagate Medalist 1010, 1721, 2120, 3230 and 4340", // ATA2, with -t permissive |
995 | "ST3(1010|1721|2120|3230|4340)A", | |
996 | "", "", "" | |
1953ff6d | 997 | }, |
ba59cff1 | 998 | { "Seagate Medalist 2110, 3221, 4321, 6531, and 8641", |
2127e193 GI |
999 | "ST3(2110|3221|4321|6531|8641)A", |
1000 | "", "", "" | |
832b75ed | 1001 | }, |
ba59cff1 | 1002 | { "Seagate U Series X family", |
2127e193 GI |
1003 | "ST3(10014A(CE)?|20014A)", |
1004 | "", "", "" | |
1005 | }, | |
1006 | { "Seagate U8 family", | |
1007 | "ST3(4313|6811|8410|13021|17221)A", | |
1008 | "", "", "" | |
832b75ed | 1009 | }, |
ba59cff1 | 1010 | { "Seagate U7 family", |
2127e193 GI |
1011 | "ST3(30012|40012|60012|80022|120020)A", |
1012 | "", "", "" | |
832b75ed GG |
1013 | }, |
1014 | { "Seagate U Series 6 family", | |
2127e193 GI |
1015 | "ST3(8002|6002|4081|3061|2041)0A", |
1016 | "", "", "" | |
832b75ed GG |
1017 | }, |
1018 | { "Seagate U Series 5 family", | |
2127e193 GI |
1019 | "ST3(40823|30621|20413|15311|10211)A", |
1020 | "", "", "" | |
832b75ed GG |
1021 | }, |
1022 | { "Seagate U4 family", | |
2127e193 GI |
1023 | "ST3(2112|4311|6421|8421)A", |
1024 | "", "", "" | |
832b75ed GG |
1025 | }, |
1026 | { "Seagate U8 family", | |
2127e193 GI |
1027 | "ST3(8410|4313|17221|13021)A", |
1028 | "", "", "" | |
832b75ed GG |
1029 | }, |
1030 | { "Seagate U10 family", | |
2127e193 GI |
1031 | "ST3(20423|15323|10212)A", |
1032 | "", "", "" | |
1033 | }, | |
1034 | { "Seagate Barracuda ATA family", | |
1035 | "ST3(2804|2724|2043|1362|1022|681)0A", | |
1036 | "", "", "" | |
832b75ed GG |
1037 | }, |
1038 | { "Seagate Barracuda ATA II family", | |
2127e193 GI |
1039 | "ST3(3063|2042|1532|1021)0A", |
1040 | "", "", "" | |
832b75ed GG |
1041 | }, |
1042 | { "Seagate Barracuda ATA III family", | |
2127e193 GI |
1043 | "ST3(40824|30620|20414|15310|10215)A", |
1044 | "", "", "" | |
832b75ed GG |
1045 | }, |
1046 | { "Seagate Barracuda ATA IV family", | |
2127e193 GI |
1047 | "ST3(20011|30011|40016|60021|80021)A", |
1048 | "", "", "" | |
832b75ed GG |
1049 | }, |
1050 | { "Seagate Barracuda ATA V family", | |
2127e193 GI |
1051 | "ST3(12002(3A|4A|9A|3AS)|800(23A|15A|23AS)|60(015A|210A)|40017A)", |
1052 | "", "", "" | |
832b75ed GG |
1053 | }, |
1054 | { "Seagate Barracuda 5400.1", | |
2127e193 GI |
1055 | "ST340015A", |
1056 | "", "", "" | |
832b75ed GG |
1057 | }, |
1058 | { "Seagate Barracuda 7200.7 and 7200.7 Plus family", | |
2127e193 GI |
1059 | "ST3(200021A|200822AS?|16002[13]AS?|12002[26]AS?|1[26]082[78]AS|8001[13]AS?|8081[79]AS|60014A|40111AS|40014AS?)", |
1060 | "", "", "" | |
832b75ed GG |
1061 | }, |
1062 | { "Seagate Barracuda 7200.8 family", | |
2127e193 GI |
1063 | "ST3(400[68]32|300[68]31|250[68]23|200826)AS?", |
1064 | "", "", "" | |
ba59cff1 GG |
1065 | }, |
1066 | { "Seagate Barracuda 7200.9 family", | |
2127e193 GI |
1067 | "ST3(402111?|80[28]110?|120[28]1[0134]|160[28]1[012]|200827|250[68]24|300[68]22|(320|400)[68]33|500[68](32|41))AS?.*", |
1068 | "", "", "" | |
ba59cff1 GG |
1069 | }, |
1070 | { "Seagate Barracuda 7200.10 family", | |
2127e193 GI |
1071 | "ST3((80|160)[28]15|200820|250[34]10|(250|300|320|400)[68]20|500[68]30|750[68]40)AS?", |
1072 | "", "", "" | |
1073 | }, | |
1074 | { "Seagate Barracuda 7200.11 family", // unaffected firmware | |
1075 | "ST3(160813|320[68]13|500[368]20|640[36]23|640[35]30|750[36]30|1000(333|[36]40)|1500341)AS?", | |
1076 | "CC.?.?", // http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207957 | |
1077 | "", "" | |
1078 | }, | |
1079 | { "Seagate Barracuda 7200.11 family", // fixed firmware | |
1080 | "ST3(500[368]20|750[36]30|1000340)AS?", | |
1081 | "SD1A", // http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207951 | |
1082 | "", "" | |
1083 | }, | |
1084 | { "Seagate Barracuda 7200.11 family", // fixed firmware | |
1085 | "ST3(160813|320[68]13|640[36]23|1000333|1500341)AS?", | |
bed94269 | 1086 | "SD[12]B", // http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207957 |
2127e193 GI |
1087 | "", "" |
1088 | }, | |
1089 | { "Seagate Barracuda 7200.11 family", // buggy firmware | |
1090 | "ST3(500[368]20|640[35]30|750[36]30|1000340)AS?", | |
1091 | "(AD14|SD1[5-9])", | |
1092 | "There are known problems with these drives,\n" | |
1093 | "AND THIS FIRMWARE VERSION IS AFFECTED,\n" | |
1094 | "see the following Seagate web pages:\n" | |
1095 | "http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207931\n" | |
1096 | "http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207951", | |
1097 | "" | |
1098 | }, | |
1099 | { "Seagate Barracuda 7200.11 family", // unknown firmware | |
1100 | "ST3(160813|320[68]13|500[368]20|640[36]23|640[35]30|750[36]30|1000(333|[36]40)|1500341)AS?", | |
1101 | "", | |
1102 | "There are known problems with these drives,\n" | |
1103 | "see the following Seagate web pages:\n" | |
1104 | "http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207931\n" | |
1105 | "http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207951\n" | |
1106 | "http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207957", | |
1107 | "" | |
1108 | }, | |
1109 | { "Seagate Barracuda 7200.12 family", | |
1110 | "ST3((160|250)318|(320|500)418|500410|(750|1000)528)AS", | |
1111 | "", "", "" | |
1953ff6d GG |
1112 | }, |
1113 | { "Seagate Barracuda ES", | |
2127e193 GI |
1114 | "ST3(250[68]2|32062|40062|50063|75064)0NS", |
1115 | "", "", "" | |
1116 | }, | |
1117 | { "Seagate Barracuda ES.2", // fixed firmware | |
1118 | "ST3(25031|50032|75033|100034)0NS", | |
1119 | "SN[01]6", // http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207963 | |
1120 | "", "" | |
1121 | }, | |
1122 | { "Seagate Barracuda ES.2", // unknown firmware | |
1123 | "ST3(25031|50032|75033|100034)0NS", | |
1124 | "", | |
1125 | "There are known problems with these drives,\n" | |
1126 | "see the following Seagate web pages:\n" | |
1127 | "http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207931\n" | |
1128 | "http://seagate.custkb.com/seagate/crm/selfservice/search.jsp?DocId=207963", | |
1129 | "" | |
832b75ed GG |
1130 | }, |
1131 | { "Seagate Medalist 17240, 13030, 10231, 8420, and 4310", | |
2127e193 GI |
1132 | "ST3(17240|13030|10231|8420|4310)A", |
1133 | "", "", "" | |
832b75ed GG |
1134 | }, |
1135 | { "Seagate Medalist 17242, 13032, 10232, 8422, and 4312", | |
2127e193 GI |
1136 | "ST3(1724|1303|1023|842|431)2A", |
1137 | "", "", "" | |
832b75ed | 1138 | }, |
ba59cff1 | 1139 | { "Seagate NL35 family", |
2127e193 GI |
1140 | "ST3(250623|250823|400632|400832|250824|250624|400633|400833|500641|500841)NS", |
1141 | "", "", "" | |
1142 | }, | |
1143 | { "Seagate SV35.2 Series", | |
1144 | "ST3(160815|250820|320620|500630|750640)(A|S)V", | |
1145 | "", "", "" | |
1146 | }, | |
1147 | { "Seagate DB35.3 Series", | |
1148 | "ST3(750640SCE|((80|160)215|(250|320|400)820|500830|750840)(A|S)CE)", | |
1149 | "", "", "" | |
ba59cff1 | 1150 | }, |
832b75ed GG |
1151 | { "Western Digital Protege", |
1152 | /* Western Digital drives with this comment all appear to use Attribute 9 in | |
1153 | * a non-standard manner. These entries may need to be updated when it | |
1154 | * is understood exactly how Attribute 9 should be interpreted. | |
1155 | * UPDATE: this is probably explained by the WD firmware bug described in the | |
1156 | * smartmontools FAQ */ | |
2127e193 GI |
1157 | "WDC WD([2468]00E|1[26]00A)B-.*", |
1158 | "", "", "" | |
832b75ed GG |
1159 | }, |
1160 | { "Western Digital Caviar family", | |
1161 | /* Western Digital drives with this comment all appear to use Attribute 9 in | |
1162 | * a non-standard manner. These entries may need to be updated when it | |
1163 | * is understood exactly how Attribute 9 should be interpreted. | |
1164 | * UPDATE: this is probably explained by the WD firmware bug described in the | |
1165 | * smartmontools FAQ */ | |
2127e193 GI |
1166 | "WDC WD(2|3|4|6|8|10|12|16|18|20|25)00BB-.*", |
1167 | "", "", "" | |
832b75ed GG |
1168 | }, |
1169 | { "Western Digital Caviar WDxxxAB series", | |
1170 | /* Western Digital drives with this comment all appear to use Attribute 9 in | |
1171 | * a non-standard manner. These entries may need to be updated when it | |
1172 | * is understood exactly how Attribute 9 should be interpreted. | |
1173 | * UPDATE: this is probably explained by the WD firmware bug described in the | |
1174 | * smartmontools FAQ */ | |
2127e193 GI |
1175 | "WDC WD(3|4|6|8|25)00AB-.*", |
1176 | "", "", "" | |
832b75ed GG |
1177 | }, |
1178 | { "Western Digital Caviar WDxxxAA series", | |
1179 | /* Western Digital drives with this comment all appear to use Attribute 9 in | |
1180 | * a non-standard manner. These entries may need to be updated when it | |
1181 | * is understood exactly how Attribute 9 should be interpreted. | |
1182 | * UPDATE: this is probably explained by the WD firmware bug described in the | |
1183 | * smartmontools FAQ */ | |
2127e193 GI |
1184 | "WDC WD...?AA(-.*)?", |
1185 | "", "", "" | |
832b75ed GG |
1186 | }, |
1187 | { "Western Digital Caviar WDxxxBA series", | |
1188 | /* Western Digital drives with this comment all appear to use Attribute 9 in | |
1189 | * a non-standard manner. These entries may need to be updated when it | |
1190 | * is understood exactly how Attribute 9 should be interpreted. | |
1191 | * UPDATE: this is probably explained by the WD firmware bug described in the | |
1192 | * smartmontools FAQ */ | |
2127e193 GI |
1193 | "WDC WD...BA", |
1194 | "", "", "" | |
832b75ed | 1195 | }, |
2127e193 GI |
1196 | { "Western Digital Caviar AC series", // add only 5400rpm/7200rpm (ata33 and faster) |
1197 | "WDC AC((116|121|125|225|132|232)|([1-4][4-9][0-9])|([1-4][0-9][0-9][0-9]))00[A-Z]?.*", | |
1198 | "", "", "" | |
ba59cff1 | 1199 | }, |
832b75ed GG |
1200 | { "Western Digital Caviar SE family", |
1201 | /* Western Digital drives with this comment all appear to use Attribute 9 in | |
1202 | * a non-standard manner. These entries may need to be updated when it | |
1203 | * is understood exactly how Attribute 9 should be interpreted. | |
1204 | * UPDATE: this is probably explained by the WD firmware bug described in the | |
1953ff6d GG |
1205 | * smartmontools FAQ |
1206 | * UPDATE 2: this does not apply to more recent models, at least WD3200AAJB */ | |
2127e193 GI |
1207 | "WDC WD(4|6|8|10|12|16|18|20|25|30|32|40|50)00(JB|PB)-.*", |
1208 | "", "", "" | |
1209 | }, | |
1210 | { "Western Digital Caviar Blue EIDE family", // WD Caviar SE EIDE family | |
1211 | /* not completely accurate: at least also WD800JB, WD(4|8|20|25)00BB sold as Caviar Blue */ | |
1212 | "WDC WD(16|25|32|40|50)00AAJB-.*", | |
1213 | "", "", "" | |
1214 | }, | |
1215 | { "Western Digital Caviar Blue EIDE family", // WD Caviar SE16 EIDE family | |
1216 | "WDC WD(25|32|40|50)00AAKB-.*", | |
1217 | "", "", "" | |
1218 | }, | |
1219 | { "Western Digital RE EIDE family", | |
1220 | "WDC WD(12|16|25|32)00SB-.*", | |
1221 | "", "", "" | |
1222 | }, | |
1223 | { "Western Digital Caviar Serial ATA family", | |
1224 | "WDC WD(4|8|20|32)00BD-.*", | |
1225 | "", "", "" | |
1226 | }, | |
1227 | { "Western Digital Caviar SE Serial ATA family", | |
1228 | "WDC WD(4|8|12|16|20|25|32|40)00(JD|KD|PD)-.*", | |
1229 | "", "", "" | |
1953ff6d GG |
1230 | }, |
1231 | { "Western Digital Caviar SE Serial ATA family", | |
2127e193 GI |
1232 | "WDC WD(8|12|16|20|25|30|32|40|50)00JS-.*", |
1233 | "", "", "" | |
1234 | }, | |
1235 | { "Western Digital Caviar SE16 Serial ATA family", | |
1236 | "WDC WD(16|20|25|32|40|50|75)00KS-.*", | |
1237 | "", "", "" | |
1238 | }, | |
1239 | { "Western Digital Caviar Blue Serial ATA family", // WD Caviar SE Serial ATA family | |
1240 | /* not completely accurate: at least also WD800BD, (4|8)00JD sold as Caviar Blue */ | |
1241 | "WDC WD((8|12|16|25|32)00AABS|(12|16|25|32|40|50)00AAJS)-.*", | |
1242 | "", "", "" | |
1243 | }, | |
1244 | { "Western Digital Caviar Blue Serial ATA family", // WD Caviar SE16 Serial ATA family | |
1245 | "WDC WD(16|20|25|32|40|50|64|75)00AAKS-.*", | |
1246 | "", "", "" | |
1247 | }, | |
1248 | { "Western Digital RE Serial ATA family", | |
1249 | "WDC WD(12|16|25|32)00(SD|YD|YS)-.*", | |
1250 | "", "", "" | |
1251 | }, | |
1252 | { "Western Digital RE2 Serial ATA family", | |
1253 | "WDC WD((40|50|75)00(YR|YS|AYYS)|(16|32|40|50)0[01]ABYS)-.*", | |
1254 | "", "", "" | |
1255 | }, | |
1256 | { "Western Digital RE2-GP family", | |
1257 | "WDC WD(5000AB|7500AY|1000FY)PS-.*", | |
1258 | "", "", "" | |
1259 | }, | |
1260 | { "Western Digital RE3 Serial ATA family", | |
1261 | "WDC WD((25|32|50)02A|(75|10)02F)BYS-.*", | |
1262 | "", "", "" | |
1263 | }, | |
1264 | { "Western Digital Caviar Green family", | |
1265 | "WDC WD((50|64|75)00AA(C|V)S|(50|75)00AADS|10EA(C|V)S|(10|15|20)EADS)-.*", | |
1266 | "", "", "" | |
832b75ed | 1267 | }, |
2127e193 GI |
1268 | { "Western Digital Caviar Black family", |
1269 | "WDC WD((500|640|750)1AA|1001FA)LS-.*", | |
1270 | "", "", "" | |
ba59cff1 | 1271 | }, |
2127e193 GI |
1272 | { "Western Digital AV ATA family", |
1273 | "WDC WD(8|16|50)00AV(B|J)B-.*", | |
1274 | "", "", "" | |
832b75ed | 1275 | }, |
2127e193 GI |
1276 | { "Western Digital AV-GP family", |
1277 | "WDC WD((16|25|32|50|64|75)00AVVS|(50|75)00AVCS|10EVVS|(10|20)EVCS|WD(10|15|20)EVDS)-.*", | |
1278 | "", "", "" | |
832b75ed GG |
1279 | }, |
1280 | { "Western Digital Raptor family", | |
2127e193 GI |
1281 | "WDC WD((360|740|800)GD|(360|740|1500)ADF[DS])-.*", |
1282 | "", "", "" | |
832b75ed | 1283 | }, |
bed94269 GI |
1284 | { "Western Digital Raptor X", |
1285 | "WDC WD1500AHFD-.*", | |
1286 | "", "", "" | |
1287 | }, | |
2127e193 GI |
1288 | { "Western Digital VelociRaptor family", |
1289 | "WDC WD((1500|3000)B|3000G)LFS-.*", | |
1290 | "", "", "" | |
1291 | }, | |
1292 | { "Western Digital Scorpio EIDE family", | |
1293 | "WDC WD(4|6|8|10|12|16)00(UE|VE)-.*", | |
1294 | "", "", "" | |
1295 | }, | |
1296 | { "Western Digital Scorpio Blue EIDE family", | |
1297 | "WDC WD(4|6|8|10|12|16|25)00BEVE-.*", | |
1298 | "", "", "" | |
1299 | }, | |
1300 | { "Western Digital Scorpio Serial ATA family", | |
1301 | "WDC WD(4|6|8|10|12|16|25)00BEAS-.*", | |
1302 | "", "", "" | |
1303 | }, | |
1304 | { "Western Digital Scorpio Blue Serial ATA family", | |
1305 | "WDC WD((4|6|8|10|12|16|25)00BEVS|(8|12|16|25|32|40|50)00BEVT)-.*", | |
1306 | "", "", "" | |
1307 | }, | |
1308 | { "Western Digital Scorpio Black Serial ATA family", | |
1309 | "WDC WD(8|12|16|25|32)00B[EJ]KT-.*", | |
1310 | "", "", "" | |
1311 | }, | |
bed94269 GI |
1312 | { "Western Digital My Passport Essential hard drive (USB interface)", |
1313 | "WDC WD3200BMVU-.*", | |
1314 | "", "", "" | |
1315 | }, | |
1316 | { "Western Digital My Passport hard drive (USB interface)", | |
1317 | "WDC WD3200BMVV-.*", | |
1318 | "", "", "" | |
1319 | }, | |
2127e193 GI |
1320 | { "Quantum Bigfoot series", |
1321 | "QUANTUM BIGFOOT TS10.0A", | |
1322 | "", "", "" | |
1323 | }, | |
1324 | { "Quantum Fireball lct15 series", | |
1325 | "QUANTUM FIREBALLlct15 ([123]0|22)", | |
1326 | "", "", "" | |
1327 | }, | |
1328 | { "Quantum Fireball lct20 series", | |
1329 | "QUANTUM FIREBALLlct20 [234]0", | |
1330 | "", "", "" | |
1331 | }, | |
1332 | { "Quantum Fireball CX series", | |
1333 | "QUANTUM FIREBALL CX10.2A", | |
1334 | "", "", "" | |
832b75ed GG |
1335 | }, |
1336 | { "Quantum Fireball CR series", | |
2127e193 GI |
1337 | "QUANTUM FIREBALL CR(4.3|6.4|8.4|13.0)A", |
1338 | "", "", "" | |
832b75ed | 1339 | }, |
2127e193 GI |
1340 | { "Quantum Fireball EX series", |
1341 | "QUANTUM FIREBALL EX(3.2|6.4)A", | |
1342 | "", "", "" | |
1343 | }, | |
1344 | { "Quantum Fireball ST series", | |
1345 | "QUANTUM FIREBALL ST(3.2|4.3|4300)A", | |
1346 | "", "", "" | |
ba59cff1 GG |
1347 | }, |
1348 | { "Quantum Fireball SE series", | |
2127e193 GI |
1349 | "QUANTUM FIREBALL SE4.3A", |
1350 | "", "", "" | |
1351 | }, | |
1352 | { "Quantum Fireball Plus LM series", | |
1353 | "QUANTUM FIREBALLP LM(10.2|15|20.[45]|30)", | |
1354 | "", "", "" | |
1355 | }, | |
1356 | { "Quantum Fireball Plus AS series", | |
1357 | "QUANTUM FIREBALLP AS(10.2|20.5|30.0|40.0)", | |
1358 | "", "", "" | |
1359 | }, | |
1360 | { "Quantum Fireball Plus KX series", | |
1361 | "QUANTUM FIREBALLP KX27.3", | |
1362 | "", "", "" | |
1363 | }, | |
1364 | { "Quantum Fireball Plus KA series", | |
1365 | "QUANTUM FIREBALLP KA(9|10).1", | |
1366 | "", "", "" | |
1367 | }, | |
1368 | // END drivedb.h (DO NOT DELETE - used by Makefile) | |
832b75ed GG |
1369 | }; |
1370 | ||
2127e193 GI |
1371 | |
1372 | /// Drive database class. Stores custom entries read from file. | |
1373 | /// Provides transparent access to concatenation of custom and | |
1374 | /// default table. | |
1375 | class drive_database | |
1376 | { | |
1377 | public: | |
1378 | drive_database(); | |
1379 | ||
1380 | ~drive_database(); | |
1381 | ||
1382 | /// Get total number of entries. | |
1383 | unsigned size() const | |
1384 | { return m_custom_tab.size() + m_builtin_size; } | |
1385 | ||
1386 | /// Get number of custom entries. | |
1387 | unsigned custom_size() const | |
1388 | { return m_custom_tab.size(); } | |
1389 | ||
1390 | /// Array access. | |
1391 | const drive_settings & operator[](unsigned i); | |
1392 | ||
1393 | /// Append new custom entry. | |
1394 | void push_back(const drive_settings & src); | |
1395 | ||
1396 | /// Append builtin table. | |
1397 | void append(const drive_settings * builtin_tab, unsigned builtin_size) | |
1398 | { m_builtin_tab = builtin_tab; m_builtin_size = builtin_size; } | |
1399 | ||
1400 | private: | |
1401 | const drive_settings * m_builtin_tab; | |
1402 | unsigned m_builtin_size; | |
1403 | ||
1404 | std::vector<drive_settings> m_custom_tab; | |
1405 | std::vector<char *> m_custom_strings; | |
1406 | ||
1407 | const char * copy_string(const char * str); | |
1408 | ||
1409 | drive_database(const drive_database &); | |
1410 | void operator=(const drive_database &); | |
1411 | }; | |
1412 | ||
1413 | drive_database::drive_database() | |
1414 | : m_builtin_tab(0), m_builtin_size(0) | |
1415 | { | |
1416 | } | |
1417 | ||
1418 | drive_database::~drive_database() | |
1419 | { | |
1420 | for (unsigned i = 0; i < m_custom_strings.size(); i++) | |
1421 | delete [] m_custom_strings[i]; | |
1422 | } | |
1423 | ||
1424 | const drive_settings & drive_database::operator[](unsigned i) | |
1425 | { | |
1426 | return (i < m_custom_tab.size() ? m_custom_tab[i] | |
1427 | : m_builtin_tab[i - m_custom_tab.size()] ); | |
1428 | } | |
1429 | ||
1430 | void drive_database::push_back(const drive_settings & src) | |
1431 | { | |
1432 | drive_settings dest; | |
1433 | dest.modelfamily = copy_string(src.modelfamily); | |
1434 | dest.modelregexp = copy_string(src.modelregexp); | |
1435 | dest.firmwareregexp = copy_string(src.firmwareregexp); | |
1436 | dest.warningmsg = copy_string(src.warningmsg); | |
1437 | dest.presets = copy_string(src.presets); | |
1438 | m_custom_tab.push_back(dest); | |
1439 | } | |
1440 | ||
1441 | const char * drive_database::copy_string(const char * src) | |
1442 | { | |
1443 | char * dest = new char[strlen(src)+1]; | |
1444 | try { | |
1445 | m_custom_strings.push_back(dest); | |
1446 | } | |
1447 | catch (...) { | |
1448 | delete [] dest; throw; | |
1449 | } | |
1450 | return strcpy(dest, src); | |
1451 | } | |
1452 | ||
1453 | ||
1454 | /// The drive database. | |
1455 | static drive_database knowndrives; | |
1456 | ||
1457 | ||
1458 | // Compile regular expression, print message on failure. | |
1459 | static bool compile(regular_expression & regex, const char *pattern) | |
1460 | { | |
1461 | if (!regex.compile(pattern, REG_EXTENDED)) { | |
1462 | pout("Internal error: unable to compile regular expression \"%s\": %s\n" | |
1463 | "Please inform smartmontools developers at " PACKAGE_BUGREPORT "\n", | |
1464 | pattern, regex.get_errmsg()); | |
1465 | return false; | |
1466 | } | |
1467 | return true; | |
1468 | } | |
1469 | ||
1470 | // Compile & match a regular expression. | |
1471 | static bool match(const char * pattern, const char * str) | |
1472 | { | |
1473 | regular_expression regex; | |
1474 | if (!compile(regex, pattern)) | |
1475 | return false; | |
1476 | return regex.full_match(str); | |
1477 | } | |
1478 | ||
832b75ed GG |
1479 | // Searches knowndrives[] for a drive with the given model number and firmware |
1480 | // string. If either the drive's model or firmware strings are not set by the | |
2127e193 GI |
1481 | // manufacturer then values of NULL may be used. Returns the entry of the |
1482 | // first match in knowndrives[] or 0 if no match if found. | |
1483 | const drive_settings * lookup_drive(const char * model, const char * firmware) | |
832b75ed | 1484 | { |
2127e193 GI |
1485 | if (!model) |
1486 | model = ""; | |
1487 | if (!firmware) | |
1488 | firmware = ""; | |
832b75ed | 1489 | |
2127e193 GI |
1490 | for (unsigned i = 0; i < knowndrives.size(); i++) { |
1491 | // Check whether model matches the regular expression in knowndrives[i]. | |
1492 | if (!match(knowndrives[i].modelregexp, model)) | |
1493 | continue; | |
832b75ed | 1494 | |
2127e193 GI |
1495 | // Model matches, now check firmware. "" matches always. |
1496 | if (!( !*knowndrives[i].firmwareregexp | |
1497 | || match(knowndrives[i].firmwareregexp, firmware))) | |
1498 | continue; | |
832b75ed | 1499 | |
2127e193 GI |
1500 | // Found |
1501 | return &knowndrives[i]; | |
832b75ed GG |
1502 | } |
1503 | ||
2127e193 GI |
1504 | // Not found |
1505 | return 0; | |
832b75ed GG |
1506 | } |
1507 | ||
2127e193 | 1508 | // Parse '-v' and '-F' options in preset string, return false on error. |
bed94269 GI |
1509 | static bool parse_presets(const char * presets, ata_vendor_attr_defs & defs, |
1510 | unsigned char & fix_firmwarebug) | |
2127e193 GI |
1511 | { |
1512 | for (int i = 0; ; ) { | |
1513 | i += strspn(presets+i, " \t"); | |
1514 | if (!presets[i]) | |
1515 | break; | |
1516 | char opt, arg[40+1+13]; int len = -1; | |
1517 | if (!(sscanf(presets+i, "-%c %40[^ ]%n", &opt, arg, &len) >= 2 && len > 0)) | |
1518 | return false; | |
1519 | if (opt == 'v') { | |
bed94269 GI |
1520 | // Parse "-v N,format[,name]" |
1521 | if (!parse_attribute_def(arg, defs, PRIOR_DATABASE)) | |
2127e193 | 1522 | return false; |
2127e193 GI |
1523 | } |
1524 | else if (opt == 'F') { | |
1525 | unsigned char fix; | |
1526 | if (!strcmp(arg, "samsung")) | |
1527 | fix = FIX_SAMSUNG; | |
1528 | else if (!strcmp(arg, "samsung2")) | |
1529 | fix = FIX_SAMSUNG2; | |
1530 | else if (!strcmp(arg, "samsung3")) | |
1531 | fix = FIX_SAMSUNG3; | |
1532 | else | |
1533 | return false; | |
1534 | // Set only if not set by user | |
1535 | if (fix_firmwarebug == FIX_NOTSPECIFIED) | |
1536 | fix_firmwarebug = fix; | |
1537 | } | |
1538 | else | |
1539 | return false; | |
832b75ed | 1540 | |
2127e193 GI |
1541 | i += len; |
1542 | } | |
1543 | return true; | |
1544 | } | |
1545 | ||
1546 | // Shows one entry of knowndrives[], returns #errors. | |
1547 | static int showonepreset(const drive_settings * dbentry) | |
1548 | { | |
832b75ed | 1549 | // Basic error check |
2127e193 GI |
1550 | if (!( dbentry |
1551 | && dbentry->modelfamily | |
1552 | && dbentry->modelregexp && *dbentry->modelregexp | |
1553 | && dbentry->firmwareregexp | |
1554 | && dbentry->warningmsg | |
1555 | && dbentry->presets )) { | |
1556 | pout("Invalid drive database entry. Please report\n" | |
832b75ed | 1557 | "this error to smartmontools developers at " PACKAGE_BUGREPORT ".\n"); |
2127e193 | 1558 | return 1; |
832b75ed GG |
1559 | } |
1560 | ||
2127e193 GI |
1561 | // print and check model and firmware regular expressions |
1562 | int errcnt = 0; | |
1563 | regular_expression regex; | |
1564 | pout("%-*s %s\n", TABLEPRINTWIDTH, "MODEL REGEXP:", dbentry->modelregexp); | |
1565 | if (!compile(regex, dbentry->modelregexp)) | |
1566 | errcnt++; | |
832b75ed | 1567 | |
2127e193 GI |
1568 | pout("%-*s %s\n", TABLEPRINTWIDTH, "FIRMWARE REGEXP:", *dbentry->firmwareregexp ? |
1569 | dbentry->firmwareregexp : ".*"); // preserve old output (TODO: Change) | |
1570 | if (*dbentry->firmwareregexp && !compile(regex, dbentry->firmwareregexp)) | |
1571 | errcnt++; | |
1572 | ||
1573 | pout("%-*s %s\n", TABLEPRINTWIDTH, "MODEL FAMILY:", dbentry->modelfamily); | |
1574 | ||
1575 | // if there are any presets, then show them | |
1576 | unsigned char fix_firmwarebug = 0; | |
1577 | bool first_preset = true; | |
1578 | if (*dbentry->presets) { | |
bed94269 GI |
1579 | ata_vendor_attr_defs defs; |
1580 | if (!parse_presets(dbentry->presets, defs, fix_firmwarebug)) { | |
2127e193 GI |
1581 | pout("Syntax error in preset option string \"%s\"\n", dbentry->presets); |
1582 | errcnt++; | |
1583 | } | |
1584 | for (int i = 0; i < MAX_ATTRIBUTE_NUM; i++) { | |
bed94269 | 1585 | if (defs[i].priority != PRIOR_DEFAULT) { |
2127e193 | 1586 | // Use leading zeros instead of spaces so that everything lines up. |
bed94269 GI |
1587 | pout("%-*s %03d %s\n", TABLEPRINTWIDTH, first_preset ? "ATTRIBUTE OPTIONS:" : "", |
1588 | i, ata_get_smart_attr_name(i, defs).c_str()); | |
2127e193 GI |
1589 | first_preset = false; |
1590 | } | |
1591 | } | |
832b75ed | 1592 | } |
2127e193 | 1593 | if (first_preset) |
832b75ed GG |
1594 | pout("%-*s %s\n", TABLEPRINTWIDTH, "ATTRIBUTE OPTIONS:", "None preset; no -v options are required."); |
1595 | ||
2127e193 GI |
1596 | // describe firmwarefix |
1597 | if (fix_firmwarebug) { | |
1598 | const char * fixdesc; | |
1599 | switch (fix_firmwarebug) { | |
1600 | case FIX_SAMSUNG: | |
1601 | fixdesc = "Fixes byte order in some SMART data (same as -F samsung)"; | |
1602 | break; | |
1603 | case FIX_SAMSUNG2: | |
1604 | fixdesc = "Fixes byte order in some SMART data (same as -F samsung2)"; | |
1605 | break; | |
1606 | case FIX_SAMSUNG3: | |
1607 | fixdesc = "Fixes completed self-test reported as in progress (same as -F samsung3)"; | |
1608 | break; | |
1609 | default: | |
1610 | fixdesc = "UNKNOWN"; errcnt++; | |
1611 | break; | |
1612 | } | |
1613 | pout("%-*s %s\n", TABLEPRINTWIDTH, "OTHER PRESETS:", fixdesc); | |
832b75ed | 1614 | } |
2127e193 | 1615 | |
832b75ed | 1616 | // Print any special warnings |
2127e193 GI |
1617 | if (*dbentry->warningmsg) |
1618 | pout("%-*s %s\n", TABLEPRINTWIDTH, "WARNINGS:", dbentry->warningmsg); | |
1619 | return errcnt; | |
832b75ed GG |
1620 | } |
1621 | ||
1622 | // Shows all presets for drives in knowndrives[]. | |
2127e193 GI |
1623 | // Returns #syntax errors. |
1624 | int showallpresets() | |
1625 | { | |
832b75ed GG |
1626 | // loop over all entries in the knowndrives[] table, printing them |
1627 | // out in a nice format | |
2127e193 GI |
1628 | int errcnt = 0; |
1629 | for (unsigned i = 0; i < knowndrives.size(); i++) { | |
1630 | errcnt += showonepreset(&knowndrives[i]); | |
832b75ed GG |
1631 | pout("\n"); |
1632 | } | |
1633 | ||
2127e193 GI |
1634 | pout("Total number of entries :%5u\n" |
1635 | "Entries read from file(s):%5u\n\n", | |
1636 | knowndrives.size(), knowndrives.custom_size()); | |
1637 | ||
832b75ed GG |
1638 | pout("For information about adding a drive to the database see the FAQ on the\n"); |
1639 | pout("smartmontools home page: " PACKAGE_HOMEPAGE "\n"); | |
2127e193 GI |
1640 | |
1641 | if (errcnt > 0) | |
1642 | pout("\nFound %d syntax error(s) in database.\n" | |
1643 | "Please inform smartmontools developers at " PACKAGE_BUGREPORT "\n", errcnt); | |
1644 | return errcnt; | |
832b75ed GG |
1645 | } |
1646 | ||
1647 | // Shows all matching presets for a drive in knowndrives[]. | |
1648 | // Returns # matching entries. | |
2127e193 GI |
1649 | int showmatchingpresets(const char *model, const char *firmware) |
1650 | { | |
832b75ed GG |
1651 | int cnt = 0; |
1652 | const char * firmwaremsg = (firmware ? firmware : "(any)"); | |
832b75ed | 1653 | |
2127e193 GI |
1654 | for (unsigned i = 0; i < knowndrives.size(); i++) { |
1655 | if (!match(knowndrives[i].modelregexp, model)) | |
832b75ed | 1656 | continue; |
2127e193 GI |
1657 | if ( firmware && *knowndrives[i].firmwareregexp |
1658 | && !match(knowndrives[i].firmwareregexp, firmware)) | |
832b75ed | 1659 | continue; |
2127e193 | 1660 | // Found |
832b75ed GG |
1661 | if (++cnt == 1) |
1662 | pout("Drive found in smartmontools Database. Drive identity strings:\n" | |
1663 | "%-*s %s\n" | |
1664 | "%-*s %s\n" | |
1665 | "match smartmontools Drive Database entry:\n", | |
1666 | TABLEPRINTWIDTH, "MODEL:", model, TABLEPRINTWIDTH, "FIRMWARE:", firmwaremsg); | |
1667 | else if (cnt == 2) | |
1668 | pout("and match these additional entries:\n"); | |
1669 | showonepreset(&knowndrives[i]); | |
1670 | pout("\n"); | |
1671 | } | |
832b75ed GG |
1672 | if (cnt == 0) |
1673 | pout("No presets are defined for this drive. Its identity strings:\n" | |
1674 | "MODEL: %s\n" | |
1675 | "FIRMWARE: %s\n" | |
1676 | "do not match any of the known regular expressions.\n", | |
1677 | model, firmwaremsg); | |
1678 | return cnt; | |
1679 | } | |
1680 | ||
1681 | // Shows the presets (if any) that are available for the given drive. | |
2127e193 GI |
1682 | void show_presets(const ata_identify_device * drive, bool fix_swapped_id) |
1683 | { | |
832b75ed GG |
1684 | char model[MODEL_STRING_LENGTH+1], firmware[FIRMWARE_STRING_LENGTH+1]; |
1685 | ||
1686 | // get the drive's model/firmware strings | |
2127e193 GI |
1687 | format_ata_string(model, drive->model, MODEL_STRING_LENGTH, fix_swapped_id); |
1688 | format_ata_string(firmware, drive->fw_rev, FIRMWARE_STRING_LENGTH, fix_swapped_id); | |
832b75ed GG |
1689 | |
1690 | // and search to see if they match values in the table | |
2127e193 GI |
1691 | const drive_settings * dbentry = lookup_drive(model, firmware); |
1692 | if (!dbentry) { | |
832b75ed GG |
1693 | // no matches found |
1694 | pout("No presets are defined for this drive. Its identity strings:\n" | |
1695 | "MODEL: %s\n" | |
1696 | "FIRMWARE: %s\n" | |
1697 | "do not match any of the known regular expressions.\n" | |
1698 | "Use -P showall to list all known regular expressions.\n", | |
1699 | model, firmware); | |
1700 | return; | |
1701 | } | |
1702 | ||
1703 | // We found a matching drive. Print out all information about it. | |
1704 | pout("Drive found in smartmontools Database. Drive identity strings:\n" | |
1705 | "%-*s %s\n" | |
1706 | "%-*s %s\n" | |
1707 | "match smartmontools Drive Database entry:\n", | |
1708 | TABLEPRINTWIDTH, "MODEL:", model, TABLEPRINTWIDTH, "FIRMWARE:", firmware); | |
2127e193 | 1709 | showonepreset(dbentry); |
832b75ed GG |
1710 | } |
1711 | ||
1712 | // Sets preset vendor attribute options in opts by finding the entry | |
1713 | // (if any) for the given drive in knowndrives[]. Values that have | |
2127e193 GI |
1714 | // already been set in opts will not be changed. Returns false if drive |
1715 | // not recognized. | |
bed94269 | 1716 | bool apply_presets(const ata_identify_device *drive, ata_vendor_attr_defs & defs, |
2127e193 GI |
1717 | unsigned char & fix_firmwarebug, bool fix_swapped_id) |
1718 | { | |
832b75ed | 1719 | // get the drive's model/firmware strings |
2127e193 GI |
1720 | char model[MODEL_STRING_LENGTH+1], firmware[FIRMWARE_STRING_LENGTH+1]; |
1721 | format_ata_string(model, drive->model, MODEL_STRING_LENGTH, fix_swapped_id); | |
1722 | format_ata_string(firmware, drive->fw_rev, FIRMWARE_STRING_LENGTH, fix_swapped_id); | |
832b75ed GG |
1723 | |
1724 | // Look up the drive in knowndrives[]. | |
2127e193 GI |
1725 | const drive_settings * dbentry = lookup_drive(model, firmware); |
1726 | if (!dbentry) | |
1727 | return false; | |
1728 | ||
1729 | if (*dbentry->presets) { | |
1730 | // Apply presets | |
bed94269 | 1731 | if (!parse_presets(dbentry->presets, defs, fix_firmwarebug)) |
2127e193 GI |
1732 | pout("Syntax error in preset option string \"%s\"\n", dbentry->presets); |
1733 | } | |
1734 | return true; | |
1735 | } | |
1736 | ||
1737 | ||
1738 | ///////////////////////////////////////////////////////////////////////////// | |
1739 | // Parser for drive database files | |
1740 | ||
1741 | // Abstract pointer to read file input. | |
1742 | // Operations supported: c = *p; c = p[1]; ++p; | |
1743 | class stdin_iterator | |
1744 | { | |
1745 | public: | |
1746 | explicit stdin_iterator(FILE * f) | |
1747 | : m_f(f) { get(); get(); } | |
1748 | ||
1749 | stdin_iterator & operator++() | |
1750 | { get(); return *this; } | |
1751 | ||
1752 | char operator*() const | |
1753 | { return m_c; } | |
1754 | ||
1755 | char operator[](int i) const | |
1756 | { | |
1757 | if (i != 1) | |
1758 | fail(); | |
1759 | return m_next; | |
1760 | } | |
1761 | ||
1762 | private: | |
1763 | FILE * m_f; | |
1764 | char m_c, m_next; | |
1765 | void get(); | |
1766 | void fail() const; | |
1767 | }; | |
1768 | ||
1769 | void stdin_iterator::get() | |
1770 | { | |
1771 | m_c = m_next; | |
1772 | int ch = getc(m_f); | |
1773 | m_next = (ch != EOF ? ch : 0); | |
1774 | } | |
1775 | ||
1776 | void stdin_iterator::fail() const | |
1777 | { | |
1778 | throw std::runtime_error("stdin_iterator: wrong usage"); | |
1779 | } | |
1780 | ||
1781 | ||
1782 | // Use above as parser input 'pointer'. Can easily be changed later | |
1783 | // to e.g. 'const char *' if above is too slow. | |
1784 | typedef stdin_iterator parse_ptr; | |
1785 | ||
1786 | // Skip whitespace and comments. | |
1787 | static parse_ptr skip_white(parse_ptr src, const char * path, int & line) | |
1788 | { | |
1789 | for ( ; ; ++src) switch (*src) { | |
1790 | case ' ': case '\t': | |
1791 | continue; | |
1792 | ||
1793 | case '\n': | |
1794 | ++line; | |
1795 | continue; | |
1796 | ||
1797 | case '/': | |
1798 | switch (src[1]) { | |
1799 | case '/': | |
1800 | // skip '// comment' | |
1801 | ++src; ++src; | |
1802 | while (*src && *src != '\n') | |
1803 | ++src; | |
1804 | if (*src) | |
1805 | ++line; | |
1806 | break; | |
1807 | case '*': | |
1808 | // skip '/* comment */' | |
1809 | ++src; ++src; | |
1810 | for (;;) { | |
1811 | if (!*src) { | |
1812 | pout("%s(%d): Missing '*/'\n", path, line); | |
1813 | return src; | |
1814 | } | |
1815 | char c = *src; ++src; | |
1816 | if (c == '\n') | |
1817 | ++line; | |
1818 | else if (c == '*' && *src == '/') | |
1819 | break; | |
1820 | } | |
1821 | break; | |
1822 | default: | |
1823 | return src; | |
832b75ed | 1824 | } |
2127e193 GI |
1825 | continue; |
1826 | ||
1827 | default: | |
1828 | return src; | |
1829 | } | |
1830 | } | |
1831 | ||
1832 | // Info about a token. | |
1833 | struct token_info | |
1834 | { | |
1835 | char type; | |
1836 | int line; | |
1837 | std::string value; | |
1838 | ||
1839 | token_info() : type(0), line(0) { } | |
1840 | }; | |
1841 | ||
1842 | // Get next token. | |
1843 | static parse_ptr get_token(parse_ptr src, token_info & token, const char * path, int & line) | |
1844 | { | |
1845 | src = skip_white(src, path, line); | |
1846 | switch (*src) { | |
1847 | case '{': case '}': case ',': | |
1848 | // Simple token | |
1849 | token.type = *src; token.line = line; | |
1850 | ++src; | |
1851 | break; | |
1852 | ||
1853 | case '"': | |
1854 | // String constant | |
1855 | token.type = '"'; token.line = line; | |
1856 | token.value = ""; | |
1857 | do { | |
1858 | for (++src; *src != '"'; ++src) { | |
1859 | char c = *src; | |
1860 | if (!c || c == '\n' || (c == '\\' && !src[1])) { | |
1861 | pout("%s(%d): Missing terminating '\"'\n", path, line); | |
1862 | token.type = '?'; token.line = line; | |
1863 | return src; | |
1864 | } | |
1865 | if (c == '\\') { | |
1866 | c = *++src; | |
1867 | switch (c) { | |
1868 | case 'n' : c = '\n'; break; | |
1869 | case '\n': ++line; break; | |
1870 | case '\\': case '"': break; | |
1871 | default: | |
1872 | pout("%s(%d): Unknown escape sequence '\\%c'\n", path, line, c); | |
1873 | token.type = '?'; token.line = line; | |
1874 | continue; | |
1875 | } | |
1876 | } | |
1877 | token.value += c; | |
1878 | } | |
1879 | // Lookahead to detect string constant concatentation | |
1880 | src = skip_white(++src, path, line); | |
1881 | } while (*src == '"'); | |
1882 | break; | |
1883 | ||
1884 | case 0: | |
1885 | // EOF | |
1886 | token.type = 0; token.line = line; | |
1887 | break; | |
1888 | ||
1889 | default: | |
1890 | pout("%s(%d): Syntax error, invalid char '%c'\n", path, line, *src); | |
1891 | token.type = '?'; token.line = line; | |
1892 | while (*src && *src != '\n') | |
1893 | ++src; | |
1894 | break; | |
1895 | } | |
1896 | ||
1897 | return src; | |
1898 | } | |
1899 | ||
1900 | // Parse drive database from abstract input pointer. | |
1901 | static bool parse_drive_database(parse_ptr src, drive_database & db, const char * path) | |
1902 | { | |
1903 | int state = 0, field = 0; | |
1904 | std::string values[5]; | |
1905 | bool ok = true; | |
1906 | ||
1907 | token_info token; int line = 1; | |
1908 | src = get_token(src, token, path, line); | |
1909 | for (;;) { | |
1910 | // EOF is ok after '}', trailing ',' is also allowed. | |
1911 | if (!token.type && (state == 0 || state == 4)) | |
1912 | break; | |
1913 | ||
1914 | // Check expected token | |
1915 | const char expect[] = "{\",},"; | |
1916 | if (token.type != expect[state]) { | |
1917 | if (token.type != '?') | |
1918 | pout("%s(%d): Syntax error, '%c' expected\n", path, token.line, expect[state]); | |
1919 | ok = false; | |
1920 | // Skip to next entry | |
1921 | while (token.type && token.type != '{') | |
1922 | src = get_token(src, token, path, line); | |
1923 | state = 0; | |
1924 | if (token.type) | |
1925 | continue; | |
1926 | break; | |
832b75ed | 1927 | } |
2127e193 GI |
1928 | |
1929 | // Interpret parser state | |
1930 | switch (state) { | |
1931 | case 0: // ... ^{...} | |
1932 | state = 1; field = 0; | |
1933 | break; | |
1934 | case 1: // {... ^"..." ...} | |
1935 | switch (field) { | |
1936 | case 1: case 2: | |
1937 | if (!token.value.empty()) { | |
1938 | regular_expression regex; | |
1939 | if (!regex.compile(token.value.c_str(), REG_EXTENDED)) { | |
1940 | pout("%s(%d): Error in regular expression: %s\n", path, token.line, regex.get_errmsg()); | |
1941 | ok = false; | |
1942 | } | |
1943 | } | |
1944 | else if (field == 1) { | |
1945 | pout("%s(%d): Missing regular expression for drive model\n", path, token.line); | |
1946 | ok = false; | |
1947 | } | |
1948 | break; | |
1949 | case 4: | |
1950 | if (!token.value.empty()) { | |
bed94269 GI |
1951 | ata_vendor_attr_defs defs; unsigned char fix = 0; |
1952 | if (!parse_presets(token.value.c_str(), defs, fix)) { | |
2127e193 GI |
1953 | pout("%s(%d): Syntax error in preset option string\n", path, token.line); |
1954 | ok = false; | |
1955 | } | |
1956 | } | |
1957 | break; | |
1958 | } | |
1959 | values[field] = token.value; | |
1960 | state = (++field < 5 ? 2 : 3); | |
1961 | break; | |
1962 | case 2: // {... "..."^, ...} | |
1963 | state = 1; | |
1964 | break; | |
1965 | case 3: // {...^}, ... | |
1966 | { | |
1967 | drive_settings entry; | |
1968 | entry.modelfamily = values[0].c_str(); | |
1969 | entry.modelregexp = values[1].c_str(); | |
1970 | entry.firmwareregexp = values[2].c_str(); | |
1971 | entry.warningmsg = values[3].c_str(); | |
1972 | entry.presets = values[4].c_str(); | |
1973 | db.push_back(entry); | |
1974 | } | |
1975 | state = 4; | |
1976 | break; | |
1977 | case 4: // {...}^, ... | |
1978 | state = 0; | |
1979 | break; | |
1980 | default: | |
1981 | pout("Bad state %d\n", state); | |
1982 | return false; | |
1983 | } | |
1984 | src = get_token(src, token, path, line); | |
832b75ed | 1985 | } |
2127e193 GI |
1986 | return ok; |
1987 | } | |
1988 | ||
1989 | // Read drive database from file. | |
1990 | bool read_drive_database(const char * path) | |
1991 | { | |
1992 | stdio_file f(path, "r"); | |
1993 | if (!f) { | |
1994 | pout("%s: cannot open drive database file\n", path); | |
1995 | return false; | |
1996 | } | |
1997 | ||
1998 | return parse_drive_database(parse_ptr(f), knowndrives, path); | |
1999 | } | |
2000 | ||
2001 | // Read drive databases from standard places. | |
2002 | bool read_default_drive_databases() | |
2003 | { | |
2004 | #ifndef _WIN32 | |
2005 | // Read file for local additions: /{,usr/local/}etc/smart_drivedb.h | |
2006 | static const char db1[] = SMARTMONTOOLS_SYSCONFDIR"/smart_drivedb.h"; | |
2007 | #else | |
2008 | static const char db1[] = "./smart_drivedb.h"; | |
2009 | #endif | |
2010 | if (!access(db1, 0)) { | |
2011 | if (!read_drive_database(db1)) | |
2012 | return false; | |
2013 | } | |
2014 | ||
2015 | #ifdef SMARTMONTOOLS_DRIVEDBDIR | |
2016 | // Read file from package: // /usr/{,local/}share/smartmontools/drivedb.h | |
2017 | static const char db2[] = SMARTMONTOOLS_DRIVEDBDIR"/drivedb.h"; | |
2018 | if (!access(db2, 0)) { | |
2019 | if (!read_drive_database(db2)) | |
2020 | return false; | |
2021 | } | |
2022 | else | |
2023 | #endif | |
2024 | { | |
2025 | // Append builtin table. | |
2026 | knowndrives.append(builtin_knowndrives, | |
2027 | sizeof(builtin_knowndrives)/sizeof(builtin_knowndrives[0])); | |
2028 | } | |
2029 | ||
2030 | return true; | |
832b75ed | 2031 | } |