Pekare, pekararitmetik

1.6.1. Vi har deklarationen: char c,*cptr; int i,*iptr; Visa kodsekvenser som evaluerar följande uttryck i register R0.

a) cptr = iptr;
b) *cptr = *iptr
c) cptr = &c;
d) c = *cptr;
e) iptr = &i;
f) i = *iptr;
@ a)	cptr = iptr;
	LDR	R0,iptr
	LDR	R7,=cptr
	STR	R0,[R7]
@ b)	*cptr = *iptr
	LDR	R7,cptr
	LDR	R0,iptr
	LDR	R0,[R0]
	STRB	R0,[R7]
@ c)	cptr = &c;
	LDR	R7,=cptr
	LDR	R0,=c
	STR	R0,[R7]
@ d)	c = *cptr;
	LDR	R0,cptr
	LDRB	R0,[R0]
	LDR	R7,=c
	STRB	R0,[R7]
@ e)	iptr = &i;
	LDR	R7,=iptr
	LDR	R0,=i
	STR	R0,[R7]
@ f)	i = *iptr;
	LDR	R7,=i
	LDR	R0,iptr
	LDR	R0,[R0]
	STR	R0,[R7]


1.6.2. De globala variablerna i, och vecc är definierade enligt: int i; char vecc[20]; Visa kodsekvenser som evaluerar följande uttryck i register R0.

a) &vecc[0];
b) &vecc[14];
c) &vecc[i];
d) &vecc[i>>1];
a)
@ adress = vecc
	LDR	R0,=vecc
b)
@ adress = vecc + 14
	LDR	R0,=vecc
	MOV	R1,#14
	ADD	R0,R0,R1
c)
@ adress = vecc + i
	LDR	R0,=vecc
	LDR	R1,i
	ADD	R0,R0,R1
d)
@ adress = vecc + (i >> 1)
	LDR	R0,=vecc
	LDR	R1,i
	ASR	R1,R1,#1
	ADD	R0,R0,R1


1.6.3. De globala variablerna i, och vecs är definierade enligt: int i; short vecs[20]; Visa kodsekvenser som evaluerar följande uttryck i register R0.

a) &vecs[0];
b) &vecs[14];
c) &vecs[i];
d) &vecs[i+1];
a)
	LDR	R0,=vecs
b)
	LDR	R0,=vecs+28
c)
	LDR	R1,i
	LSL	R1,R1,#1
	LDR	R2,=vecs
	ADD	R0,R1,R2
d)
	LDR	R3,i
	ADD	R3,R3,#1
	LSL	R3,R3,#1
	LDR	R2,=vecs
	ADD	R0,R1,R2


1.6.4. De globala variablerna i, och veci är definierade enligt: int i; int veci[20]; Visa kodsekvenser som evaluerar följande uttryck i register R0.

a) &veci[0];
b) &veci[14];
c) &veci[i];
d) &veci[i-1];
a)
	LDR	R0,=veci
b)
	LDR	R0,=veci+56
c)
	LDR	R1,i
	LSL	R1,R1,#2
	LDR	R2,=veci
	ADD	R0,R1,R2
d)
	LDR	R3,i
	SUB	R3,R3,#1
	LSL	R3,R3,#2
	LDR	R2,=veci
	ADD	R0,R1,R2


1.6.5. De globala variablerna i, och vecc är definierade enligt: int i; char vecc[20]; Visa hur följande tilldelning kodas:

	i = (int) ( &vecc[1] – &vecc[0] );
	LDR	R3,=i
	MOV	R2,#1
	STR	R2,[R3]


1.6.6. De globala variablerna i, och vecs är definierade enligt: int i; short vecs[20]; Visa hur följande tilldelning kodas:

	i = (int) ( &vecs[1] – &vecs[0] );
	LDR	R3,=i
	MOV	R2,#2
	STR	R2,[R3]


1.6.7. De globala variablerna i, och veci är definierade enligt: int i; int veci[20]; Visa hur följande tilldelning kodas:

	i = (int) ( &veci[1] – &veci[0] );
	LDR	R3,=i
	MOV	R2,#4
	STR	R2,[R3]


1.6.8. Deklarationerna int i, *ip;
är givna. Ange den bästa kodningen av tilldelningssatsen:
ip = &i;

De olika lösningsalternativen är graderade från -1p..3p.
a)
LDR R0,i
LDR R6,=ip
STR R0,[R6]
b)
LDR R0,=i
LDR R6,ip
STR R0,[R6]
c)
LDR R0,=i
STR R0,ip
d)
LDR R0,=i
LDR R6,=ip
STR R0,[R6]
e)
LDR R0,=ip
STR R0,i

Svar: d(3p), b(1p), a,d(0p), e(-1p)

1.6.9. Deklarationerna char *cp1, *cp2;
är givna. Ange den bästa kodningen av tilldelningssatsen:
cp1 = cp2;

De olika lösningsalternativen är graderade från -1p..3p.
a)
LDR R0,cp2
LDR R7,=cp1
STR R0,[R7]
b)
LDR R0,=cp2
LDR R7,=cp1
STR R0,[R7]
c)
LDR R0,=cp2
STR R0,cp1
d)
LDR R0,cp2
STR R0,cp1
e)
LDR R0,cp1
LDR R7,=cp2
STR R0,[R7]

Svar: a(3p), b,d,e(0p),c(-1p)

1.6.10. Deklarationerna int j, *ip;
är givna. Ange den bästa kodningen av tilldelningssatsen:
j = *ip;

De olika lösningsalternativen är graderade från -1p..3p.
a)
LDR R0,=ip
LDR R0,[R0]
LDR R0,[R0]
LDR R6,=j
STR R0,[R6]
b)
LDR R0,=ip
LDR R0,[R0]
STR R0,j
c)
LDR R0,=ip
LDR R0,[R0]
STR R0,j
d)
LDR R0,ip
LDR R0,[R0]
LDR R6,=j
STR R0,[R6]
e)
LDR R0,ip
LDR R0,[R0]
STR R0,j

Svar: d(3p), a(2p), b,c,e(-1p)

1.6.15. De globala variablerna i, och mc är definierade enligt: int i; char mc[12][8]; Visa kodsekvenser som evaluerar följande uttryck till register R0.

a) &mc[3][4];
b) &mc[4][3];
c) &mc[i][4];
d) &mc[3][i];
a) adress = mc + 3*8 + 4
	LDR	R0,=mc+28
b) adress = mc + 4*8+3
	LDR	R0,=mc+35
c) adress = mc + i*8 + 4
	LDR	R3,i
	LSL	R3,R3,#3
	ADD	R3,R3,#4
	LDR	R2,=mc
	ADD	R0,R3,R2
d) adress = mc + 3*8+i
	LDR	R3,i
	ADD	R3,R3,#24
	LDR	R2,=mc
	ADD	R0,R3,R2


1.6.20. Visa i C och assembler hur en pekare till funktionen void do_this( void ) placeras på address 0x2001C000 i minnet.

	*((void (**)(void) ) 0x2001C000 ) = do_this;

	LDR	R0,=do_this
	LDR	R1,=0x2001C000
	STR	R0,[r1]


1.6.21. Vi har en funktion: void do_this( void ){} och en funktionspekare: void (*func)(void); Visa en kodsekvens i assembler som utför följande:

func = do_this;
 ... 
func();
	LDR	R2,=do_this
	LDR	R3,=func
	STR	R2,[R3]
	...
	LDR	R3,func
	BLX	R3


1.6.22. Vi har en global deklaration: char **dcp; visa hur följande uttryck evalueras till R0:

a) &dcp;
b) *dcp;
c) **dcp;
a)
	LDR	R0,=dcp
b)	
	LDR	R0,=dcp
	LDR	R0,[R0]
	LDR	R0,[R0]
c)
	LDR	R3,=dcp
	LDR	R3,[R3]
	LDR	R3,[R3]
	LDRB	R2,[R3]


1.6.23. Vi har deklarationerna:

char	c, *cp;
int	i, *ip;
Koda följande tilldelningar i assemblerspråk

a)	c = *++cp;
b)	i = *ip++;
@ a) c = *++cp;
	LDR	R3,=cp		@ R7 = &cp
	LDR	R2,[R3]		@ R6 = cp
	ADD	R2,R2,#1	@ (dvs. ++cp)
	LDRB	R0,[R2]		@ R0 = *cp
	STR	R2,[R3]		@ cp = R6
	LDR	R3,=c
	STRB	R0,[R3]		@ c = R0
@ i = *ip++;
	LDR	R3,=ip		@ R7 = &ip
	LDR	R2,[R3]		@ R6 = ip
	LDR	R0,[R2]
	ADD	R2,R2,#4	@ (dvs. cp++)
	STR	R2,[R3]
	LDR	R3,=c
	STR	R0,[R3]