|
Shay Harel wrote: I have done many multithreading in my life, don't loose sleep over it.
Ok, good luck
led mike
|
|
|
|
|
The problem is you're using CAsyncSocket, which by default needs the message pump
working to dispatch asynchronous socket notifications.
I would recommend (for your prototype which doesn't use multiple threads)) using sockets
directly and using WSAEventSelect() so you can get notifications through an event instead
of a window message.
Either that, or you have to modify the way you wait.
Mark
Mark Salsbery
Microsoft MVP - Visual C++
|
|
|
|
|
"The problem is you're using CAsyncSocket, which by default needs the message pump
working to dispatch asynchronous socket notifications."
This is exactly the root cause of the problem I guess. I did not know the Async socket rely on the message pump, I was sure it's a thread of it's own.
Looks like I'll have some threads going...
Thanks !
|
|
|
|
|
Shay Harel wrote: I did not know the Async socket rely on the message pump
It does by default. You can, however, override everything you need to make it use events
instead of window messages. You don't get the virtual OnConnect(), OnReceive(), etc calls,
however, since you'd have to provide your own thread. At some point it ends up being easier to use
Winsock APIs directly IMO
Mark
Mark Salsbery
Microsoft MVP - Visual C++
|
|
|
|
|
Hi, it looks like you want to turn an asynchronous process into a synchronous process. I wonder why you decided to use CAsyncSocket in the beginning but I could suggest two designs:
If you can influence the API then I would change it, instead of calling blocking the API call could accept a window message (or another type of notification) and when the request has completed it will signal that the data is available.
If you can't change the API or it would be too costly then there is my sugestion number two which is to wrap this mechanism internally into a worker thread... or simply to implement it with blocking sockets.
Since you mentioned your application is a GUI and I assume it is event driven, perhaps the first alternative is the best.
Hope it helps!
Moak
|
|
|
|
|
As Mark said, blocking the message pump seems to be problem. Try using MsgWaitForMultipleObjects instead of WaitForMultipleObjects .
|
|
|
|
|
Hi,
Does anyone have any c++ code that will convert a web page into an image file, even if all of the page is not displayed on the screen.
|
|
|
|
|
|
Hi,
I have been trying to read a file in a program from a USB flash drive. I know that windows allows me to use the device as a drive and I can read the file like reading from any other drive. But the problem is the flash drive will be connected to different PC and the drive name could change. So I cannot use the drive name.
I am using SetupDI API to get the interface and I am also able to get the handle using CreateFile(). But I do not know how to read a particular file.
Can anyone help me here? Also is there any tutorial that will help me to work with USB drives in WinXP environment?
|
|
|
|
|
koumodaki wrote: But I do not know how to read a particular file.
Do you know the file's name?
"Normal is getting dressed in clothes that you buy for work and driving through traffic in a car that you are still paying for, in order to get to the job you need to pay for the clothes and the car and the house you leave vacant all day so you can afford to live in it." - Ellen Goodman
"To have a respect for ourselves guides our morals; to have deference for others governs our manners." - Laurence Sterne
|
|
|
|
|
Yes I do know the file's name.
|
|
|
|
|
So then can't you call ReadFile() ?
"Normal is getting dressed in clothes that you buy for work and driving through traffic in a car that you are still paying for, in order to get to the job you need to pay for the clothes and the car and the house you leave vacant all day so you can afford to live in it." - Ellen Goodman
"To have a respect for ourselves guides our morals; to have deference for others governs our manners." - Laurence Sterne
|
|
|
|
|
I have a file context.cfg which needs to be read form the flash drive. How do I specify in the ReadFile() parameters that I need to read this particular file. From what I know, I can pass the handle I obtain while opening the usb flash drive from CreateFile() to this function. How do I get hold of the file inside the flash drive
|
|
|
|
|
What does your call to CreateFile() look like?
"Normal is getting dressed in clothes that you buy for work and driving through traffic in a car that you are still paying for, in order to get to the job you need to pay for the clothes and the car and the house you leave vacant all day so you can afford to live in it." - Ellen Goodman
"To have a respect for ourselves guides our morals; to have deference for others governs our manners." - Laurence Sterne
|
|
|
|
|
I enumarate the USB device first and get the interface using SetupDiGetDeviceInterfaceDetail(). The name is stored in a vector Devices. Then I use the following call:
HANDLE hUsbDevice = CreateFile(Devices[0].c_str(), GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, 0, NULL);
|
|
|
|
|
So what happens if you use:
string str = Devices[0] + "\\context.cfg";
HANDLE hUsbDevice = CreateFile(str.c_str(), GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, 0, NULL);
"Normal is getting dressed in clothes that you buy for work and driving through traffic in a car that you are still paying for, in order to get to the job you need to pay for the clothes and the car and the house you leave vacant all day so you can afford to live in it." - Ellen Goodman
"To have a respect for ourselves guides our morals; to have deference for others governs our manners." - Laurence Sterne
|
|
|
|
|
Havent tried that. Will check it out
|
|
|
|
|
I tried the method you suggested. I did not work. The code snippet is
std::string path = Devices[0] + "\\context.cfg";
HANDLE hUsbDevice = CreateFile(Devices[0].c_str(), GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, 0, NULL);
if (hUsbDevice == INVALID_HANDLE_VALUE)
return 1;
char data[MAX_PATH];
DWORD nNumberOfBytesToRead = MAX_PATH;
DWORD lpNumberOfBytesRead = 0;
if(!ReadFile(hUsbDevice,(void*)data, nNumberOfBytesToRead, &lpNumberOfBytesRead,NULL))
{
int err = GetLastError();
return 0;
}
GetLastError() returns ERROR_INVALID_PARAMETER
|
|
|
|
|
koumodaki wrote: I tried the method you suggested.
But the code snippet you posted does not reflect such. You are not using path .
I like Judy's suggestion better.
"Normal is getting dressed in clothes that you buy for work and driving through traffic in a car that you are still paying for, in order to get to the job you need to pay for the clothes and the car and the house you leave vacant all day so you can afford to live in it." - Ellen Goodman
"To have a respect for ourselves guides our morals; to have deference for others governs our manners." - Laurence Sterne
|
|
|
|
|
I used the path but made a mistake while copying the code here. Ok so maybe I will try using WMI.
Do you have any tutorial which explains how to use Windows API in such situatuons?
|
|
|
|
|
koumodaki wrote: I can pass the handle I obtain while opening the usb flash drive from CreateFile() to this function.
The problem is that this handle is a handle to the physical drive. You can't use that to easily find a file on the drive.
Your basic problem is how to convert from a USB identifier to the logical hard drive letter. Using WMI you can go from something like USBSTOR\\DISK&VEN_SANDISK&PROD_CRUZER_MINI&REV_0.1\\20041100801E102869&0 (to take an example not at random) to G:. Stick the USB flash in your system, fire up the WMI object browser and you can see the queries you need to make to WMI to go from the former to the latter.
Judy
|
|
|
|
|
Thanks Judy. I will try this
|
|
|
|
|
JudyL_FL wrote: ...fire up the WMI object browser and you can see the queries you need to make to WMI to go from the former to the latter.
Interesting tool. I inserted a PNY Attache drive and tried it.
I found "E:" under the Win32_LogicalDisk node, and "USB\VID_154B&PID_0005\6E68190046F6" under the Win32_USBHub node. I then found "USBSTOR\DISK&VEN_PNY&PROD_USB_2.0_FD&REV_PMAP\6E68190046F6&0" under the Win32_DiskDrive node.
Where are these queries to which you refer?
"Normal is getting dressed in clothes that you buy for work and driving through traffic in a car that you are still paying for, in order to get to the job you need to pay for the clothes and the car and the house you leave vacant all day so you can afford to live in it." - Ellen Goodman
"To have a respect for ourselves guides our morals; to have deference for others governs our manners." - Laurence Sterne
|
|
|
|
|
If you follow Win32_SystemDevices to Win32_PnPEntity, you should find a leaf with a device id something like USBSTOR.....
From there, you can get (look under Win32_PnPDevice) the correct DeviceId to use for Win32_DiskDrive.
From there, you can get (look under Win32_DiskDriveToDiskPartition) the correct DeviceId to use for Win32_DiskPartition.
From there, you can get (look under Win32_LogicalDiskToPartition) the correct DeviceId to use for Win32_LogicalDisk.
That final device id is the logical drive number.
(Whew!! <wiping brow="">)
Getting that first USBSTOR... monster string is what's usually the hardest part of this sort of thing since you have to use the SetupDi API. That is truly nasty!!
Judy
|
|
|
|
|
Wow! I need an elevator to come back to the surface from drilling down that deep. It works, though.
"Normal is getting dressed in clothes that you buy for work and driving through traffic in a car that you are still paying for, in order to get to the job you need to pay for the clothes and the car and the house you leave vacant all day so you can afford to live in it." - Ellen Goodman
"To have a respect for ourselves guides our morals; to have deference for others governs our manners." - Laurence Sterne
|
|
|
|