GDS-Render v1.2.1
command-line.c
Go to the documentation of this file.
1/*
2 * GDSII-Converter
3 * Copyright (C) 2018 Mario Hüttel <mario.huettel@gmx.net>
4 *
5 * This file is part of GDSII-Converter.
6 *
7 * GDSII-Converter is free software: you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License version 2 as
9 * published by the Free Software Foundation.
10 *
11 * GDSII-Converter is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with GDSII-Converter. If not, see <http://www.gnu.org/licenses/>.
18 */
19
31#include <stdio.h>
32#include <glib/gi18n.h>
33
41
42static int string_array_count(char **string_array)
43{
44 int count;
45
46 if (!string_array)
47 return 0;
48
49 for (count = 0; *string_array; string_array++)
50 count++;
51
52 return count;
53}
54
55static int create_renderers(char **renderers,
56 char **output_file_names,
57 gboolean tex_layers,
58 gboolean tex_standalone,
59 const struct external_renderer_params *ext_params,
60 GList **renderer_list,
61 LayerSettings *layer_settings)
62{
63 char **renderer_iter;
64 char *current_renderer;
65 int idx;
66 char *current_out_file;
67 int count_render, count_out;
68 GdsOutputRenderer *output_renderer;
69
70 if (!renderer_list)
71 return -1;
72
73 if (!renderers || !output_file_names) {
74 fprintf(stderr, _("Please specify renderers and file names\n"));
75 return -1;
76 }
77
78 count_render = string_array_count(renderers);
79 count_out = string_array_count(output_file_names);
80 if (count_render != count_out) {
81 fprintf(stderr, _("Count of renderers %d does not match count of output file names %d\n"),
82 count_render, count_out);
83 return -1;
84 }
85
86 /* Parse cmd line parameters */
87 for (renderer_iter = renderers, idx = 0; *renderer_iter; renderer_iter++, idx++) {
88 current_renderer = *renderer_iter;
89 current_out_file = output_file_names[idx];
90
91 /* File valid ? */
92 if (!current_out_file || !current_out_file[0])
93 continue;
94
95 if (!strcmp(current_renderer, "tikz")) {
96 output_renderer = GDS_RENDER_OUTPUT_RENDERER(latex_renderer_new_with_options(tex_layers,
97 tex_standalone));
98 } else if (!strcmp(current_renderer, "pdf")) {
99 output_renderer = GDS_RENDER_OUTPUT_RENDERER(cairo_renderer_new_pdf());
100 } else if (!strcmp(current_renderer, "svg")) {
101 output_renderer = GDS_RENDER_OUTPUT_RENDERER(cairo_renderer_new_svg());
102 } else if (!strcmp(current_renderer, "ext")) {
103 if (!ext_params->so_path) {
104 fprintf(stderr, _("Please specify shared object for external renderer. Will ignore this renderer.\n"));
105 continue;
106 }
107 output_renderer = GDS_RENDER_OUTPUT_RENDERER(
109 ext_params->cli_params));
110 } else {
111 continue;
112 }
113
116 *renderer_list = g_list_append(*renderer_list, output_renderer);
117 }
118
119 return 0;
120}
121
122static struct gds_cell *find_gds_cell_in_lib(struct gds_library *lib, const char *cell_name)
123{
124 GList *cell_list;
125 struct gds_cell *return_cell = NULL;
126 struct gds_cell *temp_cell;
127
128 for (cell_list = lib->cells; cell_list; cell_list = g_list_next(cell_list)) {
129 temp_cell = (struct gds_cell *)cell_list->data;
130 if (!strncmp(temp_cell->name, cell_name, CELL_NAME_MAX)) {
131 return_cell = temp_cell;
132 break;
133 }
134 }
135 return return_cell;
136}
137
138int command_line_convert_gds(const char *gds_name,
139 const char *cell_name,
140 char **renderers,
141 char **output_file_names,
142 const char *layer_file,
143 struct external_renderer_params *ext_param,
144 gboolean tex_standalone,
145 gboolean tex_layers,
146 double scale)
147{
148 int ret = -1;
149 GList *libs = NULL;
150 int res;
151 GList *renderer_list = NULL;
152 GList *list_iter;
153 struct gds_library *first_lib;
154 struct gds_cell *toplevel_cell = NULL;
155 LayerSettings *layer_sett;
156 GdsOutputRenderer *current_renderer;
157
158 /* Check if parameters are valid */
159 if (!gds_name || !cell_name || !output_file_names || !layer_file || !renderers) {
160 printf(_("Probably missing argument. Check --help option\n"));
161 return -2;
162 }
163
164 /* Load layer_settings */
165 layer_sett = layer_settings_new();
166 layer_settings_load_from_csv(layer_sett, layer_file);
167
168 /* Create renderers */
169 if (create_renderers(renderers, output_file_names, tex_layers, tex_standalone,
170 ext_param, &renderer_list, layer_sett))
171 goto ret_destroy_layer_mapping;
172
173
174 /* Load GDS */
175 clear_lib_list(&libs);
176 res = parse_gds_from_file(gds_name, &libs);
177 if (res)
178 goto ret_destroy_library_list;
179
180 /* find_cell in first library. */
181 if (!libs)
182 goto ret_clear_renderers;
183
184 first_lib = (struct gds_library *)libs->data;
185 if (!first_lib) {
186 fprintf(stderr, _("No library in library list. This should not happen.\n"));
187 /* This is safe. Library destruction can handle an empty list element */
188 goto ret_destroy_library_list;
189 }
190
191 /* Find cell in first library */
192 toplevel_cell = find_gds_cell_in_lib(first_lib, cell_name);
193
194 if (!toplevel_cell) {
195 printf(_("Couldn't find cell in first library!\n"));
196 goto ret_destroy_library_list;
197 }
198
199 /* Check if cell passes vital checks */
201 if (res < 0) {
202 fprintf(stderr, _("Checking library %s failed.\n"), first_lib->name);
203 goto ret_destroy_library_list;
204 } else if (res > 0) {
205 fprintf(stderr, _("%d reference loops found.\n"), res);
206
207 /* do further checking if the specified cell and/or its subcells are affected */
208 if (toplevel_cell->checks.affected_by_reference_loop == 1) {
209 fprintf(stderr, _("Cell is affected by reference loop. Abort!\n"));
210 goto ret_destroy_library_list;
211 }
212 }
213
215 fprintf(stderr, _("Cell was not checked. This should not happen. Please report this issue. Will continue either way.\n"));
216
217 /* Note: unresolved references are not an abort condition.
218 * Deal with it.
219 */
220
221 /* Execute all rendererer instances */
222 for (list_iter = renderer_list; list_iter; list_iter = list_iter->next) {
223 current_renderer = GDS_RENDER_OUTPUT_RENDERER(list_iter->data);
224 gds_output_renderer_render_output(current_renderer, toplevel_cell, scale);
225 }
226
227ret_destroy_library_list:
228 clear_lib_list(&libs);
229ret_clear_renderers:
230 for (list_iter = renderer_list; list_iter; list_iter = list_iter->next)
231 g_object_unref(list_iter->data);
232ret_destroy_layer_mapping:
233 g_object_unref(layer_sett);
234 return ret;
235}
236
Header File for Cairo output renderer.
Render according to command line parameters.
Render according to command line parameters.
Header file for the GDS-Parser.
Checking functions of a cell tree (Header)
CairoRenderer * cairo_renderer_new_pdf()
Create new CairoRenderer for PDF output.
CairoRenderer * cairo_renderer_new_svg()
Create new CairoRenderer for SVG output.
ExternalRenderer * external_renderer_new_with_so_and_param(const char *so_path, const char *param_string)
Create new ExternalRenderer object with specified shared object path.
int gds_tree_check_reference_loops(struct gds_library *lib)
gds_tree_check_reference_loops checks if the given library contains reference loops
int clear_lib_list(GList **library_list)
Deletes all libraries including cells, references etc.
Definition: gds-parser.c:1146
int parse_gds_from_file(const char *filename, GList **library_list)
Parse a GDS file.
Definition: gds-parser.c:620
#define CELL_NAME_MAX
Maximum length of a gds_cell::name or a gds_library::name.
Definition: gds-types.h:37
@ GDS_CELL_CHECK_NOT_RUN
Definition: gds-types.h:45
void gds_output_renderer_set_output_file(GdsOutputRenderer *renderer, const gchar *file_name)
Convenience function for setting the "output-file" property.
int gds_output_renderer_render_output(GdsOutputRenderer *renderer, struct gds_cell *cell, double scale)
gds_output_renderer_render_output
void gds_output_renderer_set_layer_settings(GdsOutputRenderer *renderer, LayerSettings *settings)
Set layer settings.
LatexRenderer * latex_renderer_new_with_options(gboolean pdf_layers, gboolean standalone)
Create new LatexRenderer object.
output_renderer
return type of the RedererSettingsDialog
static int string_array_count(char **string_array)
Definition: command-line.c:42
static struct gds_cell * find_gds_cell_in_lib(struct gds_library *lib, const char *cell_name)
Definition: command-line.c:122
static int create_renderers(char **renderers, char **output_file_names, gboolean tex_layers, gboolean tex_standalone, const struct external_renderer_params *ext_params, GList **renderer_list, LayerSettings *layer_settings)
Definition: command-line.c:55
int command_line_convert_gds(const char *gds_name, const char *cell_name, char **renderers, char **output_file_names, const char *layer_file, struct external_renderer_params *ext_param, gboolean tex_standalone, gboolean tex_layers, double scale)
Convert GDS according to command line parameters.
Definition: command-line.c:138
LaTeX output renderer.
LayerSettings class header file.
LayerSettings * layer_settings_new()
New LayerSettings object.
int layer_settings_load_from_csv(LayerSettings *settings, const char *path)
Load new layer Settings from CSV.
External renderer paramameters to command line renderer.
Definition: command-line.h:39
char * cli_params
Command line parameters given.
Definition: command-line.h:48
char * so_path
Path to shared object.
Definition: command-line.h:43
int affected_by_reference_loop
1 if the cell is affected by a reference loop and therefore not renderable. Default: GDS_CELL_CHECK_N...
Definition: gds-types.h:73
A Cell inside a gds_library.
Definition: gds-types.h:122
struct gds_cell_checks checks
Checking results.
Definition: gds-types.h:129
char name[CELL_NAME_MAX]
Definition: gds-types.h:123
struct gds_library * parent_library
Pointer to parent library.
Definition: gds-types.h:128
GDS Toplevel library.
Definition: gds-types.h:135
GList * cells
Definition: gds-types.h:140
char name[CELL_NAME_MAX]
Definition: gds-types.h:136