본문 바로가기
코스웨어/11년 내장형하드웨어

[내장형]심재원_2011.10.07일일보고서

by 알 수 없는 사용자 2011. 10. 7.
728x90
반응형
1. 네트워크

●다음은 L3_TCP.c의 일부분이다.
const void* L3_TCP(const void* vpData,unsigned int* uipNext)
{
     const struct tcphdr* stpTCP=vpData;
  
     printf("Header length: %u bytes\n",(stpTCP->doff)*4);

     printf("ACK bit: %s\n",(stpTCP->ack)?"YES":"NO");

     printf("SYN bit: %s\n",(stpTCP->syn)?"YES":"NO");

     printf("FIN bit: %s\n",(stpTCP->fin)?"YES":"NO");

     *uipNext=(ntohs(stpTCP->source)<ntohs(stpTCP->dest))?
              (ntohs(stpTCP->source)):(ntohs(stpTCP->dest));
}

위의 소스를 보면 'struct tcphdr'을 사용하고 있다. 이는, '/usr/include/netinet/tcp.h'에 선언되어 있다. 다음은 'struct tcphdr'의
내용 이다.
89 struct tcphdr
90 {
91     u_int16_t source; //source port 번호
92     u_int16_t dest; //destination port 번호
93     u_int32_t seq; //sequence number
94     u_int32_t ack_seq; //acknowledgement number
95 #  if __BYTE_ORDER == __LITTLE_ENDIAN
96     u_int16_t res1:4;
97     u_int16_t doff:4;
98     u_int16_t fin:1;
99     u_int16_t syn:1;
100     u_int16_t rst:1;
101     u_int16_t psh:1;
102     u_int16_t ack:1;
103     u_int16_t urg:1;
104     u_int16_t res2:2;
105 #  elif __BYTE_ORDER == __BIG_ENDIAN //여기에 해당하는 걸 사용함
106     u_int16_t doff:4//이 값에 *4 하면 헤더 크기임    
107     u_int16_t res1:4//res1과 res2는 reserved임
108     u_int16_t res2:2;
109     u_int16_t urg:1
110     u_int16_t ack:1;
111     u_int16_t psh:1;
112     u_int16_t rst:1;
113     u_int16_t syn:1;
114     u_int16_t fin:1;
115 #  else
116 #  error "Adjust your <bits/endian.h> defines"
117 #  endif
118     u_int16_t window; //window 사이즈
119     u_int16_t check; //checksum
120     u_int16_t urg_ptr;
121 };

struct tcphdr에서 105번째 줄에 있는 #  elif __BYTE_ORDER == __BIG_ENDIAN의 elif __BYTE_ORDER는
네트워크를 의미한다. 

위에 있는 'L3_TCP.c'와 'struct tcphdr'을 서로 비교해 가며 설명을 한다.
struct tcphdr에 있는 doff는 2바이트가 할당되어지고 거기서 4비트만 사용을 한다. 'L3_TCP.c'에서 
헤더크기를 출력하기 위하여 doff는 2바이트가 할당되어져 있으니, ntohs()함수를 사용해야 겠다고 생
각할 수 있으나 이는 오산이다. doff는 정확히 말하면 4비트 이므로 ntohs()함수를 사용하지 않고 바로
출력하면 된다.  

다음의 코드는 위에 적은 'L3_TCP.c'에서 발췌한 것이다. 이는 L4_HTTP()함수를 호출할 조건문에 사용
을 하기 위한 것이다.
*uipNext=(ntohs(stpTCP->source)<ntohs(stpTCP->dest))?
         (ntohs(stpTCP->source)):(ntohs(stpTCP->dest));
우리말로 풀어보자면 소스 포트번호가 목적지 포트번호 보다 작다면 소스포트 번호를 uipNext가 가리키는 곳, 즉 main.c에 있는 uiNext에 대입을 한다는 것이다. 반대로 목적지 포트번호가 더 작은 경우에는 *uipNext에 목적지 포트번호가 대입된다. 간단히 말하면 소스와 목적지 포트번호는 서로 같은 경우가 없으니, 2개를 서로 비교하여 작은 것은 *uipNext에 대입을 하는 것이다.
일반 PC에서 사용하는 포트번호는 80번 보다 크다. 'L4_HTTP()함수'를 호출할 조건문은 source나 destination의 포트번호가 80
번이면 참이 되도록 할 것이므로, source와 destination 포트 번호 중 더 작은 것을 *uipNext에 대입을 하는 것이다.

다음은 'L4_HTTP()함수'이다.

//L4_HTTP.c 

#include "L4_HTTP.h"

const void* L4_HTTP(const void* vpData,unsigned int* uipNext) //uiNext에는 HTML문서 크기
{                                                             //가 들어가 있음
     const unsigned char* ucpData=vpData;

     while(0!=*uipNext) //*uipNext는 출력되지 않은 HTML문자 수와 동일함
     {
         putchar(*ucpData); //HTML코드를 한 문자 출력함
         ++ucpData;
         *uipNext=*uipNext-1;
     }
}

최초 while문 조건에 들어 있는 *uipNext에는 출력되지 않은 HTML문자의 수가 들어가 있다. while문 안에서는 한 문자를 출력
하고 출력되지 않은 HTML 문자 수에서 1을 빼주고 있다. 이렇게 하나 출력하고, 출력되지 않은 문자 갯수에서 하나씩 감소를
시키면 *uipNext에 들어 있는 숫자는 출력해야 될 문자의 개수라 보아도 된다. 즉, 출력해야 될 문자의 개수가 0 이면 while문
을 빠져 나오는 것이다.



728x90