hi ihr MI - Asse :-) kann mir jemand von euch diesen assembler code erklären und oder auch kommtentieren zeile für zeile :-) ? danke :-) mfg nfs2k .global SWIHandler .text SWIHandler: ldr sp, STACK stmfd sp!, {lr} ldr ip,[r14, #-4] bic ip, ip, #0xff000000 mov ip, ip, lsl #2 ldr lr, =SWIJumpTable ablegen ldr ip, [lr, ip] mov lr, pc mov pc, ip ldmfd sp!, {pc}^ STACK: .word 0x78c SWIJumpTable: .word init_ser @SWI0 .word putchar @SWI1 .word getchar @SWI2 .end
Ja, nö. Is ja auch so popeleinfach, irgendnen Code voll ausm Kontext gerissen zu erklären. Du weißt bestimmt deutlich mehr, wozu der Code gehört und was er machen soll und überhaupt, welcher CPU-Core, als Du hier verraten willst. Peter
hab zwar keine Ahnung von Assembler, aber das pdf file kann das glaub ich ;) http://www.jegerlehner.ch/intel/index_de.html grüße
nfs2k schrieb:
> mehr ist leider in dieser File nicht an code drinnen !?
Nicht mehr Code, sondern grundsätzliche Projektinformationen.
Dann ist eben nicht mehr Antwort drin, die Kristallkugeln sind nämlich
grade alle zur Reparatur.
Peter
SWI #0 => Aufruf von init_ser SWI #1 => Aufruf von putchar SWI #2 => Aufruf von getchar SWI sonst => undefiniert, lies: Handler ist Schrott. Zeile für Zeile erklärt dir ein ARM Handbuch.
Oberfläche :Ubuntu Tools: Snavigator (terminalersatz) In der Aufgabe soll ein SWI Handler genutzt werden, um eine Trennung des Low Level IOs vom Anwendungsprogramm zu erreichen. Dazu sind die Funktionen die den SWInterrupt aufrufen in Assembler zu implementieren und mit dem Debugger ist die Funktionsweise des Interrupthandlers zu untersuchen. Es sollen die Funktion puts (siehe ser_io.S) in Assembler so ergänzen, dass auch der String auf die serielle Schnittstelle ausgegeben wird. Die IO-Funktionen putchar und getchar (siehe seriell.S) werden dabei über einen SWI (siehe swi.S) aufgerufen. void puts(char *) Ausgabe eines nullterminierten Strings und Ersetzung von Newline durch Carriage Return (0x0d) und Linefeed (0x0a). Nun ist der Code des SWI-Handlers zu erklären ?????? :-))) (siehe swi.S). 3 dateien sind beinhaltet : oben genannte swi.s + 2 folgende hoffe es hilft ein bischen weiter ___________ @----------------------------------------------------------------------- ----- @ File Name : ser_io.S @ Object : Ein- Ausgabe-Funktionen der seriellen Schnittstelle @----------------------------------------------------------------------- ----- @ Debuginformationen .file "ser_io.S" @ Funktion .text .align 2 .global inits .type inits,function inits: stmfd sp!,{lr} @ Retten der Register swi 0 ldmfd sp!,{pc} @ Rücksprung @ Funktion .text .align 2 .global puts .type puts,function puts: stmfd sp!,{lr} @ Retten der Register // Hier muß Ihr Code eingefügt werden. mov r1,r0 puts_start: ldrb r0,[r1],#1 cmp r0,#0 beq puts_end // /n /r cmp r0,#0x0a moveq r0,#0x0d swieq 1 moveq r0,#0x0a bl putchar b puts_start puts_end: ldmfd sp!,{pc} @ Rücksprung @ Funktion .text .align 2 .global gets .type gets,function gets: stmfd sp!,{lr} @ Retten der Register // Hier könnte Ihr Code eingefügt werden! ldmfd sp!,{pc} @ Rücksprung .end ----------------- @----------------------------------------------------------------------- ----- @ File Name : seriell.S @ Object : Grundfunktionen der seriellen Schnittstelle @----------------------------------------------------------------------- ----- .file "seriell.S" #include "../h/pmc.inc" #include "../h/pio.inc" #include "../h/usart.inc" DEFAULT_BAUD = 38400 CLOCK_SPEED = 25000000 US_BAUD = 0x29 @ CLOCK_SPEED / (16*(DEFAULT_BAUD)) @ Funktion .text .align 2 .global init_ser .type init_ser,function init_ser: stmfd sp!, {r0-r3, lr} @ Register retten adr r0,L1 adr r1,L1_end init_ser_loop: ldmia r0!, {r2-r3} cmp r0, r1 str r3, [r2] bne init_ser_loop ldmfd sp!, {r0-r3, pc} @ Rücksprung L1: .word PMC_BASE+PMC_PCER, 0x4 .word PIOA_BASE+PIO_PDR, 0x18000 .word USART0_BASE+US_CR, 0xa0 .word USART0_BASE+US_MR, 0x8c0 .word USART0_BASE+US_BRGR, US_BAUD .word USART0_BASE+US_CR, 0x50 L1_end: @ Funktion .text .align 2 .global putchar .type putchar,function putchar: stmfd sp!, {r0-r2, lr} @ Register retten ldr r2, =USART0_BASE 1: ldr r1, [r2, #US_CSR] tst r1, #US_TXRDY @ ist Transmitter frei beq 1b str r0, [r2,#US_THR] ldmfd sp!, {r0-r2, pc} @ Rücksprung @ Funktion .text .align 2 .global getchar .type getchar,function getchar: stmfd sp!, {r1, r2, lr} @ Register retten ldr r2, =USART0_BASE 1: ldr r1, [r2, #US_CSR] ands r1, r1, #US_RXRDY beq 1b ldr r0, [r2, #US_RHR] ldmfd sp!, {r1, r2, pc} @ Rücksprung .end
Moin, also SWIs sind 'ne Möglichkeit anderen Programmen Funktionen von dem Code der die Interrupts verwaltet zugänglich zu machen. Ich hab' z.B. 'n Bootloader geschrieben der gleichzeitig auch eine Interrupt getriebene serielle USB Schnitstelle bereitstellt. Damit dann das Programm, das hochgeladen wird nicht den ganzen Interrupt code und den für USB CDC/ACM nochmal beinhalten muss mache ich dann die putc, getc, ... via SWIs sichtbar. ldr sp, STACK <- setzt den Stack Pointer auf Adresse STACK stmfd sp!, {lr} <- wirft die ReturnAddr. auf den Stack ldr ip,[r14, #-4] <- holt den auslösenden SWI opcode bic ip, ip, #0xff000000 <- extrahiert SWI Nummer mov ip, ip, lsl #2 ldr lr, =SWIJumpTable ablegen ldr ip, [lr, ip] <- lädt SWI-Fkt. Adresse mov lr, pc mov pc, ip <- ruft SWI-Fkt auf ldmfd sp!, {pc}^ <- return;
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.