Lowlevel

Lowlevel => OS-Design => Thema gestartet von: clemensoft am 20. December 2004, 17:53

Titel: Timer-Interrupt
Beitrag von: clemensoft am 20. December 2004, 17:53
Also, ich brauche einen Interrupt, der in regelmäßigen Abständen vom Prozessor aufgerufen wird. Ich kenne nur 0x1C, der 18,2 mal pro Sekunde aufgerufen wird, der ist mir zu langsam. Bei Win***s gibt es doch auch so eine Timer-Funktion mit 1000 Ticks pro Sekunde, und wenn ich mich recht entsinne, gibt es im PC einen Baustein names Performance Counter mit einem Quarzkristall...
Titel: Timer-Interrupt
Beitrag von: joachim_neu am 20. December 2004, 17:55
interessiert mich auch! allerdings is 1000 switchs pro sekunde für MultiTasking a bisserl schnell, oda? ;-)
Titel: Timer-Interrupt
Beitrag von: clemensoft am 20. December 2004, 18:00
Nehmen wir mal an, jeder Task bekommt 100 ticks. Dann hat er genügend Zeit zum Rechnen, und nach 100t kommt dann der nächste dran. Das kann man so ausweiten, dass der Kernel 200 t bekommt, ein Microsoft-Programm 1t, Open-Source-Programme eine Sekunde...
Titel: Timer-Interrupt
Beitrag von: TeeJay am 20. December 2004, 18:32
Also soweit ich weiß kann man den TImerchip auch umprogrammieren.
Sprich das er öfter als 18,2 mal pro Sek aufgerufen wird.

Und in der Tat gibt es einen Befhel "rtdsc" oder so.
Der Prozessor erhöht jede Mikrosekunde den Wert darin, wenn ich mich recht erinnere.
Man kann damit also Funktionen a la GetTickCount() von WIndows nachbauen.

Der Befehl kann auch in einem Ring3 Programm benutzt werden.
Titel: Timer-Interrupt
Beitrag von: clemensoft am 20. December 2004, 18:44
Er heißt rdtsc, aber das hilft mir leider nicht. Das Teil muss selbstständig einen int auslösen, damit die gerade arbeitenden Programme ungestört arbeiten können. Das würde unglaublich viel Rechenzeit kosten, die ganze Zeit rdtsc auszuführen!
Titel: Timer-Interrupt
Beitrag von: joachim_neu am 20. December 2004, 20:08
du übersiehst bei deinem alle-1-ms-tick-int was! und zwar, dass das ausführen des int schon länger als 1 ms dauern würde, und sich das so überschlägt. und irgendwann ist dein stack zu groß, weil du nimmer zum iret des ints kommst! deswegen ist das mit den 100 ticks zwar praktisch, allerdings ist die vergleichroutine zu lange, als dass sie in 1 tick passt!
Titel: Timer-Interrupt
Beitrag von: clemensoft am 20. December 2004, 20:14
OK, aber mit 50 ms, da muss es doch was geben! Ich kann doch nicht ständig den Timestamp abfragen! Ich habe etwas dagegen, Billy Gates nachzuahmen
Titel: Timer-Interrupt
Beitrag von: joachim_neu am 20. December 2004, 20:41
*g* 50ms reicht natürlich! ich meinte, dass eine Millisekunde net reich!
Titel: Timer-Interrupt
Beitrag von: Jidder am 21. December 2004, 13:38
Zitat von: joachim_neu
du übersiehst bei deinem alle-1-ms-tick-int was! und zwar, dass das ausführen des int schon länger als 1 ms dauern würde, und sich das so überschlägt. und irgendwann ist dein stack zu groß, weil du nimmer zum iret des ints kommst! deswegen ist das mit den 100 ticks zwar praktisch, allerdings ist die vergleichroutine zu lange, als dass sie in 1 tick passt!


Während du in einer ISR bist, kannst du die Ints deaktivieren (wird sogar automatisch bei der Auslösung des Ints gemacht) und schon bist du das Problem los. Um die Hardware-Ints wieder zu aktivieren musst du ein EOI (End of Interrupt) an den PIC (Programmable Interrupt Controller) senden.

RDTSC ist der Befehl um den Timestamp Counter (TSC) auszulesen. Dieses 64 bit Register wird bei jedem Takt um 1 erhöht. Also bei einem 200 MHz Prozessor wird er um 200.000.000 pro Sekunde erhöht. Wenn man die Prozessorfrequenz weiss kann man mit diesem Register viel genauer die Zeit messen, als mit den anderen Standardmöglichkeiten. Der TSC hat halt keine "Interruptanbindung" ...

Hier mal der Code, den ich verwende um bei meinem OS den PIT (Programmable Interrupt Timer) umzuprogrammieren:
#define PIT_FREQ 1193181 // die Standardfrequenz des PIT
#define FREQ 20 // die Frequenz die wir haben wollen

void setup_pit()
{
int counter; // nur eine temporäre variable ...

counter = PIT_FREQ / FREQ; // (achtung: bei der wahl der frequenz die (ab)rundung bei division beachten! also nicht wundern wenn der timer irgendwann "vor-" oder "nachgeht")

// achtung bei mir ist es outb(value, port); !!!!!
outb(0x34, 0x43); // control word schreiben
outb(counter & 0xFF, 0x40); // an den Counter 0 die neue Frequenz schreiben
outb(counter >> 8, 0x40);   // --------- " ----------

// todo: interrupt handler installieren
}
Titel: Timer-Interrupt
Beitrag von: joachim_neu am 21. December 2004, 13:44
@Pork: ne! denn soweit ich weiß, kommt ein interrupt, der wartet gleich zum zuge, wenn das andere sich abmeldet. das heißt also, dass entweder direkt nach dem EOI, also noch vor dem iret oder nach dem iret das int wieder aufgerufen wird. man hat also keine zeit für den task, weil gleich wieder geswitcht wird. allerdings denke ich, dass 18,2 switches schon reichen... und was ist der PIT? wird damit umgeschrieben, wie oft das Int 0x00 aufgerufen wird?

mfg

J!N
Titel: Timer-Interrupt
Beitrag von: Jidder am 21. December 2004, 13:51
Zitat von: joachim_neu
@Pork: ne! denn soweit ich weiß, kommt ein interrupt, der wartet gleich zum zuge, wenn das andere sich abmeldet. das heißt also, dass entweder direkt nach dem EOI, also noch vor dem iret oder nach dem iret das int wieder aufgerufen wird.

jo aber erst das iret aktiviert die interrupts wieder. erst wenn das iret das interrupt flag setzt kann wieder ein interrupt auftauchen.

Zitat
man hat also keine zeit für den task, weil gleich wieder geswitcht wird. allerdings denke ich, dass 18,2 switches schon reichen...

ich würd sagen nein. wenn du z.b. ein os mit 30 offenen anwendungen hast, dann kannst du ja mit bloßem auge sehen welches programm gerade am zug ist und gerade arbeitet.

Zitat
und was ist der PIT? wird damit umgeschrieben, wie oft das Int 0x00 aufgerufen wird?

nope. der PIT ist das teil was den IRQ 0 auslöst. und den kann man entsprechend programmieren wie oft er das tun soll. (der PIT macht auch noch mehr und was das genau ist verrät google.)
Titel: Timer-Interrupt
Beitrag von: Roshl am 21. December 2004, 15:17
Mein PIT ist auf 250 Hz programmiert, also 250 Switches pro Sekunde.
1ms ist viel, sogar sehr viel. Der Taskhandler der eine Milliesekunde muss wirklich äusserst schlecht gecodet sein. Auf einem 1MHZ prozessor (MHZ nicht GHZ) hat man 1000000 Takte durch 1000 (1ms) wären das 1000 Takte, und solange sollte kein Taskhandler brauchen, im worstcase hat meiner vielleicht wenns sehr hoch kommt 200-250. Und da wir heute im Bereich von     mehreren GHZ sind, ist 1ms so extrem viel^^  1GHZ->1Millionen Takte pro Task pro Sekunde, wenn wir bei 1000Hz für den PIT sind. Die Reelle Rechenzeit für den Task hängt also nur von der  PIT-Frequenz und von der Rechengeschwindigkeit der CPU ab, der Taskhandler fällt da kaum ins Gewicht.

PS: 1000 Switches ist nicht sonderlich viel, wenn man daran denkt das Videoschnitt, MP3-Audio, 3D-Rendering nebeneinanderlaufen können ohne irgendwo zu stocken!  1000 ist eher so normal^^
PPS: Soll ich noch mehr Rechnereien machen?;)
Titel: Timer-Interrupt
Beitrag von: TeeJay am 21. December 2004, 17:18
Naja das mit den 1000 Switches ist etwas sehr pauschal ausgedrückt.
So viele Tasks hat man ja kaum am laufen.
Und dann kommt ja auch noch zum tragen mit welcher Priorität der Task läuft.

10 ms Timeslice soll sehr oft benutzt werden wie ich gelesen habe. Und man muss sich mal überlegen das damit 100 Tasks pro Sekunde laufen könnten. Und selbst wenn man so viele Tasks am laufen hat, sind die meisten die größte Zeit eh inaktiv.
Titel: Timer-Interrupt
Beitrag von: Roshl am 22. December 2004, 13:06
Es ging hauptsächlich darum das joachim behauptet das 18,2 ausreichen und sich die IRQ sonst überschneiden würden, was purer blödsinn ist. Ausserdem diente 1000 nur als theoretisches Rechenbeispiel.
Titel: Timer-Interrupt
Beitrag von: joachim_neu am 22. December 2004, 13:16
Zitat von: Roshl
Es ging hauptsächlich darum das joachim behauptet das 18,2 ausreichen und sich die IRQ sonst überschneiden würden, was purer blödsinn ist. Ausserdem diente 1000 nur als theoretisches Rechenbeispiel.


achtung! du hast da was falsch verstanden! ich sagte bei 1000 aufrufen pro sekunde würden sie sich (zumindest bei mir) überschneiden! und warum sollten 18,2 net ausreichen?
Titel: Timer-Interrupt
Beitrag von: clemensoft am 22. December 2004, 14:46
Das menschliche Auge sieht ca. 24 Bilder pro Sekunde. Das Heißt also, damit dein Auge das Multitasking nicht bemerkt, muss JEDER Task mindestens 24 mal pro Sekunde ablaufen, was bei 3 Tasks schon 72 Mal pro Sekunde wechseln.
Titel: Timer-Interrupt
Beitrag von: TeeJay am 22. December 2004, 17:39
Also das mit den Bildern und dem Auge hat beim Taskwechsel nicht wirklich eine Rolle *G*

Wenn du Musik decodierst (mp3 z.B.) dann muss das nicht 24 mal pro sekunde der Task laufen. Er muss nur so oft laufen, das immer für die jeweils nächsten paar Sek die Musik decodiert wird, damit man keine Aussetzer hat.....
Titel: Timer-Interrupt
Beitrag von: joachim_neu am 22. December 2004, 19:34
er hat recht, wenn jedes programm sein fenster zeichnen muss, was er warscheinlich so meint. allerdings ist es ja so, dass man net wie in einem film immer wieder die fenster aktualisiert, sondern nur dann, wenn sie sich geändert haben.
Titel: Timer-Interrupt
Beitrag von: Roshl am 25. December 2004, 12:04
18,2 reicht aber definitiv nicht. Hättest du zum Beispiel nen Microkernel (so wie ich einen bastle) dann hast du einen Task der alle Aufgaben in Sachen Video übernimmt, die anderen Tasks melden dem nur was sie wollen. So bei 8 Tasks (ausser dem Videotask) würde der somit nur 2 mal pro Sekunde drankommen, also könnte das bild da nur 2 mal pro Sekunde gepinselt werden. Counter-Strike mit 2 Frames/s? Na supi:P
Bei einem Monokerlen mag das ja vielleicht anders aussehen, je nach Implementierung von dem ganzen. Hier reicht es halt nicht zu sagen RM PM usw. sondern das OS-Kernel-Design ist da wichtig.
Titel: Timer-Interrupt
Beitrag von: joachim_neu am 25. December 2004, 13:41
ich weiß, dass 18,2 da net reichen. bei mir ist es allerdings so, dass ich einen buffer hab, und ein int, dass den buffer überspielt. dadurch wird das nur nötig, wenn sich etwasverändert. sonst net. außerdem kann man bei mir alle anderen tasks pausieren, wenn man max. leistung braucht.
Titel: Timer-Interrupt
Beitrag von: Roshl am 25. December 2004, 14:28
Ich sag ja alles eine Frage der Implementierung
Titel: Timer-Interrupt
Beitrag von: TeeJay am 25. December 2004, 17:51
Counterstrike benutzt ja auch DX. Und da pinselt das direkt über die Hardware und nicht über nen Task :)

Versteift euch aber nicht einfach so auf die Anzahl der Taskwechsel.

Die meistens Tasks sind die größte Zeit idle. Und dann kommen ja auch noch Prioritätsklasse hinzu.

18,2 mögliche wechsel pro Sekunde ist klar zu wenig.
Aber man muss auch nicht 1000 und mehr haben. Der Timerint kann ja 1000 mal pro Sek aufgerufen werden. Aber das heisst nicht das damit auch 1000 mal pro Sek der task gewechselt werden muss.

Der Timerinterupt ist ja ursprünglich nicht umbedingt dazu gedacht gewesen für das Task-Switchen verantwortlich zu sein. In zeiten des Preemptiven Taskwechselns ist er dafür passender Weise "missbraucht" worden :)
Titel: Timer-Interrupt
Beitrag von: Roshl am 26. December 2004, 12:05
Ich hab 250 Mal nen Taskhandleraufruf, je nach Priorität wird dann gewechselt oder eben noch einmal Zeit gegeben^^.
Counterstrike läuft ja auch meistens auf Monolithischen Kerneln;)
Der Sinn von Microkerneln ist ja alles gesondert zu machen und damit die Sicherheit zu erhöhen.
Titel: Timer-Interrupt
Beitrag von: TeeJay am 26. December 2004, 13:48
Das ist nicht korrekt ROshi :)

Windows2k/XP benutzen einen Microkernel.
Es stehen für jede Verwaltungsaufgabe sogenannte Server bereit. Und das sind im Grunde auch nur Tasks die die arbeit übernehmen.

Aber trotzdem ist DirectX in der Hinsicht eine gute erweiterung.
Weil gerade Spiele etc die DirectX nutzen laufen meist eh exklusiv im Fordergrung und warum sollte man diesen dann nicht den direkten Zugriff auf die Hardware geben? Erhöht die Geschwindigkeit enorm und lässt den Verwaltungsaufwand der Server weg.

Aber es muss jeder für sich entscheiden wie er sein OS aufbauen will :)
Titel: Timer-Interrupt
Beitrag von: Another Stupid Coder am 26. December 2004, 14:36
Tut mir leid, wenn ich hiermit mal kurz komplett OT gehe, aber das WindowsXP ein richtiger Microkernel ist, wage ich zu bezweifeln. Nachdem, was ich so darüber gelesen habe, würde ich es vielmehr als "microkernel ähnlich" bezeichnen.
Titel: Timer-Interrupt
Beitrag von: Roshl am 26. December 2004, 14:58
Sehe ich auch so, Win XP usw ist definitiv kein vollständiger Microkernel, es sind lediglich Ansätze davon vorhanden. Vieles bleibt Monolithisch.
Das es sind macht einigen Anwendungen dann direkten Hardwarezugriff zugeben sehe ich ja ein, ich werde das ja auch so machen.^^
Titel: Timer-Interrupt
Beitrag von: joachim_neu am 26. December 2004, 15:05
über was ihr euch so streitet ;-)
ich fänds/finds am besten (und so werd ich es machen), dass jeder task eine stufe von 0 bis 2 hat (0=system,1=hardwarenahe,sowas, wie ICQ,2=normales proggy) und wenn dann ein task im vordergrund läuft, dann werden alle tasks auf ebene 2 außer ihm auf "pausiert" geschaltet, sodass nurnoch die wichtigen system-dienste und die sachen, die auf ports aus sind laufen. das erhöht die rechenzeit für den task (z.B. CounterStrike), außerdem können programme, die ja auf etwas warte, wie z.B. einen eingang an port xyz den ja in ner schleife auslesen, und wenn da nix drinne ist gleich wieder mit dem intaufruf zurückgeben, oder aber sich einen neuen task machen, den mit dem int verknüpfen, dass aufgerufen wird, wenn an dem port was ankommt, und sich dann schlafen legen, und das int weckt sie dann wieder. das spart mehr zeit. denn, was will ich mit einem AKTIVEN word, wenn ich CounterStrike zocke, dann benutz ich es ja net, und dann kann ich es auch gleich pausieren, denn das wartet ja auf nix, während ich aber vielleicht trotzdem noch in ICQ verfügbar sein will...

mfg

JN!
Titel: Timer-Interrupt
Beitrag von: TeeJay am 26. December 2004, 17:14
Joachim deine Idee hat einen kleinen Schönheitsfehler.

Angenommen du pausierst alle anderen Tasks, dann könnten Tauschbörsen, ICQ etc im Hintergrund garnicht weiterlaufen während du zockst....ob das so vom User gewollt ist?

Es würde genügen den Task für das Zeichnen der Fenster zu pausieren, weil das ja in dem Moment in dem ein Task im Vollbild läuft eh fürn Fuss wäre, wenn im Hintergrund Fenster neu gezeichnet werden würden.
Abgesehen davon das es sich mit jenem ins Gehege kommen würde, da es ja selbst über eine API mit der hardware kommuniziert.
Titel: Timer-Interrupt
Beitrag von: joachim_neu am 26. December 2004, 17:25
achtung: fehler!!!  ich hab gesagt, dass ich nur proggys pausiere, wie z.B. Word, die auf ebene 2 laufen. ICQ und Co. würden auf ebene 1 laufen, und die werden nicht abgeschaltet!
Titel: Timer-Interrupt
Beitrag von: GhostCoder am 26. December 2004, 18:32
Hiho,

@joachim_neu:
Wenn Word im Hintergrund ist, macht es doch sowieso nichts...
Es wartet auf Nachrichten, und währenddessen wird es vom Kernel nicht in Scheduling einbezogen. ICQ hängt ja auch nur so rum, bis ein Timer ne Message schickt, das z.B. der Onlinestatus abgefragt werden soll.

Also kriegt sowieso nur jedes Programm Rechenzeit, wenn es sie benötigt...

MfG GhostCoder
Titel: Timer-Interrupt
Beitrag von: TeeJay am 26. December 2004, 19:14
Jedenfalls würde ich das nicht so pauschal abgrenzen.

Daher wenn ein Programm exklusiv im Fordergrund (Vollbild) ist, einfach die NeuZeichen-Messages der anderen Programm solange auf die lange Bank schieben bis das exklusive Programm beendet wird, oder vom Vollbild runtergeht.