Skip to content

Commit 0242878

Browse files
committed
Updated failure recognition for packets coming back.
1 parent c12c6bd commit 0242878

File tree

5 files changed

+84
-19
lines changed

5 files changed

+84
-19
lines changed

Sources/sma2mqttLibrary/SMADevice.swift

Lines changed: 58 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@ public actor SMADevice
4343
var lastRequestSentDate = Date.distantPast
4444
let udpMinimumRequestInterval = 1.0 / 10.0 // 1 / maximumRequestsPerSecond
4545
let udpRequestTimeout = 5.0
46+
var currentRequestedObjectID: String = "UNKNOWN"
4647

4748
let requestAllObjects: Bool
4849

@@ -127,7 +128,7 @@ public extension SMADevice
127128

128129
if isHomeManager, lastRequestReceived.timeIntervalSinceNow > -1.0
129130
{
130-
JLog.debug("\(address): isHomeManager and received already at\(lastRequestReceived) - ignoring")
131+
JLog.debug("\(address): isHomeManager and received already at:\(lastRequestReceived) - ignoring")
131132
return nil
132133
}
133134
lastRequestReceived = Date()
@@ -141,12 +142,59 @@ public extension SMADevice
141142
{
142143
if let netPacket = smaPacket.netPacket
143144
{
144-
udpLoggedIn = netPacket.isLoggedIn
145-
udpSystemId = netPacket.header.sourceSystemId
146-
udpSerial = netPacket.header.sourceSerial
145+
JLog.debug("\(address): received netPacket: objectid:\(currentRequestedObjectID) result:\(String(format: "0x%04x", netPacket.header.u16result)) command:\(String(format: "0x%04x", netPacket.header.u16command)) packetid:\(String(format: "0x%04x", netPacket.header.packetId))")
146+
147+
if udpPacketCounter != (0x7FFF & netPacket.header.packetId)
148+
{
149+
JLog.notice("\(address): received netPacket: we did not await:\(String(format: "0x%04x", udpPacketCounter)) packet command:\(String(format: "0x%04x", netPacket.header.u16command)) packetid:\(String(format: "0x%04x", netPacket.header.packetId))")
150+
return nil
151+
}
147152

148153
if netPacket.header.u16command == 0xFFFD
149154
{
155+
if currentRequestedObjectID == "LOGIN"
156+
{
157+
guard netPacket.header.resultIsOk
158+
else
159+
{
160+
JLog.error("\(address): login failed.")
161+
udpLoggedIn = false
162+
return nil
163+
}
164+
JLog.notice("\(address): login success.")
165+
udpLoggedIn = true
166+
udpSystemId = netPacket.header.sourceSystemId
167+
udpSerial = netPacket.header.sourceSerial
168+
return nil
169+
}
170+
JLog.debug("\(address): login required")
171+
udpLoggedIn = false
172+
return nil
173+
}
174+
175+
if !udpLoggedIn
176+
{
177+
JLog.error("\(address): received correct packet even though we are logged out - ignoring.")
178+
return nil
179+
}
180+
181+
if netPacket.header.invalidRequest
182+
{
183+
JLog.notice("\(address):removing invalid request objectId:\(currentRequestedObjectID) : \(tagTranslator.objectsAndPaths[currentRequestedObjectID]?.path ?? "unknown")")
184+
185+
udpLoggedIn = false
186+
187+
objectsToQueryNext = objectsToQueryNext.compactMap { $0.objectid == currentRequestedObjectID ? nil : $0 }
188+
objectsToQueryContinously.removeValue(forKey: currentRequestedObjectID)
189+
190+
return nil
191+
}
192+
193+
if !netPacket.header.resultIsOk
194+
{
195+
JLog.debug("\(address): result not ok. logging out. objectId:\(currentRequestedObjectID) : \(tagTranslator.objectsAndPaths[currentRequestedObjectID]?.path ?? "unknown")")
196+
197+
udpLoggedIn = false
150198
return nil
151199
}
152200

@@ -275,13 +323,18 @@ public extension SMADevice
275323
if !udpLoggedIn
276324
{
277325
packetToSend = try SMAPacketGenerator.generateLoginPacket(packetcounter: packetcounter, password: password, userRight: .user)
326+
JLog.debug("\(address): sending login packetcounter:\(String(format: "0x%04x", packetcounter))")
327+
currentRequestedObjectID = "LOGIN"
278328
}
279329
else
280330
{
281331
packetToSend = try SMAPacketGenerator.generatePacketForObjectID(packetcounter: packetcounter, objectID: objectID, dstSystemId: udpSystemId, dstSerial: udpSerial)
332+
JLog.debug("\(address): sending udp packetcounter:\(String(format: "0x%04x", packetcounter)) objectid:\(objectID) loggedIn:\(udpLoggedIn)")
333+
currentRequestedObjectID = objectID
282334
}
283335

284-
JLog.trace("\(address): sending udp packetcounter:\(String(format: "0x04x", packetcounter)) packet:\(packetToSend)")
336+
JLog.trace("\(address): sending udp packetcounter:\(String(format: "0x%04x", packetcounter)) packet:\(packetToSend)")
337+
285338
let packets = try await udpReceiver.sendReceivePacket(data: [UInt8](packetToSend.hexStringToData()), packetcounter: packetcounter, address: address, port: 9522, receiveTimeout: udpRequestTimeout)
286339

287340
if !packets.isEmpty

Sources/sma2mqttLibrary/SMAPacket/SMANetPacket.swift

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -14,11 +14,6 @@ public struct SMANetPacket: Codable
1414
let directvalue: String?
1515
}
1616

17-
extension SMANetPacket
18-
{
19-
var isLoggedIn: Bool { header.u16result == 0 }
20-
}
21-
2217
extension SMANetPacket: BinaryDecodable
2318
{
2419
public init(fromBinary decoder: BinaryDecoder) throws

Sources/sma2mqttLibrary/SMAPacket/SMANetPacketHeader.swift

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,12 @@ extension SMANetPacketHeader // calculated
4242
// private var followingdatasize: Int { (Int(quaterlength) * 4) - Self.size }
4343
}
4444

45+
extension SMANetPacketHeader
46+
{
47+
var resultIsOk: Bool { u16result == 0x00 }
48+
var invalidRequest: Bool { u16result == 0x15 || u16result == 0x14 }
49+
}
50+
4551
extension SMANetPacketHeader: BinaryDecodable
4652
{
4753
enum SMANetPacketHeaderDecodingError: Error { case decoding(String) }

Sources/sma2mqttLibrary/SMAPacket/SMAPacketGenerator.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,7 @@ extension SMAPacketGenerator
9494
static func generateLoginPacket(packetcounter: Int, password: String, userRight: UserRight, dstSystemId: UInt16 = 0xFFFF, dstSerial: UInt32 = 0xFFFF_FFFF) throws -> String
9595
{
9696
let encodedPassword = encodePassword(password: password, userRight: userRight)
97-
let passwordCommand = "0C04 fdff 07000000 84030000 4c20cb51 00000000 " + encodedPassword
97+
let passwordCommand = "0C 04 fdff 0700 0000 84030000 4c20cb51 00000000 " + encodedPassword
9898
return try generateCommandPacket(packetcounter: packetcounter, command: passwordCommand, dstSystemId: dstSystemId, dstSerial: dstSerial)
9999
}
100100

Tests/sma2mqttTests/sma2mqttTests.swift

Lines changed: 19 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -39,14 +39,25 @@ final class sma2mqttTests: XCTestCase
3939
func testSMADecoding() throws
4040
{
4141
let packets = [
42-
// "534d4100 0004 02a0 00000001 0046 0010 6065 11 e0 07050102030400a19901f6 a22fb3 0001 0000 0000f1b10102005400000000010000000101260068d50f613b975300000000000122260068d50f61b81f000000000000 0000 0000",
43-
// "534d 4100 0004 02a0 0000 0001 0026 0010 6065 09a0 1234 9503 4321 00e0 9901 f6a2 2fb3 0001 1400 0000 ad81 0102 a072 0067 4900 ff67 4900 0000 0000",
42+
// "534d 4100 0004 02a0 0000 0001 0046 0010 6065 11 e0 0705 0102 0304 00a1 9901 f6a2 2fb3 00 01 0000 0000 f1b1 0102 0054 0000 0000 0100 00000101260068d50f613b975300000000000122260068d50f61b81f000000000000 0000 0000",
43+
// "534d 4100 0004 02a0 0000 0001 0026 0010 6065 09 a0 1234 9503 4321 00e0 9901 f6a2 2fb3 00 01 1400 0000 ad81 0102 a072 0067 4900 ff67 4900 0000 0000",
4444
// "534d 4100 0004 02a0 0000 0001 0002 0000 0001 0004 0010 0001 0003 0004 0020 0000 0001 0004 0030 0a70 100e 0004 0040 0000 0000 0002 0070 ef0c 0001 0080 0000 0000 00",
45-
"534d 4100 0004 02a0 0000 0001 002e 0010 6065 0b e0 1234 9503 4321 00 01 9901 f6a2 2fb3 00 00 0000 0000 ae81 0d 04 fdff 0700 0000 8403 0000 4c20 cb51 0000 0000 0000 0000",
46-
"534d 4100 0004 02a0 0000 0001 0026 0010 6065 09 a0 1234 9503 4321 00 e0 9901 f6a2 2fb3 00 01 1400 0000 af81 01 02 5271 005b 4940 ff5b 4940 0000 0000",
47-
"534d 4100 0004 02a0 0000 0001 002e 0010 6065 0b e0 1234 9503 4321 00 01 9901 f6a2 2fb3 00 00 0000 0000 b081 0d 04 fdff 0700 0000 8403 0000 4c20 cb51 0000 0000 0000 0000",
48-
"534d 4100 0004 02a0 0000 0001 0026 0010 6065 09 a0 1234 9503 4321 00 e0 9901 f6a2 2fb3 00 01 1500 0000 b181 01 02 0061 005a 2900 ff5a 2900 0000 0000",
49-
"534d 4100 0004 02a0 0000 0001 002e 0010 6065 0b e0 1234 9503 4321 00 01 9901 f6a2 2fb3 00 00 0000 0000 b281 0d 04 fdff 0700 0000 8403 0000 4c20 cb51 0000 0000 0000 0000",
45+
46+
// "534d 4100 0004 02a0 0000 0001 002e 0010 6065 0b e0 1234 9503 4321 00 01 9901 f6a2 2fb3 00 00 0000 0000 0180 0d 04 fdff 0700 0000 8403 0000 4c20 cb51 0000 0000 0000 0000", // login ok response
47+
// "534d 4100 0004 02a0 0000 0001 005e 0010 6065 17 a0 1234 9503 4321 00 a1 9901 f6a2 2fb3 00 01 0000 0000 0280 01 02 8063 0000 0000 0100 0000 011e 2540 e078 ae64 fe06 0000 fe06 0000 fe06 0000 fe06 0000 0100 0000 021e 2540 e078 ae64 d604 0000 d604 0000 d604 0000 d604 0000 0100 0000 0000 0000" , // normal answer
48+
// "534d 4100 0004 02a0 0000 0001 0036 0010 6065 0d a0 1234 9503 4321 00 a1 9901 f6a2 2fb3 00 01 0000 0000 0380 01 02 0064 0100 0000 0100 0000 0122 2600 e178 ae64 080f 0000 0000 0000 0000 0000", // normal answer
49+
// "534d 4100 0004 02a0 0000 0001 0026 0010 6065 09 a0 1234 9503 4321 00 e0 9901 f6a2 2fb3 00 01 1500 0000 0480 01 02 0061 005a 2900 ff5a 2900 0000 0000", // battery state on normal inverter
50+
// "534d 4100 0004 02a0 0000 0001 002e 0010 6065 0b e0 1234 9503 4321 00 01 9901 f6a2 2fb3 00 00 0000 0000 0580 0d 04 fdff 0700 0000 8403 0000 4c20 cb51 0000 0000 0000 0000",
51+
// "534d 4100 0004 02a0 0000 0001 0026 0010 6065 09 a0 1234 9503 4321 00 e0 9901 f6a2 2fb3 00 01 1400 0000 0680 01 02 5271 005b 4940 ff5b 4940 0000 0000",
52+
// "534d 4100 0004 02a0 0000 0001 002e 0010 6065 0b e0 1234 9503 4321 00 01 9901 f6a2 2fb3 00 00 0000 0000 0780 0d 04 fdff 0700 0000 8403 0000 4c20 cb51 0000 0000 0000 0000",
53+
// "534d 4100 0004 02a0 0000 0001 005e 0010 6065 17 a0 1234 9503 4321 00 a1 9901 f6a2 2fb3 00 01 0000 0000 0880 01 02 8063 0000 0000 0100 0000 011e 2540 e378 ae64 0607 0000 0607 0000 0607 0000 0607 0000 0100 0000 021e 2540 e378 ae64 dc04 0000 dc04 0000 dc04 0000 dc04 0000 0100 0000 0000 0000", // normal answer again
54+
55+
"534d 4100 0004 02a0 0000 0001 0026 0010 6065 09a0 1234 b87b 4321 00e1 9901 f6a2 2fb3 0001 1400 0000 b381 0102 5271 005b 4940 ff5b 4940 0000 0000",
56+
57+
// "534d 4100 0004 02a0 0000 0001 0026 0010 6065 09 a0 1234 9503 4321 00 e0 9901 f6a2 2fb3 00 01 1400 0000 af81 01 02 5271 005b 4940 ff5b 4940 0000 0000",
58+
// "534d 4100 0004 02a0 0000 0001 002e 0010 6065 0b e0 1234 9503 4321 00 01 9901 f6a2 2fb3 00 00 0000 0000 b081 0d 04 fdff 0700 0000 8403 0000 4c20 cb51 0000 0000 0000 0000",
59+
// "534d 4100 0004 02a0 0000 0001 0026 0010 6065 09 a0 1234 9503 4321 00 e0 9901 f6a2 2fb3 00 01 1500 0000 b181 01 02 0061 005a 2900 ff5a 2900 0000 0000",
60+
// "534d 4100 0004 02a0 0000 0001 002e 0010 6065 0b e0 1234 9503 4321 00 01 9901 f6a2 2fb3 00 00 0000 0000 b281 0d 04 fdff 0700 0000 8403 0000 4c20 cb51 0000 0000 0000 0000",
5061

5162
// """
5263
// 534d 4100
@@ -72,7 +83,7 @@ final class sma2mqttTests: XCTestCase
7283

7384
JLog.debug("SMAPacket:\(smaPacket)")
7485

75-
JLog.debug("NetPacketValues:\n\(smaPacket.netPacket?.values.map(\.json).joined(separator: "\n") ?? "")")
86+
JLog.debug("NetPacketValues:\n\n\(smaPacket.netPacket?.values.map(\.json).joined(separator: "\n") ?? "")\n")
7687

7788
XCTAssert(binaryDecoder.isAtEnd)
7889
}

0 commit comments

Comments
 (0)