* Bug #13119 fixed - fileio: mget and mgetl accepted decimal values as number of...
[scilab.git] / scilab / modules / fileio / sci_gateway / c / sci_mgetl.c
1 /*
2  * Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
3  * Copyright (C) 2006 - INRIA - Allan CORNET
4  * Copyright (C) 2010 - DIGITEO - Allan CORNET
5  *
6  * This file must be used under the terms of the CeCILL.
7  * This source file is licensed as described in the file COPYING, which
8  * you should have received as part of this distribution.  The terms
9  * are also available at
10  * http://www.cecill.info/licences/Licence_CeCILL_V2.1-en.txt
11  *
12  */
13 /*--------------------------------------------------------------------------*/
14 #include "gw_fileio.h"
15 #include "localization.h"
16 #include "Scierror.h"
17 #include "api_scilab.h"
18 #include "mgetl.h"
19 #include "mopen.h"
20 #include "mclose.h"
21 #include "expandPathVariable.h"
22 #include "filesmanagement.h"
23 #include "freeArrayOfString.h"
24 #include "BOOL.h"
25 /*--------------------------------------------------------------------------*/
26 int sci_mgetl(char *fname, unsigned long fname_len)
27 {
28     SciErr sciErr;
29     int *piAddressVarOne = NULL;
30     int numberOfLinesToRead = -1;
31
32     char **wcReadStrings = NULL;
33     int numberOfLinesRead = 0;
34     int fileDescriptor = 0;
35     int iErrorMgetl = 0;
36     BOOL bCloseFile = FALSE;
37
38     Rhs = Max(0, Rhs);
39
40     CheckRhs(1, 2);
41     CheckLhs(1, 1);
42
43
44     if (Rhs == 2)
45     {
46         int *piAddressVarTwo = NULL;
47
48         sciErr = getVarAddressFromPosition(pvApiCtx, 2, &piAddressVarTwo);
49         if (sciErr.iErr)
50         {
51             printError(&sciErr, 0);
52             Scierror(999, _("%s: Can not read input argument #%d.\n"), fname, 2);
53             return 0;
54         }
55
56         if ( isDoubleType(pvApiCtx, piAddressVarTwo) )
57         {
58             double dValue = 0.;
59             if (!isScalar(pvApiCtx, piAddressVarTwo))
60             {
61                 Scierror(999, _("%s: Wrong size for input argument #%d: An integer value expected.\n"), fname, 2);
62                 return 0;
63             }
64
65             if ( getScalarDouble(pvApiCtx, piAddressVarTwo, &dValue) == 0)
66             {
67                 if (dValue != (int) dValue)
68                 {
69                     Scierror(999, _("%s: Wrong value for input argument #%d: An integer value expected.\n"), fname, 2);
70                     return 0;
71                 }
72
73                 numberOfLinesToRead = (int) dValue;
74             }
75             else
76             {
77                 Scierror(999, _("%s: Memory allocation error.\n"), fname);
78                 return 0;
79             }
80         }
81         else
82         {
83             Scierror(999, _("%s: Wrong type for input argument #%d: An integer value expected.\n"), fname, 2);
84             return 0;
85         }
86     }
87
88     sciErr = getVarAddressFromPosition(pvApiCtx, 1, &piAddressVarOne);
89     if (sciErr.iErr)
90     {
91         printError(&sciErr, 0);
92         Scierror(999, _("%s: Can not read input argument #%d.\n"), fname, 1);
93         return 0;
94     }
95
96     if (isStringType(pvApiCtx, piAddressVarOne) == FALSE &&  isDoubleType(pvApiCtx, piAddressVarOne) == FALSE)
97     {
98         Scierror(999, _("%s: Wrong type for input argument #%d: String or logical unit expected.\n"), fname, 1);
99         return 0;
100     }
101
102     if (!isScalar(pvApiCtx, piAddressVarOne))
103     {
104         Scierror(999, _("%s: Wrong size for input argument #%d: String or logical unit expected.\n"), fname, 1);
105         return 0;
106     }
107
108     if (isStringType(pvApiCtx, piAddressVarOne))
109     {
110         char *fileName = NULL;
111         char *expandedFileName = NULL;
112         if (getAllocatedSingleString(pvApiCtx, piAddressVarOne, &fileName))
113         {
114             if (fileName)
115             {
116                 freeAllocatedSingleString(fileName);
117             }
118
119             Scierror(999, _("%s: Memory allocation error.\n"), fname);
120             return 0;
121         }
122
123         expandedFileName = expandPathVariable(fileName);
124         freeAllocatedSingleString(fileName);
125
126         if (IsAlreadyOpenedInScilab(expandedFileName))
127         {
128             int fd = GetIdFromFilename(expandedFileName);
129             fileDescriptor = fd;
130             FREE(expandedFileName);
131             bCloseFile = FALSE;
132         }
133         else
134         {
135 #define READ_ONLY_TEXT_MODE "rt"
136             int fd = 0;
137             int f_swap = 0;
138             double res = 0.0;
139             int ierr = 0;
140
141             C2F(mopen)(&fd, expandedFileName, READ_ONLY_TEXT_MODE, &f_swap, &res, &ierr);
142             bCloseFile = TRUE;
143
144             switch (ierr)
145             {
146                 case MOPEN_NO_ERROR:
147                     fileDescriptor = fd;
148                     FREE(expandedFileName);
149                     break;
150                 case MOPEN_NO_MORE_LOGICAL_UNIT:
151                 {
152                     Scierror(66, _("%s: Too many files opened!\n"), fname);
153                     FREE(expandedFileName);
154                     return 0;
155                 }
156                 break;
157                 case MOPEN_CAN_NOT_OPEN_FILE:
158                 {
159                     Scierror(999, _("%s: Cannot open file %s.\n"), fname, expandedFileName);
160                     FREE(expandedFileName);
161                     return 0;
162                 }
163                 break;
164                 case MOPEN_NO_MORE_MEMORY:
165                 {
166                     FREE(expandedFileName);
167                     Scierror(999, _("%s: No more memory.\n"), fname);
168                     return 0;
169                 }
170                 break;
171                 case MOPEN_INVALID_FILENAME:
172                 {
173                     Scierror(999, _("%s: invalid filename %s.\n"), fname, expandedFileName);
174                     FREE(expandedFileName);
175                     return 0;
176                 }
177                 break;
178                 case MOPEN_INVALID_STATUS:
179                 default:
180                 {
181                     FREE(expandedFileName);
182                     Scierror(999, _("%s: invalid status.\n"), fname);
183                     return 0;
184                 }
185                 break;
186             }
187         }
188     }
189     else /* double */
190     {
191         double dValue = 0.;
192         FILE *fd = NULL;
193
194         if (getScalarDouble(pvApiCtx, piAddressVarOne, &dValue) )
195         {
196             Scierror(999, _("%s: Memory allocation error.\n"), fname);
197             return 0;
198         }
199
200         fileDescriptor = (int)dValue;
201         if ((fileDescriptor == STDIN_ID) || (fileDescriptor == STDOUT_ID))
202         {
203             SciError(244);
204             return 0;
205         }
206
207         fd = GetFileOpenedInScilab(fileDescriptor);
208         if (fd == NULL)
209         {
210             Scierror(245, _("%s: No input file associated to logical unit %d.\n"), fname, fileDescriptor);
211             return 0;
212         }
213     }
214
215     wcReadStrings = mgetl(fileDescriptor, numberOfLinesToRead, &numberOfLinesRead, &iErrorMgetl);
216
217     if (bCloseFile)
218     {
219         double dErrClose = 0.;
220         C2F(mclose)(&fileDescriptor, &dErrClose);
221     }
222
223     switch (iErrorMgetl)
224     {
225         case MGETL_NO_ERROR:
226         {
227             if (numberOfLinesRead == 0)
228             {
229                 if (createEmptyMatrix(pvApiCtx, Rhs + 1))
230                 {
231                     freeArrayOfString(wcReadStrings, numberOfLinesRead);
232                     Scierror(999, _("%s: Memory allocation error.\n"), fname);
233                     return 0;
234                 }
235             }
236             else
237             {
238                 sciErr = createMatrixOfString(pvApiCtx, Rhs + 1, numberOfLinesRead, 1, wcReadStrings);
239                 if (sciErr.iErr)
240                 {
241                     freeArrayOfString(wcReadStrings, numberOfLinesRead);
242                     printError(&sciErr, 0);
243                     Scierror(17, _("%s: Memory allocation error.\n"), fname);
244                     return 0;
245                 }
246             }
247
248             freeArrayOfString(wcReadStrings, numberOfLinesRead);
249         }
250         break;
251
252         case MGETL_EOF:
253         {
254             if (numberOfLinesRead == 0)
255             {
256                 if (createEmptyMatrix(pvApiCtx, Rhs + 1))
257                 {
258                     freeArrayOfString(wcReadStrings, numberOfLinesRead);
259                     Scierror(999, _("%s: Memory allocation error.\n"), fname);
260                     return 0;
261                 }
262             }
263             else
264             {
265                 sciErr = createMatrixOfString(pvApiCtx, Rhs + 1, numberOfLinesRead, 1, wcReadStrings);
266                 if (sciErr.iErr)
267                 {
268                     freeArrayOfString(wcReadStrings, numberOfLinesRead);
269                     printError(&sciErr, 0);
270                     Scierror(17, _("%s: Memory allocation error.\n"), fname);
271                     return 0;
272                 }
273             }
274
275             freeArrayOfString(wcReadStrings, numberOfLinesRead);
276         }
277         break;
278
279         case MGETL_MEMORY_ALLOCATION_ERROR:
280         {
281             freeArrayOfString(wcReadStrings, numberOfLinesRead);
282             Scierror(999, _("%s: Memory allocation error.\n"), fname);
283             return 0;
284         }
285         break;
286
287         case MGETL_ERROR:
288         {
289             freeArrayOfString(wcReadStrings, numberOfLinesRead);
290             Scierror(999, _("%s: error.\n"), fname);
291             return 0;
292         }
293         break;
294     }
295
296     LhsVar(1) = Rhs + 1;
297     PutLhsVar();
298
299     return 0;
300 }
301 /*--------------------------------------------------------------------------*/