FreeCalypso > hg > ueda-linux
diff ueda/uschem-print/printpage.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 |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/ueda/uschem-print/printpage.c Mon Jul 20 00:24:37 2015 +0000 @@ -0,0 +1,204 @@ +#include <sys/types.h> +#include <stdio.h> +#include <strings.h> +#include "../libuschem/schemstruct.h" +#include "../libuschem/graphsym.h" + +extern FILE *reopen_schem_for_graphblocks(); +extern char *get_compinst_attr(); +extern char *pinname_to_pinnumber(); + +extern struct schem **schem_pages; +extern int npages; + +struct schem *schem_being_printed; +FILE *schemfile_for_graphblocks; + +static enum {LINEWIDTH_UNDEF, LINEWIDTH_NET, LINEWIDTH_BUS} pagelevel_linewidth; + +print_schem_page(pageno) + int pageno; /* zero-based */ +{ + register struct schem *schem; + register struct schemobj *obj; + + schem = schem_pages[pageno]; + schem_being_printed = schem; + schemfile_for_graphblocks = reopen_schem_for_graphblocks(schem); + printf("%%%%Page: %s %d\n", schem->orig_filename, pageno + 1); + puts("save $uschem begin"); + printf("/drawingsize_x %d def\n", schem->graph_xsize); + printf("/drawingsize_y %d def\n", schem->graph_ysize); + puts("setscale"); + pagelevel_linewidth = LINEWIDTH_UNDEF; + reset_decor_font(); + for (obj = schem->obj_next; obj != (struct schemobj *) schem; + obj = obj->obj_next) + print_schem_obj(obj); + if (schemfile_for_graphblocks) + fclose(schemfile_for_graphblocks); + puts("end restore showpage"); + return(0); +} + +print_schem_obj(obj) + register struct schemobj *obj; +{ + switch (obj->obj_type) { + case OBJTYPE_COMPINST: + if (!obj->compobj_isgraph) + return; + /* FALL THRU */ + case OBJTYPE_GRAPHSYM: + print_graph_compinst(obj); + return; + case OBJTYPE_GRAPHNET: + if (pagelevel_linewidth != LINEWIDTH_NET) { + puts("netlinewidth setlinewidth"); + pagelevel_linewidth = LINEWIDTH_NET; + } + print_graphnet(obj); + print_obj_decors(obj); + return; + case OBJTYPE_NETLINE: + if (pagelevel_linewidth != LINEWIDTH_NET) { + puts("netlinewidth setlinewidth"); + pagelevel_linewidth = LINEWIDTH_NET; + } + printf("%d %d moveto %d %d lineto stroke\n", obj->lineobj_x1, + obj->lineobj_y1, obj->lineobj_x2, obj->lineobj_y2); + print_obj_decors(obj); + return; + case OBJTYPE_BUSSEG: + if (pagelevel_linewidth != LINEWIDTH_BUS) { + puts("buslinewidth setlinewidth"); + pagelevel_linewidth = LINEWIDTH_BUS; + } + printf("%d %d moveto %d %d lineto stroke\n", obj->lineobj_x1, + obj->lineobj_y1, obj->lineobj_x2, obj->lineobj_y2); + print_obj_decors(obj); + return; + case OBJTYPE_GRAPHBLOCK: + print_graphblock(obj->graphblockobj_body); + return; + } +} + +print_graph_compinst(obj) + register struct schemobj *obj; +{ + register struct graphsym *gs; + char *slot; + + gs = obj->compobj_graphsym; + printf("save %d %d translate", obj->compobj_x, obj->compobj_y); + if (obj->compobj_rotate) + printf(" %d rotate", obj->compobj_rotate); + putchar('\n'); + printf("/mirrored %s def\n", obj->compobj_mirror ? "true" : "false"); + if (gs->gs_varpins) { + if (obj->obj_type != OBJTYPE_COMPINST) { + fprintf(stderr, +"%s: line %d: symbol \"%s\" has variable pins; may not be used w/o component\n", + schem_being_printed->orig_filename, + obj->obj_lineno, gs->gs_name); + exit(1); + } + slot = get_compinst_attr(obj, "slot"); + define_varpins(gs, obj->compobj_mclcomp, slot); + } + printf("symbols /%s get exec restore\n", gs->gs_name); + print_obj_decors(obj); +} + +define_varpins(gs, comp, slot) + struct graphsym *gs; + struct component *comp; + char *slot; +{ + register struct graphsym_pindef *pin; + register char *cp; + + puts("/pins ["); + for (pin = gs->gs_pins; pin; pin = pin->gspd_next) + if (pin->gspd_pinnumber && !strcmp(pin->gspd_pinnumber, "%d")) { + if (pin->gspd_pinname) + cp = pinname_to_pinnumber(comp, + pin->gspd_pinname, slot); + else { + fprintf(stderr, + "Symbol %s: variable pin has no pinname attribute\n", + gs->gs_name); + cp = NULL; + } + putchar(' '); + if (cp) + emit_ps_string(cp); + else { + putchar('('); + putchar(')'); + } + putchar('\n'); + } + puts("] def"); +} + +print_graphnet(obj) + struct schemobj *obj; +{ + register struct netpoint *netpt; + register int first; + + for (netpt = obj->netobj_points, first = 1; netpt; + netpt = netpt->netpt_next) { + if (!netpt->netpt_coord_valid) { + fprintf(stderr, + "%s: line %d: GraphNet contains Pin w/o coordinates, not printed\n", + schem_being_printed->orig_filename, + obj->obj_lineno); + puts("newpath"); /* kludge in lieu of abort */ + return; + } + printf("%d %d %s\n", netpt->netpt_x, netpt->netpt_y, + first ? "moveto" : "lineto"); + first = 0; + } + puts("stroke"); + /* connection dots */ + for (netpt = obj->netobj_points, first = 1; netpt; + netpt = netpt->netpt_next, first = 0) + switch (netpt->netpt_type) { + case NETPT_TYPE_PIN: + case NETPT_TYPE_PSEUDO: + if (first || !netpt->netpt_next) + continue; + /* FALL THRU */ + case NETPT_TYPE_TJOIN: + printf("%d %d conndot\n", netpt->netpt_x, + netpt->netpt_y); + continue; + } +} + +print_graphblock(blk) + register struct graphblock *blk; +{ + puts("save"); + switch (blk->type) { + case GRAPHBLOCK_TYPE_PS: + write_graphblock_to_file(blk, schemfile_for_graphblocks, + stdout); + break; + case GRAPHBLOCK_TYPE_GSCHEM: + print_gschem_code_graphblk(schemfile_for_graphblocks, blk, + schem_being_printed->orig_filename); + break; + default: + fprintf(stderr, + "Fatal internal error: unknown graphblock type %d (from %s line %d)\n", + blk->type, schem_being_printed->orig_filename, + blk->lineno); + exit(1); + } + puts("restore"); +}