close Warning: Can't synchronize with repository "(default)" (/var/svn/tolp does not appear to be a Subversion repository.). Look in the Trac log for more information.

Opened 14 years ago

Closed 14 years ago

#1069 closed enhancement (fixed)

Error al guardar un archivo muy pesado

Reported by: imendez Owned by: Víctor de Buen Remiro
Priority: highest Milestone: Mantainance
Component: OIS Version: 2.0.1
Severity: blocker Keywords:
Cc: atorre@…, irobles@…

Description

Hola, al intentar guardar en un fichero .oza un objeto muy pesado, ocurren dos cosas nada deseables:

  • Da un error por falta de memoria ("not enough memory").
  • Crea el archivo con 0 KB.

Respecto a lo primero: ¿no es posible liberar memoria conforme se va realizando el volcado?
En cuanto a lo segundo, si el archivo ya existía lo borra y por tanto se pierden ambos, tanto el antiguo como el nuevo (que crea con 0 KB). ¿Se puede hacer que, si da error, mantenga el archivo anterior?

No tengo ahora mismo ningún ejemplo que permita reproducirlo rápidamente, pero es tan sencillo como crear un objeto TOL muy pesado (pero que TOL "soporte") e intentar guardarlo con Ois.Store

Muchas gracias.

Change History (7)

comment:1 Changed 14 years ago by Víctor de Buen Remiro

Status: newaccepted

Nunca me ha pasado tal cosa y he guradado en OIS cosas muy gordas.

Los errores de memoria no pueden ser previstos y cuando ocurren ya no hay nada que hacer. Si quieres hacer copias de seguridad eso no es tarea de OIS, debes hacerlo tú. Renombra el antiguo antes o lo mandas a un directorio de backup.

Para saber qué memoria liberar tendría que poder reproducirlo para observar dónde se está gastando, o al menos saber qué tipo de objetos es el que está gastando esa RAM en el proceso de guardado. Quizás viendo el código o el proceso antes del guardado podría hacerme una idea.

comment:2 Changed 14 years ago by Iván Robles

Buenos días,

para reproducirlo con un código simple:

Matrix a = Rand(100000,300,0,1);

Set b = [[a, a*2]];

Real Ois.Store(b, "C:/matriz.oza");

Espero que sirva este ejemplo.Nos pasa al guardar otro objeto, pero creo que lo que esta pasando internamente es algo similar a este ejemplo.

Si no os vale con esto, os pasamos el código que nos esta dando problemas, pero se necesita tener instalado MMS

Un cordial saludo

comment:3 Changed 14 years ago by Víctor de Buen Remiro

Milestone: Mantainance
Type: defectenhancement

Lo que se propone como solución es una nueva función de creación de OIS que según los parámetros puede hacer ditintas cosas

1 directorio plano Real Ois.StoreEngine(b, "matriz", "");
2 OZA en RAM Real Ois.StoreEngine(b, "matriz.oza", "");
3 OZA con direcotrio temporal Real Ois.StoreEngine(b, "matriz.oza", "ZipArchive");

cuando tengamos más motores podrá hacer otras más.

El problema era que lo que tenemos de ZipArchive en OIS usa la clase CZipMemFile de ZipArchive que no hace volcados a disco hasta el final así que tiene que estar todo en RAM al mismo tiempo por eso si el Set es muy grande es necesario crear el OZA como un directorio temporal, luego comprimir por fuera usando PackArchive y después borrar ese directorio temporal.

El resultado es el mismo que usando CZipMemFile así que el Ois.Load lo lee igual sin embargo, para ficheros muy grandes pasa lo mismo y hay que descomprimir primero, cargar el OIS del directorio plano y borrarlo después.

comment:4 Changed 14 years ago by Víctor de Buen Remiro

Resolution: fixed
Status: acceptedclosed

(In [3097]) Fixes #1069

comment:5 Changed 14 years ago by Pedro Gea

Resolution: fixed
Status: closedreopened

Reabro el tique para revisar el método Ois.StoreEngine generado aquí.

En su versión "ZipArchive" el método escribe el OIS no archivado (como carpeta) en la misma ruta donde luego creará el OZA. Si esto es una ruta remota el trabajo será triple, llevar allí los archivos sin comprimir, traerlos convenientemente a RAM para comprimirlos y llevarlo allí de nuevo comprimido. Se sugiere cambiar el lugar donde se ubica temporalmente la carpeta a una ruta local.

También se sugiere comprobar la no existencia de la ruta (versión carpeta del ois) antes de escribir en ella, y por supuesto de borrarla. Ya que puede borrar algo que no le corresponde, sobre todo a causa del comportamiento inadecuado de la función GetFilePrefix (véase #1089).

comment:6 Changed 14 years ago by Víctor de Buen Remiro

Lo de crear el directorio temporal en local es sencillo, estoy en ello.

El path donde le mandan escribir puede existir o no y si existe puede que le sirva a alguien o no, no hay forma de saberlo desde dentro. Es imposible que esta función ni ninguna otra evite que el usuario le pida cosas que realmente no quiere hacer. Si el usuario le dice que guarde ahí tiene que hacerle caso, es responsabilidad del ordenante comprobar lo que haya que comprobar.

Otra cosa es que haya un error en GetFilePrefix que produzca confusiones, eso se arregla y ya está. Cuando se hizo esa función los nombres de los archivos tenían un sólo punto y una extensión de tres letras, así que es normal que no se previera este problema.

comment:7 Changed 14 years ago by Víctor de Buen Remiro

Resolution: fixed
Status: reopenedclosed
Note: See TracTickets for help on using tickets.