Exemple #1
0
// Read
template<> bool OpcXml::Read(const COpcString& cString, Decimal& cValue)
{
    bool bResult = true;

    TRY
    {
        COpcText cText;
        COpcTextReader cReader(cString);

        // parse whole integer portion.
        cText.SetType(COpcText::Delimited);
        cText.SetDelims(L".");
        cText.SetEofDelim();

        if (!cReader.GetNext(cText))
        {
            THROW_(bResult, false);
        }

        // convert to signed integer.
        Long nValue = 0;

        if (!ToSigned(cText, nValue, MAX_DECIMAL, MIN_DECIMAL))
        {
            THROW_(bResult, false);
        }

        cValue.int64 = nValue*10000;
        
        if (cText.GetDelimChar() == L'.')
        {
            // parse decimal portion.
            cText.SetType(COpcText::Delimited);
            cText.SetEofDelim();

            if (!cReader.GetNext(cText))
            {
                THROW_(bResult, false);
            }

            // convert to unsigned integer.
            ULong uValue = 0;

            if (!ToUnsigned(cText, uValue, MAX_DEC_FRACTION, 0, 10))
            {
                THROW_(bResult, false);
            }

            cValue.int64 += (Long)uValue;
        }
    }
    CATCH
    {
        cValue.int64 = 0;
    }

    return bResult;
}
Exemple #2
0
// Read
template<> bool OpcXml::Read(const COpcString& cString, DateTime& cValue)
{
    bool bResult = true;

    FILETIME cFileTime;

	// check for invalid date.
	if (cString.IsEmpty())
	{
		cValue = OpcMinDate();
		return true;
	}

    TRY
    {
        SYSTEMTIME cSystemTime; ZeroMemory(&cSystemTime, sizeof(cSystemTime));

        COpcText cText;
        COpcTextReader cReader(cString);

        // parse date fields.
        cText.SetType(COpcText::Delimited);
        cText.SetDelims(L"T");

        if (!cReader.GetNext(cText)) THROW_(bResult, false);

        if (!ToDate(cText, cSystemTime.wYear, cSystemTime.wMonth, cSystemTime.wDay))
        {
            THROW_(bResult, false);
        }

        // parse time fields.
        cText.SetType(COpcText::Delimited);
        cText.SetDelims(L"Z-+");
        cText.SetEofDelim();

        if (!cReader.GetNext(cText)) THROW_(bResult, false);

        bResult = ToTime(
            cText, 
            cSystemTime.wHour, 
            cSystemTime.wMinute, 
            cSystemTime.wSecond, 
            cSystemTime.wMilliseconds);

        if (!bResult)
        {
            THROW_(bResult, false);
        }

		// convert to a UTC file time.
		if (!SystemTimeToFileTime(&cSystemTime, &cFileTime))
		{
			THROW_(bResult, false);
		}

		if (cText.GetDelimChar() != _T('Z'))
		{
			// convert local system time to UTC file time.
			if (cText.GetEof())
			{
				FILETIME ftUtcTime;

				if (!OpcLocalTimeToUtcTime(cFileTime, ftUtcTime))
				{
					THROW_(bResult, false);
				}
				
				cFileTime = ftUtcTime;
			}

			// apply offset specified in the datetime string.
			else
			{
				bool bNegative = (cText.GetDelimChar() == _T('-'));

				// parse time fields.
				cText.SetType(COpcText::Delimited);
				cText.SetEofDelim();

				if (!cReader.GetNext(cText)) THROW_(bResult, false);

				SHORT sMinutes = 0;

				bResult = ToOffset(
					cText, 
					bNegative,
					sMinutes);

				if (!bResult)
				{
					THROW_(bResult, false);
				}

				// apply timezone offset.
				LONGLONG llTime = OpcToInt64(cFileTime);

				llTime -= ((LONGLONG)sMinutes)*60*10000000;

				cFileTime = OpcToFILETIME(llTime);	
			}
		}
			
	    cValue = cFileTime;
    }
    CATCH
    {
        ZeroMemory(&cFileTime, sizeof(cFileTime));
        cValue = cFileTime;
    }

    return bResult;
}
Exemple #3
0
// ToTime
static bool ToTime(
    const COpcString& cString, 
    WORD&             wHour,
    WORD&             wMinute,
    WORD&             wSeconds,
    WORD&             wFraction
)
{
    bool bResult = true;

    TRY
    {
        COpcText cText;
        COpcTextReader cReader(cString);

        ULong uValue = 0;

        // parse hour field.
        cText.SetType(COpcText::Delimited);
        cText.SetDelims(L":");

        if (!cReader.GetNext(cText)) THROW_(bResult, false);
        if (!ToUnsigned(cText, uValue, MAX_HOUR, MIN_HOUR, 10)) THROW_(bResult, false);
        wHour = (WORD)uValue;

        // parse month field.
        cText.SetType(COpcText::Delimited);
        cText.SetDelims(L":");

        if (!cReader.GetNext(cText)) THROW_(bResult, false);
        if (!ToUnsigned(cText, uValue, MAX_MINUTE, MIN_MINUTE, 10)) THROW_(bResult, false);
        wMinute = (WORD)uValue;

        // parse seconds field.
        cText.SetType(COpcText::Delimited);
        cText.SetDelims(L".");
        cText.SetEofDelim();

        if (!cReader.GetNext(cText)) THROW_(bResult, false);
        if (!ToUnsigned(cText, uValue, MAX_SECOND, MIN_SECOND, 10)) THROW_(bResult, false);
        wSeconds = (WORD)uValue;

        // parse seconds fraction field.
        wFraction = 0;

        if (cText.GetDelimChar() == L'.')
        {
            cText.SetType(COpcText::Delimited);
            cText.SetEofDelim();

            if (!cReader.GetNext(cText)) THROW_(bResult, false);

            // preprocess text.
            COpcString cFraction = cText;

            // add trailing zeros.
            while (cFraction.GetLength() < 3) cFraction += _T("0");

            // truncate extra digits.
            if (cFraction.GetLength() > 3) cFraction = cFraction.SubStr(0,3);

            if (!ToUnsigned(cFraction, uValue, MAX_ULONG, 0, 10))
            {
                THROW_(bResult, false);
            }

            // result is in milliseconds.
            wFraction = (WORD)uValue;
        }
    }
    CATCH
    {
        wHour     = 0;
        wMinute   = 0;
        wSeconds  = 0;
        wFraction = 0;
    }

    return bResult;
}
// GetNext
bool COpcTextReader::GetNext(COpcText& cToken)
{
    // no more data to get - give up
    if (m_uEndOfData == 0)
    {
        return false;
    }

    // find the token
    if (!FindToken(cToken))
    {
        return false;
    }     

    // all done if token is not being extracted.
    if (cToken.GetNoExtract())
    {
        return true;
    }

    UINT uEndOfToken = cToken.GetEnd() + 1;
    UINT uDataLeft   = m_uEndOfData - uEndOfToken;
  
    // extract the delimiter if extracting token.

    // new line delimiter found.
    if (cToken.GetNewLine())
    {
        if (cToken.GetDelimChar() == _T('\r'))
        {
            uEndOfToken += 2;
            uDataLeft   -= 2;
        }

        else
        {
            uEndOfToken += 1;
            uDataLeft   -= 1;
        }
    }

    // specific delimiter found.
    else if (cToken.GetDelimChar() > 0 && !cToken.GetEof())
    {
        uEndOfToken++;
        uDataLeft--;
    }

    // move leftover data to the start of the buffer
    for (UINT ii = 0; ii < uDataLeft; ii++)
    {
        m_szBuf[ii] = m_szBuf[uEndOfToken+ii];
    }

    m_szBuf[ii]  = L'\0';
    m_uEndOfData = uDataLeft;

	// set EOF flag if no data left in buffer.
	if (m_uEndOfData == 0)
	{
		cToken.SetEof();
	}
    
    return true;
}