quickfixgo / quickfix

The Go FIX Protocol Library :rocket:
https://www.quickfixgo.org/
Other
735 stars 288 forks source link

ParseMessageWithDataDictionary has an unused arg. #550

Closed hyunw55 closed 1 month ago

hyunw55 commented 1 year ago

applicationDataDictionary is received as arg, but it is not used inside the function.

this function is in message.go line 138

// ParseMessageWithDataDictionary constructs a Message from a byte slice wrapping a FIX message using an optional session and application DataDictionary for reference.
func ParseMessageWithDataDictionary(
    msg *Message,
    rawMessage *bytes.Buffer,
    transportDataDictionary *datadictionary.DataDictionary,
    applicationDataDictionary *datadictionary.DataDictionary,
) (err error) {
    msg.Header.Clear()
    msg.Body.Clear()
    msg.Trailer.Clear()
    msg.rawMessage = rawMessage

    rawBytes := rawMessage.Bytes()

    //allocate fields in one chunk
    fieldCount := 0
    for _, b := range rawBytes {
        if b == '\001' {
            fieldCount++
        }
    }

    if fieldCount == 0 {
        return parseError{OrigError: fmt.Sprintf("No Fields detected in %s", string(rawBytes))}
    }

    if cap(msg.fields) < fieldCount {
        msg.fields = make([]TagValue, fieldCount)
    } else {
        msg.fields = msg.fields[0:fieldCount]
    }

    fieldIndex := 0

    //message must start with begin string, body length, msg type
    if rawBytes, err = extractSpecificField(&msg.fields[fieldIndex], tagBeginString, rawBytes); err != nil {
        return
    }

    msg.Header.add(msg.fields[fieldIndex : fieldIndex+1])
    fieldIndex++

    parsedFieldBytes := &msg.fields[fieldIndex]
    if rawBytes, err = extractSpecificField(parsedFieldBytes, tagBodyLength, rawBytes); err != nil {
        return
    }

    msg.Header.add(msg.fields[fieldIndex : fieldIndex+1])
    fieldIndex++

    parsedFieldBytes = &msg.fields[fieldIndex]
    if rawBytes, err = extractSpecificField(parsedFieldBytes, tagMsgType, rawBytes); err != nil {
        return
    }

    msg.Header.add(msg.fields[fieldIndex : fieldIndex+1])
    fieldIndex++

    trailerBytes := []byte{}
    foundBody := false
    for {
        parsedFieldBytes = &msg.fields[fieldIndex]
        rawBytes, err = extractField(parsedFieldBytes, rawBytes)
        if err != nil {
            return
        }

        switch {
        case isHeaderField(parsedFieldBytes.tag, transportDataDictionary):
            msg.Header.add(msg.fields[fieldIndex : fieldIndex+1])
        case isTrailerField(parsedFieldBytes.tag, transportDataDictionary):
            msg.Trailer.add(msg.fields[fieldIndex : fieldIndex+1])
        default:
            foundBody = true
            trailerBytes = rawBytes
            msg.Body.add(msg.fields[fieldIndex : fieldIndex+1])
        }
        if parsedFieldBytes.tag == tagCheckSum {
            break
        }

        if !foundBody {
            msg.bodyBytes = rawBytes
        }

        fieldIndex++
    }

    //body length would only be larger than trailer if fields out of order
    if len(msg.bodyBytes) > len(trailerBytes) {
        msg.bodyBytes = msg.bodyBytes[:len(msg.bodyBytes)-len(trailerBytes)]
    }

    length := 0
    for _, field := range msg.fields {
        switch field.tag {
        case tagBeginString, tagBodyLength, tagCheckSum: //tags do not contribute to length
        default:
            length += field.length()
        }
    }

    bodyLength, err := msg.Header.GetInt(tagBodyLength)
    if err != nil {
        err = parseError{OrigError: err.Error()}
    } else if length != bodyLength {
        err = parseError{OrigError: fmt.Sprintf("Incorrect Message Length, expected %d, got %d", bodyLength, length)}
    }

    return

}