1.43k likes | 1.66k Views
Maskinnära programmering i C. Föreläsning 5 Mats Brorsson. IS1200 Datorteknik. F1. F2. Ö1. F3. Ö2. Assemblerprogram. F4. Ö3. lab nios2time. C. F5. Ö4. hemlab C. In- och utmatning. F6. Ö5. Ö6. lab nios2io. Avbrott och "trap". F7. Ö7. lab nios2int. Cacheminnen. F8.
E N D
Maskinnäraprogrammering i C Föreläsning 5 Mats Brorsson
IS1200 Datorteknik F1 F2 Ö1 F3 Ö2 Assemblerprogram F4 Ö3 lab nios2time C F5 Ö4 hemlab C In- och utmatning F6 Ö5 Ö6 lab nios2io Avbrott och "trap" F7 Ö7 lab nios2int Cacheminnen F8 Ö8 hemlab cache Trådar, synkronisering F9 Ö9 hemlab trådar F10 Ö10 tentamen
Hemlaboration 1:Maskinnäraprogrammering i C • Pekare, array, struct, mallocmedmera • Lab-PM + C-kodpåwebben, kompileraochkörmedvalfri C-kompilator • Svarapå alla frågor, tänkefter: "Varför?" • Muntligredovisning, 2 studentermed 1 lärare • Läshttp://www.ict.kth.se/courses/IS1200/bokade.txt • Mejlatillis1200@ict.kth.seochbokaGealltidfleraalternativatider
C jämfört med andra språk • Java • objekt, referenser, garbage-collection, byte-code, starkttypsystem • C • ingaobjekt, pekare, malloc/free, maskinnära, stöd för enkladatatyper • Assembler • ingatyperalls, adresser, ingeninbyggdfelkontroll
Den här föreläsningen • Enkladatatyperochdatarepresentation: Heltal, flyttal, • Merkompliceradedatatyper (struct, array) • Satserochblock • Pekare, pekar-aritmetik • Lagring av globalaochlokalavariabler • Stack • Heap • Alla exempelmedhandöversättningtillassemblerkodanvänderNios II assemblersyntax
Rekommenderad litteratur • Häftet"C för densomkan Java" • Kanhämtassom PDF, http://www.nada.kth.se/datorer/haften/java2c/ • Tips för densomvillläsaännumer: • Bilting, Skansholm: Vägentill C • Kernighan, Ritchie: The C Programming Language • Jonas Skeppstedt, Christian Söderberg, Writing efficient C code : a thorough introduction for Java programmers, http://writing-efficient-c-code.com/
C för dig somkanJava Dittförsta C-program main(intargc, char *argv[]) { printf(“hello, world\n”); } Samma program iJava: public class Hello { public staticvoidmain(String[] args) { System.out.println("Hello World!"); } }
Datatyper i C Mats Brorsson KTH
Den här föreläsningen • Enkladatatyperochdatarepresentation: Heltal, flyttal, • Merkompliceradedatatyper • Uttryck, satser, block • Pekare, pekar-aritmetik • Lagring av globalaochlokalavariabler • Stack • Heap
Lär dig denna tabell utantill! Ex: 0110 1000 1010 0001 = 0x68A1 Ett tal som börjar med 0x är i hexadecimal notation Hexadecimala talsystemet
C – inledning • Syntaxenliknar Java • Körningenbörjarmedfunktionenmain • Inga funktionerkörsommaninteanropardem • "Metoderna" kallasfunktioner i C • en Java-metodtillhör en klassochmodifierarobjektmen C haringaklasserochingaobjekt
C – inledning • Inga referenser, men pekare • en pekare är en minnesadress med viss typkontroll • kraftfullt, men lätt att göra fel • Inga objekt, men poster: struct • som objekt utan metoder, innehåller bara data • Ingen "new", ingen garbage-collection • biblioteksfunktionen malloc reserverar minne • reserverat minne måste återlämnas med free
Deklaration av variabeltypDefinition av variabelvärde • Typ-deklaration, såattkompilatornkantypkontrolleraprogrammet • Definition, en deklarationsommedförattkompilatornreserverarminnesutrymme • Initiering, en definition därprogrammerarenangervariabelnsstartvärde • intfoo = 17;
Deklaration och definition int a; /* Deklarationoch definition,kompilatornreserverarplats i minnet för variabeln a */ int b = 17; /* Definition medinitiering,kompilatornreserverarplatsochlägger in startvärdet */ int b; /*Deklarationigen, angersammatyp, tillåtet! */ int b = 85; /* Ny definition, förbjudet! */
Datatyper Grundtyper: • heltal • flyttal Kombinationstyper: • array • struct • union (ejbehandlathär)
minst 8 bit minst 16 bit minst 16 bit (oftast 32 bit) minst 32 bit minst 64 bit Filenlimits.hgervärden för aktuellkompilator#include <limits.h> Exempel: INT_MAXkan ha värdet2147483647 Datatyper: heltal signedchar short int long long long unsignedchar unsignedshort unsignedint unsigned long unsigned long long
minst 8 bit minst 16 bit minst 16 bit minst 32 bit minst 64 bit minst 32 bit minst 32 bit Exempel: gcc 3.4.6 för Nios II(Nios II har 32-bits adresser) • char • short • int • long • long long • float • double • 8 bit (1 byte) • 16 bit (2 byte) • 32 bit (4 byte) • 32 bit (4 byte) • 64 bit (8 byte) • 32 bit (4 byte) • 64 bit (8 byte)
minst 8 bit minst 16 bit minst 16 bit minst 32 bit minst 64 bit minst 32 bit minst 32 bit Exempel: gcc 4.4.3 för amd64(AMD64 har 64-bits adresser) • char • short • int • long • long long • float • double • 8 bit (1 byte) • 16 bit (2 byte) • 32 bit (4 byte) • 64 bit (8 byte) • 64 bit (8 byte) • 32 bit (4 byte) • 64 bit (8 byte)
sizeof() • Operatornsizeof( någonting )ersättsvidkompileringenmed en konstantsomär lika medstorleken i bytesför dentypsomnågontinghar • Exempellong longfsize = sizeof( float ); • Annat exempeldouble r;long longdsize = sizeof( r );
Heltal: unsigned • 1001 1111 0101 0000 1111 0111 0111 0000 • Hexadecimalt: 9f 50 f7 70 • i C: 0x9f50f770 • Tolkas som positivt heltal (2 672 883 568)
Heltal: signed • 1001 1111 0101 0000 1111 0111 0111 0000 • Hexadecimalt: 9f 50 f7 70 • i C: 0x9f50f770 • Teckenbiten (längst till vänster) är ettställd • Tolkas som negativt heltal (-1 622 083 728)
Binärkod för värdet minus ett Koden för + 1 0000 0000 .... 0001 Bitvis invertering 1111 1111 .... 1110 Addition av ett + 0000 0000 .... 0001 Och vi får kod för -1 1111 1111 .... 1111 (Koden för -1 är alltid ”bara ettor” för alla ordlängder)
Värdet av kod för negativt tal Koden för negativt tal 1111 .... 1010 0101 Bitvis invertering 0000 .... 0101 1010 Addition av ett + 0000 .... 0000 0001 Och vi får kod 0000 .... 0101 1011 Som tolkas till värdet 64+16+8+2+1 = 91 Alltså -91
Snabbfrågor • Omvandla följande decimala tal till 32-bitars tal i tvåkomplementrepresentation: • 512 • -1023 • -4000000 • Skriv talen i hexadecimalt format
Byte-ordning i minnet:little-endian, skrivning little-endian byte-order adress 0 . . . 1001 1111 0101 0000 1111 0111 0111 0000 0111 0000 1111 0111 0101 0000 1001 1111 (lilla änden först i minnet) . . . adress 2n-1
Byte-ordning i minnet:big-endian, läsning adress 0 big-endian byte-order . . . 0111 0000 1111 0111 0101 0000 1001 1111 0111 0000 1111 0111 0101 0000 1001 1111 (stora änden först i minnet) . . . adress 2n-1
Filenfloat.hgervärden för aktuellkompilator#include <float.h> Exempel: FLT_MAXkan ha värdet340282346638528859811704183484516925440.000000 Datatyper: flyttal: approximation av reellatal • float • double • long double • Oftast 32 bitar (IEEE 754 ) • Oftast64 bitar (IEEE 754 ) • ”Merändouble” 80 biteller(IEEE 754 quad precision)
Decimalt flyttal • -047,120 decimaltfixtal • -047,120 * 100decimaltflyttal • -04,7120 * 101sammaflyttal exponent mantissa tecken
-0101.110 binärt fixtal -0101,110 * 20 binärt flyttal -01,01110 * 22 normaliserat flyttal Binärt flyttal exponent mantissa tecken
-0101,110 binärt fixtal -0101,110 * 20 binärt flyttal -01,01110 * 22 normaliserat flyttal Binärt flyttal: float (32 bit) exponenten lagras med 8 bit i excess-127-kod bara bråksiffrorna av mantissan lagras, men inte "1," tecken: 1:a för negativa tal
-0101,110 binärt fixtal -0101,110 * 20 binärt flyttal -01,01110 * 22 normaliserat flyttal Binärt flyttal: double (64 bit) exponenten lagras med 11 bit i excess-1023-kod bara bråksiffrorna av mantissan lagras, men inte "1," tecken: 1:a för negativa tal
Flyttal IEEE 754, 32 bitar 1 10000011 00010000000000000000000 FLOAT: sexpmantissabitar värde = (–1)s * (1 + mantissabitar2 ) * 2 (exp–127) –17 (dec) = –1 0001 (bin) = – 1,0001 * 24 11000 0011000 1000 0000 0000 0000 0000 1100 0001 1000 1000 0000 0000 0000 0000 0x C 1 8 8 0 0 0 0
Algoritm för omvandling till flyttal • Antag ett decimalt flyttal: • -4,7120 * 1023 = -0,47120 * 1024 • Omvandlatill -1t * 1.M2 * 2(e-127) • Bestäm t, M och e så att följande villkor är uppfyllda: • 1.M2* 2(e-127) = 4,712010 * 1023 • M10< 1,0 • M2 < 1.0 • e är ett heltal 1. Antag M = 0 och bestäm exponent, x = e-127 • 4,7120 *1023 = 2x • log(4,7120 * 1023) = log(2x) • log(4,7120) + 23 = x*log(2) • x = • e = 78+127 = 205 = 0xcd = 0b1100 1101 • Lös ut M från ekvationen: 1.M*278 = 4,712*1023 • 1.M = 4,712*1023/278= 1,5590700185399465615976311028135 • M = 1000 1111 0001 1111 0011 011 • IEEE-talet är: 1 1100 1101 1000 1111 0001 1111 0011 011
Varför Excess-127/1023? För då kan man använda heltalsinstruktioner för att avgöra vilket tal som är störst
Information, 32 bitar adress / värde Little endian byte ordering FLOAT: 0xC1 0x88 0x00 0x00 - + 0x00 0x00 -17 i float-format: 0x C1 88 00 00 0x88 0xC1
Flyttal IEEE 754, 64 bitar 1 10000000011 000100 ... 000000000 DOUBLE: sexponentmantissabitar (-1)s * (1 + mantissabitar2 ) * 2 (exponent-1023) -17 (dec) = - 1 0001 (bin) = -1.0001 * 24 1100 0000 0011000 1000 0000 ... 0000 1100 0000 0011 0001 0000 0000 ... 0000 0x C 0 3 1 0 0 0 0 0 0 0 0 0 0 0 0
Information, 64 bitar adress / värde Little endian byte ordering DOUBLE: 0xC0 0x00 0x31 0x00 0x00 0x00 0x00 0x00 - + 0x00 0x00 0x00 0x00 0x00 -17 i double-format: 0x C0 31 00 00 00 00 00 00 0x00 0x31 0xC0
Snabbfrågor • Omvandla följande till 32-bitars binärkod i hexadecimalt format: • Instruktionen add r12,r1,r3 • Heltalet 147425338 • Det reella talet 1,3092239146306080983655304890341 * 10-33
Addition/subtraktion av flyttal Algoritm: 1.Jämför de bådatalensexponenter. Skiftadetminstataletssignifikand (inkl. implicit etta) till högersåatt de bådatalensexponenterblirlikastora 2.Addera/subtraherasignifikanderna 3.Normaliserasumman 4. Om detblirexponent overflow ärdetaritmetisktfel 5.Avrundasignifikanden 6. Om avrundningenmedföratttaletblironormaliserat, gå till steg 3
Multiplikation av flyttal Algoritm: 1.Adderaexponenternaochdraifrån en excess 2.Multiplicerasignifikanderna 3.Normaliseraprodukten 4. Om detblirexponent overflow ärdetaritmetisktfel 5.Avrundasignifikanden 6. Om avrundningenmedföratttaletblironormaliserat, gå till steg 3 7.Beräknaproduktenstecken
Den här föreläsningen • Enkladatatyperochdatarepresentation: Heltal, flyttal, • Merkompliceradedatatyper • Uttryck, satser, block • Pekare, pekar-aritmetik • Lagring av globalaochlokalavariabler • Stack • Heap
Mer komplicerade datatyper i C Mats Brorsson KTH
Den här föreläsningen • Enkladatatyperochdatarepresentation: Heltal, flyttal, • Merkompliceradedatatyper • Uttryck, satser, block • Pekare, pekar-aritmetik • Lagring av globalaochlokalavariabler • Stack • Heap
Arrayer • En array i C haralltidfixstorlek • Deklarationenintvektor[27];reserverarplats för 27 heltal i en array • Numreringenbörjarpånollvektor[0]vektor[1]...vektor[26] /* Nuärdetslut! */
Array i minnet adress 0 1 byte adress för v[0]: 0x800b70 0xd2 0x04 1234 (decimalt) = 0x000004d2 (hex) 0x00 0x00 0x67 och här kommer v[1]: 0x800b74 0x12 4711 (decimalt) = 0x00001267 (hex) 0x00 0x00 adress för v[2]: 0x800b78 . . . adress 0xffffffff • Heltals-vektor • int v[27];v[0] = 1234;v[1] = 4711; • Resultat i minnet(little-endian)
Matriser • Matriserfinnsintesomegentyp, utangörssomarrayer av arrayer • Deklarationenintmatris[17][42];gerplats för 17 radermed 42 heltal i varjerad • Numreringenbörjarpånollmatris[0][0]matris[0][1]...matris[16][41] /* Nuärdetslut! */ • För dynamisktallokeradematriserärdetlitemerkrångligt.
Matriser, mera detaljer • Lagring i minnetmatris[0][0]matris[0][1]...matris[0][41]matris[1][0]matris[1][1]...matris[1][41]matris[2][0]... ochsåvidaretillmatris[16][41] • Först hela rad 0 • Sedan hela rad 1 • Och sen hela rad 2 • ... • Kallas radvislagring • Eng. Rowmajorordering • Fortran harColumnmajorordering
Bokstäver och strängar • Tecknet'A'är ett litetheltal (65) • En charanvänder 1 byte i minnet, ochharplats för ett litetheltal (exempelvis 65) • En array of charharplats för en sträng:char s[20]="Nowyou C a string."; • Strängarslutarmed en nollställdchar(’\0’)somslutmarkör • Exempel:"hej" == { 'h', 'e', 'j', '\0' }
Handöversättning till assembler • C: • char s[20]="Nowyou C a string."; • Assembler: • .data .global s s: .asciz "Nowyou C a string."
I minnet (exempel) adress 0 1 byte adress för c: 0x800b62 0x51 Obs! Exempel på adresser. 0x67 adress för x: 0x800b64 0x12 0x800b65 0x800b66 0x00 0x800b67 0x00 4711 (decimalt) = 0x00001267 (hex) adress 0xffffffff • Exempel i C:char c = 'Q';int x = 4711; • Assembler: .data .global cc: .byte 'Q' .align 2 .global xx: .word 4711