LU-MOP-MD2
LU MOP kursa mājas darbs MD2.
MD2
Matricu reizināšana
Jums jāizstrādā asemblera procedūra matmul(...), kas reizina divas 2D matricas, un rezultātu ieliek trešajā. Jūsu asemblera programma tiks izsaukta no C valodā rakstītas, tātad parametriem jābūt atbilstošiem.
Zemāk dots programmas izsaukuma piemērs no komadu rindas. Ievaddati tiek padoti ar < operatoru no faila infile.txt uz stdin. Līdzīgi rezultāts no stdout tiek saglabāts izvada failā outfile.txt.
$> md2 < infile.txt > outfile.txt
Jāizstrādā un jāiesniedz sekojoši faili (visi papildus faili tiks ignorēti):
- Makefile - fails, kas ļauj kompilēt jūsu programmu
- md2.h - pirmkoda fails ar funkcijas prototipu, ko iekļaus gan C gan asemblera faili.
- md2.s - programmu asemblerā, kas aprēķina matricu reizinājumu.
- md2_main.c - programmu C valodā, kas izsauc asamblera programmu un padod tai matricas, saņem rezultātu, ko izdrukā uz ekrāna.
Matricu ievads un izvads
Testējot, matricas jāievada no komandu rindas. Matricas tiek padotas caur stdin, piemēram, no komandu rindas straumējot no teksta faila. Rezultējošā matrica tiek izvadīta uz stdout, ko arī var straumēt uz teksta failu. Arī rezultējošā matrica jāizvada tādā pat formātā kā ievaddati (skat. zemāk).
Matricas teksta failā tiek definētas kā skaitļu virkne. Tātad, jums jānodrošina matricu ievads un izvads sekojošā formātā:
- skaitlis H, kas norāda rindu skaitu matricā (augstumu)
- skaitlis W, kas norāda kolonu skaitu matricā (platumu)
- H*W skaitļi, kas aizpilda matricu, sākot no pirmās rindas.
- Pēc tam var sekot nākamā matrica tieši tādā pašā formātā.
Piemēram, 2x3 matrica:
1 2 3 4 5 6
teksta failā var tikt definēta šādi:
2 3 1 2 3 4 5 6
Vai arī šādi, viss vienā rindā. Pārejas uz jaunu rindu nav nepieciešamas un tiek ignorētas, bet tās var saglabāt lasāmības dēļ:
2 3 1 2 3 4 5 6
Skaitļu ievadam C programmā iespējams izmantot funkciju scanf(), piemēram šādi:
#include <stdlib.h>
#include <stdio.h>
...
int w,h;
int *matrix,
int *p;
...
scanf("%d", &h);
scanf("%d", &w);
/* Buferu alokācija un cikls pa visiem matricas elementiem */
matrix = (int*) malloc( w * h * sizeof(int));
p = matrix;
for(...)
{
scanf("%d", p++);
}
...
Lūdzu ņemiet vērā, ka augšminētais piemērs jāpapildina ar pārbaudēm, lai, piemēram, nekorekti ievaddati nerakstītu ārpus bufera.
Arī izvada datos jānorada matricu izmēri. Jo:
- matricas varētu tikt tālāk izmantotas, un tāpēc jāzina, piemēram, vai tā ir 2x3, 3x2, vai 6x1.
- vērtējot jūsu darbu jāsaprot, kāds ir jūsu rezultāts, tai skaitā novērtētais matricu izmērs.
Procedūras matmul(...) prototips
int matmul( int h1, int w1, int *m1, int h2, int w2, int *m2, int *m3 );
- Procedūras parametri: h1 un h2 ir matricas augstums un w1 un w2 ir platums attiecīgi pirmajai un otrajai matricām m1 un m2.
- Trešās matricas m3 dimensijas nosaka matricu reizinājuma operācija.
- Procedūra atgriež skaitli int: 0 = veiksmīga izpilde, 1 = problēma, piemēram, nesaderīgas matricas. Šādā gadījumā C programmai arī jābeidz darbs ar kodu 1: exit(1);
- Visus nepieciešamos datu buferus nodrošina (izveido) izsaucošā C programma, tai skaita arī trešajai, rezultāta matricai. Tas nozīmē, ka arī C programmai jānosaka, cik liela būs rezultāta matrica, lai tai rezervētu pietiekoši daudz atmiņas.
Matricu elementi atmiņā glabājas kā divdimensiju masīvs: Int elementi. Piemēram, 2x3 matrica
1 2 3 4 5 6
atmiņā glabājas lineāri, kā 6 int elementi, katrs izmērā 4 baiti: { 1, 2, 3, 4, 5, 6 }
Visi datu izmēri (atsevišķie skaitļi) saiet int reģistrā, tātad nepārsniedz 4 baitu garumu. Visi skaitļi ir veseli.
Testēšana un iesniegšana
Risinājumam jābūt testētam, un jādarbojās uz asm1.linux.edu.lv servera, lietojot ARM emulatoru qemu-arm. Bez tam, tas, ka risinājums darbojas uz asm1 servera, nenozīmē, ka tajā nav kļūdas un ka par to automātiski pienāktos maksimālais vērtējums. Pieredze rāda, ka reizēm "paveicas", un risinājums darbojas, lai arī tajā ir kļūdas. Testējot vai lietojot to nākamreiz vai uz citas aparatūras tas var nestrādāt. Tāpēc lūdzu pieiet savam kodam kritiski. Piemēram, vai esat saglabājuši un atjaunojuši visus izmantotos reģistrus, sākot no R4 un uz augšu? Šī ir tipiska kļūda, kas var reizēm nostrādāt un reizēm nē.
Risinājumu jāiesūta elektroniski.
Risinājumam ar visiem failiem jābūt uz servera asm1.linux.edu.lv
jūsu konta direktorijā md2:
~/md2/
Uzskaitītie faili tiks izkopēti no minētas direktorijas MD termiņa beigās.
Jautājumus un komentārus par MD lūdzu iesūtīt kursa diskusiju forumā (eStudijās).