Creating a file of arbitrary size using Windows C++ API
-
13-10-2019 - |
Question
I would like to create a file of arbitrary size using the Windows C/C++ API. I am using Windows XP service pack 2 with a 32 bit virtual address memory space. I am familiar with CreateFile.
However CreateFile does not have a size arument, The reason I want to pass in a size argument is to allow me to create memory mapping files which allow the user to access data structures of predetermined size. Could you please advise of the proper Windows C/C++ API function which allow me to create a file of arbritrary predetermined size? Thank you
Solution
To do this on UNIX, seek to (RequiredFileSize - 1) and then write a byte. The value of the byte can be anything, but zero is the obvious choice.
OTHER TIPS
You CreateFile
as usual, SetFilePointerEx
to the desired size and then call SetEndOfFile
.
You don't need a file, you can use the pagefile as the backing for your memory mapped file, from the MSDN CreateFileMapping
function page:
If hFile is INVALID_HANDLE_VALUE, the calling process must also specify a size for the file mapping object in the dwMaximumSizeHigh and dwMaximumSizeLow parameters. In this scenario, CreateFileMapping creates a file mapping object of a specified size that is backed by the system paging file instead of by a file in the file system.
You can still share the mapping object by use of DuplicateHandle
.
according to your comments, you actually need cross-platform solution, so check Boost Interprocess library. it provides cross-platform shared memory facilities and more
to do this on Linux, you can do the following:
/**
* Clear the umask permissions so we
* have full control of the file creation (see man umask on Linux)
*/
mode_t origMask = umask(0);
int fd = open("/tmp/file_name",
O_RDWR, 00666);
umask(origMask);
if (fd < 0)
{
perror("open fd failed");
return;
}
if (ftruncate(fd, size) == 0)
{
int result = lseek(data->shmmStatsDataFd, size - 1, SEEK_SET);
if (result == -1)
{
perror("lseek fd failed");
close(fd);
return ;
}
/* Something needs to be written at the end of the file to
* have the file actually have the new size.
* Just writing an empty string at the current file position will do.
*newDataSize
* Note:
* - The current position in the file is at the end of the stretched
* file due to the call to lseek().
* - An empty string is actually a single '\0' character, so a zero-byte
* will be written at the last byte of the file.
*/
result = data->write(fd, "", 1);
if (result != 1)
{
perror("write fd failed");
close(fd);
return;
}
}