Bei der Portierung eines Moduls vom PB3 mit LongLongs zu PB4 mit Quads ist mir aufgefallen, dass es hier Probleme mit Quads gibt.
Im Folgenden habe ich mal die Kernprobleme extrahiert und allgemein gültig gemacht.
Define qVar.q
Define lTmp.l
Define Daten.l
Daten = $44332211 ; zum Test, kein Byte ist für sich negativ!
; Im Speicher ist die Long wie folgt abgelegt:
; Daten+0 = $11
; Daten+1 = $22
; Daten+2 = $33
; Daten+3 = $44
qVar = PeekB(@Daten+2) | (PeekB(@Daten+1) << 8)
; qVar sollte jetzt den Wert $2233 haben (führende Nullen weggelassen)
Debug "(Falsch ) " + RSet(HexQ(qVar), 16,"0")
; In den höherwertigen Bits steht aber was :(
; Konstruktion mit Hilfs-Variable
lTmp = PeekB(@Daten+2) | (PeekB(@Daten+1) << 8) ; erst mal auf ein Long
qVar = lTmp ; dann dem Quad zuweisen
Debug "(Richtig) " + RSet(HexQ(qVar), 16,"0")
; qVar hat jetzt den Wert $2233
Bitte nicht über Sinn oder Unsinn dieses Codestückes diskutieren, es ist nur ein abstrahiertes Beispiel.
Stehe ich jetzt auf dem Schlauch oder hat hier PB4 ein Problem?
Man wird alt wie 'ne Kuh und lernt immer noch dazu
Define qVar.q
Define lTmp.l
Define Daten.l
Procedure.s HexQuad(Value.q, len = 0)
Protected i, temp.s
For i = 7 To 0 Step -1
temp + RSet(Hex(PeekB(@Value + i)), 2, "0")
Next
If len
temp = Right(temp, len)
EndIf
ProcedureReturn temp
EndProcedure
Daten = $44332211 ; zum Test, kein Byte ist für sich negativ!
; Im Speicher ist die Long wie folgt abgelegt:
; Daten+0 = $11
; Daten+1 = $22
; Daten+2 = $33
; Daten+3 = $44
qVar = PeekB(@Daten+2) | (PeekB(@Daten+1) << 8)
; qVar sollte jetzt den Wert $2233 haben (führende Nullen weggelassen)
Debug "(Falsch ) " + RSet(HexQ(qVar), 16,"0")
; In den höherwertigen Bits steht aber was :(
; Konstruktion mit Hilfs-Variable
lTmp = PeekB(@Daten+2) | (PeekB(@Daten+1) << 8) ; erst mal auf ein Long
qVar = lTmp ; dann dem Quad zuweisen
Debug "(Richtig) " + RSet(HexQ(qVar), 16,"0")
; qVar hat jetzt den Wert $2233
Debug "HexQuad: " + HexQuad(qVar)
Der Bug liegt in der Funktion HexQ().
Im Speicher liegt der richtige Quadwert. Uff
Der Fehler leigt eindeutig in der Quad-Bearbeitung.
Beim Zuweisen erhält die Quad falsche Inhalte!
Die Funktion HexQ ist nicht fehlerhaft.
Allerdings hatte die HexQuad einen kleinen aber entscheidenden Fehler.
Das ist ein schwerwiegender Bug, der die ganze Quad-Bearbeitung in Frage stellt. Immer schön kontrollieren, was da rauskommt!
Define qVar.q
Define lTmp.l
Define Daten.l
Procedure.s HexQuad(Value.q, len = 0)
Protected i, temp.s
For i = 7 To 0 Step -1
temp + RSet(Hex(PeekC(@Value + i)), 2, "0") ; kein PeekB! Achtung Vorzeichen!
Next
If len
temp = Right(temp, len)
EndIf
ProcedureReturn temp
EndProcedure
Daten = $44332211 ; zum Test, kein Byte ist für sich negativ!
; Im Speicher ist die Long wie folgt abgelegt:
; Daten+0 = $11
; Daten+1 = $22
; Daten+2 = $33
; Daten+3 = $44
qVar = PeekB(@Daten+2) | (PeekB(@Daten+1) << 8)
; qVar sollte jetzt den Wert $2233 haben (führende Nullen weggelassen)
Debug "(Falsch ) HexQ: " + RSet(HexQ(qVar), 16,"0")
; In den höherwertigen Bits steht aber was :(
Debug "(Falsch) HexQuad: " + HexQuad(qVar)
; Quad demaskieren
qVar & $FFFFFFFF
Debug "(Richtig) HexQuad: " + HexQuad(qVar)
; Konstruktion mit Hilfs-Variable
lTmp = PeekB(@Daten+2) | (PeekB(@Daten+1) << 8) ; erst mal auf ein Long
qVar = lTmp ; dann dem Quad zuweisen
Debug "(Richtig) HexQ: " + RSet(HexQ(qVar), 16,"0")
; qVar hat jetzt den Wert $2233
Debug "(Richtig) HexQuad: " + HexQuad(qVar)
Man ist nie zu alt zum lernen, auch wenn man dabei manchmal alt aussieht!
Habe mir den ASM-Output angeschaut und keinen Fehler gefunden. In der Quad-Variable landet der richtige Wert. Ursache für die falsche Ausgabe ist der zugeschaltete Debugger. Wird der ausgeschaltet und die Ausgabe über Messagerequester gemacht ist alles in Ordnung. Da muss jetzt aber wirklich jemand vom PB-Team ran!
Die "Zusatzzahl" ist übrigens die Speicheradresse von Daten+1.
BTW:
bringt mich stark ins Grübeln. Prioritäten hin und her, ich hätte jetzt erwartet, das der eingelesene Byte-Wert geshiftet wird und dann erst weiterverarbeitet wird.