File indexing completed on 2024-05-19 09:39:08
0001 /*************************************************************************** 0002 * Copyright (C) 2005 by David Saxton * 0003 * david@bluehaze.org * 0004 * * 0005 * This program is free software; you can redistribute it and/or modify * 0006 * it under the terms of the GNU General Public License as published by * 0007 * the Free Software Foundation; either version 2 of the License, or * 0008 * (at your option) any later version. * 0009 ***************************************************************************/ 0010 0011 #include "config.h" 0012 #ifndef NO_GPSIM 0013 0014 #include "micropackage.h" 0015 #include "piccomponent.h" 0016 #include "piccomponentpin.h" 0017 0018 #include <ktechlab_debug.h> 0019 0020 void PICComponentPin_logicCallback(void *objV, bool state) { 0021 PICComponentPin *objT = static_cast<PICComponentPin*>(objV); 0022 objT->logicCallback(state); 0023 } 0024 0025 PICComponentPin::PICComponentPin(PICComponent *picComponent, PicPin picPin) 0026 : m_id(picPin.pinID) 0027 { 0028 m_gOutHigh = 0.0; 0029 m_gOutLow = 0.0; 0030 m_picPin = picPin; 0031 m_pPICComponent = picComponent; 0032 m_pLogicOut = nullptr; 0033 m_pLogicIn = nullptr; 0034 m_pIOPIN = nullptr; 0035 m_pStimulusNode = nullptr; 0036 Zth = 0.0; 0037 Vth = 0.0; 0038 0039 switch (picPin.type) { 0040 case PicPin::type_input: { 0041 m_pLogicIn = picComponent->createLogicIn(picComponent->ecNodeWithID(picPin.pinID)); 0042 break; 0043 } 0044 case PicPin::type_bidir: { 0045 m_pLogicOut = picComponent->createLogicOut(picComponent->ecNodeWithID(picPin.pinID), false); 0046 m_gOutHigh = 0.004; 0047 m_gOutLow = 0.004; 0048 break; 0049 } 0050 case PicPin::type_open: { 0051 m_pLogicOut = picComponent->createLogicOut(picComponent->ecNodeWithID(picPin.pinID), false); 0052 m_pLogicOut->setOutputHighVoltage(0.0); 0053 m_pLogicOut->setOutputHighConductance(0.0); 0054 m_gOutHigh = 0.0; 0055 m_gOutLow = 0.004; 0056 break; 0057 } 0058 case PicPin::type_vss: 0059 case PicPin::type_vdd: 0060 case PicPin::type_mclr: 0061 case PicPin::type_osc: 0062 default: 0063 break; 0064 } 0065 0066 if (m_pLogicIn) { 0067 //m_pLogicIn->setCallback(this, (CallbackPtr)(&PICComponentPin::logicCallback)); 0068 m_pLogicIn->setCallback2(PICComponentPin_logicCallback, this); 0069 } 0070 if (m_pLogicOut) { 0071 //m_pLogicOut->setCallback(this, (CallbackPtr)(&PICComponentPin::logicCallback)); 0072 m_pLogicOut->setCallback2(PICComponentPin_logicCallback, this); 0073 } 0074 } 0075 0076 PICComponentPin::~PICComponentPin() 0077 { 0078 if (m_pLogicIn) { 0079 //m_pLogicIn->setCallback(nullptr, (CallbackPtr) nullptr); 0080 m_pLogicIn->setCallback2(nullptr, nullptr); 0081 } 0082 if (m_pLogicOut) { 0083 //m_pLogicOut->setCallback(nullptr, (CallbackPtr) nullptr); 0084 m_pLogicOut->setCallback2(nullptr, nullptr); 0085 } 0086 0087 delete m_pStimulusNode; 0088 } 0089 0090 void PICComponentPin::attach(IOPIN *iopin) 0091 { 0092 if (!iopin) { 0093 qCWarning(KTL_LOG) << " iopin is nullptr"; 0094 return; 0095 } 0096 0097 if (m_pStimulusNode) { 0098 qCWarning(KTL_LOG) << " Already have a node stimulus"; 0099 return; 0100 } 0101 0102 if (m_pIOPIN) { 0103 qCWarning(KTL_LOG) << " Already have an iopin"; 0104 return; 0105 } 0106 0107 m_pIOPIN = iopin; 0108 m_pStimulusNode = new Stimulus_Node(m_id.toLatin1()); 0109 m_pStimulusNode->attach_stimulus(iopin); 0110 m_pStimulusNode->attach_stimulus(this); 0111 0112 // We need to tell the iopin whether or not we are high 0113 if (m_pLogicOut) 0114 logicCallback(m_pLogicOut->isHigh()); 0115 else if (m_pLogicIn) 0116 logicCallback(m_pLogicIn->isHigh()); 0117 } 0118 0119 double PICComponentPin::get_Vth() 0120 { 0121 if (!m_pIOPIN) 0122 return 0.0; 0123 0124 if (m_pIOPIN->get_direction() == IOPIN::DIR_INPUT) 0125 return Vth; 0126 else 0127 return m_pIOPIN->get_Vth(); 0128 } 0129 0130 void PICComponentPin::set_nodeVoltage(double v) 0131 { 0132 Q_UNUSED(v); 0133 0134 if (!m_pLogicOut || !m_pIOPIN) 0135 return; 0136 0137 if (m_pIOPIN->get_direction() == IOPIN::DIR_INPUT) { 0138 m_pLogicOut->setOutputHighConductance(0.0); 0139 m_pLogicOut->setOutputLowConductance(0.0); 0140 } else { 0141 m_pLogicOut->setHigh(m_pIOPIN->getDrivingState()); 0142 m_pLogicOut->setOutputHighConductance(m_gOutHigh); 0143 m_pLogicOut->setOutputLowConductance(m_gOutLow); 0144 } 0145 } 0146 0147 void PICComponentPin::logicCallback(bool state) 0148 { 0149 if (!m_pIOPIN) 0150 return; 0151 0152 Vth = state ? 5e10 : 0; 0153 bDrivingState = state; 0154 0155 if (m_pIOPIN->get_direction() == IOPIN::DIR_INPUT) { 0156 Zth = 1e5; 0157 0158 m_pIOPIN->setDrivenState(state); 0159 if (m_pStimulusNode) 0160 m_pStimulusNode->update(); 0161 } else 0162 Zth = 0; 0163 } 0164 0165 void PICComponentPin::resetOutput() 0166 { 0167 if (m_pLogicOut) 0168 m_pLogicOut->setHigh(false); 0169 } 0170 0171 #endif