- Added daytime and quote of the day services
[reactos.git] / reactos / apps / utils / net / tcpsvcs / chargen.c
1 #include <stdio.h>
2 #include <winsock2.h>
3 #include <tchar.h>
4 #include "tcpsvcs.h"
5
6 DWORD WINAPI ChargenHandler(VOID* Sock_)
7 {
8 DWORD Retval = 0;
9 SOCKET Sock = (SOCKET)Sock_;
10
11 if (!GenerateChars(Sock)) {
12 _tprintf(_T("Char generation failed\n"));
13 Retval = 3;
14 }
15
16 _tprintf(_T("Shutting connection down...\n"));
17 if (ShutdownConnection(Sock, FALSE)) {
18 _tprintf(_T("Connection is down.\n"));
19 }
20 else
21 {
22 _tprintf(_T("Connection shutdown failed\n"));
23 Retval = 3;
24 }
25 _tprintf(_T("Terminating thread\n"));
26 ExitThread(0);
27
28 return Retval;
29 }
30
31
32 BOOL GenerateChars(SOCKET Sock)
33 {
34 int i,
35 charIndex, /* internal loop */
36 loopIndex; /* line loop */
37 char ring[END-START];
38 char *endring;
39 BOOL bLoop = TRUE;
40
41 /* fill ring with printable characters */
42 for (charIndex=0, i=START; i<=END; charIndex++, i++)
43 ring[charIndex] = i;
44 /* establish the end character in the ring */
45 endring = &ring[charIndex];
46
47 /* where we will start output from */
48 loopIndex = 0;
49
50 while (bLoop)
51 {
52 /* if the loop index is equal to number of chars previously
53 * printed, start the loop from the beginning */
54 if (loopIndex == END-START)
55 loopIndex = 0;
56
57 /* start printing from char controled by loopIndex */
58 charIndex = loopIndex;
59 for (i=0; i<LINESIZ; i++)
60 {
61 /* FIXME: Should send lines instead of chars to improve efficiency
62 * TCP will wait until it fills a packet anway before putting on
63 * the wire, so it's pointless to keep polling send */
64 if (!SendChar(Sock, ring[charIndex]))
65 {
66 return FALSE;
67 }
68 /* if current char equal last char, reset */
69 if (ring[charIndex] == *endring)
70 charIndex = 0;
71 else
72 charIndex++;
73 }
74
75 if (bLoop)
76 if ((!SendChar(Sock, L'\r')) || (!SendChar(Sock, L'\n')))
77 return FALSE;
78
79 /* increment loop index to start printing from next char in ring */
80 loopIndex++;
81 }
82
83 return TRUE;
84 }
85
86 BOOL SendChar(SOCKET Sock, TCHAR c)
87 {
88 INT RetVal;
89 INT SentBytes;
90
91 SentBytes = 0;
92 RetVal = send(Sock, &c, sizeof(TCHAR), 0);
93 /*FIXME: need to establish if peer closes connection,
94 not just report a socket error */
95 if (RetVal > 0)
96 {
97 SentBytes += RetVal;
98 return TRUE;
99 }
100 else if (RetVal == SOCKET_ERROR)
101 {
102 _tprintf(("Socket error\n"));
103 return FALSE;
104 }
105 else
106 _tprintf(("unknown error\n"));
107 //WSAGetLastError()
108
109 _tprintf(("Connection closed by peer.\n"));
110 return TRUE;
111 }