1 /*
2  * Copyright (c) 2008-2021, Christopher C. Hulbert
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions are met:
7  *
8  * 1. Redistributions of source code must retain the above copyright notice, this
9  *    list of conditions and the following disclaimer.
10  *
11  * 2. Redistributions in binary form must reproduce the above copyright notice,
12  *    this list of conditions and the following disclaimer in the documentation
13  *    and/or other materials provided with the distribution.
14  *
15  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
16  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
18  * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
19  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
21  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
22  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
23  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
24  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
25  */
26 
27 #ifndef MATIO_PRIVATE_H
28 #define MATIO_PRIVATE_H
29 
30 #include "matioConfig.h"
31 #include "matio.h"
32 #if HAVE_ZLIB
33 #include <zlib.h>
34 #endif
35 #if defined(MAT73) && MAT73
36 #include <hdf5.h>
37 #endif
38 
39 #ifndef EXTERN
40 #ifdef __cplusplus
41 #define EXTERN extern "C"
42 #else
43 #define EXTERN extern
44 #endif
45 #endif
46 
47 #if HAVE_ZLIB
48 #define ZLIB_BYTE_PTR(a) ((Bytef *)(a))
49 #endif
50 
51 #if !defined(READ_BLOCK_SIZE)
52 #define READ_BLOCK_SIZE (8192)
53 #endif
54 
55 #define _CAT(X, Y) X##Y
56 #define CAT(X, Y) _CAT(X, Y)
57 
58 /** @if mat_devman
59  * @brief Matlab MAT File information
60  *
61  * Contains information about a Matlab MAT file
62  * @ingroup mat_internal
63  * @endif
64  */
65 struct _mat_t
66 {
67     void *fp;            /**< File pointer for the MAT file */
68     char *header;        /**< MAT file header string */
69     char *subsys_offset; /**< Offset */
70     char *filename;      /**< Filename of the MAT file */
71     int version;         /**< MAT file version */
72     int byteswap;        /**< 1 if byte swapping is required, 0 otherwise */
73     int mode;            /**< Access mode */
74     long bof;            /**< Beginning of file not including any header */
75     size_t next_index;   /**< Index/File position of next variable to read */
76     size_t num_datasets; /**< Number of datasets in the file */
77 #if defined(MAT73) && MAT73
78     hid_t refs_id; /**< Id of the /#refs# group in HDF5 */
79 #endif
80     char **dir; /**< Names of the datasets in the file */
81 };
82 
83 /** @if mat_devman
84  * @brief internal structure for MAT variables
85  * @ingroup mat_internal
86  * @endif
87  */
88 struct matvar_internal
89 {
90 #if defined(MAT73) && MAT73
91     char *hdf5_name;     /**< Name */
92     hobj_ref_t hdf5_ref; /**< Reference */
93     hid_t id;            /**< Id */
94 #endif
95     long datapos;        /**< Offset from the beginning of the MAT file to the data */
96     unsigned num_fields; /**< Number of fields */
97     char **fieldnames;   /**< Pointer to fieldnames */
98 #if HAVE_ZLIB
99     z_streamp z; /**< zlib compression state */
100     void *data;  /**< Inflated data array */
101 #endif
102 };
103 
104 /* snprintf.c */
105 #if !HAVE_VSNPRINTF
106 int rpl_vsnprintf(char *, size_t, const char *, va_list);
107 #define mat_vsnprintf rpl_vsnprintf
108 #else
109 #define mat_vsnprintf vsnprintf
110 #endif /* !HAVE_VSNPRINTF */
111 #if !HAVE_SNPRINTF
112 int rpl_snprintf(char *, size_t, const char *, ...);
113 #define mat_snprintf rpl_snprintf
114 #else
115 #define mat_snprintf snprintf
116 #endif /* !HAVE_SNPRINTF */
117 #if !HAVE_VASPRINTF
118 int rpl_vasprintf(char **, const char *, va_list);
119 #define mat_vasprintf rpl_vasprintf
120 #else
121 #define mat_vasprintf vasprintf
122 #endif /* !HAVE_VASPRINTF */
123 #if !HAVE_ASPRINTF
124 int rpl_asprintf(char **, const char *, ...);
125 #define mat_asprintf rpl_asprintf
126 #else
127 #define mat_asprintf asprintf
128 #endif /* !HAVE_ASPRINTF */
129 
130 /* endian.c */
131 EXTERN double Mat_doubleSwap(double *a);
132 EXTERN float Mat_floatSwap(float *a);
133 #ifdef HAVE_MAT_INT64_T
134 EXTERN mat_int64_t Mat_int64Swap(mat_int64_t *a);
135 #endif /* HAVE_MAT_INT64_T */
136 #ifdef HAVE_MAT_UINT64_T
137 EXTERN mat_uint64_t Mat_uint64Swap(mat_uint64_t *a);
138 #endif /* HAVE_MAT_UINT64_T */
139 EXTERN mat_int32_t Mat_int32Swap(mat_int32_t *a);
140 EXTERN mat_uint32_t Mat_uint32Swap(mat_uint32_t *a);
141 EXTERN mat_int16_t Mat_int16Swap(mat_int16_t *a);
142 EXTERN mat_uint16_t Mat_uint16Swap(mat_uint16_t *a);
143 
144 /* read_data.c */
145 EXTERN size_t ReadDoubleData(mat_t *mat, double *data, enum matio_types data_type, size_t len);
146 EXTERN size_t ReadSingleData(mat_t *mat, float *data, enum matio_types data_type, size_t len);
147 #ifdef HAVE_MAT_INT64_T
148 EXTERN size_t ReadInt64Data(mat_t *mat, mat_int64_t *data, enum matio_types data_type, size_t len);
149 #endif /* HAVE_MAT_INT64_T */
150 #ifdef HAVE_MAT_UINT64_T
151 EXTERN size_t ReadUInt64Data(mat_t *mat, mat_uint64_t *data, enum matio_types data_type,
152                              size_t len);
153 #endif /* HAVE_MAT_UINT64_T */
154 EXTERN size_t ReadInt32Data(mat_t *mat, mat_int32_t *data, enum matio_types data_type, size_t len);
155 EXTERN size_t ReadUInt32Data(mat_t *mat, mat_uint32_t *data, enum matio_types data_type,
156                              size_t len);
157 EXTERN size_t ReadInt16Data(mat_t *mat, mat_int16_t *data, enum matio_types data_type, size_t len);
158 EXTERN size_t ReadUInt16Data(mat_t *mat, mat_uint16_t *data, enum matio_types data_type,
159                              size_t len);
160 EXTERN size_t ReadInt8Data(mat_t *mat, mat_int8_t *data, enum matio_types data_type, size_t len);
161 EXTERN size_t ReadUInt8Data(mat_t *mat, mat_uint8_t *data, enum matio_types data_type, size_t len);
162 EXTERN size_t ReadCharData(mat_t *mat, void *_data, enum matio_types data_type, size_t len);
163 EXTERN int ReadDataSlab1(mat_t *mat, void *data, enum matio_classes class_type,
164                          enum matio_types data_type, int start, int stride, int edge);
165 EXTERN int ReadDataSlab2(mat_t *mat, void *data, enum matio_classes class_type,
166                          enum matio_types data_type, size_t *dims, int *start, int *stride,
167                          int *edge);
168 EXTERN int ReadDataSlabN(mat_t *mat, void *data, enum matio_classes class_type,
169                          enum matio_types data_type, int rank, size_t *dims, int *start,
170                          int *stride, int *edge);
171 #if HAVE_ZLIB
172 EXTERN int ReadCompressedDoubleData(mat_t *mat, z_streamp z, double *data,
173                                     enum matio_types data_type, int len);
174 EXTERN int ReadCompressedSingleData(mat_t *mat, z_streamp z, float *data,
175                                     enum matio_types data_type, int len);
176 #ifdef HAVE_MAT_INT64_T
177 EXTERN int ReadCompressedInt64Data(mat_t *mat, z_streamp z, mat_int64_t *data,
178                                    enum matio_types data_type, int len);
179 #endif /* HAVE_MAT_INT64_T */
180 #ifdef HAVE_MAT_UINT64_T
181 EXTERN int ReadCompressedUInt64Data(mat_t *mat, z_streamp z, mat_uint64_t *data,
182                                     enum matio_types data_type, int len);
183 #endif /* HAVE_MAT_UINT64_T */
184 EXTERN int ReadCompressedInt32Data(mat_t *mat, z_streamp z, mat_int32_t *data,
185                                    enum matio_types data_type, int len);
186 EXTERN int ReadCompressedUInt32Data(mat_t *mat, z_streamp z, mat_uint32_t *data,
187                                     enum matio_types data_type, int len);
188 EXTERN int ReadCompressedInt16Data(mat_t *mat, z_streamp z, mat_int16_t *data,
189                                    enum matio_types data_type, int len);
190 EXTERN int ReadCompressedUInt16Data(mat_t *mat, z_streamp z, mat_uint16_t *data,
191                                     enum matio_types data_type, int len);
192 EXTERN int ReadCompressedInt8Data(mat_t *mat, z_streamp z, mat_int8_t *data,
193                                   enum matio_types data_type, int len);
194 EXTERN int ReadCompressedUInt8Data(mat_t *mat, z_streamp z, mat_uint8_t *data,
195                                    enum matio_types data_type, int len);
196 EXTERN int ReadCompressedCharData(mat_t *mat, z_streamp z, void *data, enum matio_types data_type,
197                                   size_t len);
198 EXTERN int ReadCompressedDataSlab1(mat_t *mat, z_streamp z, void *data,
199                                    enum matio_classes class_type, enum matio_types data_type,
200                                    int start, int stride, int edge);
201 EXTERN int ReadCompressedDataSlab2(mat_t *mat, z_streamp z, void *data,
202                                    enum matio_classes class_type, enum matio_types data_type,
203                                    size_t *dims, int *start, int *stride, int *edge);
204 EXTERN int ReadCompressedDataSlabN(mat_t *mat, z_streamp z, void *data,
205                                    enum matio_classes class_type, enum matio_types data_type,
206                                    int rank, size_t *dims, int *start, int *stride, int *edge);
207 
208 /* inflate.c */
209 EXTERN int InflateSkip(mat_t *mat, z_streamp z, int nBytes, size_t *bytesread);
210 EXTERN int InflateSkipData(mat_t *mat, z_streamp z, enum matio_types data_type, int len);
211 EXTERN int InflateRankDims(mat_t *mat, z_streamp z, void *buf, size_t nBytes, mat_uint32_t **dims,
212                            size_t *bytesread);
213 EXTERN int Inflate(mat_t *mat, z_streamp z, void *buf, unsigned int nBytes, size_t *bytesread);
214 EXTERN int InflateData(mat_t *mat, z_streamp z, void *buf, unsigned int nBytes);
215 #endif
216 
217 /* mat.c */
218 EXTERN mat_complex_split_t *ComplexMalloc(size_t nbytes);
219 EXTERN void ComplexFree(mat_complex_split_t *complex_data);
220 EXTERN enum matio_types ClassType2DataType(enum matio_classes class_type);
221 EXTERN int Add(size_t *res, size_t a, size_t b);
222 EXTERN int Mul(size_t *res, size_t a, size_t b);
223 EXTERN int Mat_MulDims(const matvar_t *matvar, size_t *nelems);
224 EXTERN int Read(void *buf, size_t size, size_t count, FILE *fp, size_t *bytesread);
225 EXTERN int IsEndOfFile(FILE *fp, long *fpos);
226 
227 /* io.c */
228 #if defined(_WIN32) && defined(_MSC_VER)
229 EXTERN wchar_t *utf82u(const char *src);
230 #endif
231 
232 #endif
233