1HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Passing Credentials
And File Description
PL 실험실
석사 1 학기 박병태
2HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
목 차목 차
Ancillary Data 소개
I/O Vector 소개
sendmsg(2) 와 recvmsg(2) 함수
Ancillary Data 구조체와 매크로
Ancillary Data 사용 예
Socket Server 의 테스트
3HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 소개소개
특징
credential 은 보조데이타의 부분으로 수락
보조데이터는 보통의 자료를 수반
보조데이터는 여러 개의 보조 항목을 포함
4HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
I/O Vector I/O Vector 소개소개 (1)(1)
I/O Vector(struct iovec) struct iovec
ptr_t iov_base; /* 시작 주소 */
size_t iov_len; /* 바이트 길이 */
Struct iovec 은 하나의 백터 원리로 정의된다
보통 이구조체는 여러 개의 요소에서 배열처럼 사용
readv(2) 와 writev(2) 의 함수에서 사용
5HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
I/O Vector I/O Vector 소개소개 (2)(2)
readv(2) 와 writev[2] 함수
함수의 원형
#include <sys/uio.h> int readv(int fd, const struct iovec *vector, int count) int writev(int fd, const struct iovec *vector, int count) - 3 가지 인수의 대한 설명 int fd : 파일 기술자 const struct iovec *vector : 읽고 쓰기 위해 사용되는 I/O vec
tor Int count: 사용하는 백터 요소의 수
6HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
I/O Vector I/O Vector 소개소개 (3)(3)
writev(2) 를 사용하는 예제 17.1 순서도
함수선언 / 초기화
Iovec iov[] 정의
I/O vector 할당스트링 길이 결정
Writev(2) 시스템 콜
7HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
I/O Vector I/O Vector 소개소개 (4)(4)
소스분석 ( 예제 17.1)
9 : static char part2[] = “ THIS IS FROM WRITEV”;10: static char part3[] = “]\n”;11: static char part1[] = “[“;
물리적으로 분리된 스트링 세개를 정의
12: struct iovec iov[3];
I/O vector iov[3] 이 정의
14: iov[0].iov_base = part1;15: iov[0].iov_len = strlen(part1);
14 라인에서 첫번째 스트링의 포인터를 I/O Vector 에 할당15 라인에서 첫번째 스트링의 길이가 결정
23: writev(1, iov, 3);
23 라인에서 writev 시스템 콜이 실행된다 . 인수의 1 은 표준출력에 사용되고I/Ovector 배열 iov 이 제공되고 3 은 세개의 값을가진 3 개의 인자로 정의 된다 .
8HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
I/O Vector I/O Vector 소개소개 (5)(5)
실행
실행결과
$ make writevgcc -g -c -D_GNU_SOURCE -Wall -Wreturn -type writev.cgcc writev -O -o writev
$ ./writev[THIS IS FROM WRITEV]$
9HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
sendmsg(2)sendmsg(2) 와 와 recvmsg(2) recvmsg(2) 함수함수 (1)(1)
sendmsg(2) 함수 sendmsg 함수의 원형
# include <sys/types.h>
# include <sys/socket.h>
int sendmsg(int s, const struct msghdr *msg, unsigned int flags);
- Sendmsg 에 대한 설명- 보내는 메시지 소켓 S
- 구조체 포인터 msg 메시지 헤더는 이 함수호출의 연산자를 제어 .
- 선택적 플래그 비트 인수 . 이것은 send(2) 와 sendto(2) 의 함수호출에 유효한 같은 플래그 임 .
- 이 함수의 리턴값은 보낸 바이트 수
10HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
sendmsg(2)sendmsg(2) 와 와 recvmsg(2) recvmsg(2) 함수함수 (2)(2)
recvmsg(2) 함수 함수의 원형 # include <sys/type.h>
# include <sys/socket.h>
int recvmsg(int s, struct msghdr *msg, unsigned int flags);
- recvmsg 에 대한 설명- 메시지를 받는 소켓 s
- 구조체 포인터 msg 메시지 헤더는 함수호출의 연산자 제어
- 선택적 플래그 비트 인수 . 이것은 recv(2) 와 recvfrom(2) 함수호출에 유용한 같은 플래그
- 이함수의 리턴값은 받은 바이트의 수
11HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
sendmsg(2)sendmsg(2) 와 와 recvmsg(2) recvmsg(2) 함수함수 (3)(3)
Struct msghdr 의 이해 구조체의 정의 Struct msghdr{
void *msg_name; socklen_t msg_namelen; struct iovec msg_iov; size_t *msg_iovlen;
void msg_control; size_t msg_controllen; int msg_flags;
}이 구조체 맴버는 4 개의 그룹으로 나눌수 있다 . 소켓 주소 맴버 msg_name 과 msg_namelen 참조 I/O vector msg_iov 와 msg_iovlen 보조자료 버퍼 맴버 msg_control 와 msg_controllen 받아진 메시지 플레그 비트 msg_flags.
12HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 구조체와 매크로구조체와 매크로 (1)(1)
struct cmsghdr 구조체 소개 구조체의 정의
struct cmsghdr{ socklen_t cmsg_len; int cmsg_level; int cmsg_type;
/* u_char cmsg_data[];*/ };- 구조체 맴버에 대한 설명
- cmsg_len 은 구조상의 헤더의 크기를 포함하는 보조 자료의 바이트 총계 이 값은 CMSG_LEN() 매크로에 의해 계산 - cmsg_level 이 값는 시작되고 있는 프로토콜 수준- cmsg_type 이 값 제어 통제 메시지 형- cmsg_data 이 멤버는 실제로는 존재하지 않는다 . 그것은 설명에서 추가 보조
자료가 물리적으로 위치하는지 설명하는 것을 나타내어진다
13HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 구조체와 매크로구조체와 매크로 (2)(2)
ancillary objectnumber 1
ancillary objectnumber 2
cmsg_len()
cmsg_level()
cmsg_type()
padding
cmsg_len()
cmsg_level()
cmsg_type() padding
cmsg_data[] cmsg_data[]cmsghdr cmsghdr
CMSG_LEN() CMSG_LEN()
CMSG_SPACE() CMSG_SPACE()
Msg_controlen
Figure 17.1
Ancillary data 구조체의 구성
14HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 구조체와 매크로구조체와 매크로 (3)(3)
cmsg(3) 매크로 소개
cmsg(3) 구성 # include <sys/socket.h>
struct cmsghdr *CMSG_FIRSTHDR(struct msghdr *msgh); size_t CMSG_ALIGN(size_t length); size_t CMSG_SPACE(size_t length); size_t CMSG_LEN(size_t length); void *CMSG_DATA(struct cmsghdr *cmsg);
- 몇개의 매크로는 다른 유닉스에서는 사용가능하지 않는다 ( 예를 들어 , FreeBSD 유닉스에는 CMSG_AIGN(), CMSG_SPACE(),
CMSG_SPACE() 매크로가 없다 .)
15HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 구조체와 매크로구조체와 매크로 (4)(4)
보조데이타 루프 예제 struct msghdr msgh; /*Message Hdr*/
struct cmsghdr *cmsg /* Ptr to ancillary hdr*/ int *fd_ptr; /* Ptr fo file descript*/ int received_fd; /*the file descriptor*/ for (cmsg=CMSG_FIRSTHDR(&msgh); cmsg!=NULL; cmsg=CMSG_NXTHDR(&msgh,cmsg)){ if(cmsg->cmsg_level == SOL_SOCKET && cmsg->cmsg_type == SCM_RIGHTS){ fd_ptr = (int*) CMSG_DATA(cmsg); received_fd = *fd_ptr; break; } } if(cmsg == NULL) { /* Error : No file descriptor recv`d */ }
16HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 구조체와 매크로구조체와 매크로 (5)(5)
보조데이타 생성 sturuct msghdr msg; /*Message header*/struct cmsghdr cmsg;/*Ptr to ancillary hdr*/int fd; /*File descriptor to send*/char buf[CMSG_SPACE(sizeof fd)]; /*Anc. Buf */int fd_ptr; /*Ptr to file descriptor*/ msg.msg_control = buf;msg.msg_controllen = sizeof buf;
cmsg = CMSG_FIRSTHDR(&msg);cmsg->cmsg_level = SOL_SOCKET;cmsg->cmsg_type = SCM_RIGHTS;cmsg->cmsg_len = CMSG_LEN(sizeof fd); /*Initialize the payload:*/fd_ptr = (int *) CMSG_DATA(cmsg);*fd_ptr = fd; /*Sum of the length of all controlmessages in the buffer: */ msg.msg_controllen = cmsg -> cmsg_len;
17HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 예제예제
recvcred.c( 예제 17.4) 순서도
Recv_fd() 호출
초 기 화
구조체 msghdr 초기화
메시지 수신
사용자 인증
18HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 예제예제
초기화 [32-49]32: int s, /*Socket
*/33: struct ucred *credp, /*Credential buffer*/34: void *buf, /*receiving Data buffer*/35: unsigned bufsiz, /* Recv. Data buf size*/36: void *addr, /*Received Peer address*/37: socklen_t *alen) /* Ptr to addr length*/38:39: int z;40: struct msghdr msgh; /* Message header */41: struct iovec iov[1]; /* I/O vector */42: struct cmsghdr *cmsgp=NULL;43: char mbuf[CMSG_SPACE(sizeof * credp)];44:45: /*46: *Zero out message areas:47: */48: memset(&msgh,0,sizeof msgh);49: memset(&mbuf,0,sizeof mbuf);
19HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 예제예제
구조체 msghdr 초기화54: msgh.msg_name=addr;55: msgh.msg_namelen=alen?*alen : 0;
60: msgh.msg_iov=iov; 61: msgh.msg_iovlen=1;
66: iov[0].iov_base=buf; 67: iov[0].iov_len=bufsiz;
72: msgh.msg_control=mbuf; 73: msgh.msg_controllen=sizeof mbuf;
20HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 예제예제
메시지 수신
78: do 79: z=recvmsg(s,&msgh,0);80: while (z==-1 && errno == EINTR);81:82: if(z==1)83: return -1; /*Failed:check errno*/84:85: /*86: * If ptr alen is non-NULL, return the87: * returned address length (datagrams):88; */89: if(alen)90: *alen=msgh.msg_namelen;91:92: /*93: *Walk the list of control messages:94: /*95: for(cmsgp=CMSG_FIRSTHDR(&msgh);96: cmsgp != NULL;97: cmsgp=CMSG_NXTHDR(&msgh,cmsgp) ) 98:99: if(cmsgp->cmsg_lever == SOL_SOCKET100: && cmsgp->cmsg_type==SCM_CREDENTIALS)
21HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 예제예제
사용자 인증
95: for(cmsgp=CMSG_FIRSTHDR(&msgh);96: cmsgp != NULL;97: cmsgp=CMSG_NXTHDR(&msgh,cmsgp) ) 98:99: if(cmsgp->cmsg_lever == SOL_SOCKET100: && cmsgp->cmsg_type==SCM_CREDENTIALS)101:102: /*103: *Pass back credentials struct:104: */105: *credp=*106: (struct ucred *) CMSG_DATA(cmsgp);107:108: return z; /* 3 of data byes read */117: errno=ENOENT;118: return -1;
22HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 예제예제
간단한 웹 서버 ( 예제 17.5) 순서도
함수선언 / 초기화
소켓 생성 / 바인드Socket(); bind();
Reqport(80) 호출
Listen(2) 호출
c=accept(s,(struct sockaddr *)&a_cln,*alen);
rx=fdopen(c,"r"); tx=fdopen(dup(c),"w");
fgets(getbuf,sizeof getbuf,rx); .
fclose() ;
fput();
23HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 예제예제
reqport() 함수 순서도 ( 예제 17.6)
reqport() 호출
소켓 생성
connect(2) 호출
write(2) 호출
recv-fd() 호출
close() 호출
24HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 예제예제
recv_fd 함수 순서도 ( 예제 17.7)
Recv_fd() 호출
선 언
msghdr 구조체 초기화memset();
구조체 msghdr 초기화
메시지 수신
종 료
25HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 예제예제
소스분석 구조체 msghdr 초기화 43: msgh.msg_iov = iov;
44: msgh.msg_iovlen = 1; 50: iov[0].iov_base = dbuf; 51: iov[0].iov_len = sizeof dbuf;
56: msgh.msg_control = buf; 57: msgh.msg_controllen = sizeof buf;
26HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 예제예제
메시지 수신62: do 63: z=recvmsg(s,&ms 호 ,0);64: while (z== -1 && reeno == EINTR);65:66: if (z==-1)67: return -1; /* Failed: see errno*/
73: for ( cmsgp = CMSG_FIRSTHDR(&msgh);74: cmsgp !=NULL;75: cmsgp = CMSG_NXTHDR(&msgh, cmsgp) 76:77: if (cmsgp->cmsg_level == SOL_SOCKET78: && cmsgp -> cmsg_type == SCM_RIGHTS)
82: return *(int *) CMSG_DATA(cmsgp);
92: if (z== sizeof (int) )93: errno = *(int *)dbuf; /* Rcvd errno*/94: else95: errno = ENOENT; /*Default errno*/96:97: return -1; /* Return failure indication */
27HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 예제예제
sockserv 서버 프로그램 순서도 ( 예제 17.8)
함 수 선언
초 기 화
UserID 생성Fputs();
socket(); 호출
listen(2); 호출
연결을 기다림accept();
종 료
28HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 예제예제
Send_fd() 함수- 소켓 서버는 요구한 처리 결과를 보내주기 위하여 send_f
d() 를 사용한다 . 순서도 ( 예제 17.9)
함 수 선언
메시지 clearmemset();
구조체 msghdr 초기화
Client process 송신sendmsg();
29HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
구조체 msghdr 초기화
33: memset(&msgh,0,sizeof msgh); 34: memset(buf,0,sizeof buf);
39: msgh.msg_name = addr; 40: msgh.msg_namelen = alen;
45: msgh.msg_iov = iov; 46: msgh.msg_iovlen = 1;
54: iov[0].iov_base = &er; 55: iov[0].iov_len = sizeof er;
60: msgh.msg_control = buf; 61: msgh.msg_controllen = sizeof buf;
Ancillary Data Ancillary Data 예제예제
30HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Ancillary Data Ancillary Data 예제예제
메시지 clear 67: cmsgp = CMSG_FIRSTHDR(&msgh); 68: cmsgp->cmsg_level = SOL_SOCKET; 69: cmsgp->cmsg_type = SCM_RIGHTS; 70: cmsgp->cmsg_len = CMSG_LEN(sizeof fd);
75: *((int *)CMSG_DATA(cmsgp)) = fd; 76: msgh.msg_controllen = cmsgp->cmsg_len;
client process 송신
81: do { 82: z = sendmsg(s,&msgh,0); 83: } while ( z == -1 && errno == EINTR ); 84: 85: return z == -1 ? -1 : 0;
31HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Socket ServerSocket Server 의 테스트의 테스트
결과$ ./web80 stand_alonePermission denied: binding port 80$
32HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Socket ServerSocket Server 의 테스트의 테스트
Sockserv 테스트예제 1
예제 2
$ su rootPssword:# ./sockserv fred &[1] 1077#
$ ./web80 &[1] 1079$
33HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
Socket ServerSocket Server 의 테스트의 테스트
예제 3$ telnet 127.0.0.1 80Trying 127.0.0.1...Connected to 127.0.0.1.Escape character is '^]'.GET/something<HTML><HEAD><TITLE> Test Page for this little web80 server</TITLE></HEAD><BODY><H1>web80 Worked!</H1><H2>From PID 1079 @Sat Nov 20 12:39:26 1999</H2></BODY></HTML>Connection closed by foreign host.$
34HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
참고자료참고자료
쓰기 함수
SCM_RIGHTS 와 SCM_CREDENTIALS
함수 추가된 특징write(2) 단순한 소켓쓰기 함수
send(2) 플래그 인자 추가 sendto(2) 소켓주소와 소켓길이 인자 추가 writev(2) 플래그와 소켓주소는 없고 , 분산해서 쓰기 sendmsg(2) 플래그와 소켓주소와 길이 추가 분산된 쓰기
cmsg_level 설 명SCM_RIGHTS 보조데이터 개체는 파일기술자이다
SCM_CREDENTIALS
보조데이터는 신임장 정보를 포함한 구조체이다
35HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
참고자료참고자료
struct msghdr msg_flags values Flag bit 설명
MSG_EOR 이 플래그 비트는 레코드를 끝까지 받았을 때 설정된다 .이것은 보통은 SOCK_SEQPACKET 소켓 형으로 사용된다
MSG_TRUNC 이 플래그 비트는 데이터그램의 끝부분이 짤려졌을 때를 나타낸다 왜냐하면 버퍼를 받을 때 너무나 작아서 이것을 적용할 수가 없다
MSG_CTRUNC 이 비트는 몇몇의 제어 ( 보조 ) 데이터가 버퍼가 너무 작기 때문에 절삭되었다는 것을 지적한다
MSG_OOB 이 비트는 데이터가 범위를 넘거나 빨리 받아 졌다는 것을 지적한다
MSG_ERRQUEUE
이 플래그 비트는 데이터를 받지 않았다는 것을 지적한다 . 그러나 확장된 애러를 돌려준다 .
36HANNAM UNIVERSITYHttp://netwk.hannam.ac.kr
참고자료참고자료