Ejemplo n.º 1
0
// >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
void Picker::process(const Record *record, const DoubleArray &) {
	// Sampling frequency has not been set yet
	if ( _stream.fsamp == 0.0 ) {
		terminate();
		return;
	}

	// Error occured while feeding a record or already finished?
	if ( isFinished() ) return;

	// Process unless the available time window does not include the
	// requested time window
	if ( !dataTimeWindow().contains(timeWindow())) return;

	// data window relative to continuous()->startTime()
	double relTriggerTime = _trigger - dataTimeWindow().startTime();

	double dt1 = relTriggerTime + _config.signalBegin;
	double dt2 = relTriggerTime + _config.signalEnd;
	double snr = -1;

	// Calculate data array indicies of requested time window
	int i1 = int(dt1*_stream.fsamp);
	int i2 = int(dt2*_stream.fsamp);

	// Calculate the initial trigger time
	int triggerIdx = relTriggerTime*_stream.fsamp;
	int lowerUncertainty = -1;
	int upperUncertainty = -1;
	OPT(Polarity) polarity;

	if ( !calculatePick(continuousData().size(), continuousData().typedData(),
	                    i1, i2, triggerIdx, lowerUncertainty, upperUncertainty,
	                    snr, polarity) ) {
		setStatus(Error, 0.0);
		return;
	}

	Core::Time pickTime = dataTimeWindow().startTime() + Core::TimeSpan(triggerIdx/_stream.fsamp);

	// Debug: print the time difference between the pick and the initial trigger
	SEISCOMP_DEBUG("Picker::process repick result: dt=%.3f  snr=%.2f",
	               (double)(pickTime - _trigger), snr);

	if ( snr >= _config.snrMin ) {
		setStatus(Finished, 100.);
		Result res;
		res.record = record;
		res.snr = snr;
		res.time = pickTime;
		res.timeLowerUncertainty = (double)lowerUncertainty / _stream.fsamp;
		res.timeUpperUncertainty = (double)upperUncertainty / _stream.fsamp;
		res.timeWindowBegin = (double)(timeWindow().startTime() - pickTime);
		res.timeWindowEnd = (double)(timeWindow().endTime() - pickTime);
		res.polarity = polarity;
		emitPick(res);
	}
	else
		setStatus(LowSNR, snr);
}
Ejemplo n.º 2
0
// >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
bool AmplitudeProcessor::handleGap(Filter *filter, const Core::TimeSpan& span,
                                   double lastSample, double nextSample,
                                   size_t missingSamples) {
	if ( _stream.dataTimeWindow.endTime()+span < timeWindow().startTime() ) {
		// Save trigger, because reset will unset it
		Core::Time t = _trigger;
		reset();
		_trigger = t;
		return true;
	}

	//TODO: Handle gaps
	setStatus(QCError, 1);
	return false;
}
Ejemplo n.º 3
0
// >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
void AmplitudeProcessor::process(const Record *record) {
	// Sampling frequency has not been set yet
	if ( _stream.fsamp == 0.0 )
		return;

	int n = (int)_data.size();

	// signal and noise window relative to _continuous->startTime()
	double dt0  = _trigger - dataTimeWindow().startTime();
	double dt1  = dataTimeWindow().endTime() - dataTimeWindow().startTime();
	double dtw1  = timeWindow().endTime() - dataTimeWindow().startTime();
	double dtn1 = dt0 + _config.noiseBegin;
	double dtn2 = dt0 + _config.noiseEnd;
	double dts1 = dt0 + _config.signalBegin;
	double dts2 = dt0 + _config.signalEnd;

	// Noise indicies
	int ni1 = int(dtn1*_stream.fsamp+0.5);
	int ni2 = int(dtn2*_stream.fsamp+0.5);

	if ( ni1 < 0 || ni2 < 0 ) {
		SEISCOMP_DEBUG("Noise data not available -> abort");
		setStatus(Error, 1);
		return;
	}

	if ( n < ni2 ) {
		// the noise window is not complete
		return;
	}


	// **** compute signal amplitude ********************************

	// these are the offsets of the beginning and end
	// of the signal window relative to the start of
	// the continuous record in samples
	int i1 = int(dts1*_stream.fsamp+0.5);
	int i2 = int(dts2*_stream.fsamp+0.5);

	//int progress = int(100.*(n-i1)/(i2-i1));
	//int progress = int(100.*(dt1-dts1)/(dts2-dts1));
	int progress = int(100.*(dt1-dts1)/(std::max(dtw1,dts2)-dts1));

	if ( progress > 100 ) progress = 100;
	setStatus(InProgress, progress);

	if ( i1 < 0 ) i1 = 0;
	if ( i2 > n ) i2 = n;

	bool unlockCalculation = ((_enableUpdates && !_enableResponses) && progress > 0) || progress >= 100;

	if ( unlockCalculation ) {
		if ( _streamConfig[_usedComponent].gain == 0.0 ) {
			setStatus(MissingGain, 0);
			return;
		}

		// **** prepare the data to compute the noise
		prepareData(_data);
		if ( isFinished() )
			return;

		// **** compute noise amplitude *********************************
		// if the noise hasn't been measured yet...
		if ( !_noiseAmplitude ) {
			// compute pre-arrival data offset and noise amplitude

			double off = 0., amp = 0.;

			if ( !computeNoise(_data, ni1, ni2, &off, &amp) ) {
				SEISCOMP_DEBUG("Noise computation failed -> abort");
				setStatus(Error, 2);
				return;
			}

			_noiseOffset = off;
			_noiseAmplitude = amp;
		}

		AmplitudeIndex index;
		Result res;
		res.component = _usedComponent;
		res.record = record;
		res.period = -1;
		res.snr = -1;

		res.amplitude.value = -1;
		res.amplitude.lowerUncertainty = Core::None;
		res.amplitude.upperUncertainty = Core::None;

		index.index = -1;
		index.begin = 0;
		index.end = 0;

		double dtsw1, dtsw2;

		if ( _searchBegin ) {
			dtsw1 = dt0 + *_searchBegin;
			if ( dtsw1 < dts1 ) dtsw1 = dts1;
			if ( dtsw1 > dts2 ) dtsw1 = dts2;
		}
		else
			dtsw1 = dts1;

		if ( _searchEnd ) {
			dtsw2 = dt0 + *_searchEnd;
			if ( dtsw2 < dts1 ) dtsw2 = dts1;
			if ( dtsw2 > dts2 ) dtsw2 = dts2;
		}
		else
			dtsw2 = dts2;

		int si1 = int(dtsw1*_stream.fsamp+0.5);
		int si2 = int(dtsw2*_stream.fsamp+0.5);

		si1 = std::max(si1, i1);
		si2 = std::min(si2, i2);

		if ( !computeAmplitude(_data, i1, i2, si1, si2, *_noiseOffset,
		                       &index, &res.amplitude, &res.period, &res.snr) ) {
			if ( progress >= 100 ) {
				if ( status() == LowSNR )
					SEISCOMP_DEBUG("Amplitude %s computation for stream %s failed because of low SNR (%.2f < %.2f)",
					              _type.c_str(), record->streamID().c_str(), res.snr, _config.snrMin);
				else {
					SEISCOMP_DEBUG("Amplitude %s computation for stream %s failed -> abort",
					              _type.c_str(), record->streamID().c_str());
					setStatus(Error, 3);
				}

				_lastAmplitude = Core::None;
			}

			return;
		}

		if ( _lastAmplitude ) {
			if ( res.amplitude.value <= *_lastAmplitude ) {
				if ( progress >= 100 ) {
					setStatus(Finished, 100.);
					_lastAmplitude = Core::None;
				}

				return;
			}
		}

		_lastAmplitude = res.amplitude.value;

		double dt = index.index / _stream.fsamp;
		res.period /= _stream.fsamp;

		if ( index.begin > index.end ) std::swap(index.begin, index.end);

		// Update status information
		res.time.reference = dataTimeWindow().startTime() + Core::TimeSpan(dt);
		//res.time.begin = index.begin / _stream.fsamp;
		//res.time.end = index.end / _stream.fsamp;
		res.time.begin = (si1 - index.index) / _stream.fsamp;
		res.time.end = (si2 - index.index) / _stream.fsamp;

		if ( progress >= 100 ) {
			setStatus(Finished, 100.);
			_lastAmplitude = Core::None;
		}

		emitAmplitude(res);
	}
}