+ EMUFS_FREE fs; /* espacio libre en el bloque */
+ EMUFS_BLOCK_ID block_id; /* identificador del 1er bloque */
+ char* block; /* buffer del bloque a guardar en disco */
+ char name_f[255];
+ int err = 0;
+
+ strcpy(name_f, efs->nombre);
+ strcat(name_f, ".dat");
+
+ /* busco lugar para el registro en un bloque existente */
+ block_id = emufs_fsc_buscar_lugar(efs, sizeof(EMUFS_TIPO1_REG_HEADER)
+ + header.size, &fs);
+ /* si no hay bloques con suficiente espacio creo un bloque nuevo */
+ if (block_id == EMUFS_NOT_FOUND) {
+ /* tamaño máximo ultilizable para datos en un bloque */
+ EMUFS_BLOCK_SIZE block_space = efs->tam_bloque - sizeof(EMUFS_TIPO1_REG_HEADER);
+ /* identificador del bloque que se guarda */
+ EMUFS_BLOCK_ID curr_block_id = EMUFS_NOT_FOUND;
+ /* tamaño de la porción de registro que se guarda */
+ EMUFS_REG_SIZE chunk_size = 0;
+ /* puntero a la poción del registro */
+ char* chunk_ptr = reg;
+
+ /* crear un nuevo bloque en memoria */
+ block = (char*) malloc(efs->tam_bloque);
+ if (block == NULL) {
+ /* TODO Manejo de errores */
+ PERR("No hay memoria");
+ return 2; /* EMUFS_ERROR_OUT_OF_MEMORY */
+ }
+ do {
+ memset(block, 0, efs->tam_bloque); /* inicializa bloque */
+ chunk_ptr += chunk_size; /* Avanzo para guardar prox chunk */
+ header.size -= chunk_size; /* Resto lo que ya guardé */
+ chunk_size = MIN(header.size, block_space);
+ /* graba porción del registro en bloque */
+ emufs_tipo1_escribir_reg_chunk_en_memoria(block, header, chunk_ptr, chunk_size);
+ /* graba el bloque en el archivo */
+ curr_block_id = emufs_tipo1_grabar_bloque(efs, block, EMUFS_NOT_FOUND, &err);
+ if (err) {
+ PERR("error al grabar bloque");
+ free(block);
+ return err;
+ }
+ /* grabo el nuevo registro en el archivo de espacios libres */
+ err = emufs_fsc_agregar(efs, curr_block_id, block_space - chunk_size);
+ if (err) {
+ PERR("No se pudo agregar fsc");
+ free(block);
+ return err;
+ }
+ /* si es el primer id de bloque obtenido, lo guardo para
+ * agregarlo después al archivo de índices. */
+ if (block_id == EMUFS_NOT_FOUND) {
+ block_id = curr_block_id;
+ }
+ } while (header.size > block_space);
+ free(block);
+
+ /* Encontró espacio en un bloque existente, graba registro ahí */
+ } else {
+ /* cargo el bloque en block_id */
+ if (!(block = (char*) emufs_tipo1_leer_bloque(efs, block_id, &err))) {
+ /* TODO Manejo de errores */
+ PERR("no se pudo leer el bloque");
+ return err;
+ }
+ /* graba registro en bloque */
+ emufs_tipo1_escribir_reg_en_memoria(block + efs->tam_bloque - fs,
+ header, reg);
+ /* graba el bloque en el archivo */
+ block_id = emufs_tipo1_grabar_bloque(efs, block, block_id, &err);
+ if (err) {
+ PERR("error al grabar bloque");
+ free(block);
+ return err;
+ }
+ free(block);
+ /* actualizo el archivo de espacios libres */
+ err = emufs_fsc_actualizar(efs, block_id, fs - header.size
+ - sizeof(EMUFS_TIPO1_REG_HEADER));
+ if (err) {
+ PERR("No se pudo actualizar fsc");
+ return err;
+ }
+ }
+
+ /* actualizo el indice de bloques y registros */
+ err = emufs_idx_agregar(efs, header.id, block_id);
+ if (err){
+ PERR("No se pudo agregar idx");
+ return err;
+ }
+
+ return err;
+}
+
+EMUFS_REG_ID emufs_tipo1_modificar_registro(EMUFS *emu, EMUFS_REG_ID id,
+ void *data, EMUFS_REG_SIZE size, int *error)
+{
+ emufs_tipo1_borrar_registro(emu, id);
+ return emufs_tipo1_grabar_registro(emu, data, size, error);