NCTU Network Programming Projects
Projects I’ve worked on in graduate-level course Network Programming in NCTU in Fall 2015.
This course was completed on Jan., 2016. 4 projects in total.
-
NP HW4: SOCKS4 Server & Client
In this network programming homework, we are asked to build SOCKS4 server and client and combine HW3 to demo.
Spec is not included; however, the basic architecture can be illustrated as follows:
There are some notable ideas I came up with:
For SOCKS client (CGI):
- Same as HW3. Just need to send SOCK4 requset and handle SOCK4 reply.
For SOCKS Server:
-
CONNECT
mode procedure:accept → read SOCKS req → check firewall rules → connect to dest host → send SOCKS reply → redirect data
-
BIND
mode procedure:accept → read SOCKS req → check firewall rules → bind socket → listen → send SOCKS reply → accpet from server → send SOCKS reply (to original client) → redirect data
- When redirecting data, should avoid using
strncpy
since it may contain'\0'
in data, which occasionally leads to data error (less bytes are copied than expected).
- Whenbind
with system-assigned port, give0
tosockaddr_in.sin_port
.Demo video:
Source → cyhuang1230/NetworkProgramming
For SOCKS client (CGI):
Please look forNP_project4_Server.cpp
.
To try:make hw4_cgi
, upload to a HTTP server and run<BASE_URL>/hw4.cgi
.For SOCKS server:
Please look forNP_project4_Server.cpp
.
To try:make hw4_server
and run./np_hw4
. - Same as HW3. Just need to send SOCK4 requset and handle SOCK4 reply.
-
NP HW3: Remote Batch System (RBS)
In this network programming homework, we are asked to build a Remote Batch System (RBS). It’s actually a combination of client and server, whose diagram can be drawn as follows:
As required in spec(
hw3Spec.txt
), we have to write three programs:CGI
: a webpage(hw3.cgi
) that displays server’s response dynamically.HTTP Server
: a cpp program that runs as a HTTP server.Winsock
: a combination of 1. and 2. but usingWinsock
.
For more details, please refer to
hw3Spec.txt
in the repository (cyhuang1230/NetworkProgramming
).There are some notable ideas I came up with and described as follows.
For CGI (Part I):
- Write may fail. Write a wrapper class to handle this.
- Parsing query string needs to be handled carefully.
- Since we’re client now, doesn’t matter which port to use, i.e. no need to
bind
anymore! - Try using
flag
(bitwise comparison) instead of individually specifying each property inlog
function. - Output recerived from servers should be handled(e.g.
\n
,<
,>
,&
,'
,"
) since JavaScript has different escape characters than C. Also, the order of processing characters matters. - Most importantly, non-blocking client design.
[1]connect
may be blocked due to slow connection.
=> SetO_NONBLOCK
to sockfd
[2] Client program may block (e.g.sleep
)
=> Don’t wait for response (i.e.read
) afterwrite
to server. Instead, useselect
to check when the response is ready toread
.
For HTTP Server (Part II):
- Use
select
to accept connections. - Fork a child process to handle request.
- Plain text file can be
read
&write
directly. Content type needs to be set properly. - CGI needs to be
exec
ed. =>dup
itsSTDOUT_FILENO
to sockfd.
For Winsock (Part III):
- Same logic as
Berkeley Socket
version. - To read file, use
ReadFile
instead ofReadFileEx
(I encountered pointer error) - Keep track of
doneMachines
. When done (== numberOfMachines
), close socket and print footer. - I like
Berkeley Socket
much more thanWinsock
:(
Demo video:
Source → cyhuang1230/NetworkProgramming
For part I (CGI):
Please look forNP_project3_1.cpp
.
To try:make hw3_1_debug
, upload to a HTTP server and run<BASE_URL>/hw3.cgi
.For part II (HTTP Server):
Please look forNP_project3_2.cpp
.
To try:make hw3_2_debug
and run./np_hw3
.For part III (Winsock):
Please look forNP_project3_3.cpp
. Run with Visual Studio is recommended. -
NP HW2: Remote Working Ground (RWG)
In this network programming homework, we are asked to build a remote working ground (RWG), which is actually a combination of hw1 and chat & public pipe function.
According to the spec(
hw2Spec.txt
), we need to write two programs:- Use the single-process concurrent paradigm.
- Use the concurrent connection-oriented paradigm with shared memory.
For more details, please refer to
hw2Spec.txt
in the repository (cyhuang1230/NetworkProgramming
).There are some notable ideas I came up with and described as follows.
(I will start with version II since I wrote that first :P)For concurrent version:
- Keep track of client’s data (e.g.
sockfd
,pid
…) so that we can send msg to each client. - Store client data & messages in shared memory so let every child can read.
- Create additional
MAX_USER
(# of user) blocks of shm to store direct msg (or broadcst msg). - There’s no way server can be closed properly (must end by
Ctrl+C
), so, in order not to leave any shm unrelaesed, we won’tshmget
until the first client is connected, and free shm when all clients are disconnected.
→ To keep track of the number of children,sa_handler
needs to be implemented separately.
→ Furthermore, MUST resetsa_handler
in the child process so that won’t mistakenly detach shm later whenexec
. - Use signal
SIGUSR1
to notify other process there’s a new msg to write. - Semaphore on public pipes to prevent concurrent issue. (Same create/release idea as shm.)
- Use
FIFO
, a.k.aNamed pipe
, to implement public pipe. [No need to store in shm]. - Implement a generic function to send msg to a specific user.
Function hierarchy:
→sendRawMsgToClient
→tell
→sendRawMsgToClient
→broadcastRawMsg
→yell
/name
/who
For single-process version:
- Basically same structure as ver. II, but as a single-process program, we don’t need any shm or semaphore, which makes it much easier, yayyy!.
- Only involves one huge adjustment.
Consider the following input:
[Client 1] % ls |1 [Client 2] % ls |1 [Client 1] % cat [Client 2] (empty) <- stucked, prompt won't display
This error is caused by the way we decide input.
→ We can no longer expect the whole input withnumbered-pipe
can be got in one while loop.
→ Instead, we have to check input line by line, and keep track of input-related information.Demo video: (client is not included in the repo)
Source → cyhuang1230/NetworkProgramming
For ver. I (Single process):
Please look forNP_project2_Single.cpp
.
To try:make hw2s
and run./np_hw2s
.
*Try with debug message:make hw2_debugs
and run./np_hw2s
.For ver. II (Concurrent):
Please look forNP_project2_Concurrent.cpp
.
To try:make hw2
and run./np_hw2
.
*Try with debug message:make hw2_debug
and run./np_hw2
.*Debug version is complied with
-g
, which may usegdb np_hw2(s)
to debug. - Use the single-process concurrent paradigm.
-
NP HW1: Remote Access System (RAS)
In this network programming homework, we were asked to build a remote access system. It’s kind of like a shell on the server side.
For more details, please refer to
hw1Spec.txt
in the repository (cyhuang1230/NetworkProgramming
).Demo video:
Source → cyhuang1230/NetworkProgramming
Please look for
NP_project1.cpp
.
To try:make hw1
and run./np_hw1
.
Try with debug message:make hw1_debug
and run./np_hw1
.