File indexing completed on 2024-09-08 08:10:28
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 "oscilloscopedata.h" 0012 #include "oscilloscope.h" 0013 0014 using namespace std; 0015 0016 // BEGIN class ProbeData 0017 ProbeData::ProbeData(int id) 0018 : m_id(id) 0019 , m_drawPosition(0.5) 0020 , m_resetTime(Simulator::self()->time()) 0021 , m_color(Qt::black) 0022 { 0023 } 0024 0025 ProbeData::~ProbeData() 0026 { 0027 unregisterProbe(m_id); 0028 } 0029 0030 void ProbeData::setColor(QColor color) 0031 { 0032 m_color = color; 0033 emit displayAttributeChanged(); 0034 } 0035 // END class ProbeData 0036 0037 // BEGIN class LogicProbeData 0038 LogicProbeData::LogicProbeData(int id) 0039 : ProbeData(id) 0040 { 0041 m_data = new vector<LogicDataPoint>; 0042 } 0043 0044 void LogicProbeData::addDataPoint(LogicDataPoint data) 0045 { 0046 if (m_data->size() < MAX_PROBE_DATA_SIZE) { 0047 m_data->push_back(data); 0048 } 0049 } 0050 0051 void LogicProbeData::eraseData() 0052 { 0053 bool lastValue = false; 0054 bool hasLastValue = false; 0055 0056 if (!m_data->empty()) { 0057 lastValue = m_data->back().value; 0058 hasLastValue = true; 0059 } 0060 0061 delete m_data; 0062 m_data = new vector<LogicDataPoint>; 0063 0064 m_resetTime = Simulator::self()->time(); 0065 0066 if (hasLastValue) 0067 addDataPoint(LogicDataPoint(lastValue, m_resetTime)); 0068 } 0069 0070 uint64_t LogicProbeData::findPos(uint64_t time) const 0071 { 0072 unsigned int pos = m_data->size(); 0073 if (!time || !pos) 0074 return 0; 0075 0076 // binary search 0077 0078 // TODO: test and debug this code. 0079 unsigned int top = pos; 0080 pos >>= 1; 0081 unsigned int bottom = 0; 0082 0083 do { 0084 uint64_t datatime = (*m_data)[pos].time; 0085 if (datatime == time) 0086 return pos; 0087 0088 if (datatime >= time) { 0089 top = pos; 0090 pos -= (top - bottom) >> 1; 0091 } else { 0092 bottom = pos; 0093 pos += (top - bottom) >> 1; 0094 } 0095 // try to avoid infinite loop when top-bottom==1 0096 if (top - bottom == 1) { 0097 if (datatime >= time) 0098 bottom = top; 0099 else 0100 top = bottom; 0101 } 0102 0103 } while (top != bottom && pos != bottom); 0104 0105 return pos; 0106 } 0107 // END class LogicProbeData 0108 0109 // BEGIN class FloatingProbeData 0110 FloatingProbeData::FloatingProbeData(int id) 0111 : ProbeData(id) 0112 { 0113 m_data = new vector<float>; 0114 m_scaling = Linear; 0115 m_upperAbsValue = 10.0; 0116 m_lowerAbsValue = 0.1; 0117 } 0118 0119 void FloatingProbeData::addDataPoint(float data) 0120 { 0121 if (m_data->size() < MAX_PROBE_DATA_SIZE) { 0122 m_data->push_back(data); 0123 } 0124 } 0125 0126 void FloatingProbeData::eraseData() 0127 { 0128 delete m_data; 0129 m_data = new vector<float>; 0130 0131 m_resetTime = Simulator::self()->time(); 0132 } 0133 0134 uint64_t FloatingProbeData::findPos(uint64_t time) const 0135 { 0136 if (time <= 0 || uint64_t(time) <= m_resetTime) 0137 return 0; 0138 0139 uint64_t at = uint64_t((time - m_resetTime) * double(LINEAR_UPDATE_RATE) / double(LOGIC_UPDATE_RATE)); 0140 0141 if (m_data->size() <= at) { // index is out of bound 0142 if (at > 0) { 0143 --at; 0144 } 0145 } 0146 0147 return at; 0148 } 0149 0150 uint64_t FloatingProbeData::toTime(uint64_t at) const 0151 { 0152 return uint64_t(m_resetTime + (at * LOGIC_UPDATE_RATE * LINEAR_UPDATE_PERIOD)); 0153 } 0154 0155 void FloatingProbeData::setScaling(Scaling scaling) 0156 { 0157 if (m_scaling == scaling) 0158 return; 0159 0160 m_scaling = scaling; 0161 emit displayAttributeChanged(); 0162 } 0163 0164 void FloatingProbeData::setUpperAbsValue(double upperAbsValue) 0165 { 0166 if (m_upperAbsValue == upperAbsValue) 0167 return; 0168 0169 m_upperAbsValue = upperAbsValue; 0170 emit displayAttributeChanged(); 0171 } 0172 0173 void FloatingProbeData::setLowerAbsValue(double lowerAbsValue) 0174 { 0175 if (m_lowerAbsValue == lowerAbsValue) 0176 return; 0177 0178 m_lowerAbsValue = lowerAbsValue; 0179 emit displayAttributeChanged(); 0180 } 0181 // END class FloatingProbeData 0182 0183 #include "moc_oscilloscopedata.cpp"