📄 server.c
字号:
/*
* Embedded Command Line Interface
*
* ./software/ch5/emcli/server.c
*
* mtj@cogitollc.com
*
*/
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <signal.h>
#include <stdio.h>
#include <sys/un.h>
#include <unistd.h>
#include <time.h>
#include "handlers.h"
const char *salutation={"+OK -- Embedded CLI\n"};
const char *ready={"+OK\n"};
const char *notready={"+ERR\n"};
#define MAX_LINE 200
int verbose = 0;
time_t startTime;
time_t lastConnect = 0;
#define EMCLI_PORT 9999
void handleConnection(int fd)
{
int len, done=0, numArgs, status;
char buffer[MAX_LINE+1];
extern int parseCommand( char * );
extern int doHelp( int );
/* Send salutation... */
len = write(fd, salutation, strlen(salutation));
while (!done) {
len = read(fd, buffer, MAX_LINE);
if (len <= 0) return;
buffer[len] = 0;
numArgs = parseCommand(buffer);
if ((buffer[0] == 0) || (buffer[0] == ' ') || (buffer[0] == '#')) {
; // Ignore blank/comment lines
status = 1;
} else if ((!strncmp(buffer, "quit", 4)) ||
(!strncmp(buffer, "exit", 4))) {
status = 0;
done = 1;
} else if (!strncmp(buffer, "help", 4)) {
doHelp( fd );
status = 0;
} else if (!strncmp(buffer, "verbose", 7)) {
if (verbose) verbose = 0;
else verbose = 1;
len = write(fd, (verbose) ? "Verbose=on \n" : "Verbose=off\n", 13);
status = 0;
} else if (!strncmp(buffer, "hexof", 5)) {
status = convdec(fd);
} else if (!strncmp(buffer, "decof", 5)) {
status = convhex(fd);
} else if (!strncmp(buffer, "uptime", 6)) {
time_t curTime = time(NULL);
sprintf(buffer, "%ld\n", curTime-startTime);
len = write(fd, buffer, strlen(buffer));
status = 0;
} else if (!strncmp(buffer, "last", 4)) {
if (lastConnect != (time_t)0) {
sprintf(buffer, "%s", ctime(&lastConnect));
len = write(fd, buffer, strlen(buffer));
} else {
len = write(fd, "none\n", 5);
}
status = 0;
} else if (!strncmp(buffer, "who", 3)) {
status = getpeer(fd);
} else if (!strncmp(buffer, "push", 4)) {
status = push(fd);
} else if (!strncmp(buffer, "pop", 3)) {
status = pop(fd);
} else if ((!strncmp(buffer, "add", 3)) ||
(!strncmp(buffer, "sub", 3)) ||
(!strncmp(buffer, "mul", 3)) ||
(!strncmp(buffer, "div", 3))) {
status = mathop(fd, buffer[0]);
} else {
status = -1;
}
if (status == 0) {
len = write(fd, ready, strlen(ready));
} else if (status == -1) {
len = write(fd, notready, strlen(notready));
}
}
return;
}
int main(int argc, char **argv)
{
int listenfd, connfd, on=1;
socklen_t clilen;
struct sockaddr_in cliaddr, servaddr;
listenfd = socket(AF_INET, SOCK_STREAM, 0);
/* Avoid TIME-WAIT on this socket and allow it to be immediately
* reused.
*/
setsockopt( listenfd, SOL_SOCKET, SO_REUSEADDR, &on, sizeof(on) );
bzero(&servaddr, sizeof(servaddr));
servaddr.sin_family = AF_INET;
servaddr.sin_addr.s_addr = htonl(INADDR_ANY);
servaddr.sin_port = htons(EMCLI_PORT);
bind(listenfd, (struct sockaddr *)&servaddr, sizeof(servaddr));
listen(listenfd, 1);
startTime = time(NULL);
for ( ; ; ) {
clilen = sizeof(cliaddr);
connfd = accept(listenfd, (struct sockaddr *)&cliaddr, &clilen);
if (connfd <= 0) {
break;
}
handleConnection(connfd);
lastConnect = time(NULL);
close(connfd);
}
close(listenfd);
return 0;
}
/*
* Copyright (c) 2002 Charles River Media. All rights reserved.
*
* Redistribution and use in source and binary forms, with or
* without modification, is hereby granted without fee provided
* that the following conditions are met:
*
* 1. Redistributions of source code must retain the above
* copyright notice, this list of conditions and the
* following disclaimer.
* 2. Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the
* following disclaimer in the documentation and/or other
* materials provided with the distribution.
* 3. Neither the name of Charles River Media nor the names of
* its contributors may be used to endorse or promote products
* derived from this software without specific prior
* written permission.
*
* THIS SOFTWARE IS PROVIDED BY CHARLES RIVER MEDIA AND CONTRIBUTERS
* 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS
* FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL CHARLES
* RIVER MEDIA OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARAY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
* BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
* OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
* AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
* ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -