FreeCalypso > hg > ueda-linux
comparison ueda/uschem-utils/rewrite.c @ 0:cd92449fdb51
initial import of ueda and ifctf-part-lib from ifctfvax CVS
author | Space Falcon <falcon@ivan.Harhan.ORG> |
---|---|
date | Mon, 20 Jul 2015 00:24:37 +0000 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 0:cd92449fdb51 |
---|---|
1 /* | |
2 * This program reads a uschem schematic into core and then writes it back out. | |
3 * -g options converts NetLines to GraphNets and then preens/canonicalizes | |
4 * all GraphNets, otherwise just exercises the parser & writer code in | |
5 * libuschem. | |
6 */ | |
7 | |
8 #include <sys/types.h> | |
9 #include <sys/file.h> | |
10 #include <stdio.h> | |
11 #include <strings.h> | |
12 #include "../libuschem/schemstruct.h" | |
13 #include "../libuschem/graphsym.h" | |
14 | |
15 extern int optind; | |
16 extern char *optarg; | |
17 extern char *malloc(); | |
18 | |
19 extern struct schem *read_schem(); | |
20 extern struct netpoint *parser_alloc_netpoint(); | |
21 extern struct graphsym_pininst *find_pin_by_coord(); | |
22 | |
23 struct schem *schem; | |
24 char *outfile; | |
25 int replace_orig; | |
26 int gflag, Oflag; | |
27 | |
28 char * | |
29 mk_temp_newfilename() | |
30 { | |
31 int len; | |
32 register char *str; | |
33 | |
34 len = strlen(schem->orig_filename) + 5; | |
35 str = malloc(len); | |
36 if (!str) { | |
37 perror("malloc"); | |
38 exit(1); | |
39 } | |
40 sprintf(str, "%s.new", schem->orig_filename); | |
41 return(str); | |
42 } | |
43 | |
44 main(argc, argv) | |
45 char **argv; | |
46 { | |
47 register int c; | |
48 int fd; | |
49 FILE *outf; | |
50 | |
51 while ((c = getopt(argc, argv, "gI:o:O")) != EOF) | |
52 switch (c) { | |
53 case 'g': | |
54 gflag++; | |
55 break; | |
56 case 'I': | |
57 add_symfile_dir(optarg); | |
58 break; | |
59 case 'o': | |
60 outfile = optarg; | |
61 break; | |
62 case 'O': | |
63 Oflag++; | |
64 break; | |
65 default: | |
66 usage: fprintf(stderr, "usage: %s [-o newfile] schemfile\n", | |
67 argv[0]); | |
68 exit(1); | |
69 } | |
70 if (!argv[optind]) | |
71 goto usage; | |
72 | |
73 schem = read_schem(argv[optind]); | |
74 if (!outfile) { | |
75 outfile = mk_temp_newfilename(); | |
76 replace_orig = 1; | |
77 } | |
78 | |
79 if (gflag) { | |
80 if (hash_component_instances(schem) < 0) | |
81 exit(1); | |
82 set_default_sympath(); | |
83 load_graphsyms(schem); | |
84 if (instantiate_graphsym_pins(schem, 1) < 0 && !Oflag) | |
85 exit(1); | |
86 convert_netlines_to_graphnets(); | |
87 if (preen_graphnets(schem, 1, 1, 0, 1) < 0) | |
88 exit(1); | |
89 } | |
90 | |
91 c = O_WRONLY | O_CREAT; | |
92 if (replace_orig) | |
93 c |= O_EXCL; | |
94 else | |
95 c |= O_TRUNC; | |
96 fd = open(outfile, c, 0644); | |
97 if (fd < 0) { | |
98 perror(outfile); | |
99 exit(1); | |
100 } | |
101 outf = fdopen(fd, "w"); | |
102 if (!outf) { | |
103 perror("fdopen"); | |
104 exit(1); | |
105 } | |
106 write_schem(schem, outf); | |
107 fclose(outf); | |
108 if (replace_orig) | |
109 rename(outfile, schem->orig_filename); | |
110 exit(0); | |
111 } | |
112 | |
113 convert_netlines_to_graphnets() | |
114 { | |
115 register struct schemobj *obj; | |
116 | |
117 for (obj = schem->obj_next; obj != (struct schemobj *)schem; | |
118 obj = obj->obj_next) | |
119 if (obj->obj_type == OBJTYPE_NETLINE) | |
120 convert_netline(obj); | |
121 } | |
122 | |
123 convert_netline(obj) | |
124 register struct schemobj *obj; | |
125 { | |
126 register struct netpoint *end1, *end2; | |
127 | |
128 end1 = parser_alloc_netpoint(NETPT_TYPE_POINT); | |
129 end1->netpt_x = obj->lineobj_x1; | |
130 end1->netpt_y = obj->lineobj_y1; | |
131 end1->netpt_coord_valid = 1; | |
132 pinify_netpoint(end1); | |
133 end2 = parser_alloc_netpoint(NETPT_TYPE_POINT); | |
134 end2->netpt_x = obj->lineobj_x2; | |
135 end2->netpt_y = obj->lineobj_y2; | |
136 end2->netpt_coord_valid = 1; | |
137 pinify_netpoint(end2); | |
138 end1->netpt_next = end2; | |
139 obj->obj_type = OBJTYPE_GRAPHNET; | |
140 obj->netobj_points = end1; | |
141 obj->netobj_netname = NULL; | |
142 if (!extend_new_graphnet(obj)) { | |
143 end1->netpt_next = NULL; | |
144 end2->netpt_next = end1; | |
145 obj->netobj_points = end2; | |
146 extend_new_graphnet(obj); | |
147 } | |
148 convert_netline_decors(obj); | |
149 } | |
150 | |
151 pinify_netpoint(netpt) | |
152 register struct netpoint *netpt; | |
153 { | |
154 register struct graphsym_pininst *pin; | |
155 | |
156 pin = find_pin_by_coord(schem, netpt->netpt_x, netpt->netpt_y); | |
157 if (!pin) | |
158 return; | |
159 switch (pin->compinst->obj_type) { | |
160 case OBJTYPE_COMPINST: | |
161 netpt->netpt_type = NETPT_TYPE_PIN; | |
162 return; | |
163 case OBJTYPE_GRAPHSYM: | |
164 netpt->netpt_type = NETPT_TYPE_PSEUDO; | |
165 return; | |
166 } | |
167 } | |
168 | |
169 convert_netline_decors(obj) | |
170 struct schemobj *obj; | |
171 { | |
172 register struct decoration *decor; | |
173 struct decoration **np; | |
174 | |
175 for (np = &obj->obj_decorations; decor = *np; ) { | |
176 switch (decor->decor_type) { | |
177 case DECOR_TYPE_ATTR: | |
178 if (strcmp(decor->decorattr_name, "netname")) | |
179 break; | |
180 if (obj->netobj_netname && | |
181 strcmp(obj->netobj_netname, decor->decorattr_value)) { | |
182 fprintf(stderr, | |
183 "%s: line %d: net name conflict\n", | |
184 schem->orig_filename, | |
185 decor->decor_lineno); | |
186 exit(1); | |
187 } | |
188 obj->netobj_netname = decor->decorattr_value; | |
189 /* drop the decoration */ | |
190 *np = decor->decor_next; | |
191 continue; | |
192 case DECOR_TYPE_DISPLAYATTR: | |
193 if (!strcmp(decor->decordisp_attr, "netname")) | |
194 decor->decor_type = DECOR_TYPE_DISPLAYNETNAME; | |
195 break; | |
196 } | |
197 np = &decor->decor_next; | |
198 } | |
199 } | |
200 | |
201 struct netpoint * | |
202 convert_netline_to_netpt(gn, nlobj, whichend) | |
203 struct schemobj *gn; | |
204 register struct schemobj *nlobj; | |
205 int whichend; | |
206 { | |
207 register struct netpoint *netpt; | |
208 | |
209 netpt = parser_alloc_netpoint(NETPT_TYPE_POINT); | |
210 switch (whichend) { | |
211 case 1: | |
212 netpt->netpt_x = nlobj->lineobj_x1; | |
213 netpt->netpt_y = nlobj->lineobj_y1; | |
214 break; | |
215 case 2: | |
216 netpt->netpt_x = nlobj->lineobj_x2; | |
217 netpt->netpt_y = nlobj->lineobj_y2; | |
218 break; | |
219 } | |
220 netpt->netpt_coord_valid = 1; | |
221 pinify_netpoint(netpt); | |
222 netconvert_append_decors(gn, nlobj); | |
223 schemobj_unlink(nlobj); | |
224 return(netpt); | |
225 } | |
226 | |
227 extend_new_graphnet(gn) | |
228 struct schemobj *gn; | |
229 { | |
230 register struct schemobj *obj; | |
231 register struct netpoint *tail, *new; | |
232 int success = 0; | |
233 | |
234 tail = gn->netobj_points->netpt_next; | |
235 loop: for (obj = gn->obj_next; obj != (struct schemobj *)schem; | |
236 obj = obj->obj_next) { | |
237 if (obj->obj_type != OBJTYPE_NETLINE) | |
238 continue; | |
239 if (obj->lineobj_x1 == tail->netpt_x && | |
240 obj->lineobj_y1 == tail->netpt_y) { | |
241 new = convert_netline_to_netpt(gn, obj, 2); | |
242 tail->netpt_next = new; | |
243 tail = new; | |
244 success = 1; | |
245 goto loop; | |
246 } | |
247 if (obj->lineobj_x2 == tail->netpt_x && | |
248 obj->lineobj_y2 == tail->netpt_y) { | |
249 new = convert_netline_to_netpt(gn, obj, 1); | |
250 tail->netpt_next = new; | |
251 tail = new; | |
252 success = 1; | |
253 goto loop; | |
254 } | |
255 } | |
256 return(success); | |
257 } | |
258 | |
259 netconvert_append_decors(gnobj, nlobj) | |
260 struct schemobj *gnobj, *nlobj; | |
261 { | |
262 register struct decoration *decor; | |
263 register struct decoration **np; | |
264 | |
265 for (np = &gnobj->obj_decorations; decor = *np; np = &decor->decor_next) | |
266 ; | |
267 *np = nlobj->obj_decorations; | |
268 } |