cannot write binary data in a file using c - c++

I am using vs2010 in an windows vista os the problem is that i want to read and exe file encrypt it and store it but when i write the data back nothing gets inserted i mean the file is created but no errors and the file is empty and i have done it a thousand times and it works on eclipse but not on vs2010 and i need to port it into a gui can anyone please redirect me where i am wrong
FILE *pFile, *file;
size_t result;
pFile = fopen(fName, "r+b");
if (pFile==NULL) {MessageBox(NULL, L"Could not open file", L"Information", MB_ICONERROR); return FALSE;}
fseek(pFile, 0 ,SEEK_END);
sData->fSize = ftell(pFile);
rewind(pFile);
sData->fbuffer = (unsigned char *) malloc(sizeof(char) * sData->fSize);
if (sData->fbuffer == NULL) {MessageBox(NULL, L"Memory error", L"Information", MB_ICONERROR); fclose(pFile); return FALSE;}
file = fopen("out.txt", "w+b");
while ((result = fread(sData->fbuffer, 1, sData->fSize, file)) > 0) {
if (!(fwrite(sData->fbuffer, 1, result, file))) {
MessageBox(NULL, L"Write error", L"Information", MB_ICONERROR);
}
fclose(file);
}
fclose(file);
//result = fread(sData->fbuffer, 1, sData->fSize, pFile);
//if (result != sData->fSize) {MessageBox(NULL, L"Read error", L"Information", MB_ICONERROR); fclose(pFile); return FALSE;}
fclose (pFile);
return TRUE;
EDIT
I am really sorry the problem is with the location of the file it is in unicode format where as fopen accepts ascii and the location only shows C I have to convert it to get the proper result thanks

You would want to use pFile instead of file in fread().
//---------------------------------------------------- pFile not file
while ((result = fread(sData->fbuffer, 1, sData->fSize, pFile)) > 0) {
if (!(fwrite(sData->fbuffer, 1, result, file))) {
MessageBox(NULL, L"Write error", L"Information", MB_ICONERROR);
}
fclose(file);
}

I think the file that you are opening for read is not Ascii, so you assumption of calculation of file size based on size of char is wrong.
if you calculate right size of file in bytes and read and write those many bytes you should be fine.

You are reading and writing to/from the same file.
while ((result = fread(sData->fbuffer, 1, sData->fSize, file)) > 0) {
if (!(fwrite(sData->fbuffer, 1, result, file))) {
Since you just opened this file it reads nothing, so nothing is written as well.
From the man page:
w+ or wb+ or w+b
Truncate to zero length or create file for update.

Related

Windows C++ API: How do I read an entire binary file into a buffer?

OS: Windows 10
Target Platform: x86
I'm trying to load the entire contents of an arbitrary-length binary file into a character array. The contents of this array will later be copied into a memory location reserved with VirtualAlloc. Here is my code so far:
#include <windows.h>
#include <fileapi.h>
#include <tchar.h>
int __cdecl _tmain(int argc, TCHAR* argv[])
{
HANDLE payload;
if (argc != 2) {
_tprintf(TEXT("Usage: runp.exe [payload_file]\nExecutes the specified binary payload.\n"));
return 0;
}
_tprintf(TEXT("[*] Loading binary payload: %s\n"), argv[1]);
payload = CreateFile(argv[1], GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL | FILE_FLAG_OVERLAPPED, NULL);
if (payload == INVALID_HANDLE_VALUE) {
_tprintf(TEXT("[!] Could not open payload: %s\n"), argv[1]);
}
else {
DWORD size = GetFileSize(payload, NULL);
_tprintf(TEXT("[*] Payload found: %d bytes.\n"), size);
// TROUBLE STARTS HERE
LPDWORD bytes_read = 0;
char* buffer = new char[size + 1];
if (FALSE == ReadFile(payload, buffer, size, bytes_read, NULL)) {
_tprintf(TEXT("[!] Could not read payload!\n"));
}
else {
_tprintf(TEXT("[*] Payload read!\n"));
}
delete[] buffer;
// TROUBLE ENDS HERE
}
CloseHandle(payload);
return 0;
}
Here's an example of how it fails:
PS C:\path\to\binary> echo "Demonstration file." > demo.file
PS C:\path\to\binary> .\runp.exe .\demo.file
[*] Loading binary payload: .\demo.file
[*] Payload found: 44 bytes.
[!] Could not read payload!
The program correctly detects and identifies the size of the binary file, yet I am unable to read the contents of the file into my custom-sized buffer.
C++ on Windows is not my native language. Python is more my speed, but I don't have a choice here. Any help would be much appreciated.
With everyone's help, I was able to overcome the issues I was having with my code. I wasn't able to entirely remove all the TCHAR stuff per selbie's suggestion, as the CreateFile function wouldn't accept a character array for the filename, nor compile without using a _tmain format for the main function. (Again, C++ on Windows isn't my native language, so doubtless there's a better way to achieve this.) But I did add the \0 (null byte) to terminate the buffer contents. I also incorporated changes suggested by Retired Ninja and Mark Ransom. Here's the code after these changes were applied:
#include <windows.h>
#include <fileapi.h>
#include <stdio.h>
#include <tchar.h>
int __cdecl _tmain(int argc, TCHAR* argv[])
{
HANDLE payload;
if (argc != 2) {
printf("Usage: runp.exe [payload_file]\nExecutes the specified binary payload.\n");
return 0;
}
printf("[*] Loading binary payload: %ws\n", argv[1]);
payload = CreateFile(argv[1], GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
if (payload == INVALID_HANDLE_VALUE) {
printf("[!] Could not open payload: %ws\n", argv[1]);
}
else {
DWORD size = GetFileSize(payload, NULL);
DWORD bytes_read = 0;
char* buffer = new char[size + 1];
if (FALSE == ReadFile(payload, buffer, size, &bytes_read, NULL)) {
printf("[!] Could not read payload!\n");
}
else {
buffer[bytes_read] = '\0';
printf("[*] %d bytes read.\n[*] File contents:\n\n%s\n", bytes_read, buffer);
}
delete[] buffer;
}
CloseHandle(payload);
return 0;
}
Here is a demonstration of the program in action:
C:\path\to\binary>echo Demonstration! > test.txt
C:\path\to\binary>type test.txt
Demonstration!
C:\path\to\binary>runp.exe test.txt
[*] Loading binary payload: test.txt
[*] 17 bytes read.
[*] File contents:
Demonstration!
Thanks again to everyone for your helpful suggestions!

auxDIBImageLoad returns null

Hi i am doing a project with opengl
What I'm stuck with is that the method 'auxDIBImageLoad' always returns null even if the file exists.
My code is below:
AUX_RGBImageRec *LoadBMPFile(char *filename)
{
FILE *hFile = NULL;
if (!filename) return NULL;
hFile = fopen(filename, "r");
if (hFile)
{
printf("file opened\n");
fclose(hFile);
if (!auxDIBImageLoad(filename)) {
printf("but file is null\n");
}
return auxDIBImageLoad( filename );
}
printf("file open failed\n");
return NULL;
}
Then the log is below:
file opened
but file is null
load bmp failed
I already searched for fixing it so that I already set to Multibyte char set.
But it doesn't work after setting that.
Please help me.

Unable to Read from File while using ReadFIle() function in C++

I am facing some issues while reading data from file using ReadFile() function of C++ (Microsoft specific probably).
Here is my code
Write On File
void ClientA::SharePublicKey()
{
printf("Sharing Public Key\n");
HANDLE hFile = NULL;
hFile = CreateFile(TEXT("D:\\My_Proj\\shared\\PublicKeyB.txt"), // name of the write
GENERIC_WRITE, // open for writing
FILE_SHARE_WRITE, // do not share
NULL, // default security
CREATE_NEW, // create new file only
FILE_ATTRIBUTE_NORMAL, // normal file
NULL); // no attr. template
if (hFile == INVALID_HANDLE_VALUE)
{
//DisplayError(TEXT("CreateFile"));
//_tprintf(TEXT("Terminal failure: Unable to open file \"%s\" for write.\n"), argv[1]);
return;
}
// _tprintf(TEXT("Writing %d bytes to %s.\n"), dwBytesToWrite, argv[1]);
bool bErrorFlag = WriteFile(
hFile, // open file handle
pbPublicKey, // start of data to write
dwPublicKeyLen, // number of bytes to write
&lpNumberOfBytesWritten, // number of bytes that were written
NULL); // no overlapped structure
if (FALSE == bErrorFlag)
{
// DisplayError(TEXT("WriteFile"));
printf("Terminal failure: Unable to write to file.\n");
return;
}
else
{
if (lpNumberOfBytesWritten != dwPublicKeyLen)
{
// This is an error because a synchronous write that results in
// success (WriteFile returns TRUE) should write all data as
// requested. This would not necessarily be the case for
// asynchronous writes.
printf("Error: dwBytesWritten != dwBytesToWrite\n");
}
else
{
// _tprintf(TEXT("Wrote %d bytes to %s successfully.\n"), dwBytesWritten, argv[1]);
}
}
CloseHandle(hFile);
}
Read That File
void ClientA::ReadPublicKeyOfOtherPeer()
{
HANDLE hFile = NULL;
DWORD dwBytesRead = 0;
BYTE* ReadBuffer = NULL;
OVERLAPPED ol = {0};
hFile = CreateFile(TEXT("D:\\My_Proj\\shared\\PublicKeyB.txt"), // file to open
GENERIC_READ, // open for reading
FILE_SHARE_READ, // share for reading
NULL, // default security
OPEN_EXISTING, // existing file only
FILE_ATTRIBUTE_NORMAL | FILE_FLAG_OVERLAPPED, // normal file
NULL // no attr. template
);
if (hFile == INVALID_HANDLE_VALUE)
{
_tprintf(TEXT("CreateFile\n"));
_tprintf(TEXT("Terminal failure: unable to open file \"%s\" for read.\n"));
printf("Error %x\n", GetLastError());
return;
}
if( FALSE == ReadFile(hFile, ReadBuffer, dwPublicKeyLen, &lpNumberOfBytesWritten, &ol) )
{
// DisplayError(TEXT("ReadFile"));
printf("Terminal failure: Unable to read from file.\n GetLastError=%08x\n", GetLastError());
CloseHandle(hFile);
return;
}
if (dwBytesRead > 0 && dwBytesRead <= dwPublicKeyLen-1)
{
ReadBuffer[dwBytesRead]='\0'; // NULL character
//_tprintf(TEXT("Data read from %s (%d bytes): \n"), argv[1], dwBytesRead);
printf("%s\n", ReadBuffer);
}
else if (dwBytesRead == 0)
{
//_tprintf(TEXT("No data read from file %s\n"), argv[1]);
}
else
{
// printf("\n ** Unexpected value for dwBytesRead ** \n");
}
retrievedPublicByteArray = ReadBuffer;
CloseHandle(hFile);
}
By SharePublicKey method I am saving the data in a file. And I have checked that it successfully saves data on the file and the data on the files are seems to be valid.
And by ReadPublicKeyOfOtherPeer method I am reading the file which was previously saved. But reading is not successful In out put I found the following line -
Terminal failure: Unable to read from file.
GetLastError=000003e6
You are passing uninitialized pointer ReadBuffer to ReadFile. You need a buffer that is large enough to receive the results.

WriteFile writing filename to file

I'm getting quite a strange problem.
I'm hooking to the Winsock function on the Xbox 360, send. This function is called a-lot in the application I'm trying to dump the Http Request information from.
First I will show the code and explain my issue:
WritetoFile function.
BOOL WritetoFile(char* filename, char* buffer, DWORD len)
{
// Setup expansion
doMountPath("Hdd:", "\\Device\\Harddisk0\\Partition1");
//print
printf("Creating %s\n", filename);
//create our file
HANDLE fileHandle = CreateFile(filename, GENERIC_WRITE, FILE_SHARE_WRITE, NULL, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, NULL);
//does file exist?
if(fileHandle!=INVALID_HANDLE_VALUE)
{
//print
printf("Writing to file... \n");
//bytes written parameter
DWORD wfbr;
//write to our file
if(WriteFile(fileHandle, (void*)&buffer, len, &wfbr, NULL))
{
printf("File written! (Bytes Written:%u) \n", wfbr);
} else {
printf("Error writing to file: (Error:%u)\n", GetLastError());
}
//close our file handle
CloseHandle(fileHandle);
} else {
printf("Error creating file: (Error:%u)\n", GetLastError());
}
return true;
}
Winsock hook
INT WINSOCK_SEND_HOOK(SOCKET s,const char FAR *buf,int len,int flags)
{
memcpy(SocketData.SendData, buf, len);
if(len>40)
{
WINSOCK_SEND_COUNT +=1;
char Filename[40];
sprintf(Filename, "Hdd:\\Dump\\Send\\Winsock_Send_%d.txt", WINSOCK_SEND_COUNT);
WritetoFile(Filename, SocketData.SendData, len);
} else { printf("Winsock skipped\n"); }
memset(SocketData.SendData, 0, 0x1388);
return send(s, buf, len, flags);
}
The problem is pretty difficult to explain. So the first time I ran my .dll to hook onto this function it worked fine up until tries to create 'Winsock_Send_85.txt'. It prints this:
`Creating b0ZEK0EwSDBwSXR2RW5EdXd5ZXFnN1IrLzFQYno4RmN0ZnI2MnNnWWQwb2JXMGlYbEdQRkxGOXFkdHJabiszb1I2MG1vUFlkSjBJVW0xcFB4UzZxWEtqZEVYSjEvQmJtOHhmMUdVMDlZaHA2SUtWZTJjb0ZVU1RsUTlvYXJhc0NDOHJNUitlUDBaQmVSOTNUWVM1TU1hLzB0NlhGZmQ2dE1CVDRKVTRxdzliRUtlRmVvVGgvaVdoMUFBczBpNzhkcXNlVUYwaTlQT3B5ekdyeU9ZTzU0QWYyVXpUSXZiTDMzRWl4SXhzOUJOZDZxaWtDQUlNQmZkNHRYVTNaS2pKZngxRmd3dXE2QnRIYmkySlgxcE9vUjFyVlRpci9iZHdTZTZEOTJDSXFqNkNqM0lSaDY1N3VKUzhOQ3VxaFZpclhTUnZMZlJCN21mTS9aV2dCRUJNWHBVeUdZcGxqOVNGUÿÿexception code=0xc0000005 thread=0xf9000044 address=0x910d0a00 read=0x910d0a00 firstxbWatson: Xbox is restarting`
And crashes. After restarting the console I then run it again and it works fine and doesnt crash but it's now writing the incorrect data to the files which is all the same repetitive data even though the buffer points to different data. This is what it writes to file:
‘ÀÛ( W
ÿÿÿÿÿÿÿÿ ÿÿÿÿ‘Á Hdd:\Dump\Send\Winsock_Send_87.txt  ‚i夀…Ü H>
I then discovered a way to stop this from happening which was to unplug the console entirely from all power but then it goes back to the first issue.
Please ignore what you may think be un-necessary uses of memcpy.
The problem was solved pretty quickly (embarrassing) and I cant believe I was struggling with this for 1 hour, silly mistake.
I wasn't checking the size of the buffer therefore I wasn't allocating enough memory.

WinINet trouble downloading file to client?

I'm curious why I'm having trouble with this function. I'm downloading a PNG file on the web to a destination path. For example, downloading the Google image to the C: drive:
netDownloadData("http://www.google.com/intl/en_ALL/images/srpr/logo1w.png", "c:\file.png");
The file size is correct after downloading. Nothing returning false. When I try opening it it won't show the image. Any ideas are helpful. Thanks!
Here's the code:
bool netDownloadData(const char *strSourceUrl, const char *strDestPath)
{
HINTERNET hINet = NULL;
HINTERNET hFile = NULL;
char buffer[1024];
DWORD dwRead;
String sTemp;
FILE *fp = NULL;
DWORD size = 0;
// Open a new internet session
hINet = netInit();
if (hINet == NULL) {
sprintf(buffer, "Initializing WinINet failed.", strSourceUrl);
utilLog(buffer);
netCloseHandle(hINet);
return false;
}
// Open the requested url.
hFile = netOpenUrl(hINet, strSourceUrl);
if (hFile == NULL) {
sprintf(buffer, "URL failed upon loading: %s\n", strSourceUrl);
utilLog(buffer);
netCloseHandle(hINet);
return false;
}
// Read file.
while (InternetReadFile(hFile, buffer, 1023, &dwRead))
{
if (dwRead == 0)
break;
buffer[dwRead] = 0;
sTemp += buffer;
size += dwRead;
}
// Load information to file.
fp = fopen(strDestPath, "wb");
if (fp == NULL)
return false;
fwrite(sTemp, size, 1, fp);
fclose(fp);
InternetCloseHandle(hFile);
InternetCloseHandle(hINet);
return true;
}
What data type is String? Avoid storing binary data in strings because NULLs in the data can potentially cause problems. Just write the buffer as and when you read it:
// Load information to file.
fp = fopen(strDestPath, "wb");
if (fp == NULL)
return false;
// Read file.
while (InternetReadFile(hFile, buffer, 1024, &dwRead))
{
if (dwRead == 0)
break;
fwrite(buffer, dwRead, 1, fp);
}
fclose(fp);
It looks like your second and third args to fwrite are transposed. See fwrite docs for explanation.
try:
fwrite(sTemp, 1, size, fp);