Index: tol/bbasic/sys.cpp
===================================================================
--- tol/bbasic/sys.cpp	(revision d74c90b08998f2bb05e8bd9710f52bd95815d327)
+++ tol/bbasic/sys.cpp	(revision bcf71ac26ce8b3a69e6c9ff74836f3a8bc62985a)
@@ -995,6 +995,22 @@
 //--------------------------------------------------------------------
 //Opens a file and locks it
-//If cannot do it then sleeps and retries again until time is out
-FILE* FOpenAndLock(
+static FILE* fOpenAndLock(
+   const char *filename,
+   const char *mode)
+//--------------------------------------------------------------------
+{
+  FILE* fil=NULL;
+  #ifdef _MSC_VER
+  fopen_s(&fil, filename, mode);
+  #else
+  fil = fopen(filename, mode);
+  #endif
+  return(fil);
+}
+
+//--------------------------------------------------------------------
+//Opens a file and locks it
+//If doesn't can do it then sleeps and retries again until time is out
+FILE* BSys::FOpenAndLock(
    const char *filename,
    const char *mode,
@@ -1004,13 +1020,44 @@
 {
   FILE* fil=NULL;
+  double sleep = 1.0;
+  double sleepCum = 0.0;
+  int tryNum = 0; 
+  bool ok = false;
+  do
+  {
+    #ifdef _MSC_VER
+    ok = fopen_s(&fil, filename, mode)==0;
+    #else
+    fil = fopen(filename, mode);
+    ok = fil!=NULL;
+    #endif
+    if(!ok)
+    {
+      fil = NULL;
+      BSys::SleepMilliSeconds((unsigned int)sleep);
+      sleepCum += sleep;
+      sleep = floor(1.1*sleep)+(1+timeOutInMilliseconds/100);
+      tryNum++;
+      Warning(BText("[BSys::FOpenAndLock] Retraying to open locked file ")+filename+" for "+tryNum+"-th time\n");
+    }
+  } while(!fil && (sleepCum<timeOutInMilliseconds));
+  if(!fil && errorMessage && errorMessage[0])
+  {
+    Error(BText("Cannot open file ")+filename+" in mode "+mode+"\n"+
+          errorMessage);
+  }
   return(fil);
 }
 
 //--------------------------------------------------------------------
-//Unlocks a file and close it
-i FUnlockAndClose(FILE* file)
-//--------------------------------------------------------------------
-{
-  FILE* fil=NULL;
-  return(fil);
-}
+//Unlocks a file and closes it
+bool BSys::FUnlockAndClose(FILE* file, const char *filename)
+//--------------------------------------------------------------------
+{
+  if(fclose(file))
+  {
+    Error(BText("Cannot close file ")+filename);
+    return(false);
+  }
+  return(true);
+}
Index: tol/bbasic/tol_bsys.h
===================================================================
--- tol/bbasic/tol_bsys.h	(revision d74c90b08998f2bb05e8bd9710f52bd95815d327)
+++ tol/bbasic/tol_bsys.h	(revision bcf71ac26ce8b3a69e6c9ff74836f3a8bc62985a)
@@ -164,8 +164,8 @@
    const char *filename,
    const char *mode,
-   unsigned int timeOutInMilliseconds=0,
-   char* errorMessage=NULL);
+   unsigned int timeOutInMilliseconds,
+   char* errorMessage);
   //Unlocks a file and close it
-  static void FUnlockAndClose(FILE* file);
+  static bool FUnlockAndClose(FILE* file, const char *filename);
 };
 
Index: tol/btol/bdb/filehandle.cpp
===================================================================
--- tol/btol/bdb/filehandle.cpp	(revision d74c90b08998f2bb05e8bd9710f52bd95815d327)
+++ tol/btol/bdb/filehandle.cpp	(revision bcf71ac26ce8b3a69e6c9ff74836f3a8bc62985a)
@@ -61,24 +61,43 @@
 
 /////////////////////////////////////////////////////////////////////////////
- FILE* BFileDesc::CheckFileHandle(int handle, bool verbose, const BText& msg, 
-                                  BFileHashByHandle::const_iterator& found)
-/////////////////////////////////////////////////////////////////////////////
-{
-  FILE* file;
+ BFileDesc* BFileDesc::FindFileHandle(
+  int handle, bool verbose, const BText& msg, 
+  BFileHashByHandle::const_iterator& found)
+/////////////////////////////////////////////////////////////////////////////
+{
+  BFileDesc* fd;
   found = FileHandle().find(handle);
   if(found==FileHandle().end())
   { 
-    file = NULL;
+    fd = NULL;
   }
   else
   {
-    file = found->second->file_;
-  }
-  if(!file && verbose)
+    fd = found->second;
+  }
+  if(!fd && verbose)
   {
     Error(I2("Invalid file descriptor ",
              "Descriptor de fichero inválido ")+handle+"\n"+msg);
   }
-  return(file);
+  return(fd);
+};
+
+/////////////////////////////////////////////////////////////////////////////
+ BFileDesc* BFileDesc::FindFileHandle(
+   int handle, bool verbose, const BText& msg)
+/////////////////////////////////////////////////////////////////////////////
+{
+  BFileHashByHandle::const_iterator found;
+  return(FindFileHandle(handle, verbose, msg, found));
+};
+
+/////////////////////////////////////////////////////////////////////////////
+ FILE* BFileDesc::CheckFileHandle(int handle, bool verbose, const BText& msg, 
+                                  BFileHashByHandle::const_iterator& found)
+/////////////////////////////////////////////////////////////////////////////
+{
+  BFileDesc* fd = FindFileHandle(handle, verbose, msg, found);
+  return((fd)?fd->file_:NULL);
 };
 
Index: tol/btol/bdb/tol_filehandle.h
===================================================================
--- tol/btol/bdb/tol_filehandle.h	(revision d74c90b08998f2bb05e8bd9710f52bd95815d327)
+++ tol/btol/bdb/tol_filehandle.h	(revision bcf71ac26ce8b3a69e6c9ff74836f3a8bc62985a)
@@ -44,4 +44,8 @@
 
   static BFileHashByHandle& FileHandle();
+  static BFileDesc* FindFileHandle(int handle, bool verbose, const BText& msg, 
+                             BFileHashByHandle::const_iterator& found);
+
+  static BFileDesc* FindFileHandle(int handle, bool verbose, const BText& msg);
   static FILE* CheckFileHandle(int handle, bool verbose, const BText& msg, 
                              BFileHashByHandle::const_iterator& found);
Index: tol/btol/matrix_type/matgra.cpp
===================================================================
--- tol/btol/matrix_type/matgra.cpp	(revision d74c90b08998f2bb05e8bd9710f52bd95815d327)
+++ tol/btol/matrix_type/matgra.cpp	(revision bcf71ac26ce8b3a69e6c9ff74836f3a8bc62985a)
@@ -175,16 +175,14 @@
 #endif
 
+//Time out for open BBM files in milliseconds
+#define BBM_TimeOut 1000
+
 //--------------------------------------------------------------------
 void BBM_BinWrite(const BText& fileName, const BMat& M)
 //--------------------------------------------------------------------
 {
-  FILE* fil = fopen(fileName.String(),"wb");
-  if(!fil)
-  {
-    Error(I2("Cannot open for write BBM file ",
-             "No se pudo abrir para escritura el fichero BBM ")+
-          fileName);
-    return;
-  }
+  FILE* fil = BSys::FOpenAndLock(fileName.String(),"wb",
+   BBM_TimeOut, "Unexpected error writing to BBM file");
+  if(!fil) { return; } 
   BInt m = M.Rows();
   BInt n = M.Columns();
@@ -192,17 +190,5 @@
   fwrite(&n,sizeof(BInt),1,fil);
   fwrite(M.Data().Buffer(), sizeof(BDat), n*m, fil);
-#ifndef NDEBUG
-  int lastPos = ftell(fil);
-#endif
-  if(fclose(fil))
-  {
-    Error(I2("Cannot close after writing BBM file ",
-             "No se pudo cerrar despues de escribir el fichero BBM ")+
-          fileName);
-  };
-#ifndef NDEBUG
-  BInt fs = GetFileSize(fileName);
-  assert(fs==lastPos);
-#endif
+  if(!BSys::FUnlockAndClose(fil,fileName.String())) { return; }
   BBM_CheckSize("BBM_BinWrite",fileName,m,n);
 }
@@ -229,47 +215,30 @@
   
   /* open for overwrite */
-  if(!(fil = fopen(fileName.String(), "r+b"))) {
-    Error(I2("Cannot open (rewrite mode) BBM file ",
-       "No se pudo abrir (modo de sobreescritura) el fichero BBM ") + 
-    fileName);
-    return;
-  }
-  fpos_t pos = 0;
-  fsetpos(fil, &pos);
+  fil = BSys::FOpenAndLock(fileName.String(),"a+b",
+   BBM_TimeOut, "Unexpected error appending BBM file");
+  if(!fil) { return; } 
+  fpos_t pos;
+  pos = 0; fsetpos(fil, &pos); 
   fread(&rows,sizeof(BInt),1,fil);
   fread(&cols,sizeof(BInt),1,fil);
   rows2w = M.Rows();
   cols2w = M.Columns();
-  if(cols!=cols2w) {
+  if(cols!=cols2w) 
+  {
     Error("MatAppendFile: Different number of columns");
-    fclose(fil);
-    return;
-  }
-  pos = 0;
-  fsetpos(fil, &pos);
-  rows += rows2w;
-  fwrite(&rows, sizeof(BInt), 1, fil);
-  fflush(fil);
-  fclose(fil);
-  fil = NULL;
-  for(int tryNum = 0; !fil && (tryNum < 1000); tryNum++)
-  {
-    fil = fopen(fileName.String(), "ab");
-  }
-  /* open for append */
-  if(!fil) {
-    Error(I2("Cannot open (append mode) BBM file ",
-       "No se pudo abrir (modo de insercion) el fichero BBM ") + 
-    fileName);
-    return;
-  }
-  fwrite(M.Data().Buffer(), sizeof(BDat), rows2w*cols2w, fil);
-  fflush(fil);
-  if(fclose(fil))
-  {
-    Error(I2("Cannot close after append BBM file ",
-             "No se pudo cerrar despues de añadir al fichero BBM ")+
-          fileName);
-  };
+  }
+  else
+  {
+    rows += rows2w;
+    pos = rows*cols*sizeof(BDat)+2*sizeof(int); fsetpos(fil, &pos); 
+    fwrite(M.Data().Buffer(), sizeof(BDat), rows2w*cols2w, fil);
+    if(!BSys::FUnlockAndClose(fil,fileName.String())) { return; }
+    fil = BSys::FOpenAndLock(fileName.String(),"r+b",
+     BBM_TimeOut*10, "Unexpected error changing BBM file");
+    if(!fil) { return; } 
+    pos = 0; fsetpos(fil, &pos); 
+    fwrite(&rows, sizeof(BInt), 1, fil); 
+  }
+  BSys::FUnlockAndClose(fil,fileName.String());
 //BBM_CheckSize("BBM_BinAppend",fileName,rows,cols);
 }
@@ -282,12 +251,8 @@
   BInt fs = GetFileSize(fileName);
 //Std(BText("\nBBM_BinRead ")+fileName+" bytes "+fs);
-  FILE* fil = fopen(fileName.String(),"rb");
-  if(!fil)
-  {
-    Error(I2("Cannot open for read BBM file ",
-             "No se pudo abrir para lectura el fichero BBM ")+
-          fileName);
-    return; 
-  }
+  FILE* fil = BSys::FOpenAndLock(fileName.String(),"rb",
+   BBM_TimeOut, "Unexpected error reading from BBM file");
+  if(!fil) { return; } 
+
   BInt i, m, n, mn;
   fread(&m,sizeof(BInt),1,fil);
@@ -295,5 +260,5 @@
   if(!m || !n) 
   { 
-    fclose(fil);
+    BSys::FUnlockAndClose(fil,fileName.String());
     return; 
   }
@@ -306,10 +271,5 @@
     if(M.Rows()!=m) { return; }
     fread(M.GetData().GetBuffer(), sizeof(BDat), mn, fil);
-    if(fclose(fil))
-    {
-      Error(I2("Cannot close after reading BBM file ",
-               "No se pudo cerrar despues de leer el fichero BBM ")+
-            fileName);
-    };
+    if(!BSys::FUnlockAndClose(fil,fileName.String())) { return; }
   }
   //In TOL versions before 2007-01-15 structure page size = 8 => sizeof(BDat)=16
@@ -320,10 +280,5 @@
     BArray<BOis::BDatOld> M_;
     fread(M_.GetBuffer(), sizeof(BOis::BDatOld), mn, fil);
-    if(fclose(fil))
-    {
-      Error(I2("Cannot close after reading BBM file ",
-               "No se pudo cerrar despues de leer el fichero BBM ")+
-            fileName);
-    };
+    if(!BSys::FUnlockAndClose(fil,fileName.String())) { return; }
     for(i=0; i<mn; i++)
     {
@@ -343,10 +298,5 @@
     BDat* data   = M.GetData().GetBuffer();
     fread(buffer, 1, s, fil);
-    if(fclose(fil))
-    {
-      Error(I2("Cannot close after reading BBM file ",
-               "No se pudo cerrar despues de leer el fichero BBM ")+
-            fileName);
-    };
+    if(!BSys::FUnlockAndClose(fil,fileName.String())) { return; }
     for(i=0; i<mn; i++)
     {
@@ -371,11 +321,5 @@
     M.Alloc(m,n);
     fread(M.GetData().GetBuffer(), sizeof(BDat), mn, fil);
-    if(fclose(fil))
-    {
-      Error(I2("Cannot close after reading BBM file ",
-               "No se pudo cerrar despues de leer el fichero BBM ")+
-            fileName);
-    };
-
+    if(!BSys::FUnlockAndClose(fil,fileName.String())) { return; }
   }
   else
@@ -386,5 +330,7 @@
 
 //--------------------------------------------------------------------
-void BBM_BinReadRows(FILE* fil, BMat& M, 
+void BBM_BinReadRows(FILE* fil, 
+                     const BText& fileName,
+                     BMat& M, 
                      int m, int n, 
                      int i, int r, int t=1)
@@ -441,5 +387,7 @@
 
 //--------------------------------------------------------------------
-void BBM_BinReadCell(FILE* fil, BDat& cell, 
+void BBM_BinReadCell(FILE* fil, 
+                     const BText& fileName,
+                     BDat& cell, 
                      int m, int n, 
                      int i, int j)
@@ -455,5 +403,5 @@
      (0>j)||(j>=n) ) 
   { 
-    fclose(fil);
+    BSys::FUnlockAndClose(fil,fileName.String());
     return; 
   }
@@ -470,20 +418,10 @@
   BInt fs = GetFileSize(fileName);
 //Std(BText("\nBBM_BinRead ")+fileName+" bytes "+fs);
-  FILE* fil = fopen(fileName.String(),"rb");
-  if(!fil)
-  {
-    Error(I2("Cannot open for read BBM file ",
-             "No se pudo abrir para lectura el fichero BBM ")+
-          fileName);
-    return; 
-  }
+  FILE* fil = BSys::FOpenAndLock(fileName.String(),"rb",
+   BBM_TimeOut, "Unexpected error reading from BBM file");
+  if(!fil) { return; } 
   fread(&rows,   sizeof(BInt),1,fil);
   fread(&columns,sizeof(BInt),1,fil);
-  if(fclose(fil))
-  {
-    Error(I2("Cannot close after reading BBM file ",
-             "No se pudo cerrar despues de leer el fichero BBM ")+
-          fileName);
-  };
+  BSys::FUnlockAndClose(fil,fileName.String());
 }
 
@@ -649,9 +587,9 @@
   {
     int handle = (int)Real(Arg(1));
-    FILE* file = BFileDesc::CheckFileHandle(handle,true,
+    BFileDesc* fd = BFileDesc::FindFileHandle(handle,true,
       I2("Fail in ","Fallo en ")+"BMatReadRows");  
-    if(file)
-    {
-      BBM_BinReadRows(file,contens_,m,n,i,r,t);
+    if(fd)
+    {
+      BBM_BinReadRows(fd->file_,fd->path_.String(),contens_,m,n,i,r,t);
     }
   }
@@ -659,14 +597,9 @@
   {
     BText& path = Text(Arg(1));
-    file = fopen(path.String(),"rb");
-    if(!file)
-    {
-      Error(I2("Cannot open for MatReadRows BBM file ",
-               "No se pudo abrir para MatReadRows el fichero BBM ")+
-            path);
-      return; 
-    }
-    BBM_BinReadRows(file,contens_,m,n,i,r,t);
-    fclose(file);
+    file = BSys::FOpenAndLock(path.String(),"rb",
+      BBM_TimeOut, "Unexpected error reading from BBM file");
+    if(!file) { return; } 
+    BBM_BinReadRows(file,path.String(),contens_,m,n,i,r,t);
+    BSys::FUnlockAndClose(file,path.String());
   }
 }
@@ -711,9 +644,9 @@
   {
     int handle = (int)Real(Arg(1));
-    FILE* file = BFileDesc::CheckFileHandle(handle,true,
+    BFileDesc* fd = BFileDesc::FindFileHandle(handle,true,
       I2("Fail in ","Fallo en ")+"MatReadCell");  
-    if(file)
-    {
-      BBM_BinReadCell(file,contens_,m,n,i,j);
+    if(fd)
+    {
+      BBM_BinReadCell(fd->file_,fd->path_.String(),contens_,m,n,i,j);
     }
   }
@@ -721,14 +654,9 @@
   {
     BText& path = Text(Arg(1));
-    file = fopen(path.String(),"rb");
-    if(!file)
-    {
-      Error(I2("Cannot open for MatReadCell BBM file ",
-               "No se pudo abrir para MatReadCell el fichero BBM ")+
-            path);
-      return; 
-    }
-    BBM_BinReadCell(file,contens_,m,n,i,j);
-    fclose(file);
+    file = BSys::FOpenAndLock(path.String(),"rb",
+     BBM_TimeOut, "Unexpected error reading from BBM file");
+    if(!file) { return; } 
+    BBM_BinReadCell(file,path.String(),contens_,m,n,i,j);
+    BSys::FUnlockAndClose(file,path.String());
   }
 }
