1 /* File: read_geogrid.c
3 Sample subroutine to read an array from the geogrid binary format.
5 Notes: Depending on the compiler and compiler flags, the name of
6 the read_geogrid() routine may need to be adjusted with respect
7 to the number of trailing underscores when calling from Fortran.
9 Michael G. Duda, NCAR/MMM
17 #define read_geogrid read_geogrid_
19 #ifdef _DOUBLEUNDERSCORE
20 #define read_geogrid read_geogrid__
24 #define LITTLE_ENDIAN 1
27 char * fname
, /* The name of the file to read from */
28 int * len
, /* The length of the filename */
29 float * rarray
, /* The array to be filled */
30 int * nx
, /* x-dimension of the array */
31 int * ny
, /* y-dimension of the array */
32 int * nz
, /* z-dimension of the array */
33 int * isigned
, /* 0=unsigned data, 1=signed data */
34 int * endian
, /* 0=big endian, 1=little endian */
35 float * scalefactor
, /* value to multiply array elements by before truncation to integers */
36 int * wordsize
, /* number of bytes to use for each array element */
39 size_t i
, cnt
, narray
;
45 char local_fname
[1024];
50 narray
= (size_t)(*nx
) * (size_t)(*ny
) * (size_t)(*nz
);
52 /* Make a null-terminated local copy of the filename */
53 strncpy(local_fname
,fname
,*len
);
54 local_fname
[*len
]='\0';
56 /* Attempt to open file for reading */
57 if (!(bfile
= fopen(local_fname
,"rb")))
63 /* Allocate memory to hold bytes from file and read data */
64 c
= (unsigned char *)malloc(sizeof(unsigned char)*(*wordsize
) * narray
);
65 cnt
= fread((void *)c
, sizeof(unsigned char), narray
*(size_t)(*wordsize
), bfile
);
76 Set up byte offsets for each wordsize depending on byte order.
77 A, B, C, D give the offsets of the LSB through MSB (i.e., for
78 word ABCD, A=MSB, D=LSB) in the array from the beginning of a word
80 if (*endian
== BIG_ENDIAN
) {
82 A3
= 0; B3
= 1; C3
= 2;
83 A4
= 0; B4
= 1; C4
= 2; D4
= 3;
87 C3
= 0; B3
= 1; A3
= 2;
88 D4
= 0; C4
= 1; B4
= 2; A4
= 3;
91 /* Convert words from native byte order */
94 for(i
=0; i
<narray
; i
++)
97 if ((*isigned
) && (ival
> (1 << 7))) ival
-= (1 << 8);
98 rarray
[i
] = (float)ival
;
103 for(i
=0; i
<narray
; i
++)
105 ival
= (int)((c
[2*i
+A2
]<<8) | (c
[2*i
+B2
]));
106 if ((*isigned
) && (ival
> (1 << 15))) ival
-= (1 << 16);
107 rarray
[i
] = (float)ival
;
112 for(i
=0; i
<narray
; i
++)
114 ival
= (int)((c
[3*i
+A3
]<<16) | (c
[3*i
+B3
]<<8) | c
[3*i
+C3
]);
115 if ((*isigned
) * (ival
> (1 << 23))) ival
-= (1 << 24);
116 rarray
[i
] = (float)ival
;
121 for(i
=0; i
<narray
; i
++)
123 ival
= (int)((c
[4*i
+A4
]<<24) | (c
[4*i
+B4
]<<16) | (c
[4*i
+C4
]<<8) | c
[4*i
+D4
]);
124 if ((*isigned
) && (ival
> (1 << 31))) ival
-= (1 << 32);
125 rarray
[i
] = (float)ival
;
132 /* Scale real-valued array by scalefactor */
133 if (*scalefactor
!= 1.0)
135 for (i
=0; i
<narray
; i
++)
136 rarray
[i
] = rarray
[i
] * (*scalefactor
);