What really is the SOCKET type? - c++

I can see it looks like an alias for an unsigned int pointer, right? Is it just like a pointer in memory? To what would it be actually pointing? Is it pointing to a struct? If yes, how is that struct defined? Is it just a number that is used by socket functions and does not map to a memory address?

In Win32, a SOCKET data type is the same as a HANDLE, which is an integer used to refer to a kernel data structure of some kind. This kernel data structure is "opaque", which means that application programs do not need to (and in fact cannot) see the internals of the structure. All access to Win32 SOCKETs is done through Winsock API functions.
Note that in Win16, a SOCKET was not the same thing because there was no Win16 HANDLE type. However, Win32 kept the same type name for source compatibility.

from wikipedia-
Generally, a file descriptor is an
index for an entry in a
kernel-resident data structure
containing the details of all open
files. In POSIX this data structure is
called a file descriptor table, and
each process has its own file
descriptor table. The user application
passes the abstract key to the kernel
through a system call, and the kernel
will access the file on behalf of the
application, based on the key. The
application itself cannot read or
write the file descriptor table
directly.
link

You could check out the Linux source for socket.h, for instance. Although in the case of sockets (the type of which is not actually described in socket.h), a socket is a file descriptor, not unlike the return of open in C (which you don't use in day-to-day programming).
As to what is a file descriptor: at a very high level, it's typically just an int that the OS translates into a way to communicate with a file object, or a socket object for network communications, or a pipe to communicate between processes...

Related

How to encapsulate C/C++ socket send and receive functions in a class?

I'm using the standard C/C++ socket function, but I'd like to encapsulate them into a C++ class. The problem is that the functions for sending and receive returns (or require) pointers to void. Is there any way to use an object that encapsulates those values?
For example, in Java the Socket class uses both ObjectOutputStream and ObjectInputStream in order to work with Object type so every object can be sent via Sockets.
I know that in Java the approach is quite different because the pointers are hidden to the programmer, but is there any similar solution in C++?
socket isn't a c++ function. It's a system level function and it doesn't know anything about objects (or indeed anything in c++), so you have to arrange to provide it with a pointer to the data you want transferred.
As #GCT says, socket isn't a function but is a system level function which is used to handle network connections. In C/C++ each socket is identified with an Integer value, so it's not easy, as you want, to handle it as an object.
I recommend you to read this tutorial to know more about socket.
Maybe it can help you: I have a project that show how to use sockets in C++. Server and client are contained in their own class. You can get it by this link.

Copy-on-write file mapping on windows

I have 3 processes communicating over named pipes: server, writer, reader. The basic idea is that the writer can store huge (~GB) binary blobs on the server, and the reader(s) can retrieve it. But instead of sending data on the named pipe, memory mapping is used.
The server creates an unnamed file-backed mapping with CreateFileMapping with PAGE_READWRITE protection, then duplicates the handle into the writer. After the writer has done its job, the handle is duplicated into any number of interested readers.
The writer maps the handle with MapViewOfFile in FILE_MAP_WRITE mode.
The reader maps the handle with MapViewOfFile in FILE_MAP_READ|FILE_MAP_COPY mode.
On the reader I want copy-on-write semantics, so as long the mapping is only read it is shared between all reader instances. But if a reader wants to write into it (eg. in-place parsing or image processing), the impacts should be limited to the modifying process with the least number of copied pages possible.
The problem
When the reader tries to write into the mapping it dies with segmentation fault as if FILE_MAP_COPY was not considered.
What's wrong with the above described method? According to MSDN this should work...
We have the same mechanism implemented on linux as well (with mmap and fd passing in AF_UNIX ancillary buffers) and it works as expected.
problem here that MapViewOfFile bad designed or/and documented. this is shell (with restricted functionality) over ZwMapViewOfSection. the dwDesiredAccess parameter of MapViewOfFile converted to Win32Protect parameter of ZwMapViewOfSection.
the FILE_MAP_READ|FILE_MAP_COPY combination converted to PAGE_READONLY page protection, because this you and get page fault on write.
you need use FILE_MAP_COPY only flag - it converted to PAGE_WRITECOPY page protection and in this case all will be work.
the best solution of course direct use ZwMapViewOfSection with PAGE_WRITECOPY page protection
TL:DR: RbMm is correct, you must pass just FILE_MAP_COPY to MapViewOfFile to get copy-on-write behavior.
The current Microsoft documentation is incorrect, it incorrectly states that FILE_MAP_COPY can be OR'ed with FILE_MAP_<ALL_ACCESS|READ|WRITE>.
Looking at older versions of MSDN it correctly says that you must choose one of the access modes:
Type of access to the file view and, therefore, the protection of the pages mapped by the file. This parameter can be one of the following values.
FILE_MAP_WRITE
FILE_MAP_READ
FILE_MAP_ALL_ACCESS
FILE_MAP_COPY
No longer relevant but still surprising, on Windows 95/98/ME the copy-on-write behavior only applies to the file, writes are propagated to views in other processes!

Can I use a Node TCP socket in a C++ extension?

I have a C++ Node.js extension that does network communication. Currently, it creates its own TCP connections in C. I would like to have it use sockets created in Node to take advantage of standard libraries like Cluster and to be able to use the existing event loop.
The solution I see is to simply create a net.Socket object and then extract the uv_tcp_t value from the underlying TCPWrap object. There are a couple of issues I see with this option:
The Socket documentation seems to indicate that a socket immediately starts reading when it connects. I would expect that to cause data loss if I want to read on the underlying UV socket in the extension instead of listening for the 'data' event in JavaScript.
While the TCPWrap class has a function to get the underlying uv_tcp_t struct, it does not seem to have an API to relinquish ownership of that struct. I expect this to cause problems later related to disposing of the struct and ownership of its data member (used for user data).
Is there any way to avoid these issues and use the socket in the extension?

SSL_* vs BIO_* functions

I am new to openSSL and want to know about the difference in using SSL_* and BIO_* functions for reading and writing data. Also it would be great if we could have some examples telling the usecases for both.
Thanks
Ravi
SSL_* functions operate on an SSL connection. BIO_* functions stand for basic input and output which are used for reading and writing operations over different input/output devices such as file, memory buffer or even socket connection.
SSL_* function performs the required encryption/decryption of the data whereas BIO_* does not.
There are plenty of use cases for both.
For SSL_* whenever you want to make an SSL client or server, you need this.
For reading and writing from the file or memory buffer, you may need BIO_* function. Common use is some i2d_ or d2i_ functions which writes or reads to/from an input/output device. For example, you want to write your public key to a BIO_* which can be memory buffer or a file, you can open the input into BIO * structure. Your writing code will not make any distinction about file or buffer and will write over BIO *

C++: DLL with memory mapped file

I have an DLL that might get called by multiple applications at the same time.
This DLL memory-maps a file.
I have 2 questions:
1) Each application will create its own instance of the DLL, right?
And thus, the file will be memory-mapped multiple times
2) If this is true, I don't understand what is happening here:
a) Application A calls the DLL.
b) Application B calls the DLL.
c) I quit application A, and the DLL will unmap the file.
d) Application B calls the DLL, and the memory-mapped file is not available anymore, and the call fails.
I don't understand this.
Does anybody do?
Thank you.
This happens because your assumption from 1) is false. A dll is by definition shared; both applications are using the same dll instance, so when you release the file in one application, it won't be available to the others.
To get around your issue, you should implement some reference counting mechanism in order to unmap the file only when no process is using it.
Edit: #sumeet is right. Each process has its own address space; when two processes load the same dll, they might share its read-only data for increased efficiency, but their writable data is local to each process. Nevertheless, a memory-mapped file is a kernel object, like semaphores, pipes and shared memory. Thus, if you unmap it in a process, you unmap it for all.
Edit2: From MSDN (Remarks section):
Multiple processes can share a view of the same file by either using a
single shared file mapping object or creating separate file mapping
objects backed by the same file. A single file mapping object can be
shared by multiple processes through inheriting the handle at process
creation, duplicating the handle, or opening the file mapping object
by name. For more information, see the CreateProcess, DuplicateHandle
and OpenFileMapping functions.
[...]
Mapped views of a file mapping object maintain internal references to
the object, and a file mapping object does not close until all
references to it are released. Therefore, to fully close a file
mapping object, an application must unmap all mapped views of the file
mapping object by calling UnmapViewOfFile and close the file mapping
object handle by calling CloseHandle. These functions can be called in
any order.
First of all, from the first paragraph, how is each app initializing the view?
From the second paragraph, I gather that calling UnmapViewofFile and CloseHandle from each app will release all references to the memory file, and then Windows will automatically release the associated resources (i.e. he keeps the reference count, you don't need to do it).
Post your memory mapping initialization and shutdown code for both apps.