Beiträge anzeigen

Diese Sektion erlaubt es dir alle Beiträge dieses Mitglieds zu sehen. Beachte, dass du nur solche Beiträge sehen kannst, zu denen du auch Zugriffsrechte hast.


Nachrichten - erik.vikinger

Seiten: 1 ... 62 63 [64]
1261
OS-Design / Re: OS für Plattform mit Segmentierung
« am: 14. August 2009, 19:31 »
Hallo,


entschuldige mein Delay, aber ich wollte mich erst mal etwas genauer in das Thema TLS einlesen. Interessant war da vor allem der Artikel in der englischen Wikipedia und dessen externe Links. http://en.wikipedia.org/wiki/Thread-local_storage

Ich bin z.B. davon ausgegangen das ein Pointer in den TLS immer auf den TLS des aktuellen Threads verweisen soll und nicht auf den TLS eines anderen Threads oder das der TLS selber in dem Segment, auf x86 eben GS, steckt.
In Wirklichkeit gibt es nur einen Thread-Spezifischen Pointer auf eine jeweilige Struktur (im normalen Adress-Raum) die den TLS für alle Threads auf die gleiche Weise aber mit verschiedenem Inhalt beschreibt. Sieht insgesamt einigermaßen kompliziert aus. Gleich im ersten externen Link des Wikipedia-Artikels wird das für einige Plattformen konkret beschrieben und ich hab jetzt auch eine Idee wie ich das für mein OS umsetzen möchte. Wenn es wirklich demnächst in den C/C++-Standard rein kommt wird wohl früher oder später die Notwendigkeit auftauchen das zu unterstützen wenn ich mal ein Programm portieren möchte.


Da Du die Stacks ansprichst, wie machst man das eigentlich in einem Flat-Memory-System?
Die einzelnen Stacks der verschiedenen Threads müssen ja hintereinander in den einen  Adress-Raum des Tasks gelegt werden, oder irre ich da? Wie sieht das aus wenn ein Thread dann mehr Stack braucht als Platz bis zum nächsten Stack eines anderen Threads ist? Merkt das das OS eigentlich zuverlässig?
Für die Segmentierung hab ich mir gedacht ich erstelle für jeden Thread ein eigenes lokales Segment mit einer kleinen Anfangsgröße und wenn der Stack wächst, auf meiner Plattform übrigens hin zu den höheren Adressen bzw. Offsets, wird das Segment vom OS vergrößert (eventuell nur bis zu einem definiertem Maximum). Beim Zugriff auf Offsets die das Stack-Segment-Limit überschreiten wird eine Exception ausgelöst aber vom OS speziell behandelt da ja wachsender Stack normal ist. Falls das Segment an seiner momentanen Position im Linearen-Adress-Raum keinen Platz mehr hat muss es eben schnell umgelegt werden. Ob ich ein Schrumpfen, wenn das OS beobachtet das der Stack eine Weile lang wieder kleiner ist, implementiere weis ich noch nicht, währe aber ne nette Idee.


Grüße
Erik
1262
OS-Design / Re: Planung der Kernelentwicklung
« am: 14. August 2009, 18:18 »
Hallo,


plane nicht zu viel, die meisten Pläne erweisen sich während der eigentlichen Ausführung als unrealistisch (sagt nicht nur meine Berufspraxis).

Versuche ein grobes Konzept-Papier (das darf ruhig auf echtem Papier, A3 oder größer, sein) und verfeinere das ganze Etappenweise währen der Umsetzung.
Nützlich ist auch eine hierarchische Dokumentation :
- grobes Konzept-Papier (muss nicht alle Details enthalten)
- einzelne Module sollten sicher noch mal einzeln und etwas detaillierter dargestellt werden
- in jeden Verzeichnis eine "Info.txt" welche grob umreißt worum es geht und welche Funktionalität sich in welcher Datei befindet, hier sollten auch Zusammenhänge erklärt werden die nicht im Quell-Code offensichtlich sind
- saubere Dokumentation im Quell-Code, die sollte immer den tatsächlichen Ist-Stand möglichst genau beschreiben. Offene Baustellen sollten als solche zu erkennen sein.
- Ideen und andere TODOs können in eine "TODO.txt".

Was APIs angeht sollten die Erfordernisse im Vordergrund stehen, implementiert werden muss das was gebraucht wird. Meistens kristallisiert sich während der Umsetzung erst heraus was Sinnvoll ist und was nicht.

Habe vor allem auch den Mut die Dinge die sich als Blöd erwiesen haben umzuwerfen und es noch mal ordentlich zu machen. Dumme Krücken durch ein Projekt zu schleifen kosten immer mehr Kraft als es noch mal neu aufzusetzen.


Grüße
Erik
1263
OS-Design / Re: OS für Plattform mit Segmentierung
« am: 12. August 2009, 21:27 »
Hallo,


Zitat
Die Basisadresse ist da.
Mehr aber auch nicht, also doch nur "Segment-Imitatoren".


Zitat
Wie kommst du auf das schmale Brett, auf diesen Architekturen könnte man keinen TLS implementieren?
Nunja das wird wohl schon irgendwie gehen. Das einzigste was mir dafür einfällt ist eine Page-Table pro Thread und nicht nur eine pro Task.
Die genanten Architekturen, so wie fast alles was zwischen 0 und 1 unterscheiden kann, haben alle (Okay der PowerPC hat wohl sowas ähnliches wie Segmentierung aber nichts berauschendes und ob der Itanium in seiner HW-x86-Emulation den 386-PM komplett unterstützt weis ich nicht) "nur" Paging und auf allen genanten (und etlichen mehr) läuft Linux und noch ne Reihe anderer Embedded/Real-Time-OS welche das Paging genau so benutzen wie die meisten OSdever hier es auch tun.

Alles was im OS-Bereich Rang und Namen hat basiert auf den selben "altgedienten" bzw. "altbewährten" Speicherverwaltungskonzepten. Wird Zeit das da mal was neues kommt. :wink:


Grüße
Erik
1264
OS-Design / Re: OS für Plattform mit Segmentierung
« am: 12. August 2009, 12:43 »
Hallo,


Zitat
Naja, der Bedarf, das Linkregister auf dem Stack zu parken, entsteht sobald eine Funktion eine weitere Funktion aufrufen will.
Ja, aber man muss es nicht sofort nach dem Einsprung in eine Funktion tun sondern kann es auf später, kurz vor dem Aufruf der Unterfunktion, erledigen. Damit ist die Rücksprungadresse nicht so lange auf dem Stack und daher weniger, eventuell gar nicht, angreifbar. Ob heutige Compiler sowas können weiß ich aber nicht.
Außerdem gibt es viele kleine Funktionen die gar keine Unterfunktionen aufrufen, die sparen sich mindestens 2 Speicherzugriffe.


Zitat
Es wird afaik über Segmentation erreicht.
:-D

Zitat
als auch unter x64
Da bleiben ja nur FS und GS als verstümmelte "Segment-Imitatoren" übrig. Viel Spaß.

Was ist dann eigentlich mit ARM, ALPHA, AVR32, MIPS, Microplace, Itanium, PowerPC ...... ??
Ob die dann wohl nicht mehr C++ kompatibel sind?


Grüße
Erik
1265
OS-Design / Re: OS für Plattform mit Segmentierung
« am: 11. August 2009, 20:46 »
Hallo,


einen Punkte hatte ich vergessen:

Zitat
Zitat
http://www.heise.de/newsticker/meldung/64624
Das Tool, welches in der zweiten Hälfte des Artikels genannt wird, hätte auf einem System mit Segmentierung deutlich weniger Chancen was passendes zusammen zu suchen.
Warum? Ich sehe das ehrlich gesagt nicht, aber ich hab kA von den Details der dort verwendeten Technik.
Entschuldige, da hab ich was unklar erklärt. Das ist weniger ein Vorteil durch die Segmentierung, auch wenn die viele der "nützlichen" Code-Fragmente seltener macht, sondern eher ein Problem von x86 (auch im 64Bit-Modus). Bei x86 kann jede beliebige Bytefolge als Code betrachtet werden, es gibt kein Alignment. Bei typischen RISC-CPUs sind Opcodes immer, auf z.B. 32Bit, ausgerichtet. Das macht solche Zufalls-Code-Sequenzen deutlich seltener. Meine Plattform geht sogar noch weiter, in Richtung Itanium, und verwendet 128Bit (ausgerichtete) Code-Wörter die immer mehrere Befehle, an krummen Bit-Offsets, enthalten. Es dürfte also extrem unwahrscheinlich sein (eigentlich unmöglich) das man Befehle findet die gar nicht bewusst vom Compiler erzeugt wurden.
Auf einer Plattform mit Segmenten benötigt man mehr zusammenhängende Befehle um einen FAR-Pointer zu laden und insbesondere der Befehl zum laden eines Selectors in ein bestimmtes Segmentregister ist recht selten. Ich kann mir vorstellen das so eine Suche nach ausreichend geeigneten Code-Sequenzen, die für einen Angriff ohne eigenen eingeschleusten Code benötigt werden, selbst bei großen Programmen erfolglos bleibt.
Hinzu kommt das x86 die Rücksprungadresse zum Aufrufer bei einem Call immer auf den Stack legt, viele andere CPUs legen denn in ein spezielles "Link-Register" und das wird nur bei Bedarf auf den Stack gesichert. Man kommt also deutlich schwieriger an eine Rücksprungadresse, ist aber trotzdem nicht unmöglich.
All diese Punkte zusammen können den Nutzwert der address layout randomization auf meiner Platform wahrscheinlich steigern, ob es reicht um dafür Speicher zu opfern werde ich sehen.


Grüße
Erik
1266
OS-Design / Re: OS für Plattform mit Segmentierung
« am: 11. August 2009, 19:51 »
Hallo,


Zitat
Alles das gleiche und dann doch irgendwie nicht.
Ja, dieses Phänomen kann ganz schön verwirren. Aber in diese Richtung will ich ja nicht.


Zitat
Ohne Paging bist du darauf angewiesen, dass der Speicher den du für einen Task bzw. dessen Segmente brauchst, jeweils an einem Stück zur Verfügung steht
Ja, das stimmt, ist aber kein unüberwindbares Problem.

Zitat
Als kaputt würde ich z.B. eine Implementierung bezeichnen die Bestehende Segmente im Speicher verschiebt um doch noch genügend große Speicherblöcke zu erhalten.
Warum? Das ist für mich gerade der Reiz. Durch die Verwendung der Segmente ist eine Live-Defragmentierung des linearen Adress-Raums keine Hexerei mehr. Genau das möchte ich implementieren. Wenn man dazu das Paging benutzt kann man das sogar beliebig langsam im Hintergrund laufen lassen und die Programme können davon nichts bemerken, noch nicht mal Performance-Einbußen da der Defragmentierer ja ein Low-Priority-User-Mode-Task ist der keine IRQs bzw. Real-Time-Tasks blockiert. Was daran "kaputt" sein soll kann ich mir beim besten Willen nicht erklären, man muss sich einfach nur mal gedanklich auf die Segmentierung einlassen und schon wird vieles klarer.


Zitat
Oder statt dessen das Verteilen von Zusammengehörigen Daten auf mehrere kleiner Segmente.
Das ist genau das was früher der Huge-Mode gemacht hat aber das muss der Compiler zur Compile-Zeit erledigen und kann nicht zur Laufzeit passieren oder man müsste noch eine weitere (mir unerklärliche) Abstraktions-Schicht dazwischen ziehen.


Zitat
Nur weil es 15bit sind heißt das noch lange nicht, dass ich alle Bits erraten muss.
In dem Fall musst Du wohl doch raten da die 15 Bits aus einem echten Zufallsgenerator kommen. Jede LDT fasst bei mir 32k-Einträge und die kann ich beliebig durcheinander verwenden. Es gibt keine Abhängigkeiten auf den nummerischen Wert eines Selectors. Solange mein Zufallsquelle von guter Qualität ist hast Du keine andere Chance als zu Raten und bei 1:32768 wird Dir kein gezielter/unauffälliger Angriff gelingen.

Zitat
Deine Selektoren sind ja auch nicht unabhängig von den Segmenten anderer Programme
Doch, jeder Task hat seine eigene LDT. In der GDT sind keine Task-Spezifischen Segmente.

Address layout randomization ist in bestimmten Situationen recht einfach und vor allem unbemerkt zu überwinden. Da ja nicht jede Funktion einzeln per Zufall verteilt wird kann man von der Adresse einer unsicheren Funktion, die ihre Adresse mit einem Bufferoverflow o.ä. verrät, auf eine andere interessante Funktion schließen. Mit so einem zweistufigem Angriff sollte sich jede address layout randomization überwinden lassen ohne zu raten. Das trifft natürlich auch meine Segmente.


Zitat
du willst Speicher bewusst verschwenden?
Vielleicht, ich sehe da keinen allzu großen Nutzwert, aber wenn dann nicht viel. Auf jeden Fall ist es möglich.


Zitat
Das wird dein System langsam machen, wäre meine Einschätzung, da eine Heapverwaltung extrem schnell von dem eigentlichen Pointer auf die Datenstrukturen kommen muss.
Die einzigste Funktion die vom User-Pointer auf die Verwaltungsstrukturen schließen muss ist free() und die kann man asynchron implementieren. free() legt einfach den User-Pointer in einen FIFO und kehrt zurück, irgendwann später kommt ein Hintergrundthread und arbeitet diesen FIFO in aller Ruhe ab. Das funktioniert auch in einem Flat-Memory-System wunderbar und hoch-performant.

Zitat
Die trivialste Implementierung ist
manchmal auch die ungeeignetste und nicht zwingenst die schnellste.


Zitat
feinkörnig, da ich Flags auf 4k-Ebene setzen kann.
Wenn ein Programm 20MByte Code hat musst Du 5000 Pages als Executable markieren. Das ist zwar feinkörnig aber auch hochgradig redundant. Ich kann da keinen Vorteil gegenüber einem Segment, das die 20MBytes mit einem einzigen Bit als executable markiert, erkennen.


Zitat
Ja, es wird sogar in den nächsten C++ Standard kommen.
Dann werden sich die verantwortlichen bestimmt auch überlegt haben wie man das in einem heute gängigen OS (alle mir bekannten nutzen Flat-Memory und Paging) umsetzt.
Eventuell wird dann nicht mehr eine Page-Table pro Task sondern eine pro Thread benötigt, und dann soll noch mal jemand behaupten das Paging keine Performance kostet. :wink:


Grüße
Erik
1267
OS-Design / Re: OS für Plattform mit Segmentierung
« am: 11. August 2009, 13:16 »
Hallo,


Zitat
Du gibst die Drecksarbeit an den Compiler ab, ...
Ja selbstverständlich, wofür sollte ich sonst eine Hochsprache benutzen wenn nicht dafür das Architektur-Spezifische Eigenheiten vor mir verborgen werden.

Zitat
Ja, in erster Linie sind es die fixen 64k, ...
Dann bin ich ja beruhigt.
Zitat
dass man Zeug auf mehrere Segmente aufteilen muss, auch wenn man es gar nicht will.
Das sollte eigentlich ein guter Compiler mit dem Huge-Modus vor Dir verbergen. Ob der Borland-Compiler das kann weis ich nicht ich habe vor diesem Huge-Modus immer einen ehrfürchtigen Bogen gemacht. Mir ist schon bewusst das ohne ordentliche Compilerunterstützung die Hölle los ist, daher ist das einer der wichtigsten Zwischenschritte zu meinem Ziel.


Zitat
... Dann ist das ganze Zeug eben nicht über eine 32-Bit-Zahl, sondern über eine 48-Bit-Zahl erreichbar. So what?
FAR-Pointer werden nicht immer in voller Größe geladen, oft ist der Selector noch im Segment-Register drin. In meinem printf-Beispiel vom 17.07. würde nie ein Selector geladen. Damit ist die Angriffsfläche deutlich kleiner. Auch wenn eine Funktion Register auf dem Stack sichert, um sie selbst verwenden zu können, müssen Selector und Offset nicht nebeneinander liegen was wieder die Anzahl an Zugriffen erhöht, die benötigt werden um einen bestimmten Pointer unter zu schieben.


Zitat
also die Flags für Segmente und/oder Pages richtig zu setzen
Mit Paging lässt sich sicher ein ähnlich hoher Schutzgrad erreichen wie mit Segmentierung nur ist die Angriffsfläche, die ein typisches User-Programm bietet, deutlich kleiner.

http://www.heise.de/newsticker/meldung/64624
Das Tool, welches in der zweiten Hälfte des Artikels genannt wird, hätte auf einem System mit Segmentierung deutlich weniger Chancen was passendes zusammen zu suchen. Dazu kommt das ein Far-Pointer nicht mit einem einzigen Speicher-Zugriff manipuliert werden kann eben weil er größer ist als die native Word-Breite.


Zitat
Man nennt dieses Konzept auch Security by Obscurity.
Ja das stimmt, genau so wie Address layout randomization. Trotzdem ist es eine weitere Hürde die ein Angreifer überwinden muss.


Zitat
Geht aber wohl auch nur, wenn der Overflow direkt bei einem Zugriff passiert
Richtig, das dürfte aber die Regel sein.
Zitat
und nicht bei irgendwelcher Pointerarithmetik davor - dort ist es ja einfach nur eine Zahl.
Hier könnte der Compiler ja immerhin die Flags prüfen. Okay wer will schon diesen (sicherlich geringen) Performance-Verlust.


Zitat
noch dazu schlechtere Obscurity (meine Einschätzung)
Also ich schätze das anders ein. Es sind immerhin 15 Bit die erraten werden müssen. Das ist zumindes nicht schlechter als Address layout randomization.

Zitat
Address layout randomization (was nur über Paging geht)
Wieso sollte Address layout randomization nur mit Paging gehen? Niemand zwingt mich den Code an Offset 0 im Code-Segment beginnen zu lassen. Code sollte immer Positionsunabhängig sein.


Zitat
Zitat
Ich werde z.B. die Heap-Verwaltung in ein zusätzliches Segment legen und da nur malloc() und free() den Segmentselector kennen kann auch erstmal kein Schadcode darauf zugreifen, dieses Segment ist quasi versteckt.
Huh? Wie soll denn das gehen.
Damit ist gemeint das die Verwaltungsdaten für den Heap in einem anderen Segment liegen. Die normalen Userdaten bleiben natürlich im normalen Heap für den jeder den Selector kennt.


Zitat
Das einzige wofür ich Segmentation noch für gerechtfertigt (auf x86) halte ist Thread local storage, das bekommt man mit Paging nicht hin.
Wird das heutzutage überhaupt benutzt? Ich hab in meinem Konzept zwar Thread local storage vorgesehen aber weiß noch nicht ob ich es implementieren will.


Zitat
Der Vorteil von Paging ist halt, das es um einiges feinkörniger ist und eine weniger kaputte Speicherverwaltung im Kernel benötigt.
Das sind zwei Behauptungen die erstmal erklärt/bewiesen werden sollten. Insbesondere das Attribut "kaputt" ist mir nicht klar.


Grüße
Erik
1268
OS-Design / Re: OS für Plattform mit Segmentierung
« am: 11. August 2009, 08:37 »
Guten Morgen,


Zitat
Du willst jetzt nicht ernsthaft anfangen, die Segmentierung im Real Mode für vergnügungssteuerpflichtig zu erklären?
Nein, natürlich nicht, aber so schlimm wie sie oft dargestellt wird ist sie IMHO auch nicht.

Meine letzten DOS-RM Erfahrungen sind jetzt knapp 4 Jahre her. Auf einer kleinen Embedded-Schachtel mit einem 80186-Clone, sone Single-Chip-Lösung wo der ganze Basis-Chipsatz (PIC, DMA, UART u.s.w.) mit drin ist, und 512kByte RAM. Das schlimmste daran was das bescheidene ROM-DOS und die Binär-Bibliotheken (TCP/IP-Stack u.a.) die ich benutzen musste. Dafür hätte ich von meinem Arbeitgeber am liebsten Gefahrenzulage verlangt. Die Segmentierung hat zwar dafür gesorgt das der Compiler (Borland-C/C++) kaum effizienten Code generieren konnte aber meinem C/C++-Code hat man davon fast nichts angesehen. Der Umgang mit Pointern war völlig normal. Der meiste Code war sogar problemlos für Windows XP und später für ThreadX auf einem ARM7 lauffähig. Der bedeutendste Unterschied war das es unter DOS kein preemptives Multithreading gibt aber unter Windows XP und ThreadX schon.

Was nun so schlimm war an der Segmentierung unter DOS hast Du immer noch nicht erläutert.


Zitat
Im Protected Mode sieht die Welt zugegebenermaßen schon wieder ganz anders aus
Was ist im PM soviel anders? Die Segmente können größer sein, also keine 64k-Grenze und damit kein HUGE-Adress-Modus. Was mir Vorschwebt würde dem damaligem Large-Mode entsprechen, also ein (oder mehrere) Code-Segmente und mehrere Daten-Segmente also einzelne Funktionen und Daten-Objekte können sich nicht über mehrere Segmente verteilen. Und meine Segmente werden sich nicht überlappen (außer eventuell für spezielle Dinge).

Zitat
... und an dem willst du dich ja eher orientieren, wenn ich das richtig verstanden habe.
Ja.


Zitat
Vermutlich will ihm da gar niemand das Wasser reichen.
Doch, ich. :evil:
Zitat
Und mit x86_64 ist das ganze ja auch schon wieder vorbei.
Ja, leider.


Zitat
NX ist sicher nicht die Erfindung von Intel. ...
Ja, Du hast recht. Entschuldige bitte, das hätte ich vorher nachlesen sollen.
Zitat
Eigentlich ist es nur eine logische Erweiterung, ...
Stimmt.


Zitat
Gehen wir einmal von aktuellen Prozessoren mit NX-Bit aus: Wo ist Segmentierung sicherer?
Das Problem ist das es im Flat-Mode nur einen Adress-Raum gibt. Eine 32/64Bit-Zahl als Pointer interpretiert kann alles erreichen/modifizieren, jedes Stückchen Code, jede Verwaltungsstruktur und jede Constante. Und das nicht nur von Deinem eigentlichem User-Mode-Programm sondern auch von allen dynamisch dazugelinkten Librarys und eventuell auch Bereiche vom Kernel falls man auf einige Dinge aus Ring 3 zugreifen darf. Und da bei 386 keine Overflow/Underflow-Behandlung für Pointer existiert funktioniert das auch immer egal wo Du den Code, Daten und Kernel in den Adress-Raum reinlegst. Sicher wird auch mit Segmentierung ein Bufferoverflow passieren nur sind die daraus folgenden Konsequenzen deutlich eingeschränkter. Ich werde z.B. die Heap-Verwaltung in ein zusätzliches Segment legen und da nur malloc() und free() den Segmentselector kennen kann auch erstmal kein Schadcode darauf zugreifen, dieses Segment ist quasi versteckt. Außerdem gibt es auf meiner Plattform keinen Pointer-Overflow also 0x00300000 + 0xFFFFFFF0 zeigt nicht auf 0x002FFFF0 sondern löst eine Exception aus.


Zitat
Also Swapping ist ungefähr das einzige an Paging, worüber ich noch nicht nachgedacht habe, es einzusetzen. :wink:
Deshalb werde ich in meinem ersten Anlauf ganz auf Paging verzichten.


Grüße
Erik
1269
OS-Design / Re: OS für Plattform mit Segmentierung
« am: 10. August 2009, 21:24 »
Hallo taljeth,


auf die Gefahr hin unverschämt zu werden.


Zitat
Insofern hat damit niemand richtig viel Erfahrung, sondern höchstens theoretisches Wissen und dunkle Erinnerungen aus DOS-Zeiten.
Ist das die Begründung für Sätze wie denn
Zitat
In die DOS-Zeiten, wo man sich beim Programmieren von Anwendungen ständig mit der Segmentierung rumschlagen musste, würde ich jedenfalls nicht zurückwollen.
??


Zitat
dass Segmentierung einfach etwas unüblich ist
Ich kenne auch keine andere Plattform, mit Marktbedeutung (noch nicht mal ohne), die Segmentierung wenigstens ähnlich gut unterstützt wie der 386-PM. Womit ich nicht sagen will das der 386 Segmentierung gut unterstützt trotzdem kann ihm da seit über 20 Jahren niemand das Wasser reichen.

Zitat
und mit Paging gibt es nur noch wenige Gründe für Segmentierung
Also mir würde da zuverlässiger Speicherschutz einfallen. Um der Code-Injektion durch Bufferoverflows auf dem Stack/Heap entgegenzuwirken hat sich Intel die umständliche Krücke "NX-Bit" ausgedacht und diese dann ans Paging drangefummelt. Von seiner einstigen Kernkompetenz, die "virtuelle Speichermehrung", hat sich das Paging auf heutigen CPUs recht weit entfernt.


Grüße
Erik
1270
OS-Design / Re: OS für Plattform mit Segmentierung
« am: 10. August 2009, 19:30 »
Hallo,


Zitat
Also mir fallen da auch nur die NE-EXEs ein...
Bei MS gibts immerhin eine knappe Dokumentation, als Anhaltspunkt was ich mindestens benötige sollte das taugen.
Danke für Deine Antwort.


Zitat
erst recht keiner mit gescheiten Fragen
Ich habe nicht den Eindruck das "Segmentierung" in die Kategorie "gescheite Fragen" gehört. Ich hab schon viele Leute darauf angesprochen und alle haben mir unisono erklärt das Segmentierung Teufelswerk ist. Bei der Frage warum kam, ebenfalls übereinstimmend, entweder Schulter zucken oder gar nichts. Manche haben sich immerhin noch an die 64k-Grenze erinnert und sind dann nach meinem Hinweis auf mein Ziel einer reinrassigen 32/64 Bit Architektur verstummt. Ist hier offensichtlich nicht anders.


Grüße
Erik
1271
OS-Design / Re: OS für Plattform mit Segmentierung
« am: 07. August 2009, 14:38 »
Hallo,


entschuldigt bitte das ich noch mal störe.

Kennt jemand ein Executable-File-Format das Segmentierung unterstützt?
Mir fällt da nur die NE-EXEs von WIN16 ein. Gibt es da noch was anderes das man als Inspirationsquelle nutzen kann?


Zitat
Zitat
In die DOS-Zeiten, wo man sich beim Programmieren von Anwendungen ständig mit der Segmentierung rumschlagen musste, würde ich jedenfalls nicht zurückwollen.
Was war denn an den Segmenten unter DOS so schlimm?

Schade das dazu nichts weiter gesagt wurde. Würde mich wirklich interessieren welcher Art die Probleme waren. Vielleicht kann ich die ja bei meinem Anlauf vermeiden.


Grüße
Erik
1272
OS-Design / Re: Absicherung gegen Buffer Overflow?
« am: 28. July 2009, 09:17 »
Hallo,


Zitat
Wie sichert man das in einem OS sauber ab?
Bearbeite niemals ein Array ohne zu wissen wie groß das ist! In allen Programmen und nicht nur in einem OS. Entweder das Array ist ein Object das seine Größe selber kennt und prüft oder Du musst die Größe immer als zusätzliche Variable/Parameter mitführen und in Deinem Code entsprechende Checks implementieren.


Zitat
Das sind üble Fehler, die hinter jedem memcpy, strcpy usw. lauern.
Deswegen sind diese Funktionen "depricated" und sollten nicht verwendet werden. Besser die Varianten mit 'n' im Namen verwenden oder andere Funktionen denen man ebenfalls die Größe des Ziel-Arrays mitteilen muss.


Grüße
Erik
1273
Lowlevel-Coding / Re: Multitasking - Frage zum Taskwechsel
« am: 27. July 2009, 17:31 »
Hallo,


diese Bit-Map kommt direkt ins TSS.
"iomap_base" ist quasie die Basis der Bit-Map innerhalb des TSS.
Wie groß Deine Bit-Map ist weiß die CPU anhand der Segment-Größe aus dem zugehörigem TSS-Descriptor. Ich weiß allerdings nicht genau was die CPU mit Ports macht die außerhalb Deiner Bit-Map liegen, ich glaube die sind per default geblockt.


Grüße
Erik
1274
Lowlevel-Coding / Re: SSE und Basic Protected Mode
« am: 27. July 2009, 09:30 »
Hallo,


SSE muss erst freigeschaltet werden (sonst gibts ne "Illegal-Opcode-Exception"), eventuell als "Unterfunktion" einer MMX-Aktivierung.
Ich glaube die betreffenden Bits findest Du im CR4.
Da kann man auch konfigurieren wie mit ungültigen Werten, NaN u.ä., umgegangen werden soll.

Von Bochs hätte ich aber eine passende Fehlermeldung erwartet.


Grüße
Erik
1275
OS-Design / Re: OS für Plattform mit Segmentierung
« am: 17. July 2009, 08:20 »
Hallo,


Zitat
Ich finde der größte Nachteil am segmentierten Speichermodell ist, dass es zwei Arten von Zeigern gibt. ...
Ja das stimmt. Deswegen sollte man IMHO für alles FAR-Pointer nehmen und NEAR-Pointer sind nur für den internen Gebrauch des Compilers geeignet, z.B. bei lokalen Variablen auf dem Stackframe oder bei globalen Variablen im Data-Segment.


Zitat
Ganz ohne Overhead sind die ja nicht. ....
Auf einer entsprechend ausgestatteten Plattform ist das kein allzu großes Problem. Der Performanceverlust ist IMHO auf jeden Fall kleiner als bei Paging.

Ein Beispiel :
Funktion int printf(const char* text,.....);müsste denn Pointer bereits in einem Segmentregister und einem normalen Register übergeben bekommen (per ABI so definiert) und der Compiler kann sämtliche Speicherzugriffe auf 'text' über das bestimmte Segment laufen lassen und es würde daher in 'printf()' kein einziger zusätzlicher Befehl oder CPU-Takt für die Segmentierung benötigt. Das geht bei 386 eben nicht da es dort schon an einer ausreichenden Anzahl an Segmentregistern mangelt und diese (vor allem FS und GS) auch nur äußerst lieblos in den Befehlssatz (siehe MOVS, LODS und STOS) integriert sind. Als ich mal ein größeres Programm für einen 80186 entwickelt hatte hab ich mir oft das Listing angeschaut und es war leider so das der Compiler gezwungen war für fast jeden zweiten Speicherzugriff ein Segmentregister (also DS oder ES) zu laden. Mit nur zwei, einigermaßen frei benutzbaren, Segmentregistern kommt kein Compiler auf guten Code. Auch ein fähiger Assemblerprogrammierer (und ich behaupte einfach mal ich bin einer) kann das nicht spürbar besser lösen. Auf meiner Wunsch-Ziel-Plattform sind 16 Segmentregister vorhanden wovon dem Programmierer/Compiler etwa 10 frei zur Verfügung stehen. Auch lassen sich alle Speicherzugriffe und alle Zugriffsarten über alle Segmentregister benutzen. Zusätzlich sind noch ein paar weitere Optimierungen in Hardware integriert, z.B. muss die CPU keinen Zugriff auf die Descriptor-Tabellen durchführen wenn das gewünschte Segment bereits in einem der anderen Segmentregister zur Verfügung steht und das dürfte sehr oft vorkommen da Pointer ja für gewöhnlich nur auf den Heap, das Data-Segment oder den Stack zeigen (natürlich lässt sich das abschalten damit das OS auch bewusst einen neuen Descriptor laden kann).

Fakt ist das dieses Konzept eine gute Unterstützung durch den Compiler benötigt um sauber und ohne Performanceeinbußen zu funktionieren.
Dann hat man auch etwas von den Vorteilen wie z.B. 100%-tigem Schutz gegen Code-Injectionen per Buffer-Overflow o.ä. oder flexible unbegrenzte Stacks.


Grüße
Erik
1276
OS-Design / Re: OS für Plattform mit Segmentierung
« am: 15. July 2009, 07:39 »
Hallo,


Zitat
Spannendes Thema,
:-D
Zitat
ich streue einfach mal ein paar Gedanken ein.
Darum hab ich das Thema ja zur Sprache gebracht.
Zitat
Und willkommen im Forum natürlich erstmal.
Danke!

Zitat
Was für eine Plattform ist es denn? Oder ist es nichts öffentlich zugängliches?
Diese Platform ist noch nicht öffentlich zugänglich. Es handelt sich um eine Soft-CPU welche auf einem FPGA läuft.


Zitat
... wie man es auf i386 am besten machen würde.
Nein, es geht mir eher um Grundsätzliche Dinge. Alles was auf meiner Zielplatform geht kann man auch mit einem 386 machen nur einiges nicht so effizient.


Zitat
An dieser Stelle stellt sich die Frage, wofür du die Segmente denn tatsächlich einsetzen willst
Zur Speicherseparierung für die einzelnen Prozesse. Jeder Prozess wird beim Start 5 Segmente bekommen (Code, Stack(für den ersten Thread), Data, Const und Heap(ist erst mal leer)).

Zitat
In die DOS-Zeiten, wo man sich beim Programmieren von Anwendungen ständig mit der Segmentierung rumschlagen musste, würde ich jedenfalls nicht zurückwollen.
Was war denn an den Segmenten unter DOS so schlimm? Von der Beschränkung auf 64kBytes mal abgesehen. Ich habe auch viel im reinen DOS, im RM, programmiert und man hat es meinem C-Code nur sehr selten angesehen das er für DOS ist. Es gibt wegen der blöden Überlappung der Segmente zwar ein paar Stolperfallen wenn man den Adress-Modus "HUGE" benutzt aber ansonsten kann ich mich nicht an ernsthafte Schwierigkeiten erinnern.

Zitat
Hm, ich glaube kaum, dass das in Sachen Performance groß was rausreißt.
Das 4-Stufige Paging des Long-Mode soll angeblich etwa 10 bis 15 Prozent Performance kosten. Da mann das Paging im Long-Mode nicht abschalten kann kann man das natürlich kaum überprüfen. Aber "etwas" Performace kostet es auf jeden Fall.


Zitat
Mit Segmentierung kommst du möglicherweise mit einem einzigen Kontext weg (kommt drauf an, ob der virtuelle Adressraum groß genug ist),
Ja, alle Programme teilen sich den linearen Adressraum, der auf 32Bit-Systemen "nur" 4GByte groß ist. Auf einer richtigen 64Bit-Architektur ist das aber auf absehbare Zeit kein Problem.

Zitat
aber du willst nicht darauf verzichten, virtuellen Speicher dynamisch zuteilen zu können.
Wieso sollte das nicht mehr gehen? Wenn ein Programm "malloc()" aufruft schaut dies ob im Heap-Segment noch Platz ist und wenn nicht wird das Segment vom OS angemessen vergrößert und da die Programme nicht wissen wo ihre Segmente im linearen Adressraum liegen kann das OS diese auch jederzeit verschieben und gar defragmentieren. Ich sehe da kein Problem nur Arbeit.


Zitat
Das ist jetzt aber nicht wirklich ein Vorteil von Segmentierung, das kriegst du mit Paging genauso hin.
Nicht wenn der gewünschte virtuelle Adressraum in einem der Prozesse bereits mit was anderem belegt ist. Und da dieser Prozess sicher irgendwo bereits einen Pointer auf dieses andere hat kann man es auch nicht mehr verschieben um Platz zu schaffen.


Zitat
Zusammenhängenden physischen Speicher braucht man immer wenn es um Hardware geht, also DMA.
Alle mir bekannte Hardware kann ihre Daten auch in mehreren verteilten Stücken in den physischen Speicher schreiben. Ich glaube das meint man mit "Scatter/Gatter".


Mir ist noch eingefallen das Memory-Mappen-File-I/O von der Segmentieren profitieren könnte. Man erstellt einfach ein Segment mit der Größe der Datei und das Programm kann ganz normal drauf rumackern und das OS kümmert sich per Paging darum das alles funktioniert. Natürlich muss auch hierfür der lineare Adressraum groß genug sein.


Grüße
Erik
1277
OS-Design / OS für Plattform mit Segmentierung
« am: 14. July 2009, 22:11 »
Hi @all,


ich bin vor ein paar Tagen auf diese interessante Seite gestoßen und möchte mal ein spezielles Thema diskutieren.


Ich will ein OS mit Segmentierung, ähnlich der des 386 im PM, implementieren.
(aber auf einer anderen Plattform welche Segmentierung sehr gut unterstützt, ob es auch einen 386-Port geben wird weis ich noch nicht)


Ich möchte das OS als Microkernel implementieren. In diesen Microkernel sollen nur die Speicherverwaltung, der Scheduler, das Process/Thread-Management, IPC-Mechanismen, Message-Pipes und ein simples Timing-System integriert werden. (das meiste davon habe ich vor einigen Jahren schon mal als Kooperatives Multithreading auf Basis des TNT-DOS-Extender in Assembler für 386-32Bit-PM implementiert, dieses Framework nutze ich heute noch gerne wenn ich mal ein sehr Hardwarenahes Programm für den PC schreiben muss und auf kein bestimmtes OS angewiesen bin)


Segmentierung bringt zwar einige Vorteile aber auch ein paar Nachteile.


Ein großer Nachteil ist natürlich das kein heute üblicher Compiler Segmentierung, also FAR-Pointer, unterstützt. Unter DOS benutze ich den Open-Watcom, dieser unterstützt zwar auch im 32Bit-PM FAR-Pointer aber mit einer ziemlich umständlichen Syntax und (was noch viel schlimmer ist) ohne Optimierungen. Für die Zielarchitektur gibt es eh noch keinen C-Compiler also werde ich sowieso die Mühe haben ein Target für den gcc zu entwickeln, so weit wie ich bis jetzt in den gcc-Source-Code hinein gesehen hab sollte es möglich sein eine vernünftige Unterstützung für FAR-Pointer zu implementieren.

Ein interessanter Vorteil der Segmentierung ist das man aufs Paging verzichten kann, falls der physische Speicher ausreicht, und man damit einen gewissen Performance-Vorteil bekommt durch das wegfallen der Adress-Umsetzung von virtual nach physisch bei jedem Speicherzugriff. Wenn man dann doch das Paging anschalten muss, zwegs Swapping, kann man mit nur einer Page-Table für alle Prozesse auskommen (da die Prozesse ja eh über verschiedene Segmente, aus verschiedenen LDTs, separiert sind) und damit das Prozess-Kontext-Umschalten nicht durch blöde TLB-Flushs ausgebremst wird.

Auch für shared Memory als IPC bietet Segmentierung einen Vorteil. Mann könnte ein spezielles Segment erstellen das beiden Prozessen zugänglich ist, innerhalb dieses Segments währen sogar NEAR-Pointer für alle teilnehmenden Prozesse gültig.

Die Speicherverwaltung ist bei Segmentierung etwas komplizierter da man als erstes den linearen Speicher, für die Segmente, verwalten muss und zusätzlich noch den physischen Speicher fürs Swapping. Dafür gibt es IMHO keinen Bedarf zusammenhängenden physischen Speicher zu allozieren, das reduziert eventuell die Komplexität der Verwaltung des physischen Speichers.


Welche Nachteile, oder auch Vorteile, seht Ihr für ein OS das ganz auf Segmentierung setzt?

Als "ähnliche" Plattform kann ruhig der 32Bit-PM des 386 gelten, meine Zielplatform hat vor allem deutlich mehr Register (auch mehr Segment-Register) und eine konsequent auf Segmentierung ausgerichtete Architektur (z.B. die Shadow-Register für die Segmente lassen sich einfach manipulieren und das globale Paging wird in Hardware synchron zwischen den CPUs gehalten).


Grüße
Erik
Seiten: 1 ... 62 63 [64]

Einloggen