#include "WaferData.h" WaferData::WaferData(void) { _SetWaferSerialNumber = 0; _ChipNumber = 0; setSourceFileName(__FILE__); } WaferData::~WaferData(void) { } void WaferData::openFileGroup(std::string pOneFileName) { info("openFileGroup"); clearAllData(); _WaferInfo.clear(); _ChipNumber = 0; std::string tFileGroupName, tWaferName; unsigned int tChipNumber = 0; //numbers of chips for this wafer size_t tSearch = pOneFileName.find(".cfg."); //if a config file is selected instead of result file if (tSearch != pOneFileName.npos) tFileGroupName = pOneFileName.replace(tSearch, 4, ""); tFileGroupName = pOneFileName.substr(0, pOneFileName.find_last_of("_")); tWaferName = tFileGroupName.substr(tFileGroupName.find_last_of("/")+1, tFileGroupName.size()); tWaferName.replace(0,6,""); //get rid of the wafer_ in the wafer name unsigned int tIndex = 0; for (unsigned int i = 1; i < __MAXNRCHIPS+1; ++i){ //numbering in STControl from 1 to 60 std::stringstream tFileName; tFileName << tFileGroupName <<"_"<::iterator iit=_resultNames.begin(); iit != _resultNames.end(); ++iit){ //loop over chip results double tAvrValue = 0; //the average of the actual chip result (e.g. noise) double tStdDevAvrValue = 0; //the standard deviation of the average of the actual chip result (e.g. noise) unsigned int tNchips = 0; //number of chips that have this test result for (std::map > >::iterator it=_data.begin(); it != _data.end(); ++it){ //loop over chips for average std::map >::iterator ti = it->second.find(*iit); //tries to find the chip result for the actual chip if (ti != it->second.end()){ //if result is available for actual chip tNchips++; if (isFinite(ti->second.first)) //check for valid number tAvrValue+=ti->second.first; switch(ti->second.second){ case GREY: _resultsStatistics[*iit][GREY]++; break; case BLUE: _resultsStatistics[*iit][BLUE]++; break; case RED: _resultsStatistics[*iit][RED]++; break; case YELLOW: _resultsStatistics[*iit][YELLOW]++; break; case GREEN: _resultsStatistics[*iit][GREEN]++; break; case SETRED: _resultsStatistics[*iit][RED]++; break; case SETYELLOW: _resultsStatistics[*iit][YELLOW]++; break; case SETGREEN: _resultsStatistics[*iit][GREEN]++; break; default: error("AverageResults: Unknown chip status", __LINE__); } } else _resultsStatistics[*iit][GREY]++; //a missing result marks the scan grey } if (tNchips == 0){ //abort condition: no chip has a result with result name _averageValues[*iit] = std::make_pair(0.,0.); continue; } tAvrValue/=tNchips; //normalization tNchips = 0; //reset to zero for std. dev. calculation for (std::map > >::iterator it=_data.begin(); it != _data.end(); ++it){ //loop over chips for average standard deviation std::map >::iterator ti = it->second.find(*iit); //tries to find the chip result for the actual chip if (ti != it->second.end()){ //if result is available for actual chip tNchips++; if (isFinite(ti->second.first)) //check for valid number tStdDevAvrValue+=pow(ti->second.first-tAvrValue,2); //variance calculation } } _averageValues[*iit] = std::make_pair(tAvrValue,sqrt(tStdDevAvrValue/(double) tNchips)); //adding result }; } unsigned int WaferData::getNchips(int pWaferIndex) { if(pWaferIndex < 0) //of no wafer is specified the number of all open chips is returned return _data.size(); unsigned int tNChips = 0; try{ tNChips = _WaferInfo[pWaferIndex].second.second.second; } catch(std::out_of_range){ std::stringstream tError; tError<<"getNchips: wafer index "<= _data.size()){ std::stringstream tError; tError<<"getChipNumber: The index "< > >::iterator it = _data.begin(); it != _data.end(); ++it){ if (it->second["ChipNr"].first == (double) pChipNumber && it->second["WaferSN"].first == (double) getWaferIndex(pWaferIndex)) return tIndex; tIndex++; } std::stringstream tError; tError<<"getChipIndex: Chip number "< 1){ std::stringstream tWaferName; tWaferName<= 0){ if (pWaferIndex >= (int) _WaferInfo.size()){ std::stringstream tError; tError<<"setWaferSerialNumber: The index "<= _data.size()){ std::stringstream tError; tError<<"getWaferSerialNumber: The index "< >::iterator it = _resultsStatistics.find(pResultName); if (it != _resultsStatistics.end()){ std::map::iterator iit = it->second.find(pStatus); if (iit != it->second.end()) return iit->second; } else{ std::stringstream tWarning; tWarning<<"getResultStatistic: Result '"< getNchips()-1){ std::stringstream tError; tError<<"get Result("< >::iterator it = _data[pIndex].find(pName); if (it != _data[pIndex].end()){ rValue = it->second.first; return true; } std::stringstream tInfo; tInfo<<"get Result: result "< getNchips()-1){ std::stringstream tError; tError<<"getResultStatus(): Index "< >::iterator it = _data[pIndex].find(pName); if (it != _data[pIndex].end()){ rStatus = it->second.second; return true; } std::stringstream tWarning; tWarning<<"getResultStatus(): status for "< getNchips()-1){ std::stringstream tError; tError<<"getChipStatus(): Index "< >::iterator it = _data[pIndex].find("status"); if (it != _data[pIndex].end()){ rStatus = it->second.second; return true; } rStatus = GREY; return false; } void WaferData::addResult(unsigned int pChipIndex, std::string const& pResultName, double const& pValue) { std::stringstream tDebug; tDebug<<"addResult: chip index="< >::iterator it = _FailColumns.find(pChipIndex); if (it != _FailColumns.end()){ std::map::iterator iit = it->second.find(pColumn); if (iit != it->second.end()){ _FailColumns[pChipIndex][pColumn]++; return; } } _FailColumns[pChipIndex][pColumn] = 1; } void WaferData::getFailPixels(unsigned int pChipIndex, std::map >& rFailPixels) { rFailPixels = _FailPixel[pChipIndex]; } void WaferData::getFailColumns(unsigned int pChipIndex, std::map& rFailColumns) { rFailColumns = _FailColumns[pChipIndex]; } void WaferData::setResultStatus(unsigned int pChipIndex, std::string const& pResultName, status const& pStatus) { std::stringstream tDebug; tDebug<<"setResultStatus: chip index="< > >::iterator it = _data.find(pChipIndex); if (it != _data.end()){ for(std::map >::iterator iit = it->second.begin(); iit != it->second.end(); ++iit){ if(iit->first.compare(pResultName) == 0){ _data[pChipIndex][pResultName].second = pStatus; return; } } } _data[pChipIndex][pResultName] = std::make_pair(std::numeric_limits::quiet_NaN(), pStatus); //if result does not exist: set the value to NaN std::stringstream tWarning; tWarning<<"setResultStatus(): result "<::iterator it = _resultNames.begin(); it != _resultNames.end(); ++it){ if (it->compare("status") != 0){ //the status is also part of the data object, but is not wanted here double tValue = 0; if (getResult(pChipIndex, *it, tValue)){//TODO: the following is pretty ugly, hard to read and error prone status tStatus = GREY; if (getResultStatus(pChipIndex,*it, tStatus)){ if(tStatus == SETRED){ tChipStatus = SETRED; } if(tStatus == RED && tChipStatus != SETRED){ if(tChipStatus == BLUE) tChipStatus = SETRED; else tChipStatus = RED; } if(tStatus == SETYELLOW && tChipStatus != RED && tChipStatus != SETRED){ tChipStatus = SETYELLOW; } if(tStatus == YELLOW && tChipStatus != SETYELLOW && tChipStatus != RED && tChipStatus != SETRED){ if(tChipStatus == BLUE) tChipStatus = SETYELLOW; else tChipStatus = YELLOW; } if(tStatus == BLUE && tChipStatus == RED){ //make chip status changeable of a blue result occurs tChipStatus = SETRED; } if(tStatus == BLUE && tChipStatus == YELLOW){ //make chip status changeable of a blue result occurs tChipStatus = SETYELLOW; } if(tStatus == BLUE && tChipStatus != YELLOW&& tChipStatus != SETYELLOW && tChipStatus != RED && tChipStatus != SETRED){ tChipStatus = BLUE; } if(tStatus == SETGREEN && tChipStatus != YELLOW && tChipStatus != RED && tChipStatus != SETYELLOW && tChipStatus != SETRED && tChipStatus != BLUE) tChipStatus = SETGREEN; if(tStatus == GREEN && tChipStatus != SETGREEN && tChipStatus != YELLOW && tChipStatus != SETYELLOW && tChipStatus != RED && tChipStatus != SETRED && tChipStatus != BLUE) tChipStatus = GREEN; if(tStatus!=GREEN && tStatus!=SETGREEN) tFailedResults++; } else{ error(std::string("calculateChipStatus: result without cut: ").append(*it),__LINE__); tChipStatus = BLUE; //should not be possible and never occur, just to be safe } } else{//result not there, chip scan aborted? double tValue = 0; getResult(pChipIndex,"RunAborted", tValue); //check if run aborted than the chip is set to red if(tValue==1){ tChipStatus = SETRED; tFailedResults++; } } } } addResult(pChipIndex, "status", (double) tFailedResults); setChipStatus(pChipIndex, tChipStatus); } void WaferData::calculateChipStatuses() { debug("calculateChipStatuses"); for (unsigned int i = 0; i < getNchips(); ++i) calculateChipStatus(i); } void WaferData::addCutNameToResultName(std::string pResultName, std::string pCutName) { debug(std::string("addCutNameToResultName: ").append(pResultName)); _CutNames[pResultName] = pCutName; } std::string WaferData::getCutName(std::string pResultName) { debug(std::string("getCutName: ").append(pResultName)); std::map::iterator it = _CutNames.find(pResultName); if(it != _CutNames.end()) return it->second; return ""; } void WaferData::getResultNames(std::list& pResultNames) { debug("getResultNames"); pResultNames = _resultNames; } void WaferData::getAverageValues(std::map >& pAverageValues) { debug("getAverageValues"); pAverageValues = _averageValues; } void WaferData::getResults(std::map > >& pResults) { debug("getResults"); pResults = _data; } void WaferData::clearAllData() { clearWaferInfo(); clearResultNames(); clearData(); clearResultStatistic(); clearFailData(); _ChipNumber = 0; } void WaferData::clearWaferInfo() { debug("clearWaferInfo"); _WaferInfo.clear(); } void WaferData::clearResultNames() { debug("clearResultNames"); _resultNames.clear(); } void WaferData::clearData() { debug("clearData"); _data.clear(); } void WaferData::clearResultStatistic() { _resultsStatistics.clear(); _averageValues.clear(); } void WaferData::clearFailData(int pChipIndex) { debug("clearFailData"); if (pChipIndex == -1){ _FailPixel.clear(); _FailColumns.clear(); } else{ _FailPixel[pChipIndex].clear(); _FailColumns[pChipIndex].clear(); } }