OpenRadioss 2025.1.11
OpenRadioss project
Loading...
Searching...
No Matches
mumps_io_basic.c
Go to the documentation of this file.
1/*
2 *
3 * This file is part of MUMPS 5.5.1, released
4 * on Tue Jul 12 13:17:24 UTC 2022
5 *
6 *
7 * Copyright 1991-2022 CERFACS, CNRS, ENS Lyon, INP Toulouse, Inria,
8 * Mumps Technologies, University of Bordeaux.
9 *
10 * This version of MUMPS is provided to you free of charge. It is
11 * released under the CeCILL-C license
12 * (see doc/CeCILL-C_V1-en.txt, doc/CeCILL-C_V1-fr.txt, and
13 * https://cecill.info/licences/Licence_CeCILL-C_V1-en.html)
14 *
15 */
16#include "mumps_io_basic.h"
17#include "mumps_io_err.h"
18#include "mumps_c_types.h"
19/* Exported global variables */
20#if ! defined (MUMPS_WIN32)
21# if defined(WITH_PFUNC) && ! defined (WITHOUT_PTHREAD)
22# include <pthread.h>
23pthread_mutex_t mumps_io_pwrite_mutex;
24# endif
25/* int* mumps_io_pfile_pointer_array; */
26/* int* mumps_io_current_file; */
27/* #else /\*MUMPS_WIN32*\/ */
28/* FILE** mumps_io_current_file; */
29/* FILE** mumps_io_pfile_pointer_array; */
30#endif /* MUMPS_WIN32 */
31/* mumps_file_struct* mumps_io_pfile_pointer_array;
32 mumps_file_struct* mumps_io_current_file; */
34/* int mumps_io_current_file_number; */
36/* char** mumps_io_pfile_name; */
37/* int mumps_io_current_file_position; */
38/* int mumps_io_write_pos; */
39/* int mumps_io_last_file_opened; */
44/* int mumps_io_nb_file; */
47/* int mumps_flag_open;*/
50/* Functions */
52 /* Defines the pattern for the file name. The last 6 'X' will be replaced
53 so as to name were unique */
54 char name[351];
55#if ! defined(_WIN32)
56 MUMPS_INT fd;
57 char buf[64]; /* for error message */
58#endif
59 mumps_file_struct *mumps_io_pfile_pointer_array;
60 if (file_number_arg > ((mumps_files+type)->mumps_io_nb_file)-1){
61 /* mumps_io_nb_file was initialized to the estimated number
62 of files inside mumps_io_init_file_struct; this block is
63 entered in case of a too small estimation of the required
64 number of files. */
65 /* We increase the number of files needed and then realloc. */
66 ((mumps_files+type)->mumps_io_nb_file)++;
67 (mumps_files+type)->mumps_io_pfile_pointer_array=(mumps_file_struct*)realloc((void *)(mumps_files+type)->mumps_io_pfile_pointer_array,((mumps_files+type)->mumps_io_nb_file)*sizeof(mumps_file_struct));
68 /* Check for reallocation problem */
69 if((mumps_files+type)->mumps_io_pfile_pointer_array==NULL){
70 return mumps_io_error(-13,"Allocation problem in low-level OOC layer\n");
71 }
72 /* initialize "is_opened", as in mumps_io_init_file_struct */
73 ((mumps_files+type)->mumps_io_pfile_pointer_array+((mumps_files+type)->mumps_io_nb_file)-1)->is_opened = 0;
74 }
75 mumps_io_pfile_pointer_array=(mumps_files+type)->mumps_io_pfile_pointer_array;
76 /*
77 Do change the current file
78 Careful: both mumps_io_current_file_number and
79 mumps_io_current_file must be changed
80 */
81 ((mumps_files+type)->mumps_io_current_file_number)=file_number_arg;
82 ((mumps_files+type)->mumps_io_current_file)=mumps_io_pfile_pointer_array+file_number_arg;
83 if((mumps_io_pfile_pointer_array+file_number_arg)->is_opened!=0){
84 /*
85 The file already exists and is open.
86 The i/o will be performed in the current file (which may not
87 be the last one.
88 */
89 return 0;
90 }
91/*********************/
92/* CREATE A NEW FILE */
93/*********************/
94/* #if ! defined( MUMPS_WIN32 )*/
95/* MinGW does not have a mkstemp function and MinGW defines _WIN32,
96 * so we also go in the else branch below with MinGW */
97#if ! defined(_WIN32)
98 strcpy(name,mumps_ooc_file_prefix);
99 fd=mkstemp(name);
100 /* Note that a file name is built by mkstemp and that the file is
101 opened. fd hold the file descriptor to access it.
102 We want to close the file that will be opened later
103 and might be removed before the end of the processus.
104 */
105 if(fd < 0) {
106 sprintf(buf,"File creation failure");
107 return mumps_io_sys_error(-90,buf);
108 } else {
109 close(fd);
110 }
111#else
112 sprintf(name,"%s_%d_%d",mumps_ooc_file_prefix,((mumps_files+type)->mumps_io_current_file_number)+1,type);
113#endif
114/* *(mumps_io_pfile_pointer_array+mumps_io_current_file_number)=fopen(name,"w+"); */
115/* *(mumps_io_pfile_name+mumps_io_current_file_number)=(char *)malloc((strlen(name)+1)*sizeof(char)); */
116/* if(*(mumps_io_pfile_name+mumps_io_current_file_number)==NULL){ */
117/* sprintf(error_str,"Allocation problem in low-level OOC layer\n"); */
118/* return -13; */
119/* } */
120 strcpy((mumps_io_pfile_pointer_array+(mumps_files+type)->mumps_io_current_file_number)->name,name);
121 /* See mumps_io_basic.h for comments on the I/O flags passed to open */
122#if ! defined( MUMPS_WIN32 )
123 (mumps_io_pfile_pointer_array+(mumps_files+type)->mumps_io_current_file_number)->file=open(name,(mumps_files+type)->mumps_flag_open,0666);
124 /*
125CPA: for LU factor file:
126(mumps_io_pfile_pointer_array+(mumps_files+type)->mumps_io_current_file_number)->file= open(name, O_WRONLY | O_CREAT | O_TRUNC, 0666); */
127 if((mumps_io_pfile_pointer_array+(mumps_files+type)->mumps_io_current_file_number)->file==-1){
128 return mumps_io_sys_error(-90,"Unable to open OOC file");
129 }
130#else
131 (mumps_io_pfile_pointer_array+(mumps_files+type)->mumps_io_current_file_number)->file=fopen(name,(mumps_files+type)->mumps_flag_open);
132 if((mumps_io_pfile_pointer_array+(mumps_files+type)->mumps_io_current_file_number)->file==NULL){
133 return mumps_io_error(-90,"Problem while opening OOC file");
134 }
135#endif
136 (mumps_files+type)->mumps_io_current_file=(mumps_io_pfile_pointer_array+(mumps_files+type)->mumps_io_current_file_number);
137 ((mumps_files+type)->mumps_io_nb_file_opened)++;
138 if((mumps_files+type)->mumps_io_current_file_number>(mumps_files+type)->mumps_io_last_file_opened){
139 (mumps_files+type)->mumps_io_last_file_opened=(mumps_files+type)->mumps_io_current_file_number;
140 }
141 /* if(*(mumps_io_pfile_pointer_array+mumps_io_current_file_number)==NULL) */
142 ((mumps_files+type)->mumps_io_current_file)->write_pos=0;
143 ((mumps_files+type)->mumps_io_current_file)->is_opened=1;
144 /* printf("new file created -> num = %d \n", ((mumps_files+type)->mumps_io_last_file_opened));*/
145 /* printf("new file created %d\n",mumps_io_current_file_number);*/
146 return 0;
147}
149 file_arg->current_pos=file_arg->write_pos;
150/* mumps_io_current_file_position=mumps_io_write_pos; */
151}
152MUMPS_INT mumps_compute_where_to_write(const double to_be_written,const MUMPS_INT type,long long vaddr,size_t already_written){
153 /* Check if the current file has enough memory to receive the whole block*/
154 MUMPS_INT ret_code;
155 MUMPS_INT file;
156 mumps_file_struct *current_file;
157 long long vaddr_loc;
158 MUMPS_INT pos;
159 /* Virtual address based file management scheme */
160 vaddr_loc=vaddr*(long long)mumps_elementary_data_size+(long long)already_written;
161 mumps_gen_file_info(vaddr_loc,&pos,&file);
162 ret_code=mumps_set_file(type,file);
163 if(ret_code<0){
164 return ret_code;
165 }
166 current_file=(mumps_files+type)->mumps_io_current_file;
167 current_file->write_pos=pos;
169 return 0;
170}
171MUMPS_INT mumps_prepare_pointers_for_write(double to_be_written,MUMPS_INT * pos_in_file, MUMPS_INT * file_number,const MUMPS_INT type,long long vaddr,size_t already_written){
172 MUMPS_INT ret_code;
173 ret_code=mumps_compute_where_to_write(to_be_written,type,vaddr,already_written);
174 if(ret_code<0){
175 return ret_code;
176 }
177 *pos_in_file=((mumps_files+type)->mumps_io_current_file)->current_pos;
178 /* should be modified to take into account the file arg */
179 *file_number=(mumps_files+type)->mumps_io_current_file_number;
180 return 0;
181}
183 *file=(MUMPS_INT)(vaddr/(long long)mumps_io_max_file_size);
184 *pos=(MUMPS_INT)(vaddr%(long long)mumps_io_max_file_size);
185 return 0;
186}
187MUMPS_INT mumps_compute_nb_concerned_files(long long block_size, MUMPS_INT * nb_concerned_files,long long vaddr){
188 MUMPS_INT file,pos,available_size;
189 long long vaddr_loc;
190 vaddr_loc=vaddr*(long long)mumps_elementary_data_size;
191 mumps_gen_file_info(vaddr_loc,&pos,&file);
192 available_size=mumps_io_max_file_size-pos+1;
193 *nb_concerned_files=(MUMPS_INT)my_ceil((double)(my_max(0,((block_size)*(double)(mumps_elementary_data_size))-available_size))/(double)mumps_io_max_file_size)+1;
194 return 0;
195}
197 long long block_size,
198 MUMPS_INT * type_arg,
199 long long vaddr,
200 MUMPS_INT * ierr){
201 /* Type of fwrite : size_t fwrite(const void *ptr, size_t size,
202 *size_t nmemb, FILE *stream); */
203 size_t write_size;
204 MUMPS_INT i;
205 MUMPS_INT nb_concerned_files=0;
206 MUMPS_INT ret_code,file_number_loc,pos_in_file_loc;
207 double to_be_written;
208#if ! defined( MUMPS_WIN32 )
209 MUMPS_INT* file;
210#else
211 FILE** file;
212#endif
213 MUMPS_INT where;
214 void* loc_addr;
215 MUMPS_INT type;
216 size_t already_written=0;
217 char buf[64];
218 type=*type_arg;
219 loc_addr=address_block;
220 mumps_compute_nb_concerned_files(block_size,&nb_concerned_files,vaddr);
221 to_be_written=((double)mumps_elementary_data_size)*((double)(block_size));
222 /* printf("nb_concerned -> %d | %lf \n",nb_concerned_files,to_be_written); */
223 for(i=0;i<nb_concerned_files;i++){
224#if ! defined( MUMPS_WIN32 ) && ! defined (WITHOUT_PTHREAD)
225# ifdef WITH_PFUNC
227 mumps_io_protect_pointers();
228 }
229# endif
230#endif
231 ret_code=mumps_prepare_pointers_for_write(to_be_written,&pos_in_file_loc,&file_number_loc,type,vaddr,already_written);
232 if(ret_code<0){
233#if ! defined( MUMPS_WIN32 ) && ! defined (WITHOUT_PTHREAD)
234# ifdef WITH_PFUNC
236 mumps_io_unprotect_pointers();
237 }
238# endif
239#endif
240 return ret_code;
241 }
242 if((double)(mumps_io_max_file_size-((mumps_files+type)->mumps_io_current_file)->write_pos)>to_be_written){
243 write_size=(size_t)to_be_written;
244 already_written=(size_t)to_be_written;
245 }else{
246 write_size=(size_t)((double)(mumps_io_max_file_size-((mumps_files+type)->mumps_io_current_file)->write_pos));
247 already_written=already_written+(size_t)write_size;
248 }
249#if defined( MUMPS_WIN32 )
250 write_size=(size_t)(MUMPS_INT)((write_size)/mumps_elementary_data_size);
251#endif
252 file=&(((mumps_files+type)->mumps_io_current_file)->file);
253 where=((mumps_files+type)->mumps_io_current_file)->write_pos;
254#if ! defined( MUMPS_WIN32 ) && ! defined (WITHOUT_PTHREAD)
255# ifdef WITH_PFUNC
257 mumps_io_unprotect_pointers();
258 }
259# endif
260#endif
261 ret_code=mumps_io_write__(file,loc_addr,write_size,where,type);
262 if(ret_code<0){
263 return ret_code;
264 }
265#if ! defined( MUMPS_WIN32 ) && ! defined (WITHOUT_PTHREAD)
266# ifdef WITH_PFUNC
268 mumps_io_protect_pointers();
269 }
270# endif
271#endif
272#if ! defined( MUMPS_WIN32 )
273 ((mumps_files+type)->mumps_io_current_file)->write_pos=((mumps_files+type)->mumps_io_current_file)->write_pos+((MUMPS_INT)write_size);
274 to_be_written=to_be_written-((MUMPS_INT)write_size);
275 loc_addr=(void*)((size_t)loc_addr+write_size);
276/* mumps_io_write_pos=mumps_io_write_pos+((MUMPS_INT)write_size); */
277/* to_be_written=to_be_written-((MUMPS_INT)write_size); */
278/* loc_addr=(void*)((size_t)loc_addr+write_size); */
279#else
280 /* fread and write */
281 ((mumps_files+type)->mumps_io_current_file)->write_pos=((mumps_files+type)->mumps_io_current_file)->write_pos+((MUMPS_INT)write_size*mumps_elementary_data_size);
282 to_be_written=to_be_written-((MUMPS_INT)write_size*mumps_elementary_data_size);
283 loc_addr=(void*)((size_t)loc_addr+(size_t)((MUMPS_INT)write_size*mumps_elementary_data_size));
284/* mumps_io_write_pos=mumps_io_write_pos+((MUMPS_INT)write_size*mumps_elementary_data_size); */
285/* to_be_written=to_be_written-((MUMPS_INT)write_size*mumps_elementary_data_size); */
286/* loc_addr=(void*)((size_t)loc_addr+(size_t)((MUMPS_INT)write_size*mumps_elementary_data_size)); */
287#endif
288#if ! defined( MUMPS_WIN32 ) && ! defined (WITHOUT_PTHREAD)
289# ifdef WITH_PFUNC
291 mumps_io_unprotect_pointers();
292 }
293# endif
294#endif
295 }
296 if(to_be_written!=0){
297 *ierr = -90;
298 sprintf(buf,"Internal (1) error in low-level I/O operation %lf",to_be_written);
299 return mumps_io_error(*ierr,buf);
300 }
301 /* printf("write ok -> %d \n");*/
302 return 0;
303}
305 long long block_size,
306 MUMPS_INT * type_arg,
307 long long vaddr,
308 MUMPS_INT * ierr){
309 size_t size;
310#if ! defined( MUMPS_WIN32 )
311 MUMPS_INT* file;
312#else
313 FILE** file;
314#endif
315 double read_size;
316 MUMPS_INT local_fnum,local_offset;
317 void *loc_addr;
318 long long vaddr_loc;
319 MUMPS_INT type;
320 type=*type_arg;
321 /* if(((double)(*block_size))*((double)(mumps_elementary_data_size))>(double)mumps_io_max_file_size){
322 sprintf(error_str,"Internal error in low-level I/O operation (requested size too big for file system) \n");
323 return -90;
324 }*/
325 if(block_size==0){
326 return 0;
327 }
328 read_size=(double)mumps_elementary_data_size*(double)(block_size);
329 /* if((*file_number<0)&&(read_size<(double)mumps_io_max_file_size)){
330 sprintf(error_str,"Internal error (1) in low level read op\n");
331 return -90;
332 }*/
333 loc_addr=address_block;
334 vaddr_loc=vaddr*(long long)mumps_elementary_data_size;
335 while(read_size>0){
336 /* Virtual addressing based management stuff */
337 local_fnum=(MUMPS_INT)(vaddr_loc/(long long)mumps_io_max_file_size);
338 local_offset=(MUMPS_INT)(vaddr_loc%(long long)mumps_io_max_file_size);
339 file=&((((mumps_files+type)->mumps_io_pfile_pointer_array)+local_fnum)->file);
340 /* printf("1 read | file -> %d | fnum -> %d | vaddr -> %d \n",*file,local_fnum,(MUMPS_INT)vaddr_loc); */
341#if ! defined( MUMPS_WIN32 )
342 if(read_size+(double)local_offset>(double)mumps_io_max_file_size){
343 size=(size_t)mumps_io_max_file_size-(size_t)local_offset;
344 }else{
345 size=(size_t)read_size;
346 }
347#else
348 if(read_size+(double)local_offset>(double)mumps_io_max_file_size){
349 size=((size_t)mumps_io_max_file_size-(size_t)local_offset)/(size_t)mumps_elementary_data_size;
350 }else{
351 size=(size_t)(read_size/mumps_elementary_data_size);
352 }
353#endif
354 *ierr=mumps_io_read__(file,loc_addr,size,local_offset,type);
355 if(*ierr<0){
356 return *ierr;
357 }
358#if defined( MUMPS_WIN32 )
360#endif
361 vaddr_loc=vaddr_loc+(long long)size;
362 read_size=read_size-(double)size;
363 loc_addr=(void*)((size_t)loc_addr+size);
364 local_fnum++;
365 local_offset=0;
366 if(local_fnum>(mumps_files+type)->mumps_io_nb_file){
367 *ierr = -90;
368 return mumps_io_error(*ierr,"Internal error (2) in low level read op\n");
369 }
370 }
371 return 0;
372}
374 MUMPS_INT i,j,bound,ierr;
375/* Free prefix only for facto */
376 if (*step == 0) free(mumps_ooc_file_prefix);
377 if(mumps_files == NULL )
378 return 0;
379#if ! defined( MUMPS_WIN32 )
380#endif
382/* if(*step==0){ */
383/* /\* factorization *\/ */
384/* bound=NB_FILE_TYPE_FACTO; */
385/* }else{ */
386/* /\* solve *\/ */
387/* bound=NB_FILE_TYPE_SOLVE; */
388/* } */
389 for(j=0;j<bound;j++){
390 if( mumps_files[j].mumps_io_pfile_pointer_array == NULL ) {
391 continue;
392 }
393 for(i=0;i<(mumps_files+j)->mumps_io_nb_file_opened;i++){
394#if ! defined( MUMPS_WIN32 )
395 ierr=close((((mumps_files+j)->mumps_io_pfile_pointer_array)+i)->file);
396 if(ierr==-1){
397 return mumps_io_sys_error(-90,"Problem while closing OOC file");
398 }
399#else
400 ierr=fclose((((mumps_files+j)->mumps_io_pfile_pointer_array)+i)->file);
401 if(ierr==-1){
402 return mumps_io_error(-90,"Problem while closing OOC file\n");
403 }
404#endif
405 /* free(*(mumps_io_pfile_name+i)); */
406 }
407 free((mumps_files+j)->mumps_io_pfile_pointer_array);
408 }
409/* free(mumps_io_pfile_name); */
410 free(mumps_files);
411#if ! defined( MUMPS_WIN32 )
412#endif
413 return 0;
414}
415/* Initialize the mumps_file_type structure at <which>th position in
416 mumps_files. It only set values with no allocation to avoid any errors. */
418{
419 (mumps_files+which)->mumps_io_current_file_number = -1;
420 (mumps_files+which)->mumps_io_last_file_opened = -1;
421 (mumps_files+which)->mumps_io_nb_file_opened = 0;
422 (mumps_files+which)->mumps_io_nb_file=*nb;
423 (mumps_files+which)->mumps_io_pfile_pointer_array = NULL;
424 (mumps_files+which)->mumps_io_current_file=NULL;
425}
426/* Allocate the file structures for factor files and initialize the is_opened filed to 0 */
428{
429 MUMPS_INT i;
430 (mumps_files+which)->mumps_io_pfile_pointer_array=(mumps_file_struct *)malloc((*nb)*sizeof(mumps_file_struct));
431 if((mumps_files+which)->mumps_io_pfile_pointer_array==NULL){
432 return mumps_io_error(-13,"Allocation problem in low-level OOC layer\n");
433 }
434 for(i=0;i<*nb;i++){
435 (((mumps_files+which)->mumps_io_pfile_pointer_array)+i)->is_opened=0;
436 }
437 return 0;
438}
439MUMPS_INT mumps_init_file_structure(MUMPS_INT* _myid, long long *total_size_io,MUMPS_INT *size_element,MUMPS_INT *nb_file_type,MUMPS_INT *flag_tab)
440{
441 /* Computes the number of files needed. Uses ceil value. */
442 MUMPS_INT ierr;
443#if ! defined( MUMPS_WIN32 )
444 MUMPS_INT mumps_flag_open;
445#endif
446 MUMPS_INT i,nb;
447 MUMPS_INT mumps_io_nb_file;
449 mumps_io_nb_file_type=*nb_file_type;
450 mumps_io_nb_file=(MUMPS_INT)((((double)(*total_size_io)*1000000)*((double)(*size_element)))/(double)mumps_io_max_file_size)+1;
452#if ! defined( MUMPS_WIN32 )
453 mumps_flag_open=0;
454#endif
455 mumps_io_myid=*_myid;
456 mumps_elementary_data_size=*size_element;
457 /* Allocates the memory necessary to handle the file pointer array.*/
459 if(mumps_files==NULL){
460 return mumps_io_error(-13,"Allocation problem in low-level OOC layer\n");
461 }
462 /* Safe initialization of the mumps_file_type elements */
463 for(i=0;i<mumps_io_nb_file_type;i++){
464 nb=(flag_tab[i]==0||flag_tab[i]==1) ? mumps_io_nb_file : 1;
466 }
467 ierr=0;
468 for(i=0;i<mumps_io_nb_file_type;i++){
469 switch(flag_tab[i]){
470 case 0:
471#if ! defined( MUMPS_WIN32 )
472 (mumps_files+i)->mumps_flag_open=mumps_flag_open|O_WRONLY|O_CREAT|O_TRUNC;
473# if defined(__MINGW32__)
474 /* O_BINARY necessary */
475 (mumps_files+i)->mumps_flag_open=(mumps_files+i)->mumps_flag_open|O_BINARY;
476# endif
477#else
478 strcpy((mumps_files+i)->mumps_flag_open,"wb");
479#endif
480 break;
481 case 1:
482#if ! defined( MUMPS_WIN32 )
483 (mumps_files+i)->mumps_flag_open=mumps_flag_open|O_RDONLY|O_CREAT|O_TRUNC;
484# if defined(__MINGW32__)
485 /* O_BINARY necessary */
486 (mumps_files+i)->mumps_flag_open=(mumps_files+i)->mumps_flag_open|O_BINARY;
487# endif
488#else
489 strcpy((mumps_files+i)->mumps_flag_open,"rb");
490#endif
491 break;
492 case 2:
493#if ! defined( MUMPS_WIN32 )
494 (mumps_files+i)->mumps_flag_open=mumps_flag_open|O_RDWR|O_CREAT|O_TRUNC;
495# if defined(__MINGW32__)
496 /* O_BINARY necessary */
497 (mumps_files+i)->mumps_flag_open=(mumps_files+i)->mumps_flag_open|O_BINARY;
498# endif
499#else
500 strcpy((mumps_files+i)->mumps_flag_open,"rwb");
501#endif
502 break;
503 default:
504 return mumps_io_error(-90,"unknown value of flag_open\n");
505 }
506 ierr=mumps_io_alloc_file_struct(&nb,i);
507 if(ierr<0){
508 return ierr;
509 }
510 ierr=mumps_set_file(i,0);
511 if(ierr<0){
512 return ierr;
513 }
514 }
515 /* Init the current file.*/
516 return 0;
517}
518MUMPS_INT mumps_init_file_name(char* mumps_dir,char* mumps_file,
519 MUMPS_INT* mumps_dim_dir,MUMPS_INT* mumps_dim_file,MUMPS_INT* _myid){
520 MUMPS_INT i;
521 char *tmp_dir,*tmp_fname;
522 char base_name[20];
523 MUMPS_INT dir_flag=0,file_flag=0;
524 char mumps_base[10]="mumps_";
525 tmp_dir=(char *)malloc(((*mumps_dim_dir)+1)*sizeof(char));
526 if(tmp_dir==NULL){
527 return mumps_io_error(-13,"Allocation problem in low-level OOC layer\n");
528 }
529 tmp_fname=(char *)malloc(((*mumps_dim_file)+1)*sizeof(char));
530 if(tmp_fname==NULL){
531 return mumps_io_error(-13,"Allocation problem in low-level OOC layer\n");
532 }
533 for(i=0;i<*mumps_dim_dir;i++){
534 tmp_dir[i]=mumps_dir[i];
535 }
536 tmp_dir[i]=0;
537 for(i=0;i<*mumps_dim_file;i++){
538 tmp_fname[i]=mumps_file[i];
539 }
540 tmp_fname[i]=0;
541 if(strcmp(tmp_dir,UNITIALIZED)==0){
542 dir_flag=1;
543 free(tmp_dir);
544 tmp_dir=getenv("MUMPS_OOC_TMPDIR");
545 if(tmp_dir==NULL){
546#ifdef _AIX
547# ifndef CINES_
548 tmp_dir=getenv("TMPDIR");
549 if(tmp_dir==NULL){
550 tmp_dir=MUMPS_OOC_DEFAULT_DIR;
551 }
552# else
553 tmp_dir=MUMPS_OOC_DEFAULT_DIR;
554# endif
555#else
556 tmp_dir=MUMPS_OOC_DEFAULT_DIR;
557#endif
558 }
559 }
560 if(strcmp(tmp_fname,UNITIALIZED)==0){
561 free(tmp_fname);
562 tmp_fname=getenv("MUMPS_OOC_PREFIX");
563 file_flag=1;
564 }
565 if(tmp_fname!=NULL){
566#if ! defined( MUMPS_WIN32 )
567 sprintf(base_name,"_%s%d_XXXXXX",mumps_base,(int)*_myid);
568#else
569 sprintf(base_name,"_%s%d",mumps_base,*_myid);
570#endif
571 mumps_ooc_file_prefix=(char *)malloc((strlen(SEPARATOR)+strlen(tmp_dir)+strlen(tmp_fname)+strlen(base_name)+1+1)*sizeof(char));
572 if(mumps_ooc_file_prefix==NULL){
573 return mumps_io_error(-13,"Allocation problem in low-level OOC layer\n");
574 }
575 sprintf(mumps_ooc_file_prefix,"%s%s%s%s",tmp_dir,SEPARATOR,tmp_fname,base_name);
576 }else{
577#if ! defined( MUMPS_WIN32 )
578 sprintf(base_name,"%s%s%d_XXXXXX",SEPARATOR,mumps_base,(int)*_myid);
579#else
580 sprintf(base_name,"%s%s%d",SEPARATOR,mumps_base,*_myid);
581#endif
582 mumps_ooc_file_prefix=(char *)malloc((strlen(SEPARATOR)+strlen(tmp_dir)+strlen(base_name)+1)*sizeof(char));
583 if(mumps_ooc_file_prefix==NULL){
584 return mumps_io_error(-13,"Allocation problem in low-level OOC layer\n");
585 }
586 sprintf(mumps_ooc_file_prefix,"%s%s%s",tmp_dir,SEPARATOR,base_name);
587 }
588 if(!dir_flag){
589 free(tmp_dir);
590 }
591 if(!file_flag){
592 free(tmp_fname);
593 }
594 return 0;
595}
597 *nb_files=((mumps_files+*type)->mumps_io_last_file_opened)+1;
598 return 0;
599}
601 MUMPS_INT i;
602 i=(*indice)-1;
603 strcpy(name,(((mumps_files+*type)->mumps_io_pfile_pointer_array)+i)->name);
604 *length=(MUMPS_INT)strlen(name)+1;
605 return 0;
606}
608 MUMPS_INT ierr;
609 MUMPS_INT i;
610 /* This is called by solve step, we have only one type of files */
611 mumps_io_nb_file_type=*nb_file_type;
613 if(mumps_files==NULL){
614 return mumps_io_error(-13,"Allocation problem in low-level OOC layer\n");
615 }
616 for(i=0;i<mumps_io_nb_file_type;i++){
618 ierr=mumps_io_alloc_file_struct(dim+i,i);
619 if(ierr<0){
620 return ierr;
621 }
622 }
623 return 0;
624}
625MUMPS_INT mumps_io_init_vars(MUMPS_INT* myid_arg,MUMPS_INT* size_element,MUMPS_INT* async_arg){
626#if ! defined( MUMPS_WIN32 )
627 MUMPS_INT mumps_flag_open;
628#endif
629 MUMPS_INT i;
632#if ! defined( MUMPS_WIN32 )
633 mumps_flag_open=0;
634#endif
635 /* must be changed when we will have more than one file type during solve step */
636 for(i=0;i<mumps_io_nb_file_type;i++){
637#if ! defined( MUMPS_WIN32 )
638 (mumps_files+i)->mumps_flag_open=mumps_flag_open|O_RDONLY;
639#else
640 strcpy((mumps_files+i)->mumps_flag_open,"rb");
641#endif
642 }
643 mumps_io_myid=*myid_arg;
644 mumps_elementary_data_size=*size_element;
645 mumps_io_flag_async=*async_arg;
646 return 0;
647}
649 MUMPS_INT i;
650 i=(*indice)-1;
651/* *(mumps_io_pfile_name+i)=(char *) malloc((*length)*strlen(name)); */
652/* if(*(mumps_io_pfile_name+i)==NULL){ */
653/* sprintf(error_str,"Allocation problem in low-level OOC layer"); */
654/* return -13; */
655/* } */
656 strcpy((((mumps_files+*type)->mumps_io_pfile_pointer_array)+i)->name,name);
657 return 0;
658}
660 MUMPS_INT i,j;
661 mumps_file_struct *mumps_io_pfile_pointer_array;
662#if defined (sgi) || defined (__sgi)
663 struct dioattr dio;
664#endif
665 for(j=0;j<mumps_io_nb_file_type;j++){
666 mumps_io_pfile_pointer_array=(mumps_files+j)->mumps_io_pfile_pointer_array;
667 for(i=0;i<(mumps_files+j)->mumps_io_nb_file;i++){
668#if ! defined( MUMPS_WIN32 )
669 (mumps_io_pfile_pointer_array+i)->file=open((mumps_io_pfile_pointer_array+i)->name,(mumps_files+j)->mumps_flag_open);
670 if((mumps_io_pfile_pointer_array+i)->file==-1){
671 return mumps_io_sys_error(-90,"Problem while opening OOC file");
672 }
673#else
674 (mumps_io_pfile_pointer_array+i)->file=fopen((mumps_io_pfile_pointer_array+i)->name,(mumps_files+j)->mumps_flag_open);
675 if((mumps_io_pfile_pointer_array+i)->file==NULL){
676 return mumps_io_error(-90,"Problem while opening OOC file");
677 }
678 (mumps_io_pfile_pointer_array+i)->is_opened=1;
679#endif
680 }
681 }
682 return 0;
683}
685 (mumps_files+*type)->mumps_io_last_file_opened=*dim-1;
686 (mumps_files+*type)->mumps_io_nb_file_opened=*dim;
687 return 0;
688}
689#if ! defined( MUMPS_WIN32 ) && ! defined (WITHOUT_PTHREAD)
690# ifdef WITH_PFUNC
691MUMPS_INT mumps_io_protect_pointers(){
692 pthread_mutex_lock(&mumps_io_pwrite_mutex);
693 return 0;
694}
695MUMPS_INT mumps_io_unprotect_pointers(){
696 pthread_mutex_unlock(&mumps_io_pwrite_mutex);
697 return 0;
698}
699MUMPS_INT mumps_io_init_pointers_lock(){
700 pthread_mutex_init(&mumps_io_pwrite_mutex,NULL);
701 return 0;
702}
703MUMPS_INT mumps_io_destroy_pointers_lock(){
704 pthread_mutex_destroy(&mumps_io_pwrite_mutex);
705 return 0;
706}
707# endif /*WITH_PFUNC*/
708#endif /* _WIN32 && WITHOUT_PTHREAD */
709 MUMPS_INT mumps_io_read__(void * file,void * loc_addr,size_t size,MUMPS_INT local_offset,MUMPS_INT type){
710 MUMPS_INT ret_code;
711#if ! defined( MUMPS_WIN32 )
713 ret_code=mumps_io_read_os_buff__(file,loc_addr, size,local_offset);
714 if(ret_code<0){
715 return ret_code;
716 }
717 }
718#else
719 ret_code=mumps_io_read_win32__(file,loc_addr, size,local_offset);
720 if(ret_code<0){
721 return ret_code;
722 }
723#endif
724 return 0;
725}
726#if ! defined( MUMPS_WIN32 )
727MUMPS_INT mumps_io_read_os_buff__(void * file,void * loc_addr,size_t size,MUMPS_INT local_offset){
728 size_t ret_code;
729 /* printf("Read with buff %d %d %d\n",(MUMPS_INT) size, local_offset,*((MUMPS_INT *)file)); */
730# ifdef WITH_PFUNC
731 ret_code=pread(*(MUMPS_INT *)file,loc_addr,size,local_offset);
732# else
733 lseek(*(MUMPS_INT *)file,(long) local_offset,SEEK_SET);
734 ret_code=read(*(MUMPS_INT *)file,loc_addr,size);
735# endif
736 if((MUMPS_INT) ret_code==-1){
737 return mumps_io_sys_error(-90,"Problem with low level read");
738 }
739 return 0;
740}
741#endif
742#if defined( MUMPS_WIN32 )
743MUMPS_INT mumps_io_read_win32__(void * file,void * loc_addr,size_t size,MUMPS_INT local_offset){
744 size_t ret_code;
745 fseek(*(FILE **)file,(long) local_offset,SEEK_SET);
746 ret_code=fread(loc_addr,mumps_elementary_data_size,size,*(FILE **)file);
747 if((ret_code!=size)||(ferror(*(FILE**)file))){
748 return mumps_io_error(-90,"Problem with I/O operation\n");
749 }
750 return 0;
751}
752#endif
753MUMPS_INT mumps_io_write__(void *file, void *loc_addr, size_t write_size, MUMPS_INT where,MUMPS_INT type){
754 MUMPS_INT ret_code;
755#if ! defined( MUMPS_WIN32 )
757 ret_code=mumps_io_write_os_buff__(file,loc_addr, write_size,where);
758 if(ret_code<0){
759 return ret_code;
760 }
761 }
762#else
763 ret_code=mumps_io_write_win32__(file,loc_addr, write_size,where);
764 if(ret_code<0){
765 return ret_code;
766 }
767#endif
768 return 0;
769}
770#if ! defined( MUMPS_WIN32 )
771MUMPS_INT mumps_io_write_os_buff__(void *file, void *loc_addr, size_t write_size, MUMPS_INT where){
772 size_t ret_code;
773 /* printf("write with buff %d %d %d\n",(MUMPS_INT) write_size, where,*((MUMPS_INT *)file)); */
774# ifdef WITH_PFUNC
775 ret_code=pwrite(*(MUMPS_INT *)file,loc_addr,write_size,where);
776# else
777 /*in this case all the I/O's are made by the I/O thread => we don't
778 need to protect the file pointer.*/
779 lseek(*(MUMPS_INT *)file,(long)where,SEEK_SET);
780 ret_code=write(*(MUMPS_INT *)file,loc_addr,write_size);
781# endif
782 if((MUMPS_INT)ret_code==-1){
783 return mumps_io_sys_error(-90,"Problem with low level write");
784 } else if(ret_code!=write_size){
785 return mumps_io_error(-90,"Error not enough space on disk \n");
786 }
787 return 0;
788}
789#endif
790#if defined( MUMPS_WIN32 )
791MUMPS_INT mumps_io_write_win32__(void *file, void *loc_addr, size_t write_size, MUMPS_INT where){
792 size_t ret_code;
793 fseek(*(FILE **)file,(long)where,SEEK_SET);
794 ret_code=fwrite(loc_addr,mumps_elementary_data_size, write_size,*(FILE**)file);
795 if((ret_code!=write_size)||(ferror(*(FILE**)file))){
796 return mumps_io_error(-90,"Problem with I/O operation\n");
797 }
798 return 0;
799}
800#endif
801MUMPS_INT mumps_compute_file_size(void *file,size_t *size){
802 /* Compute the size of the file pointed by file and return it in
803 size */
804#if defined(MUMPS_WIN32)
805 /* This works well as soon as we don't use threads under WIN32 */
806 MUMPS_INT ret_code;
807 long pos=0;
808 /* Get the current position */
809 pos=ftell(*(FILE **)file);
810 /* Move the file pointer to the end of the file */
811 fseek(*(FILE **)file,0,SEEK_END);
812 /* Get the current position which is in fact the size */
813 *size=(size_t)ftell(*(FILE **)file);
814 /* Restore the old position */
815 fseek(*(FILE **)file,pos,SEEK_SET);
816#else
817 struct stat file_info;
818 /* fstat does everything :-) */
819 fstat(*(MUMPS_INT *)file, &file_info);
820 *size = (size_t)file_info.st_size;
821#endif
822 return 0;
823}
#define MUMPS_INT
#define MUMPS_INLINE
MUMPS_INT mumps_io_get_nb_files(MUMPS_INT *nb_files, const MUMPS_INT *type)
MUMPS_INT mumps_io_flag_async
MUMPS_INT mumps_io_set_file_name(MUMPS_INT *indice, char *name, MUMPS_INT *length, MUMPS_INT *type)
MUMPS_INT mumps_io_alloc_file_struct(MUMPS_INT *nb, MUMPS_INT which)
MUMPS_INT mumps_compute_file_size(void *file, size_t *size)
MUMPS_INT mumps_io_set_last_file(MUMPS_INT *dim, MUMPS_INT *type)
void mumps_update_current_file_position(mumps_file_struct *file_arg)
MUMPS_INT mumps_io_alloc_pointers(MUMPS_INT *nb_file_type, MUMPS_INT *dim)
MUMPS_INT mumps_io_max_file_size
MUMPS_INT mumps_prepare_pointers_for_write(double to_be_written, MUMPS_INT *pos_in_file, MUMPS_INT *file_number, const MUMPS_INT type, long long vaddr, size_t already_written)
MUMPS_INT mumps_io_init_vars(MUMPS_INT *myid_arg, MUMPS_INT *size_element, MUMPS_INT *async_arg)
MUMPS_INT mumps_compute_where_to_write(const double to_be_written, const MUMPS_INT type, long long vaddr, size_t already_written)
MUMPS_INT mumps_io_write__(void *file, void *loc_addr, size_t write_size, MUMPS_INT where, MUMPS_INT type)
MUMPS_INT mumps_init_file_structure(MUMPS_INT *_myid, long long *total_size_io, MUMPS_INT *size_element, MUMPS_INT *nb_file_type, MUMPS_INT *flag_tab)
MUMPS_INT mumps_compute_nb_concerned_files(long long block_size, MUMPS_INT *nb_concerned_files, long long vaddr)
MUMPS_INT mumps_io_read__(void *file, void *loc_addr, size_t size, MUMPS_INT local_offset, MUMPS_INT type)
MUMPS_INT mumps_set_file(MUMPS_INT type, MUMPS_INT file_number_arg)
MUMPS_INT mumps_io_read_os_buff__(void *file, void *loc_addr, size_t size, MUMPS_INT local_offset)
MUMPS_INT mumps_io_get_file_name(MUMPS_INT *indice, char *name, MUMPS_INT *length, MUMPS_INT *type)
MUMPS_INT mumps_init_file_name(char *mumps_dir, char *mumps_file, MUMPS_INT *mumps_dim_dir, MUMPS_INT *mumps_dim_file, MUMPS_INT *_myid)
MUMPS_INT mumps_io_write_os_buff__(void *file, void *loc_addr, size_t write_size, MUMPS_INT where)
MUMPS_INT mumps_io_open_files_for_read()
MUMPS_INT mumps_io_nb_file_type
MUMPS_INT mumps_directio_flag
MUMPS_INLINE MUMPS_INT mumps_gen_file_info(long long vaddr, MUMPS_INT *pos, MUMPS_INT *file)
MUMPS_INT mumps_io_is_init_called
char * mumps_ooc_file_prefix
MUMPS_INT mumps_io_do_read_block(void *address_block, long long block_size, MUMPS_INT *type_arg, long long vaddr, MUMPS_INT *ierr)
MUMPS_INT mumps_io_do_write_block(void *address_block, long long block_size, MUMPS_INT *type_arg, long long vaddr, MUMPS_INT *ierr)
MUMPS_INT mumps_io_myid
MUMPS_INT mumps_io_k211
MUMPS_INT mumps_elementary_data_size
MUMPS_INT mumps_free_file_pointers(MUMPS_INT *step)
void mumps_io_init_file_struct(MUMPS_INT *nb, MUMPS_INT which)
mumps_file_type * mumps_files
#define UNITIALIZED
#define IO_ASYNC_TH
struct __mumps_file_type mumps_file_type
struct __mumps_file_struct mumps_file_struct
#define my_ceil(x)
#define MUMPS_OOC_DEFAULT_DIR
#define MAX_FILE_SIZE
#define my_max(x, y)
#define SEPARATOR
MUMPS_INT mumps_io_sys_error(MUMPS_INT mumps_errno, const char *desc)
MUMPS_INT mumps_io_error(MUMPS_INT mumps_errno, const char *desc)