I am Implementing a network spooler printer. The server is supposed to sequence print requests from each client and inform them accordingly about their number in the print queue . If the server finishes serving one client, it should inform the connected clients about their new request number or where they are in the request queue. How should i achieve such a functionality?. So far the server can handle print requests from multiple clients and generate a file at its end.
Server.c
#include <stdlib.h>
#include <stdio.h>
#include <errno.h>
#include <string.h>
#include <sys/types.h>
#include <netinet/in.h>
#include <sys/wait.h>
#include <sys/socket.h>
#include <signal.h>
#include <ctype.h>
#include <arpa/inet.h>
#include <netdb.h>
# include<pthread.h>
//#define PORT 20000
#define BACKLOG 5
#define LENGTH 1024
int f=0;
int reqnumber=0;
void error(const char *msg)
{
perror(msg);
exit(1);
}
void *myfunc(void *recvsocket);
//void *myfunc2(void *recvsocket2)
int main(int argc, char *argv[])
{
int sockfd,newsockfd,portno;
socklen_t clilen;
char buffer[32];
struct sockaddr_in serv_addr,cli_addr;
int n;
int num1,num2,sum;
char revbuf[LENGTH];
pthread_t threadid;
if(argc<2)
{
fprintf(stderr,"No port number provided\n");
exit(1);
}
sockfd=socket(AF_INET,SOCK_STREAM,0);
if(sockfd<0)
error("ERROR opning socket");
bzero((char *)&serv_addr,sizeof(serv_addr));
portno=atoi(argv[1]);
serv_addr.sin_family=AF_INET;
serv_addr.sin_addr.s_addr=INADDR_ANY;
serv_addr.sin_port=htons(portno);
if(bind(sockfd, (struct sockaddr *)&serv_addr,sizeof(serv_addr))<0)
error("error on binding");
listen(sockfd,5);
clilen=sizeof(cli_addr);
//int c=80;
while(1)
{
newsockfd=accept(sockfd,(struct sockaddr *)&cli_addr,&clilen);
int a=pthread_create(&threadid,NULL,myfunc,(void *)newsockfd);
//int l=atoi(threadid);
//printf("l:%d",threadid);
pthread_detach(threadid);
sched_yield();
}
}
void *myfunc(void *recvsocket)
{
int tempsock=(int *)recvsocket;
char revbuf[LENGTH];
bzero(revbuf,1024);
int m=read(tempsock,revbuf,sizeof(revbuf));
int d=atoi(revbuf);
if(d==1)
{
char filename[1024] = "/home/tabk/Desktop/texts/serverfiles/spooler";
f=f+1;
reqnumber=reqnumber+1;
bzero(revbuf,1024);
sprintf(revbuf,"%ld",reqnumber);
int m=write(tempsock,revbuf,strlen(revbuf));
bzero(revbuf,1024);
char sockbuf[LENGTH];
bzero(sockbuf,1024);
m=read(tempsock,sockbuf,sizeof(sockbuf));
char filetype[1024];
bzero(filetype,1024);
strcat(filetype,sockbuf);
printf("extension:%s",filetype);
bzero(revbuf,LENGTH);
sprintf(revbuf,"%ld",f);
strcat(filename,revbuf);
strcat(filename,filetype);
printf("\nourfilename:%s",filename);
bzero(revbuf,1024);
int b=1;
sprintf(revbuf,"%ld",b);
m=write(tempsock,revbuf,strlen(revbuf));
char* fr_name=filename;
FILE *fr = fopen(fr_name, "a");
if(fr == NULL)
printf("File %s Cannot be opened file on server.\n", fr_name);
else
{
bzero(revbuf, LENGTH);
int fr_block_sz = 0;
while((fr_block_sz = recv(tempsock, revbuf, LENGTH, 0)) > 0)
{
int write_sz = fwrite(revbuf, sizeof(char), fr_block_sz, fr);
if(write_sz < fr_block_sz)
{
error("File write failed on server.\n");
}
bzero(revbuf, LENGTH);
if (fr_block_sz == 0 || fr_block_sz != 1024)
{
break;
}
}
if(fr_block_sz < 0)
{
if (errno == EAGAIN)
{
printf("recv() timed out.\n");
}
else
{
fprintf(stderr, "recv() failed due to errno = %d\n", errno);
exit(1);
}
}
printf("\nOk received from client!\n");
fclose(fr);
}
close(tempsock);
printf("\n[Server] Connection with Client closed. Server will wait now...\n");
while(waitpid(-1, NULL, WNOHANG) > 0);
}
}
Client.c
#include <stdlib.h>
#include <stdio.h>
#include <errno.h>
#include <string.h>
#include <sys/types.h>
#include <netinet/in.h>
#include <sys/wait.h>
#include <sys/socket.h>
#include <signal.h>
#include <ctype.h>
#include <arpa/inet.h>
#include <netdb.h>
#define LENGTH 1024
void error(const char *msg)
{
perror(msg);
exit(0);
}
int main(int argc, char *argv[])
{
int sockfd,portno,n,s;
struct sockaddr_in serv_addr;
struct hostent *server;
char buffer[32];
char sdbuf[LENGTH];
int f;
char revbuf[LENGTH];
if(argc<3)
{
fprintf(stderr,"usage %s hostname port\n",argv[0]);
exit(0);
}
portno=atoi(argv[2]);
sockfd=socket(AF_INET,SOCK_STREAM,0);
if(sockfd<0)
error("ERROR opning socket");
server=gethostbyname(argv[1]);
if(server==NULL)
{
fprintf(stderr,"ERROR, no such host\n");
exit(0);
}
bzero((char *)&serv_addr,sizeof(serv_addr));
serv_addr.sin_family=AF_INET;
bcopy((char *)server->h_addr,(char *)&serv_addr.sin_addr.s_addr,server->h_length);
serv_addr.sin_port=htons(portno);
if(connect(sockfd,(struct sockaddr*)&serv_addr,sizeof(serv_addr))<0)
error("Errror Connecting");
printf("\nWhich service would you like to avail from network spooler:");
printf("\n1.Request a print \n2.Check Status of Request \n3.Delete Request\n");
int a;
scanf("%d",&a);
bzero(sdbuf,1024);
sprintf(sdbuf,"%ld",a);
n=write(sockfd,sdbuf,strlen(sdbuf));
if(a==1)
{
char fr_name[1024];
//sprintf(filename,"%s",sdbuf);
printf("\nPlease provide path");
scanf("%s",fr_name);
printf("\nclientfilename:%s",fr_name);
char* ext;
ext = strrchr(fr_name,'.');
printf("\nextension:%s",ext);
bzero(sdbuf,1024);
sprintf(sdbuf,"%s",ext);
n=write(sockfd,sdbuf,strlen(sdbuf));
if(n<0)
error("Error writing to socket");
bzero(sdbuf,1024);
bzero(sdbuf,1024);
n=read(sockfd,sdbuf,sizeof(sdbuf));
int c=atoi(sdbuf);
if(c==1)
{
char* filename=fr_name;
printf("\n[Client] Sending %s to the Server... ", filename);
FILE *fs = fopen(filename, "r");
if(fs == NULL)
{
printf("ERROR: File %s not found.\n", filename);
exit(1);
}
bzero(sdbuf, LENGTH);
int fs_block_sz;
while((fs_block_sz = fread(sdbuf, sizeof(char), LENGTH, fs)) > 0)
{
if(send(sockfd, sdbuf, fs_block_sz, 0) < 0)
{
fprintf(stderr, "ERROR: Failed to send file %s. (errno = %d)\n", filename, errno);
break;
}
bzero(sdbuf, LENGTH);
}
printf("Ok File %s from Client was Sent!\n", filename);
}
}
if(a==2)
{
//bzero(sdbuf,1024);
//sprintf(sdbuf,"%ld",a);
//n=write(sockfd,sdbuf,strlen(sdbuf));
printf("\nNothing");
}
if(a==3)
{
}
//}
close (sockfd);
printf("[Client] Connection lost.\n");
return (0);
}
Aucun commentaire:
Enregistrer un commentaire