diff options
| author | Clément Zrounba <6691770+clement-z@users.noreply.github.com> | 2023-09-30 23:06:01 +0200 |
|---|---|---|
| committer | Clément Zrounba <6691770+clement-z@users.noreply.github.com> | 2023-09-30 23:26:46 +0200 |
| commit | ff9b8bb838ecdfbfc1dc81038fcf3b2a87636982 (patch) | |
| tree | 21f27be782ce11c6d00b96ce100a2bff88141b2e /src/devices/directional_coupler.cpp | |
| download | specs-ff9b8bb838ecdfbfc1dc81038fcf3b2a87636982.tar.gz specs-ff9b8bb838ecdfbfc1dc81038fcf3b2a87636982.zip | |
Initial release
Diffstat (limited to 'src/devices/directional_coupler.cpp')
| -rw-r--r-- | src/devices/directional_coupler.cpp | 318 |
1 files changed, 318 insertions, 0 deletions
diff --git a/src/devices/directional_coupler.cpp b/src/devices/directional_coupler.cpp new file mode 100644 index 0000000..da0872b --- /dev/null +++ b/src/devices/directional_coupler.cpp @@ -0,0 +1,318 @@ +#include "specs.h" +#include <directional_coupler.h> + +using namespace std; + +void DirectionalCouplerUni::on_port_in1_changed() +{ + m_through_power_dB = 10*log10(m_dc_through_coupling_power) - m_dc_loss; + m_cross_power_dB = 10*log10(1.0 - m_dc_through_coupling_power) - m_dc_loss; + + m_memory_in1[0] = 0; // initializing for nan wavelength + + const double transmission_through = pow(10.0, m_through_power_dB / 20.0); + const double transmission_cross = pow(10.0, m_cross_power_dB / 20.0); + + // Pre-calculate S-parameters + OpticalSignal::field_type S13, S14, S23, S24; + S13 = polar(transmission_through, m_through_phase_rad); + S24 = polar(transmission_through, m_through_phase_rad); + S14 = polar(transmission_cross, m_cross_phase_rad); + S23 = polar(transmission_cross, m_cross_phase_rad); + + if (specsGlobalConfig.verbose_component_initialization) + { + cout << name() << ":" << endl; + cout << "through_power = " << norm(S13) << " W/W" << endl; + cout << "cross_power = " << norm(S14)<< " W/W" << endl; + cout << "through_field = " << abs(S13) << "" << endl; + cout << "cross_field = " << abs(S14)<< "" << endl; + cout << "insertion loss = " << m_dc_loss << "dB" << endl; + cout << (dynamic_cast<spx::oa_signal_type *>(p_in1.get_interface()))->name(); + cout << " --,__,-> "; + cout << (dynamic_cast<spx::oa_signal_type *>(p_out1.get_interface()))->name(); + cout << endl; + + cout << (dynamic_cast<spx::oa_signal_type *>(p_in2.get_interface()))->name(); + cout << " --' '-> "; + cout << (dynamic_cast<spx::oa_signal_type *>(p_out2.get_interface()))->name(); + cout << endl; + + cout << endl; + } + + OpticalSignal p_in1_read; + + while (true) { + // Wait for a new input signal + wait(); + + // Read current inputs + p_in1_read = p_in1->read(); + + auto cur_wavelength_id = p_in1_read.m_wavelength_id; + // Updating the field memory + m_memory_in1[cur_wavelength_id] = p_in1_read.m_field; + + auto s3 = OpticalSignal(m_memory_in1[cur_wavelength_id] * S13 + + m_memory_in2[cur_wavelength_id] * S23 + , cur_wavelength_id); + + auto s4 = OpticalSignal(m_memory_in1[cur_wavelength_id] * S14 + + m_memory_in2[cur_wavelength_id] * S24 + , cur_wavelength_id); + + m_out1_writer.delayedWrite(s3, sc_time(m_delay_ns, SC_NS)); + m_out2_writer.delayedWrite(s4, sc_time(m_delay_ns, SC_NS)); + } +} + +void DirectionalCouplerUni::on_port_in2_changed() +{ + m_through_power_dB = 10*log10(m_dc_through_coupling_power) - m_dc_loss; + m_cross_power_dB = 10*log10(1.0 - m_dc_through_coupling_power) - m_dc_loss; + + m_memory_in2[0] = 0; // initializing for nan wavelength + + const double transmission_through = pow(10.0, m_through_power_dB / 20.0); + const double transmission_cross = pow(10.0, m_cross_power_dB / 20.0); + + // Pre-calculate S-parameters + OpticalSignal::field_type S13, S14, S23, S24; + S13 = polar(transmission_through, m_through_phase_rad); + S24 = polar(transmission_through, m_through_phase_rad); + S14 = polar(transmission_cross, m_cross_phase_rad); + S23 = polar(transmission_cross, m_cross_phase_rad); + + OpticalSignal p_in2_read; + + while (true) { + // Wait for a new input signal + wait(); + + // Read current inputs + p_in2_read = p_in2->read(); + + auto cur_wavelength_id = p_in2_read.m_wavelength_id; + // Updating the field memory + m_memory_in2[cur_wavelength_id] = p_in2_read.m_field; + + auto s3 = OpticalSignal(m_memory_in1[cur_wavelength_id] * S13 + + m_memory_in2[cur_wavelength_id] * S23 + , cur_wavelength_id); + + auto s4 = OpticalSignal(m_memory_in1[cur_wavelength_id] * S14 + + m_memory_in2[cur_wavelength_id] * S24 + , cur_wavelength_id); + + m_out1_writer.delayedWrite(s3, sc_time(m_delay_ns, SC_NS)); + m_out2_writer.delayedWrite(s4, sc_time(m_delay_ns, SC_NS)); + } +} + + +void DirectionalCouplerBi::on_p0_in_changed() +{ + m_through_power_dB = 10*log10(m_dc_through_coupling_power) - m_dc_loss; + m_cross_power_dB = 10*log10(1.0 - m_dc_through_coupling_power) - m_dc_loss; + + m_memory_in0[0] = 0; // initializing for nan wavelength + + const double transmission_through = pow(10.0, m_through_power_dB / 20.0); + const double transmission_cross = pow(10.0, m_cross_power_dB / 20.0); + + // Pre-calculate S-parameters + OpticalSignal::field_type S02, S13, S03, S12; + S02 = polar(transmission_through, m_through_phase_rad); + S13 = polar(transmission_through, m_through_phase_rad); + S03 = polar(transmission_cross, m_cross_phase_rad); + S12 = polar(transmission_cross, m_cross_phase_rad); + + if (specsGlobalConfig.verbose_component_initialization) + { + cout << name() << ":" << endl; + cout << "through_power = " << norm(S02) << " W/W" << endl; + cout << "cross_power = " << norm(S03)<< " W/W" << endl; + cout << "through_field = " << abs(S02) << "" << endl; + cout << "cross_field = " << abs(S03)<< "" << endl; + cout << "insertion loss = " << m_dc_loss << "dB" << endl; + cout << (dynamic_cast<spx::oa_signal_type *>(p0_in.get_interface()))->name(); + + cout << " --,__,-> "; + cout << (dynamic_cast<spx::oa_signal_type *>(p2_out.get_interface()))->name(); + cout << endl; + cout << (dynamic_cast<spx::oa_signal_type *>(p1_in.get_interface()))->name(); + cout << " --' '-> "; + cout << (dynamic_cast<spx::oa_signal_type *>(p3_out.get_interface()))->name(); + cout << endl; + + cout << (dynamic_cast<spx::oa_signal_type *>(p0_out.get_interface()))->name(); + cout << " <-,__,-- "; + cout << (dynamic_cast<spx::oa_signal_type *>(p2_in.get_interface()))->name(); + cout << endl; + cout << (dynamic_cast<spx::oa_signal_type *>(p1_out.get_interface()))->name(); + cout << " <-' '-- "; + cout << (dynamic_cast<spx::oa_signal_type *>(p3_in.get_interface()))->name(); + cout << endl; + + cout << endl; + } + + OpticalSignal p0_in_read; + + while (true) { + // Wait for a new input signal + wait(); + + // Read current inputs + p0_in_read = p0_in->read(); + + auto cur_wavelength_id = p0_in_read.m_wavelength_id; + + // Updating the field memory + m_memory_in0[cur_wavelength_id] = p0_in_read.m_field; + + auto s2 = OpticalSignal(m_memory_in0[cur_wavelength_id] * S02 + + m_memory_in1[cur_wavelength_id] * S12 + , cur_wavelength_id); + + auto s3 = OpticalSignal(m_memory_in0[cur_wavelength_id] * S03 + + m_memory_in1[cur_wavelength_id] * S13 + , cur_wavelength_id); + + m_p2_out_writer.delayedWrite(s2, sc_time(m_delay_ns, SC_NS)); + m_p3_out_writer.delayedWrite(s3, sc_time(m_delay_ns, SC_NS)); + } +} + +void DirectionalCouplerBi::on_p1_in_changed() +{ + m_through_power_dB = 10*log10(m_dc_through_coupling_power) - m_dc_loss; + m_cross_power_dB = 10*log10(1.0 - m_dc_through_coupling_power) - m_dc_loss; + + m_memory_in1[0] = 0; // initializing for nan wavelength + + const double transmission_through = pow(10.0, m_through_power_dB / 20.0); + const double transmission_cross = pow(10.0, m_cross_power_dB / 20.0); + + // Pre-calculate S-parameters + OpticalSignal::field_type S02, S13, S03, S12; + S02 = polar(transmission_through, m_through_phase_rad); + S13 = polar(transmission_through, m_through_phase_rad); + S03 = polar(transmission_cross, m_cross_phase_rad); + S12 = polar(transmission_cross, m_cross_phase_rad); + + OpticalSignal p1_in_read; + + while (true) { + // Wait for a new input signal + wait(); + + // Read current inputs + p1_in_read = p1_in->read(); + + auto cur_wavelength_id = p1_in_read.m_wavelength_id; + + // Updating the field memory + m_memory_in1[cur_wavelength_id] = p1_in_read.m_field; + + auto s2 = OpticalSignal(m_memory_in0[cur_wavelength_id] * S02 + + m_memory_in1[cur_wavelength_id] * S12 + , cur_wavelength_id); + + auto s3 = OpticalSignal(m_memory_in0[cur_wavelength_id] * S03 + + m_memory_in1[cur_wavelength_id] * S13 + , cur_wavelength_id); + + m_p2_out_writer.delayedWrite(s2, sc_time(m_delay_ns, SC_NS)); + m_p3_out_writer.delayedWrite(s3, sc_time(m_delay_ns, SC_NS)); + } +} + +void DirectionalCouplerBi::on_p2_in_changed() +{ + m_through_power_dB = 10*log10(m_dc_through_coupling_power) - m_dc_loss; + m_cross_power_dB = 10*log10(1.0 - m_dc_through_coupling_power) - m_dc_loss; + + m_memory_in2[0] = 0; // initializing for nan wavelength + + const double transmission_through = pow(10.0, m_through_power_dB / 20.0); + const double transmission_cross = pow(10.0, m_cross_power_dB / 20.0); + + // Pre-calculate S-parameters + OpticalSignal::field_type S02, S13, S03, S12; + S02 = polar(transmission_through, m_through_phase_rad); + S13 = polar(transmission_through, m_through_phase_rad); + S03 = polar(transmission_cross, m_cross_phase_rad); + S12 = polar(transmission_cross, m_cross_phase_rad); + + OpticalSignal p2_in_read; + + while (true) { + // Wait for a new input signal + wait(); + + // Read current inputs + p2_in_read = p2_in->read(); + + auto cur_wavelength_id = p2_in_read.m_wavelength_id; + + // Updating the field memory + m_memory_in2[cur_wavelength_id] = p2_in_read.m_field; + + auto s0 = OpticalSignal(m_memory_in2[cur_wavelength_id] * S02 + + m_memory_in3[cur_wavelength_id] * S03 + , cur_wavelength_id); + + auto s1 = OpticalSignal(m_memory_in2[cur_wavelength_id] * S12 + + m_memory_in3[cur_wavelength_id] * S13 + , cur_wavelength_id); + + m_p0_out_writer.delayedWrite(s0, sc_time(m_delay_ns, SC_NS)); + m_p1_out_writer.delayedWrite(s1, sc_time(m_delay_ns, SC_NS)); + } +} + +void DirectionalCouplerBi::on_p3_in_changed() +{ + m_through_power_dB = 10*log10(m_dc_through_coupling_power) - m_dc_loss; + m_cross_power_dB = 10*log10(1.0 - m_dc_through_coupling_power) - m_dc_loss; + + m_memory_in3[0] = 0; // initializing for nan wavelength + + const double transmission_through = pow(10.0, m_through_power_dB / 20.0); + const double transmission_cross = pow(10.0, m_cross_power_dB / 20.0); + + // Pre-calculate S-parameters + OpticalSignal::field_type S02, S13, S03, S12; + S02 = polar(transmission_through, m_through_phase_rad); + S13 = polar(transmission_through, m_through_phase_rad); + S03 = polar(transmission_cross, m_cross_phase_rad); + S12 = polar(transmission_cross, m_cross_phase_rad); + + OpticalSignal p3_in_read; + + while (true) { + // Wait for a new input signal + wait(); + + // Read current inputs + p3_in_read = p3_in->read(); + + auto cur_wavelength_id = p3_in_read.m_wavelength_id; + + // Updating the field memory + m_memory_in3[cur_wavelength_id] = p3_in_read.m_field; + + auto s0 = OpticalSignal(m_memory_in2[cur_wavelength_id] * S02 + + m_memory_in3[cur_wavelength_id] * S03 + , cur_wavelength_id); + + auto s1 = OpticalSignal(m_memory_in2[cur_wavelength_id] * S12 + + m_memory_in3[cur_wavelength_id] * S13 + , cur_wavelength_id); + + m_p0_out_writer.delayedWrite(s0, sc_time(m_delay_ns, SC_NS)); + m_p1_out_writer.delayedWrite(s1, sc_time(m_delay_ns, SC_NS)); + } +}
\ No newline at end of file |
