소켓 프로그램 컴파일 문제 입니다.(리눅스에서 잘됨.. 솔라리
글쓴이: qprk / 작성시간: 수, 2003/07/16 - 7:06오후
리눅스에서 gcc agent.c
하면 아무 불평없이 컴파일 잘 되고 동작도 잘 합니다.
하지만 솔라리스에서 gcc agent.c
하면 아래와 같은 메시지를 뿌립니다.
Quote:
정의되지 않음 첫번째 참조된
기호 파일의
socket /var/tmp//ccZJnigl.o
gethostbyname /var/tmp//ccZJnigl.o
inet_addr /var/tmp//ccZJnigl.o
connect /var/tmp//ccZJnigl.o
ld: 치명적: 기호 참조 오류. a.out에 출력이 기록되지 않음
collect2: ld returned 1 exit status
솔라리스에서 코딩이 처음이라.. 난감하내요 :cry:
소스코드는 아래와 같습니다.
#include <stdlib.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/ioctl.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <netdb.h>
#include <errno.h>
#include <signal.h>
#define DEFAULT_PORT 80
#define MAX_HTML_BUFF 1000000 /* html file을 저장할 공간 */
#define INADDR_NONE -1
struct sockaddr_in serverAddress;
struct hostent hostInfo;
int startRobot(char *, char *, char *);
int HTTPConnect(char *);
void Request(int ,char *);
long Response(int , char *);
int CheckStatus(char *);
void time_out(int );
int HTTPConnectSockFD;
long fileSize;
void time_out(int sig)
{
close(HTTPConnectSockFD);
}
void SigExit(int sig)
{
printf("===== ERROR SIG_TYPE: %d =====\n",sig);
printf("===== ERROR NO: %d, %s =====\n",errno, strerror(errno));
signal(SIGINT,SIG_IGN);
kill(0,SIGINT);
printf("\a !!! 오류 : \033[>7m프로그램이 비정상적으로 종료되었습니다 \033[0m\n");
exit(-1);
}
void Signal(void)
{
signal(SIGQUIT,SigExit);
signal(SIGINT,SigExit);
signal(SIGTERM,SigExit);
signal(SIGHUP,SigExit);
signal(SIGSEGV,SigExit);
signal(SIGBUS,SigExit);
signal(SIGKILL,SigExit);
signal(SIGALRM, time_out);
}//Signal()
/***************************************************************
* main
* 각종 기본 환경 설정
***************************************************************/
int main()
{
char htmlBuff[MAX_HTML_BUFF];
Signal();
printf("===============================================\n");
if((startRobot("www.***.co.kr", "*****.html", htmlBuff)) == -1) {
printf("[<31mstartRobot() error!![<0m\n");
// continue;
}
close(HTTPConnectSockFD);
return 0;
}
/***************************************************************
* url을 할당받아 로봇을 가동
***************************************************************/
int startRobot(char *host, char *uri, char *htmlBuff)
{
char jobUrl[512];
int sockfd;
FILE *fp;
char *noHeader;
sockfd = HTTPConnect(host);
if (sockfd == -1)
return -1;
Request(sockfd,uri);
/* 서버로 부터의 응답 메세지가 없을 경우 */
if((fileSize=Response(sockfd, htmlBuff)) <=0 ) {
printf("No Response From\n");
return -1;
}
// resetBuff=fileSize;
sprintf(jobUrl, "%s%s",host,uri);
// printf("\njobUrl -> %s\n\n",jobUrl);
noHeader = strstr(htmlBuff, "\r\n\r\n");
fp = fopen("out.html", "w");
fprintf(fp, "%s", noHeader + 4);
return 1;
}
/***************************************************************
* host에 접속
***************************************************************/
int HTTPConnect(char *hostname)
{
int status;
unsigned long IPAddr;
struct hostent *hostp;
// char **addrs;
char portBuff[512];
int isPort, i;
isPort = 0;
memset(portBuff, 0, 512);
strncpy(portBuff, hostname, 512);
// signal(SIGALRM, time_out);
bzero((char *)&serverAddress, sizeof(serverAddress));
serverAddress.sin_family = AF_INET;
// prot 추출하기
if(strchr(portBuff, ':') != NULL) {
for(i=0; portBuff[i] != ':' ; i++) ;
portBuff[i]= '\0';
// printf(" 여긴가???,,,%d,,,%c,,,%s\n",i , portBuff[i], &portBuff[i+1]);
isPort = atoi(&portBuff[i+1]);
}
if(isPort) /* 80port 말고 다른거 사용할 경우 */
serverAddress.sin_port = htons(isPort);
else
serverAddress.sin_port = htons(DEFAULT_PORT);
// printf("사용 포트는 ??? %d\n",isPort);
/* IP 주소인지 도메인 이름인지 체크한다. */
if((IPAddr = inet_addr(portBuff)) != INADDR_NONE){
bcopy((char *)&IPAddr,(char *)&serverAddress.sin_addr,sizeof(IPAddr));
hostInfo.h_name = NULL;
}
else
{
if((hostp = gethostbyname(portBuff)) == NULL){
printf("[<31m!!!!TCP Error[<0m : hostname error %s\n",portBuff);
return(-1);
}
// addrs = hostp->h_addr_list;
// printf("host ip = %s\n", inet_ntoa(*(struct in_addr *)*addrs));
hostInfo = *hostp;
bcopy(hostp->h_addr, (char *)&serverAddress.sin_addr, hostp->h_length);
}
/* 실제로 소켓을 열어서 서버와 연결 */
HTTPConnectSockFD = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if(HTTPConnectSockFD < 0){
printf("[<31m[x][0m Socket open error!\n");
return -1;
}
alarm(3);
status = connect(HTTPConnectSockFD, (struct sockaddr *)&serverAddress, sizeof(serverAddress));
if(status < 0) {
// printf("[<31m호스트에 연결이 되지 않습니다.[0m\n");
alarm(0);
return -1;
}// if(status < 0) {
// printf("[<32m[o][0m 성공적으로 연결되었습니다.\n");
return HTTPConnectSockFD;
}
/***************************************************************
* 접속된 host에 html 문서를 요청
***************************************************************/
void Request(int reqsockfd, char *refer)
{
char message[512];
sprintf(message,"GET %s HTTP/1.0\r\n\n",refer);
// sprintf(message,"GET %s HTTP/1.0\n\n",refer);
// printf("....%s....\n",message);
/* 실제로 소켓을 통해서 메세지를 보낸다. */
write(reqsockfd,message,sizeof(message));
}
/***************************************************************
* 받아온 문서를 분석하여 정상적으로 처리가 되었는지 확인
***************************************************************/
long Response(int ressockfd, char *htmlBuff )
{
int cnt=0, readcnt=0;
char ch, headers[512];
long i;
do{
if((readcnt = read(ressockfd, &ch,1)) == 1){
headers[cnt++] = ch;
// printf("%c",ch);
}else{
printf("[<31m[x][<0m Socket read error\n");
// close(HTTPConnectSockFD);
return (-1);
}
}while(ch != '\n');
if(!CheckStatus(headers)){
printf("[<31m[x][<0m 서버의 상태 코드가 2xx 게열이 아닙니다.\n");
// close(HTTPConnectSockFD);
return (-1);
}
// if((fp = fopen(K_BOT,"w")) == NULL){
// printf("[%s] 파일을 열 수 없습니다.\n",K_BOT);
// return (-1);
// }
for(i=0; (readcnt = read(ressockfd,&ch,1)); i++) {
if(readcnt == 1)
*(htmlBuff+i)=ch;
// fputc( ch, fp);
else{
printf("[<31m[x][<0m Not reading\n");
// close(HTTPConnectSockFD);
return i;
}
if (i >= MAX_HTML_BUFF -1) {
printf("htmlBuff is Full!!\n");
return i;
}
}
// fclose(fp);
// printf("[<32m[o][0m 무사히 저장되었습니다.\n");
// close(HTTPConnectSockFD);
return i;
}
/***************************************************************
* http 해더가 정상인지 확인
***************************************************************/
int CheckStatus(char *count)
{
int i,k=0;
int j=0,l=0;
char res[200];
for(i=0;i<strlen(count);i++){
if(*(count + i) == ' '){
l++;
for(k=1;;k++){
res[j++] = *(count+i+k);
if(*(count+i+k) == ' ')
break;
}
res[j-1]='\0';
}
if(l == 1)
break;
}
if(atoi(res)>=300)
return 0;
else return 1;
}
Forums:


안녕하세요?링크 문제로 보입니다.socket관련 함수를 쓰
안녕하세요?
링크 문제로 보입니다.
socket관련 함수를 쓰기 위해 socket 라이브러리를 링크하시고,
gethostbyname함수를 쓰기 위해 nsl라이브러리를 링크하시면 될 겁니다.
gcc test.c -lnsl -lsocket참고삼아... 제쪽에서 테스트해보니 FILE *fp때문에 컴파일되지 않았습니다.
stdio.h를 include해야할 것 같습니다.
위와 같은 내용은 man 페이지를 참고하면 웬만한 정보는 다 있으므로
자주 써먹으시면 도움될 겁니다.
그럼...
댓글 달기