From 6b80b4d2c7b80037c557bae53e7ff42cfda4a2cb Mon Sep 17 00:00:00 2001 From: Jonathan Dowland Date: Tue, 26 Jan 2016 22:48:06 +0000 Subject: [PATCH] Imported Upstream version 6.4+svn4214 --- ChangeLog | 295 +++++++++++++- INSTALL | 4 +- Makefile.am | 237 ++++++----- NEWS | 22 +- README | 4 +- atacmdnames.cpp | 4 +- atacmdnames.h | 4 +- atacmds.cpp | 292 +++---------- atacmds.h | 16 +- ataidentify.cpp | 4 +- ataidentify.h | 4 +- ataprint.cpp | 60 ++- ataprint.h | 4 +- autogen.sh | 119 ++---- cciss.cpp | 7 +- configure.ac | 151 ++++--- dev_areca.cpp | 8 +- dev_areca.h | 11 +- dev_ata_cmd_set.cpp | 4 +- dev_ata_cmd_set.h | 4 +- dev_interface.cpp | 4 +- dev_interface.h | 8 +- dev_legacy.cpp | 6 +- dev_tunnelled.h | 4 +- drivedb.h | 384 ++++++++++++++---- examplescripts/README | 4 +- int64.h | 4 +- knowndrives.cpp | 163 ++++++-- knowndrives.h | 14 +- os_darwin.cpp | 47 ++- os_darwin.h | 4 +- os_darwin/SMART.in | 4 +- os_darwin/pkg/Distribution.in | 21 + os_darwin/pkg/PackageInfo.in | 6 + os_darwin/pkg/installer/README.html | 24 ++ .../root/usr/local/sbin/smart-pkg-uninstall | 40 ++ os_freebsd.cpp | 67 +-- os_freebsd.h | 4 +- os_generic.cpp | 4 +- os_generic.h | 4 +- os_linux.cpp | 47 +-- os_linux.h | 4 +- os_netbsd.cpp | 18 +- os_netbsd.h | 4 +- os_openbsd.cpp | 18 +- os_openbsd.h | 4 +- os_os2.cpp | 4 +- os_os2.h | 4 +- os_qnxnto.h | 4 +- os_solaris.cpp | 19 +- os_solaris.h | 4 +- os_win32.cpp | 158 +++---- os_win32/daemon_win32.cpp | 4 +- os_win32/daemon_win32.h | 4 +- os_win32/default.manifest | 27 ++ os_win32/installer.nsi | 318 +++++++++------ os_win32/runcmd.c | 4 +- os_win32/runcmda.exe.manifest | 18 - os_win32/runcmdu.exe.manifest | 18 - os_win32/syslog.h | 4 +- os_win32/syslog_win32.cpp | 8 +- os_win32/syslogevt.mc | 4 +- os_win32/update-smart-drivedb.nsi | 4 +- os_win32/wbemcli_small.h | 2 +- os_win32/wmiquery.cpp | 4 +- os_win32/wmiquery.h | 8 +- os_win32/wtssendmsg.c | 6 +- scsiata.cpp | 21 +- scsicmds.cpp | 174 ++++---- scsicmds.h | 8 +- scsiprint.cpp | 287 +++++++------ scsiprint.h | 4 +- smartctl.8.in | 6 +- smartctl.cpp | 14 +- smartctl.h | 4 +- smartd.8.in | 6 +- smartd.conf | 4 +- smartd.cpp | 82 ++-- smartd.initd.in | 4 +- update-smart-drivedb.8.in | 83 +++- update-smart-drivedb.in | 352 +++++++++++++--- utility.cpp | 15 +- utility.h | 12 +- 83 files changed, 2392 insertions(+), 1475 deletions(-) create mode 100644 os_darwin/pkg/Distribution.in create mode 100644 os_darwin/pkg/PackageInfo.in create mode 100644 os_darwin/pkg/installer/README.html create mode 100755 os_darwin/pkg/root/usr/local/sbin/smart-pkg-uninstall create mode 100644 os_win32/default.manifest delete mode 100644 os_win32/runcmda.exe.manifest delete mode 100644 os_win32/runcmdu.exe.manifest diff --git a/ChangeLog b/ChangeLog index d5ac441..2afff63 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,4 +1,297 @@ -$Id: ChangeLog 4109 2015-06-04 16:30:15Z chrfranke $ +$Id: ChangeLog 4214 2016-01-24 22:53:37Z samm2 $ + +2016-01-24 Alex Samorukov + + os_freebsd.cpp: fix possible reallocf with 0 bytes arg (ticket #640) + drivedb.h: add Corsair Extreme SSD (ticket #642) + os_darwin.cpp: fix error reporting if open fails + +2016-01-23 Alex Samorukov + + os_darwin.cpp: do not print bogus memory allocation error message if + there are no devices found + +2016-01-22 Christian Franke + + Various fixes suggested by clang analyser (ticket #640): + dev_areca.cpp: Fix check of ARCMSR_READ_RQBUFFER result. + knowndrives.cpp: Add missing member initialization. + smartd.cpp: Fix crash on missing argument to '-s' directive. + Add missing variable initialization. Remove redundant assignment. + +2016-01-21 Alex Samorukov + + drivedb.h: Added ADATA SP550 SSD (ticket #638) + os_freebsd.cpp: Reduce variable scope where possible (cppcheck: variableScope) + os_openbsd/os_netbsd - removed never used warning code defines (cppcheck) + +2016-01-21 Christian Franke + + ataprint.cpp, smartd.cpp: Don't issue SCT commands if ATA Security + is locked (ticket #637). + +2016-01-19 Alex Samorukov + + drivedb.h: + - Samsung PM871 SSD family (ticket #636) + - Fixed detection for Samsung SSD 850 EVO mSATA 120GB (ticket #635) + - Fixed Western Digital Caviar Black regexp, extended WD Black (ticket #631) + +2016-01-06 Christian Franke + + drivedb.h: + - SandForce Driven SSDs: Extra warning entry for buggy Corsair Force LS + (ticket #628) + - Innodisk 3MG2-P SSDs: 1.8" variant + - Innodisk 3ME3 SSDs + - USB: Seagate Expansion Portable (0x0bc2:0x2322) (ticket #627) + - USB: Jess-Link (0x0dbf:0x9001) + +2016-01-01 Christian Franke + + Happy New Year! Update copyright year in version info. + +2015-12-19 Christian Franke + + Makefile.am: Fix path of 'smart-pkg-uninstall' (Regression from r4190). + + update-smart-drivedb.8.in: Fix platform specific formatting. + +2015-12-18 Alex Samorukov + + os_netbsd.cpp, os_openbsd.cpp: fix ioctl returtn value check + os_darwin.cpp: fix error handling + os_darwin: use /usr/local/ prefix to install on 10.11 (El Capitan) + +2015-12-16 Douglas Gilbert + + scsiprint.cpp: stop tape drive looking for Solid State media + log page (ticket #314). + +2015-12-14 Douglas Gilbert + + scsiprint.cpp: fix compiler warning for is_tape. Clean code around + handling of tape drives. + +2015-12-14 Christian Franke + + drivedb.h: + - Intel 320 Series SSDs: 1.8" microSATA + - Intel 53x and Pro 2500 Series SSDs: Rename, add 535 (ticket #625), + add Pro 2500 + - Intel 730 and DC S35x0/3610/3700 Series SSDs: Rename, + add S3510/3610, 1.2TB, 1.6TB + - USB: LaCie (0x059f:0x106f) (ticket #624) + - USB: WD My Passport (0x1058:0x071a, 0x1058:0x0816) + - USB: Initio (0x13fd:0x1650) + - USB: Unknown (0xabcd:0x6103) + + update-smart-drivedb.in: Add '-s SMARTCTL' option. + update-smart-drivedb.8.in: Document it. + +2015-12-07 Christian Franke + + configure.ac: Append 'svn' to list of download tools. + + update-smart-drivedb.in: Use HTTPS download by default. + Add options '-t TOOL', '-u LOCATION', '--cacert FILE', + '--capath DIR', '--insecure' and '--dryrun'. + Add 'svn' as new download tool. + Ignore differences in SVN Id string (re-added). + Remove usage of 'which' command. + + update-smart-drivedb.8.in: Document the new options. + +2015-11-23 Christian Franke + + atacmds.cpp: parse_attribute_def(): Init buffers before sscanf() call + (cppcheck-1.71: uninitvar). + + scsiprint.cpp: Fix GLTSD bit set/cleared info messages (ticket #621). + +2015-11-22 Christian Franke + + Makefile.am: Add NEWS file to svnversion.h target. + + os_win32/installer.nsi: Select 64-bit version on 64-bit Windows. + Fix installation of runcmda.exe. Update links. + +2015-11-15 Christian Franke + + configure.ac: Check whether MinGW adds an application manifest. + + Makefile.am: Add default manifest for MinGW builds. + + os_win32/default.manifest: New default application manifest. + Remove external application manifests. + + os_win32/installer.nsi: Use macros from 'LogicLib.nsh' where possible. + Add missing MessageBox /SD options. + Remove external application manifests. + +2015-11-07 Christian Franke + + drivedb.h: + - Micron M500DC/M510DC Enterprise SSDs: Rename, add M510DC + - SandForce Driven SSDs: Mushkin Chronos 7mm/MX/G2, Enhanced ECO2 + - Innodisk 3MG2-P SSDs + - SiliconMotion based SSDs: Crucial BX100 (ticket #597) + +2015-10-31 Christian Franke + + atacmds.cpp, atacmds.h, knowndrives.cpp, knowndrives.h: + Read default SMART attribute settings from drivedb.h (ticket #465). + Remove hard-coded attribute names and format settings. + + drivedb.h: Uncomment default settings to create the "DEFAULT" entry. + Add ",HDD" or ",SSD" to HDD/SSD specific settings. + + smartctl.cpp, smartd.cpp: Use new database initialization function. + + Create branch RELEASE_6_4_DRIVEDB with last drivedb.h file + compatible with smartmontools 6.4. + +2015-10-22 Paul Grabinar + + drivedb.h: + - SandForce Driven SSDs: OCZ RevoDrive 350, Z-Drive 4500 + - Indilinx Barefoot 3 based SSDs: Add attributes, + OCZ ARC 100, Saber 1000, Vector 180, Vertex 460A + - OCZ Intrepid 3000 SSDs: Intrepid 3700 + - OCZ Trion + +2015-10-20 Christian Franke + + Reduce variable scope where possible (cppcheck: variableScope). + + Makefile.am: Remove *.s from files used to generate svnversion.h. + +2015-10-18 Alex Samorukov + + fixes suggested by cppcheck: + Check realloc result to avoid memory leak (memleakOnRealloc) + Fix printf() signednsess (invalidPrintfArgType_sint) + +2015-10-17 Christian Franke + + Various fixes suggested by cppcheck: + Close FILE pointer before reopening it (cppcheck: publicAllocationError). + Add missing member initializations to ctors (cppcheck: uninitMemberVar). + Remove redundant nullptr check (cppcheck: nullPointerRedundantCheck). + Remove redundant assignments (cppcheck: redundantAssignment). + Clarify calculation precedence (cppcheck: clarifyCalculation). + Use C++-style casts for pointer types (cppcheck: cstyleCast). + Remove duplicate on both sides of '||' (cppcheck: duplicateExpression). + Declare ctors with one argument as 'explicit' + (cppcheck: noExplicitConstructor). + Remove unread variables and assignments (cppcheck: unreadVariable). + Fix signedness of sscanf() formats strings + (cppcheck: invalidScanfArgType_int). + +2015-10-14 Christian Franke + + configure.ac: Disable os_solaris_ata.o by default. + Add --with-solaris-sparc-ata option to enable. + Makefile.am: Exclude os_solaris_ata.s from source tarball + (Debian bug 729842). + os_solaris.cpp: Check for WITH_SOLARIS_SPARC_ATA instead of __sparc. + +2015-10-13 Christian Franke + + Makefile.am: Fix error handling in various shell scripts. + +2015-10-13 Casper Dik <...> + + os_solaris.cpp: Detect SATA devices as SCSI devices. This adds + support for auto detection of SATA devices behind SAT layer. + Set USCSI_SILENT flag to suppress /dev/console messages on command + error. + +2015-10-11 Christian Franke + + drivedb.h: SiliconMotion based SSDs: Transcend SSD370S, SSD420, + update attribute 245 (ticket #595, ticket #602). + +2015-10-10 Christian Franke + + Makefile.am: Use MKDIR_P to create directories + (available since automake 1.10). + + os_win32.cpp: Detect USB ID if WMI reports type name "SCSI" instead + of "USBSTOR". + Detect USB ID also if drive letter is specified as device name. + +2015-10-04 Christian Franke + + drivedb.h: + - USB: Genesys Logic (0x05e3:0x0735) + - USB: Addonics (0x0bf6:0x1001): unsupported (ticket #609) + - USB: Initio (0x13fd:0x3920) + - USB: JMicron JMS539 (0x152d:0x0539, 0x0100): Set from -d usbjmicron to + unsupported because some devices may require -d sat instead (ticket #552). + - USB: JMicron (0x152d:0x0565) (ticket #607) + - USB: VIA VL711 (0x2109:0x0711): unsupported (ticket #594) + - USB: Hitachi Touro Mobile (0x4971:0x1024) + +2015-09-25 Christian Franke + + scsiata.cpp: Ignore SAT ATA PASS-THROUGH fixed format sense data if no + ATA status bit is set (ticket #612). + +2015-09-23 Alex Samorukov + + drivedb.h: Innostor USB3.0 to SATAIII bridge (#611) + +2015-09-21 Alex Samorukov + + drivedb.h: decode 188 attribute for the "Seagate Enterprise Capacity + 3.5 HDD" drives family, (see #551). + +2015-09-04 Alex Samorukov + + Makefile.am: integrate darwin dmg build process to the Makefile + +2015-09-03 Alex Samorukov + + os_darwin: Initial import of the files required to build + OSX/smartmontools native package (see #555). + +2015-08-27 Alex Samorukov + + Homepage URL updated from the sourceforge to smartmontools.org (r4120) + +2015-08-26 Alex Samorukov + + os_darwin.cpp: Implement get_os_version_str() for the darwin. + +2015-08-17 Christian Franke + + scsiata.cpp: Ignore bogus SCSI sense_key if ATA status in + SAT ATA Return Descriptor indicates success (ticket #548). + +2015-08-08 Christian Franke + + os_win32.cpp: Fix get_os_version_str() for Windows >= 8.1. + Add Windows 10 Final. + +2015-08-02 Christian Franke + + configure.ac: Remove '--disable-drivedb', + '--enable-savestates', '--enable-attributelog'. + Print error message if used. + +2015-07-15 Christian Franke + + autogen.sh: Drop support for automake 1.7 - 1.9.x. + Rework search for automake-VERSION. + configure.ac: Drop support for autoconf 2.5x. + Drop support for automake 1.7 - 1.9.x. + Remove --with-docdir option. + +2015-06-24 Alex Samorukov + + drivedb.h: + - USB: SimpleTech 3.0 bridge (0x4971:0x8017), reported in #554 2015-06-04 Christian Franke diff --git a/INSTALL b/INSTALL index 49a6479..011622a 100644 --- a/INSTALL +++ b/INSTALL @@ -1,10 +1,10 @@ Smartmontools installation instructions ======================================= -$Id: INSTALL 4094 2015-05-27 21:41:17Z chrfranke $ +$Id: INSTALL 4120 2015-08-27 16:12:21Z samm2 $ Please also see the smartmontools home page: -http://smartmontools.sourceforge.net/ +http://www.smartmontools.org/ Table of contents: diff --git a/Makefile.am b/Makefile.am index dafe358..4812701 100644 --- a/Makefile.am +++ b/Makefile.am @@ -1,6 +1,6 @@ ## Process this file with automake to produce Makefile.in # -# $Id: Makefile.am 4102 2015-06-01 19:25:47Z chrfranke $ +# $Id: Makefile.am 4192 2015-12-19 13:59:40Z chrfranke $ # @SET_MAKE@ @@ -96,7 +96,6 @@ EXTRA_smartctl_SOURCES = \ os_qnxnto.h \ os_solaris.cpp \ os_solaris.h \ - os_solaris_ata.s \ os_win32.cpp \ os_generic.cpp \ os_generic.h \ @@ -111,8 +110,8 @@ EXTRA_smartctl_SOURCES = \ if OS_WIN32_MINGW -smartctl_LDADD += smartctl_res.o -smartctl_DEPENDENCIES += smartctl_res.o +smartctl_LDADD += smartctl_res.o $(os_win32_manifest) +smartctl_DEPENDENCIES += smartctl_res.o $(os_win32_manifest) endif @@ -156,7 +155,6 @@ EXTRA_smartd_SOURCES = \ os_qnxnto.h \ os_solaris.cpp \ os_solaris.h \ - os_solaris_ata.s \ os_win32.cpp \ os_generic.cpp \ os_generic.h \ @@ -177,11 +175,14 @@ smartd_SOURCES += \ os_win32/syslog_win32.cpp \ os_win32/syslog.h -smartd_LDADD += smartd_res.o -smartd_DEPENDENCIES += smartd_res.o +smartd_LDADD += smartd_res.o $(os_win32_manifest) +smartd_DEPENDENCIES += smartd_res.o $(os_win32_manifest) endif +# Exclude from source tarball +nodist_EXTRA_smartctl_SOURCES = os_solaris_ata.s +nodist_EXTRA_smartd_SOURCES = os_solaris_ata.s if NEED_GETOPT_LONG @@ -255,8 +256,8 @@ endif all-local: $(extra_MANS) install-man: $(extra_MANS) @$(NORMAL_INSTALL) - $(mkinstalldirs) '$(DESTDIR)$(mandir)/man4' - $(mkinstalldirs) '$(DESTDIR)$(mandir)/man1m' + $(MKDIR_P) '$(DESTDIR)$(mandir)/man4' + $(MKDIR_P) '$(DESTDIR)$(mandir)/man1m' for i in $(extra_MANS); do \ if test -f $(srcdir)/$$i; then file=$(srcdir)/$$i; \ else file=$$i; fi; \ @@ -319,7 +320,7 @@ sysconf_DATA = smartd.conf # If modified smartd.conf exists install smartd.conf.sample instead install-sysconfDATA: $(sysconf_DATA) - $(mkinstalldirs) '$(DESTDIR)$(sysconfdir)' + $(MKDIR_P) '$(DESTDIR)$(sysconfdir)' @s="$(srcdir)/smartd.conf"; \ f="$(DESTDIR)$(sysconfdir)/smartd.conf$(smartd_suffix)"; \ if test -z "$(smartd_suffix)" && test -f "$$f"; then \ @@ -365,10 +366,13 @@ EXTRA_DIST = \ os_darwin/SMART.in \ os_darwin/StartupParameters.plist \ os_darwin/English_Localizable.strings \ + os_darwin/pkg/PackageInfo.in \ + os_darwin/pkg/Distribution.in \ + os_darwin/pkg/installer/README.html \ + os_darwin/pkg/root/usr/local/sbin/smart-pkg-uninstall \ + os_win32/default.manifest \ os_win32/installer.nsi \ os_win32/runcmd.c \ - os_win32/runcmda.exe.manifest \ - os_win32/runcmdu.exe.manifest \ os_win32/smartctl_res.rc.in \ os_win32/smartd_res.rc.in \ os_win32/smartd_warning.cmd \ @@ -386,12 +390,15 @@ CLEANFILES = \ smartd.8 \ smartd.1m \ smartd.8.html \ + smartd.8.html.tmp \ smartd.8.txt \ smartctl.8 \ smartctl.1m \ smartctl.8.html \ + smartctl.8.html.tmp \ smartctl.8.txt \ smartd.conf.5.html \ + smartd.conf.5.html.tmp \ smartd.conf.5.txt \ smartd.initd \ smartd.freebsd.initd \ @@ -416,7 +423,6 @@ MAINTAINERCLEANFILES = \ $(srcdir)/depcomp \ $(srcdir)/install-sh \ $(srcdir)/missing \ - $(srcdir)/mkinstalldirs \ $(srcdir)/m4/pkg.m4 utility.o: svnversion.h @@ -424,7 +430,7 @@ utility.o: svnversion.h if IS_SVN_BUILD # Get version info from SVN svnversion.h: ChangeLog Makefile $(svn_deps) - @echo ' svn info | $$(VERSION_FROM_SVN_INFO) > $@' + @echo ' svn info | $$(VERSION_FROM_SVN_INFO) > $@' @echo '/* svnversion.h. Generated by Makefile from svn info. */' > $@ @(cd $(srcdir) \ && svnversion 2>/dev/null | sed -n 's,^\([0-9].*\),REV "\1",p' \ @@ -434,10 +440,10 @@ svnversion.h: ChangeLog Makefile $(svn_deps) else # SVN not available, guess version info from Id strings -svnversion.h: ChangeLog Makefile - @echo ' cat ChangeLog $$(SOURCES) | $$(VERSION_FROM_SVN_IDS) > $@' +svnversion.h: ChangeLog Makefile NEWS + @echo ' cat ChangeLog NEWS $$(SOURCES) | $$(VERSION_FROM_SVN_IDS) > $@' @echo '/* svnversion.h. Generated by Makefile from Id strings. */' > $@ - @(cd $(srcdir) && cat ChangeLog Makefile.am configure.ac smart*.in *.cpp *.h *.s) \ + @(cd $(srcdir) && cat ChangeLog NEWS Makefile.am configure.ac smart*.in *.cpp *.h) \ | sed -n 's,^.*\$$[I][d]: [^ ]* \([0-9][0-9]* [0-9][-0-9]* [0-9][:0-9]*\)[^:0-9][^$$]*\$$.*$$,\1,p' \ | sort -n -r \ | sed -n 'h;s,^\([^ ]*\) .*$$,REV "\1",p;g;s,^[^ ]* \([^ ]*\) .*$$,DATE "\1",p;g;s,^[^ ]* [^ ]* \([^ ]*\)$$,TIME "\1",p;q' \ @@ -472,15 +478,15 @@ SMART : os_darwin/SMART.in sed "s|/usr/sbin/|$(sbindir)/|" $< > $@ install-initdDATA-darwin: $(initd_DATA) - $(mkinstalldirs) $(DESTDIR)$(initddir) - $(mkinstalldirs) $(DESTDIR)$(initddir)/SMART - $(mkinstalldirs) $(DESTDIR)$(initddir)/SMART/Resources + $(MKDIR_P) $(DESTDIR)$(initddir) + $(MKDIR_P) $(DESTDIR)$(initddir)/SMART + $(MKDIR_P) $(DESTDIR)$(initddir)/SMART/Resources $(INSTALL_SCRIPT) $(top_builddir)/SMART $(DESTDIR)$(initddir)/SMART $(INSTALL_DATA) $(srcdir)/os_darwin/StartupParameters.plist \ $(DESTDIR)$(initddir)/SMART/StartupParameters.plist for i in English ; do \ RDIR=$(DESTDIR)$(initddir)/SMART/Resources/$${i}.lproj ; \ - $(mkinstalldirs) $$RDIR ;\ + $(MKDIR_P) $$RDIR ;\ $(INSTALL_DATA) $(srcdir)/os_darwin/$${i}_Localizable.strings \ $$RDIR/Localizable.strings ; \ done @@ -501,7 +507,7 @@ initd_DATA_install = install-initdDATA-generic initd_DATA_uninstall = uninstall-initdDATA-generic install-initdDATA-generic: $(initd_DATA) - $(mkinstalldirs) '$(DESTDIR)$(initddir)' + $(MKDIR_P) '$(DESTDIR)$(initddir)' $(INSTALL_SCRIPT) '$(top_builddir)/$(initdfile)' '$(DESTDIR)$(initddir)/smartd$(smartd_suffix)' uninstall-initdDATA-generic: @@ -525,24 +531,23 @@ systemdsystemunit_DATA = smartd.service endif smartd.service: smartd.service.in Makefile - @echo ' cat $(srcdir)/smartd.service.in | $$(SMARTD_SERVICE_FILTER) > $@' - @cat $(srcdir)/smartd.service.in | \ + @echo ' $$(SMARTD_SERVICE_FILTER) < $(srcdir)/smartd.service.in > $@' + @{ \ sed 's|/usr/local/sbin/smartd|$(sbindir)/smartd|' | \ if test -n '$(systemdenvfile)'; then \ sed 's|/usr/local/etc/sysconfig/smartmontools|$(systemdenvfile)|'; \ else \ sed -e '/^EnvironmentFile=/d' -e 's| *\$$smartd[_a-z]* *||g'; \ - fi > $@ + fi; } < $(srcdir)/smartd.service.in > $@ # Create empty directories if configured. # Default install rules no longer create empty directories since automake 1.11. -# Uses $(mkinstalldirs) instead of $(MKDIR_P) to preserve support for automake 1.7 - 1.9. installdirs-local: @for d in '$(smartdplugindir)' '$(savestatesdir)' '$(attributelogdir)'; do \ test -n "$$d" || continue; \ - echo " $(mkinstalldirs) '$(DESTDIR)$$d'"; \ - $(mkinstalldirs) "$(DESTDIR)$$d" || exit 1; \ + echo " $(MKDIR_P) '$(DESTDIR)$$d'"; \ + $(MKDIR_P) "$(DESTDIR)$$d" || exit 1; \ done install-data-local: installdirs-local @@ -550,7 +555,7 @@ install-data-local: installdirs-local # # Build man pages # -MAN_FILTER = \ +MAN_FILTER = { \ sed -e 's|CURRENT_SVN_VERSION|$(releaseversion)|g' \ -e "s|CURRENT_SVN_DATE|`sed -n 's,^.*DATE[^"]*"\([^"]*\)".*$$,\1,p' svnversion.h`|g" \ -e "s|CURRENT_SVN_REV|`sed -n 's,^.*REV[^"]*"\([^"]*\)".*$$,r\1,p' svnversion.h`|g" \ @@ -606,24 +611,24 @@ MAN_FILTER = \ -e 's,^!!!*,,' ; \ else \ cat; \ - fi + fi; } # Implicit rule 'smart%: smart%.in ...' does not work with BSD make smartctl.8: smartctl.8.in Makefile svnversion.h - @echo ' cat $(srcdir)/smartctl.8.in | $$(MAN_FILTER) > $@' - @cat $(srcdir)/smartctl.8.in | $(MAN_FILTER) > $@ + @echo ' $$(MAN_FILTER) < $(srcdir)/smartctl.8.in > $@' + @$(MAN_FILTER) < $(srcdir)/smartctl.8.in > $@ smartd.8: smartd.8.in Makefile svnversion.h - @echo ' cat $(srcdir)/smartd.8.in | $$(MAN_FILTER) > $@' - @cat $(srcdir)/smartd.8.in | $(MAN_FILTER) > $@ + @echo ' $$(MAN_FILTER) < $(srcdir)/smartd.8.in > $@' + @$(MAN_FILTER) < $(srcdir)/smartd.8.in > $@ smartd.conf.5: smartd.conf.5.in Makefile svnversion.h - @echo ' cat $(srcdir)/smartd.conf.5.in | $$(MAN_FILTER) > $@' - @cat $(srcdir)/smartd.conf.5.in | $(MAN_FILTER) > $@ + @echo ' $$(MAN_FILTER) < $(srcdir)/smartd.conf.5.in > $@' + @$(MAN_FILTER) < $(srcdir)/smartd.conf.5.in > $@ update-smart-drivedb.8: update-smart-drivedb.8.in Makefile svnversion.h - @echo ' cat $(srcdir)/update-smart-drivedb.8.in | $$(MAN_FILTER) > $@' - @cat $(srcdir)/update-smart-drivedb.8.in | $(MAN_FILTER) > $@ + @echo ' $$(MAN_FILTER) < $(srcdir)/update-smart-drivedb.8.in > $@' + @$(MAN_FILTER) < $(srcdir)/update-smart-drivedb.8.in > $@ # Build Solaris specific man pages SOLARIS_MAN_FILTER = \ @@ -634,20 +639,20 @@ SOLARIS_MAN_FILTER = \ -e 's,/var/log/messages,/var/adm/messages,g' smartctl.1m: smartctl.8 - @echo ' cat smartctl.8 | $$(SOLARIS_MAN_FILTER) > $@' - @cat smartctl.8 | $(SOLARIS_MAN_FILTER) > $@ + @echo ' $$(SOLARIS_MAN_FILTER) < smartctl.8 > $@' + @$(SOLARIS_MAN_FILTER) < smartctl.8 > $@ smartd.1m: smartd.8 - @echo ' cat smartd.8 | $$(SOLARIS_MAN_FILTER) > $@' - @cat smartd.8 | $(SOLARIS_MAN_FILTER) > $@ + @echo ' $$(SOLARIS_MAN_FILTER) < smartd.8 > $@' + @$(SOLARIS_MAN_FILTER) < smartd.8 > $@ smartd.conf.4: smartd.conf.5 - @echo ' cat smartd.conf.5 | $$(SOLARIS_MAN_FILTER) > $@' - @cat smartd.conf.5 | $(SOLARIS_MAN_FILTER) > $@ + @echo ' $$(SOLARIS_MAN_FILTER) < smartd.conf.5 > $@' + @$(SOLARIS_MAN_FILTER) < smartd.conf.5 > $@ update-smart-drivedb.1m: update-smart-drivedb.8 - @echo ' cat update-smart-drivedb.8 | $$(SOLARIS_MAN_FILTER) > $@' - @cat update-smart-drivedb.8 | $(SOLARIS_MAN_FILTER) > $@ + @echo ' $$(SOLARIS_MAN_FILTER) < update-smart-drivedb.8 > $@' + @$(SOLARIS_MAN_FILTER) < update-smart-drivedb.8 > $@ # Commands to convert man pages into .html and .txt @@ -669,21 +674,15 @@ htmlman: smartctl.8.html smartd.8.html smartd.conf.5.html txtman: smartctl.8.txt smartd.8.txt smartd.conf.5.txt -if OS_WIN32_MINGW - %.5.html: %.5 - $(DOS2UNIX) < $< | $(MAN2HTML) | $(FIXHTML) > $@ + $(MAN2HTML) $< > $@.tmp + @echo ' $$(FIXHTML) < $@.tmp > $@' + @$(FIXHTML) < $@.tmp > $@ %.8.html: %.8 - $(DOS2UNIX) < $< | $(MAN2HTML) | $(FIXHTML) > $@ -else - -%.5.html: %.5 - $(MAN2HTML) $< | $(FIXHTML) > $@ - -%.8.html: %.8 - $(MAN2HTML) $< | $(FIXHTML) > $@ -endif + $(MAN2HTML) $< > $@.tmp + @echo ' $$(FIXHTML) < $@.tmp > $@' + @$(FIXHTML) < $@.tmp > $@ %.5.txt: %.5 $(MAN2TXT) $< > $@ @@ -711,22 +710,35 @@ smartd_res.o: smartd_res.rc syslogevt.rc $(WINDRES) -I. $< $@ # Convert version for VERSIONINFO resource: 6.1 r3754 -> 6.1.0.3754, set Copyright year -WIN_RC_FILTER = \ - ( ver=`echo '$(PACKAGE_VERSION).0' | sed -n 's,^\([0-9]*\.[0-9]*\.[0-9]*\).*$$,\1,p'`; \ - rev=`sed -n 's,^.*REV[^"]*"\([0-9]*\).*$$,\1,p' svnversion.h`; \ - txtver="$${ver:-0.0.0}.$${rev:-0}"; binver=`echo "$$txtver" | sed 's|\.|,|g'`; \ - yy=`sed -n 's,^.*DATE[^"]*"20\([0-9][0-9]\).*$$,\1,p' svnversion.h`; yy="$${yy:-XX}"; \ - sed -e "s|@BINARY_VERSION@|$$binver|g" -e "s|@TEXT_VERSION@|$$txtver|g" -e "s|@YY@|$$yy|g"; ) +WIN_RC_FILTER = { \ + ver=`echo '$(PACKAGE_VERSION).0' | sed -n 's,^\([0-9]*\.[0-9]*\.[0-9]*\).*$$,\1,p'` && \ + rev=`sed -n 's,^.*REV[^"]*"\([0-9]*\).*$$,\1,p' svnversion.h` && \ + txtver="$${ver:-0.0.0}.$${rev:-0}" && binver=`echo "$$txtver" | sed 's|\.|,|g'` && \ + yy=`sed -n 's,^.*DATE[^"]*"20\([0-9][0-9]\).*$$,\1,p' svnversion.h` && yy="$${yy:-XX}" && \ + sed -e "s|@BINARY_VERSION@|$$binver|g" -e "s|@TEXT_VERSION@|$$txtver|g" -e "s|@YY@|$$yy|g"; } smartctl_res.rc: os_win32/smartctl_res.rc.in Makefile svnversion.h - cat $< | $(WIN_RC_FILTER) > $@ + @echo ' $$(WIN_RC_FILTER) < $< > $@' + @$(WIN_RC_FILTER) < $< > $@ smartd_res.rc: os_win32/smartd_res.rc.in Makefile svnversion.h - cat $< | $(WIN_RC_FILTER) > $@ + @echo ' $$(WIN_RC_FILTER) < $< > $@' + @$(WIN_RC_FILTER) < $< > $@ syslogevt.rc: os_win32/syslogevt.mc $(WINDMC) -b $< +# Application manifests + +default.manifest.o: os_win32/default.manifest + echo '1 24 "$<"' | $(WINDRES) -J rc -o $@ + +defadmin.manifest.o: defadmin.manifest + echo '1 24 "$<"' | $(WINDRES) -J rc -o $@ + +defadmin.manifest: os_win32/default.manifest + sed 's,"asInvoker","requireAdministrator",' $< > $@ + # Definitions for Windows distribution if OS_WIN64 @@ -775,9 +787,7 @@ FILES_WIN32 = \ $(docdir_win32)/smartd.8.html \ $(docdir_win32)/smartd.8.txt \ $(docdir_win32)/smartd.conf.5.html \ - $(docdir_win32)/smartd.conf.5.txt \ - $(exedir_win32)/runcmda.exe.manifest \ - $(exedir_win32)/runcmdu.exe.manifest + $(docdir_win32)/smartd.conf.5.txt if ENABLE_DRIVEDB FILES_WIN32 += \ @@ -786,20 +796,18 @@ endif CLEANFILES += \ $(FILES_WIN32) \ - runcmdu.exe \ + defadmin.manifest \ + distdir.mkdir \ + runcmda.exe runcmdu.exe \ smartctl-nc.exe smartctl-nc.exe.tmp \ - smartctl_res.rc smartctl_res.o \ - smartd_res.rc smartd_res.o \ - syslogevt.h syslogevt.o \ + smartctl_res.rc smartd_res.rc \ + syslogevt.h \ syslogevt.rc syslogevt_*.bin \ - wtssendmsg.exe \ update-smart-drivedb.exe \ - distdir.mkdir + wtssendmsg.exe -# Textfile converter from package cygutils or tofrodos -# Note: Only use without options to be compatible with both packages +# Note: Only use without options to be compatible with all variants UNIX2DOS = unix2dos -DOS2UNIX = dos2unix # Build Windows distribution @@ -824,11 +832,11 @@ if OS_WIN32_NSIS # Note: Only option character '-' is also compatible with Linux version of makensis $(distinst_win32): os_win32/installer.nsi distdir.mkdir $(FILES_WIN32) test -z '$(builddir_win64)' || ( cd $(builddir_win64) && make distdir-win32 ) - @date=`sed -n 's,^.*DATE[^"]*"\([^"]*\)".*$$,\1,p' svnversion.h`; \ - rev=`sed -n 's,^.*REV[^"]*"\([^"]*\)".*$$,r\1,p' svnversion.h`; \ - verstr="$(PACKAGE_VERSION) $$date $$rev "$(BUILD_INFO); \ - d64=; test -z '$(builddir_win64)' || d64='-DINPDIR64=$(builddir_win64)/$(PACKAGE)-$(VERSION).win64'; \ - echo "'$(MAKENSIS)' -V2 -NOCD -DINPDIR=$(distdir_win32) $$d64 -DOUTFILE=$@ -DVERSTR='$$verstr' $<"; \ + @date=`sed -n 's,^.*DATE[^"]*"\([^"]*\)".*$$,\1,p' svnversion.h` && \ + rev=`sed -n 's,^.*REV[^"]*"\([^"]*\)".*$$,r\1,p' svnversion.h` && \ + verstr="$(PACKAGE_VERSION) $$date $$rev "$(BUILD_INFO) && \ + d64= && if [ -n '$(builddir_win64)' ]; then d64='-DINPDIR64=$(builddir_win64)/$(PACKAGE)-$(VERSION).win64'; fi && \ + echo "'$(MAKENSIS)' -V2 -NOCD -DINPDIR=$(distdir_win32) $$d64 -DOUTFILE=$@ -DVERSTR='$$verstr' $<" && \ '$(MAKENSIS)' -V2 -NOCD -DINPDIR=$(distdir_win32) $$d64 -DOUTFILE=$@ -DVERSTR="$$verstr" $< md5sum $@ > $@.md5 sha1sum $@ > $@.sha1 @@ -861,18 +869,10 @@ $(exedir_win32)/%.exe: %.exe $(exedir_win32)/update-smart-drivedb.exe: update-smart-drivedb.exe cp -p $< $@ -# runcmd?.exe only differ by .exe.manifest files -$(exedir_win32)/runcmda.exe: $(exedir_win32)/runcmdu.exe - cp -p $< $@ - $(exedir_win32)/%.h: $(srcdir)/%.h $(UNIX2DOS) < $< > $@ touch -r $< $@ -$(exedir_win32)/%.exe.manifest: $(srcdir)/os_win32/%.exe.manifest - $(UNIX2DOS) < $< > $@ - touch -r $< $@ - $(exedir_win32)/%.cmd: $(srcdir)/os_win32/%.cmd $(UNIX2DOS) < $< > $@ touch -r $< $@ @@ -914,11 +914,17 @@ smartctl-nc.exe: smartctl.exe mv -f $@.tmp $@ # Build runcmd?.exe and wtssendmsg.exe -runcmdu.exe: os_win32/runcmd.c - $(CC) -Os -o $@ $< +runcmd.o: os_win32/runcmd.c + $(CC) -c -Os $< -wtssendmsg.exe: os_win32/wtssendmsg.c - $(CC) -Os -o $@ $< -lwtsapi32 +runcmdu.exe: runcmd.o $(os_win32_manifest) + $(CC) -o $@ $^ + +runcmda.exe: runcmd.o defadmin.manifest.o + $(CC) -o $@ $^ + +wtssendmsg.exe: os_win32/wtssendmsg.c $(os_win32_manifest) + $(CC) -Os -o $@ $< $(os_win32_manifest) -lwtsapi32 # Build os_win32/vc10/{config.h,smart*.rc,svnversion.h} for MSVC10 from MinGW files @@ -942,3 +948,44 @@ $(srcdir)/os_win32/vc10/smartd_res.rc: smartd_res.rc cp $< $@ endif +if OS_DARWIN +# Definitions for OSX distribution +distdir_darwin = $(PACKAGE)-$(VERSION).darwin +dmg_darwin = $(PACKAGE)-$(VERSION).dmg +pkg_darwin = $(PACKAGE)-$(VERSION).pkg + +# build darwin installer +$(pkg_darwin): + ${MAKE} install DESTDIR=$(distdir_darwin)/root + @cp $(srcdir)/os_darwin/pkg/root/usr/local/sbin/smart-pkg-uninstall $(distdir_darwin)/root$(sbindir) + @mkdir -p $(distdir_darwin)/pkg + @( cd $(distdir_darwin)/root && find . | cpio -o --format odc --owner 0:80 | gzip -c ) > $(distdir_darwin)/pkg/Payload + PAYLOAD_FILES=`find $(distdir_darwin)/root | wc -l` &&\ + PAYLOAD_SIZEKB=`du -BK -s $(distdir_darwin)/root|${AWK} '{print $$1}'|tr -d 'K'` &&\ + sed -e "s|@version@|$(VERSION)|" -e "s|@files@|$${PAYLOAD_FILES}|" \ + -e "s|@size@|$${PAYLOAD_SIZEKB}|" $(srcdir)/os_darwin/pkg/PackageInfo.in \ + > $(distdir_darwin)/pkg/PackageInfo &&\ + sed -e "s|@version@|$(VERSION)|" -e "s|@files@|$${PAYLOAD_FILES}|" -e "s|@size@|$${PAYLOAD_SIZEKB}|" \ + -e "s|@pkgname@|$(pkg_darwin)|" \ + $(srcdir)/os_darwin/pkg/Distribution.in > $(distdir_darwin)/pkg/Distribution + @mkdir -p $(distdir_darwin)/pkg/Resources/English.lproj + @cp $(srcdir)/COPYING $(distdir_darwin)/pkg/Resources/English.lproj/license.txt + @mkbom -u 0 -g 80 $(distdir_darwin)/root $(distdir_darwin)/pkg/Bom + @mkdir -p $(distdir_darwin)/dmg + @( cd $(distdir_darwin)/pkg && xar --compression none -cf "../dmg/$(pkg_darwin)" * ) + +# build darwon dmg image +$(dmg_darwin): + @cp $(srcdir)/os_darwin/pkg/installer/README.html $(distdir_darwin)/dmg + @mkisofs -V 'smartmontools' -no-pad -r -apple -o $(distdir_darwin)/smartmontools-$(VERSION).iso \ + -hfs-bless "$(distdir_darwin)/dmg/" "$(distdir_darwin)/dmg/" + @dmg dmg $(distdir_darwin)/smartmontools-$(VERSION).iso $(dmg_darwin) + md5sum $@ > $@.md5 + sha1sum $@ > $@.sha1 + sha256sum $@ > $@.sha256 + +install-darwin: install-darwin-cleanup $(pkg_darwin) $(dmg_darwin) + +install-darwin-cleanup: + @rm -rf $(distdir_darwin) +endif diff --git a/NEWS b/NEWS index b14909b..e522ad5 100644 --- a/NEWS +++ b/NEWS @@ -1,10 +1,30 @@ smartmontools NEWS ------------------ -$Id: NEWS 4109 2015-06-04 16:30:15Z chrfranke $ +$Id: NEWS 4176 2015-11-22 16:45:30Z chrfranke $ The most up-to-date version of this file is: http://sourceforge.net/p/smartmontools/code/HEAD/tree/trunk/smartmontools/NEWS +Date +Summary: smartmontools release 6.5 +----------------------------------------------------------- +- SAT: Improved heuristics to detect bogus sense data from SAT layer. +- configure options '--disable-drivedb', '--enable-savestates', + '--enable-attributelog' and '--with-docdir' are no longer supported. +- autoconf < 2.60 and automake < 1.10 are no longer supported. +- Drive database file now also includes the DEFAULT setting + for each attribute. +- HDD, SSD and USB additions to drive database. +- Darwin: New support files for package installer. + New makefile target 'install-darwin' builds DMG image. +- Solaris: Auto detection of SATA devices behind SAT layer. +- Solaris SPARC: Legacy ATA support disabled by default. + New configure option '--with-solaris-sparc-ata' enables it. + File os_solaris_ata.s is no longer included in source tarball. +- Windows: Auto detection of USB devices specified by drive letter. +- Windows: New application manifests indicating Win 10 support. +- Windows installer: Defaults to 64-bit version on 64-bit Windows. + Date 2015-06-04 Summary: smartmontools release 6.4 ----------------------------------------------------------- diff --git a/README b/README index 48f592e..6d20c01 100644 --- a/README +++ b/README @@ -3,12 +3,12 @@ smartmontools - S.M.A.R.T. utility toolset for Darwin/Mac OSX, FreeBSD, Linux, NetBSD, OpenBSD, Solaris, and Windows. ========================================================== -$Id: README 4063 2015-04-19 17:34:25Z chrfranke $ +$Id: README 4120 2015-08-27 16:12:21Z samm2 $ == HOME == The home for smartmontools is located at: - http://smartmontools.sourceforge.net/ + http://www.smartmontools.org/ Please see this web site for updates, documentation, and for submitting patches and bug reports. diff --git a/atacmdnames.cpp b/atacmdnames.cpp index 9ba90f6..9a57c17 100644 --- a/atacmdnames.cpp +++ b/atacmdnames.cpp @@ -1,7 +1,7 @@ /* * atacmdnames.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2003-8 Philip Williams * Copyright (C) 2012 Christian Franke @@ -20,7 +20,7 @@ #include #include -const char * atacmdnames_cpp_cvsid = "$Id: atacmdnames.cpp 3670 2012-10-31 22:00:50Z chrfranke $" +const char * atacmdnames_cpp_cvsid = "$Id: atacmdnames.cpp 4120 2015-08-27 16:12:21Z samm2 $" ATACMDNAMES_H_CVSID; const char cmd_reserved[] = "[RESERVED]"; diff --git a/atacmdnames.h b/atacmdnames.h index ac0e446..20f99ed 100644 --- a/atacmdnames.h +++ b/atacmdnames.h @@ -4,7 +4,7 @@ * This module is based on the T13/1532D Volume 1 Revision 3 (ATA/ATAPI-7) * specification, which is available from http://www.t13.org/#FTP_site * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * Address of support mailing list: smartmontools-support@lists.sourceforge.net * * Copyright (C) 2003-8 Philip Williams @@ -23,7 +23,7 @@ #ifndef ATACMDNAMES_H_ #define ATACMDNAMES_H_ -#define ATACMDNAMES_H_CVSID "$Id: atacmdnames.h 3728 2012-12-13 17:57:50Z chrfranke $\n" +#define ATACMDNAMES_H_CVSID "$Id: atacmdnames.h 4120 2015-08-27 16:12:21Z samm2 $\n" /* Returns the name of the command (and possibly sub-command) with the given command code and feature register values. */ diff --git a/atacmds.cpp b/atacmds.cpp index 88ec6b9..3a2bec4 100644 --- a/atacmds.cpp +++ b/atacmds.cpp @@ -1,10 +1,10 @@ /* * atacmds.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * - * Copyright (C) 2002-11 Bruce Allen - * Copyright (C) 2008-15 Christian Franke + * Copyright (C) 2002-11 Bruce Allen + * Copyright (C) 2008-15 Christian Franke * Copyright (C) 1999-2000 Michael Cornwell * Copyright (C) 2000 Andre Hedrick * @@ -32,10 +32,11 @@ #include "config.h" #include "int64.h" #include "atacmds.h" +#include "knowndrives.h" // get_default_attr_defs() #include "utility.h" #include "dev_ata_cmd_set.h" // for parsed_ata_device -const char * atacmds_cpp_cvsid = "$Id: atacmds.cpp 4048 2015-03-29 16:09:04Z chrfranke $" +const char * atacmds_cpp_cvsid = "$Id: atacmds.cpp 4178 2015-11-23 18:44:27Z chrfranke $" ATACMDS_H_CVSID; // Print ATA debug messages? @@ -170,7 +171,9 @@ bool parse_attribute_def(const char * opt, ata_vendor_attr_defs & defs, // Parse option int len = strlen(opt); int id = 0, n1 = -1, n2 = -1; - char fmtname[32+1], attrname[32+1]; + char fmtname[32+1], attrname[32+1], hddssd[3+1]; + attrname[0] = hddssd[0] = 0; + if (opt[0] == 'N') { // "N,format[,name]" if (!( sscanf(opt, "N,%32[^,]%n,%32[^,]%n", fmtname, &n1, attrname, &n2) >= 1 @@ -178,13 +181,16 @@ bool parse_attribute_def(const char * opt, ata_vendor_attr_defs & defs, return false; } else { - // "id,format[+][,name]" - if (!( sscanf(opt, "%d,%32[^,]%n,%32[^,]%n", &id, fmtname, &n1, attrname, &n2) >= 2 - && 1 <= id && id <= 255 && (n1 == len || n2 == len))) + // "id,format[+][,name[,HDD|SSD]]" + int n3 = -1; + if (!( sscanf(opt, "%d,%32[^,]%n,%32[^,]%n,%3[DHS]%n", + &id, fmtname, &n1, attrname, &n2, hddssd, &n3) >= 2 + && 1 <= id && id <= 255 + && ( n1 == len || n2 == len + // ",HDD|SSD" for DEFAULT settings only + || (n3 == len && priority == PRIOR_DEFAULT)))) return false; } - if (n1 == len) - attrname[0] = 0; unsigned flags = 0; // For "-v 19[78],increasing" above @@ -196,6 +202,9 @@ bool parse_attribute_def(const char * opt, ata_vendor_attr_defs & defs, // Split "format[:byteorder]" char byteorder[8+1] = ""; if (strchr(fmtname, ':')) { + if (priority == PRIOR_DEFAULT) + // TODO: Allow Byteorder in DEFAULT entry + return false; n1 = n2 = -1; if (!( sscanf(fmtname, "%*[^:]%n:%8[012345rvwz]%n", &n1, byteorder, &n2) >= 1 && n2 == (int)strlen(fmtname))) @@ -220,6 +229,16 @@ bool parse_attribute_def(const char * opt, ata_vendor_attr_defs & defs, if (!*byteorder && (format == RAWFMT_RAW64 || format == RAWFMT_HEX64)) flags |= (ATTRFLAG_NO_NORMVAL|ATTRFLAG_NO_WORSTVAL); + // ",HDD|SSD" suffix for DEFAULT settings + if (hddssd[0]) { + if (!strcmp(hddssd, "HDD")) + flags |= ATTRFLAG_HDD_ONLY; + else if (!strcmp(hddssd, "SSD")) + flags |= ATTRFLAG_SSD_ONLY; + else + return false; + } + if (!id) { // "N,format" -> set format for all entries for (i = 0; i < MAX_ATTRIBUTE_NUM; i++) { @@ -617,7 +636,7 @@ int smartcommandhandler(ata_device * device, smart_command_set command, int sele // If requested, invalidate serial number before any printing is done if ((command == IDENTIFY || command == PIDENTIFY) && !retval && dont_print_serial_number) - invalidate_serno((ata_identify_device *)data); + invalidate_serno( reinterpret_cast(data) ); // If reporting is enabled, say what output was produced by the command if (ata_debugmode) { @@ -831,9 +850,9 @@ int ata_read_identity(ata_device * device, ata_identify_device * buf, bool fix_s packet = true; } - unsigned i; if (fix_swapped_id) { // Swap ID strings + unsigned i; for (i = 0; i < sizeof(buf->serial_no)-1; i += 2) swap2((char *)(buf->serial_no+i)); for (i = 0; i < sizeof(buf->fw_rev)-1; i += 2) @@ -851,14 +870,12 @@ int ata_read_identity(ata_device * device, ata_identify_device * buf, bool fix_s // NetBSD kernel delivers IDENTIFY data in host byte order // TODO: Handle NetBSD case in os_netbsd.cpp if (isbigendian()){ - // swap various capability words that are needed + unsigned i; for (i=0; i<33; i++) swap2((char *)(buf->words047_079+i)); - for (i=80; i<=87; i++) swap2((char *)(rawshort+i)); - for (i=0; i<168; i++) swap2((char *)(buf->words088_255+i)); } @@ -1859,35 +1876,12 @@ ata_attr_state ata_get_attr_state(const ata_smart_attribute & attr, return ATTRSTATE_OK; } -// Get default raw value print format -static ata_attr_raw_format get_default_raw_format(unsigned char id) -{ - switch (id) { - case 3: // Spin-up time - return RAWFMT_RAW16_OPT_AVG16; - - case 5: // Reallocated sector count - case 196: // Reallocated event count - return RAWFMT_RAW16_OPT_RAW16; - - case 9: // Power on hours - case 240: // Head flying hours - return RAWFMT_RAW24_OPT_RAW8; - - case 190: // Temperature - case 194: - return RAWFMT_TEMPMINMAX; - - default: - return RAWFMT_RAW48; - } -} - // Get attribute raw value. uint64_t ata_get_attr_raw_value(const ata_smart_attribute & attr, const ata_vendor_attr_defs & defs) { const ata_vendor_attr_defs::entry & def = defs[attr.id]; + // TODO: Allow Byteorder in DEFAULT entry // Use default byteorder if not specified const char * byteorder = def.byteorder; @@ -1978,8 +1972,13 @@ std::string ata_format_attr_raw_value(const ata_smart_attribute & attr, // Get print format ata_attr_raw_format format = defs[attr.id].raw_format; - if (format == RAWFMT_DEFAULT) - format = get_default_raw_format(attr.id); + if (format == RAWFMT_DEFAULT) { + // Get format from DEFAULT entry + format = get_default_attr_defs()[attr.id].raw_format; + if (format == RAWFMT_DEFAULT) + // Unknown Attribute + format = RAWFMT_RAW48; + } // Print std::string s; @@ -2158,212 +2157,23 @@ std::string ata_format_attr_raw_value(const ata_smart_attribute & attr, return s; } -// Attribute names shouldn't be longer than 23 chars, otherwise they break the -// output of smartctl. -static const char * get_default_attr_name(unsigned char id, int rpm) -{ - bool hdd = (rpm > 1), ssd = (rpm == 1); - - static const char Unknown_HDD_Attribute[] = "Unknown_HDD_Attribute"; - static const char Unknown_SSD_Attribute[] = "Unknown_SSD_Attribute"; - - switch (id) { - case 1: - return "Raw_Read_Error_Rate"; - case 2: - return "Throughput_Performance"; - case 3: - return "Spin_Up_Time"; - case 4: - return "Start_Stop_Count"; - case 5: - return "Reallocated_Sector_Ct"; - case 6: - if (ssd) return Unknown_SSD_Attribute; - return "Read_Channel_Margin"; - case 7: - if (ssd) return Unknown_SSD_Attribute; - return "Seek_Error_Rate"; - case 8: - if (ssd) return Unknown_SSD_Attribute; - return "Seek_Time_Performance"; - case 9: - return "Power_On_Hours"; - case 10: - if (ssd) return Unknown_SSD_Attribute; - return "Spin_Retry_Count"; - case 11: - if (ssd) return Unknown_SSD_Attribute; - return "Calibration_Retry_Count"; - case 12: - return "Power_Cycle_Count"; - case 13: - return "Read_Soft_Error_Rate"; - case 175: - if (hdd) return Unknown_HDD_Attribute; - return "Program_Fail_Count_Chip"; - case 176: - if (hdd) return Unknown_HDD_Attribute; - return "Erase_Fail_Count_Chip"; - case 177: - if (hdd) return Unknown_HDD_Attribute; - return "Wear_Leveling_Count"; - case 178: - if (hdd) return Unknown_HDD_Attribute; - return "Used_Rsvd_Blk_Cnt_Chip"; - case 179: - if (hdd) return Unknown_HDD_Attribute; - return "Used_Rsvd_Blk_Cnt_Tot"; - case 180: - if (hdd) return Unknown_HDD_Attribute; - return "Unused_Rsvd_Blk_Cnt_Tot"; - case 181: - return "Program_Fail_Cnt_Total"; - case 182: - if (hdd) return Unknown_HDD_Attribute; - return "Erase_Fail_Count_Total"; - case 183: - return "Runtime_Bad_Block"; - case 184: - return "End-to-End_Error"; - case 187: - return "Reported_Uncorrect"; - case 188: - return "Command_Timeout"; - case 189: - if (ssd) return Unknown_SSD_Attribute; - return "High_Fly_Writes"; - case 190: - // Western Digital uses this for temperature. - // It's identical to Attribute 194 except that it - // has a failure threshold set to correspond to the - // max allowed operating temperature of the drive, which - // is typically 55C. So if this attribute has failed - // in the past, it indicates that the drive temp exceeded - // 55C sometime in the past. - return "Airflow_Temperature_Cel"; - case 191: - if (ssd) return Unknown_SSD_Attribute; - return "G-Sense_Error_Rate"; - case 192: - return "Power-Off_Retract_Count"; - case 193: - if (ssd) return Unknown_SSD_Attribute; - return "Load_Cycle_Count"; - case 194: - return "Temperature_Celsius"; - case 195: - // Fujitsu: "ECC_On_The_Fly_Count"; - return "Hardware_ECC_Recovered"; - case 196: - return "Reallocated_Event_Count"; - case 197: - return "Current_Pending_Sector"; - case 198: - return "Offline_Uncorrectable"; - case 199: - return "UDMA_CRC_Error_Count"; - case 200: - if (ssd) return Unknown_SSD_Attribute; - // Western Digital - return "Multi_Zone_Error_Rate"; - case 201: - if (ssd) return Unknown_SSD_Attribute; - return "Soft_Read_Error_Rate"; - case 202: - if (ssd) return Unknown_SSD_Attribute; - // Fujitsu: "TA_Increase_Count" - return "Data_Address_Mark_Errs"; - case 203: - // Fujitsu - return "Run_Out_Cancel"; - // Maxtor: ECC Errors - case 204: - // Fujitsu: "Shock_Count_Write_Opern" - return "Soft_ECC_Correction"; - case 205: - // Fujitsu: "Shock_Rate_Write_Opern" - return "Thermal_Asperity_Rate"; - case 206: - // Fujitsu - if (ssd) return Unknown_SSD_Attribute; - return "Flying_Height"; - case 207: - // Maxtor - if (ssd) return Unknown_SSD_Attribute; - return "Spin_High_Current"; - case 208: - // Maxtor - if (ssd) return Unknown_SSD_Attribute; - return "Spin_Buzz"; - case 209: - // Maxtor - if (ssd) return Unknown_SSD_Attribute; - return "Offline_Seek_Performnce"; - case 220: - if (ssd) return Unknown_SSD_Attribute; - return "Disk_Shift"; - case 221: - if (ssd) return Unknown_SSD_Attribute; - return "G-Sense_Error_Rate"; - case 222: - if (ssd) return Unknown_SSD_Attribute; - return "Loaded_Hours"; - case 223: - if (ssd) return Unknown_SSD_Attribute; - return "Load_Retry_Count"; - case 224: - if (ssd) return Unknown_SSD_Attribute; - return "Load_Friction"; - case 225: - if (ssd) return Unknown_SSD_Attribute; - return "Load_Cycle_Count"; - case 226: - if (ssd) return Unknown_SSD_Attribute; - return "Load-in_Time"; - case 227: - if (ssd) return Unknown_SSD_Attribute; - return "Torq-amp_Count"; - case 228: - return "Power-off_Retract_Count"; - case 230: - // seen in IBM DTPA-353750 - if (ssd) return Unknown_SSD_Attribute; - return "Head_Amplitude"; - case 231: - return "Temperature_Celsius"; - case 232: - // seen in Intel X25-E SSD - return "Available_Reservd_Space"; - case 233: - // seen in Intel X25-E SSD - if (hdd) return Unknown_HDD_Attribute; - return "Media_Wearout_Indicator"; - case 240: - if (ssd) return Unknown_SSD_Attribute; - return "Head_Flying_Hours"; - case 241: - return "Total_LBAs_Written"; - case 242: - return "Total_LBAs_Read"; - case 250: - return "Read_Error_Retry_Rate"; - case 254: - if (ssd) return Unknown_SSD_Attribute; - return "Free_Fall_Sensor"; - default: - return "Unknown_Attribute"; - } -} - // Get attribute name std::string ata_get_smart_attr_name(unsigned char id, const ata_vendor_attr_defs & defs, int rpm /* = 0 */) { if (!defs[id].name.empty()) return defs[id].name; - else - return get_default_attr_name(id, rpm); + else { + const ata_vendor_attr_defs::entry & def = get_default_attr_defs()[id]; + if (def.name.empty()) + return "Unknown_Attribute"; + else if ((def.flags & ATTRFLAG_HDD_ONLY) && rpm == 1) + return "Unknown_SSD_Attribute"; + else if ((def.flags & ATTRFLAG_SSD_ONLY) && rpm > 1) + return "Unknown_HDD_Attribute"; + else + return def.name; + } } // Find attribute index for attribute id, -1 if not found. diff --git a/atacmds.h b/atacmds.h index 5ac43ff..5768677 100644 --- a/atacmds.h +++ b/atacmds.h @@ -1,10 +1,10 @@ /* * atacmds.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * - * Copyright (C) 2002-11 Bruce Allen - * Copyright (C) 2008-15 Christian Franke + * Copyright (C) 2002-11 Bruce Allen + * Copyright (C) 2008-15 Christian Franke * Copyright (C) 1999-2000 Michael Cornwell * * This program is free software; you can redistribute it and/or modify @@ -25,7 +25,7 @@ #ifndef ATACMDS_H_ #define ATACMDS_H_ -#define ATACMDS_H_CVSID "$Id: atacmds.h 4048 2015-03-29 16:09:04Z chrfranke $" +#define ATACMDS_H_CVSID "$Id: atacmds.h 4162 2015-10-31 16:36:16Z chrfranke $" #include "dev_interface.h" // ata_device @@ -684,9 +684,11 @@ enum ata_attr_raw_format // Attribute flags enum { - ATTRFLAG_INCREASING = 0x01, // Value not reset (for reallocated/pending counts) - ATTRFLAG_NO_NORMVAL = 0x02, // Normalized value not valid - ATTRFLAG_NO_WORSTVAL = 0x04 // Worst value not valid + ATTRFLAG_INCREASING = 0x01, // Value not reset (for reallocated/pending counts) + ATTRFLAG_NO_NORMVAL = 0x02, // Normalized value not valid + ATTRFLAG_NO_WORSTVAL = 0x04, // Worst value not valid + ATTRFLAG_HDD_ONLY = 0x08, // DEFAULT setting for HDD only + ATTRFLAG_SSD_ONLY = 0x10, // DEFAULT setting for SSD only }; // Vendor attribute display defs for all attribute ids diff --git a/ataidentify.cpp b/ataidentify.cpp index 0565323..ec3c40e 100644 --- a/ataidentify.cpp +++ b/ataidentify.cpp @@ -1,7 +1,7 @@ /* * ataidentify.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2012-15 Christian Franke * @@ -18,7 +18,7 @@ #include "config.h" #include "ataidentify.h" -const char * ataidentify_cpp_cvsid = "$Id: ataidentify.cpp 4074 2015-05-01 16:03:50Z chrfranke $" +const char * ataidentify_cpp_cvsid = "$Id: ataidentify.cpp 4120 2015-08-27 16:12:21Z samm2 $" ATAIDENTIFY_H_CVSID; #include "int64.h" diff --git a/ataidentify.h b/ataidentify.h index 6375388..76593b0 100644 --- a/ataidentify.h +++ b/ataidentify.h @@ -1,7 +1,7 @@ /* * ataidentify.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2012 Christian Franke * @@ -18,7 +18,7 @@ #ifndef ATAIDENTIFY_H #define ATAIDENTIFY_H -#define ATAIDENTIFY_H_CVSID "$Id: ataidentify.h 3610 2012-09-20 21:27:19Z chrfranke $" +#define ATAIDENTIFY_H_CVSID "$Id: ataidentify.h 4120 2015-08-27 16:12:21Z samm2 $" void ata_print_identify_data(const void * id, bool all_words, int bit_level); diff --git a/ataprint.cpp b/ataprint.cpp index 33fd8b7..02ca736 100644 --- a/ataprint.cpp +++ b/ataprint.cpp @@ -1,10 +1,10 @@ /* * ataprint.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2002-11 Bruce Allen - * Copyright (C) 2008-15 Christian Franke + * Copyright (C) 2008-16 Christian Franke * Copyright (C) 1999-2000 Michael Cornwell * * This program is free software; you can redistribute it and/or modify @@ -40,7 +40,7 @@ #include "utility.h" #include "knowndrives.h" -const char * ataprint_cpp_cvsid = "$Id: ataprint.cpp 4104 2015-06-03 18:50:39Z chrfranke $" +const char * ataprint_cpp_cvsid = "$Id: ataprint.cpp 4203 2016-01-21 20:42:39Z chrfranke $" ATAPRINT_H_CVSID; @@ -697,6 +697,7 @@ static void print_drive_info(const ata_identify_device * drive, pout("ATA Version is: %s\n", infofound(ataver.c_str())); // Print Transport specific version + // cppcheck-suppress variableScope char buf[32] = ""; unsigned short word222 = drive->words088_255[222-88]; if (word222 != 0x0000 && word222 != 0xffff) switch (word222 >> 12) { @@ -1542,13 +1543,13 @@ static void print_device_statistics_page(const unsigned char * data, int page) page, offset, abs(size), valstr, - (flags & 0x20 ? 'N' : '-'), // normalized statistics - (flags & 0x10 ? 'D' : '-'), // supports DSN (ACS-3) - (flags & 0x08 ? 'C' : '-'), // monitored condition met (ACS-3) - (flags & 0x07 ? '+' : ' '), // reserved flags - (info ? info[i].name : - page == 0xff ? "Vendor Specific" // ACS-4 - : "Unknown" )); + ((flags & 0x20) ? 'N' : '-'), // normalized statistics + ((flags & 0x10) ? 'D' : '-'), // supports DSN (ACS-3) + ((flags & 0x08) ? 'C' : '-'), // monitored condition met (ACS-3) + ((flags & 0x07) ? '+' : ' '), // reserved flags + ( info ? info[i].name : + (page == 0xff) ? "Vendor Specific" // ACS-4 + : "Unknown" )); } } @@ -1714,7 +1715,7 @@ static void PrintSataPhyEventCounters(const unsigned char * data, bool reset) case 0x010: name = "R_ERR response for host-to-device data FIS, non-CRC"; break; case 0x012: name = "R_ERR response for host-to-device non-data FIS, CRC"; break; case 0x013: name = "R_ERR response for host-to-device non-data FIS, non-CRC"; break; - default: name = (id & 0x8000 ? "Vendor specific" : "Unknown"); break; + default: name = ((id & 0x8000) ? "Vendor specific" : "Unknown"); break; } // Counters stop at max value, add '+' in this case @@ -1812,7 +1813,7 @@ static int PrintSmartErrorlog(const ata_smart_errorlog *data, for (int k = 4; k >= 0; k-- ) { // The error log data structure entries are a circular buffer - int j, i=(data->error_log_pointer+k)%5; + int i = (data->error_log_pointer + k) % 5; const ata_smart_errorlog_struct * elog = data->errorlog_struct+i; const ata_smart_errorlog_error_struct * summary = &(elog->error_struct); @@ -1848,7 +1849,7 @@ static int PrintSmartErrorlog(const ata_smart_errorlog *data, pout(" Commands leading to the command that caused the error were:\n" " CR FR SC SN CL CH DH DC Powered_Up_Time Command/Feature_Name\n" " -- -- -- -- -- -- -- -- ---------------- --------------------\n"); - for ( j = 4; j >= 0; j--){ + for (int j = 4; j >= 0; j--) { const ata_smart_errorlog_command_struct * thiscommand = elog->commands+j; // Spec says: unused data command structures shall be zero filled @@ -2775,13 +2776,21 @@ int ataPrintMain (ata_device * device, const ata_print_options & options) !(drive.cfs_enable_1 & 0x0020) ? "Disabled" : "Enabled"); // word085 } - // Print ATA security status + // Check for ATA Security LOCK + unsigned short word128 = drive.words088_255[128-88]; + bool locked = ((word128 & 0x0007) == 0x0007); // LOCKED|ENABLED|SUPPORTED + + // Print ATA Security status if (options.get_security) - print_ata_security_status("ATA Security is: ", drive.words088_255[128-88]); + print_ata_security_status("ATA Security is: ", word128); // Print write cache reordering status if (options.sct_wcache_reorder_get) { - if (isSCTFeatureControlCapable(&drive)) { + if (!isSCTFeatureControlCapable(&drive)) + pout("Wt Cache Reorder: Unavailable\n"); + else if (locked) + pout("Wt Cache Reorder: Unknown (SCT not supported if ATA Security is LOCKED)\n"); + else { int wcache_reorder = ataGetSetSCTWriteCacheReordering(device, false /*enable*/, false /*persistent*/, false /*set*/); @@ -2793,8 +2802,6 @@ int ataPrintMain (ata_device * device, const ata_print_options & options) else pout("Wt Cache Reorder: Unknown (0x%02x)\n", wcache_reorder); } - else - pout("Wt Cache Reorder: Unavailable\n"); } // Print remaining drive info @@ -2886,6 +2893,9 @@ int ataPrintMain (ata_device * device, const ata_print_options & options) if (!isSCTFeatureControlCapable(&drive)) pout("Write cache reordering %sable failed: SCT Feature Control command not supported\n", (enable ? "en" : "dis")); + else if (locked) + pout("Write cache reordering %sable failed: SCT not supported if ATA Security is LOCKED\n", + (enable ? "en" : "dis")); else if (ataGetSetSCTWriteCacheReordering(device, enable, false /*persistent*/, true /*set*/) < 0) { pout("Write cache reordering %sable failed: %s\n", (enable ? "en" : "dis"), device->get_errmsg()); @@ -3310,7 +3320,7 @@ int ataPrintMain (ata_device * device, const ata_print_options & options) pout("SMART Extended Self-test Log size %u not supported\n\n", nsectors); else { raw_buffer log_07_buf(nsectors * 512); - ata_smart_extselftestlog * log_07 = (ata_smart_extselftestlog *)log_07_buf.data(); + ata_smart_extselftestlog * log_07 = reinterpret_cast(log_07_buf.data()); if (!ataReadExtSelfTestLog(device, log_07, nsectors)) { pout("Read SMART Extended Self-test Log failed\n\n"); failuretest(OPTIONAL_CMD, returnval|=FAILSMART); @@ -3378,9 +3388,15 @@ int ataPrintMain (ata_device * device, const ata_print_options & options) // Check if SCT commands available bool sct_ok = isSCTCapable(&drive); - if(!sct_ok && (options.sct_temp_sts || options.sct_temp_hist || options.sct_temp_int - || options.sct_erc_get || options.sct_erc_set )) - pout("SCT Commands not supported\n\n"); + if ( options.sct_temp_sts || options.sct_temp_hist || options.sct_temp_int + || options.sct_erc_get || options.sct_erc_set ) { + if (!sct_ok) + pout("SCT Commands not supported\n\n"); + else if (locked) { + pout("SCT Commands not supported if ATA Security is LOCKED\n\n"); + sct_ok = false; + } + } // Print SCT status and temperature history table if (sct_ok && (options.sct_temp_sts || options.sct_temp_hist || options.sct_temp_int)) { diff --git a/ataprint.h b/ataprint.h index e83020f..b0b2f1b 100644 --- a/ataprint.h +++ b/ataprint.h @@ -1,7 +1,7 @@ /* * ataprint.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2002-9 Bruce Allen * Copyright (C) 2008-12 Christian Franke @@ -25,7 +25,7 @@ #ifndef ATAPRINT_H_ #define ATAPRINT_H_ -#define ATAPRINT_H_CVSID "$Id: ataprint.h 3825 2013-07-06 21:38:25Z samm2 $\n" +#define ATAPRINT_H_CVSID "$Id: ataprint.h 4120 2015-08-27 16:12:21Z samm2 $\n" #include diff --git a/autogen.sh b/autogen.sh index caf1744..f73610b 100755 --- a/autogen.sh +++ b/autogen.sh @@ -1,7 +1,7 @@ #!/bin/sh -# $Id: autogen.sh 4053 2015-04-14 20:18:50Z chrfranke $ +# $Id: autogen.sh 4115 2015-07-15 20:52:26Z chrfranke $ # -# Generate ./configure from config.in and Makefile.in from Makefile.am. +# Generate ./configure from configure.ac and Makefile.in from Makefile.am. # This also adds files like missing,depcomp,install-sh to the source # directory. To update these files at a later date use: # autoreconf -f -i -v @@ -23,77 +23,40 @@ test -x /usr/bin/uname && /usr/bin/uname | grep -i CYGWIN >/dev/null && rm -f dostest.tmp } -typep() -{ - cmd=$1 ; TMP=$IFS ; IFS=: ; set $PATH - for dir - do - if [ -x "$dir/$cmd" ]; then - echo "$dir/$cmd" - IFS=$TMP - return 0 - fi - done - IFS=$TMP - return 1 -} +# Find automake +if [ -n "$AUTOMAKE" ]; then + ver=$("$AUTOMAKE" --version) || exit 1 +else + maxver= + for v in 1.15 1.14 1.13 1.12 1.11 1.10; do + minver=$v; test -n "$maxver" || maxver=$v + ver=$(automake-$v --version 2>/dev/null) || continue + AUTOMAKE="automake-$v" + break + done + if [ -z "$AUTOMAKE" ]; then + echo "GNU Automake $minver (up to $maxver) is required to bootstrap smartmontools from SVN." + exit 1; + fi +fi -test -x "$AUTOMAKE" || - AUTOMAKE=`typep automake-1.15` || AUTOMAKE=`typep automake-1.14` || - AUTOMAKE=`typep automake-1.13` || AUTOMAKE=`typep automake-1.12` || - AUTOMAKE=`typep automake-1.11` || AUTOMAKE=`typep automake-1.10` || - AUTOMAKE=`typep automake-1.9` || AUTOMAKE=`typep automake-1.8` || - AUTOMAKE=`typep automake-1.7` || AUTOMAKE=`typep automake17` || -{ -echo -echo "You must have at least GNU Automake 1.7 (up to 1.15) installed" -echo "in order to bootstrap smartmontools from SVN. Download the" -echo "appropriate package for your distribution, or the source tarball" -echo "from ftp://ftp.gnu.org/gnu/automake/ ." -echo -echo "Also note that support for new Automake series (anything newer" -echo "than 1.15) is only added after extensive tests. If you live in" -echo "the bleeding edge, you should know what you're doing, mainly how" -echo "to test it before the developers. Be patient." -exit 1; -} +ver=$(echo "$ver" | sed -n '1s,^.*[^.0-9]\([12]\.[0-9][-.0-9pl]*\).*$,\1,p') +if [ -z "$ver" ]; then + echo "$AUTOMAKE: Unable to determine automake version." + exit 1 +fi -test -x "$ACLOCAL" || ACLOCAL="aclocal`echo "$AUTOMAKE" | sed 's/.*automake//'`" && ACLOCAL=`typep "$ACLOCAL"` || -{ -echo -echo "autogen.sh found automake-1.X, but not the respective aclocal-1.X." -echo "Your installation of GNU Automake is broken or incomplete." -exit 2; -} +# Check aclocal +if [ -z "$ACLOCAL" ]; then + ACLOCAL="aclocal$(echo "$AUTOMAKE" | sed -n 's,^.*automake\(-[.0-9]*\),\1,p')" +fi -# Detect Automake version -case "$AUTOMAKE" in - *automake-1.7|*automake17) - ver=1.7 ;; - *automake-1.8) - ver=1.8 ;; - *) - ver="`$AUTOMAKE --version | sed -n '1s,^.*[^.0-9]\([12]\.[0-9][-.0-9pl]*\).*$,\1,p'`" - ver="${ver:-?.?.?}" -esac +"$ACLOCAL" --version >/dev/null || exit 1 -# Warn if Automake version was not tested or does not support filesystem +# Warn if Automake version was not tested amwarnings=$warnings case "$ver" in - 1.[78]|1.[78].*) - # Check for case sensitive filesystem - # (to avoid e.g. "DIST_COMMON = ... ChangeLog ..." in Makefile.in on Cygwin) - rm -f CASETEST.TMP - echo > casetest.tmp - test -f CASETEST.TMP && - { - echo "Warning: GNU Automake version ${ver} does not properly handle case" - echo "insensitive filesystems. Some make targets may not work." - } - rm -f casetest.tmp - ;; - - 1.9.[1-6]|1.10|1.10.[123]|1.11|1.11.[1-6]|1.12.[2-6]|1.13.[34]) + 1.10|1.10.[123]|1.11|1.11.[1-6]|1.12.[2-6]|1.13.[34]) # OK ;; @@ -108,32 +71,14 @@ case "$ver" in echo "Please report success/failure to the smartmontools-support mailing list." esac -# Warn if Automake version is too old -case "$ver" in - 1.[789]|1.[789].*) - echo "WARNING:" - echo "The use of GNU Automake version $ver is deprecated. Support for Automake" - echo "versions 1.7 - 1.9.x will be removed in a future release of smartmontools." -esac - -# Install pkg-config macros -# (Don't use 'aclocal -I m4 --install' to keep support for automake < 1.10) +# required for aclocal-1.10 --install test -d m4 || mkdir m4 || exit 1 -test -z "$force" || rm -f m4/pkg.m4 -test -f m4/pkg.m4 || acdir=`${ACLOCAL} --print-ac-dir` && - test -n "$acdir" && test -f "$acdir/pkg.m4" && -{ - echo "$0: installing \`m4/pkg.m4' from \`$acdir/pkg.m4'" - cp "$acdir/pkg.m4" m4/pkg.m4 -} -test -f m4/pkg.m4 || - echo "Warning: cannot install m4/pkg.m4, 'make dist' and systemd detection will not work." set -e # stops on error status test -z "$warnings" || set -x -${ACLOCAL} -I m4 $force $warnings +${ACLOCAL} -I m4 --install $force $warnings autoheader $force $warnings ${AUTOMAKE} --add-missing --copy ${force:+--force-missing} $amwarnings autoconf $force $warnings diff --git a/cciss.cpp b/cciss.cpp index bf074ed..f5871dd 100644 --- a/cciss.cpp +++ b/cciss.cpp @@ -38,7 +38,7 @@ #include "scsicmds.h" #include "utility.h" -const char * cciss_cpp_cvsid = "$Id: cciss.cpp 3945 2014-07-13 15:29:05Z chrfranke $" +const char * cciss_cpp_cvsid = "$Id: cciss.cpp 4156 2015-10-18 12:20:40Z samm2 $" CCISS_H_CVSID; typedef struct _ReportLUNdata_struct @@ -73,10 +73,9 @@ int cciss_io_interface(int device, int target, struct scsi_cmnd_io * iop, int re unsigned char pBuf[512] = {0}; unsigned char phylun[8] = {0}; int iBufLen = 512; - int status = -1; int len = 0; // used later in the code. - status = cciss_getlun(device, target, phylun, report); + int status = cciss_getlun(device, target, phylun, report); if (report > 0) printf(" cciss_getlun(%d, %d) = 0x%x; scsi3addr: %02x %02x %02x %02x %02x %02x %02x %02x\n", device, target, status, @@ -181,7 +180,7 @@ static int cciss_sendpassthru(unsigned int cmdtype, unsigned char *CDB, if ((err = ioctl(fd, CCISS_PASSTHRU, &iocommand))) { - fprintf(stderr, "CCISS ioctl error %d (fd %d CDBLen %d buf_size %d)\n", + fprintf(stderr, "CCISS ioctl error %d (fd %d CDBLen %u buf_size %u)\n", fd, err, CDBlen, size); } return err; diff --git a/configure.ac b/configure.ac index 804291f..1eb6d8d 100644 --- a/configure.ac +++ b/configure.ac @@ -1,12 +1,12 @@ # -# $Id: configure.ac 4109 2015-06-04 16:30:15Z chrfranke $ +# $Id: configure.ac 4181 2015-12-07 20:58:40Z chrfranke $ # dnl Process this file with autoconf to produce a configure script. -AC_PREREQ(2.50) -AC_INIT(smartmontools, 6.4, smartmontools-support@lists.sourceforge.net) -AC_CONFIG_SRCDIR(smartctl.cpp) +AC_PREREQ([2.60]) +AC_INIT(smartmontools, 6.5, smartmontools-support@lists.sourceforge.net) +AM_INIT_AUTOMAKE([1.10 foreign]) -smartmontools_cvs_tag=`echo '$Id: configure.ac 4109 2015-06-04 16:30:15Z chrfranke $'` +smartmontools_cvs_tag=`echo '$Id: configure.ac 4181 2015-12-07 20:58:40Z chrfranke $'` smartmontools_release_date=2015-06-04 smartmontools_release_time="16:29:41 UTC" @@ -14,12 +14,11 @@ AC_DEFINE_UNQUOTED(SMARTMONTOOLS_CONFIGURE_ARGS, "$ac_configure_args", AC_DEFINE_UNQUOTED(SMARTMONTOOLS_RELEASE_DATE, "$smartmontools_release_date", [smartmontools Release Date]) AC_DEFINE_UNQUOTED(SMARTMONTOOLS_RELEASE_TIME, "$smartmontools_release_time", [smartmontools Release Time]) AC_DEFINE_UNQUOTED(CONFIG_H_CVSID, "$smartmontools_cvs_tag", [smartmontools CVS Tag]) -AC_DEFINE_UNQUOTED(PACKAGE_HOMEPAGE, "http://smartmontools.sourceforge.net/", [smartmontools Home Page]) +AC_DEFINE_UNQUOTED(PACKAGE_HOMEPAGE, "http://www.smartmontools.org/", [smartmontools Home Page]) +AC_CONFIG_SRCDIR([smartctl.cpp]) AC_CONFIG_HEADER([config.h]) -AM_INIT_AUTOMAKE([foreign]) - AM_MAINTAINER_MODE AC_LANG([C++]) @@ -231,32 +230,15 @@ case "${host}" in esac AC_SUBST(initdfile) -autoconf_25x=${docdir:-yes} -AC_ARG_WITH(docdir, - [AS_HELP_STRING([--with-docdir=DIR], [Deprecated (use --docdir=DIR instead)])], - [docdir="$withval"], - [ if test -z "$docdir"; then - # autoconf 2.5x without '--docdir' support - docdir='${datadir}/doc/${PACKAGE}' - fi - ]) -AC_SUBST(docdir) - AC_ARG_WITH(exampledir, [AS_HELP_STRING([--with-exampledir=DIR], [Location of example scripts [DOCDIR/examplescripts]])], [exampledir="$withval"], [exampledir='${docdir}/examplescripts']) AC_SUBST(exampledir) -used_deprecated_option=no -AC_ARG_ENABLE(drivedb, - [AS_HELP_STRING([--disable-drivedb], [Deprecated (use --without-drivedbdir instead)])], - [used_deprecated_option=yes], [enable_drivedb=yes]) - -drivedbdir= +drivedbdir='${datadir}/${PACKAGE}' AC_ARG_WITH(drivedbdir, - [AS_HELP_STRING([--with-drivedbdir=@<:@DIR|no@:>@], [Location of drive database file [DATADIR/smartmontools]])], - [test "$withval" != "no" && drivedbdir="$withval"], - [test "$enable_drivedb" != "no" && drivedbdir='${datadir}/${PACKAGE}']) + [AS_HELP_STRING([--with-drivedbdir@<:@=DIR|yes|no@:>@], [Location of drive database file [DATADIR/smartmontools]])], + [case "$withval" in yes) ;; no) drivedbdir= ;; *) drivedbdir="$withval" ;; esac]) AC_SUBST(drivedbdir) AM_CONDITIONAL(ENABLE_DRIVEDB, [test -n "$drivedbdir"]) @@ -272,31 +254,23 @@ AC_ARG_WITH(smartdplugindir, [smartdplugindir='${smartdscriptdir}/smartd_warning.d']) AC_SUBST(smartdplugindir) -AC_ARG_ENABLE(savestates, - [AS_HELP_STRING([--enable-savestates], [Deprecated (use --with-savestates@<:@=yes@:>@ instead)])], - [used_deprecated_option=yes], [enable_savestates=no]) - -savestates='${localstatedir}/lib/${PACKAGE}/smartd.' +savestates= AC_ARG_WITH(savestates, [AS_HELP_STRING([--with-savestates@<:@=PREFIX|yes|no@:>@], [Enable default smartd state files [no] (yes=LOCALSTATEDIR/lib/smartmontools/smartd.)])], - [case "$withval" in yes) ;; no) savestates= ;; *) savestates="$withval" ;; esac], - [test "$enable_savestates" != "yes" && savestates=]) + [case "$withval" in yes) savestates='${localstatedir}/lib/${PACKAGE}/smartd.' ;; + no) ;; *) savestates="$withval" ;; esac]) savestatesdir="${savestates%/*}" AC_SUBST(savestates) AC_SUBST(savestatesdir) AM_CONDITIONAL(ENABLE_SAVESTATES, [test -n "$savestates"]) -AC_ARG_ENABLE(attributelog, - [AS_HELP_STRING([--enable-attributelog], [Deprecated (use --with-attributelog@<:@=yes@:>@ instead)])], - [used_deprecated_option=yes], [enable_attributelog=no]) - -attributelog='${localstatedir}/lib/${PACKAGE}/attrlog.' +attributelog= AC_ARG_WITH(attributelog, [AS_HELP_STRING([--with-attributelog@<:@=PREFIX|yes|no@:>@], [Enable default smartd attribute log files [no] (yes=LOCALSTATEDIR/lib/smartmontools/attrlog.)])], - [case "$withval" in yes) ;; no) attributelog= ;; *) attributelog="$withval" ;; esac], - [test "$enable_attributelog" != "yes" && attributelog=]) + [case "$withval" in yes) attributelog='${localstatedir}/lib/${PACKAGE}/attrlog.' ;; + no) ;; *) attributelog="$withval" ;; esac]) attributelogdir="${attributelog%/*}" AC_SUBST(attributelog) AC_SUBST(attributelogdir) @@ -351,6 +325,21 @@ AC_MSG_CHECKING([whether to use libcap-ng]) AC_SUBST(CAPNG_LDADD) AC_MSG_RESULT([$use_libcap_ng]) +AC_ARG_WITH(solaris-sparc-ata, + [AS_HELP_STRING([--with-solaris-sparc-ata@<:@=yes|no@:>@], + [Enable legacy ATA support on Solaris SPARC (requires os_solaris_ata.s from SVN repository) [no]])]) + +case "$host:$with_solaris_sparc_ata" in + sparc-*-solaris*:yes) + if test ! -f "$srcdir/os_solaris_ata.s"; then + AC_MSG_ERROR([Missing source file: $srcdir/os_solaris_ata.s +This file is no longer included in the source tarball but still +available in the SVN repository.]) + fi + AC_DEFINE(WITH_SOLARIS_SPARC_ATA, 1, [Define to 1 to enable legacy ATA support on Solaris SPARC.]) + ;; +esac + # Assume broken snprintf only on Windows with MSVCRT (MinGW without ANSI stdio support) libc_have_working_snprintf=yes @@ -385,20 +374,49 @@ if test "$libc_have_working_snprintf" = "yes"; then AC_DEFINE(HAVE_WORKING_SNPRINTF, 1, [Define to 1 if the `snprintf' function is sane.]) dnl `vim syntax fi -if test "$prefix" = "NONE"; then - # Fix mandir default set by autoconf 2.5x - if test "$mandir" = '${prefix}/man'; then - AC_SUBST([mandir], ['${prefix}/share/man']) - fi +os_win32_manifest= +case "$host" in + *-*-mingw*) + # Newer MinGW may add a default manifest + AC_MSG_CHECKING([whether $CC adds an application manifest]) + cc_adds_manifest=no + AC_LINK_IFELSE([AC_LANG_PROGRAM()], [ + if "$WINDRES" -O rc conftest.exe 2>/dev/null | grep '^1.*RT_MANIFEST' >/dev/null 2>&1; then + cc_adds_manifest=incomplete + # Manifest must provide a Win 10 compatibility ID + if "$WINDRES" -O rc conftest.exe 2>/dev/null | grep '{8e0f7a12-bfb3-4fe8-b9a5-48fd50a15a9a}' >/dev/null 2>&1; then + cc_adds_manifest=yes + fi + fi], + [AC_MSG_ERROR([test compile failed])]) + AC_MSG_RESULT([$cc_adds_manifest]) + test "$cc_adds_manifest" = "yes" || os_win32_manifest='default.manifest.o' + ;; +esac + +# TODO: Remove after smartmontools 6.5 +AC_ARG_WITH(docdir, + [AS_HELP_STRING([--with-docdir=DIR], [(removed, use --docdir=DIR instead)])], + [AC_MSG_ERROR([--with-docdir is no longer supported, use --docdir instead])]) +AC_ARG_ENABLE(drivedb, + [AS_HELP_STRING([--disable-drivedb], [(removed, use --without-drivedbdir instead)])]) +AC_ARG_ENABLE(savestates, + [AS_HELP_STRING([--enable-savestates], [(removed, use --with-savestates@<:@=yes@:>@ instead)])]) +AC_ARG_ENABLE(attributelog, + [AS_HELP_STRING([--enable-attributelog], [(removed, use --with-attributelog@<:@=yes@:>@ instead)])]) +if test -n "${enable_drivedb+set}${enable_savestates+set}${enable_attributelog+set}"; then + AC_MSG_ERROR([Options --disable-drivedb, --enable-savestates, --enable-attributelog are no longer supported. +Use --without-drivedbdir, --with-savestates, --with-attributelog instead.]) fi + AC_SUBST(releaseversion,['${PACKAGE}-${VERSION}']) AC_SUBST(smartmontools_release_date) AC_SUBST(smartmontools_release_time) # Set platform-specific modules and symbols os_libs= -os_dltools='curl wget lynx' +os_dltools='curl wget lynx svn' os_mailer=mail os_hostname="'hostname'" os_dnsdomainname= @@ -419,12 +437,14 @@ case "${host}" in *-*-freebsd*|*-*-dragonfly*|*-*-kfreebsd*-gnu*) os_deps='os_freebsd.o cciss.o dev_areca.o' os_libs='-lcam' - os_dltools='curl wget lynx fetch' + os_dltools='curl wget lynx fetch svn' AC_CHECK_LIB(usb, libusb20_dev_get_device_desc) os_man_filter=FreeBSD ;; sparc-*-solaris*) - os_deps='os_solaris.o os_solaris_ata.o' + os_deps='os_solaris.o' + test "$with_solaris_sparc_ata" = "yes" \ + && os_deps="$os_deps os_solaris_ata.o" os_mailer='mailx' os_solaris=yes os_man_filter=Solaris @@ -443,7 +463,7 @@ case "${host}" in *-*-openbsd*) os_deps='os_openbsd.o' os_libs='-lutil' - os_dltools='curl wget lynx ftp' + os_dltools='curl wget lynx ftp svn' os_man_filter=OpenBSD ;; *-*-cygwin*) @@ -505,6 +525,7 @@ AC_SUBST([os_hostname]) AC_SUBST([os_dnsdomainname]) AC_SUBST([os_nisdomainname]) AC_SUBST([os_man_filter]) +AC_SUBST([os_win32_manifest]) # Create drivedb.h update branch name from version: 5.41[.X] -> RELEASE_5_41_DRIVEDB DRIVEDB_BRANCH=`echo $VERSION | sed 's,^\([[0-9]]*\.[[0-9]]*\)\..*$,\1,' \ @@ -576,6 +597,7 @@ echo "OS specific modules: $os_deps $os_libs $LIBS" >&AS_MESSAGE_FD case "$host_os" in mingw*) + echo "application manifest: ${os_win32_manifest:-built-in}" >&AS_MESSAGE_FD echo "resource compiler: $WINDRES" >&AS_MESSAGE_FD echo "message compiler: $WINDMC" >&AS_MESSAGE_FD echo "NSIS compiler: $MAKENSIS" >&AS_MESSAGE_FD @@ -646,19 +668,14 @@ case "$host_os" in esac echo "-----------------------------------------------------------------------------" >&AS_MESSAGE_FD -if test "$autoconf_25x" = "yes"; then - echo "WARNING:" >&AS_MESSAGE_FD - echo "Support for old autoconf 2.5x versions will be removed in a future" >&AS_MESSAGE_FD - echo "release of smartmontools." >&AS_MESSAGE_FD -elif test "${with_docdir+set}" = "set"; then - echo "WARNING:" >&AS_MESSAGE_FD - echo "Option --with-docdir is deprecated and will be removed in a future" >&AS_MESSAGE_FD - echo "release of smartmontools. Use --docdir instead." >&AS_MESSAGE_FD -fi - -if test "$used_deprecated_option" = "yes"; then - echo "WARNING:" >&AS_MESSAGE_FD - echo "Options --disable-drivedb, --enable-savestates, --enable-attributelog are" >&AS_MESSAGE_FD - echo "deprecated and will be removed in a future release of smartmontools." >&AS_MESSAGE_FD - echo "Use --without-drivedb, --with-savestates, --with-attributelog instead." >&AS_MESSAGE_FD -fi +# TODO: Remove after smartmontools 6.5 +case "$host:${with_solaris_sparc_ata+set}" in + sparc-*-solaris*:) + AC_MSG_WARN([ +Legacy ATA support is no longer enabled by default on Solaris SPARC. +The required source file 'os_solaris_ata.s' is no longer included in +the source tarball but still available in the SVN repository. +Use option '--with-solaris-sparc-ata' to enable legacy ATA support. +Use option '--without-solaris-sparc-ata' to suppress this warning.]) + ;; +esac diff --git a/dev_areca.cpp b/dev_areca.cpp index 941d90a..91edb03 100644 --- a/dev_areca.cpp +++ b/dev_areca.cpp @@ -1,7 +1,7 @@ /* * dev_areca.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2012 Hank Wu * @@ -21,7 +21,7 @@ #include "dev_interface.h" #include "dev_areca.h" -const char * dev_areca_cpp_cvsid = "$Id: dev_areca.cpp 3872 2014-02-03 21:07:51Z chrfranke $" +const char * dev_areca_cpp_cvsid = "$Id: dev_areca.cpp 4209 2016-01-22 20:49:44Z chrfranke $" DEV_ARECA_H_CVSID; #include "atacmds.h" @@ -297,14 +297,14 @@ int generic_areca_device::arcmsr_ui_handler(unsigned char *areca_packet, int are if (expected==-3) { return set_err(EIO); } - expected = arcmsr_command_handler(ARCMSR_CLEAR_WQBUFFER, NULL, 0); + arcmsr_command_handler(ARCMSR_CLEAR_WQBUFFER, NULL, 0); expected = arcmsr_command_handler(ARCMSR_WRITE_WQBUFFER, areca_packet, areca_packet_len); if ( expected > 0 ) { expected = arcmsr_command_handler(ARCMSR_READ_RQBUFFER, return_buff, sizeof(return_buff)); } - if ( expected < 0 ) + if ( expected < 3 + 1 ) // Prefix + Checksum { return -1; } diff --git a/dev_areca.h b/dev_areca.h index 6127171..0297be9 100644 --- a/dev_areca.h +++ b/dev_areca.h @@ -1,7 +1,7 @@ /* * dev_areca.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2012 Hank Wu * @@ -18,7 +18,7 @@ #ifndef DEV_ARECA_H #define DEV_ARECA_H -#define DEV_ARECA_H_CVSID "$Id: dev_areca.h 3854 2013-09-12 05:36:20Z chrfranke $" +#define DEV_ARECA_H_CVSID "$Id: dev_areca.h 4146 2015-10-17 12:12:49Z chrfranke $" ///////////////////////////////////////////////////////////////////////////// /// Areca RAID support @@ -118,9 +118,10 @@ public: virtual bool arcmsr_ata_pass_through(const ata_cmd_in & in, ata_cmd_out & out); protected: - generic_areca_device() : smart_device(never_called) - { - } + generic_areca_device() + : smart_device(never_called), + m_disknum(-1), m_encnum(-1) + { } void set_disknum(int disknum) {m_disknum = disknum;} diff --git a/dev_ata_cmd_set.cpp b/dev_ata_cmd_set.cpp index 41c6234..93cb339 100644 --- a/dev_ata_cmd_set.cpp +++ b/dev_ata_cmd_set.cpp @@ -1,7 +1,7 @@ /* * dev_ata_cmd_set.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2008 Christian Franke * @@ -22,7 +22,7 @@ #include -const char * dev_ata_cmd_set_cpp_cvsid = "$Id: dev_ata_cmd_set.cpp,v 1.4 2008/10/24 21:49:23 manfred99 Exp $" +const char * dev_ata_cmd_set_cpp_cvsid = "$Id: dev_ata_cmd_set.cpp 4122 2015-08-27 19:08:07Z chrfranke $" DEV_ATA_CMD_SET_H_CVSID; diff --git a/dev_ata_cmd_set.h b/dev_ata_cmd_set.h index ec1457b..7cdddc1 100644 --- a/dev_ata_cmd_set.h +++ b/dev_ata_cmd_set.h @@ -1,7 +1,7 @@ /* * dev_ata_cmd_set.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2008 Christian Franke * @@ -18,7 +18,7 @@ #ifndef DEV_ATA_CMD_SET_H #define DEV_ATA_CMD_SET_H -#define DEV_ATA_CMD_SET_H_CVSID "$Id: dev_ata_cmd_set.h,v 1.3 2008/08/23 21:32:12 chrfranke Exp $\n" +#define DEV_ATA_CMD_SET_H_CVSID "$Id: dev_ata_cmd_set.h 4122 2015-08-27 19:08:07Z chrfranke $" #include "atacmds.h" // smart_command_set #include "dev_interface.h" diff --git a/dev_interface.cpp b/dev_interface.cpp index 71bf8bc..a680e7d 100644 --- a/dev_interface.cpp +++ b/dev_interface.cpp @@ -1,7 +1,7 @@ /* * dev_interface.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2008-13 Christian Franke * @@ -32,7 +32,7 @@ #include #endif -const char * dev_interface_cpp_cvsid = "$Id: dev_interface.cpp 3741 2013-01-02 17:06:54Z chrfranke $" +const char * dev_interface_cpp_cvsid = "$Id: dev_interface.cpp 4120 2015-08-27 16:12:21Z samm2 $" DEV_INTERFACE_H_CVSID; ///////////////////////////////////////////////////////////////////////////// diff --git a/dev_interface.h b/dev_interface.h index fe3bb2a..f524a17 100644 --- a/dev_interface.h +++ b/dev_interface.h @@ -1,9 +1,9 @@ /* * dev_interface.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * - * Copyright (C) 2008-12 Christian Franke + * Copyright (C) 2008-15 Christian Franke * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -18,7 +18,7 @@ #ifndef DEV_INTERFACE_H #define DEV_INTERFACE_H -#define DEV_INTERFACE_H_CVSID "$Id: dev_interface.h 3663 2012-10-24 20:35:55Z chrfranke $\n" +#define DEV_INTERFACE_H_CVSID "$Id: dev_interface.h 4152 2015-10-17 16:08:21Z chrfranke $\n" #include "utility.h" @@ -78,7 +78,7 @@ protected: enum do_not_use_in_implementation_classes { never_called }; /// Dummy constructor for abstract classes. /// Must never be called in implementation classes. - smart_device(do_not_use_in_implementation_classes); + explicit smart_device(do_not_use_in_implementation_classes); public: virtual ~smart_device() throw(); diff --git a/dev_legacy.cpp b/dev_legacy.cpp index ca4575b..13d3a84 100644 --- a/dev_legacy.cpp +++ b/dev_legacy.cpp @@ -1,7 +1,7 @@ /* * dev_legacy.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2008-11 Christian Franke * @@ -25,7 +25,7 @@ #include -const char * dev_legacy_cpp_cvsid = "$Id: dev_legacy.cpp 3263 2011-02-20 18:32:56Z chrfranke $" +const char * dev_legacy_cpp_cvsid = "$Id: dev_legacy.cpp 4120 2015-08-27 16:12:21Z samm2 $" DEV_INTERFACE_H_CVSID; ///////////////////////////////////////////////////////////////////////////// @@ -275,7 +275,7 @@ smart_device * legacy_smart_interface::autodetect_smart_device(const char * name static void free_devnames(char * * devnames, int numdevs) { - static const char version[] = "$Id: dev_legacy.cpp 3263 2011-02-20 18:32:56Z chrfranke $"; + static const char version[] = "$Id: dev_legacy.cpp 4120 2015-08-27 16:12:21Z samm2 $"; for (int i = 0; i < numdevs; i++) FreeNonZero(devnames[i], -1,__LINE__, version); FreeNonZero(devnames, (sizeof (char*) * numdevs),__LINE__, version); diff --git a/dev_tunnelled.h b/dev_tunnelled.h index 173c6f4..aa4ff2b 100644 --- a/dev_tunnelled.h +++ b/dev_tunnelled.h @@ -1,7 +1,7 @@ /* * dev_tunnelled.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2008 Christian Franke * @@ -18,7 +18,7 @@ #ifndef DEV_TUNNELLED_H #define DEV_TUNNELLED_H -#define DEV_TUNNELLED_H_CVSID "$Id: dev_tunnelled.h,v 1.1 2008/07/25 21:16:00 chrfranke Exp $\n" +#define DEV_TUNNELLED_H_CVSID "$Id: dev_tunnelled.h 4122 2015-08-27 19:08:07Z chrfranke $" #include "dev_interface.h" diff --git a/drivedb.h b/drivedb.h index 0a4336b..72df43d 100644 --- a/drivedb.h +++ b/drivedb.h @@ -1,10 +1,10 @@ /* * drivedb.h - smartmontools drive database file * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2003-11 Philip Williams, Bruce Allen - * Copyright (C) 2008-15 Christian Franke + * Copyright (C) 2008-16 Christian Franke * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -75,83 +75,85 @@ /* const drive_settings builtin_knowndrives[] = { */ - { "$Id: drivedb.h 4105 2015-06-03 19:32:30Z chrfranke $", + { "$Id: drivedb.h 4212 2016-01-24 21:53:53Z samm2 $", "-", "-", "This is a dummy entry to hold the SVN-Id of drivedb.h", "" - /* Default settings: + }, + { "DEFAULT", + "-", "-", + "Default settings", "-v 1,raw48,Raw_Read_Error_Rate " "-v 2,raw48,Throughput_Performance " "-v 3,raw16(avg16),Spin_Up_Time " "-v 4,raw48,Start_Stop_Count " "-v 5,raw16(raw16),Reallocated_Sector_Ct " - "-v 6,raw48,Read_Channel_Margin " // HDD only - "-v 7,raw48,Seek_Error_Rate " // HDD only - "-v 8,raw48,Seek_Time_Performance " // HDD only + "-v 6,raw48,Read_Channel_Margin,HDD " + "-v 7,raw48,Seek_Error_Rate,HDD " + "-v 8,raw48,Seek_Time_Performance,HDD " "-v 9,raw24(raw8),Power_On_Hours " - "-v 10,raw48,Spin_Retry_Count " // HDD only - "-v 11,raw48,Calibration_Retry_Count " // HDD only + "-v 10,raw48,Spin_Retry_Count,HDD " + "-v 11,raw48,Calibration_Retry_Count,HDD " "-v 12,raw48,Power_Cycle_Count " "-v 13,raw48,Read_Soft_Error_Rate " // 14-174 Unknown_Attribute - "-v 175,raw48,Program_Fail_Count_Chip " // SSD only - "-v 176,raw48,Erase_Fail_Count_Chip " // SSD only - "-v 177,raw48,Wear_Leveling_Count " // SSD only - "-v 178,raw48,Used_Rsvd_Blk_Cnt_Chip " // SSD only - "-v 179,raw48,Used_Rsvd_Blk_Cnt_Tot " // SSD only - "-v 180,raw48,Unused_Rsvd_Blk_Cnt_Tot " // SSD only + "-v 175,raw48,Program_Fail_Count_Chip,SSD " + "-v 176,raw48,Erase_Fail_Count_Chip,SSD " + "-v 177,raw48,Wear_Leveling_Count,SSD " + "-v 178,raw48,Used_Rsvd_Blk_Cnt_Chip,SSD " + "-v 179,raw48,Used_Rsvd_Blk_Cnt_Tot,SSD " + "-v 180,raw48,Unused_Rsvd_Blk_Cnt_Tot,SSD " "-v 181,raw48,Program_Fail_Cnt_Total " - "-v 182,raw48,Erase_Fail_Count_Total " // SSD only + "-v 182,raw48,Erase_Fail_Count_Total,SSD " "-v 183,raw48,Runtime_Bad_Block " "-v 184,raw48,End-to-End_Error " // 185-186 Unknown_Attribute "-v 187,raw48,Reported_Uncorrect " "-v 188,raw48,Command_Timeout " - "-v 189,raw48,High_Fly_Writes " // HDD only + "-v 189,raw48,High_Fly_Writes,HDD " "-v 190,tempminmax,Airflow_Temperature_Cel " - "-v 191,raw48,G-Sense_Error_Rate " // HDD only + "-v 191,raw48,G-Sense_Error_Rate,HDD " "-v 192,raw48,Power-Off_Retract_Count " - "-v 193,raw48,Load_Cycle_Count " // HDD only + "-v 193,raw48,Load_Cycle_Count,HDD " "-v 194,tempminmax,Temperature_Celsius " "-v 195,raw48,Hardware_ECC_Recovered " "-v 196,raw16(raw16),Reallocated_Event_Count " "-v 197,raw48,Current_Pending_Sector " "-v 198,raw48,Offline_Uncorrectable " "-v 199,raw48,UDMA_CRC_Error_Count " - "-v 200,raw48,Multi_Zone_Error_Rate " // HDD only - "-v 201,raw48,Soft_Read_Error_Rate " // HDD only - "-v 202,raw48,Data_Address_Mark_Errs " // HDD only + "-v 200,raw48,Multi_Zone_Error_Rate,HDD " + "-v 201,raw48,Soft_Read_Error_Rate,HDD " + "-v 202,raw48,Data_Address_Mark_Errs,HDD " "-v 203,raw48,Run_Out_Cancel " "-v 204,raw48,Soft_ECC_Correction " "-v 205,raw48,Thermal_Asperity_Rate " - "-v 206,raw48,Flying_Height " // HDD only - "-v 207,raw48,Spin_High_Current " // HDD only - "-v 208,raw48,Spin_Buzz " // HDD only - "-v 209,raw48,Offline_Seek_Performnce " // HDD only + "-v 206,raw48,Flying_Height,HDD " + "-v 207,raw48,Spin_High_Current,HDD " + "-v 208,raw48,Spin_Buzz,HDD " + "-v 209,raw48,Offline_Seek_Performnce,HDD " // 210-219 Unknown_Attribute - "-v 220,raw48,Disk_Shift " // HDD only - "-v 221,raw48,G-Sense_Error_Rate " // HDD only - "-v 222,raw48,Loaded_Hours " // HDD only - "-v 223,raw48,Load_Retry_Count " // HDD only - "-v 224,raw48,Load_Friction " // HDD only - "-v 225,raw48,Load_Cycle_Count " // HDD only - "-v 226,raw48,Load-in_Time " // HDD only - "-v 227,raw48,Torq-amp_Count " // HDD only + "-v 220,raw48,Disk_Shift,HDD " + "-v 221,raw48,G-Sense_Error_Rate,HDD " + "-v 222,raw48,Loaded_Hours,HDD " + "-v 223,raw48,Load_Retry_Count,HDD " + "-v 224,raw48,Load_Friction,HDD " + "-v 225,raw48,Load_Cycle_Count,HDD " + "-v 226,raw48,Load-in_Time,HDD " + "-v 227,raw48,Torq-amp_Count,HDD " "-v 228,raw48,Power-off_Retract_Count " // 229 Unknown_Attribute - "-v 230,raw48,Head_Amplitude " // HDD only + "-v 230,raw48,Head_Amplitude,HDD " "-v 231,raw48,Temperature_Celsius " "-v 232,raw48,Available_Reservd_Space " - "-v 233,raw48,Media_Wearout_Indicator " // SSD only + "-v 233,raw48,Media_Wearout_Indicator,SSD " // 234-239 Unknown_Attribute - "-v 240,raw24(raw8),Head_Flying_Hours " // HDD only, smartmontools <= r3966: raw48 + "-v 240,raw24(raw8),Head_Flying_Hours,HDD " "-v 241,raw48,Total_LBAs_Written " "-v 242,raw48,Total_LBAs_Read " // 243-249 Unknown_Attribute "-v 250,raw48,Read_Error_Retry_Rate " // 251-253 Unknown_Attribute - "-v 254,raw48,Free_Fall_Sensor " // HDD only - */ + "-v 254,raw48,Free_Fall_Sensor,HDD" }, { "Apacer SSD", "(2|4|8|16|32)GB SATA Flash Drive", // tested with APSDM002G15AN-CT/SFDDA01C and SFI2101D, APSDM004G13AN-AT/SFDE001A @@ -305,9 +307,11 @@ const drive_settings builtin_knowndrives[] = { "-v 247,raw48,Host_Program_Page_Count " "-v 248,raw48,Bckgnd_Program_Page_Cnt" }, - { "Micron M500DC Enterprise SSDs", - "Micron_M500DC_(EE|MT)FDDA[AK](120|240|480|800)MBB", // tested with + { "Micron M500DC/M510DC Enterprise SSDs", + "Micron_M500DC_(EE|MT)FDDA[AK](120|240|480|800)MBB|" // tested with // Micron_M500DC_EEFDDAA120MBB/129, Micron_M500DC_MTFDDAK800MBB/0129 + "MICRON_M510DC_(EE|MT)FDDAK(120|240|480|800|960)MBP", // tested with + // Micron_M510DC_MTFDDAK240MBP/0005 "", "", //"-v 1,raw48,Raw_Read_Error_Rate " "-v 5,raw48,Reallocated_Block_Count " @@ -331,6 +335,33 @@ const drive_settings builtin_knowndrives[] = { "-v 247,raw48,Host_Program_Page_Count " "-v 248,raw48,Bckgnd_Program_Page_Cnt" }, + { "SandForce Driven SSDs", // Corsair Force LS with buggy firmware only + "Corsair Force LS SSD", // tested with Corsair Force LS SSD/S9FM01.8 + "S9FM01\\.8", + "A firmware update is available for this drive.\n" + "It is HIGHLY RECOMMENDED for drives with specific serial numbers.\n" + "See the following web pages for details:\n" + "http://www.corsair.com/en-us/force-series-ls-60gb-sata-3-6gb-s-ssd\n" + "https://www.smartmontools.org/ticket/628", + "-v 1,raw24/raw32,Raw_Read_Error_Rate " + "-v 5,raw48,Retired_Block_Count " + "-v 9,msec24hour32,Power_On_Hours_and_Msec " + //"-v 12,raw48,Power_Cycle_Count " + "-v 162,raw48,Unknown_SandForce_Attr " + "-v 170,raw48,Reserve_Block_Count " + "-v 172,raw48,Erase_Fail_Count " + "-v 173,raw48,Unknown_SandForce_Attr " + "-v 174,raw48,Unexpect_Power_Loss_Ct " + "-v 181,raw48,Program_Fail_Count " + //"-v 187,raw48,Reported_Uncorrect " + //"-v 192,raw48,Power-Off_Retract_Count " + //"-v 194,tempminmax,Temperature_Celsius " + //"-v 196,raw16(raw16),Reallocated_Event_Count " + "-v 218,raw48,Unknown_SandForce_Attr " + "-v 231,raw48,SSD_Life_Left " + "-v 241,raw48,Lifetime_Writes_GiB " + "-v 242,raw48,Lifetime_Reads_GiB" + }, { "SandForce Driven SSDs", "SandForce 1st Ed\\.|" // Demo Drive, tested with firmware 320A13F0 "ADATA SSD S(396|510|599) .?..GB|" // tested with ADATA SSD S510 60GB/320ABBF0, @@ -344,7 +375,8 @@ const drive_settings builtin_knowndrives[] = { "Corsair CSSD-F(40|60|80|115|120|160|240)GBP?2.*|" // Corsair Force, tested with // Corsair CSSD-F40GB2/1.1, Corsair CSSD-F115GB2-A/2.1a "Corsair Force ((3 |LS )?SSD|GS|GT)|" // SF-2281, tested with - // Corsair Force SSD/5.05, 3 SSD/1.3.2, GT/1.3.3, GS/5.03, LS SSD/S8FM06.5 + // Corsair Force SSD/5.05, 3 SSD/1.3.2, GT/1.3.3, GS/5.03, + // Corsair Force LS SSD/S8FM06.5, S9FM01.8, S9FM02.0 "FM-25S2S-(60|120|240)GBP2|" // G.SKILL Phoenix Pro, SF-1200, tested with // FM-25S2S-240GBP2/4.2 "FTM(06|12|24|48)CT25H|" // Supertalent TeraDrive CT, tested with @@ -359,8 +391,9 @@ const drive_settings builtin_knowndrives[] = { "KINGSTON SMS200S3(30|60|120)G|" // mSATA, SF-2241, tested with SMS200S3120G/KC3ABBF0 "KINGSTON SMS450S3(32|64|128)G|" // mSATA, SF-2281, tested with SMS450S3128G/503ABBF0 "KINGSTON (SV300|SKC100|SE100)S3.*G|" // other SF-2281 - "MKNSSDCR(45|60|90|120|180|240|480)GB(-[DM]X)?|" // Mushkin Chronos (Deluxe/Enhanced), SF-2281, - // tested with MKNSSDCR120GB, MKNSSDCR120GB-MX/560ABBF0 + "MKNSSDCR(45|60|90|120|180|240|360|480)GB(-(7|DX7?|MX|G2))?|" // Mushkin Chronos (7mm/Deluxe/MX/G2), + // SF-2281, tested with MKNSSDCR120GB, MKNSSDCR120GB-MX/560ABBF0, MKNSSDCR480GB-DX7/603ABBF0 + "MKNSSDEC(60|120|240|480|512)GB|" // Mushkin Enhanced ECO2, tested with MKNSSDEC120GB/604ABBF0 "MKNSSDAT(30|40|60|120|180|240|480)GB(-(DX|V))?|" // Mushkin Atlas (Deluxe/Value), mSATA, SF-2281, // tested with MKNSSDAT120GB-V/540ABBF0 "Mushkin MKNSSDCL(40|60|80|90|115|120|180|240|480)GB-DX2?|" // Mushkin Callisto deluxe, @@ -370,6 +403,7 @@ const drive_settings builtin_knowndrives[] = { "OCZ-NOCTI|" // mSATA, SF-2100, tested with OCZ-NOCTI/2.15 "OCZ-REVODRIVE3?( X2)?|" // PCIe, SF-1200/2281, tested with // OCZ-REVODRIVE( X2)?/1.20, OCZ-REVODRIVE3 X2/2.11 + "OCZ-REVODRIVE350|" "OCZ[ -](VELO|VERTEX2[ -](EX|PRO))( [123]\\..*)?|" // SF-1500, tested with // OCZ VERTEX2-PRO/1.10 (Bogus thresholds for attribute 232 and 235) "D2[CR]STK251...-....|" // OCZ Deneva 2 C/R, SF-22xx/25xx, @@ -378,6 +412,7 @@ const drive_settings builtin_knowndrives[] = { // OCZ-AGILITY3/2.11, OCZ-SOLID3/2.15, OCZ-VERTEX3 MI/2.15 "OCZ Z-DRIVE R4 [CR]M8[48]|" // PCIe, SF-2282/2582, tested with OCZ Z-DRIVE R4 CM84/2.13 // (Bogus attributes under Linux) + "OCZ Z-DRIVE 4500|" "TALOS2|" // OCZ Talos 2 C/R, SAS (works with -d sat), 2*SF-2282, tested with TALOS2/3.20E "(APOC|DENC|DENEVA|FTNC|GFGC|MANG|MMOC|NIMC|TMSC).*|" // other OCZ SF-1200, // tested with DENCSTE251M11-0120/1.33, DENEVA PCI-E/1.33 @@ -409,9 +444,11 @@ const drive_settings builtin_knowndrives[] = { //"-v 12,raw48,Power_Cycle_Count " "-v 13,raw24/raw32,Soft_Read_Error_Rate " "-v 100,raw48,Gigabytes_Erased " + "-v 162,raw48,Unknown_SandForce_Attr " // Corsair Force LS SSD/S9FM01.8, *2.0 "-v 170,raw48,Reserve_Block_Count " "-v 171,raw48,Program_Fail_Count " "-v 172,raw48,Erase_Fail_Count " + "-v 173,raw48,Unknown_SandForce_Attr " // Corsair Force LS SSD/S9FM01.8, *2.0 "-v 174,raw48,Unexpect_Power_Loss_Ct " "-v 177,raw48,Wear_Range_Delta " "-v 181,raw48,Program_Fail_Count " @@ -419,6 +456,7 @@ const drive_settings builtin_knowndrives[] = { "-v 184,raw48,IO_Error_Detect_Code_Ct " //"-v 187,raw48,Reported_Uncorrect " "-v 189,tempminmax,Airflow_Temperature_Cel " + //"-v 192,raw48,Power-Off_Retract_Count " //"-v 194,tempminmax,Temperature_Celsius " "-v 195,raw24/raw32,ECC_Uncorr_Error_Count " //"-v 196,raw16(raw16),Reallocated_Event_Count " @@ -426,6 +464,7 @@ const drive_settings builtin_knowndrives[] = { "-v 199,raw48,SATA_CRC_Error_Count " "-v 201,raw24/raw32,Unc_Soft_Read_Err_Rate " "-v 204,raw24/raw32,Soft_ECC_Correct_Rate " + "-v 218,raw48,Unknown_SandForce_Attr " // Corsair Force LS SSD/S9FM01.8, *2.0 "-v 230,raw48,Life_Curve_Status " "-v 231,raw48,SSD_Life_Left " //"-v 232,raw48,Available_Reservd_Space " @@ -437,6 +476,7 @@ const drive_settings builtin_knowndrives[] = { }, { "Indilinx Barefoot based SSDs", "Corsair CSSD-V(32|60|64|128|256)GB2|" // Corsair Nova, tested with Corsair CSSD-V32GB2/2.2 + "Corsair CMFSSD-(32|64|128|256)D1|" // Corsair Extreme, tested with Corsair CMFSSD-128D1/1.0 "CRUCIAL_CT(64|128|256)M225|" // tested with CRUCIAL_CT64M225/1571 "G.SKILL FALCON (64|128|256)GB SSD|" // tested with G.SKILL FALCON 128GB SSD/2030 "OCZ[ -](AGILITY|ONYX|VERTEX( 1199|-TURBO| v1\\.10)?)|" // tested with @@ -489,8 +529,10 @@ const drive_settings builtin_knowndrives[] = { //"-v 233,raw48,Media_Wearout_Indicator" }, { "Indilinx Barefoot 3 based SSDs", - "OCZ-VECTOR(150)?|" // tested with OCZ-VECTOR/1.03, OCZ-VECTOR150/1.2 - "OCZ-VERTEX4[56]0|" // Barefoot 3 M10, tested with OCZ-VERTEX450/1.0, OCZ-VERTEX460/1.0 + "OCZ-VECTOR(1[58]0)?|" // tested with OCZ-VECTOR/1.03, OCZ-VECTOR150/1.2, OCZ-VECTOR180 + "OCZ-VERTEX4[56]0A?|" // Barefoot 3 M10, tested with OCZ-VERTEX450/1.0, OCZ-VERTEX460/1.0, VERTEX460A + "OCZ-SABER1000|" + "OCZ-ARC100|" "Radeon R7", // Barefoot 3 M00, tested with Radeon R7/1.00 "", "", "-v 5,raw48,Runtime_Bad_Block " @@ -504,15 +546,27 @@ const drive_settings builtin_knowndrives[] = { "-v 197,raw48,Total_Unc_Read_Failures " "-v 198,raw48,Host_Reads_GiB " "-v 199,raw48,Host_Writes_GiB " + "-v 205,raw48,Max_Rated_PE_Count " + "-v 206,raw48,Min_Erase_Count " + "-v 207,raw48,Max_Erase_Count " "-v 208,raw48,Average_Erase_Count " "-v 210,raw48,SATA_CRC_Error_Count " + "-v 212,raw48,Pages_Requiring_Rd_Rtry " + "-v 213,raw48,Snmple_Retry_Attempts " + "-v 214,raw48,Adaptive_Retry_Attempts " + "-v 222,raw48,RAID_Recovery_Count " + "-v 224,raw48,In_Warranty " + "-v 225,raw48,DAS_Polarity " + "-v 226,raw48,Partial_Pfail " + "-v 230,raw48,Write_Throttling " "-v 233,raw48,Remaining_Lifetime_Perc " "-v 241,raw48,Host_Writes_GiB " // M00/M10 "-v 242,raw48,Host_Reads_GiB " // M00/M10 - "-v 249,raw48,Total_NAND_Prog_Ct_GiB" + "-v 249,raw48,Total_NAND_Prog_Ct_GiB " + "-v 251,raw48,Total_NAND_Read_Ct_GiB" }, - { "OCZ Intrepid 3000 SSDs", // tested with OCZ INTREPID 3600/1.4.3.6, 3800/1.4.3.0 - "OCZ INTREPID 3[68]00", + { "OCZ Intrepid 3000 SSDs", // tested with OCZ INTREPID 3600/1.4.3.6, 3800/1.4.3.0, 3700/1.5.0.4 + "OCZ INTREPID 3[678]00", "", "", "-v 5,raw48,Runtime_Bad_Block " //"-v 9,raw24(raw8),Power_On_Hours " @@ -545,6 +599,19 @@ const drive_settings builtin_knowndrives[] = { "-v 249,raw48,Total_NAND_Prog_Ct_GiB " "-v 251,raw48,Total_NAND_Read_Ct_GiB" }, + { + "OCZ Trion", + "OCZ-TRION100", // tested with OCZ-TRION100/SAFM11.2 + "", "", + //"-v 9,raw24(raw8),Power_On_Hours " + //"-v 12,raw48,Power_Cycle_Count " + "-v 167,raw48,SSD_Protect_Mode " + "-v 168,raw48,SATA_PHY_Error_Count " + "-v 169,raw48,Bad_Block_Count " + "-v 173,raw48,Erase_Count " + "-v 192,raw48,Unexpect_Power_Loss_Ct" + //"-v 194,tempminmax,Temperature_Celsius " + }, { "InnoDisk InnoLite SATADOM D150QV-L SSDs", // tested with InnoLite SATADOM D150QV-L/120319 "InnoLite SATADOM D150QV-L", "", "", @@ -569,6 +636,84 @@ const drive_settings builtin_knowndrives[] = { "-v 236,raw48,Unstable_Power_Count " "-v 240,raw48,Write_Head" }, + { "Innodisk 3MG2-P SSDs", // tested with 2.5" SATA SSD 3MG2-P/M140402, + // 1.8 SATA SSD 3IE2-P/M150821, 2.5" SATA SSD 3IE2-P/M150821, + // SATA Slim 3MG2-P/M141114, M.2 (S80) 3MG2-P/M141114 + "((1\\.8|2\\.5)\"? SATA SSD|SATA Slim|M\\.2 \\(S80\\)) 3(MG|IE)2-P", + "", "", + //"-v 1,raw48,Raw_Read_Error_Rate " + //"-v 2,raw48,Throughput_Performance " + //"-v 9,raw24(raw8),Power_On_Hours " + //"-v 12,raw48,Power_Cycle_Count " + "-v 160,raw48,Uncorrectable_Error_Cnt " + "-v 161,raw48,Number_of_Pure_Spare " + "-v 163,raw48,Initial_Bad_Block_Count " + "-v 164,raw48,Total_Erase_Count " + "-v 165,raw48,Max_Erase_Count " + "-v 166,raw48,Min_Erase_Count " + "-v 167,raw48,Average_Erase_Count " + "-v 168,raw48,Max_Erase_Count_of_Spec " + "-v 169,raw48,Remaining_Lifetime_Perc " + //"-v 175,raw48,Program_Fail_Count_Chip " + //"-v 176,raw48,Erase_Fail_Count_Chip " + //"-v 177,raw48,Wear_Leveling_Count " + "-v 178,raw48,Runtime_Invalid_Blk_Cnt " + //"-v 181,raw48,Program_Fail_Cnt_Total " + //"-v 182,raw48,Erase_Fail_Count_Total " + //"-v 187,raw48,Reported_Uncorrect " // ] only in spec + //"-v 192,raw48,Power-Off_Retract_Count " + //"-v 194,tempminmax,Temperature_Celsius " + //"-v 195,raw48,Hardware_ECC_Recovered " + //"-v 196,raw16(raw16),Reallocated_Event_Count " + //"-v 197,raw48,Current_Pending_Sector " + //"-v 198,raw48,Offline_Uncorrectable " + //"-v 199,raw48,UDMA_CRC_Error_Count " + "-v 225,raw48,Host_Writes_32MiB " // ] + //"-v 232,raw48,Available_Reservd_Space " + "-v 233,raw48,Flash_Writes_32MiB " // ] + "-v 234,raw48,Flash_Reads_32MiB " // ] + "-v 241,raw48,Host_Writes_32MiB " + "-v 242,raw48,Host_Reads_32MiB " + "-v 245,raw48,Flash_Writes_32MiB" + }, + { "Innodisk 3ME3 SSDs", // tested with 2.5" SATA SSD 3ME3/S15A19, CFast 3ME3/S15A19 + // InnoDisk Corp. - mSATA 3ME3/S15A19, mSATA mini 3ME3/S15A19, M.2 (S42) 3ME3, + // SATA Slim 3ME3/S15A19, SATADOM-MH 3ME3/S15A19, SATADOM-ML 3ME3/S15A19, + // SATADOM-MV 3ME3/S15A19, SATADOM-SL 3ME3/S15A19, SATADOM-SV 3ME3/S15A19 + "(2.5\" SATA SSD|CFast|InnoDisk Corp\\. - mSATA|mSATA mini|" + "M\\.2 \\(S42\\)|SATA Slim|SATADOM-(MH|ML|MV|SL|SV)) 3ME3", + "", "", + //"-v 1,raw48,Raw_Read_Error_Rate " + //"-v 2,raw48,Throughput_Performance " + //"-v 3,raw16(avg16),Spin_Up_Time " + "-v 5,raw48,Later_Bad_Block " + "-v 7,raw48,Seek_Error_Rate " // ? + "-v 8,raw48,Seek_Time_Performance " // ? + //"-v 9,raw24(raw8),Power_On_Hours " + "-v 10,raw48,Spin_Retry_Count " // ? + //"-v 12,raw48,Power_Cycle_Count " + "-v 163,raw48,Total_Bad_Block_Count " + "-v 165,raw48,Max_Erase_Count " + "-v 167,raw48,Average_Erase_Count " + "-v 168,raw48,SATA_PHY_Error_Count " + "-v 169,raw48,Remaining_Lifetime_Perc " + "-v 170,raw48,Spare_Block_Count " + "-v 171,raw48,Program_Fail_Count " + "-v 172,raw48,Erase_Fail_Count " + "-v 175,raw48,Bad_Cluster_Table_Count " + "-v 176,raw48,RANGE_RECORD_Count " + //"-v 187,raw48,Reported_Uncorrect " + //"-v 192,raw48,Power-Off_Retract_Count " + //"-v 194,tempminmax,Temperature_Celsius " + //"-v 197,raw48,Current_Pending_Sector " + "-v 225,raw48,Data_Log_Write_Count " + "-v 229,hex48,Flash_ID " + "-v 232,raw48,Spares_Remaining_Perc " + "-v 235,raw16,Later_Bad_Blk_Inf_R/W/E " // Read/Write/Erase + "-v 240,raw48,Write_Head " + "-v 241,raw48,Host_Writes_32MiB " + "-v 242,raw48,Host_Reads_32MiB" + }, { "InnoDisk iCF 9000 CompactFlash Cards", // tested with InnoDisk Corp. - iCF9000 1GB/140808, // ..., InnoDisk Corp. - iCF9000 64GB/140808 "InnoDisk Corp\\. - iCF9000 (1|2|4|8|16|32|64)GB", @@ -684,9 +829,10 @@ const drive_settings builtin_knowndrives[] = { "-v 242,raw48,Host_Reads_32MiB" }, { "Intel 320 Series SSDs", // tested with INTEL SSDSA2CT040G3/4PC10362, - // INTEL SSDSA2CW160G3/4PC10362, INTEL SSDSA2BT040G3/4PC10362, INTEL SSDSA2BW120G3A/4PC10362, - // INTEL SSDSA2BW300G3D/4PC10362, INTEL SSDSA2BW160G3L/4PC1LE04 - "INTEL SSDSA[12][BC][WT](040|080|120|160|300|600)G3[ADL]?", + // INTEL SSDSA2CW160G3/4PC10362, SSDSA2BT040G3/4PC10362, SSDSA2BW120G3A/4PC10362, + // INTEL SSDSA2BW300G3D/4PC10362, SSDSA2BW160G3L/4PC1LE04, SSDSA1NW160G3/4PC10362 + "INTEL SSDSA[12][BCN][WT](040|080|120|160|300|600)G3[ADL]?", + // 2B = 2.5" 7mm, 2C = 2.5" 9.5mm, 1N = 1.8" microSATA "", "", "-F nologdir " //"-v 3,raw16(avg16),Spin_Up_Time " @@ -800,9 +946,11 @@ const drive_settings builtin_knowndrives[] = { "-v 242,raw48,Host_Reads_32MiB " "-v 249,raw48,NAND_Writes_1GiB" }, - { "Intel 530 Series SSDs", // tested with INTEL SSDSC2BW180A4/DC12, SSDSC2BW240A4/DC12, - // INTEL SSDMCEAW120A4/DC33, INTEL SSDMCEAW240A4/DC33 - "INTEL SSD(MCEA|SC2B)W(080|120|180|240|360|480)A4", // MCEA = mSATA + { "Intel 53x and Pro 2500 Series SSDs", // SandForce SF-2281, tested with + // INTEL SSDSC2BW180A4/DC12, SSDSC2BW240A4/DC12, SSDMCEAW120A4/DC33 + // INTEL SSDMCEAW240A4/DC33, SSDSC2BF480A5/TG26, SSDSC2BW240H6/RG21 + "INTEL SSD(MCEA|SC2B|SCKJ)[WF](056|080|120|180|240|360|480)(A4|A5|H6)", + // SC2B = 2.5", MCEA = mSATA, SCKJ = M.2; A4 = 530, A5 = Pro 2500, H6 = 535 "", "", //"-v 5,raw16(raw16),Reallocated_Sector_Ct " "-v 9,msec24hour32,Power_On_Hours_and_Msec " @@ -844,9 +992,11 @@ const drive_settings builtin_knowndrives[] = { "-v 242,raw48,Host_Reads_32MiB " "-v 249,raw48,NAND_Writes_1GiB" }, - { "Intel 730 and DC S3500/S3700 Series SSDs", // tested with INTEL SSDSC2BP480G4, SSDSC2BB120G4/D2010355, - // INTEL SSDSC2BB800G4T, SSDSC2BA200G3/5DV10250 - "INTEL SSDSC(1N|2B)[ABP](080|100|120|160|200|240|300|400|480|600|800)G[34]T?", // A=S3700, B=S3500, P=730 + { "Intel 730 and DC S35x0/3610/3700 Series SSDs", // tested with INTEL SSDSC2BP480G4, SSDSC2BB120G4/D2010355, + // INTEL SSDSC2BB800G4T, SSDSC2BA200G3/5DV10250, SSDSC2BB080G6/G2010130, SSDSC2BX200G4/G2010110, + // INTEL SSDSC2BB016T6/G2010140, SSDSC2BX016T4/G2010140 + "INTEL SSDSC(1N|2B)[ABPX]((080|100|120|160|200|240|300|400|480|600|800)G[346]T?|(012|016)T[46])", + // A = S3700, B*4 = S3500, B*6 = S3510, P = 730, X = S3610 "", "", //"-v 3,raw16(avg16),Spin_Up_Time " //"-v 4,raw48,Start_Stop_Count " @@ -875,6 +1025,7 @@ const drive_settings builtin_knowndrives[] = { "-v 234,raw24/raw32:04321,Thermal_Throttle " "-v 241,raw48,Host_Writes_32MiB " "-v 242,raw48,Host_Reads_32MiB " + "-v 243,raw48,NAND_Writes_32MiB " // S3510/3610 "-F xerrorlba" // tested with SSDSC2BB600G4/D2010355 }, { "Kingston branded X25-V SSDs", // fixed firmware @@ -1006,15 +1157,17 @@ const drive_settings builtin_knowndrives[] = { "SAMSUNG SSD 830 Series|" // tested with SAMSUNG SSD 830 Series 64GB/CXM03B1Q "Samsung SSD 840 (PRO )?Series|" // tested with Samsung SSD 840 PRO Series 128GB/DXM04B0Q, // Samsung SSD 840 Series/DXT06B0Q - "Samsung SSD 8[45]0 EVO ((120|250|500)G|1T)B( mSATA)?|" // tested with Samsung SSD 840 EVO (120|250|500)GB/EXT0AB0Q, + "Samsung SSD 8[45]0 EVO (mSATA )?((120|250|500)G|1T)B( mSATA)?|" // tested with Samsung SSD 840 EVO (120|250|500)GB/EXT0AB0Q, // Samsung SSD 840 EVO (120|250)GB/EXT0BB6Q, 1TB/EXT0BB0Q, 120GB mSATA/EXT41B6Q, // Samsung SSD 850 EVO 250GB/EMT01B6Q + // Samsung SSD 850 EVO mSATA 120GB/EMT41B6Q "Samsung SSD 850 PRO ((128|256|512)G|1T)B|" // tested with Samsung SSD 850 PRO 128GB/EXM01B6Q, // Samsung SSD 850 PRO 1TB/EXM01B6Q "SAMSUNG MZ7WD((120|240)HAFV|480HAGM|960HAGP)-00003|" // SM843T Series, tested with // SAMSUNG MZ7WD120HAFV-00003/DXM85W3Q - "SAMSUNG MZ7GE(240HMGR|(480|960)HMHP)-00003", // SM853T Series, tested with + "SAMSUNG MZ7GE(240HMGR|(480|960)HMHP)-00003|" // SM853T Series, tested with // SAMSUNG MZ7GE240HMGR-00003/EXT0303Q + "SAMSUNG MZ[7N]LN(128|256|512)HC(HP|GR|JH)-.*", // PM871 Series, tested with SAMSUNG MZ7LN128HCHP "", "", //"-v 5,raw16(raw16),Reallocated_Sector_Ct " //"-v 9,raw24(raw8),Power_On_Hours " @@ -1106,8 +1259,12 @@ const drive_settings builtin_knowndrives[] = { "-v 244,raw48,Thermal_Throttle " }, { "SiliconMotion based SSDs", // SM2246EN (Transcend TS6500) - "TS((16|32|64|128|256|512)G|1T)(SSD|MSA)370", // Transcend SSD370 SATA/mSATA, TS6500, tested with - // TS32GMSA370/20140402, TS16GMSA370/20140516, TS64GSSD370/20140516, TS256GSSD370/N0815B + "CT(120|250|500|1000)BX100SSD1|" // Crucial BX100, tested with CT250BX100SSD1/MU02, + // CT500BX100SSD1/MU02, CT1000BX100SSD1/MU02 + "TS((16|32|64|128|256|512)G|1T)(SSD|MSA)(370S?|420I?)|" // Transcend SSD370/420 SATA/mSATA, TS6500, + // tested with TS32GMSA370/20140402, TS16GMSA370/20140516, TS64GSSD370/20140516, + // TS256GSSD370/N0815B, TS256GSSD370S/N1114H, TS512GSSD370S/N1114H, TS32GSSD420I/N1114H + "ADATA SP550", // ADATA SP550/O0803B5a "", "", //"-v 1,raw48,Raw_Read_Error_Rate " //"-v 2,raw48,Throughput_Performance " @@ -1140,7 +1297,7 @@ const drive_settings builtin_knowndrives[] = { //"-v 232,raw48,Available_Reservd_Space " "-v 241,raw48,Host_Writes_32MiB " "-v 242,raw48,Host_Reads_32MiB " - "-v 245,raw48,Unkn_SiliconMotion_Attr" // FW N0815B + "-v 245,raw48,Flash_Writes_32MiB" // FW N0815B, N1114H }, { "Smart Storage Systems Xcel-10 SSDs", // based on http://www.smartm.com/files/salesLiterature/storage/xcel10.pdf "SMART A25FD-(32|64|128)GI32N", // tested with SMART A25FD-128GI32N/B9F23D4K @@ -2780,7 +2937,8 @@ const drive_settings builtin_knowndrives[] = { }, { "Seagate Enterprise Capacity 3.5 HDD", // tested with ST6000NM0024-1HT17Z/SN02 "ST[2456]000NM0[01][248]4-.*", // *[069]4 = 4Kn - "", "", "" + "", "", + "-v 188,raw16" }, { "Seagate NAS HDD", // tested with ST2000VN000-1H3164/SC42, ST3000VN000-1H4167/SC43 "ST[234]000VN000-.*", @@ -3001,13 +3159,21 @@ const drive_settings builtin_knowndrives[] = { "", "", "" }, { "Western Digital Caviar Black", - "WDC WD((500|640|750)1AAL|1001FA[EL]|2001FAS)S-.*", + "WDC WD((500|640|750)1AAL|1001FA[EL]|2001FAS)S-.*|" + "WDC WD(2002|7502|1502|5003|1002|5002)(FAE|AAE|AZE|AAL)X-.*", // could be + // WD2002FAEX, WD7502AAEX, WD1502FAEX, WD5003AZEX, WD1002FAEX, WD5002AALX "", "", "" }, { "Western Digital Black", // tested with // WDC WD5003AZEX-00RKKA0/80.00A80, WDC WD1003FZEX-00MK2A0/01.01A01, // WDC WD3001FAEX-00MJRA0/01.01L01, WDC WD4001FAEX-00MJRA0/01.01L01 - "WDC WD(5002AAL|5003AZE|(64|75)02AAE|((10|15|20)0[23]|[34]001)F[AZ]E)X-.*", + // WDC WD4003FZEX-00Z4SA0/01.01A01 + "WDC WD(6001|2003|5001|1003|4003|5003|3003|3001)(FZW|FZE|AZE)X-.*|" // could be + // new series WD6001FZWX WD2003FZEX WD5001FZWX WD1003FZEX + // WD4003FZEX WD5003AZEX WD3003FZEX + "WDC WD(4001|3001|2002|1002|5003|7500|5000|3200|2500|1600)(FAE|AZE|B[PE]K)[XT]-.*", + // old series: WD4001FAEX WD3001FAEX WD2002FAEX WD1002FAEX WD5003AZEX + // WD7500BPKT WD5000BPKT WD3200BEKT WD2500BEKT WD1600BEKT "", "", "" }, { "Western Digital AV ATA", // tested with WDC WD3200AVJB-63J5A0/01.03E01 @@ -3313,8 +3479,7 @@ const drive_settings builtin_knowndrives[] = { "", "-d sat" }, - // Fujitsu chip on DeLock 42475 - { "USB: Fujitsu SATA-to-USB3.0 bridge chip", // USB 3.0 + { "USB: ; Fujitsu", // DeLock 42475, USB 3.0 "0x04c5:0x201d", "", // 0x0001 "", @@ -3523,6 +3688,12 @@ const drive_settings builtin_knowndrives[] = { "", "-d sat" }, + { "USB: LaCie; ", + "0x059f:0x106f", + "", // 0x0001 + "", + "-d sat" + }, // In-System Design { "USB: ; In-System/Cypress ISD-300A1", "0x05ab:0x0060", @@ -3549,6 +3720,12 @@ const drive_settings builtin_knowndrives[] = { "", "-d sat" }, + { "USB: ; Genesys Logic", + "0x05e3:0x0735", + "", // 0x1003 + "", + "-d sat" + }, // Micron { "USB: Micron USB SSD; ", "0x0634:0x0655", @@ -3590,6 +3767,12 @@ const drive_settings builtin_knowndrives[] = { "-d sat" }, // Freecom + { "USB: ; Innostor IS631", // No Name USB3->SATA Enclosure + "0x07ab:0x0621", + "", + "", + "-d sat" + }, { "USB: Freecom Mobile Drive XXS; JMicron", "0x07ab:0xfc88", "", // 0x0101 @@ -3698,8 +3881,8 @@ const drive_settings builtin_knowndrives[] = { "-d sat" }, { "USB: Seagate Expansion Portable; ", - "0x0bc2:0x23(00|12|20|21)", - "", // 0x0219 (0x2312) + "0x0bc2:0x23(00|12|20|21|22)", + "", // 12=0x0219, 22=0x0000 "", "-d sat" }, @@ -3799,6 +3982,13 @@ const drive_settings builtin_knowndrives[] = { "", "-d sat" }, + // Addonics + { "USB: Addonics HDMU3; ", // (ticket #609) + "0x0bf6:0x1001", + "", // 0x0100 + "", + "" + }, // Dura Micro { "USB: Dura Micro; Cypress", "0x0c0b:0xb001", @@ -3855,6 +4045,13 @@ const drive_settings builtin_knowndrives[] = { "", "-d sat" }, + // Jess-Link International + { "USB: ; Cypress", // Medion HDDrive2Go + "0x0dbf:0x9001", + "", // 0x0240 + "", + "-d usbcypress" + }, // Oyen Digital { "USB: Oyen Digital MiniPro USB 3.0; ", "0x0dc4:0x020a", @@ -3884,7 +4081,7 @@ const drive_settings builtin_knowndrives[] = { "-d usbcypress" }, { "USB: WD My Passport; ", - "0x1058:0x0(70[245a]|730|74[0128a]|7a8|8[123]0)", + "0x1058:0x0(70[245a]|71a|730|74[0128a]|7a8|8(10|16|20|30))", "", "", "-d sat" @@ -3971,8 +4168,8 @@ const drive_settings builtin_knowndrives[] = { "-d sat" }, { "USB: ; Initio", - "0x13fd:0x1640", - "", // 0x0864 + "0x13fd:0x16[45]0", + "", // 0x1640: 0x0864, 0x1650: 0x0436 "", "-d sat,12" // some SMART commands fail, see ticket #295 }, @@ -3989,9 +4186,9 @@ const drive_settings builtin_knowndrives[] = { "-d sat" }, { "USB: ; Initio", - "0x13fd:0x39[14]0", // 0x3910: Seagate Expansion Portable SRD00F1 (0x0100) + "0x13fd:0x39[124]0", // 0x3910: Seagate Expansion Portable SRD00F1 (0x0100) + "", // 0x3920: ezDISK EZ370 (0x0205) "", // 0x3940: MS-TECH LU-275S (0x0306) - "", "-d sat" }, // Super Top @@ -4004,23 +4201,29 @@ const drive_settings builtin_knowndrives[] = { // JMicron { "USB: ; JMicron JMS539", // USB2/3->SATA (old firmware) "0x152d:0x0539", - "0x0100", // 1.00 - "", - "-d usbjmicron" + "0x0100", // 1.00, various devices support -d usbjmicron + "", // 1.00, SSI SI-1359RUS3 supports -d sat, + "" // -d usbjmicron may disconnect drive (ticket #552) }, { "USB: ; JMicron JMS539", // USB2/3->SATA (new firmware) "0x152d:0x0539", - "0x020[56]|" // 2.05, ticket #338 + "0x020[56]|" // 2.05, ZTC USB 3.0 enclosure (ticket #338) "0x28(03|12)", // 28.03, Mediasonic ProBox HF2-SU3S2 Rev 2 (port multiplier, ticket #504) "", // 28.12, Mediasonic ProBox H82-SU3S2 (port multiplier) "-d sat" }, { "USB: ; JMicron ", // USB->SATA->4xSATA (port multiplier) - "0x152d:0x0551", + "0x152d:0x0551", // JMS539? (old firmware may use 0x152d:0x0539, ticket #552) "", // 0x0100 "", "-d usbjmicron,x" }, + { "USB: ; JMicron", // USB2/3->2xSATA + "0x152d:0x0565", + "", // 0x9114, Akasa DuoDock X (ticket #607) + "", + "-d sat" + }, { "USB: ; JMicron JMS567", // USB2/3->SATA "0x152d:0x0567", "", // 0x0114 @@ -4247,6 +4450,12 @@ const drive_settings builtin_knowndrives[] = { "", "-d sat" // ATA output registers missing }, + { "USB: ; VIA VL711", // USB2/3->SATA + "0x2109:0x0711", + "", // 0x0114, Mediasonic ProBox K32-SU3 (ticket #594) + "", + "" // unsupported + }, // 0x2537 (?) { "USB: ; ", // USB 3.0 "0x2537:0x106[68]", // 0x1066: Orico 2599US3, 0x1068: Fantec ER-35U3 @@ -4275,7 +4484,13 @@ const drive_settings builtin_knowndrives[] = { "-d sat" // ATA output registers missing }, { "USB: Hitachi Touro Mobile; ", // 1TB - "0x4971:0x1020", + "0x4971:0x102[04]", + "", // 0x0100 + "", + "-d sat" + }, + { "USB: SimpleTech;", // USB 3.0 HDD BOX Agestar, Rock External HDD 3,5" UASP + "0x4971:0x8017", "", "", "-d sat" @@ -4300,6 +4515,13 @@ const drive_settings builtin_knowndrives[] = { "", "-d sat" }, + // 0xabcd (?) + { "USB: ; ", + "0xabcd:0x6103", // LogiLink AU0028A V1.0 USB 3.0 to IDE & SATA Adapter + "", + "", + "-d sat" + }, /* }; // builtin_knowndrives[] */ diff --git a/examplescripts/README b/examplescripts/README index 43a351b..baa211a 100644 --- a/examplescripts/README +++ b/examplescripts/README @@ -1,6 +1,6 @@ -# Home page: http://smartmontools.sourceforge.net +# Home page: http://www.smartmontools.org # -# $Id: README 3958 2014-07-18 19:13:32Z chrfranke $ +# $Id: README 4120 2015-08-27 16:12:21Z samm2 $ # # Copyright (C) 2003-8 Bruce Allen # Copyright (C) 2009-14 Christian Franke diff --git a/int64.h b/int64.h index bc328ab..c713538 100644 --- a/int64.h +++ b/int64.h @@ -1,7 +1,7 @@ /* * int64.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2002-11 Bruce Allen * Copyright (C) 2004-11 Christian Franke @@ -20,7 +20,7 @@ #ifndef INT64_H_ #define INT64_H_ -#define INT64_H_CVSID "$Id: int64.h 3727 2012-12-13 17:23:06Z samm2 $" +#define INT64_H_CVSID "$Id: int64.h 4120 2015-08-27 16:12:21Z samm2 $" // 64 bit integer typedefs and format strings diff --git a/knowndrives.cpp b/knowndrives.cpp index 25d3bab..050733e 100644 --- a/knowndrives.cpp +++ b/knowndrives.cpp @@ -1,11 +1,10 @@ /* * knowndrives.cpp * - * Home page of code is: http://smartmontools.sourceforge.net - * Address of support mailing list: smartmontools-support@lists.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2003-11 Philip Williams, Bruce Allen - * Copyright (C) 2008-12 Christian Franke + * Copyright (C) 2008-16 Christian Franke * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -33,7 +32,7 @@ #include -const char * knowndrives_cpp_cvsid = "$Id: knowndrives.cpp 3719 2012-12-03 21:19:33Z chrfranke $" +const char * knowndrives_cpp_cvsid = "$Id: knowndrives.cpp 4208 2016-01-22 19:45:35Z chrfranke $" KNOWNDRIVES_H_CVSID; #define MODEL_STRING_LENGTH 40 @@ -51,6 +50,8 @@ const drive_settings builtin_knowndrives[] = { #include "drivedb.h" }; +const unsigned builtin_knowndrives_size = + sizeof(builtin_knowndrives) / sizeof(builtin_knowndrives[0]); /// Drive database class. Stores custom entries read from file. /// Provides transparent access to concatenation of custom and @@ -140,16 +141,26 @@ const char * drive_database::copy_string(const char * src) static drive_database knowndrives; -// Return true if modelfamily string describes entry for USB ID -static bool is_usb_modelfamily(const char * modelfamily) +enum dbentry_type { + DBENTRY_ATA_DEFAULT, + DBENTRY_ATA, + DBENTRY_USB +}; + +// Return type of entry +static dbentry_type get_modelfamily_type(const char * modelfamily) { - return !strncmp(modelfamily, "USB:", 4); + if (modelfamily[0] == 'D' && !strcmp(modelfamily, "DEFAULT")) + return DBENTRY_ATA_DEFAULT; + else if(modelfamily[0] == 'U' && str_starts_with(modelfamily, "USB:")) + return DBENTRY_USB; + else + return DBENTRY_ATA; } -// Return true if entry for USB ID -static inline bool is_usb_entry(const drive_settings * dbentry) +static inline dbentry_type get_dbentry_type(const drive_settings * dbentry) { - return is_usb_modelfamily(dbentry->modelfamily); + return get_modelfamily_type(dbentry->modelfamily); } // Compile regular expression, print message on failure. @@ -185,8 +196,8 @@ static const drive_settings * lookup_drive(const char * model, const char * firm firmware = ""; for (unsigned i = 0; i < knowndrives.size(); i++) { - // Skip USB entries - if (is_usb_entry(&knowndrives[i])) + // Skip DEFAULT and USB entries + if (get_dbentry_type(&knowndrives[i]) != DBENTRY_ATA) continue; // Check whether model matches the regular expression in knowndrives[i]. @@ -219,8 +230,8 @@ static bool parse_db_presets(const char * presets, ata_vendor_attr_defs * defs, if (!(sscanf(presets+i, "-%c %80[^ ]%n", &opt, arg, &len) >= 2 && len > 0)) return false; if (opt == 'v' && defs) { - // Parse "-v N,format[,name]" - if (!parse_attribute_def(arg, *defs, PRIOR_DATABASE)) + // Parse "-v N,format[,name[,HDD|SSD]]" + if (!parse_attribute_def(arg, *defs, (firmwarebugs ? PRIOR_DATABASE : PRIOR_DEFAULT))) return false; } else if (opt == 'F' && firmwarebugs) { @@ -243,6 +254,13 @@ static bool parse_db_presets(const char * presets, ata_vendor_attr_defs * defs, return true; } +// Parse '-v' options in default preset string, return false on error. +static inline bool parse_default_presets(const char * presets, + ata_vendor_attr_defs & defs) +{ + return parse_db_presets(presets, &defs, 0, 0); +} + // Parse '-v' and '-F' options in preset string, return false on error. static inline bool parse_presets(const char * presets, ata_vendor_attr_defs & defs, @@ -287,7 +305,7 @@ int lookup_usb_device(int vendor_id, int product_id, int bcd_device, const drive_settings & dbentry = knowndrives[i]; // Skip drive entries - if (!is_usb_entry(&dbentry)) + if (get_dbentry_type(&dbentry) != DBENTRY_USB) continue; // Check whether USB vendor:product ID matches @@ -341,7 +359,8 @@ static int showonepreset(const drive_settings * dbentry) return 1; } - bool usb = is_usb_entry(dbentry); + dbentry_type type = get_dbentry_type(dbentry); + bool usb = (type == DBENTRY_USB); // print and check model and firmware regular expressions int errcnt = 0; @@ -364,12 +383,21 @@ static int showonepreset(const drive_settings * dbentry) bool first_preset = true; if (*dbentry->presets) { ata_vendor_attr_defs defs; - if (!parse_presets(dbentry->presets, defs, firmwarebugs)) { - pout("Syntax error in preset option string \"%s\"\n", dbentry->presets); - errcnt++; + if (type == DBENTRY_ATA_DEFAULT) { + if (!parse_default_presets(dbentry->presets, defs)) { + pout("Syntax error in DEFAULT option string \"%s\"\n", dbentry->presets); + errcnt++; + } } + else { + if (!parse_presets(dbentry->presets, defs, firmwarebugs)) { + pout("Syntax error in preset option string \"%s\"\n", dbentry->presets); + errcnt++; + } + } + for (int i = 0; i < MAX_ATTRIBUTE_NUM; i++) { - if (defs[i].priority != PRIOR_DEFAULT) { + if (defs[i].priority != PRIOR_DEFAULT || !defs[i].name.empty()) { std::string name = ata_get_smart_attr_name(i, defs); // Use leading zeros instead of spaces so that everything lines up. pout("%-*s %03d %s\n", TABLEPRINTWIDTH, first_preset ? "ATTRIBUTE OPTIONS:" : "", @@ -563,7 +591,7 @@ class stdin_iterator { public: explicit stdin_iterator(FILE * f) - : m_f(f) { get(); get(); } + : m_f(f), m_next(0) { get(); get(); } stdin_iterator & operator++() { get(); return *this; } @@ -767,19 +795,29 @@ static bool parse_drive_database(parse_ptr src, drive_database & db, const char break; case 4: if (!token.value.empty()) { - if (!is_usb_modelfamily(values[0].c_str())) { - ata_vendor_attr_defs defs; firmwarebug_defs fix; - if (!parse_presets(token.value.c_str(), defs, fix)) { - pout("%s(%d): Syntax error in preset option string\n", path, token.line); - ok = false; - } - } - else { - std::string type; - if (!parse_usb_type(token.value.c_str(), type)) { - pout("%s(%d): Syntax error in USB type string\n", path, token.line); - ok = false; - } + // Syntax check + switch (get_modelfamily_type(values[0].c_str())) { + case DBENTRY_ATA_DEFAULT: { + ata_vendor_attr_defs defs; + if (!parse_default_presets(token.value.c_str(), defs)) { + pout("%s(%d): Syntax error in DEFAULT option string\n", path, token.line); + ok = false; + } + } break; + default: { // DBENTRY_ATA + ata_vendor_attr_defs defs; firmwarebug_defs fix; + if (!parse_presets(token.value.c_str(), defs, fix)) { + pout("%s(%d): Syntax error in preset option string\n", path, token.line); + ok = false; + } + } break; + case DBENTRY_USB: { + std::string type; + if (!parse_usb_type(token.value.c_str(), type)) { + pout("%s(%d): Syntax error in USB type string\n", path, token.line); + ok = false; + } + } break; } } break; @@ -857,7 +895,7 @@ const char * get_drivedb_path_default() #endif // Read drive databases from standard places. -bool read_default_drive_databases() +static bool read_default_drive_databases() { // Read file for local additions: /{,usr/local/}etc/smart_drivedb.h const char * db1 = get_drivedb_path_add(); @@ -877,9 +915,60 @@ bool read_default_drive_databases() #endif { // Append builtin table. - knowndrives.append(builtin_knowndrives, - sizeof(builtin_knowndrives)/sizeof(builtin_knowndrives[0])); + knowndrives.append(builtin_knowndrives, builtin_knowndrives_size); + } + + return true; +} + +static ata_vendor_attr_defs default_attr_defs; + +// Initialize default_attr_defs. +static bool init_default_attr_defs() +{ + // Lookup default entry + const drive_settings * entry = 0; + for (unsigned i = 0; i < knowndrives.size(); i++) { + if (get_dbentry_type(&knowndrives[i]) != DBENTRY_ATA_DEFAULT) + continue; + entry = &knowndrives[i]; + break; + } + + if (!entry) { + // Fall back to builtin database + for (unsigned i = 0; i < builtin_knowndrives_size; i++) { + if (get_dbentry_type(&builtin_knowndrives[i]) != DBENTRY_ATA_DEFAULT) + continue; + entry = &builtin_knowndrives[i]; + break; + } + + if (!entry) + throw std::logic_error("DEFAULT entry missing in builtin drive database"); + + pout("Warning: DEFAULT entry missing in drive database file(s)\n"); + } + + if (!parse_default_presets(entry->presets, default_attr_defs)) { + pout("Syntax error in DEFAULT drive database entry\n"); + return false; } return true; } + +// Init default db entry and optionally read drive databases from standard places. +bool init_drive_database(bool use_default_db) +{ + if (use_default_db && !read_default_drive_databases()) + return false; + + return init_default_attr_defs(); +} + +// Get vendor attribute options from default db entry. +const ata_vendor_attr_defs & get_default_attr_defs() +{ + return default_attr_defs; +} diff --git a/knowndrives.h b/knowndrives.h index 7d2a8cc..3c754e7 100644 --- a/knowndrives.h +++ b/knowndrives.h @@ -1,11 +1,10 @@ /* * knowndrives.h * - * Home page of code is: http://smartmontools.sourceforge.net - * Address of support mailing list: smartmontools-support@lists.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2003-11 Philip Williams, Bruce Allen - * Copyright (C) 2008-12 Christian Franke + * Copyright (C) 2008-15 Christian Franke * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -20,7 +19,7 @@ #ifndef KNOWNDRIVES_H_ #define KNOWNDRIVES_H_ -#define KNOWNDRIVES_H_CVSID "$Id: knowndrives.h 3597 2012-09-04 21:10:37Z chrfranke $\n" +#define KNOWNDRIVES_H_CVSID "$Id: knowndrives.h 4162 2015-10-31 16:36:16Z chrfranke $\n" // Structure to store drive database entries, see drivedb.h for a description. struct drive_settings { @@ -73,7 +72,10 @@ const char * get_drivedb_path_default(); // Read drive database from file. bool read_drive_database(const char * path); -// Read drive databases from standard places. -bool read_default_drive_databases(); +// Init default db entry and optionally read drive databases from standard places. +bool init_drive_database(bool use_default_db); + +// Get vendor attribute options from default db entry. +const ata_vendor_attr_defs & get_default_attr_defs(); #endif diff --git a/os_darwin.cpp b/os_darwin.cpp index 8d05d1c..53a0f46 100644 --- a/os_darwin.cpp +++ b/os_darwin.cpp @@ -1,7 +1,7 @@ /* * os_darwin.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2004-8 Geoffrey Keating * Copyright (C) 2014 Alex Samorukov @@ -22,6 +22,7 @@ #include #include #include +#include #include #include #include @@ -45,7 +46,7 @@ #include "dev_interface.h" // Needed by '-V' option (CVS versioning) of smartd/smartctl -const char *os_darwin_cpp_cvsid="$Id: os_darwin.cpp 3982 2014-08-16 21:07:19Z samm2 $" \ +const char *os_darwin_cpp_cvsid="$Id: os_darwin.cpp 4214 2016-01-24 22:53:37Z samm2 $" \ ATACMDS_H_CVSID CONFIG_H_CVSID INT64_H_CVSID OS_DARWIN_H_CVSID SCSICMDS_H_CVSID UTILITY_H_CVSID; // examples for smartctl @@ -77,7 +78,7 @@ static struct { IOATASMARTInterface **smartIf; } devices[20]; -const char * dev_darwin_cpp_cvsid = "$Id: os_darwin.cpp 3982 2014-08-16 21:07:19Z samm2 $" +const char * dev_darwin_cpp_cvsid = "$Id: os_darwin.cpp 4214 2016-01-24 22:53:37Z samm2 $" DEV_INTERFACE_H_CVSID; ///////////////////////////////////////////////////////////////////////////// @@ -181,8 +182,8 @@ bool darwin_smart_device::open() if (strcmp (type, "ATA") != 0) { - errno = EINVAL; - return -1; + set_err (EINVAL); + return false; } // Find a free device number. @@ -191,8 +192,8 @@ bool darwin_smart_device::open() break; if (devnum == sizeof (devices) / sizeof (devices[0])) { - errno = EMFILE; - return -1; + set_err (EMFILE); + return false; } devname = NULL; @@ -218,8 +219,8 @@ bool darwin_smart_device::open() if (! disk) { - errno = ENOENT; - return -1; + set_err(ENOENT); + return false; } // Find a SMART-capable driver which is a parent of this device. @@ -232,9 +233,9 @@ bool darwin_smart_device::open() err = IORegistryEntryGetParentEntry (disk, kIOServicePlane, &disk); if (err != kIOReturnSuccess || ! disk) { - errno = ENODEV; + set_err(ENODEV); IOObjectRelease (prevdisk); - return -1; + return false; } } @@ -257,8 +258,8 @@ bool darwin_smart_device::open() CFUUIDGetUUIDBytes ( kIOATASMARTInterfaceID), (void **)&devices[devnum].smartIf); } - - + + m_fd = devnum; if (m_fd < 0) { set_err((errno==ENOENT || errno==ENOTDIR) ? ENODEV : errno); @@ -311,9 +312,9 @@ static int make_device_names (char*** devlist, const char* name) { // Create an array of service names. IOIteratorReset (i); - *devlist = (char**)calloc (result, sizeof (char *)); - if (! *devlist) + if (! result) goto error; + *devlist = (char**)calloc (result, sizeof (char *)); index = 0; while ((device = IOIteratorNext (i)) != MACH_PORT_NULL) { if (is_smart_capable (device)) @@ -342,6 +343,9 @@ static int make_device_names (char*** devlist, const char* name) { free ((*devlist)[index]); free (*devlist); } + if(!result) // no devs found + return 0; + return -1; } @@ -454,7 +458,7 @@ bool darwin_ata_device::ata_pass_through(const ata_cmd_in & in, ata_cmd_out & ou if (select != SHORT_SELF_TEST && select != EXTEND_SELF_TEST) { errno = EINVAL; - err = -1; + return set_err(ENOSYS, "Unsupported SMART self-test mode"); } err = smartIf->SMARTExecuteOffLineImmediate (ifp, select == EXTEND_SELF_TEST); @@ -488,6 +492,8 @@ class darwin_smart_interface : public /*implements*/ smart_interface { public: + virtual std::string get_os_version_str(); + virtual std::string get_app_examples(const char * appname); virtual bool scan_smart_devices(smart_device_list & devlist, const char * type, @@ -505,6 +511,15 @@ protected: ////////////////////////////////////////////////////////////////////// +std::string darwin_smart_interface::get_os_version_str() +{ + // now we are just getting darwin runtime version, to get OSX version more things needs to be done, see + // http://stackoverflow.com/questions/11072804/how-do-i-determine-the-os-version-at-runtime-in-os-x-or-ios-without-using-gesta + struct utsname osname; + uname(&osname); + return strprintf("%s %s %s", osname.sysname, osname.release, osname.machine); +} + std::string darwin_smart_interface::get_app_examples(const char * appname) { if (!strcmp(appname, "smartctl")) diff --git a/os_darwin.h b/os_darwin.h index 5978187..8031b73 100644 --- a/os_darwin.h +++ b/os_darwin.h @@ -1,7 +1,7 @@ /* * os_generic.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2004-8 Geoff Keating * @@ -24,7 +24,7 @@ #ifndef OS_DARWIN_H_ #define OS_DARWIN_H_ -#define OS_DARWIN_H_CVSID "$Id: os_darwin.h 3728 2012-12-13 17:57:50Z chrfranke $\n" +#define OS_DARWIN_H_CVSID "$Id: os_darwin.h 4120 2015-08-27 16:12:21Z samm2 $\n" // Isn't in 10.3.9? diff --git a/os_darwin/SMART.in b/os_darwin/SMART.in index df2cb5c..19a155c 100644 --- a/os_darwin/SMART.in +++ b/os_darwin/SMART.in @@ -2,7 +2,7 @@ # Darwin init file for smartd # -# Home page of code is: http://smartmontools.sourceforge.net +# Home page of code is: http://www.smartmontools.org # # Copyright (C) 2004-8 Geoffrey Keating # @@ -15,7 +15,7 @@ # example COPYING); if not, write to the Free Software Foundation, Inc., # 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. -# $Id: SMART.in 3728 2012-12-13 17:57:50Z chrfranke $ +# $Id: SMART.in 4120 2015-08-27 16:12:21Z samm2 $ ## # SMART monitoring diff --git a/os_darwin/pkg/Distribution.in b/os_darwin/pkg/Distribution.in new file mode 100644 index 0000000..df3ec9c --- /dev/null +++ b/os_darwin/pkg/Distribution.in @@ -0,0 +1,21 @@ + + + + + + + + S.M.A.R.T. disk monitoring tools + + + + + + + + + @pkgname@ + + + + diff --git a/os_darwin/pkg/PackageInfo.in b/os_darwin/pkg/PackageInfo.in new file mode 100644 index 0000000..92ea7a2 --- /dev/null +++ b/os_darwin/pkg/PackageInfo.in @@ -0,0 +1,6 @@ + + + + diff --git a/os_darwin/pkg/installer/README.html b/os_darwin/pkg/installer/README.html new file mode 100644 index 0000000..2ddeee2 --- /dev/null +++ b/os_darwin/pkg/installer/README.html @@ -0,0 +1,24 @@ + + +

About this package

+The smartmontools package contains two utility programs (smartctl and smartd) to control +and monitor storage systems using the Self-Monitoring, Analysis and Reporting +Technology System (SMART) built into most modern ATA and SCSI harddisks. +In many cases, these utilities will provide advanced warning of disk degradation and failure. +

Installing

+To install package click on the smartmontools.pkg icon and follow installation process. Files will be installed to the /usr/local/ directory. +

Usage

+ If you are having trouble understanding the output of smartctl or smartd, please first read the manual pages installed on your system: +
+  man 8 smartctl
+  man 8 smartd
+  man 8 update-smart-drivedb
+  man 5 smartd.conf
+
+To use smartmontools with USB drives please download and install +Max OS X kernel driver for providing access to external drive SMART data. +More information could be found on the www.smartmontools.org website. +

Uninstalling

+If you want to uninstall already installed package run 'sudo smart-pkg-uninstall' in the terminal. + + diff --git a/os_darwin/pkg/root/usr/local/sbin/smart-pkg-uninstall b/os_darwin/pkg/root/usr/local/sbin/smart-pkg-uninstall new file mode 100755 index 0000000..72bb3fa --- /dev/null +++ b/os_darwin/pkg/root/usr/local/sbin/smart-pkg-uninstall @@ -0,0 +1,40 @@ +#!/bin/sh + +echo "Smartmontools package uninstaller:" + +# check if we are running with root uid +if [[ $EUID -ne 0 ]]; then + echo " Error: this script must be run as root" + exit 1 +fi + +# check if package is installed +pkgutil --info com.smartmontools.pkg > /dev/null 2>/dev/null +if [ $? -ne 0 ]; then + echo " Error: smartmontools package is not installed" + exit 1 +fi + +# smartmontools pkg could be installed only on system volume, so this should be safe +cd / + +echo " - removing files" +for str in `pkgutil --files com.smartmontools.pkg` +do + if [ -f "$str" ] + then + rm -f "$str" + fi +done +echo " - removing empty directories" +for str in `pkgutil --files com.smartmontools.pkg` +do + if [ -d "$str" ] + then + rmdir -p "$str" 2>/dev/null + fi +done + +echo " - removing package system entry" +pkgutil --forget com.smartmontools.pkg +echo "Done, smartmontolls package removed" diff --git a/os_freebsd.cpp b/os_freebsd.cpp index 9c5db2b..01d261c 100644 --- a/os_freebsd.cpp +++ b/os_freebsd.cpp @@ -1,9 +1,9 @@ /* * os_freebsd.c * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * - * Copyright (C) 2003-10 Eduard Martinescu + * Copyright (C) 2003-10 Eduard Martinescu * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -38,6 +38,8 @@ #include "config.h" #include "int64.h" +// set by /usr/include/sys/ata.h, suppress warning +#undef ATA_READ_LOG_EXT #include "atacmds.h" #include "scsicmds.h" #include "cciss.h" @@ -75,7 +77,7 @@ #define PATHINQ_SETTINGS_SIZE 128 #endif -const char *os_XXXX_c_cvsid="$Id: os_freebsd.cpp 3902 2014-05-23 19:14:15Z samm2 $" \ +const char *os_XXXX_c_cvsid="$Id: os_freebsd.cpp 4211 2016-01-24 07:56:06Z samm2 $" \ ATACMDS_H_CVSID CCISS_H_CVSID CONFIG_H_CVSID INT64_H_CVSID OS_FREEBSD_H_CVSID SCSICMDS_H_CVSID UTILITY_H_CVSID; #define NO_RETURN 0 @@ -86,19 +88,21 @@ ATACMDS_H_CVSID CCISS_H_CVSID CONFIG_H_CVSID INT64_H_CVSID OS_FREEBSD_H_CVSID SC // Utility function for printing warnings void printwarning(int msgNo, const char* extra) { - static int printed[] = {0,0,0,0}; - static const char* message[]={ - "The SMART RETURN STATUS return value (smartmontools -H option/Directive)\n can not be retrieved with this version of ATAng, please do not rely on this value\nYou should update to at least 5.2\n", - "Error SMART Status command failed\nPlease get assistance from \n" PACKAGE_HOMEPAGE "\nRegister values returned from SMART Status command are:\n", + if (msgNo >= 0 && msgNo <= MAX_MSG) { + static int printed[] = {0,0,0,0}; + if (!printed[msgNo]) { - "You must specify a DISK # for 3ware drives with -d 3ware, where begins with 1 for first disk drive\n", + static const char* message[]={ + "The SMART RETURN STATUS return value (smartmontools -H option/Directive)\n can not be retrieved with this version of ATAng, please do not rely on this value\nYou should update to at least 5.2\n", - "ATA support is not provided for this kernel version. Please ugrade to a recent 5-CURRENT kernel (post 09/01/2003 or so)\n" - }; + "Error SMART Status command failed\nPlease get assistance from \n" PACKAGE_HOMEPAGE "\nRegister values returned from SMART Status command are:\n", + + "You must specify a DISK # for 3ware drives with -d 3ware, where begins with 1 for first disk drive\n", + + "ATA support is not provided for this kernel version. Please ugrade to a recent 5-CURRENT kernel (post 09/01/2003 or so)\n" + }; - if (msgNo >= 0 && msgNo <= MAX_MSG) { - if (!printed[msgNo]) { printed[msgNo] = 1; pout("%s", message[msgNo]); if (extra) @@ -917,7 +921,8 @@ bool freebsd_scsi_device::close(){ freebsd_scsi_device::freebsd_scsi_device(smart_interface * intf, const char * dev_name, const char * req_type) : smart_device(intf, dev_name, "scsi", req_type), - freebsd_smart_device() + freebsd_smart_device(), + m_camdev(0) { } @@ -1122,10 +1127,8 @@ freebsd_areca_ata_device::freebsd_areca_ata_device(smart_interface * intf, const smart_device * freebsd_areca_ata_device::autodetect_open() { - int is_ata = 1; - // autodetect device type - is_ata = arcmsr_get_dev_type(); + int is_ata = arcmsr_get_dev_type(); if(is_ata < 0) { set_err(EIO); @@ -1476,11 +1479,12 @@ bool get_dev_names_cam(std::vector & names, bool show_all) } for (unsigned i = 0; i < ccb.cdm.num_matches; i++) { - struct bus_match_result *bus_result; struct device_match_result *dev_result; struct periph_match_result *periph_result; if (ccb.cdm.matches[i].type == DEV_MATCH_BUS) { + struct bus_match_result *bus_result; + bus_result = &ccb.cdm.matches[i].result.bus_result; if (strcmp(bus_result->dev_name,"xpt") == 0) /* skip XPT bus at all */ @@ -1592,9 +1596,11 @@ int get_dev_names_ata(char*** names) { n++; }; }; - }; + }; + if (n <= 0) + goto end; mp = (char **)reallocf(mp,n*(sizeof (char*))); // shrink to correct size - if (mp == NULL && n > 0 ) { // reallocf never fail for size=0, but may return NULL + if (mp == NULL) { serrno=errno; pout("Out of memory constructing scan device list (on line %d)\n", __LINE__); n = -1; @@ -1779,13 +1785,13 @@ static int usbdevlist(int busno,unsigned short & vendor_id, return false; #else // freebsd < 8.0 USB stack, ioctl interface - int i, f, a, rc; + int i, a, rc; char buf[50]; int ncont; for (ncont = 0, i = 0; i < 10; i++) { snprintf(buf, sizeof(buf), "%s%d", USBDEV, i); - f = open(buf, O_RDONLY); + int f = open(buf, O_RDONLY); if (f >= 0) { memset(done, 0, sizeof done); for (a = 1; a < USB_MAX_DEVICES; a++) { @@ -1813,12 +1819,11 @@ smart_device * freebsd_smart_interface::autodetect_smart_device(const char * nam struct cam_device *cam_dev; union ccb ccb; int bus=-1; - int i,c; - int len; + int i; const char * test_name = name; // if dev_name null, or string length zero - if (!name || !(len = strlen(name))) + if (!name || !*name) return 0; // Dereference symlinks @@ -1840,7 +1845,7 @@ smart_device * freebsd_smart_interface::autodetect_smart_device(const char * nam // check ATA/ATAPI devices for (i = 0; i < numata; i++) { if(!strcmp(atanames[i],test_name)) { - for (c = i; c < numata; c++) free(atanames[c]); + for (int c = i; c < numata; c++) free(atanames[c]); free(atanames); return new freebsd_ata_device(this, test_name, ""); } @@ -1917,13 +1922,15 @@ smart_device * freebsd_smart_interface::autodetect_smart_device(const char * nam smart_device * freebsd_smart_interface::get_custom_smart_device(const char * name, const char * type) { - // 3Ware ? - static const char * fbsd_dev_twe_ctrl = "/dev/twe"; - static const char * fbsd_dev_twa_ctrl = "/dev/twa"; - static const char * fbsd_dev_tws_ctrl = "/dev/tws"; - int disknum = -1, n1 = -1, n2 = -1, contr = -1; + int disknum = -1, n1 = -1, n2 = -1; if (sscanf(type, "3ware,%n%d%n", &n1, &disknum, &n2) == 1 || n1 == 6) { + // 3Ware ? + static const char * fbsd_dev_twe_ctrl = "/dev/twe"; + static const char * fbsd_dev_twa_ctrl = "/dev/twa"; + static const char * fbsd_dev_tws_ctrl = "/dev/tws"; + int contr = -1; + if (n2 != (int)strlen(type)) { set_err(EINVAL, "Option -d 3ware,N requires N to be a non-negative integer"); return 0; diff --git a/os_freebsd.h b/os_freebsd.h index a22442f..4832154 100644 --- a/os_freebsd.h +++ b/os_freebsd.h @@ -1,7 +1,7 @@ /* * os_freebsd.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2003-8 Eduard Martinescu * @@ -82,7 +82,7 @@ #ifndef OS_FREEBSD_H_ #define OS_FREEBSD_H_ -#define OS_FREEBSD_H_CVSID "$Id: os_freebsd.h 3727 2012-12-13 17:23:06Z samm2 $" +#define OS_FREEBSD_H_CVSID "$Id: os_freebsd.h 4120 2015-08-27 16:12:21Z samm2 $" #define MAX_NUM_DEV 26 diff --git a/os_generic.cpp b/os_generic.cpp index 0999833..de39f55 100644 --- a/os_generic.cpp +++ b/os_generic.cpp @@ -1,7 +1,7 @@ /* * os_generic.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) YEAR YOUR_NAME * Copyright (C) 2003-8 Bruce Allen @@ -83,7 +83,7 @@ // should have one *_H_CVSID macro appearing below for each file // appearing with #include "*.h" above. Please list these (below) in // alphabetic/dictionary order. -const char * os_XXXX_cpp_cvsid="$Id: os_generic.cpp 3579 2012-07-20 17:50:12Z chrfranke $" +const char * os_XXXX_cpp_cvsid="$Id: os_generic.cpp 4120 2015-08-27 16:12:21Z samm2 $" ATACMDS_H_CVSID CONFIG_H_CVSID INT64_H_CVSID OS_GENERIC_H_CVSID UTILITY_H_CVSID; // This is here to prevent compiler warnings for unused arguments of diff --git a/os_generic.h b/os_generic.h index 4c0ba66..211ce1e 100644 --- a/os_generic.h +++ b/os_generic.h @@ -1,7 +1,7 @@ /* * os_generic.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) YEAR YOUR_NAME * Copyright (C) 2003-8 Bruce Allen @@ -25,7 +25,7 @@ // In the three following lines, change 'GENERIC' to your OS name #ifndef OS_GENERIC_H_ #define OS_GENERIC_H_ -#define OS_GENERIC_H_CVSID "$Id: os_generic.h 3728 2012-12-13 17:57:50Z chrfranke $\n" +#define OS_GENERIC_H_CVSID "$Id: os_generic.h 4120 2015-08-27 16:12:21Z samm2 $\n" // Additional material should start here. Note: to keep the '-V' CVS // reporting option working as intended, you should only #include diff --git a/os_linux.cpp b/os_linux.cpp index c9b58a3..6374a5b 100644 --- a/os_linux.cpp +++ b/os_linux.cpp @@ -1,11 +1,11 @@ /* * os_linux.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * - * Copyright (C) 2003-11 Bruce Allen + * Copyright (C) 2003-11 Bruce Allen * Copyright (C) 2003-11 Doug Gilbert - * Copyright (C) 2008-15 Christian Franke + * Copyright (C) 2008-15 Christian Franke * * Original AACRaid code: * Copyright (C) 2014 Raghava Aditya @@ -99,7 +99,7 @@ #define ARGUSED(x) ((void)(x)) -const char * os_linux_cpp_cvsid = "$Id: os_linux.cpp 4047 2015-03-22 16:16:24Z chrfranke $" +const char * os_linux_cpp_cvsid = "$Id: os_linux.cpp 4157 2015-10-20 16:03:57Z chrfranke $" OS_LINUX_H_CVSID; extern unsigned char failuretest_permissive; @@ -356,7 +356,6 @@ int linux_ata_device::ata_command_interface(smart_command_set command, int selec unsigned char task[sizeof(ide_task_request_t)+512]; ide_task_request_t *reqtask=(ide_task_request_t *) task; task_struct_t *taskfile=(task_struct_t *) reqtask->io_ports; - int retval; memset(task, 0, sizeof(task)); @@ -377,7 +376,7 @@ int linux_ata_device::ata_command_interface(smart_command_set command, int selec // copy user data into the task request structure memcpy(task+sizeof(ide_task_request_t), data, 512); - if ((retval=ioctl(get_fd(), HDIO_DRIVE_TASKFILE, task))) { + if (ioctl(get_fd(), HDIO_DRIVE_TASKFILE, task)) { if (errno==-EINVAL) pout("Kernel lacks HDIO_DRIVE_TASKFILE support; compile kernel with CONFIG_IDE_TASKFILE_IO set\n"); return -1; @@ -388,8 +387,6 @@ int linux_ata_device::ata_command_interface(smart_command_set command, int selec // There are two different types of ioctls(). The HDIO_DRIVE_TASK // one is this: if (command==STATUS_CHECK || command==AUTOSAVE || command==AUTO_OFFLINE){ - int retval; - // NOT DOCUMENTED in /usr/src/linux/include/linux/hdreg.h. You // have to read the IDE driver source code. Sigh. // buff[0]: ATA COMMAND CODE REGISTER @@ -405,7 +402,7 @@ int linux_ata_device::ata_command_interface(smart_command_set command, int selec buff[4]=normal_lo; buff[5]=normal_hi; - if ((retval=ioctl(get_fd(), HDIO_DRIVE_TASK, buff))) { + if (ioctl(get_fd(), HDIO_DRIVE_TASK, buff)) { if (errno==-EINVAL) { pout("Error SMART Status command via HDIO_DRIVE_TASK failed"); pout("Rebuild older linux 2.2 kernels with HDIO_DRIVE_TASK support added\n"); @@ -1202,7 +1199,7 @@ bool linux_megaraid_device::open() int mjr; int report = scsi_debugmode; - if(sscanf(get_dev_name(),"/dev/bus/%d", &m_hba) == 0) { + if (sscanf(get_dev_name(), "/dev/bus/%u", &m_hba) == 0) { if (!linux_smart_device::open()) return false; /* Get device HBA */ @@ -1325,7 +1322,6 @@ bool linux_megaraid_device::megasas_cmd(int cdbLen, void *cdb, { struct megasas_pthru_frame *pthru; struct megasas_iocpacket uio; - int rc; memset(&uio, 0, sizeof(uio)); pthru = &uio.frame.pthru; @@ -1367,9 +1363,8 @@ bool linux_megaraid_device::megasas_cmd(int cdbLen, void *cdb, uio.sgl[0].iov_len = dataLen; } - rc = 0; errno = 0; - rc = ioctl(m_fd, MEGASAS_IOC_FIRMWARE, &uio); + int rc = ioctl(m_fd, MEGASAS_IOC_FIRMWARE, &uio); if (pthru->cmd_status || rc != 0) { if (pthru->cmd_status == 12) { return set_err(EIO, "megasas_cmd: Device %d does not exist\n", m_disknum); @@ -1991,10 +1986,8 @@ linux_areca_ata_device::linux_areca_ata_device(smart_interface * intf, const cha smart_device * linux_areca_ata_device::autodetect_open() { - int is_ata = 1; - // autodetect device type - is_ata = arcmsr_get_dev_type(); + int is_ata = arcmsr_get_dev_type(); if(is_ata < 0) { set_err(EIO); @@ -2824,20 +2817,19 @@ bool linux_smart_interface::get_dev_megasas(smart_device_list & devlist) return false; // getting bus numbers with megasas devices - struct dirent *ep; - unsigned int host_no = 0; - char sysfsdir[256]; - - /* we are using sysfs to get list of all scsi hosts */ + // we are using sysfs to get list of all scsi hosts DIR * dp = opendir ("/sys/class/scsi_host/"); if (dp != NULL) { + struct dirent *ep; while ((ep = readdir (dp)) != NULL) { - if (!sscanf(ep->d_name, "host%d", &host_no)) + unsigned int host_no = 0; + if (!sscanf(ep->d_name, "host%u", &host_no)) continue; /* proc_name should be megaraid_sas */ + char sysfsdir[256]; snprintf(sysfsdir, sizeof(sysfsdir) - 1, - "/sys/class/scsi_host/host%d/proc_name", host_no); + "/sys/class/scsi_host/host%u/proc_name", host_no); if((fp = fopen(sysfsdir, "r")) == NULL) continue; if(fgets(line, sizeof(line), fp) != NULL && !strncmp(line,"megaraid_sas",12)) { @@ -2972,7 +2964,7 @@ linux_smart_interface::megasas_pd_add_list(int bus_no, smart_device_list & devli */ megasas_pd_list * list = 0; for (unsigned list_size = 1024; ; ) { - list = (megasas_pd_list *)realloc(list, list_size); + list = reinterpret_cast(realloc(list, list_size)); if (!list) throw std::bad_alloc(); bzero(list, list_size); @@ -3186,12 +3178,11 @@ smart_device * linux_smart_interface::get_custom_smart_device(const char * name, } //aacraid? - unsigned int device; - unsigned int host; - if(sscanf(type, "aacraid,%d,%d,%d", &host, &channel, &device)==3) { + unsigned host, chan, device; + if (sscanf(type, "aacraid,%u,%u,%u", &host, &chan, &device) == 3) { //return new linux_aacraid_device(this,name,channel,device); return get_sat_device("sat,auto", - new linux_aacraid_device(this, name, host, channel, device)); + new linux_aacraid_device(this, name, host, chan, device)); } diff --git a/os_linux.h b/os_linux.h index 3cb2f33..104d176 100644 --- a/os_linux.h +++ b/os_linux.h @@ -1,7 +1,7 @@ /* * os_linux.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2003-8 Bruce Allen * @@ -38,7 +38,7 @@ #ifndef OS_LINUX_H_ #define OS_LINUX_H_ -#define OS_LINUX_H_CVSID "$Id: os_linux.h 3728 2012-12-13 17:57:50Z chrfranke $\n" +#define OS_LINUX_H_CVSID "$Id: os_linux.h 4120 2015-08-27 16:12:21Z samm2 $\n" /* The following definitions/macros/prototypes are used for three diff --git a/os_netbsd.cpp b/os_netbsd.cpp index dce2d9d..c76065c 100644 --- a/os_netbsd.cpp +++ b/os_netbsd.cpp @@ -1,7 +1,7 @@ /* * os_netbsd.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2003-8 Sergey Svishchev * @@ -26,14 +26,14 @@ #include #include -const char * os_netbsd_cpp_cvsid = "$Id: os_netbsd.cpp 3806 2013-03-29 20:17:03Z chrfranke $" +const char * os_netbsd_cpp_cvsid = "$Id: os_netbsd.cpp 4205 2016-01-22 15:22:53Z samm2 $" OS_NETBSD_H_CVSID; /* global variable holding byte count of allocated memory */ extern long long bytes; enum warnings { - BAD_SMART, NO_3WARE, NO_ARECA, MAX_MSG + BAD_SMART, MAX_MSG }; /* Utility function for printing warnings */ @@ -132,7 +132,14 @@ get_dev_names(char ***names, const char *prefix) n++; } - mp = (char **)realloc(mp, n * (sizeof(char *))); + void * tmp = (char **)realloc(mp, n * (sizeof(char *))); + if (NULL == tmp) { + pout("Out of memory constructing scan device list\n"); + free(mp); + return -1; + } + else + mp = tmp; bytes += (n) * (sizeof(char *)); *names = mp; return n; @@ -320,7 +327,8 @@ ata_command_interface(int fd, smart_command_set command, int select, char *data) return 0; } - if ((retval = ioctl(fd, ATAIOCCOMMAND, &req))) { + retval = ioctl(fd, ATAIOCCOMMAND, &req); + if (retval < 0) { perror("Failed command"); return -1; } diff --git a/os_netbsd.h b/os_netbsd.h index 6b8c758..7bf7b76 100644 --- a/os_netbsd.h +++ b/os_netbsd.h @@ -1,7 +1,7 @@ /* * os_netbsd.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2003-8 Sergey Svishchev * @@ -24,7 +24,7 @@ #ifndef OS_NETBSD_H_ #define OS_NETBSD_H_ -#define OS_NETBSD_H_CVSID "$Id: os_netbsd.h 3728 2012-12-13 17:57:50Z chrfranke $\n" +#define OS_NETBSD_H_CVSID "$Id: os_netbsd.h 4120 2015-08-27 16:12:21Z samm2 $\n" #include #include diff --git a/os_openbsd.cpp b/os_openbsd.cpp index 896b88d..d457430 100644 --- a/os_openbsd.cpp +++ b/os_openbsd.cpp @@ -1,7 +1,7 @@ /* * os_openbsd.c * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2004-10 David Snyder * @@ -27,14 +27,14 @@ #include -const char * os_openbsd_cpp_cvsid = "$Id: os_openbsd.cpp 3727 2012-12-13 17:23:06Z samm2 $" +const char * os_openbsd_cpp_cvsid = "$Id: os_openbsd.cpp 4205 2016-01-22 15:22:53Z samm2 $" OS_OPENBSD_H_CVSID; /* global variable holding byte count of allocated memory */ extern long long bytes; enum warnings { - BAD_SMART, NO_3WARE, NO_ARECA, MAX_MSG + BAD_SMART, MAX_MSG }; /* Utility function for printing warnings */ @@ -136,7 +136,14 @@ get_dev_names(char ***names, const char *prefix) n++; } - mp = (char **)realloc(mp, n * (sizeof(char *))); + void * tmp = (char **)realloc(mp, n * (sizeof(char *))); + if (NULL == tmp) { + pout("Out of memory constructing scan device list\n"); + free(mp); + return -1; + } + else + mp = tmp; bytes += (n) * (sizeof(char *)); *names = mp; return n; @@ -316,7 +323,8 @@ ata_command_interface(int fd, smart_command_set command, int select, char *data) unsigned const short normal = WDSMART_CYL, failed = 0x2cf4; - if ((retval = ioctl(fd, ATAIOCCOMMAND, &req))) { + retval = ioctl(fd, ATAIOCCOMMAND, &req); + if (retval < 0) { perror("Failed command"); return -1; } diff --git a/os_openbsd.h b/os_openbsd.h index b686c78..358627f 100644 --- a/os_openbsd.h +++ b/os_openbsd.h @@ -1,7 +1,7 @@ /* * os_openbsd.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2004-8 David Snyder * @@ -26,7 +26,7 @@ #ifndef OS_OPENBSD_H_ #define OS_OPENBSD_H_ -#define OS_OPENBSD_H_CVSID "$Id: os_openbsd.h 3728 2012-12-13 17:57:50Z chrfranke $\n" +#define OS_OPENBSD_H_CVSID "$Id: os_openbsd.h 4120 2015-08-27 16:12:21Z samm2 $\n" /* from NetBSD: atareg.h,v 1.17, by Manuel Bouyer */ /* Actually fits _perfectly_ into OBSDs wdcreg.h, but... */ diff --git a/os_os2.cpp b/os_os2.cpp index 7ad7f19..2846f4a 100644 --- a/os_os2.cpp +++ b/os_os2.cpp @@ -1,7 +1,7 @@ /* * os_os2.c * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2004-8 Yuri Dario * @@ -31,7 +31,7 @@ #include "os_os2.h" // Needed by '-V' option (CVS versioning) of smartd/smartctl -const char *os_XXXX_c_cvsid="$Id: os_os2.cpp 3806 2013-03-29 20:17:03Z chrfranke $" \ +const char *os_XXXX_c_cvsid="$Id: os_os2.cpp 4120 2015-08-27 16:12:21Z samm2 $" \ ATACMDS_H_CVSID OS_XXXX_H_CVSID SCSICMDS_H_CVSID UTILITY_H_CVSID; // global handle to device driver diff --git a/os_os2.h b/os_os2.h index 3d8cb86..6a7b1ff 100644 --- a/os_os2.h +++ b/os_os2.h @@ -1,7 +1,7 @@ /* * os_os2.c * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2004-8 Yuri Dario * @@ -18,7 +18,7 @@ #ifndef OS_OS2_H_ #define OS_OS2_H_ -#define OS_XXXX_H_CVSID "$Id: os_os2.h 3728 2012-12-13 17:57:50Z chrfranke $\n" +#define OS_XXXX_H_CVSID "$Id: os_os2.h 4120 2015-08-27 16:12:21Z samm2 $\n" // Additional material should start here. Note: to keep the '-V' CVS // reporting option working as intended, you should only #include diff --git a/os_qnxnto.h b/os_qnxnto.h index 3b12cd4..f6d4697 100644 --- a/os_qnxnto.h +++ b/os_qnxnto.h @@ -1,7 +1,7 @@ /* * os_generic.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) Joerg Hering * Copyright (C) 2003-8 Bruce Allen @@ -23,7 +23,7 @@ */ #ifndef OS_QNXNTO_H_ #define OS_QNXNTO_H_ -#define OS_QNXNTO_H_CVSID "$Id: os_qnxnto.h 3728 2012-12-13 17:57:50Z chrfranke $\n" +#define OS_QNXNTO_H_CVSID "$Id: os_qnxnto.h 4120 2015-08-27 16:12:21Z samm2 $\n" // Additional material should start here. Note: to keep the '-V' CVS // reporting option working as intended, you should only #include diff --git a/os_solaris.cpp b/os_solaris.cpp index 793aec7..147fa1e 100644 --- a/os_solaris.cpp +++ b/os_solaris.cpp @@ -1,10 +1,10 @@ /* * os_solaris.c * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * - * Copyright (C) 2003-8 SAWADA Keiji - * Copyright (C) 2003-8 Casper Dik + * Copyright (C) 2003-08 SAWADA Keiji + * Copyright (C) 2003-15 Casper Dik * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -39,9 +39,9 @@ extern long long bytes; -static const char *filenameandversion="$Id: os_solaris.cpp 3806 2013-03-29 20:17:03Z chrfranke $"; +static const char *filenameandversion="$Id: os_solaris.cpp 4142 2015-10-14 19:05:19Z chrfranke $"; -const char *os_XXXX_c_cvsid="$Id: os_solaris.cpp 3806 2013-03-29 20:17:03Z chrfranke $" \ +const char *os_XXXX_c_cvsid="$Id: os_solaris.cpp 4142 2015-10-14 19:05:19Z chrfranke $" \ ATACMDS_H_CVSID CONFIG_H_CVSID INT64_H_CVSID OS_SOLARIS_H_CVSID SCSICMDS_H_CVSID UTILITY_H_CVSID; // The printwarning() function warns about unimplemented functions @@ -99,6 +99,7 @@ void print_smartctl_examples(){ static const char *uscsidrvrs[] = { "sd", "ssd", + "disk", // SATA devices "st" }; @@ -271,7 +272,7 @@ int deviceclose(int fd){ return close(fd); } -#if defined(__sparc) +#if defined(WITH_SOLARIS_SPARC_ATA) // swap each 2-byte pairs in a sector static void swap_sector(void *p) { @@ -286,7 +287,7 @@ static void swap_sector(void *p) // Interface to ATA devices. See os_linux.c int ata_command_interface(int fd, smart_command_set command, int select, char *data){ -#if defined(__sparc) +#if defined(WITH_SOLARIS_SPARC_ATA) int err; switch (command){ @@ -328,7 +329,7 @@ int ata_command_interface(int fd, smart_command_set command, int select, char *d EXIT(1); break; } -#else /* __sparc */ +#else /* WITH_SOLARIS_SPARC_ATA */ ARGUSED(fd); ARGUSED(command); ARGUSED(select); ARGUSED(data); /* Above smart_* routines uses undocumented ioctls of "dada" @@ -395,7 +396,7 @@ int do_scsi_cmnd_io(int fd, struct scsi_cmnd_io * iop, int report) default: return -EINVAL; } - uscsi.uscsi_flags |= (USCSI_ISOLATE | USCSI_RQENABLE); + uscsi.uscsi_flags |= (USCSI_ISOLATE | USCSI_RQENABLE | USCSI_SILENT); if (ioctl(fd, USCSICMD, &uscsi)) { int err = errno; diff --git a/os_solaris.h b/os_solaris.h index 70dc3ee..3d8d1bb 100644 --- a/os_solaris.h +++ b/os_solaris.h @@ -1,7 +1,7 @@ /* * os_solaris.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2003-8 SAWADA Keiji * Copyright (C) 2003-8 Casper Dik @@ -25,7 +25,7 @@ #ifndef OS_SOLARIS_H_ #define OS_SOLARIS_H_ -#define OS_SOLARIS_H_CVSID "$Id: os_solaris.h 3728 2012-12-13 17:57:50Z chrfranke $\n" +#define OS_SOLARIS_H_CVSID "$Id: os_solaris.h 4120 2015-08-27 16:12:21Z samm2 $\n" // Additional material should start here. Note: to keep the '-V' CVS // reporting option working as intended, you should only #include diff --git a/os_win32.cpp b/os_win32.cpp index 11b7319..dae4f66 100644 --- a/os_win32.cpp +++ b/os_win32.cpp @@ -1,7 +1,7 @@ /* * os_win32.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2004-15 Christian Franke * @@ -111,7 +111,7 @@ #define strnicmp strncasecmp #endif -const char * os_win32_cpp_cvsid = "$Id: os_win32.cpp 4098 2015-05-30 16:37:37Z chrfranke $"; +const char * os_win32_cpp_cvsid = "$Id: os_win32.cpp 4156 2015-10-18 12:20:40Z samm2 $"; ///////////////////////////////////////////////////////////////////////////// // Windows I/O-controls, some declarations are missing in the include files @@ -643,60 +643,37 @@ std::string win_smart_interface::get_os_version_str() const int vlen = sizeof(vstr)-sizeof(SMARTMONTOOLS_BUILD_HOST); assert(vptr == vstr+strlen(vstr) && vptr+vlen+1 == vstr+sizeof(vstr)); - OSVERSIONINFOEXA vi; memset(&vi, 0, sizeof(vi)); + // Starting with Windows 8.1, GetVersionEx() does no longer report the + // actual OS version, see: + // http://msdn.microsoft.com/en-us/library/windows/desktop/dn302074.aspx + + // RtlGetVersion() is not affected + LONG /*NTSTATUS*/ (WINAPI /*NTAPI*/ * RtlGetVersion_p)(LPOSVERSIONINFOEXW) = + (LONG (WINAPI *)(LPOSVERSIONINFOEXW)) + GetProcAddress(GetModuleHandleA("ntdll.dll"), "RtlGetVersion"); + + OSVERSIONINFOEXW vi; memset(&vi, 0, sizeof(vi)); vi.dwOSVersionInfoSize = sizeof(vi); - if (!GetVersionExA((OSVERSIONINFOA *)&vi)) { - memset(&vi, 0, sizeof(vi)); - vi.dwOSVersionInfoSize = sizeof(OSVERSIONINFOA); - if (!GetVersionExA((OSVERSIONINFOA *)&vi)) + if (!RtlGetVersion_p || RtlGetVersion_p(&vi)) { + if (!GetVersionExW((OSVERSIONINFOW *)&vi)) return vstr; } const char * w = 0; - if (vi.dwPlatformId == VER_PLATFORM_WIN32_NT) { - - if (vi.dwMajorVersion > 6 || (vi.dwMajorVersion == 6 && vi.dwMinorVersion >= 2)) { - // Starting with Windows 8.1 Preview, GetVersionEx() does no longer report the - // actual OS version, see: - // http://msdn.microsoft.com/en-us/library/windows/desktop/dn302074.aspx - - ULONGLONG major_equal = VerSetConditionMask(0, VER_MAJORVERSION, VER_EQUAL); - for (unsigned major = vi.dwMajorVersion; major <= 9; major++) { - OSVERSIONINFOEXA vi2; memset(&vi2, 0, sizeof(vi2)); - vi2.dwOSVersionInfoSize = sizeof(vi2); vi2.dwMajorVersion = major; - if (!VerifyVersionInfo(&vi2, VER_MAJORVERSION, major_equal)) - continue; - if (vi.dwMajorVersion < major) { - vi.dwMajorVersion = major; vi.dwMinorVersion = 0; - } - - ULONGLONG minor_equal = VerSetConditionMask(0, VER_MINORVERSION, VER_EQUAL); - for (unsigned minor = vi.dwMinorVersion; minor <= 9; minor++) { - memset(&vi2, 0, sizeof(vi2)); vi2.dwOSVersionInfoSize = sizeof(vi2); - vi2.dwMinorVersion = minor; - if (!VerifyVersionInfo(&vi2, VER_MINORVERSION, minor_equal)) - continue; - vi.dwMinorVersion = minor; - break; - } - - break; - } - } - - if (vi.dwMajorVersion <= 0xf && vi.dwMinorVersion <= 0xf) { - bool ws = (vi.wProductType <= VER_NT_WORKSTATION); - switch (vi.dwMajorVersion << 4 | vi.dwMinorVersion) { - case 0x50: w = "2000"; break; - case 0x51: w = "xp"; break; - case 0x52: w = (!GetSystemMetrics(89/*SM_SERVERR2*/) - ? "2003" : "2003r2"); break; - case 0x60: w = (ws ? "vista" : "2008" ); break; - case 0x61: w = (ws ? "win7" : "2008r2"); break; - case 0x62: w = (ws ? "win8" : "2012" ); break; - case 0x63: w = (ws ? "win8.1": "2012r2"); break; - case 0x64: w = (ws ? "win10" : "w10srv"); break; - } + if ( vi.dwPlatformId == VER_PLATFORM_WIN32_NT + && vi.dwMajorVersion <= 0xf && vi.dwMinorVersion <= 0xf) { + bool ws = (vi.wProductType <= VER_NT_WORKSTATION); + switch (vi.dwMajorVersion << 4 | vi.dwMinorVersion) { + case 0x50: w = "2000"; break; + case 0x51: w = "xp"; break; + case 0x52: w = (!GetSystemMetrics(89/*SM_SERVERR2*/) + ? "2003" : "2003r2"); break; + case 0x60: w = (ws ? "vista" : "2008" ); break; + case 0x61: w = (ws ? "win7" : "2008r2"); break; + case 0x62: w = (ws ? "win8" : "2012" ); break; + case 0x63: w = (ws ? "win8.1": "2012r2"); break; + case 0x64: w = (ws ? "w10tp" : "w10tps"); break; // 6.4 = Win 10 Technical Preview + case 0xa0: w = (ws ? "win10" : "w10srv"); break; // 10.0 = Win 10 Final } } @@ -750,7 +727,8 @@ enum win_dev_type { DEV_UNKNOWN = 0, DEV_ATA, DEV_SCSI, DEV_SAT, DEV_USB }; static win_dev_type get_phy_drive_type(int drive); static win_dev_type get_phy_drive_type(int drive, GETVERSIONINPARAMS_EX * ata_version_ex); static win_dev_type get_log_drive_type(int drive); -static bool get_usb_id(int drive, unsigned short & vendor_id, +static bool get_usb_id(int phydrive, int logdrive, + unsigned short & vendor_id, unsigned short & product_id); static const char * ata_get_def_options(void); @@ -807,9 +785,10 @@ static int sdxy_to_phydrive(const char (& xy)[2+1]) return phydrive; } -static win_dev_type get_dev_type(const char * name, int & phydrive) +static win_dev_type get_dev_type(const char * name, int & phydrive, int & logdrive) { - phydrive = -1; + phydrive = logdrive = -1; + name = skipdev(name); if (!strncmp(name, "st", 2)) return DEV_SCSI; @@ -818,7 +797,7 @@ static win_dev_type get_dev_type(const char * name, int & phydrive) if (!strncmp(name, "tape", 4)) return DEV_SCSI; - int logdrive = drive_letter(name); + logdrive = drive_letter(name); if (logdrive >= 0) { win_dev_type type = get_log_drive_type(logdrive); return (type != DEV_UNKNOWN ? type : DEV_SCSI); @@ -830,9 +809,9 @@ static win_dev_type get_dev_type(const char * name, int & phydrive) return get_phy_drive_type(phydrive); } - phydrive = -1; if (sscanf(name, "pd%d", &phydrive) == 1 && phydrive >= 0) return get_phy_drive_type(phydrive); + return DEV_UNKNOWN; } @@ -949,8 +928,8 @@ smart_device * win_smart_interface::autodetect_smart_device(const char * name) if (str_starts_with(testname, "csmi")) return new win_csmi_device(this, name, ""); - int phydrive = -1; - win_dev_type type = get_dev_type(name, phydrive); + int phydrive = -1, logdrive = -1; + win_dev_type type = get_dev_type(name, phydrive, logdrive); if (type == DEV_ATA) return new win_ata_device(this, name, ""); @@ -964,7 +943,7 @@ smart_device * win_smart_interface::autodetect_smart_device(const char * name) if (type == DEV_USB) { // Get USB bridge ID unsigned short vendor_id = 0, product_id = 0; - if (!(phydrive >= 0 && get_usb_id(phydrive, vendor_id, product_id))) { + if (!get_usb_id(phydrive, logdrive, vendor_id, product_id)) { set_err(EINVAL, "Unable to read USB device ID"); return 0; } @@ -1064,7 +1043,7 @@ bool win_smart_interface::scan_smart_devices(smart_device_list & devlist, raid_seen[vers_ex.wControllerId] = true; // Add physical drives int len = strlen(name); - for (int pi = 0; pi < 32; pi++) { + for (unsigned int pi = 0; pi < 32; pi++) { if (vers_ex.dwDeviceMapEx & (1L << pi)) { snprintf(name+len, sizeof(name)-1-len, ",%u", pi); devlist.push_back( new win_ata_device(this, name, "ata") ); @@ -1098,7 +1077,7 @@ bool win_smart_interface::scan_smart_devices(smart_device_list & devlist, // TODO: Use common function for this and autodetect_smart_device() // Get USB bridge ID unsigned short vendor_id = 0, product_id = 0; - if (!get_usb_id(i, vendor_id, product_id)) + if (!get_usb_id(i, -1, vendor_id, product_id)) continue; // Get type name for this ID const char * usbtype = get_usb_dev_type_by_id(vendor_id, product_id); @@ -2314,8 +2293,10 @@ static bool get_serial_from_wmi(int drive, ata_identify_device * id) ///////////////////////////////////////////////////////////////////////////// // USB ID detection using WMI -// Get USB ID for a physical drive number -static bool get_usb_id(int drive, unsigned short & vendor_id, unsigned short & product_id) +// Get USB ID for a physical or logical drive number +static bool get_usb_id(int phydrive, int logdrive, + unsigned short & vendor_id, + unsigned short & product_id) { bool debug = (scsi_debugmode > 1); @@ -2327,13 +2308,41 @@ static bool get_usb_id(int drive, unsigned short & vendor_id, unsigned short & p } // Get device name + std::string name; + wbem_object wo; - if (!ws.query1(wo, "SELECT Model FROM Win32_DiskDrive WHERE DeviceID=\"\\\\\\\\.\\\\PHYSICALDRIVE%d\"", drive)) + if (0 <= logdrive && logdrive <= 'Z'-'A') { + // Drive letter -> Partition info + if (!ws.query1(wo, "ASSOCIATORS OF {Win32_LogicalDisk.DeviceID=\"%c:\"} WHERE ResultClass = Win32_DiskPartition", + 'A'+logdrive)) + return false; + + std::string partid = wo.get_str("DeviceID"); + if (debug) + pout("%c: --> \"%s\" -->\n", 'A'+logdrive, partid.c_str()); + + // Partition ID -> Physical drive info + if (!ws.query1(wo, "ASSOCIATORS OF {Win32_DiskPartition.DeviceID=\"%s\"} WHERE ResultClass = Win32_DiskDrive", + partid.c_str())) + return false; + + name = wo.get_str("Model"); + if (debug) + pout("%s --> \"%s\":\n", wo.get_str("DeviceID").c_str(), name.c_str()); + } + + else if (phydrive >= 0) { + // Physical drive number -> Physical drive info + if (!ws.query1(wo, "SELECT Model FROM Win32_DiskDrive WHERE DeviceID=\"\\\\\\\\.\\\\PHYSICALDRIVE%d\"", phydrive)) + return false; + + name = wo.get_str("Model"); + if (debug) + pout("\\.\\\\PHYSICALDRIVE%d --> \"%s\":\n", phydrive, name.c_str()); + } + else return false; - std::string name = wo.get_str("Model"); - if (debug) - pout("PhysicalDrive%d, \"%s\":\n", drive, name.c_str()); // Get USB_CONTROLLER -> DEVICE associations wbem_enumerator we; @@ -2376,10 +2385,9 @@ static bool get_usb_id(int drive, unsigned short & vendor_id, unsigned short & p prev_usb_ant = ant; if (debug) pout(" +-> \"%s\" [0x%04x:0x%04x]\n", devid.c_str(), prev_usb_venid, prev_usb_proid); - continue; } - else if (str_starts_with(devid, "USBSTOR\\\\")) { - // USBSTOR device found + else if (str_starts_with(devid, "USBSTOR\\\\") || str_starts_with(devid, "SCSI\\\\")) { + // USBSTORage or SCSI device found if (debug) pout(" +--> \"%s\"\n", devid.c_str()); @@ -2643,7 +2651,6 @@ bool win_ata_device::open(int phydrive, int logdrive, const char * options, int close(); return set_err(ENOSYS); } - devmap = 0x0f; } m_smartver_state = 1; @@ -2896,9 +2903,10 @@ bool win_ata_device::ata_pass_through(const ata_cmd_in & in, ata_cmd_out & out) break; case 'f': if (in.in_regs.command == ATA_IDENTIFY_DEVICE) { - rc = get_identify_from_device_property(get_fh(), (ata_identify_device *)data); + ata_identify_device * id = reinterpret_cast(data); + rc = get_identify_from_device_property(get_fh(), id); if (rc == 0 && m_phydrive >= 0) - get_serial_from_wmi(m_phydrive, (ata_identify_device *)data); + get_serial_from_wmi(m_phydrive, id); id_is_cached = true; } else if (in.in_regs.command == ATA_SMART_CMD) switch (in.in_regs.features) { @@ -3889,10 +3897,8 @@ bool win_areca_ata_device::open() smart_device * win_areca_ata_device::autodetect_open() { - int is_ata = 1; - // autodetect device type - is_ata = arcmsr_get_dev_type(); + int is_ata = arcmsr_get_dev_type(); if(is_ata < 0) { set_err(EIO); diff --git a/os_win32/daemon_win32.cpp b/os_win32/daemon_win32.cpp index 56b0d79..c4cce58 100644 --- a/os_win32/daemon_win32.cpp +++ b/os_win32/daemon_win32.cpp @@ -1,7 +1,7 @@ /* * os_win32/daemon_win32.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2004-14 Christian Franke * @@ -20,7 +20,7 @@ #include "daemon_win32.h" -const char * daemon_win32_cpp_cvsid = "$Id: daemon_win32.cpp 3959 2014-07-18 19:22:18Z chrfranke $" +const char * daemon_win32_cpp_cvsid = "$Id: daemon_win32.cpp 4120 2015-08-27 16:12:21Z samm2 $" DAEMON_WIN32_H_CVSID; #include diff --git a/os_win32/daemon_win32.h b/os_win32/daemon_win32.h index 2d9c1c5..e87d002 100644 --- a/os_win32/daemon_win32.h +++ b/os_win32/daemon_win32.h @@ -1,7 +1,7 @@ /* * os_win32/daemon_win32.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2004-12 Christian Franke * @@ -18,7 +18,7 @@ #ifndef DAEMON_WIN32_H #define DAEMON_WIN32_H -#define DAEMON_WIN32_H_CVSID "$Id: daemon_win32.h 3584 2012-08-05 17:05:32Z chrfranke $" +#define DAEMON_WIN32_H_CVSID "$Id: daemon_win32.h 4120 2015-08-27 16:12:21Z samm2 $" #include diff --git a/os_win32/default.manifest b/os_win32/default.manifest new file mode 100644 index 0000000..01379b9 --- /dev/null +++ b/os_win32/default.manifest @@ -0,0 +1,27 @@ + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/os_win32/installer.nsi b/os_win32/installer.nsi index d06e085..78ce014 100644 --- a/os_win32/installer.nsi +++ b/os_win32/installer.nsi @@ -1,7 +1,7 @@ ; -; smartmontools install NSIS script +; os_win32/installer.nsi - smartmontools install NSIS script ; -; Home page of code is: http://smartmontools.sourceforge.net +; Home page of code is: http://www.smartmontools.org ; ; Copyright (C) 2006-15 Christian Franke ; @@ -13,7 +13,7 @@ ; You should have received a copy of the GNU General Public License ; (for example COPYING); If not, see . ; -; $Id: installer.nsi 4072 2015-04-28 20:35:15Z chrfranke $ +; $Id: installer.nsi 4174 2015-11-22 16:19:29Z chrfranke $ ; @@ -36,6 +36,8 @@ Name "smartmontools" OutFile "${OUTFILE}" +RequestExecutionLevel admin + SetCompressor /solid lzma XPStyle on @@ -43,7 +45,7 @@ InstallColors /windows ; Set in .onInit ;InstallDir "$PROGRAMFILES\smartmontools" -;InstallDirRegKey HKLM "Software\smartmontools" "Install_Dir" +;InstallDirRegKey HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" "InstallLocation" Var EDITOR @@ -56,12 +58,9 @@ Var EDITOR LicenseData "${INPDIR}\doc\COPYING.txt" !include "FileFunc.nsh" +!include "LogicLib.nsh" !include "Sections.nsh" -!insertmacro GetParameters -!insertmacro GetOptions - -RequestExecutionLevel admin ;-------------------------------------------------------------------- ; Pages @@ -81,6 +80,11 @@ UninstPage instfiles InstType "Full" InstType "Extract files only" InstType "Drive menu" +!ifdef INPDIR64 +InstType "Full (x64)" +InstType "Extract files only (x64)" +InstType "Drive menu (x64)" +!endif ;-------------------------------------------------------------------- @@ -88,8 +92,17 @@ InstType "Drive menu" !ifdef INPDIR64 Section "64-bit version" X64_SECTION + SectionIn 4 5 6 ; Handled in Function CheckX64 SectionEnd + + !define FULL_TYPES "1 4" + !define EXTRACT_TYPES "2 5" + !define DRIVEMENU_TYPE "3 6" +!else + !define FULL_TYPES "1" + !define EXTRACT_TYPES "2" + !define DRIVEMENU_TYPE "3" !endif SectionGroup "!Program files" @@ -97,14 +110,15 @@ SectionGroup "!Program files" !macro FileExe path option !ifdef INPDIR64 ; Use dummy SetOutPath to control archive location of executables - StrCmp $X64 "" +5 + ${If} $X64 != "" Goto +2 SetOutPath "$INSTDIR\bin64" File ${option} '${INPDIR64}\${path}' - GoTo +4 + ${Else} Goto +2 SetOutPath "$INSTDIR\bin" File ${option} '${INPDIR}\${path}' + ${EndIf} !else File ${option} '${INPDIR}\${path}' !endif @@ -112,7 +126,7 @@ SectionGroup "!Program files" Section "smartctl" SMARTCTL_SECTION - SectionIn 1 2 + SectionIn ${FULL_TYPES} ${EXTRACT_TYPES} SetOutPath "$INSTDIR\bin" !insertmacro FileExe "bin\smartctl.exe" "" @@ -121,17 +135,18 @@ SectionGroup "!Program files" Section "smartd" SMARTD_SECTION - SectionIn 1 2 + SectionIn ${FULL_TYPES} ${EXTRACT_TYPES} SetOutPath "$INSTDIR\bin" ; Stop service ? StrCpy $1 "" - IfFileExists "$INSTDIR\bin\smartd.exe" 0 nosrv + ${If} ${FileExists} "$INSTDIR\bin\smartd.exe" ReadRegStr $0 HKLM "System\CurrentControlSet\Services\smartd" "ImagePath" - StrCmp $0 "" nosrv + ${If} $0 != "" ExecWait "net stop smartd" $1 - nosrv: + ${EndIf} + ${EndIf} !insertmacro FileExe "bin\smartd.exe" "" IfFileExists "$INSTDIR\bin\smartd.conf" 0 +2 @@ -142,15 +157,16 @@ SectionGroup "!Program files" !insertmacro FileExe "bin\wtssendmsg.exe" "" ; Restart service ? - StrCmp $1 "0" 0 +3 + ${If} $1 == "0" MessageBox MB_YESNO|MB_ICONQUESTION|MB_DEFBUTTON2 "Restart smartd service ?" /SD IDNO IDYES 0 IDNO +2 ExecWait "net start smartd" + ${EndIf} SectionEnd Section "smartctl-nc (GSmartControl)" SMARTCTL_NC_SECTION - SectionIn 1 2 + SectionIn ${FULL_TYPES} ${EXTRACT_TYPES} SetOutPath "$INSTDIR\bin" !insertmacro FileExe "bin\smartctl-nc.exe" "" @@ -159,7 +175,7 @@ SectionGroup "!Program files" Section "drivedb.h (Drive Database)" DRIVEDB_SECTION - SectionIn 1 2 + SectionIn ${FULL_TYPES} ${EXTRACT_TYPES} SetOutPath "$INSTDIR\bin" File "${INPDIR}\bin\drivedb.h" @@ -171,7 +187,7 @@ SectionGroupEnd Section "!Documentation" DOC_SECTION - SectionIn 1 2 + SectionIn ${FULL_TYPES} ${EXTRACT_TYPES} SetOutPath "$INSTDIR\doc" File "${INPDIR}\doc\AUTHORS.txt" @@ -183,10 +199,11 @@ Section "!Documentation" DOC_SECTION File "${INPDIR}\doc\README.txt" File "${INPDIR}\doc\TODO.txt" !ifdef INPDIR64 - StrCmp $X64 "" +3 + ${If} $X64 != "" File "${INPDIR64}\doc\checksums64.txt" - GoTo +2 + ${Else} File "${INPDIR}\doc\checksums32.txt" + ${EndIf} !else File "${INPDIR}\doc\checksums??.txt" !endif @@ -202,7 +219,7 @@ SectionEnd Section "Uninstaller" UNINST_SECTION - SectionIn 1 + SectionIn ${FULL_TYPES} AddSize 40 CreateDirectory "$INSTDIR" @@ -210,8 +227,9 @@ Section "Uninstaller" UNINST_SECTION ; Keep old Install_Dir registry entry for GSmartControl ReadRegStr $0 HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\GSmartControl" "InstallLocation" ReadRegStr $1 HKLM "Software\smartmontools" "Install_Dir" - StrCmp "$0$1" "" +2 0 + ${If} "$0$1" != "" WriteRegStr HKLM "Software\smartmontools" "Install_Dir" "$INSTDIR" + ${EndIf} ; Write uninstall keys and program WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" "DisplayName" "smartmontools" @@ -221,9 +239,9 @@ Section "Uninstaller" UNINST_SECTION WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" "InstallLocation" "$INSTDIR" WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" "UninstallString" '"$INSTDIR\uninst-smartmontools.exe"' WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" "Publisher" "smartmontools.org" - WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" "URLInfoAbout" "http://www.smartmontools.org/" + WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" "URLInfoAbout" "https://www.smartmontools.org/" WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" "HelpLink" "http://sourceforge.net/projects/smartmontools/support" - WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" "URLUpdateInfo" "http://smartmontools.no-ip.org/" + WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" "URLUpdateInfo" "http://builds.smartmontools.org/" WriteRegDWORD HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" "NoModify" 1 WriteRegDWORD HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" "NoRepair" 1 WriteUninstaller "uninst-smartmontools.exe" @@ -232,7 +250,7 @@ SectionEnd Section "Start Menu Shortcuts" MENU_SECTION - SectionIn 1 + SectionIn ${FULL_TYPES} SetShellVarContext all @@ -245,15 +263,15 @@ Section "Start Menu Shortcuts" MENU_SECTION !macroend ; runcmdu - IfFileExists "$INSTDIR\bin\smartctl.exe" 0 +2 - IfFileExists "$INSTDIR\bin\smartd.exe" 0 noruncmd + ${If} ${FileExists} "$INSTDIR\bin\smartctl.exe" + ${OrIf} ${FileExists} "$INSTDIR\bin\smartd.exe" SetOutPath "$INSTDIR\bin" !insertmacro FileExe "bin\runcmdu.exe" "" - File "${INPDIR}\bin\runcmdu.exe.manifest" - noruncmd: + Delete "$INSTDIR\bin\runcmdu.exe.manifest" ; TODO: Remove after smartmontools 6.5 + ${EndIf} ; smartctl - IfFileExists "$INSTDIR\bin\smartctl.exe" 0 noctl + ${If} ${FileExists} "$INSTDIR\bin\smartctl.exe" SetOutPath "$INSTDIR\bin" !insertmacro CreateAdminShortCut "$SMPROGRAMS\smartmontools\smartctl (Admin CMD).lnk" "$WINDIR\system32\cmd.exe" '/k PATH=$INSTDIR\bin;%PATH%&cd /d "$INSTDIR\bin"' CreateDirectory "$SMPROGRAMS\smartmontools\smartctl Examples" @@ -273,10 +291,10 @@ Section "Start Menu Shortcuts" MENU_SECTION !insertmacro CreateAdminShortCut "$SMPROGRAMS\smartmontools\smartctl Examples\Stop(Abort) selftest (-X).lnk" "$INSTDIR\bin\runcmdu.exe" "smartctl -X sda" !insertmacro CreateAdminShortCut "$SMPROGRAMS\smartmontools\smartctl Examples\Turn SMART off (-s off).lnk" "$INSTDIR\bin\runcmdu.exe" "smartctl -s off sda" !insertmacro CreateAdminShortCut "$SMPROGRAMS\smartmontools\smartctl Examples\Turn SMART on (-s on).lnk" "$INSTDIR\bin\runcmdu.exe" "smartctl -s on sda" - noctl: + ${EndIf} ; smartd - IfFileExists "$INSTDIR\bin\smartd.exe" 0 nod + ${If} ${FileExists} "$INSTDIR\bin\smartd.exe" SetOutPath "$INSTDIR\bin" CreateDirectory "$SMPROGRAMS\smartmontools\smartd Examples" !insertmacro CreateAdminShortCut "$SMPROGRAMS\smartmontools\smartd Examples\Daemon start, smartd.log.lnk" "$INSTDIR\bin\runcmdu.exe" "smartd -l local0" @@ -295,10 +313,10 @@ Section "Start Menu Shortcuts" MENU_SECTION !insertmacro CreateAdminShortCut "$SMPROGRAMS\smartmontools\smartd Examples\Service remove.lnk" "$INSTDIR\bin\runcmdu.exe" "smartd remove" !insertmacro CreateAdminShortCut "$SMPROGRAMS\smartmontools\smartd Examples\Service start.lnk" "$INSTDIR\bin\runcmdu.exe" "net start smartd" !insertmacro CreateAdminShortCut "$SMPROGRAMS\smartmontools\smartd Examples\Service stop.lnk" "$INSTDIR\bin\runcmdu.exe" "net stop smartd" - nod: + ${EndIf} ; Documentation - IfFileExists "$INSTDIR\doc\README.TXT" 0 nodoc + ${If} ${FileExists} "$INSTDIR\doc\README.TXT" SetOutPath "$INSTDIR\doc" CreateDirectory "$SMPROGRAMS\smartmontools\Documentation" CreateShortCut "$SMPROGRAMS\smartmontools\Documentation\smartctl manual page (html).lnk" "$INSTDIR\doc\smartctl.8.html" @@ -308,36 +326,36 @@ Section "Start Menu Shortcuts" MENU_SECTION CreateShortCut "$SMPROGRAMS\smartmontools\Documentation\smartd manual page (txt).lnk" "$INSTDIR\doc\smartd.8.txt" CreateShortCut "$SMPROGRAMS\smartmontools\Documentation\smartd.conf manual page (txt).lnk" "$INSTDIR\doc\smartd.conf.5.txt" CreateShortCut "$SMPROGRAMS\smartmontools\Documentation\smartd.conf sample.lnk" "$EDITOR" "$INSTDIR\doc\smartd.conf" - IfFileExists "$INSTDIR\bin\drivedb.h" 0 nodb + ${If} ${FileExists} "$INSTDIR\bin\drivedb.h" CreateShortCut "$SMPROGRAMS\smartmontools\Documentation\drivedb.h (view).lnk" "$EDITOR" "$INSTDIR\bin\drivedb.h" !insertmacro CreateAdminShortCut "$SMPROGRAMS\smartmontools\Documentation\drivedb-add.h (create, edit).lnk" "$EDITOR" "$INSTDIR\bin\drivedb-add.h" - nodb: + ${EndIf} CreateShortCut "$SMPROGRAMS\smartmontools\Documentation\ChangeLog.lnk" "$INSTDIR\doc\ChangeLog.txt" CreateShortCut "$SMPROGRAMS\smartmontools\Documentation\COPYING.lnk" "$INSTDIR\doc\COPYING.txt" CreateShortCut "$SMPROGRAMS\smartmontools\Documentation\NEWS.lnk" "$INSTDIR\doc\NEWS.txt" - CreateShortCut "$SMPROGRAMS\smartmontools\Documentation\Windows version download page.lnk" "http://smartmontools.no-ip.org/" - nodoc: + ${EndIf} ; Homepage - CreateShortCut "$SMPROGRAMS\smartmontools\smartmontools Home Page.lnk" "http://www.smartmontools.org/" + CreateShortCut "$SMPROGRAMS\smartmontools\smartmontools Home Page.lnk" "https://www.smartmontools.org/" + CreateShortCut "$SMPROGRAMS\smartmontools\smartmontools Daily Builds.lnk" "http://builds.smartmontools.org/" ; drivedb.h update - IfFileExists "$INSTDIR\bin\update-smart-drivedb.exe" 0 noupdb + ${If} ${FileExists} "$INSTDIR\bin\update-smart-drivedb.exe" SetOutPath "$INSTDIR\bin" !insertmacro CreateAdminShortCut "$SMPROGRAMS\smartmontools\drivedb.h update.lnk" "$INSTDIR\bin\update-smart-drivedb.exe" "" - noupdb: + ${EndIf} ; Uninstall - IfFileExists "$INSTDIR\uninst-smartmontools.exe" 0 noinst + ${If} ${FileExists} "$INSTDIR\uninst-smartmontools.exe" SetOutPath "$INSTDIR" !insertmacro CreateAdminShortCut "$SMPROGRAMS\smartmontools\Uninstall smartmontools.lnk" "$INSTDIR\uninst-smartmontools.exe" "" - noinst: + ${EndIf} SectionEnd Section "Add install dir to PATH" PATH_SECTION - SectionIn 1 + SectionIn ${FULL_TYPES} Push "$INSTDIR\bin" Call AddToPath @@ -357,13 +375,13 @@ SectionGroup "Add smartctl to drive menu" !macroend Section "Remove existing entries first" DRIVE_REMOVE_SECTION - SectionIn 3 + SectionIn ${DRIVEMENU_TYPE} !insertmacro DriveMenuRemove SectionEnd !macro DriveSection id name args Section 'smartctl ${args} ...' DRIVE_${id}_SECTION - SectionIn 3 + SectionIn ${DRIVEMENU_TYPE} Call CheckRunCmdA DetailPrint 'Add drive menu entry "${name}": smartctl ${args} ...' WriteRegStr HKCR "Drive\shell\smartctl${id}" "" "${name}" @@ -385,37 +403,40 @@ SectionGroupEnd Section "Uninstall" ; Stop & remove service - IfFileExists "$INSTDIR\bin\smartd.exe" 0 nosrv + ${If} ${FileExists} "$INSTDIR\bin\smartd.exe" ReadRegStr $0 HKLM "System\CurrentControlSet\Services\smartd" "ImagePath" - StrCmp $0 "" nosrv + ${If} $0 != "" ExecWait "net stop smartd" - MessageBox MB_YESNO|MB_ICONQUESTION|MB_DEFBUTTON2 "Remove smartd service ?" /SD IDNO IDYES 0 IDNO nosrv + MessageBox MB_YESNO|MB_ICONQUESTION|MB_DEFBUTTON2 "Remove smartd service ?" /SD IDNO IDYES 0 IDNO +2 ExecWait "$INSTDIR\bin\smartd.exe remove" - nosrv: + ${EndIf} + ${EndIf} ; Remove installer registry keys DeleteRegKey HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" DeleteRegKey HKLM "Software\smartmontools" ; Remove conf file ? - IfFileExists "$INSTDIR\bin\smartd.conf" 0 noconf + ${If} ${FileExists} "$INSTDIR\bin\smartd.conf" ; Assume unchanged if timestamp is equal to sample file GetFileTime "$INSTDIR\bin\smartd.conf" $0 $1 GetFileTime "$INSTDIR\doc\smartd.conf" $2 $3 StrCmp "$0:$1" "$2:$3" +2 0 - MessageBox MB_YESNO|MB_ICONQUESTION|MB_DEFBUTTON2 "Delete configuration file$\n$INSTDIR\bin\smartd.conf ?" /SD IDNO IDYES 0 IDNO noconf + MessageBox MB_YESNO|MB_ICONQUESTION|MB_DEFBUTTON2 "Delete configuration file$\n$INSTDIR\bin\smartd.conf ?" /SD IDNO IDYES 0 IDNO +2 Delete "$INSTDIR\bin\smartd.conf" - noconf: + ${EndIf} ; Remove log file ? - IfFileExists "$INSTDIR\bin\smartd.log" 0 +3 + ${If} ${FileExists} "$INSTDIR\bin\smartd.log" MessageBox MB_YESNO|MB_ICONQUESTION|MB_DEFBUTTON2 "Delete log file$\n$INSTDIR\bin\smartd.log ?" /SD IDNO IDYES 0 IDNO +2 Delete "$INSTDIR\bin\smartd.log" + ${EndIf} ; Remove drivedb-add file ? - IfFileExists "$INSTDIR\bin\drivedb-add.h" 0 +3 + ${If} ${FileExists} "$INSTDIR\bin\drivedb-add.h" MessageBox MB_YESNO|MB_ICONQUESTION|MB_DEFBUTTON2 "Delete local drive database file$\n$INSTDIR\bin\drivedb-add.h ?" /SD IDNO IDYES 0 IDNO +2 Delete "$INSTDIR\bin\drivedb-add.h" + ${EndIf} ; Remove files Delete "$INSTDIR\bin\smartctl.exe" @@ -431,9 +452,9 @@ Section "Uninstall" Delete "$INSTDIR\bin\smartd-run.bat" Delete "$INSTDIR\bin\net-run.bat" Delete "$INSTDIR\bin\runcmda.exe" - Delete "$INSTDIR\bin\runcmda.exe.manifest" + Delete "$INSTDIR\bin\runcmda.exe.manifest" ; TODO: Remove after smartmontools 6.5 Delete "$INSTDIR\bin\runcmdu.exe" - Delete "$INSTDIR\bin\runcmdu.exe.manifest" + Delete "$INSTDIR\bin\runcmdu.exe.manifest" ; TODO: Remove after smartmontools 6.5 Delete "$INSTDIR\bin\wtssendmsg.exe" Delete "$INSTDIR\doc\AUTHORS.txt" Delete "$INSTDIR\doc\ChangeLog.txt" @@ -477,14 +498,15 @@ Section "Uninstall" !insertmacro DriveMenuRemove ; Check for still existing entries - IfFileExists "$INSTDIR\bin\smartd.exe" 0 +3 + ${If} ${FileExists} "$INSTDIR\bin\smartd.exe" MessageBox MB_OK|MB_ICONEXCLAMATION "$INSTDIR\bin\smartd.exe could not be removed.$\nsmartd is possibly still running." /SD IDOK - Goto +3 - IfFileExists "$INSTDIR" 0 +2 + ${ElseIf} ${FileExists} "$INSTDIR" MessageBox MB_OK "Note: $INSTDIR could not be removed." /SD IDOK + ${EndIf} - IfFileExists "$SMPROGRAMS\smartmontools" 0 +2 + ${If} ${FileExists} "$SMPROGRAMS\smartmontools" MessageBox MB_OK "Note: $SMPROGRAMS\smartmontools could not be removed." /SD IDOK + ${EndIf} SectionEnd @@ -500,19 +522,32 @@ SectionEnd Function .onInit ; Set default install directories - StrCmp $INSTDIR "" 0 endinst ; /D=PATH option specified ? - ReadRegStr $INSTDIR HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" "InstallLocation" - StrCmp $INSTDIR "" 0 endinst ; Already installed ? - ReadRegStr $INSTDIR HKLM "Software\smartmontools" "Install_Dir" - StrCmp $INSTDIR "" 0 endinst ; Already installed ? - StrCpy $INSTDIR "$PROGRAMFILES\smartmontools" + ${If} $INSTDIR == "" ; /D=PATH option not specified ? + ReadRegStr $INSTDIR HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\smartmontools" "InstallLocation" + ${If} $INSTDIR == "" ; Not already installed ? + ReadRegStr $INSTDIR HKLM "Software\smartmontools" "Install_Dir" + ${If} $INSTDIR == "" ; Not already installed (smartmontools < r3911/6.3) ? + StrCpy $INSTDIR "$PROGRAMFILES\smartmontools" !ifdef INPDIR64 - StrCpy $INSTDIR32 $INSTDIR - StrCpy $INSTDIR64 "$PROGRAMFILES64\smartmontools" + StrCpy $INSTDIR32 $INSTDIR + StrCpy $INSTDIR64 "$PROGRAMFILES64\smartmontools" !endif - endinst: + ${EndIf} + ${EndIf} + ${EndIf} !ifdef INPDIR64 + ; Check for 64-bit unless already installed in 32-bit location + ${If} $INSTDIR64 != "" + ${OrIf} $INSTDIR != "$PROGRAMFILES\smartmontools" + ; $1 = IsWow64Process(GetCurrentProcess(), ($0=FALSE, &$0)) + System::Call "kernel32::GetCurrentProcess() i.s" + System::Call "kernel32::IsWow64Process(i s, *i 0 r0) i.r1" + ${If} "$0 $1" == "1 1" ; 64-bit Windows ? + !insertmacro SelectSection ${X64_SECTION} + ${EndIf} + ${EndIf} + ; Sizes of binary sections include 32-bit and 64-bit executables !insertmacro AdjustSectionSize ${SMARTCTL_SECTION} !insertmacro AdjustSectionSize ${SMARTD_SECTION} @@ -521,47 +556,57 @@ Function .onInit ; Use Notepad++ if installed StrCpy $EDITOR "$PROGRAMFILES\Notepad++\notepad++.exe" - IfFileExists "$EDITOR" +2 0 + ${IfNot} ${FileExists} "$EDITOR" StrCpy $EDITOR "notepad.exe" + ${EndIf} Call ParseCmdLine + +!ifdef INPDIR64 + Call CheckX64 +!endif FunctionEnd ; Check x64 section and update INSTDIR accordingly !ifdef INPDIR64 Function CheckX64 - SectionGetFlags ${X64_SECTION} $0 - IntOp $0 $0 & ${SF_SELECTED} - IntCmp $0 ${SF_SELECTED} x64 + ${IfNot} ${SectionIsSelected} ${X64_SECTION} StrCpy $X64 "" - StrCmp $INSTDIR32 "" +3 + ${If} $INSTDIR32 != "" + ${AndIf} $INSTDIR == $INSTDIR64 StrCpy $INSTDIR $INSTDIR32 - StrCpy $INSTDIR32 "" - Goto done - x64: + ${EndIf} + ${Else} StrCpy $X64 "t" - StrCmp $INSTDIR64 "" +3 + ${If} $INSTDIR64 != "" + ${AndIf} $INSTDIR == $INSTDIR32 StrCpy $INSTDIR $INSTDIR64 - StrCpy $INSTDIR64 "" - done: + ${EndIf} + ${EndIf} FunctionEnd !endif ; Command line parsing -!macro CheckCmdLineOption name section - StrCpy $allopts "$allopts,${name}" + +!macro GetCmdLineOption var name Push ",$opts," Push ",${name}," Call StrStr - Pop $0 - StrCmp $0 "" 0 sel_${name} - !insertmacro UnselectSection ${section} - Goto done_${name} -sel_${name}: - !insertmacro SelectSection ${section} - StrCpy $nomatch "" -done_${name}: + Pop ${var} + ${If} ${var} != "" + StrCpy $nomatch "" + ${EndIf} +!macroend + +!macro CheckCmdLineOption name section + StrCpy $allopts "$allopts,${name}" + !insertmacro GetCmdLineOption $0 ${name} + ${If} $0 == "" + !insertmacro UnselectSection ${section} + ${Else} + !insertmacro SelectSection ${section} + ${EndIf} !macroend Function ParseCmdLine @@ -569,19 +614,30 @@ Function ParseCmdLine Var /global opts ${GetParameters} $R0 ${GetOptions} $R0 "/SO" $opts - IfErrors 0 +2 + ${If} ${Errors} Return + ${EndIf} Var /global allopts - StrCpy $allopts "" Var /global nomatch StrCpy $nomatch "t" - ; turn sections on or off !ifdef INPDIR64 - !insertmacro CheckCmdLineOption "x64" ${X64_SECTION} - Call CheckX64 - StrCmp $opts "x64" 0 +2 - Return ; leave sections unchanged if only "x64" is specified + ; Change previous 64-bit setting + StrCpy $allopts ",x32|x64" + !insertmacro GetCmdLineOption $0 "x32" + ${If} $0 != "" + !insertmacro UnselectSection ${X64_SECTION} + ${EndIf} + !insertmacro GetCmdLineOption $0 "x64" + ${If} $0 != "" + !insertmacro SelectSection ${X64_SECTION} + ${EndIf} + ; Leave other sections unchanged if only "x32" or "x64" is specified + ${If} $opts == "x32" + ${OrIf} $opts == "x64" + Return + ${EndIf} !endif + ; Turn sections on or off !insertmacro CheckCmdLineOption "smartctl" ${SMARTCTL_SECTION} !insertmacro CheckCmdLineOption "smartd" ${SMARTD_SECTION} !insertmacro CheckCmdLineOption "smartctlnc" ${SMARTCTL_NC_SECTION} @@ -597,22 +653,25 @@ Function ParseCmdLine !insertmacro CheckCmdLineOption "drive3" ${DRIVE_3_SECTION} !insertmacro CheckCmdLineOption "drive4" ${DRIVE_4_SECTION} !insertmacro CheckCmdLineOption "drive5" ${DRIVE_5_SECTION} - StrCmp $opts "-" done - StrCmp $nomatch "" done - StrCpy $0 "$allopts,-" "" 1 - MessageBox MB_OK "Usage: smartmontools-VERSION.win32-setup [/S] [/SO component,...] [/D=INSTDIR]$\n$\ncomponents:$\n $0" - Abort -done: + ${If} $opts != "-" + ${If} $nomatch != "" + StrCpy $0 "$allopts,-" "" 1 + MessageBox MB_OK "Usage: smartmontools-VERSION.win32-setup [/S] [/SO component,...] [/D=INSTDIR]$\n$\ncomponents:$\n $0" + Abort + ${EndIf} + ${EndIf} FunctionEnd -; Install runcmda.exe if missing +; Install runcmda.exe only once Function CheckRunCmdA - IfFileExists "$INSTDIR\bin\runcmda.exe" done 0 + Var /global runcmda + ${If} $runcmda == "" + StrCpy $runcmda "t" SetOutPath "$INSTDIR\bin" !insertmacro FileExe "bin\runcmda.exe" "" - File "${INPDIR}\bin\runcmda.exe.manifest" - done: + Delete "$INSTDIR\bin\runcmda.exe.manifest" ; TODO: Remove after smartmontools 6.5 + ${EndIf} FunctionEnd @@ -658,16 +717,19 @@ Function AddToPath System::Call "advapi32::RegQueryValueEx(i $3, t'PATH', i 0, i 0, t.r1, *i ${NSIS_MAX_STRLEN} r2) i.r4" System::Call "advapi32::RegCloseKey(i $3)" - IntCmp $4 234 0 +4 +4 ; $4 == ERROR_MORE_DATA + ${If} $4 = 234 ; ERROR_MORE_DATA DetailPrint "AddToPath: original length $2 > ${NSIS_MAX_STRLEN}" - MessageBox MB_OK "PATH not updated, original length $2 > ${NSIS_MAX_STRLEN}" + MessageBox MB_OK "PATH not updated, original length $2 > ${NSIS_MAX_STRLEN}" /SD IDOK Goto done + ${EndIf} - IntCmp $4 0 +5 ; $4 != NO_ERROR - IntCmp $4 2 +3 ; $4 != ERROR_FILE_NOT_FOUND + ${If} $4 <> 0 ; NO_ERROR + ${If} $4 <> 2 ; ERROR_FILE_NOT_FOUND DetailPrint "AddToPath: unexpected error code $4" Goto done + ${EndIf} StrCpy $1 "" + ${EndIf} ; Check if already in PATH Push "$1;" @@ -686,18 +748,21 @@ Function AddToPath StrLen $3 $1 IntOp $2 $2 + $3 IntOp $2 $2 + 2 ; $2 = strlen(dir) + strlen(PATH) + sizeof(";") - IntCmp $2 ${NSIS_MAX_STRLEN} +4 +4 0 + ${If} $2 > ${NSIS_MAX_STRLEN} DetailPrint "AddToPath: new length $2 > ${NSIS_MAX_STRLEN}" - MessageBox MB_OK "PATH not updated, new length $2 > ${NSIS_MAX_STRLEN}." + MessageBox MB_OK "PATH not updated, new length $2 > ${NSIS_MAX_STRLEN}." /SD IDOK Goto done + ${EndIf} ; Append dir to PATH DetailPrint "Add to PATH: $0" StrCpy $2 $1 1 -1 - StrCmp $2 ";" 0 +2 + ${If} $2 == ";" StrCpy $1 $1 -1 ; remove trailing ';' - StrCmp $1 "" +2 ; no leading ';' + ${EndIf} + ${If} $1 != "" ; no leading ';' StrCpy $0 "$1;$0" + ${EndIf} WriteRegExpandStr ${Environ} "PATH" $0 SendMessage ${HWND_BROADCAST} ${WM_WININICHANGE} 0 "STR:Environment" /TIMEOUT=5000 @@ -727,8 +792,9 @@ Function un.RemoveFromPath ReadRegStr $1 ${Environ} "PATH" StrCpy $5 $1 1 -1 - StrCmp $5 ";" +2 + ${If} $5 != ";" StrCpy $1 "$1;" ; ensure trailing ';' + ${EndIf} Push $1 Push "$0;" Call un.StrStr @@ -742,8 +808,9 @@ Function un.RemoveFromPath StrCpy $6 $2 "" $3 ; $6 is now the part after the path to remove StrCpy $3 "$5$6" StrCpy $5 $3 1 -1 - StrCmp $5 ";" 0 +2 + ${If} $5 == ";" StrCpy $3 $3 -1 ; remove trailing ';' + ${EndIf} WriteRegExpandStr ${Environ} "PATH" $3 SendMessage ${HWND_BROADCAST} ${WM_WININICHANGE} 0 "STR:Environment" /TIMEOUT=5000 @@ -778,13 +845,12 @@ Function ${un}StrStr StrCpy $R4 0 ; $R1=substring, $R2=string, $R3=strlen(substring) ; $R4=count, $R5=tmp - loop: + ${Do} StrCpy $R5 $R2 $R3 $R4 - StrCmp $R5 $R1 done - StrCmp $R5 "" done + ${IfThen} $R5 == $R1 ${|} ${ExitDo} ${|} + ${IfThen} $R5 == "" ${|} ${ExitDo} ${|} IntOp $R4 $R4 + 1 - Goto loop -done: + ${Loop} StrCpy $R1 $R2 "" $R4 Pop $R5 Pop $R4 @@ -804,8 +870,6 @@ FunctionEnd ; http://nsis.sourceforge.net/IShellLink_Set_RunAs_flag ; -!include "LogicLib.nsh" - !define IPersistFile {0000010b-0000-0000-c000-000000000046} !define CLSID_ShellLink {00021401-0000-0000-C000-000000000046} !define IID_IShellLinkA {000214EE-0000-0000-C000-000000000046} @@ -852,5 +916,5 @@ Function ShellLinkSetRunAs ${Else} DetailPrint "Set RunAsAdmin: $9" ${EndIf} - System::Store L ; push $0-$9, $R0-$R9 + System::Store L ; pop $R9-$R0, $9-$0 FunctionEnd diff --git a/os_win32/runcmd.c b/os_win32/runcmd.c index 8be8198..2a26cda 100644 --- a/os_win32/runcmd.c +++ b/os_win32/runcmd.c @@ -1,7 +1,7 @@ /* * Run console command and wait for user input * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2011 Christian Franke * @@ -15,7 +15,7 @@ * */ -char svnid[] = "$Id: runcmd.c 3453 2011-10-16 12:45:27Z chrfranke $"; +char svnid[] = "$Id: runcmd.c 4120 2015-08-27 16:12:21Z samm2 $"; #include #include diff --git a/os_win32/runcmda.exe.manifest b/os_win32/runcmda.exe.manifest deleted file mode 100644 index 2b57539..0000000 --- a/os_win32/runcmda.exe.manifest +++ /dev/null @@ -1,18 +0,0 @@ - - - - - - - - - - - diff --git a/os_win32/runcmdu.exe.manifest b/os_win32/runcmdu.exe.manifest deleted file mode 100644 index f6eb707..0000000 --- a/os_win32/runcmdu.exe.manifest +++ /dev/null @@ -1,18 +0,0 @@ - - - - - - - - - - - diff --git a/os_win32/syslog.h b/os_win32/syslog.h index 3061d07..4d83999 100644 --- a/os_win32/syslog.h +++ b/os_win32/syslog.h @@ -1,7 +1,7 @@ /* * os_win32/syslog.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2004-8 Christian Franke * @@ -19,7 +19,7 @@ #ifndef SYSLOG_H #define SYSLOG_H -#define SYSLOG_H_CVSID "$Id: syslog.h 3728 2012-12-13 17:57:50Z chrfranke $\n" +#define SYSLOG_H_CVSID "$Id: syslog.h 4120 2015-08-27 16:12:21Z samm2 $\n" #include diff --git a/os_win32/syslog_win32.cpp b/os_win32/syslog_win32.cpp index 02fa4de..57e14e6 100644 --- a/os_win32/syslog_win32.cpp +++ b/os_win32/syslog_win32.cpp @@ -1,9 +1,9 @@ /* * os_win32/syslog_win32.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * - * Copyright (C) 2004-12 Christian Franke + * Copyright (C) 2004-15 Christian Franke * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -33,7 +33,7 @@ #define WIN32_LEAN_AND_MEAN #include // RegisterEventSourceA(), ReportEventA(), ... -const char *syslog_win32_cpp_cvsid = "$Id: syslog_win32.cpp 3575 2012-07-19 21:32:56Z chrfranke $" +const char *syslog_win32_cpp_cvsid = "$Id: syslog_win32.cpp 4149 2015-10-17 15:38:01Z chrfranke $" SYSLOG_H_CVSID; #ifdef _MSC_VER @@ -420,7 +420,7 @@ int main(int argc, char* argv[]) if (i % 13 == 0) Sleep(1000L); sprintf(buf, "Log Line %d\n", i); - syslog(i % 17 ? LOG_INFO : LOG_ERR, buf); + syslog((i % 17) ? LOG_INFO : LOG_ERR, buf); } closelog(); return 0; diff --git a/os_win32/syslogevt.mc b/os_win32/syslogevt.mc index c6d3ac6..8c34ef6 100644 --- a/os_win32/syslogevt.mc +++ b/os_win32/syslogevt.mc @@ -1,7 +1,7 @@ ;/* ; * os_win32/syslogevt.mc ; * -; * Home page of code is: http://smartmontools.sourceforge.net +; * Home page of code is: http://www.smartmontools.org ; * ; * Copyright (C) 2004-10 Christian Franke ; * @@ -16,7 +16,7 @@ ; * ; */ ; -;// $Id: syslogevt.mc 3727 2012-12-13 17:23:06Z samm2 $ +;// $Id: syslogevt.mc 4120 2015-08-27 16:12:21Z samm2 $ ; ;// Use message compiler "mc" or "windmc" to generate ;// syslogevt.rc, syslogevt.h, msg00001.bin diff --git a/os_win32/update-smart-drivedb.nsi b/os_win32/update-smart-drivedb.nsi index aa2d525..7b8295a 100644 --- a/os_win32/update-smart-drivedb.nsi +++ b/os_win32/update-smart-drivedb.nsi @@ -1,7 +1,7 @@ ; ; smartmontools drive database update NSIS script ; -; Home page of code is: http://smartmontools.sourceforge.net +; Home page of code is: http://www.smartmontools.org ; ; Copyright (C) 2011-13 Christian Franke ; @@ -13,7 +13,7 @@ ; You should have received a copy of the GNU General Public License ; (for example COPYING); If not, see . ; -; $Id: update-smart-drivedb.nsi 3815 2013-06-06 17:31:59Z chrfranke $ +; $Id: update-smart-drivedb.nsi 4120 2015-08-27 16:12:21Z samm2 $ ; diff --git a/os_win32/wbemcli_small.h b/os_win32/wbemcli_small.h index 9732890..ce85af0 100644 --- a/os_win32/wbemcli_small.h +++ b/os_win32/wbemcli_small.h @@ -1,7 +1,7 @@ /* * os_win32/wbemcli_small.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * This file was extracted from wbemcli.h of the w64 mingw-runtime package * (http://mingw-w64.sourceforge.net/). See original copyright below. diff --git a/os_win32/wmiquery.cpp b/os_win32/wmiquery.cpp index ade992d..861ae4a 100644 --- a/os_win32/wmiquery.cpp +++ b/os_win32/wmiquery.cpp @@ -1,7 +1,7 @@ /* * os_win32/wmiquery.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2011-13 Christian Franke * @@ -23,7 +23,7 @@ #include -const char * wmiquery_cpp_cvsid = "$Id: wmiquery.cpp 3802 2013-03-24 18:36:21Z chrfranke $" +const char * wmiquery_cpp_cvsid = "$Id: wmiquery.cpp 4120 2015-08-27 16:12:21Z samm2 $" WMIQUERY_H_CVSID; diff --git a/os_win32/wmiquery.h b/os_win32/wmiquery.h index 730dcb1..3000a37 100644 --- a/os_win32/wmiquery.h +++ b/os_win32/wmiquery.h @@ -1,9 +1,9 @@ /* * os_win32/wmiquery.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * - * Copyright (C) 2011 Christian Franke + * Copyright (C) 2011-15 Christian Franke * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -18,7 +18,7 @@ #ifndef WMIQUERY_H #define WMIQUERY_H -#define WMIQUERY_H_CVSID "$Id: wmiquery.h 3475 2011-11-10 21:43:40Z chrfranke $" +#define WMIQUERY_H_CVSID "$Id: wmiquery.h 4152 2015-10-17 16:08:21Z chrfranke $" #ifdef HAVE_WBEMCLI_H #include @@ -45,7 +45,7 @@ class com_bstr { public: /// Construct from string. - com_bstr(const char * str); + explicit com_bstr(const char * str); /// Destructor frees BSTR. ~com_bstr() diff --git a/os_win32/wtssendmsg.c b/os_win32/wtssendmsg.c index 3298dfc..dca7fb7 100644 --- a/os_win32/wtssendmsg.c +++ b/os_win32/wtssendmsg.c @@ -1,7 +1,7 @@ /* * WTSSendMessage() command line tool * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2012 Christian Franke * @@ -18,7 +18,7 @@ #define WINVER 0x0500 #define _WIN32_WINNT WINVER -char svnid[] = "$Id: wtssendmsg.c 3714 2012-11-24 16:34:47Z chrfranke $"; +char svnid[] = "$Id: wtssendmsg.c 4120 2015-08-27 16:12:21Z samm2 $"; #include #include @@ -30,7 +30,7 @@ char svnid[] = "$Id: wtssendmsg.c 3714 2012-11-24 16:34:47Z chrfranke $"; static int usage() { - printf("wtssendmsg $Revision: 3714 $ - Display a message box on client desktops\n" + printf("wtssendmsg $Revision: 4120 $ - Display a message box on client desktops\n" "Copyright (C) 2012 Christian Franke, smartmontools.org\n\n" "Usage: wtssendmsg [-cas] [-v] [\"Caption\"] \"Message\"|-\n" " wtssendmsg -v\n\n" diff --git a/scsiata.cpp b/scsiata.cpp index fbe603b..c76e9bd 100644 --- a/scsiata.cpp +++ b/scsiata.cpp @@ -1,10 +1,10 @@ /* * scsiata.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * - * Copyright (C) 2006-12 Douglas Gilbert - * Copyright (C) 2009-13 Christian Franke + * Copyright (C) 2006-15 Douglas Gilbert + * Copyright (C) 2009-15 Christian Franke * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -62,7 +62,7 @@ #include "dev_ata_cmd_set.h" // ata_device_with_command_set #include "dev_tunnelled.h" // tunnelled_device<> -const char * scsiata_cpp_cvsid = "$Id: scsiata.cpp 4041 2015-03-14 00:50:20Z dpgilbert $"; +const char * scsiata_cpp_cvsid = "$Id: scsiata.cpp 4130 2015-09-25 15:08:06Z chrfranke $"; /* This is a slightly stretched SCSI sense "descriptor" format header. The addition is to allow the 0x70 and 0x71 response codes. The idea @@ -394,6 +394,16 @@ bool sat_device::ata_pass_through(const ata_cmd_in & in, ata_cmd_out & out) } scsi_do_sense_disect(&io_hdr, &sinfo); int status = scsiSimpleSenseFilter(&sinfo); + + // Workaround for bogus sense_key in sense data with SAT ATA Return Descriptor + if ( status && ck_cond && ardp && ard_len > 13 + && (ardp[13] & 0xc1) == 0x40 /* !BSY && DRDY && !ERR */) { + if (scsi_debugmode > 0) + pout("ATA status (0x%02x) indicates success, ignoring SCSI sense_key\n", + ardp[13]); + status = 0; + } + if (0 != status) { /* other than no_sense and recovered_error */ if (scsi_debugmode > 0) { pout("sat_device::ata_pass_through: scsi error: %s\n", @@ -433,7 +443,8 @@ bool sat_device::ata_pass_through(const ata_cmd_in & in, ata_cmd_out & out) } } else if ((! sense_descriptor) && (0 == ssh.asc) && - (SCSI_ASCQ_ATA_PASS_THROUGH == ssh.ascq)) { + (SCSI_ASCQ_ATA_PASS_THROUGH == ssh.ascq) && + (0 != io_hdr.sensep[4] /* Some ATA STATUS bit must be set */)) { /* in SAT-2 and later, ATA registers may be passed back via * fixed format sense data [ref: sat3r07 section 12.2.2.7] */ ata_out_regs & lo = out.out_regs; diff --git a/scsicmds.cpp b/scsicmds.cpp index d306d72..f59c66a 100644 --- a/scsicmds.cpp +++ b/scsicmds.cpp @@ -1,12 +1,10 @@ /* * scsicmds.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2002-8 Bruce Allen * Copyright (C) 1999-2000 Michael Cornwell - * - * Additional SCSI work: * Copyright (C) 2003-15 Douglas Gilbert * * This program is free software; you can redistribute it and/or modify @@ -49,7 +47,7 @@ #include "dev_interface.h" #include "utility.h" -const char *scsicmds_c_cvsid="$Id: scsicmds.cpp 4081 2015-05-10 16:42:50Z chrfranke $" +const char *scsicmds_c_cvsid="$Id: scsicmds.cpp 4157 2015-10-20 16:03:57Z chrfranke $" SCSICMDS_H_CVSID; // Print SCSI debug messages? @@ -61,13 +59,11 @@ supported_vpd_pages * supported_vpd_pages_p = NULL; supported_vpd_pages::supported_vpd_pages(scsi_device * device) : num_valid(0) { unsigned char b[0xfc]; /* pre SPC-3 INQUIRY max response size */ - int n; - memset(b, 0, sizeof(b)); if (device && (0 == scsiInquiryVpd(device, SCSI_VPD_SUPPORTED_VPD_PAGES, b, sizeof(b)))) { num_valid = (b[2] << 8) + b[3]; - n = sizeof(pages); + int n = sizeof(pages); if (num_valid > n) num_valid = n; memcpy(pages, b + 4, num_valid); @@ -91,7 +87,6 @@ void dStrHex(const char* str, int len, int no_ascii) { const char* p = str; - unsigned char c; char buff[82]; int a = 0; const int bpstart = 5; @@ -110,7 +105,7 @@ dStrHex(const char* str, int len, int no_ascii) for(i = 0; i < len; i++) { - c = *p++; + unsigned char c = *p++; bpos += 3; if (bpos == (bpstart + (9 * 3))) bpos++; @@ -175,14 +170,12 @@ static const char * vendor_specific = ""; const char * scsi_get_opcode_name(UINT8 opcode) { - int k; int len = sizeof(opcode_name_arr) / sizeof(opcode_name_arr[0]); - struct scsi_opcode_name * onp; if (opcode >= 0xc0) return vendor_specific; - for (k = 0; k < len; ++k) { - onp = &opcode_name_arr[k]; + for (int k = 0; k < len; ++k) { + struct scsi_opcode_name * onp = &opcode_name_arr[k]; if (opcode == onp->opcode) return onp->name; else if (opcode < onp->opcode) @@ -195,11 +188,9 @@ void scsi_do_sense_disect(const struct scsi_cmnd_io * io_buf, struct scsi_sense_disect * out) { - int resp_code; - memset(out, 0, sizeof(struct scsi_sense_disect)); if (SCSI_STATUS_CHECK_CONDITION == io_buf->scsi_status) { - resp_code = (io_buf->sensep[0] & 0x7f); + int resp_code = (io_buf->sensep[0] & 0x7f); out->resp_code = resp_code; if (resp_code >= 0x72) { out->sense_key = (io_buf->sensep[1] & 0xf); @@ -302,19 +293,19 @@ scsi_vpd_dev_id_iter(const unsigned char * initial_desig_desc, int page_len, int * off, int m_assoc, int m_desig_type, int m_code_set) { const unsigned char * ucp; - int k, c_set, assoc, desig_type; + int k; for (k = *off, ucp = initial_desig_desc ; (k + 3) < page_len; ) { k = (k < 0) ? 0 : (k + ucp[k + 3] + 4); if ((k + 4) > page_len) break; - c_set = (ucp[k] & 0xf); + int c_set = (ucp[k] & 0xf); if ((m_code_set >= 0) && (m_code_set != c_set)) continue; - assoc = ((ucp[k + 1] >> 4) & 0x3); + int assoc = ((ucp[k + 1] >> 4) & 0x3); if ((m_assoc >= 0) && (m_assoc != assoc)) continue; - desig_type = (ucp[k + 1] & 0xf); + int desig_type = (ucp[k + 1] & 0xf); if ((m_desig_type >= 0) && (m_desig_type != desig_type)) continue; *off = k; @@ -330,11 +321,6 @@ int scsi_decode_lu_dev_id(const unsigned char * b, int blen, char * s, int slen, int * transport) { - int m, c_set, assoc, desig_type, i_len, naa, off, u, have_scsi_ns; - const unsigned char * ucp; - const unsigned char * ip; - int si = 0; - if (transport) *transport = -1; if (slen < 32) { @@ -342,25 +328,29 @@ scsi_decode_lu_dev_id(const unsigned char * b, int blen, char * s, int slen, s[0] = '\0'; return -1; } - have_scsi_ns = 0; + s[0] = '\0'; - off = -1; + int si = 0; + int have_scsi_ns = 0; + int off = -1; + int u; while ((u = scsi_vpd_dev_id_iter(b, blen, &off, -1, -1, -1)) == 0) { - ucp = b + off; - i_len = ucp[3]; + const unsigned char * ucp = b + off; + int i_len = ucp[3]; if ((off + i_len + 4) > blen) { snprintf(s+si, slen-si, "error: designator length"); return -1; } - assoc = ((ucp[1] >> 4) & 0x3); + int assoc = ((ucp[1] >> 4) & 0x3); if (transport && assoc && (ucp[1] & 0x80) && (*transport < 0)) *transport = (ucp[0] >> 4) & 0xf; if (0 != assoc) continue; - ip = ucp + 4; - c_set = (ucp[0] & 0xf); - desig_type = (ucp[1] & 0xf); + const unsigned char * ip = ucp + 4; + int c_set = (ucp[0] & 0xf); + int desig_type = (ucp[1] & 0xf); + int naa; switch (desig_type) { case 0: /* vendor specific */ case 1: /* T10 vendor identification */ @@ -373,7 +363,7 @@ scsi_decode_lu_dev_id(const unsigned char * b, int blen, char * s, int slen, if (have_scsi_ns) si = 0; si += snprintf(s+si, slen-si, "0x"); - for (m = 0; m < i_len; ++m) + for (int m = 0; m < i_len; ++m) si += snprintf(s+si, slen-si, "%02x", (unsigned int)ip[m]); break; case 3: /* NAA */ @@ -394,7 +384,7 @@ scsi_decode_lu_dev_id(const unsigned char * b, int blen, char * s, int slen, return -1; } si += snprintf(s+si, slen-si, "0x"); - for (m = 0; m < 8; ++m) + for (int m = 0; m < 8; ++m) si += snprintf(s+si, slen-si, "%02x", (unsigned int)ip[m]); } else if ((3 == naa ) || (5 == naa)) { /* NAA=3 Locally assigned; NAA=5 IEEE Registered */ @@ -403,7 +393,7 @@ scsi_decode_lu_dev_id(const unsigned char * b, int blen, char * s, int slen, return -1; } si += snprintf(s+si, slen-si, "0x"); - for (m = 0; m < 8; ++m) + for (int m = 0; m < 8; ++m) si += snprintf(s+si, slen-si, "%02x", (unsigned int)ip[m]); } else if (6 == naa) { /* NAA IEEE Registered extended */ if (16 != i_len) { @@ -411,7 +401,7 @@ scsi_decode_lu_dev_id(const unsigned char * b, int blen, char * s, int slen, return -1; } si += snprintf(s+si, slen-si, "0x"); - for (m = 0; m < 16; ++m) + for (int m = 0; m < 16; ++m) si += snprintf(s+si, slen-si, "%02x", (unsigned int)ip[m]); } break; @@ -461,7 +451,6 @@ scsiLogSense(scsi_device * device, int pagenum, int subpagenum, UINT8 *pBuf, UINT8 cdb[10]; UINT8 sense[32]; int pageLen; - int status, res; if (known_resp_len > bufLen) return -EIO; @@ -494,6 +483,7 @@ scsiLogSense(scsi_device * device, int pagenum, int subpagenum, UINT8 *pBuf, if (!device->scsi_pass_through(&io_hdr)) return -device->get_errno(); scsi_do_sense_disect(&io_hdr, &sinfo); + int res; if ((res = scsiSimpleSenseFilter(&sinfo))) return res; /* sanity check on response */ @@ -529,7 +519,7 @@ scsiLogSense(scsi_device * device, int pagenum, int subpagenum, UINT8 *pBuf, if (!device->scsi_pass_through(&io_hdr)) return -device->get_errno(); scsi_do_sense_disect(&io_hdr, &sinfo); - status = scsiSimpleSenseFilter(&sinfo); + int status = scsiSimpleSenseFilter(&sinfo); if (0 != status) return status; /* sanity check on response */ @@ -589,7 +579,6 @@ scsiModeSense(scsi_device * device, int pagenum, int subpagenum, int pc, struct scsi_sense_disect sinfo; UINT8 cdb[6]; UINT8 sense[32]; - int status; if ((bufLen < 0) || (bufLen > 255)) return -EINVAL; @@ -611,7 +600,7 @@ scsiModeSense(scsi_device * device, int pagenum, int subpagenum, int pc, if (!device->scsi_pass_through(&io_hdr)) return -device->get_errno(); scsi_do_sense_disect(&io_hdr, &sinfo); - status = scsiSimpleSenseFilter(&sinfo); + int status = scsiSimpleSenseFilter(&sinfo); if (SIMPLE_ERR_TRY_AGAIN == status) { if (!device->scsi_pass_through(&io_hdr)) return -device->get_errno(); @@ -687,7 +676,6 @@ scsiModeSense10(scsi_device * device, int pagenum, int subpagenum, int pc, struct scsi_sense_disect sinfo; UINT8 cdb[10]; UINT8 sense[32]; - int status; memset(&io_hdr, 0, sizeof(io_hdr)); memset(cdb, 0, sizeof(cdb)); @@ -708,7 +696,7 @@ scsiModeSense10(scsi_device * device, int pagenum, int subpagenum, int pc, if (!device->scsi_pass_through(&io_hdr)) return -device->get_errno(); scsi_do_sense_disect(&io_hdr, &sinfo); - status = scsiSimpleSenseFilter(&sinfo); + int status = scsiSimpleSenseFilter(&sinfo); if (SIMPLE_ERR_TRY_AGAIN == status) { if (!device->scsi_pass_through(&io_hdr)) return -device->get_errno(); @@ -879,8 +867,6 @@ scsiRequestSense(scsi_device * device, struct scsi_sense_disect * sense_info) UINT8 cdb[6]; UINT8 sense[32]; UINT8 buff[18]; - int len; - UINT8 resp_code; memset(&io_hdr, 0, sizeof(io_hdr)); memset(cdb, 0, sizeof(cdb)); @@ -898,13 +884,13 @@ scsiRequestSense(scsi_device * device, struct scsi_sense_disect * sense_info) if (!device->scsi_pass_through(&io_hdr)) return -device->get_errno(); if (sense_info) { - resp_code = buff[0] & 0x7f; + UINT8 resp_code = buff[0] & 0x7f; sense_info->resp_code = resp_code; sense_info->sense_key = buff[2] & 0xf; sense_info->asc = 0; sense_info->ascq = 0; if ((0x70 == resp_code) || (0x71 == resp_code)) { - len = buff[7] + 8; + int len = buff[7] + 8; if (len > 13) { sense_info->asc = buff[12]; sense_info->ascq = buff[13]; @@ -1203,7 +1189,7 @@ scsiGetSize(scsi_device * device, unsigned int * lb_sizep, int * lb_per_pb_expp) { unsigned int last_lba = 0, lb_size = 0; - int k, res; + int res; uint64_t ret_val = 0; UINT8 rc16resp[32]; @@ -1220,7 +1206,7 @@ scsiGetSize(scsi_device * device, unsigned int * lb_sizep, pout("scsiGetSize: READ CAPACITY(16) failed, res=%d\n", res); return 0; } - for (k = 0; k < 8; ++k) { + for (int k = 0; k < 8; ++k) { if (k > 0) ret_val <<= 8; ret_val |= rc16resp[k + 0]; @@ -1265,10 +1251,10 @@ scsiGetProtPBInfo(scsi_device * device, unsigned char * rc16_12_31p) int scsiModePageOffset(const UINT8 * resp, int len, int modese_len) { - int resp_len, bd_len; int offset = -1; if (resp) { + int resp_len, bd_len; if (10 == modese_len) { resp_len = (resp[0] << 8) + resp[1] + 2; bd_len = (resp[6] << 8) + resp[7]; @@ -1355,11 +1341,9 @@ scsiFetchIECmpage(scsi_device * device, struct scsi_iec_mode_page *iecp, int scsi_IsExceptionControlEnabled(const struct scsi_iec_mode_page *iecp) { - int offset; - if (iecp && iecp->gotCurrent) { - offset = scsiModePageOffset(iecp->raw_curr, sizeof(iecp->raw_curr), - iecp->modese_len); + int offset = scsiModePageOffset(iecp->raw_curr, sizeof(iecp->raw_curr), + iecp->modese_len); if (offset >= 0) return (iecp->raw_curr[offset + 2] & DEXCPT_ENABLE) ? 0 : 1; else @@ -1371,11 +1355,9 @@ scsi_IsExceptionControlEnabled(const struct scsi_iec_mode_page *iecp) int scsi_IsWarningEnabled(const struct scsi_iec_mode_page *iecp) { - int offset; - if (iecp && iecp->gotCurrent) { - offset = scsiModePageOffset(iecp->raw_curr, sizeof(iecp->raw_curr), - iecp->modese_len); + int offset = scsiModePageOffset(iecp->raw_curr, sizeof(iecp->raw_curr), + iecp->modese_len); if (offset >= 0) return (iecp->raw_curr[offset + 2] & EWASC_ENABLE) ? 1 : 0; else @@ -1403,10 +1385,9 @@ int scsiSetExceptionControlAndWarning(scsi_device * device, int enabled, const struct scsi_iec_mode_page *iecp) { - int k, offset, resp_len; + int offset, resp_len; int err = 0; UINT8 rout[SCSI_IECMP_RAW_LEN]; - int sp, eCEnabled, wEnabled; if ((! iecp) || (! iecp->gotCurrent)) return -EINVAL; @@ -1423,7 +1404,7 @@ scsiSetExceptionControlAndWarning(scsi_device * device, int enabled, resp_len = rout[0] + 1; rout[2] &= 0xef; } - sp = (rout[offset] & 0x80) ? 1 : 0; /* PS bit becomes 'SELECT's SP bit */ + int sp = (rout[offset] & 0x80) ? 1 : 0; /* PS bit becomes 'SELECT's SP bit */ if (enabled) { rout[offset + 2] = SCSI_IEC_MP_BYTE2_ENABLED; if (scsi_debugmode > 2) @@ -1442,7 +1423,7 @@ scsiSetExceptionControlAndWarning(scsi_device * device, int enabled, rout[offset + 2] = chg2 ? (rout[offset + 2] & chg2) : iecp->raw_curr[offset + 2]; - for (k = 3; k < 12; ++k) { + for (int k = 3; k < 12; ++k) { if (0 == iecp->raw_chg[offset + k]) rout[offset + k] = iecp->raw_curr[offset + k]; } @@ -1453,8 +1434,8 @@ scsiSetExceptionControlAndWarning(scsi_device * device, int enabled, return 0; } } else { /* disabling Exception Control and (temperature) Warnings */ - eCEnabled = (rout[offset + 2] & DEXCPT_ENABLE) ? 0 : 1; - wEnabled = (rout[offset + 2] & EWASC_ENABLE) ? 1 : 0; + int eCEnabled = (rout[offset + 2] & DEXCPT_ENABLE) ? 0 : 1; + int wEnabled = (rout[offset + 2] & EWASC_ENABLE) ? 1 : 0; if ((! eCEnabled) && (! wEnabled)) { if (scsi_debugmode > 0) pout("scsiSetExceptionControlAndWarning: already disabled\n"); @@ -1507,7 +1488,6 @@ scsiCheckIE(scsi_device * device, int hasIELogPage, int hasTempLogPage, struct scsi_sense_disect sense_info; int err; int temperatureSet = 0; - unsigned short pagesize; UINT8 currTemp, trTemp; *asc = 0; @@ -1523,7 +1503,7 @@ scsiCheckIE(scsi_device * device, int hasIELogPage, int hasTempLogPage, return err; } // pull out page size from response, don't forget to add 4 - pagesize = (unsigned short) ((tBuf[2] << 8) | tBuf[3]) + 4; + unsigned short pagesize = (unsigned short) ((tBuf[2] << 8) | tBuf[3]) + 4; if ((pagesize < 4) || tBuf[4] || tBuf[5]) { pout("Log Sense failed, IE page, bad parameter code or length\n"); return SIMPLE_ERR_BAD_PARAM; @@ -2157,7 +2137,7 @@ int scsiFetchExtendedSelfTestTime(scsi_device * device, int * durationSec, int modese_len) { - int err, offset, res; + int err, offset; UINT8 buff[64]; memset(buff, 0, sizeof(buff)); @@ -2183,7 +2163,7 @@ scsiFetchExtendedSelfTestTime(scsi_device * device, int * durationSec, if (offset < 0) return -EINVAL; if (buff[offset + 1] >= 0xa) { - res = (buff[offset + 10] << 8) | buff[offset + 11]; + int res = (buff[offset + 10] << 8) | buff[offset + 11]; *durationSec = res; return 0; } @@ -2194,17 +2174,13 @@ scsiFetchExtendedSelfTestTime(scsi_device * device, int * durationSec, void scsiDecodeErrCounterPage(unsigned char * resp, struct scsiErrorCounter *ecp) { - int k, j, num, pl, pc; - unsigned char * ucp; - unsigned char * xp; - uint64_t * ullp; - memset(ecp, 0, sizeof(*ecp)); - num = (resp[2] << 8) | resp[3]; - ucp = &resp[0] + 4; + int num = (resp[2] << 8) | resp[3]; + unsigned char * ucp = &resp[0] + 4; while (num > 3) { - pc = (ucp[0] << 8) | ucp[1]; - pl = ucp[3] + 4; + int pc = (ucp[0] << 8) | ucp[1]; + int pl = ucp[3] + 4; + uint64_t * ullp; switch (pc) { case 0: case 1: @@ -2221,14 +2197,14 @@ scsiDecodeErrCounterPage(unsigned char * resp, struct scsiErrorCounter *ecp) ullp = &ecp->counter[7]; break; } - k = pl - 4; - xp = ucp + 4; + int k = pl - 4; + unsigned char * xp = ucp + 4; if (k > (int)sizeof(*ullp)) { xp += (k - sizeof(*ullp)); k = sizeof(*ullp); } *ullp = 0; - for (j = 0; j < k; ++j) { + for (int j = 0; j < k; ++j) { if (j > 0) *ullp <<= 8; *ullp |= xp[j]; @@ -2242,17 +2218,15 @@ void scsiDecodeNonMediumErrPage(unsigned char *resp, struct scsiNonMediumError *nmep) { - int k, j, num, pl, pc, szof; - unsigned char * ucp; - unsigned char * xp; - memset(nmep, 0, sizeof(*nmep)); - num = (resp[2] << 8) | resp[3]; - ucp = &resp[0] + 4; - szof = sizeof(nmep->counterPC0); + int num = (resp[2] << 8) | resp[3]; + unsigned char * ucp = &resp[0] + 4; + int szof = sizeof(nmep->counterPC0); while (num > 3) { - pc = (ucp[0] << 8) | ucp[1]; - pl = ucp[3] + 4; + int pc = (ucp[0] << 8) | ucp[1]; + int pl = ucp[3] + 4; + int k; + unsigned char * xp; switch (pc) { case 0: nmep->gotPC0 = 1; @@ -2263,7 +2237,7 @@ scsiDecodeNonMediumErrPage(unsigned char *resp, k = szof; } nmep->counterPC0 = 0; - for (j = 0; j < k; ++j) { + for (int j = 0; j < k; ++j) { if (j > 0) nmep->counterPC0 <<= 8; nmep->counterPC0 |= xp[j]; @@ -2278,7 +2252,7 @@ scsiDecodeNonMediumErrPage(unsigned char *resp, k = szof; } nmep->counterTFE_H = 0; - for (j = 0; j < k; ++j) { + for (int j = 0; j < k; ++j) { if (j > 0) nmep->counterTFE_H <<= 8; nmep->counterTFE_H |= xp[j]; @@ -2293,7 +2267,7 @@ scsiDecodeNonMediumErrPage(unsigned char *resp, k = szof; } nmep->counterPE_H = 0; - for (j = 0; j < k; ++j) { + for (int j = 0; j < k; ++j) { if (j > 0) nmep->counterPE_H <<= 8; nmep->counterPE_H |= xp[j]; @@ -2319,7 +2293,7 @@ scsiDecodeNonMediumErrPage(unsigned char *resp, int scsiCountFailedSelfTests(scsi_device * fd, int noisy) { - int num, k, n, err, res, fails, fail_hour; + int num, k, err, fails, fail_hour; UINT8 * ucp; unsigned char resp[LOG_RESP_SELF_TEST_LEN]; @@ -2348,13 +2322,13 @@ scsiCountFailedSelfTests(scsi_device * fd, int noisy) for (k = 0, ucp = resp + 4; k < 20; ++k, ucp += 20 ) { // timestamp in power-on hours (or zero if test in progress) - n = (ucp[6] << 8) | ucp[7]; + int n = (ucp[6] << 8) | ucp[7]; // The spec says "all 20 bytes will be zero if no test" but // DG has found otherwise. So this is a heuristic. if ((0 == n) && (0 == ucp[4])) break; - res = ucp[4] & 0xf; + int res = ucp[4] & 0xf; if ((res > 2) && (res < 8)) { fails++; if (1 == fails) @@ -2433,7 +2407,7 @@ int scsiGetRPM(scsi_device * device, int modese_len, int * form_factorp, int * haw_zbcp) { - int err, offset, speed; + int err, offset; UINT8 buff[64]; int pc = MPAGE_CONTROL_DEFAULT; @@ -2441,7 +2415,7 @@ scsiGetRPM(scsi_device * device, int modese_len, int * form_factorp, if ((0 == scsiInquiryVpd(device, SCSI_VPD_BLOCK_DEVICE_CHARACTERISTICS, buff, sizeof(buff))) && (((buff[2] << 8) + buff[3]) > 2)) { - speed = (buff[4] << 8) + buff[5]; + int speed = (buff[4] << 8) + buff[5]; if (form_factorp) *form_factorp = buff[7] & 0xf; if (haw_zbcp) @@ -2687,7 +2661,7 @@ const unsigned char * sg_scsi_sense_desc_find(const unsigned char * sensep, int sense_len, int desc_type) { - int add_sen_len, add_len, desc_len, k; + int add_sen_len; const unsigned char * descp; if ((sense_len < 8) || (0 == (add_sen_len = sensep[7]))) @@ -2697,9 +2671,9 @@ sg_scsi_sense_desc_find(const unsigned char * sensep, int sense_len, add_sen_len = (add_sen_len < (sense_len - 8)) ? add_sen_len : (sense_len - 8); descp = &sensep[8]; - for (desc_len = 0, k = 0; k < add_sen_len; k += desc_len) { + for (int desc_len = 0, k = 0; k < add_sen_len; k += desc_len) { descp += desc_len; - add_len = (k < (add_sen_len - 1)) ? descp[1]: -1; + int add_len = (k < (add_sen_len - 1)) ? descp[1]: -1; desc_len = add_len + 2; if (descp[0] == desc_type) return descp; diff --git a/scsicmds.h b/scsicmds.h index 30a5c97..65402fa 100644 --- a/scsicmds.h +++ b/scsicmds.h @@ -1,12 +1,10 @@ /* * scsicmds.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2002-8 Bruce Allen * Copyright (C) 2000 Michael Cornwell - * - * Additional SCSI work: * Copyright (C) 2003-15 Douglas Gilbert * * This program is free software; you can redistribute it and/or modify @@ -32,7 +30,7 @@ #ifndef SCSICMDS_H_ #define SCSICMDS_H_ -#define SCSICMDS_H_CVSID "$Id: scsicmds.h 4081 2015-05-10 16:42:50Z chrfranke $\n" +#define SCSICMDS_H_CVSID "$Id: scsicmds.h 4152 2015-10-17 16:08:21Z chrfranke $\n" #include #include @@ -322,7 +320,7 @@ class scsi_device; class supported_vpd_pages { public: - supported_vpd_pages(scsi_device * device); + explicit supported_vpd_pages(scsi_device * device); ~supported_vpd_pages() { num_valid = 0; } bool is_supported(int vpd_page_num) const; diff --git a/scsiprint.cpp b/scsiprint.cpp index 5e4cb4d..47f5a36 100644 --- a/scsiprint.cpp +++ b/scsiprint.cpp @@ -1,13 +1,11 @@ /* * scsiprint.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * - * Copyright (C) 2002-11 Bruce Allen + * Copyright (C) 2002-11 Bruce Allen * Copyright (C) 2000 Michael Cornwell - * - * Additional SCSI work: - * Copyright (C) 2003-13 Douglas Gilbert + * Copyright (C) 2003-15 Douglas Gilbert * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -42,7 +40,7 @@ #define GBUF_SIZE 65535 -const char * scsiprint_c_cvsid = "$Id: scsiprint.cpp 4040 2015-03-10 22:30:44Z dpgilbert $" +const char * scsiprint_c_cvsid = "$Id: scsiprint.cpp 4189 2015-12-16 14:53:41Z dpgilbert $" SCSIPRINT_H_CVSID; @@ -244,8 +242,7 @@ scsiGetTapeAlertsData(scsi_device * device, int peripheral_type) static void scsiGetStartStopData(scsi_device * device) { - UINT32 u; - int err, len, k, extra, pc; + int err, len, k, extra; unsigned char * ucp; if ((err = scsiLogSense(device, STARTSTOP_CYCLE_COUNTER_LPAGE, 0, gBuf, @@ -271,7 +268,8 @@ scsiGetStartStopData(scsi_device * device) return; } extra = ucp[3] + 4; - pc = (ucp[0] << 8) + ucp[1]; + int pc = (ucp[0] << 8) + ucp[1]; + UINT32 u; switch (pc) { case 1: if (10 == extra) @@ -321,7 +319,7 @@ scsiGetStartStopData(scsi_device * device) static void scsiPrintGrownDefectListLen(scsi_device * device) { - int err, dl_format, got_rd12, generation; + int err, dl_format, got_rd12; unsigned int dl_len, div; memset(gBuf, 0, 8); @@ -353,7 +351,7 @@ scsiPrintGrownDefectListLen(scsi_device * device) got_rd12 = 1; if (got_rd12) { - generation = (gBuf[2] << 8) + gBuf[3]; + int generation = (gBuf[2] << 8) + gBuf[3]; if ((generation > 1) && (scsi_debugmode > 0)) { print_on(); pout("Read defect list (12): generation=%d\n", generation); @@ -405,9 +403,8 @@ scsiPrintGrownDefectListLen(scsi_device * device) static void scsiPrintSeagateCacheLPage(scsi_device * device) { - int k, j, num, pl, pc, err, len; + int num, pl, pc, err, len; unsigned char * ucp; - unsigned char * xp; uint64_t ull; if ((err = scsiLogSense(device, SEAGATE_CACHE_LPAGE, 0, gBuf, @@ -460,14 +457,14 @@ scsiPrintSeagateCacheLPage(scsi_device * device) "> segment size"); break; default: pout(" Unknown Seagate parameter code [0x%x]", pc); break; } - k = pl - 4; - xp = ucp + 4; + int k = pl - 4; + unsigned char * xp = ucp + 4; if (k > (int)sizeof(ull)) { xp += (k - (int)sizeof(ull)); k = (int)sizeof(ull); } ull = 0; - for (j = 0; j < k; ++j) { + for (int j = 0; j < k; ++j) { if (j > 0) ull <<= 8; ull |= xp[j]; @@ -482,9 +479,8 @@ scsiPrintSeagateCacheLPage(scsi_device * device) static void scsiPrintSeagateFactoryLPage(scsi_device * device) { - int k, j, num, pl, pc, len, err, good, bad; + int num, pl, pc, len, err, good, bad; unsigned char * ucp; - unsigned char * xp; uint64_t ull; if ((err = scsiLogSense(device, SEAGATE_FACTORY_LPAGE, 0, gBuf, @@ -552,14 +548,14 @@ scsiPrintSeagateFactoryLPage(scsi_device * device) break; } if (good) { - k = pl - 4; - xp = ucp + 4; + int k = pl - 4; + unsigned char * xp = ucp + 4; if (k > (int)sizeof(ull)) { xp += (k - (int)sizeof(ull)); k = (int)sizeof(ull); } ull = 0; - for (j = 0; j < k; ++j) { + for (int j = 0; j < k; ++j) { if (j > 0) ull <<= 8; ull |= xp[j]; @@ -580,10 +576,7 @@ scsiPrintErrorCounterLog(scsi_device * device) { struct scsiErrorCounter errCounterArr[3]; struct scsiErrorCounter * ecp; - struct scsiNonMediumError nme; int found[3] = {0, 0, 0}; - const char * pageNames[3] = {"read: ", "write: ", "verify: "}; - double processed_gb; if (gReadECounterLPage && (0 == scsiLogSense(device, READ_ERROR_COUNTER_LPAGE, 0, gBuf, LOG_RESP_LEN, 0))) { @@ -618,10 +611,11 @@ scsiPrintErrorCounterLog(scsi_device * device) if (! found[k]) continue; ecp = &errCounterArr[k]; + static const char * const pageNames[3] = {"read: ", "write: ", "verify: "}; pout("%s%8" PRIu64 " %8" PRIu64 " %8" PRIu64 " %8" PRIu64 " %8" PRIu64, pageNames[k], ecp->counter[0], ecp->counter[1], ecp->counter[2], ecp->counter[3], ecp->counter[4]); - processed_gb = ecp->counter[5] / 1000000000.0; + double processed_gb = ecp->counter[5] / 1000000000.0; pout(" %12.3f %8" PRIu64 "\n", processed_gb, ecp->counter[6]); } } @@ -629,6 +623,7 @@ scsiPrintErrorCounterLog(scsi_device * device) pout("Error Counter logging not supported\n"); if (gNonMediumELPage && (0 == scsiLogSense(device, NON_MEDIUM_ERROR_LPAGE, 0, gBuf, LOG_RESP_LEN, 0))) { + struct scsiNonMediumError nme; scsiDecodeNonMediumErrPage(gBuf, &nme); if (nme.gotPC0) pout("\nNon-medium error count: %8" PRIu64 "\n", nme.counterPC0); @@ -720,7 +715,7 @@ static const char * self_test_result[] = { static int scsiPrintSelfTest(scsi_device * device) { - int num, k, n, res, err, durationSec; + int num, k, err, durationSec; int noheader = 1; int retval = 0; UINT8 * ucp; @@ -762,7 +757,7 @@ scsiPrintSelfTest(scsi_device * device) int i; // timestamp in power-on hours (or zero if test in progress) - n = (ucp[6] << 8) | ucp[7]; + int n = (ucp[6] << 8) | ucp[7]; // The spec says "all 20 bytes will be zero if no test" but // DG has found otherwise. So this is a heuristic. @@ -785,6 +780,7 @@ scsiPrintSelfTest(scsi_device * device) // check the self-test result nibble, using the self-test results // field table from T10/1416-D (SPC-3) Rev. 23, section 7.2.10: + int res; switch ((res = ucp[4] & 0xf)) { case 0x3: // an unknown error occurred while the device server @@ -903,7 +899,7 @@ static const char * reassign_status[] = { static int scsiPrintBackgroundResults(scsi_device * device) { - int num, j, m, err, pc, pl, truncated; + int num, j, m, err, truncated; int noheader = 1; int firstresult = 1; int retval = 0; @@ -937,9 +933,9 @@ scsiPrintBackgroundResults(scsi_device * device) ucp = gBuf + 4; num -= 4; while (num > 3) { - pc = (ucp[0] << 8) | ucp[1]; + int pc = (ucp[0] << 8) | ucp[1]; // pcb = ucp[2]; - pl = ucp[3] + 4; + int pl = ucp[3] + 4; switch (pc) { case 0: if (noheader) { @@ -1012,7 +1008,7 @@ scsiPrintBackgroundResults(scsi_device * device) static int scsiPrintSSMedia(scsi_device * device) { - int num, err, pc, pl, truncated; + int num, err, truncated; int retval = 0; UINT8 * ucp; @@ -1043,9 +1039,9 @@ scsiPrintSSMedia(scsi_device * device) ucp = gBuf + 4; num -= 4; while (num > 3) { - pc = (ucp[0] << 8) | ucp[1]; + int pc = (ucp[0] << 8) | ucp[1]; // pcb = ucp[2]; - pl = ucp[3] + 4; + int pl = ucp[3] + 4; switch (pc) { case 1: if (pl < 8) { @@ -1202,7 +1198,6 @@ show_sas_port_param(unsigned char * ucp, int param_len) int j, m, n, nphys, t, sz, spld_len; unsigned char * vcp; uint64_t ull; - unsigned int ui; char s[64]; sz = sizeof(s); @@ -1299,6 +1294,7 @@ show_sas_port_param(unsigned char * ucp, int param_len) } pout(" attached SAS address = 0x%" PRIx64 "\n", ull); pout(" attached phy identifier = %d\n", vcp[24]); + unsigned int ui; ui = (vcp[32] << 24) | (vcp[33] << 16) | (vcp[34] << 8) | vcp[35]; pout(" Invalid DWORD count = %u\n", ui); ui = (vcp[36] << 24) | (vcp[37] << 16) | (vcp[38] << 8) | vcp[39]; @@ -1308,15 +1304,16 @@ show_sas_port_param(unsigned char * ucp, int param_len) ui = (vcp[44] << 24) | (vcp[45] << 16) | (vcp[46] << 8) | vcp[47]; pout(" Phy reset problem = %u\n", ui); if (spld_len > 51) { - int num_ped, peis; + int num_ped; unsigned char * xcp; - unsigned int pvdt; num_ped = vcp[51]; if (num_ped > 0) pout(" Phy event descriptors:\n"); xcp = vcp + 52; for (m = 0; m < (num_ped * 12); m += 12, xcp += 12) { + int peis; + unsigned int pvdt; peis = xcp[3]; ui = (xcp[4] << 24) | (xcp[5] << 16) | (xcp[6] << 8) | xcp[7]; @@ -1332,12 +1329,12 @@ show_sas_port_param(unsigned char * ucp, int param_len) static int show_protocol_specific_page(unsigned char * resp, int len) { - int k, num, param_len; + int k, num; unsigned char * ucp; num = len - 4; for (k = 0, ucp = resp + 4; k < num; ) { - param_len = ucp[3] + 4; + int param_len = ucp[3] + 4; if (6 != (0xf & ucp[4])) return 0; /* only decode SAS log page */ if (0 == k) @@ -1453,10 +1450,9 @@ scsiGetDriveInfo(scsi_device * device, UINT8 * peripheral_type, bool all) { char timedatetz[DATEANDEPOCHLEN]; struct scsi_iec_mode_page iec; - int err, iec_err, len, req_len, avail_len, n, scsi_version; - int is_tape = 0; + int err, iec_err, len, req_len, avail_len, scsi_version; + bool is_tape = false; int peri_dt = 0; - int returnval = 0; int transport = -1; int form_factor = 0; int haw_zbc = 0; @@ -1482,8 +1478,10 @@ scsiGetDriveInfo(scsi_device * device, UINT8 * peripheral_type, bool all) avail_len = gBuf[4] + 5; len = (avail_len < req_len) ? avail_len : req_len; peri_dt = gBuf[0] & 0x1f; - if (peripheral_type) - *peripheral_type = peri_dt; + *peripheral_type = peri_dt; + if ((SCSI_PT_SEQUENTIAL_ACCESS == peri_dt) || + (SCSI_PT_MEDIUM_CHANGER == peri_dt)) + is_tape = true; if (len < 36) { print_on(); @@ -1523,16 +1521,15 @@ scsiGetDriveInfo(scsi_device * device, UINT8 * peripheral_type, bool all) protect = gBuf[5] & 0x1; /* from and including SPC-3 */ - if (! is_tape) { /* only do this for disks */ + if (! is_tape) { /* assume disk if not tape drive (or tape changer) */ unsigned int lb_size = 0; unsigned char lb_prov_resp[8]; - char cap_str[64]; - char si_str[64]; char lb_str[16]; int lb_per_pb_exp = 0; uint64_t capacity = scsiGetSize(device, &lb_size, &lb_per_pb_exp); if (capacity) { + char cap_str[64], si_str[64]; format_with_thousands_sep(cap_str, sizeof(cap_str), capacity); format_capacity(si_str, sizeof(si_str), capacity); pout("User Capacity: %s bytes [%s]\n", cap_str, si_str); @@ -1550,7 +1547,7 @@ scsiGetDriveInfo(scsi_device * device, UINT8 * peripheral_type, bool all) snprintf(lb_str, sizeof(lb_str) - 1, "%u", (lb_size * (1 << lb_per_pb_exp))); pout("Physical block size: %s bytes\n", lb_str); - n = ((rc16_12[2] & 0x3f) << 8) + rc16_12[3]; + int n = ((rc16_12[2] & 0x3f) << 8) + rc16_12[3]; if (n > 0) // not common so cut the clutter pout("Lowest aligned LBA: %d\n", n); } @@ -1711,9 +1708,6 @@ scsiGetDriveInfo(scsi_device * device, UINT8 * peripheral_type, bool all) dateandtimezone(timedatetz); pout("Local Time is: %s\n", timedatetz); - if ((SCSI_PT_SEQUENTIAL_ACCESS == *peripheral_type) || - (SCSI_PT_MEDIUM_CHANGER == *peripheral_type)) - is_tape = 1; // See if unit accepts SCSI commmands from us if ((err = scsiTestUnitReady(device))) { if (SIMPLE_ERR_NOT_READY == err) { @@ -1736,6 +1730,7 @@ scsiGetDriveInfo(scsi_device * device, UINT8 * peripheral_type, bool all) pout("device Test Unit Ready [%s]\n", scsiErrString(err)); print_off(); } + int returnval = 0; // TODO: exit with FAILID if failuretest returns failuretest(MANDATORY_CMD, returnval|=FAILID); } @@ -1865,6 +1860,8 @@ scsiPrintMain(scsi_device * device, const scsi_print_options & options) int returnval = 0; int res, durationSec; struct scsi_sense_disect sense_info; + bool is_disk; + bool is_tape; bool any_output = options.drive_info; @@ -1882,115 +1879,108 @@ scsiPrintMain(scsi_device * device, const scsi_print_options & options) failuretest(MANDATORY_CMD, returnval |= FAILID); any_output = true; } + is_disk = (SCSI_PT_DIRECT_ACCESS == peripheral_type); + is_tape = ((SCSI_PT_SEQUENTIAL_ACCESS == peripheral_type) || + (SCSI_PT_MEDIUM_CHANGER == peripheral_type)); + + short int wce = -1, rcd = -1; + // Print read look-ahead status for disks + if (options.get_rcd || options.get_wce) { + if (is_disk) { + res = scsiGetSetCache(device, modese_len, &wce, &rcd); + if (options.get_rcd) + pout("Read Cache is: %s\n", + res ? "Unavailable" : // error + rcd ? "Disabled" : "Enabled"); + if (options.get_wce) + pout("Writeback Cache is: %s\n", + res ? "Unavailable" : // error + !wce ? "Disabled" : "Enabled"); + } + } else + any_output = true; - // Print read look-ahead status for disks - short int wce = -1, rcd = -1; - if (options.get_rcd || options.get_wce) { - if (SCSI_PT_DIRECT_ACCESS == peripheral_type) - res = scsiGetSetCache(device, modese_len, &wce, &rcd); - else - res = -1; // fetch for disks only - any_output = true; - } - - if (options.get_rcd) { - pout("Read Cache is: %s\n", - res ? "Unavailable" : // error - rcd ? "Disabled" : "Enabled"); - } - - if (options.get_wce) { - pout("Writeback Cache is: %s\n", - res ? "Unavailable" : // error - !wce ? "Disabled" : "Enabled"); - } - if (options.drive_info) - pout("\n"); - - // START OF THE ENABLE/DISABLE SECTION OF THE CODE - if ( options.smart_disable || options.smart_enable - || options.smart_auto_save_disable || options.smart_auto_save_enable) - pout("=== START OF ENABLE/DISABLE COMMANDS SECTION ===\n"); + if (options.drive_info) + pout("\n"); + + // START OF THE ENABLE/DISABLE SECTION OF THE CODE + if (options.smart_disable || options.smart_enable || + options.smart_auto_save_disable || options.smart_auto_save_enable) + pout("=== START OF ENABLE/DISABLE COMMANDS SECTION ===\n"); if (options.smart_enable) { if (scsiSmartEnable(device)) failuretest(MANDATORY_CMD, returnval |= FAILSMART); - any_output = true; + any_output = true; } if (options.smart_disable) { if (scsiSmartDisable(device)) failuretest(MANDATORY_CMD,returnval |= FAILSMART); - any_output = true; + any_output = true; } if (options.smart_auto_save_enable) { - if (scsiSetControlGLTSD(device, 0, modese_len)) { - pout("Enable autosave (clear GLTSD bit) failed\n"); - failuretest(OPTIONAL_CMD,returnval |= FAILSMART); - } - else { - pout("Autosave enabled (GLTSD bit set).\n"); - } - any_output = true; + if (scsiSetControlGLTSD(device, 0, modese_len)) { + pout("Enable autosave (clear GLTSD bit) failed\n"); + failuretest(OPTIONAL_CMD,returnval |= FAILSMART); + } else + pout("Autosave enabled (GLTSD bit cleared).\n"); + any_output = true; } // Enable/Disable write cache - if (options.set_wce && SCSI_PT_DIRECT_ACCESS == peripheral_type) { - short int enable = wce = (options.set_wce > 0); - rcd = -1; - if (scsiGetSetCache(device, modese_len, &wce, &rcd)) { - pout("Write cache %sable failed: %s\n", (enable ? "en" : "dis"), - device->get_errmsg()); - failuretest(OPTIONAL_CMD,returnval |= FAILSMART); - } - else - pout("Write cache %sabled\n", (enable ? "en" : "dis")); - any_output = true; + if (options.set_wce && is_disk) { + short int enable = wce = (options.set_wce > 0); + + rcd = -1; + if (scsiGetSetCache(device, modese_len, &wce, &rcd)) { + pout("Write cache %sable failed: %s\n", (enable ? "en" : "dis"), + device->get_errmsg()); + failuretest(OPTIONAL_CMD,returnval |= FAILSMART); + } else + pout("Write cache %sabled\n", (enable ? "en" : "dis")); + any_output = true; } // Enable/Disable read cache - if (options.set_rcd && SCSI_PT_DIRECT_ACCESS == peripheral_type) { - short int enable = (options.set_rcd > 0); - rcd = !enable; - wce = -1; - if (scsiGetSetCache(device, modese_len, &wce, &rcd)) { - pout("Read cache %sable failed: %s\n", (enable ? "en" : "dis"), + if (options.set_rcd && is_disk) { + short int enable = (options.set_rcd > 0); + + rcd = !enable; + wce = -1; + if (scsiGetSetCache(device, modese_len, &wce, &rcd)) { + pout("Read cache %sable failed: %s\n", (enable ? "en" : "dis"), device->get_errmsg()); - failuretest(OPTIONAL_CMD,returnval |= FAILSMART); - } - else - pout("Read cache %sabled\n", (enable ? "en" : "dis")); - any_output = true; + failuretest(OPTIONAL_CMD,returnval |= FAILSMART); + } else + pout("Read cache %sabled\n", (enable ? "en" : "dis")); + any_output = true; } if (options.smart_auto_save_disable) { - if (scsiSetControlGLTSD(device, 1, modese_len)) { - pout("Disable autosave (set GLTSD bit) failed\n"); - failuretest(OPTIONAL_CMD,returnval |= FAILSMART); - } - else { - pout("Autosave disabled (GLTSD bit cleared).\n"); - } - any_output = true; - } - if ( options.smart_disable || options.smart_enable - || options.smart_auto_save_disable || options.smart_auto_save_enable) - pout("\n"); // END OF THE ENABLE/DISABLE SECTION OF THE CODE + if (scsiSetControlGLTSD(device, 1, modese_len)) { + pout("Disable autosave (set GLTSD bit) failed\n"); + failuretest(OPTIONAL_CMD,returnval |= FAILSMART); + } else + pout("Autosave disabled (GLTSD bit set).\n"); + any_output = true; + } + if (options.smart_disable || options.smart_enable || + options.smart_auto_save_disable || options.smart_auto_save_enable) + pout("\n"); // END OF THE ENABLE/DISABLE SECTION OF THE CODE // START OF READ-ONLY OPTIONS APART FROM -V and -i - if ( options.smart_check_status || options.smart_ss_media_log - || options.smart_vendor_attrib || options.smart_error_log - || options.smart_selftest_log || options.smart_vendor_attrib - || options.smart_background_log || options.sasphy - ) - pout("=== START OF READ SMART DATA SECTION ===\n"); + if (options.smart_check_status || options.smart_ss_media_log || + options.smart_vendor_attrib || options.smart_error_log || + options.smart_selftest_log || options.smart_background_log || + options.sasphy) + pout("=== START OF READ SMART DATA SECTION ===\n"); if (options.smart_check_status) { scsiGetSupportedLogPages(device); checkedSupportedLogPages = 1; - if ((SCSI_PT_SEQUENTIAL_ACCESS == peripheral_type) || - (SCSI_PT_MEDIUM_CHANGER == peripheral_type)) { /* tape device */ + if (is_tape) { if (gTapeAlertsLPage) { if (options.drive_info) pout("TapeAlert Supported\n"); @@ -2010,7 +2000,7 @@ scsiPrintMain(scsi_device * device, const scsi_print_options & options) any_output = true; } - if (options.smart_ss_media_log) { + if (is_disk && options.smart_ss_media_log) { if (! checkedSupportedLogPages) scsiGetSupportedLogPages(device); res = 0; @@ -2023,12 +2013,11 @@ scsiPrintMain(scsi_device * device, const scsi_print_options & options) if (options.smart_vendor_attrib) { if (! checkedSupportedLogPages) scsiGetSupportedLogPages(device); - if (gTempLPage) { + if (gTempLPage) scsiPrintTemp(device); - } if (gStartStopLPage) scsiGetStartStopData(device); - if (SCSI_PT_DIRECT_ACCESS == peripheral_type) { + if (is_disk) { scsiPrintGrownDefectListLen(device); if (gSeagateCacheLPage) scsiPrintSeagateCacheLPage(device); @@ -2088,21 +2077,19 @@ scsiPrintMain(scsi_device * device, const scsi_print_options & options) } // check if another test is running if (options.smart_short_selftest || options.smart_extend_selftest) { - if (!scsiRequestSense(device, &sense_info) && + if (!scsiRequestSense(device, &sense_info) && (sense_info.asc == 0x04 && sense_info.ascq == 0x09)) { - if (!options.smart_selftest_force) { - pout("Can't start self-test without aborting current test"); - if (sense_info.progress != -1) { - pout(" (%d%% remaining)", - 100 - sense_info.progress * 100 / 65535); - } - pout(",\nadd '-t force' option to override, or run 'smartctl -X' " - "to abort test.\n"); - return -1; - } - else - scsiSmartSelfTestAbort(device); - } + if (!options.smart_selftest_force) { + pout("Can't start self-test without aborting current test"); + if (sense_info.progress != -1) + pout(" (%d%% remaining)", + 100 - sense_info.progress * 100 / 65535); + pout(",\nadd '-t force' option to override, or run " + "'smartctl -X' to abort test.\n"); + return -1; + } else + scsiSmartSelfTestAbort(device); + } } if (options.smart_short_selftest) { if (scsiSmartShortSelfTest(device)) @@ -2145,8 +2132,8 @@ scsiPrintMain(scsi_device * device, const scsi_print_options & options) } if (!any_output) - pout("SCSI device successfully opened\n\n" - "Use 'smartctl -a' (or '-x') to print SMART (and more) information\n\n"); + pout("SCSI device successfully opened\n\nUse 'smartctl -a' (or '-x') " + "to print SMART (and more) information\n\n"); return returnval; } diff --git a/scsiprint.h b/scsiprint.h index fad594d..29632ad 100644 --- a/scsiprint.h +++ b/scsiprint.h @@ -1,7 +1,7 @@ /* * scsiprint.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2002-9 Bruce Allen * Copyright (C) 2000 Michael Cornwell @@ -29,7 +29,7 @@ #ifndef SCSI_PRINT_H_ #define SCSI_PRINT_H_ -#define SCSIPRINT_H_CVSID "$Id: scsiprint.h 3776 2013-02-17 04:25:42Z dpgilbert $\n" +#define SCSIPRINT_H_CVSID "$Id: scsiprint.h 4120 2015-08-27 16:12:21Z samm2 $\n" // Options for scsiPrintMain struct scsi_print_options diff --git a/smartctl.8.in b/smartctl.8.in index b9bf574..108445c 100644 --- a/smartctl.8.in +++ b/smartctl.8.in @@ -2,7 +2,7 @@ Copyright (C) 2002-10 Bruce Allen Copyright (C) 2004-15 Christian Franke -$Id: smartctl.8.in 4099 2015-05-30 17:32:13Z chrfranke $ +$Id: smartctl.8.in 4120 2015-08-27 16:12:21Z samm2 $ This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -2233,7 +2233,7 @@ Alternatively send the info to the smartmontools support mailing list: .SH REFERENCES Please see the following web site for more info: -\fBhttp://smartmontools.sourceforge.net/\fP +\fBhttp://www.smartmontools.org/\fP An introductory article about smartmontools is \fIMonitoring Hard Disks with SMART\fP, by Bruce Allen, Linux Journal, January 2004, @@ -2256,4 +2256,4 @@ Links to these and other documents may be found on the Links page of the .SH PACKAGE VERSION CURRENT_SVN_VERSION CURRENT_SVN_DATE CURRENT_SVN_REV .br -$Id: smartctl.8.in 4099 2015-05-30 17:32:13Z chrfranke $ +$Id: smartctl.8.in 4120 2015-08-27 16:12:21Z samm2 $ diff --git a/smartctl.cpp b/smartctl.cpp index 53ee298..e211639 100644 --- a/smartctl.cpp +++ b/smartctl.cpp @@ -1,7 +1,7 @@ /* * smartctl.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * * Copyright (C) 2002-11 Bruce Allen * Copyright (C) 2008-15 Christian Franke @@ -51,7 +51,7 @@ #include "smartctl.h" #include "utility.h" -const char * smartctl_cpp_cvsid = "$Id: smartctl.cpp 4080 2015-05-05 20:31:22Z chrfranke $" +const char * smartctl_cpp_cvsid = "$Id: smartctl.cpp 4162 2015-10-31 16:36:16Z chrfranke $" CONFIG_H_CVSID SMARTCTL_H_CVSID; // Globals to control printing @@ -313,7 +313,7 @@ static const char * parse_options(int argc, char** argv, opterr=optopt=0; const char * type = 0; // set to -d optarg - bool no_defaultdb = false; // set true on '-B FILE' + bool use_default_db = true; // set false on '-B FILE' bool output_format_set = false; // set true on '-f FORMAT' int scan = 0; // set by --scan, --scan-open bool badarg = false, captive = false; @@ -665,7 +665,7 @@ static const char * parse_options(int argc, char** argv, } else if (!strcmp(optarg, "show")) { ataopts.show_presets = true; } else if (!strcmp(optarg, "showall")) { - if (!no_defaultdb && !read_default_drive_databases()) + if (!init_drive_database(use_default_db)) EXIT(FAILCMD); if (optind < argc) { // -P showall MODEL [FIRMWARE] int cnt = showmatchingpresets(argv[optind], (optind+1 * Copyright (C) 2008-10 Christian Franke @@ -26,7 +26,7 @@ #ifndef SMARTCTL_H_ #define SMARTCTL_H_ -#define SMARTCTL_H_CVSID "$Id: smartctl.h 3727 2012-12-13 17:23:06Z samm2 $\n" +#define SMARTCTL_H_CVSID "$Id: smartctl.h 4120 2015-08-27 16:12:21Z samm2 $\n" // Return codes (bitmask) diff --git a/smartd.8.in b/smartd.8.in index 8dd7ef4..38fcfaf 100644 --- a/smartd.8.in +++ b/smartd.8.in @@ -2,7 +2,7 @@ Copyright (C) 2002-10 Bruce Allen Copyright (C) 2004-15 Christian Franke -$Id: smartd.8.in 4102 2015-06-01 19:25:47Z chrfranke $ +$Id: smartd.8.in 4120 2015-08-27 16:12:21Z samm2 $ This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -745,7 +745,7 @@ Alternatively send the info to the smartmontools support mailing list: .SH REFERENCES Please see the following web site for more info: -\fBhttp://smartmontools.sourceforge.net/\fP +\fBhttp://www.smartmontools.org/\fP An introductory article about smartmontools is \fIMonitoring Hard Disks with SMART\fP, by Bruce Allen, Linux Journal, January 2004, @@ -768,4 +768,4 @@ Links to these and other documents may be found on the Links page of the .SH PACKAGE VERSION CURRENT_SVN_VERSION CURRENT_SVN_DATE CURRENT_SVN_REV .br -$Id: smartd.8.in 4102 2015-06-01 19:25:47Z chrfranke $ +$Id: smartd.8.in 4120 2015-08-27 16:12:21Z samm2 $ diff --git a/smartd.conf b/smartd.conf index 40fa10e..d4a0d10 100644 --- a/smartd.conf +++ b/smartd.conf @@ -1,8 +1,8 @@ # Sample configuration file for smartd. See man smartd.conf. -# Home page is: http://smartmontools.sourceforge.net +# Home page is: http://www.smartmontools.org -# $Id: smartd.conf 4047 2015-03-22 16:16:24Z chrfranke $ +# $Id: smartd.conf 4120 2015-08-27 16:12:21Z samm2 $ # smartd will re-read the configuration file if it receives a HUP # signal diff --git a/smartd.cpp b/smartd.cpp index 98c8ca4..f5df666 100644 --- a/smartd.cpp +++ b/smartd.cpp @@ -1,10 +1,10 @@ /* - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * - * Copyright (C) 2002-11 Bruce Allen + * Copyright (C) 2002-11 Bruce Allen + * Copyright (C) 2008-16 Christian Franke * Copyright (C) 2000 Michael Cornwell * Copyright (C) 2008 Oliver Bock - * Copyright (C) 2008-15 Christian Franke * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -106,7 +106,7 @@ typedef int pid_t; extern "C" int getdomainname(char *, int); // no declaration in header files! #endif -const char * smartd_cpp_cvsid = "$Id: smartd.cpp 4059 2015-04-18 17:01:31Z chrfranke $" +const char * smartd_cpp_cvsid = "$Id: smartd.cpp 4207 2016-01-22 19:35:10Z chrfranke $" CONFIG_H_CVSID; // smartd exit codes @@ -385,19 +385,21 @@ struct persistent_dev_state // SCSI ONLY - struct scsi_error_counter { + struct scsi_error_counter_t { struct scsiErrorCounter errCounter; unsigned char found; - scsi_error_counter() : found(0) { } + scsi_error_counter_t() : found(0) + { memset(&errCounter, 0, sizeof(errCounter)); } }; - scsi_error_counter scsi_error_counters[3]; + scsi_error_counter_t scsi_error_counters[3]; - struct scsi_nonmedium_error { + struct scsi_nonmedium_error_t { struct scsiNonMediumError nme; unsigned char found; - scsi_nonmedium_error() : found(0) { } + scsi_nonmedium_error_t() : found(0) + { memset(&nme, 0, sizeof(nme)); } }; - scsi_nonmedium_error scsi_nonmedium_error; + scsi_nonmedium_error_t scsi_nonmedium_error; persistent_dev_state(); }; @@ -1056,13 +1058,13 @@ static void MailWarning(const dev_config & cfg, dev_state & state, int which, co env[11].set("SMARTD_NEXTDAYS", dates); // now construct a command to send this as EMAIL - char command[2048]; if (!*executable) executable = ""; const char * newadd = (!address.empty()? address.c_str() : ""); const char * newwarn = (which? "Warning via" : "Test of"); #ifndef _WIN32 + char command[2048]; snprintf(command, sizeof(command), "%s 2>&1", warning_script.c_str()); // tell SYSLOG what we are about to do... @@ -1109,12 +1111,9 @@ static void MailWarning(const dev_config & cfg, dev_state & state, int which, co errno?strerror(errno):""); else { // mail process apparently succeeded. Check and report exit status - int status8; - if (WIFEXITED(status)) { // exited 'normally' (but perhaps with nonzero status) - status8=WEXITSTATUS(status); - + int status8 = WEXITSTATUS(status); if (status8>128) PrintOut(LOG_CRIT,"%s %s to %s: failed (32-bit/8-bit exit status: %d/%d) perhaps caught signal %d [%s]\n", newwarn, executable, newadd, status, status8, status8-128, strsignal(status8-128)); @@ -1140,6 +1139,7 @@ static void MailWarning(const dev_config & cfg, dev_state & state, int which, co #else // _WIN32 { + char command[2048]; snprintf(command, sizeof(command), "cmd /c \"%s\"", warning_script.c_str()); char stdoutbuf[800]; // < buffer in syslog_win32::vsyslog() @@ -1808,6 +1808,12 @@ static int ATADeviceScan(dev_config & cfg, dev_state & state, ata_device * atade } } + // Check for ATA Security LOCK + unsigned short word128 = drive.words088_255[128-88]; + bool locked = ((word128 & 0x0007) == 0x0007); // LOCKED|ENABLED|SUPPORTED + if (locked) + PrintOut(LOG_INFO, "Device: %s, ATA Security is **LOCKED**\n", name); + // Set default '-C 197[+]' if no '-C ID' is specified. if (!cfg.curr_pending_set) cfg.curr_pending_id = get_unc_attr_id(false, cfg.attribute_defs, cfg.curr_pending_incr); @@ -2110,6 +2116,9 @@ static int ATADeviceScan(dev_config & cfg, dev_state & state, ata_device * atade if (!isSCTErrorRecoveryControlCapable(&drive)) PrintOut(LOG_INFO, "Device: %s, no SCT Error Recovery Control support, ignoring -l scterc\n", name); + else if (locked) + PrintOut(LOG_INFO, "Device: %s, no SCT support if ATA Security is LOCKED, ignoring -l scterc\n", + name); else if ( ataSetSCTErrorRecoveryControltime(atadev, 1, cfg.sct_erc_readtime ) || ataSetSCTErrorRecoveryControltime(atadev, 2, cfg.sct_erc_writetime)) PrintOut(LOG_INFO, "Device: %s, set of SCT Error Recovery Control failed\n", name); @@ -2160,7 +2169,7 @@ static int ATADeviceScan(dev_config & cfg, dev_state & state, ata_device * atade // please. static int SCSIDeviceScan(dev_config & cfg, dev_state & state, scsi_device * scsidev) { - int k, err, req_len, avail_len, version, len; + int err, req_len, avail_len, version, len; const char *device = cfg.name.c_str(); struct scsi_iec_mode_page iec; UINT8 tBuf[64]; @@ -2289,7 +2298,7 @@ static int SCSIDeviceScan(dev_config & cfg, dev_state & state, scsi_device * scs // Flag that certain log pages are supported (information may be // available from other sources). if (0 == scsiLogSense(scsidev, SUPPORTED_LPAGES, 0, tBuf, sizeof(tBuf), 0)) { - for (k = 4; k < tBuf[3] + LOGPAGEHDRSIZE; ++k) { + for (int k = 4; k < tBuf[3] + LOGPAGEHDRSIZE; ++k) { switch (tBuf[k]) { case TEMPERATURE_LPAGE: state.TempPageSupported = 1; @@ -3222,12 +3231,7 @@ static int ATACheckDevice(const dev_config & cfg, dev_state & state, ata_device static int SCSICheckDevice(const dev_config & cfg, dev_state & state, scsi_device * scsidev, bool allow_selftests) { - UINT8 asc, ascq; - UINT8 currenttemp; - UINT8 triptemp; - UINT8 tBuf[252]; const char * name = cfg.name.c_str(); - const char *cp; // If the user has asked for it, test the email warning system if (cfg.emailtest) @@ -3242,9 +3246,9 @@ static int SCSICheckDevice(const dev_config & cfg, dev_state & state, scsi_devic } else if (debugmode) PrintOut(LOG_INFO,"Device: %s, opened SCSI device\n", name); reset_warning_mail(cfg, state, 9, "open device worked again"); - currenttemp = 0; - asc = 0; - ascq = 0; + + UINT8 asc = 0, ascq = 0; + UINT8 currenttemp = 0, triptemp = 0; if (!state.SuppressReport) { if (scsiCheckIE(scsidev, state.SmartPageSupported, state.TempPageSupported, &asc, &ascq, ¤ttemp, &triptemp)) { @@ -3255,7 +3259,7 @@ static int SCSICheckDevice(const dev_config & cfg, dev_state & state, scsi_devic } } if (asc > 0) { - cp = scsiGetIEString(asc, ascq); + const char * cp = scsiGetIEString(asc, ascq); if (cp) { PrintOut(LOG_CRIT, "Device: %s, SMART Failure: %s\n", name, cp); MailWarning(cfg, state, 1,"Device: %s, SMART Failure: %s", name, cp); @@ -3282,6 +3286,7 @@ static int SCSICheckDevice(const dev_config & cfg, dev_state & state, scsi_devic } if (!cfg.attrlog_file.empty()){ // saving error counters to state + UINT8 tBuf[252]; if (state.ReadECounterPageSupported && (0 == scsiLogSense(scsidev, READ_ERROR_COUNTER_LPAGE, 0, tBuf, sizeof(tBuf), 0))) { scsiDecodeErrCounterPage(tBuf, &state.scsi_error_counters[0].errCounter); @@ -3902,13 +3907,13 @@ static int ParseToken(char * token, dev_config & cfg) configfile, lineno, name, arg, cfg.test_regex.get_errmsg()); return -1; } + // Do a bit of sanity checking and warn user if we think that + // their regexp is "strange". User probably confused about shell + // glob(3) syntax versus regular expression syntax regexp(7). + if (arg[(val = strspn(arg, "0123456789/.-+*|()?^$[]SLCOcnr"))]) + PrintOut(LOG_INFO, "File %s line %d (drive %s): warning, character %d (%c) looks odd in extended regular expression %s\n", + configfile, lineno, name, val+1, arg[val], arg); } - // Do a bit of sanity checking and warn user if we think that - // their regexp is "strange". User probably confused about shell - // glob(3) syntax versus regular expression syntax regexp(7). - if (arg[(val = strspn(arg, "0123456789/.-+*|()?^$[]SLCOcnr"))]) - PrintOut(LOG_INFO, "File %s line %d (drive %s): warning, character %d (%c) looks odd in extended regular expression %s\n", - configfile, lineno, name, val+1, arg[val], arg); break; case 'm': // send email to address that follows @@ -4002,8 +4007,8 @@ static int ParseToken(char * token, dev_config & cfg) break; case 'W': // track Temperature - if ((val=Get3Integers(arg=strtok(NULL,delim), name, token, lineno, configfile, - &cfg.tempdiff, &cfg.tempinfo, &cfg.tempcrit))<0) + if (Get3Integers(arg=strtok(NULL, delim), name, token, lineno, configfile, + &cfg.tempdiff, &cfg.tempinfo, &cfg.tempcrit) < 0) return -1; break; case 'v': @@ -4300,7 +4305,6 @@ static int ParseConfigFile(dev_config_vector & conf_entries) if (scandevice==-2) return -1; // the final line is part of a continuation line - cont=0; entry+=scandevice; } break; @@ -4446,7 +4450,7 @@ static void ParseOpts(int argc, char **argv) opterr=optopt=0; bool badarg = false; - bool no_defaultdb = false; // set true on '-B FILE' + bool use_default_db = true; // set false on '-B FILE' // Parse input options. int optchar; @@ -4587,7 +4591,7 @@ static void ParseOpts(int argc, char **argv) if (*path == '+' && path[1]) path++; else - no_defaultdb = true; + use_default_db = false; unsigned char savedebug = debugmode; debugmode = 1; if (!read_drive_database(path)) EXIT(EXIT_BADCMD); @@ -4692,9 +4696,9 @@ static void ParseOpts(int argc, char **argv) #endif // Read or init drive database - if (!no_defaultdb) { + { unsigned char savedebug = debugmode; debugmode = 1; - if (!read_default_drive_databases()) + if (!init_drive_database(use_default_db)) EXIT(EXIT_BADCMD); debugmode = savedebug; } diff --git a/smartd.initd.in b/smartd.initd.in index 0c1e52c..afc67db 100644 --- a/smartd.initd.in +++ b/smartd.initd.in @@ -2,7 +2,7 @@ # smartmontools init file for smartd # Copyright (C) 2002-8 Bruce Allen -# $Id: smartd.initd.in 3727 2012-12-13 17:23:06Z samm2 $ +# $Id: smartd.initd.in 4120 2015-08-27 16:12:21Z samm2 $ # For RedHat and cousins: # chkconfig: 2345 40 40 @@ -540,7 +540,7 @@ elif uname | grep -i CYGWIN > /dev/null 2>&1 ; then Controls and monitors storage devices using the Self-Monitoring \ Analysis and Reporting Technology System (S.M.A.R.T.) \ built into ATA and SCSI Hard Drives. \ -http://smartmontools.sourceforge.net/" +http://www.smartmontools.org/" # Source configuration file. This should define the shell variable smartd_opts. # Email smartmontools-support@lists.sourceforge.net if there is a better choice diff --git a/update-smart-drivedb.8.in b/update-smart-drivedb.8.in index 092791e..e072d7b 100644 --- a/update-smart-drivedb.8.in +++ b/update-smart-drivedb.8.in @@ -1,8 +1,8 @@ .ig Copyright (C) 2013 Hannes von Haugwitz -Copyright (C) 2014-15 Christian Franke +Copyright (C) 2014-15 Christian Franke -$Id: update-smart-drivedb.8.in 4054 2015-04-15 19:04:49Z chrfranke $ +$Id: update-smart-drivedb.8.in 4193 2015-12-19 14:43:50Z chrfranke $ This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -19,10 +19,15 @@ update-smart-drivedb \- update smartmontools drive database .SH "SYNOPSIS" .B update-smart-drivedb -.RB [ -v ] +.RI [ OPTIONS ] .RI [ DESTFILE ] .SH "DESCRIPTION" +.\" %IF NOT OS ALL +.\"! [This man page is generated for the OS_MAN_FILTER version of smartmontools. +.\"! It does not contain info specific to other platforms.] +.\"! .PP +.\" %ENDIF NOT OS ALL .B update-smart-drivedb updates .B /usr/local/share/smartmontools/drivedb.h @@ -33,18 +38,18 @@ from smartmontools SVN repository. It tries to download first from the current branch and then from trunk. The tools used for downloading are either .BR curl (1), -.BR wget "(1) or" -.BR lynx (1). +.BR wget (1), +.BR lynx (1), .\" %IF OS FreeBSD -On FreeBSD, .BR fetch (1) -is used as a fallback. +[FreeBSD only], .\" %ENDIF OS FreeBSD .\" %IF OS OpenBSD -On OpenBSD, .BR ftp (1) -is used as a fallback. +[OpenBSD only], .\" %ENDIF OS OpenBSD +or +.BR svn (1). The old file is kept if the downloaded file is identical (ignoring the differences in Id string) otherwise it is moved to @@ -52,8 +57,60 @@ the differences in Id string) otherwise it is moved to .SH "OPTIONS" .TP -\-v -verbose output +.B \-s SMARTCTL +Use the +.BR smartctl (8) +executable at path SMARTCTL for drive database syntax check. +The form \'\-s \-\' disables the syntax check. +The default is +.BR /usr/local/sbin/smartctl . +.TP +.B \-t TOOL +Use TOOL for download. +TOOL is one of: +.I curl wget lynx +.\" %IF OS FreeBSD +.I fetch +.\" %ENDIF OS FreeBSD +.\" %IF OS OpenBSD +.I ftp +.\" %ENDIF OS OpenBSD +.IR svn . +The default is the first one found in PATH. +.TP +.B \-u LOCATION +Use URL of LOCATION for download. LOCATION is one of: +.br +.I sf +(Sourceforge code browser via HTTP), +.br +.I svn +(SVN repository via HTTPS), +.br +.I svni +(SVN repository via HTTP), +.br +.I trac +(Trac code browser via HTTPS). +.br +The default is +.IR svn . +.TP +.B \-\-cacert FILE +Use CA certificates from FILE to verify the peer. +.TP +.B \-\-capath DIR +Use CA certificate files from DIR to verify the peer. +.TP +.B \-\-insecure +Don't abort download if certificate verification fails. +This option is also required if a HTTP URL is selected with \'-u\' option. +.TP +.B \-\-dryrun +Print download commands only. +.TP +.B \-v +Verbose output. .SH "EXAMPLES" .nf @@ -80,7 +137,7 @@ current drive database. previous drive database. .TP .B /usr/local/share/smartmontools/drivedb.h.error -new drive database rejected due to syntax errors. +new drive database if rejected due to syntax errors. .TP .B /usr/local/share/smartmontools/drivedb.h.lastcheck empty file created if downloaded file was identical. @@ -106,4 +163,4 @@ Alternatively send the info to the smartmontools support mailing list: .SH PACKAGE VERSION CURRENT_SVN_VERSION CURRENT_SVN_DATE CURRENT_SVN_REV .br -$Id: update-smart-drivedb.8.in 4054 2015-04-15 19:04:49Z chrfranke $ +$Id: update-smart-drivedb.8.in 4193 2015-12-19 14:43:50Z chrfranke $ diff --git a/update-smart-drivedb.in b/update-smart-drivedb.in index 1b53a52..8e34a12 100644 --- a/update-smart-drivedb.in +++ b/update-smart-drivedb.in @@ -2,7 +2,7 @@ # # smartmontools drive database update script # -# Copyright (C) 2010-14 Christian Franke +# Copyright (C) 2010-15 Christian Franke # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by @@ -12,7 +12,7 @@ # You should have received a copy of the GNU General Public License # (for example COPYING); If not, see . # -# $Id: update-smart-drivedb.in 4019 2014-12-06 20:12:50Z chrfranke $ +# $Id: update-smart-drivedb.in 4184 2015-12-14 19:20:44Z chrfranke $ # set -e @@ -34,104 +34,342 @@ os_dltools="@os_dltools@" BRANCH="@DRIVEDB_BRANCH@" # Default drivedb location -DEST="$drivedbdir/drivedb.h" +DRIVEDB="$drivedbdir/drivedb.h" # Smartctl used for syntax check SMARTCTL="$sbindir/smartctl" -# Download URL for sourceforge code browser -SRCEXPR='http://sourceforge.net/p/smartmontools/code/HEAD/tree/$location/smartmontools/drivedb.h?format=raw' +myname=$0 -# Parse options -q="-q " -case "$1" in - -v) q=; shift ;; -esac - -case "$*" in - -*|*\ *) - cat <&2 + exit 1 +} -# Abort if 'which' is not available -which which >/dev/null || exit 1 - -# Find download tool -DOWNLOAD= -for t in $os_dltools; do - if which $t >/dev/null 2>/dev/null; then - case $t in - curl) DOWNLOAD="curl ${q:+-s }"'-f -o "$DEST.new" "$SRC"' ;; - lynx) DOWNLOAD='lynx -source "$SRC" >"$DEST.new"' ;; - wget) DOWNLOAD="wget $q"'-O "$DEST.new" "$SRC"' ;; - fetch) DOWNLOAD='fetch -o "$DEST.new" "$SRC"' ;; # FreeBSD - ftp) DOWNLOAD='ftp -o "$DEST.new" "$SRC"' ;; # OpenBSD - esac +warning() +{ + echo "$myname: (Warning) $*" >&2 +} + +selecturl() +{ + case $1 in + sf) url='http://sourceforge.net/p/smartmontools/code/HEAD/tree/trunk/smartmontools/drivedb.h?format=raw' ;; + svn) url='https://svn.code.sf.net/p/smartmontools/code/trunk/smartmontools/drivedb.h' ;; + svni) url='http://svn.code.sf.net/p/smartmontools/code/trunk/smartmontools/drivedb.h' ;; + trac) url='https://www.smartmontools.org/export/HEAD/trunk/smartmontools/drivedb.h' ;; + *) usage ;; + esac +} + +inpath() +{ + local d rc save + rc=1 + save=$IFS + IFS=':' + for d in $PATH; do + test -f "$d/$1" || continue + test -x "$d/$1" || continue + rc=0 break + done + IFS=$save + return $rc +} + +vecho() +{ + test -n "$q" || echo "$*" +} + +# vrun COMMAND ARGS... +vrun() +{ + if [ -n "$dryrun" ]; then + echo "$*" + elif [ -n "$q" ]; then + "$@" 2>/dev/null + else + echo "$*" + "$@" fi -done -if [ -z "$DOWNLOAD" ]; then - echo "$0: found none of: $os_dltools" >&2; exit 1 +} + +# vrun2 OUTFILE COMMAND ARGS... +vrun2() +{ + local f err rc + f=$1; shift + rc=0 + if [ -n "$dryrun" ]; then + echo "$* > $f" + else + vecho "$* > $f" + err=`"$@" 2>&1 > $f` || rc=$? + if [ -n "$err" ]; then + vecho "$err" >&2 + test $rc != 0 || rc=42 + fi + fi + return $rc +} + +# download URL FILE +download() +{ + local f u se rc + u=$1; f=$2 + rc=0 + + case $tool in + curl) + vrun curl ${q:+-s} -f --max-redirs 0 \ + ${cacert:+--cacert "$cacert"} \ + ${capath:+--capath "$capath"} \ + ${insecure:+--insecure} \ + -o "$f" "$u" || rc=$? + ;; + + wget) + vrun wget $q --max-redirect=0 \ + ${cacert:+--ca-certificate="$cacert"} \ + ${capath:+--ca-directory="$capath"} \ + ${insecure:+--no-check-certificate} \ + -O "$f" "$u" || rc=$? + ;; + + lynx) + test -z "$cacert" || vrun export SSL_CERT_FILE="$cacert" + test -z "$capath" || vrun export SSL_CERT_DIR="$capath" + # Check also stderr as lynx does not return != 0 on HTTP error + vrun2 "$f" lynx -stderr -noredir -source "$u" || rc=$? + ;; + + svn) + vrun svn $q export \ + --non-interactive --no-auth-cache \ + ${cacert:+--config-option "servers:global:ssl-trust-default-ca=no"} \ + ${cacert:+--config-option "servers:global:ssl-authority-files=$cacert"} \ + ${insecure:+--trust-server-cert} \ + "$u" "$f" || rc=$? + ;; + + fetch) # FreeBSD + vrun fetch $q --no-redirect \ + ${cacert:+--ca-cert "$cacert"} \ + ${capath:+--ca-path "$capath"} \ + ${insecure:+--no-verify-hostname} \ + -o "$f" "$u" || rc=$? + ;; + + ftp) # OpenBSD + vrun ftp \ + ${cacert:+-S cafile="$cacert"} \ + ${capath:+-S capath="$capath"} \ + ${insecure:+-S dont} \ + -o "$f" "$u" || rc=$? + ;; + + *) error "$tool: unknown (internal error)" ;; + esac + return $rc +} + +# Parse options +smtctl=$SMARTCTL +tool= +url= +q="-q" +dryrun= +cacert= +capath= +insecure= + +while true; do case $1 in + -s) + shift; test -n "$1" || usage + smtctl=$1 ;; + + -t) + shift + case $1 in *\ *) usage ;; esac + case " $os_dltools " in *\ $1\ *) ;; *) usage ;; esac + tool=$1 ;; + + -u) + shift; selecturl "$1" ;; + + -v) + q= ;; + + --dryrun) + dryrun=t ;; + + --cacert) + shift; test -n "$1" || usage + cacert=$1 ;; + + --capath) + shift; test -n "$1" || usage + capath=$1 ;; + + --insecure) + insecure=t ;; + + -*) + usage ;; + + *) + break ;; +esac; shift; done + +case $# in + 0) DEST=$DRIVEDB ;; + 1) DEST=$1 ;; + *) usage ;; +esac + +if [ -z "$tool" ]; then + # Find download tool in PATH + for t in $os_dltools; do + if inpath "$t"; then + tool=$t + break + fi + done + test -n "$tool" || error "found none of: $os_dltools" fi +test -n "$url" || selecturl "svn" + +# Check option compatibility +case "$tool:$url" in + svn:http*://svn.code.sf.net*) ;; + svn:*) error "'-t svn' requires '-u svn' or '-u svni'" ;; +esac +case "$tool:${capath:+set}" in + svn:set) warning "'--capath' is ignored if '-t svn' is used" ;; +esac +case "${insecure:-f}:$url" in + t:http:*) insecure= ;; + ?:https:*) ;; + *) error "'-u sf' and '-u svni' require '--insecure'" ;; +esac +case "$tool:$insecure" in + lynx:t) warning "'--insecure' is ignored if '-t lynx' is used" ;; +esac + # Try possible branch first, then trunk +errmsg= +errmsg2= for location in "branches/$BRANCH" "trunk"; do - test -n "$q" || echo "Download from $location" + test -z "$errmsg" || errmsg2=$errmsg + vecho "Download from $location with $tool" - errmsg= - rm -f "$DEST.new" - SRC="`eval echo "$SRCEXPR"`" + # Adjust URL + case $location in + trunk) src=$url ;; + *) src=`echo "$url" | sed "s,/trunk/,/$location/,"` ;; + esac + + # Download + test -n "$dryrun" || rm -f "$DEST.new" || exit 1 + rc=0 + download "$src" "$DEST.new" || rc=$? + test -z "$dryrun" || continue - if (eval $DOWNLOAD); then :; else - errmsg="download from $location failed (HTTP error)" + errmsg= + if [ $rc != 0 ]; then + errmsg="download from $location failed ($tool: exit $rc)" continue fi - if grep -i '.*Error has Occurred' "$DEST.new" >/dev/null; then - errmsg="download from $location failed (SF code browser error)" + + # Check file contents + case `sed 1q "$DEST.new"` in + /*) ;; + \<*) + errmsg="download from $location failed (HTML error message)" + continue ;; + *) + errmsg="download from $location failed (Unknown file contents)" + continue ;; + esac + + # Check file size + size=`wc -c < "$DEST.new"` + if [ "$size" -lt 10000 ]; then + errmsg="download from $location failed (too small file size $size bytes)" continue fi + if [ "$size" -gt 1000000 ]; then + errmsg="download from $location failed (too large file size $size bytes)" + break + fi break done +test -z "$dryrun" || exit 0 + if [ -n "$errmsg" ]; then rm -f "$DEST.new" - echo "$0: $errmsg" >&2 - exit 1 + test -z "$errmsg2" || echo "$myname: $errmsg2" >&2 + error "$errmsg" fi # Adjust timestamp and permissions touch "$DEST.new" chmod 0644 "$DEST.new" -# Check syntax -rm -f "$DEST.error" -if "$SMARTCTL" -B "$DEST.new" -P showall >/dev/null; then :; else - mv "$DEST.new" "$DEST.error" - echo "$DEST.error: rejected by $SMARTCTL, probably no longer compatible" >&2 - exit 1 +if [ "$smtctl" != "-" ]; then + # Check syntax + rm -f "$DEST.error" + if "$smtctl" -B "$DEST.new" -P showall >/dev/null; then + test -n "$q" || echo "$smtctl: syntax OK" + else + mv "$DEST.new" "$DEST.error" + echo "$DEST.error: rejected by $smtctl, probably no longer compatible" >&2 + exit 1 + fi fi -# Keep old file if identical +# Keep old file if identical, ignore differences in Id string rm -f "$DEST.lastcheck" if [ -f "$DEST" ]; then - if cmp "$DEST" "$DEST.new" >/dev/null 2>/dev/null; then + if cat "$DEST" | sed 's|\$''Id''[^$]*\$|$''Id''$|' \ + | cmp - "$DEST.new" >/dev/null 2>/dev/null; then rm -f "$DEST.new" touch "$DEST.lastcheck" echo "$DEST is already up to date" diff --git a/utility.cpp b/utility.cpp index ee6aadb..43bd6fa 100644 --- a/utility.cpp +++ b/utility.cpp @@ -1,10 +1,10 @@ /* * utility.cpp * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * - * Copyright (C) 2002-12 Bruce Allen <smartmontools-support@lists.sourceforge.net> - * Copyright (C) 2008-15 Christian Franke <smartmontools-support@lists.sourceforge.net> + * Copyright (C) 2002-12 Bruce Allen + * Copyright (C) 2008-16 Christian Franke * Copyright (C) 2000 Michael Cornwell <cornwell@acm.org> * * This program is free software; you can redistribute it and/or modify @@ -52,7 +52,7 @@ #include "atacmds.h" #include "dev_interface.h" -const char * utility_cpp_cvsid = "$Id: utility.cpp 4031 2015-01-01 10:47:48Z chrfranke $" +const char * utility_cpp_cvsid = "$Id: utility.cpp 4194 2016-01-01 13:46:00Z chrfranke $" UTILITY_H_CVSID INT64_H_CVSID; const char * packet_types[] = { @@ -90,7 +90,7 @@ std::string format_version_info(const char * prog_name, bool full /*= false*/) "(build date " __DATE__ ")" // checkout without expansion of Id keywords #endif " [%s] " BUILD_INFO "\n" - "Copyright (C) 2002-15, Bruce Allen, Christian Franke, www.smartmontools.org\n", + "Copyright (C) 2002-16, Bruce Allen, Christian Franke, www.smartmontools.org\n", prog_name, smi()->get_os_version_str().c_str() ); if (!full) @@ -291,9 +291,6 @@ void dateandtimezoneepoch(char *buffer, time_t tval){ const char *timezonename; char datebuffer[DATEANDEPOCHLEN]; int lenm1; -#ifdef _WIN32 - char tzfixbuf[6+1]; -#endif FixGlibcTimeZoneBug(); @@ -323,6 +320,8 @@ void dateandtimezoneepoch(char *buffer, time_t tval){ #ifdef _WIN32 // Fix long non-ascii timezone names + // cppcheck-suppress variableScope + char tzfixbuf[6+1] = ""; if (!getenv("TZ")) timezonename=fixtzname(tzfixbuf, sizeof(tzfixbuf), timezonename); #endif diff --git a/utility.h b/utility.h index 346e0f3..02c913b 100644 --- a/utility.h +++ b/utility.h @@ -1,10 +1,10 @@ /* * utility.h * - * Home page of code is: http://smartmontools.sourceforge.net + * Home page of code is: http://www.smartmontools.org * - * Copyright (C) 2002-11 Bruce Allen <smartmontools-support@lists.sourceforge.net> - * Copyright (C) 2008-14 Christian Franke <smartmontools-support@lists.sourceforge.net> + * Copyright (C) 2002-11 Bruce Allen + * Copyright (C) 2008-15 Christian Franke * Copyright (C) 2000 Michael Cornwell <cornwell@acm.org> * * This program is free software; you can redistribute it and/or modify @@ -25,7 +25,7 @@ #ifndef UTILITY_H_ #define UTILITY_H_ -#define UTILITY_H_CVSID "$Id: utility.h 4028 2014-12-13 14:59:48Z chrfranke $" +#define UTILITY_H_CVSID "$Id: utility.h 4145 2015-10-17 12:01:38Z chrfranke $" #include <time.h> #include <sys/types.h> // for regex.h (according to POSIX) @@ -194,6 +194,8 @@ public: bool open(const char * name, const char * mode) { + if (m_file && m_owner) + fclose(m_file); m_file = fopen(name, mode); m_owner = true; return !!m_file; @@ -201,6 +203,8 @@ public: void open(FILE * f, bool owner = false) { + if (m_file && m_owner) + fclose(m_file); m_file = f; m_owner = owner; } -- 2.39.2