Index: trunk/FACT++/src/Fits.cc
===================================================================
--- trunk/FACT++/src/Fits.cc	(revision 11715)
+++ trunk/FACT++/src/Fits.cc	(revision 11716)
@@ -37,13 +37,15 @@
 void Fits::AddStandardColumn(const Description& desc, const string &dataFormat, void* dataPointer, long unsigned int numDataBytes)
 {
-	//check if entry already exist
-	for (vector<Description>::const_iterator it=fStandardColDesc.begin(); it != fStandardColDesc.end(); it++)
-		if (it->name == desc.name)
-			return;
-	fStandardColDesc.push_back(desc);
-	fStandardFormats.push_back(dataFormat);
-	fStandardPointers.push_back(dataPointer);
-	fStandardNumBytes.push_back(numDataBytes);
-}
+    //check if entry already exist
+    for (vector<Description>::const_iterator it=fStandardColDesc.begin(); it != fStandardColDesc.end(); it++)
+        if (it->name == desc.name)
+            return;
+
+    fStandardColDesc.push_back(desc);
+    fStandardFormats.push_back(dataFormat);
+    fStandardPointers.push_back(dataPointer);
+    fStandardNumBytes.push_back(numDataBytes);
+}
+
 // --------------------------------------------------------------------------
 //
@@ -54,69 +56,25 @@
 //! @param numDataBytes the number of bytes taken by the DIM data. 
 //	
-void Fits::InitDataColumns(const vector<Description> &desc, vector<string>& dataFormat, void* dataPointer, int numDataBytes)
-{//we will copy this information here. It duplicates the data, which is not great, but it is the easiest way of doing it right now
-	if (desc.size() == dataFormat.size())
-	{
-	 	fDataColDesc = desc;
-	}
-	else
-	{
-		fDataColDesc.clear();
-		for (unsigned int i=0;i<dataFormat.size();i++)
-		{
-			ostringstream stt;
-			stt << "Data" << i;
-			fDataColDesc.push_back(Description(stt.str(), "comment", "unit"));
-		}
-	}		
-	fDataFormats = dataFormat;
-	fDataPointer = dataPointer;
-	fDataNumBytes = numDataBytes; 	
-}
-// --------------------------------------------------------------------------
-//
-//! This looks for a suitable table in the fits file, i.e. that corresponds to the name and column names. (no format check yet)
-//! @param tableName. the base table name to be obtained. If not suitable, numbers are appened to the name
-//! @param allNames. the name of all columns
-//! @param allDataTypes. the data types of all columns
-//! @param allUnits. the units of the columns
-//! @return a pointer to the newly retrieved/created table
-//
-CCfits::Table* Fits::findSuitableTableInFitsFile(const string& tableName,const vector<string>& allNames, const vector<string>& allDataTypes, const vector<string>& allUnits)
-{
-    const multimap< string, CCfits::ExtHDU * >& extMap = fFile->extension();
-    for (int i=0;i<100;i++)
-    {
-        if (i==10)
-            fMess->Error("Already 10 different tables with different formats exist in this file. Please consider re-creating the file entirely (i.e. delete it please)");
-        ostringstream cTableName;
-        cTableName << tableName;
-        if (i != 0)
-            cTableName << "-" << i;
-        //current table name does not exist yet. return its associated fits table newly created
-        if (extMap.find(cTableName.str()) == extMap.end())
-        {
-            for (multimap<string, CCfits::ExtHDU*>::const_iterator it=extMap.begin(); it!= extMap.end(); it++)
-                fMess->Debug(it->first);
-            return fFile->addTable(cTableName.str(), 0, allNames, allDataTypes, allUnits);
-        }
-        CCfits::Table* cTable;
-        cTable = dynamic_cast<CCfits::Table*>(extMap.find(cTableName.str())->second);
-
-        if (!cTable)
-            return NULL;//something wrong happened while getting the table pointer
-
-        //now check that the table columns are the same as the service columns
-        cTable->makeThisCurrent();
-        const map<string, Column*> cMap = cTable->column();
-        for (unsigned int j=0;j<allNames.size();j++)
-            if (cMap.find(allNames[j]) == cMap.end())
-                continue;
-
-        return cTable;
-    }
-    fMess->Error("One hundred trials for new table format failed. aborting");
-    return NULL;
-}
+void Fits::InitDataColumns(const vector<Description> &desc, const vector<string>& dataFormat, void* dataPointer)
+{
+    fDataFormats = dataFormat;
+    fDataPointer = dataPointer;
+
+    //we will copy this information here. It duplicates the data, which is not great, but it is the easiest way of doing it right now
+    if (desc.size() == dataFormat.size())
+    {
+        fDataColDesc = desc;
+        return;
+    }
+
+    fDataColDesc.clear();
+    for (unsigned int i=0;i<dataFormat.size();i++)
+    {
+        ostringstream stt;
+        stt << "Data" << i;
+        fDataColDesc.push_back(Description(stt.str(), "comment", "unit"));
+    }
+}
+
 // --------------------------------------------------------------------------
 //
@@ -129,160 +87,74 @@
 //! @param runNumber the runNumber for which this file is opened. 0 means nightly file.
 //
-bool Fits::Open(const string& fileName, const string& tableName, FITS* file, uint32_t* fitsCounter, MessageImp* out, int runNumber)
-{		
-//	if (fMess)
-//		delete fMess;
-//	fMess = new MessageImp(out);
+bool Fits::Open(const string& fileName, const string& tableName, uint32_t* fitsCounter, MessageImp* out, int runNumber, FITS* file)
+{
     fRunNumber = runNumber;
-	fMess = out;
-	fFileName = fileName;
-	if (file == NULL)
-	{
-		try
-		{
-			fFile = new FITS(fileName, RWmode::Write);
-		}
-		catch (CCfits::FitsException e)
-		{			
-			ostringstream str;
-			str << "Opening FITS file " << fileName << ": " << e.message();
-			fMess->Error(str);
-			fFile = NULL;
-			return false;
-		}	
-		fOwner = true;
-		fNumOpenFitsFiles = fitsCounter;
-		(*fNumOpenFitsFiles)++;
-	}
-	else
-	{
-		fFile = file;
-		fOwner = false;
-	}
-	//concatenate the standard and data columns
-	//do it the inneficient way first: its easier and faster to code.
-	vector<string> allNames;
-	vector<string> allDataTypes;
-	vector<string> allUnits;
-	fTotalNumBytes = 0;
-	for (unsigned int i=0;i<fStandardColDesc.size();i++)
-	{
-		allNames.push_back(fStandardColDesc[i].name);
-		allDataTypes.push_back(fStandardFormats[i]);
-		allUnits.push_back(fStandardColDesc[i].unit);
-		fTotalNumBytes += fStandardNumBytes[i];
-	}
-	//for (int i=static_cast<int>(fDataColDesc.size())-1;i>=0;i--)
-	for (unsigned int i=0; i<fDataColDesc.size(); i++)
-	{
-		if (fDataColDesc[i].name != "")
-			allNames.push_back(fDataColDesc[i].name);
-		else 
-		{
-			ostringstream stt;
-			stt << "Data" << i;
-			allNames.push_back(stt.str());
-		}
-		allDataTypes.push_back(fDataFormats[i]);
-		allUnits.push_back(fDataColDesc[i].unit);	
-	}
-	fTotalNumBytes += fDataNumBytes;
-	
-	bool updating = false;
-	try
-	{
-		//first, let's check if the table already exist in the file
-		vector<string> tryToLoadName;
-		tryToLoadName.push_back(tableName);
-                fFile->read(tryToLoadName);
-
-//	    const multimap< string, CCfits::ExtHDU * >& extMap = fFile->extension();
-//	    if (extMap.find(tableName) == extMap.end())
-//	    {
-//	        for (multimap<string, CCfits::ExtHDU*>::const_iterator it=extMap.begin(); it!= extMap.end(); it++)
-//	            fMess->Debug(it->first);
-//	        fTable = fFile->addTable(tableName, 0, allNames, allDataTypes, allUnits);
-//	    }
-//	    else
-//	    {
-//	        fTable = dynamic_cast<CCfits::Table*>(extMap.find(tableName)->second);
-//	    }
-        fTable = findSuitableTableInFitsFile(tableName, allNames, allDataTypes, allUnits);
-
-	    if (!fTable)
-	    {
-	        fMess->Error("Table " + tableName + " could not be created nor loaded from "+fileName);
-	        Close();
-	        return false;
-	    }
-	    fTable->makeThisCurrent();
-		fCopyBuffer = new unsigned char[fTotalNumBytes]; 
-		fNumRows = fTable->rows();
-		if (fNumRows !=0)
-		{//If the file already existed, then we must load its data to memory before writing to it.
-			BinTable* bTable = dynamic_cast<BinTable*>(fTable);
-			if (!bTable)
-			{
-				fMess->Error("Table " + tableName + " in "+fileName+" could not be converted to a binary table.");
-				Close();
-				return false;
-			}	
-			//read the table binary data.
-			vector<string> colName;
-			bTable->readData(true, colName);
-
-			//double check that the data was indeed read from the disk. Go through the fTable instead as colName is empty (yes, it is !)
-			const map<string, Column*> cMap = fTable->column();
-
-            for (map<string, Column*>::const_iterator cMapIt = cMap.begin(); cMapIt != cMap.end(); cMapIt++)
-			{
-				if (!cMapIt->second->isRead())
-				{
-					fMess->Error("Reading column " + cMapIt->first + " back from "+fileName+" failed.");
-					Close();
-					return false;
-				}	
-			}
-			updating = true;
-		}
-
-	}
-	catch(CCfits::FitsException e)
-	{
-		ostringstream str;
-                str << "Opening or creating table " << tableName << " in " << fileName << ": " << e.message();
-		fMess->Error(str);
-		fTable = NULL;
-		Close();
-		return false;
-	}
-			
-	if (!updating)
-		return WriteHeaderKeys();
-
-	return true;
-}
-// --------------------------------------------------------------------------
-//
-//!This writes a single header key in the currently open file.
-//!@param name the key
-//!@param value the key value
-//!@param a comment explaining the meaning of the key
-template <typename T>
-bool Fits::WriteSingleHeaderKey(const string &name, const T &value, const string &comment)
-{
-	try
-	{
-		fTable->addKey(name, value, comment);
-	}
-	catch (CCfits::FitsException e)
-	{
-		ostringstream str;
-		str << "Could not add header keys in file " << fFileName << " reason: " << e.message();
-		fMess->Error(str);
-		return false;
-	}
-	return true;
-}
+    fMess = out;
+
+    if (fFile)
+    {
+        fMess->Error("File already open...");
+        return false;
+    }
+
+    fFile = new FitsFile(*fMess);
+
+    if (file == NULL)
+    {
+        if (!fFile->OpenFile(fileName, true))
+            return false;
+
+        fNumOpenFitsFiles = fitsCounter;
+        (*fNumOpenFitsFiles)++;
+    }
+    else
+    {
+        if (!fFile->SetFile(file))
+            return false;
+    }
+
+    //concatenate the standard and data columns
+    //do it the inneficient way first: its easier and faster to code.
+    for (unsigned int i=0;i<fStandardColDesc.size();i++)
+    {
+        fFile->AddColumn(fStandardColDesc[i].name, fStandardFormats[i],
+                         fStandardColDesc[i].unit);
+    }
+
+    for (unsigned int i=0; i<fDataColDesc.size(); i++)
+    {
+        string name = fDataColDesc[i].name;
+        if (name.empty())
+        {
+            ostringstream stt;
+            stt << "Data" << i;
+            name = stt.str();
+        }
+
+        fFile->AddColumn(name, fDataFormats[i], fDataColDesc[i].unit);
+    }
+
+    try
+    {
+        if (!fFile->OpenNewTable(tableName, 100))
+        {
+            Close();
+            return false;
+        }
+
+        fCopyBuffer.resize(fFile->GetDataSize());
+
+        return fFile->GetNumRows()==0 ? true : WriteHeaderKeys();
+    }
+    catch (const CCfits::FitsException &e)
+    {
+        fMess->Error("Opening or creating table '"+tableName+"' in '"+fileName+"': "+e.message());
+
+        fFile->fTable = NULL;
+        Close();
+        return false;
+    }
+}
+
 // --------------------------------------------------------------------------
 //
@@ -291,23 +163,19 @@
 bool Fits::WriteHeaderKeys()
 {
-    if (!fTable)
-        return false;
-
-    const Time now;
-    if (!WriteSingleHeaderKey("EXTREL",   1.0f, "Release Number")) return false;
-    if (!WriteSingleHeaderKey("TELESCOP", "FACT", "Telescope that acquired this data")) return false;
-    if (!WriteSingleHeaderKey("ORIGIN",   "ISDC", "Institution that wrote the file")) return false;
-    if (!WriteSingleHeaderKey("CREATOR",  "fadctrl", "Program that wrote this file (FACT++ datalogger)")) return false;
-    if (!WriteSingleHeaderKey("PACKAGE",   PACKAGE_NAME, "Package name")) return false;
-    if (!WriteSingleHeaderKey("VERSION",   PACKAGE_VERSION, "Package description")) return false;
-    if (!WriteSingleHeaderKey("COMPILED",  __DATE__" "__TIME__, "Compile time")) return false;
-    if (!WriteSingleHeaderKey("REVISION",  REVISION, "SVN revision")) return false;
-    if (!WriteSingleHeaderKey("DATE",     now.Iso(), "File creation date")) return false;
-    if (!WriteSingleHeaderKey("NIGHT",    now.NightAsInt(), "Night as int")) return false;
-    if (!WriteSingleHeaderKey("TIMESYS",  "UTC", "Time systen")) return false;
-    if (!WriteSingleHeaderKey("TSTART",   "", "Time of the first receied data")) return false;
-    if (!WriteSingleHeaderKey("TSTOP",    "", "Time of the last receied data")) return false;
+    if (!fFile->fTable)
+        return false;
+
+    if (!fFile->WriteDefaultKeys("datalogger"))
+        return false;
+
+    if (!fFile->WriteKeyNT("TSTART", "", "Time of the first receied data"))
+        return false;
+
+    if (!fFile->WriteKeyNT("TSTOP",  "", "Time of the last receied data"))
+        return false;
+
     return true;
 }
+
 // --------------------------------------------------------------------------
 //
@@ -322,5 +190,5 @@
     {
         const char *charSrc = reinterpret_cast<char*>(fStandardPointers[i]);
-        reverse_copy(charSrc, charSrc+fStandardNumBytes[i], &fCopyBuffer[shift]);
+        reverse_copy(charSrc, charSrc+fStandardNumBytes[i], fCopyBuffer.data()+shift);
         shift += fStandardNumBytes[i];
     }
@@ -329,50 +197,39 @@
     {
         //now take care of the DIM data. The Converter is here for that purpose
-        conv.ToFits(&fCopyBuffer[shift], fDataPointer, fDataNumBytes);
+        conv.ToFits(fCopyBuffer.data()+shift, fDataPointer, fCopyBuffer.size()-shift);
     }
     catch (const runtime_error &e)
     {
         ostringstream str;
-        str << fFileName << ": " << e.what();
+        str << fFile->GetName() << ": " << e.what();
         fMess->Error(str);
         return false;
     }
 
-    fTable->makeThisCurrent();
-
-    int status(0);
-    if (fits_insert_rows(fTable->fitsPointer(), fNumRows, 1, &status))
-    {
-        ostringstream str;
-        char text[30];
-        fits_get_errstatus(status, text);
-        str << "Inserting row into " << fFileName << ": " << text << " (fits_insert_rows, rc=" << status << ")";
-        fMess->Error(str);
+    // This is not necessary, is it?
+    // fFile->fTable->makeThisCurrent();
+
+    if (!fFile->AddRow())
+    {
         Close();
         return false;
     }
 
-    fNumRows++;
+    if (!fFile->WriteData(fCopyBuffer))
+    {
+        Close();
+        return false;
+    }
 
     //the first standard variable is the current MjD
     if (fEndMjD==0)
     {
+        // FIXME: Check error?
         const double doubleValue = *reinterpret_cast<double*>(fStandardPointers[0]);
-        WriteSingleHeaderKey("TSTART", Time(doubleValue).Iso(),
-                             "Time of the first received data");
+        fFile->WriteKeyNT("TSTART", Time(doubleValue).Iso(),
+                          "Time of the first received data");
     }
     fEndMjD = *reinterpret_cast<double*>(fStandardPointers[0]);
 
-    //data copied to buffer, can write to fits
-    if (fits_write_tblbytes(fFile->fitsPointer(), fNumRows, 1, fTotalNumBytes, fCopyBuffer, &status))
-    {
-        char text[30];//max length of cfitsio error strings (from doc)
-        fits_get_errstatus(status, text);
-        ostringstream str;
-        str << "Writing FITS row " << fNumRows << " in " << fFileName << ": " << text << " (file_write_tblbytes, rc=" << status << ")";
-        fMess->Error(str);
-        Close();
-        return false;
-    }
     return true;
 }
@@ -385,27 +242,24 @@
 void Fits::Close() 
 {
-//WARNING: do NOT delete the table as it gets deleted by the fFile object
-//			if (fTable != NULL)
-//				delete fTable;
-	if (fFile != NULL && fOwner)
-	{
-//	    CCfits::FITS* backupFits = fFile;
-//	    fFile = NULL;
-	    WriteSingleHeaderKey("TSTOP", Time(fEndMjD).Iso(), "Time of the last receied data");
-	    delete fFile;
-
-        fMess->Info("Closed: "+fFileName);
+    if (!fFile)
+        return;
+
+    if (fFile->IsOpen() && fFile->IsOwner())
+    {
+        // FIMXE: Check for error? (It is allowed that fFile is NULL)
+        fFile->WriteKeyNT("TSTOP", Time(fEndMjD).Iso(),
+                          "Time of the last receied data");
+    }
+
+    if (fFile->IsOwner())
+    {
         if (fNumOpenFitsFiles != NULL)
             (*fNumOpenFitsFiles)--;
-	}
-	fFile = NULL;
-	if (fCopyBuffer != NULL)
-		delete [] fCopyBuffer;
-	fCopyBuffer = NULL;
-
-//fMess is the MessageImp part of the dataLogger itself. Thus it should NOT be deleted by the Fits files destructor.
-//	if (fMess)
-//		delete fMess;
-	fMess = NULL;
+    }
+
+    delete fFile;
+    fFile = NULL;
+
+    fMess = NULL;
 }
 
@@ -414,11 +268,19 @@
 int Fits::GetWrittenSize() const
 {
-	if (!IsOpen())
-		return 0;
-		
-	struct stat st;
-	if (stat(fFileName.c_str(), &st))
-		return 0;
-
-        return st.st_size;
-}
+    if (!IsOpen())
+        return 0;
+
+    struct stat st;
+    if (stat(fFile->GetName().c_str(), &st))
+        return 0;
+
+    return st.st_size;
+}
+
+/*
+ To be done:
+ - Check the check for column names in opennewtable
+ - If Open return false we end in an infinite loop (at least if
+   the dynamic cats to Bintable fails.
+
+*/
Index: trunk/FACT++/src/Fits.h
===================================================================
--- trunk/FACT++/src/Fits.h	(revision 11715)
+++ trunk/FACT++/src/Fits.h	(revision 11716)
@@ -2,11 +2,13 @@
 #define FACT_Fits
 
-#include <CCfits/CCfits>
-#include <vector>
+//#include <CCfits/CCfits>
+//#include <vector>
 
 #include "Description.h"
+//#include "MessageImp.h"
+//#include "Time.h"
+#include "FitsFile.h"
 
 class Converter;
-class MessageImp;
 
 using namespace std;
@@ -14,95 +16,76 @@
 class Fits
 {
-	private:
-		///The CCfits object to the FITS file
-        CCfits::FITS* fFile;
-		///Flag indicating whether the FITS object should be managed internally or not.
-		bool fOwner;
-		///The CCfits Table
-		CCfits::Table* fTable;
-		///The current number of Rows in the table
-		int fNumRows;
-		///Name of the "standard", i.e. data found in every fits file
-		///TODO make these variable static so that they are shared by every object.
-		///TODO add also a static boolean to initialize these only once
-		vector<Description> fStandardColDesc;
-		///Format of the standard columns.
-		vector<string> fStandardFormats;
-		///the pointers to the standard variables
-		vector<void*> fStandardPointers;
-		///the number of bytes taken by each standard variable
-		vector<int> fStandardNumBytes;
-		///the vector of data column names
-		vector<Description> fDataColDesc;
-		///the data format of the data columns
-		vector<string> fDataFormats;
-		///the pointer to the contiguous memory location where the data is stored (i.e. the dim data pointer)
-		void* fDataPointer;
-		///the size of the data, in bytes.
-		int fDataNumBytes;
-		///the copy buffer. Required to put the standard and data variable in contguous memory 
-		unsigned char* fCopyBuffer;
-		///the total number of bytes per FITS row
-		int fTotalNumBytes;
-		///to keep track of the time of the latest written entry (to update the header when closing the file)
-		double fEndMjD;
-		///Write the FITS header keys
-		bool WriteHeaderKeys();
+private:
+    FitsFile *fFile;
+
+    ///Name of the "standard", i.e. data found in every fits file
+    ///TODO make these variable static so that they are shared by every object.
+    ///TODO add also a static boolean to initialize these only once
+    vector<Description> fStandardColDesc;
+    ///Format of the standard columns.
+    vector<string> fStandardFormats;
+    ///the pointers to the standard variables
+    vector<void*> fStandardPointers;
+    ///the number of bytes taken by each standard variable
+    vector<int> fStandardNumBytes;
+
+    ///the vector of data column names
+    vector<Description> fDataColDesc;
+    ///the data format of the data columns
+    vector<string> fDataFormats;
+
+    ///the pointer to the contiguous memory location where the data is stored (i.e. the dim data pointer)
+    void* fDataPointer;
+    ///the copy buffer. Required to put the standard and data variable in contguous memory
+    vector<char> fCopyBuffer;
+    ///to keep track of the time of the latest written entry (to update the header when closing the file)
+    double fEndMjD;
+    ///Keep track of number of opened fits
+    uint32_t* fNumOpenFitsFiles;
+    ///were to log the errors
+    MessageImp* fMess;
+
+    ///Write the FITS header keys
+    bool WriteHeaderKeys();
+
 public:
-		///Name of the openned file. For querying stats
-		string fFileName;
-private:
-		///Keep track of number of opened fits
-		uint32_t* fNumOpenFitsFiles;
-		///were to log the errors
-		MessageImp* fMess;		
-public:
-        ///current run number being logged
-		uint32_t fRunNumber;
-		
-		Fits() :  fFile(NULL),
-				  fOwner(false),
-				  fTable(NULL), 
-					 fNumRows(0), 
-					 fDataPointer(NULL), 
-					 fDataNumBytes(0), 
-					 fCopyBuffer(NULL), 
-					 fTotalNumBytes(0),
-					 fEndMjD(0.0),
-					 fFileName(""),
-					 fNumOpenFitsFiles(NULL),
-					 fMess(NULL),
-					 fRunNumber(0)
-		 {}
-		
-		virtual ~Fits() 
-		{
-			if (IsOpen())
-				Close();
-		}
-		///returns wether or not the file is currently open or not
-		bool IsOpen() const {return fFile != NULL;}
-		
-		///Adds a column that exists in all FITS files
-		void AddStandardColumn(const Description& desc, const string &dataFormat, void* dataPointer, long unsigned int numDataBytes);
-		
-		///Adds columns specific to the service being logged.
-		void InitDataColumns(const vector<Description> &desc, vector<string>& dataFormat, void* dataPointer, int numDataBytes);
+    ///current run number being logged
+    uint32_t fRunNumber;
 
-		///Opens a FITS file
-        bool Open(const string& fileName, const string& tableName, CCfits::FITS* file, uint32_t* fitsCounter, MessageImp* out, int runNumber);//ostream& out);
+    Fits() : fFile(NULL),
+        fDataPointer(NULL),
+        fEndMjD(0.0),
+        fNumOpenFitsFiles(NULL),
+        fMess(NULL),
+        fRunNumber(0)
+    {}
 
-		///Write one line of data. Use the given converter.
-		bool Write(const Converter &conv);
-		
-		///Close the currently opened file.
-		void Close();
-		
-		///Get the size currently written on the disk
-		int GetWrittenSize() const;
-private:
-		template <typename T>
-		bool WriteSingleHeaderKey(const string &name, const T &value, const string &comment);
-		CCfits::Table* findSuitableTableInFitsFile(const string& tableName,const vector<string>& allNames, const vector<string>& allDataTypes, const vector<string>& allUnits);
+    virtual ~Fits()
+    {
+        Close();
+    }
+
+    ///returns wether or not the file is currently open or not
+    bool IsOpen() const { return fFile != NULL && fFile->IsOpen(); }
+
+    ///Adds a column that exists in all FITS files
+    void AddStandardColumn(const Description& desc, const string &dataFormat, void* dataPointer, long unsigned int numDataBytes);
+
+    ///Adds columns specific to the service being logged.
+    void InitDataColumns(const vector<Description> &desc, const vector<string>& dataFormat, void* dataPointer);
+
+    ///Opens a FITS file
+    bool Open(const string& fileName, const string& tableName,  uint32_t* fitsCounter, MessageImp* out, int runNumber, CCfits::FITS *file=0);//ostream& out);
+
+    ///Write one line of data. Use the given converter.
+    bool Write(const Converter &conv);
+
+    ///Close the currently opened file.
+    void Close();
+
+    ///Get the size currently written on the disk
+    int GetWrittenSize() const;
+
+    string GetName() const { return fFile ? fFile->GetName() : ""; }
 
 };//Fits
@@ -111,2 +94,3 @@
 #endif /*FITS_H_*/
 
+// WriteToFITS vs Open/Close
