KiBot/kibot/resources/parsers/electro.lark

215 lines
7.0 KiB
Plaintext

//*****************************************************************************
//
// Copyright (c) 2023 Salvador E. Tropea
// Copyright (c) 2023 Instituto Nacional de Tecnologia Industrial
// Copyright (c) 2017-2018 Kaspar Emanuel
//
// LICENSE: MIT
//
// Grammar to parse electronic components.
// Can currently parse resistors, capacitors, inductors and LEDs.
// Is strongly based on "electro-grammar" created by Kaspar Emanuel.
// This description was coded to be used with Lark, a Python tool.
// Is an ambiguous description, so it needs the Early algorithm.
// Unlike the original version by Kaspar, implemented using Nearly, this
// grammar handles the stuff to ignore in the grammar description, not retrying
// in the parser. I think Lark can't retry. This makes things a little bit more
// complicated, and harder to debug.
//
//*****************************************************************************
%import common.INT
%import common.NUMBER
%import common.WS
%import common.CNAME
?main: capacitor | inductor | resistor | led
// All we ignore
crap: CNAME | NUMBER | CNAME "/" CNAME
// Whitespace and separators
_WS: WS
_SEP: _WS | /[,;]/
//************************************
//************ Capacitors ************
//************************************
// When we know this is a capacitor we don't need the units
capacitor: _CAP? _c_specs capacitance _c_specs
| _CAP _c_specs (capacitance_no_farad | capacitance)? (_c_specs | c_spec)
_c_specs: ((c_spec _SEP)+ | (_SEP c_spec)+ | _SEP)*
?c_spec: tolerance | temp_coef | voltage_rating | package_size | crap
// Give priority to things like "25 V" to avoid separating the "V" as crap
voltage_rating.6: NUMBER _WS? _VOLT INT?
// See https://en.wikipedia.org/wiki/Ceramic_capacitor#Class_1_ceramic_capacitor
// https://en.wikipedia.org/wiki/Ceramic_capacitor#Class_2_ceramic_capacitor
temp_coef: _class1 | _class2
_class1: P100 | C0G | N33 | N75 | N150 | N220 | N330 | N470 | N750 | N1000 | N1500
_class2: /[XYZ]/i "4".."9" /[PRSTUV]/i
tolerance: (_PLUSMINUS _WS?)? NUMBER _WS? "%"
capacitance.10: (_capacitance_no_farad | NUMBER) _WS? _FARAD
capacitance_no_farad.10: _capacitance_no_farad
_capacitance_no_farad: INT _c_metric_prefix INT?
| NUMBER _WS? _c_metric_prefix
_c_metric_prefix: milli | micro | nano | pico
//***********************************
//************ Inductors ************
//***********************************
// When we know this is an inductor we don't need the units
inductor: _IND? _l_specs inductance _l_specs
| _IND _l_specs (inductance_no_henry | inductance)? (_l_specs | l_spec)
_l_specs: ((l_spec _SEP)+ | (_SEP l_spec)+ | _SEP)*
?l_spec: tolerance | voltage_rating | package_size | crap
inductance: _inductance_no_henry _WS? _HENRY
inductance_no_henry: _inductance_no_henry
_inductance_no_henry: NUMBER _WS? _l_metric_prefix? INT?
_l_metric_prefix: milli | micro | nano | pico
//***********************************
//************ Resistors ************
//***********************************
// When we know this is a resistor we don't need the units
resistor: _RES? _r_specs resistance _r_specs
| _RES _r_specs (resistance_no_r | resistance)? (_r_specs | r_spec)
_r_specs: ((r_spec _SEP)+ | (_SEP r_spec)+ | _SEP)*
?r_spec: tolerance | power_rating | package_size | crap
power_rating: _power_rating_decimal | _power_rating_fraction
_power_rating_fraction: INT "/" INT _WS? _WATTS
_power_rating_decimal: NUMBER _WS? _power_metric_prefix? _WS? _WATTS
_power_metric_prefix: giga | mega | kilo | milli | micro | nano | pico | femto
resistance.9: NUMBER _WS? (_r_metric_prefix INT? (_WS? _OHM)? | _OHM)
// Just a number, no R, K, ohm etc.
resistance_no_r.9: NUMBER
_r_metric_prefix: giga | mega | kilo | unit | milli | micro
//******************************
//************ LEDs ************
//******************************
led: _led_specs _LED (_SEP _led_specs _led_spec?)?
_led_specs: ((_led_spec _SEP)+ | (_SEP _led_spec)+ | _SEP)*
_led_spec: package_size | color | crap
!color: "red"i
| "green"i
| "blue"i
| "yellow"i
| "orange"i
| "white"i
| "amber"i
| "cyan"i
| "purple"i
| "yellow" WS "green"
//******************************
//************ Size ************
//******************************
// Sizes looks like numbers and resistors doesn't need units, things like 2512 are hard to differentiate from a
// resistor value. So we use a high priority here
?package_size.11: imperial_size | metric_size
!imperial_size.11: IS01005 | IS0201 | IS0402 | IS0603 | IS0805 | IS1008 | IS1206 | IS1210 | IS1806 | IS2010 | IS2512
?metric_size.11: metric_size_base _WS _METRIC
| _METRIC _WS metric_size_base
| unambigious_metric_size
// Metric sizes, with names to avoid anonymous
!unambigious_metric_size.11: MS1005 | MS1608 | MS2012 | MS2520 | MS3216 | MS3225 | MS4516 | MS5025 | MS6332
!metric_size_base.11: unambigious_metric_size | MS0402 | MS0603
//******************************
//****** Metric prefixes *******
//******************************
// !exa: "E" | "exa"i
// !peta: "P" | "peta"i
// !tera: "T" | "tera"i
!giga: "G" | "gig"i "a"i?
!mega: "M" | "meg"i "a"i?
!kilo: "K"i "ilo"i?
!unit: "R"i
// !hecto: "h" | "hecto"i
// !deci: "d" | "deci"i
// !centi: "c" | "centi"i
!milli: "m" | "milli"i
!micro: "U"i
| "\u03BC"
| "\u00B5"
| "𝛍"
| "𝜇"
| "𝝁"
| "𝝻"
| "𝞵"
| /micro/i
!nano: "N"i | "nan"i "o"i?
!pico: "P"i "ico"i?
!femto: "f" | "femto"i
// !atto: "a" | "atto"i
//******************************
//****** Named terminals *******
//******************************
// Components
_CAP: ("CAPACITOR"i | "CAPA"i | "C"i "AP"i?) _SEP
_RES: ("RESISTOR"i | "RES"i | "R"i) _SEP
_IND: ("IND"i "UCTOR"i? | "L"i) _SEP
_LED: "LED"i
// Units
_FARAD: "F"i "arad"i?
_OHM: "ohm"i "s"i? | "Ω" | "Ω"
_HENRY: "h"i "enry"i?
_VOLT: "Volt"i "s"i? | "V"i
_WATTS: "W"i ("atts"i | "att"i)?
// Used for percent
_PLUSMINUS: "+/-" | "±" | "+-"
// Size
IS01005: "01005"
IS0201: "0201"
IS0402: "0402"
IS0603: "0603"
IS0805: "0805"
IS1008: "1008"
IS1206: "1206"
IS1210: "1210"
IS1806: "1806"
IS2010: "2010"
IS2512: "2512"
_METRIC: "METRIC"i
MS1005: "1005"
MS1608: "1608"
MS2012: "2012"
MS2520: "2520"
MS3216: "3216"
MS3225: "3225"
MS4516: "4516"
MS5025: "5025"
MS6332: "6332"
MS0402: "0402"
MS0603: "0603"
// Capacitor temp. coef. classes
P100: "P100"i "/" "M7G"i | "M7G"i "/" "P100"i | "P100"i | "M7G"i
N33: "N33"i "/" "H2G"i | "H2G"i "/" "N33"i | "N33"i | "H2G"i
N75: "N75"i "/" "L2G"i | "L2G"i "/" "N75"i | "N75"i | "L2G"i
N150: "N150"i "/" "P2H"i | "P2H"i "/" "N150"i | "N150"i | "P2H"i
N220: "N220"i "/" "R2H"i | "R2H"i "/" "N220"i | "N220"i | "R2H"i
N330: "N330"i "/" "S2H"i | "S2H"i "/" "N330"i | "N330"i | "S2H"i
N470: "N470"i "/" "T2H"i | "T2H"i "/" "N470"i | "N470"i | "T2H"i
N750: "N750"i "/" "U2J"i | "U2J"i "/" "N750"i | "N750"i | "U2J"i
N1000: "N1000"i "/" "Q3K"i | "Q3K"i "/" "N1000"i | "N1000"i | "Q3K"i
N1500: "N1500"i "/" "P3K"i | "P3K"i "/" "N1500"i | "N1500"i | "P3K"i
C0G: /C[O0]G/i "/" /NP[O0]/i | /NP[O0]/i "/" /C[O0]G/i | /C[O0]G/i | /NP[O0]/i