Coverity: graphic_export module resource leaks fixed
[scilab.git] / scilab / modules / graphic_export / src / cpp / xs2file.cpp
1 /*
2  * Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
3  * Copyright (C) 2006 - INRIA - Fabrice Leray
4  * Copyright (C) 2006 - INRIA - Jean-Baptiste Silvy
5  * Copyright (C) 2009 - DIGITEO - Allan CORNET
6  * desc : interface for xs2file routine
7  *
8  * Copyright (C) 2012 - 2016 - Scilab Enterprises
9  *
10  * This file is hereby licensed under the terms of the GNU GPL v2.0,
11  * pursuant to article 5.3.4 of the CeCILL v.2.1.
12  * This file was originally licensed under the terms of the CeCILL v2.1,
13  * and continues to be available under such terms.
14  * For more information, see the COPYING file which you should have received
15  * along with this program.
16  *
17  */
18
19 #include <string.h>
20 #include <stdio.h>
21 #include <stdlib.h>
22
23 extern "C"
24 {
25 #include "xs2file.h"
26 #include "api_scilab.h"
27 #include "GetProperty.h"
28 #include "localization.h"
29 #include "SetJavaProperty.h"
30 #include "Scierror.h"
31 #include "expandPathVariable.h"
32 #include "PATH_MAX.h"
33 #include "sci_malloc.h"
34 #include "FigureList.h"
35 #include "freeArrayOfString.h"
36 #include "../../../graphics/src/c/getHandleProperty/getPropertyAssignedValue.h"
37 #include "HandleManagement.h"
38 #include "getGraphicObjectProperty.h"
39 #include "graphicObjectProperties.h"
40 }
41
42 /*--------------------------------------------------------------------------*/
43 static bool isVectorialExport(ExportFileType fileType);
44 /*--------------------------------------------------------------------------*/
45 int xs2file(char * fname, ExportFileType fileType, void* pvApiCtx)
46 {
47     SciErr sciErr;
48
49     int* piAddrl1 = NULL;
50     int* piAddrfileName = NULL;
51     int* piAddrsciOrientation = NULL;
52     int* piAddrquality = NULL;
53     double* quality = NULL;
54
55     /* Check input and output sizes */
56     CheckOutputArgument(pvApiCtx, 0, 1);
57     if (isVectorialExport(fileType) || fileType == JPG_EXPORT)
58     {
59         CheckInputArgument(pvApiCtx, 2, 3);
60     }
61     else
62     {
63         CheckInputArgument(pvApiCtx, 2, 2);
64     }
65
66     if ((!checkInputArgumentType(pvApiCtx, 1, sci_matrix)) && (!checkInputArgumentType(pvApiCtx, 1, sci_handles)))
67     {
68         Scierror(999, _("%s: Wrong type for input argument #%d: An integer or a handle expected.\n"), fname, 1);
69         AssignOutputVariable(pvApiCtx, 1) = 0;
70         ReturnArguments(pvApiCtx);
71         return 1;
72     }
73
74     if ( (checkInputArgumentType(pvApiCtx, 2, sci_strings)) )
75     {
76         char **fileName = NULL;
77         char *real_filename = NULL;
78         float jpegCompressionQuality = 0.95f;
79         ExportOrientation orientation = EXPORT_PORTRAIT; /* default orientation */
80         int m1 = 0, n1 = 0;
81         int figurenum = -1;
82         int figureUID = 0;
83         char *status = NULL;
84
85         sciErr = getVarAddressFromPosition(pvApiCtx, 1, &piAddrl1);
86         if (sciErr.iErr)
87         {
88             printError(&sciErr, 0);
89             return 1;
90         }
91
92         /* get handle by figure number */
93         if (checkInputArgumentType(pvApiCtx, 1, sci_matrix))
94         {
95             // Retrieve a matrix of double at position 1.
96             int* l1 = NULL;
97             sciErr = getMatrixOfDoubleAsInteger(pvApiCtx, piAddrl1, &m1, &n1, &l1);
98             if (sciErr.iErr)
99             {
100                 printError(&sciErr, 0);
101                 Scierror(202, _("%s: Wrong type for argument #%d: A real expected.\n"), fname, 1);
102                 return 1;
103             }
104
105             if (m1 * n1 != 1)
106             {
107                 Scierror(999, _("%s: Wrong size for input argument #%d: A scalar expected.\n"), fname, 1);
108                 return 1;
109             }
110
111             figurenum = *l1;
112             if (!sciIsExistingFigure(figurenum))
113             {
114                 Scierror(999, "%s: Input argument #%d must be a valid figure_id.\n", fname, 1);
115                 return 1;
116             }
117             figureUID = getFigureFromIndex(figurenum);
118         }
119         /* check given handle */
120         else if (checkInputArgumentType(pvApiCtx, 1, sci_handles))
121         {
122             int iHandleType = -1;
123             int* piHandleType = &iHandleType;
124             long long* l1 = NULL;
125
126             // Retrieve a matrix of handle at position 1.
127             sciErr = getMatrixOfHandle(pvApiCtx, piAddrl1, &m1, &n1, &l1);
128             if (sciErr.iErr)
129             {
130                 printError(&sciErr, 0);
131                 Scierror(202, _("%s: Wrong type for argument #%d: Handle matrix expected.\n"), fname, 1);
132                 return 1;
133             }
134
135             if (m1 * n1 != 1)
136             {
137                 Scierror(999, _("%s: Wrong size for input argument #%d: A graphic handle expected.\n"), fname, 1);
138                 return 1;
139             }
140
141             figureUID = getObjectFromHandle((unsigned long) * l1);
142             if (figureUID == 0)
143             {
144                 Scierror(999, _("%s: Input argument #%d must be a valid handle.\n"), fname, 1);
145                 return 1;
146             }
147
148             getGraphicObjectProperty(figureUID, __GO_TYPE__, jni_int, (void**)&piHandleType);
149
150             if (iHandleType != __GO_FIGURE__)
151             {
152                 Scierror(999, _("%s: Wrong type for input argument #%d: A ''%s'' handle expected.\n"), fname, 1, "Figure");
153                 return 1;
154             }
155         }
156         else
157         {
158             Scierror(999, _("%s: Wrong type for input argument #%d: A scalar or figure handle expected.\n"), fname, 1);
159             return 1;
160         }
161
162         /* get file name */
163         sciErr = getVarAddressFromPosition(pvApiCtx, 2, &piAddrfileName);
164         if (sciErr.iErr)
165         {
166             printError(&sciErr, 0);
167             return 1;
168         }
169
170         // Retrieve a matrix of string at position 2.
171         if (getAllocatedMatrixOfString(pvApiCtx, piAddrfileName, &m1, &n1, &fileName))
172         {
173             Scierror(202, _("%s: Wrong type for argument #%d: string expected.\n"), fname, 2);
174             return 1;
175         }
176
177         if (m1 * n1 == 1)
178         {
179             if (nbInputArgument(pvApiCtx) == 3)
180             {
181                 int nbCol = 0;
182                 int nbRow = 0;
183
184                 if (isVectorialExport(fileType))
185                 {
186
187                     char **sciOrientation = NULL;
188
189                     if ((!checkInputArgumentType(pvApiCtx, 3, sci_strings)))
190                     {
191                         Scierror(999, _("%s: Wrong type for input argument #%d: Single character string expected.\n"), fname, 3);
192                         freeAllocatedMatrixOfString(m1, n1, fileName);
193                         return 1;
194                     }
195
196                     sciErr = getVarAddressFromPosition(pvApiCtx, 3, &piAddrsciOrientation);
197                     if (sciErr.iErr)
198                     {
199                         printError(&sciErr, 0);
200                         freeAllocatedMatrixOfString(m1, n1, fileName);
201                         return 1;
202                     }
203
204                     // Retrieve a matrix of string at position 3.
205                     if (getAllocatedMatrixOfString(pvApiCtx, piAddrsciOrientation, &nbRow, &nbCol, &sciOrientation))
206                     {
207                         Scierror(202, _("%s: Wrong type for argument #%d: string expected.\n"), fname, 3);
208                         freeAllocatedMatrixOfString(m1, n1, fileName);
209                         return 1;
210                     }
211
212                     if (nbRow * nbCol == 1)
213                     {
214                         /* Value should be 'landscape' or 'portrait' but check only the first character */
215                         /* for compatibility with Scilab 4*/
216                         if (strcmp(sciOrientation[0], "landscape") == 0 || strcmp(sciOrientation[0], "l") == 0)
217                         {
218                             freeAllocatedMatrixOfString(nbRow, nbCol, sciOrientation);
219                             orientation = EXPORT_LANDSCAPE;
220                         }
221                         else if (strcmp(sciOrientation[0], "portrait") == 0 || strcmp(sciOrientation[0], "p") == 0)
222                         {
223                             freeAllocatedMatrixOfString(nbRow, nbCol, sciOrientation);
224                             orientation = EXPORT_PORTRAIT;
225                         }
226                         else
227                         {
228                             Scierror(999, _("%s: Wrong value for input argument #%d: '%s' or '%s' expected.\n"), fname, 3, "portrait", "landscape");
229                             freeAllocatedMatrixOfString(m1, n1, fileName);
230                             freeAllocatedMatrixOfString(nbRow, nbCol, sciOrientation);
231                             return 1;
232                         }
233                     }
234                     else
235                     {
236                         Scierror(999, _("%s: Wrong size for input argument #%d: Single character string expected.\n"), fname, 3);
237                         freeAllocatedMatrixOfString(m1, n1, fileName);
238                         freeAllocatedMatrixOfString(nbRow, nbCol, sciOrientation);
239                         return 1;
240                     }
241                 }
242                 else
243                 {
244                     sciErr = getVarAddressFromPosition(pvApiCtx, 3, &piAddrquality);
245                     if (sciErr.iErr)
246                     {
247                         printError(&sciErr, 0);
248                         freeAllocatedMatrixOfString(m1, n1, fileName);
249                         return 1;
250                     }
251
252                     // Retrieve a matrix of double at position 3.
253                     sciErr = getMatrixOfDouble(pvApiCtx, piAddrquality, &nbRow, &nbCol, &quality);
254                     if (sciErr.iErr)
255                     {
256                         printError(&sciErr, 0);
257                         Scierror(202, _("%s: Wrong type for argument #%d: A real expected.\n"), fname, 3);
258                         freeAllocatedMatrixOfString(m1, n1, fileName);
259                         return 1;
260                     }
261
262                     if (nbRow != 1 || nbCol != 1 || *quality < 0 || *quality > 1)
263                     {
264                         Scierror(999, _("%s: Wrong type for input argument #%d: A real between 0 and 1 expected.\n"), fname, 3);
265                         freeAllocatedMatrixOfString(m1, n1, fileName);
266                         return 1;
267                     }
268                     jpegCompressionQuality = (float) * quality;
269                 }
270             }
271
272             /* Replaces SCI, ~, HOME, TMPDIR by the real path */
273             real_filename = expandPathVariable(fileName[0]);
274             freeAllocatedMatrixOfString(m1, n1, fileName);
275
276             /* Call the function for exporting file */
277             status = exportToFile(figureUID, real_filename, fileType, jpegCompressionQuality, orientation);
278
279             /* free pointers no more used */
280             if (real_filename)
281             {
282                 FREE(real_filename);
283                 real_filename = NULL;
284             }
285
286             /* treat errors */
287             if (strlen(status) != 0)
288             {
289                 Scierror(999, _("%s: %s\n"), fname, status);
290                 delete[] status;
291                 return 1;
292             }
293
294             delete[] status;
295         }
296         else
297         {
298             Scierror(999, _("%s: Wrong size for input argument #%d: Single character string expected.\n"), fname, 2);
299             freeAllocatedMatrixOfString(m1, n1, fileName);
300             return 1;
301         }
302     }
303     else
304     {
305         Scierror(999, _("%s: Wrong type for input argument #%d: Single character string expected.\n"), fname, 2);
306         return 1;
307     }
308
309     AssignOutputVariable(pvApiCtx, 1) = 0;
310     ReturnArguments(pvApiCtx);
311
312     return 0;
313 }
314 /*--------------------------------------------------------------------------*/
315 static bool isVectorialExport(ExportFileType fileType)
316 {
317     return fileType == EPS_EXPORT
318            || fileType == PS_EXPORT
319            || fileType == PDF_EXPORT
320            || fileType == SVG_EXPORT
321            || fileType == EMF_EXPORT;
322 }
323 /*--------------------------------------------------------------------------*/