~cypheon/kicad2spice

ref: 96e390bc4f914314da98ecdfd7bd775e620563e2 kicad2spice/lib/parser.ml -rw-r--r-- 2.6 KiB
96e390bc — Johann Rudloff Implement correct pin order according to field "Spice_Node_Sequence" 3 years ago
                                                                                
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
open Lexing

let print_position outx lexbuf =
  let pos = lexbuf.lex_curr_p in
  Printf.fprintf outx "%s:%d:%d" pos.pos_fname
    pos.pos_lnum (pos.pos_cnum - pos.pos_bol + 1)

let parse_with_error p l lexbuf =
  try Some (p l lexbuf) with
  | Lex_sch_legacy.SyntaxError msg ->
    Printf.fprintf stderr "%a: %s\n" print_position lexbuf msg;
    None
  | Lex_lib.SyntaxError msg ->
    Printf.fprintf stderr "%a: %s\n" print_position lexbuf msg;
    None
  | Sch_legacy.Error ->
    Printf.fprintf stderr "%a: syntax error\n" print_position lexbuf;
    exit (-1)

let parse_and_print p l printer lexbuf =
  match parse_with_error p l lexbuf with
  | Some value ->
    Printf.printf "%a@\n" printer value;
    Some value
  | None -> None

let process p l printer filename =
  let inch = open_in filename in
  let lexbuf = Lexing.from_channel inch in
  lexbuf.lex_curr_p <- { lexbuf.lex_curr_p with pos_fname = filename };
  let ret = parse_and_print p l printer lexbuf in
  close_in inch;
  ret

let format_compdeflist outch cd =
  Printf.fprintf outch "COMPDEFS: %s"
  (String.concat "\n---\n" (List.map Schematic.CompDef.show cd))

let ignore2 _ _ = ()

let mangle_compname n =
  n |>
  String.split_on_char ':' |>
  String.concat "_"

let resolve_item compdefs = let open Sch_legacy_ast in function
  | ParserItem.Wire w -> Schematic.Item.Wire w
  | ParserItem.Junction j -> Schematic.Item.Junction j
  | ParserItem.Comp c ->
      let mangled = mangle_compname c.name in
      match (List.find_opt (fun c -> c.Schematic.CompDef.name = mangled) compdefs) with
        | Some part -> Schematic.Item.Comp {name=c.name; part;ref=c.ref;pos=c.pos;transform=c.transform;value=c.value;fields=c.fields;}
        | None -> failwith ("unknown component: " ^ mangled)

let resolve compdefs (version, items) =
  {Schematic. version;
   items=List.map (resolve_item compdefs) items;
  }

let cache_lib sch_filename = match (Util.replace_suffix sch_filename ".sch" "-cache.lib") with
  | Some v -> v
  | None -> raise (Invalid_argument ("can not find cache lib for file: " ^ sch_filename))

let convert compdef_filename sch_filename output_filename = match process Parse_lib.main Lex_lib.read format_compdeflist compdef_filename with
  | Some compdefs -> begin
    match process Sch_legacy.main Lex_sch_legacy.read ignore2 sch_filename with
      | Some parser_schematic ->
          let schematic = resolve compdefs parser_schematic in
          let netlist = Connectiongraph.connection schematic in
          let outch = open_out output_filename in
          Export_spice.write_netlist outch schematic netlist
      | _ -> ()
  end
  | _ -> ()