2
2
! !
3
3
module fpm_filesystem
4
4
use ,intrinsic :: iso_fortran_env, only : stdin= >input_unit, stdout= >output_unit, stderr= >error_unit
5
+ use ,intrinsic :: iso_c_binding, only: c_new_line
5
6
use fpm_environment, only: get_os_type, &
6
7
OS_UNKNOWN, OS_LINUX, OS_MACOS, OS_WINDOWS, &
7
8
OS_CYGWIN, OS_SOLARIS, OS_FREEBSD, OS_OPENBSD
@@ -50,6 +51,8 @@ end function c_is_dir
50
51
end interface
51
52
#endif
52
53
54
+ integer , parameter :: max_line = 100000 ! ! maximum number of lines in a text file
55
+
53
56
contains
54
57
55
58
! > Extract filename from path with/without suffix
@@ -307,13 +310,27 @@ function read_lines_expanded(fh) result(lines)
307
310
type (string_t), allocatable :: lines(:)
308
311
309
312
integer :: i
310
- integer :: iostat
311
- character (len= :),allocatable :: line_buffer_read
313
+ integer :: length, count
314
+ character (len= :), allocatable :: content
315
+ integer , save :: idx(max_line) = 1
316
+
317
+ inquire (fh, size= length)
318
+ allocate (character (len= length) :: content)
319
+
320
+ ! read file into a single string
321
+ read (fh) content
322
+ count = 0
323
+ do i = 1 , length
324
+ if (content(i:i) == c_new_line) then
325
+ count = count + 1
326
+ idx(count + 1 ) = i + 1
327
+ end if
328
+ end do
312
329
313
- allocate ( lines(number_of_rows(fh)))
314
- do i = 1 , size (lines)
315
- call getline(fh, line_buffer_read, iostat)
316
- lines(i)% s = dilate(line_buffer_read )
330
+ ! allocate lines from file content string
331
+ allocate (lines(count) )
332
+ do i = 1 , count
333
+ allocate ( lines(i)% s, source = dilate(content(idx(i):idx(i + 1 ) - 1 )) )
317
334
end do
318
335
319
336
end function read_lines_expanded
@@ -324,11 +341,27 @@ function read_lines(fh) result(lines)
324
341
type (string_t), allocatable :: lines(:)
325
342
326
343
integer :: i
327
- integer :: iostat
344
+ integer :: length, count
345
+ character (len= :), allocatable :: content
346
+ integer , save :: idx(max_line) = 1
347
+
348
+ inquire (fh, size= length)
349
+ allocate (character (len= length) :: content)
350
+
351
+ ! read file into a single string
352
+ read (fh) content
353
+ count = 0
354
+ do i = 1 , length
355
+ if (content(i:i) == c_new_line) then
356
+ count = count + 1
357
+ idx(count + 1 ) = i + 1
358
+ end if
359
+ end do
328
360
329
- allocate (lines(number_of_rows(fh)))
330
- do i = 1 , size (lines)
331
- call getline(fh, lines(i)% s, iostat)
361
+ ! allocate lines from file content string
362
+ allocate (lines(count))
363
+ do i = 1 , count
364
+ allocate (lines(i)% s, source= content(idx(i):idx(i + 1 ) - 1 ))
332
365
end do
333
366
334
367
end function read_lines
0 commit comments