1 /***************************************************************************
2 * Copyright (C) 2007 by Prabakaran Thirumalai *
3 * praba_tuty@yahoo.com *
5 * This program is free software; you can redistribute it and/or modify *
6 * it under the terms of the GNU General Public License as published by *
7 * the Free Software Foundation; either version 2 of the License, or *
8 * (at your option) any later version. *
10 * This program is distributed in the hope that it will be useful, *
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13 * GNU General Public License for more details. *
15 * You should have received a copy of the GNU General Public License *
16 * along with this program; if not, write to the *
17 * Free Software Foundation, Inc., *
18 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19 ***************************************************************************/
22 #include <SqlNetworkHandler.h>
24 DbRetVal
TCPServer::start()
29 printError(ErrBadArg
, "Set the port first before starting\n");
32 struct sockaddr_in my_addr
;
33 if ((sockfd
= socket(AF_INET
, SOCK_STREAM
, 0)) == -1) {
34 printError(ErrOS
, "Unable to create socket\n");
37 my_addr
.sin_family
= AF_INET
;
38 my_addr
.sin_port
= htons(port
);
39 my_addr
.sin_addr
.s_addr
= INADDR_ANY
;
40 memset(&(my_addr
.sin_zero
), '\0', 8);
41 if (bind(sockfd
, (struct sockaddr
*)&my_addr
,
42 sizeof(struct sockaddr
)) == -1) {
43 printError(ErrOS
, "bind failed");
46 if (listen(sockfd
, 10) == -1) {
47 printError(ErrOS
, "listen failed");
53 DbRetVal
TCPServer::stop()
59 DbRetVal
TCPServer::handleClient()
61 // printf("PRABA::handling client \n");
63 socklen_t addressLen
= sizeof(struct sockaddr
);
64 clientfd
= accept(sockfd
, (struct sockaddr
*) &clientAddress
, &addressLen
);
68 os::signal(SIGCHLD
, SIG_IGN
);
74 int ret
= os::send(clientfd
, &response
, 4, 0);
77 printError(ErrOS
, "Unable to communicate to peer\n");
80 // printf("sent connect ack packet to client\n");
82 struct timeval timeout
;
83 SqlNetworkHandler handler
;
87 FD_SET(clientfd
, &fdset
);
90 int ret
= os::select(clientfd
+1, &fdset
, 0, 0, &timeout
);
92 // printf("something in fd\n");
93 int numbytes
= os::recv(clientfd
,&header
,sizeof(PacketHeader
),0);
96 printError(ErrOS
, "Error reading from socket\n");
99 // printf("HEADER says packet type is %d\n", header.packetType);
101 if (header
.packetType
!= SQL_NW_PKT_DISCONNECT
&&
102 header
.packetType
!= SQL_NW_PKT_COMMIT
&&
103 header
.packetType
!= SQL_NW_PKT_ROLLBACK
&&
104 header
.packetType
!= SQL_NW_PKT_SHOWTABLES
)
106 buffer
= (char*) malloc(header
.packetLength
);
107 numbytes
= os::recv(clientfd
,buffer
,header
.packetLength
,0);
110 printError(ErrOS
, "Error reading from socket\n");
114 ResponsePacket
*rpkt
= (ResponsePacket
*) handler
.process(header
, buffer
);
115 numbytes
= os::send(clientfd
, rpkt
, sizeof(ResponsePacket
), 0);
118 printError(ErrOS
, "Error writing to socket\n");
121 char *ptr
= (char *)&rpkt
->retVal
;
122 if (*ptr
==0) continue;
123 if (*(ptr
+ 1) == 1) continue; // for end of fetch
124 NetworkStmt
*stmt
=NULL
;
125 int params
= *(ptr
+ 2);
126 int proj
= *(ptr
+ 3);
127 if ((header
.packetType
== SQL_NW_PKT_PREPARE
&& params
!= 0) ||
128 (header
.packetType
== SQL_NW_PKT_PREPARE
&& proj
!= 0)) {
130 SqlPacketParamMetadata
*prmpkt
= new SqlPacketParamMetadata();
131 prmpkt
->stmtID
= rpkt
->stmtID
;
132 ListIterator stmtIter
= SqlNetworkHandler::stmtList
.getIterator();
133 while (stmtIter
.hasElement()) {
134 stmt
= (NetworkStmt
*) stmtIter
.nextElement();
135 if (stmt
->stmtID
== prmpkt
->stmtID
) break;
137 prmpkt
->noParams
= stmt
->paramList
.size();
138 rv
= prmpkt
->marshall();
140 printf("marshall failed\n");
142 rv
= send(SQL_NW_PKT_PARAM_METADATA
, prmpkt
->getMarshalledBuffer(), prmpkt
->getBufferSize());
144 printf("Error in sending the metadata to the client\n");
149 //fill projection list and send it to client
150 SqlPacketProjMetadata
*prjpkt
= new SqlPacketProjMetadata();
151 prjpkt
->stmtID
= rpkt
->stmtID
;
152 ListIterator stmtIter
= SqlNetworkHandler::stmtList
.getIterator();
153 while (stmtIter
.hasElement()) {
154 stmt
= (NetworkStmt
*) stmtIter
.nextElement();
155 if (stmt
->stmtID
== prjpkt
->stmtID
) break;
157 prjpkt
->noProjs
= stmt
->projList
.size();
158 rv
= prjpkt
->marshall();
160 printf("marshall failed\n");
162 rv
= send(SQL_NW_PKT_PROJ_METADATA
, prjpkt
->getMarshalledBuffer(), prjpkt
->getBufferSize());
164 printf("Error in sending the metadata to the client\n");
169 if (header
.packetType
== SQL_NW_PKT_FETCH
) {
170 SqlPacketResultSet
*rspkt
= new SqlPacketResultSet();
171 rspkt
->stmtID
= rpkt
->stmtID
;
172 ListIterator stmtIter
= SqlNetworkHandler::stmtList
.getIterator();
173 while (stmtIter
.hasElement()) {
174 stmt
= (NetworkStmt
*) stmtIter
.nextElement();
175 if (stmt
->stmtID
== rspkt
->stmtID
) break;
177 rspkt
->noProjs
= stmt
->projList
.size();
178 rspkt
->setProjList(stmt
->projList
);
180 if (rv
!= OK
) { printf("marshall failed\n"); }
181 rv
= send(SQL_NW_PKT_RESULT_SET
, rspkt
->getMarshalledBuffer(), rspkt
->getBufferSize());
183 printf("Error in sending the metadata to the client\n");
187 if (header
.packetType
== SQL_NW_PKT_SHOWTABLES
) {
188 SqlPacketShowTables
*shTblPkt
= new SqlPacketShowTables();
189 shTblPkt
->stmtID
= rpkt
->stmtID
;
190 shTblPkt
->numOfTables
= rpkt
->rows
;
191 ListIterator stmtIter
= SqlNetworkHandler::stmtList
.getIterator();
192 while (stmtIter
.hasElement()) {
193 stmt
= (NetworkStmt
*) stmtIter
.nextElement();
194 if (stmt
->stmtID
== shTblPkt
->stmtID
) break;
196 rv
= shTblPkt
->marshall();
197 if (rv
!= OK
) { printf("marshall failed\n"); }
198 rv
= send(SQL_NW_PKT_SHOWTABLES
, shTblPkt
->getMarshalledBuffer(), shTblPkt
->getBufferSize());
200 printf("Error in sending the metadata to the client\n");
204 if (header
.packetType
== SQL_NW_PKT_DISCONNECT
) {
207 } //else printf("Nothing in fd %d\n", ret);
210 printError(ErrOS
, "Unable to fork new process");
216 DbRetVal
TCPServer::send(NetworkPacketType type
, char *buf
, int len
)
219 void* totalBuffer
= malloc(sizeof(PacketHeader
)+ len
);
220 PacketHeader
*hdr
= new PacketHeader();
221 hdr
->packetType
= type
;
222 hdr
->packetLength
= len
;
223 hdr
->srcNetworkID
= 0;//networkid;
225 memcpy(((char*)totalBuffer
) + sizeof(PacketHeader
) , buf
, len
);
227 if ((numbytes
=os::send(clientfd
, hdr
, sizeof(PacketHeader
), 0)) == -1) {
228 printError(ErrOS
, "Unable to send the packet\n");
231 // printf("Sent bytes %d\n", numbytes);
232 if ((numbytes
=os::send(clientfd
, buf
, len
, 0)) == -1) {
233 printError(ErrOS
, "Unable to send the packet\n");
236 // printf("Sent bytes %d\n", numbytes);