1 /*
2 #
3 # File : gmic_libc.cpp
4 # ( C++ source file )
5 #
6 # Description : GREYC's Magic for Image Computing - C bridge to the libgmic
7 # ( http://gmic.eu )
8 #
9 # Copyright : Tobias Fleischer
10 # ( https://plus.google.com/u/0/b/117441237982283011318/+TobiasFleischer )
11 #
12 # License : CeCILL-B v1.0
13 # ( http://cecill.info/licences/Licence_CeCILL-B_V1-en.html )
14 #
15 # This software is governed either by the CeCILL-B license
16 # under French law and abiding by the rules of distribution of free software.
17 # You can use, modify and or redistribute the software under the terms of
18 # the CeCILL-B licenses as circulated by CEA, CNRS and INRIA
19 # at the following URL: "http://cecill.info".
20 #
21 # As a counterpart to the access to the source code and rights to copy,
22 # modify and redistribute granted by the license, users are provided only
23 # with a limited warranty and the software's author, the holder of the
24 # economic rights, and the successive licensors have only limited
25 # liability.
26 #
27 # In this respect, the user's attention is drawn to the risks associated
28 # with loading, using, modifying and/or developing or reproducing the
29 # software by the user in light of its specific status of free software,
30 # that may mean that it is complicated to manipulate, and that also
31 # therefore means that it is reserved for developers and experienced
32 # professionals having in-depth computer knowledge. Users are therefore
33 # encouraged to load and test the software's suitability as regards their
34 # requirements in conditions enabling the security of their systems and/or
35 # data to be ensured and, more generally, to use and operate it in the
36 # same conditions as regards security.
37 #
38 # The fact that you are presently reading this means that you have had
39 # knowledge of the CeCILL-B licenses and that you accept its terms.
40 #
41 */
42
43 #include "gmic_libc.h"
44 #include "gmic.h"
45
gmic_delete_external(float * p)46 GMIC_DLLINTERFACE int GMIC_CALLCONV gmic_delete_external(float* p) {
47 delete[] p;
48 return 0;
49 }
50
gmic_call(const char * _cmd,unsigned int * _nofImages,gmic_interface_image * _images,gmic_interface_options * _options)51 GMIC_DLLINTERFACE int GMIC_CALLCONV gmic_call(const char* _cmd, unsigned int* _nofImages,
52 gmic_interface_image* _images, gmic_interface_options* _options) {
53 int err = 0;
54 bool no_inplace = _options?_options->no_inplace_processing:false;
55 int nofImages = 0;
56 if (_nofImages && _images) nofImages = *_nofImages;
57 gmic_list<float> images;
58 gmic_list<char> images_names;
59 images.assign(nofImages);
60 images_names.assign(nofImages);
61
62 for (unsigned int i = 0; i < images._width; ++i) {
63 gmic_image<float>& img = images[i];
64 if (_images[i].format == E_FORMAT_BYTE) {
65 gmic_image<unsigned char> img_tmp;
66 if (_images[i].is_interleaved) {
67 img_tmp.assign((unsigned char*)_images[i].data, _images[i].spectrum, _images[i].width,
68 _images[i].height, _images[i].depth, true);
69 img_tmp.permute_axes("YZCX");
70 } else {
71 img_tmp.assign((unsigned char*)_images[i].data, _images[i].width, _images[i].height,
72 _images[i].depth, _images[i].spectrum, true);
73 }
74 img = img_tmp;
75 } else {
76 if (no_inplace) {
77 gmic_image<float> img_tmp;
78 if (_images[i].is_interleaved) {
79 img_tmp.assign((float*)_images[i].data, _images[i].spectrum, _images[i].width,
80 _images[i].height, _images[i].depth, true);
81 img_tmp.permute_axes("YZCX");
82 } else {
83 img_tmp.assign((float*)_images[i].data, _images[i].width, _images[i].height,
84 _images[i].depth, _images[i].spectrum, true);
85 }
86 img = img_tmp;
87 } else {
88 if (_images[i].is_interleaved) {
89 img.assign((float*)_images[i].data, _images[i].spectrum, _images[i].width,
90 _images[i].height, _images[i].depth, true);
91 img.permute_axes("YZCX");
92 } else {
93 img.assign((float*)_images[i].data, _images[i].width, _images[i].height,
94 _images[i].depth, _images[i].spectrum, true);
95 }
96 }
97 }
98 images_names[i].assign(std::strlen(_images[i].name) + 1);
99 std::strcpy(images_names[i], _images[i].name);
100 }
101
102 try {
103 if (_options)
104 gmic(_cmd, images, images_names, _options->custom_commands, !_options->ignore_stdlib,
105 _options->p_progress, _options->p_is_abort);
106 else
107 gmic(_cmd, images, images_names);
108
109 } catch (gmic_exception &e) { // catch exception, if an error occurred in the interpreter.
110 std::string error_string = e.what();
111 std::fprintf(stderr, "\n- Error encountered when calling G'MIC : '%s'\n", e.what());
112 if (_options && _options->error_message_buffer) {
113 std::strcpy(_options->error_message_buffer, error_string.substr(0, 255).c_str());
114 }
115 err = -1;
116 }
117
118 if (_nofImages && _images && err == 0) {
119 *_nofImages = images._width;
120 for (unsigned int i = 0; i < images._width; ++i) {
121 gmic_image<float>& img = images[i];
122 if (_options && _options->interleave_output) {
123 img.permute_axes("CXYZ");
124 _images[i].is_interleaved = true;
125 _images[i].width = img._height;
126 _images[i].height = img._depth;
127 _images[i].depth = img._spectrum;
128 _images[i].spectrum = img._width;
129 } else {
130 _images[i].is_interleaved = false;
131 _images[i].width = img._width;
132 _images[i].height = img._height;
133 _images[i].depth = img._depth;
134 _images[i].spectrum = img._spectrum;
135 }
136 if (_options && _options->output_format == E_FORMAT_BYTE) {
137 gmic_image<unsigned char> img_tmp;
138 img_tmp = img;
139 _images[i].format = E_FORMAT_BYTE;
140 _images[i].data = img_tmp._data;
141 img_tmp._is_shared = true;
142 img._is_shared = false;
143 } else {
144 _images[i].format = E_FORMAT_FLOAT;
145 _images[i].data = img._data;
146 img._is_shared = true;
147 }
148 std::strcpy(_images[i].name, images_names[i]);
149 }
150 }
151 images.assign(0U);
152 images_names.assign(0U);
153 return err;
154 }
155
gmic_get_stdlib()156 GMIC_DLLINTERFACE const char* GMIC_CALLCONV gmic_get_stdlib() {
157 gmic_image<char> lib = gmic::decompress_stdlib();
158 lib._is_shared = true;
159 return lib.data();
160 }
161