embedded systems c programming. reference data definition and storage const int a=43; unsigned int...

47
Embedded Systems C programming

Upload: gregory-shepherd

Post on 04-Jan-2016

263 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Embedded Systems

C programming

Page 2: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Reference

Page 3: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Data definition and storage

const int a=43;

unsigned int b=66;unsigned int c;

int main(void){ static int d; ……}

.text.text.data.data

.bss.bss

.rodata.rodata

RAM ROM

the file *.lds give detailed address of

each data block

Page 4: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Keyword: const

• Unchanging Value const int five = 5; const double pi = 3.141593;

• Cannot Write a const Data Object const double pi = 3.141593; pi = 3.2;

Page 5: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Keyword: volatile•Value May be Changed Outside Current Program•Exchange data with an external device int check_iobuf(void) { volatile int iobuf; int val; while (iobuf == 0) { } val = iobuf; iobuf = 0; return(val); }

if iobuf had not been declared volatile, the compiler would notice that nothing happens inside the loop and thus eliminate the loop

Page 6: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Const + volatile

• An input-only buffer for an external device could be declared as const volatile (or volatile const) to make sure the compiler knows that the variable should not be changed (because it is input-only) and that its value may be altered by external processes

Page 7: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Constant

• readability

• Easily update a const used in several pace in the codes

• Easily update several related parameters in the program

Page 8: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Constant Rule (1)

• a Clear name#define WIDTH 320#define MAX_VALUE 100const float PI = 3.14159;

Page 9: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

“const” or “#define” ?

• const has data type while Macro doesn’t– Compiler has type check for const but not for

Macro

• Most debugger can show value of const but not Macro

Page 10: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Keyword: inline

void data_process(){…inc(p);…

}

void data_process(){…inc(p);…

}

void data_process(){

(*a)++; …

}

inline int inc (int *a) { (*a)++; }

inline int inc (int *a) { (*a)++; }

put them to header file

Page 11: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Macro as a Function

#define abs(x) (((x)>=0)?(x) : -(x))

#define max(a,b) ((a)>(b)?(a) : (b))

#define abs(x) x>0?x:-x

abs(a-b); // abs(a-b) a-b>0?a-b:-a-b

Note the usage of ()

Page 12: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

inline function vs. Macro

• inline function has input data type, can be checked by compiler

• Compiler cannot check input data type in Macro

#define ABS(x) (((x)>=0)?(x) : -(x))

inline double ABS(double x){ return (x>=0)?x : -x; }

• inline function can reduce () used in Macro

Page 13: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

inline function vs. Macro

• inline function execute inputted expression once, while Macro may run several times

 // Macro #define unsafe(i)  ((i)>=0?(i):-(i))  // Inline inline int safe(int i) {return i>=0?i:-i; }  int f() {……}  void userCode(int x) {   int ans;    ans = unsafe(x++);   // Error, Execute x++ twice   ans = unsafe(f());   // Error, f() invoked twice    ans = safe(x++);     // correct   ans = safe(f());     // correct }

Page 14: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Calculate Array Size

User can know the length of array by ending NULL

int MyData[] = { 7, // Number of element in array

3, 4, 5, 6, 7, 0, 1 };

Page 15: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Calculate Array Size

#define ARRAY_SIZE 20

double a[ARRAY_SIZE]={…};

void main (){ int c; for (c=0; c<ARRAY_SIZE; c++) {…}}

Page 16: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Using Macro to Calculate Array Size

Page 17: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Keyword Register

int fac(int n){   register int i,f=1;

   for(i=1;i<=n;i++)      f=f*i;

   return(f);}

Fast, but only a suggestion to the compiler, and maybe

ignored by the compiler

Page 18: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Bit Filed in C

struct packed_struct { unsigned int f1:1; unsigned int f2:1; unsigned int f3:1; unsigned int f4:1; unsigned int type:4; unsigned int byte_int:8; } pack;

pack.type = 7; // accept value <=15

f1 f2 f3 f4 type byte_int

Page 19: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Struct & Alignment

struct data{

u8 c;u32 d;u8 e;

};

sizeof(data)? 12

Page 20: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Struct & Alignment

struct data{

u8 c;u8 e;u32 d;

};

sizeof (data)? 8

Page 21: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Data Pack and Alignment

typedef struct {          u8  p[3]; u32  v; } test;

sizeof(test) ?

p[0]

v

p[1] p[2] v

empty

v

emptyp[0] p[1] p[2]

struct … {…} __attribute__ ((packed));

gcc -fpack-struct …

Page 22: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Typedef & Data Type• unsigned int• short int• unsigned long • char

typedef signed char s8;typedef signed short s16;typedef signed long s32;

typedef unsigned char u8;typedef unsigned short u16;typedef unsigned long u32;

Page 23: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

C Memory Types• Static

Global variable, static variableAllocate memory at compile stage

• StackLocal variable within a function(de-allocated automatically after return of the function)

• Heap (Dynamically allocated)allocated by malloc or newdeleted by free deletebe care of the memory leakage problem

Page 24: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Memory Access Error• Check memory allocation resulkt

if(p==NULL) …;

• initialize memory before usememset(ptr, 0, 200);

• Out of boundary errorchar str[] = “Hello”;char *str1 = malloc(strlen(str));strcpy(str1, str); strcat(str1, str);

• For/wile loop variable used in memory access

Page 25: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Memory Access Error (cont.)• Forget to release allocated memory (pointer)

• malloc free• Use deleted pointer

Page 26: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Malloc/Free Debugint count=0;

void *my_malloc(int size){ void *p; if (size<=0) return 0; // error() p=malloc(size); if (p!=NULL) count++; return p;}

void my_free(void *p){ if (p==NULL) return; // error(); free (p); count--;}

Page 27: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Memory Region

struct mem_region_t a[REGION_NUM];void my_malloc(int size, int id){ void *p=malloc(size); if (!p) return; add_pointer(a[id],p); return p;}void my_free(void *p, int id){ void *p=del_pointer(a[id], p); if (p) free p;}void my_free_all(int id){ void *p; while(p=get_1st_pointer(a[id])) free p; }

a[]

region_ID

Page 28: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Resource Allocation method

(use of List)

Free NodeList

Block

Block

Block

Block

Block

User Data List 1

Block

Block

Block

User Data List 2

Block

Block

Page 29: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Pointers in Function Call

void Func(void){ char *p = (char *) malloc(100); }

Remember to free it after the function call

void Func1(void){ char p[100]; …;} No need to free it manually

Page 30: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Pointer Access Example

int *x;*x=100;

char* get_hello_str(){

char abc[]=“hello”; … return abc;}

char* get_str(){

char abc[32]; … return abc;}

char* get_hello_ptr(){

char *abc=“hello”; … return abc;}

x pointer to where?

abc only existed in te stack of get_str(), and it is desyoried after

function return

“hello” is stored in the stack of function get_hello_str(), which is released when function is returned

“hello” is in const torage area, not released or deleted

Page 31: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Memory Example (1)char *ptr1 = NULL;char *ptr2 = NULL;

void Func() { if ((ptr1 = (char*)malloc(100)) = = NULL) { printf(“Out of memory!\n”); return; } if ((ptr2 = (char*)malloc(500)) = = NULL) { printf(“Out of memory!\n”); free(ptr1); return; } … free(ptr1); free(ptr2);}

// remember to delete the 1st point

Page 32: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Memory Example (2)char *ptr = NULL;

void Init() { ptr = NULL; …}

int main() { Init(); …; GetMemory(); …; FreeMemory();

…}

void FreeMemory(){ if (ptr != NULL) { free(ptr); ptr = NULL; } else printf(“Error!\n”); }

void GetMemory(){ if (ptr = = NULL) { ptr = (char*)malloc(100); } else printf(“Error!\n”); }

initialize before access

check before release

reset after release

check before reuse

Page 33: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

“goto” Clause

• may skip important object construction, variable initialization codes

goto state;String s1, s2; // skippedint sum = 0; // skipped…state:…

{ … { … { … goto error; } }}error: …

Page 34: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

“switch” Clause

• don’t forget break for each case

• Don’t forget default branch• Default is a label?

void func(){ switch (m) { … default: … } switch (n) { … default1: … }}

Page 35: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Assert•Only valid in debug version , check invalid conditionsvoid *memcpy(void *To, const void *From, size_t size){ assert((To != NULL) && (From != NULL)); byte *To = (byte *) To; byte *From = (byte *) From; while(size -- > 0 ) *To ++ = *From ++ ; return To;}

•Note, the error is in the caller function instead of memcpy

Page 36: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

IO Port Access

#define PORT_X (*((volatile u8 *)0x10001004))

#define PORT_BASE 0xF021C000#define PORT_A0 (*((volatile U32 *)(PORTA_BASE+0x04)))#define PORT_A1 (*((volatile U32 *)(PORTA_BASE+0x08)))

char s=PORT_X;PORT_X=0xff;PORT_A0=0x24000006;

different hardware may have different device base address

Page 37: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Bit Operation

• Set bitport |= 1<<12;port |= FLAG_RUN;

• Reset bitport &= ~(1<<12);port &= ~ FLAG_RUN;

• Test Bitwhile (!(port & FLAG_READY));if (port & FLAG_READY) …;

Page 38: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Write a Small Printf Function

• printf()“%s”, “%d” and “%x”

#include <stdarg.h>

int my_printf(const char *fmt, ...)int my_printf(const char *fmt, ...){ const char *s; int d; char buf[16]; va_listap; va_start(ap, fmt); while (*fmt) { if (*fmt != '%') { putchar(*fmt++); continue; } switch (*++fmt) { case 's': s = va_arg(ap,const char*); for (;*s;s++) putchar(*s); break; case 'd': d = va_arg(ap, int); itoa(d,buf,10); for (s=buf;*s;s++) putchar(*s); break; /* Add other specifiers here... */ default: putchar(*fmt); break; } fmt++; } va_end(ap); return 1; /* Dummy return value */}

Page 39: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Write a Small Printf Function (1)

#include <stdarg.h>intprintf(const char *fmt, ...){ … va_listap; va_start(ap, fmt); while (*fmt) { if (*fmt != '%') {…} switch (*++fmt) { case 's': s = va_arg(ap, const char *); … case 'd': … default: putchar(*fmt); break; } fmt++; } va_end(ap); …}

……

……

Page 40: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Style of Head File/**************************************** File description(ver, Author) ** ... ****************************************/

#ifndef MY_MUDOLE_H // prevent repeation#define MY_MUDOLE_H#include <stdio.h> // standard header...#include “MY_Header.h” // user defined header...typdef ... // data types...extern ... // global variable3...void Func(...); // global function...#endif // MY_MUDOLE_H

Page 41: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Example of including head file

#include “B.h”#include “B.h”

#define OK 1void func(void);#define OK 1void func(void);

A.h

B.h

#include “A.h”#include “B.h”…

#include “A.h”#include “B.h”…

code.c

void func(void);#define OK 1void func(void);#define OK 1…

void func(void);#define OK 1void func(void);#define OK 1…

re-define xxx error

Page 42: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Example of including head filecont.

#include “B.h”...#include “B.h”...

#ifndef __B_H__#define __B_H__

void func(void);

#endif // __B_H__

#ifndef __B_H__#define __B_H__

void func(void);

#endif // __B_H__

A.h

B.h

// __B_H__ is not defined#include “A.h”// __B_H__ is defined now

// will skip contents of B.h since // __B_H__ is already defined#include “B.h”

// __B_H__ is not defined#include “A.h”// __B_H__ is defined now

// will skip contents of B.h since // __B_H__ is already defined#include “B.h”

code.c

Page 43: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Comments#if 0

int GetValue(int Flag){ char *pBuffer = GetBuffer(); /* The Flag indicates whether the pointer should be adjusted */ if (Flag) return (*pBuffer) else // Adjust the reading point return *(pBuffer+1); }

#endif

Comments for several lines below

Comments for 1 lines on the left

int func(void){ /* debug_codes(); if (error==1) { printf(…); /*error=0;*/ } */}

Note /* … */ cannot nest

Page 44: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Math optimization

a*2^n // a<<n a*16 // a<<4

a/2^n // a>>n a/32 // a>>5

a%2^n // a&(2^n-1)a%8 // a&0x07

3/2 // 3>>1

r0*5 // r0<<2 + r0, mov r1,r0,r0,lsl #2

most of constant calculation can be recognized

and optimized by compiler

automatically

Page 45: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Fixed Point Arithmetic (1)

• Q16.16

Integer Fraction

16-bit 16-bit

Page 46: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Fixed Point Arithmetic (2)•Add add r0, r1, r2

•Sub sub r0, r1, r2

•Mulsmull r1,r2,x,ymovs r1,r1,lsr #16adc r0,r1,r2,lsl #16

r2[31:0] r1[31:0]

r2[15:0]r1[31:16

]r0[31:0]

00…00r1[31:16

]r2[15:0] 00…00

Page 47: Embedded Systems C programming. Reference Data definition and storage const int a=43; unsigned int b=66; unsigned int c; int main(void) { static int

Fixed Point Arithmetic (3) ldr r1, dividend ldr r2, divider

mov r9,#0x10000 clz r3,r1 @how many 0 in the head of r1 clz r4,r2 subs r4,r4,r3 @r4-r3 movgt r2,r2,lsl r4 movgt r9,r9,lsl r4 @r9<<=r4 rsblt r4,r4,#0 @r4=-r4 if r4<0 movlt r1,r1,lsl r4 movlt r9,r9,lsr r4 @r9>>=r4

loop: subs r3,r1,r2 addhs r0,r0,r9 @r3>=0: r0+=r9, hs/cs is unsigned >=@note that must used unsigned compare@because r1 may overflow to bigger than 0x80000000 when <<1 movhi r1,r3,lsl #1 @r3> 0: r1=r3<<1, hi unsigned > movlo r1,r1,lsl #1 @r3< 0: r1<<=1, lo/cc is unsigned < beq finish @r3= 0: end movs r9,r9,lsr #1 @r3<>0: r9>>=1 bne loop @r9<>0: loop @it means that @if r1>r2: r0+=r9, r1=(r1-r2)<<1,r9>>=1 @if r1=r2: r0+=r9, go finish @if r1<r2: r1=r1<<1,r9>>=1

clz r4,r2 @find how many 0 in the head of r2loop: subs r3,r1,r2 addhs r0,r0,r9 @r3>=0: r0+=r9, hs/cs is unsigned >=

beq finish @r3= 0: end clzhi r5,r3 subhi r5,r5,r4 @r5=r5-r4,then should lsl r3 for r5 bit movhi r1,r3,lsl r5 @r3> 0: r1=r3<<r5, hi unsigned > movlo r1,r1,lsl #1 @r3< 0: r1<<=1, lo/cc is unsigned < movs r9,r9,lsr r5 @r3<>0: r9>>=r5 bne loop @r9> 0: loop @it means that @if r1>r2: r0+=r9, r1=(r1-r2)<<n,r9>>=n @if r1=r2: r0+=r9, go finish @if r1<r2: r1=r1<<1,r9>>=1

clz r4,r2 @find how many 0 in the head of r2loop: subs r3,r1,r2 movlo r9,r9,lsr #1 @r1<r2: r9>>=1 rsblos r3,r2,r1,lsl #1@r1<r2: r3=(r1<<1)-r2 and then the compare result must be >=0 @so the next few instruction omit compare condition > or >= add r0,r0,r9 @r3>=0: r0+=r9, hs/cs is unsigned >=

beq finish @r3= 0: end clz r5,r3 @compare result must be >=0, so omit hi(>) sub r5,r5,r4 @r5=r5-r4,then should lsl r3 for r5 bit, r5 must >=1 mov r1,r3,lsl r5 @r3> 0: r1=r3<<r5, then r1 and r2's clz is equal movs r9,r9,lsr r5 @r3<>0: r9>>=r5 bne loop @r9> 0: loop