0. Hvorfor denne tekst

 

1. Det binære tal system.. 3

 

2. Logic Gates 5

GATES ELEKTRONIK.. 6

FULL ADDER. 11

SIMPLERE UDGAVE AF FULL ADDER. 13

INTEGRATED CIRCUIT(IC) 17

ALU (ARITHMETIC LOGIC UNIT) 19

HUGKOMMELSE (MAIN MEMORY) 20

KONKLUSION PÅ LOGIC GATES: 21

Video: 1-bit ALU
Video: 4x3 bit MEMORY

3. En Computer 22

COMPUTERENS OPBYGNING.. 22

HARRY PORTERS RELAY COMPUTER. 23

KONTROL UNIT

 

4. Et Program (instruktion) 25

MOVE INSTRUKTIONEN BEHANDLET AF KONTROL UNIT. 26

MIN IMPLEMENTERING AF MOVE. 28

INPUT/OUTPUT (I/O) 29

PROGRAMMED I/O.. 29

INTERUPT-DRIVEN I/O

Video: Logic Gates Computer (Manual ADD)
Video: Logic Gates Computer (Program - Manual 1 of 2)
Video: Logic Gates Computer (Program - Manual 2 of 2)
Video: Logic Gates Computer (Program - AUTO)
Video: Logic Gates Computer (Multiplication 1 of 2)
Video: Logic Gates Computer (Multiplication 2 of 2)

5. Mic-1 Computeren. 31

HVORDAN HOPPER MAN FRA ISA TIL MICRO OG FRA MICRO TIL ISA?. 33

SUB-PROGRAM.. 34

SUB-PROGRAM EKSEMPEL FRA MIC-1

 

6. Parameter Transmision. 43

C# PARAMETERS EKSEMPLER

 

7. Operativ Systemet 46

HVAD LAVER OPERATIV SYSTEMET. 46

HVORDAN KØRES ET PROGRAM AF OS. 47

FILER. 50

BRUGERE. 50

VIRTUAL MEMORY (PAGES) 51

VIRTUAL MEMORY (SEGMENTATION) 52

PARALLEL PROCESSER. 53

OS TJENESTER OG OPBYGNING.. 54

3 OPBYGNINGS TYPER

 
   
   
   


 


0. Hvorfor denne tekst

 

 

 

 

 

Hvordan fungerer computeren? Ret svært at svare på, men dette dokument er et forsøg.

 

Dette dokument har som formål et dække det meste. Jeg undlader de ting som forstyrrer i forståelse af det store billede. Når man har fået det store billede kan man nemmer kikke på de andre ”lidt mindre vigtige” ting og sætte dem i perspektiv.

 

Dette er en ”Bottom Up approach” og som helst skulle munde ud i et klart billede når du når til toppen. Lad os komme i gang.

 

Bøger/Tekster og Værktøjer som bruges:

·        Bog: Structured Computer Organization af Andrew S. Tanenbaum

·        Tekst &Video: Harry Porters Relay Computer fra http://web.cecs.pdx.edu/~harry/Relay/

·        Bog: Programming Languages af Pratt

·        Værktøj: Logic Gates Simulator fra www.kolls.net/gatesim

·        Værktøj: Mic 1 Simulator fra http://www.cs.oberlin.edu/~rms/mic1/

 

 

Jákup W Hansen                                                                                                           29. november 2013

 

www.jakupwhansen.dk

 

 

 

 


 


1. Det binære tal system

 

 

Det første du skal forstå, og som alt andet bygger på, er det binære system. Hvis dette ikke ligger på ryggraden bliver det svært at forstå senere emner som Logic Gates.

 

Det binære system har kun 2 tal, 0 og 1, mens vores decimal system som vi bruger til daglig har 10 tal 0,1,2,3,4,5,6,7,8 og 9.

 

Grunden til at computeren bruger det binære tal system, er simpel, den kan bedst arbejde med strøm ON og strøm OFF, hvor ON = 1, og OFF = 0.

 

 

Men vi skal nu alligevel bruge store tal, vi kan ikke klare os kun med 0 og 1, vi må kunne lægge store tal sammen som f.eks. (12 + 3 = 15), så hvordan gør vi det?

Jo, vi bygger bare disse decimal tal op binært. Dvs. at 12 bliver til 1100. Hvordan kan 1100 blive til 12?

Det får vi ved at tallene får forskellig værdi, afhængig af deres position. Det kender vi også fra vores normale Decimal system hvor 23 fås fra at de første tal som er 2 er tiere og efter som vi har 2 har vi tyve, og tallet 3 er ettere og dem har vi 3 af, så sammenlagt har vi tyve + tre, som giver tre og tyve. Med det binære system har positionen også forskellig værdi.

 

128

64

32

16

8

4

2

1

 

0

0

0

0

1

1

0

0

 = 12

+

+

0

0

0

0

0

0

1

1

= 3

=

=

0

0

0

0

1

1

1

1

= 15

 

Se tabellen her. Den første række viser positionens værdi. Som du kan se i anden række, så har vi et 1 tal i kolonne med 8, og et 1 tal i kolonnen med 4. Det giver så 12 samlet.

 

 

 

Lad os kikke på et lidt mere kompliceret regnestykke. nemlig 15 + 7 = 22.

 

128

64

32

16

8

4

2

1

 

 

 

 

1 mente

1 mente

1 mente

1 mente

 

 

0

0

0

0

1

1

1

1

=15

+

+

0

0

0

0

0

1

1

1

=7

=

=

0

0

0

1

0

1

1

0

=22

 

 

 

 

 

 

 

Der findes følgende kombinationer når du skal lægge binære tal sammen.

0 + 0 = 0

1 + 0 = 1

0 + 1 = 1

1 + 1 = 0 og en i mente

1 + 1 + en i mente = 1 og en i mente

0 + 0 + en i mente = 1

1 + 0 + en i mente = 0 og en i mente

0 + 1 + en i mente = 0 og en i mente

 

 

Nu kender du til den bagvedliggende matematik som computeren bygger på. Nu skal vi gå videre til hvordan man fysisk bruger denne matematik.


 

2. Logic Gates

 

 

For at bruge binær matematik i den fysiske computer bruger man noget som kaldes en TRANSISTOR. Det som denne transistor kan er ret smart, den kan nemlig tænde eller slukke for strøm, kun ved at bruge en lille smule strøm.

 

Prøv og se fig 3-1 (b) hvor strømmen går fra +V og ned til bunden hvis vi har en værdi på 1 og hvis ingen strøm kører har vi en værdi på 0. Men hvad bestemmer om strøm kører, jo det bestemmes af V1 og V2. Hvis de begge har en lille strøm, så er "vand hanen" åben og strøm går helt igennem, men hvis en af hanerne eller begge er lukket, så er ingen strøm ned til bunden. Dette er en AND gate, dvs. at begge V´er skal være tændt for at vi skal få 1.

asset 

 

Prøv og undersøg de tre GATES fordi de er grundlaget under alle de andre GATES. Vi bruger disse 3 Gates til at lave andre GATES.

 

 

Hvad skal du forstå her. Jo at man kan styre om strøm kommer fra et sted til det andet. Og det er denne styring som bestemmer om vi har 1 eller 0.

 

Inden i computeren er der MILLIONER af disse GATES. De bliver faktisk brændt ned i en plade, og tager Micro millimeter pr. styk, man kan simpelthen ikke se dem med det blotte øjne, men princippet er alligevel det samme.

 

Lad os nu rykke et lille nivo op, og undersøge disse GATES, og hvilke tilstande de kan have.

 

Lad os undersøge Fig. 3-2 (d) som er AND gate. Her følger en "truth table" med, den siger at kommer der strøm ind i A og B, så kommer der strøm ud af X. Alle de andre kombinationer giver ingen strøm ud af X. Det er altså KUN når både A og B er ON at X er ON, eller kun når A og B = 1 at X = 1.

asset

 

 

Vi kender denne tankegang i programmering hvor vi har en IF sætning, den kunne se sådan ud:

                                                IF (i == 4 && a ==3)

Her er i==4 det samme som A og a==3 det samme som B, og hvis begge er TRUE, så er X = 1 eller vi kommer ind i sætningen.

 

Programmering og Maskinarkitektur har meget tilfælles, og det hjælper helt sikker at forstå Maskinarkitektur for at forstå programmering og modsat.

 

Gates er måden hvorpå vi styrer strømmen i komputeren. Med strøm styrer vi strømmen. Vi lukker eller tænder for en forbindelse med strøm. Når vi taster på tastaturet åbner vi og slukker for en masse af forbindelser i computeren, det går så stærkt at vi ikke observerer det. Men en lille instruktion, et tryk på tastaturet aktiverer måske flere millioner af GATES, for til sidst at skrive en bogstav på skærmen, det er ret imponerende.

 

GATES ELEKTRONIK

 

 

For at kunne lave disse Gates, har jeg købt et start kit. Det kostede 100-200 kroner og indeholder 5 transistorer og en masse andre ting, så det er rigeligt til at lave nogle simple gates.

 

Her til højre ser du mit KIT. Der findes en masse lignende KIT´s.

 


 

FORKLARING

Først lige en forklaring på hvordan alt hænger sammen.

 

Strømmen kommer ind fra den røde ledning i toppen, Og både punkt 1 og 2 har strøm. Fra punkt 1 går der strøm ned til punkt 4 i gennem en modstand, og ind i Base (B) som styrer hvor meget strøm der kører fra C til E (se Transistor tegningen til højre). Strøm på BASE´en åbner for strøm igennem transistoren fra C (punkt 3) til E (punkt 5)

 

Fra punkt 2 går strømmen ind i lys dioden og  ned til jorden (-).

 

 

Forklaring

 

MEN efter som der går strøm igennem Base i dette her tilfælde, så vælger strømmer at gå fra punkt 2 og ned til punkt 3 og ud af punkt 5 som er jord (-).

 

Strømmen vælger altid at gå den letteste vej, og efter som der er modstand i lys dioden kan det ikke betale sig at gå den vej. Derfor lyser dioden ikke.

 

 


 

NOT GATE

Dette billede er identisk med det som jeg bruger ovenover for at foklare hvordan det fungerer. Du ser at lys dioden ikke lyser her, og det er fordi der går strøm ind i Base.

 

 

A=1

X=0

 

INVERTER 1af2

Her lyser dioden, og det er fordi der ingen strøm går ind i Base, og derfor må strømmen gå igennem lys dioden.

 

 

A=0

X=1

INVERTER 2af2

 


 

NAND GATE

Her har vi 2 transistorer som er sat sammen i serie. Vi har 2 indput som er de grå ledninger nederst i venstre hjørne.

 

I dette billede ser du at ingen af de 2 grå ledninger er sat ind, de hænger uden for bread boardet. Derfor har vi lys i dioden fordi strømmen går igennem dioden og ned til jord og ikke igennem transistorerne.

 

 

 

A=0

B=0

X=1

NAND 1af4

Nu ser du at den ene af de grå ledninger er sag i den første transistors BASE.

 

Nu går strømmer faktisk igennem den første transistor og ned til den næste, men så kommer den ikke videre, og derfor er strømme blokeret denne vej, og strømmen må igennem lys dioden.

 

 

 

A=1

B=0

X=1

NAND 2af4

Her har vi et den anden grå ledning som nu går ind i BASE hos den næste transistor, men det hjælper ikke, fordi strømmer kan ikke komme denne vej, fordi den første transistor nu er lukket. Strømmen er igen tvungen til at gå igennem lys dioden.

 

 

 

A=0

B=1

X=1

NAND 3af4

MEN nu har vi åbnet for begge transistorer ved at de 2 ledninger går ind i BASE og de 2 transistorer. Nu er der fri adgang for strømmen at gå igennem begge transistorer og ned til jord.

 

Nu vælger strømmen IKKE at gå igennem lys dioden fordi den har en lille modstand, som er nok til at det er lettere at gå igennem transistorerne.

 

 

 

A=1

B=1

X=0

NAND 4af4

 

 

 

 


 

FULL ADDER

Lad os kikke på et eksempel hvor vi bruger disse gates til at bygge et STØRRE system, en samling af GATES bliver ofte kaldt for en Integrated Circuit (IC). Vi kan lave en IC som opfører sig logisk og løser en bestemt opgave. Lad os kikke på hvordan vi kan lave et system som automatisk lægger binære tal sammen.

 

Figur 3-18 viser hvordan en computer lægger to binære tal sammen. Dette er den fysiske måde at lave de vi snakkede om i 1. afsnit ”Det binære tal system”. I figuren her har vi en ny Gate som vi ikke har set før, nemlig XOR.  Den er nu ikke specielt svær, den svarer true når der er en OR og kun når der er en OR, dette kaldes en Exclusive OR.

 


Det er lidt besværligt at følge med i hvordan strømmen kører i sådan et kresløb, så her kommer 4 eksempler.

4 eksempler på full adder tilstande

FullAdder eks_01

FullAdder eks_02

FullAdder eks_03

FullAdder eks_04

 

Nu har du set hvordan man kan plusse 2 1 bit tal sammen. Men det mest normale er at de bit man skal plusse er større end 1 bit, så hvordan kan vi bygge sådan en løsning ? Jo, vi sætter bare flere af disse 1 bit addere sammen.

SIMPLERE UDGAVE AF FULL ADDER

Den udgave (fra bogen) vi lige har gennemgået er ret svær at forstå, så jeg har lavet en anden udgave som er mere pædagogisk men så lidt dyrere fordi man skal bruge flere gates.

SimpelFullAdder_01.jpg

SimpelFullAdder_02.jpg

SimpelFullAdder_03.jpg

SimpelFullAdder_04.jpg

SimpelFullAdder_05.jpg

SimpelFullAdder_06.jpg

SimpelFullAdder_07.jpg

SimpelFullAdder_08.jpg

 

 

 


 

INTEGRATED CIRCUIT(IC)

Her nedenfor ser du at jeg har sat 2 sammen, således at vi nu har en 2 bit adder. Vi kan sagtens lave flere forbindelser og f.eks. lave en 8 bit adder. Men dette er måden man gør det på.

 

Med Logic Gate simulatoren som vi bruger er det nemt at lave IC´er. Man markerer bare de Gates man ønsker at have med og så vælger man lave IC.

Ovenover ser du hvordan jeg har markeret full adderen og lavet en IC (nederst til venstre). Den har de samme indput og output som den orginale. Nu kan jeg sætte flære IC´er sammen til f.eks en 2 bit full adder, se billedet nedenfor.

Her ovenover ser du at jeg har lavet en 2 bit full adder. Den lægger følgende binære tal sammen

11  + 01 = 100

 

Sådan kan man nemt lave komplicerede komponenter, således at vi til sidst har en komplet computer, var det det vi ville.

 


 

ALU (ARITHMETIC LOGIC UNIT)

En vigtig komponent i CPU´en (computeren hjerte) er ALU. Det er der vi blandt anden har Full Adderen, og også andre funktioner, men adderen er nok den vigtigste. Vi har i undervisningen implineteret fig 3-19 , lad os kikke lidt på den.

 

Du kan prøve at følge strømmen her men det er lidt kompliceret. Det vigtigste at forstå her, er at F0 og F1 som er de indput du ser nederst til venstre i Fig 3-19, bestemmer hvilken funktion (Add, And, OR) der udføres. Vi har testet denne del i undervisningen, og det viser sig at sætter vi F0=1 og F1=1 så er ALU i en tilstand af ADD (A+B). Det betyder så, at når vi sender vores data ind i A og B oppe i venstre hjørne, så er det ikke nok, vi må også sige hvad der skal laves med disse to værdier, og det gør vi med F0 og F1. Det er Kontrol Busse som er knytet til F0 og F1. Det vigtige at forstå her er at der skal ske 2 ting når man lægger et tal sammen i ALU´en, først skal A og B aktiveres ved at strøm sættes til hvis de ønskes at være 1 eller strøm er slukket der hvor man ønsker 0, og så skal man aktiver den funktion man ønsker ved at sætte strøm til F0 og F1, afhængi af hvilken funktion man ønsker. Det er derfor vi har Flere busser i Computeren, fordi vi nemlig ønsker at styre flere ting samtidig. Så lad os kikke på et lille eksempel. Vi ønsker at lægge A=1 og B=0 sammen. Det gør vi ved at sætte strøm til A indputtet og ingen strøm til B indputtet. Så skal vi også sætte strøm til F0 og strøm til F1. Nu vil vi få det ønskede resultat ud af output og Carry Out

 

Du kan se, at det er ret besværligt bare at lægge to binær tal sammen, men nu har du set hvordan det foregør inden i computeren på det laveste nivo.

 

 

 

 

 

HUGKOMMELSE (MAIN MEMORY)

Fig 3-29 er også en figur vi har implimenteret i simulerings værktøjet i undervisningen. Den er lige som 1 bit ALU, ret omfattende. Men det som er vigtigt at forstå er hvordan den betjenes og ikke nødvendigvis indmaden.

 

Hvad kan vi med denne konstruktion ? jo, vi kan gemme 4 ord og hente dem igen når vi ønsker. Et ord her er 3 bit.

 

Lad os prøve et eksempel, vi ønsker at gemme 101 i denne her memory, hvordan gør vi det. Først skal vi lægge 101 ud på Data Bussen som er knyttet til Data in oppe i venstre hjørne (I0, I1 og I2). Siden skal vi vælge hvor vi skal gemme henne, vi har 4 positioner (2 bit) at vælge i mellem. Lad os sige at vi vil gemme i (01), så sætter vi strøm på Adresse Bussen ved 01 og så er dette ord valgt. Men vi mangler en ting endnu, nemlig at vælge i mellem at skrive eller læse, og efter som vi ønsker at skrive, må vi sætte strøm til de rigtige ledninge hos Control Bussen som har direkte adgang til CS, RD og OE som er nederst i venstre hjørne. Når alle disse 3 dele (Data, Adresse og Control Bus) er sat, bliver vores 101 gemt. Ønsker vi nu at læse denne igen, skal vi lave det samme igen men nu skal vi vælge at sætte Control bussen til at læse i stedet for, så får vi værdien som er gemt, ud i nederste venstre hjørne (O0, O1 og O2), som også er knytte til Data Busser.

 

 

 

 

 

KONKLUSION PÅ LOGIC GATES:

Du har nu set hvordan man med Logic Gates styrer informationen (1 og 0) på det laveste nivo i en computer. Du har set at det er ret indviklet at få strømmen til at opføre sig logisk, således at den udfører det arbejde vi ønsker, som f.eks. at lægge 2 binær tal sammen.

 

Computeren som vi til daglig arbejder med kan en frygtelig masse ting, MEN når man kikker ned i Logic Gates nivo, så viser det sig at den faktisk ikke kan ret meget. Den kan groft sagt lægge to tal sammen, den kan se om to tal er ens, og flyte tal fra et sted og til et andet, og nogle få andre ting. Men med disse få funktionaliteter kan man skabe en så fantastisk computer som vi alle besider, det er lidt mærkeligt, men det er det som du helst skal have set nu.

 


 

3. En Computer

 

Vi ved at en computer er bygget op af mange lag, men hvad er det laveste lag, hvor man kan kalde det en computer. Det det lag vi skal kikke på nu. Det er sådan her de første digitale computer så ud, og stadigvæk ser ud.

 

Jeg har valgt at bruge Harry Porter´s Relay Computer her, fordi den er lidt simplere end den som illustreres i Bogen (Structure Computer Organization By: Tanenbaum), særlig når forståelse er i centrum. Men vi kommer tilbage til Tanenbaum sener, når vi skal kikke på Mic-1 simulatoren.

 

I forrige afdeling havde vi om Logic Gates, som er byggestenene, vi kan se det som det laveste nivo en computer har. Så tog vi disse og lavede lidt større konstruktioner, vi lavede nemlig en 1bit ALU og 4x3 bit Memory. Nu er vi kommet dertil at vi skal bruge disse komponenter og sætte dem sammen, lige som vi i ALU´en brugte Logic Gates, så bruger vi her ALU, MEMORY og sætter dem sammen, til en lille computer. Vi får derfor følgende hierarchi:

 

Nivo 3: En samlet computer.

Nivo 2: ALU, Memory…

Nivo 1: Logic Gates

 

Se nedenfor på Fig 2-1 hvordan en computer er organiseret. Den er i 2 dele, CPU og I/0. Men hvordan hænger dette samme med det vi allerede har lavet? Hvis du kikker ind i CPU´en så ser du at der ligger ALU´en, Og vi har også Registers, som er en anden måde at kalde Hukommelse/Memory. Det eneste vi mangler er Control Unit, men den har vi været lidt inde på, fordi når man styrer hukommelse og ALU´en må man også sætte Control Bussen, og det er dette arbejde som Control Unit laver.

 

COMPUTERENS OPBYGNING

Det er fra denne tegning alle efterfølgende computere er blevet designet.

Her ser vi en lidt anderledes udgave, men principperne fra Neumann er der stadigvæk.

 

 

Det du helst skal se her, er at de komponenter vi laver ud af Logic Gates, her bliver sat sammen til et helt system, til en computer.

 

Hvordan fungerer denne computer så, eller hvordan kører data igennem den? Det skal vi kikke på nu.

HARRY PORTERS RELAY COMPUTER

 

Denne computer har en arkitektur som ser sådan ud, og det er ret tæt på Newmans model, dog mangler Control Unit på tegningen, men den er der, vi ser den bare ikke.

 

En computer laver det samme hele tiden, det kaldes Fetch-Decode-Execute, Harry har en lidt anderledes gang, nemlig Fetch-Increment-Execute, men princippet er det samme. Denne 3 dels kørsel, gentages så hele tiden, én gang pr. instruktion. Så et program som har 10 instruktioner kører denne cirkel 10 gange, hvis den altså ikke indeholder en loop, så kører den oftere selvfølgelig.

Fetch Instruction

 

Det først som sker, er at adressen som er gemt i PC (Program Counter) føres over på Address Bussen som er knyttet til Memory, og så vælges memory til at læse, og så henter memory det som er gemt på tilsvarende adresse, og lægger det ud på Data bussen. Så vælges Inst til at modtage det som er på Data bussen og gemme det.

 

Nu er instruktione hentet fra memory, dette kaldes Fetch.

Increment PC

 

Så skal PC tælles ét op, det gøres ved at den lægges på address bussen og Increment komponenten tager den ind og lægger ét til, og gemmer det i Inc.

Update PC

 

Inc lægger så igen sit indehold ud på address bussen og PC modtager den, nu er PC blevet ét større.

 

De to sidste aktioner kalder hos Harry for Increment

Execute Instruction

 

Til sidst er vi kommet til selve kørselen af den instruktion vi fik ved Fetch, det første skridt. I dette tilfælde er det en ADD, som tager de 2 værdier gemt i B og C og fører dem over i ALU ´en, så vælges en funktion og så gemmes resultatet over i A registeret.

Her er et billede af hvad der lige er gennemgået ovenover, men nu set i TIDSENHEDER. 

 

ALU instruktioner kræver 8 tidsenheder for at gennemføres.

 

KONTROL UNIT

Kontrol enheden mangler på disse tegninger, og det er lidt mangelfuldt. Men alle de forskelige LOAD, FUNCTION, SELECT osv. som er på tegningerne, er noget som Kontrol enheden styrer. Den ved hele tiden hvad den skal gør ud fra tidsenheden og hvilken Instruktion som er i gang. Forskellige Instruktioner vil aktivere forskellige ting (Regne, læse, skrive osv.), alt foregår UDEN SOFTWARE, men er fysisk bundet med ledninger.

 

Lad mig prøve at vise hvordan Harrys computer ville se ud MED Kontrol Unit.

 

Det som er vigtigt at forstå her, er at det er virkelige ledninger som føres fra Control Unit (CU) og ned til resten af computeren. Der er en masser af ledninger fra CU, ja næsten alle enheder er forbundet til CU. CU kan styre det hele ved at sende strøm på disse forbindelser. Rækkefølgen er meget vigtig, man må huske at åbne først og så sende data på data bussen osv, det siger sig selv, at skal men gemme data i et register, må man sætte strøm på Data Bussen og denne strøm må være tændt hele tiden indtil registeret har fået tid til at gemme. Derfor er rækkefølgen vigtig, og det styres af disse tids intervaller. Du kan f.eks. se i billedet at Select PC er åben i tid 1,2 og 3, mens andre bruger denne værdi, og den lukker først når alle som har brug for den er færdige med den. Således bliver alt designe ned i mindste detalje sålede at det passer perfekt sammen.

 

Nu er computeren forhåbentlig blevet afmystificeret lidt, og du forstår computerens basale arkitektur.

 

På side 58 under afsnittet (2.1.3 RISC versus CISC) står der at en RISC computer har typisk 50 instrukser.  Det er alt hvad computeren i princippet kan, og så kan man bruge disse instrukser på et højere nivo og lave lidt smartere instrukser som så bruger flere af disse 50. Sådan bygger man lag på lag indtil vi har C# sproget, som med én instruktion helst aktiver nogle af disse 50 flere tusind gange, bare for at udføre én C# instruktion.

 

4. Et Program (instruktion)

 

Vi har set hvordan computeren er bygget og fungerer, men vi har ikke set hvordan et program bliver afviklet og hvad én instruktion består af og hvordan den styrer data strømmen. Et program er en samling af instrukser/data, disse er gemt i RAM som CPU´en har adgang til. Programmet hentes ind fra f.eks. harddisken. Men det som er lidt mærkeligt er at der er instrukser og data, men når man tænke sig om, så giver det mening, fordi vi må have instrukser som siger hvad der skal laves, men vi må også kunne gemme forskellige tilstande som programmet er i. For at undgå at man læser en instruktion ind som er data og ikke en instruks, kan man vælge at holde disse adskilt i sin egen afdeling af RAM´en, men det er ikke nødvendig.

 

Her nedenfor ser du 3 instrukser fra Harry Porter, og en kender vi allerede lidt nemlig ALU instruktionen.

 

Men hvordan bliver disse bits til noget fornuftig. Til at forklare det må vi lige en tur tilbage til Logic Gates. Men lad mig lige først forklare selve instruktionen.

Move instruktionen består groft sagt af de første 2 bit. Dvs. at hvis denne bit række ligger gemt i Instruktion registeret (00100110) så ved vi helt sikkert at det er en Move, fordi de 2 første bit er 00, og det er KUN move som har det. ALU har 1000xxxx som de 4 første og resten siger bare hvad den skal gøre. Load Immediate har 01xxxxxx. Som du kan se, så er alle instruktionerne forskellige fordi de starter forskelligt. Resten af instruktionen bliver brugt til at sige hvad den skal gøre. Og nu skal jeg vise jer et eksempel på en Move instruktion, og hvordan den virkelig gør noget, vi skal se hvordan Kontrol Unit modtager En instruktion og beslutter om det er en MOVE eller ikke er en MOVE.

 


 

MOVE INSTRUKTIONEN BEHANDLET AF KONTROL UNIT.

Prøv og undersøg dette Logic Gate diagram, vi har de 8 indpunt oppe i toppen, og så har vi nogle output nede i bunden. Der mangler ledninger fra indput 6,7 og 8, fordi der er ikke plads, og de er ikke nødvendige for at forklare princippet.

 

Lad mig forklarer:

 

Først: Hvor får dette Kontrol Element indput fra? Jo det er ret nemt at forstå, den er nemlig knyttet til Instruktions Registret, og hvis vi vælger LÆS på Registret, så ryger de 8 bit direkte til de tilhørende indput her. Der er altså 8 ledninger fra Instruktions Registret og over i disse 8 indputs.

 

Se på indput 1 og 2, her har vi 1 er tændt og 2 er ikke tændt. Hvis du nu sammenligner med Move instruktionen, så siger den at 1 og 2 SKAL være 0, altso ikke tændt. Så denne her er IKKE en Move instruktion.  I Control Unit er der mange af disse Kontrol Elementer, så akkurat denne her kombination er der sikkert en anden instruktion, som har og så styrer det hele.

 

Reslutatet er at INGEN output er tændt. De kan ikke tændes når 1 og 2 ikke er slukket. Dette er vigtigt, fordi disse output er knyttet direkte til registre og andet, og må ikke forstyre andre instruktioner som helst er i gang lige nu.

Dette eksempel lever op til MOVE instruktionen fordi 1 og 2 indput er slukket. Nu er der strøm på output.

 

De 3 indput 3,4 og 5 er Destination Register, dvs. det register vi skal flytte data til, og de 3 andre 6,7 og 8 er det register vi skal hente data fra, som skal ind i destinationen.

 

Men kik på 3,4 og 5, her har vi kun 4 tændt, så vi får 010 som indput. Og du kan se at der er positivt output nederst til højre.

 

Lige dette aktive output er for 010 som destination. Denne ledning er så forbundet med akkurat 010 registret (som kan være A, B,C….osv det har Harry bestemt) , og sat til at SKRIVER. Altså der er ET bestemt register knyttet til akkurat dette output, ikke flere kun et bestemt.

 

Jeg har her lave 3 ud af de 8 mulige kombinationer vi kan have. Jeg har lavet (000), (001) og (010), så jeg mangler stadigvæk 6 stykker, men du ser fidusen. De to andre output er så også knyttet til sit eget Register. Således at (000) styrer måske A, (001) Styrer måske B, og (010) styrer måske C…osv.

 

Så kan man bare lave akkurat det samme for indput 6,7 og 8, og forbinde disse til registrene og i stedet for SKRIVE vælger man LÆSE. Nu vil det register man har knyttet til at læser sende sine 8 bit( 1 og 0) over på Data Bussen og det register som står til at SKRIVE vil gemme disse i sit register.

 

Nu har vi flyttet det WORD (8 bit) som var i et register over i et andet register, og det er akkurat det som MOVE instruktionen gør.

Jeg har taget de 2 andre kombinationer med også, men vil ikke forklare yderligere.

 

Her har vi Destination 000.

 

Her har vi Destination 001.

 


 

MIN IMPLEMENTERING AF MOVE

Her er en oversigt over min metode. Den har en lidt anderlede signatur, men er i princippet det samme. Min har 0011 som definition, hvor Harry bruger 00. Og min kan kun flytte fra 2 (D og B) bestemte registre og over til 2 (C og D) bestemte registre. Lad mig forklare billedet.

1.      Her ser du den tidstilstand vi er i lige nu, det er tidspunkt nr.4 (eller clock 4). Der er en forbindelse direkte fra denne tilstand og ned til Instruktionsregisteret. Du ser den røde linje fra (1) og ned til bunden og så over til Instruktionsregistret.

2.      Instruktions registeret bliver sat til READ/LÆS, og instruktionen bliver IKKE lagt ud på Data Bussen, men går direkte over til KONTROL UNIT som er hele afdelingen oppe i højre hjørne med de  9 kasser (IC), som indikerer at dette system her har 9 instruktioner, en IC pr. instruktion. Grunden til at den IKKE bliver lagt ud på Databussen, er at så kan man ikke bruge den til det vi ønsker, nemlig at flytte fra et register til et andet, fordi nu ligger Instruktionen på bussen. Man kan nemlig kun have én ting på bussen ad gangen.

3.      Instruktionen kommer her til, men fra dette punkt går der nu disse 8 ledninger ud til alle Insruktioner (IC).  Dette er bare en forgrening fra dette punkt og ud, på denne måde gør vi det lidt mere overskueligt at se på, selv om det allerede er ret rodet.

4.      Det er næsten umuligt at se, men den ENESTE Instruktion som bliver aktiv er MOVE, alle de andre laver intet, fordi signature af instruktionen ikke passer til dem. Dvs. at den eneste Control component som har noget output overhoved, er MOVE. Hvis der var andre som også havde output, så ville hele comptueren ikke fungere. Man kan kun have en instruktion i kontrol ad gangen.

5.      Her har jeg dobbeltrykket på MOVE IC´en og så kommer den frem sådan. Du kan se at den er aktiv og flere outputs er tændt. Oppe i toppen er der 3 indput, disse er bare lavet for 3 tidsenheder. Det er vist nok ikke et nødvendig design, kunne sagtens klare os med et indput her. Du kan også se at der er output aktive nede i bunden, som viser os at denne enhed er i gang med at lave et arbejde.

6.      Fra MOVE Kontrol enheden går der nu en ledning som er tændt, og som sætter D registret til at LÆSE. Man kan se hvad der er gemt i D, nemlig 00000011 altså tallet 3.

7.      MOVE Kontrol enheden sætter også C registret til at SKRIVE, og de skriver det som ligger på Data Bussen, og det er indeholdet fra D, som er talet 3.Når denne tidsenhed så bliver færdig, så har MOVE lavet det den skulle, nemlig tage værdien i D og copieret den over i C.

 

 

 

 

 

INPUT/OUTPUT (I/O)

Vi har nu set hvordan computeren behandler programmet og data, men hvordan får man noget ind og ud af computeren. Hvad sker når der f.eks. trykkes på en tast på tastaturet? Her er tastetrykket vores input, og så kan det være at et bogstav vises på skærmen, som så er vores output. Men hvordan fungerer dette? Der findes 3 forskellige måder at styre I/O.

Programmed I/O

Interrupt-driven I/O

DMA I/O. (ikke gennemgået her)

Den simpleste at forstå, og den som blev brugt i de første computere er Programmed I/O og lad os undersøge den nu.

 

PROGRAMMED I/O

Hele fidusen her er at man betragter input og output hukommelsen, som en del af hukommelsen, men med sit eget adress område. Det betyder at for CPU´en tilgår den I/O på samme måde som den tilgår Main Memory, så der er ingen forskel på I/O og Main Memory, set fra CPU´en. Dette gør systemet ret rent og nemt at forstå, men der er nogle vanskeligheder, som vi kommer ind på senere.

 

Arbejdsgangen for CPU´en når den skal hente eller aflevere fra I/O er følgende cyklus. Denne her cyklus køres så hele tiden om og om igen: Her kommer cyklusen/loop´en

 

Address a Device.

Check its status.

If ready, do the data transfer. (én enkel karakter pr. cyklus)

 

Ud fra disse 3 handlinger kan du se at den eneste forskel på en almindelig Main Memory tilgang, er punkt 2. hvor der tjekkes om der er ok at gøre noget.

 

Men hvad er det som gør disse 3 skridt? Det er et program – lige som et hvilken som helst andet program, derfor kaldes det Programmed I/O – som ligger i Main Memory, og som så bliver udført, og udfører disse 3 skridt, om og om igen. Og ikke nok med det, men det gør dette for alle de elementer (devices) som er knyttet til computeren, f.eks tastaturet, CD-rom, USB osv.

Se billedet ovenover her. Her ser vi CPU´en som er knyttet til BUS´en og Memory og så flere andre I/O´er. Når CPU´en skal hente fra Memory, bruges der samme BUS som ved I/O og groft sagt samme tilgang, som jeg har været inde på.

 

Et mere detaljeret eksempel kommer efterfølgende her.

En vigtig ting her, er at vide at de forskellige enheder på Bussen, har sit eget adresse område. Vi ser at Main Memory har fra 00000000 til 00000100 i hvert fald(Har ikke taget de første 4 bit med, men de er null alle sammen). Tastatur I/O har fået én adresse fordi den behøves ikke mere, nemlig 00001000, og skærmen har fået én også, nemlig 00001001.

 

PULLING. Det er altså CPU´en som hele tiden Spørger om den må hente eller aflevere data fra I/O´erne. Det vigtigste her er at forstå, at det er CPU´en som tager initiativet hele tiden.

 

INTERUPT-DRIVEN I/O

Vi skal ikke bruge tid på denne, men bare sige, at her sætter CPU´en et register hos I/O som siger at CPU´en ønsker at blive interrupted når I/O har noget nyt at aflever, eller er klar til at modtage. På denne måde er CPU´en fri til at lave andet arbejde, i stedet for hele tiden at bruge kræfter til at spørge om I/O har noget der skal laves. Så denne tilgang er bare en udvikling fra Programmed I/O som gør at CPU´en ikke spilder alt for meget tid på at skulle ud til I/O devices at spørge om der er noget nyt at lave.

 

 

 

 

 

 


 


5. Mic-1 Computeren

 

Så er vi kommet til den computer som bogen bruger mest tid på og som der også er en simulator til. Hvordan adskiller den sig fra Harry Porters computer? Ikke serlig meget, kun ved én væsentlig ting. Den har nemlig ét lag mere, det er det. Lad mig forklare.

Som du ser på billede ovenover, så har Mic-1 Level 0, 1 og 2 og så også Assembly, men det kunne Harry Porter sagtens efterfølgende udvikle, så det er ikke afgørende her. Se så på Harry Porters Computer, her mangler han Level 1 Microarchitecture level.

 

Begge har altså ISA (Instruction Set architecture) og det har alle computere, fordi dette lag er det lag som alt andet ovenover bruger, altså Operativ Systemet bruger ISA instrukserne og ikke Microarchitecture instrukserne, de er ikke tilgængelige for nogen, kun for ISA laget. Så ISA er det man kalder Maskinens Instrukser. Og det har de begge selvfølgelig.

 

Men hvad sker der med Micro laget, hvorfor har vi brug for det? Det er der også store diskussioner om, du kan læse mere om det på side 58 under afsnittet (2.1.3 RISC versus CISC). Men overordnet troede man at computeren blev hurtigere om man lavede de mere komplekse instrukser – så som at gange – ned på dette lag, men nu er man faktisk gået over til at dette helst ikke er optimalt, og flere går over imod Harry Porters model. Årsagen er, at ISA skal fortolkes ned til Micro, og det tager ofte mere tid end man sparer ved at lave instruktionen på Micro laget. En anden fordel med Micro laget er at man så kan implementer Micro laget lige som man vil (lægge ledninger som man vil), men bare ISA instruktionerne er de samme, så kan alle Operativ Systemer bruge det.

 

Micro instrukserne har en smart ting som ISA instrukserne ikke har, den har nemlig adressen til næste instruktion i sig. På denne måde behøves man ikke at have en Program Counter på dette lag, og man sparer dermed sikker også en del tid.

 

Så når vi nu skal til at kikke på Mic-1, så fungerer den groft sagt akkurat på samme måde som Harrys, men kan lidt flere ting også.

 

Vi har også den luksus med Mic-1 simulatoren at vi kan programmere den med Assembler kode, det kan vi ikke med Harry´s, fordi han må indsætte instrukserne som bits (tændt eller slukket).

 

Vigtigt: En ting mere som er ret godt med Mic-1, er at vi selv kan se hvordan de 3 lag arbejder sammen (Assembler, ISA og Micro). Når vi laver et program i Assembler kan vi compile det til ISA instrukser og se disse i Vinduet, og så ser vi også hvordan disse ISA instrukser bliver til flere micro instrukser. Således ser vi med vores egne øjne at én instruks på et højere nivo, bliver til flere instrukser på et lavere nivo.

Se billedet nedenfor her, som viser hvor det forskellige lag ses/bruges af Mic-1 simulatoren.

VhnxQtWV7NipzO0pkYz9OMq7_kVxJbSvpFkMtRzho_keJm16OGBMCkIhuXzmJd1yvOeyCktgUZ7aI9SDkC8ipxG2lXTQUBCnoxq6jzOGvSpnrqj7vBag

Her ser du at jeg har lavet et lille Assembler program (helt til venstre) og hvad det bliver compilet til (Midt i vinduet. ISA Instructions) og så ser du også Mircroprogammet som er yderst til højre. Dette program ændrer sig ikke. Det er altid det samme, lige som vores ledninger altid er forbundet ens, hvor det bare er tænd og sluk som ænder sig. Hvis du kikke godt på Microprogrammet, så ser du også at alle instruktionerne slutermed en goto, som er den efterfølgende instruktion, altså Microprogrammet bruger ikke en Program Counter som ISA laget. På billedet kan vi også se Stack Area og Constant Pool, dette er en lidt mere avanceret måde at arbejde med data på, hvor det er en del af Main Memory bliv bruges til at holde disse værdier, dette er nemmere for programmet at gøre det sådan, men ikke noget vi behøves at gå i dybden med. Billede til venstre(det med C Bus og B Bus) ligner ret meget de arkitekturer vi har set før, og der er også en ALU og en dedikeret C og B bus. Man kan også køre programmet på forskellige måder, det mest interessante er Clock og SubClock, hvor SubClock er det mest detaljerede man kan følge en instruktion. Man kan også have input og output fra programmet mens det kører, lige som vi har det i vores normale computer, det indsættes nederst mit på billedet, men er ikke kommet helt med på tegningen.

 


 

HVORDAN HOPPER MAN FRA ISA TIL MICRO OG FRA MICRO TIL ISA?

Som det fremgår tydeligt på billedet med de forskellige lag, så er ISA og Micro lagene, to forskellige lag. Det er derfor oplagt at der må ske en eller anden slags kommunikation imellem disse, men hvordan se den ud i Mic-1?

 

Fra Micro til ISA

 

For én ISA er der flere Micro instruktioner. Når så den sidste Micro instruktion er færdig, står der i denne, at nu skal MBR bruges. Og MBR er den instruktion som PC peger på, altså den næste ISA instruktion.

 

Lige som Micro instruktionerne selv peger på den næste Micro, så er den sidste Micro altså lidt anderledes ved at den ikke peger på den næste Micro, men den næste ISA.

 

 

Fra ISA til Micro

 

Hver ISA instruktion har et nummer (her er det 10). Dette tal er akkurat det samme nummer som Micro instruktionen har. Så på den måde er det simpelt, bare at tage nummeret på ISA instruktionen og flytte det ned tim MPC som så loader selve instruktionen in i MIR registeret. Og nu når Micro 10 kører vil den automatisk pege på den næste micro og så til sidst igen pege på en ISA, og så kører det rundt og rundt indtil hele ISA programmet er slut.

 


 

SUB-PROGRAM

STACK: En vigtig ting som Mic-1 har som Harry ikke har, er en stack. Harry snakker selv om dette i hans video, at han har det meget svært ved at håndtere Recursive metoder. Men det kan Mic-1 ret nemt fordi den har en stack til at holde styr på de forskellig metode kald. Recursive metoder er lige som når en metode kalder en anden metode som igen kalder en anden metode, fordi den først metode er ikke færdig men venter intil nr 2 er færdig, mens nr.2 venter på nr.3. Og når nu der kun er en CPU, så må tilstanden som nr.1 og nr.2 og nr.3 er i gemmes et eller andet sted. Til det bruger man en Stack, hvor den aktive metode er øverst i stakken og den første er nederst i stakken, således at når stakken er tom, er hele metode rækken færdig. Recursive metoder er akkurat det samme men her er det bare samme metode som bliver kaldt flere gange, men de forskellig metode kald har forskellige tilstande som må huskes. Se billede nedenfor.

Figur 4-8 (a) har én metoden som vi kalder A. Altså A kører lige nu, men så kalder A metoden en anden metode B (b), og nu rykker B´s variabler ind i stakken og ligger ovenover A. Vi har SP og LV til at holde styr på hvor den aktuelle metode starter og slutter. B metoden kalder så C metoden og vi har billede (c) nu.  Billede (d) er efter at C og B er færdige og A kommer tilbage på banen, og som så kalder endnu en metode nemlig D.

 

Når en metode kalder en anden metode som igen kalder en anden metode, ser det ud som i billedet nedenfor her.

.DSC_0115-1

Det som er vigtigt her, er at Subprogram A har sit eget område af lokale variabler og en pointer/adresse til det sted som kaldte på den (l1). For at holde styr på disse lokal variabler og pointeren tilbage bruger Mic-1 en stack. Men hvordan fungerer det? Det ser du på billedet efterfølgende.

SubProgram i Mic-1.jpg

Her ser du Mic-1 med et program som kalder en metode (adddigits(num 1, num 2)). Billedet viser tilstanden lig før return er færdig, altså vi er i slutningen af metoden, og er ved at gå tilbage til Main programmet som kaldte metoden. For at holde styr på de lokale variabler, bruger CPU´en 2 registre nemlig LV og SP, så det som er indenfor området af LV og SP er det som tilhører metoden som kører lige nu. Du kan se at der er både 3 og 4 inde i området og også 7 som er summen af disse to. Dertil ser du en reference til det sted som kontrollen skal tilbage til nemlig ’a’. Stakken gemmer også den oprindelige LV, og den oprindelige SP er nem, fordi det er bare LV lige nu (8011). En lille opklaring, SP peger på 8016 men der står 20058 i stakken. Men det får vi ved at tage 8016 som hexidecimal og gange det med 4 så får vi nemlig 20058.


 

SUB-PROGRAM EKSEMPEL FRA MIC-1

Et uddybende eksempel på hvordan stakken opfører sige i Mic-1 kommer efterfølgende her. Det passer udmærke med det gennerelle vi har snakke om ovenover.

Først skal vi kikke på selve programmet. Du ser her til højre hvordan koden ser ud i Assembly, og hvordan denne bliver om til ISA instrukser som Mic-1 bruger.

 

Main kalder plus metoden og plus kalder plusTo metoden. Så vi har et  eksempel her som ligner Fig.9.2 fra ovenover. Koden kommer her:

 

.main

    BIPUSH 0x02

    BIPUSH 0x03

 

    INVOKEVIRTUAL plus

 

    BIPUSH 0x30 //Convert til Numbers, ANSI.

    IADD

    OUT    

    HALT

.end-main

 

.method plus(num1, num2)

    ILOAD num1

    ILOAD num2

   

    INVOKEVIRTUAL plusTo

   

    ILOAD num1

    IADD 

    IRETURN

.end-method

 

.method plusTo(num3)

    ILOAD num3

    ILOAD num3

    BIPUSH 0x02

    IADD

    IRETURN

.end-method

SubProgramMic1_AssemblyToISA.jpg

Tilstand 1:

Programmet er klart til at køre. PC peger på 0 = fffffffff.

 

Man kan ikke rigtig se det fordi addresserne falder sammen, men endelsen af Invoke indeholder addr. til Constant Pool (CP), og i CP er adressen til metoden.

Det er lidt misvisende at denne her har 000c og så starter den rigtig

i 0010, disse NOP og Error springes over (ved ikke hvorfor det er lavet sådan).

Tilstand 2

Vi er nu kommet til 1.metode kald. Den skal til at begynde nu.

Har som du ser lagt værdierne 2 og 3 i stakken.

 

SubProgramMic1_01.jpg

Tilstand 3

Selve Metode kalt instruktionen er nu gennemført, og vi er lige kommet ind i selve metoden.

LV og SP har flyttet sig til et nyt område. 8013 holder returnering addressen.

SP peger på 8014 som er forige metodes LV. SP findes ved at bruge LV nu. LV peger på den stak address som har returnerings addressen.

 

SubProgramMic1_03.jpg

Læg mærke til at LV peger på 8010 som er 2 nedenfor SP var. Det giver mening fordi metode tager 2 parameter ind, og disse får vi ved at sætte LV til at inkludere disse værdier.

Tilstand 4

Vi er stadigvæk inde i 1. metode, men nu skal vi til at kalde 2.metode.

SubProgramMic1_04.jpg

Tilstand 5

Så er 2. metode sat op. Vi ser at LV og SP nu igen har rykket sig til et nyt område. Læg mærke til at LV denne gang (i modsætning til 1. metode) kun flyttet sig således at én værdi er til gængelig fra forige stak område. Og det passer fint fordi denne her metode kun har én parameter.

SubProgramMic1_05.jpg

LV har addressen som holder returnerings addressen. 8017 holder så selve returnerings addressen 17 i programmet. SP har forige LV.

Tilstand 6

Metode 2 er kommet til return nu. De udregniner som skulle laves er lavet og resultatet ligger i 801A som er værdien 5. Dette er returnerings værdien som metode 1 skal have.

SubProgramMic1_06.jpg

Tilstand 7

Så er return fra metode 2 færdig. PC peget på 17 som var gemt i 8017. LV er nu tilbage på 8010 som var gemt i 8018. Og ikke mindst så er værdien 5 placeret i toppen af stakken, der hvor SP peger. Se også at SP er lige der som forige LV var.

SubProgramMic1_07.jpg

Tilstand 8

Metode 1 er nu klar til return, og har lavet det de skulle. Den har nu værdien 7 som den skal returnere til Main programmet.

SubProgramMic1_08.jpg

Tilstand 9

Nu er vi tilbage i Main og på toppen af stakken ligger værdien 7, som vi fik fra Metode 1.

SubProgramMic1_09.jpg

Tilstand 10

Programmet er nu stoppet, og vi har fået 7 ud på skærmen (Output Console), ved at 30 er flytte på stakken, og så ADD på 30 og 7 som giver 37 på samme position som 7 var. Og så blev SP værdien printet ud, og derfor er SP et laver end hvor 37 er. Grunden til vi får 7 ud, selv om det er 37 som printes ud, er at Hexidecimal af 37 er 55 i decimal. Og 55 giver 7  i Ansi tabellen. Her kommer et lille uddrag fra ANSI tabellen.

 

SubProgramMic1_10.jpg

 

En oversigt over hvordan stakken opfører sig fra eksemplet ovenover. Du kan se at det ligner ret meget fig.4-8 fra ovenover.

Mic-1 stack Oversigt.jpg

Det du skal lægge mærke til er at vi har 3 forskellige områder. Først er det Main som har LV 8000 til SP 8012, siden er det den første metode som har LV 8010 til SP 8016 og så den næste metode har LV8015 til SP 801A. Og når vi returner så går vi tilbage til den oprindelige position, i hvert fald LV er 100% stabil. SP er jo stakken som kan variere, som er formålet med SP.

 


6. Parameter Transmision

 

Afsnittet ovenover om Subprogram i Mic-1, kunne du se hvordan parametrene blev sent til metoder. Det var ikke specielt avanceret, faktisk bare en kopi af variablen blev brugt. Men det skyldes helst det eksempel vi brugte, fordi vi ikke prøvede med et objekt, kun med tal. Men det vi skal snakke om her, er de forskellige filosofier bag parameter transmission. Forskellige programmeringssprog har forskellige tilgange til dette emne. Og nogle af de ældre sprog var lidt mærkelige set i vores C# øjne.

 

I bogen “Programming Languages af Pratt (PLP)” siger han sådan: Når en metode kalder en anden metode og sender en parameter, bruges der 2 måder til at løse det:

1.      Parameteren kan blive evalueret og værdien sendes med til den nye metode. Eller

2.      Man sender selve parameteren med som metoden selv kan bruge.

 

EVALUATION

An expression in a programming language is a combination of explicit values, constants, variables, operators, and functions that are interpreted according to the particular rules of precedence and of association for a particular programming language, which computes and then produces (returns, in a stateful environment) another value. This process, like for mathematical expressions, is called evaluation. The value can be of various types, such as numerical, string, and logical.

 

For example, 2+3 is an arithmetic and programming expression which evaluates to 5. A variable is an expression because it denotes a value in memory, so y+6 is an expression. An example of a relational expression is 4≠4, which evaluates to false.

 

http://en.wikipedia.org/wiki/Expression_(programming)

 

PLP beskriver disse 6 typer:

 

·        call by name,

·        call by reference,

·        call by result.

·        call by value,

·        call by value-result,

·        call by constant-result

 

Call by name:

Den mærkeligste af alle. Her evalueres variablen ”hver gang” den bruges af metoden. Lige som hvis du sender en funktion/metode med som parameter, så kører den hver gang du kalder den i metoden. Forskellen er at man ikke kan se at det er en funktion som sendes med, fordi det ser ud som en almindelig parameter med et almindeligt navn, altså uden parenteser, kun et navn. Se video her..

 

Call by reference:

Her send en pointer til data objektet location. Bruger l-value. C# har denne, når man sætter ref eller out foran.

 

Call by result:

Her er variablen som sendes med ikke engang blevet initialiseret. Altså, det er bare int a, uden at a er sat til noget endnu. Men vi her kun interesseret i variablen når vi får den tilbage, og da skulle den helst indeholde noget som kalderen kan bruge.

 

Call by value:

Her tages en kopi når parameteren evalueres. Bruger r-value. C# har denne som standard. Læg mærke til, at når vi sender objekt referencer i C#, så er det faktisk by value og ikke by reference som man skulle tro. Der er markant forskel. Du bør prøve at sende et objekt som ref, og se hvad der sker.

 

 

 

Call by value-result:

Det samme som value, men når metoden er slut, kopieres den lokale værdi tilbage til kalderens. Altså, metoden kan ændre variablen lokalt som den vil, men ændringeren vil først blive sent tilbage til sidst. Det giver selvfølgelig den fordel at der ikke skal bruges tid på at opdatere kalderen hele tide, til ingen nytte fordi det er jo den sidste tilstand som er interessant.

 

Call by constant-result:

Her modtages en konstant, og den sende så tilbage til sidst. Kan bruges til at fastsætte en konstant ved at vente indtil metoden svarer.

 

 

 

 


 

C# PARAMETERS EKSEMPLER

C# har de to metoder (Call by Value & call by Reference). Call by reference er mest interessant fordi vi kender meget godt til den anden.

 

Her kommer et eksempel som viser begge metoder. Se hvordan REF er en dybere reference end en almindelig objekt reference som bliver sent via parameteren.

 

Call by Value &  Call by Reference

    class Program

    {

        static void Main(string[] args)

        {

            Bil bilB = new Bil();

            bilB.navn = "FORD";

            bilB.alder = 1978;

            Console.WriteLine(bilB.navn + " " + bilB.alder);

            MethodB(bilB);

            Console.WriteLine(bilB.navn + " " + bilB.alder);

 

            Bil bilA = new Bil();

            bilA.navn = "TOYOTA";

            bilA.alder = 2012;

            Console.WriteLine(bilA.navn + " " + bilA.alder);

            MethodA(ref bilA);

            Console.WriteLine(bilA.navn + " " + bilA.alder);           

        }

        static void MethodB( Bil b) //--Call by value--

        {

            b = null;

        }

        static void MethodA(ref Bil b) //--Call by reference--

        {

            b = null;

        }

    }

    class Bil

    {

        public String navn ;

        public int alder ;

    }

Som du ser her, så går det galt. Der mangler en reference, og det gør det fordi MothodB sletter den, og så er den også væk for BilB, hvor BilA ikke mister sin reference selv om MethodA også sletter referencen.

 

Årsagen er den, at med ref er det den orginale reference som vi får tilsendt og ikke en kopi.

 

OUT er også noget som findes i C#, og er også en call-by-reference, med den eneste forskel, at variablen som sendes ikke behøves at initiliseres først.


 



7. Operativ Systemet

 

Operativ systemet er noget mærkeligt noget. Det ligger imellem Assembly og ISA hos Tanenbaum, men hvis vi kikker på Mic-1 så er der intet OS i brug der. Det må betyde at det ikke er nødvændig. Men hvorfor har han lagt det ind i mellem Assembly og ISA forstår jeg ikke og det står bestemt ikke beskrevet i bogen.

 

En anden m odel findes i Alan Clements bog, se billede fra bogen nedenfor.

Tanenbaum

Alan Clements

 

 

Nå men vi kan konstatere at der er ikke enighed om hvor OS skal placeres, men lad os slippe den diskussion og kaste os over hvad OS laver.

 

HVAD LAVER OPERATIV SYSTEMET

Overordnet vil computeren ikke være meget værd, om vi ikke havde et operativ system, fordi alle programmer som vi bruger til daglig, bruger OS.

 

Programmer som bruger OS (som næsten er alle programmer) bruger de metoder som OS tilbyder. Der er 2 typer metoder OS tilbyder, nemlig ISA metoderne som ligger nedenfor OS, og så har OS også lavet sine egne metoder (som selv bruger ISA selvfølgelig) som kaldes System Calls. Det betyder at ISA metoderne er for specifikke til at systemerne ovenover kan bruger dem på en let måde. Et godt eksempel er, når vi i C# henter eller skriver til en fil, så er det ret nemt. Vi skal måske bruge 2-3 metoder så er det fikset. Denne simple adgang til filer har ISA slet ikke. Faktisk eksisterer begrebet FIL slet ikke på ISA nivo. Men med OS får vi dette begreb.


 

HVORDAN KØRES ET PROGRAM AF OS

Lad os først undersøge hvordan et program er gemt i Main Memory (RAM).

 

Alle programmer starter fra adresse 0 (set fra dem selv), men I hukommelsen kan de jo ikke alle starte fra 0, fordi så var der kun et program inde ad gangen og det går ikke.

 

For at løse dette problem har man en pointer til start og slut af programmet. Og hvis nu et program virkelig starter ved adresse 330, så lægger man bare denne konstant til alle adresser når de skal køre.

 

Dette giver en sikkerhed fordi, at hvis et program prøver at snyde og tilgå en adresse som er udenfor sin egen, så vil CPU´en fange dette, fordi den ved i hvilket område det aktuelle program må arbejde (kender start og slut). Et almindeligt program må IKKE arbejde med adresser som er udenfor dets eget område. Forestil dig at et program begyndte at ændre i Operativ Systemet, det går ikke.

 

Denne egenskab vi har illustreret her er Hardware implementeret og ligger imellem CPU og Memory og kaldes MMU (Main Management Unit). Og det er operativ systemet som styrer MMU´en.

 

 

 

 

Lad os nu undersøge hvordan vi får lavet et program og kører det fra RAM. Der kommer efterfølgende nogle billeder hvor jeg prøver at illustrere dette ret komplekse område.

 

Det første man gør er at lave et program (High level program) som kan gemme på Harddisken.

 

Så bliver man nød til at Compile det til noget som kan køre af CPU´en og kan ligge i Main Memory.

 

Vi har nu gemt et program på harddisken som er lavet af Maskin koden (ISA instrukser).  Dette kan nu køres.

P.S: En lille bemærkning. Java og C# er ikke helt så simpelt. Men jeg vil ikke her komme ind på emnet, fordi det forvirrer mere end gavner i vores ønske at forstå dette område.

 

 

Når du dobbelt trykker på et ikon for at køre et program sker følgende.

 

OS tager maskin koden som ligger på harddisken og indsætter den i Main Memory (RAM). Den får sin egen plads, som jeg har været inde på ovenover. Du kan se her, at nu er der 2 programmer i RAM samt OS selvfølgelig.

 

Så er det også OS som sætter programmet i gang, se næste billede for hvordan.

 

 

OS sætter nu vores program i gang, ved at opsætte CPU´en til at køre vores program.

 

Jeg har medtaget et lille udkast af hvad der sker. Du kan se at Inst registeret nu indeholder den første instruktion af vores program. Du kan også se at PC peger på næste instruktion, som er den næste vi vil køre, efter den første er kørt, hvis det altså ikke er en branch instruktion vi har lige nu.

 

Address som jeg har tegner er kun 3 bit (der var ikke plads) men de er selvfølgelig meget større. I inst registeret er de 10 bit, men de kan godt være større, men jeg tror du forstår princippet.

Et vigtigt emne som vi kan undersøge her, fordi vi har billeder som hjælp, er multi-processing. Forestil dig at OS nu syns at vores program ikke må køre mere, men at et andet program skal køre, så kan OS bare sætte PC til den adresse som det andet program har og så kører det. Men hvad nu når OS syns at vi må køre igen? Hvorfra skal vi nu køre? Skal vi starte fra adresse 0000000000 igen? Det ville være meget ubrugeligt. Nej OS må nemlig huske hvor vi var kommet. Vi var nemlig kommet til Adresse 0000000001 som PC stod på når vi blev stoppet. Og dette gør OS nemlig.

 

OS gemmer og indsætter de tilstande de to processer har (PC, Stack Pointer, register indehold) som skal skifte med at køre. Du kan se at det er et meget omstændeligt arbejde OS har, hver gang en proces skifter, med først at gemme og siden at indsætte tilstanden.

 

Så er vi kommet til det sidste skridt i kørsel af et program.

 

Et program som vores kører i User Mode. Det betyder at der er en del ting vi ikke må. Vi kan f.eks. ikke tilgå Harddisken. Hvis vi ønsker det må vi lave et System Call. Det betyder at vi må bede OS om at hente de data vi ønsker.

 

For at lave et System Call, kan man ikke bare kalde på OS. Vi kan jo ikke bare flytte PC til det område som OS har, fordi vi må nemlig ikke pege på en adresse som ikke er indenfor vores eget adresse område.

 

Man må lave en Trap/Interrupt. Det er bare at man ændrer en tilstand i et register og så vil CPU´en se at nu ønsker vi at få hjælp fra OS. OS tjekker nu i TRAP´en, hvad det er vi vil og OS er nu selv i Kernel Mode som betyder at OS kan bruge alle ISA instruktionerne som findes (det kan User mode nemlig ikke).

OS henter nu den data som vi har bedt om, og flytter den ind i et område som vi har adgang til. Så starter OS vores program igen, der hvor vi slap (når vi lavede System Call´et) og vi kan nu bruge den data vi har fået.

 

En lidt interessant ting: User Mode og Kernel Mode er noget som er bestemt i hardware. Der findes nemlig et register hos CPU´en som hedder PSW (Program Status Word) hvor der er én bit som bestemmer om man er i User eller Kernel mode. I User Mode kan man læse denne, men selvfølgelig ikke ændre den.

 

User Mode giver ikke adgang til de ISA instruktioner som f.eks. tilgår en harddisk, derfor må OS hjælpe User programmerne.

 

 

Interrupt = Asynchrone

Trap = Synchrone.


 

 

FILER

Det er nemlig OS som giver os filer, men en fil er et virtuelt begreb. Der findes ingen fil på harddiske, alt ligger gemt forskellige steder på disken. Men OS har en mekanisme som holder styr på hvad en FIL er og hvor de forskellige data ligger og henter disse og giver det til os i en lang strøm af data, således at vi tror det er gemt sådan også.  

 

Grunden til at OS og ikke ISA laget tager sig af filer, er at ISA instruktionerne er simple.

 

EKSEMPEL: Forestil dig en bibliotekar som arbejder i et bibliotek hvor alle bøgerne er nummererede og står på gulvet i sorteret orden. ISA bibliotekaren kan kun få at vide hvad nummer bogen er som han skal hente og så henter han den. Og han kan kun hente én bog ad gangen. Du kan altså ikke sige til ISA bibliotekaren at han skal hente alle bøger til og fra et nummer, fordi han kun kan bære en bog ad gangen. For ham eksisterer der ikke en samling bøger (fil som er en samling ord). Men med OS får vi denne egenskab at hente en samling. Det får vi, fordi OS gemmer et navn (filens navn) og hvor alle orden (bøgerne) som tilhører den ligger. Nu kan vi så sige til OS at vi ønsker en fil, og så er det OS som sætter ISA bibliotekaren til at hente alle de enkelte ord (bøger) og samler det og aflevere det til os. 

 

Denne egenskab som OS har, ved at den holder styr på hvad hører sammen, ser vi også i styringen af forskellige samtidige processer.

  

Filer gemmes i Directory (Mappe) og hver fil har et navn, længde osv. Se til højre at det også indgår hvor på disken filen ligger, og man kan se at filen ikke er en samlet mængde af data, men er spredt ud over 4 forskellige sektorer.

 

Som du kan se på det nederste billedet så kan en Directory gemmes i en træ struktur, som vi jo alle kender når vi arbejder med filer på vores egen computer.

 

 

BRUGERE

OS har også styring over rettigheder. Det betyder at vi til f.eks. en fil kan bestemme hvem  der  har adgang til den og hvem der kan rediger den. Det har vi nok alle prøvet, men dette begreb eksisterer ikke på ISA men er noget som OS giver os.

VIRTUAL MEMORY (PAGES)

OS snyder os som bruger til at tro at der findes filer, men OS snyder også selve CPU´en til at tro at den har meget mere Main Memory end den har. OS giver CPU´en storhedsvanvid J. CPU´en har ofte en Adresse Bus som er meget større end den har Main Memory, så det burde ikke kunne lade sig gøre, men her kommer OS ind og sørger for at gå ud på Hard disken efter de instrukser og Data som ikke findes i Main Memory, således at CPU´en ikke skal bekymre sig om det.

 

De addresser som CPU´en bruger kalder men Virtuel Addresser, men i stedet for at flytte én instruktion ad gangen, så har man fundet frem til at det er bedre at hente en SAMLING af addresser hver gang man alligevel skal hent fra Hard disken, disse samlinger kalder man for PAGE som her har en størrelse af 4096 addresser.

 

 

 

Fig 6-3 viser til venstre at CPU´tror at den har mere end 15 Page´s mens man til højre ser, at i virkeligheden er der kun plads til 7 Page´s i Main Memory.

Hvis nu CPU´en ønsker adresse 53248, så findes den ikke i Main Memory, og kan ikke køre. Nu må CPU´en vente indtil OS har har hentet den PAGE (13) ind i Main Memory, og så giver OS besked til CPU´en at nu er klart at hente instruksionen.

For at CPU´en ikke for ofte skal stå og vente, så har OS forskellig regler hvor den prøver at forudsige hvilke addresser/Page der snart skal bruges før CPU´en skal bruge dem. Den må selvfølgelig også smide ud, og der prøver den at smide dem ud som ikke skal bruges.

 

Lad os se et eksempel (Figure 6-4).

 

Hvis CPU´en ønsker en adresse som er i VIRTUAL PAGE 3, så får den at vide at den skal hente den i den Fysisk memory position 6 også kaldt PAGE FRAME. Den får altså aflevere et 15 bit WORD hvor de 3 første er PAGE FRAME´en, mens de andre 12 er Selve addressen. Vi ved at hver Page Frame indeholder 4096 addresser og 2 i 12 = 4096. Så når CPU´en ved hvilken Page Fram den skal kontakte, så kan de også gå direkte ind til den af de 4096 addresser den skulle ønske.

 

OS har altså hele tiden styr på denne her Page Tabel så at det kan gå hurtigt.

 

Grunden til at vi har 12-bit-offset, er fordi når CPU´en kører, så arbejder den på én instruktion/data ad gangen, og derfor kan den ikke bare kalde en PAGE, men må først få Pagen, og så

 

kan den gå præcis ind i til den adresse (offset) som den ønsker

.

VIRTUAL MEMORY (SEGMENTATION)

 

Et problem som mangler i Paging som vi har undersøgt ovenover, er det rod man får når ALT er indenfor ét adresse område.

 

Figure 6-7 viser at vi kan få et problem med at de forskellige områder (Source text, Call Stack …)kan komme til at gå ind i hinanden. Det kan løses ved at man bygger virtuelle SEGMENTER som er adskildt. Disse segmenter har sit eget adresse område, som er adskildt og ikke kan vokse ind i hinanden.

 

 

Lige som vi har diskuteret før, med I/O devices og Main Memory har sit eget adresse område

 

 

 

Figur 6-8 viser hvordan segmenteringen ser ud. Her har vi opdelt et program i 5 forskellige dele, som hver har forskellige egenskaber. De forskellig Segmenter har deres egne Adresse områder, som starter et sted og har en eller anden maximum som er stor nok til fleste alle programmer. En anden vigtigt ting man får med Segmentering er ADGANGSKONTROL. Et eksempel er et program, som vi ved er opdelt i minimum program kode og Data, koden ændrer sig ikke mens data gør, og med

 Segmentering kan man nu beslutte at det segment som holder koden ikke må skrives til men kun læses fra. Og man kan også DELES om kode således at man sparer en masse plads, f.eks. flere browsere som kører, kan deles om selv koden, men data er gemt i forskellige segmenter. En lille ekstra ting er, at nogle systemer bruger Pages som den mindste enhed i et segment, dvs. at et segment er opbygget af minimum én page, man kan altså ikke have mindre enheder end en page i et segment.

 

 

 

 

 

 

PARALLEL PROCESSER

En mekanisme som OS også kan gøre, er at køre flere programmer samtidig, eller faktisk snyder den igen her, fordi de kører ikke samtidig men skifter så hurtigt, at vi tror de kører samtidig. Se fig 6-23 (b), hvordan de enkelte prosesser får en lille bid af CPU´e, mens vi oplever det som (a).

 

OS holder hele tiden styr på de forskellige tilstande (PC, Stack Pointer, Register) som de forskellige processer har. Det er lidt som med Filer hvor OS også holder styr på hvad der tilhører de enkelte filer.

 

Men efter som det er sådan at processerne bliver splittet op, får vi et andet problem, som kaldes Race Condition, her ser du en god deffinition på emenet.

 

 

http://support.microsoft.com/kb/317723

A race condition occurs when two threads access a shared variable at the same time. The first thread reads the variable, and the second thread reads the same value from the variable. Then the first thread and second thread perform their operations on the value, and they race to see which thread can write the value last to the shared variable. The value of the thread that writes its value last is preserved, because the thread is writing over the value that the previous thread wrote.

 

Lad mig prøve at forklare problemet med en tegning.

 

Proces 1 kalder metoden men så stoppes den, så kalder proces 2 metoden og får nok tid til også at sætte tal op til 2 men så stoppes den. Så er det P1 som sætter tal op til 3, så er det P2 som returnerer tal, men ville forvente at den returnerede 2, men faktisk er det 3 fordi P1 er kommet ind i metoden samtidig med at P1 var inde. De var i konkurrence (Race).

 

For at håndtere disse situation når flere processer har adgang til en ressource/variabel samtidig, har OS udviklet mekanismer til at LUKKE adgangen. Man kan f.eks. i C# lukke en hel metode, således at KUN en tråd kan være inde ad gange. Der findes andre LUKKE mekanismer, men det er ikke vigtigt her, det som er vigtigt er at du ser problemet og at OS også kan løse det.

 

 

OS TJENESTER OG OPBYGNING

Her nedenfor har du en illustration af Operativsystemet.

 

Operativsystems tjenester og opbygning.jpg

3 OPBYGNINGS TYPER

 

Der findes 3 mulige typer af OS opbygninger. Monolithic, Microkernel og Hybrid Kernel(f.eks.Mac OS X).

 

File:OS-structure2.svg