annotate extra/NaN/src/xptopen.cpp @ 7574:7d52643b01c4 octave-forge

SPSS: decode some more header information - still not ready
author schloegl
date Tue, 21 Sep 2010 19:28:18 +0000
parents 123c5c0081cf
children c211a946f136
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
1 //-------------------------------------------------------------------
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
2 // C-MEX implementation of kth element - this function is part of the NaN-toolbox.
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
3 //
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
4 // usage: x = xptopen(filename)
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
5 // usage: x = xptopen(filename,'r')
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
6 // read filename and return variables in struct x
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
7
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
8 // usage: xptopen(filename,'w',x)
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
9 // save fields of struct x in filename
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
10
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
11 // usage: x = xptopen(filename,'a',x)
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
12 // append fields of struct x to filename
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
13 //
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
14 // References:
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
15 //
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
16 // This program is free software; you can redistribute it and/or modify
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
17 // it under the terms of the GNU General Public License as published by
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
18 // the Free Software Foundation; either version 3 of the License, or
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
19 // (at your option) any later version.
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
20 //
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
21 // This program is distributed in the hope that it will be useful,
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
22 // but WITHOUT ANY WARRANTY; without even the implied warranty of
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
23 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
24 // GNU General Public License for more details.
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
25 //
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
26 // You should have received a copy of the GNU General Public License
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
27 // along with this program; if not, see <http://www.gnu.org/licenses/>.
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
28 //
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
29 // $Id$
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
30 // Copyright (C) 2010 Alois Schloegl <a.schloegl@ieee.org>
7415
780e178d44f7 remove obsolete code; improve reading variable names (prevents seg-fault in some special case); write: put XPTOPEN into header; experimental date/time conversion
schloegl
parents: 7376
diff changeset
31 // This function is part of the NaN-toolbox
780e178d44f7 remove obsolete code; improve reading variable names (prevents seg-fault in some special case); write: put XPTOPEN into header; experimental date/time conversion
schloegl
parents: 7376
diff changeset
32 // http://biosig-consulting.com/matlab/NaN/
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
33 //
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
34 // References:
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
35 // [1] TS-140 THE RECORD LAYOUT OF A DATA SET IN SAS TRANSPORT (XPORT) FORMAT
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
36 // http://support.sas.com/techsup/technote/ts140.html
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
37 // [2] IBM floating point format
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
38 // http://en.wikipedia.org/wiki/IBM_Floating_Point_Architecture
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
39 // [3] see http://old.nabble.com/Re%3A-IBM-integer-and-double-formats-p20428979.html
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
40 // [4] STATA File Format
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
41 // http://www.stata.com/help.cgi?dta
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
42 // http://www.stata.com/help.cgi?dta_113
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
43 //-------------------------------------------------------------------
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
44
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
45 /*
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
46 SPSS file format
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
47 // http://cvs.savannah.gnu.org/pspp/doc/data-file-format.texi?root=pspp&content-type=text%2Fplain
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
48 */
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
49
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
50 #define TEST_CONVERSION 2 // 0: ieee754, 1: SAS converter (big endian bug), 2: experimental
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
51 #define DEBUG 0
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
52
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
53 #include <ctype.h>
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
54 #include <inttypes.h>
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
55 #include <math.h>
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
56 #include <stdio.h>
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
57 #include <string.h>
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
58 #include <time.h>
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
59 #include "mex.h"
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
60
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
61 #ifdef tmwtypes_h
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
62 #if (MX_API_VER<=0x07020000)
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
63 typedef int mwSize;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
64 typedef int mwIndex;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
65 #endif
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
66 #endif
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
67
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
68 #define NaN (0.0/0.0)
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
69 #define fix(m) (m<0 ? ceil(m) : floor(m))
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
70 #define max(a,b) (((a) > (b)) ? (a) : (b))
7415
780e178d44f7 remove obsolete code; improve reading variable names (prevents seg-fault in some special case); write: put XPTOPEN into header; experimental date/time conversion
schloegl
parents: 7376
diff changeset
71 #define min(a,b) (((a) < (b)) ? (a) : (b))
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
72
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
73
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
74 #ifdef __linux__
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
75 /* use byteswap macros from the host system, hopefully optimized ones ;-) */
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
76 #include <byteswap.h>
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
77 #endif
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
78
7490
123c5c0081cf Matlab/WIN32 support added
schloegl
parents: 7462
diff changeset
79 #ifdef _WIN32
123c5c0081cf Matlab/WIN32 support added
schloegl
parents: 7462
diff changeset
80 #define __LITTLE_ENDIAN 1234
123c5c0081cf Matlab/WIN32 support added
schloegl
parents: 7462
diff changeset
81 #define __BIG_ENDIAN 4321
123c5c0081cf Matlab/WIN32 support added
schloegl
parents: 7462
diff changeset
82 #define __BYTE_ORDER __LITTLE_ENDIAN
123c5c0081cf Matlab/WIN32 support added
schloegl
parents: 7462
diff changeset
83 #endif
123c5c0081cf Matlab/WIN32 support added
schloegl
parents: 7462
diff changeset
84
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
85 #ifndef _BYTESWAP_H
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
86 /* define our own version - needed for Max OS X*/
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
87 #define bswap_16(x) \
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
88 ((((x) & 0xff00) >> 8) | (((x) & 0x00ff) << 8))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
89
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
90 #define bswap_32(x) \
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
91 ((((x) & 0xff000000) >> 24) \
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
92 | (((x) & 0x00ff0000) >> 8) \
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
93 | (((x) & 0x0000ff00) << 8) \
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
94 | (((x) & 0x000000ff) << 24))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
95
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
96 #define bswap_64(x) \
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
97 ((((x) & 0xff00000000000000ull) >> 56) \
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
98 | (((x) & 0x00ff000000000000ull) >> 40) \
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
99 | (((x) & 0x0000ff0000000000ull) >> 24) \
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
100 | (((x) & 0x000000ff00000000ull) >> 8) \
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
101 | (((x) & 0x00000000ff000000ull) << 8) \
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
102 | (((x) & 0x0000000000ff0000ull) << 24) \
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
103 | (((x) & 0x000000000000ff00ull) << 40) \
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
104 | (((x) & 0x00000000000000ffull) << 56))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
105 #endif /* _BYTESWAP_H */
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
106
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
107
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
108 #if __BYTE_ORDER == __BIG_ENDIAN
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
109 #define l_endian_u16(x) ((uint16_t)bswap_16((uint16_t)(x)))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
110 #define l_endian_u32(x) ((uint32_t)bswap_32((uint32_t)(x)))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
111 #define l_endian_u64(x) ((uint64_t)bswap_64((uint64_t)(x)))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
112 #define l_endian_i16(x) ((int16_t)bswap_16((int16_t)(x)))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
113 #define l_endian_i32(x) ((int32_t)bswap_32((int32_t)(x)))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
114 #define l_endian_i64(x) ((int64_t)bswap_64((int64_t)(x)))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
115
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
116 #define b_endian_u16(x) ((uint16_t)(x))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
117 #define b_endian_u32(x) ((uint32_t)(x))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
118 #define b_endian_u64(x) ((uint64_t)(x))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
119 #define b_endian_i16(x) ((int16_t)(x))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
120 #define b_endian_i32(x) ((int32_t)(x))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
121 #define b_endian_i64(x) ((int64_t)(x))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
122
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
123 #elif __BYTE_ORDER==__LITTLE_ENDIAN
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
124 #define l_endian_u16(x) ((uint16_t)(x))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
125 #define l_endian_u32(x) ((uint32_t)(x))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
126 #define l_endian_u64(x) ((uint64_t)(x))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
127 #define l_endian_i16(x) ((int16_t)(x))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
128 #define l_endian_i32(x) ((int32_t)(x))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
129 #define l_endian_i64(x) ((int64_t)(x))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
130
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
131 #define b_endian_u16(x) ((uint16_t)bswap_16((uint16_t)(x)))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
132 #define b_endian_u32(x) ((uint32_t)bswap_32((uint32_t)(x)))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
133 #define b_endian_u64(x) ((uint64_t)bswap_64((uint64_t)(x)))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
134 #define b_endian_i16(x) ((int16_t)bswap_16((int16_t)(x)))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
135 #define b_endian_i32(x) ((int32_t)bswap_32((int32_t)(x)))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
136 #define b_endian_i64(x) ((int64_t)bswap_64((int64_t)(x)))
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
137
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
138 #endif /* __BYTE_ORDER */
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
139
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
140
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
141 double xpt2d(uint64_t x);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
142 uint64_t d2xpt(double x);
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
143 double tm_time2gdf_time(struct tm *t);
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
144
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
145 /*
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
146 compare first n characters of two strings, ignore case
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
147 */
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
148 int strncmpi(const char* str1, const char* str2, size_t n)
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
149 {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
150 unsigned int k=0;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
151 int r=0;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
152 while (!r && str1[k] && str2[k] && (k<n)) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
153 r = tolower(str1[k]) - tolower(str2[k]);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
154 k++;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
155 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
156 return(r);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
157 }
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
158
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
159 void mexFunction(int POutputCount, mxArray* POutput[], int PInputCount, const mxArray *PInputs[])
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
160 {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
161 const char L1[] = "HEADER RECORD*******LIBRARY HEADER RECORD!!!!!!!000000000000000000000000000000 ";
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
162 const char L2[] = "SAS SAS SASLIB 6.06 bsd4.2 13APR89:10:20:06";
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
163 const char L3[] = "";
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
164 const char L4[] = "HEADER RECORD*******MEMBER HEADER RECORD!!!!!!!000000000000000001600000000140 ";
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
165 const char L5[] = "HEADER RECORD*******DSCRPTR HEADER RECORD!!!!!!!000000000000000000000000000000 ";
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
166 const char L6[] = "SAS ABC SASLIB 6.06 bsd4.2 13APR89:10:20:06";
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
167 const char L7[] = "";
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
168 const char L8[] = "HEADER RECORD*******NAMESTR HEADER RECORD!!!!!!!000000000200000000000000000000 ";
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
169 const char LO[] = "HEADER RECORD*******OBS HEADER RECORD!!!!!!!000000000000000000000000000000 ";
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
170
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
171 const char DATEFORMAT[] = "%d%b%y:%H:%M:%S";
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
172 char *fn = NULL;
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
173 char Mode[3] = "r";
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
174 FILE *fid;
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
175 size_t count = 0, NS = 0, HeadLen0=80*8, HeadLen2=0, sz2 = 0, M=0;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
176 char H0[HeadLen0];
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
177 char *H2 = NULL;
7574
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
178 char SWAP = 0;
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
179
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
180 // check for proper number of input and output arguments
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
181 if ( PInputCount > 0 && mxGetClassID(PInputs[1])==mxCHAR_CLASS) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
182 size_t buflen = (mxGetM(PInputs[0]) * mxGetN(PInputs[0]) * sizeof(mxChar)) + 1;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
183 fn = (char*)malloc(buflen);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
184 mxGetString(PInputs[0], fn, buflen);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
185 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
186 else {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
187 mexPrintf("XPTOPEN read and writes the SAS Transport Format (*.xpt)\n");
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
188 mexPrintf("\n\tX = xptopen(filename)\n");
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
189 mexPrintf("\tX = xptopen(filename,'r')\n");
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
190 mexPrintf("\t\tread filename and return variables in struct X\n");
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
191 mexPrintf("\n\tX = xptopen(filename,'w',X)\n");
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
192 mexPrintf("\t\tsave fields of struct X in filename.\n\n");
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
193 mexPrintf("\tThe fields of X must be column vectors of equal length.\n");
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
194 mexPrintf("\tEach vector is either a numeric vector or a cell array of strings.\n");
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
195 mexPrintf("\nSupported data formats: SAS-XPT (rw), STATA(r).\n");
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
196 mexPrintf("\nThe SAS-XPT format stores Date/Time as numeric value counting the number of days since 1960-01-01.\n\n");
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
197 return;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
198 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
199 if ( PInputCount > 1)
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
200 if (mxGetClassID(PInputs[1])==mxCHAR_CLASS && mxGetNumberOfElements(PInputs[1])) {
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
201 mxGetString(PInputs[1],Mode,3);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
202 Mode[2]=0;
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
203 }
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
204
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
205 fid = fopen(fn,Mode);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
206 if (fid < 0) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
207 mexErrMsgTxt("Error XPTOPEN: cannot open file\n");
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
208 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
209
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
210 if (Mode[0]=='r' || Mode[0]=='a' ) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
211
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
212 count += fread(H0,1,80*8,fid);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
213 enum FileFormat {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
214 noFile, unknown, ARFF, SASXPT, SPSS, STATA
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
215 };
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
216 enum FileFormat TYPE; /* type of file format */
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
217 uint8_t LittleEndian; /* 1 if file is LittleEndian data format and 0 for big endian data format*/
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
218
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
219 TYPE = unknown;
7462
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
220 if (!memcmp(H0,"$FL2@(#) SPSS DATA FILE",27) || !memcmp(H0,"$FL2@(#) PASW STATISTICS DATA FILE",27)) {
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
221 /*
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
222 SPSS file format
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
223 */
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
224 TYPE = SPSS;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
225 switch (*(uint32_t*)(H0+64)) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
226 case 0x00000002:
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
227 case 0x00000003:
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
228 LittleEndian = 1;
7574
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
229 SWAP = __BYTE_ORDER==__BIG_ENDIAN;
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
230 NS = l_endian_u32(*(uint32_t*)(H0+68));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
231 M = l_endian_u32(*(uint32_t*)(H0+80));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
232 break;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
233 case 0x02000000:
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
234 case 0x03000000:
7574
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
235 SWAP = __BYTE_ORDER==__LITTLE_ENDIAN;
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
236 LittleEndian = 0;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
237 NS = b_endian_i32(*(uint32_t*)(H0+68));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
238 M = b_endian_i32(*(uint32_t*)(H0+80));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
239 break;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
240 default:
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
241 TYPE = unknown;
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
242 }
7574
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
243 NS = *(int32_t*)(H0+80);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
244 M = *(int32_t*)(H0+80);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
245 if (SWAP) {
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
246 NS = bswap_32(NS);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
247 M = bswap_32(M);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
248 }
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
249 HeadLen0 = 184;
7574
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
250 char *H2 = (char*)malloc(NS*32);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
251 size_t c2 = 0;
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
252
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
253 /*
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
254 Read Variable SPSS header
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
255 */
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
256 int ns = 0;
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
257 const char **ListOfVarNames = (const char**)malloc((NS+1) * sizeof(char*));
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
258 char *VarNames = (char*)malloc((NS+1) * sizeof(char) * 9);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
259 double *MISSINGS = (double*)malloc((NS+1) * sizeof(double));
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
260 for (uint32_t k=0; k<NS; k++) {
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
261 int32_t rec_type, type, FlagHasLabel, FlagMissing;
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
262 c2 += fread(&rec_type,1,4,fid);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
263 c2 += fread(&type,1,4,fid);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
264 c2 += fread(&FlagHasLabel,1,4,fid);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
265 c2 += fread(&FlagMissing,1,4,fid);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
266 fseek(fid,4,SEEK_CUR);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
267 if (SWAP) {
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
268 rec_type = bswap_32(rec_type);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
269 type = bswap_32(type);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
270 FlagHasLabel = bswap_32(FlagHasLabel);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
271 }
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
272 if (rec_type != 2) ;//error('invalid SPSS file');
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
273 c2 += fread(VarNames+9*ns,1,8,fid);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
274 VarNames[9*ns+8] = 0;
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
275 ListOfVarNames[ns] = VarNames+9*ns;
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
276 if (FlagHasLabel==1) {
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
277 int32_t LenLabel;
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
278 c2 += fread(&LenLabel,1,4,fid);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
279 if (SWAP) LenLabel = bswap_32(LenLabel);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
280 if (LenLabel%4) LenLabel += 4 - LenLabel % 4;
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
281 fseek(fid,LenLabel,SEEK_CUR);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
282 }
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
283 if (FlagMissing)
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
284 c2 += fread(MISSINGS+ns,1,8,fid);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
285
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
286 if (type != -1) ns++;
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
287 }
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
288
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
289
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
290 NS = ns;
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
291 mxArray **R = (mxArray**) mxMalloc(NS * sizeof(mxArray*));
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
292 /* ToDo:
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
293 EXTRACT data
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
294 */
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
295
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
296 /* convert into output */
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
297 POutput[0] = mxCreateStructMatrix(1, 1, NS, ListOfVarNames);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
298 for (uint32_t k = 0; k < NS; k++) {
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
299 mxSetField(POutput[0], 0, ListOfVarNames[k], R[k]);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
300 }
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
301
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
302 if (MISSINGS) free(MISSINGS);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
303 if (VarNames) free(VarNames);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
304 if (ListOfVarNames) free(ListOfVarNames);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
305 if (H2) free(H2);
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
306 }
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
307
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
308 if (TYPE == SPSS) {
7574
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
309 /*
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
310 The records must appear in the following order:
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
311 - File header record.
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
312 - Variable records.
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
313 - All pairs of value labels records and value label variables records,
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
314 if present.
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
315 - Document record, if present.
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
316 - Any of the following records, if present, in any order:
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
317 Machine integer info record.
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
318 Machine floating-point info record.
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
319 Variable display parameter record.
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
320 Long variable names record.
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
321 Miscellaneous informational records.
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
322 - Dictionary termination record.
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
323 - Data record.
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
324
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
325 */ ;
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
326 }
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
327 else if ((H0[0]==113 || H0[0]==114) && (H0[1]==1 || H0[1]==2) && H0[2]==1 && H0[3]==0) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
328 /*
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
329 STATA File Format
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
330 http://www.stata.com/help.cgi?dta
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
331 http://www.stata.com/help.cgi?dta_113
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
332 */
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
333 TYPE = STATA;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
334 // Header 119 bytes
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
335 LittleEndian = H0[1]==2;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
336 if (LittleEndian) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
337 NS = l_endian_u16(*(uint16_t*)(H0+4));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
338 M = l_endian_u32(*(uint32_t*)(H0+6));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
339 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
340 else {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
341 NS = b_endian_u16(*(uint16_t*)(H0+4));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
342 M = b_endian_u32(*(uint32_t*)(H0+6));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
343 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
344
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
345 // Descriptors
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
346 int fmtlen = (H0[0]==113) ? 12 : 49;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
347 fseek(fid,109,SEEK_SET);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
348 size_t HeadLen2 = 2+NS*(1+33+2+fmtlen+33+81);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
349 char *H1 = (char*)malloc(HeadLen2);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
350 fread(H1,1,HeadLen2,fid);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
351
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
352 // expansion fields
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
353 char typ; int32_t len,c;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
354 char flagSWAP = (((__BYTE_ORDER == __BIG_ENDIAN) && LittleEndian) || ((__BYTE_ORDER == __LITTLE_ENDIAN) && !LittleEndian));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
355 do {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
356 fread(&typ,1,1,fid);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
357 fread(&len,4,1,fid);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
358 if (flagSWAP) bswap_32(len);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
359 fseek(fid,len,SEEK_CUR);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
360 } while (len);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
361 uint8_t *typlist = (uint8_t*)H1;
7574
7d52643b01c4 SPSS: decode some more header information - still not ready
schloegl
parents: 7490
diff changeset
362
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
363 /*
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
364 char *varlist = H1+NS;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
365 char *srtlist;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
366 char *fmtlist = H1+NS*36+2;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
367 char *lbllist = H1+NS*(36+fmtlen)+2;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
368 */
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
369
7462
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
370 mxArray **R = (mxArray**) mxMalloc(NS*sizeof(mxArray*));
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
371 size_t *bi = (size_t*) malloc((NS+1)*sizeof(size_t*));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
372 const char **ListOfVarNames = (const char**)malloc(NS * sizeof(char*));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
373 bi[0] = 0;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
374 for (size_t k = 0; k < NS; k++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
375 size_t sz;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
376 ListOfVarNames[k] = H1+NS+33*k;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
377 switch (typlist[k]) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
378 case 0xfb: sz = 1; break;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
379 case 0xfc: sz = 2; break;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
380 case 0xfd: sz = 4; break;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
381 case 0xfe: sz = 4; break;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
382 case 0xff: sz = 8; break;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
383 otherwise: sz = typlist[k];
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
384 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
385 bi[k+1] = bi[k]+sz;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
386 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
387
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
388 // data
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
389 uint8_t *data = (uint8_t *) malloc(bi[NS] * M);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
390 fread(data, bi[NS], M, fid);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
391
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
392 char *f = (char*)malloc(bi[NS]+1);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
393 for (size_t k = 0; k < NS; k++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
394 switch (typlist[k]) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
395 case 0xfb:
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
396 R[k] = mxCreateDoubleMatrix(M, 1, mxREAL);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
397 for (size_t m = 0; m < M; m++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
398 int8_t d = *(int8_t*)(data+bi[k]+m*bi[NS]);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
399 ((double*)mxGetData(R[k]))[m] = (d>100) ? NaN : d;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
400 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
401 break;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
402 case 0xfc:
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
403 R[k] = mxCreateDoubleMatrix(M, 1, mxREAL);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
404 if (flagSWAP) for (size_t m = 0; m < M; m++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
405 int16_t d = (int16_t) bswap_16(*(uint16_t*)(data+bi[k]+m*bi[NS]));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
406 ((double*)mxGetData(R[k]))[m] = (d>32740) ? NaN : d;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
407 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
408 else for (size_t m = 0; m < M; m++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
409 int16_t d = *(int16_t*)(data+bi[k]+m*bi[NS]);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
410 ((double*)mxGetData(R[k]))[m] = (d>32740) ? NaN : d;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
411 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
412 break;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
413 case 0xfd:
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
414 R[k] = mxCreateDoubleMatrix(M, 1, mxREAL);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
415 if (flagSWAP) for (size_t m = 0; m < M; m++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
416 int32_t d = (int32_t)bswap_32(*(uint32_t*)(data+bi[k]+m*bi[NS]));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
417 ((double*)mxGetData(R[k]))[m] = (d>2147483620) ? NaN : d;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
418 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
419 else for (size_t m = 0; m < M; m++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
420 int32_t d = *(int32_t*)(data+bi[k]+m*bi[NS]);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
421 ((double*)mxGetData(R[k]))[m] = (d>2147483620) ? NaN : d;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
422 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
423 break;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
424 case 0xfe:
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
425 R[k] = mxCreateNumericMatrix(M, 1, mxSINGLE_CLASS, mxREAL);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
426 if (flagSWAP) for (size_t m = 0; m < M; m++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
427 ((uint32_t*)mxGetData(R[k]))[m] = bswap_32(*(uint32_t*)(data+bi[k]+m*bi[NS]));;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
428 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
429 else for (size_t m = 0; m < M; m++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
430 ((uint32_t*)mxGetData(R[k]))[m] = *(uint32_t*)(data+bi[k]+m*bi[NS]);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
431 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
432 break;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
433 case 0xff:
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
434 R[k] = mxCreateDoubleMatrix(M, 1, mxREAL);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
435 if (flagSWAP) for (size_t m = 0; m < M; m++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
436 ((uint64_t*)mxGetData(R[k]))[m] = bswap_64(*(uint64_t*)(data+bi[k]+m*bi[NS]));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
437 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
438 else for (size_t m = 0; m < M; m++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
439 ((uint64_t*)mxGetData(R[k]))[m] = *(uint64_t*)(data+bi[k]+m*bi[NS]);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
440 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
441 break;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
442 default:
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
443 R[k] = mxCreateCellMatrix(M, 1);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
444 size_t sz = typlist[k];
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
445 for (size_t m = 0; m < M; m++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
446 memcpy(f, data+bi[k]+m*bi[NS], sz);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
447 f[sz] = 0;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
448 mxSetCell(R[k], m, mxCreateString(f));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
449 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
450 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
451 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
452 if (f) free(f);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
453 if (H1) free(H1);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
454 if (bi) free(bi);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
455
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
456 /* convert into output */
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
457 POutput[0] = mxCreateStructMatrix(1, 1, NS, ListOfVarNames);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
458 for (size_t k = 0; k < NS; k++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
459 mxSetField(POutput[0], 0, ListOfVarNames[k], R[k]);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
460 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
461
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
462 if (ListOfVarNames) free(ListOfVarNames);
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
463 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
464
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
465 else if (H0[0]=='%' || H0[0]=='@') {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
466 /*
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
467 ARFF
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
468 */
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
469 TYPE = ARFF;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
470 rewind(fid);
7462
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
471
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
472 char *H1 = NULL;
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
473 count = 0;
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
474 size_t ns = 0;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
475 char *vartyp = NULL;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
476 char **datestr = NULL;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
477 const char **ListOfVarNames = NULL;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
478 mxArray **R = NULL;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
479 size_t m = 0;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
480
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
481 while (!feof(fid)) {
7462
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
482 HeadLen0 = max(1024,HeadLen0*2);
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
483 H1 = (char*)realloc(H1,HeadLen0);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
484 count += fread(H1+count,1,HeadLen0-count-1,fid);
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
485 }
7462
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
486 H1[count] = 0;
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
487
7462
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
488 switch (H1[count-1]) {
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
489 case 0x0a:
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
490 case 0x0d:
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
491 H1[count] = 0;
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
492 break;
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
493 default:
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
494 H1[count] = 0x0a;
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
495 }
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
496 H1[count+1] = 0;
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
497
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
498 char *line = strtok(H1,"\x0a\0x0d");
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
499
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
500 int status = 0;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
501 while (line) {
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
502
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
503 if (!strncmpi(line,"@relation",9)) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
504 status = 1;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
505 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
506
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
507 else if (status == 1 && !strncmpi(line,"@attribute",10)) {
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
508 if (ns<=NS) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
509 ns = max(16, ns*2);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
510 ListOfVarNames = (const char**)realloc(ListOfVarNames,ns*sizeof(char*));
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
511 vartyp = (char*)realloc(vartyp,ns*sizeof(char));
7462
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
512 R = (mxArray**) mxRealloc(R,ns*sizeof(mxArray*));
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
513 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
514 size_t k = 10;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
515 char *p1, *p2;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
516 while (isspace(line[k])) k++;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
517 p1 = line+k;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
518 while (!isspace(line[k])) k++;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
519 line[k++]=0;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
520 while (isspace(line[k])) k++;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
521 p2 = line+k;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
522
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
523 ListOfVarNames[NS] = p1;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
524 if (!strncmpi(p2,"numeric",7)) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
525 vartyp[NS] = 1;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
526 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
527 else if (!strncmpi(p2,"integer",7)) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
528 vartyp[NS] = 2;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
529 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
530 else if (!strncmpi(p2,"real",4)) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
531 vartyp[NS] = 3;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
532 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
533 else if (!strncmpi(p2,"string",6)) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
534 vartyp[NS] = 4;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
535 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
536 else if (!strncmpi(p2,"{",1)) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
537 vartyp[NS] = 5;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
538 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
539 else if (!strncmpi(p2,"date",4)) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
540 vartyp[NS] = 6;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
541 datestr = (char**)realloc(datestr,(NS+1)*sizeof(char*));
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
542 p2+=4;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
543 while (isspace(*p2)) p2++;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
544 datestr[NS] = p2;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
545 if (p2[0]==34) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
546 p2++;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
547 while (p2[0]!=34 && p2[0]) p2++;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
548 p2[1]=0;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
549 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
550 }
7462
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
551 else if (!strncmpi(p2,"relational",10)) {
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
552 vartyp[NS] = 7;
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
553 }
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
554 else vartyp[NS] = 99;
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
555
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
556 NS++;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
557 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
558
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
559 else if (status == 1 && !strncmpi(line,"@data",5)) {
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
560 status = 2;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
561 char *p = line;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
562 while (*p) p++; // goto end of current line
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
563 p++; // skip \x00
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
564 M = 0;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
565 while (*p) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
566 if (p[0]==0x0a || p[0]==0x0d) {
7462
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
567 // count number of <CR>
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
568 M++;
7462
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
569 // skip next char (deals with <CR><NL>)
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
570 p+=2;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
571 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
572 else p++;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
573 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
574 for (size_t k=0; k<NS; k++) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
575 if (vartyp[k]==4 || vartyp[k]==5)
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
576 R[k] = mxCreateCellMatrix(M, 1);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
577 else
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
578 R[k] = mxCreateDoubleMatrix(M, 1, mxREAL);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
579 }
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
580 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
581
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
582 else if (status == 2) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
583
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
584 size_t p = 0,k;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
585 for (ns = 0; ns<NS; ns++) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
586 // read next token
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
587 while (isspace(line[p])) p++;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
588 if (line[p]==39) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
589 p++; k=p;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
590 while (line[k]!=39 && line[k]) k++;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
591 // if (!line[k]) ; // error
7462
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
592 line[k++] = 0;
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
593 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
594 else
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
595 k=p;
7462
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
596 while (line[k] != ',' && line[k] != 0) k++;
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
597 line[k] = 0;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
598
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
599 if (vartyp[ns] < 4) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
600 double d = atof(line+p);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
601 *(mxGetPr(R[ns])+m) = d;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
602 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
603 else if (vartyp[ns] < 6) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
604 mxSetCell(R[ns], m, mxCreateString(line+p));
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
605 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
606 else if (vartyp[ns] == 6) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
607 size_t kk[6],n=0, N=strlen(datestr[ns]);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
608 char T0[6][5];
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
609 char ix = 0;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
610 struct tm t;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
611
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
612 for (n=0; n < N; n++) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
613 switch (datestr[ns][n]) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
614 case 'Y':
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
615 ix = 0;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
616 break;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
617 case 'M':
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
618 ix = 1;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
619 break;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
620 case 'd':
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
621 ix = 2;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
622 break;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
623 case 'H':
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
624 ix = 3;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
625 break;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
626 case 'm':
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
627 ix = 4;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
628 break;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
629 case 's':
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
630 ix = 5;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
631 break;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
632 default:
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
633 ix = 99;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
634 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
635
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
636 if (ix < 6) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
637 T0[ix][kk[ix]++] = line[p+n];
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
638 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
639 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
640 for (n=0; n<6; n++) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
641 T0[n][kk[n]] = 0;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
642 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
643 t.tm_year = atoi(T0[0]);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
644 t.tm_mon = atoi(T0[1]);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
645 t.tm_mday = atoi(T0[2]);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
646 t.tm_hour = atoi(T0[3]);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
647 t.tm_min = atoi(T0[4]);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
648 t.tm_sec = atoi(T0[5]);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
649
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
650 *(mxGetPr(R[ns])+m) = tm_time2gdf_time(&t);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
651 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
652 p = k+1;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
653 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
654 m++;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
655 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
656 line = strtok(NULL, "\x0a\x0d");
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
657 }
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
658
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
659 /* convert into output */
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
660 POutput[0] = mxCreateStructMatrix(1, 1, NS, ListOfVarNames);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
661 for (size_t k = 0; k < NS; k++) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
662 mxSetField(POutput[0], 0, ListOfVarNames[k], R[k]);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
663 }
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
664
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
665 if (ListOfVarNames) free(ListOfVarNames);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
666 if (vartyp) free(vartyp);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
667 if (datestr) free(datestr);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
668 if (H1) free(H1);
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
669 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
670
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
671 else if (!memcmp(H0,"HEADER RECORD*******LIBRARY HEADER RECORD!!!!!!!000000000000000000000000000000",78)) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
672 /*
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
673 SAS Transport file format (XPORT)
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
674 */
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
675 TYPE = SASXPT;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
676
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
677 /* TODO: sanity checks */
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
678
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
679 char tmp[5];
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
680 memcpy(tmp,H0+7*80+54,4);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
681 tmp[4] = 0;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
682 NS = atoi(tmp);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
683
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
684 char *tmp2;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
685 sz2 = strtoul(H0+4*80-6, &tmp2, 10);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
686
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
687 HeadLen2 = NS*sz2;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
688 if (HeadLen2 % 80) HeadLen2 = (HeadLen2 / 80 + 1) * 80;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
689
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
690 /* read namestr header, and header line "OBS" */
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
691 H2 = (char*) realloc(H2, HeadLen2+81);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
692 count += fread(H2,1,HeadLen2+80,fid);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
693
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
694 /* size of single record */
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
695 size_t pos=0, recsize = 0, POS = 0;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
696 for (size_t k = 0; k < NS; k++)
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
697 recsize += b_endian_u16(*(int16_t*)(H2+k*sz2+4));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
698
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
699 /* read data section */
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
700 size_t szData = 0;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
701 uint8_t *Data = NULL;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
702 while (!feof(fid)) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
703 size_t szNew = max(16,szData*2);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
704 Data = (uint8_t*)realloc(Data,szNew);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
705 szData += fread(Data+szData,1,szNew-szData,fid);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
706 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
707
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
708 M = szData/recsize;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
709
7462
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
710 mxArray **R = (mxArray**) mxMalloc(NS*sizeof(mxArray*));
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
711 const char **ListOfVarNames = (const char**)malloc(NS * sizeof(char*));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
712 char *VarNames = (char*)malloc(NS * 9);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
713
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
714 for (size_t k = 0; k < NS; k++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
715 size_t maxlen = b_endian_u16(*(int16_t*)(H2+k*sz2+4));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
716
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
717 ListOfVarNames[k] = VarNames+pos;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
718 int n = k*sz2+8;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
719 int flagDate = (!memcmp(H2+n+48,"DATE ",8) || !memcmp(H2+n+48,"MONNAME ",8));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
720 do {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
721 VarNames[pos++] = H2[n];
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
722 } while (isalnum(H2[++n]) && (n < k*sz2+16));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
723
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
724
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
725 VarNames[pos++] = 0;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
726
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
727 if ((*(int16_t*)(H2+k*sz2)) == b_endian_u16(1) && (*(int16_t*)(H2+k*sz2+4)) == b_endian_u16(8) ) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
728 // numerical data
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
729 R[k] = mxCreateDoubleMatrix(M, 1, mxREAL);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
730 for (size_t m=0; m<M; m++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
731 double d = xpt2d(b_endian_u64(*(uint64_t*)(Data+m*recsize+POS)));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
732
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
733 // if (flagDate) d += 715876; // add number of days from 0000-Jan-01 to 1960-Jan-01
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
734
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
735 *(mxGetPr(R[k])+m) = d;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
736
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
737 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
738 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
739 else if ((*(int16_t*)(H2+k*sz2)) == b_endian_u16(2)) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
740 // character string
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
741 R[k] = mxCreateCellMatrix(M, 1);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
742 char *f = (char*)malloc(maxlen+1);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
743 for (size_t m=0; m<M; m++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
744 memcpy(f, Data+m*recsize+POS, maxlen);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
745 f[maxlen] = 0;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
746 mxSetCell(R[k], m, mxCreateString(f));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
747 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
748 if (f) free(f);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
749 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
750 POS += maxlen;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
751 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
752
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
753 POutput[0] = mxCreateStructMatrix(1, 1, NS, ListOfVarNames);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
754 for (size_t k = 0; k < NS; k++) {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
755 mxSetField(POutput[0], 0, ListOfVarNames[k], R[k]);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
756 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
757
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
758 if (VarNames) free(VarNames);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
759 if (ListOfVarNames) free(ListOfVarNames);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
760 if (Data) free(Data);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
761 /* end of reading SAS format */
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
762 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
763
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
764 else {
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
765 fclose(fid);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
766 mexErrMsgTxt("file format not supported");
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
767 return;
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
768 }
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
769
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
770
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
771
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
772 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
773
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
774 // if (Mode[0]=='w' || Mode[0]=='a' ) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
775 if (Mode[0]=='w') {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
776
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
777 NS += mxGetNumberOfFields(PInputs[2]);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
778
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
779 // generate default (fixed) header
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
780 if (Mode[0]=='w') {
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
781 memset(H0,' ',80*8);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
782 memcpy(H0,L1,strlen(L1));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
783 memcpy(H0+80,L2,strlen(L2));
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
784
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
785 memcpy(H0+80*3,L4,strlen(L4));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
786 memcpy(H0+80*4,L5,strlen(L5));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
787 memcpy(H0+80*5,L6,strlen(L6));
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
788
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
789 memcpy(H0+80*7,L8,strlen(L8));
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
790 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
791
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
792 time_t t;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
793 time(&t);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
794 char tt[20];
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
795 strftime(tt, 17, DATEFORMAT, localtime(&t));
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
796 memcpy(H0+80*2-16,tt,16);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
797 memcpy(H0+80*2,tt,16);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
798 memcpy(H0+80*5+8,fn,min(8,strcspn(fn,".\x00")));
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
799 memcpy(H0+80*5+32,"XPTOPEN.MEX (OCTAVE/MATLAB)",27);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
800 memcpy(H0+80*6-16,tt,16);
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
801 memcpy(H0+80*6,tt,16);
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
802
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
803 char tmp[17];
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
804 sprintf(tmp,"%04i", NS); // number of variables
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
805 memcpy(H0+80*7+54, tmp, 4);
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
806
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
807 if (sz2==0) sz2 = 140;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
808 if (sz2 < 136)
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
809 mexErrMsgTxt("error XPTOPEN: incorrect length of namestr field");
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
810
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
811 /* generate variable NAMESTR header */
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
812 HeadLen2 = NS*sz2;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
813 if (HeadLen2 % 80) HeadLen2 = (HeadLen2 / 80 + 1) * 80;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
814 H2 = (char*) realloc(H2,HeadLen2);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
815 memset(H2,0,HeadLen2);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
816
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
817 mwIndex M = 0;
7462
40c9ff0bf296 reading ARFF files improved; SPSS: better identification
schloegl
parents: 7434
diff changeset
818 mxArray **F = (mxArray**) mxMalloc(NS*sizeof(mxArray*));
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
819 char **Fstr = (char**) malloc(NS*sizeof(char*));
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
820 size_t *MAXLEN = (size_t*) malloc(NS*sizeof(size_t*));
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
821 for (int16_t k = 0; k < NS; k++) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
822 Fstr[k] = NULL;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
823 MAXLEN[k]=0;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
824 F[k] = mxGetFieldByNumber(PInputs[2],0,k);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
825 if (k==0) M = mxGetM(F[k]);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
826 else if (M != mxGetM(F[k])) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
827 if (H2) free(H2);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
828 if (F) free(F);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
829 mexErrMsgTxt("Error XPTOPEN: number of elements (rows) do not fit !!!");
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
830 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
831
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
832 if (mxIsChar(F[k])) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
833 *(int16_t*)(H2+k*sz2) = b_endian_u16(2);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
834 *(int16_t*)(H2+k*sz2+4) = b_endian_u16(mxGetN(F[k]));
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
835 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
836 else if (mxIsCell(F[k])) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
837 size_t maxlen = 0;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
838 for (mwIndex m = 0; m<M; m++) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
839 mxArray *f = mxGetCell(F[k],m);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
840 if (mxIsChar(f) || mxIsEmpty(f)) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
841 size_t len = mxGetNumberOfElements(f);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
842 if (maxlen<len) maxlen = len;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
843 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
844 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
845 Fstr[k] = (char*) malloc(maxlen+1);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
846 *(int16_t*)(H2+k*sz2) = b_endian_u16(2);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
847 *(int16_t*)(H2+k*sz2+4) = b_endian_u16(maxlen);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
848 MAXLEN[k] = maxlen;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
849 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
850 else {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
851 *(int16_t*)(H2+k*sz2) = b_endian_u16(1);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
852 *(int16_t*)(H2+k*sz2+4) = b_endian_u16(8);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
853 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
854 *(int16_t*)(H2+k*sz2+6) = b_endian_u16(k);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
855 strncpy(H2+k*sz2+8,mxGetFieldNameByNumber(PInputs[2],k),8);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
856 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
857
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
858 count = fwrite(H0, 1, HeadLen0, fid);
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
859 count += fwrite(H2, 1, HeadLen2, fid);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
860 /* write OBS header line */
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
861 count += fwrite(LO, 1, strlen(LO), fid);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
862 for (mwIndex m = 0; m < M; m++) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
863 for (int16_t k = 0; k < NS; k++) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
864
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
865 if (*(int16_t*)(H2+k*sz2) == b_endian_u16(1)) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
866 // numeric
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
867 uint64_t u64 = b_endian_u64(d2xpt(*(mxGetPr(F[k])+m)));
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
868 count += fwrite(&u64, 1, 8, fid);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
869 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
870
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
871 /* else if (mxIsChar(F[k])) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
872 *(int16_t*)(H2+k*sz2) = b_endian_u16(2);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
873 *(int16_t*)(H2+k*sz2+4) = b_endian_u16(mxGetN(F[k]));
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
874 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
875 */
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
876 else if (mxIsCell(F[k])) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
877 size_t maxlen = MAXLEN[k];
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
878 mxArray *f = mxGetCell(F[k],m);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
879 mxGetString(f, Fstr[k], maxlen+1);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
880 count += fwrite(Fstr[k], 1, maxlen, fid);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
881 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
882 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
883 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
884 /*
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
885 // padding to full multiple of 80 byte:
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
886 // FIXME: this might introduce spurios sample values
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
887 char d = count%80;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
888 while (d--) fwrite("\x20",1,1,fid);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
889 */
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
890 // free memory
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
891 for (size_t k=0; k<NS; k++) if (Fstr[k]) free(Fstr[k]);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
892 if (Fstr) free(Fstr);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
893 if (MAXLEN) free(MAXLEN);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
894 Fstr = NULL;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
895 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
896 fclose(fid);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
897
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
898 if (H2) free(H2);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
899 H2 = NULL;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
900
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
901 return;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
902 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
903
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
904
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
905 /*
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
906 XPT2D converts from little-endian IBM to little-endian IEEE format
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
907 */
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
908
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
909 double xpt2d(uint64_t x) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
910 // x is little-endian 64bit IBM floating point format
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
911 char c = *((char*)&x+7) & 0x7f;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
912 uint64_t u = x;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
913 *((char*)&u+7)=0;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
914
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
915 #if __BYTE_ORDER == __BIG_ENDIAN
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
916
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
917 mexErrMsgTxt("IEEE-to-IBM conversion on big-endian platform not supported, yet");
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
918
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
919 #elif __BYTE_ORDER==__LITTLE_ENDIAN
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
920
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
921 #if DEBUG
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
922 mexPrintf("xpt2d(%016Lx): [0x%x]\n",x,c);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
923 #endif
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
924
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
925 // missing values
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
926 if ((c==0x2e || c==0x5f || (c>0x40 && c<0x5b)) && !u )
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
927 return(NaN);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
928
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
929 int s,e;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
930 s = *(((char*)&x) + 7) & 0x80; // sign
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
931 e = (*(((char*)&x) + 7) & 0x7f) - 64; // exponent
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
932 *(((char*)&x) + 7) = 0; // mantisse x
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
933
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
934 #if DEBUG
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
935 mexPrintf("%x %x %016Lx\n",s,e,x);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
936 #endif
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
937
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
938 double y = ldexp(x, e*4-56);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
939 if (s) return(-y);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
940 else return( y);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
941
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
942 #endif
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
943 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
944
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
945
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
946 /*
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
947 D2XPT converts from little-endian IEEE to little-endian IBM format
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
948 */
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
949
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
950 uint64_t d2xpt(double x) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
951 uint64_t s,m;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
952 int e;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
953
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
954 #if __BYTE_ORDER == __BIG_ENDIAN
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
955
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
956 mexErrMsgTxt("IEEE-to-IBM conversion on big-endian platform not supported, yet");
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
957
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
958
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
959 #elif __BYTE_ORDER==__LITTLE_ENDIAN
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
960
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
961 if (x != x) return(0x2eLL << 56); // NaN - not a number
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
962
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
963 if (fabs(x) == 1.0/0.0) return(0x5fLL << 56); // +-infinity
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
964
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
965 if (x == 0.0) return(0);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
966
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
967 if (x > 0.0) s=0;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
968 else s=1;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
969
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
970 x = frexp(x,&e);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
971
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
972 #if DEBUG
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
973 mexPrintf("d2xpt(%f)\n",x);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
974 #endif
7426
6ecaa4abc5ae support for reading STATA files added
schloegl
parents: 7415
diff changeset
975 // see http://old.nabble.com/Re%3A-IBM-integer-and-double-formats-p20428979.html
7376
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
976 m = *(uint64_t*) &x;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
977 *(((char*)&m) + 6) &= 0x0f; //
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
978 if (e) *(((char*)&m) + 6) |= 0x10; // reconstruct implicit leading '1' for normalized numbers
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
979 m <<= (3-(-e & 3));
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
980 *(((char*)&m) + 7) = s ? 0x80 : 0;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
981 e = (e + (-e & 3)) / 4 + 64;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
982
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
983 if (e >= 128) return(0x5f); // overflow
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
984 if (e < 0) {
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
985 uint64_t h = 1<<(4*-e - 1);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
986 m = m / (2*h) + (m & h && m & (3*h-1) ? 1 : 0);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
987 e = 0;
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
988 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
989 return (((uint64_t)e)<<56 | m);
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
990
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
991 #endif
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
992
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
993 }
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
994
37789a34b615 add reading and writing of XPT (SAS Transport File) format
schloegl
parents:
diff changeset
995
7434
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
996 double tm_time2gdf_time(struct tm *t) {
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
997 /* based Octave's datevec.m
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
998 it referes Peter Baum's algorithm at http://vsg.cape.com/~pbaum/date/date0.htm
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
999 but the link is not working anymore as of 2008-12-03.
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1000
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1001 Other links to Peter Baum's algorithm are
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1002 http://www.rexswain.com/b2mmddyy.rex
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1003 http://www.dpwr.net/forums/index.php?s=ecfa72e38be61327403126e23aeea7e5&showtopic=4309
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1004 */
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1005
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1006 int Y,M,s; //h,m,
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1007 double D;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1008
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1009 D = t->tm_mday;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1010 M = t->tm_mon+1;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1011 Y = t->tm_year+1900;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1012
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1013 // Set start of year to March by moving Jan. and Feb. to previous year.
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1014 // Correct for months > 12 by moving to subsequent years.
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1015 Y += fix ((M-14.0)/12);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1016
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1017 const int monthstart[] = {306, 337, 0, 31, 61, 92, 122, 153, 184, 214, 245, 275};
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1018 // Lookup number of days since start of the current year.
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1019 D += monthstart[t->tm_mon % 12] + 60;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1020
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1021 // Add number of days to the start of the current year. Correct
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1022 // for leap year every 4 years except centuries not divisible by 400.
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1023 D += 365*Y + floor (Y/4) - floor (Y/100) + floor (Y/400);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1024
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1025 // Add fraction representing current second of the day.
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1026 s = t->tm_hour*3600 + t->tm_min*60 + t->tm_sec;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1027
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1028 // s -= timezone;
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1029 return(D + s/86400.0);
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1030 }
0992c00355af experimental ARFF support
schloegl
parents: 7426
diff changeset
1031