Microsoft KB Archive/225029

= How To Determine Which Version of Excel Wrote a Workbook =

Article ID: 225029

Article Last Modified on 1/24/2007

-

APPLIES TO


 * Microsoft Excel 2000 Standard Edition
 * Microsoft Excel 2002 Standard Edition
 * Microsoft Excel 97 Standard Edition
 * Microsoft Excel 5.0 Standard Edition
 * Microsoft Excel 95 Standard Edition

-



This article was previously published under Q225029



SUMMARY
This article demonstrates how to determine the version of Microsoft Excel that wrote a given workbook.



MORE INFORMATION
Microsoft Excel saves data using structured storage. In particular, it creates a data stream called "Workbook" (previously just "Book") where it saves the contents starting with a Beginning of File (BOF) record. This record contains useful attributes of the workbook, as well as the version. The following Microsoft Visual C++ code demonstrates how to open a file, read it, and return the version number based on the BOF:  Create a new Win32 Console Application in Microsoft Developer Studio, and name it XlVer.  Add a C++ Source File (.cpp) to the project and add the following code to the source file: #include   #include 

int XLVersionThatWroteFile(char *filename) { // Translate filename to Unicode WCHAR wcFilename[1024]; int i = mbstowcs(wcFilename, filename, strlen(filename)); wcFilename[i] = 0;

// Open the document as an OLE compound document IStorage *pStorage; HRESULT hr; hr = ::StgOpenStorage(wcFilename, NULL,                STGM_READ | STGM_SHARE_EXCLUSIVE, NULL, 0, &pStorage);

if(FAILED(hr)) return 0; // Open the data-stream where Microsoft Excel stores the data IStream *pStream; hr = pStorage->OpenStream(L"Workbook", NULL,        STGM_READ | STGM_SHARE_EXCLUSIVE, 0, &pStream);

// If "Workbook" does not exist, try "Book" if(FAILED(hr)) { hr = pStorage->OpenStream(L"Book", NULL,

STGM_READ | STGM_SHARE_EXCLUSIVE, 0, &pStream);     }      if(FAILED(hr)) {         pStorage->Release;         return 0;      }

// Get rupBuild & rupYear short rupBuild, rupYear; LARGE_INTEGER off; ULARGE_INTEGER newPos; off.QuadPart = 8; pStream->Seek(off, STREAM_SEEK_SET, &newPos); DWORD bytesRead; pStream->Read(&rupBuild, 2, &bytesRead); pStream->Read(&rupYear, 2, &bytesRead);

// Let go of the IStorage pointer pStorage->Release;

// Excel 8.0's rupyear = 1996 if(rupYear == 1996) return 8; // Excel 9.0 comes after Excel 8.0... if(rupYear > 1996) return 9; // Excel 5.0's rupyear < 1994 if(        (rupYear < 1994) ||         // Excel 5.0 & 7.0 have rupYear=1994 for some versions...         (rupBuild == 2412) || (rupBuild == 3218) || (rupBuild == 3321)      ) return 5; // All that's left is Excel 7.0 return 7;

}

void main(int argc, char **argv) { if(argc != 2) { printf("Usage: XLVER filename.xls"); }     else { printf("Excel version = %d", XLVersionThatWroteFile(argv[1])); }  }                     Compile, and then find an .xls file on your machine and run the program as follows:

XlVer.exe myfile.x

