ParamManagerScripts/backend/script_groups/XML Parser to SCL/processors/process_sr.py

106 lines
3.9 KiB
Python

# processors/process_sr.py
# -*- coding: utf-8 -*-
import sympy
import traceback
from .processor_utils import (
get_sympy_representation,
sympy_expr_to_scl,
get_target_scl_name,
format_variable_name,
)
from .symbol_manager import SymbolManager
SCL_SUFFIX = "_sympy_processed"
def process_sr(instruction, network_id, sympy_map, symbol_manager: SymbolManager, data):
"""
Genera SCL para Set/Reset flip-flop (Sr).
"""
instr_uid = instruction["instruction_uid"]
instr_type_original = instruction.get("type", "Sr")
if instr_type_original.endswith(SCL_SUFFIX) or "_error" in instr_type_original:
return False
# Verificar si la instrucción tiene conexiones válidas
inputs = instruction.get("inputs", {})
outputs = instruction.get("outputs", {})
# Si no tiene conexiones, marcar como procesado sin generar código
if not inputs and not outputs:
instruction["scl"] = (
"// Sr flip-flop sin conexiones - procesado como placeholder"
)
instruction["type"] = instr_type_original + SCL_SUFFIX
return True
# Extraer la variable de salida (operand)
operand_info = inputs.get("operand")
if not operand_info or operand_info.get("type") != "variable":
instruction["scl"] = f"// ERROR: Sr {instr_uid} sin variable operand válida."
instruction["type"] = instr_type_original + "_error"
return True
output_var = operand_info.get("name", f"Unknown_Sr_{instr_uid}")
output_var_formatted = format_variable_name(output_var)
# Obtener condiciones Set y Reset
set_condition = inputs.get("s")
reset_condition = inputs.get("r1")
scl_lines = []
scl_lines.append(f"// Sr flip-flop for {output_var_formatted}")
# Generar código Set (prioridad alta)
if set_condition:
try:
set_key = (network_id, instr_uid, "s")
set_sympy_expr = get_sympy_representation(
set_condition, network_id, sympy_map, symbol_manager
)
if set_sympy_expr is not None:
sympy_map[set_key] = set_sympy_expr
set_scl = sympy_expr_to_scl(set_sympy_expr, symbol_manager)
scl_lines.append(f"IF {set_scl} THEN")
scl_lines.append(f" {output_var_formatted} := TRUE;")
scl_lines.append("END_IF;")
except Exception as e:
scl_lines.append(f"// ERROR procesando condición Set: {e}")
# Generar código Reset (prioridad baja)
if reset_condition:
try:
reset_key = (network_id, instr_uid, "r1")
reset_sympy_expr = get_sympy_representation(
reset_condition, network_id, sympy_map, symbol_manager
)
if reset_sympy_expr is not None:
sympy_map[reset_key] = reset_sympy_expr
reset_scl = sympy_expr_to_scl(reset_sympy_expr, symbol_manager)
scl_lines.append(f"IF {reset_scl} THEN")
scl_lines.append(f" {output_var_formatted} := FALSE;")
scl_lines.append("END_IF;")
except Exception as e:
scl_lines.append(f"// ERROR procesando condición Reset: {e}")
# Generar también la salida Q del Sr en sympy_map para que otros puedan usarla
try:
output_key = (network_id, instr_uid, "Q")
output_symbol = symbol_manager.get_symbol(output_var_formatted)
if output_symbol:
sympy_map[output_key] = output_symbol
except Exception as e:
print(
f"Warning: No se pudo crear símbolo sympy para Sr output {output_var_formatted}: {e}"
)
instruction["scl"] = "\n".join(scl_lines)
instruction["type"] = instr_type_original + SCL_SUFFIX
return True
# --- Processor Information Function ---
def get_processor_info():
"""Devuelve la información para el procesador Sr."""
return {"type_name": "sr", "processor_func": process_sr, "priority": 4}