
Emulator in Python...
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
Also ich glaube ich komme so nicht weiter...
Habe immer wieder einen Crash, ob nun CPython oder PyPy. Das Grundproblem sind wohl threads und TKinter (Wobei das wohl auch mit anderen Toolkits so wäre, vermute ich mal...)
Dann ist generell die Frage, ob Threads überhaupt Sinn machen. Denn durch den Global Interpreter Lock ("GIL") kann ja eh nur wirklich ein Thread laufen. Von daher kann ein Thread dennoch die GUI lähmen...
Vielleicht macht wegen des GIL multiprocessing doch Sinn?!?
Also doch fast so wie es jetzt ist, blos das "Main Thread" zum "Main Process" und "Sub Thread" zu "Sub Process" wird:
Wie kann man das umgehen?
Wird es was bringen alle multiprocess.queue "zwischen zu puffern" ?
Also evtl.:
Der Austausch multiprocessing.Queue <--> Queue.Queue könnte dann evtl. jeweils in separaten Threads erfolgen?
Habe immer wieder einen Crash, ob nun CPython oder PyPy. Das Grundproblem sind wohl threads und TKinter (Wobei das wohl auch mit anderen Toolkits so wäre, vermute ich mal...)
Dann ist generell die Frage, ob Threads überhaupt Sinn machen. Denn durch den Global Interpreter Lock ("GIL") kann ja eh nur wirklich ein Thread laufen. Von daher kann ein Thread dennoch die GUI lähmen...
Vielleicht macht wegen des GIL multiprocessing doch Sinn?!?
Also doch fast so wie es jetzt ist, blos das "Main Thread" zum "Main Process" und "Sub Thread" zu "Sub Process" wird:
Doch dann bremst wieder die Interprocess-Kommunikation aus?!?jens hat geschrieben:[/size]Code: Alles auswählen
Main Thread Sub Thread +------------------+ +---------------------+ | | | | | +-------------+ | CPU cycles/sec queue | | | | <------------------------------------+6809 CPU | | | | | | + ^ | | | GUI | | | | | | | | | | Display RAM write queue | +--v-----+--+ | | | .--------------------------------------------+ Memory | | | | | | | | +--+-----^--+ | | | | | | | | | | | | | | | | +-----v-----+-----+ | | | | | | | | Periphery | | | | | | | Keyboard queue | | MC6883 SAM | | | | | +--------------------------------->MC6821 PIA | | | | | | | | | | | | +--+-----^----+ | | | | | | | | | | +-----------------+ | | | | | | | | +--v-----+----+ | | | | | | | | | | | Display | | | | | | | | | | | +-------------+ | | | +------------------+ +---------------------+
Wie kann man das umgehen?
Wird es was bringen alle multiprocess.queue "zwischen zu puffern" ?
Also evtl.:
Code: Alles auswählen
Main Process Sub Process
+------------------+ +-------------------+
| | | |
| Queue.Queue <-----> multiprocessing.Queue <-------> Queue.Queue |
| | | |
+------------------+ +-------------------+
Das legt die Vermutung nahe, dass du aus dem Thread auf die GUI zugreifst.jens hat geschrieben:Habe immer wieder einen Crash, ob nun CPython oder PyPy. Das Grundproblem sind wohl threads und TKinter (Wobei das wohl auch mit anderen Toolkits so wäre, vermute ich mal...)
Jein. Wenn die parallelisierten Threads nur Berechnungen durchführen, dann macht dir der GIL einen Strich durch die Rechnung. Threads lohnen sich aber dann, wenn ein Thread Berechnungen durchführt und ein anderer irgendwo IO-Aufgaben durchführt. Daten von der Festplatte lesen, Daten über das Netzwer verschicken, etc. In deinem Fall kommen die letzten Aufgaben wohl eher selten vor. Wenn du allerdings pseude-parallele Berechnungen brauchst, dann wirst du um irgendeinen Threadingmechanismus nicht herumkommen. Egal ob nun Threads, Prozesse oder Pseude-Threads mit Generatoren.jens hat geschrieben:Dann ist generell die Frage, ob Threads überhaupt Sinn machen. Denn durch den Global Interpreter Lock ("GIL") kann ja eh nur wirklich ein Thread laufen.
Nein, das kann nicht passieren. In CPython werden 100 Instruktionen durchgeführt, das ist zumindest der letzte Wert an den ich mich erinnern kann, und dann ein Thread-Wechsel durchgeführt. Blockiert ein Aufruf, eine Queue oder ein Lock, so wird immer gewechselt.jens hat geschrieben:Von daher kann ein Thread dennoch die GUI lähmen...
Das hatte ich in einem der vorherigen Beiträge ja schon geschrieben. Das macht nur Sinn, wenn die Berechnungen auch wirklich parallel sind. Wenn du ständig Synchronisieren musst, dann macht dir der Overhead den ganzen Gewinn kaputt.jens hat geschrieben:Vielleicht macht wegen des GIL multiprocessing doch Sinn?!?
Das Leben ist wie ein Tennisball.
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
Das ist nach wie vor die Frage.EyDu hat geschrieben:Das hatte ich in einem der vorherigen Beiträge ja schon geschrieben. Das macht nur Sinn, wenn die Berechnungen auch wirklich parallel sind. Wenn du ständig Synchronisieren musst, dann macht dir der Overhead den ganzen Gewinn kaputt.jens hat geschrieben:Vielleicht macht wegen des GIL multiprocessing doch Sinn?!?
Fazit wäre dann: Entweder multiprocessing oder keine Threads...
Ich glaube ich habe einen "Flaschenhals" bzw. Fehler gefunden: http://www.python-forum.de/viewtopic.ph ... 42#p262542
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
Mit https://github.com/jedie/DragonPy/commi ... e2cd8114d2 geht nun auch der andere Weg. Also auf dem BASIC Text Editor Fenster den Code in den Emulator packen 
Alerdings noch recht unbenutztbar vom GUI Design her

Alerdings noch recht unbenutztbar vom GUI Design her

- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
Nachdem es nun einen Benachmark gibt, der komplett ohne Threads läuft, denke ich das Threads/Multiprocessing nicht wirklich was bringen. Denn die benchmark Werte sind auch nicht viel höher, als die GUI Werte...
Deswegen habe ich mal die ganze eigene Thread-Geschichte in die Tonne und die CPU nur per Tkinter after() laufen lassen.
Im Tkinter after() lasse ich immer x CPU op codes abarbeiten. Wie viele auf einmal berechne ich dynamisch, sodass ein Durchgang immer gleich lange dauert und die GUI auch benutzbar bleibt. Passender Commit: https://github.com/jedie/DragonPy/commi ... 64bb3660e9
Aktuell hab ich als target_burst_duration 0.1 Sek. eingestellt. So kann man ganz gut die GUI bedienun und der Wert wird auch eingehalte, egal ob CPython oder PyPy...
Sieht dann so aus (hier mit PyPy):

Wie man sehen kann, hat PyPy in 0.1Sek rund 750.000 Operationen der 6809 CPU ausgeführt. Allerdings erscheint mir der 35Mio. cycles/sek doch etwas hoch. Wobei das durchschnittlich 5,8 MPU Cycles pro Op gebraucht hat, was hin kommen kann, wenn man sich die Werte bei http://techheap.packetizer.com/processo ... n_set.html anschaut.
Komisch ist allerdings das der benchmark auf ganz andere Werte kommt. Deswegen hab ich nochmal getestet:
--loops 1 -> 2,4 Mio CPU Cycles/sec - dauer 0,60 Sec
--loops 2 -> 4,2 Mio CPU Cycles/sec - dauer 0,70 Sec
--loops 5 -> 8,7 Mio CPU Cycles/sec - dauer 0,85 Sec
--loops 10 -> 14 Mio CPU Cycles/sec - dauer 1,0 Sec
--loops 20 -> 20 Mio CPU Cycles/sec - dauer 1,5 Sec
--loops 50 -> 28 Mio CPU Cycles/sec - dauer 2,6 Sec
--loops 100 -> 33 Mio CPU Cycles/sec - dauer 4,5 Sec
--loops 250 -> 35 Mio CPU Cycles/sec - dauer 10 Sec
--loops 500 -> 37 Mio CPU Cycles/sec - dauer 19 Sec
--loops 1000 -> 38 Mio CPU Cycles/sec - dauer 39 Sec
PyPy braucht halt einige Durchgänge damit der JIT wirklich gute Ergebnisse liefert. Passt also doch alles ganz gut...
Deswegen habe ich mal die ganze eigene Thread-Geschichte in die Tonne und die CPU nur per Tkinter after() laufen lassen.
Im Tkinter after() lasse ich immer x CPU op codes abarbeiten. Wie viele auf einmal berechne ich dynamisch, sodass ein Durchgang immer gleich lange dauert und die GUI auch benutzbar bleibt. Passender Commit: https://github.com/jedie/DragonPy/commi ... 64bb3660e9
Aktuell hab ich als target_burst_duration 0.1 Sek. eingestellt. So kann man ganz gut die GUI bedienun und der Wert wird auch eingehalte, egal ob CPython oder PyPy...
Sieht dann so aus (hier mit PyPy):

Wie man sehen kann, hat PyPy in 0.1Sek rund 750.000 Operationen der 6809 CPU ausgeführt. Allerdings erscheint mir der 35Mio. cycles/sek doch etwas hoch. Wobei das durchschnittlich 5,8 MPU Cycles pro Op gebraucht hat, was hin kommen kann, wenn man sich die Werte bei http://techheap.packetizer.com/processo ... n_set.html anschaut.
Komisch ist allerdings das der benchmark auf ganz andere Werte kommt. Deswegen hab ich nochmal getestet:
--loops 1 -> 2,4 Mio CPU Cycles/sec - dauer 0,60 Sec
--loops 2 -> 4,2 Mio CPU Cycles/sec - dauer 0,70 Sec
--loops 5 -> 8,7 Mio CPU Cycles/sec - dauer 0,85 Sec
--loops 10 -> 14 Mio CPU Cycles/sec - dauer 1,0 Sec
--loops 20 -> 20 Mio CPU Cycles/sec - dauer 1,5 Sec
--loops 50 -> 28 Mio CPU Cycles/sec - dauer 2,6 Sec
--loops 100 -> 33 Mio CPU Cycles/sec - dauer 4,5 Sec
--loops 250 -> 35 Mio CPU Cycles/sec - dauer 10 Sec
--loops 500 -> 37 Mio CPU Cycles/sec - dauer 19 Sec
--loops 1000 -> 38 Mio CPU Cycles/sec - dauer 39 Sec
PyPy braucht halt einige Durchgänge damit der JIT wirklich gute Ergebnisse liefert. Passt also doch alles ganz gut...
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
So, nun ist v0.1.0 release raus: https://pypi.python.org/pypi/DragonPyEmulator
Leider ist DragonPy schon vergeben: https://pypi.python.org/pypi/DragonPy
Hab an der GUI ein wenig geschraubt und man kann nun die CPU beeinflussen:


Leider ist DragonPy schon vergeben: https://pypi.python.org/pypi/DragonPy

Hab an der GUI ein wenig geschraubt und man kann nun die CPU beeinflussen:

- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
Hab auf dem pyCologne ( http://pycologne.de/ ) Treffen gestern (10.9.2014) einen Vortrag über DragonPy gehalten...
Zwei Dinge fallen mir ein, die ich mitnehmen konnte:
DragonPy läuft mit CPython 3 wahrscheinlich langsamer, weil integer <=sys.maxint in 2 effizienter sind, dafür aber Integer in 3 einheitlicher.
Kurzer Test:
Aus der Docu: https://docs.python.org/3.1/whatsnew/3.0.html#integers
siehe auch: http://stackoverflow.com/questions/2104 ... t-and-long
Dann: bytearray wäre eigentlich das richtige für RAM/ROM. z.Z. nutzte ich dafür ja eine einfache Liste aus Integer mit dem byte wert.
Wobei meine Tests ja nicht so gut liefen, aber vielleicht habe ich bytearray auch einfach falsch genutzt, siehe: http://www.python-forum.de/viewtopic.ph ... ay#p263775
EDIT: Ne, also das scheint mir nichts zu bringen. Etwas schlechter Performance mit bytearray, dafür ein wenig Speicherplatz eingespart. Es bestätigen sich die Werte aus dem anderen Thread...
Zwei Dinge fallen mir ein, die ich mitnehmen konnte:
DragonPy läuft mit CPython 3 wahrscheinlich langsamer, weil integer <=sys.maxint in 2 effizienter sind, dafür aber Integer in 3 einheitlicher.
Kurzer Test:
Code: Alles auswählen
import sys
if sys.version_info[0] == 2:
# python 2.7
print(type(1)) # <type 'int'>
print(type(int(sys.maxint))) # <type 'int'>
print(type(int(sys.maxint+1))) # <type 'long'>
else:
# Python 3
print(type(1)) # <class 'int'>
print(type(int(sys.maxsize))) # <class 'int'>
print(type(int(sys.maxsize+1))) # <class 'int'>
siehe auch: http://stackoverflow.com/questions/2104 ... t-and-long
Dann: bytearray wäre eigentlich das richtige für RAM/ROM. z.Z. nutzte ich dafür ja eine einfache Liste aus Integer mit dem byte wert.
Wobei meine Tests ja nicht so gut liefen, aber vielleicht habe ich bytearray auch einfach falsch genutzt, siehe: http://www.python-forum.de/viewtopic.ph ... ay#p263775
EDIT: Ne, also das scheint mir nichts zu bringen. Etwas schlechter Performance mit bytearray, dafür ein wenig Speicherplatz eingespart. Es bestätigen sich die Werte aus dem anderen Thread...
@jens: Den Unterschied hatte ich doch schon mal erklärt: `bytearray` wird kompakter gespeichert, ist aber geringfügig langsamer (in CPython) weil dort immer der Zwischenschritt interne ”native” Zahl in Python `int` umsetzen, und umgekehrt, bei jedem Indexzugriff besteht. Ob das also das richtige für Deinen Emulator ist, hängt davon ab was Dir wichtiger ist, Speicherplatz oder Geschwindigkeit, beziehungsweise welche Python-Implementierung Du verwendest, weil PyPy bei `bytearray` natürlich mehr ”statische” Typinformationen hat als bei einer Liste in der zwar immer nur ganze Zahlen im Bereich 0 bis 255 gespeichert werden, aber jederzeit auch etwas völlig anderes kommen könnte und PyPy das zur Laufzeit natürlich zusätzlich prüfen muss.
Edit: Ich sehe nicht warum Python 3 mit dem Zusammenlegen von `int` und `long` zwingend langsamer sein muss. Grundsätzlich kann man doch intern genau das gleiche machen wie bei Python 2, also zwei Varianten von `int` implementieren beziegungsweise die bereits vorhandenen nutzen, nur diesmal ohne das nach aussen durch den Typ zu zeigen.
Edit: Ich sehe nicht warum Python 3 mit dem Zusammenlegen von `int` und `long` zwingend langsamer sein muss. Grundsätzlich kann man doch intern genau das gleiche machen wie bei Python 2, also zwei Varianten von `int` implementieren beziegungsweise die bereits vorhandenen nutzen, nur diesmal ohne das nach aussen durch den Typ zu zeigen.
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
Ja, ich habe deine Erklärung nicht vergessen. Auf weniger Speichernutztung muß ich IMHO nicht achten. Da ist alles im grünen Bereich...BlackJack hat geschrieben:@jens: Den Unterschied hatte ich doch schon mal erklärt: `bytearray` wird kompakter gespeichert, ist aber geringfügig langsamer (in CPython) weil dort immer der Zwischenschritt interne ”native” Zahl in Python `int` umsetzen, und umgekehrt, bei jedem Indexzugriff besteht. Ob das also das richtige für Deinen Emulator ist, hängt davon ab was Dir wichtiger ist, Speicherplatz oder Geschwindigkeit, beziehungsweise welche Python-Implementierung Du verwendest, weil PyPy bei `bytearray` natürlich mehr ”statische” Typinformationen hat als bei einer Liste in der zwar immer nur ganze Zahlen im Bereich 0 bis 255 gespeichert werden, aber jederzeit auch etwas völlig anderes kommen könnte und PyPy das zur Laufzeit natürlich zusätzlich prüfen muss.
Bin noch auf die Idee gekommen, mal array zu probieren, siehe: http://www.python-forum.de/viewtopic.ph ... 60#p264060
Die Überlegung war, das meine Speicher intern nur ints sind und die schneller sind als long...BlackJack hat geschrieben:Edit: Ich sehe nicht warum Python 3 mit dem Zusammenlegen von `int` und `long` zwingend langsamer sein muss. Grundsätzlich kann man doch intern genau das gleiche machen wie bei Python 2, also zwei Varianten von `int` implementieren beziegungsweise die bereits vorhandenen nutzen, nur diesmal ohne das nach aussen durch den Typ zu zeigen.
Ich finde es schon komisch, warum Python 3 langsamer ist. Ich meine, war nicht immer auch ein "Pro Python 3" Argument, das es schneller ist?!?
@jens: Python 3 ist bei den Benchmarks die für diese Aussage herangezogen werden schneller. Also bei einem Mix von verschiedenen Aufgaben. Konkret gibt es Sachen die schneller sind, und welche die langsamer sind. Solange der Unterschied nicht sehr stark ausfällt, wäre das für mich aber kein Grund das eine oder das andere zu bevorzugen. Python 3 ist nicht schneller als Python 2 in Grössenordnungen die tatsächlich relevant sind IMHO.
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
Jep, da sollte alles stehen.
Ist pure Python, man braucht keine externen Dinge, bis auf die ROM Dateien, die aber unter Linux automatisch mit einem shell Skript geholt werden können
EDIT: z.B.:
Wenn es Probleme gibt, einfach hier melden
Ist pure Python, man braucht keine externen Dinge, bis auf die ROM Dateien, die aber unter Linux automatisch mit einem shell Skript geholt werden können

EDIT: z.B.:
-> https://github.com/jedie/DragonPy/#readme# clone the repro:
~$ git clone https://github.com/jedie/DragonPy.git
# Alternative download as .zip: https://github.com/jedie/DragonPy/archive/master.zip
~$ cd DragonPy
# Download all ROM files:
~/DragonPy$ ./download_ROMs.sh
# Start Dragon 32
~/DragonPy$ python2 DragonPy_CLI.py --machine=Dragon32 run
Wenn es Probleme gibt, einfach hier melden

- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
Ich hab nun den IRQ branch gemerged.
Nun ist es möglich die Geschwindigkeit zu drosseln. Über ein "config" Menü kann man Parameter dazu einstellen:

Von einem "realtime" timeing ist es allerdings noch weit weg. Das wird auch IMHO nie richtig funktionieren, denke ich mal...
Nun ist es möglich die Geschwindigkeit zu drosseln. Über ein "config" Menü kann man Parameter dazu einstellen:

Von einem "realtime" timeing ist es allerdings noch weit weg. Das wird auch IMHO nie richtig funktionieren, denke ich mal...
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
v0.3.0 ist raus: https://pypi.python.org/pypi/DragonPyEmulator/0.3.0
Änderungen:
Änderungen:
Change Display Queue to a simple Callback
Reimplement Multicomp 6809 and SBC09
Many code refactoring and cleanup
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
DragonPy läuft auch in ReactOS:

1:1 -> http://www.jensdiemer.de/static/jensdie ... eactOS.png
Aber warum auch nicht?

1:1 -> http://www.jensdiemer.de/static/jensdie ... eactOS.png
Aber warum auch nicht?
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
Auch hier mal ein Status-Update...
Wegen der Froscon hab ich noch im Vorfeld einige Änderungen vorgenommen:
Die Installation ist nun einfacher, gerade für Windows.
Denn die nötigen ROM Dateien werden nun per Python runtergeladen und entpackt.
Vorher waren es einfacher .sh scripte, die unter Windows natürlich nicht funktionierten
Die Downloads werden nach wie vor per SHA Checksum geprüft.
Wie man es Installiert, siehe README:
Wer kann eigentlich mal das ganze unter MacOSX testen?!? Und eine Anleitung dazu einsenden?!?
Dann gibt es ja neu, die "starter GUI":

und aktuell ist der "Freeze" Bug behoben. Der trat hin und wieder auf, wenn man den "Speed Limit" also den Echtzeitmodus aktivierte...
Wegen der Froscon hab ich noch im Vorfeld einige Änderungen vorgenommen:
Die Installation ist nun einfacher, gerade für Windows.
Denn die nötigen ROM Dateien werden nun per Python runtergeladen und entpackt.
Vorher waren es einfacher .sh scripte, die unter Windows natürlich nicht funktionierten

Die Downloads werden nach wie vor per SHA Checksum geprüft.
Wie man es Installiert, siehe README:
- Linux: https://github.com/jedie/DragonPy#installation
- Windows: https://github.com/jedie/DragonPy#windows
Wer kann eigentlich mal das ganze unter MacOSX testen?!? Und eine Anleitung dazu einsenden?!?
Dann gibt es ja neu, die "starter GUI":

und aktuell ist der "Freeze" Bug behoben. Der trat hin und wieder auf, wenn man den "Speed Limit" also den Echtzeitmodus aktivierte...
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
Ja, da hast du sicherlich recht. Es gibt noch einiges an Optimierungspotential.jerch hat geschrieben:@jens:
Alles innerhalb Deiner self.get_and_call_next_op Methode ist "busy loop", d.h. jeder kleine Zusatzaufwand summiert sich auf. Und von da absteigend hast Du immernoch self.-Zugriffe drin, diese sind halt teurer als lokale. Was spricht dagegen, den äusseren Zustand per Parameter an den lokalen Namensraum mitzugeben (siehe memory-Übergabe im Bsp. oben)?
Bei Deiner Registerimplementation nutzt Du u.a. getter und setter-Methoden. Die sind deutlich teurer in CPython als der direkte lesende/schreibende Attributzugriff. Da die Registermanipulation die Hauptarbeit der CPU ist, wirkt sich das massiv aus.
Ich vermute, dass Du mit Umstellung auf lokale Namen und direkten Attributzugriff die Cyclerate der CPython-Version etwa verdoppelt könntest.
Ich hab mal mit https://github.com/ymichael/cprofilev nachgesehen:
Alles Werte nach: 225213360 function calls (225053689 primitive calls) in 489.819 seconds:
Ordered by: cumulative time
Code: Alles auswählen
ncalls tottime percall cumtime percall filename:lineno(function)
12541/11961 0.052 0.000 487.153 0.041 /usr/lib/python3.4/tkinter/__init__.py:1485(__call__)
8240 0.122 0.000 485.559 0.059 /home/jens/DragonPy_env/src/dragonpy/dragonpy/core/gui.py:241(cpu_interval)
8240 0.073 0.000 485.027 0.059 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:404(run)
8240 8.553 0.001 484.876 0.059 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:333(burst_run)
12512 0.063 0.000 483.947 0.039 /usr/lib/python3.4/tkinter/__init__.py:533(callit)
8255100 25.451 0.000 476.791 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:272(get_and_call_next_op)
8403598/8255100 20.331 0.000 371.806 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:288(call_instruction_func)
15549487 66.446 0.000 149.411 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:535(read_pc_byte)
2254891 7.468 0.000 54.801 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/instruction_call.py:537(relative_ea)
16584767 33.130 0.000 50.417 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:37(increment)
646331 2.206 0.000 42.781 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/instruction_call.py:136(direct_word_X_read16)
668298 2.237 0.000 38.780 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/instruction_call.py:365(indexed_A_read8)
1792270 11.384 0.000 36.726 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:592(get_ea_indexed)
2254891 9.770 0.000 35.719 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:756(get_ea_relative)
709969 3.198 0.000 29.866 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:1709(instruction_CMP16)
20645223/20638957 27.729 0.000 28.087 0.000 /home/jens/DragonPy_env/src/dragonpy/dragonpy/components/memory.py:191(read_byte)
27069837 27.168 0.000 27.168 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:98(set_flag)
1931097 6.406 0.000 26.688 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:561(get_ea_direct)
1010482 4.428 0.000 26.634 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:1517(instruction_LD8)
1897318 5.883 0.000 25.682 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:293(update_NZ_8)
26651989 25.038 0.000 25.038 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:31(get)
355525 1.643 0.000 22.798 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/instruction_call.py:50(direct_ea_read8_write8)
843845 4.508 0.000 22.251 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:329(update_NZVC_8)
21038722 22.019 0.000 22.019 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:81(set)
614495 2.060 0.000 20.639 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/instruction_call.py:455(indexed_ea_X)
357440 1.230 0.000 20.088 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/instruction_call.py:289(immediate_A_read8)
41281/40419 1.656 0.000 19.682 0.000 {method 'call' of 'tkapp' objects}
734403 4.039 0.000 19.604 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:335(update_NZVC_16)
1 0.000 0.000 19.125 19.125 /home/jens/DragonPy_env/src/dragonpy/basic_editor/editor.py:189(command_load_file)
698567 2.273 0.000 19.040 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:712(get_m_indexed)
...
Code: Alles auswählen
ncalls tottime percall cumtime percall filename:lineno(function)
15549487 66.446 0.000 149.411 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:535(read_pc_byte)
16584767 33.130 0.000 50.417 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:37(increment)
20645223/20638957 27.729 0.000 28.087 0.000 /home/jens/DragonPy_env/src/dragonpy/dragonpy/components/memory.py:191(read_byte)
27069837 27.168 0.000 27.168 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:98(set_flag)
8255100 25.451 0.000 476.791 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:272(get_and_call_next_op)
26651989 25.038 0.000 25.038 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:31(get)
21038722 22.019 0.000 22.019 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:81(set)
8403598/8255100 20.331 0.000 371.806 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:288(call_instruction_func)
14943248 14.632 0.000 14.632 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:101(get_flag)
1792270 11.384 0.000 36.726 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:592(get_ea_indexed)
2254891 9.770 0.000 35.719 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:756(get_ea_relative)
2885523 9.441 0.000 15.200 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:197(set_N8)
2893451 9.213 0.000 14.940 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:177(set_Z8)
2068990 8.881 0.000 15.147 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:270(clear_NZV)
8240 8.553 0.001 484.876 0.059 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:333(burst_run)
1578248 8.419 0.000 14.731 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:276(clear_NZVC)
2254891 7.468 0.000 54.801 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/instruction_call.py:537(relative_ea)
1931097 6.406 0.000 26.688 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:561(get_ea_direct)
1897318 5.883 0.000 25.682 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:293(update_NZ_8)
1684193 5.427 0.000 8.761 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:187(set_Z16)
1661084 5.426 0.000 9.744 0.000 /home/jens/DragonPy_env/src/dragonpy/dragonpy/components/memory.py:227(read_word)
843845 4.508 0.000 22.251 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:329(update_NZVC_8)
1010482 4.428 0.000 26.634 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:1517(instruction_LD8)
2428999 4.375 0.000 5.602 0.000 /home/jens/DragonPy_env/src/dragonpy/dragonpy/components/memory.py:242(write_byte)
734403 4.039 0.000 19.604 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:335(update_NZVC_16)
1233863 3.955 0.000 6.414 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:2116(instruction_BNE)
1069682 3.515 0.000 5.663 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:207(set_N16)
919873 3.242 0.000 5.041 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:237(set_V8)
709969 3.198 0.000 29.866 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:1709(instruction_CMP16)
2517144 3.182 0.000 3.182 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/utils/bits.py:20(is_bit_set)
...
Code: Alles auswählen
ncalls tottime percall cumtime percall filename:lineno(function)
12541/11961 0.052 0.000 487.153 0.041 /usr/lib/python3.4/tkinter/__init__.py:1485(__call__)
8240 0.122 0.000 485.559 0.059 /home/jens/DragonPy_env/src/dragonpy/dragonpy/core/gui.py:241(cpu_interval)
8240 0.073 0.000 485.027 0.059 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:404(run)
8240 8.553 0.001 484.876 0.059 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:333(burst_run)
12512 0.063 0.000 483.947 0.039 /usr/lib/python3.4/tkinter/__init__.py:533(callit)
8255100 25.451 0.000 476.791 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:272(get_and_call_next_op)
8403598/8255100 20.331 0.000 371.806 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:288(call_instruction_func)
15549487 66.446 0.000 149.411 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:535(read_pc_byte)
2254891 7.468 0.000 54.801 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/instruction_call.py:537(relative_ea)
16584767 33.130 0.000 50.417 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:37(increment)
646331 2.206 0.000 42.781 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/instruction_call.py:136(direct_word_X_read16)
668298 2.237 0.000 38.780 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/instruction_call.py:365(indexed_A_read8)
1792270 11.384 0.000 36.726 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:592(get_ea_indexed)
2254891 9.770 0.000 35.719 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:756(get_ea_relative)
709969 3.198 0.000 29.866 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:1709(instruction_CMP16)
20645223/20638957 27.729 0.000 28.087 0.000 /home/jens/DragonPy_env/src/dragonpy/dragonpy/components/memory.py:191(read_byte)
27069837 27.168 0.000 27.168 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:98(set_flag)
1931097 6.406 0.000 26.688 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:561(get_ea_direct)
1010482 4.428 0.000 26.634 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:1517(instruction_LD8)
1897318 5.883 0.000 25.682 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:293(update_NZ_8)
26651989 25.038 0.000 25.038 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:31(get)
355525 1.643 0.000 22.798 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/instruction_call.py:50(direct_ea_read8_write8)
843845 4.508 0.000 22.251 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:329(update_NZVC_8)
21038722 22.019 0.000 22.019 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:81(set)
614495 2.060 0.000 20.639 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/instruction_call.py:455(indexed_ea_X)
357440 1.230 0.000 20.088 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/instruction_call.py:289(immediate_A_read8)
41281/40419 1.656 0.000 19.682 0.000 {method 'call' of 'tkapp' objects}
734403 4.039 0.000 19.604 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu_utils/MC6809_registers.py:335(update_NZVC_16)
1 0.000 0.000 19.125 19.125 /home/jens/DragonPy_env/src/dragonpy/basic_editor/editor.py:189(command_load_file)
698567 2.273 0.000 19.040 0.000 /home/jens/DragonPy_env/src/mc6809/MC6809/components/cpu6809.py:712(get_m_indexed)
...