Hilfe bei plötzlichem Timer-Stopp während ReadMemory

  • VB.NET

Es gibt 11 Antworten in diesem Thema. Der letzte Beitrag () ist von RodFromGermany.

    Hilfe bei plötzlichem Timer-Stopp während ReadMemory

    Hallöchen,
    ich hoffe ich bin mit meinem Anliegen hier richtig.

    Vorweg, ich habe mir bisher alles selbst beigebracht, weshalb ich wohl eher weniger zu diversen Spezifikationen sagen kann.

    Ich lese mit meinem Programm u.a. Daten aus einem Spiel aus - genauer gesagt einer alten Version von WoW.
    An sich tut das allerdings nichts zur Sache, ich kann ganz normal das Handle holen, mit meinem Pointer + diversen Offsets auf das Spiel zugreifen und alles auslesen was ich möchte.

    Nun stehe ich allerdings vor einem Problem: In kurzen Abständen möchte ich meine aktuellen Koordinaten angezeigt bekommen. Echtzeit muss nicht sein, alle 5ms, zur Not auch alle 250ms, wäre schön.

    Dafür habe ich pro Koordinate ein Label, das ich innerhalb eines Timers dann ändere - im Tick steht pseudo:

    lies x speichere in currx
    speichere currx in labelx

    ...y in y
    ...z in z

    Das funktioniert auch gut, allerdings abhängig vom Timer-Intervall nur für 0,5 bis 15s - ausprobiert habe ich es mit 5ms, 50ms und 250ms Intervall.
    Hat irgendjemand eine Idee woran das liegen könnte? Hören Timer standardmäßig nach einer gewissen Durchlaufzahl auf? Können Variablen "überlaufen" (wobei ich denen ja jeden Durchgang einen neuen Wert zuweise)? Sonst irgendwas? Bei Bedarf kann ich gerne Code-Snippets posten, da meine Funktionen jedoch eigentlich funktionieren denke ich es liegt an etwas anderem.

    Noch ergänzend: Ich lasse es als Admin unter Win8 laufen. Stoppe ich den Timer per Button und starte ihn wieder neu funktioniert er wieder (auch nur zeitlich begrenzt).
    Ich werde mal noch ein paar Tests anstellen und eine Variable mitzählen lassen, nach wievielen Durchläufen meine Funktion stoppt. Der Debugger bringt übrigens keine Meldung.

    Grüße und vielen Dank,

    Uwee
    Willkommen im Forum. :thumbup:
    Wenn Du mal Deinen Code posten würdest, könnten wir eher sehen, was los ist.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    Hallo Rod,
    danke für deine schnelle Antwort und das Willkommen ;)

    Hier also mal ein paar Teile vom Code:

    Deklaration der einzelnen Variablen:

    VB.NET-Quellcode

    1. Private Property pointer As Integer
    2. Private Property XAddress As Integer = &HBF0
    3. Private Property YAddress As Integer = &HBF4
    4. Private Property ZAddress As Integer = &HBF8


    Das ist (wie vermutlich ersichtlich) die Timer-Funktion

    VB.NET-Quellcode

    1. Private Sub ProfileMaker_Timer_CurrentXYZ_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles ProfileMaker_Timer_CurrentXYZ.Tick
    2. ReadProcessMemory(readHandle, pointer + XAddress, currX, 4, 0)
    3. ProfileMaker_CurrWP_x.Text = currX
    4. ReadProcessMemory(readHandle, pointer + YAddress, currY, 4, 0)
    5. ProfileMaker_CurrWP_y.Text = currY
    6. ReadProcessMemory(readHandle, pointer + ZAddress, currZ, 4, 0)
    7. ProfileMaker_CurrWP_z.Text = currZ
    8. End Sub


    Und, falls benötigt, noch die Funktion die den Timer aufruft:

    VB.NET-Quellcode

    1. Dim wow As Process() = Process.GetProcessesByName("WoW")
    2. If wow.Length < 1 Then
    3. MsgBox("Error! Please start WoW first and log into your Character!", , "No WoW found!")
    4. Else
    5. Dim prozess As Process = wow(0)
    6. readHandle = prozess.Handle
    7. bytes = New Byte(23) {}
    8. 'Pointer setzen
    9. ReadProcessMemory(readHandle, DirectCast(&HE29D28, Integer), bytes, DirectCast(24, Integer), rw)
    10. pointer = BitConverter.ToInt32(bytes, 0)
    11. 'ProfileMaker Timer aktivieren
    12. ProfileMaker_Timer_CurrentXYZ.Enabled = True

    Uweee schrieb:

    noch die Funktion die den Timer aufruft:
    Der Timer sollte nicht aufgerufen, sondern nur gestartet werden.
    Wie sieht dieser Code aus?
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!

    VB.NET-Quellcode

    1. 'ProfileMaker Timer aktivieren
    2. ProfileMaker_Timer_CurrentXYZ.Enabled = True


    So.

    €dit: Habe es nun auch noch auf meinem Rechner mit Win7 getestet. Der hat es länger durchgehalten. Anders ist an sich nur der Ram, nämlich doppelt so groß. Falls das indirekt damit zusammenhängt.

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „Uweee“ ()

    Das sieht gut aus.
    Und welchen Wert hast Du bei Timer.Interval drin stehen?
    Probier mal dies:
    Stoppe den den Timer, wenn Du in die Timer-Tock-Routine reinkommst und starte ihn wieder als letzten Befehl.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    Definiere

    Uweee schrieb:

    er bleibt immernoch "stecken".
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    Ich aktiviere den Timer per Funktion -> er zeigt mir meine Koordinaten im 250ms Intervall an, für schätzungsweise 10-15 Sekunden. In diesem Zeitraum aktualisiert er sie auch ständig. Dann bleibt er einfach auf dem letzten Wert hängen, beispielsweise bei -250, -400, 10. Auch mit warten geht es nicht mehr weiter.

    Deaktiviere ich dann den Timer und starte ihn erneut geht es wieder weiter bis er nach 10-15 Sekunden wieder hängen bleibt.
    Wird da das readHandle neu geholt?
    Hole es einfach regelmäßig neu, bei jedem 10. Tick oder so.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    WOW!
    Es funktioniert! ;)
    Vielen, vielen Dank!

    Für alle, die das selbe Problem haben sollten (auch wenn ich das stark bezweifle) hier noch der Code des Timers:

    VB.NET-Quellcode

    1. ProfileMaker_Timer_CurrentXYZ.Enabled = False
    2. If timerzaehler = 10 Then
    3. Dim wow As Process() = Process.GetProcessesByName("WoW")
    4. Dim prozess As Process = wow(0)
    5. readHandle = prozess.Handle
    6. timerzaehler = 0
    7. End If
    8. ReadProcessMemory(readHandle, pointer + XAddress, currX, 4, 0)
    9. ProfileMaker_CurrWP_x.Text = currX
    10. ReadProcessMemory(readHandle, pointer + YAddress, currY, 4, 0)
    11. ProfileMaker_CurrWP_y.Text = currY
    12. ReadProcessMemory(readHandle, pointer + ZAddress, currZ, 4, 0)
    13. ProfileMaker_CurrWP_z.Text = currZ
    14. ProfileMaker_Timer_CurrentXYZ.Enabled = True
    15. timerzaehler = timerzaehler + 1


    Damit bleibt die Anzeige immer mal wieder (ca der gleiche Zeitabschnitt wie vorher) kurz stecken, allerdings nur für ca 0,5s, dann läuft er wieder weiter.

    @Rod: Nochmals vielen, vielen Dank!
    Aus Interesse, hast du mir für die aufgetretenen Probleme eine Erklärung? Ändert sich das handle hin und wieder?

    Uweee schrieb:

    eine Erklärung?
    Nein, das ist ein Arbeits-Drumherum. :D

    VB.NET-Quellcode

    1. If timerzaehler = 10 Then
    2. Dim wow As Process() = Process.GetProcessesByName("WoW")
    3. readHandle = wow(0).Handle ' hier gleich wow(0) einsetzen
    4. timerzaehler = 0
    5. End If
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!