[T106][ZXW-22]7520V3SCV2.01.01.02P42U09_VEC_V0.8_AP_VEC origin source commit
Change-Id: Ic6e05d89ecd62fc34f82b23dcf306c93764aec4b
diff --git a/ap/app/goahead/server/sock.c b/ap/app/goahead/server/sock.c
new file mode 100755
index 0000000..1990f71
--- /dev/null
+++ b/ap/app/goahead/server/sock.c
@@ -0,0 +1,499 @@
+#include <string.h>
+#include <stdlib.h>
+
+#ifdef UEMF
+ #include "uemf.h"
+#else
+ #include <socket.h>
+ #include <types.h>
+ #include <unistd.h>
+ #include "emfInternal.h"
+#endif
+
+static int socketDoOutput(socket_t *sp, char *buf, int toWrite, int *errCode);
+static int tryAlternateSendTo(int sock, char *buf, int toWrite, int i,
+ struct sockaddr *server);
+
+int socketHighestFd = -1;
+
+socket_t **socketList;
+int socketMax;
+
+
+int socketWriteString(int sid, char_t *buf)
+{
+ #ifdef UNICODE
+ char *byteBuf;
+ int r, buf_len;
+
+ buf_len = gstrlen(buf);
+ byteBuf = ballocUniToAsc(buf, buf_len);
+ r = socketWrite(sid, byteBuf, buf_len);
+ bfreeSafe(B_L, byteBuf);
+ return r;
+ #else
+ return socketWrite(sid, buf, strlen(buf));
+ #endif /* UNICODE */
+}
+
+
+int socketWrite(int sid, char *buf, int bufsize)
+{
+ socket_t *sp;
+ ringq_t *rq;
+ int buf_len, bytesWritten, room;
+
+ a_assert(buf);
+ a_assert(bufsize >= 0);
+
+ if ((sp = socketPtr(sid)) == NULL) {
+ return -1;
+ }
+
+ rq = &sp->outBuf;
+ for (bytesWritten = 0; bufsize > 0; ) {
+ if ((room = ringqPutBlkMax(rq)) == 0) {
+ if (socketFlush(sid) < 0) {
+ return -1;
+ }
+ if ((room = ringqPutBlkMax(rq)) == 0) {
+ if (sp->flags & SOCKET_BLOCK) {
+#if (defined (WIN) || defined (CE))
+ int errCode;
+ if (! socketWaitForEvent(sp, FD_WRITE | SOCKET_WRITABLE, &errCode)) {
+ return -1;
+ }
+#endif
+ continue;
+ }
+ break;
+ }
+ continue;
+ }
+ buf_len = min(room, bufsize);
+ ringqPutBlk(rq, (unsigned char *) buf, buf_len);
+ bytesWritten += buf_len;
+ bufsize -= buf_len;
+ buf += buf_len;
+ }
+ return bytesWritten;
+}
+
+
+int socketRead(int sid, char *buf, int bufsize)
+{
+ socket_t *sp;
+ ringq_t *rq;
+ int buf_len, room, errCode, bytesRead;
+
+ a_assert(buf);
+ a_assert(bufsize > 0);
+
+ if ((sp = socketPtr(sid)) == NULL) {
+ return -1;
+ }
+
+ if (sp->flags & SOCKET_EOF) {
+ return 0;
+ }
+
+ rq = &sp->inBuf;
+ for (bytesRead = 0; bufsize > 0; ) {
+ buf_len = min(ringqLen(rq), bufsize);
+ if (buf_len <= 0) {
+
+ if ((sp->flags & SOCKET_BLOCK) &&
+ (bytesRead > 0)) {
+ break;
+ }
+
+ ringqFlush(rq);
+ room = ringqPutBlkMax(rq);
+ buf_len = socketGetInput(sid, (char *) rq->endp, room, &errCode);
+ if (buf_len < 0) {
+ if (errCode == EWOULDBLOCK) {
+ if ((sp->flags & SOCKET_BLOCK) &&
+ (bytesRead == 0)) {
+ continue;
+ }
+// if (bytesRead >= 0) { // kw 3 ; bytesRead>=0 always be true
+ return bytesRead;
+// }
+ }
+ return -1;
+
+ } else if (buf_len == 0) {
+
+ if (bytesRead == 0) {
+ sp->flags |= SOCKET_EOF;
+ }
+ return bytesRead;
+ }
+ ringqPutBlkAdj(rq, buf_len);
+ buf_len = min(buf_len, bufsize);
+ }
+ memcpy(&buf[bytesRead], rq->servp, buf_len);
+ ringqGetBlkAdj(rq, buf_len);
+ bufsize -= buf_len;
+ bytesRead += buf_len;
+ }
+ return bytesRead;
+}
+
+int socketFlush(int sid)
+{
+ socket_t *sp;
+ ringq_t *rq;
+ int rq_len, bytesWritten, errCode;
+ int errEINTRNum = 0; /* myp: ÓÃÓÚ¹æ±Üsocket´íÎó */
+
+ if ((sp = socketPtr(sid)) == NULL) {
+ return -1;
+ }
+ rq = &sp->outBuf;
+
+ if (! (sp->flags & SOCKET_BLOCK)) {
+ sp->flags |= SOCKET_FLUSHING;
+ }
+
+ while (ringqLen(rq) > 0) {
+ rq_len = ringqGetBlkMax(&sp->outBuf);
+ bytesWritten = socketDoOutput(sp, (char*) rq->servp, rq_len, &errCode);
+ if (bytesWritten < 0) {
+ if (errCode == EINTR && errEINTRNum++ < 1000) {
+ continue;
+// } else if (errCode == EWOULDBLOCK || errCode == EAGAIN) { kw 3 // #define EWOULDBLOCK EAGAIN
+ } else if (errCode == EAGAIN) {
+ if (sp->saveMask < 0 ) {
+ sp->saveMask = sp->handlerMask;
+ socketRegisterInterest(sp,
+ sp->handlerMask | SOCKET_WRITABLE);
+ }
+ return 0;
+ }
+ return -1;
+ }
+ ringqGetBlkAdj(rq, bytesWritten);
+ }
+
+ if (ringqLen(rq) == 0) {
+ ringqFlush(rq);
+ }
+
+ if (sp->saveMask >= 0) {
+ socketRegisterInterest(sp, sp->saveMask);
+ sp->saveMask = -1;
+ }
+ sp->flags &= ~SOCKET_FLUSHING;
+ return 0;
+}
+
+int socketGets(int sid, char_t **buf)
+{
+ socket_t *sp;
+ ringq_t *lq;
+ char c = '\0'; //cov
+ int rc, rq_len;
+
+ a_assert(buf);
+ *buf = NULL;
+
+ if ((sp = socketPtr(sid)) == NULL) {
+ return -1;
+ }
+ lq = &sp->lineBuf;
+
+ while (ringqLen(lq) < 1536) {
+
+ if ((rc = socketRead(sid, &c, 1)) < 0) {
+ return rc;
+ }
+
+ if (rc == 0) {
+ if (ringqLen(lq) > 0 && (sp->flags & SOCKET_EOF)) {
+ c = '\n';
+ } else {
+ return -1;
+ }
+ }
+
+ if (c == '\n') {
+ rq_len = ringqLen(lq);
+ if (rq_len > 0) {
+ *buf = ballocAscToUni((char *)lq->servp, rq_len);
+ } else {
+ *buf = NULL;
+ }
+ ringqFlush(lq);
+ return rq_len;
+
+ } else if (c == '\r') {
+ continue;
+ }
+ ringqPutcA(lq, c);
+ }
+ ringqFlush(lq);
+ return -1;
+}
+
+
+int socketInputBuffered(int sid)
+{
+ socket_t *sp;
+
+ if ((sp = socketPtr(sid)) == NULL) {
+ return -1;
+ }
+ if (socketEof(sid)) {
+ return -1;
+ }
+ return ringqLen(&sp->lineBuf) + ringqLen(&sp->inBuf);
+}
+
+int socketEof(int sid)
+{
+ socket_t *sp;
+
+ if ((sp = socketPtr(sid)) == NULL) {
+ return -1;
+ }
+ return sp->flags & SOCKET_EOF;
+}
+
+void socketCreateHandler(int sid, int handlerMask, socketHandler_t handler,
+ int data)
+{
+ socket_t *sp;
+
+ if ((sp = socketPtr(sid)) == NULL) {
+ return;
+ }
+ sp->handler = handler;
+ sp->handler_data = data;
+ socketRegisterInterest(sp, handlerMask);
+}
+
+static int socketDoOutput(socket_t *sp, char *buf, int toWrite, int *errCode)
+{
+ struct sockaddr_in server;
+ int bytes;
+
+ a_assert(sp);
+ a_assert(buf);
+ a_assert(toWrite > 0);
+ a_assert(errCode);
+
+ *errCode = 0;
+
+ if (sp->flags & SOCKET_BROADCAST) {
+ server.sin_family = AF_INET;
+ server.sin_addr.s_addr = INADDR_BROADCAST;
+ server.sin_port = htons((short)(sp->port & 0xFFFF));
+ bytes = sendto(sp->sock, buf, toWrite, 0,(struct sockaddr *) &server, sizeof(server));
+ } else if (sp->flags & SOCKET_DATAGRAM) {
+ server.sin_family = AF_INET;
+ server.sin_addr.s_addr = inet_addr(sp->host);
+ server.sin_port = htons((short)(sp->port & 0xFFFF));
+ bytes = sendto(sp->sock, buf, toWrite, 0,(struct sockaddr *) &server, sizeof(server));
+
+ } else {
+ bytes = send(sp->sock, buf, toWrite, 0);
+ }
+
+ if (bytes < 0) {
+ *errCode = socketGetError();
+ //printf("\n socketDoOutput ERROR: bytes = %d, *errCode = %d! ", bytes, *errCode);
+ return -1;
+
+ } else if (bytes == 0 && bytes != toWrite) {
+ *errCode = EWOULDBLOCK;
+ //printf("\n socketDoOutput ERROR: bytes = %d, *errCode = %d! ", bytes, *errCode);
+ return -1;
+ }
+
+ return bytes;
+}
+
+void socketDeleteHandler(int sid)
+{
+ socket_t *sp;
+
+ if ((sp = socketPtr(sid)) == NULL) {
+ return;
+ }
+ sp->handler = NULL;
+ socketRegisterInterest(sp, 0);
+}
+
+int socketAlloc(char *host, int port, socketAccept_t accept, int flags)
+{
+ socket_t *sp;
+ int sid;
+
+ if ((sid = hAllocEntry((void***) &socketList, &socketMax,
+ sizeof(socket_t))) < 0) {
+ return -1;
+ }
+ sp = socketList[sid];
+
+ sp->sid = sid;
+ sp->accept = accept;
+ sp->port = port;
+ sp->fileHandle = -1;
+ sp->saveMask = -1;
+
+ if (host) {
+ strncpy(sp->host, host, sizeof(sp->host)-1);
+ }
+
+ a_assert((flags & ~(SOCKET_BROADCAST|SOCKET_DATAGRAM|SOCKET_BLOCK|
+ SOCKET_LISTENING)) == 0);
+ sp->flags = flags & (SOCKET_BROADCAST | SOCKET_DATAGRAM | SOCKET_BLOCK|
+ SOCKET_LISTENING);
+
+
+ ringqOpen(&sp->inBuf, SOCKET_BUFSIZ, SOCKET_BUFSIZ);
+ ringqOpen(&sp->outBuf, SOCKET_BUFSIZ + 1, SOCKET_BUFSIZ + 1);
+ ringqOpen(&sp->lineBuf, SOCKET_BUFSIZ, -1);
+
+ return sid;
+}
+
+void socketFree(int sid)
+{
+ socket_t *sp;
+ char_t buf[256];
+ int i;
+ int recv_len = -1;
+
+ if ((sp = socketPtr(sid)) == NULL) {
+ return;
+ }
+
+ socketRegisterInterest(sp, 0);
+ if (sp->sock >= 0) {
+ socketSetBlock(sid, 0);
+ if (shutdown(sp->sock, 1) >= 0) {
+ recv_len = recv(sp->sock, buf, sizeof(buf), 0);
+ if(recv_len < 0){
+ ;
+ }else if(recv_len == 0){
+ // ÕâÀï±íʾ¶Ô¶ËµÄsocketÒÑÕý³£¹Ø±Õ?
+ ;
+ }else if(recv_len == sizeof(buf)){
+ ;
+ }else{
+ ;// ÐèÒªÔٴζÁÈ¡
+ }
+ }
+#if (defined (WIN) || defined (CE))
+ closesocket(sp->sock);
+#else
+ close(sp->sock);
+#endif
+ }
+
+ ringqClose(&sp->inBuf);
+ ringqClose(&sp->outBuf);
+ ringqClose(&sp->lineBuf);
+
+ bfree(B_L, sp);
+ socketMax = hFree((void***) &socketList, sid);
+
+ socketHighestFd = -1;
+ for (i = 0; i < socketMax; i++) {
+ if ((sp = socketList[i]) == NULL) {
+ continue;
+ }
+ socketHighestFd = max(socketHighestFd, sp->sock);
+ }
+}
+
+
+int socketGetError()
+{
+#if (defined (WIN) || defined (CE))
+ switch (WSAGetLastError()) {
+ case WSAEWOULDBLOCK:
+ return EWOULDBLOCK;
+ case WSAECONNRESET:
+ return ECONNRESET;
+ case WSAENETDOWN:
+ return ENETDOWN;
+ case WSAEPROCLIM:
+ return EAGAIN;
+ case WSAEINTR:
+ return EINTR;
+ default:
+ return EINVAL;
+ }
+#else
+ return errno;
+#endif
+}
+
+socket_t *socketPtr(int sid)
+{
+ if (sid < 0 || sid >= socketMax || socketList[sid] == NULL) {
+ a_assert(NULL);
+ errno = EBADF;
+ return NULL;
+ }
+
+ a_assert(socketList[sid]);
+ return socketList[sid];
+}
+
+int socketGetHandle(int sid)
+{
+ socket_t *sp;
+
+ if ((sp = socketPtr(sid)) == NULL) {
+ return -1;
+ }
+ return sp->sock;
+}
+
+int socketGetBlock(int sid)
+{
+ socket_t *sp;
+
+ if ((sp = socketPtr(sid)) == NULL) {
+ a_assert(0);
+ return 0;
+ }
+ return (sp->flags & SOCKET_BLOCK);
+}
+
+int socketGetMode(int sid)
+{
+ socket_t *sp;
+
+ if ((sp = socketPtr(sid)) == NULL) {
+ a_assert(0);
+ return 0;
+ }
+ return sp->flags;
+}
+
+void socketSetMode(int sid, int mode)
+{
+ socket_t *sp;
+
+ if ((sp = socketPtr(sid)) == NULL) {
+ a_assert(0);
+ return;
+ }
+ sp->flags = mode;
+}
+
+int socketGetPort(int sid)
+{
+ socket_t *sp;
+
+ if ((sp = socketPtr(sid)) == NULL) {
+ return -1;
+ }
+ return sp->port;
+}
+