카테고리 없음

20160315_최기영_업무일지

embsoft90 2016. 3. 16. 11:47
오전




11일에 작성한 소스와 14일에 작성한 함수를 합쳐보자

/*
FND가 깜빡거리긴하는데 제대로 작동하는지 모르겠다.
*/

#include "main.h"


int main(void) 
{
    volatile unsigned int uiCnt;
       volatile unsigned int uiLoop;
    uiCnt = 0;
    DDRA = 0xFF;
    PORTA = 0x00;    //전체 LED를 켠다.
    EICRA = (3<<ISC0);    //상승엣지 binary 11= decimal 3이므로
    EIMSK = (1<<INT0);
    SREG = SREG | (1<<7);//sei(); 와 같은 말, 기존에 있던 값을 유지해야하기 때문에 SREG | 를 추가 해야한다.
                        //sei(); 어셈블리 명령어로 7번 비트만 1로 만드는 것   


    while(1)
    {
        PORTA = ((uiCnt/10)<<4)|(uiCnt%10);   
            for(uiLoop = 0; uiLoop<60000; ++uiLoop);
            for(uiLoop = 0; uiLoop<60000; ++uiLoop);
               ++uiCnt;   
            if(uiCnt > 99)
            {
                 uiCnt = 0;
               }
        sleep();   
    }   
    return 0;
}
void __vector_1(void)
{
    volatile unsigned int uiCnt;
    for(uiCnt = 0; uiCnt<60000; ++uiCnt);
    PORTA = 0xFF;

}

/*
보이드 벡터를 주석 처리했더니 리셋이 가능해졌다....

*/


#include "main.h"


int main(void) 
{
    volatile unsigned int uiCnt;
       volatile unsigned int uiLoop;
    uiCnt = 0;
    DDRA = 0xFF;
    PORTA = 0x00;    //전체 LED를 켠다.
    EICRA = (3<<ISC0);    //상승엣지 binary 11= decimal 3이므로
    EIMSK = (1<<INT0);
    SREG = SREG | (1<<7);//sei(); 와 같은 말, 기존에 있던 값을 유지해야하기 때문에 SREG | 를 추가 해야한다.
                        //sei(); 어셈블리 명령어로 7번 비트만 1로 만드는 것   


    while(1)
    {
        PORTA = ((uiCnt/10)<<4)|(uiCnt%10);   
            for(uiLoop = 0; uiLoop<60000; ++uiLoop);
            for(uiLoop = 0; uiLoop<60000; ++uiLoop);
               ++uiCnt;   
            if(uiCnt > 99)
            {
                 uiCnt = 0;
               }
        sleep();   
    }   
    return 0;
}
/*
void __vector_1(void)
{
    volatile unsigned int uiCnt;
    for(uiCnt = 0; uiCnt<60000; ++uiCnt);
    PORTA = 0xFF;

}*/









위의 소스를 함수를 만들어서 분리해보자
  1.     void Init(void){} 추가
  2.     void Port_Init(void){} 추가
  3.     void INT_Init(void){} 추가

/*
파일 이름 : main.c
작성 날짜 : 2016-03-15
작성 시간 : 09:40
*/

#include "main.h"
int main(void) 
{
    volatile unsigned int uiCnt;
       volatile unsigned int uiLoop;
    uiCnt = 0;
    DDRA = 0xFF;
    PORTA = 0x00;    //전체 LED를 켠다.
    EICRA = (3<<ISC0);    //상승엣지 binary 11= decimal 3이므로
    EIMSK = (1<<INT0);
    SREG = SREG | (1<<7);//sei(); 와 같은 말, 기존에 있던 값을 유지해야하기 때문에 SREG | 를 추가 해야한다.
                        //sei(); 어셈블리 명령어로 7번 비트만 1로 만드는 것   


    while(1)
    {
        PORTA = ((uiCnt/10)<<4)|(uiCnt%10);   
            for(uiLoop = 0; uiLoop<60000; ++uiLoop);
            for(uiLoop = 0; uiLoop<60000; ++uiLoop);
               ++uiCnt;   
            if(uiCnt > 99)
            {
                 uiCnt = 0;
               }
        sleep();   
    }   
    return 0;
}

void Init(void)
{
    INT_Init();
    Port_Init();
}
void Port_Init(void)
{ }
void INT_Init(void)
{ }
void __vector_1(void)
{
    volatile unsigned int uiCnt;
    for(uiCnt = 0; uiCnt<60000; ++uiCnt);
    PORTA = 0xFF;

}
/*
파일 이름 : main.h
작성 날짜 : 2016-03-15
작성 시간 : 09:40
*/

#ifndef __MAIN_H__
#define __MAIN_H__

#define PINA (*((volatile unsigned char *)0x20))
#define DDRA (*((volatile unsigned char *)0x21))
#define PORTA (*((volatile unsigned char *)0x22))

#define EICRA (*((volatile unsigned char *)0x69))
#define EICRB (*((volatile unsigned char *)0x6A))

#define EIMSK (*((volatile unsigned char *)0x3D))
#define SREG (*((volatile unsigned char *)0x5F))

#define sei()   __asm__ __volatile__ ("sei" ::)
#define sleep()    __asm__ __volatile__ ( "sleep" "\n\t" :: )    //무한 while보단 좋다.

#define INT7 7
#define INT6 6
#define INT5 5
#define INT4 4
#define INT3 3
#define INT2 2
#define INT1 1
#define INT0 0

#define ISC7 6
#define ISC6 4
#define ISC5 2
#define ISC4 0
#define ISC3 6
#define ISC2 4
#define ISC1 2
#define ISC0 0

void __vector_1 (void) __attribute__((signal, used, externally_visible));    //0번 인터럽트에 대한 코드 pdf에 있는것 +1==>인터럽트 0번
void Init(void);
void INT_Init(void);
void Port_Init(void);

#endif //__MAIN_H__

#include "main.h"





int main(void) 
{
    volatile unsigned int uiCnt;
       volatile unsigned int uiLoop;
    uiCnt = 0;
    Init(void);

    while(1)
    {
        PORTA = ((uiCnt/10)<<4)|(uiCnt%10);   
            for(uiLoop = 0; uiLoop<60000; ++uiLoop);
            for(uiLoop = 0; uiLoop<60000; ++uiLoop);
               ++uiCnt;   
            if(uiCnt > 99)
            {
                 uiCnt = 0;
               }
        sleep();   
    }   
    return 0;
}

void Init(void)
{
    Port_Init();
    INT_Init();
}

void Port_Init(void)
{
    DDRA = 0xFF;
    PORTA = 0x00;    //전체 LED를 켠다.
}

void INT_Init(void)    //인터럽트 초기화
{
    EICRA = (3<<ISC0);    //상승엣지 binary 11= decimal 3이므로
    EIMSK = (1<<INT0);
    SREG = SREG | (1<<7);//sei(); 와 같은 말, 기존에 있던 값을 유지해야하기 때문에 SREG | 를 추가 해야한다.
                        //sei(); 어셈블리 명령어로 7번 비트만 1로 만드는 것       
}
void __vector_1(void)
{
    volatile unsigned int uiCnt;
    for(uiCnt = 0; uiCnt<60000; ++uiCnt);
    PORTA = 0xFF;   
}

#include "main.h"

int main(void) 
{
    volatile unsigned int uiCnt;
       volatile unsigned int uiLoop;
    uiCnt = 0;
    Init(void);

    while(1)
    {
        PORTA = ((uiCnt/10)<<4)|(uiCnt%10);   
            for(uiLoop = 0; uiLoop<60000; ++uiLoop);
            for(uiLoop = 0; uiLoop<60000; ++uiLoop);
               ++uiCnt;   
            if(uiCnt > 99)
            {
                 uiCnt = 0;
               }
        sleep();   
    }   
    return 0;
}

void Init(void)
{
    Port_Init();
    INT_Init();
}

void Port_Init(void)
{
    DDRA = 0xFF;
    PORTA = 0x00;    //전체 LED를 켠다.
}

void INT_Init(void)    //인터럽트 초기화
{
    EICRA = (3<<ISC0);    //상승엣지 binary 11= decimal 3이므로
    EIMSK = (1<<INT0);
    SREG = SREG | (1<<7);//sei(); 와 같은 말, 기존에 있던 값을 유지해야하기 때문에 SREG | 를 추가 해야한다.
                        //sei(); 어셈블리 명령어로 7번 비트만 1로 만드는 것       
}
void __vector_1(void)
{
    volatile unsigned int uiCnt;
    for(uiCnt = 0; uiCnt<60000; ++uiCnt);
    PORTA = ~PORTA;   
}
void __vector_2(void)
{
    volatile unsigned int uiCnt;
    for(uiCnt = 0; uiCnt<60000; ++uiCnt);
    PORTA = ~PORTA;   
}
#ifndef __MAIN_H__
#define __MAIN_H__

#define PINA (*((volatile unsigned char *)0x20))
#define DDRA (*((volatile unsigned char *)0x21))
#define PORTA (*((volatile unsigned char *)0x22))

#define EICRA (*((volatile unsigned char *)0x69))
#define EICRB (*((volatile unsigned char *)0x6A))

#define EIMSK (*((volatile unsigned char *)0x3D))
#define SREG (*((volatile unsigned char *)0x5F))

#define sei()   __asm__ __volatile__ ("sei" ::)
#define sleep()    __asm__ __volatile__ ( "sleep" "\n\t" :: )    //무한 while보단 좋다.

#define INT7 7
#define INT6 6
#define INT5 5
#define INT4 4
#define INT3 3
#define INT2 2
#define INT1 1
#define INT0 0

#define ISC7 6
#define ISC6 4
#define ISC5 2
#define ISC4 0
#define ISC3 6
#define ISC2 4
#define ISC1 2
#define ISC0 0

void Init(void);
void INT_Init(void);
void Port_Init(void);

void __vector_1 (void) __attribute__((signal, used, externally_visible));    //0번 인터럽트에 대한 코드 pdf에 있는것 +1==>인터럽트 1번
void __vector_2 (void) __attribute__((signal, used, externally_visible));    //1번 인터럽트에 대한 코드 pdf에 있는것 +1==>인터럽트 2번

#endif //__MAIN_H__





위의 코드에 전역변수를 사용하기 위해
전역변수 만들기 연습

컴파일은 주소를 고정시키는 코드를 사용한다.
cl main.c /link /DYNAMICBASE:no
/*
작성 날짜 : 2016-03-15
작성 시간 : 10:48
전역변수 연습
*/
#include <stdio.h>

int D;
int E;
int F;
int G;
int H;

int main()
{
    int A = 0;
    int B;
    int C = 100;

    printf("   A의 주소 : %x \n",&A);
    printf("   B의 주소 : %x \n",&B);
    printf("   C의 주소 : %x \n",&C);
    printf("   D의 주소 : %x \n",&D);
    printf("   E의 주소 : %x \n",&E);
    printf("   F의 주소 : %x \n",&F);
    printf("   G의 주소 : %x \n",&G);
    printf("   H의 주소 : %x \n",&H);

    return 0;
}


#include <stdio.h>

int D;
int E = 99;
int F;
int G = 98;
int H;

int main()
{
    int A = 0;
    int B;
    int C = 100;

    printf("   A의 주소 : %p \n",&A);
    printf("   B의 주소 : %p \n",&B);
    printf("   C의 주소 : %p \n",&C);
    printf("   D의 주소 : %p \n",&D);
    printf("   E의 주소 : %p \n",&E);
    printf("   F의 주소 : %p \n",&F);
    printf("   G의 주소 : %p \n",&G);
    printf("   H의 주소 : %p \n",&H);

    printf("  printf()의 주소 : %p\n",&printf);
    printf("  main()의 주소 : %p\n",&main);
    return 0;
}

/*
2016-03-15
10:48
전역변수 연습
*/
#include <stdio.h>

int D;
int E = 99;
int F;
int G = 98;
int H;

int main()
{
    int A = 0;
    int B;
    int C = 100;
    printf("------Stack 영역-------\n");
    printf("   A의 주소 : %p \n",&A);
    printf("   B의 주소 : %p \n",&B);
    printf("   C의 주소 : %p \n",&C);
    printf("-------BSS 영역--------\n");   
    printf("   H의 주소 : %p \n",&H);
    printf("   F의 주소 : %p \n",&F);
    printf("   D의 주소 : %p \n",&D);
    printf("-------Data 영역-------\n");
    printf("   G의 주소 : %p \n",&G);
    printf("   E의 주소 : %p \n",&E);
    printf("-------Code 영역-------\n");
    printf("  main()의 주소 : %p\n",&main);
    printf("  printf()의 주소 : %p\n",&printf);
    printf("------------------\n");
    return 0;
}




전역변수의 특징을 알아보자

/*
특성1 : 전역변수를  초기화 하지 않으면 값은 binary 0으로 초기화 된다.
*/
#include <stdio.h>

int A;

int main()
{
    printf("%d\n",A);
    return 0;
}

/*
특성2 : 전역변수보다 printf가 속해있는 공간을 우선적으로 찾는다.
*/
#include <stdio.h>

int A;

int main()
{
    int A = 100;
    printf("%d\n",A);
    return 0;
}




#include <stdio.h>

void smart();

int A;

int main()
{
    //int A = 100;

    printf("%d\n",A);
    return 0;
}

void smart(void)
{

}

/*
전역변수 사용시 단점
단점1 :변수 관리가 어렵다.

단점2 :전역변수는 프로그램이 종료될때까지 유지되므로 메모리를 차지하고 있다.
(전역변수는 왠만하면 많이 안쓰는게 좋다.
대부분의 변수는 지역변수로 만들어야한다.)

단점3 : 실행파일 자체의 용량을 키운다.
*/
#include <stdio.h>

void smart();

int A;

int main()
{
    //int A = 100;
    printf("%d\n",A);
    smart();
    printf("%d\n",A);
    return 0;
}

void smart(void)
{
    A=99;
}




다시 인터럽트


/*
main.c만 이렇게 바꿔준다.
*/
#include "main.h"

volatile unsigned int uiState;    //int는 bus의 크기에 맞춰져있다. 양수만 사용하는 unsigned int가 가장 빠른 변수이다.

int main(void) 
{
    volatile unsigned int uiCnt;
       volatile unsigned int uiLoop;
    uiCnt = 0;
    Init();
    uiState = 1;
    while(1)
    {
        PORTA = ((uiCnt/10)<<4)|(uiCnt%10);   
            for(uiLoop = 0; uiLoop<60000; ++uiLoop);
               if(uiState == 1)
        {
            ++uiCnt;
        }   
            if(uiCnt > 99)
            {
                 uiCnt = 0;
               }
        sleep();   
    }   
    return 0;
}

void Init(void)
{
    Port_Init();
    INT_Init();
}

void Port_Init(void)
{
    DDRA = 0xFF;
    PORTA = 0x00;    //전체 LED를 켠다.
}

void INT_Init(void)    //인터럽트 초기화
{
    EICRA = (3<<ISC1) | (3<<ISC0);    //상승엣지 binary 11= decimal 3이므로
    EIMSK = (1<<INT1) | (1<<INT0);
    SREG = SREG | (1<<7);//sei(); 와 같은 말, 기존에 있던 값을 유지해야하기 때문에 SREG | 를 추가 해야한다.
                        //sei(); 어셈블리 명령어로 7번 비트만 1로 만드는 것       
}
void __vector_1(void)//INT0
{
    volatile unsigned int uiCnt;
    for(uiCnt = 0; uiCnt<60000; ++uiCnt);
    uiState = 1;   
}
void __vector_2(void)//INT1
{
    volatile unsigned int uiCnt;
    for(uiCnt = 0; uiCnt<60000; ++uiCnt);
    uiState = 0;
}



















오후