Example #1
0
void CAdvancedLineEditWidget::testBorders()
{
	const int _true_size = text().size();

	if (_true_size == m_currentLength)
		return;

	if (_true_size <= m_minLength && m_currentLength > m_minLength)
		Q_EMIT minLengthReached();

	if (_true_size >= maxLength() && m_currentLength < maxLength())
		Q_EMIT maxLengthReached();
}
Example #2
0
void QLineEdit::insert( const char * newText )
{
    QString t( newText );
    if ( t.isEmpty() )
	return;

    uchar *p = (uchar *) t.data();
    while ( *p ) {		// unprintable/nl becomes space
	if ( *p < 32 )
	    *p = 32;
	p++;
    }

    QString test( tbuf.copy() );
    int cp = cursorPos;
    if ( hasMarkedText() ) {
	test.remove( minMark(), maxMark() - minMark() );
	cp = minMark();
    }
    test.insert( cp, t );
    cp = QMIN( cp+t.length(), (uint)maxLength() );
    cursorOn = FALSE;
    blinkSlot();
    validateAndSet( test, cp, cp, cp );
}
Example #3
0
static inline void run(MainWindow * window ) {

    QImage image0("images:000000");

    const float width_image_=image0.width();
    const float height_image_=image0.height();

    auto len_ =maxLength(width_image_,height_image_ );

    const float diff_width_image_=0.0f;
    const float diff_height_image_=len_/2;

    std::vector< cv::Point2f > from_{ {0,4},{4,0},{0,0} };
    std::vector< cv::Point2f > to_{
        {2+diff_width_image_,diff_height_image_+2},
        {2+diff_width_image_,diff_height_image_-2},
        {diff_width_image_,diff_height_image_}
    };

    cv::Mat atmax_ = cv::getAffineTransform(from_,to_);

    auto cvImage0=qImage2CVmat(image0);
    cv::Mat ans( len_,len_,atmax_.type() );
    cv::warpAffine(cvImage0.first,ans,atmax_,{len_,len_});

    window->insertImage( cvMat2QImage(ans).first.copy() )
        ->setWindowTitle(QObject::trUtf8(u8"变换后图像"));
    window->insertImage(image0)
        ->setWindowTitle(QObject::trUtf8(u8"原始图像"));
}
Example #4
0
void HTMLTextAreaElement::handleBeforeTextInsertedEvent(BeforeTextInsertedEvent* event) const
{
    ASSERT(event);
    ASSERT(renderer());
    int signedMaxLength = maxLength();
    if (signedMaxLength < 0)
        return;
    unsigned unsignedMaxLength = static_cast<unsigned>(signedMaxLength);

    const String& currentValue = innerTextValue();
    unsigned numberOfLineBreaksInCurrentValue = numberOfLineBreaks(currentValue);
    if (upperBoundForLengthForSubmission(currentValue, numberOfLineBreaksInCurrentValue)
        + upperBoundForLengthForSubmission(event->text(), numberOfLineBreaks(event->text())) < unsignedMaxLength)
        return;

    unsigned currentLength = computeLengthForSubmission(currentValue, numberOfLineBreaksInCurrentValue);
    // selectionLength represents the selection length of this text field to be
    // removed by this insertion.
    // If the text field has no focus, we don't need to take account of the
    // selection length. The selection is the source of text drag-and-drop in
    // that case, and nothing in the text field will be removed.
    unsigned selectionLength = focused() ? computeLengthForSubmission(plainText(document().frame()->selection().selection().toNormalizedRange().get())) : 0;
    ASSERT(currentLength >= selectionLength);
    unsigned baseLength = currentLength - selectionLength;
    unsigned appendableLength = unsignedMaxLength > baseLength ? unsignedMaxLength - baseLength : 0;
    event->setText(sanitizeUserInputValue(event->text(), appendableLength));
}
QByteArray IQSMPPOptionalParameter<QString>::encode() const
{
    QByteArray result;
    //Если не устанавливали значения для данной опции, то вернем пустой массив, т.к. данная опция
    //не используется
    if (!_valueSets)
        return result;

    if (tag() == IQSMPP::UndefinedOptionalParameter)
        return result;
    if (maxLength() == 0)
        return result;

    QDataStream stream (&result, QIODevice::WriteOnly);
    stream << (quint16) tag();
    stream << (quint16) 0;

    //Запишим данные
    //Если это строка
    QByteArray stringBA = _value.toLatin1();
    const char * stringShar = stringBA.constData();
    int stringLength = stringBA.length();
    stream.writeRawData(stringShar, stringLength);
    if (_cOctetString)
        stream << (quint8)0x00;

    //Сохраним размер
    stream.device()->seek(2);
    stream << (quint16) result.size() - 4;

    return result;
}
void IQSMPPOptionalParameter<QString>::setValue(const QString &value)
{
    if (value.length() > maxLength())
        return;
    _value = value;
    _valueSets = true;
}
Example #7
0
void HTMLTextAreaElement::handleBeforeTextInsertedEvent(
    BeforeTextInsertedEvent* event) const {
  DCHECK(event);
  DCHECK(layoutObject());
  int signedMaxLength = maxLength();
  if (signedMaxLength < 0)
    return;
  unsigned unsignedMaxLength = static_cast<unsigned>(signedMaxLength);

  const String& currentValue = innerEditorValue();
  unsigned currentLength = computeLengthForAPIValue(currentValue);
  if (currentLength + computeLengthForAPIValue(event->text()) <
      unsignedMaxLength)
    return;

  // selectionLength represents the selection length of this text field to be
  // removed by this insertion.
  // If the text field has no focus, we don't need to take account of the
  // selection length. The selection is the source of text drag-and-drop in
  // that case, and nothing in the text field will be removed.
  unsigned selectionLength = 0;
  if (isFocused()) {
    // TODO(xiaochengh): The use of updateStyleAndLayoutIgnorePendingStylesheets
    // needs to be audited.  See http://crbug.com/590369 for more details.
    document().updateStyleAndLayoutIgnorePendingStylesheets();

    selectionLength = computeLengthForAPIValue(
        document().frame()->selection().selectedText());
  }
  DCHECK_GE(currentLength, selectionLength);
  unsigned baseLength = currentLength - selectionLength;
  unsigned appendableLength =
      unsignedMaxLength > baseLength ? unsignedMaxLength - baseLength : 0;
  event->setText(sanitizeUserInputValue(event->text(), appendableLength));
}
Example #8
0
void prettyPrint(FILE* file, 
		 const List<HeckeMonomial<P> >& h,
		 const Permutation& a,
		 const SchubertContext& p, 
		 const Interface& I, 
		 const Length& l, 
		 const Ulong& ls)

/*
  This function does the prettyprinting of h to the file. The formatting
  of the output is optimized for screen viewing. This means that if two
  entries fit on a line, we will do two-column output. Otherwise, we do
  one-column output, and moreover we try to fold long lines decently.

  The parameter l is needed to determine the non-zero mu-coefficients.
*/

{
  static String buf(0);

  Ulong maxl = maxLength(h,p,I,l);
  Ulong hl = (ls-1)/2;

  if (maxl > hl)
    return oneColumnPrint(file,h,a,p,I,l,ls);
  else
    return twoColumnPrint(file,h,a,p,I,l,ls);

  return;
}
void HTMLTextAreaElement::handleBeforeTextInsertedEvent(BeforeTextInsertedEvent* event) const
{
    ASSERT(event);
    ASSERT(layoutObject());
    int signedMaxLength = maxLength();
    if (signedMaxLength < 0)
        return;
    unsigned unsignedMaxLength = static_cast<unsigned>(signedMaxLength);

    const String& currentValue = innerEditorValue();
    unsigned currentLength = computeLengthForSubmission(currentValue);
    if (currentLength + computeLengthForSubmission(event->text()) < unsignedMaxLength)
        return;

    // selectionLength represents the selection length of this text field to be
    // removed by this insertion.
    // If the text field has no focus, we don't need to take account of the
    // selection length. The selection is the source of text drag-and-drop in
    // that case, and nothing in the text field will be removed.
    unsigned selectionLength = 0;
    if (focused()) {
        const EphemeralRange range = document().frame()->selection().selection().toNormalizedEphemeralRange();
        selectionLength = computeLengthForSubmission(plainText(range));
    }
    ASSERT(currentLength >= selectionLength);
    unsigned baseLength = currentLength - selectionLength;
    unsigned appendableLength = unsignedMaxLength > baseLength ? unsignedMaxLength - baseLength : 0;
    event->setText(sanitizeUserInputValue(event->text(), appendableLength));
}
Example #10
0
void HTMLTextAreaElement::setMinLength(int newValue, ExceptionState& exceptionState)
{
    int max = maxLength();
    if (newValue < 0)
        exceptionState.throwDOMException(IndexSizeError, "The value provided (" + String::number(newValue) + ") is not positive or 0.");
    else if (max >= 0 && newValue > max)
        exceptionState.throwDOMException(IndexSizeError, ExceptionMessages::indexExceedsMaximumBound("minLength", newValue, max));
    else
        setIntegralAttribute(minlengthAttr, newValue);
}
Example #11
0
bool HTMLTextAreaElement::tooLong(const String& value, NeedsToCheckDirtyFlag check) const
{
    // Return false for the default value even if it is longer than maxLength.
    if (check == CheckDirtyFlag && !m_isDirty)
        return false;

    int max = maxLength();
    if (max < 0)
        return false;
    return numGraphemeClusters(value) > static_cast<unsigned>(max);
}
bool HTMLTextAreaElement::tooLong() const
{
    // Return false for the default value even if it is longer than maxLength.
    if (!m_isDirty)
        return false;

    int max = maxLength();
    if (max < 0)
        return false;
    return value().length() > static_cast<unsigned>(max);
}
Example #13
0
bool HTMLTextAreaElement::tooLong(const String* value, NeedsToCheckDirtyFlag check) const
{
    // Return false for the default value or value set by script even if it is
    // longer than maxLength.
    if (check == CheckDirtyFlag && !lastChangeWasUserEdit())
        return false;

    int max = maxLength();
    if (max < 0)
        return false;
    return computeLengthForSubmission(value ? *value : this->value()) > static_cast<unsigned>(max);
}
Example #14
0
bool HTMLTextAreaElement::tooLong(const String& value, NeedsToCheckDirtyFlag check) const
{
    // Return false for the default value or value set by script even if it is
    // longer than maxLength.
    if (check == CheckDirtyFlag && !m_wasModifiedByUser)
        return false;

    int max = maxLength();
    if (max < 0)
        return false;
    return computeLengthForSubmission(value) > static_cast<unsigned>(max);
}
QByteArray IQSMPPOptionalParameter<T>::encode() const
{
    QByteArray result;
    //Если не устанавливали значения для данной опции, то вернем пустой массив, т.к. данная опция
    //не используется
    if (!_valueSets)
        return result;

    if (tag() == IQSMPP::UndefinedOptionalParameter)
        return result;
    if (maxLength() == 0)
        return result;

    QDataStream stream (&result, QIODevice::WriteOnly);
    stream << (quint16) tag();
    stream << (quint16) 0;

    //Запишим данные
    if (maxLength() == 1)
    {
        quint8 temp = static_cast<quint8>(_value);
        stream << temp;
    }
    else if (maxLength() == 2)
    {
        quint16 temp = static_cast<quint16>(_value);
        stream << temp;
    }
    else if (maxLength() == 4)
    {
        quint32 temp = static_cast<quint32>(_value);
        stream << temp;
    }

    //Сохраним размер
    stream.device()->seek(2);
    stream << (quint16) (result.size() - 4);

    return result;
}
Example #16
0
TEST(MaximumTrajectoryLength, test) {
	MaximumTrajectoryLength maxLength(10);
	Candidate c;

	c.setTrajectoryLength(9.9);
	maxLength.process(&c);
	EXPECT_TRUE(c.isActive());

	c.setTrajectoryLength(10.1);
	maxLength.process(&c);
	EXPECT_FALSE(c.isActive());
	EXPECT_TRUE(c.hasProperty("Rejected"));
}
Example #17
0
// returns if the anchor was found
// result 1 is int[nrows], list of anchor starts
// result 2 is ANCHOR (it is modified)
bool findAnchor(int* result, int nrows,
        const char** rows, const int* lens,
        int& ANCHOR, int MIN_LENGTH, int MIN_ANCHOR) {
    int max_len = maxLength(nrows, lens);
    do {
        bool ok = tryFindAnchor(result, nrows, rows, lens,
                    ANCHOR, MIN_LENGTH, max_len);
        if (ok) {
            return true;
        }
        ANCHOR -= 1;
    } while (ANCHOR >= MIN_ANCHOR);
    return false;
}
Example #18
0
const bool Shader::setSource(
    const QString & source
,   const bool update)
{
    m_source = source;

    const QByteArray bytes(m_source.toLocal8Bit());
    const GLchar * chr(bytes.constData());

    glShaderSource(m_shader, 1, &chr, nullptr);
    glError();
    glCompileShader(m_shader);
    glError();

    GLint status(GL_FALSE);
    glGetShaderiv(m_shader, GL_COMPILE_STATUS, &status);

    m_compiled = (GL_TRUE == status);
    m_log = "";

    if(!m_compiled)
    {
        GLint maxLength(0);
        GLint logLength(0);

        glGetShaderiv(m_shader, GL_INFO_LOG_LENGTH, &maxLength);
        glError();

        GLchar *log = new GLchar[maxLength];
        glGetShaderInfoLog(m_shader, maxLength, &logLength, log);
        glError();

        m_log = log;

        t_typeStrings::const_iterator i(typeStrings.find(type()));
        if(typeStrings.end() != i)
            qCritical("Compiling shader of type %s failed.", qPrintable(i.value()));
        else
            qCritical("Compiling shader of type %i failed.", type());

        if(!m_log.isEmpty())
            qCritical("%s", qPrintable(m_log));
    }

    if(update)
        this->update();

    return isCompiled();
}
Example #19
0
bool HTMLTextAreaElement::tooLong(const String& value, NeedsToCheckDirtyFlag check) const
{
    // Return false for the default value or value set by script even if it is
    // longer than maxLength.
    if (check == CheckDirtyFlag && !m_wasModifiedByUser)
        return false;

    int max = maxLength();
    if (max < 0)
        return false;
    unsigned unsignedMax = static_cast<unsigned>(max);
    unsigned numberOfLineBreaksInValue = numberOfLineBreaks(value);
    return upperBoundForLengthForSubmission(value, numberOfLineBreaksInValue) > unsignedMax
        && computeLengthForSubmission(value, numberOfLineBreaksInValue) > unsignedMax;
}
Example #20
0
String HTMLTextAreaElement::validationMessage() const
{
    if (!willValidate())
        return String();

    if (customError())
        return customValidationMessage();

    if (valueMissing())
        return validationMessageValueMissingText();

    if (tooLong())
        return validationMessageTooLongText(computeLengthForSubmission(value()), maxLength());

    return String();
}
void HTMLTextAreaElement::handleBeforeTextInsertedEvent(BeforeTextInsertedEvent* event) const
{
    ASSERT(event);
    ASSERT(renderer());
    int signedMaxLength = maxLength();
    if (signedMaxLength < 0)
        return;
    unsigned unsignedMaxLength = static_cast<unsigned>(signedMaxLength);

    unsigned currentLength = toRenderTextControl(renderer())->text().numGraphemeClusters();
    unsigned selectionLength = plainText(document()->frame()->selection()->selection().toNormalizedRange().get()).numGraphemeClusters();
    ASSERT(currentLength >= selectionLength);
    unsigned baseLength = currentLength - selectionLength;
    unsigned appendableLength = unsignedMaxLength > baseLength ? unsignedMaxLength - baseLength : 0;
    event->setText(sanitizeUserInputValue(event->text(), appendableLength));
}
Example #22
0
String HTMLTextAreaElement::validationMessage() const {
  if (!willValidate())
    return String();

  if (customError())
    return customValidationMessage();

  if (valueMissing())
    return locale().queryString(WebLocalizedString::ValidationValueMissing);

  if (tooLong())
    return locale().validationMessageTooLongText(value().length(), maxLength());

  if (tooShort())
    return locale().validationMessageTooShortText(value().length(),
                                                  minLength());

  return String();
}
Example #23
0
void HTMLTextAreaElement::handleBeforeTextInsertedEvent(BeforeTextInsertedEvent* event) const
{
    ASSERT(event);
    ASSERT(renderer());
    int signedMaxLength = maxLength();
    if (signedMaxLength < 0)
        return;
    unsigned unsignedMaxLength = static_cast<unsigned>(signedMaxLength);

    unsigned currentLength = numGraphemeClusters(toRenderTextControl(renderer())->text());
    // selectionLength represents the selection length of this text field to be
    // removed by this insertion.
    // If the text field has no focus, we don't need to take account of the
    // selection length. The selection is the source of text drag-and-drop in
    // that case, and nothing in the text field will be removed.
    unsigned selectionLength = focused() ? numGraphemeClusters(plainText(document()->frame()->selection()->selection().toNormalizedRange().get())) : 0;
    ASSERT(currentLength >= selectionLength);
    unsigned baseLength = currentLength - selectionLength;
    unsigned appendableLength = unsignedMaxLength > baseLength ? unsignedMaxLength - baseLength : 0;
    event->setText(sanitizeUserInputValue(event->text(), appendableLength));
}
Example #24
0
bool QLineEdit::validateAndSet( const char * newText, int newPos,
				int newMarkAnchor, int newMarkDrag )
{
    QString t( newText );
    if ( !t.isEmpty() ) {
	uchar *p = (uchar *) t.data();
	while ( *p ) {		// unprintable/linefeed becomes space
	    if ( *p < 32 )
		*p = 32;
	    p++;
	}
    }
    if ( t.length() > (uint)maxLength() )
	t.truncate( maxLength() );

    QValidator * v = validator();

    if ( v && v->validate( t, newPos ) == QValidator::Invalid &&
	 v->validate( tbuf, cursorPos ) != QValidator::Invalid ) {
	return FALSE;
    }

    // okay, it succeeded
    if ( newMarkDrag != markDrag ||
	 newMarkAnchor |! markAnchor ||
	 newPos != cursorPos ||
	 t != tbuf ) {
	int minP = QMIN( cursorPos, minMark() );
	int maxP = QMAX( cursorPos, maxMark() );
	cursorPos = newPos;
	markAnchor = newMarkAnchor;
	markDrag = newMarkDrag;
	d->pmDirty = TRUE;

	minP = QMIN( minP, QMIN( cursorPos, minMark() ) );
	maxP = QMAX( maxP, QMAX( cursorPos, maxMark() ) );
	
	if ( tbuf == t || tbuf == t.right( tbuf.length() ) ) {
	    int i = 0;
	    while( i < minP && t[i] == tbuf[i] )
		i++;
	    minP = i;
	    i = t.length();
	    if ( i > (int) tbuf.length() ) {
		tbuf = t;
	    } else {
		while( i > maxP && t[i] == tbuf[i] )
		    i--;
	    }
	    maxP = i;
	    repaintArea( minP, maxP );
	} else {
	    tbuf = t;
	    d->pmDirty = TRUE;
	    QFontMetrics fm = fontMetrics();
	    int x;
	    if ( offset > cursorPos )
		x = 0;
	    else
		x = fm.width(t.mid( offset, cursorPos - offset) );
	    int margin = frame() ? 2 : 0;
	    if ( x >= width() - margin ) {
		while( x >= width() - margin ) {
		    int w = fm.width( tbuf[offset] );
		    x -= w;
		    offset++;
		}
	    }
	    d->pmDirty = TRUE;
	    repaint( FALSE );
	}
    }
    emit textChanged( tbuf );
    return TRUE;
}
int QLineEdit::qt_metacall(QMetaObject::Call _c, int _id, void **_a)
{
    _id = QWidget::qt_metacall(_c, _id, _a);
    if (_id < 0)
        return _id;
    if (_c == QMetaObject::InvokeMetaMethod) {
        if (_id < 21)
            qt_static_metacall(this, _c, _id, _a);
        _id -= 21;
    }
#ifndef QT_NO_PROPERTIES
      else if (_c == QMetaObject::ReadProperty) {
        void *_v = _a[0];
        switch (_id) {
        case 0: *reinterpret_cast< QString*>(_v) = inputMask(); break;
        case 1: *reinterpret_cast< QString*>(_v) = text(); break;
        case 2: *reinterpret_cast< int*>(_v) = maxLength(); break;
        case 3: *reinterpret_cast< bool*>(_v) = hasFrame(); break;
        case 4: *reinterpret_cast< EchoMode*>(_v) = echoMode(); break;
        case 5: *reinterpret_cast< QString*>(_v) = displayText(); break;
        case 6: *reinterpret_cast< int*>(_v) = cursorPosition(); break;
        case 7: *reinterpret_cast< Qt::Alignment*>(_v) = alignment(); break;
        case 8: *reinterpret_cast< bool*>(_v) = isModified(); break;
        case 9: *reinterpret_cast< bool*>(_v) = hasSelectedText(); break;
        case 10: *reinterpret_cast< QString*>(_v) = selectedText(); break;
        case 11: *reinterpret_cast< bool*>(_v) = dragEnabled(); break;
        case 12: *reinterpret_cast< bool*>(_v) = isReadOnly(); break;
        case 13: *reinterpret_cast< bool*>(_v) = isUndoAvailable(); break;
        case 14: *reinterpret_cast< bool*>(_v) = isRedoAvailable(); break;
        case 15: *reinterpret_cast< bool*>(_v) = hasAcceptableInput(); break;
        case 16: *reinterpret_cast< QString*>(_v) = placeholderText(); break;
        case 17: *reinterpret_cast< Qt::CursorMoveStyle*>(_v) = cursorMoveStyle(); break;
        }
        _id -= 18;
    } else if (_c == QMetaObject::WriteProperty) {
        void *_v = _a[0];
        switch (_id) {
        case 0: setInputMask(*reinterpret_cast< QString*>(_v)); break;
        case 1: setText(*reinterpret_cast< QString*>(_v)); break;
        case 2: setMaxLength(*reinterpret_cast< int*>(_v)); break;
        case 3: setFrame(*reinterpret_cast< bool*>(_v)); break;
        case 4: setEchoMode(*reinterpret_cast< EchoMode*>(_v)); break;
        case 6: setCursorPosition(*reinterpret_cast< int*>(_v)); break;
        case 7: setAlignment(*reinterpret_cast< Qt::Alignment*>(_v)); break;
        case 8: setModified(*reinterpret_cast< bool*>(_v)); break;
        case 11: setDragEnabled(*reinterpret_cast< bool*>(_v)); break;
        case 12: setReadOnly(*reinterpret_cast< bool*>(_v)); break;
        case 16: setPlaceholderText(*reinterpret_cast< QString*>(_v)); break;
        case 17: setCursorMoveStyle(*reinterpret_cast< Qt::CursorMoveStyle*>(_v)); break;
        }
        _id -= 18;
    } else if (_c == QMetaObject::ResetProperty) {
        _id -= 18;
    } else if (_c == QMetaObject::QueryPropertyDesignable) {
        _id -= 18;
    } else if (_c == QMetaObject::QueryPropertyScriptable) {
        _id -= 18;
    } else if (_c == QMetaObject::QueryPropertyStored) {
        _id -= 18;
    } else if (_c == QMetaObject::QueryPropertyEditable) {
        _id -= 18;
    } else if (_c == QMetaObject::QueryPropertyUser) {
        _id -= 18;
    }
#endif // QT_NO_PROPERTIES
    return _id;
}
Example #26
0
BerthaBuffer* BerthaBuffer::append(char ch) {
  if (length() < maxLength())
    strncat(buffer(), &ch, 1);
  return this;
}
Example #27
0
/////////////////////////////////////////////////////
// Handle a protocol level packet. This could be either a top-level
// EQUDPIPPacket or a subpacket that is just an EQProtocolPacket. Either way
// we use net opcodes here.
void EQPacketStream::processPacket(EQProtocolPacket& packet, bool /*isSubpacket*/)
{
#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 2)
  seqDebug("-->EQPacketStream::processPacket, subpacket=%s on stream %s (%d)",
    (isSubpacket ? "true" : "false"), EQStreamStr[m_streamid], m_streamid);
#endif

  if (IS_APP_OPCODE(packet.getNetOpCode()))
  {
    // This is an app-opcode directly on the wire with no wrapping protocol
    // information. Weird, but whatever gets the stream read, right?
	dispatchPacket(packet.payload(), packet.payloadLength(), 
      packet.getNetOpCode(), m_opcodeDB.find(packet.getNetOpCode()));
    return;
  }

  // Process the net opcode
  switch (packet.getNetOpCode())
  {
    case OP_Combined:
    {
#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 2)
      seqDebug("EQPacket: found combined packet (net op: %04x, size %d) on stream %s (%d). Unrolling.", 
        packet.getNetOpCode(), packet.payloadLength(), 
        EQStreamStr[m_streamid], m_streamid);
#endif

      // Rolled up multiple packets inside this packet. Need to unroll them
      // and process them individually. subpacket starts after the net opcode.
      uint8_t* subpacket = packet.payload();

      while (subpacket < packet.payload() + packet.payloadLength())
      {
        // Length specified first on the wire.
        uint8_t subpacketLength = subpacket[0];

        // Move past the length
        subpacket++;

        // OpCode (in net order)
        uint16_t subOpCode = *(uint16_t*)subpacket;
        
#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 2)
        seqDebug("EQPacket: unrolling length %d bytes from combined packet on stream %s (%d). Opcode %04x", 
          subpacketLength, EQStreamStr[m_streamid], m_streamid, subOpCode);
#endif
        
        // Opcode is next. Net opcode or app opcode?
        if (subOpCode == 0)
        {
          // App opcode < 0x00ff. Skip the first byte and dispatch the app
          // opcode appropriately
          subpacket++;

          subOpCode = *(uint16_t*)subpacket;

#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 2)
          seqDebug("EQPacket: processing unrolled special app opcode, length %d bytes from combined packet on stream %s (%d). Opcode %04x", 
            subpacketLength-3, EQStreamStr[m_streamid], m_streamid, subOpCode);
#endif

          // App opcode. Dispatch it, skipping opcode.
          dispatchPacket(&subpacket[2], subpacketLength-2, 
            subOpCode, m_opcodeDB.find(subOpCode));

        }
        else if (IS_NET_OPCODE(subOpCode))
        {
#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 2)
          seqDebug("EQPacket: processing unrolled net opcode, length %d bytes from combined packet on stream %s (%d). Opcode %04x", 
            subpacketLength, EQStreamStr[m_streamid], m_streamid, subOpCode);
#endif

          // Net opcode. false = copy. true = subpacket
          EQProtocolPacket spacket(subpacket, subpacketLength, false, true);

          processPacket(spacket, true);
        }
        else
        {
#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 2)
        seqDebug("EQPacket: processing unrolled app opcode, length %d bytes from combined packet on stream %s (%d). Opcode %04x", 
          subpacketLength-2, EQStreamStr[m_streamid], m_streamid, subOpCode);
#endif

          // App opcode. Dispatch it, skipping opcode.
          dispatchPacket(&subpacket[2], subpacketLength-2, 
            subOpCode, m_opcodeDB.find(subOpCode));
        }
        subpacket += subpacketLength;
      }
    }
    break;
    case OP_AppCombined:
    {
#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 2)
      seqDebug("EQPacket: found appcombined packet (net op: %04x, size %d) on stream %s (%d). Unrolling.", 
        packet.getNetOpCode(), packet.payloadLength(), 
        EQStreamStr[m_streamid], m_streamid);
#endif

      // Multiple app op codes in the same packet. Need to unroll and dispatch
      // them.
      uint8_t* subpacket = packet.payload();

      while (subpacket < packet.payload() + packet.payloadLength())
      {
        // Length specified first on the wire.
        uint8_t subpacketLength = subpacket[0];

        // Move past the length
        subpacket++;

        if (subpacketLength != 0xff)
        {
          // Dispatch app op code using given packet length. Net order!
          uint16_t subOpCode = *(uint16_t*)(subpacket);

          // Handle 3 byte opcodes properly
          if (subOpCode == 0)
          {
            // 3 byte opcode. Drop the first byte, opcode is byte 2 and 3
            subpacket++;
            subpacketLength--;
            subOpCode = *(uint16_t*)(subpacket);
          }

#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 2)
        seqDebug("EQPacket: unrolling length %d bytes from combined packet on stream %s (%d). Opcode %04x", 
          subpacketLength, EQStreamStr[m_streamid], m_streamid, subOpCode);
        seqDebug("EQPacket: processing unrolled app opcode, length %d bytes from combined packet on stream %s (%d). Opcode %04x", 
          subpacketLength-2, EQStreamStr[m_streamid], m_streamid, subOpCode);
#endif

          // Dispatch, skipping op code.
          dispatchPacket(&subpacket[2], subpacketLength-2, 
            subOpCode, m_opcodeDB.find(subOpCode));

          // Move ahead
          subpacket += subpacketLength;
        }
        else
        {
          // If original length is 0xff, it means it is a long one. The length
          // is 2 bytes and next.
          uint16_t longOne = eqntohuint16(subpacket);
 
          // Move past the 2 byte length
          subpacket += 2;

          // OpCode next. Net order for op codes.
          uint16_t subOpCode = *(uint16_t*)subpacket;

          // Handle 3 byte opcodes properly
          if (subOpCode == 0)
          {
            // 3 byte opcode. Drop the first byte, opcode is byte 2 and 3
            subpacket++;
            longOne--;
            subOpCode = *(uint16_t*)(subpacket);
          }
          
#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 2)
        seqDebug("EQPacket: unrolling length %d bytes from combined packet on stream %s (%d). Opcode %04x", 
          longOne, EQStreamStr[m_streamid], m_streamid, subOpCode);
        seqDebug("EQPacket: processing unrolled app opcode, length %d bytes from combined packet on stream %s (%d). Opcode %04x", 
          longOne-2, EQStreamStr[m_streamid], m_streamid, subOpCode);
#endif

          // Dispatch, skipping op code.
          dispatchPacket(&subpacket[2], longOne-2, 
            subOpCode, m_opcodeDB.find(subOpCode));

          // Move ahead
          subpacket += longOne;
        }
      }
    }
    break;
    case OP_Packet:
    {
      // Normal unfragmented sequenced packet.
      uint16_t seq = packet.arqSeq();
      emit seqReceive(seq, (int)m_streamid);

      // Future packet?
      if (seq == m_arqSeqExp)
      {
        // Expected packet.
        m_arqSeqExp++;
        emit seqExpect(m_arqSeqExp, (int)m_streamid);

        // OpCode next. Net order for op codes.
        uint16_t subOpCode = *(uint16_t*)(packet.payload());
       
#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 1)
        seqDebug("SEQ: Found next sequence number in data stream %s (%d), incrementing expected seq, %04x (op code %04x, sub opcode %04x)", 
          EQStreamStr[m_streamid], m_streamid, seq, 
          packet.getNetOpCode(), subOpCode);
#endif

        // Opcode is next. Net opcode or app opcode?
        if (subOpCode == 0)
        {
          // App opcode < 0x00ff. Skip the first byte and dispatch the app
          // opcode appropriately
          subOpCode = *(uint16_t*)&packet.payload()[1];

#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 1)
          seqDebug("EQPacket: special app opcode extracted for opcode 0000 on stream %s (%d). Opcode %04x", 
            EQStreamStr[m_streamid], m_streamid, subOpCode);
#endif

          // App opcode. Dispatch it, skipping opcode.
          dispatchPacket(&packet.payload()[3], packet.payloadLength()-3, 
            subOpCode, m_opcodeDB.find(subOpCode));

        }
        else if (IS_NET_OPCODE(subOpCode))
        {
          // Net opcode. false = no copy. true = subpacket.
          EQProtocolPacket spacket(packet.payload(), 
            packet.payloadLength(), false, true);

          processPacket(spacket, true);
        }
        else
        {
          // App opcode. Dispatch, skipping opcode.
          dispatchPacket(&packet.payload()[2], packet.payloadLength()-2,
            subOpCode, m_opcodeDB.find(subOpCode));
        }
      }
      else if ((seq > m_arqSeqExp && 
                  seq < (uint32_t(m_arqSeqExp + arqSeqWrapCutoff))) ||
               seq < (int32_t(m_arqSeqExp) - arqSeqWrapCutoff))
      {
        // Yeah, future packet. Push it on the packet cache.
#ifdef PACKET_PROCESS_DIAG
        seqDebug("SEQ: out of order sequence %04x stream %s (%d) expecting %04x, sending to cache, %04d",
          seq, EQStreamStr[m_streamid], m_streamid, 
          m_arqSeqExp, m_cache.size());
#endif
        setCache(seq, packet);
      }
      else
      {
#ifdef PACKET_PROCESS_DIAG
        // Past packet outside the cut off
        seqWarn("SEQ: received sequenced %spacket outside expected window on stream %s (%d) netopcode=%04x size=%d. Expecting seq=%04x got seq=%04x, window size %d, dropping packet as in the past.", 
          (isSubpacket ? "sub" : ""),
          EQStreamStr[m_streamid], m_streamid,
          packet.getNetOpCode(), packet.payloadLength(), 
          m_arqSeqExp, seq, arqSeqWrapCutoff);
#endif
      }
    }
    break;
    case OP_Oversized:
    {
      // Fragmented sequenced data packet.
      uint16_t seq = packet.arqSeq();
      emit seqReceive(seq, (int)m_streamid);

      // Future packet?
      if (seq == m_arqSeqExp)
      {
        // Expected packet.
        m_arqSeqExp++;
        emit seqExpect(m_arqSeqExp, (int)m_streamid);
       
#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 1)
        seqDebug("SEQ: Found next sequence number in data stream %s (%d), incrementing expected seq, %04x (op code %04x)", 
          EQStreamStr[m_streamid], m_streamid, seq, packet.getNetOpCode());
#endif

        // Push the fragment on.
        m_fragment.addFragment(packet);

        if (m_fragment.isComplete())
        {
          // OpCode from fragment. In network order.
          uint16_t fragOpCode = *(uint16_t*)(m_fragment.data());

#ifdef PACKET_PROCESS_DIAG
        seqDebug("SEQ: Completed oversized app packet on stream %s with seq %04x, total size %d opcode %04x", 
          EQStreamStr[m_streamid], seq, m_fragment.size()-2, fragOpCode);
#endif

          // dispatch fragment. Skip opcode.
          if (fragOpCode == 0)
          {
            // Special app opcode. Skip first byte and op is byte 2 and 3.
            fragOpCode = *(uint16_t*)(&m_fragment.data()[1]);

#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 1)
            seqDebug("EQPacket: special app opcode on completed fragment for opcode 0000 on stream %s (%d). Opcode %04x", 
            EQStreamStr[m_streamid], m_streamid, fragOpCode);
#endif

            dispatchPacket(&m_fragment.data()[3], m_fragment.size()-3,
              fragOpCode, m_opcodeDB.find(fragOpCode)); 
          }
          else
          {
            dispatchPacket(&m_fragment.data()[2], m_fragment.size()-2,
              fragOpCode, m_opcodeDB.find(fragOpCode)); 
          }

          m_fragment.reset();
        }
      }
      else if ((seq > m_arqSeqExp && 
                  seq < (uint32_t(m_arqSeqExp + arqSeqWrapCutoff))) ||
               seq < (int32_t(m_arqSeqExp) - arqSeqWrapCutoff))
      {
        // Yeah, future packet. Push it on the packet cache.
#ifdef PACKET_PROCESS_DIAG
        seqDebug("SEQ: out of order sequence %04x stream %s (%d) expecting %04x, sending to cache, %04d",
          seq, EQStreamStr[m_streamid], m_streamid, 
          m_arqSeqExp, m_cache.size());
#endif
        setCache(seq, packet);
      }
      else
      {
#ifdef PACKET_PROCESS_DIAG
        // Past packet outside the cut off
        seqWarn("SEQ: received sequenced %spacket outside expected window on stream %s (%d) netopcode=%04x size=%d. Expecting seq=%04x got seq=%04x, window size %d, dropping packet as in the past.", 
          (isSubpacket ? "sub" : ""),
          EQStreamStr[m_streamid], m_streamid,
          packet.getNetOpCode(), packet.payloadLength(), 
          m_arqSeqExp, seq, arqSeqWrapCutoff);
#endif
      }
    }
    break;
    case OP_SessionRequest:
    {
      // Session request from client to server.
      // 
      // Sanity check the size. Don't assume any packet we see is an EQ
      // session request, since we're gonna cause a huge freakin' malloc
      // on the maxlength of the session which for some reason some people
      // won't enjoy!
      if (packet.payloadLength() != sizeof(SessionRequestStruct))
      {
          // Either SessionRequestStruct changed or this isn't a session
          // request.
#if defined(PACKET_PROCESS_DIAG) || defined(PACKET_SESSION_DIAG)
          seqDebug("EQPacket: Ignoring SessionRequest %s:%u->%s:%u with invalid size %d.",
            ((EQUDPIPPacketFormat&) packet).getIPv4SourceA().ascii(),
            ((EQUDPIPPacketFormat&) packet).getSourcePort(),
            ((EQUDPIPPacketFormat&) packet).getIPv4DestA().ascii(),
            ((EQUDPIPPacketFormat&) packet).getDestPort(),
            packet.payloadLength());
#endif
          break;
      }

      // Pull off session request information
      SessionRequestStruct* request = (SessionRequestStruct*) packet.payload();

      m_sessionId = eqntohuint32((uint8_t*)&(request->sessionId));
      m_maxLength = eqntohuint32((uint8_t*)&(request->maxLength));

      // Sanity check the max length requested
      if (m_maxLength > maxPacketSize)
      {
        seqWarn("EQPacket: SessionRequest wanted a max packet size of %d which is above our sane max packet size of %d. Using our max",
          m_maxLength, maxPacketSize);

        m_maxLength = maxPacketSize;
      }

      emit maxLength((int) m_maxLength, (int) m_streamid);

#if defined(PACKET_PROCESS_DIAG) || defined(PACKET_SESSION_DIAG)
      seqDebug("EQPacket: SessionRequest found, resetting expected seq, stream %s (%d) (session tracking %s)",
	    EQStreamStr[m_streamid], m_streamid,
        (m_session_tracking_enabled == 2 ? "locked on" : 
          (m_session_tracking_enabled == 1 ? "enabled" : "disabled")));
#endif

#if defined(PACKET_SESSION_DIAG)
      seqDebug("EQPacket: SessionRequest %s:%u->%s:%u, sessionId %u maxLength %u, awaiting key for stream %s (%d)",
        ((EQUDPIPPacketFormat&) packet).getIPv4SourceA().ascii(),
        ((EQUDPIPPacketFormat&) packet).getSourcePort(),
        ((EQUDPIPPacketFormat&) packet).getIPv4DestA().ascii(),
        ((EQUDPIPPacketFormat&) packet).getDestPort(),
        m_sessionId, m_maxLength, EQStreamStr[m_streamid], m_streamid);
#endif

#if defined(PACKET_SESSION_DIAG) && (PACKET_SESSION_DIAG > 1)
      seqDebug("EQPacket: SessionRequest contents: unknown %u, sessionId %u, maxLength %u",
        eqntohuint32((uint8_t*)&(request->unknown0000)), 
        m_sessionId, m_maxLength);
#endif

#if defined(PACKET_SESSION_DIAG) && (PACKET_SESSION_DIAG > 2)
      seqDebug("EQPacket: Raw SessionRequest: %02x%02x %02x%02x %02x%02x %02x%02x %02x%02x %02x%02x",
        packet.payload()[0], packet.payload()[1], packet.payload()[2], 
        packet.payload()[3], packet.payload()[4], packet.payload()[5], 
        packet.payload()[6], packet.payload()[7], packet.payload()[8], 
        packet.payload()[9], packet.payload()[10], packet.payload()[11]);
#endif

      m_arqSeqExp = 0;
      m_arqSeqFound = true;

      if (m_session_tracking_enabled)
      {
        // Save off client port for the stream so we can match against it
        // later. SessionRequest should always be an outer protocol packet
        // so we can cast it to EQUDPIPPacketFormat to get the ip headers.
        m_sessionClientPort = ((EQUDPIPPacketFormat&) packet).getSourcePort();
      }
    }
    break;
    case OP_SessionResponse:
    {
      // Session response from server

      // Sanity check the size. Don't assume any packet we see is an EQ
      // session response, since we're gonna cause a huge freakin' malloc
      // on the maxlength of the session which for some reason some people
      // won't enjoy!
      if (packet.payloadLength() != sizeof(SessionResponseStruct))
      {
          // Either SessionResponseStruct changed or this isn't a session
          // response.
#if defined(PACKET_PROCESS_DIAG) || defined(PACKET_SESSION_DIAG)
          seqDebug("EQPacket: Ignoring SessionResponse %s:%u->%s:%u with invalid size %d.",
            ((EQUDPIPPacketFormat&) packet).getIPv4SourceA().ascii(),
            ((EQUDPIPPacketFormat&) packet).getSourcePort(),
            ((EQUDPIPPacketFormat&) packet).getIPv4DestA().ascii(),
            ((EQUDPIPPacketFormat&) packet).getDestPort(),
            packet.payloadLength());
#endif
          break;
      }

      // Pull off session response information
      SessionResponseStruct* response = 
        (SessionResponseStruct*) packet.payload();

      m_maxLength = eqntohuint32((uint8_t*)&(response->maxLength));
      m_sessionKey = eqntohuint32((uint8_t*)&(response->key));
      m_sessionId = eqntohuint32((uint8_t*)&(response->sessionId));

      // Sanity check the max length requested
      if (m_maxLength > maxPacketSize)
      {
        seqWarn("EQPacket: SessionResponse wanted a max packet size of %d which is above our sane max packet size of %d. Using our max",
          m_maxLength, maxPacketSize);

        m_maxLength = maxPacketSize;
      }

      emit maxLength((int) m_maxLength, (int) m_streamid);

#if defined(PACKET_PROCESS_DIAG) || defined(PACKET_SESSION_DIAG)
      seqDebug("EQPacket: SessionResponse found %s:%u->%s:%u, resetting expected seq, stream %s (%d) (session tracking %s)",
        ((EQUDPIPPacketFormat&) packet).getIPv4SourceA().ascii(),
        ((EQUDPIPPacketFormat&) packet).getSourcePort(),
        ((EQUDPIPPacketFormat&) packet).getIPv4DestA().ascii(),
        ((EQUDPIPPacketFormat&) packet).getDestPort(),
	    EQStreamStr[m_streamid], m_streamid,
        (m_session_tracking_enabled == 2 ? "locked on" : 
          (m_session_tracking_enabled == 1 ? "enabled" : "disabled")));
#endif
      
#if defined(PACKET_SESSION_DIAG)
      seqDebug("EQPacket: SessionResponse sessionId %u maxLength %u, key is %u for stream %s (%d)",
        m_sessionId, m_maxLength, m_sessionKey, 
        EQStreamStr[m_streamid], m_streamid);
#endif

#if defined(PACKET_SESSION_DIAG) && (PACKET_SESSION_DIAG > 1)
      seqDebug("EQPacket: SessionResponse contents: sessionId %u, key %u, unknown %u, unknown %u, maxLength %u, unknown %u",
        m_sessionId, m_sessionKey, 
        eqntohuint16((uint8_t*)&(response->unknown0008)),
        response->unknown0010, m_maxLength,
        eqntohuint32((uint8_t*) &(response->unknown0015)));
#endif

#if defined(PACKET_SESSION_DIAG) && (PACKET_SESSION_DIAG > 2)
      seqDebug("EQPacket: Raw SessionResponse: %02x%02x %02x%02x %02x%02x %02x%02x %02x%02x %02x%02x %02x%02x %02x%02x %02x%02x %02x",
        packet.payload()[0], packet.payload()[1], packet.payload()[2], 
        packet.payload()[3], packet.payload()[4], packet.payload()[5], 
        packet.payload()[6], packet.payload()[7], packet.payload()[8], 
        packet.payload()[9], packet.payload()[10], packet.payload()[11],
        packet.payload()[12], packet.payload()[13], packet.payload()[14], 
        packet.payload()[15], packet.payload()[16], packet.payload()[17], 
        packet.payload()[18]);
#endif

      // Provide key to corresponding stream from this session/stream
      emit sessionKey(m_sessionId, m_streamid, m_sessionKey);

      m_arqSeqExp = 0;
      m_arqSeqFound = true;

      // Session tracking
      if (m_session_tracking_enabled)
      {
        // Save off client port for the stream so we can match against it
        // later. SessionRequest should always be an outer protocol packet
        // so we can cast it to EQUDPIPPacketFormat to get the ip headers.
        m_sessionClientPort = ((EQUDPIPPacketFormat&) packet).getDestPort();

        // If this is the world server talking to us, reset session tracking if
        // it is on so we unlatch the client in case of getting kicked.
        if (m_streamid == world2client)
        {
          m_session_tracking_enabled = 1;
          emit sessionTrackingChanged(m_session_tracking_enabled);
        }
        // If this is the zone server talking to us, close the latch and lock
        else if (m_streamid == zone2client)
        {
          // SessionResponse should always be an outer protocol packet, so
          // the EQProtocolPacket passed in can be cast back to
          // EQUDPIPPacketFormat, which we need to go to get access to the IP
          // headers!
          m_session_tracking_enabled = 2;
  
          emit lockOnClient(((EQUDPIPPacketFormat&) packet).getSourcePort(), 
            ((EQUDPIPPacketFormat&) packet).getDestPort());
          emit sessionTrackingChanged(m_session_tracking_enabled);
        }
      }
    }
    break;
    case OP_SessionDisconnect:
    {
#if defined(PACKET_PROCESS_DIAG) || defined(PACKET_SESSION_DIAG)
      seqDebug("EQPacket: SessionDisconnect found %s:%u->%s:%u, resetting expected seq, stream %s (%d) (session tracking %s)",
        ((EQUDPIPPacketFormat&) packet).getIPv4SourceA().ascii(),
        ((EQUDPIPPacketFormat&) packet).getSourcePort(),
        ((EQUDPIPPacketFormat&) packet).getIPv4DestA().ascii(),
        ((EQUDPIPPacketFormat&) packet).getDestPort(),
	    EQStreamStr[m_streamid], m_streamid,
        (m_session_tracking_enabled == 2 ? "locked on" : 
          (m_session_tracking_enabled == 1 ? "enabled" : "disabled")));
#endif

#if defined(PACKET_SESSION_DIAG) && (PACKET_SESSION_DIAG > 2)
      seqDebug("EQPacket: Raw SessionDisconnect: %02x%02x %02x%02x %02x%02x %02x%02x",
        packet.payload()[0], packet.payload()[1], packet.payload()[2], 
        packet.payload()[3], packet.payload()[4], packet.payload()[5], 
        packet.payload()[6], packet.payload()[7]);
#endif

      m_arqSeqExp = 0;

      // Clear cache
      resetCache();

      // Signal closing. Unlatch session tracking if it is on.
      if (m_session_tracking_enabled)
      {
        m_session_tracking_enabled = 1;
        emit sessionTrackingChanged(m_session_tracking_enabled);

        m_sessionClientPort = 0;
      }

      emit closing(m_sessionId, m_streamid);
    }
    break;
    case OP_Ack:
    case OP_AckFuture:
    case OP_AckAfterDisconnect:
    {
#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 2)
      seqDebug("EQPacket: no-op on ACK for net opcode %04x seq %04x, stream %s (%d)",
	    packet.getNetOpCode(), eqntohuint16(packet.payload()), 
        EQStreamStr[m_streamid], m_streamid);
#endif
    }
    break;
    case OP_KeepAlive:
    case OP_SessionStatRequest:
    case OP_SessionStatResponse:
    {
#if defined(PACKET_PROCESS_DIAG) && (PACKET_PROCESS_DIAG > 2)
      seqDebug("EQPacket: no-op on stats for net opcode %04x, stream %s (%d)",
	    packet.getNetOpCode(), EQStreamStr[m_streamid], m_streamid);
#endif
    }
    break;
    default :
    {
      seqWarn("EQPacket: Unhandled net opcode %04x, stream %s, size %d",
        packet.getNetOpCode(), EQStreamStr[m_streamid], packet.payloadLength());
    }
  }
}
Example #28
0
void Communicator::makeMaxLength() {
	MaxLengthPacket maxLength(buffer);
}
String HTMLTextAreaElement::validationMessage() const
{
    if (!willValidate())
        return String();

    if (customError())
        return customValidationMessage();

    if (valueMissing())
        return locale().queryString(WebKit::WebLocalizedString::ValidationValueMissing);

    if (tooLong())
        return locale().validationMessageTooLongText(computeLengthForSubmission(value()), maxLength());

    return String();
}
Example #30
0
/*	Function: gpsMerge
	Pre-Conditions: An opened and filled in GpFile structure and the name of the merging file taken from the command line
	Post-Conditions: A modified GpFile which includes all the information from the merging file
	Errors Returned:EXIT_FAILURE
	Description: This function takes all the information from the merging file and merges it with the first GpFile structure. 
		     The problem of duplicate waypoints, different ID and symbol lengths and date/timezone differences are addressed
*/
int gpsMerge( GpFile *filep, const char *const fnameB ){

	GpFile* fileA = filep;
	GpFile* fileB;
	GpStatus fileStatus;
	FILE* inputfileB;
	int maxIDLen=0;
	int maxSymLen=0;
	int i=0;
	int j=0;
	int oldnwaypts=0;
	int maxRouteno=0;
	int convTZ=0;
	double convDist=0.0;
	double convTime=0.0;
	char* thisStr=NULL;
	char* IDbuffer=NULL;
	char* Symbuffer=NULL;
	char copies;

	fileB = malloc(sizeof(GpFile));
	assert(fileB);

	inputfileB = fopen(fnameB, "r");
	if(inputfileB == NULL) {
		fprintf(stderr, "Fatal Error: Cannot open file B for reading\n");
		return EXIT_FAILURE;
	}

	fileStatus =  readGpFile(inputfileB, fileB);

	if(fileStatus.code != OK) {
		fprintf(stderr, "Fatal Error: readGpFile returns error %d on line %d for file B\n", fileStatus.code, fileStatus.lineno);
		return EXIT_FAILURE;
	}

	if(fileA->nwaypts>0 && fileB->nwaypts>0) {
		fileA->waypt = realloc(fileA->waypt, sizeof(GpWaypt) * (fileA->nwaypts + fileB->nwaypts));
		maxIDLen = maxLength(fileA->waypt[0].ID, fileB->waypt[0].ID);
		maxSymLen = maxLength(fileA->waypt[0].symbol, fileB->waypt[0].symbol);
		IDbuffer = malloc(sizeof(char) * maxIDLen);
		Symbuffer = malloc(sizeof(char) * maxSymLen);

		for(i=0; i<fileB->nwaypts; i++) {
			fileA->waypt[(fileA->nwaypts) + i].textChoice = fileA->waypt[0].textChoice;
			fileA->waypt[(fileA->nwaypts) + i].textPlace = fileA->waypt[0].textPlace;
			fileA->waypt[(fileA->nwaypts) + i].ID = malloc(sizeof(char) * (strlen(fileB->waypt[i].ID)+1));
			assert(fileA->waypt[(fileA->nwaypts) + i].ID);
			strcpy(fileA->waypt[(fileA->nwaypts) + i].ID, fileB->waypt[i].ID);\
			fileA->waypt[(fileA->nwaypts) + i].coord.lat = fileB->waypt[i].coord.lat;
			fileA->waypt[(fileA->nwaypts) + i].coord.lon = fileB->waypt[i].coord.lon;
			fileA->waypt[(fileA->nwaypts) + i].symbol = malloc(sizeof(char) * (strlen(fileB->waypt[i].symbol)+1));
			assert(fileA->waypt[(fileA->nwaypts) + i].symbol);
			strcpy(fileA->waypt[(fileA->nwaypts) + i].symbol, fileB->waypt[i].symbol);
			fileA->waypt[(fileA->nwaypts) + i].comment = malloc(sizeof(char) * (strlen(fileB->waypt[i].comment)+1));
			assert(fileA->waypt[(fileA->nwaypts) + i].comment);
			strcpy(fileA->waypt[(fileA->nwaypts) + i].comment, fileB->waypt[i].comment);
		}
		oldnwaypts = fileA->nwaypts;
		fileA->nwaypts += fileB->nwaypts;

		for(i=0; i<fileA->nwaypts; i++) {
			fileA->waypt[i].ID = padSpace(fileA->waypt[i].ID, maxIDLen);
			fileA->waypt[i].symbol = padSpace(fileA->waypt[i].symbol, maxSymLen);
		}
	}

	/*Duplicates file B's elements into file A*/
	if(fileA->nwaypts==0 && fileB->nwaypts>0) {
		fileA->waypt = realloc(fileA->waypt, sizeof(GpWaypt) * (fileB->nwaypts));

		for(i=0; i<fileB->nwaypts; i++) {
			fileA->waypt[i].ID = strdup(fileB->waypt[i].ID);
			assert(fileA->waypt[i].ID);
			fileA->waypt[i].coord.lat = fileB->waypt[i].coord.lat;
			fileA->waypt[i].coord.lon = fileB->waypt[i].coord.lon;
			fileA->waypt[i].textChoice = fileB->waypt[0].textChoice;
			fileA->waypt[i].textPlace = fileB->waypt[0].textPlace;
			fileA->waypt[i].symbol = strdup(fileB->waypt[i].symbol);
			assert(fileA->waypt[i].symbol);	
			fileA->waypt[i].comment = strdup(fileB->waypt[i].comment);
			assert(fileA->waypt[i].comment);
		}
	}

	thisStr = malloc(sizeof(char) * maxIDLen+1);

	/*Checking through the new filepointer to find duplicate waypoints*/
	for(i=0; i<fileA->nwaypts; i++) {
		copies = '0';
		strcpy(thisStr, fileA->waypt[i].ID);
		for(j=i+1; j<fileA->nwaypts; j++) {
			/*If there is a match, it will append a 0 at the last character*/
			if(strcmp(fileA->waypt[j].ID, thisStr) == 0) {
				fileA->waypt[j].ID[maxIDLen-1] = copies;
				copies++;
			}
		}
	}

	for(i=0; i<fileA->nroutes; i++) {
		if(fileA->route[i]->number > maxRouteno) {
			maxRouteno = fileA->route[i]->number;
		}
	}

	maxRouteno = maxRouteno / 100;
	maxRouteno += 1;
	maxRouteno = maxRouteno*100;
	maxRouteno += 1;

	if(fileA->nroutes>0 && fileB->nroutes>0) {
		fileA->route = realloc(fileA->route, sizeof(GpRoute*) * (fileA->nroutes + fileB->nroutes));

		for(i=0; i<fileB->nroutes; i++) {
			fileA->route[fileA->nroutes + i] = malloc(sizeof(GpRoute) + (sizeof(int) * fileB->route[i]->npoints));
			fileA->route[fileA->nroutes + i]->number = maxRouteno+i;
			fileA->route[fileA->nroutes + i]->comment = malloc(sizeof(char) * (strlen(fileB->route[i]->comment)+1));
			assert(fileA->route[fileA->nroutes + i]->comment);
			strcpy(fileA->route[fileA->nroutes + i]->comment, fileB->route[i]->comment);
			fileA->route[fileA->nroutes + i]->npoints = fileB->route[i]->npoints;
			for(j=0; j<fileB->route[i]->npoints; j++) {
				fileA->route[fileA->nroutes + i]->leg[j] = fileB->route[i]->leg[j] + fileA->nroutes;
			}

		}
	}

	/*Duplicates file B's elements into file A*/
	if(fileA->nroutes==0 && fileB->nroutes>0) {
		fileA->route = realloc(fileA->route, sizeof(GpRoute*) * (fileB->nroutes));
		for(i=0; i<fileB->nroutes; i++) {
			fileA->route[i] = malloc(sizeof(GpRoute) + (sizeof(int) * fileB->route[i]->npoints));
			fileA->route[i]->number = fileB->route[i]->number;
			fileA->route[i]->comment = malloc(sizeof(char) * (strlen(fileB->route[i]->comment)+1));
			assert(fileA->route[i]->comment);
			strcpy(fileA->route[i]->comment, fileB->route[i]->comment);
			fileA->route[i]->npoints = fileB->route[i]->npoints;
			for(j=0; j<fileB->route[i]->npoints; j++) {
				fileA->route[i]->leg[j] = fileB->route[i]->leg[j];
			}
		}
	}
	fileA->nroutes += fileB->nroutes;
	
	if(fileA->ntrkpts>0 && fileB->ntrkpts>0) {
		fileA->trkpt = realloc(fileA->trkpt, sizeof(GpTrkpt) * (fileA->ntrkpts + fileB->ntrkpts));
		convDist = convertDist(fileB->unitHorz, fileA->unitHorz);
		convTime = convertTime(fileA->unitTime, fileB->unitTime);
		convTZ = fileA->timeZone - fileB->timeZone;
		for(i=0; i<fileB->ntrkpts; i++) {
			fileA->trkpt[fileA->ntrkpts + i].coord.lat = fileB->trkpt[i].coord.lat;
			fileA->trkpt[fileA->ntrkpts + i].coord.lon = fileB->trkpt[i].coord.lon;
			fileA->trkpt[fileA->ntrkpts + i].dateTime = fileB->trkpt[i].dateTime + convTZ*3600;	//The datetime needs to be modifed by the timezone difference
			fileA->trkpt[fileA->ntrkpts + i].segFlag = fileB->trkpt[i].segFlag;
			if (fileA->trkpt[fileA->ntrkpts + i].segFlag) {
				fileA->trkpt[fileA->ntrkpts + i].comment = malloc(sizeof(char) * strlen(fileB->trkpt[i].comment)+1);
				assert(fileA->trkpt[fileA->ntrkpts + i].comment);
				strcpy(fileA->trkpt[fileA->ntrkpts + i].comment, fileB->trkpt[i].comment);
			}
 		fileA->trkpt[fileA->ntrkpts + i].speed = ((fileB->trkpt[i].speed * convDist)/convTime);	//speed needs to be converted to file A's specified units
 		fileA->trkpt[fileA->ntrkpts + i].dist = (fileB->trkpt[i].dist / convDist);	//Distance needs to be converted to file A's specified units
 		fileA->trkpt[fileA->ntrkpts + i].duration = (fileB->trkpt[i].duration);
		}

	}
	/*Duplicates file B's elements into file A*/
	else if(fileA->ntrkpts==0 && fileB->ntrkpts>0) {
		for(i=0; i<fileB->ntrkpts; i++) {
			fileA->trkpt = realloc(fileA->trkpt, sizeof(GpTrkpt) * (fileB->ntrkpts));
			fileA->trkpt[i].coord.lat = fileB->trkpt[i].coord.lat;
			fileA->trkpt[i].coord.lon = fileA->trkpt[i].coord.lon;
			fileA->trkpt[i].coord.lon = fileA->trkpt[i].coord.lon;
			fileA->trkpt[i].segFlag = fileB->trkpt[i].segFlag;
			fileA->trkpt[i].comment = malloc(sizeof(char) * strlen(fileB->trkpt[i].comment));
			assert(fileA->trkpt[i].comment);
			strcpy(fileA->trkpt[i].comment, fileB->trkpt[i].comment);
			fileA->trkpt[i].speed = (fileB->trkpt[i].speed);
			fileA->trkpt[i].dist = (fileB->trkpt[i].dist);
			fileA->trkpt[i].duration = (fileB->trkpt[i].duration);
		}
	}

	fileA->ntrkpts += fileB->ntrkpts;

	
	if(fileB) {
		freeGpFile(fileB);
		free(fileB);
	}
	
	if(inputfileB) fclose(inputfileB);
	
	if(IDbuffer) free(IDbuffer);
	
	if(Symbuffer) free(Symbuffer);

	return EXIT_SUCCESS;
	
}