%begin
%include "inc:util.imp"
%include "inc:region.imp"

%constinteger fmax=25
%conststring (31) %array name(1:fmax) = %c
"header_length", "image_type", "height", "width", "signed",
"fov_height", "fov_width", "stereo", "baseline", "vergence",
"gaze", "source_id", "processed", "date", "time",
"stop", "focus", "magic", "title", "subheader",
"x offset", "y offset", "aspect", "mapwidth", "maplen"

%constintegerarray type(0:fmax) = %c
-1,0,0,0,0,1,0,0,1,0,2,2,0,1,3,3,0,0,0,4, 1,0,0,0,0,0
!0=unsigned short 1=boolean 2=signed short 3=string(8),4=string(n)

%constintegerarray offset(0:fmax) = %c
-1,0,1,2,3,4,5,6,7,8,9,10,11,12,13,17,21,22,23,24, 250,251,252,253,254,255

%string (255) file, s
%integer i, f, fredno, len, m, n, c
%shortarray buff(0:511)

%routine read field(%integer f)
   !read buff field n.  Done this way in case of casting problems
   %integer i; %shortinteger s
   read(i)
   s = i
   buff(f) = s
%end

%routine dump field(%integer f)
   %integer c,i
   printstring(name(f)); spaces(12 - length(name(f)))
   printstring("(")
   %if type(f)=0 %start
      phex4(buff(offset(f)))
   %elseif type(f)=1
      %if buff(offset(f)) = 1 %then printstring("True") %else printstring("False")
   %elseif type(f)=2
      phex4(buff(offset(f)))
   %elseif type(f)=3
      %for i=0,1,3 %cycle
         c=buff(offset(f)+i); printsymbol(c>>8); printsymbol(c&255)
      %repeat
   %elseif type(f)=4
      %for i=0,1,127 %cycle
         c=buff(offset(f)+i)
         %exit %if c>>8&255=0
         printsymbol(c>>8)
         %exit %if c&255=0
         printsymbol(c&255)
      %repeat
   %finish
%end

%on 0 %start; ->abend; %finish

file = cli param
file = file.".iff" %if exists(file.".iff")
printline("File ".file." inaccessible") %and %stop %unless exists(file)

access file(file, 1, fredno, len)

printline("Reading bytes 0 to 1023")
read region(fredno, 0, 1024, byteinteger(addr(buff(0))))

printline("** Warning: ".file." is not a valid IFF file") %if buff(23)#16_8516
%cycle
   prompt("Field:")
   skipsymbol %while nextsymbol<'0'
   %if '0'<=nextsymbol<='9' %start
      read(f)
   %else
      readline(s)
      %for f=1, 1, fmax %cycle
         -> got it %if name(f) = s
      %repeat
      %exit
   %finish

got it:
   %if 1<=f<=fmax %start
      dump field(f)
      printstring("): ")

      prompt("Alter?")
      %cycle; readsymbol(c); %repeatuntil c&16_5F='Y' %or c&16_5F='N'
      %if c&16_5F='Y' %start
         prompt("New Value:  ")
         %if type(f)=0 %or type(f)=2 %start
            read field(offset(f))
         %elseif type(f)=4
            skipsymbol %while nextsymbol<=' '
            readline(s)
            s=s.tostring(0)
            string(addr(buff(offset(f)))) = s
         %finish
      %finish
   %elseif f=0
      %for f=1, 1, fmax %cycle
         dump field(f); newline
      %repeat
   %else
      printstring("Invalid field number ".itos(f,-1))
   %finish
   newline
%repeat

prompt("Write patches?:")
%cycle; readsymbol(c); %repeatuntil c&16_5F='Y' %or c&16_5F='N'
%if c&16_5F='Y' %start
   printline("Writing bytes 0 to 1023..")
   write region(fredno, 0, 1024, byteinteger(addr(buff(0))))
%finish

abend:
deaccess file(fredno)
%endofprogram
