Università degli Studi di Udine Corsi di laurea in Ingegneria

Transcript

Università degli Studi di Udine Corsi di laurea in Ingegneria
Università degli Studi di Udine
Corsi di laurea in Ingegneria Elettronica
Architettura dei calcolatori (ex Fondamenti di Informatica II)
28 giugno 2011 - Prova scritta
Matricola __________________
Nome _____________________
Cognome __________________
ISTRUZIONI (da leggere attentamente)
1) Lo studente è tenuto a scrivere, correggere, compilare ed eseguire su computer (a casa o in laboratorio) gli esercizi di
programmazione prima della prova orale. Alla prova orale lo studente deve portare un floppy disk contenente i sorgenti
dei programmi corretti e le stampe dei relativi file.
2) Non è consentito l’uso di libri, appunti, calcolatrici programmabili, telefoni cellulari.
3) Rispondere sinteticamente negli spazi di fianco o seguenti le domande, oppure sul retro del foglio.
1.
(3 punti) Si svolga, utilizzando la rappresentazione in complemento a 2 su 16 bit, l’operazione 409610 – 409510, riportando
nel dettaglio tutti i passaggi.
2.
(3 punti) Cos’è e come si calcola un CRC?
3.
(2 punti) Cosa significa “codifica entropica”?
Si consideri una libreria in linguaggio C per manipolare file audio così definita:
typedef
typedef
typedef
unsigned char
unsigned short int
unsigned long int
byte;
word;
dword;
#define SAMPLE(wave, channel, offset) \
wave.wavedata.sample
\
[2 * (offset) + (channel)]
#define
#define
#define
#define
#define
#define
#define
#define
#define
#define
FMTPCM
1
SAMPLINGRATE 44100
CHANNELS
2
BITSPERSAMPLE 16
LEFT 0
RIGHT 1
RIFF_ID "RIFF"
WAV_ID
"WAVE"
FMT_ID
"fmt "
DATA_ID "data"
typedef struct tagRIFFHEADER
{
char riffid[4];
dword FileSize;
char waveid[4];
} RIFFHEADER;
typedef struct tagWAVEDATA
{
char dataid[4];
dword DataSize;
signed short int *sample;
} WAVEDATA;
typedef struct tagFMTHEADER
{
char fmtid[4];
dword fmtsize;
word format;
word channels;
dword SampleRate;
dword BytesPerSecond;
word BlockAlign;
word BitsPerSample;
} FMTHEADER;
typedef struct tagWAVE
{
RIFFHEADER riffheader;
FMTHEADER fmtheader;
unsigned long int numofstereosamples;
WAVEDATA wavedata;
} WAVE;
void
WAVE
WAVE
void
WriteWave (WAVE wave, FILE *fp);
ReadWave (FILE *fp);
CreateEmptyCDaudioWave
(unsigned long int
numofstereosamples);
ReleaseWaveData (WAVE *wave);
4. (8 punti) Volete riprodurre, tramite la scheda audio del vostro computer, il contenuto di due file audio stereo in formato
standard WAV (44.100 campioni/secondo, 16 bit per campione). Il primo file contiene del parlato mentre il secondo file
contiene della musica da usare come sottofondo del parlato. I due file hanno durata differente e, se quella della musica di
sottofondo è inferiore a quella del parlato, la riproduzione della musica deve ripartire dall’inizio ed essere ripetuta per quante
volte è necessario per arrivare fino alla fine del parlato. La riproduzione simultanea dei due file audio avviene
semplicemente miscelandoli in proporzioni uguali, cioè effettuando la media dei valori dei campioni provenienti dai due file.
Periodicamente il driver della scheda audio chiama la funzione
void load_buffer (signed short int *sample, int dim)
per “richiedere” al programma i campioni audio da riprodurre. La funzione riceve come argomenti un vettore di campioni
(da riempire) e la sua dimensione (sempre pari, corrispondente a un numero intero di campioni stereo). Nel vettore i
campioni stereo sono alternati: quelli di indice pari corrispondono al canale di sinistra e quelli dispari a quello di destra.
Supponendo che il programma preveda le seguenti variabili globali:
int posizione_parlato = 0;
int posizione_musica = 0;
WAVE audio_parlato;
WAVE audio_musica;
e che le due strutture di tipo WAVE siano già state caricate (ad opera del main) con il contenuto dei due file audio in
oggetto, si scriva la funzione load_buffer. Il valore dei campioni successivi all’ultimo del parlato devono essere posti a
zero.
(svolgere sul retro)
Un elaboratore (il modello didattico SimCPU visto a lezione) dispone di CPU (a 16 bit) con 16 registri di uso generale (R0, R1,
..., R15) più il Program Counter, l’Instruction Register, lo Stack Pointer e 4 flag Z (zero), N (negative), C (carry) e V
(overflow). Si ricorda che il linguaggio assembler di tale elaboratore dispone delle seguenti istruzioni:
assembly
inst. name
machine code
LDWI
LDWA
LDWR
LDBI
LDBA
LDBR
STWA
STWR
STBA
STBR
MV
PUSH
POP
SPRD
SPWR
load word
load word
load word
load byte
load byte
load byte
store word
store word
store byte
store byte
move
push
pop
read SP
write SP
00010000dddd0000
00100000dddd0000
00110000ddddaaaa
00010001dddd0000
00100001dddd0000
00110001ddddaaaa
00100010ssss0000
00110010ssssaaaa
00100011ssss0000
00110011ssssaaaa
00000100ssssdddd
00001000ssss0000
00001001dddd0000
00001101ssss0000
00001110ssss0000
add
subtract
bitwise NOT
bitwise AND
bitwise OR
bitwise XOR
increment
decrement
left shift
right shift
01000000ssssdddd
01000001ssssdddd
01000010rrrr0000
01000011ssssdddd
01000100ssssdddd
01000101ssssdddd
01001000rrrr0000
01001001rrrr0000
01001010rrrr0000
01001011rrrr0000
ADD
SUB
NOT
AND
OR
XOR
INC
DEC
LSH
RSH
5.
d
d
d
d
d
d
s
s
s
s
s
s
d
d
s
s
s
r
s
s
s
r
r
r
r
X
A
a
X
A
a
A
a
A
a
d
d
d
d
d
d
DATA(16)
ADDR(16)
DATA(8)
ADDR(16)
ADDR(16)
ADDR(16)
action
assembly inst. name
machine code
d <- X
d <- mem[A]
d <- mem[a]
d <- X
d <- mem[A]
d <- mem[a]
mem[A] <- s
mem[a] <- s
mem[A] <- s
mem[a] <- s
d <- s
push (s)
d <- pop ()
d <- SP
SP <- s
INW
INB
OUTW
OUTB
TSTI
10000000dddd0000
10000001dddd0000
10000010ssss0000
10000011ssss0000
1000010000000000
d
d
r
d
d
d
r
r
r
r
<<<<<<<<<<-
d + s
d - s
~r
d & s
d | s
d ^ s
r + 1
r + 1
r << 1
r >> 1
d
d
s
s
A
A
A
A
A
input word
input byte
out word
out byte
test input
action
IN_ADDR(16)
IN_ADDR(16)
OUT_ADDR(16)
OUT_ADDR(16)
IN_ADDR(16)
TSTO A
test output 1000010100000000 OUT_ADDR(16)
BR
JMP
JMPZ
JMPNZ
JMPN
JMPNN
JMPC
JMPV
CALL
RET
HLT
branch
jump
jump if zero
jump if not zero
jump if negative
jump if not neg.
jump if carry
jump if overflow
subroutine call
return from sub.
halt
A
F
F
F
F
F
F
F
A
d <- read[A]
d <- read[A]
out[A] <- s
out[A] <- s
if completed then Z <- 1
else Z <- 0
if completed then Z <- 1
else Z <- 0
1100000000000000 ADDR(16) PC <- A
11000001FFFFFFFF
PC <- PC + F
11000010FFFFFFFF
if (z == 1) PC <- PC
11000011FFFFFFFF
if (z == 0) PC <- PC
11000100FFFFFFFF
if (N == 1) PC <- PC
11000101FFFFFFFF
if (N == 0) PC <- PC
11000110FFFFFFFF
if (C == 1) PC <- PC
11000111FFFFFFFF
if (V == 1) PC <- PC
1100100000000000 ADDR(16) push (PC); PC <- A
1100100100000000
PC <- pop()
1100111100000000
halt
LEGENDA:
- lettere minuscole = registri;
lettere maiuscole = dati numerici
- ‘r’ = registro letto e modificato
- ‘s’ = registro soltanto letto
- ‘d’ = registro modificato
- ‘a’ = registro il cui contenuto è usato come indirizzo
- FFFFFFFF = offset (in complemento a 2)
(10 punti) Si scriva in linguaggio assembler la funzione DIVISIBILE che riceve in R1 ed R2 due numeri interi positivi e
che restituisce in R0 il valore 1 se R1 è divisibile per R2, zero altrimenti.
(svolgere sul retro)
6.
(4 punti) Si descrivano i supporti di memoria di massa magnetici e ottici e se ne giustifichino le differenze.
(svolgere sul retro)
7.
(2 punti) Si discuta il significato e l’utilizzo del simbolo ‘$’ nelle espressioni di calcolo in un foglio elettronico.
+
+
+
+
+
+
F
F
F
F
F
F