@@ -258,8 +258,9 @@ module json_value_module
258258
259259 integer :: ichunk = 0 ! ! index in `chunk` for [[pop_char]]
260260 ! ! when `use_unformatted_stream=True`
261- character (kind= CK,len= stream_chunk_size) :: chunk = CK_' ' ! ! a chunk read from a stream file
262- ! ! when `use_unformatted_stream=True`
261+ integer :: filesize = 0 ! ! the file size when when `use_unformatted_stream=True`
262+ character (kind= CK,len= :),allocatable :: chunk ! ! a chunk read from a stream file
263+ ! ! when `use_unformatted_stream=True`
263264
264265 contains
265266
@@ -922,8 +923,11 @@ subroutine json_initialize(me,verbose,compact_reals,&
922923 me% char_count = 0
923924 me% line_count = 1
924925 me% ipos = 1
925- me% ichunk = 0
926- me% chunk = ' '
926+ if (use_unformatted_stream) then
927+ me% filesize = 0
928+ me% ichunk = 0
929+ me% chunk = repeat (' ' , stream_chunk_size) ! default chunk size
930+ end if
927931
928932#ifdef USE_UCS4
929933 ! reopen stdout and stderr with utf-8 encoding
@@ -8761,6 +8765,11 @@ subroutine json_parse_file(json, file, p, unit)
87618765
87628766 if (istat== 0 ) then
87638767
8768+ if (use_unformatted_stream) then
8769+ ! save the file save to be read:
8770+ inquire (unit= iunit, size= json% filesize, iostat= istat)
8771+ end if
8772+
87648773 ! create the value and associate the pointer
87658774 call json_value_create(p)
87668775
@@ -9926,7 +9935,7 @@ subroutine parse_string(json, unit, str, string)
99269935 character (kind= CK,len= :),allocatable :: error_message ! ! for string unescaping
99279936
99289937 ! at least return a blank string if there is a problem:
9929- string = repeat (space, chunk_size)
9938+ string = blank_chunk
99309939
99319940 if (.not. json% exception_thrown) then
99329941
@@ -9951,7 +9960,7 @@ subroutine parse_string(json, unit, str, string)
99519960 else
99529961
99539962 ! if the string is not big enough, then add another chunk:
9954- if (ip> len (string)) string = string // repeat (space, chunk_size)
9963+ if (ip> len (string)) string = string // blank_chunk
99559964
99569965 ! append to string:
99579966 string (ip:ip) = c
@@ -10067,7 +10076,7 @@ subroutine parse_number(json, unit, str, value)
1006710076
1006810077 if (.not. json% exception_thrown) then
1006910078
10070- tmp = repeat (space, chunk_size)
10079+ tmp = blank_chunk
1007110080 ip = 1
1007210081 first = .true.
1007310082 is_integer = .true. ! assume it may be an integer, unless otherwise determined
@@ -10091,7 +10100,7 @@ subroutine parse_number(json, unit, str, value)
1009110100
1009210101 ! add it to the string:
1009310102 ! tmp = tmp // c !...original
10094- if (ip> len (tmp)) tmp = tmp // repeat (space, chunk_size)
10103+ if (ip> len (tmp)) tmp = tmp // blank_chunk
1009510104 tmp(ip:ip) = c
1009610105 ip = ip + 1
1009710106
@@ -10101,15 +10110,15 @@ subroutine parse_number(json, unit, str, value)
1010110110
1010210111 ! add it to the string:
1010310112 ! tmp = tmp // c !...original
10104- if (ip> len (tmp)) tmp = tmp // repeat (space, chunk_size)
10113+ if (ip> len (tmp)) tmp = tmp // blank_chunk
1010510114 tmp(ip:ip) = c
1010610115 ip = ip + 1
1010710116
1010810117 case (CK_' 0' :CK_' 9' ) ! valid characters for numbers
1010910118
1011010119 ! add it to the string:
1011110120 ! tmp = tmp // c !...original
10112- if (ip> len (tmp)) tmp = tmp // repeat (space, chunk_size)
10121+ if (ip> len (tmp)) tmp = tmp // blank_chunk
1011310122 tmp(ip:ip) = c
1011410123 ip = ip + 1
1011510124
@@ -10177,10 +10186,6 @@ subroutine pop_char(json,unit,str,skip_ws,skip_comments,eof,popped)
1017710186 logical (LK) :: parsing_comment ! ! if we are in the process
1017810187 ! ! of parsing a comment line
1017910188
10180- logical ,parameter :: chunk_it = .true. ! ! if true, stream files are read in chunks,
10181- ! ! rather than one character at a time.
10182- ! ! this speeds up the parsing dramatically.
10183-
1018410189 if (.not. json% exception_thrown) then
1018510190
1018610191 eof = .false.
@@ -10213,32 +10218,36 @@ subroutine pop_char(json,unit,str,skip_ws,skip_comments,eof,popped)
1021310218 ! read the next character:
1021410219 if (use_unformatted_stream) then
1021510220
10216- if (chunk_it) then
10217- ! in this case, we read the file in chunks.
10218- ! if we already have the character we need ,
10219- ! then get it from the chunk. Otherwise,
10220- ! read another chunk
10221-
10222- if ( json% ichunk< 1 ) then
10223- json% ichunk = 0
10224- read (unit = unit,pos = json % ipos,iostat = ios) json % chunk
10225- else
10226- ios = 0
10221+ ! in this case, we read the file in chunks.
10222+ ! if we already have the character we need,
10223+ ! then get it from the chunk. Otherwise ,
10224+ ! read in another chunk.
10225+ if (json % ichunk < 1 ) then
10226+ ! read in a chunk:
10227+ json% ichunk = 0
10228+ if ( json% filesize < json % ipos + len (json % chunk) - 1 ) then
10229+ ! for the last chunk, we resize
10230+ ! it to the correct size:
10231+ json % chunk = repeat ( ' ' , json % filesize - json % ipos +1 )
1022710232 end if
10228- json% ichunk = json% ichunk + 1
10233+ read (unit= unit,pos= json% ipos,iostat= ios) json% chunk
10234+ else
10235+ ios = 0
10236+ end if
10237+ json% ichunk = json% ichunk + 1
10238+ if (json% ichunk> len (json% chunk)) then
10239+ ! check this just in case
10240+ ios = IOSTAT_END
10241+ else
10242+ ! get the next character from the chunk:
1022910243 c = json% chunk(json% ichunk:json% ichunk)
1023010244 if (json% ichunk== len (json% chunk)) then
10231- json% ichunk = 0 ! reset
10232- else
10233- ! we have to finish getting
10234- ! characters from this chunk:
10235- if (IS_IOSTAT_END(ios)) ios = 0
10245+ json% ichunk = 0 ! reset for next chunk
1023610246 end if
10237- else
10238- read (unit= unit,pos= json% ipos,iostat= ios) c
1023910247 end if
1024010248
1024110249 else
10250+ ! a formatted read:
1024210251 read (unit= unit,fmt= ' (A1)' ,advance= ' NO' ,iostat= ios) c
1024310252 end if
1024410253 json% ipos = json% ipos + 1
@@ -10333,7 +10342,7 @@ subroutine push_char(json,c)
1033310342
1033410343 ! in this case, c is ignored, and we just
1033510344 ! decrement the stream position counter:
10336- json% ipos = json% ipos - 1
10345+ json% ipos = json% ipos - 1
1033710346 json% ichunk = json% ichunk - 1
1033810347
1033910348 else
0 commit comments