You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

141 lines
2.4 KiB

package sltcpsrv
import (
"fmt"
"log"
"strconv"
"strings"
)
type message struct {
pri uint8
version int
timestamp string
hostname string
appName string
pid int
body string
}
func newMessage(line []byte) *message {
if len(line) == 0 {
return nil
}
msg := &message{
version: -1,
pid: -1,
}
in := ""
accum := []byte{}
everythingElse := ""
n := len(line)
for i, b := range line {
if *isDebug {
log.Printf("in = %q, accum = %q\n", in, string(accum))
}
if i == 0 && b == '<' {
in = "pri"
continue
}
if in == "pri" {
if b == '>' {
in = "pridone"
pri, err := strconv.ParseUint(string(accum), 10, 8)
if err != nil {
if *isDebug {
log.Println("ERROR:", err)
}
return msg
}
msg.pri = uint8(pri)
accum = []byte{}
continue
} else {
accum = append(accum, b)
continue
}
}
if in == "pridone" {
in = "everything_else"
accum = append(accum, b)
continue
}
if in == "everything_else" {
if i == n-1 {
accum = append(accum, b)
everythingElse = string(accum)
break
}
accum = append(accum, b)
continue
}
}
dateParts := []string{}
broken := strings.SplitN(everythingElse, ":", 4)
if len(broken) != 4 {
if *isDebug {
log.Printf("ERROR: got back unexpected parts for %q: %+v\n", everythingElse, broken)
}
return msg
}
verMonthDateHour := strings.Split(broken[0], " ")
minutes := broken[1]
secsHostProc := strings.Split(broken[2], " ")
msg.body = string(broken[3])
hour := ""
switch len(verMonthDateHour) {
case 4:
v, err := strconv.ParseUint(verMonthDateHour[0], 10, 8)
if err != nil {
if *isDebug {
log.Println("ERROR:", err)
}
} else {
msg.version = int(v)
}
dateParts = append(dateParts, verMonthDateHour[1:3]...)
hour = verMonthDateHour[3]
case 3:
dateParts = append(dateParts, verMonthDateHour[:2]...)
hour = verMonthDateHour[2]
}
dateParts = append(dateParts, fmt.Sprintf("%s:%s:%s", hour, minutes, secsHostProc[0]))
msg.timestamp = strings.Join(dateParts, " ")
msg.hostname = string(secsHostProc[1])
procParts := strings.Split(secsHostProc[2], "[")
if len(procParts) > 1 {
msg.appName = string(procParts[0])
p, err := strconv.ParseUint(strings.Trim(procParts[1], "[]"), 10, 16)
if err != nil {
if *isDebug {
log.Println("ERROR:", err)
}
} else {
msg.pid = int(p)
}
} else {
msg.appName = string(procParts[0])
}
return msg
}